1 // Copyright (c) 2011-2014 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.
9 #include "test/test_bitcoin.h"
11 #include <boost/test/unit_test.hpp>
14 BOOST_FIXTURE_TEST_SUITE(mempool_tests, TestingSetup)
16 BOOST_AUTO_TEST_CASE(MempoolRemoveTest)
18 // Test CTxMemPool::remove functionality
20 // Parent transaction with three children,
21 // and three grand-children:
22 CMutableTransaction txParent;
23 txParent.vin.resize(1);
24 txParent.vin[0].scriptSig = CScript() << OP_11;
25 txParent.vout.resize(3);
26 for (int i = 0; i < 3; i++)
28 txParent.vout[i].scriptPubKey = CScript() << OP_11 << OP_EQUAL;
29 txParent.vout[i].nValue = 33000LL;
31 CMutableTransaction txChild[3];
32 for (int i = 0; i < 3; i++)
34 txChild[i].vin.resize(1);
35 txChild[i].vin[0].scriptSig = CScript() << OP_11;
36 txChild[i].vin[0].prevout.hash = txParent.GetHash();
37 txChild[i].vin[0].prevout.n = i;
38 txChild[i].vout.resize(1);
39 txChild[i].vout[0].scriptPubKey = CScript() << OP_11 << OP_EQUAL;
40 txChild[i].vout[0].nValue = 11000LL;
42 CMutableTransaction txGrandChild[3];
43 for (int i = 0; i < 3; i++)
45 txGrandChild[i].vin.resize(1);
46 txGrandChild[i].vin[0].scriptSig = CScript() << OP_11;
47 txGrandChild[i].vin[0].prevout.hash = txChild[i].GetHash();
48 txGrandChild[i].vin[0].prevout.n = 0;
49 txGrandChild[i].vout.resize(1);
50 txGrandChild[i].vout[0].scriptPubKey = CScript() << OP_11 << OP_EQUAL;
51 txGrandChild[i].vout[0].nValue = 11000LL;
55 CTxMemPool testPool(CFeeRate(0));
56 std::list<CTransaction> removed;
58 // Nothing in pool, remove should do nothing:
59 testPool.remove(txParent, removed, true);
60 BOOST_CHECK_EQUAL(removed.size(), 0);
63 testPool.addUnchecked(txParent.GetHash(), CTxMemPoolEntry(txParent, 0, 0, 0.0, 1));
64 testPool.remove(txParent, removed, true);
65 BOOST_CHECK_EQUAL(removed.size(), 1);
68 // Parent, children, grandchildren:
69 testPool.addUnchecked(txParent.GetHash(), CTxMemPoolEntry(txParent, 0, 0, 0.0, 1));
70 for (int i = 0; i < 3; i++)
72 testPool.addUnchecked(txChild[i].GetHash(), CTxMemPoolEntry(txChild[i], 0, 0, 0.0, 1));
73 testPool.addUnchecked(txGrandChild[i].GetHash(), CTxMemPoolEntry(txGrandChild[i], 0, 0, 0.0, 1));
75 // Remove Child[0], GrandChild[0] should be removed:
76 testPool.remove(txChild[0], removed, true);
77 BOOST_CHECK_EQUAL(removed.size(), 2);
79 // ... make sure grandchild and child are gone:
80 testPool.remove(txGrandChild[0], removed, true);
81 BOOST_CHECK_EQUAL(removed.size(), 0);
82 testPool.remove(txChild[0], removed, true);
83 BOOST_CHECK_EQUAL(removed.size(), 0);
84 // Remove parent, all children/grandchildren should go:
85 testPool.remove(txParent, removed, true);
86 BOOST_CHECK_EQUAL(removed.size(), 5);
87 BOOST_CHECK_EQUAL(testPool.size(), 0);
90 // Add children and grandchildren, but NOT the parent (simulate the parent being in a block)
91 for (int i = 0; i < 3; i++)
93 testPool.addUnchecked(txChild[i].GetHash(), CTxMemPoolEntry(txChild[i], 0, 0, 0.0, 1));
94 testPool.addUnchecked(txGrandChild[i].GetHash(), CTxMemPoolEntry(txGrandChild[i], 0, 0, 0.0, 1));
96 // Now remove the parent, as might happen if a block-re-org occurs but the parent cannot be
97 // put into the mempool (maybe because it is non-standard):
98 testPool.remove(txParent, removed, true);
99 BOOST_CHECK_EQUAL(removed.size(), 6);
100 BOOST_CHECK_EQUAL(testPool.size(), 0);
104 BOOST_AUTO_TEST_SUITE_END()