From 1cdbea7f742fa128062009ea8ca22383bceacd1e Mon Sep 17 00:00:00 2001 From: Thomas Kerin Date: Fri, 13 Jul 2018 12:47:07 +0100 Subject: [PATCH] bitcoinconsensus: invalid flags should be set to bitcoinconsensus_error type, add test cases covering bitcoinconsensus error codes Github-Pull: #13655 Rebased-From: 417b6c1d2990ffc78c029442e027797d724a101f --- src/script/bitcoinconsensus.cpp | 2 +- src/test/script_tests.cpp | 142 ++++++++++++++++++++++++++++++++ 2 files changed, 143 insertions(+), 1 deletion(-) diff --git a/src/script/bitcoinconsensus.cpp b/src/script/bitcoinconsensus.cpp index 7d3587e2c..752176f73 100644 --- a/src/script/bitcoinconsensus.cpp +++ b/src/script/bitcoinconsensus.cpp @@ -81,7 +81,7 @@ static int verify_script(const unsigned char *scriptPubKey, unsigned int scriptP unsigned int nIn, unsigned int flags, bitcoinconsensus_error* err) { if (!verify_flags(flags)) { - return bitcoinconsensus_ERR_INVALID_FLAGS; + return set_error(err, bitcoinconsensus_ERR_INVALID_FLAGS); } try { TxInputStream stream(SER_NETWORK, PROTOCOL_VERSION, txTo, txToLen); diff --git a/src/test/script_tests.cpp b/src/test/script_tests.cpp index c7a497f3a..de90b00ab 100644 --- a/src/test/script_tests.cpp +++ b/src/test/script_tests.cpp @@ -1479,4 +1479,146 @@ BOOST_AUTO_TEST_CASE(script_can_append_self) BOOST_CHECK(s == d); } + +#if defined(HAVE_CONSENSUS_LIB) + +/* Test simple (successful) usage of bitcoinconsensus_verify_script */ +BOOST_AUTO_TEST_CASE(bitcoinconsensus_verify_script_returns_true) +{ + unsigned int libconsensus_flags = 0; + int nIn = 0; + + CScript scriptPubKey; + CScript scriptSig; + CScriptWitness wit; + + scriptPubKey << OP_1; + CTransaction creditTx = BuildCreditingTransaction(scriptPubKey, 1); + CTransaction spendTx = BuildSpendingTransaction(scriptSig, wit, creditTx); + + CDataStream stream(SER_NETWORK, PROTOCOL_VERSION); + stream << spendTx; + + bitcoinconsensus_error err; + int result = bitcoinconsensus_verify_script(scriptPubKey.data(), scriptPubKey.size(), (const unsigned char*)&stream[0], stream.size(), nIn, libconsensus_flags, &err); + BOOST_CHECK_EQUAL(result, 1); + BOOST_CHECK_EQUAL(err, bitcoinconsensus_ERR_OK); +} + +/* Test bitcoinconsensus_verify_script returns invalid tx index err*/ +BOOST_AUTO_TEST_CASE(bitcoinconsensus_verify_script_tx_index_err) +{ + unsigned int libconsensus_flags = 0; + int nIn = 3; + + CScript scriptPubKey; + CScript scriptSig; + CScriptWitness wit; + + scriptPubKey << OP_EQUAL; + CTransaction creditTx = BuildCreditingTransaction(scriptPubKey, 1); + CTransaction spendTx = BuildSpendingTransaction(scriptSig, wit, creditTx); + + CDataStream stream(SER_NETWORK, PROTOCOL_VERSION); + stream << spendTx; + + bitcoinconsensus_error err; + int result = bitcoinconsensus_verify_script(scriptPubKey.data(), scriptPubKey.size(), (const unsigned char*)&stream[0], stream.size(), nIn, libconsensus_flags, &err); + BOOST_CHECK_EQUAL(result, 0); + BOOST_CHECK_EQUAL(err, bitcoinconsensus_ERR_TX_INDEX); +} + +/* Test bitcoinconsensus_verify_script returns tx size mismatch err*/ +BOOST_AUTO_TEST_CASE(bitcoinconsensus_verify_script_tx_size) +{ + unsigned int libconsensus_flags = 0; + int nIn = 0; + + CScript scriptPubKey; + CScript scriptSig; + CScriptWitness wit; + + scriptPubKey << OP_EQUAL; + CTransaction creditTx = BuildCreditingTransaction(scriptPubKey, 1); + CTransaction spendTx = BuildSpendingTransaction(scriptSig, wit, creditTx); + + CDataStream stream(SER_NETWORK, PROTOCOL_VERSION); + stream << spendTx; + + bitcoinconsensus_error err; + int result = bitcoinconsensus_verify_script(scriptPubKey.data(), scriptPubKey.size(), (const unsigned char*)&stream[0], stream.size() * 2, nIn, libconsensus_flags, &err); + BOOST_CHECK_EQUAL(result, 0); + BOOST_CHECK_EQUAL(err, bitcoinconsensus_ERR_TX_SIZE_MISMATCH); +} + +/* Test bitcoinconsensus_verify_script returns invalid tx serialization error */ +BOOST_AUTO_TEST_CASE(bitcoinconsensus_verify_script_tx_serialization) +{ + unsigned int libconsensus_flags = 0; + int nIn = 0; + + CScript scriptPubKey; + CScript scriptSig; + CScriptWitness wit; + + scriptPubKey << OP_EQUAL; + CTransaction creditTx = BuildCreditingTransaction(scriptPubKey, 1); + CTransaction spendTx = BuildSpendingTransaction(scriptSig, wit, creditTx); + + CDataStream stream(SER_NETWORK, PROTOCOL_VERSION); + stream << 0xffffffff; + + bitcoinconsensus_error err; + int result = bitcoinconsensus_verify_script(scriptPubKey.data(), scriptPubKey.size(), (const unsigned char*)&stream[0], stream.size(), nIn, libconsensus_flags, &err); + BOOST_CHECK_EQUAL(result, 0); + BOOST_CHECK_EQUAL(err, bitcoinconsensus_ERR_TX_DESERIALIZE); +} + +/* Test bitcoinconsensus_verify_script returns amount required error */ +BOOST_AUTO_TEST_CASE(bitcoinconsensus_verify_script_amount_required_err) +{ + unsigned int libconsensus_flags = bitcoinconsensus_SCRIPT_FLAGS_VERIFY_WITNESS; + int nIn = 0; + + CScript scriptPubKey; + CScript scriptSig; + CScriptWitness wit; + + scriptPubKey << OP_EQUAL; + CTransaction creditTx = BuildCreditingTransaction(scriptPubKey, 1); + CTransaction spendTx = BuildSpendingTransaction(scriptSig, wit, creditTx); + + CDataStream stream(SER_NETWORK, PROTOCOL_VERSION); + stream << spendTx; + + bitcoinconsensus_error err; + int result = bitcoinconsensus_verify_script(scriptPubKey.data(), scriptPubKey.size(), (const unsigned char*)&stream[0], stream.size(), nIn, libconsensus_flags, &err); + BOOST_CHECK_EQUAL(result, 0); + BOOST_CHECK_EQUAL(err, bitcoinconsensus_ERR_AMOUNT_REQUIRED); +} + +/* Test bitcoinconsensus_verify_script returns invalid flags err */ +BOOST_AUTO_TEST_CASE(bitcoinconsensus_verify_script_invalid_flags) +{ + unsigned int libconsensus_flags = 1 << 3; + int nIn = 0; + + CScript scriptPubKey; + CScript scriptSig; + CScriptWitness wit; + + scriptPubKey << OP_EQUAL; + CTransaction creditTx = BuildCreditingTransaction(scriptPubKey, 1); + CTransaction spendTx = BuildSpendingTransaction(scriptSig, wit, creditTx); + + CDataStream stream(SER_NETWORK, PROTOCOL_VERSION); + stream << spendTx; + + bitcoinconsensus_error err; + int result = bitcoinconsensus_verify_script(scriptPubKey.data(), scriptPubKey.size(), (const unsigned char*)&stream[0], stream.size(), nIn, libconsensus_flags, &err); + BOOST_CHECK_EQUAL(result, 0); + BOOST_CHECK_EQUAL(err, bitcoinconsensus_ERR_INVALID_FLAGS); +} + +#endif BOOST_AUTO_TEST_SUITE_END()