diff --git a/src/init.cpp b/src/init.cpp --- a/src/init.cpp +++ b/src/init.cpp @@ -244,8 +244,11 @@ // avoid missing // g_chainstate is referenced here directly (instead of // ::ChainstateActive()) because it may not have been initialized yet. - if (g_chainstate && g_chainstate->CanFlushToDisk()) { - g_chainstate->ForceFlushStateToDisk(); + { + LOCK(cs_main); + if (g_chainstate && g_chainstate->CanFlushToDisk()) { + g_chainstate->ForceFlushStateToDisk(); + } } // After there are no more peers/RPC left to give us new data which may diff --git a/src/rpc/blockchain.cpp b/src/rpc/blockchain.cpp --- a/src/rpc/blockchain.cpp +++ b/src/rpc/blockchain.cpp @@ -1138,7 +1138,10 @@ CCoinsStats stats; ::ChainstateActive().ForceFlushStateToDisk(); - if (GetUTXOStats(&::ChainstateActive().CoinsDB(), stats)) { + + CCoinsView *coins_view = + WITH_LOCK(cs_main, return &ChainstateActive().CoinsDB()); + if (GetUTXOStats(coins_view, stats)) { ret.pushKV("height", int64_t(stats.nHeight)); ret.pushKV("bestblock", stats.hashBlock.GetHex()); ret.pushKV("transactions", int64_t(stats.nTransactions)); diff --git a/src/test/txvalidationcache_tests.cpp b/src/test/txvalidationcache_tests.cpp --- a/src/test/txvalidationcache_tests.cpp +++ b/src/test/txvalidationcache_tests.cpp @@ -232,6 +232,7 @@ { CBlock block = CreateAndProcessBlock({funding_tx}, p2pk_scriptPubKey); BOOST_CHECK(::ChainActive().Tip()->GetBlockHash() == block.GetHash()); + LOCK(cs_main); BOOST_CHECK(::ChainstateActive().CoinsTip().GetBestBlock() == block.GetHash()); } diff --git a/src/txmempool.h b/src/txmempool.h --- a/src/txmempool.h +++ b/src/txmempool.h @@ -736,7 +736,7 @@ * Reduce the size of the mempool by expiring and then trimming the mempool. */ void LimitSize(size_t limit, std::chrono::seconds age) - EXCLUSIVE_LOCKS_REQUIRED(cs); + EXCLUSIVE_LOCKS_REQUIRED(cs, ::cs_main); /** * Calculate the ancestor and descendant count for the given transaction. diff --git a/src/validation.h b/src/validation.h --- a/src/validation.h +++ b/src/validation.h @@ -764,15 +764,15 @@ public: //! The lowest level of the CoinsViews cache hierarchy sits in a leveldb //! database on disk. All unspent coins reside in this store. - CCoinsViewDB m_dbview; + CCoinsViewDB m_dbview GUARDED_BY(cs_main); //! This view wraps access to the leveldb instance and handles read errors //! gracefully. - CCoinsViewErrorCatcher m_catcherview; + CCoinsViewErrorCatcher m_catcherview GUARDED_BY(cs_main); //! This is the top layer of the cache hierarchy - it keeps as many coins in //! memory as can fit per the dbcache setting. - std::unique_ptr m_cacheview; + std::unique_ptr m_cacheview GUARDED_BY(cs_main); //! This constructor initializes CCoinsViewDB and CCoinsViewErrorCatcher //! instances, but it *does not* create a CCoinsViewCache instance by @@ -786,7 +786,7 @@ bool should_wipe); //! Initialize the CCoinsViewCache member. - void InitCache(); + void InitCache() EXCLUSIVE_LOCKS_REQUIRED(::cs_main); }; /** @@ -861,12 +861,12 @@ //! Initialize the in-memory coins cache (to be done after the health of the //! on-disk database is verified). - void InitCoinsCache(); + void InitCoinsCache() EXCLUSIVE_LOCKS_REQUIRED(::cs_main); //! @returns whether or not the CoinsViews object has been fully initialized //! and we can //! safely flush this object to disk. - bool CanFlushToDisk() { + bool CanFlushToDisk() EXCLUSIVE_LOCKS_REQUIRED(cs_main) { return m_coins_views && m_coins_views->m_cacheview; } @@ -882,7 +882,7 @@ std::set setBlockIndexCandidates; //! @returns A reference to the in-memory cache of the UTXO set. - CCoinsViewCache &CoinsTip() { + CCoinsViewCache &CoinsTip() EXCLUSIVE_LOCKS_REQUIRED(cs_main) { assert(m_coins_views->m_cacheview); return *m_coins_views->m_cacheview.get(); } @@ -892,7 +892,8 @@ //! @returns A reference to a wrapped view of the in-memory UTXO set that //! handles disk read errors gracefully. - CCoinsViewErrorCatcher &CoinsErrorCatcher() { + CCoinsViewErrorCatcher &CoinsErrorCatcher() + EXCLUSIVE_LOCKS_REQUIRED(cs_main) { return m_coins_views->m_catcherview; } diff --git a/src/validation.cpp b/src/validation.cpp --- a/src/validation.cpp +++ b/src/validation.cpp @@ -2038,7 +2038,8 @@ } /** Check warning conditions and do some notifications on new chain tip set. */ -static void UpdateTip(const CChainParams ¶ms, CBlockIndex *pindexNew) { +static void UpdateTip(const CChainParams ¶ms, CBlockIndex *pindexNew) + EXCLUSIVE_LOCKS_REQUIRED(::cs_main) { // New best block g_mempool.AddTransactionsUpdated(1);