]> Git Repo - VerusCoin.git/blame - src/rpcnet.cpp
Auto merge of #1907 - bitcartel:1903_z_sendmany_fee_parameter, r=ebfull
[VerusCoin.git] / src / rpcnet.cpp
CommitLineData
f914f1a7 1// Copyright (c) 2009-2014 The Bitcoin Core developers
72fb3d29 2// Distributed under the MIT software license, see the accompanying
70ab73a0 3// file COPYING or http://www.opensource.org/licenses/mit-license.php.
b2864d2f 4
fdbdb7f3 5#include "rpcserver.h"
b2864d2f 6
71697f97 7#include "clientversion.h"
b2864d2f 8#include "main.h"
51ed9ec9
BD
9#include "net.h"
10#include "netbase.h"
11#include "protocol.h"
12#include "sync.h"
14f888ca 13#include "timedata.h"
51ed9ec9 14#include "util.h"
ff36cbe8 15#include "version.h"
51ed9ec9 16
51ed9ec9 17#include <boost/foreach.hpp>
611116d4 18
51ed9ec9 19#include "json/json_spirit_value.h"
70ab73a0
JG
20
21using namespace json_spirit;
22using namespace std;
23
24Value getconnectioncount(const Array& params, bool fHelp)
25{
26 if (fHelp || params.size() != 0)
27 throw runtime_error(
28 "getconnectioncount\n"
a6099ef3 29 "\nReturns the number of connections to other nodes.\n"
30 "\nbResult:\n"
31 "n (numeric) The connection count\n"
32 "\nExamples:\n"
33 + HelpExampleCli("getconnectioncount", "")
34 + HelpExampleRpc("getconnectioncount", "")
35 );
70ab73a0 36
4401b2d7
EL
37 LOCK2(cs_main, cs_vNodes);
38
70ab73a0
JG
39 return (int)vNodes.size();
40}
41
971bb3e9
JL
42Value ping(const Array& params, bool fHelp)
43{
44 if (fHelp || params.size() != 0)
45 throw runtime_error(
46 "ping\n"
a6099ef3 47 "\nRequests that a ping be sent to all other nodes, to measure ping time.\n"
971bb3e9 48 "Results provided in getpeerinfo, pingtime and pingwait fields are decimal seconds.\n"
6943cb9b 49 "Ping command is handled in queue with all other commands, so it measures processing backlog, not just network ping.\n"
a6099ef3 50 "\nExamples:\n"
51 + HelpExampleCli("ping", "")
52 + HelpExampleRpc("ping", "")
53 );
4315ec1a 54
971bb3e9 55 // Request that each node send a ping during next message processing pass
4401b2d7
EL
56 LOCK2(cs_main, cs_vNodes);
57
971bb3e9
JL
58 BOOST_FOREACH(CNode* pNode, vNodes) {
59 pNode->fPingQueued = true;
60 }
61
62 return Value::null;
63}
64
1006f070
JG
65static void CopyNodeStats(std::vector<CNodeStats>& vstats)
66{
67 vstats.clear();
68
69 LOCK(cs_vNodes);
70 vstats.reserve(vNodes.size());
71 BOOST_FOREACH(CNode* pnode, vNodes) {
72 CNodeStats stats;
73 pnode->copyStats(stats);
74 vstats.push_back(stats);
75 }
76}
77
78Value getpeerinfo(const Array& params, bool fHelp)
79{
80 if (fHelp || params.size() != 0)
81 throw runtime_error(
82 "getpeerinfo\n"
a6099ef3 83 "\nReturns data about each connected network node as a json array of objects.\n"
84 "\nbResult:\n"
85 "[\n"
86 " {\n"
c4a321f5 87 " \"id\": n, (numeric) Peer index\n"
a6099ef3 88 " \"addr\":\"host:port\", (string) The ip address and port of the peer\n"
89 " \"addrlocal\":\"ip:port\", (string) local address\n"
99ddc6cb 90 " \"services\":\"xxxxxxxxxxxxxxxx\", (string) The services offered\n"
a6099ef3 91 " \"lastsend\": ttt, (numeric) The time in seconds since epoch (Jan 1 1970 GMT) of the last send\n"
92 " \"lastrecv\": ttt, (numeric) The time in seconds since epoch (Jan 1 1970 GMT) of the last receive\n"
93 " \"bytessent\": n, (numeric) The total bytes sent\n"
94 " \"bytesrecv\": n, (numeric) The total bytes received\n"
95 " \"conntime\": ttt, (numeric) The connection time in seconds since epoch (Jan 1 1970 GMT)\n"
26a6bae7 96 " \"timeoffset\": ttt, (numeric) The time offset in seconds\n"
a6099ef3 97 " \"pingtime\": n, (numeric) ping time\n"
98 " \"pingwait\": n, (numeric) ping wait\n"
5bd677f5
S
99 " \"version\": v, (numeric) The peer version, such as 170002\n"
100 " \"subver\": \"/MagicBean:x.y.z[-v]/\", (string) The string version\n"
a6099ef3 101 " \"inbound\": true|false, (boolean) Inbound (true) or Outbound (false)\n"
102 " \"startingheight\": n, (numeric) The starting height (block) of the peer\n"
ee304b6e 103 " \"banscore\": n, (numeric) The ban score\n"
ad6e6017
PW
104 " \"synced_headers\": n, (numeric) The last header we have in common with this peer\n"
105 " \"synced_blocks\": n, (numeric) The last block we have in common with this peer\n"
106 " \"inflight\": [\n"
107 " n, (numeric) The heights of blocks we're currently asking from this peer\n"
108 " ...\n"
109 " ]\n"
a6099ef3 110 " }\n"
111 " ,...\n"
7de3f1cf 112 "]\n"
a6099ef3 113 "\nExamples:\n"
114 + HelpExampleCli("getpeerinfo", "")
115 + HelpExampleRpc("getpeerinfo", "")
116 );
1006f070 117
4401b2d7
EL
118 LOCK(cs_main);
119
1006f070
JG
120 vector<CNodeStats> vstats;
121 CopyNodeStats(vstats);
122
123 Array ret;
124
125 BOOST_FOREACH(const CNodeStats& stats, vstats) {
126 Object obj;
b2864d2f
PW
127 CNodeStateStats statestats;
128 bool fStateStats = GetNodeStateStats(stats.nodeid, statestats);
c4a321f5 129 obj.push_back(Pair("id", stats.nodeid));
1006f070 130 obj.push_back(Pair("addr", stats.addrName));
547c61f8
JL
131 if (!(stats.addrLocal.empty()))
132 obj.push_back(Pair("addrlocal", stats.addrLocal));
99ddc6cb 133 obj.push_back(Pair("services", strprintf("%016x", stats.nServices)));
d56e30ca
KD
134 obj.push_back(Pair("lastsend", stats.nLastSend));
135 obj.push_back(Pair("lastrecv", stats.nLastRecv));
136 obj.push_back(Pair("bytessent", stats.nSendBytes));
137 obj.push_back(Pair("bytesrecv", stats.nRecvBytes));
138 obj.push_back(Pair("conntime", stats.nTimeConnected));
26a6bae7 139 obj.push_back(Pair("timeoffset", stats.nTimeOffset));
971bb3e9
JL
140 obj.push_back(Pair("pingtime", stats.dPingTime));
141 if (stats.dPingWait > 0.0)
142 obj.push_back(Pair("pingwait", stats.dPingWait));
1006f070 143 obj.push_back(Pair("version", stats.nVersion));
a946aa8d
MH
144 // Use the sanitized form of subver here, to avoid tricksy remote peers from
145 // corrupting or modifiying the JSON output by putting special characters in
146 // their ver message.
147 obj.push_back(Pair("subver", stats.cleanSubVer));
1006f070 148 obj.push_back(Pair("inbound", stats.fInbound));
18e8e437 149 obj.push_back(Pair("startingheight", stats.nStartingHeight));
b2864d2f
PW
150 if (fStateStats) {
151 obj.push_back(Pair("banscore", statestats.nMisbehavior));
ad6e6017
PW
152 obj.push_back(Pair("synced_headers", statestats.nSyncHeight));
153 obj.push_back(Pair("synced_blocks", statestats.nCommonHeight));
154 Array heights;
155 BOOST_FOREACH(int height, statestats.vHeightInFlight) {
156 heights.push_back(height);
157 }
158 obj.push_back(Pair("inflight", heights));
b2864d2f 159 }
dc942e6f 160 obj.push_back(Pair("whitelisted", stats.fWhitelisted));
1006f070
JG
161
162 ret.push_back(obj);
163 }
ea0796bd 164
1006f070
JG
165 return ret;
166}
70ab73a0 167
72a348fd
MC
168Value addnode(const Array& params, bool fHelp)
169{
170 string strCommand;
171 if (params.size() == 2)
172 strCommand = params[1].get_str();
173 if (fHelp || params.size() != 2 ||
174 (strCommand != "onetry" && strCommand != "add" && strCommand != "remove"))
175 throw runtime_error(
a6099ef3 176 "addnode \"node\" \"add|remove|onetry\"\n"
177 "\nAttempts add or remove a node from the addnode list.\n"
178 "Or try a connection to a node once.\n"
179 "\nArguments:\n"
180 "1. \"node\" (string, required) The node (see getpeerinfo for nodes)\n"
181 "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"
182 "\nExamples:\n"
3985a40d
JG
183 + HelpExampleCli("addnode", "\"192.168.0.6:8233\" \"onetry\"")
184 + HelpExampleRpc("addnode", "\"192.168.0.6:8233\", \"onetry\"")
a6099ef3 185 );
72a348fd
MC
186
187 string strNode = params[0].get_str();
188
189 if (strCommand == "onetry")
190 {
191 CAddress addr;
b641c9cd 192 OpenNetworkConnection(addr, NULL, strNode.c_str());
72a348fd
MC
193 return Value::null;
194 }
195
196 LOCK(cs_vAddedNodes);
197 vector<string>::iterator it = vAddedNodes.begin();
198 for(; it != vAddedNodes.end(); it++)
199 if (strNode == *it)
200 break;
201
202 if (strCommand == "add")
203 {
204 if (it != vAddedNodes.end())
4315ec1a 205 throw JSONRPCError(RPC_CLIENT_NODE_ALREADY_ADDED, "Error: Node already added");
72a348fd
MC
206 vAddedNodes.push_back(strNode);
207 }
208 else if(strCommand == "remove")
209 {
210 if (it == vAddedNodes.end())
4315ec1a 211 throw JSONRPCError(RPC_CLIENT_NODE_NOT_ADDED, "Error: Node has not been added.");
72a348fd
MC
212 vAddedNodes.erase(it);
213 }
214
215 return Value::null;
216}
217
67a11bd6
MC
218Value getaddednodeinfo(const Array& params, bool fHelp)
219{
220 if (fHelp || params.size() < 1 || params.size() > 2)
221 throw runtime_error(
a6099ef3 222 "getaddednodeinfo dns ( \"node\" )\n"
223 "\nReturns information about the given added node, or all added nodes\n"
67a11bd6
MC
224 "(note that onetry addnodes are not listed here)\n"
225 "If dns is false, only a list of added nodes will be provided,\n"
a6099ef3 226 "otherwise connected information will also be available.\n"
227 "\nArguments:\n"
228 "1. dns (boolean, required) If false, only a list of added nodes will be provided, otherwise connected information will also be available.\n"
229 "2. \"node\" (string, optional) If provided, return information about this specific node, otherwise all nodes are returned.\n"
230 "\nResult:\n"
231 "[\n"
232 " {\n"
233 " \"addednode\" : \"192.168.0.201\", (string) The node ip address\n"
234 " \"connected\" : true|false, (boolean) If connected\n"
235 " \"addresses\" : [\n"
236 " {\n"
3985a40d 237 " \"address\" : \"192.168.0.201:8233\", (string) The bitcoin server host and port\n"
a6099ef3 238 " \"connected\" : \"outbound\" (string) connection, inbound or outbound\n"
239 " }\n"
240 " ,...\n"
241 " ]\n"
242 " }\n"
243 " ,...\n"
244 "]\n"
245 "\nExamples:\n"
246 + HelpExampleCli("getaddednodeinfo", "true")
247 + HelpExampleCli("getaddednodeinfo", "true \"192.168.0.201\"")
248 + HelpExampleRpc("getaddednodeinfo", "true, \"192.168.0.201\"")
249 );
67a11bd6
MC
250
251 bool fDns = params[0].get_bool();
252
253 list<string> laddedNodes(0);
254 if (params.size() == 1)
255 {
256 LOCK(cs_vAddedNodes);
257 BOOST_FOREACH(string& strAddNode, vAddedNodes)
258 laddedNodes.push_back(strAddNode);
259 }
260 else
261 {
262 string strNode = params[1].get_str();
263 LOCK(cs_vAddedNodes);
264 BOOST_FOREACH(string& strAddNode, vAddedNodes)
265 if (strAddNode == strNode)
266 {
267 laddedNodes.push_back(strAddNode);
268 break;
269 }
270 if (laddedNodes.size() == 0)
4315ec1a 271 throw JSONRPCError(RPC_CLIENT_NODE_NOT_ADDED, "Error: Node has not been added.");
67a11bd6
MC
272 }
273
4412c5a7 274 Array ret;
67a11bd6
MC
275 if (!fDns)
276 {
67a11bd6 277 BOOST_FOREACH(string& strAddNode, laddedNodes)
4412c5a7
WL
278 {
279 Object obj;
280 obj.push_back(Pair("addednode", strAddNode));
281 ret.push_back(obj);
282 }
67a11bd6
MC
283 return ret;
284 }
285
67a11bd6
MC
286 list<pair<string, vector<CService> > > laddedAddreses(0);
287 BOOST_FOREACH(string& strAddNode, laddedNodes)
288 {
289 vector<CService> vservNode(0);
0e4b3175 290 if(Lookup(strAddNode.c_str(), vservNode, Params().GetDefaultPort(), fNameLookup, 0))
67a11bd6
MC
291 laddedAddreses.push_back(make_pair(strAddNode, vservNode));
292 else
293 {
294 Object obj;
295 obj.push_back(Pair("addednode", strAddNode));
296 obj.push_back(Pair("connected", false));
297 Array addresses;
298 obj.push_back(Pair("addresses", addresses));
299 }
300 }
301
302 LOCK(cs_vNodes);
303 for (list<pair<string, vector<CService> > >::iterator it = laddedAddreses.begin(); it != laddedAddreses.end(); it++)
304 {
305 Object obj;
306 obj.push_back(Pair("addednode", it->first));
307
308 Array addresses;
309 bool fConnected = false;
310 BOOST_FOREACH(CService& addrNode, it->second)
311 {
312 bool fFound = false;
313 Object node;
314 node.push_back(Pair("address", addrNode.ToString()));
315 BOOST_FOREACH(CNode* pnode, vNodes)
316 if (pnode->addr == addrNode)
317 {
318 fFound = true;
319 fConnected = true;
320 node.push_back(Pair("connected", pnode->fInbound ? "inbound" : "outbound"));
321 break;
322 }
323 if (!fFound)
324 node.push_back(Pair("connected", "false"));
325 addresses.push_back(node);
326 }
327 obj.push_back(Pair("connected", fConnected));
328 obj.push_back(Pair("addresses", addresses));
329 ret.push_back(obj);
330 }
331
332 return ret;
333}
334
ce14345a
SE
335Value getnettotals(const Array& params, bool fHelp)
336{
337 if (fHelp || params.size() > 0)
338 throw runtime_error(
339 "getnettotals\n"
a6099ef3 340 "\nReturns information about network traffic, including bytes in, bytes out,\n"
341 "and current time.\n"
342 "\nResult:\n"
343 "{\n"
344 " \"totalbytesrecv\": n, (numeric) Total bytes received\n"
38cbeab1 345 " \"totalbytessent\": n, (numeric) Total bytes sent\n"
a6099ef3 346 " \"timemillis\": t (numeric) Total cpu time\n"
347 "}\n"
348 "\nExamples:\n"
349 + HelpExampleCli("getnettotals", "")
350 + HelpExampleRpc("getnettotals", "")
351 );
ce14345a
SE
352
353 Object obj;
d56e30ca
KD
354 obj.push_back(Pair("totalbytesrecv", CNode::GetTotalBytesRecv()));
355 obj.push_back(Pair("totalbytessent", CNode::GetTotalBytesSent()));
356 obj.push_back(Pair("timemillis", GetTimeMillis()));
ce14345a
SE
357 return obj;
358}
d387b8ec 359
aa827951
WL
360static Array GetNetworksInfo()
361{
362 Array networks;
363 for(int n=0; n<NET_MAX; ++n)
364 {
365 enum Network network = static_cast<enum Network>(n);
366 if(network == NET_UNROUTABLE)
367 continue;
368 proxyType proxy;
369 Object obj;
370 GetProxy(network, proxy);
371 obj.push_back(Pair("name", GetNetworkName(network)));
372 obj.push_back(Pair("limited", IsLimited(network)));
373 obj.push_back(Pair("reachable", IsReachable(network)));
67a79493
WL
374 obj.push_back(Pair("proxy", proxy.IsValid() ? proxy.proxy.ToStringIPPort() : string()));
375 obj.push_back(Pair("proxy_randomize_credentials", proxy.randomize_credentials));
aa827951
WL
376 networks.push_back(obj);
377 }
378 return networks;
379}
380
d387b8ec
WL
381Value getnetworkinfo(const Array& params, bool fHelp)
382{
383 if (fHelp || params.size() != 0)
384 throw runtime_error(
385 "getnetworkinfo\n"
386 "Returns an object containing various state info regarding P2P networking.\n"
387 "\nResult:\n"
388 "{\n"
b5ec5fe0 389 " \"version\": xxxxx, (numeric) the server version\n"
5bd677f5 390 " \"subversion\": \"/MagicBean:x.y.z[-v]/\", (string) the server subversion string\n"
b5ec5fe0
PK
391 " \"protocolversion\": xxxxx, (numeric) the protocol version\n"
392 " \"localservices\": \"xxxxxxxxxxxxxxxx\", (string) the services we offer to the network\n"
393 " \"timeoffset\": xxxxx, (numeric) the time offset\n"
394 " \"connections\": xxxxx, (numeric) the number of connections\n"
395 " \"networks\": [ (array) information per network\n"
396 " {\n"
397 " \"name\": \"xxx\", (string) network (ipv4, ipv6 or onion)\n"
398 " \"limited\": true|false, (boolean) is the network limited using -onlynet?\n"
399 " \"reachable\": true|false, (boolean) is the network reachable?\n"
400 " \"proxy\": \"host:port\" (string) the proxy that is used for this network, or empty if none\n"
401 " }\n"
402 " ,...\n"
aa827951 403 " ],\n"
b5ec5fe0
PK
404 " \"relayfee\": x.xxxxxxxx, (numeric) minimum relay fee for non-free transactions in btc/kb\n"
405 " \"localaddresses\": [ (array) list of local addresses\n"
406 " {\n"
407 " \"address\": \"xxxx\", (string) network address\n"
408 " \"port\": xxx, (numeric) network port\n"
409 " \"score\": xxx (numeric) relative score\n"
410 " }\n"
411 " ,...\n"
d387b8ec
WL
412 " ]\n"
413 "}\n"
414 "\nExamples:\n"
415 + HelpExampleCli("getnetworkinfo", "")
416 + HelpExampleRpc("getnetworkinfo", "")
417 );
418
4401b2d7
EL
419 LOCK(cs_main);
420
d387b8ec 421 Object obj;
b5ec5fe0 422 obj.push_back(Pair("version", CLIENT_VERSION));
ff36cbe8
JG
423 obj.push_back(Pair("subversion",
424 FormatSubVersion(CLIENT_NAME, CLIENT_VERSION, std::vector<string>())));
b5ec5fe0 425 obj.push_back(Pair("protocolversion",PROTOCOL_VERSION));
99ddc6cb 426 obj.push_back(Pair("localservices", strprintf("%016x", nLocalServices)));
d56e30ca 427 obj.push_back(Pair("timeoffset", GetTimeOffset()));
d387b8ec 428 obj.push_back(Pair("connections", (int)vNodes.size()));
aa827951 429 obj.push_back(Pair("networks", GetNetworksInfo()));
13fc83c7 430 obj.push_back(Pair("relayfee", ValueFromAmount(::minRelayTxFee.GetFeePerK())));
d387b8ec
WL
431 Array localAddresses;
432 {
433 LOCK(cs_mapLocalHost);
434 BOOST_FOREACH(const PAIRTYPE(CNetAddr, LocalServiceInfo) &item, mapLocalHost)
435 {
436 Object rec;
437 rec.push_back(Pair("address", item.first.ToString()));
438 rec.push_back(Pair("port", item.second.nPort));
439 rec.push_back(Pair("score", item.second.nScore));
440 localAddresses.push_back(rec);
441 }
442 }
443 obj.push_back(Pair("localaddresses", localAddresses));
444 return obj;
445}
This page took 0.235412 seconds and 4 git commands to generate.