8#include <chainparams.h>
42#include <validation.h>
46#if defined(HAVE_CONFIG_H)
47#include <config/bitcoin-config.h>
52#include <boost/signals2/signal.hpp>
70 class NodeImpl :
public Node {
75 explicit NodeImpl(NodeContext *context) { setContext(context); }
77 void initParameterInteraction()
override {
81 int getExitStatus()
override {
84 bool baseInitialize(
Config &config)
override {
92 m_context->kernel = std::make_unique<kernel::Context>();
109 if (
AppInitMain(config, rpcServer, httpRPCRequestProcessor,
114 m_context->exit_status.store(EXIT_FAILURE);
117 void appShutdown()
override {
121 void startShutdown()
override {
131 bool isPersistentSettingIgnored(
const std::string &
name)
override {
132 bool ignored =
false;
136 ignored = !options->empty();
142 getPersistentSetting(
const std::string &
name)
override {
145 void updateRwSetting(
const std::string &
name,
149 settings.rw_settings.erase(name);
151 settings.rw_settings[name] = value;
156 void forceSetting(
const std::string &
name,
160 settings.forced_settings.erase(name);
162 settings.forced_settings[name] = value;
166 void resetSettings()
override {
173 void mapPort(
bool enable)
override {
StartMapPort(enable); }
174 bool getProxy(
Network net,
Proxy &proxy_info)
override {
181 bool getNodesStats(NodesStats &stats)
override {
185 std::vector<CNodeStats> stats_temp;
186 m_context->connman->GetNodeStats(stats_temp);
188 stats.reserve(stats_temp.size());
189 for (
auto &node_stats_temp : stats_temp) {
190 stats.emplace_back(std::move(node_stats_temp),
false,
198 for (
auto &node_stats : stats) {
199 std::get<1>(node_stats) =
201 std::get<0>(node_stats).nodeid,
202 std::get<2>(node_stats));
210 bool getBanned(
banmap_t &banmap)
override {
217 bool ban(
const CNetAddr &net_addr, int64_t ban_time_offset)
override {
219 m_context->banman->Ban(net_addr, ban_time_offset);
224 bool unban(
const CSubNet &ip)
override {
231 bool disconnectByAddress(
const CNetAddr &net_addr)
override {
233 return m_context->connman->DisconnectNode(net_addr);
237 bool disconnectById(
NodeId id)
override {
239 return m_context->connman->DisconnectNode(
id);
243 int64_t getTotalBytesRecv()
override {
247 int64_t getTotalBytesSent()
override {
251 size_t getMempoolSize()
override {
254 size_t getMempoolDynamicUsage()
override {
258 bool getHeaderTip(
int &height, int64_t &block_time)
override {
260 auto best_header = chainman().m_best_header;
262 height = best_header->nHeight;
263 block_time = best_header->GetBlockTime();
268 int getNumBlocks()
override {
270 return chainman().ActiveChain().Height();
276 : chainman().GetParams().GenesisBlock().GetHash();
278 int64_t getLastBlockTime()
override {
280 if (chainman().ActiveChain().Tip()) {
281 return chainman().ActiveChain().Tip()->GetBlockTime();
284 return chainman().GetParams().GenesisBlock().GetBlockTime();
286 double getVerificationProgress()
override {
290 tip = chainman().ActiveChain().Tip();
295 bool isInitialBlockDownload()
override {
296 return chainman().IsInitialBlockDownload();
298 bool isLoadingBlocks()
override {
299 return chainman().m_blockman.LoadingBlocks();
301 void setNetworkActive(
bool active)
override {
303 m_context->connman->SetNetworkActive(active);
306 bool getNetworkActive()
override {
309 CFeeRate getDustRelayFee()
override {
313 return m_context->mempool->m_opts.dust_relay_feerate;
315 UniValue executeRpc(
const Config &config,
const std::string &command,
317 const std::string &uri)
override {
325 std::vector<std::string> listRpcCommands()
override {
334 std::optional<Coin> getUnspentOutput(
const COutPoint &output)
override {
336 return chainman().ActiveChainstate().CoinsTip().GetCoin(output);
341 std::unique_ptr<Handler> handleInitMessage(InitMessageFn fn)
override {
344 std::unique_ptr<Handler> handleMessageBox(MessageBoxFn fn)
override {
347 std::unique_ptr<Handler> handleQuestion(QuestionFn fn)
override {
350 std::unique_ptr<Handler>
351 handleShowProgress(ShowProgressFn fn)
override {
354 std::unique_ptr<Handler> handleNotifyNumConnectionsChanged(
355 NotifyNumConnectionsChangedFn fn)
override {
359 std::unique_ptr<Handler> handleNotifyNetworkActiveChanged(
360 NotifyNetworkActiveChangedFn fn)
override {
364 std::unique_ptr<Handler>
365 handleNotifyAlertChanged(NotifyAlertChangedFn fn)
override {
368 std::unique_ptr<Handler>
369 handleBannedListChanged(BannedListChangedFn fn)
override {
372 std::unique_ptr<Handler>
373 handleNotifyBlockTip(NotifyBlockTipFn fn)
override {
383 std::unique_ptr<Handler>
384 handleNotifyHeaderTip(NotifyHeaderTipFn fn)
override {
388 int64_t timestamp,
bool presync) {
393 NodeContext *context()
override {
return m_context; }
394 void setContext(NodeContext *context)
override {
m_context = context; }
400 const BlockManager &blockman) {
426 FillBlock(active[index->
nHeight] == index
433 if (!blockman.ReadBlock(*block.
m_data, *index)) {
442 explicit NotificationsProxy(
443 std::shared_ptr<Chain::Notifications> notifications)
445 virtual ~NotificationsProxy() =
default;
447 std::shared_ptr<
const std::vector<Coin>>,
448 uint64_t mempool_sequence)
override {
453 uint64_t mempool_sequence)
override {
458 const std::shared_ptr<const CBlock> &block,
462 void BlockDisconnected(
const std::shared_ptr<const CBlock> &block,
468 bool is_ibd)
override {
478 class NotificationsHandlerImpl :
public Handler {
480 explicit NotificationsHandlerImpl(
482 std::shared_ptr<Chain::Notifications> notifications)
484 std::move(notifications))} {
487 ~NotificationsHandlerImpl()
override { disconnect(); }
488 void disconnect()
override {
498 class RpcHandlerImpl :
public Handler {
500 explicit RpcHandlerImpl(
const CRPCCommand &command)
504 UniValue &result,
bool last_handler) {
529 void disconnect() final {
536 ~RpcHandlerImpl()
override { disconnect(); }
542 class ChainImpl :
public Chain {
549 std::optional<int> getHeight()
override {
552 int height = active.
Height();
558 BlockHash getBlockHash(
int height)
override {
565 bool haveBlockOnDisk(
int height)
override {
569 return block && (block->nStatus.hasData() != 0) && block->
nTx > 0;
584 return fork->nHeight;
592 return FillBlock(
m_node.chainman->m_blockman.LookupBlockIndex(hash),
593 block, lock, active, chainman().m_blockman);
595 bool findFirstBlockWithTimeAndHeight(int64_t min_time,
int min_height,
600 block, lock, active, chainman().m_blockman);
602 bool findAncestorByHeight(
const BlockHash &block_hash,
608 m_node.chainman->m_blockman.LookupBlockIndex(block_hash)) {
610 block->GetAncestor(ancestor_height)) {
611 return FillBlock(ancestor, ancestor_out, lock, active,
612 chainman().m_blockman);
615 return FillBlock(
nullptr, ancestor_out, lock, active,
616 chainman().m_blockman);
618 bool findAncestorByHash(
const BlockHash &block_hash,
624 m_node.chainman->m_blockman.LookupBlockIndex(block_hash);
626 m_node.chainman->m_blockman.LookupBlockIndex(ancestor_hash);
627 if (block && ancestor &&
631 return FillBlock(ancestor, ancestor_out, lock, active,
632 chainman().m_blockman);
634 bool findCommonAncestor(
const BlockHash &block_hash1,
642 m_node.chainman->m_blockman.LookupBlockIndex(block_hash1);
644 m_node.chainman->m_blockman.LookupBlockIndex(block_hash2);
650 return int{FillBlock(ancestor, ancestor_out, lock, active,
651 chainman().m_blockman)} &
652 int{FillBlock(block1, block1_out, lock, active,
653 chainman().m_blockman)} &
654 int{FillBlock(block2, block2_out, lock, active,
655 chainman().m_blockman)};
657 void findCoins(std::map<COutPoint, Coin> &coins)
override {
660 double guessVerificationProgress(
const BlockHash &block_hash)
override {
663 chainman().GetParams().TxData(),
664 chainman().m_blockman.LookupBlockIndex(block_hash));
666 bool hasBlocks(
const BlockHash &block_hash,
int min_height,
667 std::optional<int> max_height)
override {
677 chainman().m_blockman.LookupBlockIndex(block_hash)) {
678 if (max_height && block->
nHeight >= *max_height) {
681 for (; block->nStatus.hasData(); block = block->
pprev) {
690 bool broadcastTransaction(
const Config &config,
692 const Amount &max_tx_fee,
bool relay,
693 std::string &err_string)
override {
704 CFeeRate estimateFee()
const override {
708 return m_node.mempool->estimateFee();
714 return m_node.mempool->m_opts.min_relay_feerate;
720 return m_node.mempool->m_opts.dust_relay_feerate;
722 bool havePruned()
override {
724 return m_node.chainman->m_blockman.m_have_pruned;
726 bool isReadyToBroadcast()
override {
727 return !chainman().m_blockman.LoadingBlocks() &&
728 !isInitialBlockDownload();
730 std::optional<int> getPruneHeight()
override {
731 LOCK(chainman().GetMutex());
733 chainman().ActiveChain());
735 bool isInitialBlockDownload()
override {
736 return chainman().IsInitialBlockDownload();
739 void initMessage(
const std::string &message)
override {
748 void showProgress(
const std::string &title,
int progress,
749 bool resume_possible)
override {
750 ::uiInterface.ShowProgress(title, progress, resume_possible);
752 std::unique_ptr<Handler> handleNotifications(
753 std::shared_ptr<Notifications> notifications)
override {
754 return std::make_unique<NotificationsHandlerImpl>(
755 validation_signals(), std::move(notifications));
758 waitForNotificationsIfTipChanged(
const BlockHash &old_tip)
override {
766 validation_signals().SyncWithValidationInterfaceQueue();
769 std::unique_ptr<Handler>
771 return std::make_unique<RpcHandlerImpl>(command);
773 bool rpcEnableDeprecated(
const std::string &method)
override {
776 void rpcRunLater(
const std::string &
name, std::function<
void()> fn,
777 int64_t seconds)
override {
783 std::vector<util::SettingsValue>
784 getSettingsList(
const std::string &
name)
override {
797 bool updateRwSetting(
const std::string &
name,
799 bool write)
override {
802 settings.rw_settings.erase(name);
804 settings.rw_settings[name] = value;
809 void requestMempoolTransactions(Notifications ¬ifications)
override {
815 notifications.transactionAddedToMempool(entry->GetSharedTx(),
819 bool hasAssumedValidChain()
override {
823 NodeContext *context()
override {
return &
m_node; }
835 return std::make_unique<node::NodeImpl>(context);
839 return std::make_unique<node::ChainImpl>(
node, params);
std::optional< int > GetPruneHeight(const BlockManager &blockman, const CChain &chain)
CBlockLocator GetLocator(const CBlockIndex *index)
Get a locator for a block index entry.
const CBlockIndex * LastCommonAncestor(const CBlockIndex *pa, const CBlockIndex *pb)
Find the last common ancestor two blocks have.
const CChainParams & Params()
Return the currently selected parameters.
#define Assert(val)
Identity function.
util::SettingsValue GetPersistentSetting(const std::string &name) const
Get current setting from config file or read/write settings file, ignoring nonpersistent command line...
void LockSettings(Fn &&fn)
Access settings with lock held.
bool WriteSettingsFile(std::vector< std::string > *errors=nullptr, bool backup=false) const
Write settings file or backup settings file.
std::vector< util::SettingsValue > GetSettingsList(const std::string &arg) const
Get list of setting values.
util::SettingsValue GetSetting(const std::string &arg) const
Get setting value.
bool GetBoolArg(const std::string &strArg, bool fDefault) const
Return boolean argument or default value.
The block chain is a tree shaped structure starting with the genesis block at the root,...
CBlockIndex * pprev
pointer to the index of the predecessor of this block
int64_t GetBlockTime() const
int64_t GetMedianTimePast() const
int64_t GetBlockTimeMax() const
unsigned int nTx
Number of transactions in this block.
CBlockIndex * GetAncestor(int height)
Efficiently find an ancestor of this block.
BlockHash GetBlockHash() const
int nHeight
height of the entry in the chain. The genesis block has height 0
An in-memory indexed chain of blocks.
CBlockIndex * Tip() const
Returns the index entry for the tip of this chain, or nullptr if none.
CBlockIndex * FindEarliestAtLeast(int64_t nTime, int height) const
Find the earliest block with timestamp equal or greater than the given time and height equal or great...
int Height() const
Return the maximal height in the chain.
CBlockLocator GetLocator() const
Return a CBlockLocator that refers to the tip of this chain.
CChainParams defines various tweakable parameters of a given instance of the Bitcoin system.
Fee rate in satoshis per virtualbyte: Amount / vB the feerate is represented internally as FeeFrac.
bool removeCommand(const std::string &name, const CRPCCommand *pcmd)
std::vector< std::string > listCommands() const
Returns a list of registered commands.
UniValue execute(const Config &config, const JSONRPCRequest &request) const
Execute a method.
void appendCommand(const std::string &name, const CRPCCommand *pcmd)
Appends a CRPCCommand to the dispatch table.
Implement this to subscribe to events generated in validation.
Chainstate stores and provides an API to update our local knowledge of the current best chain.
void ClearBlockIndexCandidates() EXCLUSIVE_LOCKS_REQUIRED(const CBlockIndex * FindForkInGlobalIndex(const CBlockLocator &locator) const EXCLUSIVE_LOCKS_REQUIRED(cs_main)
Find the last common block of this chain and a locator.
Provides an interface for creating and interacting with one or two chainstates: an IBD chainstate gen...
Class for registering and managing all RPC calls.
Wrapper around std::unique_lock style lock for MutexType.
void RegisterSharedValidationInterface(std::shared_ptr< CValidationInterface > callbacks)
Register subscriber.
void UnregisterSharedValidationInterface(std::shared_ptr< CValidationInterface > callbacks)
Unregister subscriber.
constexpr bool IsNull() const
Interface giving clients (wallet processes, maybe other analysis tools in the future) ability to acce...
Helper for findBlock to selectively return pieces of block data.
const FoundBlock * m_next_block
CBlockLocator * m_locator
Generic interface for managing an event handler or callback function registered with another interfac...
Top-level interface for a bitcoin node (bitcoind process).
Wallet chain client that in addition to having chain client methods for starting up,...
RecursiveMutex cs_main
Mutex to guard access to validation specific variables, such as reading or changing the chainstate.
void Interrupt(NodeContext &node)
Interrupt threads.
void InitLogging(const ArgsManager &args)
Initialize global loggers.
bool AppInitLockDataDirectory()
Lock bitcoin data directory.
void Shutdown(NodeContext &node)
bool AppInitBasicSetup(const ArgsManager &args, std::atomic< int > &exit_status)
Initialize bitcoin: Basic context setup.
bool AppInitMain(Config &config, RPCServer &rpcServer, HTTPRPCRequestProcessor &httpRPCRequestProcessor, NodeContext &node, interfaces::BlockAndHeaderTipInfo *tip_info)
Bitcoin main initialization.
bool AppInitInterfaces(NodeContext &node)
Initialize node and wallet interface pointers.
void InitParameterInteraction(ArgsManager &args)
Parameter interaction: change current parameters depending on various rules.
bool AppInitParameterInteraction(Config &config, const ArgsManager &args)
Initialization: parameter interaction.
bool AppInitSanityChecks(const kernel::Context &kernel)
Initialization sanity checks.
ChainstateRole
This enum describes the various roles a specific Chainstate instance can take.
void StartMapPort(bool enable)
std::unique_ptr< Handler > MakeHandler(boost::signals2::connection connection)
Return handler wrapping a boost signal connection.
std::unique_ptr< Node > MakeNode(node::NodeContext *context)
Return implementation of Node interface.
std::unique_ptr< Chain > MakeChain(node::NodeContext &node, const CChainParams ¶ms)
Return implementation of Chain interface.
TransactionError BroadcastTransaction(const NodeContext &node, const CTransactionRef tx, std::string &err_string, const Amount max_tx_fee, bool relay, bool wait_callback)
Submit a transaction to the mempool and (optionally) relay it to all P2P peers.
void FindCoins(const NodeContext &node, std::map< COutPoint, Coin > &coins)
Look up unspent output information.
Implement std::hash so RCUPtr can be used as a key for maps or sets.
auto FindKey(Map &&map, Key &&key) -> decltype(&map.at(key))
Map lookup helper.
std::map< CSubNet, CBanEntry > banmap_t
bool GetProxy(enum Network net, Proxy &proxyInfoOut)
ValidationSignals & m_signals
std::shared_ptr< Chain::Notifications > m_notifications
const CChainParams & m_params
const CRPCCommand * m_wrapped_command
std::shared_ptr< NotificationsProxy > m_proxy
is a home for public enum and struct type definitions that are used by internally by node code,...
static constexpr Amount DUST_RELAY_TX_FEE(3000 *SATOSHI)
Min feerate for defining dust.
static constexpr Amount DEFAULT_MIN_RELAY_TX_FEE_PER_KB(1000 *SATOSHI)
Default for -minrelaytxfee, minimum relay fee for transactions.
std::shared_ptr< const CTransaction > CTransactionRef
@ RPC_WALLET_NOT_FOUND
Invalid wallet specified.
void RPCSetTimerInterfaceIfUnset(RPCTimerInterface *iface)
Set the factory function for timer, but only, if unset.
bool IsDeprecatedRPCEnabled(const ArgsManager &args, const std::string &method)
void RPCUnsetTimerInterface(RPCTimerInterface *iface)
Unset factory function for timers.
void RPCRunLater(const std::string &name, std::function< void()> func, int64_t nSeconds)
Run func nSeconds from now.
bool ShutdownRequested()
Returns true if a shutdown is requested, false otherwise.
void StartShutdown()
Request shutdown of the application.
static constexpr Amount zero() noexcept
A BlockHash is a unqiue identifier for a block.
Describes a place in the block chain to another node such that if the other node doesn't have the sam...
Block and header tip information.
Block tip (could be a header or not, depends on the subscribed signal).
NodeContext struct containing references to chain state and connection state.
std::map< std::string, SettingsValue > rw_settings
Map of setting name to read-write file setting value.
std::map< std::string, std::vector< SettingsValue > > command_line_options
Map of setting name to list of command line values.
#define WAIT_LOCK(cs, name)
#define WITH_LOCK(cs, code)
Run code while locking a mutex.
#define TRY_LOCK(cs, name)
MemPoolRemovalReason
Reason why a transaction was removed from the mempool, this is passed to the notification signal.
CClientUIInterface uiInterface
void InitWarning(const bilingual_str &str)
Show warning message.
bool InitError(const bilingual_str &str)
Show error message.
double GuessVerificationProgress(const ChainTxData &data, const CBlockIndex *pindex)
Guess how far we are in the verification process at the given block index require cs_main if pindex h...
SynchronizationState
Current sync state passed to tip changed callbacks.
bilingual_str GetWarnings(bool verbose)
Format a string that describes several potential problems detected by the core.