Skip to content

Commit 8adb03a

Browse files
sdaftuarsipa
authored andcommitted
Improve RewindBlockIndex when pruning
Pruning nodes that upgrade after segwit activation may not HAVE_DATA for all blocks back to the activation point. Since pruning nodes won't be serving such blocks to peers anyway, don't try to rewind past the HAVE_DATA point, as that would fail and force pruning nodes to redownload the blockchain.
1 parent 7eb0d75 commit 8adb03a

File tree

1 file changed

+15
-1
lines changed

1 file changed

+15
-1
lines changed

src/main.cpp

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4084,6 +4084,14 @@ bool RewindBlockIndex(const CChainParams& params)
40844084
CValidationState state;
40854085
CBlockIndex* pindex = chainActive.Tip();
40864086
while (chainActive.Height() >= nHeight) {
4087+
if (fPruneMode && !(chainActive.Tip()->nStatus & BLOCK_HAVE_DATA)) {
4088+
// If pruning, don't try rewinding past the HAVE_DATA point;
4089+
// since older blocks can't be served anyway, there's
4090+
// no need to walk further, and trying to DisconnectTip()
4091+
// will fail (and require a needless reindex/redownload
4092+
// of the blockchain).
4093+
break;
4094+
}
40874095
if (!DisconnectTip(state, params.GetConsensus(), true)) {
40884096
return error("RewindBlockIndex: unable to disconnect block at height %i", pindex->nHeight);
40894097
}
@@ -4097,7 +4105,13 @@ bool RewindBlockIndex(const CChainParams& params)
40974105
// to disk before writing the chainstate, resulting in a failure to continue if interrupted.
40984106
for (BlockMap::iterator it = mapBlockIndex.begin(); it != mapBlockIndex.end(); it++) {
40994107
CBlockIndex* pindexIter = it->second;
4100-
if (IsWitnessEnabled(pindexIter->pprev, params.GetConsensus()) && !(pindexIter->nStatus & BLOCK_OPT_WITNESS)) {
4108+
4109+
// Note: If we encounter an insufficiently validated block that
4110+
// is on chainActive, it must be because we are a pruning node, and
4111+
// this block or some successor doesn't HAVE_DATA, so we were unable to
4112+
// rewind all the way. Blocks remaining on chainActive at this point
4113+
// must not have their validity reduced.
4114+
if (IsWitnessEnabled(pindexIter->pprev, params.GetConsensus()) && !(pindexIter->nStatus & BLOCK_OPT_WITNESS) && !chainActive.Contains(pindexIter)) {
41014115
// Reduce validity
41024116
pindexIter->nStatus = std::min<unsigned int>(pindexIter->nStatus & BLOCK_VALID_MASK, BLOCK_VALID_TREE) | (pindexIter->nStatus & ~BLOCK_VALID_MASK);
41034117
// Remove have-data flags.

0 commit comments

Comments
 (0)