From 8baa1b5ef53a8005e6ba9043d706418f5c91c8c9 Mon Sep 17 00:00:00 2001 From: Matt Corallo Date: Wed, 27 May 2015 12:30:42 -0700 Subject: [PATCH] Tweak SignatureChecker to expose a bit more about the transaction --- src/Makefile.am | 2 +- src/bitcoin-tx.cpp | 2 +- src/main.cpp | 8 ++++-- src/main.h | 16 +++++++++-- src/rpcrawtransaction.cpp | 2 +- src/script/bitcoinconsensus.cpp | 7 +++-- src/script/bitcoinconsensus.h | 9 ++++-- src/script/interpreter.cpp | 43 ++++++++++++++++++++++++++-- src/script/interpreter.h | 50 +++++++++++++++++++++++++++------ src/script/sigcache.h | 2 +- src/script/sign.cpp | 4 +-- src/test/multisig_tests.cpp | 16 +++++------ src/test/script_P2SH_tests.cpp | 4 +-- src/test/script_tests.cpp | 30 ++++++++++---------- src/test/transaction_tests.cpp | 4 +-- 15 files changed, 143 insertions(+), 56 deletions(-) diff --git a/src/Makefile.am b/src/Makefile.am index 81b16d1ea9..59aff516bb 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -373,7 +373,7 @@ if GLIBC_BACK_COMPAT libbitcoinconsensus_la_SOURCES += compat/glibcxx_compat.cpp endif -libbitcoinconsensus_la_LDFLAGS = -no-undefined $(RELDFLAGS) +libbitcoinconsensus_la_LDFLAGS = -no-undefined -version-info 1:0:0 $(RELDFLAGS) libbitcoinconsensus_la_LIBADD = $(CRYPTO_LIBS) libbitcoinconsensus_la_CPPFLAGS = $(CRYPTO_CFLAGS) -I$(builddir)/obj -DBUILD_BITCOIN_INTERNAL if USE_LIBSECP256K1 diff --git a/src/bitcoin-tx.cpp b/src/bitcoin-tx.cpp index 8e612d5dbe..91c98c9111 100644 --- a/src/bitcoin-tx.cpp +++ b/src/bitcoin-tx.cpp @@ -464,7 +464,7 @@ static void MutateTxSign(CMutableTransaction& tx, const string& flagStr) BOOST_FOREACH(const CTransaction& txv, txVariants) { txin.scriptSig = CombineSignatures(prevPubKey, mergedTx, i, txin.scriptSig, txv.vin[i].scriptSig); } - if (!VerifyScript(txin.scriptSig, prevPubKey, STANDARD_SCRIPT_VERIFY_FLAGS, MutableTransactionSignatureChecker(&mergedTx, i))) + if (!VerifyScript(txin.scriptSig, prevPubKey, STANDARD_SCRIPT_VERIFY_FLAGS, MutableTransactionNoWithdrawsSignatureChecker(&mergedTx, i))) fComplete = false; } diff --git a/src/main.cpp b/src/main.cpp index f99226b85f..43a3246436 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -1511,7 +1511,7 @@ void UpdateCoins(const CTransaction& tx, CValidationState &state, CCoinsViewCach bool CScriptCheck::operator()() { const CScript &scriptSig = ptxTo->vin[nIn].scriptSig; - if (!VerifyScript(scriptSig, scriptPubKey, nFlags, CachingTransactionSignatureChecker(ptxTo, nIn, cacheStore), &error)) { + if (!VerifyScript(scriptSig, scriptPubKey, nFlags, CachingTransactionSignatureChecker(ptxTo, nIn, nValueIn, nValueInPreviousIn, nTxFee, nSpendHeight, cacheStore), &error)) { return ::error("CScriptCheck(): %s:%d VerifySignature failed: %s", ptxTo->GetHash().ToString(), nIn, ScriptErrorString(error)); } return true; @@ -1580,13 +1580,14 @@ bool CheckInputs(const CTransaction& tx, CValidationState &state, const CCoinsVi // before the last block chain checkpoint. This is safe because block merkle hashes are // still computed and checked, and any change will be caught at the next checkpoint. if (fScriptChecks) { + CAmount prevValueIn = -1; for (unsigned int i = 0; i < tx.vin.size(); i++) { const COutPoint &prevout = tx.vin[i].prevout; const CCoins* coins = inputs.AccessCoins(prevout.hash); assert(coins); // Verify signature - CScriptCheck check(*coins, tx, i, flags, cacheStore); + CScriptCheck check(*coins, tx, i, prevValueIn, nTxFee, nSpendHeight, flags, cacheStore); if (pvChecks) { pvChecks->push_back(CScriptCheck()); check.swap(pvChecks->back()); @@ -1598,7 +1599,7 @@ bool CheckInputs(const CTransaction& tx, CValidationState &state, const CCoinsVi // arguments; if so, don't trigger DoS protection to // avoid splitting the network between upgraded and // non-upgraded nodes. - CScriptCheck check(*coins, tx, i, + CScriptCheck check(*coins, tx, i, prevValueIn, nTxFee, nSpendHeight, flags & ~STANDARD_NOT_MANDATORY_VERIFY_FLAGS, cacheStore); if (check()) return state.Invalid(false, REJECT_NONSTANDARD, strprintf("non-mandatory-script-verify-flag (%s)", ScriptErrorString(check.GetScriptError()))); @@ -1612,6 +1613,7 @@ bool CheckInputs(const CTransaction& tx, CValidationState &state, const CCoinsVi // super-majority vote has passed. return state.DoS(100,false, REJECT_INVALID, strprintf("mandatory-script-verify-flag-failed (%s)", ScriptErrorString(check.GetScriptError()))); } + prevValueIn = coins->vout[tx.vin[i].prevout.n].nValue; } } } diff --git a/src/main.h b/src/main.h index 23a6109652..57169cf6c2 100644 --- a/src/main.h +++ b/src/main.h @@ -352,15 +352,21 @@ private: CScript scriptPubKey; const CTransaction *ptxTo; unsigned int nIn; + CAmount nValueIn; + CAmount nValueInPreviousIn; + CAmount nTxFee; + int nSpendHeight; unsigned int nFlags; bool cacheStore; ScriptError error; public: - CScriptCheck(): ptxTo(0), nIn(0), nFlags(0), cacheStore(false), error(SCRIPT_ERR_UNKNOWN_ERROR) {} - CScriptCheck(const CCoins& txFromIn, const CTransaction& txToIn, unsigned int nInIn, unsigned int nFlagsIn, bool cacheIn) : + CScriptCheck(): ptxTo(0), nIn(0), nValueIn(-1), nValueInPreviousIn(-1), nTxFee(-1), nSpendHeight(-1), nFlags(0), cacheStore(false), error(SCRIPT_ERR_UNKNOWN_ERROR) {} + CScriptCheck(const CCoins& txFromIn, const CTransaction& txToIn, unsigned int nInIn, CAmount nValueInPreviousInIn, CAmount nTxFeeIn, int nSpendHeightIn, unsigned int nFlagsIn, bool cacheIn) : scriptPubKey(txFromIn.vout[txToIn.vin[nInIn].prevout.n].scriptPubKey), - ptxTo(&txToIn), nIn(nInIn), nFlags(nFlagsIn), cacheStore(cacheIn), error(SCRIPT_ERR_UNKNOWN_ERROR) { } + ptxTo(&txToIn), nIn(nInIn), nValueIn(txFromIn.vout[txToIn.vin[nInIn].prevout.n].nValue), + nValueInPreviousIn(nValueInPreviousInIn), nTxFee(nTxFeeIn), nSpendHeight(nSpendHeightIn), + nFlags(nFlagsIn), cacheStore(cacheIn), error(SCRIPT_ERR_UNKNOWN_ERROR) { } bool operator()(); @@ -368,6 +374,10 @@ public: scriptPubKey.swap(check.scriptPubKey); std::swap(ptxTo, check.ptxTo); std::swap(nIn, check.nIn); + std::swap(nValueIn, check.nValueIn); + std::swap(nValueInPreviousIn, check.nValueInPreviousIn); + std::swap(nTxFee, check.nTxFee); + std::swap(nSpendHeight, check.nSpendHeight); std::swap(nFlags, check.nFlags); std::swap(cacheStore, check.cacheStore); std::swap(error, check.error); diff --git a/src/rpcrawtransaction.cpp b/src/rpcrawtransaction.cpp index bf7bfe96d7..419cb7968b 100644 --- a/src/rpcrawtransaction.cpp +++ b/src/rpcrawtransaction.cpp @@ -800,7 +800,7 @@ Value signrawtransaction(const Array& params, bool fHelp) BOOST_FOREACH(const CMutableTransaction& txv, txVariants) { txin.scriptSig = CombineSignatures(prevPubKey, mergedTx, i, txin.scriptSig, txv.vin[i].scriptSig); } - if (!VerifyScript(txin.scriptSig, prevPubKey, STANDARD_SCRIPT_VERIFY_FLAGS, MutableTransactionSignatureChecker(&mergedTx, i))) + if (!VerifyScript(txin.scriptSig, prevPubKey, STANDARD_SCRIPT_VERIFY_FLAGS, MutableTransactionNoWithdrawsSignatureChecker(&mergedTx, i))) fComplete = false; } diff --git a/src/script/bitcoinconsensus.cpp b/src/script/bitcoinconsensus.cpp index f0d7e54e77..e4c2cafb10 100644 --- a/src/script/bitcoinconsensus.cpp +++ b/src/script/bitcoinconsensus.cpp @@ -63,8 +63,9 @@ inline int set_error(bitcoinconsensus_error* ret, bitcoinconsensus_error serror) } // anon namespace int bitcoinconsensus_verify_script(const unsigned char *scriptPubKey, unsigned int scriptPubKeyLen, - const unsigned char *txTo , unsigned int txToLen, - unsigned int nIn, unsigned int flags, bitcoinconsensus_error* err) + const unsigned char *txTo, unsigned int txToLen, + int64_t nInValue, int64_t nInMinusOneValue, int64_t nTxFee, int nSpendHeight, + unsigned int nIn, unsigned int flags, bitcoinconsensus_error* err) { try { TxInputStream stream(SER_NETWORK, PROTOCOL_VERSION, txTo, txToLen); @@ -78,7 +79,7 @@ int bitcoinconsensus_verify_script(const unsigned char *scriptPubKey, unsigned i // Regardless of the verification result, the tx did not error. set_error(err, bitcoinconsensus_ERR_OK); - return VerifyScript(tx.vin[nIn].scriptSig, CScript(scriptPubKey, scriptPubKey + scriptPubKeyLen), flags, TransactionSignatureChecker(&tx, nIn), NULL); + return VerifyScript(tx.vin[nIn].scriptSig, CScript(scriptPubKey, scriptPubKey + scriptPubKeyLen), flags, TransactionSignatureChecker(&tx, nIn, nInValue, nInMinusOneValue, nTxFee, nSpendHeight), NULL); } catch (const std::exception&) { return set_error(err, bitcoinconsensus_ERR_TX_DESERIALIZE); // Error deserializing } diff --git a/src/script/bitcoinconsensus.h b/src/script/bitcoinconsensus.h index c57d8b3cc5..6f47ba5d41 100644 --- a/src/script/bitcoinconsensus.h +++ b/src/script/bitcoinconsensus.h @@ -27,11 +27,13 @@ #define EXPORT_SYMBOL #endif +#include + #ifdef __cplusplus extern "C" { #endif -#define BITCOINCONSENSUS_API_VER 0 +#define BITCOINCONSENSUS_API_VER 1 typedef enum bitcoinconsensus_error_t { @@ -54,8 +56,9 @@ enum /// the additional constraints specified by flags. /// If not NULL, err will contain an error/success code for the operation EXPORT_SYMBOL int bitcoinconsensus_verify_script(const unsigned char *scriptPubKey, unsigned int scriptPubKeyLen, - const unsigned char *txTo , unsigned int txToLen, - unsigned int nIn, unsigned int flags, bitcoinconsensus_error* err); + const unsigned char *txTo, unsigned int txToLen, + int64_t nInValue, int64_t nInMinusOneValue, int64_t nTxFee, int nSpendHeight, + unsigned int nIn, unsigned int flags, bitcoinconsensus_error* err); EXPORT_SYMBOL unsigned int bitcoinconsensus_version(); diff --git a/src/script/interpreter.cpp b/src/script/interpreter.cpp index c4c40ff2c2..0b48c7c9d7 100644 --- a/src/script/interpreter.cpp +++ b/src/script/interpreter.cpp @@ -1140,12 +1140,22 @@ uint256 SignatureHash(const CScript& scriptCode, const CTransaction& txTo, unsig return ss.GetHash(); } -bool TransactionSignatureChecker::VerifySignature(const std::vector& vchSig, const CPubKey& pubkey, const uint256& sighash) const +CTxOut BaseSignatureChecker::GetOutputOffsetFromCurrent(const int offset) const +{ + return CTxOut(); +} + +COutPoint BaseSignatureChecker::GetPrevOut() const +{ + return COutPoint(); +} + +bool TransactionNoWithdrawsSignatureChecker::VerifySignature(const std::vector& vchSig, const CPubKey& pubkey, const uint256& sighash) const { return pubkey.Verify(sighash, vchSig); } -bool TransactionSignatureChecker::CheckSig(const vector& vchSigIn, const vector& vchPubKey, const CScript& scriptCode) const +bool TransactionNoWithdrawsSignatureChecker::CheckSig(const vector& vchSigIn, const vector& vchPubKey, const CScript& scriptCode) const { CPubKey pubkey(vchPubKey); if (!pubkey.IsValid()) @@ -1166,7 +1176,7 @@ bool TransactionSignatureChecker::CheckSig(const vector& vchSigIn return true; } -bool TransactionSignatureChecker::CheckLockTime(const CScriptNum& nLockTime, bool fSequence) const +bool TransactionNoWithdrawsSignatureChecker::CheckLockTime(const CScriptNum& nLockTime, bool fSequence) const { // Relative lock times are supported by comparing the passed // in lock time to the sequence number of the input. All other @@ -1215,6 +1225,33 @@ bool TransactionSignatureChecker::CheckLockTime(const CScriptNum& nLockTime, boo return true; } +CTxOut TransactionSignatureChecker::GetOutputOffsetFromCurrent(const int offset) const +{ + assert(int(nIn) >= 0 && int(txTo->vout.size()) > 0); + if (int(nIn) + offset < 0 || int(txTo->vout.size()) <= int(nIn) + offset) + return CTxOut(); + return txTo->vout[int(nIn) + offset]; +} + +COutPoint TransactionSignatureChecker::GetPrevOut() const +{ + return txTo->vin[nIn].prevout; +} + +CAmount TransactionSignatureChecker::GetValueIn() const +{ + return nInValue; +} + +CAmount TransactionSignatureChecker::GetTransactionFee() const +{ + return nTransactionFee; +} + +CAmount TransactionSignatureChecker::GetValueInPrevIn() const +{ + return nInMinusOneValue; +} bool VerifyScript(const CScript& scriptSig, const CScript& scriptPubKey, unsigned int flags, const BaseSignatureChecker& checker, ScriptError* serror) { diff --git a/src/script/interpreter.h b/src/script/interpreter.h index 4467a702e0..bdb1390a50 100644 --- a/src/script/interpreter.h +++ b/src/script/interpreter.h @@ -14,6 +14,7 @@ #include class CPubKey; +class COutPoint; class CScript; class CTransaction; class uint256; @@ -92,31 +93,64 @@ public: return false; } + virtual CTxOut GetOutputOffsetFromCurrent(const int offset) const; + virtual COutPoint GetPrevOut() const; + + virtual CAmount GetValueIn() const + { + return -1; + } + + virtual CAmount GetValueInPrevIn() const + { + return -1; + } + + virtual CAmount GetTransactionFee() const + { + return -1; + } + virtual ~BaseSignatureChecker() {} }; -class TransactionSignatureChecker : public BaseSignatureChecker +class TransactionNoWithdrawsSignatureChecker : public BaseSignatureChecker { -private: - const CTransaction* txTo; - unsigned int nIn; - protected: + const CTransaction* txTo; + const unsigned int nIn; virtual bool VerifySignature(const std::vector& vchSig, const CPubKey& vchPubKey, const uint256& sighash) const; public: - TransactionSignatureChecker(const CTransaction* txToIn, unsigned int nInIn) : txTo(txToIn), nIn(nInIn) {} + TransactionNoWithdrawsSignatureChecker(const CTransaction* txToIn, unsigned int nInIn) : txTo(txToIn), nIn(nInIn) {} bool CheckSig(const std::vector& scriptSig, const std::vector& vchPubKey, const CScript& scriptCode) const; bool CheckLockTime(const CScriptNum& nLockTime, bool fSequence = false) const; }; -class MutableTransactionSignatureChecker : public TransactionSignatureChecker +class MutableTransactionNoWithdrawsSignatureChecker : public TransactionNoWithdrawsSignatureChecker { private: const CTransaction txTo; public: - MutableTransactionSignatureChecker(const CMutableTransaction* txToIn, unsigned int nInIn) : TransactionSignatureChecker(&txTo, nInIn), txTo(*txToIn) {} + MutableTransactionNoWithdrawsSignatureChecker(const CMutableTransaction* txToIn, unsigned int nInIn) : TransactionNoWithdrawsSignatureChecker(&txTo, nInIn), txTo(*txToIn) {} +}; + +class TransactionSignatureChecker : public TransactionNoWithdrawsSignatureChecker +{ +private: + const CAmount nInValue; + const CAmount nInMinusOneValue; + const CAmount nTransactionFee; + const int nSpendHeight; + +public: + TransactionSignatureChecker(const CTransaction* txToIn, unsigned int nInIn, CAmount nInValueIn, CAmount nInMinusOneValueIn, CAmount nTransactionFeeIn, int nSpendHeightIn) : TransactionNoWithdrawsSignatureChecker(txToIn, nInIn), nInValue(nInValueIn), nInMinusOneValue(nInMinusOneValueIn), nTransactionFee(nTransactionFeeIn), nSpendHeight(nSpendHeightIn) {} + CTxOut GetOutputOffsetFromCurrent(const int offset) const; + COutPoint GetPrevOut() const; + CAmount GetValueIn() const; + CAmount GetValueInPrevIn() const; + CAmount GetTransactionFee() const; }; bool EvalScript(std::vector >& stack, const CScript& script, unsigned int flags, const BaseSignatureChecker& checker, ScriptError* error = NULL); diff --git a/src/script/sigcache.h b/src/script/sigcache.h index 38b032b67b..f3e1e56e46 100644 --- a/src/script/sigcache.h +++ b/src/script/sigcache.h @@ -18,7 +18,7 @@ private: bool store; public: - CachingTransactionSignatureChecker(const CTransaction* txToIn, unsigned int nInIn, bool storeIn=true) : TransactionSignatureChecker(txToIn, nInIn), store(storeIn) {} + CachingTransactionSignatureChecker(const CTransaction* txToIn, unsigned int nInIn, CAmount nInValueIn, CAmount nInMinusOneValueIn, CAmount nTransactionFeeIn, int nSpendHeightIn, bool storeIn=true) : TransactionSignatureChecker(txToIn, nInIn, nInValueIn, nInMinusOneValueIn, nTransactionFeeIn, nSpendHeightIn), store(storeIn) {} bool VerifySignature(const std::vector& vchSig, const CPubKey& vchPubKey, const uint256& sighash) const; }; diff --git a/src/script/sign.cpp b/src/script/sign.cpp index 2069398b43..e0c7c77726 100644 --- a/src/script/sign.cpp +++ b/src/script/sign.cpp @@ -125,7 +125,7 @@ bool SignSignature(const CKeyStore &keystore, const CScript& fromPubKey, CMutabl } // Test solution - return VerifyScript(txin.scriptSig, fromPubKey, STANDARD_SCRIPT_VERIFY_FLAGS, MutableTransactionSignatureChecker(&txTo, nIn)); + return VerifyScript(txin.scriptSig, fromPubKey, STANDARD_SCRIPT_VERIFY_FLAGS, MutableTransactionNoWithdrawsSignatureChecker(&txTo, nIn)); } bool SignSignature(const CKeyStore &keystore, const CTransaction& txFrom, CMutableTransaction& txTo, unsigned int nIn, int nHashType) @@ -176,7 +176,7 @@ static CScript CombineMultisig(const CScript& scriptPubKey, const CTransaction& if (sigs.count(pubkey)) continue; // Already got a sig for this pubkey - if (TransactionSignatureChecker(&txTo, nIn).CheckSig(sig, pubkey, scriptPubKey)) + if (TransactionNoWithdrawsSignatureChecker(&txTo, nIn).CheckSig(sig, pubkey, scriptPubKey)) { sigs[pubkey] = sig; break; diff --git a/src/test/multisig_tests.cpp b/src/test/multisig_tests.cpp index 0b5402f2fd..ab5aaab504 100644 --- a/src/test/multisig_tests.cpp +++ b/src/test/multisig_tests.cpp @@ -84,7 +84,7 @@ BOOST_AUTO_TEST_CASE(multisig_verify) keys.clear(); keys += key[0],key[1]; // magic operator+= from boost.assign s = sign_multisig(a_and_b, keys, txTo[0], 0); - BOOST_CHECK(VerifyScript(s, a_and_b, flags, MutableTransactionSignatureChecker(&txTo[0], 0), &err)); + BOOST_CHECK(VerifyScript(s, a_and_b, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo[0], 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_OK, ScriptErrorString(err)); for (int i = 0; i < 4; i++) @@ -92,13 +92,13 @@ BOOST_AUTO_TEST_CASE(multisig_verify) keys.clear(); keys += key[i]; s = sign_multisig(a_and_b, keys, txTo[0], 0); - BOOST_CHECK_MESSAGE(!VerifyScript(s, a_and_b, flags, MutableTransactionSignatureChecker(&txTo[0], 0), &err), strprintf("a&b 1: %d", i)); + BOOST_CHECK_MESSAGE(!VerifyScript(s, a_and_b, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo[0], 0), &err), strprintf("a&b 1: %d", i)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_INVALID_STACK_OPERATION, ScriptErrorString(err)); keys.clear(); keys += key[1],key[i]; s = sign_multisig(a_and_b, keys, txTo[0], 0); - BOOST_CHECK_MESSAGE(!VerifyScript(s, a_and_b, flags, MutableTransactionSignatureChecker(&txTo[0], 0), &err), strprintf("a&b 2: %d", i)); + BOOST_CHECK_MESSAGE(!VerifyScript(s, a_and_b, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo[0], 0), &err), strprintf("a&b 2: %d", i)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); } @@ -110,18 +110,18 @@ BOOST_AUTO_TEST_CASE(multisig_verify) s = sign_multisig(a_or_b, keys, txTo[1], 0); if (i == 0 || i == 1) { - BOOST_CHECK_MESSAGE(VerifyScript(s, a_or_b, flags, MutableTransactionSignatureChecker(&txTo[1], 0), &err), strprintf("a|b: %d", i)); + BOOST_CHECK_MESSAGE(VerifyScript(s, a_or_b, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo[1], 0), &err), strprintf("a|b: %d", i)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_OK, ScriptErrorString(err)); } else { - BOOST_CHECK_MESSAGE(!VerifyScript(s, a_or_b, flags, MutableTransactionSignatureChecker(&txTo[1], 0), &err), strprintf("a|b: %d", i)); + BOOST_CHECK_MESSAGE(!VerifyScript(s, a_or_b, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo[1], 0), &err), strprintf("a|b: %d", i)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); } } s.clear(); s << OP_0 << OP_1; - BOOST_CHECK(!VerifyScript(s, a_or_b, flags, MutableTransactionSignatureChecker(&txTo[1], 0), &err)); + BOOST_CHECK(!VerifyScript(s, a_or_b, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo[1], 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_SIG_DER, ScriptErrorString(err)); @@ -133,12 +133,12 @@ BOOST_AUTO_TEST_CASE(multisig_verify) s = sign_multisig(escrow, keys, txTo[2], 0); if (i < j && i < 3 && j < 3) { - BOOST_CHECK_MESSAGE(VerifyScript(s, escrow, flags, MutableTransactionSignatureChecker(&txTo[2], 0), &err), strprintf("escrow 1: %d %d", i, j)); + BOOST_CHECK_MESSAGE(VerifyScript(s, escrow, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo[2], 0), &err), strprintf("escrow 1: %d %d", i, j)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_OK, ScriptErrorString(err)); } else { - BOOST_CHECK_MESSAGE(!VerifyScript(s, escrow, flags, MutableTransactionSignatureChecker(&txTo[2], 0), &err), strprintf("escrow 2: %d %d", i, j)); + BOOST_CHECK_MESSAGE(!VerifyScript(s, escrow, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo[2], 0), &err), strprintf("escrow 2: %d %d", i, j)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); } } diff --git a/src/test/script_P2SH_tests.cpp b/src/test/script_P2SH_tests.cpp index bc40fd1b97..1a787064a7 100644 --- a/src/test/script_P2SH_tests.cpp +++ b/src/test/script_P2SH_tests.cpp @@ -43,7 +43,7 @@ Verify(const CScript& scriptSig, const CScript& scriptPubKey, bool fStrict, Scri txTo.vin[0].scriptSig = scriptSig; txTo.vout[0].nValue = 1; - return VerifyScript(scriptSig, scriptPubKey, fStrict ? SCRIPT_VERIFY_P2SH : SCRIPT_VERIFY_NONE, MutableTransactionSignatureChecker(&txTo, 0), &err); + return VerifyScript(scriptSig, scriptPubKey, fStrict ? SCRIPT_VERIFY_P2SH : SCRIPT_VERIFY_NONE, MutableTransactionNoWithdrawsSignatureChecker(&txTo, 0), &err); } @@ -114,7 +114,7 @@ BOOST_AUTO_TEST_CASE(sign) { CScript sigSave = txTo[i].vin[0].scriptSig; txTo[i].vin[0].scriptSig = txTo[j].vin[0].scriptSig; - bool sigOK = CScriptCheck(CCoins(txFrom, 0), txTo[i], 0, SCRIPT_VERIFY_P2SH | SCRIPT_VERIFY_STRICTENC, false)(); + bool sigOK = CScriptCheck(CCoins(txFrom, 0), txTo[i], 0, -1, -1, -1, SCRIPT_VERIFY_P2SH | SCRIPT_VERIFY_STRICTENC, false)(); if (i == j) BOOST_CHECK_MESSAGE(sigOK, strprintf("VerifySignature %d %d", i, j)); else diff --git a/src/test/script_tests.cpp b/src/test/script_tests.cpp index d96eff1d7a..12e04827d1 100644 --- a/src/test/script_tests.cpp +++ b/src/test/script_tests.cpp @@ -100,12 +100,12 @@ void DoTest(const CScript& scriptPubKey, const CScript& scriptSig, int flags, bo ScriptError err; CMutableTransaction tx = BuildSpendingTransaction(scriptSig, BuildCreditingTransaction(scriptPubKey)); CMutableTransaction tx2 = tx; - BOOST_CHECK_MESSAGE(VerifyScript(scriptSig, scriptPubKey, flags, MutableTransactionSignatureChecker(&tx, 0), &err) == expect, message); + BOOST_CHECK_MESSAGE(VerifyScript(scriptSig, scriptPubKey, flags, MutableTransactionNoWithdrawsSignatureChecker(&tx, 0), &err) == expect, message); BOOST_CHECK_MESSAGE(expect == (err == SCRIPT_ERR_OK), std::string(ScriptErrorString(err)) + ": " + message); #if defined(HAVE_CONSENSUS_LIB) CDataStream stream(SER_NETWORK, PROTOCOL_VERSION); stream << tx2; - BOOST_CHECK_MESSAGE(bitcoinconsensus_verify_script(begin_ptr(scriptPubKey), scriptPubKey.size(), (const unsigned char*)&stream[0], stream.size(), 0, flags, NULL) == expect,message); + BOOST_CHECK_MESSAGE(bitcoinconsensus_verify_script(begin_ptr(scriptPubKey), scriptPubKey.size(), (const unsigned char*)&stream[0], stream.size(), 0, 0, 0, 0, 0, flags, NULL) == expect,message); #endif } @@ -746,18 +746,18 @@ BOOST_AUTO_TEST_CASE(script_CHECKMULTISIG12) CMutableTransaction txTo12 = BuildSpendingTransaction(CScript(), txFrom12); CScript goodsig1 = sign_multisig(scriptPubKey12, key1, txTo12); - BOOST_CHECK(VerifyScript(goodsig1, scriptPubKey12, flags, MutableTransactionSignatureChecker(&txTo12, 0), &err)); + BOOST_CHECK(VerifyScript(goodsig1, scriptPubKey12, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo12, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_OK, ScriptErrorString(err)); txTo12.vout[0].nValue = 2; - BOOST_CHECK(!VerifyScript(goodsig1, scriptPubKey12, flags, MutableTransactionSignatureChecker(&txTo12, 0), &err)); + BOOST_CHECK(!VerifyScript(goodsig1, scriptPubKey12, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo12, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); CScript goodsig2 = sign_multisig(scriptPubKey12, key2, txTo12); - BOOST_CHECK(VerifyScript(goodsig2, scriptPubKey12, flags, MutableTransactionSignatureChecker(&txTo12, 0), &err)); + BOOST_CHECK(VerifyScript(goodsig2, scriptPubKey12, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo12, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_OK, ScriptErrorString(err)); CScript badsig1 = sign_multisig(scriptPubKey12, key3, txTo12); - BOOST_CHECK(!VerifyScript(badsig1, scriptPubKey12, flags, MutableTransactionSignatureChecker(&txTo12, 0), &err)); + BOOST_CHECK(!VerifyScript(badsig1, scriptPubKey12, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo12, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); } @@ -779,54 +779,54 @@ BOOST_AUTO_TEST_CASE(script_CHECKMULTISIG23) std::vector keys; keys.push_back(key1); keys.push_back(key2); CScript goodsig1 = sign_multisig(scriptPubKey23, keys, txTo23); - BOOST_CHECK(VerifyScript(goodsig1, scriptPubKey23, flags, MutableTransactionSignatureChecker(&txTo23, 0), &err)); + BOOST_CHECK(VerifyScript(goodsig1, scriptPubKey23, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo23, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_OK, ScriptErrorString(err)); keys.clear(); keys.push_back(key1); keys.push_back(key3); CScript goodsig2 = sign_multisig(scriptPubKey23, keys, txTo23); - BOOST_CHECK(VerifyScript(goodsig2, scriptPubKey23, flags, MutableTransactionSignatureChecker(&txTo23, 0), &err)); + BOOST_CHECK(VerifyScript(goodsig2, scriptPubKey23, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo23, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_OK, ScriptErrorString(err)); keys.clear(); keys.push_back(key2); keys.push_back(key3); CScript goodsig3 = sign_multisig(scriptPubKey23, keys, txTo23); - BOOST_CHECK(VerifyScript(goodsig3, scriptPubKey23, flags, MutableTransactionSignatureChecker(&txTo23, 0), &err)); + BOOST_CHECK(VerifyScript(goodsig3, scriptPubKey23, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo23, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_OK, ScriptErrorString(err)); keys.clear(); keys.push_back(key2); keys.push_back(key2); // Can't re-use sig CScript badsig1 = sign_multisig(scriptPubKey23, keys, txTo23); - BOOST_CHECK(!VerifyScript(badsig1, scriptPubKey23, flags, MutableTransactionSignatureChecker(&txTo23, 0), &err)); + BOOST_CHECK(!VerifyScript(badsig1, scriptPubKey23, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo23, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); keys.clear(); keys.push_back(key2); keys.push_back(key1); // sigs must be in correct order CScript badsig2 = sign_multisig(scriptPubKey23, keys, txTo23); - BOOST_CHECK(!VerifyScript(badsig2, scriptPubKey23, flags, MutableTransactionSignatureChecker(&txTo23, 0), &err)); + BOOST_CHECK(!VerifyScript(badsig2, scriptPubKey23, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo23, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); keys.clear(); keys.push_back(key3); keys.push_back(key2); // sigs must be in correct order CScript badsig3 = sign_multisig(scriptPubKey23, keys, txTo23); - BOOST_CHECK(!VerifyScript(badsig3, scriptPubKey23, flags, MutableTransactionSignatureChecker(&txTo23, 0), &err)); + BOOST_CHECK(!VerifyScript(badsig3, scriptPubKey23, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo23, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); keys.clear(); keys.push_back(key4); keys.push_back(key2); // sigs must match pubkeys CScript badsig4 = sign_multisig(scriptPubKey23, keys, txTo23); - BOOST_CHECK(!VerifyScript(badsig4, scriptPubKey23, flags, MutableTransactionSignatureChecker(&txTo23, 0), &err)); + BOOST_CHECK(!VerifyScript(badsig4, scriptPubKey23, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo23, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); keys.clear(); keys.push_back(key1); keys.push_back(key4); // sigs must match pubkeys CScript badsig5 = sign_multisig(scriptPubKey23, keys, txTo23); - BOOST_CHECK(!VerifyScript(badsig5, scriptPubKey23, flags, MutableTransactionSignatureChecker(&txTo23, 0), &err)); + BOOST_CHECK(!VerifyScript(badsig5, scriptPubKey23, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo23, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_EVAL_FALSE, ScriptErrorString(err)); keys.clear(); // Must have signatures CScript badsig6 = sign_multisig(scriptPubKey23, keys, txTo23); - BOOST_CHECK(!VerifyScript(badsig6, scriptPubKey23, flags, MutableTransactionSignatureChecker(&txTo23, 0), &err)); + BOOST_CHECK(!VerifyScript(badsig6, scriptPubKey23, flags, MutableTransactionNoWithdrawsSignatureChecker(&txTo23, 0), &err)); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_INVALID_STACK_OPERATION, ScriptErrorString(err)); } diff --git a/src/test/transaction_tests.cpp b/src/test/transaction_tests.cpp index 0e16662084..a86788ff8d 100644 --- a/src/test/transaction_tests.cpp +++ b/src/test/transaction_tests.cpp @@ -147,7 +147,7 @@ BOOST_AUTO_TEST_CASE(tx_valid) unsigned int verify_flags = ParseScriptFlags(test[2].get_str()); BOOST_CHECK_MESSAGE(VerifyScript(tx.vin[i].scriptSig, mapprevOutScriptPubKeys[tx.vin[i].prevout], - verify_flags, TransactionSignatureChecker(&tx, i), &err), + verify_flags, TransactionNoWithdrawsSignatureChecker(&tx, i), &err), strTest); BOOST_CHECK_MESSAGE(err == SCRIPT_ERR_OK, ScriptErrorString(err)); } @@ -222,7 +222,7 @@ BOOST_AUTO_TEST_CASE(tx_invalid) unsigned int verify_flags = ParseScriptFlags(test[2].get_str()); fValid = VerifyScript(tx.vin[i].scriptSig, mapprevOutScriptPubKeys[tx.vin[i].prevout], - verify_flags, TransactionSignatureChecker(&tx, i), &err); + verify_flags, TransactionNoWithdrawsSignatureChecker(&tx, i), &err); } BOOST_CHECK_MESSAGE(!fValid, strTest); BOOST_CHECK_MESSAGE(err != SCRIPT_ERR_OK, ScriptErrorString(err));