Bitcoin Core  22.99.0
P2P Digital Currency
interfaces_tests.cpp
Go to the documentation of this file.
1 // Copyright (c) 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 <consensus/validation.h>
7 #include <interfaces/chain.h>
8 #include <script/standard.h>
10 #include <validation.h>
11 
12 #include <boost/test/unit_test.hpp>
13 
15 
17 
19 {
20  auto& chain = m_node.chain;
21  const CChain& active = Assert(m_node.chainman)->ActiveChain();
22 
23  uint256 hash;
24  BOOST_CHECK(chain->findBlock(active[10]->GetBlockHash(), FoundBlock().hash(hash)));
25  BOOST_CHECK_EQUAL(hash, active[10]->GetBlockHash());
26 
27  int height = -1;
28  BOOST_CHECK(chain->findBlock(active[20]->GetBlockHash(), FoundBlock().height(height)));
29  BOOST_CHECK_EQUAL(height, active[20]->nHeight);
30 
31  CBlock data;
32  BOOST_CHECK(chain->findBlock(active[30]->GetBlockHash(), FoundBlock().data(data)));
33  BOOST_CHECK_EQUAL(data.GetHash(), active[30]->GetBlockHash());
34 
35  int64_t time = -1;
36  BOOST_CHECK(chain->findBlock(active[40]->GetBlockHash(), FoundBlock().time(time)));
37  BOOST_CHECK_EQUAL(time, active[40]->GetBlockTime());
38 
39  int64_t max_time = -1;
40  BOOST_CHECK(chain->findBlock(active[50]->GetBlockHash(), FoundBlock().maxTime(max_time)));
41  BOOST_CHECK_EQUAL(max_time, active[50]->GetBlockTimeMax());
42 
43  int64_t mtp_time = -1;
44  BOOST_CHECK(chain->findBlock(active[60]->GetBlockHash(), FoundBlock().mtpTime(mtp_time)));
45  BOOST_CHECK_EQUAL(mtp_time, active[60]->GetMedianTimePast());
46 
47  bool cur_active{false}, next_active{false};
48  uint256 next_hash;
49  BOOST_CHECK_EQUAL(active.Height(), 100);
50  BOOST_CHECK(chain->findBlock(active[99]->GetBlockHash(), FoundBlock().inActiveChain(cur_active).nextBlock(FoundBlock().inActiveChain(next_active).hash(next_hash))));
51  BOOST_CHECK(cur_active);
52  BOOST_CHECK(next_active);
53  BOOST_CHECK_EQUAL(next_hash, active[100]->GetBlockHash());
54  cur_active = next_active = false;
55  BOOST_CHECK(chain->findBlock(active[100]->GetBlockHash(), FoundBlock().inActiveChain(cur_active).nextBlock(FoundBlock().inActiveChain(next_active))));
56  BOOST_CHECK(cur_active);
57  BOOST_CHECK(!next_active);
58 
59  BOOST_CHECK(!chain->findBlock({}, FoundBlock()));
60 }
61 
62 BOOST_AUTO_TEST_CASE(findFirstBlockWithTimeAndHeight)
63 {
64  auto& chain = m_node.chain;
65  const CChain& active = Assert(m_node.chainman)->ActiveChain();
66  uint256 hash;
67  int height;
68  BOOST_CHECK(chain->findFirstBlockWithTimeAndHeight(/* min_time= */ 0, /* min_height= */ 5, FoundBlock().hash(hash).height(height)));
69  BOOST_CHECK_EQUAL(hash, active[5]->GetBlockHash());
70  BOOST_CHECK_EQUAL(height, 5);
71  BOOST_CHECK(!chain->findFirstBlockWithTimeAndHeight(/* min_time= */ active.Tip()->GetBlockTimeMax() + 1, /* min_height= */ 0));
72 }
73 
74 BOOST_AUTO_TEST_CASE(findAncestorByHeight)
75 {
76  auto& chain = m_node.chain;
77  const CChain& active = Assert(m_node.chainman)->ActiveChain();
78  uint256 hash;
79  BOOST_CHECK(chain->findAncestorByHeight(active[20]->GetBlockHash(), 10, FoundBlock().hash(hash)));
80  BOOST_CHECK_EQUAL(hash, active[10]->GetBlockHash());
81  BOOST_CHECK(!chain->findAncestorByHeight(active[10]->GetBlockHash(), 20));
82 }
83 
84 BOOST_AUTO_TEST_CASE(findAncestorByHash)
85 {
86  auto& chain = m_node.chain;
87  const CChain& active = Assert(m_node.chainman)->ActiveChain();
88  int height = -1;
89  BOOST_CHECK(chain->findAncestorByHash(active[20]->GetBlockHash(), active[10]->GetBlockHash(), FoundBlock().height(height)));
90  BOOST_CHECK_EQUAL(height, 10);
91  BOOST_CHECK(!chain->findAncestorByHash(active[10]->GetBlockHash(), active[20]->GetBlockHash()));
92 }
93 
94 BOOST_AUTO_TEST_CASE(findCommonAncestor)
95 {
96  auto& chain = m_node.chain;
97  const CChain& active = Assert(m_node.chainman)->ActiveChain();
98  auto* orig_tip = active.Tip();
99  for (int i = 0; i < 10; ++i) {
100  BlockValidationState state;
101  m_node.chainman->ActiveChainstate().InvalidateBlock(state, active.Tip());
102  }
103  BOOST_CHECK_EQUAL(active.Height(), orig_tip->nHeight - 10);
104  coinbaseKey.MakeNewKey(true);
105  for (int i = 0; i < 20; ++i) {
106  CreateAndProcessBlock({}, GetScriptForRawPubKey(coinbaseKey.GetPubKey()));
107  }
108  BOOST_CHECK_EQUAL(active.Height(), orig_tip->nHeight + 10);
109  uint256 fork_hash;
110  int fork_height;
111  int orig_height;
112  BOOST_CHECK(chain->findCommonAncestor(orig_tip->GetBlockHash(), active.Tip()->GetBlockHash(), FoundBlock().height(fork_height).hash(fork_hash), FoundBlock().height(orig_height)));
113  BOOST_CHECK_EQUAL(orig_height, orig_tip->nHeight);
114  BOOST_CHECK_EQUAL(fork_height, orig_tip->nHeight - 10);
115  BOOST_CHECK_EQUAL(fork_hash, active[fork_height]->GetBlockHash());
116 
117  uint256 active_hash, orig_hash;
118  BOOST_CHECK(!chain->findCommonAncestor(active.Tip()->GetBlockHash(), {}, {}, FoundBlock().hash(active_hash), {}));
119  BOOST_CHECK(!chain->findCommonAncestor({}, orig_tip->GetBlockHash(), {}, {}, FoundBlock().hash(orig_hash)));
120  BOOST_CHECK_EQUAL(active_hash, active.Tip()->GetBlockHash());
121  BOOST_CHECK_EQUAL(orig_hash, orig_tip->GetBlockHash());
122 }
123 
125 {
126  auto& chain = m_node.chain;
127  const CChain& active = Assert(m_node.chainman)->ActiveChain();
128 
129  // Test ranges
130  BOOST_CHECK(chain->hasBlocks(active.Tip()->GetBlockHash(), 10, 90));
131  BOOST_CHECK(chain->hasBlocks(active.Tip()->GetBlockHash(), 10, {}));
132  BOOST_CHECK(chain->hasBlocks(active.Tip()->GetBlockHash(), 0, 90));
133  BOOST_CHECK(chain->hasBlocks(active.Tip()->GetBlockHash(), 0, {}));
134  BOOST_CHECK(chain->hasBlocks(active.Tip()->GetBlockHash(), -1000, 1000));
135  active[5]->nStatus &= ~BLOCK_HAVE_DATA;
136  BOOST_CHECK(chain->hasBlocks(active.Tip()->GetBlockHash(), 10, 90));
137  BOOST_CHECK(chain->hasBlocks(active.Tip()->GetBlockHash(), 10, {}));
138  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 0, 90));
139  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 0, {}));
140  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), -1000, 1000));
141  active[95]->nStatus &= ~BLOCK_HAVE_DATA;
142  BOOST_CHECK(chain->hasBlocks(active.Tip()->GetBlockHash(), 10, 90));
143  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 10, {}));
144  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 0, 90));
145  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 0, {}));
146  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), -1000, 1000));
147  active[50]->nStatus &= ~BLOCK_HAVE_DATA;
148  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 10, 90));
149  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 10, {}));
150  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 0, 90));
151  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 0, {}));
152  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), -1000, 1000));
153 
154  // Test edge cases
155  BOOST_CHECK(chain->hasBlocks(active.Tip()->GetBlockHash(), 6, 49));
156  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 5, 49));
157  BOOST_CHECK(!chain->hasBlocks(active.Tip()->GetBlockHash(), 6, 50));
158 }
159 
BOOST_AUTO_TEST_CASE
BOOST_AUTO_TEST_CASE(findBlock)
Definition: interfaces_tests.cpp:18
nHeight
unsigned int nHeight
Definition: mempool_eviction.cpp:14
BlockValidationState
Definition: validation.h:140
setup_common.h
m_node
NodeContext & m_node
Definition: bitcoin-node.cpp:38
validation.h
chainparams.h
chain.h
BOOST_FIXTURE_TEST_SUITE
#define BOOST_FIXTURE_TEST_SUITE(a, b)
Definition: object.cpp:14
CChain::Tip
CBlockIndex * Tip() const
Returns the index entry for the tip of this chain, or nullptr if none.
Definition: chain.h:403
BOOST_AUTO_TEST_SUITE_END
BOOST_AUTO_TEST_SUITE_END()
NodeContext::chain
std::unique_ptr< interfaces::Chain > chain
Definition: context.h:50
Assert
#define Assert(val)
Identity function.
Definition: check.h:57
CBlockHeader::GetHash
uint256 GetHash() const
Definition: block.cpp:11
CBlockIndex::GetBlockTimeMax
int64_t GetBlockTimeMax() const
Definition: chain.h:265
GetScriptForRawPubKey
CScript GetScriptForRawPubKey(const CPubKey &pubKey)
Generate a P2PK script for the given pubkey.
Definition: standard.cpp:356
standard.h
TestChain100Setup
Testing fixture that pre-creates a 100-block REGTEST-mode block chain.
Definition: setup_common.h:116
interfaces::FoundBlock
Helper for findBlock to selectively return pieces of block data.
Definition: chain.h:41
uint256
256-bit opaque blob.
Definition: uint256.h:124
CBlockIndex::GetBlockHash
uint256 GetBlockHash() const
Definition: chain.h:246
CChain::Height
int Height() const
Return the maximal height in the chain.
Definition: chain.h:428
CBlock
Definition: block.h:62
CChain
An in-memory indexed chain of blocks.
Definition: chain.h:392
NodeContext::chainman
std::unique_ptr< ChainstateManager > chainman
Definition: context.h:47
BLOCK_HAVE_DATA
@ BLOCK_HAVE_DATA
full block available in blk*.dat
Definition: chain.h:121
BOOST_CHECK
#define BOOST_CHECK(expr)
Definition: object.cpp:17
BOOST_CHECK_EQUAL
#define BOOST_CHECK_EQUAL(v1, v2)
Definition: object.cpp:18