diff --git a/src/init.cpp b/src/init.cpp --- a/src/init.cpp +++ b/src/init.cpp @@ -270,7 +270,7 @@ // FlushStateToDisk generates a ChainStateFlushed callback, which we should // avoid missing if (pcoinsTip != nullptr) { - FlushStateToDisk(); + ::ChainstateActive().ForceFlushStateToDisk(); } // After there are no more peers/RPC left to give us new data which may @@ -286,7 +286,7 @@ { LOCK(cs_main); if (pcoinsTip != nullptr) { - FlushStateToDisk(); + ::ChainstateActive().ForceFlushStateToDisk(); } pcoinsTip.reset(); pcoinscatcher.reset(); @@ -2491,7 +2491,7 @@ nLocalServices = ServiceFlags(nLocalServices & ~NODE_NETWORK); if (!fReindex) { uiInterface.InitMessage(_("Pruning blockstore...")); - PruneAndFlush(); + ::ChainstateActive().PruneAndFlush(); } } diff --git a/src/rpc/blockchain.cpp b/src/rpc/blockchain.cpp --- a/src/rpc/blockchain.cpp +++ b/src/rpc/blockchain.cpp @@ -1218,7 +1218,7 @@ UniValue ret(UniValue::VOBJ); CCoinsStats stats; - FlushStateToDisk(); + ::ChainstateActive().ForceFlushStateToDisk(); if (GetUTXOStats(pcoinsdbview.get(), stats)) { ret.pushKV("height", int64_t(stats.nHeight)); ret.pushKV("bestblock", stats.hashBlock.GetHex()); @@ -2735,7 +2735,7 @@ std::unique_ptr pcursor; { LOCK(cs_main); - FlushStateToDisk(); + ::ChainstateActive().ForceFlushStateToDisk(); pcursor = std::unique_ptr(pcoinsdbview->Cursor()); assert(pcursor); } diff --git a/src/validation.h b/src/validation.h --- a/src/validation.h +++ b/src/validation.h @@ -36,8 +36,6 @@ #include #include -class arith_uint256; - class CBlockIndex; class CBlockTreeDB; class CChainParams; @@ -425,10 +423,6 @@ */ void UnlinkPrunedFiles(const std::set &setFilesToPrune); -/** Flush all state, indexes and buffers to disk. */ -void FlushStateToDisk(); -/** Prune block files and flush state to disk. */ -void PruneAndFlush(); /** Prune block files up to a given height */ void PruneBlockFilesManual(int nManualPruneHeight); @@ -707,6 +701,9 @@ const CBlockLocator &locator) EXCLUSIVE_LOCKS_REQUIRED(cs_main); +/** @see CChainState::FlushStateToDisk */ +enum class FlushStateMode { NONE, IF_NEEDED, PERIODIC, ALWAYS }; + /** * CChainState stores and provides an API to update our local knowledge of the * current best chain and header tree. @@ -781,6 +778,26 @@ bool LoadBlockIndex(const Config &config, CBlockTreeDB &blocktree) EXCLUSIVE_LOCKS_REQUIRED(cs_main); + /** + * Update the on-disk chain state. + * The caches and indexes are flushed depending on the mode we're called + * with if they're too large, if it's been a while since the last write, or + * always and in all cases if we're in prune mode and are deleting files. + * + * If FlushStateMode::NONE is used, then FlushStateToDisk(...) won't do + * anything besides checking if we need to prune. + */ + bool FlushStateToDisk(const CChainParams &chainparams, + CValidationState &state, FlushStateMode mode, + int nManualPruneHeight = 0); + + //! Unconditionally flush all changes to disk. + void ForceFlushStateToDisk(); + + //! Prune blockfiles from the disk if necessary and then flush chainstate + //! changes if we pruned. + void PruneAndFlush(); + bool ActivateBestChain( const Config &config, CValidationState &state, std::shared_ptr pblock = std::shared_ptr()); diff --git a/src/validation.cpp b/src/validation.cpp --- a/src/validation.cpp +++ b/src/validation.cpp @@ -180,12 +180,7 @@ std::unique_ptr pcoinsTip; std::unique_ptr pblocktree; -enum class FlushStateMode { NONE, IF_NEEDED, PERIODIC, ALWAYS }; - // See definition for documentation -static bool FlushStateToDisk(const CChainParams &chainParams, - CValidationState &state, FlushStateMode mode, - int nManualPruneHeight = 0); static void FindFilesToPruneManual(std::set &setFilesToPrune, int nManualPruneHeight); static void FindFilesToPrune(std::set &setFilesToPrune, @@ -689,8 +684,8 @@ // After we've (potentially) uncached entries, ensure our coins cache is // still within its size limits CValidationState stateDummy; - FlushStateToDisk(config.GetChainParams(), stateDummy, - FlushStateMode::PERIODIC); + ::ChainstateActive().FlushStateToDisk(config.GetChainParams(), stateDummy, + FlushStateMode::PERIODIC); return res; } @@ -1952,18 +1947,9 @@ return true; } -/** - * Update the on-disk chain state. - * The caches and indexes are flushed depending on the mode we're called with if - * they're too large, if it's been a while since the last write, or always and - * in all cases if we're in prune mode and are deleting files. - * - * If FlushStateMode::NONE is used, then FlushStateToDisk(...) won't do anything - * besides checking if we need to prune. - */ -static bool FlushStateToDisk(const CChainParams &chainparams, - CValidationState &state, FlushStateMode mode, - int nManualPruneHeight) { +bool CChainState::FlushStateToDisk(const CChainParams &chainparams, + CValidationState &state, FlushStateMode mode, + int nManualPruneHeight) { int64_t nMempoolUsage = g_mempool.DynamicMemoryUsage(); LOCK(cs_main); static int64_t nLastWrite = 0; @@ -2098,7 +2084,7 @@ if (full_flush_completed) { // Update best block in wallet (so we can detect restored wallets). - GetMainSignals().ChainStateFlushed(::ChainActive().GetLocator()); + GetMainSignals().ChainStateFlushed(m_chain.GetLocator()); } } catch (const std::runtime_error &e) { return AbortNode(state, std::string("System error while flushing: ") + @@ -2107,20 +2093,20 @@ return true; } -void FlushStateToDisk() { +void CChainState::ForceFlushStateToDisk() { CValidationState state; const CChainParams &chainparams = Params(); - if (!FlushStateToDisk(chainparams, state, FlushStateMode::ALWAYS)) { + if (!this->FlushStateToDisk(chainparams, state, FlushStateMode::ALWAYS)) { LogPrintf("%s: failed to flush state (%s)\n", __func__, FormatStateMessage(state)); } } -void PruneAndFlush() { +void CChainState::PruneAndFlush() { CValidationState state; fCheckForPruning = true; const CChainParams &chainparams = Params(); - if (!FlushStateToDisk(chainparams, state, FlushStateMode::NONE)) { + if (!this->FlushStateToDisk(chainparams, state, FlushStateMode::NONE)) { LogPrintf("%s: failed to flush state (%s)\n", __func__, FormatStateMessage(state)); } @@ -4325,8 +4311,8 @@ void PruneBlockFilesManual(int nManualPruneHeight) { CValidationState state; const CChainParams &chainparams = Params(); - if (!FlushStateToDisk(chainparams, state, FlushStateMode::NONE, - nManualPruneHeight)) { + if (!::ChainstateActive().FlushStateToDisk( + chainparams, state, FlushStateMode::NONE, nManualPruneHeight)) { LogPrintf("%s: failed to flush state (%s)\n", __func__, FormatStateMessage(state)); }