PIVX Core  5.6.99
P2P Digital Currency
net.cpp
Go to the documentation of this file.
1 // Copyright (c) 2009-2015 The Bitcoin developers
2 // Copyright (c) 2014-2015 The Dash developers
3 // Copyright (c) 2015-2022 The PIVX Core developers
4 // Distributed under the MIT software license, see the accompanying
5 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
6 
7 #include "rpc/server.h"
8 
9 #include "clientversion.h"
10 #include "net.h"
11 #include "netbase.h"
12 #include "net_processing.h"
13 #include "optional.h"
14 #include "protocol.h"
15 #include "sync.h"
16 #include "timedata.h"
17 #include "guiinterface.h"
18 #include "util/system.h"
19 #include "version.h"
20 #include "validation.h"
21 #include "warnings.h"
22 
23 #include <univalue.h>
24 
25 
27 {
28  if (request.fHelp || request.params.size() != 0)
29  throw std::runtime_error(
30  "getconnectioncount\n"
31  "\nReturns the number of connections to other nodes.\n"
32 
33  "\nbResult:\n"
34  "n (numeric) The connection count\n"
35 
36  "\nExamples:\n" +
37  HelpExampleCli("getconnectioncount", "") + HelpExampleRpc("getconnectioncount", ""));
38 
39  if(!g_connman)
40  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
41 
42  return (int)g_connman->GetNodeCount(CConnman::CONNECTIONS_ALL);
43 }
44 
45 UniValue ping(const JSONRPCRequest& request)
46 {
47  if (request.fHelp || request.params.size() != 0)
48  throw std::runtime_error(
49  "ping\n"
50  "\nRequests that a ping be sent to all other nodes, to measure ping time.\n"
51  "Results provided in getpeerinfo, pingtime and pingwait fields are decimal seconds.\n"
52  "Ping command is handled in queue with all other commands, so it measures processing backlog, not just network ping.\n"
53 
54  "\nExamples:\n" +
55  HelpExampleCli("ping", "") + HelpExampleRpc("ping", ""));
56 
57  if(!g_connman)
58  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
59 
60  // Request that each node send a ping during next message processing pass
61  g_connman->ForEachNode([](CNode* pnode) {
62  pnode->fPingQueued = true;
63  });
64  return NullUniValue;
65 }
66 
68 {
69  if (request.fHelp || request.params.size() != 0)
70  throw std::runtime_error(
71  "getpeerinfo\n"
72  "\nReturns data about each connected network node as a json array of objects.\n"
73 
74  "\nbResult:\n"
75  "[\n"
76  " {\n"
77  " \"id\": n, (numeric) Peer index\n"
78  " \"addr\":\"host:port\", (string) The ip address and port of the peer\n"
79  " \"addrlocal\":\"ip:port\", (string) local address\n"
80  " \"mapped_as\":\"mapped_as\", (string) The AS in the BGP route to the peer used for diversifying\n"
81  "peer selection (only available if the asmap config flag is set)\n"
82  " \"services\":\"xxxxxxxxxxxxxxxx\", (string) The services offered\n"
83  " \"lastsend\": ttt, (numeric) The time in seconds since epoch (Jan 1 1970 GMT) of the last send\n"
84  " \"lastrecv\": ttt, (numeric) The time in seconds since epoch (Jan 1 1970 GMT) of the last receive\n"
85  " \"bytessent\": n, (numeric) The total bytes sent\n"
86  " \"bytesrecv\": n, (numeric) The total bytes received\n"
87  " \"conntime\": ttt, (numeric) The connection time in seconds since epoch (Jan 1 1970 GMT)\n"
88  " \"timeoffset\": ttt, (numeric) The time offset in seconds\n"
89  " \"pingtime\": n, (numeric) ping time\n"
90  " \"pingwait\": n, (numeric) ping wait\n"
91  " \"version\": v, (numeric) The peer version, such as 7001\n"
92  " \"subver\": \"/Pivx Core:x.x.x.x/\", (string) The string version\n"
93  " \"inbound\": true|false, (boolean) Inbound (true) or Outbound (false)\n"
94  " \"addnode\": true|false, (boolean) Whether connection was due to addnode and is using an addnode slot\n"
95  " \"masternode\": true|false, (boolean) Whether the connection is only for masternode quorums related messages\n"
96  " \"startingheight\": n, (numeric) The starting height (block) of the peer\n"
97  " \"banscore\": n, (numeric) The ban score\n"
98  " \"synced_headers\": n, (numeric) The last header we have in common with this peer\n"
99  " \"synced_blocks\": n, (numeric) The last block we have in common with this peer\n"
100  " \"inflight\": [\n"
101  " n, (numeric) The heights of blocks we're currently asking from this peer\n"
102  " ...\n"
103  " ]\n"
104  " \"addr_processed\": n, (numeric) The total number of addresses processed, excluding those dropped due to rate limiting\n"
105  " \"addr_rate_limited\": n, (numeric) The total number of addresses dropped due to rate limiting\n"
106  " \"bytessent_per_msg\": {\n"
107  " \"addr\": n, (numeric) The total bytes sent aggregated by message type\n"
108  " ...\n"
109  " }\n"
110  " \"bytesrecv_per_msg\": {\n"
111  " \"addr\": n, (numeric) The total bytes received aggregated by message type\n"
112  " ...\n"
113  " }\n"
114  " \"masternode_iqr_conn\": true|false, (boolean) Whether the connection is an intra-quorum relay connection or not\n"
115  " \"verif_mn_proreg_tx_hash\": \"hex\", (string) The MN provider register tx hash (if the connection is verified)\n"
116  " \"verif_mn_operator_pubkey_hash\": \"hex\", (string) The MN operator pubkey hash (if the connection is verified)\n"
117  " }\n"
118  " ,...\n"
119  "]\n"
120 
121  "\nExamples:\n" +
122  HelpExampleCli("getpeerinfo", "") + HelpExampleRpc("getpeerinfo", ""));
123 
124  if(!g_connman)
125  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
126 
127  std::vector<CNodeStats> vstats;
128  g_connman->GetNodeStats(vstats);
129 
131 
132  for (const CNodeStats& stats : vstats) {
134  CNodeStateStats statestats;
135  bool fStateStats = GetNodeStateStats(stats.nodeid, statestats);
136  obj.pushKV("id", stats.nodeid);
137  obj.pushKV("addr", stats.addrName);
138  if (!(stats.addrLocal.empty()))
139  obj.pushKV("addrlocal", stats.addrLocal);
140  if (stats.m_mapped_as != 0) {
141  obj.pushKV("mapped_as", uint64_t(stats.m_mapped_as));
142  }
143  obj.pushKV("services", strprintf("%016x", stats.nServices));
144  obj.pushKV("lastsend", stats.nLastSend);
145  obj.pushKV("lastrecv", stats.nLastRecv);
146  obj.pushKV("bytessent", stats.nSendBytes);
147  obj.pushKV("bytesrecv", stats.nRecvBytes);
148  obj.pushKV("conntime", stats.nTimeConnected);
149  obj.pushKV("timeoffset", stats.nTimeOffset);
150  obj.pushKV("pingtime", stats.dPingTime);
151  if (stats.dPingWait > 0.0)
152  obj.pushKV("pingwait", stats.dPingWait);
153  obj.pushKV("version", stats.nVersion);
154  // Use the sanitized form of subver here, to avoid tricksy remote peers from
155  // corrupting or modifying the JSON output by putting special characters in
156  // their ver message.
157  obj.pushKV("subver", stats.cleanSubVer);
158  obj.pushKV("inbound", stats.fInbound);
159  obj.pushKV("addnode", stats.fAddnode);
160  obj.pushKV("masternode", stats.m_masternode_connection);
161  obj.pushKV("startingheight", stats.nStartingHeight);
162  if (fStateStats) {
163  obj.pushKV("banscore", statestats.nMisbehavior);
164  obj.pushKV("synced_headers", statestats.nSyncHeight);
165  obj.pushKV("synced_blocks", statestats.nCommonHeight);
166  UniValue heights(UniValue::VARR);
167  for (int height : statestats.vHeightInFlight) {
168  heights.push_back(height);
169  }
170  obj.pushKV("inflight", heights);
171  obj.pushKV("addr_processed", statestats.m_addr_processed);
172  obj.pushKV("addr_rate_limited", statestats.m_addr_rate_limited);
173  }
174  obj.pushKV("whitelisted", stats.fWhitelisted);
175 
176  UniValue sendPerMsgCmd(UniValue::VOBJ);
177  for (const mapMsgCmdSize::value_type &i : stats.mapSendBytesPerMsgCmd) {
178  if (i.second > 0)
179  sendPerMsgCmd.pushKV(i.first, i.second);
180  }
181  obj.pushKV("bytessent_per_msg", sendPerMsgCmd);
182 
183  UniValue recvPerMsgCmd(UniValue::VOBJ);
184  for (const mapMsgCmdSize::value_type &i : stats.mapRecvBytesPerMsgCmd) {
185  if (i.second > 0)
186  recvPerMsgCmd.pushKV(i.first, i.second);
187  }
188  obj.pushKV("bytesrecv_per_msg", recvPerMsgCmd);
189 
190  // DMN data
191  if (stats.m_masternode_connection) {
192  obj.pushKV("masternode_iqr_conn", stats.m_masternode_iqr_connection);
193  obj.pushKV("verif_mn_proreg_tx_hash", stats.verifiedProRegTxHash.GetHex());
194  obj.pushKV("verif_mn_operator_pubkey_hash", stats.verifiedPubKeyHash.GetHex());
195  }
196 
197  ret.push_back(obj);
198  }
199 
200  return ret;
201 }
202 
204 {
205  std::string strCommand;
206  if (request.params.size() == 2)
207  strCommand = request.params[1].get_str();
208  if (request.fHelp || request.params.size() != 2 ||
209  (strCommand != "onetry" && strCommand != "add" && strCommand != "remove"))
210  throw std::runtime_error(
211  "addnode \"node\" \"add|remove|onetry\"\n"
212  "\nAttempts add or remove a node from the addnode list.\n"
213  "Or try a connection to a node once.\n"
214 
215  "\nArguments:\n"
216  "1. \"node\" (string, required) The node (see getpeerinfo for nodes)\n"
217  "2. \"command\" (string, required) 'add' to add a node to the list, 'remove' to remove a node from the list, 'onetry' to try a connection to the node once\n"
218 
219  "\nExamples:\n" +
220  HelpExampleCli("addnode", "\"192.168.0.6:51472\" \"onetry\"") + HelpExampleRpc("addnode", "\"192.168.0.6:51472\", \"onetry\""));
221 
222  if(!g_connman)
223  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
224 
225  std::string strNode = request.params[0].get_str();
226 
227  if (strCommand == "onetry") {
228  CAddress addr;
229  g_connman->OpenNetworkConnection(addr, false, nullptr, strNode.c_str());
230  return NullUniValue;
231  }
232 
233  if (strCommand == "add") {
234  if(!g_connman->AddNode(strNode))
235  throw JSONRPCError(RPC_CLIENT_NODE_ALREADY_ADDED, "Error: Node already added");
236  } else if (strCommand == "remove") {
237  if(!g_connman->RemoveAddedNode(strNode))
238  throw JSONRPCError(RPC_CLIENT_NODE_NOT_ADDED, "Error: Node has not been added.");
239  }
240 
241  return NullUniValue;
242 }
243 
245 {
246  if (request.fHelp || request.params.size() != 1)
247  throw std::runtime_error(
248  "disconnectnode \"node\" \n"
249  "\nImmediately disconnects from the specified node.\n"
250 
251  "\nArguments:\n"
252  "1. \"node\" (string, required) The node (see getpeerinfo for nodes)\n"
253 
254  "\nExamples:\n"
255  + HelpExampleCli("disconnectnode", "\"192.168.0.6:8333\"")
256  + HelpExampleRpc("disconnectnode", "\"192.168.0.6:8333\"")
257  );
258 
259  if(!g_connman)
260  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
261 
262  bool ret = g_connman->DisconnectNode(request.params[0].get_str());
263  if (!ret)
264  throw JSONRPCError(RPC_CLIENT_NODE_NOT_CONNECTED, "Node not found in connected nodes");
265 
266  return NullUniValue;
267 }
268 
270 {
271  if (request.fHelp || request.params.size() < 1 || request.params.size() > 2)
272  throw std::runtime_error(
273  "getaddednodeinfo dummy ( \"node\" )\n"
274  "\nReturns information about the given added node, or all added nodes\n"
275  "(note that onetry addnodes are not listed here)\n"
276 
277  "\nArguments:\n"
278  "1. dummy (boolean, required) Kept for historical purposes but ignored\n"
279  "2. \"node\" (string, optional) If provided, return information about this specific node, otherwise all nodes are returned.\n"
280 
281  "\nResult:\n"
282  "[\n"
283  " {\n"
284  " \"addednode\" : \"192.168.0.201\", (string) The node ip address or name (as provided to addnode)\n"
285  " \"connected\" : true|false, (boolean) If connected\n"
286  " \"addresses\" : [ (list of objects) Only when connected = true\n"
287  " {\n"
288  " \"address\" : \"192.168.0.201:51472\", (string) The pivx server IP and port we're connected to\n"
289  " \"connected\" : \"outbound\" (string) connection, inbound or outbound\n"
290  " }\n"
291  " ]\n"
292  " }\n"
293  " ,...\n"
294  "]\n"
295 
296  "\nExamples:\n" +
297  HelpExampleCli("getaddednodeinfo", "true") + HelpExampleCli("getaddednodeinfo", "true \"192.168.0.201\"") + HelpExampleRpc("getaddednodeinfo", "true, \"192.168.0.201\""));
298 
299  if(!g_connman)
300  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
301 
302  std::vector<AddedNodeInfo> vInfo = g_connman->GetAddedNodeInfo();
303 
304  if (request.params.size() == 2) {
305  bool found = false;
306  for (const AddedNodeInfo& info : vInfo) {
307  if (info.strAddedNode == request.params[1].get_str()) {
308  vInfo.assign(1, info);
309  found = true;
310  break;
311  }
312  }
313  if (!found) {
314  throw JSONRPCError(RPC_CLIENT_NODE_NOT_ADDED, "Error: Node has not been added.");
315  }
316  }
317 
319 
320  for (const AddedNodeInfo& info : vInfo) {
322  obj.pushKV("addednode", info.strAddedNode);
323  obj.pushKV("connected", info.fConnected);
324  UniValue addresses(UniValue::VARR);
325  if (info.fConnected) {
326  UniValue address(UniValue::VOBJ);
327  address.pushKV("address", info.resolvedAddress.ToString());
328  address.pushKV("connected", info.fInbound ? "inbound" : "outbound");
329  addresses.push_back(address);
330  }
331  obj.pushKV("addresses", addresses);
332  ret.push_back(obj);
333  }
334 
335  return ret;
336 }
337 
339 {
340  if (request.fHelp || request.params.size() > 0)
341  throw std::runtime_error(
342  "getnettotals\n"
343  "\nReturns information about network traffic, including bytes in, bytes out,\n"
344  "and current time.\n"
345 
346  "\nResult:\n"
347  "{\n"
348  " \"totalbytesrecv\": n, (numeric) Total bytes received\n"
349  " \"totalbytessent\": n, (numeric) Total bytes sent\n"
350  " \"timemillis\": t (numeric) Total cpu time\n"
351  "}\n"
352 
353  "\nExamples:\n" +
354  HelpExampleCli("getnettotals", "") + HelpExampleRpc("getnettotals", ""));
355 
356  if(!g_connman)
357  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
358 
360  obj.pushKV("totalbytesrecv", g_connman->GetTotalBytesRecv());
361  obj.pushKV("totalbytessent", g_connman->GetTotalBytesSent());
362  obj.pushKV("timemillis", GetTimeMillis());
363  return obj;
364 }
365 
366 static UniValue GetNetworksInfo()
367 {
368  UniValue networks(UniValue::VARR);
369  for (int n = 0; n < NET_MAX; ++n) {
370  enum Network network = static_cast<enum Network>(n);
371  if (network == NET_UNROUTABLE || network == NET_I2P || network == NET_CJDNS || network == NET_INTERNAL) continue;
372  proxyType proxy;
374  GetProxy(network, proxy);
375  obj.pushKV("name", GetNetworkName(network));
376  obj.pushKV("limited", !IsReachable(network));
377  obj.pushKV("reachable", IsReachable(network));
378  obj.pushKV("proxy", proxy.IsValid() ? proxy.proxy.ToStringIPPort() : std::string());
379  obj.pushKV("proxy_randomize_credentials", proxy.randomize_credentials);
380  networks.push_back(obj);
381  }
382  return networks;
383 }
384 
386 {
387  if (request.fHelp || request.params.size() != 0)
388  throw std::runtime_error(
389  "getnetworkinfo\n"
390  "\nReturns an object containing various state info regarding P2P networking.\n"
391 
392  "\nResult:\n"
393  "{\n"
394  " \"version\": xxxxx, (numeric) the server version\n"
395  " \"subversion\": \"/Pivx Core:x.x.x.x/\", (string) the server subversion string\n"
396  " \"protocolversion\": xxxxx, (numeric) the protocol version\n"
397  " \"localservices\": \"xxxxxxxxxxxxxxxx\", (string) the services we offer to the network\n"
398  " \"timeoffset\": xxxxx, (numeric) the time offset\n"
399  " \"connections\": xxxxx, (numeric) the number of connections\n"
400  " \"networkactive\": true|false, (boolean) the network activity status\n"
401  " \"networks\": [ (array) information per network\n"
402  " {\n"
403  " \"name\": \"xxx\", (string) network (ipv4, ipv6 or onion)\n"
404  " \"limited\": true|false, (boolean) is the network limited using -onlynet?\n"
405  " \"reachable\": true|false, (boolean) is the network reachable?\n"
406  " \"proxy\": \"host:port\" (string) the proxy that is used for this network, or empty if none\n"
407  " }\n"
408  " ,...\n"
409  " ],\n"
410  " \"relayfee\": x.xxxxxxxx, (numeric) minimum relay fee for transactions in " + CURRENCY_UNIT + "/kB\n"
411  " \"incrementalfee\": x.xxxxxxxx, (numeric) minimum fee increment for mempool limiting or BIP 125 replacement in " + CURRENCY_UNIT + "/kB\n"
412  " \"localaddresses\": [ (array) list of local addresses\n"
413  " {\n"
414  " \"address\": \"xxxx\", (string) network address\n"
415  " \"port\": xxx, (numeric) network port\n"
416  " \"score\": xxx (numeric) relative score\n"
417  " }\n"
418  " ,...\n"
419  " ]\n"
420  " \"warnings\": \"...\" (string) any network and blockchain warnings\n"
421  "}\n"
422 
423  "\nExamples:\n" +
424  HelpExampleCli("getnetworkinfo", "") + HelpExampleRpc("getnetworkinfo", ""));
425 
426  LOCK(cs_main);
428  obj.pushKV("version", CLIENT_VERSION);
429  obj.pushKV("subversion", strSubVersion);
430  obj.pushKV("protocolversion", PROTOCOL_VERSION);
431  if (g_connman)
432  obj.pushKV("localservices", strprintf("%016x", g_connman->GetLocalServices()));
433  obj.pushKV("timeoffset", GetTimeOffset());
434  if (g_connman) {
435  obj.pushKV("networkactive", g_connman->GetNetworkActive());
436  obj.pushKV("connections", (int)g_connman->GetNodeCount(CConnman::CONNECTIONS_ALL));
437  }
438  obj.pushKV("networks", GetNetworksInfo());
439  obj.pushKV("relayfee", ValueFromAmount(::minRelayTxFee.GetFeePerK()));
440  UniValue localAddresses(UniValue::VARR);
441  {
443  for (const std::pair<const CNetAddr, LocalServiceInfo> &item : mapLocalHost) {
445  rec.pushKV("address", item.first.ToString());
446  rec.pushKV("port", item.second.nPort);
447  rec.pushKV("score", item.second.nScore);
448  localAddresses.push_back(rec);
449  }
450  }
451  obj.pushKV("localaddresses", localAddresses);
452  obj.pushKV("warnings", GetWarnings("statusbar"));
453  return obj;
454 }
455 
457 {
458  std::string strCommand;
459  if (request.params.size() >= 2)
460  strCommand = request.params[1].get_str();
461  if (request.fHelp || request.params.size() < 2 ||
462  (strCommand != "add" && strCommand != "remove"))
463  throw std::runtime_error(
464  "setban \"subnet\" \"add|remove\" ( bantime absolute )\n"
465  "\nAttempts add or remove a IP/Subnet from the banned list.\n"
466 
467  "\nArguments:\n"
468  "1. \"subnet\" (string, required) The IP/Subnet (see getpeerinfo for nodes ip) with a optional netmask (default is /32 = single ip)\n"
469  "2. \"command\" (string, required) 'add' to add a IP/Subnet to the list, 'remove' to remove a IP/Subnet from the list\n"
470  "3. \"bantime\" (numeric, optional) time in seconds how long (or until when if [absolute] is set) the ip is banned (0 or empty means using the default time of 24h which can also be overwritten by the -bantime startup argument)\n"
471  "4. \"absolute\" (boolean, optional) If set, the bantime must be a absolute timestamp in seconds since epoch (Jan 1 1970 GMT)\n"
472 
473  "\nExamples:\n"
474  + HelpExampleCli("setban", "\"192.168.0.6\" \"add\" 86400")
475  + HelpExampleCli("setban", "\"192.168.0.0/24\" \"add\"")
476  + HelpExampleRpc("setban", "\"192.168.0.6\", \"add\" 86400"));
477 
478  if (!g_connman)
479  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
480 
481  CSubNet subNet;
482  CNetAddr netAddr;
483  bool isSubnet = false;
484 
485  if (request.params[0].get_str().find('/') != std::string::npos)
486  isSubnet = true;
487 
488  if (!isSubnet) {
489  CNetAddr resolved;
490  LookupHost(request.params[0].get_str(), resolved, false);
491  netAddr = resolved;
492  } else
493  LookupSubNet(request.params[0].get_str(), subNet);
494 
495  if (! (isSubnet ? subNet.IsValid() : netAddr.IsValid()) )
496  throw JSONRPCError(RPC_CLIENT_NODE_ALREADY_ADDED, "Error: Invalid IP/Subnet");
497 
498  if (strCommand == "add")
499  {
500  if (isSubnet ? g_connman->IsBanned(subNet) : g_connman->IsBanned(netAddr))
501  throw JSONRPCError(RPC_CLIENT_NODE_ALREADY_ADDED, "Error: IP/Subnet already banned");
502 
503  int64_t banTime = 0; //use standard bantime if not specified
504  if (request.params.size() >= 3 && !request.params[2].isNull())
505  banTime = request.params[2].get_int64();
506 
507  bool absolute = false;
508  if (request.params.size() == 4)
509  absolute = request.params[3].get_bool();
510 
511  isSubnet ? g_connman->Ban(subNet, BanReasonManuallyAdded, banTime, absolute) : g_connman->Ban(netAddr, BanReasonManuallyAdded, banTime, absolute);
512  }
513  else if(strCommand == "remove")
514  {
515  if (!( isSubnet ? g_connman->Unban(subNet) : g_connman->Unban(netAddr) ))
516  throw JSONRPCError(RPC_MISC_ERROR, "Error: Unban failed");
517  }
518  return NullUniValue;
519 }
520 
522 {
523  if (request.fHelp || request.params.size() != 0)
524  throw std::runtime_error(
525  "listbanned\n"
526  "\nList all banned IPs/Subnets.\n"
527 
528  "\nResult:\n"
529  "[\n"
530  " {\n"
531  " \"address\": \"xxx\", (string) Network address of banned client.\n"
532  " \"banned_until\": nnn, (numeric) Timestamp when the ban is lifted.\n"
533  " \"ban_created\": nnn, (numeric) Timestamp when the ban was created.\n"
534  " \"ban_reason\": \"xxx\" (string) Reason for banning.\n"
535  " }\n"
536  " ,...\n"
537  "]\n"
538 
539  "\nExamples:\n"
540  + HelpExampleCli("listbanned", "")
541  + HelpExampleRpc("listbanned", ""));
542 
543  if (!g_connman)
544  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
545 
546  banmap_t banMap;
547  g_connman->GetBanned(banMap);
548 
549  UniValue bannedAddresses(UniValue::VARR);
550  for (const auto& entry : banMap)
551  {
552  const CBanEntry& banEntry = entry.second;
554  rec.pushKV("address", entry.first.ToString());
555  rec.pushKV("banned_until", banEntry.nBanUntil);
556  rec.pushKV("ban_created", banEntry.nCreateTime);
557  rec.pushKV("ban_reason", banEntry.banReasonToString());
558 
559  bannedAddresses.push_back(rec);
560  }
561 
562  return bannedAddresses;
563 }
564 
566 {
567  if (request.fHelp || request.params.size() != 0)
568  throw std::runtime_error(
569  "clearbanned\n"
570  "\nClear all banned IPs.\n"
571 
572  "\nExamples:\n"
573  + HelpExampleCli("clearbanned", "")
574  + HelpExampleRpc("clearbanned", ""));
575 
576  if (!g_connman)
577  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
578 
579  g_connman->ClearBanned();
580 
581  return NullUniValue;
582 }
583 
584 static UniValue getnodeaddresses(const JSONRPCRequest& request)
585 {
586  if (request.fHelp || request.params.size() > 2) {
587  throw std::runtime_error(
588  "getnodeaddresses ( count \"network\" )\n"
589  "\nReturn known addresses which can potentially be used to find new nodes in the network\n"
590 
591  "\nArguments:\n"
592  "1. count (numeric, optional) The maximum number of addresses to return. Specify 0 to return all known addresses.\n"
593  "2. \"network\" (string, optional) Return only addresses of the specified network. Can be one of: ipv4, ipv6, onion."
594 
595  "\nResult:\n"
596  "[\n"
597  " {\n"
598  " \"time\": ttt, (numeric) Timestamp in seconds since epoch (Jan 1 1970 GMT) when the node was last seen\n"
599  " \"services\": n, (numeric) The services offered by the node\n"
600  " \"address\": \"host\", (string) The address of the node\n"
601  " \"port\": n, (numeric) The port number of the node\n"
602  " \"network\": \"xxxx\" (string) The network (ipv4, ipv6, onion) the node connected through\n"
603  " }\n"
604  " ,...\n"
605  "]\n"
606 
607  "\nExamples:\n"
608  + HelpExampleCli("getnodeaddresses", "8")
609  + HelpExampleCli("getnodeaddresses", "4 \"ipv4\"")
610  + HelpExampleRpc("getnodeaddresses", "8")
611  + HelpExampleRpc("getnodeaddresses", "4 \"ipv4\"")
612  );
613  }
614  if (!g_connman) {
615  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
616  }
617 
618  const int count{request.params[0].isNull() ? 1 : request.params[0].get_int()};
619  if (count < 0) throw JSONRPCError(RPC_INVALID_PARAMETER, "Address count out of range");
620 
621  const Optional<Network> network{request.params[1].isNull() ? nullopt : Optional<Network>{ParseNetwork(request.params[1].get_str())}};
622  if (network == NET_UNROUTABLE) {
623  throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("Network not recognized: %s", request.params[1].get_str()));
624  }
625 
626  // returns a shuffled list of CAddress
627  const std::vector<CAddress> vAddr{g_connman->GetAddresses(count, /* max_pct */ 0, network)};
629 
630  for (const CAddress& addr : vAddr) {
632  obj.pushKV("time", (int)addr.nTime);
633  obj.pushKV("services", (uint64_t)addr.nServices);
634  obj.pushKV("address", addr.ToStringIP());
635  obj.pushKV("port", addr.GetPort());
636  obj.pushKV("network", GetNetworkName(addr.GetNetClass()));
637  ret.push_back(obj);
638  }
639  return ret;
640 }
641 
642 static UniValue addpeeraddress(const JSONRPCRequest& request)
643 {
644  if (request.fHelp || request.params.size() != 2) {
645  throw std::runtime_error(
646  "addpeeraddress \"address\" port\n"
647  "\nAdd the address of a potential peer to the address manager. This RPC is for testing only.\n"
648 
649  "\nArguments\n"
650  "1. \"address\" (string, required) The IP address of the peer\n"
651  "2. port (numeric, required) The port of the peer\n"
652 
653  "\nResult:\n"
654  "{\n"
655  " \"success\": true|false (boolean) Whether the peer address was successfully added to the address manager\n"
656  "}\n"
657 
658  "\nExamples:\n"
659  + HelpExampleCli("addpeeraddress", "\"1.2.3.4\" 51472")
660  + HelpExampleRpc("addpeeraddress", "\"1.2.3.4\", 51472"));
661  }
662  if (!g_connman) {
663  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
664  }
665 
667 
668  std::string addr_string = request.params[0].get_str();
669  uint16_t port = request.params[1].get_int();
670 
671  CNetAddr net_addr;
672  if (!LookupHost(addr_string, net_addr, false)) {
673  obj.pushKV("success", false);
674  return obj;
675  }
676  CAddress address = CAddress({net_addr, port}, ServiceFlags(NODE_NETWORK));
677  address.nTime = GetAdjustedTime();
678  // The source address is set equal to the address. This is equivalent to the peer
679  // announcing itself.
680  if (!g_connman->AddNewAddresses({address}, address)) {
681  obj.pushKV("success", false);
682  return obj;
683  }
684 
685  obj.pushKV("success", true);
686  return obj;
687 }
688 
690 {
691  if (request.fHelp || request.params.size() != 1) {
692  throw std::runtime_error(
693  "setnetworkactive \"true|false\"\n"
694  "Disable/enable all p2p network activity.\n"
695 
696  "\nResult:\n"
697  "status (boolean) The final network activity status\n"
698  "\nExamples:\n" +
699  HelpExampleCli("setnetworkactive", "true") + HelpExampleRpc("setnetworkactive", "true"));
700  }
701  if (!g_connman) {
702  throw JSONRPCError(RPC_CLIENT_P2P_DISABLED, "Error: Peer-to-peer functionality missing or disabled");
703  }
704  g_connman->SetNetworkActive(request.params[0].get_bool());
705  return g_connman->GetNetworkActive();
706 }
707 
708 // clang-format off
709 static const CRPCCommand commands[] =
710 { // category name actor (function) okSafe argNames
711  // --------------------- ------------------------ ----------------------- ------ --------
712  { "network", "addnode", &addnode, true, {"node","command"} },
713  { "network", "clearbanned", &clearbanned, true, {} },
714  { "network", "disconnectnode", &disconnectnode, true, {"node"} },
715  { "network", "getaddednodeinfo", &getaddednodeinfo, true, {"dummy","node"} },
716  { "network", "getconnectioncount", &getconnectioncount, true, {} },
717  { "network", "getnettotals", &getnettotals, true, {} },
718  { "network", "getnetworkinfo", &getnetworkinfo, true, {} },
719  { "network", "getnodeaddresses", &getnodeaddresses, true, {"count"} },
720  { "network", "getpeerinfo", &getpeerinfo, true, {} },
721  { "network", "listbanned", &listbanned, true, {} },
722  { "network", "ping", &ping, true, {} },
723  { "network", "setban", &setban, true, {"subnet", "command", "bantime", "absolute"} },
724  { "network", "setnetworkactive", &setnetworkactive, true, {"active"} },
725 
727  { "hidden", "addpeeraddress", &addpeeraddress, true, {"address", "port"} },
728 };
729 // clang-format on
730 
732 {
733  for (unsigned int vcidx = 0; vcidx < ARRAYLEN(commands); vcidx++)
734  tableRPC.appendCommand(commands[vcidx].name, &commands[vcidx]);
735 }
@ BanReasonManuallyAdded
Definition: addrdb.h:25
std::map< CSubNet, CBanEntry > banmap_t
Definition: addrdb.h:71
A CService with information about it as peer.
Definition: protocol.h:338
uint32_t nTime
Always included in serialization, except in the network format on INIT_PROTO_VERSION.
Definition: protocol.h:428
Definition: addrdb.h:29
std::string banReasonToString() const
Definition: addrdb.h:58
int64_t nCreateTime
Definition: addrdb.h:33
int64_t nBanUntil
Definition: addrdb.h:34
@ CONNECTIONS_ALL
Definition: net.h:152
CAmount GetFeePerK() const
Definition: feerate.h:29
Network address.
Definition: netaddress.h:120
bool IsValid() const
Definition: netaddress.cpp:418
Information about a peer.
Definition: net.h:669
std::atomic< bool > fPingQueued
Definition: net.h:796
std::string name
Definition: server.h:137
PIVX RPC command dispatcher.
Definition: server.h:147
bool appendCommand(const std::string &name, const CRPCCommand *pcmd)
Appends a CRPCCommand to the dispatch table.
Definition: server.cpp:314
std::string ToStringIPPort() const
Definition: netaddress.cpp:945
bool IsValid() const
UniValue params
Definition: server.h:47
bool fHelp
Definition: server.h:48
const std::string & get_str() const
@ VOBJ
Definition: univalue.h:21
@ VARR
Definition: univalue.h:21
int64_t get_int64() const
bool isNull() const
Definition: univalue.h:77
size_t size() const
Definition: univalue.h:68
bool push_back(const UniValue &val)
Definition: univalue.cpp:108
bool pushKV(const std::string &key, const UniValue &val)
Definition: univalue.cpp:133
bool get_bool() const
int get_int() const
bool IsValid() const
Definition: netbase.h:35
CService proxy
Definition: netbase.h:37
bool randomize_credentials
Definition: netbase.h:38
const std::string CURRENCY_UNIT
Definition: feerate.cpp:11
std::unique_ptr< CConnman > g_connman
Definition: init.cpp:90
@ LOCK
Definition: lockunlock.h:16
std::map< CNetAddr, LocalServiceInfo > mapLocalHost
Definition: net.cpp:92
RecursiveMutex cs_mapLocalHost
Definition: net.cpp:91
std::string strSubVersion
Subversion as sent to the P2P network in version messages.
Definition: net.cpp:94
bool IsReachable(enum Network net)
Definition: net.cpp:253
bool GetNodeStateStats(NodeId nodeid, CNodeStateStats &stats)
Get statistics from node state.
RecursiveMutex cs_main
Global state.
Definition: validation.cpp:80
Network
A network type.
Definition: netaddress.h:44
@ NET_I2P
I2P.
Definition: netaddress.h:58
@ NET_CJDNS
CJDNS.
Definition: netaddress.h:61
@ NET_MAX
Dummy value to indicate the number of NET_* constants.
Definition: netaddress.h:68
@ NET_UNROUTABLE
Addresses from these networks are not publicly routable on the global Internet.
Definition: netaddress.h:46
@ NET_INTERNAL
A set of addresses that represent the hash of a string or FQDN.
Definition: netaddress.h:65
enum Network ParseNetwork(std::string net)
Definition: netbase.cpp:46
std::string GetNetworkName(enum Network net)
Definition: netbase.cpp:55
bool GetProxy(enum Network net, proxyType &proxyInfoOut)
Definition: netbase.cpp:605
bool LookupHost(const std::string &name, std::vector< CNetAddr > &vIP, unsigned int nMaxSolutions, bool fAllowLookup)
Definition: netbase.cpp:149
bool LookupSubNet(const std::string &strSubnet, CSubNet &ret)
Definition: netbase.cpp:673
boost::optional< T > Optional
Substitute for C++17 std::optional.
Definition: optional.h:12
ServiceFlags
nServices flags
Definition: protocol.h:312
@ NODE_NETWORK
Definition: protocol.h:318
UniValue getpeerinfo(const JSONRPCRequest &request)
Definition: net.cpp:67
UniValue setban(const JSONRPCRequest &request)
Definition: net.cpp:456
UniValue setnetworkactive(const JSONRPCRequest &request)
Definition: net.cpp:689
UniValue clearbanned(const JSONRPCRequest &request)
Definition: net.cpp:565
UniValue getnettotals(const JSONRPCRequest &request)
Definition: net.cpp:338
void RegisterNetRPCCommands(CRPCTable &tableRPC)
Register P2P networking RPC commands.
Definition: net.cpp:731
UniValue getnetworkinfo(const JSONRPCRequest &request)
Definition: net.cpp:385
UniValue ping(const JSONRPCRequest &request)
Definition: net.cpp:45
UniValue listbanned(const JSONRPCRequest &request)
Definition: net.cpp:521
UniValue addnode(const JSONRPCRequest &request)
Definition: net.cpp:203
UniValue disconnectnode(const JSONRPCRequest &request)
Definition: net.cpp:244
UniValue getconnectioncount(const JSONRPCRequest &request)
Definition: net.cpp:26
UniValue getaddednodeinfo(const JSONRPCRequest &request)
Definition: net.cpp:269
UniValue JSONRPCError(int code, const std::string &message)
Definition: protocol.cpp:53
@ RPC_CLIENT_NODE_NOT_CONNECTED
Node has not been added before.
Definition: protocol.h:65
@ RPC_MISC_ERROR
General application defined errors.
Definition: protocol.h:41
@ RPC_CLIENT_NODE_ALREADY_ADDED
Still downloading initial blocks.
Definition: protocol.h:63
@ RPC_INVALID_PARAMETER
Ran out of memory during operation.
Definition: protocol.h:46
@ RPC_CLIENT_NODE_NOT_ADDED
Node is already added.
Definition: protocol.h:64
@ RPC_CLIENT_P2P_DISABLED
Invalid IP/Subnet.
Definition: protocol.h:67
UniValue ValueFromAmount(const CAmount &amount)
Definition: server.cpp:128
std::string HelpExampleCli(std::string methodname, std::string args)
Definition: server.cpp:527
std::string HelpExampleRpc(std::string methodname, std::string args)
Definition: server.cpp:532
CRPCTable tableRPC
Definition: server.cpp:565
std::vector< int > vHeightInFlight
uint64_t m_addr_rate_limited
uint64_t m_addr_processed
int64_t GetAdjustedTime()
Definition: timedata.cpp:36
int64_t GetTimeOffset()
"Never go to sea with two chronometers; take one or three." Our three time sources are:
Definition: timedata.cpp:30
#define strprintf
Definition: tinyformat.h:1056
const UniValue NullUniValue
Definition: univalue.cpp:13
#define ARRAYLEN(array)
int64_t GetTimeMillis()
Returns the system time (not mockable)
Definition: utiltime.cpp:61
CFeeRate minRelayTxFee
Fees smaller than this (in upiv) are considered zero fee (for relaying, mining and transaction creati...
Definition: validation.cpp:108
std::string GetWarnings(const std::string &strFor)
Definition: warnings.cpp:47