diff options
author | Pieter Wuille <pieter.wuille@gmail.com> | 2012-08-10 15:13:57 +0200 |
---|---|---|
committer | Pieter Wuille <pieter.wuille@gmail.com> | 2012-10-20 23:08:57 +0200 |
commit | 4fea06db25108e7f72710bf22c3d1896707eeb74 (patch) | |
tree | ef480d212b7da3b484bdb066453e874d2c5c6c84 | |
parent | 13c51f20f619b9001bb6caf225b8cd6c5c2fbb31 (diff) |
Automatically reorganize at startup to best known block
Given that the block tree database (chain.dat) and the active chain
database (coins.dat) are entirely separate now, it becomes legal to
swap one with another instance without affecting the other.
This commit introduces a check in the startup code that detects the
presence of a better chain in chain.dat that has not been activated
yet, and does so efficiently (in batch, while reusing the blk???.dat
files).
-rw-r--r-- | src/db.cpp | 1 | ||||
-rw-r--r-- | src/init.cpp | 34 |
2 files changed, 34 insertions, 1 deletions
diff --git a/src/db.cpp b/src/db.cpp index 06e5543b2e..5ca9ea2c34 100644 --- a/src/db.cpp +++ b/src/db.cpp @@ -636,7 +636,6 @@ bool LoadBlockIndex(CChainDB &chaindb) { if (pindexGenesisBlock == NULL) return true; - return error("CTxDB::LoadBlockIndex() : hashBestChain not loaded"); } hashBestChain = pindexBest->GetBlockHash(); nBestHeight = pindexBest->nHeight; diff --git a/src/init.cpp b/src/init.cpp index b05d57abfe..85aa4f6007 100644 --- a/src/init.cpp +++ b/src/init.cpp @@ -780,6 +780,40 @@ bool AppInit2() // ********************************************************* Step 9: import blocks + // scan for better chains in the block chain database, that are not yet connected in the active best chain + CBlockIndex *pindexFoundBest = pindexBest; + for (std::map<uint256,CBlockIndex*>::iterator it = mapBlockIndex.begin(); it != mapBlockIndex.end(); it++) { + CBlockIndex *pindex = it->second; + if (pindexFoundBest==NULL || pindex->bnChainWork > pindexFoundBest->bnChainWork) + pindexFoundBest = pindex; + } + if (pindexFoundBest != pindexBest) { + uiInterface.InitMessage(_("Importing blocks from block database...")); + uint64 nTxs = 0; + uint64 nBlocks = 0; + std::vector<CBlockIndex*> vAttach; + vAttach.reserve(pindexFoundBest->nHeight - (pindexBest==NULL ? 0 : pindexBest->nHeight)); + while (pindexFoundBest && pindexFoundBest->bnChainWork > (pindexBest==NULL ? 0 : pindexBest->bnChainWork)) { + vAttach.push_back(pindexFoundBest); + pindexFoundBest = pindexFoundBest->pprev; + } + for (std::vector<CBlockIndex*>::reverse_iterator it = vAttach.rbegin(); it != vAttach.rend(); it++) { + CBlockIndex *pindex = *it; + CBlock block; + if (!block.ReadFromDisk(pindex)) + break; + nTxs += block.vtx.size(); + nBlocks++; + if (pindex->nHeight == 0 || nTxs + nBlocks*3 > 500) { + nTxs=0; + nBlocks=0; + block.SetBestChain(pindex); + } + if (fRequestShutdown) + break; + } + } + std::vector<boost::filesystem::path> *vPath = new std::vector<boost::filesystem::path>(); if (mapArgs.count("-loadblock")) { |