@@ -307,12 +307,47 @@ bool CBlockTreeDB::WritePAKList(const std::vector<std::vector<unsigned char> >&
307307 return Write (std::make_pair (DB_PAK, uint256S (" 1" )), offline_list) && Write (std::make_pair (DB_PAK, uint256S (" 2" )), online_list) && Write (std::make_pair (DB_PAK, uint256S (" 3" )), reject);
308308}
309309
310- bool CBlockTreeDB::LoadBlockIndexGuts (const Consensus::Params& consensusParams, std::function<CBlockIndex*(const uint256&)> insertBlockIndex)
310+ bool CBlockTreeDB::WalkBlockIndexGutsForMaxHeight (int * nHeight) {
311+ std::unique_ptr<CDBIterator> pcursor (NewIterator ());
312+ *nHeight = 0 ;
313+ int i = 0 ;
314+ pcursor->Seek (std::make_pair (DB_BLOCK_INDEX, uint256 ()));
315+ while (pcursor->Valid ()) {
316+ if (ShutdownRequested ()) return false ;
317+ std::pair<uint8_t , uint256> key;
318+ if (pcursor->GetKey (key) && key.first == DB_BLOCK_INDEX) {
319+ i++;
320+ if (i > 10'000 ) {
321+ // Under the (accurate) assumption hat the headers on disk are effectively in random height order,
322+ // we have a good-enough (conservative) estimate of the max height very quickly, and don't need to
323+ // waste more time. Shortcutting like this will cause us to keep a few extra headers, which is fine.
324+ break ;
325+ }
326+ CDiskBlockIndex diskindex;
327+ if (pcursor->GetValue (diskindex)) {
328+ if (diskindex.nHeight > *nHeight) {
329+ *nHeight = diskindex.nHeight ;
330+ }
331+ pcursor->Next ();
332+ } else {
333+ return error (" %s: failed to read value" , __func__);
334+ }
335+ } else {
336+ break ;
337+ }
338+ }
339+ return true ;
340+ }
341+
342+ bool CBlockTreeDB::LoadBlockIndexGuts (const Consensus::Params& consensusParams, std::function<CBlockIndex*(const uint256&)> insertBlockIndex, int trim_below_height)
311343{
312344 std::unique_ptr<CDBIterator> pcursor (NewIterator ());
313345
314346 pcursor->Seek (std::make_pair (DB_BLOCK_INDEX, uint256 ()));
315347
348+ int n_untrimmed = 0 ;
349+ int n_total = 0 ;
350+
316351 // Load m_block_index
317352 while (pcursor->Valid ()) {
318353 if (ShutdownRequested ()) return false ;
@@ -332,19 +367,27 @@ bool CBlockTreeDB::LoadBlockIndexGuts(const Consensus::Params& consensusParams,
332367 pindexNew->nTime = diskindex.nTime ;
333368 pindexNew->nBits = diskindex.nBits ;
334369 pindexNew->nNonce = diskindex.nNonce ;
335- pindexNew->proof = diskindex.proof ;
336370 pindexNew->nStatus = diskindex.nStatus ;
337371 pindexNew->nTx = diskindex.nTx ;
338- pindexNew->m_dynafed_params = diskindex.m_dynafed_params ;
339- pindexNew->m_signblock_witness = diskindex.m_signblock_witness ;
340-
341- const uint256 block_hash = pindexNew->GetBlockHash ();
342- // Only validate one of every 1000 block header for sanity check
343- if (pindexNew->nHeight % 1000 == 0 &&
344- block_hash != consensusParams.hashGenesisBlock &&
345- !CheckProof (pindexNew->GetBlockHeader (), consensusParams)) {
346- return error (" %s: CheckProof: %s, %s" , __func__, block_hash.ToString (), pindexNew->ToString ());
372+
373+ n_total++;
374+ if (diskindex.nHeight >= trim_below_height) {
375+ n_untrimmed++;
376+ pindexNew->proof = diskindex.proof ;
377+ pindexNew->m_dynafed_params = diskindex.m_dynafed_params ;
378+ pindexNew->m_signblock_witness = diskindex.m_signblock_witness ;
379+
380+ const uint256 block_hash = pindexNew->GetBlockHash ();
381+ // Only validate one of every 1000 block header for sanity check
382+ if (pindexNew->nHeight % 1000 == 0 &&
383+ block_hash != consensusParams.hashGenesisBlock &&
384+ !CheckProof (pindexNew->GetBlockHeader (), consensusParams)) {
385+ return error (" %s: CheckProof: %s, %s" , __func__, block_hash.ToString (), pindexNew->ToString ());
386+ }
387+ } else {
388+ pindexNew->m_trimmed = true ;
347389 }
390+
348391 pcursor->Next ();
349392 } else {
350393 return error (" %s: failed to read value" , __func__);
@@ -354,6 +397,7 @@ bool CBlockTreeDB::LoadBlockIndexGuts(const Consensus::Params& consensusParams,
354397 }
355398 }
356399
400+ LogPrintf (" LoadBlockIndexGuts: loaded %d total / %d untrimmed (fully in-memory) headers\n " , n_total, n_untrimmed);
357401 return true ;
358402}
359403
0 commit comments