Skip to content

Commit 3c914d5

Browse files
committed
index: Coinstats index can be activated with command line flag
1 parent dd58a4d commit 3c914d5

File tree

5 files changed

+38
-5
lines changed

5 files changed

+38
-5
lines changed

src/init.cpp

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
#include <httprpc.h>
2222
#include <httpserver.h>
2323
#include <index/blockfilterindex.h>
24+
#include <index/coinstatsindex.h>
2425
#include <index/txindex.h>
2526
#include <interfaces/chain.h>
2627
#include <interfaces/node.h>
@@ -167,6 +168,9 @@ void Interrupt(NodeContext& node)
167168
g_txindex->Interrupt();
168169
}
169170
ForEachBlockFilterIndex([](BlockFilterIndex& index) { index.Interrupt(); });
171+
if (g_coin_stats_index) {
172+
g_coin_stats_index->Interrupt();
173+
}
170174
}
171175

172176
void Shutdown(NodeContext& node)
@@ -252,6 +256,10 @@ void Shutdown(NodeContext& node)
252256
g_txindex->Stop();
253257
g_txindex.reset();
254258
}
259+
if (g_coin_stats_index) {
260+
g_coin_stats_index->Stop();
261+
g_coin_stats_index.reset();
262+
}
255263
ForEachBlockFilterIndex([](BlockFilterIndex& index) { index.Stop(); });
256264
DestroyAllBlockFilterIndexes();
257265

@@ -390,6 +398,7 @@ void SetupServerArgs(NodeContext& node)
390398
#endif
391399
argsman.AddArg("-blockreconstructionextratxn=<n>", strprintf("Extra transactions to keep in memory for compact block reconstructions (default: %u)", DEFAULT_BLOCK_RECONSTRUCTION_EXTRA_TXN), ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
392400
argsman.AddArg("-blocksonly", strprintf("Whether to reject transactions from network peers. Automatic broadcast and rebroadcast of any transactions from inbound peers is disabled, unless the peer has the 'forcerelay' permission. RPC transactions are not affected. (default: %u)", DEFAULT_BLOCKSONLY), ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
401+
argsman.AddArg("-coinstatsindex", strprintf("Maintain coinstats index used by the gettxoutset RPC (default: %u)", DEFAULT_COINSTATSINDEX), ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
393402
argsman.AddArg("-conf=<file>", strprintf("Specify path to read-only configuration file. Relative paths will be prefixed by datadir location. (default: %s)", BITCOIN_CONF_FILENAME), ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
394403
argsman.AddArg("-datadir=<dir>", "Specify data directory", ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
395404
argsman.AddArg("-dbbatchsize", strprintf("Maximum database write batch size in bytes (default: %u)", nDefaultDbBatchSize), ArgsManager::ALLOW_ANY | ArgsManager::DEBUG_ONLY, OptionsCategory::OPTIONS);
@@ -406,7 +415,7 @@ void SetupServerArgs(NodeContext& node)
406415
-GetNumCores(), MAX_SCRIPTCHECK_THREADS, DEFAULT_SCRIPTCHECK_THREADS), ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
407416
argsman.AddArg("-persistmempool", strprintf("Whether to save the mempool on shutdown and load on restart (default: %u)", DEFAULT_PERSIST_MEMPOOL), ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
408417
argsman.AddArg("-pid=<file>", strprintf("Specify pid file. Relative paths will be prefixed by a net-specific datadir location. (default: %s)", BITCOIN_PID_FILENAME), ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
409-
argsman.AddArg("-prune=<n>", strprintf("Reduce storage requirements by enabling pruning (deleting) of old blocks. This allows the pruneblockchain RPC to be called to delete specific blocks, and enables automatic pruning of old blocks if a target size in MiB is provided. This mode is incompatible with -txindex and -rescan. "
418+
argsman.AddArg("-prune=<n>", strprintf("Reduce storage requirements by enabling pruning (deleting) of old blocks. This allows the pruneblockchain RPC to be called to delete specific blocks, and enables automatic pruning of old blocks if a target size in MiB is provided. This mode is incompatible with -txindex, -coinstatsindex and -rescan. "
410419
"Warning: Reverting this setting requires re-downloading the entire blockchain. "
411420
"(default: 0 = disable pruning blocks, 1 = allow manual pruning via RPC, >=%u = automatically prune block files to stay under the specified target size in MiB)", MIN_DISK_SPACE_FOR_BLOCK_FILES / 1024 / 1024), ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
412421
argsman.AddArg("-reindex", "Rebuild chain state and block index from the blk*.dat files on disk", ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
@@ -947,10 +956,12 @@ bool AppInitParameterInteraction(const ArgsManager& args)
947956
nLocalServices = ServiceFlags(nLocalServices | NODE_COMPACT_FILTERS);
948957
}
949958

950-
// if using block pruning, then disallow txindex
959+
// if using block pruning, then disallow txindex and coinstatsindex
951960
if (args.GetArg("-prune", 0)) {
952961
if (args.GetBoolArg("-txindex", DEFAULT_TXINDEX))
953962
return InitError(_("Prune mode is incompatible with -txindex."));
963+
if (args.GetBoolArg("-coinstatsindex", DEFAULT_COINSTATSINDEX))
964+
return InitError(_("Prune mode is incompatible with -coinstatsindex."));
954965
}
955966

956967
// -bind and -whitebind can't be set when not listening
@@ -1724,6 +1735,11 @@ bool AppInitMain(NodeContext& node, interfaces::BlockAndHeaderTipInfo* tip_info)
17241735
GetBlockFilterIndex(filter_type)->Start();
17251736
}
17261737

1738+
if (args.GetBoolArg("-coinstatsindex", DEFAULT_COINSTATSINDEX)) {
1739+
g_coin_stats_index = std::make_unique<CoinStatsIndex>(/* cache size */ 0, false, fReindex);
1740+
g_coin_stats_index->Start();
1741+
}
1742+
17271743
// ********************************************************* Step 9: load wallet
17281744
for (const auto& client : node.chain_clients) {
17291745
if (!client->load()) {

src/node/coinstats.cpp

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
#include <coins.h>
99
#include <crypto/muhash.h>
1010
#include <hash.h>
11+
#include <index/coinstatsindex.h>
1112
#include <serialize.h>
1213
#include <uint256.h>
1314
#include <util/system.h>
@@ -92,13 +93,19 @@ static bool GetUTXOStats(CCoinsView* view, BlockManager& blockman, CCoinsStats&
9293
{
9394
std::unique_ptr<CCoinsViewCursor> pcursor(view->Cursor());
9495
assert(pcursor);
95-
9696
stats.hashBlock = pcursor->GetBestBlock();
97+
98+
const CBlockIndex* pindex;
9799
{
98100
LOCK(cs_main);
99101
assert(std::addressof(g_chainman.m_blockman) == std::addressof(blockman));
100-
const CBlockIndex* block = blockman.LookupBlockIndex(stats.hashBlock);
101-
stats.nHeight = Assert(block)->nHeight;
102+
pindex = blockman.LookupBlockIndex(stats.hashBlock);
103+
stats.nHeight = Assert(pindex)->nHeight;
104+
}
105+
106+
// Use CoinStatsIndex if it is available and a hash_type of Muhash or None was requested
107+
if ((stats.m_hash_type == CoinStatsHashType::MUHASH || stats.m_hash_type == CoinStatsHashType::NONE) && g_coin_stats_index) {
108+
return g_coin_stats_index->LookUpStats(pindex, stats);
102109
}
103110

104111
PrepareHash(hash_obj, stats);

src/rpc/blockchain.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
#include <core_io.h>
1515
#include <hash.h>
1616
#include <index/blockfilterindex.h>
17+
#include <index/coinstatsindex.h>
1718
#include <node/blockstorage.h>
1819
#include <node/coinstats.h>
1920
#include <node/context.h>
@@ -1124,6 +1125,13 @@ static RPCHelpMan gettxoutsetinfo()
11241125
ret.pushKV("disk_size", stats.nDiskSize);
11251126
ret.pushKV("total_amount", ValueFromAmount(stats.nTotalAmount));
11261127
} else {
1128+
if (g_coin_stats_index) {
1129+
const IndexSummary summary{g_coin_stats_index->GetSummary()};
1130+
1131+
if (!summary.synced) {
1132+
throw JSONRPCError(RPC_INTERNAL_ERROR, strprintf("Unable to read UTXO set because coinstatsindex is still syncing. Current height: %d", summary.best_block_height));
1133+
}
1134+
}
11271135
throw JSONRPCError(RPC_INTERNAL_ERROR, "Unable to read UTXO set");
11281136
}
11291137
return ret;

src/validation.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,7 @@ static const int DEFAULT_SCRIPTCHECK_THREADS = 0;
7979
static const int64_t DEFAULT_MAX_TIP_AGE = 24 * 60 * 60;
8080
static const bool DEFAULT_CHECKPOINTS_ENABLED = true;
8181
static const bool DEFAULT_TXINDEX = false;
82+
static constexpr bool DEFAULT_COINSTATSINDEX{false};
8283
static const char* const DEFAULT_BLOCKFILTERINDEX = "0";
8384
/** Default for -persistmempool */
8485
static const bool DEFAULT_PERSIST_MEMPOOL = true;

test/lint/lint-circular-dependencies.sh

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ EXPECTED_CIRCULAR_DEPENDENCIES=(
1414
"node/blockstorage -> validation -> node/blockstorage"
1515
"index/blockfilterindex -> node/blockstorage -> validation -> index/blockfilterindex"
1616
"index/base -> validation -> index/blockfilterindex -> index/base"
17+
"index/coinstatsindex -> node/coinstats -> index/coinstatsindex"
1718
"policy/fees -> txmempool -> policy/fees"
1819
"qt/addresstablemodel -> qt/walletmodel -> qt/addresstablemodel"
1920
"qt/bitcoingui -> qt/walletframe -> qt/bitcoingui"

0 commit comments

Comments
 (0)