diff options
-rw-r--r-- | README.md | 10 | ||||
-rw-r--r-- | doc/build-osx.md | 4 | ||||
-rwxr-xr-x | share/genbuild.sh | 2 | ||||
-rw-r--r-- | src/base58.cpp | 3 | ||||
-rw-r--r-- | src/hash.cpp | 69 | ||||
-rw-r--r-- | src/limitedmap.h | 15 | ||||
-rw-r--r-- | src/qt/bitcoingui.cpp | 14 | ||||
-rw-r--r-- | src/rpcnet.cpp | 3 | ||||
-rw-r--r-- | src/serialize.h | 2 | ||||
-rw-r--r-- | src/test/crypto_tests.cpp | 2 | ||||
-rw-r--r-- | src/test/data/script_invalid.json | 27 | ||||
-rw-r--r-- | src/test/data/script_valid.json | 26 | ||||
-rw-r--r-- | src/test/script_tests.cpp | 49 |
13 files changed, 160 insertions, 66 deletions
@@ -97,7 +97,7 @@ CXXFLAGS="-g -ggdb -O0" or whatever debug flags you need. **debug.log** If the code is behaving strangely, take a look in the debug.log file in the data directory; -error and debugging message are written there. +error and debugging messages are written there. The -debug=... command-line option controls debugging; running with just -debug will turn on all categories (and give you a very large debug.log file). @@ -111,12 +111,12 @@ Run with the -testnet option to run with "play bitcoins" on the test network, if are testing multi-machine code that needs to operate across the internet. If you are testing something that can run on one machine, run with the -regtest option. -In regression test mode blocks can be created on-demand; see qa/rpc-tests/ for tests -that run in -regest mode. +In regression test mode, blocks can be created on-demand; see qa/rpc-tests/ for tests +that run in -regtest mode. **DEBUG_LOCKORDER** Bitcoin Core is a multithreaded application, and deadlocks or other multithreading bugs can be very difficult to track down. Compiling with -DDEBUG_LOCKORDER (configure -CXXFLAGS="-DDEBUG_LOCKORDER -g") inserts run-time checks to keep track of what locks -are held, and adds warning to the debug.log file if inconsistencies are detected. +CXXFLAGS="-DDEBUG_LOCKORDER -g") inserts run-time checks to keep track of which locks +are held, and adds warnings to the debug.log file if inconsistencies are detected. diff --git a/doc/build-osx.md b/doc/build-osx.md index 5eeda5b08e..0364d3a01b 100644 --- a/doc/build-osx.md +++ b/doc/build-osx.md @@ -50,7 +50,7 @@ Running this command takes you into brew's interactive mode, which allows you to $ brew install https://raw.github.com/mxcl/homebrew/master/Library/Formula/berkeley-db4.rb -–without-java ``` -These rest of these commands are run inside brew interactive mode: +The rest of these commands are run inside brew interactive mode: ``` /private/tmp/berkeley-db4-UGpd0O/db-4.8.30 $ cd .. /private/tmp/berkeley-db4-UGpd0O $ db-4.8.30/dist/configure --prefix=/usr/local/Cellar/berkeley-db4/4.8.30 --mandir=/usr/local/Cellar/berkeley-db4/4.8.30/share/man --enable-cxx @@ -61,7 +61,7 @@ These rest of these commands are run inside brew interactive mode: After exiting, you'll get a warning that the install is keg-only, which means it wasn't symlinked to `/usr/local`. You don't need it to link it to build bitcoin, but if you want to, here's how: - $ brew --force link berkeley-db4 + $ brew link --force berkeley-db4 ### Building `bitcoind` diff --git a/share/genbuild.sh b/share/genbuild.sh index 0800b31229..679566e596 100755 --- a/share/genbuild.sh +++ b/share/genbuild.sh @@ -16,7 +16,7 @@ fi DESC="" SUFFIX="" LAST_COMMIT_DATE="" -if [ -e "$(which git 2>/dev/null)" -a -d ".git" ]; then +if [ -e "$(which git 2>/dev/null)" -a $(git rev-parse --is-inside-work-tree 2>/dev/null) = "true" ]; then # clean 'dirty' status of touched files that haven't been modified git diff >/dev/null 2>/dev/null diff --git a/src/base58.cpp b/src/base58.cpp index 9750f0a161..d94db2c51b 100644 --- a/src/base58.cpp +++ b/src/base58.cpp @@ -288,7 +288,8 @@ void CBitcoinSecret::SetKey(const CKey& vchSecret) CKey CBitcoinSecret::GetKey() { CKey ret; - ret.Set(&vchData[0], &vchData[32], vchData.size() > 32 && vchData[32] == 1); + assert(vchData.size() >= 32); + ret.Set(vchData.begin(), vchData.begin() + 32, vchData.size() > 32 && vchData[32] == 1); return ret; } diff --git a/src/hash.cpp b/src/hash.cpp index 4ce4da4c30..218607a6fd 100644 --- a/src/hash.cpp +++ b/src/hash.cpp @@ -9,45 +9,48 @@ unsigned int MurmurHash3(unsigned int nHashSeed, const std::vector<unsigned char { // The following is MurmurHash3 (x86_32), see http://code.google.com/p/smhasher/source/browse/trunk/MurmurHash3.cpp uint32_t h1 = nHashSeed; - const uint32_t c1 = 0xcc9e2d51; - const uint32_t c2 = 0x1b873593; + if (vDataToHash.size() > 0) + { + const uint32_t c1 = 0xcc9e2d51; + const uint32_t c2 = 0x1b873593; - const int nblocks = vDataToHash.size() / 4; + const int nblocks = vDataToHash.size() / 4; - //---------- - // body - const uint32_t* blocks = (const uint32_t*)(&vDataToHash[0] + nblocks * 4); + //---------- + // body + const uint32_t* blocks = (const uint32_t*)(&vDataToHash[0] + nblocks * 4); - for (int i = -nblocks; i; i++) { - uint32_t k1 = blocks[i]; + for (int i = -nblocks; i; i++) { + uint32_t k1 = blocks[i]; - k1 *= c1; - k1 = ROTL32(k1, 15); - k1 *= c2; + k1 *= c1; + k1 = ROTL32(k1, 15); + k1 *= c2; - h1 ^= k1; - h1 = ROTL32(h1, 13); - h1 = h1 * 5 + 0xe6546b64; - } + h1 ^= k1; + h1 = ROTL32(h1, 13); + h1 = h1 * 5 + 0xe6546b64; + } - //---------- - // tail - const uint8_t* tail = (const uint8_t*)(&vDataToHash[0] + nblocks * 4); - - uint32_t k1 = 0; - - switch (vDataToHash.size() & 3) { - case 3: - k1 ^= tail[2] << 16; - case 2: - k1 ^= tail[1] << 8; - case 1: - k1 ^= tail[0]; - k1 *= c1; - k1 = ROTL32(k1, 15); - k1 *= c2; - h1 ^= k1; - }; + //---------- + // tail + const uint8_t* tail = (const uint8_t*)(&vDataToHash[0] + nblocks * 4); + + uint32_t k1 = 0; + + switch (vDataToHash.size() & 3) { + case 3: + k1 ^= tail[2] << 16; + case 2: + k1 ^= tail[1] << 8; + case 1: + k1 ^= tail[0]; + k1 *= c1; + k1 = ROTL32(k1, 15); + k1 *= c2; + h1 ^= k1; + }; + } //---------- // finalization diff --git a/src/limitedmap.h b/src/limitedmap.h index 4bc8d9e5aa..03727d7c42 100644 --- a/src/limitedmap.h +++ b/src/limitedmap.h @@ -1,11 +1,11 @@ -// Copyright (c) 2012 The Bitcoin developers -// Distributed under the MIT/X11 software license, see the accompanying +// Copyright (c) 2012-2014 The Bitcoin developers +// Distributed under the MIT software license, see the accompanying // file COPYING or http://www.opensource.org/licenses/mit-license.php. #ifndef BITCOIN_LIMITEDMAP_H #define BITCOIN_LIMITEDMAP_H -#include <assert.h> // TODO: remove +#include <assert.h> #include <map> /** STL-like map container that only keeps the N elements with the highest value. */ @@ -59,12 +59,11 @@ public: return; } // Shouldn't ever get here - assert(0); //TODO remove me - map.erase(itTarget); + assert(0); } void update(const_iterator itIn, const mapped_type& v) { - //TODO: When we switch to C++11, use map.erase(itIn, itIn) to get the non-const iterator + // TODO: When we switch to C++11, use map.erase(itIn, itIn) to get the non-const iterator. iterator itTarget = map.find(itIn->first); if (itTarget == map.end()) return; @@ -77,9 +76,7 @@ public: return; } // Shouldn't ever get here - assert(0); //TODO remove me - itTarget->second = v; - rmap.insert(make_pair(v, itTarget)); + assert(0); } size_type max_size() const { return nMaxSize; } size_type max_size(size_type s) diff --git a/src/qt/bitcoingui.cpp b/src/qt/bitcoingui.cpp index dd5192982e..443bed14d7 100644 --- a/src/qt/bitcoingui.cpp +++ b/src/qt/bitcoingui.cpp @@ -662,6 +662,9 @@ void BitcoinGUI::setNumConnections(int count) void BitcoinGUI::setNumBlocks(int count) { + if(!clientModel) + return; + // Prevent orphan statusbar messages (e.g. hover Quit in main menu, wait until chain-sync starts -> garbelled text) statusBar()->clearMessage(); @@ -832,7 +835,7 @@ void BitcoinGUI::changeEvent(QEvent *e) #ifndef Q_OS_MAC // Ignored on Mac if(e->type() == QEvent::WindowStateChange) { - if(clientModel && clientModel->getOptionsModel()->getMinimizeToTray()) + if(clientModel && clientModel->getOptionsModel() && clientModel->getOptionsModel()->getMinimizeToTray()) { QWindowStateChangeEvent *wsevt = static_cast<QWindowStateChangeEvent*>(e); if(!(wsevt->oldState() & Qt::WindowMinimized) && isMinimized()) @@ -847,16 +850,16 @@ void BitcoinGUI::changeEvent(QEvent *e) void BitcoinGUI::closeEvent(QCloseEvent *event) { - if(clientModel) - { #ifndef Q_OS_MAC // Ignored on Mac + if(clientModel && clientModel->getOptionsModel()) + { if(!clientModel->getOptionsModel()->getMinimizeToTray() && !clientModel->getOptionsModel()->getMinimizeOnClose()) { QApplication::quit(); } -#endif } +#endif QMainWindow::closeEvent(event); } @@ -917,8 +920,7 @@ bool BitcoinGUI::handlePaymentRequest(const SendCoinsRecipient& recipient) gotoSendCoinsPage(); return true; } - else - return false; + return false; } void BitcoinGUI::setEncryptionStatus(int status) diff --git a/src/rpcnet.cpp b/src/rpcnet.cpp index 95f42eb47f..fb159d96f6 100644 --- a/src/rpcnet.cpp +++ b/src/rpcnet.cpp @@ -11,6 +11,7 @@ #include "sync.h" #include "timedata.h" #include "util.h" +#include "version.h" #include <boost/foreach.hpp> @@ -393,6 +394,8 @@ Value getnetworkinfo(const Array& params, bool fHelp) Object obj; obj.push_back(Pair("version", (int)CLIENT_VERSION)); + obj.push_back(Pair("subversion", + FormatSubVersion(CLIENT_NAME, CLIENT_VERSION, std::vector<string>()))); obj.push_back(Pair("protocolversion",(int)PROTOCOL_VERSION)); obj.push_back(Pair("localservices", strprintf("%016x", nLocalServices))); obj.push_back(Pair("timeoffset", GetTimeOffset())); diff --git a/src/serialize.h b/src/serialize.h index 57f5fd069b..447d808dee 100644 --- a/src/serialize.h +++ b/src/serialize.h @@ -921,7 +921,7 @@ public: Init(nTypeIn, nVersionIn); } - CDataStream(const std::vector<unsigned char>& vchIn, int nTypeIn, int nVersionIn) : vch((char*)&vchIn.begin()[0], (char*)&vchIn.end()[0]) + CDataStream(const std::vector<unsigned char>& vchIn, int nTypeIn, int nVersionIn) : vch(vchIn.begin(), vchIn.end()) { Init(nTypeIn, nVersionIn); } diff --git a/src/test/crypto_tests.cpp b/src/test/crypto_tests.cpp index a3eec270ee..68232a2ff1 100644 --- a/src/test/crypto_tests.cpp +++ b/src/test/crypto_tests.cpp @@ -32,7 +32,7 @@ void TestVector(const Hasher &h, const In &in, const Out &out) { size_t len = insecure_rand() % ((in.size() - pos + 1) / 2 + 1); hasher.Write((unsigned char*)&in[pos], len); pos += len; - if (pos > 0 && pos + 2 * out.size() > in.size()) { + if (pos > 0 && pos + 2 * out.size() > in.size() && pos < in.size()) { // Test that writing the rest at once to a copy of a hasher works. Hasher(hasher).Write((unsigned char*)&in[pos], in.size() - pos).Finalize(&hash[0]); BOOST_CHECK(hash == out); diff --git a/src/test/data/script_invalid.json b/src/test/data/script_invalid.json index 75de4716f8..401031ad12 100644 --- a/src/test/data/script_invalid.json +++ b/src/test/data/script_invalid.json @@ -1,4 +1,13 @@ [ +[" +Format is: [scriptPubKey, scriptSig, flags, ... comments] +It is evaluated as if there was a crediting coinbase transaction with two 0 +pushes as scriptSig, and one output of 0 satoshi and given scriptPubKey, +followed by a spending transaction which spends this output as only input (and +correct prevout hash), using the given scriptSig. All nLockTimes are 0, all +nSequences are max. +"], + ["", "DEPTH", "P2SH,STRICTENC", "Test the test: we should have an empty stack after scriptSig evaluation"], [" ", "DEPTH", "P2SH,STRICTENC", "and multiple spaces should not change that."], [" ", "DEPTH", "P2SH,STRICTENC"], @@ -373,5 +382,21 @@ ["0 0x01 0x50", "HASH160 0x14 0xece424a6bb6ddf4db592c0faed60685047a361b1 EQUAL", "P2SH,STRICTENC", "OP_RESERVED in P2SH should fail"], ["0 0x01 VER", "HASH160 0x14 0x0f4d7845db968f2a81b530b6f3c1d6246d4c7e01 EQUAL", "P2SH,STRICTENC", "OP_VER in P2SH should fail"], -["0x00", "'00' EQUAL", "P2SH,STRICTENC", "Basic OP_0 execution"] +["0x00", "'00' EQUAL", "P2SH,STRICTENC", "Basic OP_0 execution"], + +["0x48 0x3045022100ea4d62e1fb351ad977596457bb01dfce58e050541784277bd825c33bd98c2a9502203003347cf04573be4dc786c3fc5e7db09821565bf45c7d60160709b962f0398401 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH,STRICTENC", "Normal pay to pubkeyhash with wrong signature"], +["0x47 0x304402207d09de5e34968c3f8b27d8217f173629f1106ee5216aa11d6b1f9813b3a214060220610a6ed25c704f901c6278f4f57fb11eadefdf0b22df298cfb6ce7ea84c86bf401 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH,STRICTENC", "Normal pay to pubkeyhash using an anyonecanpay sighash"], +["0x47 0x3044022028686fb3c8d3e5068cc9924c494fb5026df201d23340896da62fe9bb73fd9d5f02202a239609524959c4ca3651fd0cc48245b0b240862146fc579f3a962a4f46942b01", "0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 CHECKSIG", "P2SH,STRICTENC", "Normal pay to pubkey with wrong signature"], +["0x47 0x3044022054cb0a3fca8694a0c231848ed9f965078148fd653e49dd4b6981fadac0f5ba0702204085be5af427d4561f13a07fd5a1c5ab0ff02126e9ba191448f5a9dae0da585301 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 0x19 0x76a914751e76e8199196d454941c45d1b3a323f1433bd688ac", "HASH160 0x14 0xcd7b44d0b03f2d026d1e586d7ae18903b0d385f6 EQUAL", "P2SH,STRICTENC", "P2SH with a pay to pubkeyhash inside with wrong signature"], +["0 0x48 0x3045022100e1c4e8800bd00c9ec3cd3df0e53e63bc5e8c018d0b68099a652f0b121f1a7e020220108dab275be7d1358530d3451d48aed747af77cc54e0423cbae5c572b2e1abb801", "1 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 1 CHECKMULTISIG", "P2SH,STRICTENC", "Raw multisig with one pubkey with wrong signature"], +["0x49 0x304602220000ea4d62e1fb351ad977596457bb01dfce58e050541774277bd825c33bd98c2a9502203003347cf04573be4dc786c3fc5e7db09821565bf45c7d60160709b962f0398401 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH,STRICTENC", "Normal pay to pubkeyhash with non-DER signature (too much R padding)"], +["0x47 0x30440220ea4d62e1fb351ad977596457bb01dfce58e050541774277bd825c33bd98c2a9502203003347cf04573be4dc786c3fc5e7db09821565bf45c7d60160709b962f0398401 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH,STRICTENC", "Normal pay to pubkeyhash with non-DER signature (too little R padding)"], +["0x49 0x3046022100ea4d62e1fb351ad977596457bb01dfce58e050541774277bd825c33bd98c2a950221003003347cf04573be4dc786c3fc5e7db09821565bf45c7d60160709b962f0398401 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH,STRICTENC", "Normal pay to pubkeyhash with non-DER signature (too much S padding)"], +["0x48 0x3045022100e6eda3fd34862078233463cae19f0b47995e3f892102e5b175175e92a9163cc402204bf58445819093638481084322b61a2d49b68c96fd6fea17ed494722d0d67b4f01", "0x41 0x0679be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798483ada7726a3c4655da4fbfc0e1108a8fd17b448a68554199c47d08ffb10d4b8 CHECKSIG", "P2SH,STRICTENC", "Pay to pubkey with hybrid pubkey encoding"], +["0x48 0x304502203b56d65863e0cdb89313043c2402f46f518c31658648151b01ec6b5b6c89206a022100d71efefb4c24fab36abb44ade106963d8114c5af1bda033faa1923f54ec4ea6a01", "0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 CHECKSIG", "P2SH,STRICTENC,LOW_S", "Pay to pubkey with high S"], +["0x47 0x3044022054cb0a3fca8694a0c231848fd9f965078148fd653e49dd4b6980fadac0f5ba0702204085be5af427d4561f13a07fd5a1c5ab0ff02126e9ba191448f5a9dae0da585301 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 0x19 0x76a914751e76e8199196d454941c45d1b3a323f1433bd688ac", "HASH160 0x14 0xcd7b44d0b03f2d026d1e586d7ae18903b0d385f6 EQUAL", "P2SH,STRICTENC", "P2SH with a pay to pubkeyhash inside with invalid signature"], +["1 0x48 0x3045022100e1c4e8800bd00c9ec3cd3de0e53e63bc5e8c018d0b68099a652f0b121f1a7e020220108dab275be7d1358530d3451d48aed747af77cc54e0423cbae5c572b2e1abb801", "1 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 1 CHECKMULTISIG", "P2SH,STRICTENC,NULLDUMMY", "Raw multisig with one pubkey with non-zero dummy"], + +["The End"] + ] diff --git a/src/test/data/script_valid.json b/src/test/data/script_valid.json index c1db4c6061..e0b527996c 100644 --- a/src/test/data/script_valid.json +++ b/src/test/data/script_valid.json @@ -1,4 +1,13 @@ [ +[" +Format is: [scriptPubKey, scriptSig, flags, ... comments] +It is evaluated as if there was a crediting coinbase transaction with two 0 +pushes as scriptSig, and one output of 0 satoshi and given scriptPubKey, +followed by a spending transaction which spends this output as only input (and +correct prevout hash), using the given scriptSig. All nLockTimes are 0, all +nSequences are max. +"], + ["", "DEPTH 0 EQUAL", "P2SH,STRICTENC", "Test the test: we should have an empty stack after scriptSig evaluation"], [" ", "DEPTH 0 EQUAL", "P2SH,STRICTENC", "and multiple spaces should not change that."], [" ", "DEPTH 0 EQUAL", "P2SH,STRICTENC"], @@ -518,5 +527,20 @@ "P2SH,STRICTENC", "Basic PUSHDATA1 signedness check"], -["0x00", "SIZE 0 EQUAL", "P2SH,STRICTENC", "Basic OP_0 execution"] +["0x00", "SIZE 0 EQUAL", "P2SH,STRICTENC", "Basic OP_0 execution"], + +["0x48 0x3045022100ea4d62e1fb351ad977596457bb01dfce58e050541774277bd825c33bd98c2a9502203003347cf04573be4dc786c3fc5e7db09821565bf45c7d60160709b962f0398401 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH,STRICTENC", "Normal pay to pubkeyhash"], +["0x47 0x304402207d09de5e34968c3f8b27d8217f173629f1106ee5216aa11d6b1f9813b3a214060220610a6ed25c704f901c6278f4f57fb11eadefdf0b22df298cfb6ce7ea84c86bf481 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH,STRICTENC", "Anyonecanpay pay to pubkeyhash"], +["0x47 0x3044022028686fb3c8d3e5069cc9924c494fb5026df201d23340896da62fe9bb73fd9d5f02202a239609524959c4ca3651fd0cc48245b0b240862146fc579f3a962a4f46942b01", "0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 CHECKSIG", "P2SH,STRICTENC", "Normal pay to pubkey"], +["0x47 0x3044022054cb0a3fca8694a0c231848ed9f965078148fd653e49dd4b6980fadac0f5ba0702204085be5af427d4561f13a07fd5a1c5ab0ff02126e9ba191448f5a9dae0da585301 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 0x19 0x76a914751e76e8199196d454941c45d1b3a323f1433bd688ac", "HASH160 0x14 0xcd7b44d0b03f2d026d1e586d7ae18903b0d385f6 EQUAL", "P2SH,STRICTENC", "P2SH with a pay to pubkeyhash inside"], +["0 0x48 0x3045022100e1c4e8800bd00c9ec3cd3de0e53e63bc5e8c018d0b68099a652f0b121f1a7e020220108dab275be7d1358530d3451d48aed747af77cc54e0423cbae5c572b2e1abb801", "1 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 1 CHECKMULTISIG", "P2SH,STRICTENC", "Raw multisig with one pubkey"], +["0x49 0x304602220000ea4d62e1fb351ad977596457bb01dfce58e050541774277bd825c33bd98c2a9502203003347cf04573be4dc786c3fc5e7db09821565bf45c7d60160709b962f0398401 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH", "Normal pay to pubkeyhash with non-DER signature (too much R padding)"], +["0x47 0x30440220ea4d62e1fb351ad977596457bb01dfce58e050541774277bd825c33bd98c2a9502203003347cf04573be4dc786c3fc5e7db09821565bf45c7d60160709b962f0398401 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH", "Normal pay to pubkeyhash with non-DER signature (too little R padding)"], +["0x49 0x3046022100ea4d62e1fb351ad977596457bb01dfce58e050541774277bd825c33bd98c2a950221003003347cf04573be4dc786c3fc5e7db09821565bf45c7d60160709b962f0398401 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798", "DUP HASH160 0x14 0x751e76e8199196d454941c45d1b3a323f1433bd6 EQUALVERIFY CHECKSIG", "P2SH", "Normal pay to pubkeyhash with non-DER signature (too much S padding)"], +["0x48 0x3045022100e6eda3fd34862078233463cae19f0b47995e3f892102e5b175175e92a9163cc402204bf58445819093638481084322b61a2d49b68c96fd6fea17ed494722d0d67b4f01", "0x41 0x0679be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798483ada7726a3c4655da4fbfc0e1108a8fd17b448a68554199c47d08ffb10d4b8 CHECKSIG", "P2SH", "Pay to pubkey with hybrid pubkey encoding"], +["0x48 0x304502203b56d65863e0cdb89313043c2402f46f518c31658648151b01ec6b5b6c89206a022100d71efefb4c24fab36abb44ade106963d8114c5af1bda033faa1923f54ec4ea6a01", "0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 CHECKSIG", "P2SH,STRICTENC", "Pay to pubkey with high S"], +["0x47 0x3044022054cb0a3fca8694a0c231848fd9f965078148fd653e49dd4b6980fadac0f5ba0702204085be5af427d4561f13a07fd5a1c5ab0ff02126e9ba191448f5a9dae0da585301 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 0x19 0x76a914751e76e8199196d454941c45d1b3a323f1433bd688ac", "HASH160 0x14 0xcd7b44d0b03f2d026d1e586d7ae18903b0d385f6 EQUAL", "STRICTENC", "P2SH with a pay to pubkeyhash inside with invalid signature"], +["1 0x48 0x3045022100e1c4e8800bd00c9ec3cd3de0e53e63bc5e8c018d0b68099a652f0b121f1a7e020220108dab275be7d1358530d3451d48aed747af77cc54e0423cbae5c572b2e1abb801", "1 0x21 0x0279be667ef9dcbbac55a06295ce870b07029bfcdb2dce28d959f2815b16f81798 1 CHECKMULTISIG", "P2SH,STRICTENC", "Raw multisig with one pubkey with non-zero dummy"], + +["The End"] ] diff --git a/src/test/script_tests.cpp b/src/test/script_tests.cpp index cb543a0cf1..178b35fa2d 100644 --- a/src/test/script_tests.cpp +++ b/src/test/script_tests.cpp @@ -52,6 +52,41 @@ read_json(const std::string& jsondata) BOOST_AUTO_TEST_SUITE(script_tests) +CMutableTransaction BuildCreditingTransaction(const CScript& scriptPubKey) +{ + CMutableTransaction txCredit; + txCredit.nVersion = 1; + txCredit.nLockTime = 0; + txCredit.vin.resize(1); + txCredit.vout.resize(1); + txCredit.vin[0].prevout.SetNull(); + txCredit.vin[0].scriptSig = CScript() << CScriptNum(0) << CScriptNum(0); + txCredit.vin[0].nSequence = std::numeric_limits<unsigned int>::max(); + txCredit.vout[0].scriptPubKey = scriptPubKey; + txCredit.vout[0].nValue = 0; + + return txCredit; +} + +CMutableTransaction BuildSpendingTransaction(const CScript& scriptSig, const CScript& scriptPubKey) +{ + CMutableTransaction txCredit = BuildCreditingTransaction(scriptPubKey); + + CMutableTransaction txSpend; + txSpend.nVersion = 1; + txSpend.nLockTime = 0; + txSpend.vin.resize(1); + txSpend.vout.resize(1); + txSpend.vin[0].prevout.hash = txCredit.GetHash(); + txSpend.vin[0].prevout.n = 0; + txSpend.vin[0].scriptSig = scriptSig; + txSpend.vin[0].nSequence = std::numeric_limits<unsigned int>::max(); + txSpend.vout[0].scriptPubKey = CScript(); + txSpend.vout[0].nValue = 0; + + return txSpend; +} + BOOST_AUTO_TEST_CASE(script_valid) { // Read tests from test/data/script_valid.json @@ -67,7 +102,9 @@ BOOST_AUTO_TEST_CASE(script_valid) string strTest = write_string(tv, false); if (test.size() < 3) // Allow size > 3; extra stuff ignored (useful for comments) { - BOOST_ERROR("Bad test: " << strTest); + if (test.size() != 1) { + BOOST_ERROR("Bad test: " << strTest); + } continue; } string scriptSigString = test[0].get_str(); @@ -77,7 +114,7 @@ BOOST_AUTO_TEST_CASE(script_valid) unsigned int scriptflags = ParseScriptFlags(test[2].get_str()); CTransaction tx; - BOOST_CHECK_MESSAGE(VerifyScript(scriptSig, scriptPubKey, tx, 0, scriptflags), strTest); + BOOST_CHECK_MESSAGE(VerifyScript(scriptSig, scriptPubKey, BuildSpendingTransaction(scriptSig, scriptPubKey), 0, scriptflags), strTest); } } @@ -90,9 +127,11 @@ BOOST_AUTO_TEST_CASE(script_invalid) { Array test = tv.get_array(); string strTest = write_string(tv, false); - if (test.size() < 2) // Allow size > 2; extra stuff ignored (useful for comments) + if (test.size() < 3) // Allow size > 3; extra stuff ignored (useful for comments) { - BOOST_ERROR("Bad test: " << strTest); + if (test.size() != 1) { + BOOST_ERROR("Bad test: " << strTest); + } continue; } string scriptSigString = test[0].get_str(); @@ -102,7 +141,7 @@ BOOST_AUTO_TEST_CASE(script_invalid) unsigned int scriptflags = ParseScriptFlags(test[2].get_str()); CTransaction tx; - BOOST_CHECK_MESSAGE(!VerifyScript(scriptSig, scriptPubKey, tx, 0, scriptflags), strTest); + BOOST_CHECK_MESSAGE(!VerifyScript(scriptSig, scriptPubKey, BuildSpendingTransaction(scriptSig, scriptPubKey), 0, scriptflags), strTest); } } |