Bitcoin Core  0.20.99
P2P Digital Currency
node.cpp
Go to the documentation of this file.
1 // Copyright (c) 2018-2020 The Bitcoin Core developers
2 // Distributed under the MIT software license, see the accompanying
3 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
4 
5 #include <interfaces/node.h>
6 
7 #include <addrdb.h>
8 #include <banman.h>
9 #include <chain.h>
10 #include <chainparams.h>
11 #include <init.h>
12 #include <interfaces/chain.h>
13 #include <interfaces/handler.h>
14 #include <interfaces/wallet.h>
15 #include <net.h>
16 #include <net_processing.h>
17 #include <netaddress.h>
18 #include <netbase.h>
19 #include <node/context.h>
20 #include <node/ui_interface.h>
21 #include <policy/feerate.h>
22 #include <policy/fees.h>
23 #include <policy/settings.h>
24 #include <primitives/block.h>
25 #include <rpc/server.h>
26 #include <shutdown.h>
28 #include <sync.h>
29 #include <txmempool.h>
30 #include <util/check.h>
31 #include <util/ref.h>
32 #include <util/system.h>
33 #include <util/translation.h>
34 #include <validation.h>
35 #include <warnings.h>
36 
37 #if defined(HAVE_CONFIG_H)
38 #include <config/bitcoin-config.h>
39 #endif
40 
41 #include <univalue.h>
42 
43 #include <boost/signals2/signal.hpp>
44 
45 namespace interfaces {
46 namespace {
47 
48 class NodeImpl : public Node
49 {
50 public:
51  NodeImpl(NodeContext* context) { setContext(context); }
52  void initLogging() override { InitLogging(*Assert(m_context->args)); }
53  void initParameterInteraction() override { InitParameterInteraction(*Assert(m_context->args)); }
54  bilingual_str getWarnings() override { return GetWarnings(true); }
55  uint32_t getLogCategories() override { return LogInstance().GetCategoryMask(); }
56  bool baseInitialize() override
57  {
60  }
61  bool appInitMain(interfaces::BlockAndHeaderTipInfo* tip_info) override
62  {
63  return AppInitMain(m_context_ref, *m_context, tip_info);
64  }
65  void appShutdown() override
66  {
69  }
70  void startShutdown() override
71  {
72  StartShutdown();
73  // Stop RPC for clean shutdown if any of waitfor* commands is executed.
74  if (gArgs.GetBoolArg("-server", false)) {
75  InterruptRPC();
76  StopRPC();
77  }
78  }
79  bool shutdownRequested() override { return ShutdownRequested(); }
80  void mapPort(bool use_upnp) override
81  {
82  if (use_upnp) {
83  StartMapPort();
84  } else {
86  StopMapPort();
87  }
88  }
89  bool getProxy(Network net, proxyType& proxy_info) override { return GetProxy(net, proxy_info); }
90  size_t getNodeCount(CConnman::NumConnections flags) override
91  {
92  return m_context->connman ? m_context->connman->GetNodeCount(flags) : 0;
93  }
94  bool getNodesStats(NodesStats& stats) override
95  {
96  stats.clear();
97 
98  if (m_context->connman) {
99  std::vector<CNodeStats> stats_temp;
100  m_context->connman->GetNodeStats(stats_temp);
101 
102  stats.reserve(stats_temp.size());
103  for (auto& node_stats_temp : stats_temp) {
104  stats.emplace_back(std::move(node_stats_temp), false, CNodeStateStats());
105  }
106 
107  // Try to retrieve the CNodeStateStats for each node.
108  TRY_LOCK(::cs_main, lockMain);
109  if (lockMain) {
110  for (auto& node_stats : stats) {
111  std::get<1>(node_stats) =
112  GetNodeStateStats(std::get<0>(node_stats).nodeid, std::get<2>(node_stats));
113  }
114  }
115  return true;
116  }
117  return false;
118  }
119  bool getBanned(banmap_t& banmap) override
120  {
121  if (m_context->banman) {
122  m_context->banman->GetBanned(banmap);
123  return true;
124  }
125  return false;
126  }
127  bool ban(const CNetAddr& net_addr, int64_t ban_time_offset) override
128  {
129  if (m_context->banman) {
130  m_context->banman->Ban(net_addr, ban_time_offset);
131  return true;
132  }
133  return false;
134  }
135  bool unban(const CSubNet& ip) override
136  {
137  if (m_context->banman) {
138  m_context->banman->Unban(ip);
139  return true;
140  }
141  return false;
142  }
143  bool disconnectByAddress(const CNetAddr& net_addr) override
144  {
145  if (m_context->connman) {
146  return m_context->connman->DisconnectNode(net_addr);
147  }
148  return false;
149  }
150  bool disconnectById(NodeId id) override
151  {
152  if (m_context->connman) {
153  return m_context->connman->DisconnectNode(id);
154  }
155  return false;
156  }
157  int64_t getTotalBytesRecv() override { return m_context->connman ? m_context->connman->GetTotalBytesRecv() : 0; }
158  int64_t getTotalBytesSent() override { return m_context->connman ? m_context->connman->GetTotalBytesSent() : 0; }
159  size_t getMempoolSize() override { return m_context->mempool ? m_context->mempool->size() : 0; }
160  size_t getMempoolDynamicUsage() override { return m_context->mempool ? m_context->mempool->DynamicMemoryUsage() : 0; }
161  bool getHeaderTip(int& height, int64_t& block_time) override
162  {
163  LOCK(::cs_main);
164  if (::pindexBestHeader) {
165  height = ::pindexBestHeader->nHeight;
166  block_time = ::pindexBestHeader->GetBlockTime();
167  return true;
168  }
169  return false;
170  }
171  int getNumBlocks() override
172  {
173  LOCK(::cs_main);
175  }
176  uint256 getBestBlockHash() override
177  {
178  const CBlockIndex* tip = WITH_LOCK(::cs_main, return ::ChainActive().Tip());
179  return tip ? tip->GetBlockHash() : Params().GenesisBlock().GetHash();
180  }
181  int64_t getLastBlockTime() override
182  {
183  LOCK(::cs_main);
184  if (::ChainActive().Tip()) {
186  }
187  return Params().GenesisBlock().GetBlockTime(); // Genesis block's time of current network
188  }
189  double getVerificationProgress() override
190  {
191  const CBlockIndex* tip;
192  {
193  LOCK(::cs_main);
194  tip = ::ChainActive().Tip();
195  }
196  return GuessVerificationProgress(Params().TxData(), tip);
197  }
198  bool isInitialBlockDownload() override { return ::ChainstateActive().IsInitialBlockDownload(); }
199  bool getReindex() override { return ::fReindex; }
200  bool getImporting() override { return ::fImporting; }
201  void setNetworkActive(bool active) override
202  {
203  if (m_context->connman) {
204  m_context->connman->SetNetworkActive(active);
205  }
206  }
207  bool getNetworkActive() override { return m_context->connman && m_context->connman->GetNetworkActive(); }
208  CFeeRate estimateSmartFee(int num_blocks, bool conservative, int* returned_target = nullptr) override
209  {
210  FeeCalculation fee_calc;
211  CFeeRate result = ::feeEstimator.estimateSmartFee(num_blocks, &fee_calc, conservative);
212  if (returned_target) {
213  *returned_target = fee_calc.returnedTarget;
214  }
215  return result;
216  }
217  CFeeRate getDustRelayFee() override { return ::dustRelayFee; }
218  UniValue executeRpc(const std::string& command, const UniValue& params, const std::string& uri) override
219  {
221  req.params = params;
222  req.strMethod = command;
223  req.URI = uri;
225  }
226  std::vector<std::string> listRpcCommands() override { return ::tableRPC.listCommands(); }
227  void rpcSetTimerInterfaceIfUnset(RPCTimerInterface* iface) override { RPCSetTimerInterfaceIfUnset(iface); }
228  void rpcUnsetTimerInterface(RPCTimerInterface* iface) override { RPCUnsetTimerInterface(iface); }
229  bool getUnspentOutput(const COutPoint& output, Coin& coin) override
230  {
231  LOCK(::cs_main);
232  return ::ChainstateActive().CoinsTip().GetCoin(output, coin);
233  }
234  WalletClient& walletClient() override
235  {
236  return *Assert(m_context->wallet_client);
237  }
238  std::unique_ptr<Handler> handleInitMessage(InitMessageFn fn) override
239  {
240  return MakeHandler(::uiInterface.InitMessage_connect(fn));
241  }
242  std::unique_ptr<Handler> handleMessageBox(MessageBoxFn fn) override
243  {
244  return MakeHandler(::uiInterface.ThreadSafeMessageBox_connect(fn));
245  }
246  std::unique_ptr<Handler> handleQuestion(QuestionFn fn) override
247  {
248  return MakeHandler(::uiInterface.ThreadSafeQuestion_connect(fn));
249  }
250  std::unique_ptr<Handler> handleShowProgress(ShowProgressFn fn) override
251  {
252  return MakeHandler(::uiInterface.ShowProgress_connect(fn));
253  }
254  std::unique_ptr<Handler> handleNotifyNumConnectionsChanged(NotifyNumConnectionsChangedFn fn) override
255  {
256  return MakeHandler(::uiInterface.NotifyNumConnectionsChanged_connect(fn));
257  }
258  std::unique_ptr<Handler> handleNotifyNetworkActiveChanged(NotifyNetworkActiveChangedFn fn) override
259  {
260  return MakeHandler(::uiInterface.NotifyNetworkActiveChanged_connect(fn));
261  }
262  std::unique_ptr<Handler> handleNotifyAlertChanged(NotifyAlertChangedFn fn) override
263  {
264  return MakeHandler(::uiInterface.NotifyAlertChanged_connect(fn));
265  }
266  std::unique_ptr<Handler> handleBannedListChanged(BannedListChangedFn fn) override
267  {
268  return MakeHandler(::uiInterface.BannedListChanged_connect(fn));
269  }
270  std::unique_ptr<Handler> handleNotifyBlockTip(NotifyBlockTipFn fn) override
271  {
272  return MakeHandler(::uiInterface.NotifyBlockTip_connect([fn](SynchronizationState sync_state, const CBlockIndex* block) {
273  fn(sync_state, BlockTip{block->nHeight, block->GetBlockTime(), block->GetBlockHash()},
274  GuessVerificationProgress(Params().TxData(), block));
275  }));
276  }
277  std::unique_ptr<Handler> handleNotifyHeaderTip(NotifyHeaderTipFn fn) override
278  {
279  return MakeHandler(
280  ::uiInterface.NotifyHeaderTip_connect([fn](SynchronizationState sync_state, const CBlockIndex* block) {
281  fn(sync_state, BlockTip{block->nHeight, block->GetBlockTime(), block->GetBlockHash()},
282  /* verification progress is unused when a header was received */ 0);
283  }));
284  }
285  NodeContext* context() override { return m_context; }
286  void setContext(NodeContext* context) override
287  {
288  m_context = context;
289  if (context) {
290  m_context_ref.Set(*context);
291  } else {
293  }
294  }
297 };
298 
299 } // namespace
300 
301 std::unique_ptr<Node> MakeNode(NodeContext* context) { return MakeUnique<NodeImpl>(context); }
302 
303 } // namespace interfaces
bool ShutdownRequested()
Definition: shutdown.cpp:20
RPC timer "driver".
Definition: server.h:60
void InitLogging(const ArgsManager &args)
Initialize global loggers.
Definition: init.cpp:871
SynchronizationState
Current sync state passed to tip changed callbacks.
Definition: validation.h:106
BCLog::Logger & LogInstance()
Definition: logging.cpp:14
int64_t GetBlockTime() const
Definition: chain.h:247
int returnedTarget
Definition: fees.h:73
#define TRY_LOCK(cs, name)
Definition: sync.h:234
void Shutdown(NodeContext &node)
Definition: init.cpp:178
A UTXO entry.
Definition: coins.h:30
Bilingual messages:
Definition: translation.h:16
CChain & ChainActive()
Please prefer the identical ChainstateManager::ActiveChain.
Definition: validation.cpp:113
std::unique_ptr< BanMan > banman
Definition: context.h:41
std::unique_ptr< CTxMemPool > mempool
Definition: context.h:38
bool GetNodeStateStats(NodeId nodeid, CNodeStateStats &stats)
Get statistics from node state.
util::Ref m_context_ref
Definition: node.cpp:296
int Height() const
Return the maximal height in the chain.
Definition: chain.h:415
void InterruptRPC()
Definition: server.cpp:291
const CBlock & GenesisBlock() const
Definition: chainparams.h:69
std::unique_ptr< Handler > MakeHandler(boost::signals2::connection connection)
Return handler wrapping a boost signal connection.
Definition: handler.cpp:36
bool GetBoolArg(const std::string &strArg, bool fDefault) const
Return boolean argument or default value.
Definition: system.cpp:478
void RPCUnsetTimerInterface(RPCTimerInterface *iface)
Unset factory function for timers.
Definition: server.cpp:493
UniValue execute(const JSONRPCRequest &request) const
Execute a method.
Definition: server.cpp:435
uint256 GetBlockHash() const
Definition: chain.h:233
void Set(T &value)
Definition: ref.h:27
CBlockPolicyEstimator feeEstimator
Definition: validation.cpp:151
void StopMapPort()
Definition: net.cpp:1672
CRPCTable tableRPC
Definition: server.cpp:517
bool AppInitSanityChecks()
Initialization sanity checks: ecc init, sanity checks, dir lock.
Definition: init.cpp:1219
NodeContext struct containing references to chain state and connection state.
Definition: context.h:36
std::unique_ptr< CConnman > connman
Definition: context.h:37
void Interrupt(NodeContext &node)
Interrupt threads.
Definition: init.cpp:162
CBlockIndex * pindexBestHeader
Best header we&#39;ve seen so far (used for getheaders queries&#39; starting points).
Definition: validation.cpp:131
#define LOCK(cs)
Definition: sync.h:230
CFeeRate estimateSmartFee(int confTarget, FeeCalculation *feeCalc, bool conservative) const
Estimate feerate needed to get be included in a block within confTarget blocks.
Definition: fees.cpp:781
interfaces::WalletClient * wallet_client
Reference to chain client that should used to load or create wallets opened by the gui...
Definition: context.h:48
RecursiveMutex cs_main
Mutex to guard access to validation specific variables, such as reading or changing the chainstate...
Definition: validation.cpp:129
uint32_t GetCategoryMask() const
Definition: logging.h:129
Network
A network type.
Definition: netaddress.h:43
Block and header tip information.
Definition: node.h:42
int64_t NodeId
Definition: net.h:92
NumConnections
Definition: net.h:191
std::atomic_bool fImporting
An outpoint - a combination of a transaction hash and an index n into its vout.
Definition: transaction.h:26
int64_t GetBlockTime() const
Definition: block.h:55
#define WITH_LOCK(cs, code)
Run code while locking a mutex.
Definition: sync.h:257
Type-safe dynamic reference.
Definition: ref.h:21
void RPCSetTimerInterfaceIfUnset(RPCTimerInterface *iface)
Set the factory function for timer, but only, if unset.
Definition: server.cpp:482
int flags
Definition: bitcoin-tx.cpp:506
std::atomic_bool fReindex
Network address.
Definition: netaddress.h:119
uint256 GetHash() const
Definition: block.cpp:11
256-bit opaque blob.
Definition: uint256.h:124
ArgsManager * args
Definition: context.h:42
CChainState & ChainstateActive()
Please prefer the identical ChainstateManager::ActiveChainstate.
Definition: validation.cpp:106
bilingual_str GetWarnings(bool verbose)
Format a string that describes several potential problems detected by the core.
Definition: warnings.cpp:44
void StopRPC()
Definition: server.cpp:302
bool GetCoin(const COutPoint &outpoint, Coin &coin) const override
Retrieve the Coin (unspent transaction output) for a given outpoint.
Definition: coins.cpp:59
bool AppInitParameterInteraction(const ArgsManager &args)
Initialization: parameter interaction.
Definition: init.cpp:959
The block chain is a tree shaped structure starting with the genesis block at the root...
Definition: chain.h:137
const CChainParams & Params()
Return the currently selected parameters.
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...
bool AppInitBasicSetup(ArgsManager &args)
Initialize bitcoin core: Basic context setup.
Definition: init.cpp:917
CBlockIndex * Tip() const
Returns the index entry for the tip of this chain, or nullptr if none.
Definition: chain.h:390
bool IsInitialBlockDownload() const
Check whether we are doing an initial block download (synchronizing from disk or network) ...
ArgsManager gArgs
Definition: system.cpp:76
Fee rate in satoshis per kilobyte: CAmount / kB.
Definition: feerate.h:29
NodeContext * m_context
Definition: node.cpp:295
void StartShutdown()
Definition: shutdown.cpp:12
CCoinsViewCache & CoinsTip() EXCLUSIVE_LOCKS_REQUIRED(cs_main)
Definition: validation.h:590
std::map< CSubNet, CBanEntry > banmap_t
Definition: net_types.h:13
bool GetProxy(enum Network net, proxyType &proxyInfoOut)
Definition: netbase.cpp:721
bool AppInitInterfaces(NodeContext &node)
Initialize node and wallet interface pointers.
Definition: init.cpp:1252
bool AppInitLockDataDirectory()
Lock bitcoin core data directory.
Definition: init.cpp:1240
bool AppInitMain(const util::Ref &context, NodeContext &node, interfaces::BlockAndHeaderTipInfo *tip_info)
Bitcoin core main initialization.
Definition: init.cpp:1263
CClientUIInterface uiInterface
int nHeight
height of the entry in the chain. The genesis block has height 0
Definition: chain.h:150
std::vector< std::string > listCommands() const
Returns a list of registered commands.
Definition: server.cpp:475
std::unique_ptr< Node > MakeNode(NodeContext *context)
Return implementation of Node interface.
Definition: node.cpp:301
void Clear()
Definition: ref.h:29
CFeeRate dustRelayFee
Definition: settings.cpp:13
void StartMapPort()
Definition: net.cpp:1664
void InitParameterInteraction(ArgsManager &args)
Parameter interaction: change current parameters depending on various rules.
Definition: init.cpp:802
void InterruptMapPort()
Definition: net.cpp:1668
#define Assert(val)
Identity function.
Definition: check.h:57