aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/Makefile.test.include1
-rw-r--r--src/bitcoin-cli.cpp13
-rw-r--r--src/fs.h22
-rw-r--r--src/index/base.h4
-rw-r--r--src/index/coinstatsindex.cpp8
-rw-r--r--src/primitives/transaction.h2
-rw-r--r--src/rpc/blockchain.cpp2
-rw-r--r--src/streams.h101
-rw-r--r--src/test/dbwrapper_tests.cpp4
-rw-r--r--src/test/fs_tests.cpp24
-rw-r--r--src/test/fuzz/script.cpp8
-rw-r--r--src/test/fuzz/script_format.cpp30
-rw-r--r--src/util/overflow.h1
-rw-r--r--src/util/syscall_sandbox.cpp6
-rw-r--r--src/validation.cpp13
-rw-r--r--src/validation.h2
16 files changed, 161 insertions, 80 deletions
diff --git a/src/Makefile.test.include b/src/Makefile.test.include
index 1763dcb562..e2e08468a7 100644
--- a/src/Makefile.test.include
+++ b/src/Makefile.test.include
@@ -294,6 +294,7 @@ test_fuzz_fuzz_SOURCES = \
test/fuzz/script_bitcoin_consensus.cpp \
test/fuzz/script_descriptor_cache.cpp \
test/fuzz/script_flags.cpp \
+ test/fuzz/script_format.cpp \
test/fuzz/script_interpreter.cpp \
test/fuzz/script_ops.cpp \
test/fuzz/script_sigcache.cpp \
diff --git a/src/bitcoin-cli.cpp b/src/bitcoin-cli.cpp
index 6557360a71..a85a74835d 100644
--- a/src/bitcoin-cli.cpp
+++ b/src/bitcoin-cli.cpp
@@ -606,8 +606,9 @@ public:
"Suggestion: use with the Linux watch(1) command for a live dashboard; see example below.\n\n"
"Arguments:\n"
+ strprintf("1. level (integer 0-%d, optional) Specify the info level of the peers dashboard (default 0):\n", MAX_DETAIL_LEVEL) +
- " 0 - Connection counts and local addresses\n"
- " 1 - Like 0 but with a peers listing (without address or version columns)\n"
+ " 0 - Peer counts for each reachable network as well as for block relay peers\n"
+ " and manual peers, and the list of local addresses and ports\n"
+ " 1 - Like 0 but preceded by a peers listing (without address and version columns)\n"
" 2 - Like 1 but with an address column\n"
" 3 - Like 1 but with a version column\n"
" 4 - Like 1 but with both address and version columns\n"
@@ -645,13 +646,13 @@ public:
" id Peer index, in increasing order of peer connections since node startup\n"
" address IP address and port of the peer\n"
" version Peer version and subversion concatenated, e.g. \"70016/Satoshi:21.0.0/\"\n\n"
- "* The connection counts table displays the number of peers by direction, network, and the totals\n"
- " for each, as well as two special outbound columns for block relay peers and manual peers.\n\n"
+ "* The peer counts table displays the number of peers for each reachable network as well as\n"
+ " the number of block relay peers and manual peers.\n\n"
"* The local addresses table lists each local address broadcast by the node, the port, and the score.\n\n"
"Examples:\n\n"
- "Connection counts and local addresses only\n"
+ "Peer counts table of reachable networks and list of local addresses\n"
"> bitcoin-cli -netinfo\n\n"
- "Compact peers listing\n"
+ "The same, preceded by a peers listing without address and version columns\n"
"> bitcoin-cli -netinfo 1\n\n"
"Full dashboard\n"
+ strprintf("> bitcoin-cli -netinfo %d\n\n", MAX_DETAIL_LEVEL) +
diff --git a/src/fs.h b/src/fs.h
index d2299db168..00b786453c 100644
--- a/src/fs.h
+++ b/src/fs.h
@@ -140,6 +140,28 @@ static inline path PathFromString(const std::string& string)
return std::filesystem::path(string);
#endif
}
+
+/**
+ * Create directory (and if necessary its parents), unless the leaf directory
+ * already exists or is a symlink to an existing directory.
+ * This is a temporary workaround for an issue in libstdc++ that has been fixed
+ * upstream [PR101510].
+ */
+static inline bool create_directories(const std::filesystem::path& p)
+{
+ if (std::filesystem::is_symlink(p) && std::filesystem::is_directory(p)) {
+ return false;
+ }
+ return std::filesystem::create_directories(p);
+}
+
+/**
+ * This variant is not used. Delete it to prevent it from accidentally working
+ * around the workaround. If it is needed, add a workaround in the same pattern
+ * as above.
+ */
+bool create_directories(const std::filesystem::path& p, std::error_code& ec) = delete;
+
} // namespace fs
/** Bridge operations to C stdio */
diff --git a/src/index/base.h b/src/index/base.h
index 66149686f0..c4a8215bc4 100644
--- a/src/index/base.h
+++ b/src/index/base.h
@@ -40,10 +40,10 @@ protected:
DB(const fs::path& path, size_t n_cache_size,
bool f_memory = false, bool f_wipe = false, bool f_obfuscate = false);
- /// Read block locator of the chain that the txindex is in sync with.
+ /// Read block locator of the chain that the index is in sync with.
bool ReadBestBlock(CBlockLocator& locator) const;
- /// Write block locator of the chain that the txindex is in sync with.
+ /// Write block locator of the chain that the index is in sync with.
void WriteBestBlock(CDBBatch& batch, const CBlockLocator& locator);
};
diff --git a/src/index/coinstatsindex.cpp b/src/index/coinstatsindex.cpp
index 7d4860b20b..a1c8a5937c 100644
--- a/src/index/coinstatsindex.cpp
+++ b/src/index/coinstatsindex.cpp
@@ -363,6 +363,14 @@ bool CoinStatsIndex::Init()
return error("%s: Cannot read current %s state; index may be corrupted",
__func__, GetName());
}
+
+ uint256 out;
+ m_muhash.Finalize(out);
+ if (entry.muhash != out) {
+ return error("%s: Cannot read current %s state; index may be corrupted",
+ __func__, GetName());
+ }
+
m_transaction_output_count = entry.transaction_output_count;
m_bogo_size = entry.bogo_size;
m_total_amount = entry.total_amount;
diff --git a/src/primitives/transaction.h b/src/primitives/transaction.h
index 1fcbc45c72..fb98fb6868 100644
--- a/src/primitives/transaction.h
+++ b/src/primitives/transaction.h
@@ -201,7 +201,7 @@ struct CMutableTransaction;
* - std::vector<CTxIn> vin
* - std::vector<CTxOut> vout
* - if (flags & 1):
- * - CTxWitness wit;
+ * - CScriptWitness scriptWitness; (deserialized into CTxIn)
* - uint32_t nLockTime
*/
template<typename Stream, typename TxType>
diff --git a/src/rpc/blockchain.cpp b/src/rpc/blockchain.cpp
index 69204e346a..e5ad8f1a60 100644
--- a/src/rpc/blockchain.cpp
+++ b/src/rpc/blockchain.cpp
@@ -1417,7 +1417,7 @@ static RPCHelpMan verifychain()
},
[&](const RPCHelpMan& self, const JSONRPCRequest& request) -> UniValue
{
- const int check_level(request.params[0].isNull() ? DEFAULT_CHECKLEVEL : request.params[0].get_int());
+ const int check_level{request.params[0].isNull() ? DEFAULT_CHECKLEVEL : request.params[0].get_int()};
const int check_depth{request.params[1].isNull() ? DEFAULT_CHECKBLOCKS : request.params[1].get_int()};
ChainstateManager& chainman = EnsureAnyChainman(request.context);
diff --git a/src/streams.h b/src/streams.h
index cf8b4eb96f..96b7696f72 100644
--- a/src/streams.h
+++ b/src/streams.h
@@ -9,6 +9,7 @@
#include <serialize.h>
#include <span.h>
#include <support/allocators/zeroafterfree.h>
+#include <util/overflow.h>
#include <algorithm>
#include <assert.h>
@@ -186,7 +187,7 @@ class CDataStream
protected:
using vector_type = SerializeData;
vector_type vch;
- unsigned int nReadPos{0};
+ vector_type::size_type m_read_pos{0};
int nType;
int nVersion;
@@ -229,37 +230,37 @@ public:
//
// Vector subset
//
- const_iterator begin() const { return vch.begin() + nReadPos; }
- iterator begin() { return vch.begin() + nReadPos; }
+ const_iterator begin() const { return vch.begin() + m_read_pos; }
+ iterator begin() { return vch.begin() + m_read_pos; }
const_iterator end() const { return vch.end(); }
iterator end() { return vch.end(); }
- size_type size() const { return vch.size() - nReadPos; }
- bool empty() const { return vch.size() == nReadPos; }
- void resize(size_type n, value_type c = value_type{}) { vch.resize(n + nReadPos, c); }
- void reserve(size_type n) { vch.reserve(n + nReadPos); }
- const_reference operator[](size_type pos) const { return vch[pos + nReadPos]; }
- reference operator[](size_type pos) { return vch[pos + nReadPos]; }
- void clear() { vch.clear(); nReadPos = 0; }
- value_type* data() { return vch.data() + nReadPos; }
- const value_type* data() const { return vch.data() + nReadPos; }
+ size_type size() const { return vch.size() - m_read_pos; }
+ bool empty() const { return vch.size() == m_read_pos; }
+ void resize(size_type n, value_type c = value_type{}) { vch.resize(n + m_read_pos, c); }
+ void reserve(size_type n) { vch.reserve(n + m_read_pos); }
+ const_reference operator[](size_type pos) const { return vch[pos + m_read_pos]; }
+ reference operator[](size_type pos) { return vch[pos + m_read_pos]; }
+ void clear() { vch.clear(); m_read_pos = 0; }
+ value_type* data() { return vch.data() + m_read_pos; }
+ const value_type* data() const { return vch.data() + m_read_pos; }
inline void Compact()
{
- vch.erase(vch.begin(), vch.begin() + nReadPos);
- nReadPos = 0;
+ vch.erase(vch.begin(), vch.begin() + m_read_pos);
+ m_read_pos = 0;
}
bool Rewind(std::optional<size_type> n = std::nullopt)
{
// Total rewind if no size is passed
if (!n) {
- nReadPos = 0;
+ m_read_pos = 0;
return true;
}
// Rewind by n characters if the buffer hasn't been compacted yet
- if (*n > nReadPos)
+ if (*n > m_read_pos)
return false;
- nReadPos -= *n;
+ m_read_pos -= *n;
return true;
}
@@ -281,36 +282,32 @@ public:
if (dst.size() == 0) return;
// Read from the beginning of the buffer
- unsigned int nReadPosNext = nReadPos + dst.size();
- if (nReadPosNext > vch.size()) {
+ auto next_read_pos{CheckedAdd(m_read_pos, dst.size())};
+ if (!next_read_pos.has_value() || next_read_pos.value() > vch.size()) {
throw std::ios_base::failure("CDataStream::read(): end of data");
}
- memcpy(dst.data(), &vch[nReadPos], dst.size());
- if (nReadPosNext == vch.size())
- {
- nReadPos = 0;
+ memcpy(dst.data(), &vch[m_read_pos], dst.size());
+ if (next_read_pos.value() == vch.size()) {
+ m_read_pos = 0;
vch.clear();
return;
}
- nReadPos = nReadPosNext;
+ m_read_pos = next_read_pos.value();
}
- void ignore(int nSize)
+ void ignore(size_t num_ignore)
{
// Ignore from the beginning of the buffer
- if (nSize < 0) {
- throw std::ios_base::failure("CDataStream::ignore(): nSize negative");
+ auto next_read_pos{CheckedAdd(m_read_pos, num_ignore)};
+ if (!next_read_pos.has_value() || next_read_pos.value() > vch.size()) {
+ throw std::ios_base::failure("CDataStream::ignore(): end of data");
}
- unsigned int nReadPosNext = nReadPos + nSize;
- if (nReadPosNext >= vch.size())
- {
- if (nReadPosNext > vch.size())
- throw std::ios_base::failure("CDataStream::ignore(): end of data");
- nReadPos = 0;
+ if (next_read_pos.value() == vch.size()) {
+ m_read_pos = 0;
vch.clear();
return;
}
- nReadPos = nReadPosNext;
+ m_read_pos = next_read_pos.value();
}
void write(Span<const value_type> src)
@@ -594,7 +591,7 @@ private:
FILE *src; //!< source file
uint64_t nSrcPos; //!< how many bytes have been read from source
- uint64_t nReadPos; //!< how many bytes have been read from this
+ uint64_t m_read_pos; //!< how many bytes have been read from this
uint64_t nReadLimit; //!< up to which position we're allowed to read
uint64_t nRewind; //!< how many bytes we guarantee to rewind
std::vector<std::byte> vchBuf; //!< the buffer
@@ -604,7 +601,7 @@ protected:
bool Fill() {
unsigned int pos = nSrcPos % vchBuf.size();
unsigned int readNow = vchBuf.size() - pos;
- unsigned int nAvail = vchBuf.size() - (nSrcPos - nReadPos) - nRewind;
+ unsigned int nAvail = vchBuf.size() - (nSrcPos - m_read_pos) - nRewind;
if (nAvail < readNow)
readNow = nAvail;
if (readNow == 0)
@@ -619,7 +616,7 @@ protected:
public:
CBufferedFile(FILE* fileIn, uint64_t nBufSize, uint64_t nRewindIn, int nTypeIn, int nVersionIn)
- : nType(nTypeIn), nVersion(nVersionIn), nSrcPos(0), nReadPos(0), nReadLimit(std::numeric_limits<uint64_t>::max()), nRewind(nRewindIn), vchBuf(nBufSize, std::byte{0})
+ : nType(nTypeIn), nVersion(nVersionIn), nSrcPos(0), m_read_pos(0), nReadLimit(std::numeric_limits<uint64_t>::max()), nRewind(nRewindIn), vchBuf(nBufSize, std::byte{0})
{
if (nRewindIn >= nBufSize)
throw std::ios_base::failure("Rewind limit must be less than buffer size");
@@ -648,33 +645,33 @@ public:
//! check whether we're at the end of the source file
bool eof() const {
- return nReadPos == nSrcPos && feof(src);
+ return m_read_pos == nSrcPos && feof(src);
}
//! read a number of bytes
void read(Span<std::byte> dst)
{
- if (dst.size() + nReadPos > nReadLimit) {
+ if (dst.size() + m_read_pos > nReadLimit) {
throw std::ios_base::failure("Read attempted past buffer limit");
}
while (dst.size() > 0) {
- if (nReadPos == nSrcPos)
+ if (m_read_pos == nSrcPos)
Fill();
- unsigned int pos = nReadPos % vchBuf.size();
+ unsigned int pos = m_read_pos % vchBuf.size();
size_t nNow = dst.size();
if (nNow + pos > vchBuf.size())
nNow = vchBuf.size() - pos;
- if (nNow + nReadPos > nSrcPos)
- nNow = nSrcPos - nReadPos;
+ if (nNow + m_read_pos > nSrcPos)
+ nNow = nSrcPos - m_read_pos;
memcpy(dst.data(), &vchBuf[pos], nNow);
- nReadPos += nNow;
+ m_read_pos += nNow;
dst = dst.subspan(nNow);
}
}
//! return the current reading position
uint64_t GetPos() const {
- return nReadPos;
+ return m_read_pos;
}
//! rewind to a given reading position
@@ -682,22 +679,22 @@ public:
size_t bufsize = vchBuf.size();
if (nPos + bufsize < nSrcPos) {
// rewinding too far, rewind as far as possible
- nReadPos = nSrcPos - bufsize;
+ m_read_pos = nSrcPos - bufsize;
return false;
}
if (nPos > nSrcPos) {
// can't go this far forward, go as far as possible
- nReadPos = nSrcPos;
+ m_read_pos = nSrcPos;
return false;
}
- nReadPos = nPos;
+ m_read_pos = nPos;
return true;
}
//! prevent reading beyond a certain position
//! no argument removes the limit
bool SetLimit(uint64_t nPos = std::numeric_limits<uint64_t>::max()) {
- if (nPos < nReadPos)
+ if (nPos < m_read_pos)
return false;
nReadLimit = nPos;
return true;
@@ -714,12 +711,12 @@ public:
void FindByte(uint8_t ch)
{
while (true) {
- if (nReadPos == nSrcPos)
+ if (m_read_pos == nSrcPos)
Fill();
- if (vchBuf[nReadPos % vchBuf.size()] == std::byte{ch}) {
+ if (vchBuf[m_read_pos % vchBuf.size()] == std::byte{ch}) {
break;
}
- nReadPos++;
+ m_read_pos++;
}
}
};
diff --git a/src/test/dbwrapper_tests.cpp b/src/test/dbwrapper_tests.cpp
index 2f95cc27a3..fc89fe1450 100644
--- a/src/test/dbwrapper_tests.cpp
+++ b/src/test/dbwrapper_tests.cpp
@@ -203,7 +203,7 @@ BOOST_AUTO_TEST_CASE(existing_data_no_obfuscate)
{
// We're going to share this fs::path between two wrappers
fs::path ph = m_args.GetDataDirBase() / "existing_data_no_obfuscate";
- create_directories(ph);
+ fs::create_directories(ph);
// Set up a non-obfuscated wrapper to write some initial data.
std::unique_ptr<CDBWrapper> dbw = std::make_unique<CDBWrapper>(ph, (1 << 10), false, false, false);
@@ -244,7 +244,7 @@ BOOST_AUTO_TEST_CASE(existing_data_reindex)
{
// We're going to share this fs::path between two wrappers
fs::path ph = m_args.GetDataDirBase() / "existing_data_reindex";
- create_directories(ph);
+ fs::create_directories(ph);
// Set up a non-obfuscated wrapper to write some initial data.
std::unique_ptr<CDBWrapper> dbw = std::make_unique<CDBWrapper>(ph, (1 << 10), false, false, false);
diff --git a/src/test/fs_tests.cpp b/src/test/fs_tests.cpp
index 4fb2c23d98..313064b294 100644
--- a/src/test/fs_tests.cpp
+++ b/src/test/fs_tests.cpp
@@ -152,4 +152,28 @@ BOOST_AUTO_TEST_CASE(rename)
fs::remove(path2);
}
+#ifndef WIN32
+BOOST_AUTO_TEST_CASE(create_directories)
+{
+ // Test fs::create_directories workaround.
+ const fs::path tmpfolder{m_args.GetDataDirBase()};
+
+ const fs::path dir{GetUniquePath(tmpfolder)};
+ fs::create_directory(dir);
+ BOOST_CHECK(fs::exists(dir));
+ BOOST_CHECK(fs::is_directory(dir));
+ BOOST_CHECK(!fs::create_directories(dir));
+
+ const fs::path symlink{GetUniquePath(tmpfolder)};
+ fs::create_directory_symlink(dir, symlink);
+ BOOST_CHECK(fs::exists(symlink));
+ BOOST_CHECK(fs::is_symlink(symlink));
+ BOOST_CHECK(fs::is_directory(symlink));
+ BOOST_CHECK(!fs::create_directories(symlink));
+
+ fs::remove(symlink);
+ fs::remove(dir);
+}
+#endif // WIN32
+
BOOST_AUTO_TEST_SUITE_END()
diff --git a/src/test/fuzz/script.cpp b/src/test/fuzz/script.cpp
index 14a59912db..fdcd0da37d 100644
--- a/src/test/fuzz/script.cpp
+++ b/src/test/fuzz/script.cpp
@@ -167,12 +167,4 @@ FUZZ_TARGET_INIT(script, initialize_script)
Assert(dest == GetScriptForDestination(tx_destination_2));
}
}
-
- (void)FormatScript(script);
- (void)ScriptToAsmStr(script, /*fAttemptSighashDecode=*/fuzzed_data_provider.ConsumeBool());
-
- UniValue o1(UniValue::VOBJ);
- ScriptPubKeyToUniv(script, o1, /*include_hex=*/fuzzed_data_provider.ConsumeBool());
- UniValue o3(UniValue::VOBJ);
- ScriptToUniv(script, o3);
}
diff --git a/src/test/fuzz/script_format.cpp b/src/test/fuzz/script_format.cpp
new file mode 100644
index 0000000000..2fa893f812
--- /dev/null
+++ b/src/test/fuzz/script_format.cpp
@@ -0,0 +1,30 @@
+// Copyright (c) 2019-2022 The Bitcoin Core developers
+// Distributed under the MIT software license, see the accompanying
+// file COPYING or http://www.opensource.org/licenses/mit-license.php.
+
+#include <chainparams.h>
+#include <core_io.h>
+#include <script/script.h>
+#include <test/fuzz/FuzzedDataProvider.h>
+#include <test/fuzz/fuzz.h>
+#include <test/fuzz/util.h>
+#include <univalue.h>
+
+void initialize_script_format()
+{
+ SelectParams(CBaseChainParams::REGTEST);
+}
+
+FUZZ_TARGET_INIT(script_format, initialize_script_format)
+{
+ FuzzedDataProvider fuzzed_data_provider(buffer.data(), buffer.size());
+ const CScript script{ConsumeScript(fuzzed_data_provider)};
+
+ (void)FormatScript(script);
+ (void)ScriptToAsmStr(script, /*fAttemptSighashDecode=*/fuzzed_data_provider.ConsumeBool());
+
+ UniValue o1(UniValue::VOBJ);
+ ScriptPubKeyToUniv(script, o1, /*include_hex=*/fuzzed_data_provider.ConsumeBool());
+ UniValue o3(UniValue::VOBJ);
+ ScriptToUniv(script, o3);
+}
diff --git a/src/util/overflow.h b/src/util/overflow.h
index 5982af8d04..c70a8b663e 100644
--- a/src/util/overflow.h
+++ b/src/util/overflow.h
@@ -6,6 +6,7 @@
#define BITCOIN_UTIL_OVERFLOW_H
#include <limits>
+#include <optional>
#include <type_traits>
template <class T>
diff --git a/src/util/syscall_sandbox.cpp b/src/util/syscall_sandbox.cpp
index f513dba598..f2a9cf664d 100644
--- a/src/util/syscall_sandbox.cpp
+++ b/src/util/syscall_sandbox.cpp
@@ -68,6 +68,10 @@ bool g_syscall_sandbox_log_violation_before_terminating{false};
#define __NR_copy_file_range 326
#endif
+#ifndef __NR_rseq
+#define __NR_rseq 334
+#endif
+
// This list of syscalls in LINUX_SYSCALLS is only used to map syscall numbers to syscall names in
// order to be able to print user friendly error messages which include the syscall name in addition
// to the syscall number.
@@ -327,6 +331,7 @@ const std::map<uint32_t, std::string> LINUX_SYSCALLS{
{__NR_request_key, "request_key"},
{__NR_restart_syscall, "restart_syscall"},
{__NR_rmdir, "rmdir"},
+ {__NR_rseq, "rseq"},
{__NR_rt_sigaction, "rt_sigaction"},
{__NR_rt_sigpending, "rt_sigpending"},
{__NR_rt_sigprocmask, "rt_sigprocmask"},
@@ -723,6 +728,7 @@ public:
allowed_syscalls.insert(__NR_fork); // create a child process
allowed_syscalls.insert(__NR_tgkill); // send a signal to a thread
allowed_syscalls.insert(__NR_wait4); // wait for process to change state, BSD style
+ allowed_syscalls.insert(__NR_rseq); // register restartable sequence for thread
}
void AllowScheduling()
diff --git a/src/validation.cpp b/src/validation.cpp
index 5b52638fc5..2813b62462 100644
--- a/src/validation.cpp
+++ b/src/validation.cpp
@@ -2373,14 +2373,13 @@ bool CChainState::FlushStateToDisk(
return AbortNode(state, "Failed to write to coin database");
nLastFlush = nNow;
full_flush_completed = true;
+ TRACE5(utxocache, flush,
+ (int64_t)(GetTimeMicros() - nNow.count()), // in microseconds (µs)
+ (u_int32_t)mode,
+ (u_int64_t)coins_count,
+ (u_int64_t)coins_mem_usage,
+ (bool)fFlushForPrune);
}
- TRACE6(utxocache, flush,
- (int64_t)(GetTimeMicros() - nNow.count()), // in microseconds (µs)
- (u_int32_t)mode,
- (u_int64_t)coins_count,
- (u_int64_t)coins_mem_usage,
- (bool)fFlushForPrune,
- (bool)fDoFullFlush);
}
if (full_flush_completed) {
// Update best block in wallet (so we can detect restored wallets).
diff --git a/src/validation.h b/src/validation.h
index 968f62aa9a..7766d77a88 100644
--- a/src/validation.h
+++ b/src/validation.h
@@ -90,7 +90,7 @@ static const int DEFAULT_STOPATHEIGHT = 0;
/** Block files containing a block-height within MIN_BLOCKS_TO_KEEP of ActiveChain().Tip() will not be pruned. */
static const unsigned int MIN_BLOCKS_TO_KEEP = 288;
static const signed int DEFAULT_CHECKBLOCKS = 6;
-static const unsigned int DEFAULT_CHECKLEVEL = 3;
+static constexpr int DEFAULT_CHECKLEVEL{3};
// Require that user allocate at least 550 MiB for block & undo files (blk???.dat and rev???.dat)
// At 1MB per block, 288 blocks = 288MB.
// Add 15% for Undo data = 331MB