Line data Source code
1 : // Copyright (c) 2017-2020 The Bitcoin Core developers 2 : // Distributed under the MIT software license, see the accompanying 3 : // file COPYING or http://www.opensource.org/licenses/mit-license.php. 4 : 5 : #include <chainparams.h> 6 : #include <index/txindex.h> 7 : #include <script/standard.h> 8 : #include <test/util/setup_common.h> 9 : #include <util/time.h> 10 : 11 : #include <boost/test/unit_test.hpp> 12 : 13 89 : BOOST_AUTO_TEST_SUITE(txindex_tests) 14 : 15 95 : BOOST_FIXTURE_TEST_CASE(txindex_initial_sync, TestChain100Setup) 16 : { 17 1 : TxIndex txindex(1 << 20, true); 18 : 19 1 : CTransactionRef tx_disk; 20 1 : uint256 block_hash; 21 : 22 : // Transaction should not be found in the index before it is started. 23 101 : for (const auto& txn : m_coinbase_txns) { 24 100 : BOOST_CHECK(!txindex.FindTx(txn->GetHash(), block_hash, tx_disk)); 25 : } 26 : 27 : // BlockUntilSyncedToCurrentChain should return false before txindex is started. 28 1 : BOOST_CHECK(!txindex.BlockUntilSyncedToCurrentChain()); 29 : 30 1 : txindex.Start(); 31 : 32 : // Allow tx index to catch up with the block index. 33 : constexpr int64_t timeout_ms = 10 * 1000; 34 1 : int64_t time_start = GetTimeMillis(); 35 2 : while (!txindex.BlockUntilSyncedToCurrentChain()) { 36 1 : BOOST_REQUIRE(time_start + timeout_ms > GetTimeMillis()); 37 1 : UninterruptibleSleep(std::chrono::milliseconds{100}); 38 : } 39 : 40 : // Check that txindex excludes genesis block transactions. 41 1 : const CBlock& genesis_block = Params().GenesisBlock(); 42 2 : for (const auto& txn : genesis_block.vtx) { 43 1 : BOOST_CHECK(!txindex.FindTx(txn->GetHash(), block_hash, tx_disk)); 44 : } 45 : 46 : // Check that txindex has all txs that were in the chain before it started. 47 101 : for (const auto& txn : m_coinbase_txns) { 48 100 : if (!txindex.FindTx(txn->GetHash(), block_hash, tx_disk)) { 49 0 : BOOST_ERROR("FindTx failed"); 50 100 : } else if (tx_disk->GetHash() != txn->GetHash()) { 51 0 : BOOST_ERROR("Read incorrect tx"); 52 : } 53 : } 54 : 55 : // Check that new transactions in new blocks make it into the index. 56 11 : for (int i = 0; i < 10; i++) { 57 10 : CScript coinbase_script_pub_key = GetScriptForDestination(PKHash(coinbaseKey.GetPubKey())); 58 10 : std::vector<CMutableTransaction> no_txns; 59 10 : const CBlock& block = CreateAndProcessBlock(no_txns, coinbase_script_pub_key); 60 10 : const CTransaction& txn = *block.vtx[0]; 61 : 62 10 : BOOST_CHECK(txindex.BlockUntilSyncedToCurrentChain()); 63 10 : if (!txindex.FindTx(txn.GetHash(), block_hash, tx_disk)) { 64 0 : BOOST_ERROR("FindTx failed"); 65 10 : } else if (tx_disk->GetHash() != txn.GetHash()) { 66 0 : BOOST_ERROR("Read incorrect tx"); 67 : } 68 10 : } 69 : 70 : // shutdown sequence (c.f. Shutdown() in init.cpp) 71 1 : txindex.Stop(); 72 : 73 : // Let scheduler events finish running to avoid accessing any memory related to txindex after it is destructed 74 1 : SyncWithValidationInterfaceQueue(); 75 1 : } 76 : 77 89 : BOOST_AUTO_TEST_SUITE_END()