|
7 | 7 | #include <coins.h>
|
8 | 8 | #include <consensus/consensus.h>
|
9 | 9 | #include <consensus/validation.h>
|
| 10 | +#include <kernel/coinstats.h> |
10 | 11 | #include <node/blockstorage.h>
|
11 | 12 | #include <node/utxo_snapshot.h>
|
12 | 13 | #include <primitives/block.h>
|
@@ -39,14 +40,42 @@ using node::SnapshotMetadata;
|
39 | 40 | namespace {
|
40 | 41 |
|
41 | 42 | const std::vector<std::shared_ptr<CBlock>>* g_chain;
|
42 |
| -TestingSetup* g_setup; |
| 43 | +TestingSetup* g_setup{nullptr}; |
| 44 | + |
| 45 | +/** Sanity check the assumeutxo values hardcoded in chainparams for the fuzz target. */ |
| 46 | +void sanity_check_snapshot() |
| 47 | +{ |
| 48 | + Assert(g_chain && g_setup == nullptr); |
| 49 | + |
| 50 | + // Create a temporary chainstate manager to connect the chain to. |
| 51 | + const auto tmp_setup{MakeNoLogFileContext<TestingSetup>(ChainType::REGTEST, TestOpts{.setup_net = false})}; |
| 52 | + const auto& node{tmp_setup->m_node}; |
| 53 | + for (auto& block: *g_chain) { |
| 54 | + ProcessBlock(node, block); |
| 55 | + } |
| 56 | + |
| 57 | + // Connect the chain to the tmp chainman and sanity check the chainparams snapshot values. |
| 58 | + LOCK(cs_main); |
| 59 | + auto& cs{node.chainman->ActiveChainstate()}; |
| 60 | + cs.ForceFlushStateToDisk(); |
| 61 | + const auto stats{*Assert(kernel::ComputeUTXOStats(kernel::CoinStatsHashType::HASH_SERIALIZED, &cs.CoinsDB(), node.chainman->m_blockman))}; |
| 62 | + const auto cp_au_data{*Assert(node.chainman->GetParams().AssumeutxoForHeight(2 * COINBASE_MATURITY))}; |
| 63 | + Assert(stats.nHeight == cp_au_data.height); |
| 64 | + Assert(stats.nTransactions + 1 == cp_au_data.m_chain_tx_count); // +1 for the genesis tx. |
| 65 | + Assert(stats.hashBlock == cp_au_data.blockhash); |
| 66 | + Assert(AssumeutxoHash{stats.hashSerialized} == cp_au_data.hash_serialized); |
| 67 | +} |
43 | 68 |
|
44 | 69 | template <bool INVALID>
|
45 | 70 | void initialize_chain()
|
46 | 71 | {
|
47 | 72 | const auto params{CreateChainParams(ArgsManager{}, ChainType::REGTEST)};
|
48 | 73 | static const auto chain{CreateBlockChain(2 * COINBASE_MATURITY, *params)};
|
49 | 74 | g_chain = &chain;
|
| 75 | + |
| 76 | + // Make sure we can generate a valid snapshot. |
| 77 | + sanity_check_snapshot(); |
| 78 | + |
50 | 79 | static const auto setup{
|
51 | 80 | MakeNoLogFileContext<TestingSetup>(ChainType::REGTEST,
|
52 | 81 | TestOpts{
|
@@ -101,7 +130,7 @@ void utxo_snapshot_fuzz(FuzzBufferType buffer)
|
101 | 130 | std::vector<uint8_t> file_data{ConsumeRandomLengthByteVector(fuzzed_data_provider)};
|
102 | 131 | outfile << std::span{file_data};
|
103 | 132 | } else {
|
104 |
| - int height{0}; |
| 133 | + int height{1}; |
105 | 134 | for (const auto& block : *g_chain) {
|
106 | 135 | auto coinbase{block->vtx.at(0)};
|
107 | 136 | outfile << coinbase->GetHash();
|
|
0 commit comments