{"id":15330266,"url":"https://github.com/wolfstudy/tx_unsignature","last_synced_at":"2025-06-11T09:35:01.575Z","repository":{"id":73616461,"uuid":"116116141","full_name":"wolfstudy/tx_unsignature","owner":"wolfstudy","description":"the project will analyze the not signature transaction","archived":false,"fork":false,"pushed_at":"2018-01-06T07:59:54.000Z","size":14,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-03-13T03:29:18.097Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/wolfstudy.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2018-01-03T09:08:06.000Z","updated_at":"2018-01-04T01:29:41.000Z","dependencies_parsed_at":null,"dependency_job_id":"d4d9dfaa-7334-460e-b434-3bba370eaae3","html_url":"https://github.com/wolfstudy/tx_unsignature","commit_stats":{"total_commits":9,"total_committers":1,"mean_commits":9.0,"dds":0.0,"last_synced_commit":"46b5f89664d35b219bf2888a247387e1de7e39e5"},"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/wolfstudy%2Ftx_unsignature","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/wolfstudy%2Ftx_unsignature/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/wolfstudy%2Ftx_unsignature/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/wolfstudy%2Ftx_unsignature/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/wolfstudy","download_url":"https://codeload.github.com/wolfstudy/tx_unsignature/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/wolfstudy%2Ftx_unsignature/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":259239290,"owners_count":22826897,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-10-01T09:52:20.936Z","updated_at":"2025-06-11T09:35:01.530Z","avatar_url":"https://github.com/wolfstudy.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# tx_unsignature\nthe project will analyze the not signature transaction\n\n\nthe project use btcd(golang) lib\n\nand fix the code.\nin opcode.go add follow code on `func opcodeCheckMultiSig()`\n\n```\nvar Result [][]string      //by wolf4j\nfunc opcodeCheckMultiSig(op *parsedOpcode, vm *Engine) error {\n\tnumKeys, err := vm.dstack.PopInt()\n\tif err != nil {\n\t\treturn err\n\t}\n\n\tnumPubKeys := int(numKeys.Int32())\n\tif numPubKeys \u003c 0 {\n\t\tstr := fmt.Sprintf(\"number of pubkeys %d is negative\",\n\t\t\tnumPubKeys)\n\t\treturn scriptError(ErrInvalidPubKeyCount, str)\n\t}\n\tif numPubKeys \u003e MaxPubKeysPerMultiSig {\n\t\tstr := fmt.Sprintf(\"too many pubkeys: %d \u003e %d\",\n\t\t\tnumPubKeys, MaxPubKeysPerMultiSig)\n\t\treturn scriptError(ErrInvalidPubKeyCount, str)\n\t}\n\tvm.numOps += numPubKeys\n\tif vm.numOps \u003e MaxOpsPerScript {\n\t\tstr := fmt.Sprintf(\"exceeded max operation limit of %d\",\n\t\t\tMaxOpsPerScript)\n\t\treturn scriptError(ErrTooManyOperations, str)\n\t}\n\n\tpubKeys := make([][]byte, 0, numPubKeys)\n\tfor i := 0; i \u003c numPubKeys; i++ {\n\t\tpubKey, err := vm.dstack.PopByteArray()\n\t\tif err != nil {\n\t\t\treturn err\n\t\t}\n\t\tpubKeys = append(pubKeys, pubKey)\n\t}\n\n\tnumSigs, err := vm.dstack.PopInt()\n\tif err != nil {\n\t\treturn err\n\t}\n\tnumSignatures := int(numSigs.Int32())\n\tif numSignatures \u003c 0 {\n\t\tstr := fmt.Sprintf(\"number of signatures %d is negative\",\n\t\t\tnumSignatures)\n\t\treturn scriptError(ErrInvalidSignatureCount, str)\n\n\t}\n\tif numSignatures \u003e numPubKeys {\n\t\tstr := fmt.Sprintf(\"more signatures than pubkeys: %d \u003e %d\",\n\t\t\tnumSignatures, numPubKeys)\n\t\treturn scriptError(ErrInvalidSignatureCount, str)\n\t}\n\n\tsignatures := make([]*parsedSigInfo, 0, numSignatures)\n\tfor i := 0; i \u003c numSignatures; i++ {\n\t\tsignature, err := vm.dstack.PopByteArray()\n\t\tif err != nil {\n\t\t\treturn err\n\t\t}\n\t\tsigInfo := \u0026parsedSigInfo{signature: signature}\n\t\tsignatures = append(signatures, sigInfo)\n\t}\n\n\t// A bug in the original Satoshi client implementation means one more\n\t// stack value than should be used must be popped.  Unfortunately, this\n\t// buggy behavior is now part of the consensus and a hard fork would be\n\t// required to fix it.\n\tdummy, err := vm.dstack.PopByteArray()\n\tif err != nil {\n\t\treturn err\n\t}\n\n\t// Since the dummy argument is otherwise not checked, it could be any\n\t// value which unfortunately provides a source of malleability.  Thus,\n\t// there is a script flag to force an error when the value is NOT 0.\n\tif vm.hasFlag(ScriptStrictMultiSig) \u0026\u0026 len(dummy) != 0 {\n\t\tstr := fmt.Sprintf(\"multisig dummy argument has length %d \"+\n\t\t\t\"instead of 0\", len(dummy))\n\t\treturn scriptError(ErrSigNullDummy, str)\n\t}\n\n\t// Get script starting from the most recent OP_CODESEPARATOR.\n\tscript := vm.subScript()\n\n\t// Remove the signature in pre version 0 segwit scripts since there is\n\t// no way for a signature to sign itself.\n\tif !vm.isWitnessVersionActive(0) {\n\t\tfor _, sigInfo := range signatures {\n\t\t\tscript = removeOpcodeByData(script, sigInfo.signature)\n\t\t}\n\t}\n\n\tsuccess := true\n\tnumPubKeys++\n\tpubKeyIdx := -1\n\tsignatureIdx := 0\n\tfor numSignatures \u003e 0 {\n\t\t// When there are more signatures than public keys remaining,\n\t\t// there is no way to succeed since too many signatures are\n\t\t// invalid, so exit early.\n\t\tpubKeyIdx++\n\t\tnumPubKeys--\n\t\tif numSignatures \u003e numPubKeys {\n\t\t\tsuccess = false\n\t\t\tbreak\n\t\t}\n\n\t\tsigInfo := signatures[signatureIdx]\n\t\tpubKey := pubKeys[pubKeyIdx]\n\n\t\t// The order of the signature and public key evaluation is\n\t\t// important here since it can be distinguished by an\n\t\t// OP_CHECKMULTISIG NOT when the strict encoding flag is set.\n\n\t\trawSig := sigInfo.signature\n\t\tif len(rawSig) == 0 {\n\t\t\t// Skip to the next pubkey if signature is empty.\n\t\t\tcontinue\n\t\t}\n\n\t\t// Split the signature into hash type and signature components.\n\t\thashType := SigHashType(rawSig[len(rawSig)-1])\n\t\tsignature := rawSig[:len(rawSig)-1]\n\n\t\t// Only parse and check the signature encoding once.\n\t\tvar parsedSig *btcec.Signature\n\t\tif !sigInfo.parsed {\n\t\t\tif err := vm.checkHashTypeEncoding(hashType); err != nil {\n\t\t\t\treturn err\n\t\t\t}\n\t\t\tif err := vm.checkSignatureEncoding(signature); err != nil {\n\t\t\t\treturn err\n\t\t\t}\n\n\t\t\t// Parse the signature.\n\t\t\tvar err error\n\t\t\tif vm.hasFlag(ScriptVerifyStrictEncoding) ||\n\t\t\t\tvm.hasFlag(ScriptVerifyDERSignatures) {\n\n\t\t\t\tparsedSig, err = btcec.ParseDERSignature(signature,\n\t\t\t\t\tbtcec.S256())\n\t\t\t} else {\n\t\t\t\tparsedSig, err = btcec.ParseSignature(signature,\n\t\t\t\t\tbtcec.S256())\n\t\t\t}\n\t\t\tsigInfo.parsed = true\n\t\t\tif err != nil {\n\t\t\t\tcontinue\n\t\t\t}\n\t\t\tsigInfo.parsedSignature = parsedSig\n\t\t} else {\n\t\t\t// Skip to the next pubkey if the signature is invalid.\n\t\t\tif sigInfo.parsedSignature == nil {\n\t\t\t\tcontinue\n\t\t\t}\n\n\t\t\t// Use the already parsed signature.\n\t\t\tparsedSig = sigInfo.parsedSignature\n\t\t}\n\n\t\tif err := vm.checkPubKeyEncoding(pubKey); err != nil {\n\t\t\treturn err\n\t\t}\n\n\t\t// Parse the pubkey.\n\t\tparsedPubKey, err := btcec.ParsePubKey(pubKey, btcec.S256())\n\t\tif err != nil {\n\t\t\tcontinue\n\t\t}\n\n\t\t// Generate the signature hash based on the signature hash type.\n\t\tvar hash []byte\n\t\tif vm.isWitnessVersionActive(0) {\n\t\t\tvar sigHashes *TxSigHashes\n\t\t\tif vm.hashCache != nil {\n\t\t\t\tsigHashes = vm.hashCache\n\t\t\t} else {\n\t\t\t\tsigHashes = NewTxSigHashes(\u0026vm.tx)\n\t\t\t}\n\n\t\t\thash, err = calcWitnessSignatureHash(script, sigHashes, hashType,\n\t\t\t\t\u0026vm.tx, vm.txIdx, vm.inputAmount)\n\t\t\tif err != nil {\n\t\t\t\treturn err\n\t\t\t}\n\t\t} else {\n\t\t\thash = calcSignatureHash(script, hashType, \u0026vm.tx, vm.txIdx)\n\t\t}\n\n\t\tvar valid bool\n\t\tif vm.sigCache != nil {\n\t\t\tvar sigHash chainhash.Hash\n\t\t\tcopy(sigHash[:], hash)\n\n\t\t\tvalid = vm.sigCache.Exists(sigHash, parsedSig, parsedPubKey)\n\t\t\tif !valid \u0026\u0026 parsedSig.Verify(hash, parsedPubKey) {\n\t\t\t\tvm.sigCache.Add(sigHash, parsedSig, parsedPubKey)\n\t\t\t\tvalid = true\n\t\t\t}\n\t\t} else {\n\t\t\tvalid = parsedSig.Verify(hash, parsedPubKey)\n\t\t\t// by wolf4j\n\t\t\tif valid {\n\t\t\t\tpublicKey := hex.EncodeToString(parsedPubKey.SerializeCompressed())\n\t\t\t\tResult[vm.txIdx] = append(Result[vm.txIdx], publicKey)\n\t\t\t\tfmt.Println(\"matched public key...\")\n\t\t\t}\n\t\t}\n\n\t\tif valid {\n\t\t\t// PubKey verified, move on to the next signature.\n\t\t\tsignatureIdx++\n\t\t\tnumSignatures--\n\t\t}\n\t}\n\n\tif !success \u0026\u0026 vm.hasFlag(ScriptVerifyNullFail) {\n\t\tfor _, sig := range signatures {\n\t\t\tif len(sig.signature) \u003e 0 {\n\t\t\t\tstr := \"not all signatures empty on failed checkmultisig\"\n\t\t\t\treturn scriptError(ErrNullFail, str)\n\t\t\t}\n\t\t}\n\t}\n\n\tvm.dstack.PushBool(success)\n\treturn nil\n}\n\n\n```","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fwolfstudy%2Ftx_unsignature","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fwolfstudy%2Ftx_unsignature","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fwolfstudy%2Ftx_unsignature/lists"}