mirror of
https://github.com/bitcoin/bitcoin.git
synced 2025-04-09 04:39:08 +02:00
refactor: De-globalize g_signals
This commit is contained in:
parent
473dd4b97a
commit
84f5c135b8
@ -39,7 +39,8 @@ static void WalletBalance(benchmark::Bench& bench, const bool set_dirty, const b
|
||||
generatetoaddress(test_setup->m_node, address_mine.value_or(ADDRESS_WATCHONLY));
|
||||
generatetoaddress(test_setup->m_node, ADDRESS_WATCHONLY);
|
||||
}
|
||||
SyncWithValidationInterfaceQueue();
|
||||
// Calls SyncWithValidationInterfaceQueue
|
||||
wallet.chain().waitForNotificationsIfTipChanged(uint256::ZERO);
|
||||
|
||||
auto bal = GetBalance(wallet); // Cache
|
||||
|
||||
|
@ -74,10 +74,12 @@ int main(int argc, char* argv[])
|
||||
// Start the lightweight task scheduler thread
|
||||
scheduler.m_service_thread = std::thread(util::TraceThread, "scheduler", [&] { scheduler.serviceQueue(); });
|
||||
|
||||
CMainSignals validation_signals{};
|
||||
|
||||
// Gather some entropy once per minute.
|
||||
scheduler.scheduleEvery(RandAddPeriodic, std::chrono::minutes{1});
|
||||
|
||||
GetMainSignals().RegisterBackgroundSignalScheduler(scheduler);
|
||||
validation_signals.RegisterBackgroundSignalScheduler(scheduler);
|
||||
|
||||
class KernelNotifications : public kernel::Notifications
|
||||
{
|
||||
@ -118,7 +120,7 @@ int main(int argc, char* argv[])
|
||||
.chainparams = *chainparams,
|
||||
.datadir = abs_datadir,
|
||||
.notifications = *notifications,
|
||||
.signals = &GetMainSignals(),
|
||||
.signals = &validation_signals,
|
||||
};
|
||||
const node::BlockManager::Options blockman_opts{
|
||||
.chainparams = chainman_opts.chainparams,
|
||||
@ -236,9 +238,9 @@ int main(int argc, char* argv[])
|
||||
|
||||
bool new_block;
|
||||
auto sc = std::make_shared<submitblock_StateCatcher>(block.GetHash());
|
||||
RegisterSharedValidationInterface(sc);
|
||||
validation_signals.RegisterSharedValidationInterface(sc);
|
||||
bool accepted = chainman.ProcessNewBlock(blockptr, /*force_processing=*/true, /*min_pow_checked=*/true, /*new_block=*/&new_block);
|
||||
UnregisterSharedValidationInterface(sc);
|
||||
validation_signals.UnregisterSharedValidationInterface(sc);
|
||||
if (!new_block && accepted) {
|
||||
std::cerr << "duplicate" << std::endl;
|
||||
break;
|
||||
@ -291,7 +293,7 @@ epilogue:
|
||||
scheduler.stop();
|
||||
if (chainman.m_thread_load.joinable()) chainman.m_thread_load.join();
|
||||
|
||||
GetMainSignals().FlushBackgroundCallbacks();
|
||||
validation_signals.FlushBackgroundCallbacks();
|
||||
{
|
||||
LOCK(cs_main);
|
||||
for (Chainstate* chainstate : chainman.GetAll()) {
|
||||
@ -301,5 +303,5 @@ epilogue:
|
||||
}
|
||||
}
|
||||
}
|
||||
GetMainSignals().UnregisterBackgroundSignalScheduler();
|
||||
validation_signals.UnregisterBackgroundSignalScheduler();
|
||||
}
|
||||
|
@ -89,7 +89,7 @@ bool BaseIndex::Init()
|
||||
return &m_chain->context()->chainman->GetChainstateForIndexing());
|
||||
// Register to validation interface before setting the 'm_synced' flag, so that
|
||||
// callbacks are not missed once m_synced is true.
|
||||
RegisterValidationInterface(this);
|
||||
m_chain->context()->validation_signals->RegisterValidationInterface(this);
|
||||
|
||||
CBlockLocator locator;
|
||||
if (!GetDB().ReadBestBlock(locator)) {
|
||||
@ -380,7 +380,7 @@ bool BaseIndex::BlockUntilSyncedToCurrentChain() const
|
||||
}
|
||||
|
||||
LogPrintf("%s: %s is catching up on block notifications\n", __func__, GetName());
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_chain->context()->validation_signals->SyncWithValidationInterfaceQueue();
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -399,7 +399,9 @@ bool BaseIndex::StartBackgroundSync()
|
||||
|
||||
void BaseIndex::Stop()
|
||||
{
|
||||
UnregisterValidationInterface(this);
|
||||
if (m_chain->context()->validation_signals) {
|
||||
m_chain->context()->validation_signals->UnregisterValidationInterface(this);
|
||||
}
|
||||
|
||||
if (m_thread_sync.joinable()) {
|
||||
m_thread_sync.join();
|
||||
|
34
src/init.cpp
34
src/init.cpp
@ -291,7 +291,7 @@ void Shutdown(NodeContext& node)
|
||||
|
||||
// Because these depend on each-other, we make sure that neither can be
|
||||
// using the other before destroying them.
|
||||
if (node.peerman) UnregisterValidationInterface(node.peerman.get());
|
||||
if (node.peerman && node.validation_signals) node.validation_signals->UnregisterValidationInterface(node.peerman.get());
|
||||
if (node.connman) node.connman->Stop();
|
||||
|
||||
StopTorControl();
|
||||
@ -317,7 +317,9 @@ void Shutdown(NodeContext& node)
|
||||
// fee estimator from validation interface.
|
||||
if (node.fee_estimator) {
|
||||
node.fee_estimator->Flush();
|
||||
UnregisterValidationInterface(node.fee_estimator.get());
|
||||
if (node.validation_signals) {
|
||||
node.validation_signals->UnregisterValidationInterface(node.fee_estimator.get());
|
||||
}
|
||||
}
|
||||
|
||||
// FlushStateToDisk generates a ChainStateFlushed callback, which we should avoid missing
|
||||
@ -332,7 +334,7 @@ void Shutdown(NodeContext& node)
|
||||
|
||||
// After there are no more peers/RPC left to give us new data which may generate
|
||||
// CValidationInterface callbacks, flush them...
|
||||
GetMainSignals().FlushBackgroundCallbacks();
|
||||
if (node.validation_signals) node.validation_signals->FlushBackgroundCallbacks();
|
||||
|
||||
// Stop and delete all indexes only after flushing background callbacks.
|
||||
if (g_txindex) {
|
||||
@ -367,17 +369,20 @@ void Shutdown(NodeContext& node)
|
||||
|
||||
#if ENABLE_ZMQ
|
||||
if (g_zmq_notification_interface) {
|
||||
UnregisterValidationInterface(g_zmq_notification_interface.get());
|
||||
if (node.validation_signals) node.validation_signals->UnregisterValidationInterface(g_zmq_notification_interface.get());
|
||||
g_zmq_notification_interface.reset();
|
||||
}
|
||||
#endif
|
||||
|
||||
node.chain_clients.clear();
|
||||
UnregisterAllValidationInterfaces();
|
||||
GetMainSignals().UnregisterBackgroundSignalScheduler();
|
||||
if (node.validation_signals) {
|
||||
node.validation_signals->UnregisterAllValidationInterfaces();
|
||||
node.validation_signals->UnregisterBackgroundSignalScheduler();
|
||||
}
|
||||
node.mempool.reset();
|
||||
node.fee_estimator.reset();
|
||||
node.chainman.reset();
|
||||
node.validation_signals.reset();
|
||||
node.scheduler.reset();
|
||||
node.kernel.reset();
|
||||
|
||||
@ -1158,7 +1163,10 @@ bool AppInitMain(NodeContext& node, interfaces::BlockAndHeaderTipInfo* tip_info)
|
||||
}
|
||||
}, std::chrono::minutes{5});
|
||||
|
||||
GetMainSignals().RegisterBackgroundSignalScheduler(*node.scheduler);
|
||||
assert(!node.validation_signals);
|
||||
node.validation_signals = std::make_unique<CMainSignals>();
|
||||
auto& validation_signals = *node.validation_signals;
|
||||
validation_signals.RegisterBackgroundSignalScheduler(*node.scheduler);
|
||||
|
||||
// Create client interfaces for wallets that are supposed to be loaded
|
||||
// according to -wallet and -disablewallet options. This only constructs
|
||||
@ -1264,7 +1272,7 @@ bool AppInitMain(NodeContext& node, interfaces::BlockAndHeaderTipInfo* tip_info)
|
||||
// Flush estimates to disk periodically
|
||||
CBlockPolicyEstimator* fee_estimator = node.fee_estimator.get();
|
||||
node.scheduler->scheduleEvery([fee_estimator] { fee_estimator->FlushFeeEstimates(); }, FEE_FLUSH_INTERVAL);
|
||||
RegisterValidationInterface(fee_estimator);
|
||||
validation_signals.RegisterValidationInterface(fee_estimator);
|
||||
}
|
||||
|
||||
// Check port numbers
|
||||
@ -1435,7 +1443,7 @@ bool AppInitMain(NodeContext& node, interfaces::BlockAndHeaderTipInfo* tip_info)
|
||||
});
|
||||
|
||||
if (g_zmq_notification_interface) {
|
||||
RegisterValidationInterface(g_zmq_notification_interface.get());
|
||||
validation_signals.RegisterValidationInterface(g_zmq_notification_interface.get());
|
||||
}
|
||||
#endif
|
||||
|
||||
@ -1449,7 +1457,7 @@ bool AppInitMain(NodeContext& node, interfaces::BlockAndHeaderTipInfo* tip_info)
|
||||
.chainparams = chainparams,
|
||||
.datadir = args.GetDataDirNet(),
|
||||
.notifications = *node.notifications,
|
||||
.signals = &GetMainSignals(),
|
||||
.signals = &validation_signals,
|
||||
};
|
||||
Assert(ApplyArgsManOptions(args, chainman_opts)); // no error can happen, already checked in AppInitParameterInteraction
|
||||
|
||||
@ -1479,7 +1487,7 @@ bool AppInitMain(NodeContext& node, interfaces::BlockAndHeaderTipInfo* tip_info)
|
||||
|
||||
CTxMemPool::Options mempool_opts{
|
||||
.check_ratio = chainparams.DefaultConsistencyChecks() ? 1 : 0,
|
||||
.signals = &GetMainSignals(),
|
||||
.signals = &validation_signals,
|
||||
};
|
||||
auto result{ApplyArgsManOptions(args, chainparams, mempool_opts)};
|
||||
if (!result) {
|
||||
@ -1507,7 +1515,7 @@ bool AppInitMain(NodeContext& node, interfaces::BlockAndHeaderTipInfo* tip_info)
|
||||
|
||||
// Drain the validation interface queue to ensure that the old indexes
|
||||
// don't have any pending work.
|
||||
SyncWithValidationInterfaceQueue();
|
||||
Assert(node.validation_signals)->SyncWithValidationInterfaceQueue();
|
||||
|
||||
for (auto* index : node.indexes) {
|
||||
index->Interrupt();
|
||||
@ -1596,7 +1604,7 @@ bool AppInitMain(NodeContext& node, interfaces::BlockAndHeaderTipInfo* tip_info)
|
||||
node.peerman = PeerManager::make(*node.connman, *node.addrman,
|
||||
node.banman.get(), chainman,
|
||||
*node.mempool, peerman_opts);
|
||||
RegisterValidationInterface(node.peerman.get());
|
||||
validation_signals.RegisterValidationInterface(node.peerman.get());
|
||||
|
||||
// ********************************************************* Step 8: start indexers
|
||||
|
||||
|
@ -20,6 +20,7 @@ class BanMan;
|
||||
class BaseIndex;
|
||||
class CBlockPolicyEstimator;
|
||||
class CConnman;
|
||||
class CMainSignals;
|
||||
class CScheduler;
|
||||
class CTxMemPool;
|
||||
class ChainstateManager;
|
||||
@ -70,7 +71,10 @@ struct NodeContext {
|
||||
interfaces::WalletLoader* wallet_loader{nullptr};
|
||||
std::unique_ptr<CScheduler> scheduler;
|
||||
std::function<void()> rpc_interruption_point = [] {};
|
||||
//! Issues blocking calls about sync status, errors and warnings
|
||||
std::unique_ptr<KernelNotifications> notifications;
|
||||
//! Issues calls about blocks and transactions
|
||||
std::unique_ptr<CMainSignals> validation_signals;
|
||||
std::atomic<int> exit_status{EXIT_SUCCESS};
|
||||
|
||||
//! Declare default constructor and destructor that are not inline, so code
|
||||
|
@ -460,19 +460,20 @@ public:
|
||||
class NotificationsHandlerImpl : public Handler
|
||||
{
|
||||
public:
|
||||
explicit NotificationsHandlerImpl(std::shared_ptr<Chain::Notifications> notifications)
|
||||
: m_proxy(std::make_shared<NotificationsProxy>(std::move(notifications)))
|
||||
explicit NotificationsHandlerImpl(CMainSignals& signals, std::shared_ptr<Chain::Notifications> notifications)
|
||||
: m_signals{signals}, m_proxy{std::make_shared<NotificationsProxy>(std::move(notifications))}
|
||||
{
|
||||
RegisterSharedValidationInterface(m_proxy);
|
||||
m_signals.RegisterSharedValidationInterface(m_proxy);
|
||||
}
|
||||
~NotificationsHandlerImpl() override { disconnect(); }
|
||||
void disconnect() override
|
||||
{
|
||||
if (m_proxy) {
|
||||
UnregisterSharedValidationInterface(m_proxy);
|
||||
m_signals.UnregisterSharedValidationInterface(m_proxy);
|
||||
m_proxy.reset();
|
||||
}
|
||||
}
|
||||
CMainSignals& m_signals;
|
||||
std::shared_ptr<NotificationsProxy> m_proxy;
|
||||
};
|
||||
|
||||
@ -761,12 +762,12 @@ public:
|
||||
}
|
||||
std::unique_ptr<Handler> handleNotifications(std::shared_ptr<Notifications> notifications) override
|
||||
{
|
||||
return std::make_unique<NotificationsHandlerImpl>(std::move(notifications));
|
||||
return std::make_unique<NotificationsHandlerImpl>(validation_signals(), std::move(notifications));
|
||||
}
|
||||
void waitForNotificationsIfTipChanged(const uint256& old_tip) override
|
||||
{
|
||||
if (!old_tip.IsNull() && old_tip == WITH_LOCK(::cs_main, return chainman().ActiveChain().Tip()->GetBlockHash())) return;
|
||||
SyncWithValidationInterfaceQueue();
|
||||
validation_signals().SyncWithValidationInterfaceQueue();
|
||||
}
|
||||
std::unique_ptr<Handler> handleRpc(const CRPCCommand& command) override
|
||||
{
|
||||
@ -822,6 +823,7 @@ public:
|
||||
NodeContext* context() override { return &m_node; }
|
||||
ArgsManager& args() { return *Assert(m_node.args); }
|
||||
ChainstateManager& chainman() { return *Assert(m_node.chainman); }
|
||||
CMainSignals& validation_signals() { return *Assert(m_node.validation_signals); }
|
||||
NodeContext& m_node;
|
||||
};
|
||||
} // namespace
|
||||
|
@ -92,7 +92,7 @@ TransactionError BroadcastTransaction(NodeContext& node, const CTransactionRef t
|
||||
node.mempool->AddUnbroadcastTx(txid);
|
||||
}
|
||||
|
||||
if (wait_callback) {
|
||||
if (wait_callback && node.validation_signals) {
|
||||
// For transactions broadcast from outside the wallet, make sure
|
||||
// that the wallet has been notified of the transaction before
|
||||
// continuing.
|
||||
@ -101,7 +101,7 @@ TransactionError BroadcastTransaction(NodeContext& node, const CTransactionRef t
|
||||
// with a transaction to/from their wallet, immediately call some
|
||||
// wallet RPC, and get a stale result because callbacks have not
|
||||
// yet been processed.
|
||||
CallFunctionInValidationInterfaceQueue([&promise] {
|
||||
node.validation_signals->CallFunctionInValidationInterfaceQueue([&promise] {
|
||||
promise.set_value();
|
||||
});
|
||||
callback_set = true;
|
||||
|
@ -395,7 +395,8 @@ static RPCHelpMan syncwithvalidationinterfacequeue()
|
||||
},
|
||||
[&](const RPCHelpMan& self, const JSONRPCRequest& request) -> UniValue
|
||||
{
|
||||
SyncWithValidationInterfaceQueue();
|
||||
NodeContext& node = EnsureAnyNodeContext(request.context);
|
||||
CHECK_NONFATAL(node.validation_signals)->SyncWithValidationInterfaceQueue();
|
||||
return UniValue::VNULL;
|
||||
},
|
||||
};
|
||||
|
@ -4,6 +4,7 @@
|
||||
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
|
||||
|
||||
#include <core_io.h>
|
||||
#include <node/context.h>
|
||||
#include <policy/feerate.h>
|
||||
#include <policy/fees.h>
|
||||
#include <rpc/protocol.h>
|
||||
@ -21,10 +22,6 @@
|
||||
#include <cmath>
|
||||
#include <string>
|
||||
|
||||
namespace node {
|
||||
struct NodeContext;
|
||||
}
|
||||
|
||||
using node::NodeContext;
|
||||
|
||||
static RPCHelpMan estimatesmartfee()
|
||||
@ -68,7 +65,7 @@ static RPCHelpMan estimatesmartfee()
|
||||
const NodeContext& node = EnsureAnyNodeContext(request.context);
|
||||
const CTxMemPool& mempool = EnsureMemPool(node);
|
||||
|
||||
SyncWithValidationInterfaceQueue();
|
||||
CHECK_NONFATAL(mempool.m_signals)->SyncWithValidationInterfaceQueue();
|
||||
unsigned int max_target = fee_estimator.HighestTargetTracked(FeeEstimateHorizon::LONG_HALFLIFE);
|
||||
unsigned int conf_target = ParseConfirmTarget(request.params[0], max_target);
|
||||
bool conservative = true;
|
||||
@ -156,8 +153,9 @@ static RPCHelpMan estimaterawfee()
|
||||
[&](const RPCHelpMan& self, const JSONRPCRequest& request) -> UniValue
|
||||
{
|
||||
CBlockPolicyEstimator& fee_estimator = EnsureAnyFeeEstimator(request.context);
|
||||
const NodeContext& node = EnsureAnyNodeContext(request.context);
|
||||
|
||||
SyncWithValidationInterfaceQueue();
|
||||
CHECK_NONFATAL(node.validation_signals)->SyncWithValidationInterfaceQueue();
|
||||
unsigned int max_target = fee_estimator.HighestTargetTracked(FeeEstimateHorizon::LONG_HALFLIFE);
|
||||
unsigned int conf_target = ParseConfirmTarget(request.params[0], max_target);
|
||||
double threshold = 0.95;
|
||||
|
@ -1038,9 +1038,9 @@ static RPCHelpMan submitblock()
|
||||
|
||||
bool new_block;
|
||||
auto sc = std::make_shared<submitblock_StateCatcher>(block.GetHash());
|
||||
RegisterSharedValidationInterface(sc);
|
||||
CHECK_NONFATAL(chainman.m_options.signals)->RegisterSharedValidationInterface(sc);
|
||||
bool accepted = chainman.ProcessNewBlock(blockptr, /*force_processing=*/true, /*min_pow_checked=*/true, /*new_block=*/&new_block);
|
||||
UnregisterSharedValidationInterface(sc);
|
||||
CHECK_NONFATAL(chainman.m_options.signals)->UnregisterSharedValidationInterface(sc);
|
||||
if (!new_block && accepted) {
|
||||
return "duplicate";
|
||||
}
|
||||
|
@ -90,7 +90,7 @@ static RPCHelpMan mockscheduler()
|
||||
|
||||
const NodeContext& node_context{EnsureAnyNodeContext(request.context)};
|
||||
CHECK_NONFATAL(node_context.scheduler)->MockForward(std::chrono::seconds{delta_seconds});
|
||||
SyncWithValidationInterfaceQueue();
|
||||
CHECK_NONFATAL(node_context.validation_signals)->SyncWithValidationInterfaceQueue();
|
||||
for (const auto& chain_client : node_context.chain_clients) {
|
||||
chain_client->schedulerMockForward(std::chrono::seconds(delta_seconds));
|
||||
}
|
||||
|
@ -70,7 +70,7 @@ BOOST_FIXTURE_TEST_CASE(coinstatsindex_initial_sync, TestChain100Setup)
|
||||
// SyncWithValidationInterfaceQueue() call below is also needed to ensure
|
||||
// TSAN always sees the test thread waiting for the notification thread, and
|
||||
// avoid potential false positive reports.
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
|
||||
// Shutdown sequence (c.f. Shutdown() in init.cpp)
|
||||
coin_stats_index.Stop();
|
||||
|
@ -47,7 +47,7 @@ void initialize_tx_pool()
|
||||
g_outpoints_coinbase_init_mature.push_back(prevout);
|
||||
}
|
||||
}
|
||||
SyncWithValidationInterfaceQueue();
|
||||
g_setup->m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
}
|
||||
|
||||
struct OutpointsUpdater final : public CValidationInterface {
|
||||
@ -147,7 +147,7 @@ FUZZ_TARGET(tx_package_eval, .init = initialize_tx_pool)
|
||||
}
|
||||
|
||||
auto outpoints_updater = std::make_shared<OutpointsUpdater>(mempool_outpoints);
|
||||
RegisterSharedValidationInterface(outpoints_updater);
|
||||
node.validation_signals->RegisterSharedValidationInterface(outpoints_updater);
|
||||
|
||||
CTxMemPool tx_pool_{MakeMempool(fuzzed_data_provider, node)};
|
||||
MockedTxPool& tx_pool = *static_cast<MockedTxPool*>(&tx_pool_);
|
||||
@ -269,7 +269,7 @@ FUZZ_TARGET(tx_package_eval, .init = initialize_tx_pool)
|
||||
// Remember all added transactions
|
||||
std::set<CTransactionRef> added;
|
||||
auto txr = std::make_shared<TransactionsDelta>(added);
|
||||
RegisterSharedValidationInterface(txr);
|
||||
node.validation_signals->RegisterSharedValidationInterface(txr);
|
||||
|
||||
// When there are multiple transactions in the package, we call ProcessNewPackage(txs, test_accept=false)
|
||||
// and AcceptToMemoryPool(txs.back(), test_accept=true). When there is only 1 transaction, we might flip it
|
||||
@ -285,8 +285,8 @@ FUZZ_TARGET(tx_package_eval, .init = initialize_tx_pool)
|
||||
/*bypass_limits=*/false, /*test_accept=*/!single_submit));
|
||||
const bool passed = res.m_result_type == MempoolAcceptResult::ResultType::VALID;
|
||||
|
||||
SyncWithValidationInterfaceQueue();
|
||||
UnregisterSharedValidationInterface(txr);
|
||||
node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
node.validation_signals->UnregisterSharedValidationInterface(txr);
|
||||
|
||||
// There is only 1 transaction in the package. We did a test-package-accept and a ATMP
|
||||
if (single_submit) {
|
||||
@ -310,7 +310,7 @@ FUZZ_TARGET(tx_package_eval, .init = initialize_tx_pool)
|
||||
CheckMempoolV3Invariants(tx_pool);
|
||||
}
|
||||
|
||||
UnregisterSharedValidationInterface(outpoints_updater);
|
||||
node.validation_signals->UnregisterSharedValidationInterface(outpoints_updater);
|
||||
|
||||
WITH_LOCK(::cs_main, tx_pool.check(chainstate.CoinsTip(), chainstate.m_chain.Height() + 1));
|
||||
}
|
||||
|
@ -47,7 +47,7 @@ void initialize_process_message()
|
||||
for (int i = 0; i < 2 * COINBASE_MATURITY; i++) {
|
||||
MineBlock(g_setup->m_node, CScript() << OP_TRUE);
|
||||
}
|
||||
SyncWithValidationInterfaceQueue();
|
||||
g_setup->m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
}
|
||||
|
||||
FUZZ_TARGET(process_message, .init = initialize_process_message)
|
||||
@ -89,6 +89,6 @@ FUZZ_TARGET(process_message, .init = initialize_process_message)
|
||||
}
|
||||
g_setup->m_node.peerman->SendMessages(&p2p_node);
|
||||
}
|
||||
SyncWithValidationInterfaceQueue();
|
||||
g_setup->m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
g_setup->m_node.connman->StopNodes();
|
||||
}
|
||||
|
@ -37,7 +37,7 @@ void initialize_process_messages()
|
||||
for (int i = 0; i < 2 * COINBASE_MATURITY; i++) {
|
||||
MineBlock(g_setup->m_node, CScript() << OP_TRUE);
|
||||
}
|
||||
SyncWithValidationInterfaceQueue();
|
||||
g_setup->m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
}
|
||||
|
||||
FUZZ_TARGET(process_messages, .init = initialize_process_messages)
|
||||
@ -89,6 +89,6 @@ FUZZ_TARGET(process_messages, .init = initialize_process_messages)
|
||||
g_setup->m_node.peerman->SendMessages(&random_node);
|
||||
}
|
||||
}
|
||||
SyncWithValidationInterfaceQueue();
|
||||
g_setup->m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
g_setup->m_node.connman->StopNodes();
|
||||
}
|
||||
|
@ -50,7 +50,7 @@ void initialize_tx_pool()
|
||||
g_outpoints_coinbase_init_immature;
|
||||
outpoints.push_back(prevout);
|
||||
}
|
||||
SyncWithValidationInterfaceQueue();
|
||||
g_setup->m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
}
|
||||
|
||||
struct TransactionsDelta final : public CValidationInterface {
|
||||
@ -105,7 +105,7 @@ void Finish(FuzzedDataProvider& fuzzed_data_provider, MockedTxPool& tx_pool, Cha
|
||||
assert(tx_pool.size() < info_all.size());
|
||||
WITH_LOCK(::cs_main, tx_pool.check(chainstate.CoinsTip(), chainstate.m_chain.Height() + 1));
|
||||
}
|
||||
SyncWithValidationInterfaceQueue();
|
||||
g_setup->m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
}
|
||||
|
||||
void MockTime(FuzzedDataProvider& fuzzed_data_provider, const Chainstate& chainstate)
|
||||
@ -285,7 +285,7 @@ FUZZ_TARGET(tx_pool_standard, .init = initialize_tx_pool)
|
||||
std::set<CTransactionRef> removed;
|
||||
std::set<CTransactionRef> added;
|
||||
auto txr = std::make_shared<TransactionsDelta>(removed, added);
|
||||
RegisterSharedValidationInterface(txr);
|
||||
node.validation_signals->RegisterSharedValidationInterface(txr);
|
||||
const bool bypass_limits = fuzzed_data_provider.ConsumeBool();
|
||||
|
||||
// Make sure ProcessNewPackage on one transaction works.
|
||||
@ -303,8 +303,8 @@ FUZZ_TARGET(tx_pool_standard, .init = initialize_tx_pool)
|
||||
|
||||
const auto res = WITH_LOCK(::cs_main, return AcceptToMemoryPool(chainstate, tx, GetTime(), bypass_limits, /*test_accept=*/false));
|
||||
const bool accepted = res.m_result_type == MempoolAcceptResult::ResultType::VALID;
|
||||
SyncWithValidationInterfaceQueue();
|
||||
UnregisterSharedValidationInterface(txr);
|
||||
node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
node.validation_signals->UnregisterSharedValidationInterface(txr);
|
||||
|
||||
bool txid_in_mempool = tx_pool.exists(GenTxid::Txid(tx->GetHash()));
|
||||
bool wtxid_in_mempool = tx_pool.exists(GenTxid::Wtxid(tx->GetWitnessHash()));
|
||||
|
@ -25,7 +25,7 @@ static void mineBlock(const node::NodeContext& node, std::chrono::seconds block_
|
||||
block.fChecked = true; // little speedup
|
||||
SetMockTime(curr_time); // process block at current time
|
||||
Assert(node.chainman->ProcessNewBlock(std::make_shared<const CBlock>(block), /*force_processing=*/true, /*min_pow_checked=*/true, nullptr));
|
||||
SyncWithValidationInterfaceQueue(); // drain events queue
|
||||
node.validation_signals->SyncWithValidationInterfaceQueue(); // drain events queue
|
||||
}
|
||||
|
||||
// Verifying when network-limited peer connections are desirable based on the node's proximity to the tip
|
||||
@ -57,7 +57,7 @@ BOOST_AUTO_TEST_CASE(connections_desirable_service_flags)
|
||||
|
||||
// By now, we tested that the connections desirable services flags change based on the node's time proximity to the tip.
|
||||
// Now, perform the same tests for when the node receives a block.
|
||||
RegisterValidationInterface(peerman.get());
|
||||
m_node.validation_signals->RegisterValidationInterface(peerman.get());
|
||||
|
||||
// First, verify a block in the past doesn't enable limited peers connections
|
||||
// At this point, our time is (NODE_NETWORK_LIMITED_ALLOW_CONN_BLOCKS + 1) * 10 minutes ahead the tip's time.
|
||||
|
@ -20,7 +20,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
{
|
||||
CBlockPolicyEstimator& feeEst = *Assert(m_node.fee_estimator);
|
||||
CTxMemPool& mpool = *Assert(m_node.mempool);
|
||||
RegisterValidationInterface(&feeEst);
|
||||
m_node.validation_signals->RegisterValidationInterface(&feeEst);
|
||||
TestMemPoolEntryHelper entry;
|
||||
CAmount basefee(2000);
|
||||
CAmount deltaFee(100);
|
||||
@ -74,7 +74,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
/*submitted_in_package=*/false,
|
||||
/*chainstate_is_current=*/true,
|
||||
/*has_no_mempool_parents=*/true)};
|
||||
GetMainSignals().TransactionAddedToMempool(tx_info, mpool.GetAndIncrementSequence());
|
||||
m_node.validation_signals->TransactionAddedToMempool(tx_info, mpool.GetAndIncrementSequence());
|
||||
}
|
||||
uint256 hash = tx.GetHash();
|
||||
txHashes[j].push_back(hash);
|
||||
@ -102,7 +102,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
// Check after just a few txs that combining buckets works as expected
|
||||
if (blocknum == 3) {
|
||||
// Wait for fee estimator to catch up
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
// At this point we should need to combine 3 buckets to get enough data points
|
||||
// So estimateFee(1) should fail and estimateFee(2) should return somewhere around
|
||||
// 9*baserate. estimateFee(2) %'s are 100,100,90 = average 97%
|
||||
@ -113,7 +113,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
}
|
||||
|
||||
// Wait for fee estimator to catch up
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
|
||||
std::vector<CAmount> origFeeEst;
|
||||
// Highest feerate is 10*baseRate and gets in all blocks,
|
||||
@ -146,7 +146,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
}
|
||||
|
||||
// Wait for fee estimator to catch up
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
|
||||
BOOST_CHECK(feeEst.estimateFee(1) == CFeeRate(0));
|
||||
for (int i = 2; i < 10;i++) {
|
||||
@ -175,7 +175,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
/*submitted_in_package=*/false,
|
||||
/*chainstate_is_current=*/true,
|
||||
/*has_no_mempool_parents=*/true)};
|
||||
GetMainSignals().TransactionAddedToMempool(tx_info, mpool.GetAndIncrementSequence());
|
||||
m_node.validation_signals->TransactionAddedToMempool(tx_info, mpool.GetAndIncrementSequence());
|
||||
}
|
||||
uint256 hash = tx.GetHash();
|
||||
txHashes[j].push_back(hash);
|
||||
@ -188,7 +188,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
}
|
||||
|
||||
// Wait for fee estimator to catch up
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
|
||||
for (int i = 1; i < 10;i++) {
|
||||
BOOST_CHECK(feeEst.estimateFee(i) == CFeeRate(0) || feeEst.estimateFee(i).GetFeePerK() > origFeeEst[i-1] - deltaFee);
|
||||
@ -212,7 +212,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
block.clear();
|
||||
|
||||
// Wait for fee estimator to catch up
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
|
||||
BOOST_CHECK(feeEst.estimateFee(1) == CFeeRate(0));
|
||||
for (int i = 2; i < 10;i++) {
|
||||
@ -239,7 +239,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
/*submitted_in_package=*/false,
|
||||
/*chainstate_is_current=*/true,
|
||||
/*has_no_mempool_parents=*/true)};
|
||||
GetMainSignals().TransactionAddedToMempool(tx_info, mpool.GetAndIncrementSequence());
|
||||
m_node.validation_signals->TransactionAddedToMempool(tx_info, mpool.GetAndIncrementSequence());
|
||||
}
|
||||
uint256 hash = tx.GetHash();
|
||||
CTransactionRef ptx = mpool.get(hash);
|
||||
@ -257,7 +257,7 @@ BOOST_AUTO_TEST_CASE(BlockPolicyEstimates)
|
||||
block.clear();
|
||||
}
|
||||
// Wait for fee estimator to catch up
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
BOOST_CHECK(feeEst.estimateFee(1) == CFeeRate(0));
|
||||
for (int i = 2; i < 9; i++) { // At 9, the original estimate was already at the bottom (b/c scale = 2)
|
||||
BOOST_CHECK(feeEst.estimateFee(i).GetFeePerK() < origFeeEst[i-1] - deltaFee);
|
||||
|
@ -71,7 +71,7 @@ BOOST_FIXTURE_TEST_CASE(txindex_initial_sync, TestChain100Setup)
|
||||
// SyncWithValidationInterfaceQueue() call below is also needed to ensure
|
||||
// TSAN always sees the test thread waiting for the notification thread, and
|
||||
// avoid potential false positive reports.
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
|
||||
// shutdown sequence (c.f. Shutdown() in init.cpp)
|
||||
txindex.Stop();
|
||||
|
@ -95,12 +95,12 @@ COutPoint MineBlock(const NodeContext& node, std::shared_ptr<CBlock>& block)
|
||||
const auto old_height = WITH_LOCK(chainman.GetMutex(), return chainman.ActiveHeight());
|
||||
bool new_block;
|
||||
BlockValidationStateCatcher bvsc{block->GetHash()};
|
||||
RegisterValidationInterface(&bvsc);
|
||||
node.validation_signals->RegisterValidationInterface(&bvsc);
|
||||
const bool processed{chainman.ProcessNewBlock(block, true, true, &new_block)};
|
||||
const bool duplicate{!new_block && processed};
|
||||
assert(!duplicate);
|
||||
UnregisterValidationInterface(&bvsc);
|
||||
SyncWithValidationInterfaceQueue();
|
||||
node.validation_signals->UnregisterValidationInterface(&bvsc);
|
||||
node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
const bool was_valid{bvsc.m_state && bvsc.m_state->IsValid()};
|
||||
assert(old_height + was_valid == WITH_LOCK(chainman.GetMutex(), return chainman.ActiveHeight()));
|
||||
|
||||
|
@ -171,7 +171,8 @@ ChainTestingSetup::ChainTestingSetup(const ChainType chainType, const std::vecto
|
||||
// from blocking due to queue overrun.
|
||||
m_node.scheduler = std::make_unique<CScheduler>();
|
||||
m_node.scheduler->m_service_thread = std::thread(util::TraceThread, "scheduler", [&] { m_node.scheduler->serviceQueue(); });
|
||||
GetMainSignals().RegisterBackgroundSignalScheduler(*m_node.scheduler);
|
||||
m_node.validation_signals = std::make_unique<CMainSignals>();
|
||||
m_node.validation_signals->RegisterBackgroundSignalScheduler(*m_node.scheduler);
|
||||
|
||||
m_node.fee_estimator = std::make_unique<CBlockPolicyEstimator>(FeeestPath(*m_node.args), DEFAULT_ACCEPT_STALE_FEE_ESTIMATES);
|
||||
m_node.mempool = std::make_unique<CTxMemPool>(MemPoolOptionsForTest(m_node));
|
||||
@ -185,7 +186,7 @@ ChainTestingSetup::ChainTestingSetup(const ChainType chainType, const std::vecto
|
||||
.datadir = m_args.GetDataDirNet(),
|
||||
.check_block_index = true,
|
||||
.notifications = *m_node.notifications,
|
||||
.signals = &GetMainSignals(),
|
||||
.signals = m_node.validation_signals.get(),
|
||||
.worker_threads_num = 2,
|
||||
};
|
||||
const BlockManager::Options blockman_opts{
|
||||
@ -203,8 +204,8 @@ ChainTestingSetup::ChainTestingSetup(const ChainType chainType, const std::vecto
|
||||
ChainTestingSetup::~ChainTestingSetup()
|
||||
{
|
||||
if (m_node.scheduler) m_node.scheduler->stop();
|
||||
GetMainSignals().FlushBackgroundCallbacks();
|
||||
GetMainSignals().UnregisterBackgroundSignalScheduler();
|
||||
m_node.validation_signals->FlushBackgroundCallbacks();
|
||||
m_node.validation_signals->UnregisterBackgroundSignalScheduler();
|
||||
m_node.connman.reset();
|
||||
m_node.banman.reset();
|
||||
m_node.addrman.reset();
|
||||
@ -213,6 +214,7 @@ ChainTestingSetup::~ChainTestingSetup()
|
||||
m_node.mempool.reset();
|
||||
m_node.fee_estimator.reset();
|
||||
m_node.chainman.reset();
|
||||
m_node.validation_signals.reset();
|
||||
m_node.scheduler.reset();
|
||||
}
|
||||
|
||||
|
@ -13,7 +13,6 @@
|
||||
#include <util/time.h>
|
||||
#include <util/translation.h>
|
||||
#include <validation.h>
|
||||
#include <validationinterface.h>
|
||||
|
||||
using node::NodeContext;
|
||||
|
||||
@ -23,7 +22,7 @@ CTxMemPool::Options MemPoolOptionsForTest(const NodeContext& node)
|
||||
// Default to always checking mempool regardless of
|
||||
// chainparams.DefaultConsistencyChecks for tests
|
||||
.check_ratio = 1,
|
||||
.signals = &GetMainSignals(),
|
||||
.signals = node.validation_signals.get(),
|
||||
};
|
||||
const auto result{ApplyArgsManOptions(*node.args, ::Params(), mempool_opts)};
|
||||
Assert(result);
|
||||
|
@ -158,7 +158,7 @@ BOOST_AUTO_TEST_CASE(processnewblock_signals_ordering)
|
||||
bool ignored;
|
||||
// Connect the genesis block and drain any outstanding events
|
||||
BOOST_CHECK(Assert(m_node.chainman)->ProcessNewBlock(std::make_shared<CBlock>(Params().GenesisBlock()), true, true, &ignored));
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
|
||||
// subscribe to events (this subscriber will validate event ordering)
|
||||
const CBlockIndex* initial_tip = nullptr;
|
||||
@ -167,7 +167,7 @@ BOOST_AUTO_TEST_CASE(processnewblock_signals_ordering)
|
||||
initial_tip = m_node.chainman->ActiveChain().Tip();
|
||||
}
|
||||
auto sub = std::make_shared<TestSubscriber>(initial_tip->GetBlockHash());
|
||||
RegisterSharedValidationInterface(sub);
|
||||
m_node.validation_signals->RegisterSharedValidationInterface(sub);
|
||||
|
||||
// create a bunch of threads that repeatedly process a block generated above at random
|
||||
// this will create parallelism and randomness inside validation - the ValidationInterface
|
||||
@ -196,9 +196,9 @@ BOOST_AUTO_TEST_CASE(processnewblock_signals_ordering)
|
||||
for (auto& t : threads) {
|
||||
t.join();
|
||||
}
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
|
||||
UnregisterSharedValidationInterface(sub);
|
||||
m_node.validation_signals->UnregisterSharedValidationInterface(sub);
|
||||
|
||||
LOCK(cs_main);
|
||||
BOOST_CHECK_EQUAL(sub->m_expected_tip, m_node.chainman->ActiveChain().Tip()->GetBlockHash());
|
||||
|
@ -102,7 +102,7 @@ BOOST_FIXTURE_TEST_CASE(chainstatemanager, TestChain100Setup)
|
||||
BOOST_CHECK_EQUAL(active_tip2, c2.m_chain.Tip());
|
||||
|
||||
// Let scheduler events finish running to avoid accessing memory that is going to be unloaded
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
}
|
||||
|
||||
//! Test rebalancing the caches associated with each chainstate.
|
||||
@ -374,7 +374,7 @@ struct SnapshotTestSetup : TestChain100Setup {
|
||||
cs->ForceFlushStateToDisk();
|
||||
}
|
||||
// Process all callbacks referring to the old manager before wiping it.
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
LOCK(::cs_main);
|
||||
chainman.ResetChainstates();
|
||||
BOOST_CHECK_EQUAL(chainman.GetAll().size(), 0);
|
||||
@ -383,7 +383,7 @@ struct SnapshotTestSetup : TestChain100Setup {
|
||||
.chainparams = ::Params(),
|
||||
.datadir = chainman.m_options.datadir,
|
||||
.notifications = *m_node.notifications,
|
||||
.signals = &GetMainSignals(),
|
||||
.signals = m_node.validation_signals.get(),
|
||||
};
|
||||
const BlockManager::Options blockman_opts{
|
||||
.chainparams = chainman_opts.chainparams,
|
||||
|
@ -28,7 +28,7 @@ BOOST_AUTO_TEST_CASE(unregister_validation_interface_race)
|
||||
const CBlock block_dummy;
|
||||
BlockValidationState state_dummy;
|
||||
while (generate) {
|
||||
GetMainSignals().BlockChecked(block_dummy, state_dummy);
|
||||
m_node.validation_signals->BlockChecked(block_dummy, state_dummy);
|
||||
}
|
||||
}};
|
||||
|
||||
@ -37,8 +37,8 @@ BOOST_AUTO_TEST_CASE(unregister_validation_interface_race)
|
||||
// keep going for about 1 sec, which is 250k iterations
|
||||
for (int i = 0; i < 250000; i++) {
|
||||
auto sub = std::make_shared<TestSubscriberNoop>();
|
||||
RegisterSharedValidationInterface(sub);
|
||||
UnregisterSharedValidationInterface(sub);
|
||||
m_node.validation_signals->RegisterSharedValidationInterface(sub);
|
||||
m_node.validation_signals->UnregisterSharedValidationInterface(sub);
|
||||
}
|
||||
// tell the other thread we are done
|
||||
generate = false;
|
||||
@ -52,8 +52,8 @@ BOOST_AUTO_TEST_CASE(unregister_validation_interface_race)
|
||||
class TestInterface : public CValidationInterface
|
||||
{
|
||||
public:
|
||||
TestInterface(std::function<void()> on_call = nullptr, std::function<void()> on_destroy = nullptr)
|
||||
: m_on_call(std::move(on_call)), m_on_destroy(std::move(on_destroy))
|
||||
TestInterface(CMainSignals& signals, std::function<void()> on_call = nullptr, std::function<void()> on_destroy = nullptr)
|
||||
: m_on_call(std::move(on_call)), m_on_destroy(std::move(on_destroy)), m_signals{signals}
|
||||
{
|
||||
}
|
||||
virtual ~TestInterface()
|
||||
@ -64,14 +64,15 @@ public:
|
||||
{
|
||||
if (m_on_call) m_on_call();
|
||||
}
|
||||
static void Call()
|
||||
void Call()
|
||||
{
|
||||
CBlock block;
|
||||
BlockValidationState state;
|
||||
GetMainSignals().BlockChecked(block, state);
|
||||
m_signals.BlockChecked(block, state);
|
||||
}
|
||||
std::function<void()> m_on_call;
|
||||
std::function<void()> m_on_destroy;
|
||||
CMainSignals& m_signals;
|
||||
};
|
||||
|
||||
// Regression test to ensure UnregisterAllValidationInterfaces calls don't
|
||||
@ -80,17 +81,23 @@ public:
|
||||
BOOST_AUTO_TEST_CASE(unregister_all_during_call)
|
||||
{
|
||||
bool destroyed = false;
|
||||
RegisterSharedValidationInterface(std::make_shared<TestInterface>(
|
||||
auto shared{std::make_shared<TestInterface>(
|
||||
*m_node.validation_signals,
|
||||
[&] {
|
||||
// First call should decrements reference count 2 -> 1
|
||||
UnregisterAllValidationInterfaces();
|
||||
m_node.validation_signals->UnregisterAllValidationInterfaces();
|
||||
BOOST_CHECK(!destroyed);
|
||||
// Second call should not decrement reference count 1 -> 0
|
||||
UnregisterAllValidationInterfaces();
|
||||
m_node.validation_signals->UnregisterAllValidationInterfaces();
|
||||
BOOST_CHECK(!destroyed);
|
||||
},
|
||||
[&] { destroyed = true; }));
|
||||
TestInterface::Call();
|
||||
[&] { destroyed = true; })};
|
||||
m_node.validation_signals->RegisterSharedValidationInterface(shared);
|
||||
BOOST_CHECK(shared.use_count() == 2);
|
||||
shared->Call();
|
||||
BOOST_CHECK(shared.use_count() == 1);
|
||||
BOOST_CHECK(!destroyed);
|
||||
shared.reset();
|
||||
BOOST_CHECK(destroyed);
|
||||
}
|
||||
|
||||
|
@ -3217,7 +3217,7 @@ static void LimitValidationInterfaceQueue(CMainSignals& signals) LOCKS_EXCLUDED(
|
||||
AssertLockNotHeld(cs_main);
|
||||
|
||||
if (signals.CallbacksPending() > 10) {
|
||||
SyncWithValidationInterfaceQueue();
|
||||
signals.SyncWithValidationInterfaceQueue();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -94,8 +94,6 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
static CMainSignals g_signals;
|
||||
|
||||
CMainSignals::CMainSignals() {}
|
||||
|
||||
CMainSignals::~CMainSignals() {}
|
||||
@ -124,11 +122,6 @@ size_t CMainSignals::CallbacksPending()
|
||||
return m_internals->m_schedulerClient.CallbacksPending();
|
||||
}
|
||||
|
||||
CMainSignals& GetMainSignals()
|
||||
{
|
||||
return g_signals;
|
||||
}
|
||||
|
||||
void CMainSignals::RegisterSharedValidationInterface(std::shared_ptr<CValidationInterface> callbacks)
|
||||
{
|
||||
// Each connection captures the shared_ptr to ensure that each callback is
|
||||
@ -277,33 +270,3 @@ void CMainSignals::NewPoWValidBlock(const CBlockIndex *pindex, const std::shared
|
||||
LOG_EVENT("%s: block hash=%s", __func__, block->GetHash().ToString());
|
||||
m_internals->Iterate([&](CValidationInterface& callbacks) { callbacks.NewPoWValidBlock(pindex, block); });
|
||||
}
|
||||
|
||||
// These functions are temporary and will be removed in the following commit
|
||||
void RegisterValidationInterface(CValidationInterface* callbacks)
|
||||
{
|
||||
GetMainSignals().RegisterValidationInterface(callbacks);
|
||||
}
|
||||
void UnregisterValidationInterface(CValidationInterface* callbacks)
|
||||
{
|
||||
GetMainSignals().UnregisterValidationInterface(callbacks);
|
||||
}
|
||||
void UnregisterAllValidationInterfaces()
|
||||
{
|
||||
GetMainSignals().UnregisterAllValidationInterfaces();
|
||||
}
|
||||
void RegisterSharedValidationInterface(std::shared_ptr<CValidationInterface> callbacks)
|
||||
{
|
||||
GetMainSignals().RegisterSharedValidationInterface(callbacks);
|
||||
}
|
||||
void UnregisterSharedValidationInterface(std::shared_ptr<CValidationInterface> callbacks)
|
||||
{
|
||||
GetMainSignals().UnregisterSharedValidationInterface(callbacks);
|
||||
}
|
||||
void CallFunctionInValidationInterfaceQueue(std::function<void ()> func)
|
||||
{
|
||||
GetMainSignals().CallFunctionInValidationInterfaceQueue(func);
|
||||
}
|
||||
void SyncWithValidationInterfaceQueue()
|
||||
{
|
||||
GetMainSignals().SyncWithValidationInterfaceQueue();
|
||||
}
|
||||
|
@ -21,22 +21,11 @@ class BlockValidationState;
|
||||
class CBlock;
|
||||
class CBlockIndex;
|
||||
struct CBlockLocator;
|
||||
class CValidationInterface;
|
||||
class CScheduler;
|
||||
enum class MemPoolRemovalReason;
|
||||
struct RemovedMempoolTransactionInfo;
|
||||
struct NewMempoolTransactionInfo;
|
||||
|
||||
void RegisterValidationInterface(CValidationInterface* callbacks);
|
||||
void UnregisterValidationInterface(CValidationInterface* callbacks);
|
||||
void UnregisterAllValidationInterfaces();
|
||||
|
||||
void RegisterSharedValidationInterface(std::shared_ptr<CValidationInterface> callbacks);
|
||||
void UnregisterSharedValidationInterface(std::shared_ptr<CValidationInterface> callbacks);
|
||||
|
||||
void CallFunctionInValidationInterfaceQueue(std::function<void ()> func);
|
||||
void SyncWithValidationInterfaceQueue() LOCKS_EXCLUDED(cs_main);
|
||||
|
||||
/**
|
||||
* Implement this to subscribe to events generated in validation and mempool
|
||||
*
|
||||
@ -232,6 +221,4 @@ public:
|
||||
void NewPoWValidBlock(const CBlockIndex *, const std::shared_ptr<const CBlock>&);
|
||||
};
|
||||
|
||||
CMainSignals& GetMainSignals();
|
||||
|
||||
#endif // BITCOIN_VALIDATIONINTERFACE_H
|
||||
|
@ -71,7 +71,8 @@ std::shared_ptr<CWallet> TestLoadWallet(WalletContext& context)
|
||||
|
||||
void TestUnloadWallet(std::shared_ptr<CWallet>&& wallet)
|
||||
{
|
||||
SyncWithValidationInterfaceQueue();
|
||||
// Calls SyncWithValidationInterfaceQueue
|
||||
wallet->chain().waitForNotificationsIfTipChanged({});
|
||||
wallet->m_chain_notifications_handler.reset();
|
||||
UnloadWallet(std::move(wallet));
|
||||
}
|
||||
|
@ -812,7 +812,7 @@ BOOST_FIXTURE_TEST_CASE(CreateWallet, TestChain100Setup)
|
||||
// transactionAddedToMempool notifications, and create block and mempool
|
||||
// transactions paying to the wallet
|
||||
std::promise<void> promise;
|
||||
CallFunctionInValidationInterfaceQueue([&promise] {
|
||||
m_node.validation_signals->CallFunctionInValidationInterfaceQueue([&promise] {
|
||||
promise.get_future().wait();
|
||||
});
|
||||
std::string error;
|
||||
@ -840,7 +840,7 @@ BOOST_FIXTURE_TEST_CASE(CreateWallet, TestChain100Setup)
|
||||
// Unblock notification queue and make sure stale blockConnected and
|
||||
// transactionAddedToMempool events are processed
|
||||
promise.set_value();
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
// AddToWallet events for block_tx and mempool_tx events are counted a
|
||||
// second time as the notification queue is processed
|
||||
BOOST_CHECK_EQUAL(addtx_count, 5);
|
||||
@ -863,7 +863,7 @@ BOOST_FIXTURE_TEST_CASE(CreateWallet, TestChain100Setup)
|
||||
m_coinbase_txns.push_back(CreateAndProcessBlock({block_tx}, GetScriptForRawPubKey(coinbaseKey.GetPubKey())).vtx[0]);
|
||||
mempool_tx = TestSimpleSpend(*m_coinbase_txns[3], 0, coinbaseKey, GetScriptForRawPubKey(key.GetPubKey()));
|
||||
BOOST_CHECK(m_node.chain->broadcastTransaction(MakeTransactionRef(mempool_tx), DEFAULT_TRANSACTION_MAXFEE, false, error));
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
});
|
||||
wallet = TestLoadWallet(context);
|
||||
// Since mempool transactions are requested at the end of loading, there will
|
||||
@ -903,7 +903,7 @@ BOOST_FIXTURE_TEST_CASE(ZapSelectTx, TestChain100Setup)
|
||||
auto block_tx = TestSimpleSpend(*m_coinbase_txns[0], 0, coinbaseKey, GetScriptForRawPubKey(key.GetPubKey()));
|
||||
CreateAndProcessBlock({block_tx}, GetScriptForRawPubKey(coinbaseKey.GetPubKey()));
|
||||
|
||||
SyncWithValidationInterfaceQueue();
|
||||
m_node.validation_signals->SyncWithValidationInterfaceQueue();
|
||||
|
||||
{
|
||||
auto block_hash = block_tx.GetHash();
|
||||
|
Loading…
x
Reference in New Issue
Block a user