@@ -206,8 +206,10 @@ class CChainState {
206206 CBlockIndex* FindMostWorkChain () EXCLUSIVE_LOCKS_REQUIRED(cs_main);
207207 void ReceivedBlockTransactions (const CBlock& block, CBlockIndex* pindexNew, const CDiskBlockPos& pos, const Consensus::Params& consensusParams) EXCLUSIVE_LOCKS_REQUIRED(cs_main);
208208
209-
210209 bool RollforwardBlock (const CBlockIndex* pindex, CCoinsViewCache& inputs, const CChainParams& params) EXCLUSIVE_LOCKS_REQUIRED(cs_main);
210+
211+ // ! Mark a block as not having block data
212+ void EraseBlockData (CBlockIndex* index) EXCLUSIVE_LOCKS_REQUIRED(cs_main);
211213} g_chainstate;
212214
213215/* *
@@ -4168,6 +4170,42 @@ bool ReplayBlocks(const CChainParams& params, CCoinsView* view) {
41684170 return g_chainstate.ReplayBlocks (params, view);
41694171}
41704172
4173+ // ! Helper for CChainState::RewindBlockIndex
4174+ void CChainState::EraseBlockData (CBlockIndex* index)
4175+ {
4176+ AssertLockHeld (cs_main);
4177+ assert (!chainActive.Contains (index)); // Make sure this block isn't active
4178+
4179+ // Reduce validity
4180+ index->nStatus = std::min<unsigned int >(index->nStatus & BLOCK_VALID_MASK, BLOCK_VALID_TREE) | (index->nStatus & ~BLOCK_VALID_MASK);
4181+ // Remove have-data flags.
4182+ index->nStatus &= ~(BLOCK_HAVE_DATA | BLOCK_HAVE_UNDO);
4183+ // Remove storage location.
4184+ index->nFile = 0 ;
4185+ index->nDataPos = 0 ;
4186+ index->nUndoPos = 0 ;
4187+ // Remove various other things
4188+ index->nTx = 0 ;
4189+ index->nChainTx = 0 ;
4190+ index->nSequenceId = 0 ;
4191+ // Make sure it gets written.
4192+ setDirtyBlockIndex.insert (index);
4193+ // Update indexes
4194+ setBlockIndexCandidates.erase (index);
4195+ std::pair<std::multimap<CBlockIndex*, CBlockIndex*>::iterator, std::multimap<CBlockIndex*, CBlockIndex*>::iterator> ret = mapBlocksUnlinked.equal_range (index->pprev );
4196+ while (ret.first != ret.second ) {
4197+ if (ret.first ->second == index) {
4198+ mapBlocksUnlinked.erase (ret.first ++);
4199+ } else {
4200+ ++ret.first ;
4201+ }
4202+ }
4203+ // Mark parent as eligible for main chain again
4204+ if (index->pprev && index->pprev ->IsValid (BLOCK_VALID_TRANSACTIONS) && index->pprev ->HaveTxsDownloaded ()) {
4205+ setBlockIndexCandidates.insert (index->pprev );
4206+ }
4207+ }
4208+
41714209bool CChainState::RewindBlockIndex (const CChainParams& params)
41724210{
41734211 LOCK (cs_main);
@@ -4219,32 +4257,7 @@ bool CChainState::RewindBlockIndex(const CChainParams& params)
42194257 // rewind all the way. Blocks remaining on chainActive at this point
42204258 // must not have their validity reduced.
42214259 if (IsWitnessEnabled (pindexIter->pprev , params.GetConsensus ()) && !(pindexIter->nStatus & BLOCK_OPT_WITNESS) && !chainActive.Contains (pindexIter)) {
4222- // Reduce validity
4223- pindexIter->nStatus = std::min<unsigned int >(pindexIter->nStatus & BLOCK_VALID_MASK, BLOCK_VALID_TREE) | (pindexIter->nStatus & ~BLOCK_VALID_MASK);
4224- // Remove have-data flags.
4225- pindexIter->nStatus &= ~(BLOCK_HAVE_DATA | BLOCK_HAVE_UNDO);
4226- // Remove storage location.
4227- pindexIter->nFile = 0 ;
4228- pindexIter->nDataPos = 0 ;
4229- pindexIter->nUndoPos = 0 ;
4230- // Remove various other things
4231- pindexIter->nTx = 0 ;
4232- pindexIter->nChainTx = 0 ;
4233- pindexIter->nSequenceId = 0 ;
4234- // Make sure it gets written.
4235- setDirtyBlockIndex.insert (pindexIter);
4236- // Update indexes
4237- setBlockIndexCandidates.erase (pindexIter);
4238- std::pair<std::multimap<CBlockIndex*, CBlockIndex*>::iterator, std::multimap<CBlockIndex*, CBlockIndex*>::iterator> ret = mapBlocksUnlinked.equal_range (pindexIter->pprev );
4239- while (ret.first != ret.second ) {
4240- if (ret.first ->second == pindexIter) {
4241- mapBlocksUnlinked.erase (ret.first ++);
4242- } else {
4243- ++ret.first ;
4244- }
4245- }
4246- } else if (pindexIter->IsValid (BLOCK_VALID_TRANSACTIONS) && pindexIter->HaveTxsDownloaded ()) {
4247- setBlockIndexCandidates.insert (pindexIter);
4260+ EraseBlockData (pindexIter);
42484261 }
42494262 }
42504263
0 commit comments