BSHA3  0.17.99
P2P Blockchain, based on Bitcoin
blockchain.cpp
Go to the documentation of this file.
1 // Copyright (c) 2010 Satoshi Nakamoto
2 // Copyright (c) 2009-2018 The Bitcoin Core developers
3 // Distributed under the MIT software license, see the accompanying
4 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
5 
6 #include <rpc/blockchain.h>
7 
8 #include <amount.h>
9 #include <base58.h>
10 #include <chain.h>
11 #include <chainparams.h>
12 #include <checkpoints.h>
13 #include <coins.h>
14 #include <consensus/validation.h>
15 #include <validation.h>
16 #include <core_io.h>
17 #include <index/txindex.h>
18 #include <key_io.h>
19 #include <policy/feerate.h>
20 #include <policy/policy.h>
21 #include <policy/rbf.h>
22 #include <primitives/transaction.h>
23 #include <rpc/server.h>
24 #include <script/descriptor.h>
25 #include <streams.h>
26 #include <sync.h>
27 #include <txdb.h>
28 #include <txmempool.h>
29 #include <util.h>
30 #include <utilstrencodings.h>
31 #include <hash.h>
32 #include <validationinterface.h>
33 #include <versionbitsinfo.h>
34 #include <warnings.h>
35 
36 #include <assert.h>
37 #include <stdint.h>
38 
39 #include <univalue.h>
40 
41 #include <boost/algorithm/string.hpp>
42 #include <boost/thread/thread.hpp> // boost::thread::interrupt
43 
44 #include <memory>
45 #include <mutex>
46 #include <condition_variable>
47 
49 {
51  int height;
52 };
53 
54 static Mutex cs_blockchange;
55 static std::condition_variable cond_blockchange;
56 static CUpdatedBlock latestblock;
57 
58 /* Calculate the difficulty for a given block index.
59  */
60 double GetDifficulty(const CBlockIndex* blockindex)
61 {
62  if (blockindex == nullptr)
63  {
64  if (chainActive.Tip() == nullptr)
65  return 1.0;
66  else
67  blockindex = chainActive.Tip();
68  }
69 
70  int nShift = (blockindex->nBits >> 24) & 0xff;
71  double dDiff =
72  (double)0x0000ffff / (double)(blockindex->nBits & 0x00ffffff);
73 
74  while (nShift < 29)
75  {
76  dDiff *= 256.0;
77  nShift++;
78  }
79  while (nShift > 29)
80  {
81  dDiff /= 256.0;
82  nShift--;
83  }
84 
85  return dDiff;
86 }
87 
89 {
91  UniValue result(UniValue::VOBJ);
92  result.pushKV("hash", blockindex->GetBlockHash().GetHex());
93  int confirmations = -1;
94  // Only report confirmations if the block is on the main chain
95  if (chainActive.Contains(blockindex))
96  confirmations = chainActive.Height() - blockindex->nHeight + 1;
97  result.pushKV("confirmations", confirmations);
98  result.pushKV("height", blockindex->nHeight);
99  result.pushKV("version", blockindex->nVersion);
100  result.pushKV("versionHex", strprintf("%08x", blockindex->nVersion));
101  result.pushKV("merkleroot", blockindex->hashMerkleRoot.GetHex());
102  result.pushKV("time", (int64_t)blockindex->nTime);
103  result.pushKV("mediantime", (int64_t)blockindex->GetMedianTimePast());
104  result.pushKV("nonce", (uint64_t)blockindex->nNonce);
105  result.pushKV("bits", strprintf("%08x", blockindex->nBits));
106  result.pushKV("difficulty", GetDifficulty(blockindex));
107  result.pushKV("chainwork", blockindex->nChainWork.GetHex());
108  result.pushKV("nTx", (uint64_t)blockindex->nTx);
109 
110  if (blockindex->pprev)
111  result.pushKV("previousblockhash", blockindex->pprev->GetBlockHash().GetHex());
112  CBlockIndex *pnext = chainActive.Next(blockindex);
113  if (pnext)
114  result.pushKV("nextblockhash", pnext->GetBlockHash().GetHex());
115  return result;
116 }
117 
118 UniValue blockToJSON(const CBlock& block, const CBlockIndex* blockindex, bool txDetails)
119 {
121  UniValue result(UniValue::VOBJ);
122  result.pushKV("hash", blockindex->GetBlockHash().GetHex());
123  int confirmations = -1;
124  // Only report confirmations if the block is on the main chain
125  if (chainActive.Contains(blockindex))
126  confirmations = chainActive.Height() - blockindex->nHeight + 1;
127  result.pushKV("confirmations", confirmations);
128  result.pushKV("strippedsize", (int)::GetSerializeSize(block, PROTOCOL_VERSION | SERIALIZE_TRANSACTION_NO_WITNESS));
129  result.pushKV("size", (int)::GetSerializeSize(block, PROTOCOL_VERSION));
130  result.pushKV("weight", (int)::GetBlockWeight(block));
131  result.pushKV("height", blockindex->nHeight);
132  result.pushKV("version", block.nVersion);
133  result.pushKV("versionHex", strprintf("%08x", block.nVersion));
134  result.pushKV("merkleroot", block.hashMerkleRoot.GetHex());
136  for(const auto& tx : block.vtx)
137  {
138  if(txDetails)
139  {
140  UniValue objTx(UniValue::VOBJ);
141  TxToUniv(*tx, uint256(), objTx, true, RPCSerializationFlags());
142  txs.push_back(objTx);
143  }
144  else
145  txs.push_back(tx->GetHash().GetHex());
146  }
147  result.pushKV("tx", txs);
148  result.pushKV("time", block.GetBlockTime());
149  result.pushKV("mediantime", (int64_t)blockindex->GetMedianTimePast());
150  result.pushKV("nonce", (uint64_t)block.nNonce);
151  result.pushKV("bits", strprintf("%08x", block.nBits));
152  result.pushKV("difficulty", GetDifficulty(blockindex));
153  result.pushKV("chainwork", blockindex->nChainWork.GetHex());
154  result.pushKV("nTx", (uint64_t)blockindex->nTx);
155 
156  if (blockindex->pprev)
157  result.pushKV("previousblockhash", blockindex->pprev->GetBlockHash().GetHex());
158  CBlockIndex *pnext = chainActive.Next(blockindex);
159  if (pnext)
160  result.pushKV("nextblockhash", pnext->GetBlockHash().GetHex());
161  return result;
162 }
163 
164 static UniValue getblockcount(const JSONRPCRequest& request)
165 {
166  if (request.fHelp || request.params.size() != 0)
167  throw std::runtime_error(
168  "getblockcount\n"
169  "\nReturns the number of blocks in the longest blockchain.\n"
170  "\nResult:\n"
171  "n (numeric) The current block count\n"
172  "\nExamples:\n"
173  + HelpExampleCli("getblockcount", "")
174  + HelpExampleRpc("getblockcount", "")
175  );
176 
177  LOCK(cs_main);
178  return chainActive.Height();
179 }
180 
181 static UniValue getbestblockhash(const JSONRPCRequest& request)
182 {
183  if (request.fHelp || request.params.size() != 0)
184  throw std::runtime_error(
185  "getbestblockhash\n"
186  "\nReturns the hash of the best (tip) block in the longest blockchain.\n"
187  "\nResult:\n"
188  "\"hex\" (string) the block hash, hex-encoded\n"
189  "\nExamples:\n"
190  + HelpExampleCli("getbestblockhash", "")
191  + HelpExampleRpc("getbestblockhash", "")
192  );
193 
194  LOCK(cs_main);
195  return chainActive.Tip()->GetBlockHash().GetHex();
196 }
197 
198 void RPCNotifyBlockChange(bool ibd, const CBlockIndex * pindex)
199 {
200  if(pindex) {
201  std::lock_guard<std::mutex> lock(cs_blockchange);
202  latestblock.hash = pindex->GetBlockHash();
203  latestblock.height = pindex->nHeight;
204  }
205  cond_blockchange.notify_all();
206 }
207 
208 static UniValue waitfornewblock(const JSONRPCRequest& request)
209 {
210  if (request.fHelp || request.params.size() > 1)
211  throw std::runtime_error(
212  "waitfornewblock (timeout)\n"
213  "\nWaits for a specific new block and returns useful info about it.\n"
214  "\nReturns the current block on timeout or exit.\n"
215  "\nArguments:\n"
216  "1. timeout (int, optional, default=0) Time in milliseconds to wait for a response. 0 indicates no timeout.\n"
217  "\nResult:\n"
218  "{ (json object)\n"
219  " \"hash\" : { (string) The blockhash\n"
220  " \"height\" : { (int) Block height\n"
221  "}\n"
222  "\nExamples:\n"
223  + HelpExampleCli("waitfornewblock", "1000")
224  + HelpExampleRpc("waitfornewblock", "1000")
225  );
226  int timeout = 0;
227  if (!request.params[0].isNull())
228  timeout = request.params[0].get_int();
229 
230  CUpdatedBlock block;
231  {
232  WAIT_LOCK(cs_blockchange, lock);
233  block = latestblock;
234  if(timeout)
235  cond_blockchange.wait_for(lock, std::chrono::milliseconds(timeout), [&block]{return latestblock.height != block.height || latestblock.hash != block.hash || !IsRPCRunning(); });
236  else
237  cond_blockchange.wait(lock, [&block]{return latestblock.height != block.height || latestblock.hash != block.hash || !IsRPCRunning(); });
238  block = latestblock;
239  }
241  ret.pushKV("hash", block.hash.GetHex());
242  ret.pushKV("height", block.height);
243  return ret;
244 }
245 
246 static UniValue waitforblock(const JSONRPCRequest& request)
247 {
248  if (request.fHelp || request.params.size() < 1 || request.params.size() > 2)
249  throw std::runtime_error(
250  "waitforblock <blockhash> (timeout)\n"
251  "\nWaits for a specific new block and returns useful info about it.\n"
252  "\nReturns the current block on timeout or exit.\n"
253  "\nArguments:\n"
254  "1. \"blockhash\" (required, string) Block hash to wait for.\n"
255  "2. timeout (int, optional, default=0) Time in milliseconds to wait for a response. 0 indicates no timeout.\n"
256  "\nResult:\n"
257  "{ (json object)\n"
258  " \"hash\" : { (string) The blockhash\n"
259  " \"height\" : { (int) Block height\n"
260  "}\n"
261  "\nExamples:\n"
262  + HelpExampleCli("waitforblock", "\"0000000000079f8ef3d2c688c244eb7a4570b24c9ed7b4a8c619eb02596f8862\", 1000")
263  + HelpExampleRpc("waitforblock", "\"0000000000079f8ef3d2c688c244eb7a4570b24c9ed7b4a8c619eb02596f8862\", 1000")
264  );
265  int timeout = 0;
266 
267  uint256 hash(ParseHashV(request.params[0], "blockhash"));
268 
269  if (!request.params[1].isNull())
270  timeout = request.params[1].get_int();
271 
272  CUpdatedBlock block;
273  {
274  WAIT_LOCK(cs_blockchange, lock);
275  if(timeout)
276  cond_blockchange.wait_for(lock, std::chrono::milliseconds(timeout), [&hash]{return latestblock.hash == hash || !IsRPCRunning();});
277  else
278  cond_blockchange.wait(lock, [&hash]{return latestblock.hash == hash || !IsRPCRunning(); });
279  block = latestblock;
280  }
281 
283  ret.pushKV("hash", block.hash.GetHex());
284  ret.pushKV("height", block.height);
285  return ret;
286 }
287 
288 static UniValue waitforblockheight(const JSONRPCRequest& request)
289 {
290  if (request.fHelp || request.params.size() < 1 || request.params.size() > 2)
291  throw std::runtime_error(
292  "waitforblockheight <height> (timeout)\n"
293  "\nWaits for (at least) block height and returns the height and hash\n"
294  "of the current tip.\n"
295  "\nReturns the current block on timeout or exit.\n"
296  "\nArguments:\n"
297  "1. height (required, int) Block height to wait for (int)\n"
298  "2. timeout (int, optional, default=0) Time in milliseconds to wait for a response. 0 indicates no timeout.\n"
299  "\nResult:\n"
300  "{ (json object)\n"
301  " \"hash\" : { (string) The blockhash\n"
302  " \"height\" : { (int) Block height\n"
303  "}\n"
304  "\nExamples:\n"
305  + HelpExampleCli("waitforblockheight", "\"100\", 1000")
306  + HelpExampleRpc("waitforblockheight", "\"100\", 1000")
307  );
308  int timeout = 0;
309 
310  int height = request.params[0].get_int();
311 
312  if (!request.params[1].isNull())
313  timeout = request.params[1].get_int();
314 
315  CUpdatedBlock block;
316  {
317  WAIT_LOCK(cs_blockchange, lock);
318  if(timeout)
319  cond_blockchange.wait_for(lock, std::chrono::milliseconds(timeout), [&height]{return latestblock.height >= height || !IsRPCRunning();});
320  else
321  cond_blockchange.wait(lock, [&height]{return latestblock.height >= height || !IsRPCRunning(); });
322  block = latestblock;
323  }
325  ret.pushKV("hash", block.hash.GetHex());
326  ret.pushKV("height", block.height);
327  return ret;
328 }
329 
330 static UniValue syncwithvalidationinterfacequeue(const JSONRPCRequest& request)
331 {
332  if (request.fHelp || request.params.size() > 0) {
333  throw std::runtime_error(
334  "syncwithvalidationinterfacequeue\n"
335  "\nWaits for the validation interface queue to catch up on everything that was there when we entered this function.\n"
336  "\nExamples:\n"
337  + HelpExampleCli("syncwithvalidationinterfacequeue","")
338  + HelpExampleRpc("syncwithvalidationinterfacequeue","")
339  );
340  }
342  return NullUniValue;
343 }
344 
345 static UniValue getdifficulty(const JSONRPCRequest& request)
346 {
347  if (request.fHelp || request.params.size() != 0)
348  throw std::runtime_error(
349  "getdifficulty\n"
350  "\nReturns the proof-of-work difficulty as a multiple of the minimum difficulty.\n"
351  "\nResult:\n"
352  "n.nnn (numeric) the proof-of-work difficulty as a multiple of the minimum difficulty.\n"
353  "\nExamples:\n"
354  + HelpExampleCli("getdifficulty", "")
355  + HelpExampleRpc("getdifficulty", "")
356  );
357 
358  LOCK(cs_main);
359  return GetDifficulty(chainActive.Tip());
360 }
361 
362 static std::string EntryDescriptionString()
363 {
364  return " \"size\" : n, (numeric) virtual transaction size as defined in BIP 141. This is different from actual serialized size for witness transactions as witness data is discounted.\n"
365  " \"fee\" : n, (numeric) transaction fee in " + CURRENCY_UNIT + " (DEPRECATED)\n"
366  " \"modifiedfee\" : n, (numeric) transaction fee with fee deltas used for mining priority (DEPRECATED)\n"
367  " \"time\" : n, (numeric) local time transaction entered pool in seconds since 1 Jan 1970 GMT\n"
368  " \"height\" : n, (numeric) block height when transaction entered pool\n"
369  " \"descendantcount\" : n, (numeric) number of in-mempool descendant transactions (including this one)\n"
370  " \"descendantsize\" : n, (numeric) virtual transaction size of in-mempool descendants (including this one)\n"
371  " \"descendantfees\" : n, (numeric) modified fees (see above) of in-mempool descendants (including this one) (DEPRECATED)\n"
372  " \"ancestorcount\" : n, (numeric) number of in-mempool ancestor transactions (including this one)\n"
373  " \"ancestorsize\" : n, (numeric) virtual transaction size of in-mempool ancestors (including this one)\n"
374  " \"ancestorfees\" : n, (numeric) modified fees (see above) of in-mempool ancestors (including this one) (DEPRECATED)\n"
375  " \"wtxid\" : hash, (string) hash of serialized transaction, including witness data\n"
376  " \"fees\" : {\n"
377  " \"base\" : n, (numeric) transaction fee in " + CURRENCY_UNIT + "\n"
378  " \"modified\" : n, (numeric) transaction fee with fee deltas used for mining priority in " + CURRENCY_UNIT + "\n"
379  " \"ancestor\" : n, (numeric) modified fees (see above) of in-mempool ancestors (including this one) in " + CURRENCY_UNIT + "\n"
380  " \"descendant\" : n, (numeric) modified fees (see above) of in-mempool descendants (including this one) in " + CURRENCY_UNIT + "\n"
381  " }\n"
382  " \"depends\" : [ (array) unconfirmed transactions used as inputs for this transaction\n"
383  " \"transactionid\", (string) parent transaction id\n"
384  " ... ]\n"
385  " \"spentby\" : [ (array) unconfirmed transactions spending outputs from this transaction\n"
386  " \"transactionid\", (string) child transaction id\n"
387  " ... ]\n"
388  " \"bip125-replaceable\" : true|false, (boolean) Whether this transaction could be replaced due to BIP125 (replace-by-fee)\n";
389 }
390 
391 static void entryToJSON(UniValue &info, const CTxMemPoolEntry &e) EXCLUSIVE_LOCKS_REQUIRED(::mempool.cs)
392 {
394 
395  UniValue fees(UniValue::VOBJ);
396  fees.pushKV("base", ValueFromAmount(e.GetFee()));
397  fees.pushKV("modified", ValueFromAmount(e.GetModifiedFee()));
398  fees.pushKV("ancestor", ValueFromAmount(e.GetModFeesWithAncestors()));
399  fees.pushKV("descendant", ValueFromAmount(e.GetModFeesWithDescendants()));
400  info.pushKV("fees", fees);
401 
402  info.pushKV("size", (int)e.GetTxSize());
403  info.pushKV("fee", ValueFromAmount(e.GetFee()));
404  info.pushKV("modifiedfee", ValueFromAmount(e.GetModifiedFee()));
405  info.pushKV("time", e.GetTime());
406  info.pushKV("height", (int)e.GetHeight());
407  info.pushKV("descendantcount", e.GetCountWithDescendants());
408  info.pushKV("descendantsize", e.GetSizeWithDescendants());
409  info.pushKV("descendantfees", e.GetModFeesWithDescendants());
410  info.pushKV("ancestorcount", e.GetCountWithAncestors());
411  info.pushKV("ancestorsize", e.GetSizeWithAncestors());
412  info.pushKV("ancestorfees", e.GetModFeesWithAncestors());
413  info.pushKV("wtxid", mempool.vTxHashes[e.vTxHashesIdx].first.ToString());
414  const CTransaction& tx = e.GetTx();
415  std::set<std::string> setDepends;
416  for (const CTxIn& txin : tx.vin)
417  {
418  if (mempool.exists(txin.prevout.hash))
419  setDepends.insert(txin.prevout.hash.ToString());
420  }
421 
422  UniValue depends(UniValue::VARR);
423  for (const std::string& dep : setDepends)
424  {
425  depends.push_back(dep);
426  }
427 
428  info.pushKV("depends", depends);
429 
430  UniValue spent(UniValue::VARR);
431  const CTxMemPool::txiter &it = mempool.mapTx.find(tx.GetHash());
432  const CTxMemPool::setEntries &setChildren = mempool.GetMemPoolChildren(it);
433  for (CTxMemPool::txiter childiter : setChildren) {
434  spent.push_back(childiter->GetTx().GetHash().ToString());
435  }
436 
437  info.pushKV("spentby", spent);
438 
439  // Add opt-in RBF status
440  bool rbfStatus = false;
441  RBFTransactionState rbfState = IsRBFOptIn(tx, mempool);
442  if (rbfState == RBFTransactionState::UNKNOWN) {
443  throw JSONRPCError(RPC_MISC_ERROR, "Transaction is not in mempool");
444  } else if (rbfState == RBFTransactionState::REPLACEABLE_BIP125) {
445  rbfStatus = true;
446  }
447 
448  info.pushKV("bip125-replaceable", rbfStatus);
449 }
450 
451 UniValue mempoolToJSON(bool fVerbose)
452 {
453  if (fVerbose)
454  {
455  LOCK(mempool.cs);
457  for (const CTxMemPoolEntry& e : mempool.mapTx)
458  {
459  const uint256& hash = e.GetTx().GetHash();
460  UniValue info(UniValue::VOBJ);
461  entryToJSON(info, e);
462  o.pushKV(hash.ToString(), info);
463  }
464  return o;
465  }
466  else
467  {
468  std::vector<uint256> vtxid;
469  mempool.queryHashes(vtxid);
470 
472  for (const uint256& hash : vtxid)
473  a.push_back(hash.ToString());
474 
475  return a;
476  }
477 }
478 
479 static UniValue getrawmempool(const JSONRPCRequest& request)
480 {
481  if (request.fHelp || request.params.size() > 1)
482  throw std::runtime_error(
483  "getrawmempool ( verbose )\n"
484  "\nReturns all transaction ids in memory pool as a json array of string transaction ids.\n"
485  "\nHint: use getmempoolentry to fetch a specific transaction from the mempool.\n"
486  "\nArguments:\n"
487  "1. verbose (boolean, optional, default=false) True for a json object, false for array of transaction ids\n"
488  "\nResult: (for verbose = false):\n"
489  "[ (json array of string)\n"
490  " \"transactionid\" (string) The transaction id\n"
491  " ,...\n"
492  "]\n"
493  "\nResult: (for verbose = true):\n"
494  "{ (json object)\n"
495  " \"transactionid\" : { (json object)\n"
496  + EntryDescriptionString()
497  + " }, ...\n"
498  "}\n"
499  "\nExamples:\n"
500  + HelpExampleCli("getrawmempool", "true")
501  + HelpExampleRpc("getrawmempool", "true")
502  );
503 
504  bool fVerbose = false;
505  if (!request.params[0].isNull())
506  fVerbose = request.params[0].get_bool();
507 
508  return mempoolToJSON(fVerbose);
509 }
510 
511 static UniValue getmempoolancestors(const JSONRPCRequest& request)
512 {
513  if (request.fHelp || request.params.size() < 1 || request.params.size() > 2) {
514  throw std::runtime_error(
515  "getmempoolancestors txid ( verbose )\n"
516  "\nIf txid is in the mempool, returns all in-mempool ancestors.\n"
517  "\nArguments:\n"
518  "1. \"txid\" (string, required) The transaction id (must be in mempool)\n"
519  "2. verbose (boolean, optional, default=false) True for a json object, false for array of transaction ids\n"
520  "\nResult (for verbose = false):\n"
521  "[ (json array of strings)\n"
522  " \"transactionid\" (string) The transaction id of an in-mempool ancestor transaction\n"
523  " ,...\n"
524  "]\n"
525  "\nResult (for verbose = true):\n"
526  "{ (json object)\n"
527  " \"transactionid\" : { (json object)\n"
528  + EntryDescriptionString()
529  + " }, ...\n"
530  "}\n"
531  "\nExamples:\n"
532  + HelpExampleCli("getmempoolancestors", "\"mytxid\"")
533  + HelpExampleRpc("getmempoolancestors", "\"mytxid\"")
534  );
535  }
536 
537  bool fVerbose = false;
538  if (!request.params[1].isNull())
539  fVerbose = request.params[1].get_bool();
540 
541  uint256 hash = ParseHashV(request.params[0], "parameter 1");
542 
543  LOCK(mempool.cs);
544 
545  CTxMemPool::txiter it = mempool.mapTx.find(hash);
546  if (it == mempool.mapTx.end()) {
547  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Transaction not in mempool");
548  }
549 
550  CTxMemPool::setEntries setAncestors;
551  uint64_t noLimit = std::numeric_limits<uint64_t>::max();
552  std::string dummy;
553  mempool.CalculateMemPoolAncestors(*it, setAncestors, noLimit, noLimit, noLimit, noLimit, dummy, false);
554 
555  if (!fVerbose) {
557  for (CTxMemPool::txiter ancestorIt : setAncestors) {
558  o.push_back(ancestorIt->GetTx().GetHash().ToString());
559  }
560 
561  return o;
562  } else {
564  for (CTxMemPool::txiter ancestorIt : setAncestors) {
565  const CTxMemPoolEntry &e = *ancestorIt;
566  const uint256& _hash = e.GetTx().GetHash();
567  UniValue info(UniValue::VOBJ);
568  entryToJSON(info, e);
569  o.pushKV(_hash.ToString(), info);
570  }
571  return o;
572  }
573 }
574 
575 static UniValue getmempooldescendants(const JSONRPCRequest& request)
576 {
577  if (request.fHelp || request.params.size() < 1 || request.params.size() > 2) {
578  throw std::runtime_error(
579  "getmempooldescendants txid ( verbose )\n"
580  "\nIf txid is in the mempool, returns all in-mempool descendants.\n"
581  "\nArguments:\n"
582  "1. \"txid\" (string, required) The transaction id (must be in mempool)\n"
583  "2. verbose (boolean, optional, default=false) True for a json object, false for array of transaction ids\n"
584  "\nResult (for verbose = false):\n"
585  "[ (json array of strings)\n"
586  " \"transactionid\" (string) The transaction id of an in-mempool descendant transaction\n"
587  " ,...\n"
588  "]\n"
589  "\nResult (for verbose = true):\n"
590  "{ (json object)\n"
591  " \"transactionid\" : { (json object)\n"
592  + EntryDescriptionString()
593  + " }, ...\n"
594  "}\n"
595  "\nExamples:\n"
596  + HelpExampleCli("getmempooldescendants", "\"mytxid\"")
597  + HelpExampleRpc("getmempooldescendants", "\"mytxid\"")
598  );
599  }
600 
601  bool fVerbose = false;
602  if (!request.params[1].isNull())
603  fVerbose = request.params[1].get_bool();
604 
605  uint256 hash = ParseHashV(request.params[0], "parameter 1");
606 
607  LOCK(mempool.cs);
608 
609  CTxMemPool::txiter it = mempool.mapTx.find(hash);
610  if (it == mempool.mapTx.end()) {
611  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Transaction not in mempool");
612  }
613 
614  CTxMemPool::setEntries setDescendants;
615  mempool.CalculateDescendants(it, setDescendants);
616  // CTxMemPool::CalculateDescendants will include the given tx
617  setDescendants.erase(it);
618 
619  if (!fVerbose) {
621  for (CTxMemPool::txiter descendantIt : setDescendants) {
622  o.push_back(descendantIt->GetTx().GetHash().ToString());
623  }
624 
625  return o;
626  } else {
628  for (CTxMemPool::txiter descendantIt : setDescendants) {
629  const CTxMemPoolEntry &e = *descendantIt;
630  const uint256& _hash = e.GetTx().GetHash();
631  UniValue info(UniValue::VOBJ);
632  entryToJSON(info, e);
633  o.pushKV(_hash.ToString(), info);
634  }
635  return o;
636  }
637 }
638 
639 static UniValue getmempoolentry(const JSONRPCRequest& request)
640 {
641  if (request.fHelp || request.params.size() != 1) {
642  throw std::runtime_error(
643  "getmempoolentry txid\n"
644  "\nReturns mempool data for given transaction\n"
645  "\nArguments:\n"
646  "1. \"txid\" (string, required) The transaction id (must be in mempool)\n"
647  "\nResult:\n"
648  "{ (json object)\n"
649  + EntryDescriptionString()
650  + "}\n"
651  "\nExamples:\n"
652  + HelpExampleCli("getmempoolentry", "\"mytxid\"")
653  + HelpExampleRpc("getmempoolentry", "\"mytxid\"")
654  );
655  }
656 
657  uint256 hash = ParseHashV(request.params[0], "parameter 1");
658 
659  LOCK(mempool.cs);
660 
661  CTxMemPool::txiter it = mempool.mapTx.find(hash);
662  if (it == mempool.mapTx.end()) {
663  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Transaction not in mempool");
664  }
665 
666  const CTxMemPoolEntry &e = *it;
667  UniValue info(UniValue::VOBJ);
668  entryToJSON(info, e);
669  return info;
670 }
671 
672 static UniValue getblockhash(const JSONRPCRequest& request)
673 {
674  if (request.fHelp || request.params.size() != 1)
675  throw std::runtime_error(
676  "getblockhash height\n"
677  "\nReturns hash of block in best-block-chain at height provided.\n"
678  "\nArguments:\n"
679  "1. height (numeric, required) The height index\n"
680  "\nResult:\n"
681  "\"hash\" (string) The block hash\n"
682  "\nExamples:\n"
683  + HelpExampleCli("getblockhash", "1000")
684  + HelpExampleRpc("getblockhash", "1000")
685  );
686 
687  LOCK(cs_main);
688 
689  int nHeight = request.params[0].get_int();
690  if (nHeight < 0 || nHeight > chainActive.Height())
691  throw JSONRPCError(RPC_INVALID_PARAMETER, "Block height out of range");
692 
693  CBlockIndex* pblockindex = chainActive[nHeight];
694  return pblockindex->GetBlockHash().GetHex();
695 }
696 
697 static UniValue getblockheader(const JSONRPCRequest& request)
698 {
699  if (request.fHelp || request.params.size() < 1 || request.params.size() > 2)
700  throw std::runtime_error(
701  "getblockheader \"hash\" ( verbose )\n"
702  "\nIf verbose is false, returns a string that is serialized, hex-encoded data for blockheader 'hash'.\n"
703  "If verbose is true, returns an Object with information about blockheader <hash>.\n"
704  "\nArguments:\n"
705  "1. \"hash\" (string, required) The block hash\n"
706  "2. verbose (boolean, optional, default=true) true for a json object, false for the hex-encoded data\n"
707  "\nResult (for verbose = true):\n"
708  "{\n"
709  " \"hash\" : \"hash\", (string) the block hash (same as provided)\n"
710  " \"confirmations\" : n, (numeric) The number of confirmations, or -1 if the block is not on the main chain\n"
711  " \"height\" : n, (numeric) The block height or index\n"
712  " \"version\" : n, (numeric) The block version\n"
713  " \"versionHex\" : \"00000000\", (string) The block version formatted in hexadecimal\n"
714  " \"merkleroot\" : \"xxxx\", (string) The merkle root\n"
715  " \"time\" : ttt, (numeric) The block time in seconds since epoch (Jan 1 1970 GMT)\n"
716  " \"mediantime\" : ttt, (numeric) The median block time in seconds since epoch (Jan 1 1970 GMT)\n"
717  " \"nonce\" : n, (numeric) The nonce\n"
718  " \"bits\" : \"1d00ffff\", (string) The bits\n"
719  " \"difficulty\" : x.xxx, (numeric) The difficulty\n"
720  " \"chainwork\" : \"0000...1f3\" (string) Expected number of hashes required to produce the current chain (in hex)\n"
721  " \"nTx\" : n, (numeric) The number of transactions in the block.\n"
722  " \"previousblockhash\" : \"hash\", (string) The hash of the previous block\n"
723  " \"nextblockhash\" : \"hash\", (string) The hash of the next block\n"
724  "}\n"
725  "\nResult (for verbose=false):\n"
726  "\"data\" (string) A string that is serialized, hex-encoded data for block 'hash'.\n"
727  "\nExamples:\n"
728  + HelpExampleCli("getblockheader", "\"00000000c937983704a73af28acdec37b049d214adbda81d7e2a3dd146f6ed09\"")
729  + HelpExampleRpc("getblockheader", "\"00000000c937983704a73af28acdec37b049d214adbda81d7e2a3dd146f6ed09\"")
730  );
731 
732  LOCK(cs_main);
733 
734  uint256 hash(ParseHashV(request.params[0], "hash"));
735 
736  bool fVerbose = true;
737  if (!request.params[1].isNull())
738  fVerbose = request.params[1].get_bool();
739 
740  const CBlockIndex* pblockindex = LookupBlockIndex(hash);
741  if (!pblockindex) {
742  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Block not found");
743  }
744 
745  if (!fVerbose)
746  {
747  CDataStream ssBlock(SER_NETWORK, PROTOCOL_VERSION);
748  ssBlock << pblockindex->GetBlockHeader();
749  std::string strHex = HexStr(ssBlock.begin(), ssBlock.end());
750  return strHex;
751  }
752 
753  return blockheaderToJSON(pblockindex);
754 }
755 
756 static CBlock GetBlockChecked(const CBlockIndex* pblockindex)
757 {
758  CBlock block;
759  if (IsBlockPruned(pblockindex)) {
760  throw JSONRPCError(RPC_MISC_ERROR, "Block not available (pruned data)");
761  }
762 
763  if (!ReadBlockFromDisk(block, pblockindex, Params().GetConsensus())) {
764  // Block not found on disk. This could be because we have the block
765  // header in our index but don't have the block (for example if a
766  // non-whitelisted node sends us an unrequested long chain of valid
767  // blocks, we add the headers to our index, but don't accept the
768  // block).
769  throw JSONRPCError(RPC_MISC_ERROR, "Block not found on disk");
770  }
771 
772  return block;
773 }
774 
775 static UniValue getblock(const JSONRPCRequest& request)
776 {
777  if (request.fHelp || request.params.size() < 1 || request.params.size() > 2)
778  throw std::runtime_error(
779  "getblock \"blockhash\" ( verbosity ) \n"
780  "\nIf verbosity is 0, returns a string that is serialized, hex-encoded data for block 'hash'.\n"
781  "If verbosity is 1, returns an Object with information about block <hash>.\n"
782  "If verbosity is 2, returns an Object with information about block <hash> and information about each transaction. \n"
783  "\nArguments:\n"
784  "1. \"blockhash\" (string, required) The block hash\n"
785  "2. verbosity (numeric, optional, default=1) 0 for hex-encoded data, 1 for a json object, and 2 for json object with transaction data\n"
786  "\nResult (for verbosity = 0):\n"
787  "\"data\" (string) A string that is serialized, hex-encoded data for block 'hash'.\n"
788  "\nResult (for verbosity = 1):\n"
789  "{\n"
790  " \"hash\" : \"hash\", (string) the block hash (same as provided)\n"
791  " \"confirmations\" : n, (numeric) The number of confirmations, or -1 if the block is not on the main chain\n"
792  " \"size\" : n, (numeric) The block size\n"
793  " \"strippedsize\" : n, (numeric) The block size excluding witness data\n"
794  " \"weight\" : n (numeric) The block weight as defined in BIP 141\n"
795  " \"height\" : n, (numeric) The block height or index\n"
796  " \"version\" : n, (numeric) The block version\n"
797  " \"versionHex\" : \"00000000\", (string) The block version formatted in hexadecimal\n"
798  " \"merkleroot\" : \"xxxx\", (string) The merkle root\n"
799  " \"tx\" : [ (array of string) The transaction ids\n"
800  " \"transactionid\" (string) The transaction id\n"
801  " ,...\n"
802  " ],\n"
803  " \"time\" : ttt, (numeric) The block time in seconds since epoch (Jan 1 1970 GMT)\n"
804  " \"mediantime\" : ttt, (numeric) The median block time in seconds since epoch (Jan 1 1970 GMT)\n"
805  " \"nonce\" : n, (numeric) The nonce\n"
806  " \"bits\" : \"1d00ffff\", (string) The bits\n"
807  " \"difficulty\" : x.xxx, (numeric) The difficulty\n"
808  " \"chainwork\" : \"xxxx\", (string) Expected number of hashes required to produce the chain up to this block (in hex)\n"
809  " \"nTx\" : n, (numeric) The number of transactions in the block.\n"
810  " \"previousblockhash\" : \"hash\", (string) The hash of the previous block\n"
811  " \"nextblockhash\" : \"hash\" (string) The hash of the next block\n"
812  "}\n"
813  "\nResult (for verbosity = 2):\n"
814  "{\n"
815  " ..., Same output as verbosity = 1.\n"
816  " \"tx\" : [ (array of Objects) The transactions in the format of the getrawtransaction RPC. Different from verbosity = 1 \"tx\" result.\n"
817  " ,...\n"
818  " ],\n"
819  " ,... Same output as verbosity = 1.\n"
820  "}\n"
821  "\nExamples:\n"
822  + HelpExampleCli("getblock", "\"00000000c937983704a73af28acdec37b049d214adbda81d7e2a3dd146f6ed09\"")
823  + HelpExampleRpc("getblock", "\"00000000c937983704a73af28acdec37b049d214adbda81d7e2a3dd146f6ed09\"")
824  );
825 
826  LOCK(cs_main);
827 
828  uint256 hash(ParseHashV(request.params[0], "blockhash"));
829 
830  int verbosity = 1;
831  if (!request.params[1].isNull()) {
832  if(request.params[1].isNum())
833  verbosity = request.params[1].get_int();
834  else
835  verbosity = request.params[1].get_bool() ? 1 : 0;
836  }
837 
838  const CBlockIndex* pblockindex = LookupBlockIndex(hash);
839  if (!pblockindex) {
840  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Block not found");
841  }
842 
843  const CBlock block = GetBlockChecked(pblockindex);
844 
845  if (verbosity <= 0)
846  {
847  CDataStream ssBlock(SER_NETWORK, PROTOCOL_VERSION | RPCSerializationFlags());
848  ssBlock << block;
849  std::string strHex = HexStr(ssBlock.begin(), ssBlock.end());
850  return strHex;
851  }
852 
853  return blockToJSON(block, pblockindex, verbosity >= 2);
854 }
855 
857 {
858  int nHeight;
860  uint64_t nTransactions;
862  uint64_t nBogoSize;
864  uint64_t nDiskSize;
866 
868 };
869 
870 static void ApplyStats(CCoinsStats &stats, CHashWriter& ss, const uint256& hash, const std::map<uint32_t, Coin>& outputs)
871 {
872  assert(!outputs.empty());
873  ss << hash;
874  ss << VARINT(outputs.begin()->second.nHeight * 2 + outputs.begin()->second.fCoinBase ? 1u : 0u);
875  stats.nTransactions++;
876  for (const auto& output : outputs) {
877  ss << VARINT(output.first + 1);
878  ss << output.second.out.scriptPubKey;
879  ss << VARINT(output.second.out.nValue, VarIntMode::NONNEGATIVE_SIGNED);
880  stats.nTransactionOutputs++;
881  stats.nTotalAmount += output.second.out.nValue;
882  stats.nBogoSize += 32 /* txid */ + 4 /* vout index */ + 4 /* height + coinbase */ + 8 /* amount */ +
883  2 /* scriptPubKey len */ + output.second.out.scriptPubKey.size() /* scriptPubKey */;
884  }
885  ss << VARINT(0u);
886 }
887 
889 static bool GetUTXOStats(CCoinsView *view, CCoinsStats &stats)
890 {
891  std::unique_ptr<CCoinsViewCursor> pcursor(view->Cursor());
892  assert(pcursor);
893 
894  CHashWriter ss(SER_GETHASH, PROTOCOL_VERSION);
895  stats.hashBlock = pcursor->GetBestBlock();
896  {
897  LOCK(cs_main);
898  stats.nHeight = LookupBlockIndex(stats.hashBlock)->nHeight;
899  }
900  ss << stats.hashBlock;
901  uint256 prevkey;
902  std::map<uint32_t, Coin> outputs;
903  while (pcursor->Valid()) {
904  boost::this_thread::interruption_point();
905  COutPoint key;
906  Coin coin;
907  if (pcursor->GetKey(key) && pcursor->GetValue(coin)) {
908  if (!outputs.empty() && key.hash != prevkey) {
909  ApplyStats(stats, ss, prevkey, outputs);
910  outputs.clear();
911  }
912  prevkey = key.hash;
913  outputs[key.n] = std::move(coin);
914  } else {
915  return error("%s: unable to read value", __func__);
916  }
917  pcursor->Next();
918  }
919  if (!outputs.empty()) {
920  ApplyStats(stats, ss, prevkey, outputs);
921  }
922  stats.hashSerialized = ss.GetHash();
923  stats.nDiskSize = view->EstimateSize();
924  return true;
925 }
926 
927 static UniValue pruneblockchain(const JSONRPCRequest& request)
928 {
929  if (request.fHelp || request.params.size() != 1)
930  throw std::runtime_error(
931  "pruneblockchain\n"
932  "\nArguments:\n"
933  "1. \"height\" (numeric, required) The block height to prune up to. May be set to a discrete height, or a unix timestamp\n"
934  " to prune blocks whose block time is at least 2 hours older than the provided timestamp.\n"
935  "\nResult:\n"
936  "n (numeric) Height of the last block pruned.\n"
937  "\nExamples:\n"
938  + HelpExampleCli("pruneblockchain", "1000")
939  + HelpExampleRpc("pruneblockchain", "1000"));
940 
941  if (!fPruneMode)
942  throw JSONRPCError(RPC_MISC_ERROR, "Cannot prune blocks because node is not in prune mode.");
943 
944  LOCK(cs_main);
945 
946  int heightParam = request.params[0].get_int();
947  if (heightParam < 0)
948  throw JSONRPCError(RPC_INVALID_PARAMETER, "Negative block height.");
949 
950  // Height value more than a billion is too high to be a block height, and
951  // too low to be a block time (corresponds to timestamp from Sep 2001).
952  if (heightParam > 1000000000) {
953  // Add a 2 hour buffer to include blocks which might have had old timestamps
954  CBlockIndex* pindex = chainActive.FindEarliestAtLeast(heightParam - TIMESTAMP_WINDOW);
955  if (!pindex) {
956  throw JSONRPCError(RPC_INVALID_PARAMETER, "Could not find block with at least the specified timestamp.");
957  }
958  heightParam = pindex->nHeight;
959  }
960 
961  unsigned int height = (unsigned int) heightParam;
962  unsigned int chainHeight = (unsigned int) chainActive.Height();
963  if (chainHeight < Params().PruneAfterHeight())
964  throw JSONRPCError(RPC_MISC_ERROR, "Blockchain is too short for pruning.");
965  else if (height > chainHeight)
966  throw JSONRPCError(RPC_INVALID_PARAMETER, "Blockchain is shorter than the attempted prune height.");
967  else if (height > chainHeight - MIN_BLOCKS_TO_KEEP) {
968  LogPrint(BCLog::RPC, "Attempt to prune blocks close to the tip. Retaining the minimum number of blocks.\n");
969  height = chainHeight - MIN_BLOCKS_TO_KEEP;
970  }
971 
972  PruneBlockFilesManual(height);
973  return uint64_t(height);
974 }
975 
976 static UniValue gettxoutsetinfo(const JSONRPCRequest& request)
977 {
978  if (request.fHelp || request.params.size() != 0)
979  throw std::runtime_error(
980  "gettxoutsetinfo\n"
981  "\nReturns statistics about the unspent transaction output set.\n"
982  "Note this call may take some time.\n"
983  "\nResult:\n"
984  "{\n"
985  " \"height\":n, (numeric) The current block height (index)\n"
986  " \"bestblock\": \"hex\", (string) The hash of the block at the tip of the chain\n"
987  " \"transactions\": n, (numeric) The number of transactions with unspent outputs\n"
988  " \"txouts\": n, (numeric) The number of unspent transaction outputs\n"
989  " \"bogosize\": n, (numeric) A meaningless metric for UTXO set size\n"
990  " \"hash_serialized_2\": \"hash\", (string) The serialized hash\n"
991  " \"disk_size\": n, (numeric) The estimated size of the chainstate on disk\n"
992  " \"total_amount\": x.xxx (numeric) The total amount\n"
993  "}\n"
994  "\nExamples:\n"
995  + HelpExampleCli("gettxoutsetinfo", "")
996  + HelpExampleRpc("gettxoutsetinfo", "")
997  );
998 
1000 
1001  CCoinsStats stats;
1002  FlushStateToDisk();
1003  if (GetUTXOStats(pcoinsdbview.get(), stats)) {
1004  ret.pushKV("height", (int64_t)stats.nHeight);
1005  ret.pushKV("bestblock", stats.hashBlock.GetHex());
1006  ret.pushKV("transactions", (int64_t)stats.nTransactions);
1007  ret.pushKV("txouts", (int64_t)stats.nTransactionOutputs);
1008  ret.pushKV("bogosize", (int64_t)stats.nBogoSize);
1009  ret.pushKV("hash_serialized_2", stats.hashSerialized.GetHex());
1010  ret.pushKV("disk_size", stats.nDiskSize);
1011  ret.pushKV("total_amount", ValueFromAmount(stats.nTotalAmount));
1012  } else {
1013  throw JSONRPCError(RPC_INTERNAL_ERROR, "Unable to read UTXO set");
1014  }
1015  return ret;
1016 }
1017 
1019 {
1020  if (request.fHelp || request.params.size() < 2 || request.params.size() > 3)
1021  throw std::runtime_error(
1022  "gettxout \"txid\" n ( include_mempool )\n"
1023  "\nReturns details about an unspent transaction output.\n"
1024  "\nArguments:\n"
1025  "1. \"txid\" (string, required) The transaction id\n"
1026  "2. \"n\" (numeric, required) vout number\n"
1027  "3. \"include_mempool\" (boolean, optional) Whether to include the mempool. Default: true."
1028  " Note that an unspent output that is spent in the mempool won't appear.\n"
1029  "\nResult:\n"
1030  "{\n"
1031  " \"bestblock\": \"hash\", (string) The hash of the block at the tip of the chain\n"
1032  " \"confirmations\" : n, (numeric) The number of confirmations\n"
1033  " \"value\" : x.xxx, (numeric) The transaction value in " + CURRENCY_UNIT + "\n"
1034  " \"scriptPubKey\" : { (json object)\n"
1035  " \"asm\" : \"code\", (string) \n"
1036  " \"hex\" : \"hex\", (string) \n"
1037  " \"reqSigs\" : n, (numeric) Number of required signatures\n"
1038  " \"type\" : \"pubkeyhash\", (string) The type, eg pubkeyhash\n"
1039  " \"addresses\" : [ (array of string) array of bitcoin addresses\n"
1040  " \"address\" (string) bitcoin address\n"
1041  " ,...\n"
1042  " ]\n"
1043  " },\n"
1044  " \"coinbase\" : true|false (boolean) Coinbase or not\n"
1045  "}\n"
1046 
1047  "\nExamples:\n"
1048  "\nGet unspent transactions\n"
1049  + HelpExampleCli("listunspent", "") +
1050  "\nView the details\n"
1051  + HelpExampleCli("gettxout", "\"txid\" 1") +
1052  "\nAs a JSON-RPC call\n"
1053  + HelpExampleRpc("gettxout", "\"txid\", 1")
1054  );
1055 
1056  LOCK(cs_main);
1057 
1059 
1060  uint256 hash(ParseHashV(request.params[0], "txid"));
1061  int n = request.params[1].get_int();
1062  COutPoint out(hash, n);
1063  bool fMempool = true;
1064  if (!request.params[2].isNull())
1065  fMempool = request.params[2].get_bool();
1066 
1067  Coin coin;
1068  if (fMempool) {
1069  LOCK(mempool.cs);
1070  CCoinsViewMemPool view(pcoinsTip.get(), mempool);
1071  if (!view.GetCoin(out, coin) || mempool.isSpent(out)) {
1072  return NullUniValue;
1073  }
1074  } else {
1075  if (!pcoinsTip->GetCoin(out, coin)) {
1076  return NullUniValue;
1077  }
1078  }
1079 
1080  const CBlockIndex* pindex = LookupBlockIndex(pcoinsTip->GetBestBlock());
1081  ret.pushKV("bestblock", pindex->GetBlockHash().GetHex());
1082  if (coin.nHeight == MEMPOOL_HEIGHT) {
1083  ret.pushKV("confirmations", 0);
1084  } else {
1085  ret.pushKV("confirmations", (int64_t)(pindex->nHeight - coin.nHeight + 1));
1086  }
1087  ret.pushKV("value", ValueFromAmount(coin.out.nValue));
1089  ScriptPubKeyToUniv(coin.out.scriptPubKey, o, true);
1090  ret.pushKV("scriptPubKey", o);
1091  ret.pushKV("coinbase", (bool)coin.fCoinBase);
1092 
1093  return ret;
1094 }
1095 
1096 static UniValue verifychain(const JSONRPCRequest& request)
1097 {
1098  int nCheckLevel = gArgs.GetArg("-checklevel", DEFAULT_CHECKLEVEL);
1099  int nCheckDepth = gArgs.GetArg("-checkblocks", DEFAULT_CHECKBLOCKS);
1100  if (request.fHelp || request.params.size() > 2)
1101  throw std::runtime_error(
1102  "verifychain ( checklevel nblocks )\n"
1103  "\nVerifies blockchain database.\n"
1104  "\nArguments:\n"
1105  "1. checklevel (numeric, optional, 0-4, default=" + strprintf("%d", nCheckLevel) + ") How thorough the block verification is.\n"
1106  "2. nblocks (numeric, optional, default=" + strprintf("%d", nCheckDepth) + ", 0=all) The number of blocks to check.\n"
1107  "\nResult:\n"
1108  "true|false (boolean) Verified or not\n"
1109  "\nExamples:\n"
1110  + HelpExampleCli("verifychain", "")
1111  + HelpExampleRpc("verifychain", "")
1112  );
1113 
1114  LOCK(cs_main);
1115 
1116  if (!request.params[0].isNull())
1117  nCheckLevel = request.params[0].get_int();
1118  if (!request.params[1].isNull())
1119  nCheckDepth = request.params[1].get_int();
1120 
1121  return CVerifyDB().VerifyDB(Params(), pcoinsTip.get(), nCheckLevel, nCheckDepth);
1122 }
1123 
1125 /*
1126 static UniValue SoftForkMajorityDesc(int version, CBlockIndex* pindex, const Consensus::Params& consensusParams)
1127 {
1128  UniValue rv(UniValue::VOBJ);
1129  bool activated = false;
1130  switch(version)
1131  {
1132  case 2:
1133  activated = pindex->nHeight >= consensusParams.BIP34Height;
1134  break;
1135  case 3:
1136  activated = pindex->nHeight >= consensusParams.BIP66Height;
1137  break;
1138  case 4:
1139  activated = pindex->nHeight >= consensusParams.BIP65Height;
1140  break;
1141  }
1142  rv.pushKV("status", activated);
1143  return rv;
1144 }
1145 
1146 static UniValue SoftForkDesc(const std::string &name, int version, CBlockIndex* pindex, const Consensus::Params& consensusParams)
1147 {
1148  UniValue rv(UniValue::VOBJ);
1149  rv.pushKV("id", name);
1150  rv.pushKV("version", version);
1151  rv.pushKV("reject", SoftForkMajorityDesc(version, pindex, consensusParams));
1152  return rv;
1153 }
1154 */
1155 
1156 /*
1157 static UniValue BIP9SoftForkDesc(const Consensus::Params& consensusParams, Consensus::DeploymentPos id)
1158 {
1159  UniValue rv(UniValue::VOBJ);
1160  const ThresholdState thresholdState = VersionBitsTipState(consensusParams, id);
1161  switch (thresholdState) {
1162  case ThresholdState::DEFINED: rv.pushKV("status", "defined"); break;
1163  case ThresholdState::STARTED: rv.pushKV("status", "started"); break;
1164  case ThresholdState::LOCKED_IN: rv.pushKV("status", "locked_in"); break;
1165  case ThresholdState::ACTIVE: rv.pushKV("status", "active"); break;
1166  case ThresholdState::FAILED: rv.pushKV("status", "failed"); break;
1167  }
1168  if (ThresholdState::STARTED == thresholdState)
1169  {
1170  rv.pushKV("bit", consensusParams.vDeployments[id].bit);
1171  }
1172  rv.pushKV("startTime", consensusParams.vDeployments[id].nStartTime);
1173  rv.pushKV("timeout", consensusParams.vDeployments[id].nTimeout);
1174  rv.pushKV("since", VersionBitsTipStateSinceHeight(consensusParams, id));
1175  if (ThresholdState::STARTED == thresholdState)
1176  {
1177  UniValue statsUV(UniValue::VOBJ);
1178  BIP9Stats statsStruct = VersionBitsTipStatistics(consensusParams, id);
1179  statsUV.pushKV("period", statsStruct.period);
1180  statsUV.pushKV("threshold", statsStruct.threshold);
1181  statsUV.pushKV("elapsed", statsStruct.elapsed);
1182  statsUV.pushKV("count", statsStruct.count);
1183  statsUV.pushKV("possible", statsStruct.possible);
1184  rv.pushKV("statistics", statsUV);
1185  }
1186  return rv;
1187 }
1188 */
1189 
1190 /*
1191 static void BIP9SoftForkDescPushBack(UniValue& bip9_softforks, const Consensus::Params& consensusParams, Consensus::DeploymentPos id)
1192 {
1193  // Deployments with timeout value of 0 are hidden.
1194  // A timeout value of 0 guarantees a softfork will never be activated.
1195  // This is used when softfork codes are merged without specifying the deployment schedule.
1196  if (consensusParams.vDeployments[id].nTimeout > 0)
1197  bip9_softforks.pushKV(VersionBitsDeploymentInfo[id].name, BIP9SoftForkDesc(consensusParams, id));
1198 }
1199 */
1200 
1202 {
1203  if (request.fHelp || request.params.size() != 0)
1204  throw std::runtime_error(
1205  "getblockchaininfo\n"
1206  "Returns an object containing various state info regarding blockchain processing.\n"
1207  "\nResult:\n"
1208  "{\n"
1209  " \"chain\": \"xxxx\", (string) current network name as defined in BIP70 (main, test, regtest)\n"
1210  " \"blocks\": xxxxxx, (numeric) the current number of blocks processed in the server\n"
1211  " \"headers\": xxxxxx, (numeric) the current number of headers we have validated\n"
1212  " \"bestblockhash\": \"...\", (string) the hash of the currently best block\n"
1213  " \"difficulty\": xxxxxx, (numeric) the current difficulty\n"
1214  " \"mediantime\": xxxxxx, (numeric) median time for the current best block\n"
1215  " \"verificationprogress\": xxxx, (numeric) estimate of verification progress [0..1]\n"
1216  " \"initialblockdownload\": xxxx, (bool) (debug information) estimate of whether this node is in Initial Block Download mode.\n"
1217  " \"chainwork\": \"xxxx\" (string) total amount of work in active chain, in hexadecimal\n"
1218  " \"size_on_disk\": xxxxxx, (numeric) the estimated size of the block and undo files on disk\n"
1219  " \"pruned\": xx, (boolean) if the blocks are subject to pruning\n"
1220  " \"pruneheight\": xxxxxx, (numeric) lowest-height complete block stored (only present if pruning is enabled)\n"
1221  " \"automatic_pruning\": xx, (boolean) whether automatic pruning is enabled (only present if pruning is enabled)\n"
1222  " \"prune_target_size\": xxxxxx, (numeric) the target size used by pruning (only present if automatic pruning is enabled)\n"
1223  " \"softforks\": [ (array) status of softforks in progress\n"
1224  " {\n"
1225  " \"id\": \"xxxx\", (string) name of softfork\n"
1226  " \"version\": xx, (numeric) block version\n"
1227  " \"reject\": { (object) progress toward rejecting pre-softfork blocks\n"
1228  " \"status\": xx, (boolean) true if threshold reached\n"
1229  " },\n"
1230  " }, ...\n"
1231  " ],\n"
1232  " \"bip9_softforks\": { (object) status of BIP9 softforks in progress\n"
1233  " \"xxxx\" : { (string) name of the softfork\n"
1234  " \"status\": \"xxxx\", (string) one of \"defined\", \"started\", \"locked_in\", \"active\", \"failed\"\n"
1235  " \"bit\": xx, (numeric) the bit (0-28) in the block version field used to signal this softfork (only for \"started\" status)\n"
1236  " \"startTime\": xx, (numeric) the minimum median time past of a block at which the bit gains its meaning\n"
1237  " \"timeout\": xx, (numeric) the median time past of a block at which the deployment is considered failed if not yet locked in\n"
1238  " \"since\": xx, (numeric) height of the first block to which the status applies\n"
1239  " \"statistics\": { (object) numeric statistics about BIP9 signalling for a softfork (only for \"started\" status)\n"
1240  " \"period\": xx, (numeric) the length in blocks of the BIP9 signalling period \n"
1241  " \"threshold\": xx, (numeric) the number of blocks with the version bit set required to activate the feature \n"
1242  " \"elapsed\": xx, (numeric) the number of blocks elapsed since the beginning of the current period \n"
1243  " \"count\": xx, (numeric) the number of blocks with the version bit set in the current period \n"
1244  " \"possible\": xx (boolean) returns false if there are not enough blocks left in this period to pass activation threshold \n"
1245  " }\n"
1246  " }\n"
1247  " }\n"
1248  " \"warnings\" : \"...\", (string) any network and blockchain warnings.\n"
1249  "}\n"
1250  "\nExamples:\n"
1251  + HelpExampleCli("getblockchaininfo", "")
1252  + HelpExampleRpc("getblockchaininfo", "")
1253  );
1254 
1255  LOCK(cs_main);
1256 
1257  UniValue obj(UniValue::VOBJ);
1258  obj.pushKV("chain", Params().NetworkIDString());
1259  obj.pushKV("blocks", (int)chainActive.Height());
1260  obj.pushKV("headers", pindexBestHeader ? pindexBestHeader->nHeight : -1);
1261  obj.pushKV("bestblockhash", chainActive.Tip()->GetBlockHash().GetHex());
1262  obj.pushKV("difficulty", (double)GetDifficulty(chainActive.Tip()));
1263  obj.pushKV("mediantime", (int64_t)chainActive.Tip()->GetMedianTimePast());
1264  obj.pushKV("verificationprogress", GuessVerificationProgress(Params().TxData(), chainActive.Tip()));
1265  obj.pushKV("initialblockdownload", IsInitialBlockDownload());
1266  obj.pushKV("chainwork", chainActive.Tip()->nChainWork.GetHex());
1267  obj.pushKV("size_on_disk", CalculateCurrentUsage());
1268  obj.pushKV("pruned", fPruneMode);
1269  if (fPruneMode) {
1270  CBlockIndex* block = chainActive.Tip();
1271  assert(block);
1272  while (block->pprev && (block->pprev->nStatus & BLOCK_HAVE_DATA)) {
1273  block = block->pprev;
1274  }
1275 
1276  obj.pushKV("pruneheight", block->nHeight);
1277 
1278  // if 0, execution bypasses the whole if block.
1279  bool automatic_pruning = (gArgs.GetArg("-prune", 0) != 1);
1280  obj.pushKV("automatic_pruning", automatic_pruning);
1281  if (automatic_pruning) {
1282  obj.pushKV("prune_target_size", nPruneTarget);
1283  }
1284  }
1285 
1286  //const Consensus::Params& consensusParams = Params().GetConsensus();
1287  //CBlockIndex* tip = chainActive.Tip();
1288  UniValue softforks(UniValue::VARR);
1289  UniValue bip9_softforks(UniValue::VOBJ);
1290  //softforks.push_back(SoftForkDesc("bip34", 2, tip, consensusParams));
1291  //softforks.push_back(SoftForkDesc("bip66", 3, tip, consensusParams));
1292  //softforks.push_back(SoftForkDesc("bip65", 4, tip, consensusParams));
1293  /*
1294  for (int pos = Consensus::DEPLOYMENT_CSV; pos != Consensus::MAX_VERSION_BITS_DEPLOYMENTS; ++pos) {
1295  BIP9SoftForkDescPushBack(bip9_softforks, consensusParams, static_cast<Consensus::DeploymentPos>(pos));
1296  }
1297  */
1298  obj.pushKV("softforks", softforks);
1299  obj.pushKV("bip9_softforks", bip9_softforks);
1300 
1301  obj.pushKV("warnings", GetWarnings("statusbar"));
1302  return obj;
1303 }
1304 
1307 {
1308  bool operator()(const CBlockIndex* a, const CBlockIndex* b) const
1309  {
1310  /* Make sure that unequal blocks with the same height do not compare
1311  equal. Use the pointers themselves to make a distinction. */
1312 
1313  if (a->nHeight != b->nHeight)
1314  return (a->nHeight > b->nHeight);
1315 
1316  return a < b;
1317  }
1318 };
1319 
1320 static UniValue getchaintips(const JSONRPCRequest& request)
1321 {
1322  if (request.fHelp || request.params.size() != 0)
1323  throw std::runtime_error(
1324  "getchaintips\n"
1325  "Return information about all known tips in the block tree,"
1326  " including the main chain as well as orphaned branches.\n"
1327  "\nResult:\n"
1328  "[\n"
1329  " {\n"
1330  " \"height\": xxxx, (numeric) height of the chain tip\n"
1331  " \"hash\": \"xxxx\", (string) block hash of the tip\n"
1332  " \"branchlen\": 0 (numeric) zero for main chain\n"
1333  " \"status\": \"active\" (string) \"active\" for the main chain\n"
1334  " },\n"
1335  " {\n"
1336  " \"height\": xxxx,\n"
1337  " \"hash\": \"xxxx\",\n"
1338  " \"branchlen\": 1 (numeric) length of branch connecting the tip to the main chain\n"
1339  " \"status\": \"xxxx\" (string) status of the chain (active, valid-fork, valid-headers, headers-only, invalid)\n"
1340  " }\n"
1341  "]\n"
1342  "Possible values for status:\n"
1343  "1. \"invalid\" This branch contains at least one invalid block\n"
1344  "2. \"headers-only\" Not all blocks for this branch are available, but the headers are valid\n"
1345  "3. \"valid-headers\" All blocks are available for this branch, but they were never fully validated\n"
1346  "4. \"valid-fork\" This branch is not part of the active chain, but is fully validated\n"
1347  "5. \"active\" This is the tip of the active main chain, which is certainly valid\n"
1348  "\nExamples:\n"
1349  + HelpExampleCli("getchaintips", "")
1350  + HelpExampleRpc("getchaintips", "")
1351  );
1352 
1353  LOCK(cs_main);
1354 
1355  /*
1356  * Idea: the set of chain tips is chainActive.tip, plus orphan blocks which do not have another orphan building off of them.
1357  * Algorithm:
1358  * - Make one pass through mapBlockIndex, picking out the orphan blocks, and also storing a set of the orphan block's pprev pointers.
1359  * - Iterate through the orphan blocks. If the block isn't pointed to by another orphan, it is a chain tip.
1360  * - add chainActive.Tip()
1361  */
1362  std::set<const CBlockIndex*, CompareBlocksByHeight> setTips;
1363  std::set<const CBlockIndex*> setOrphans;
1364  std::set<const CBlockIndex*> setPrevs;
1365 
1366  for (const std::pair<const uint256, CBlockIndex*>& item : mapBlockIndex)
1367  {
1368  if (!chainActive.Contains(item.second)) {
1369  setOrphans.insert(item.second);
1370  setPrevs.insert(item.second->pprev);
1371  }
1372  }
1373 
1374  for (std::set<const CBlockIndex*>::iterator it = setOrphans.begin(); it != setOrphans.end(); ++it)
1375  {
1376  if (setPrevs.erase(*it) == 0) {
1377  setTips.insert(*it);
1378  }
1379  }
1380 
1381  // Always report the currently active tip.
1382  setTips.insert(chainActive.Tip());
1383 
1384  /* Construct the output array. */
1385  UniValue res(UniValue::VARR);
1386  for (const CBlockIndex* block : setTips)
1387  {
1388  UniValue obj(UniValue::VOBJ);
1389  obj.pushKV("height", block->nHeight);
1390  obj.pushKV("hash", block->phashBlock->GetHex());
1391 
1392  const int branchLen = block->nHeight - chainActive.FindFork(block)->nHeight;
1393  obj.pushKV("branchlen", branchLen);
1394 
1395  std::string status;
1396  if (chainActive.Contains(block)) {
1397  // This block is part of the currently active chain.
1398  status = "active";
1399  } else if (block->nStatus & BLOCK_FAILED_MASK) {
1400  // This block or one of its ancestors is invalid.
1401  status = "invalid";
1402  } else if (block->nChainTx == 0) {
1403  // This block cannot be connected because full block data for it or one of its parents is missing.
1404  status = "headers-only";
1405  } else if (block->IsValid(BLOCK_VALID_SCRIPTS)) {
1406  // This block is fully validated, but no longer part of the active chain. It was probably the active block once, but was reorganized.
1407  status = "valid-fork";
1408  } else if (block->IsValid(BLOCK_VALID_TREE)) {
1409  // The headers for this block are valid, but it has not been validated. It was probably never part of the most-work chain.
1410  status = "valid-headers";
1411  } else {
1412  // No clue.
1413  status = "unknown";
1414  }
1415  obj.pushKV("status", status);
1416 
1417  res.push_back(obj);
1418  }
1419 
1420  return res;
1421 }
1422 
1424 {
1426  ret.pushKV("size", (int64_t) mempool.size());
1427  ret.pushKV("bytes", (int64_t) mempool.GetTotalTxSize());
1428  ret.pushKV("usage", (int64_t) mempool.DynamicMemoryUsage());
1429  size_t maxmempool = gArgs.GetArg("-maxmempool", DEFAULT_MAX_MEMPOOL_SIZE) * 1000000;
1430  ret.pushKV("maxmempool", (int64_t) maxmempool);
1431  ret.pushKV("mempoolminfee", ValueFromAmount(std::max(mempool.GetMinFee(maxmempool), ::minRelayTxFee).GetFeePerK()));
1432  ret.pushKV("minrelaytxfee", ValueFromAmount(::minRelayTxFee.GetFeePerK()));
1433 
1434  return ret;
1435 }
1436 
1437 static UniValue getmempoolinfo(const JSONRPCRequest& request)
1438 {
1439  if (request.fHelp || request.params.size() != 0)
1440  throw std::runtime_error(
1441  "getmempoolinfo\n"
1442  "\nReturns details on the active state of the TX memory pool.\n"
1443  "\nResult:\n"
1444  "{\n"
1445  " \"size\": xxxxx, (numeric) Current tx count\n"
1446  " \"bytes\": xxxxx, (numeric) Sum of all virtual transaction sizes as defined in BIP 141. Differs from actual serialized size because witness data is discounted\n"
1447  " \"usage\": xxxxx, (numeric) Total memory usage for the mempool\n"
1448  " \"maxmempool\": xxxxx, (numeric) Maximum memory usage for the mempool\n"
1449  " \"mempoolminfee\": xxxxx (numeric) Minimum fee rate in " + CURRENCY_UNIT + "/kB for tx to be accepted. Is the maximum of minrelaytxfee and minimum mempool fee\n"
1450  " \"minrelaytxfee\": xxxxx (numeric) Current minimum relay fee for transactions\n"
1451  "}\n"
1452  "\nExamples:\n"
1453  + HelpExampleCli("getmempoolinfo", "")
1454  + HelpExampleRpc("getmempoolinfo", "")
1455  );
1456 
1457  return mempoolInfoToJSON();
1458 }
1459 
1460 static UniValue preciousblock(const JSONRPCRequest& request)
1461 {
1462  if (request.fHelp || request.params.size() != 1)
1463  throw std::runtime_error(
1464  "preciousblock \"blockhash\"\n"
1465  "\nTreats a block as if it were received before others with the same work.\n"
1466  "\nA later preciousblock call can override the effect of an earlier one.\n"
1467  "\nThe effects of preciousblock are not retained across restarts.\n"
1468  "\nArguments:\n"
1469  "1. \"blockhash\" (string, required) the hash of the block to mark as precious\n"
1470  "\nResult:\n"
1471  "\nExamples:\n"
1472  + HelpExampleCli("preciousblock", "\"blockhash\"")
1473  + HelpExampleRpc("preciousblock", "\"blockhash\"")
1474  );
1475 
1476  uint256 hash(ParseHashV(request.params[0], "blockhash"));
1477  CBlockIndex* pblockindex;
1478 
1479  {
1480  LOCK(cs_main);
1481  pblockindex = LookupBlockIndex(hash);
1482  if (!pblockindex) {
1483  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Block not found");
1484  }
1485  }
1486 
1487  CValidationState state;
1488  PreciousBlock(state, Params(), pblockindex);
1489 
1490  if (!state.IsValid()) {
1492  }
1493 
1494  return NullUniValue;
1495 }
1496 
1497 static UniValue invalidateblock(const JSONRPCRequest& request)
1498 {
1499  if (request.fHelp || request.params.size() != 1)
1500  throw std::runtime_error(
1501  "invalidateblock \"blockhash\"\n"
1502  "\nPermanently marks a block as invalid, as if it violated a consensus rule.\n"
1503  "\nArguments:\n"
1504  "1. \"blockhash\" (string, required) the hash of the block to mark as invalid\n"
1505  "\nResult:\n"
1506  "\nExamples:\n"
1507  + HelpExampleCli("invalidateblock", "\"blockhash\"")
1508  + HelpExampleRpc("invalidateblock", "\"blockhash\"")
1509  );
1510 
1511  uint256 hash(ParseHashV(request.params[0], "blockhash"));
1512  CValidationState state;
1513 
1514  {
1515  LOCK(cs_main);
1516  CBlockIndex* pblockindex = LookupBlockIndex(hash);
1517  if (!pblockindex) {
1518  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Block not found");
1519  }
1520 
1521  InvalidateBlock(state, Params(), pblockindex);
1522  }
1523 
1524  if (state.IsValid()) {
1525  ActivateBestChain(state, Params());
1526  }
1527 
1528  if (!state.IsValid()) {
1530  }
1531 
1532  return NullUniValue;
1533 }
1534 
1535 static UniValue reconsiderblock(const JSONRPCRequest& request)
1536 {
1537  if (request.fHelp || request.params.size() != 1)
1538  throw std::runtime_error(
1539  "reconsiderblock \"blockhash\"\n"
1540  "\nRemoves invalidity status of a block and its descendants, reconsider them for activation.\n"
1541  "This can be used to undo the effects of invalidateblock.\n"
1542  "\nArguments:\n"
1543  "1. \"blockhash\" (string, required) the hash of the block to reconsider\n"
1544  "\nResult:\n"
1545  "\nExamples:\n"
1546  + HelpExampleCli("reconsiderblock", "\"blockhash\"")
1547  + HelpExampleRpc("reconsiderblock", "\"blockhash\"")
1548  );
1549 
1550  uint256 hash(ParseHashV(request.params[0], "blockhash"));
1551 
1552  {
1553  LOCK(cs_main);
1554  CBlockIndex* pblockindex = LookupBlockIndex(hash);
1555  if (!pblockindex) {
1556  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Block not found");
1557  }
1558 
1559  ResetBlockFailureFlags(pblockindex);
1560  }
1561 
1562  CValidationState state;
1563  ActivateBestChain(state, Params());
1564 
1565  if (!state.IsValid()) {
1567  }
1568 
1569  return NullUniValue;
1570 }
1571 
1572 static UniValue getchaintxstats(const JSONRPCRequest& request)
1573 {
1574  if (request.fHelp || request.params.size() > 2)
1575  throw std::runtime_error(
1576  "getchaintxstats ( nblocks blockhash )\n"
1577  "\nCompute statistics about the total number and rate of transactions in the chain.\n"
1578  "\nArguments:\n"
1579  "1. nblocks (numeric, optional) Size of the window in number of blocks (default: one month).\n"
1580  "2. \"blockhash\" (string, optional) The hash of the block that ends the window.\n"
1581  "\nResult:\n"
1582  "{\n"
1583  " \"time\": xxxxx, (numeric) The timestamp for the final block in the window in UNIX format.\n"
1584  " \"txcount\": xxxxx, (numeric) The total number of transactions in the chain up to that point.\n"
1585  " \"window_final_block_hash\": \"...\", (string) The hash of the final block in the window.\n"
1586  " \"window_block_count\": xxxxx, (numeric) Size of the window in number of blocks.\n"
1587  " \"window_tx_count\": xxxxx, (numeric) The number of transactions in the window. Only returned if \"window_block_count\" is > 0.\n"
1588  " \"window_interval\": xxxxx, (numeric) The elapsed time in the window in seconds. Only returned if \"window_block_count\" is > 0.\n"
1589  " \"txrate\": x.xx, (numeric) The average rate of transactions per second in the window. Only returned if \"window_interval\" is > 0.\n"
1590  "}\n"
1591  "\nExamples:\n"
1592  + HelpExampleCli("getchaintxstats", "")
1593  + HelpExampleRpc("getchaintxstats", "2016")
1594  );
1595 
1596  const CBlockIndex* pindex;
1597  int blockcount = 30 * 24 * 60 * 60 / Params().GetConsensus().nPowTargetSpacing; // By default: 1 month
1598 
1599  if (request.params[1].isNull()) {
1600  LOCK(cs_main);
1601  pindex = chainActive.Tip();
1602  } else {
1603  uint256 hash(ParseHashV(request.params[1], "blockhash"));
1604  LOCK(cs_main);
1605  pindex = LookupBlockIndex(hash);
1606  if (!pindex) {
1607  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Block not found");
1608  }
1609  if (!chainActive.Contains(pindex)) {
1610  throw JSONRPCError(RPC_INVALID_PARAMETER, "Block is not in main chain");
1611  }
1612  }
1613 
1614  assert(pindex != nullptr);
1615 
1616  if (request.params[0].isNull()) {
1617  blockcount = std::max(0, std::min(blockcount, pindex->nHeight - 1));
1618  } else {
1619  blockcount = request.params[0].get_int();
1620 
1621  if (blockcount < 0 || (blockcount > 0 && blockcount >= pindex->nHeight)) {
1622  throw JSONRPCError(RPC_INVALID_PARAMETER, "Invalid block count: should be between 0 and the block's height - 1");
1623  }
1624  }
1625 
1626  const CBlockIndex* pindexPast = pindex->GetAncestor(pindex->nHeight - blockcount);
1627  int nTimeDiff = pindex->GetMedianTimePast() - pindexPast->GetMedianTimePast();
1628  int nTxDiff = pindex->nChainTx - pindexPast->nChainTx;
1629 
1631  ret.pushKV("time", (int64_t)pindex->nTime);
1632  ret.pushKV("txcount", (int64_t)pindex->nChainTx);
1633  ret.pushKV("window_final_block_hash", pindex->GetBlockHash().GetHex());
1634  ret.pushKV("window_block_count", blockcount);
1635  if (blockcount > 0) {
1636  ret.pushKV("window_tx_count", nTxDiff);
1637  ret.pushKV("window_interval", nTimeDiff);
1638  if (nTimeDiff > 0) {
1639  ret.pushKV("txrate", ((double)nTxDiff) / nTimeDiff);
1640  }
1641  }
1642 
1643  return ret;
1644 }
1645 
1646 template<typename T>
1647 static T CalculateTruncatedMedian(std::vector<T>& scores)
1648 {
1649  size_t size = scores.size();
1650  if (size == 0) {
1651  return 0;
1652  }
1653 
1654  std::sort(scores.begin(), scores.end());
1655  if (size % 2 == 0) {
1656  return (scores[size / 2 - 1] + scores[size / 2]) / 2;
1657  } else {
1658  return scores[size / 2];
1659  }
1660 }
1661 
1662 void CalculatePercentilesByWeight(CAmount result[NUM_GETBLOCKSTATS_PERCENTILES], std::vector<std::pair<CAmount, int64_t>>& scores, int64_t total_weight)
1663 {
1664  if (scores.empty()) {
1665  return;
1666  }
1667 
1668  std::sort(scores.begin(), scores.end());
1669 
1670  // 10th, 25th, 50th, 75th, and 90th percentile weight units.
1671  const double weights[NUM_GETBLOCKSTATS_PERCENTILES] = {
1672  total_weight / 10.0, total_weight / 4.0, total_weight / 2.0, (total_weight * 3.0) / 4.0, (total_weight * 9.0) / 10.0
1673  };
1674 
1675  int64_t next_percentile_index = 0;
1676  int64_t cumulative_weight = 0;
1677  for (const auto& element : scores) {
1678  cumulative_weight += element.second;
1679  while (next_percentile_index < NUM_GETBLOCKSTATS_PERCENTILES && cumulative_weight >= weights[next_percentile_index]) {
1680  result[next_percentile_index] = element.first;
1681  ++next_percentile_index;
1682  }
1683  }
1684 
1685  // Fill any remaining percentiles with the last value.
1686  for (int64_t i = next_percentile_index; i < NUM_GETBLOCKSTATS_PERCENTILES; i++) {
1687  result[i] = scores.back().first;
1688  }
1689 }
1690 
1691 template<typename T>
1692 static inline bool SetHasKeys(const std::set<T>& set) {return false;}
1693 template<typename T, typename Tk, typename... Args>
1694 static inline bool SetHasKeys(const std::set<T>& set, const Tk& key, const Args&... args)
1695 {
1696  return (set.count(key) != 0) || SetHasKeys(set, args...);
1697 }
1698 
1699 // outpoint (needed for the utxo index) + nHeight + fCoinBase
1700 static constexpr size_t PER_UTXO_OVERHEAD = sizeof(COutPoint) + sizeof(uint32_t) + sizeof(bool);
1701 
1702 static UniValue getblockstats(const JSONRPCRequest& request)
1703 {
1704  if (request.fHelp || request.params.size() < 1 || request.params.size() > 4) {
1705  throw std::runtime_error(
1706  "getblockstats hash_or_height ( stats )\n"
1707  "\nCompute per block statistics for a given window. All amounts are in satoshis.\n"
1708  "It won't work for some heights with pruning.\n"
1709  "It won't work without -txindex for utxo_size_inc, *fee or *feerate stats.\n"
1710  "\nArguments:\n"
1711  "1. \"hash_or_height\" (string or numeric, required) The block hash or height of the target block\n"
1712  "2. \"stats\" (array, optional) Values to plot, by default all values (see result below)\n"
1713  " [\n"
1714  " \"height\", (string, optional) Selected statistic\n"
1715  " \"time\", (string, optional) Selected statistic\n"
1716  " ,...\n"
1717  " ]\n"
1718  "\nResult:\n"
1719  "{ (json object)\n"
1720  " \"avgfee\": xxxxx, (numeric) Average fee in the block\n"
1721  " \"avgfeerate\": xxxxx, (numeric) Average feerate (in satoshis per virtual byte)\n"
1722  " \"avgtxsize\": xxxxx, (numeric) Average transaction size\n"
1723  " \"blockhash\": xxxxx, (string) The block hash (to check for potential reorgs)\n"
1724  " \"feerate_percentiles\": [ (array of numeric) Feerates at the 10th, 25th, 50th, 75th, and 90th percentile weight unit (in satoshis per virtual byte)\n"
1725  " \"10th_percentile_feerate\", (numeric) The 10th percentile feerate\n"
1726  " \"25th_percentile_feerate\", (numeric) The 25th percentile feerate\n"
1727  " \"50th_percentile_feerate\", (numeric) The 50th percentile feerate\n"
1728  " \"75th_percentile_feerate\", (numeric) The 75th percentile feerate\n"
1729  " \"90th_percentile_feerate\", (numeric) The 90th percentile feerate\n"
1730  " ],\n"
1731  " \"height\": xxxxx, (numeric) The height of the block\n"
1732  " \"ins\": xxxxx, (numeric) The number of inputs (excluding coinbase)\n"
1733  " \"maxfee\": xxxxx, (numeric) Maximum fee in the block\n"
1734  " \"maxfeerate\": xxxxx, (numeric) Maximum feerate (in satoshis per virtual byte)\n"
1735  " \"maxtxsize\": xxxxx, (numeric) Maximum transaction size\n"
1736  " \"medianfee\": xxxxx, (numeric) Truncated median fee in the block\n"
1737  " \"mediantime\": xxxxx, (numeric) The block median time past\n"
1738  " \"mediantxsize\": xxxxx, (numeric) Truncated median transaction size\n"
1739  " \"minfee\": xxxxx, (numeric) Minimum fee in the block\n"
1740  " \"minfeerate\": xxxxx, (numeric) Minimum feerate (in satoshis per virtual byte)\n"
1741  " \"mintxsize\": xxxxx, (numeric) Minimum transaction size\n"
1742  " \"outs\": xxxxx, (numeric) The number of outputs\n"
1743  " \"subsidy\": xxxxx, (numeric) The block subsidy\n"
1744  " \"swtotal_size\": xxxxx, (numeric) Total size of all segwit transactions\n"
1745  " \"swtotal_weight\": xxxxx, (numeric) Total weight of all segwit transactions divided by segwit scale factor (4)\n"
1746  " \"swtxs\": xxxxx, (numeric) The number of segwit transactions\n"
1747  " \"time\": xxxxx, (numeric) The block time\n"
1748  " \"total_out\": xxxxx, (numeric) Total amount in all outputs (excluding coinbase and thus reward [ie subsidy + totalfee])\n"
1749  " \"total_size\": xxxxx, (numeric) Total size of all non-coinbase transactions\n"
1750  " \"total_weight\": xxxxx, (numeric) Total weight of all non-coinbase transactions divided by segwit scale factor (4)\n"
1751  " \"totalfee\": xxxxx, (numeric) The fee total\n"
1752  " \"txs\": xxxxx, (numeric) The number of transactions (excluding coinbase)\n"
1753  " \"utxo_increase\": xxxxx, (numeric) The increase/decrease in the number of unspent outputs\n"
1754  " \"utxo_size_inc\": xxxxx, (numeric) The increase/decrease in size for the utxo index (not discounting op_return and similar)\n"
1755  "}\n"
1756  "\nExamples:\n"
1757  + HelpExampleCli("getblockstats", "1000 '[\"minfeerate\",\"avgfeerate\"]'")
1758  + HelpExampleRpc("getblockstats", "1000 '[\"minfeerate\",\"avgfeerate\"]'")
1759  );
1760  }
1761 
1762  LOCK(cs_main);
1763 
1764  CBlockIndex* pindex;
1765  if (request.params[0].isNum()) {
1766  const int height = request.params[0].get_int();
1767  const int current_tip = chainActive.Height();
1768  if (height < 0) {
1769  throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("Target block height %d is negative", height));
1770  }
1771  if (height > current_tip) {
1772  throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("Target block height %d after current tip %d", height, current_tip));
1773  }
1774 
1775  pindex = chainActive[height];
1776  } else {
1777  const uint256 hash(ParseHashV(request.params[0], "hash_or_height"));
1778  pindex = LookupBlockIndex(hash);
1779  if (!pindex) {
1780  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Block not found");
1781  }
1782  if (!chainActive.Contains(pindex)) {
1783  throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("Block is not in chain %s", Params().NetworkIDString()));
1784  }
1785  }
1786 
1787  assert(pindex != nullptr);
1788 
1789  std::set<std::string> stats;
1790  if (!request.params[1].isNull()) {
1791  const UniValue stats_univalue = request.params[1].get_array();
1792  for (unsigned int i = 0; i < stats_univalue.size(); i++) {
1793  const std::string stat = stats_univalue[i].get_str();
1794  stats.insert(stat);
1795  }
1796  }
1797 
1798  const CBlock block = GetBlockChecked(pindex);
1799 
1800  const bool do_all = stats.size() == 0; // Calculate everything if nothing selected (default)
1801  const bool do_mediantxsize = do_all || stats.count("mediantxsize") != 0;
1802  const bool do_medianfee = do_all || stats.count("medianfee") != 0;
1803  const bool do_feerate_percentiles = do_all || stats.count("feerate_percentiles") != 0;
1804  const bool loop_inputs = do_all || do_medianfee || do_feerate_percentiles ||
1805  SetHasKeys(stats, "utxo_size_inc", "totalfee", "avgfee", "avgfeerate", "minfee", "maxfee", "minfeerate", "maxfeerate");
1806  const bool loop_outputs = do_all || loop_inputs || stats.count("total_out");
1807  const bool do_calculate_size = do_mediantxsize ||
1808  SetHasKeys(stats, "total_size", "avgtxsize", "mintxsize", "maxtxsize", "swtotal_size");
1809  const bool do_calculate_weight = do_all || SetHasKeys(stats, "total_weight", "avgfeerate", "swtotal_weight", "avgfeerate", "feerate_percentiles", "minfeerate", "maxfeerate");
1810  const bool do_calculate_sw = do_all || SetHasKeys(stats, "swtxs", "swtotal_size", "swtotal_weight");
1811 
1812  if (loop_inputs && !g_txindex) {
1813  throw JSONRPCError(RPC_INVALID_PARAMETER, "One or more of the selected stats requires -txindex enabled");
1814  }
1815 
1816  CAmount maxfee = 0;
1817  CAmount maxfeerate = 0;
1818  CAmount minfee = MAX_MONEY;
1819  CAmount minfeerate = MAX_MONEY;
1820  CAmount total_out = 0;
1821  CAmount totalfee = 0;
1822  int64_t inputs = 0;
1823  int64_t maxtxsize = 0;
1824  int64_t mintxsize = MAX_BLOCK_SERIALIZED_SIZE;
1825  int64_t outputs = 0;
1826  int64_t swtotal_size = 0;
1827  int64_t swtotal_weight = 0;
1828  int64_t swtxs = 0;
1829  int64_t total_size = 0;
1830  int64_t total_weight = 0;
1831  int64_t utxo_size_inc = 0;
1832  std::vector<CAmount> fee_array;
1833  std::vector<std::pair<CAmount, int64_t>> feerate_array;
1834  std::vector<int64_t> txsize_array;
1835 
1836  for (const auto& tx : block.vtx) {
1837  outputs += tx->vout.size();
1838 
1839  CAmount tx_total_out = 0;
1840  if (loop_outputs) {
1841  for (const CTxOut& out : tx->vout) {
1842  tx_total_out += out.nValue;
1843  utxo_size_inc += GetSerializeSize(out, PROTOCOL_VERSION) + PER_UTXO_OVERHEAD;
1844  }
1845  }
1846 
1847  if (tx->IsCoinBase()) {
1848  continue;
1849  }
1850 
1851  inputs += tx->vin.size(); // Don't count coinbase's fake input
1852  total_out += tx_total_out; // Don't count coinbase reward
1853 
1854  int64_t tx_size = 0;
1855  if (do_calculate_size) {
1856 
1857  tx_size = tx->GetTotalSize();
1858  if (do_mediantxsize) {
1859  txsize_array.push_back(tx_size);
1860  }
1861  maxtxsize = std::max(maxtxsize, tx_size);
1862  mintxsize = std::min(mintxsize, tx_size);
1863  total_size += tx_size;
1864  }
1865 
1866  int64_t weight = 0;
1867  if (do_calculate_weight) {
1868  weight = GetTransactionWeight(*tx);
1869  total_weight += weight;
1870  }
1871 
1872  if (do_calculate_sw && tx->HasWitness()) {
1873  ++swtxs;
1874  swtotal_size += tx_size;
1875  swtotal_weight += weight;
1876  }
1877 
1878  if (loop_inputs) {
1879  CAmount tx_total_in = 0;
1880  for (const CTxIn& in : tx->vin) {
1881  CTransactionRef tx_in;
1882  uint256 hashBlock;
1883  if (!GetTransaction(in.prevout.hash, tx_in, Params().GetConsensus(), hashBlock, false)) {
1884  throw JSONRPCError(RPC_INTERNAL_ERROR, std::string("Unexpected internal error (tx index seems corrupt)"));
1885  }
1886 
1887  CTxOut prevoutput = tx_in->vout[in.prevout.n];
1888 
1889  tx_total_in += prevoutput.nValue;
1890  utxo_size_inc -= GetSerializeSize(prevoutput, PROTOCOL_VERSION) + PER_UTXO_OVERHEAD;
1891  }
1892 
1893  CAmount txfee = tx_total_in - tx_total_out;
1894  assert(MoneyRange(txfee));
1895  if (do_medianfee) {
1896  fee_array.push_back(txfee);
1897  }
1898  maxfee = std::max(maxfee, txfee);
1899  minfee = std::min(minfee, txfee);
1900  totalfee += txfee;
1901 
1902  // New feerate uses satoshis per virtual byte instead of per serialized byte
1903  CAmount feerate = weight ? (txfee * WITNESS_SCALE_FACTOR) / weight : 0;
1904  if (do_feerate_percentiles) {
1905  feerate_array.emplace_back(std::make_pair(feerate, weight));
1906  }
1907  maxfeerate = std::max(maxfeerate, feerate);
1908  minfeerate = std::min(minfeerate, feerate);
1909  }
1910  }
1911 
1912  CAmount feerate_percentiles[NUM_GETBLOCKSTATS_PERCENTILES] = { 0 };
1913  CalculatePercentilesByWeight(feerate_percentiles, feerate_array, total_weight);
1914 
1915  UniValue feerates_res(UniValue::VARR);
1916  for (int64_t i = 0; i < NUM_GETBLOCKSTATS_PERCENTILES; i++) {
1917  feerates_res.push_back(feerate_percentiles[i]);
1918  }
1919 
1920  UniValue ret_all(UniValue::VOBJ);
1921  ret_all.pushKV("avgfee", (block.vtx.size() > 1) ? totalfee / (block.vtx.size() - 1) : 0);
1922  ret_all.pushKV("avgfeerate", total_weight ? (totalfee * WITNESS_SCALE_FACTOR) / total_weight : 0); // Unit: sat/vbyte
1923  ret_all.pushKV("avgtxsize", (block.vtx.size() > 1) ? total_size / (block.vtx.size() - 1) : 0);
1924  ret_all.pushKV("blockhash", pindex->GetBlockHash().GetHex());
1925  ret_all.pushKV("feerate_percentiles", feerates_res);
1926  ret_all.pushKV("height", (int64_t)pindex->nHeight);
1927  ret_all.pushKV("ins", inputs);
1928  ret_all.pushKV("maxfee", maxfee);
1929  ret_all.pushKV("maxfeerate", maxfeerate);
1930  ret_all.pushKV("maxtxsize", maxtxsize);
1931  ret_all.pushKV("medianfee", CalculateTruncatedMedian(fee_array));
1932  ret_all.pushKV("mediantime", pindex->GetMedianTimePast());
1933  ret_all.pushKV("mediantxsize", CalculateTruncatedMedian(txsize_array));
1934  ret_all.pushKV("minfee", (minfee == MAX_MONEY) ? 0 : minfee);
1935  ret_all.pushKV("minfeerate", (minfeerate == MAX_MONEY) ? 0 : minfeerate);
1936  ret_all.pushKV("mintxsize", mintxsize == MAX_BLOCK_SERIALIZED_SIZE ? 0 : mintxsize);
1937  ret_all.pushKV("outs", outputs);
1938  ret_all.pushKV("subsidy", GetBlockSubsidy(pindex->nHeight, Params().GetConsensus()));
1939  ret_all.pushKV("swtotal_size", swtotal_size);
1940  ret_all.pushKV("swtotal_weight", swtotal_weight);
1941  ret_all.pushKV("swtxs", swtxs);
1942  ret_all.pushKV("time", pindex->GetBlockTime());
1943  ret_all.pushKV("total_out", total_out);
1944  ret_all.pushKV("total_size", total_size);
1945  ret_all.pushKV("total_weight", total_weight);
1946  ret_all.pushKV("totalfee", totalfee);
1947  ret_all.pushKV("txs", (int64_t)block.vtx.size());
1948  ret_all.pushKV("utxo_increase", outputs - inputs);
1949  ret_all.pushKV("utxo_size_inc", utxo_size_inc);
1950 
1951  if (do_all) {
1952  return ret_all;
1953  }
1954 
1956  for (const std::string& stat : stats) {
1957  const UniValue& value = ret_all[stat];
1958  if (value.isNull()) {
1959  throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("Invalid selected statistic %s", stat));
1960  }
1961  ret.pushKV(stat, value);
1962  }
1963  return ret;
1964 }
1965 
1966 static UniValue savemempool(const JSONRPCRequest& request)
1967 {
1968  if (request.fHelp || request.params.size() != 0) {
1969  throw std::runtime_error(
1970  "savemempool\n"
1971  "\nDumps the mempool to disk. It will fail until the previous dump is fully loaded.\n"
1972  "\nExamples:\n"
1973  + HelpExampleCli("savemempool", "")
1974  + HelpExampleRpc("savemempool", "")
1975  );
1976  }
1977 
1978  if (!g_is_mempool_loaded) {
1979  throw JSONRPCError(RPC_MISC_ERROR, "The mempool was not loaded yet");
1980  }
1981 
1982  if (!DumpMempool()) {
1983  throw JSONRPCError(RPC_MISC_ERROR, "Unable to dump mempool to disk");
1984  }
1985 
1986  return NullUniValue;
1987 }
1988 
1990 bool FindScriptPubKey(std::atomic<int>& scan_progress, const std::atomic<bool>& should_abort, int64_t& count, CCoinsViewCursor* cursor, const std::set<CScript>& needles, std::map<COutPoint, Coin>& out_results) {
1991  scan_progress = 0;
1992  count = 0;
1993  while (cursor->Valid()) {
1994  COutPoint key;
1995  Coin coin;
1996  if (!cursor->GetKey(key) || !cursor->GetValue(coin)) return false;
1997  if (++count % 8192 == 0) {
1998  boost::this_thread::interruption_point();
1999  if (should_abort) {
2000  // allow to abort the scan via the abort reference
2001  return false;
2002  }
2003  }
2004  if (count % 256 == 0) {
2005  // update progress reference every 256 item
2006  uint32_t high = 0x100 * *key.hash.begin() + *(key.hash.begin() + 1);
2007  scan_progress = (int)(high * 100.0 / 65536.0 + 0.5);
2008  }
2009  if (needles.count(coin.out.scriptPubKey)) {
2010  out_results.emplace(key, coin);
2011  }
2012  cursor->Next();
2013  }
2014  scan_progress = 100;
2015  return true;
2016 }
2017 
2019 static std::mutex g_utxosetscan;
2020 static std::atomic<int> g_scan_progress;
2021 static std::atomic<bool> g_scan_in_progress;
2022 static std::atomic<bool> g_should_abort_scan;
2024 {
2025 private:
2027 public:
2029 
2030  bool reserve() {
2031  assert (!m_could_reserve);
2032  std::lock_guard<std::mutex> lock(g_utxosetscan);
2033  if (g_scan_in_progress) {
2034  return false;
2035  }
2036  g_scan_in_progress = true;
2037  m_could_reserve = true;
2038  return true;
2039  }
2040 
2042  if (m_could_reserve) {
2043  std::lock_guard<std::mutex> lock(g_utxosetscan);
2044  g_scan_in_progress = false;
2045  }
2046  }
2047 };
2048 
2050 {
2051  if (request.fHelp || request.params.size() < 1 || request.params.size() > 2)
2052  throw std::runtime_error(
2053  "scantxoutset <action> ( <scanobjects> )\n"
2054  "\nEXPERIMENTAL warning: this call may be removed or changed in future releases.\n"
2055  "\nScans the unspent transaction output set for entries that match certain output descriptors.\n"
2056  "Examples of output descriptors are:\n"
2057  " addr(<address>) Outputs whose scriptPubKey corresponds to the specified address (does not include P2PK)\n"
2058  " raw(<hex script>) Outputs whose scriptPubKey equals the specified hex scripts\n"
2059  " combo(<pubkey>) P2PK, P2PKH, P2WPKH, and P2SH-P2WPKH outputs for the given pubkey\n"
2060  " pkh(<pubkey>) P2PKH outputs for the given pubkey\n"
2061  " sh(multi(<n>,<pubkey>,<pubkey>,...)) P2SH-multisig outputs for the given threshold and pubkeys\n"
2062  "\nIn the above, <pubkey> either refers to a fixed public key in hexadecimal notation, or to an xpub/xprv optionally followed by one\n"
2063  "or more path elements separated by \"/\", and optionally ending in \"/*\" (unhardened), or \"/*'\" or \"/*h\" (hardened) to specify all\n"
2064  "unhardened or hardened child keys.\n"
2065  "In the latter case, a range needs to be specified by below if different from 1000.\n"
2066  "For more information on output descriptors, see the documentation in the doc/descriptors.md file.\n"
2067  "\nArguments:\n"
2068  "1. \"action\" (string, required) The action to execute\n"
2069  " \"start\" for starting a scan\n"
2070  " \"abort\" for aborting the current scan (returns true when abort was successful)\n"
2071  " \"status\" for progress report (in %) of the current scan\n"
2072  "2. \"scanobjects\" (array, required) Array of scan objects\n"
2073  " [ Every scan object is either a string descriptor or an object:\n"
2074  " \"descriptor\", (string, optional) An output descriptor\n"
2075  " { (object, optional) An object with output descriptor and metadata\n"
2076  " \"desc\": \"descriptor\", (string, required) An output descriptor\n"
2077  " \"range\": n, (numeric, optional) Up to what child index HD chains should be explored (default: 1000)\n"
2078  " },\n"
2079  " ...\n"
2080  " ]\n"
2081  "\nResult:\n"
2082  "{\n"
2083  " \"unspents\": [\n"
2084  " {\n"
2085  " \"txid\" : \"transactionid\", (string) The transaction id\n"
2086  " \"vout\": n, (numeric) the vout value\n"
2087  " \"scriptPubKey\" : \"script\", (string) the script key\n"
2088  " \"amount\" : x.xxx, (numeric) The total amount in " + CURRENCY_UNIT + " of the unspent output\n"
2089  " \"height\" : n, (numeric) Height of the unspent transaction output\n"
2090  " }\n"
2091  " ,...], \n"
2092  " \"total_amount\" : x.xxx, (numeric) The total amount of all found unspent outputs in " + CURRENCY_UNIT + "\n"
2093  "]\n"
2094  );
2095 
2096  RPCTypeCheck(request.params, {UniValue::VSTR, UniValue::VARR});
2097 
2098  UniValue result(UniValue::VOBJ);
2099  if (request.params[0].get_str() == "status") {
2100  CoinsViewScanReserver reserver;
2101  if (reserver.reserve()) {
2102  // no scan in progress
2103  return NullUniValue;
2104  }
2105  result.pushKV("progress", g_scan_progress);
2106  return result;
2107  } else if (request.params[0].get_str() == "abort") {
2108  CoinsViewScanReserver reserver;
2109  if (reserver.reserve()) {
2110  // reserve was possible which means no scan was running
2111  return false;
2112  }
2113  // set the abort flag
2114  g_should_abort_scan = true;
2115  return true;
2116  } else if (request.params[0].get_str() == "start") {
2117  CoinsViewScanReserver reserver;
2118  if (!reserver.reserve()) {
2119  throw JSONRPCError(RPC_INVALID_PARAMETER, "Scan already in progress, use action \"abort\" or \"status\"");
2120  }
2121  std::set<CScript> needles;
2122  CAmount total_in = 0;
2123 
2124  // loop through the scan objects
2125  for (const UniValue& scanobject : request.params[1].get_array().getValues()) {
2126  std::string desc_str;
2127  int range = 1000;
2128  if (scanobject.isStr()) {
2129  desc_str = scanobject.get_str();
2130  } else if (scanobject.isObject()) {
2131  UniValue desc_uni = find_value(scanobject, "desc");
2132  if (desc_uni.isNull()) throw JSONRPCError(RPC_INVALID_PARAMETER, "Descriptor needs to be provided in scan object");
2133  desc_str = desc_uni.get_str();
2134  UniValue range_uni = find_value(scanobject, "range");
2135  if (!range_uni.isNull()) {
2136  range = range_uni.get_int();
2137  if (range < 0 || range > 1000000) throw JSONRPCError(RPC_INVALID_PARAMETER, "range out of range");
2138  }
2139  } else {
2140  throw JSONRPCError(RPC_INVALID_PARAMETER, "Scan object needs to be either a string or an object");
2141  }
2142 
2143  FlatSigningProvider provider;
2144  auto desc = Parse(desc_str, provider);
2145  if (!desc) {
2146  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, strprintf("Invalid descriptor '%s'", desc_str));
2147  }
2148  if (!desc->IsRange()) range = 0;
2149  for (int i = 0; i <= range; ++i) {
2150  std::vector<CScript> scripts;
2151  if (!desc->Expand(i, provider, scripts, provider)) {
2152  throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, strprintf("Cannot derive script without private keys: '%s'", desc_str));
2153  }
2154  needles.insert(scripts.begin(), scripts.end());
2155  }
2156  }
2157 
2158  // Scan the unspent transaction output set for inputs
2159  UniValue unspents(UniValue::VARR);
2160  std::vector<CTxOut> input_txos;
2161  std::map<COutPoint, Coin> coins;
2162  g_should_abort_scan = false;
2163  g_scan_progress = 0;
2164  int64_t count = 0;
2165  std::unique_ptr<CCoinsViewCursor> pcursor;
2166  {
2167  LOCK(cs_main);
2168  FlushStateToDisk();
2169  pcursor = std::unique_ptr<CCoinsViewCursor>(pcoinsdbview->Cursor());
2170  assert(pcursor);
2171  }
2172  bool res = FindScriptPubKey(g_scan_progress, g_should_abort_scan, count, pcursor.get(), needles, coins);
2173  result.pushKV("success", res);
2174  result.pushKV("searched_items", count);
2175 
2176  for (const auto& it : coins) {
2177  const COutPoint& outpoint = it.first;
2178  const Coin& coin = it.second;
2179  const CTxOut& txo = coin.out;
2180  input_txos.push_back(txo);
2181  total_in += txo.nValue;
2182 
2183  UniValue unspent(UniValue::VOBJ);
2184  unspent.pushKV("txid", outpoint.hash.GetHex());
2185  unspent.pushKV("vout", (int32_t)outpoint.n);
2186  unspent.pushKV("scriptPubKey", HexStr(txo.scriptPubKey.begin(), txo.scriptPubKey.end()));
2187  unspent.pushKV("amount", ValueFromAmount(txo.nValue));
2188  unspent.pushKV("height", (int32_t)coin.nHeight);
2189 
2190  unspents.push_back(unspent);
2191  }
2192  result.pushKV("unspents", unspents);
2193  result.pushKV("total_amount", ValueFromAmount(total_in));
2194  } else {
2195  throw JSONRPCError(RPC_INVALID_PARAMETER, "Invalid command");
2196  }
2197  return result;
2198 }
2199 
2200 // clang-format off
2201 static const CRPCCommand commands[] =
2202 { // category name actor (function) argNames
2203  // --------------------- ------------------------ ----------------------- ----------
2204  { "blockchain", "getblockchaininfo", &getblockchaininfo, {} },
2205  { "blockchain", "getchaintxstats", &getchaintxstats, {"nblocks", "blockhash"} },
2206  { "blockchain", "getblockstats", &getblockstats, {"hash_or_height", "stats"} },
2207  { "blockchain", "getbestblockhash", &getbestblockhash, {} },
2208  { "blockchain", "getblockcount", &getblockcount, {} },
2209  { "blockchain", "getblock", &getblock, {"blockhash","verbosity|verbose"} },
2210  { "blockchain", "getblockhash", &getblockhash, {"height"} },
2211  { "blockchain", "getblockheader", &getblockheader, {"blockhash","verbose"} },
2212  { "blockchain", "getchaintips", &getchaintips, {} },
2213  { "blockchain", "getdifficulty", &getdifficulty, {} },
2214  { "blockchain", "getmempoolancestors", &getmempoolancestors, {"txid","verbose"} },
2215  { "blockchain", "getmempooldescendants", &getmempooldescendants, {"txid","verbose"} },
2216  { "blockchain", "getmempoolentry", &getmempoolentry, {"txid"} },
2217  { "blockchain", "getmempoolinfo", &getmempoolinfo, {} },
2218  { "blockchain", "getrawmempool", &getrawmempool, {"verbose"} },
2219  { "blockchain", "gettxout", &gettxout, {"txid","n","include_mempool"} },
2220  { "blockchain", "gettxoutsetinfo", &gettxoutsetinfo, {} },
2221  { "blockchain", "pruneblockchain", &pruneblockchain, {"height"} },
2222  { "blockchain", "savemempool", &savemempool, {} },
2223  { "blockchain", "verifychain", &verifychain, {"checklevel","nblocks"} },
2224 
2225  { "blockchain", "preciousblock", &preciousblock, {"blockhash"} },
2226  { "blockchain", "scantxoutset", &scantxoutset, {"action", "scanobjects"} },
2227 
2228  /* Not shown in help */
2229  { "hidden", "invalidateblock", &invalidateblock, {"blockhash"} },
2230  { "hidden", "reconsiderblock", &reconsiderblock, {"blockhash"} },
2231  { "hidden", "waitfornewblock", &waitfornewblock, {"timeout"} },
2232  { "hidden", "waitforblock", &waitforblock, {"blockhash","timeout"} },
2233  { "hidden", "waitforblockheight", &waitforblockheight, {"height","timeout"} },
2234  { "hidden", "syncwithvalidationinterfacequeue", &syncwithvalidationinterfacequeue, {} },
2235 };
2236 // clang-format on
2237 
2239 {
2240  for (unsigned int vcidx = 0; vcidx < ARRAYLEN(commands); vcidx++)
2241  t.appendCommand(commands[vcidx].name, &commands[vcidx]);
2242 }
uint32_t nNonce
Definition: block.h:29
arith_uint256 nChainWork
(memory only) Total amount of work (expected number of hashes) in the chain up to and including this ...
Definition: chain.h:195
CAmount nValue
Definition: transaction.h:134
CTxMemPool mempool
void SyncWithValidationInterfaceQueue()
This is a synonym for the following, which asserts certain locks are not held: std::promise<void> pro...
uint64_t nTransactionOutputs
Definition: blockchain.cpp:861
bool fPruneMode
True if we&#39;re running in -prune mode.
Definition: validation.cpp:228
CAmount GetBlockSubsidy(int nHeight, const Consensus::Params &consensusParams)
const std::vector< UniValue > & getValues() const
bool GetTransaction(const uint256 &hash, CTransactionRef &txOut, const Consensus::Params &consensusParams, uint256 &hashBlock, bool fAllowSlow, CBlockIndex *blockIndex)
Return transaction in txOut, and if it was found inside a block, its hash is placed in hashBlock...
Definition: validation.cpp:998
Bitcoin RPC command dispatcher.
Definition: server.h:143
int64_t GetBlockTime() const
Definition: chain.h:297
indexed_transaction_set::nth_index< 0 >::type::const_iterator txiter
Definition: txmempool.h:490
uint256 hashBlock
Definition: blockchain.cpp:859
virtual bool GetCoin(const COutPoint &outpoint, Coin &coin) const
Retrieve the Coin (unspent transaction output) for a given outpoint.
Definition: coins.cpp:10
CScript scriptPubKey
Definition: transaction.h:135
CBlockIndex * pprev
pointer to the index of the predecessor of this block
Definition: chain.h:177
uint32_t nStatus
Verification status of this block. See enum BlockStatus.
Definition: chain.h:207
bool get_bool() const
bool IsRPCRunning()
Query whether RPC is running.
Definition: server.cpp:321
A UTXO entry.
Definition: coins.h:29
Definition: block.h:74
#define strprintf
Definition: tinyformat.h:1066
bool VerifyDB(const CChainParams &chainparams, CCoinsView *coinsview, int nCheckLevel, int nCheckDepth)
std::unique_ptr< Descriptor > Parse(const std::string &descriptor, FlatSigningProvider &out)
Parse a descriptor string.
Definition: descriptor.cpp:630
bool InvalidateBlock(CValidationState &state, const CChainParams &chainparams, CBlockIndex *pindex)
Mark a block as invalid.
void CalculateDescendants(txiter it, setEntries &setDescendants) const EXCLUSIVE_LOCKS_REQUIRED(cs)
Populate setDescendants with all in-mempool descendants of hash.
Definition: txmempool.cpp:437
size_t DynamicMemoryUsage() const
Definition: txmempool.cpp:911
BlockMap & mapBlockIndex
Definition: validation.cpp:218
RBFTransactionState
Definition: rbf.h:12
virtual void Next()=0
UniValue mempoolInfoToJSON()
Mempool information to JSON.
Comparison function for sorting the getchaintips heads.
UniValue ret(UniValue::VARR)
Definition: rpcwallet.cpp:1140
UniValue scantxoutset(const JSONRPCRequest &request)
All parent headers found, difficulty matches, timestamp >= median previous, checkpoint.
Definition: chain.h:134
bool MoneyRange(const CAmount &nValue)
Definition: amount.h:26
CBlockHeader GetBlockHeader() const
Definition: chain.h:279
int Height() const
Return the maximal height in the chain.
Definition: chain.h:476
bool IsValid() const
Definition: validation.h:65
CTxOut out
unspent transaction output
Definition: coins.h:33
UniValue ValueFromAmount(const CAmount &amount)
Definition: core_write.cpp:19
std::string HexStr(const T itbegin, const T itend, bool fSpaces=false)
unsigned int fCoinBase
whether containing transaction was a coinbase
Definition: coins.h:36
uint64_t GetTotalTxSize() const
Definition: txmempool.h:644
UniValue blockheaderToJSON(const CBlockIndex *blockindex)
Block header to JSON.
Definition: blockchain.cpp:88
virtual CCoinsViewCursor * Cursor() const
Get a cursor to iterate over the whole state.
Definition: coins.cpp:14
std::set< txiter, CompareIteratorByHash > setEntries
Definition: txmempool.h:498
uint64_t nTransactions
Definition: blockchain.cpp:860
const std::string & get_str() const
void queryHashes(std::vector< uint256 > &vtxid)
Definition: txmempool.cpp:767
uint64_t nDiskSize
Definition: blockchain.cpp:864
bool isNum() const
Definition: univalue.h:83
std::string HelpExampleRpc(const std::string &methodname, const std::string &args)
Definition: server.cpp:516
const UniValue & get_array() const
const std::string CURRENCY_UNIT
Definition: feerate.cpp:10
Double ended buffer combining vector and stream-like interfaces.
Definition: streams.h:221
uint32_t nTime
Definition: chain.h:212
double GetDifficulty(const CBlockIndex *blockindex)
Get the difficulty of the net wrt to the given block index.
Definition: blockchain.cpp:60
std::string GetWarnings(const std::string &strFor)
Format a string that describes several potential problems detected by the core.
Definition: warnings.cpp:40
bool FindScriptPubKey(std::atomic< int > &scan_progress, const std::atomic< bool > &should_abort, int64_t &count, CCoinsViewCursor *cursor, const std::set< CScript > &needles, std::map< COutPoint, Coin > &out_results)
Search for a given set of pubkey scripts.
uint64_t nPruneTarget
Number of MiB of block files that we&#39;re trying to stay below.
Definition: validation.cpp:234
unsigned char * begin()
Definition: uint256.h:56
std::shared_ptr< const CTransaction > CTransactionRef
Definition: transaction.h:402
bool appendCommand(const std::string &name, const CRPCCommand *pcmd)
Appends a CRPCCommand to the dispatch table.
Definition: server.cpp:285
uint64_t nBogoSize
Definition: blockchain.cpp:862
bool IsCoinBase() const
Definition: transaction.h:331
unsigned int nChainTx
(memory only) Number of transactions in the chain up to and including this block. ...
Definition: chain.h:204
bool ActivateBestChain(CValidationState &state, const CChainParams &chainparams, std::shared_ptr< const CBlock > pblock)
Find the best known block, and make it the tip of the block chain.
uint256 hash
Definition: blockchain.cpp:50
bool isSpent(const COutPoint &outpoint) const
Definition: txmempool.cpp:337
const std::vector< CTxIn > vin
Definition: transaction.h:281
Invalid, missing or duplicate parameter.
Definition: protocol.h:52
uint256 ParseHashV(const UniValue &v, std::string strName)
Utilities: convert hex-encoded Values (throws error if not hex).
Definition: server.cpp:117
size_t GetSerializeSize(const T &t, int nVersion=0)
Definition: serialize.h:981
const UniValue & find_value(const UniValue &obj, const std::string &name)
Definition: univalue.cpp:234
CTxMemPoolEntry stores data about the corresponding transaction, as well as data about all in-mempool...
Definition: txmempool.h:65
CAmount nTotalAmount
Definition: blockchain.cpp:865
std::unique_ptr< CCoinsViewCache > pcoinsTip
Global variable that points to the active CCoinsView (protected by cs_main)
Definition: validation.cpp:298
uint256 hashSerialized
Definition: blockchain.cpp:863
int64_t CAmount
Amount in satoshis (Can be negative)
Definition: amount.h:12
virtual bool GetValue(Coin &coin) const =0
uint256 GetBlockHash() const
Definition: chain.h:292
#define AssertLockHeld(cs)
Definition: sync.h:70
uint32_t nHeight
at which height this containing transaction was included in the active block chain ...
Definition: coins.h:39
iterator end()
Definition: prevector.h:303
std::string name
Definition: server.h:135
std::vector< std::pair< uint256, txiter > > vTxHashes
All tx witness hashes/entries in mapTx, in random order.
Definition: txmempool.h:491
bool push_back(const UniValue &val)
Definition: univalue.cpp:108
bool operator()(const CBlockIndex *a, const CBlockIndex *b) const
void ResetBlockFailureFlags(CBlockIndex *pindex)
Remove invalidity status from a block and its descendants.
CCriticalSection cs_main
Definition: validation.cpp:216
virtual bool Valid() const =0
Scripts & signatures ok. Implies all parents are also at least SCRIPTS.
Definition: chain.h:148
unsigned long size()
Definition: txmempool.h:638
uint256 hashMerkleRoot
Definition: block.h:26
void RegisterBlockchainRPCCommands(CRPCTable &t)
Register block chain RPC commands.
uint32_t nNonce
Definition: chain.h:214
Abstract view on the open txout dataset.
Definition: coins.h:145
CFeeRate minRelayTxFee
A fee rate smaller than this is considered zero fee (for relaying, mining and transaction creation) ...
Definition: validation.cpp:241
UniValue params
Definition: server.h:44
CBlockIndex * pindexBestHeader
Best header we&#39;ve seen so far (used for getheaders queries&#39; starting points).
Definition: validation.cpp:220
bool exists(const uint256 &hash) const
Definition: txmempool.h:650
An input of a transaction.
Definition: transaction.h:61
#define LOCK(cs)
Definition: sync.h:181
std::unique_ptr< TxIndex > g_txindex
The global transaction index, used in GetTransaction. May be null.
Definition: txindex.cpp:17
const uint256 & GetHash() const
Definition: transaction.h:316
std::unique_ptr< CCoinsViewDB > pcoinsdbview
Global variable that points to the coins database (protected by cs_main)
Definition: validation.cpp:297
bool Contains(const CBlockIndex *pindex) const
Efficiently check whether a block is present in this chain.
Definition: chain.h:463
CBlockIndex * FindEarliestAtLeast(int64_t nTime) const
Find the earliest block with timestamp equal or greater than the given.
Definition: chain.cpp:62
int64_t nPowTargetSpacing
Definition: params.h:60
CBlockIndex * Next(const CBlockIndex *pindex) const
Find the successor of a block in this chain, or nullptr if the given index is not found or is the tip...
Definition: chain.h:468
RAII wrapper for VerifyDB: Verify consistency of the block and coin databases.
Definition: validation.h:421
uint32_t n
Definition: transaction.h:22
const std::vector< CTxOut > vout
Definition: transaction.h:282
bool IsInitialBlockDownload()
Check whether we are doing an initial block download (synchronizing from disk or network) ...
uint256 hashMerkleRoot
Definition: chain.h:211
General application defined errors.
Definition: protocol.h:48
bool pushKV(const std::string &key, const UniValue &val)
Definition: univalue.cpp:133
void RPCTypeCheck(const UniValue &params, const std::list< UniValueType > &typesExpected, bool fAllowNull)
Type-check arguments; throws JSONRPCError if wrong type given.
Definition: server.cpp:51
#define WAIT_LOCK(cs, name)
Definition: sync.h:186
An output of a transaction.
Definition: transaction.h:131
int get_int() const
std::string ToString() const
Definition: uint256.cpp:62
const setEntries & GetMemPoolChildren(txiter entry) const EXCLUSIVE_LOCKS_REQUIRED(cs)
Definition: txmempool.cpp:978
Invalid address or key.
Definition: protocol.h:50
std::string HelpExampleCli(const std::string &methodname, const std::string &args)
Definition: server.cpp:511
bool CalculateMemPoolAncestors(const CTxMemPoolEntry &entry, setEntries &setAncestors, uint64_t limitAncestorCount, uint64_t limitAncestorSize, uint64_t limitDescendantCount, uint64_t limitDescendantSize, std::string &errString, bool fSearchForParents=true) const EXCLUSIVE_LOCKS_REQUIRED(cs)
Try to calculate all in-mempool ancestors of entry.
Definition: txmempool.cpp:149
An outpoint - a combination of a transaction hash and an index n into its vout.
Definition: transaction.h:18
int64_t GetBlockTime() const
Definition: block.h:67
CFeeRate GetMinFee(size_t sizelimit) const
The minimum fee to get into the mempool, which may itself not be enough for larger-sized transactions...
Definition: txmempool.cpp:986
UniValue gettxout(const JSONRPCRequest &request)
bool DumpMempool()
Dump the mempool to disk.
bool isNull() const
Definition: univalue.h:78
int64_t GetMedianTimePast() const
Definition: chain.h:309
CCriticalSection cs
Definition: txmempool.h:487
void FlushStateToDisk()
Flush all state, indexes and buffers to disk.
UniValue mempoolToJSON(bool fVerbose)
Mempool to JSON.
Definition: blockchain.cpp:451
virtual bool GetKey(COutPoint &key) const =0
Database error.
Definition: protocol.h:53
uint256 GetHash()
Definition: hash.h:184
bool fHelp
Definition: server.h:45
int32_t nVersion
block header
Definition: chain.h:210
Capture information about block/transaction validation.
Definition: validation.h:26
256-bit opaque blob.
Definition: uint256.h:122
bool HasWitness() const
Definition: transaction.h:348
ArgsManager gArgs
Definition: util.cpp:88
std::atomic_bool g_is_mempool_loaded
Definition: validation.cpp:246
#define EXCLUSIVE_LOCKS_REQUIRED(...)
Definition: threadsafety.h:51
std::vector< CTransactionRef > vtx
Definition: block.h:78
std::string FormatStateMessage(const CValidationState &state)
Convert CValidationState to a human-readable message for logging.
Definition: validation.cpp:453
RBFTransactionState IsRBFOptIn(const CTransaction &tx, CTxMemPool &pool)
Definition: rbf.cpp:17
#define ARRAYLEN(array)
virtual size_t EstimateSize() const
Estimate database size (0 if not implemented)
Definition: coins.h:177
The block chain is a tree shaped structure starting with the genesis block at the root...
Definition: chain.h:170
const CChainParams & Params()
Return the currently selected parameters.
bool IsBlockPruned(const CBlockIndex *pblockindex)
Check whether the block associated with this index entry is pruned or not.
Definition: validation.h:498
int RPCSerializationFlags()
Definition: server.cpp:548
const CTransaction & GetTx() const
Definition: txmempool.h:98
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...
UniValue getblockchaininfo(const JSONRPCRequest &request)
Implementation of IsSuperMajority with better feedback.
std::string GetArg(const std::string &strArg, const std::string &strDefault) const
Return string argument or default value.
Definition: util.cpp:526
void PruneBlockFilesManual(int nManualPruneHeight)
Prune block files up to a given height.
bool PreciousBlock(CValidationState &state, const CChainParams &params, CBlockIndex *pindex)
Mark a block as precious and reorganize.
CBlockIndex * Tip() const
Returns the index entry for the tip of this chain, or nullptr if none.
Definition: chain.h:445
std::string GetHex() const
Definition: uint256.cpp:21
const UniValue NullUniValue
Definition: univalue.cpp:13
bool error(const char *fmt, const Args &... args)
Definition: util.h:59
iterator begin()
Definition: prevector.h:301
void ScriptPubKeyToUniv(const CScript &scriptPubKey, UniValue &out, bool fIncludeHex)
Definition: core_write.cpp:153
A writer stream (for serialization) that computes a 256-bit SHA-3-256 hash.
Definition: hash.h:165
unsigned int GetTotalSize() const
Get the total transaction size in bytes, including witness data.
Definition: transaction.cpp:94
void RPCNotifyBlockChange(bool ibd, const CBlockIndex *pindex)
Callback for when block tip changed.
Definition: blockchain.cpp:198
void TxToUniv(const CTransaction &tx, const uint256 &hashBlock, UniValue &entry, bool include_hex=true, int serialize_flags=0)
Definition: core_write.cpp:179
UniValue JSONRPCError(int code, const std::string &message)
Definition: protocol.cpp:51
std::string GetHex() const
size_t size() const
Definition: univalue.h:69
The basic transaction that is broadcasted on the network and contained in blocks. ...
Definition: transaction.h:264
int nHeight
height of the entry in the chain. The genesis block has height 0
Definition: chain.h:183
const Consensus::Params & GetConsensus() const
Definition: chainparams.h:60
bool ReadBlockFromDisk(CBlock &block, const CDiskBlockPos &pos, const Consensus::Params &consensusParams)
Functions for disk access for blocks.
CBlockIndex * GetAncestor(int height)
Efficiently find an ancestor of this block.
Definition: chain.cpp:110
full block available in blk*.dat
Definition: chain.h:154
CChain & chainActive
The currently-connected chain of blocks (protected by cs_main).
Definition: validation.cpp:219
uint64_t CalculateCurrentUsage()
BLOCK PRUNING CODE.
UniValue blockToJSON(const CBlock &block, const CBlockIndex *blockindex, bool txDetails)
Block description to JSON.
Definition: blockchain.cpp:118
COutPoint prevout
Definition: transaction.h:64
const CBlockIndex * FindFork(const CBlockIndex *pindex) const
Find the last common block between this chain and a block index entry.
Definition: chain.cpp:51
CCoinsView that brings transactions from a mempool into view.
Definition: txmempool.h:715
int32_t nVersion
Definition: block.h:24
void CalculatePercentilesByWeight(CAmount result[NUM_GETBLOCKSTATS_PERCENTILES], std::vector< std::pair< CAmount, int64_t >> &scores, int64_t total_weight)
Used by getblockstats to get feerates at different percentiles by weight.
uint32_t nBits
Definition: chain.h:213
#define VARINT(obj,...)
Definition: serialize.h:411
CAmount GetFeePerK() const
Return the fee in satoshis for a size of 1000 bytes.
Definition: feerate.h:41
unsigned int nTx
Number of transactions in this block.
Definition: chain.h:199
uint32_t nBits
Definition: block.h:28
uint256 hash
Definition: transaction.h:21
CBlockIndex * LookupBlockIndex(const uint256 &hash)
Definition: validation.h:431
Cursor for iterating over CoinsView state.
Definition: coins.h:125