Skip to content

Commit

Permalink
Make initial block index loading faster (#1420)
Browse files Browse the repository at this point in the history
  • Loading branch information
psolstice authored Mar 11, 2024
1 parent 8bd4abd commit f011c3a
Show file tree
Hide file tree
Showing 2 changed files with 39 additions and 2 deletions.
36 changes: 34 additions & 2 deletions src/txdb.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -356,6 +356,16 @@ bool CBlockTreeDB::LoadBlockIndexGuts(boost::function<CBlockIndex*(const uint256
pcursor->Seek(std::make_pair(DB_BLOCK_INDEX, uint256()));

// Load mapBlockIndex

// We need to check PoW for the last N blocks. To do so we can't just save a pointer to the last block and go back
// from it because of possible forks. This multimap is used to track the most recent blocks (by height) saved in
// the block index on disk
std::multimap<int, CBlockIndex*> lastNBlocks;
// lowest height of all the elements in lastNBlocks
int firstInLastNBlocksHeight = 0;

bool fCheckPoWForAllBlocks = GetBoolArg("-fullblockindexcheck", DEFAULT_FULL_BLOCKINDEX_CHECK);

while (pcursor->Valid()) {
boost::this_thread::interruption_point();
std::pair<char, uint256> key;
Expand Down Expand Up @@ -406,8 +416,22 @@ bool CBlockTreeDB::LoadBlockIndexGuts(boost::function<CBlockIndex*(const uint256

pindexNew->activeDisablingSporks = diskindex.activeDisablingSporks;

if (!CheckProofOfWork(pindexNew->GetBlockPoWHash(), pindexNew->nBits, consensusParams))
return error("LoadBlockIndex(): CheckProofOfWork failed: %s", pindexNew->ToString());
if (fCheckPoWForAllBlocks) {
if (!CheckProofOfWork(pindexNew->GetBlockPoWHash(), pindexNew->nBits, consensusParams))
return error("LoadBlockIndex(): CheckProofOfWork failed: %s", pindexNew->ToString());
}
else {
if (pindexNew->nHeight >= firstInLastNBlocksHeight) {
lastNBlocks.insert(std::pair<int, CBlockIndex*>(pindexNew->nHeight, pindexNew));
if (lastNBlocks.size() > DEFAULT_BLOCKINDEX_NUMBER_OF_BLOCKS_TO_CHECK) {
// pop the first element from the map
auto firstElement = lastNBlocks.begin();
auto elementToPop = firstElement++;
lastNBlocks.erase(elementToPop);
firstInLastNBlocksHeight = firstElement->first;
}
}
}

pcursor->Next();
} else {
Expand All @@ -418,6 +442,14 @@ bool CBlockTreeDB::LoadBlockIndexGuts(boost::function<CBlockIndex*(const uint256
}
}

if (!fCheckPoWForAllBlocks) {
// delayed check for all the blocks
for (const auto &blockIndex: lastNBlocks) {
if (!CheckProofOfWork(blockIndex.second->GetBlockPoWHash(), blockIndex.second->nBits, consensusParams))
return error("LoadBlockIndex(): CheckProofOfWork failed: %s", blockIndex.second->ToString());
}
}

return true;
}

Expand Down
5 changes: 5 additions & 0 deletions src/txdb.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,11 @@ static const int64_t nMaxBlockDBAndTxIndexCache = 1024;
//! Max memory allocated to coin DB specific cache (MiB)
static const int64_t nMaxCoinsDBCache = 8;

//! By default don't check block index PoW on client startup
static const bool DEFAULT_FULL_BLOCKINDEX_CHECK = false;
//! If not doing full check of block index, check only N of the latest blocks
static const int DEFAULT_BLOCKINDEX_NUMBER_OF_BLOCKS_TO_CHECK = 10000;

struct CDiskTxPos : public CDiskBlockPos
{
unsigned int nTxOffset; // after header
Expand Down

0 comments on commit f011c3a

Please sign in to comment.