mirror of
https://github.com/dashpay/dash.git
synced 2024-12-24 19:42:46 +01:00
merge bitcoin#21767: Prune g_chainman usage in auxiliary modules
This commit is contained in:
parent
d577d8bc57
commit
4e9d9a69e8
@ -42,7 +42,7 @@ static void AssembleBlock(benchmark::Bench& bench)
|
||||
|
||||
for (const auto& txr : txs) {
|
||||
TxValidationState state;
|
||||
bool ret{::AcceptToMemoryPool(::ChainstateActive(), *test_setup.m_node.mempool, state, txr, false /* bypass_limits */, /* nAbsurdFee */ 0)};
|
||||
bool ret{::AcceptToMemoryPool(test_setup.m_node.chainman->ActiveChainstate(), *test_setup.m_node.mempool, state, txr, false /* bypass_limits */, /* nAbsurdFee */ 0)};
|
||||
assert(ret);
|
||||
}
|
||||
}
|
||||
|
@ -26,7 +26,8 @@ static void DuplicateInputs(benchmark::Bench& bench)
|
||||
CMutableTransaction coinbaseTx{};
|
||||
CMutableTransaction naughtyTx{};
|
||||
|
||||
CBlockIndex* pindexPrev = ::ChainActive().Tip();
|
||||
assert(std::addressof(::ChainActive()) == std::addressof(test_setup.m_node.chainman->ActiveChain()));
|
||||
CBlockIndex* pindexPrev = test_setup.m_node.chainman->ActiveChain().Tip();
|
||||
assert(pindexPrev != nullptr);
|
||||
block.nBits = GetNextWorkRequired(pindexPrev, &block, chainparams.GetConsensus());
|
||||
block.nNonce = 0;
|
||||
|
@ -59,33 +59,34 @@ bool BaseIndex::Init()
|
||||
}
|
||||
|
||||
LOCK(cs_main);
|
||||
CChain& active_chain = m_chainstate->m_chain;
|
||||
if (locator.IsNull()) {
|
||||
m_best_block_index = nullptr;
|
||||
} else {
|
||||
m_best_block_index = g_chainman.m_blockman.FindForkInGlobalIndex(::ChainActive(), locator);
|
||||
m_best_block_index = m_chainstate->m_blockman.FindForkInGlobalIndex(active_chain, locator);
|
||||
}
|
||||
m_synced = m_best_block_index.load() == ::ChainActive().Tip();
|
||||
m_synced = m_best_block_index.load() == active_chain.Tip();
|
||||
if (!m_synced) {
|
||||
bool prune_violation = false;
|
||||
if (!m_best_block_index) {
|
||||
// index is not built yet
|
||||
// make sure we have all block data back to the genesis
|
||||
const CBlockIndex* block = ::ChainActive().Tip();
|
||||
const CBlockIndex* block = active_chain.Tip();
|
||||
while (block->pprev && (block->pprev->nStatus & BLOCK_HAVE_DATA)) {
|
||||
block = block->pprev;
|
||||
}
|
||||
prune_violation = block != ::ChainActive().Genesis();
|
||||
prune_violation = block != active_chain.Genesis();
|
||||
}
|
||||
// in case the index has a best block set and is not fully synced
|
||||
// check if we have the required blocks to continue building the index
|
||||
else {
|
||||
const CBlockIndex* block_to_test = m_best_block_index.load();
|
||||
if (!ChainActive().Contains(block_to_test)) {
|
||||
if (!active_chain.Contains(block_to_test)) {
|
||||
// if the bestblock is not part of the mainchain, find the fork
|
||||
// and make sure we have all data down to the fork
|
||||
block_to_test = ::ChainActive().FindFork(block_to_test);
|
||||
block_to_test = active_chain.FindFork(block_to_test);
|
||||
}
|
||||
const CBlockIndex* block = ::ChainActive().Tip();
|
||||
const CBlockIndex* block = active_chain.Tip();
|
||||
prune_violation = true;
|
||||
// check backwards from the tip if we have all block data until we reach the indexes bestblock
|
||||
while (block_to_test && block->pprev && (block->pprev->nStatus & BLOCK_HAVE_DATA)) {
|
||||
@ -103,20 +104,20 @@ bool BaseIndex::Init()
|
||||
return true;
|
||||
}
|
||||
|
||||
static const CBlockIndex* NextSyncBlock(const CBlockIndex* pindex_prev) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
|
||||
static const CBlockIndex* NextSyncBlock(const CBlockIndex* pindex_prev, CChain& chain) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
|
||||
{
|
||||
AssertLockHeld(cs_main);
|
||||
|
||||
if (!pindex_prev) {
|
||||
return ::ChainActive().Genesis();
|
||||
return chain.Genesis();
|
||||
}
|
||||
|
||||
const CBlockIndex* pindex = ::ChainActive().Next(pindex_prev);
|
||||
const CBlockIndex* pindex = chain.Next(pindex_prev);
|
||||
if (pindex) {
|
||||
return pindex;
|
||||
}
|
||||
|
||||
return ::ChainActive().Next(::ChainActive().FindFork(pindex_prev));
|
||||
return chain.Next(chain.FindFork(pindex_prev));
|
||||
}
|
||||
|
||||
void BaseIndex::ThreadSync()
|
||||
@ -139,7 +140,7 @@ void BaseIndex::ThreadSync()
|
||||
|
||||
{
|
||||
LOCK(cs_main);
|
||||
const CBlockIndex* pindex_next = NextSyncBlock(pindex);
|
||||
const CBlockIndex* pindex_next = NextSyncBlock(pindex, m_chainstate->m_chain);
|
||||
if (!pindex_next) {
|
||||
m_best_block_index = pindex;
|
||||
m_synced = true;
|
||||
@ -202,7 +203,7 @@ bool BaseIndex::Commit()
|
||||
bool BaseIndex::CommitInternal(CDBBatch& batch)
|
||||
{
|
||||
LOCK(cs_main);
|
||||
GetDB().WriteBestBlock(batch, ::ChainActive().GetLocator(m_best_block_index));
|
||||
GetDB().WriteBestBlock(batch, m_chainstate->m_chain.GetLocator(m_best_block_index));
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -278,7 +279,7 @@ void BaseIndex::ChainStateFlushed(const CBlockLocator& locator)
|
||||
const CBlockIndex* locator_tip_index;
|
||||
{
|
||||
LOCK(cs_main);
|
||||
locator_tip_index = g_chainman.m_blockman.LookupBlockIndex(locator_tip_hash);
|
||||
locator_tip_index = m_chainstate->m_blockman.LookupBlockIndex(locator_tip_hash);
|
||||
}
|
||||
|
||||
if (!locator_tip_index) {
|
||||
@ -319,7 +320,7 @@ bool BaseIndex::BlockUntilSyncedToCurrentChain() const
|
||||
// Skip the queue-draining stuff if we know we're caught up with
|
||||
// ::ChainActive().Tip().
|
||||
LOCK(cs_main);
|
||||
const CBlockIndex* chain_tip = ::ChainActive().Tip();
|
||||
const CBlockIndex* chain_tip = m_chainstate->m_chain.Tip();
|
||||
const CBlockIndex* best_block_index = m_best_block_index.load();
|
||||
if (best_block_index->GetAncestor(chain_tip->nHeight) == chain_tip) {
|
||||
return true;
|
||||
@ -336,8 +337,10 @@ void BaseIndex::Interrupt()
|
||||
m_interrupt();
|
||||
}
|
||||
|
||||
bool BaseIndex::Start()
|
||||
bool BaseIndex::Start(CChainState& active_chainstate)
|
||||
{
|
||||
assert(std::addressof(::ChainstateActive()) == std::addressof(active_chainstate));
|
||||
m_chainstate = &active_chainstate;
|
||||
// Need to register this ValidationInterface before running Init(), so that
|
||||
// callbacks are not missed if Init sets m_synced to true.
|
||||
RegisterValidationInterface(this);
|
||||
|
@ -12,6 +12,7 @@
|
||||
#include <validationinterface.h>
|
||||
|
||||
class CBlockIndex;
|
||||
class CChainState;
|
||||
|
||||
struct IndexSummary {
|
||||
std::string name;
|
||||
@ -75,8 +76,9 @@ private:
|
||||
/// to a chain reorganization), the index must halt until Commit succeeds or else it could end up
|
||||
/// getting corrupted.
|
||||
bool Commit();
|
||||
|
||||
protected:
|
||||
CChainState* m_chainstate{nullptr};
|
||||
|
||||
void BlockConnected(const std::shared_ptr<const CBlock>& block, const CBlockIndex* pindex) override;
|
||||
|
||||
void ChainStateFlushed(const CBlockLocator& locator) override;
|
||||
@ -117,7 +119,7 @@ public:
|
||||
|
||||
/// Start initializes the sync state and registers the instance as a
|
||||
/// ValidationInterface so that it stays in sync with blockchain updates.
|
||||
[[nodiscard]] bool Start();
|
||||
[[nodiscard]] bool Start(CChainState& active_chainstate);
|
||||
|
||||
/// Stops the instance from staying in sync with blockchain updates.
|
||||
void Stop();
|
||||
|
@ -273,7 +273,7 @@ bool CoinStatsIndex::Rewind(const CBlockIndex* current_tip, const CBlockIndex* n
|
||||
|
||||
{
|
||||
LOCK(cs_main);
|
||||
CBlockIndex* iter_tip{g_chainman.m_blockman.LookupBlockIndex(current_tip->GetBlockHash())};
|
||||
CBlockIndex* iter_tip{m_chainstate->m_blockman.LookupBlockIndex(current_tip->GetBlockHash())};
|
||||
const auto& consensus_params{Params().GetConsensus()};
|
||||
|
||||
do {
|
||||
|
@ -204,7 +204,7 @@ bool TxIndex::Init()
|
||||
// Attempt to migrate txindex from the old database to the new one. Even if
|
||||
// chain_tip is null, the node could be reindexing and we still want to
|
||||
// delete txindex records in the old database.
|
||||
if (!m_db->MigrateData(*pblocktree, ::ChainActive().GetLocator())) {
|
||||
if (!m_db->MigrateData(*pblocktree, m_chainstate->m_chain.GetLocator())) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -2186,21 +2186,21 @@ bool AppInitMain(const CoreContext& context, NodeContext& node, interfaces::Bloc
|
||||
// ********************************************************* Step 8: start indexers
|
||||
if (args.GetBoolArg("-txindex", DEFAULT_TXINDEX)) {
|
||||
g_txindex = std::make_unique<TxIndex>(nTxIndexCache, false, fReindex);
|
||||
if (!g_txindex->Start()) {
|
||||
if (!g_txindex->Start(::ChainstateActive())) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
for (const auto& filter_type : g_enabled_filter_types) {
|
||||
InitBlockFilterIndex(filter_type, filter_index_cache, false, fReindex);
|
||||
if (!GetBlockFilterIndex(filter_type)->Start()) {
|
||||
if (!GetBlockFilterIndex(filter_type)->Start(::ChainstateActive())) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
if (args.GetBoolArg("-coinstatsindex", DEFAULT_COINSTATSINDEX)) {
|
||||
g_coin_stats_index = std::make_unique<CoinStatsIndex>(/* cache size */ 0, false, fReindex);
|
||||
if (!g_coin_stats_index->Start()) {
|
||||
if (!g_coin_stats_index->Start(::ChainstateActive())) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
37
src/rest.cpp
37
src/rest.cpp
@ -106,6 +106,27 @@ static CTxMemPool* GetMemPool(const CoreContext& context, HTTPRequest* req)
|
||||
return node_context->mempool.get();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the node context chainstatemanager.
|
||||
*
|
||||
* @param[in] req The HTTP request, whose status code will be set if node
|
||||
* context chainstatemanager is not found.
|
||||
* @returns Pointer to the chainstatemanager or nullptr if none found.
|
||||
*/
|
||||
static ChainstateManager* GetChainman(const CoreContext& context, HTTPRequest* req)
|
||||
{
|
||||
auto node_context = GetContext<NodeContext>(context);
|
||||
if (!node_context || !node_context->chainman) {
|
||||
RESTERR(req, HTTP_INTERNAL_SERVER_ERROR,
|
||||
strprintf("%s:%d (%s)\n"
|
||||
"Internal bug detected: Chainman disabled or instance not found!\n"
|
||||
"You may report this issue here: %s\n",
|
||||
__FILE__, __LINE__, __func__, PACKAGE_BUGREPORT));
|
||||
return nullptr;
|
||||
}
|
||||
return node_context->chainman;
|
||||
}
|
||||
|
||||
static RetFormat ParseDataFormat(std::string& param, const std::string& strReq)
|
||||
{
|
||||
const std::string::size_type pos = strReq.rfind('.');
|
||||
@ -179,7 +200,9 @@ static bool rest_headers(const CoreContext& context,
|
||||
std::vector<const CBlockIndex *> headers;
|
||||
headers.reserve(count);
|
||||
{
|
||||
ChainstateManager& chainman = EnsureAnyChainman(context);
|
||||
ChainstateManager* maybe_chainman = GetChainman(context, req);
|
||||
if (!maybe_chainman) return false;
|
||||
ChainstateManager& chainman = *maybe_chainman;
|
||||
LOCK(cs_main);
|
||||
CChain& active_chain = chainman.ActiveChain();
|
||||
tip = active_chain.Tip();
|
||||
@ -250,7 +273,9 @@ static bool rest_block(const CoreContext& context,
|
||||
CBlockIndex* pblockindex = nullptr;
|
||||
CBlockIndex* tip = nullptr;
|
||||
{
|
||||
ChainstateManager& chainman = EnsureAnyChainman(context);
|
||||
ChainstateManager* maybe_chainman = GetChainman(context, req);
|
||||
if (!maybe_chainman) return false;
|
||||
ChainstateManager& chainman = *maybe_chainman;
|
||||
LOCK(cs_main);
|
||||
tip = chainman.ActiveChain().Tip();
|
||||
pblockindex = chainman.m_blockman.LookupBlockIndex(hash);
|
||||
@ -538,7 +563,9 @@ static bool rest_getutxos(const CoreContext& context, HTTPRequest* req, const st
|
||||
std::string bitmapStringRepresentation;
|
||||
std::vector<bool> hits;
|
||||
bitmap.resize((vOutPoints.size() + 7) / 8);
|
||||
ChainstateManager& chainman = EnsureAnyChainman(context);
|
||||
ChainstateManager* maybe_chainman = GetChainman(context, req);
|
||||
if (!maybe_chainman) return false;
|
||||
ChainstateManager& chainman = *maybe_chainman;
|
||||
{
|
||||
auto process_utxos = [&vOutPoints, &outs, &hits](const CCoinsView& view, const CTxMemPool& mempool) {
|
||||
for (const COutPoint& vOutPoint : vOutPoints) {
|
||||
@ -641,7 +668,9 @@ static bool rest_blockhash_by_height(const CoreContext& context, HTTPRequest* re
|
||||
|
||||
CBlockIndex* pblockindex = nullptr;
|
||||
{
|
||||
ChainstateManager& chainman = EnsureAnyChainman(context);
|
||||
ChainstateManager* maybe_chainman = GetChainman(context, req);
|
||||
if (!maybe_chainman) return false;
|
||||
ChainstateManager& chainman = *maybe_chainman;
|
||||
LOCK(cs_main);
|
||||
const CChain& active_chain = chainman.ActiveChain();
|
||||
if (blockheight > active_chain.Height()) {
|
||||
|
@ -1435,7 +1435,7 @@ static UniValue gettxoutsetinfo(const JSONRPCRequest& request)
|
||||
CCoinsStats prev_stats{hash_type};
|
||||
|
||||
if (pindex->nHeight > 0) {
|
||||
GetUTXOStats(coins_view, WITH_LOCK(::cs_main, return std::ref(g_chainman.m_blockman)), prev_stats, node.rpc_interruption_point, pindex->pprev);
|
||||
GetUTXOStats(coins_view, *blockman, prev_stats, node.rpc_interruption_point, pindex->pprev);
|
||||
}
|
||||
|
||||
UniValue block_info(UniValue::VOBJ);
|
||||
|
@ -138,7 +138,7 @@ BOOST_FIXTURE_TEST_CASE(blockfilter_index_initial_sync, BuildChainTestingSetup)
|
||||
// BlockUntilSyncedToCurrentChain should return false before index is started.
|
||||
BOOST_CHECK(!filter_index.BlockUntilSyncedToCurrentChain());
|
||||
|
||||
BOOST_REQUIRE(filter_index.Start());
|
||||
BOOST_REQUIRE(filter_index.Start(::ChainstateActive()));
|
||||
|
||||
// Allow filter index to catch up with the block index.
|
||||
constexpr int64_t timeout_ms = 10 * 1000;
|
||||
|
@ -32,7 +32,7 @@ BOOST_FIXTURE_TEST_CASE(coinstatsindex_initial_sync, TestChain100Setup)
|
||||
// is started.
|
||||
BOOST_CHECK(!coin_stats_index.BlockUntilSyncedToCurrentChain());
|
||||
|
||||
BOOST_REQUIRE(coin_stats_index.Start());
|
||||
BOOST_REQUIRE(coin_stats_index.Start(::ChainstateActive()));
|
||||
|
||||
// Allow the CoinStatsIndex to catch up with the block index that is syncing
|
||||
// in a background thread.
|
||||
|
@ -7,6 +7,7 @@
|
||||
#include <script/standard.h>
|
||||
#include <test/util/setup_common.h>
|
||||
#include <util/time.h>
|
||||
#include <validation.h>
|
||||
|
||||
#include <boost/test/unit_test.hpp>
|
||||
|
||||
@ -27,7 +28,7 @@ BOOST_FIXTURE_TEST_CASE(txindex_initial_sync, TestChain100Setup)
|
||||
// BlockUntilSyncedToCurrentChain should return false before txindex is started.
|
||||
BOOST_CHECK(!txindex.BlockUntilSyncedToCurrentChain());
|
||||
|
||||
BOOST_REQUIRE(txindex.Start());
|
||||
BOOST_REQUIRE(txindex.Start(::ChainstateActive()));
|
||||
|
||||
// Allow tx index to catch up with the block index.
|
||||
constexpr int64_t timeout_ms = 10 * 1000;
|
||||
|
@ -313,7 +313,7 @@ void TestChainSetup::mineBlocks(int num_blocks)
|
||||
}
|
||||
|
||||
g_txindex = std::make_unique<TxIndex>(1 << 20, true);
|
||||
assert(g_txindex->Start());
|
||||
assert(g_txindex->Start(::ChainstateActive()));
|
||||
|
||||
// Allow tx index to catch up with the block index.
|
||||
constexpr int64_t timeout_ms = 10 * 1000;
|
||||
|
Loading…
Reference in New Issue
Block a user