From 92a0f7e58d4b6323d21f1c45d4c20266c35df030 Mon Sep 17 00:00:00 2001 From: Vasil Dimov Date: Fri, 8 Oct 2021 18:11:40 +0200 Subject: test: parse the command line arguments in unit tests Retrieve the command line arguments from boost and pass them to `BasicTestingSetup` so that we gain extra flexibility of passing any config options on the test command line, e.g.: ``` test_bitcoin -- -printtoconsole=1 -checkaddrman=5 ``` --- src/bench/bench.cpp | 2 ++ src/qt/test/test_main.cpp | 3 +++ src/test/README.md | 28 ++++++++++++++++++++-------- src/test/fuzz/fuzz.cpp | 3 +++ src/test/main.cpp | 15 +++++++++++++++ src/test/util/setup_common.cpp | 13 +++++++++---- src/test/util/setup_common.h | 4 ++++ 7 files changed, 56 insertions(+), 12 deletions(-) (limited to 'src') diff --git a/src/bench/bench.cpp b/src/bench/bench.cpp index f696396e12..d7b4228566 100644 --- a/src/bench/bench.cpp +++ b/src/bench/bench.cpp @@ -19,6 +19,8 @@ using namespace std::chrono_literals; const std::function G_TEST_LOG_FUN{}; +const std::function()> G_TEST_COMMAND_LINE_ARGUMENTS{}; + namespace { void GenerateTemplateResults(const std::vector& benchmarkResults, const std::string& filename, const char* tpl) diff --git a/src/qt/test/test_main.cpp b/src/qt/test/test_main.cpp index 11aa61c7fc..10b7e2ffe7 100644 --- a/src/qt/test/test_main.cpp +++ b/src/qt/test/test_main.cpp @@ -22,6 +22,7 @@ #include #include #include +#include #if defined(QT_STATICPLUGIN) #include @@ -43,6 +44,8 @@ using node::NodeContext; const std::function G_TEST_LOG_FUN{}; +const std::function()> G_TEST_COMMAND_LINE_ARGUMENTS{}; + // This is all you need to run all the tests int main(int argc, char* argv[]) { diff --git a/src/test/README.md b/src/test/README.md index d03411c3ed..90d0e7102d 100644 --- a/src/test/README.md +++ b/src/test/README.md @@ -33,19 +33,31 @@ the `src/qt/test/test_main.cpp` file. ### Running individual tests -`test_bitcoin` has some built-in command-line arguments; for -example, to run just the `getarg_tests` verbosely: +`test_bitcoin` accepts the command line arguments from the boost framework. +For example, to run just the `getarg_tests` suite of tests: - test_bitcoin --log_level=all --run_test=getarg_tests -- DEBUG_LOG_OUT +```bash +test_bitcoin --log_level=all --run_test=getarg_tests +``` `log_level` controls the verbosity of the test framework, which logs when a -test case is entered, for example. The `DEBUG_LOG_OUT` after the two dashes -redirects the debug log, which would normally go to a file in the test datadir +test case is entered, for example. `test_bitcoin` also accepts the command +line arguments accepted by `bitcoind`. Use `--` to separate both types of +arguments: + +```bash +test_bitcoin --log_level=all --run_test=getarg_tests -- -printtoconsole=1 +``` + +The `-printtoconsole=1` after the two dashes redirects the debug log, which +would normally go to a file in the test datadir (`BasicTestingSetup::m_path_root`), to the standard terminal output. ... or to run just the doubledash test: - test_bitcoin --run_test=getarg_tests/doubledash +```bash +test_bitcoin --run_test=getarg_tests/doubledash +``` Run `test_bitcoin --help` for the full list. @@ -68,7 +80,7 @@ on failure. For running individual tests verbosely, refer to the section To write to logs from unit tests you need to use specific message methods provided by Boost. The simplest is `BOOST_TEST_MESSAGE`. -For debugging you can launch the `test_bitcoin` executable with `gdb`or `lldb` and +For debugging you can launch the `test_bitcoin` executable with `gdb` or `lldb` and start debugging, just like you would with any other program: ```bash @@ -95,7 +107,7 @@ Running the tests and hitting a segmentation fault should now produce a file cal `/proc/sys/kernel/core_pattern`). You can then explore the core dump using -``` bash +```bash gdb src/test/test_bitcoin core (gbd) bt # produce a backtrace for where a segfault occurred diff --git a/src/test/fuzz/fuzz.cpp b/src/test/fuzz/fuzz.cpp index a33297e0ed..1c994a53cf 100644 --- a/src/test/fuzz/fuzz.cpp +++ b/src/test/fuzz/fuzz.cpp @@ -12,6 +12,7 @@ #include #include +#include #include #include #include @@ -19,6 +20,8 @@ const std::function G_TEST_LOG_FUN{}; +const std::function()> G_TEST_COMMAND_LINE_ARGUMENTS{}; + std::map>& FuzzTargets() { static std::map> g_fuzz_targets; diff --git a/src/test/main.cpp b/src/test/main.cpp index 5885564074..1ad8fcce3a 100644 --- a/src/test/main.cpp +++ b/src/test/main.cpp @@ -11,6 +11,7 @@ #include +#include #include /** Redirect debug log to unit_test.log files */ @@ -24,3 +25,17 @@ const std::function G_TEST_LOG_FUN = [](const std::str if (!should_log) return; std::cout << s; }; + +/** + * Retrieve the command line arguments from boost. + * Allows usage like: + * `test_bitcoin --run_test="net_tests/cnode_listen_port" -- -checkaddrman=1 -printtoconsole=1` + * which would return `["-checkaddrman=1", "-printtoconsole=1"]`. + */ +const std::function()> G_TEST_COMMAND_LINE_ARGUMENTS = []() { + std::vector args; + for (int i = 1; i < boost::unit_test::framework::master_test_suite().argc; ++i) { + args.push_back(boost::unit_test::framework::master_test_suite().argv[i]); + } + return args; +}; diff --git a/src/test/util/setup_common.cpp b/src/test/util/setup_common.cpp index 87546f45f2..b41c2aa12f 100644 --- a/src/test/util/setup_common.cpp +++ b/src/test/util/setup_common.cpp @@ -42,6 +42,7 @@ #include #include +#include using node::BlockAssembler; using node::CalculateCacheSizes; @@ -88,7 +89,7 @@ BasicTestingSetup::BasicTestingSetup(const std::string& chainName, const std::ve m_args{} { m_node.args = &gArgs; - const std::vector arguments = Cat( + std::vector arguments = Cat( { "dummy", "-printtoconsole=0", @@ -100,6 +101,9 @@ BasicTestingSetup::BasicTestingSetup(const std::string& chainName, const std::ve "-debugexclude=leveldb", }, extra_args); + if (G_TEST_COMMAND_LINE_ARGUMENTS) { + arguments = Cat(arguments, G_TEST_COMMAND_LINE_ARGUMENTS()); + } util::ThreadRename("test"); fs::create_directories(m_path_root); m_args.ForceSetArg("-datadir", fs::PathToString(m_path_root)); @@ -108,9 +112,10 @@ BasicTestingSetup::BasicTestingSetup(const std::string& chainName, const std::ve { SetupServerArgs(*m_node.args); std::string error; - const bool success{m_node.args->ParseParameters(arguments.size(), arguments.data(), error)}; - assert(success); - assert(error.empty()); + if (!m_node.args->ParseParameters(arguments.size(), arguments.data(), error)) { + m_node.args->ClearArgs(); + throw std::runtime_error{error}; + } } SelectParams(chainName); SeedInsecureRand(); diff --git a/src/test/util/setup_common.h b/src/test/util/setup_common.h index 58ffd77995..a1b7525cf4 100644 --- a/src/test/util/setup_common.h +++ b/src/test/util/setup_common.h @@ -19,12 +19,16 @@ #include #include +#include #include #include /** This is connected to the logger. Can be used to redirect logs to any other log */ extern const std::function G_TEST_LOG_FUN; +/** Retrieve the command line arguments. */ +extern const std::function()> G_TEST_COMMAND_LINE_ARGUMENTS; + // Enable BOOST_CHECK_EQUAL for enum class types namespace std { template -- cgit v1.2.3 From 6f7c7567c578b5a41f8e90ce4491e40f7faeaa56 Mon Sep 17 00:00:00 2001 From: Vasil Dimov Date: Tue, 26 Oct 2021 17:26:16 +0200 Subject: fuzz: parse the command line arguments in fuzz tests Retrieve the command line arguments from the fuzzer and save them for later retrieval by `BasicTestingSetup` so that we gain extra flexibility of passing any config options on the test command line, e.g.: ``` FUZZ=addrman ./src/test/fuzz/fuzz --checkaddrman=5 ``` A fuzz test should call `MakeNoLogFileContext<>()` in its initialize function in order to invoke the constructor of `BasicTestingSetup`, which sets `gArgs`. --- src/test/fuzz/fuzz.cpp | 24 +++++++++++++++++++++++- 1 file changed, 23 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/test/fuzz/fuzz.cpp b/src/test/fuzz/fuzz.cpp index 1c994a53cf..e9debd8c45 100644 --- a/src/test/fuzz/fuzz.cpp +++ b/src/test/fuzz/fuzz.cpp @@ -20,7 +20,28 @@ const std::function G_TEST_LOG_FUN{}; -const std::function()> G_TEST_COMMAND_LINE_ARGUMENTS{}; +/** + * A copy of the command line arguments that start with `--`. + * First `LLVMFuzzerInitialize()` is called, which saves the arguments to `g_args`. + * Later, depending on the fuzz test, `G_TEST_COMMAND_LINE_ARGUMENTS()` may be + * called by `BasicTestingSetup` constructor to fetch those arguments and store + * them in `BasicTestingSetup::m_node::args`. + */ +static std::vector g_args; + +static void SetArgs(int argc, char** argv) { + for (int i = 1; i < argc; ++i) { + // Only take into account arguments that start with `--`. The others are for the fuzz engine: + // `fuzz -runs=1 fuzz_seed_corpus/address_deserialize_v2 --checkaddrman=5` + if (strlen(argv[i]) > 2 && argv[i][0] == '-' && argv[i][1] == '-') { + g_args.push_back(argv[i]); + } + } +} + +const std::function()> G_TEST_COMMAND_LINE_ARGUMENTS = []() { + return g_args; +}; std::map>& FuzzTargets() { @@ -98,6 +119,7 @@ extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) // This function is used by libFuzzer extern "C" int LLVMFuzzerInitialize(int* argc, char*** argv) { + SetArgs(*argc, *argv); initialize(); return 0; } -- cgit v1.2.3 From 6dff6214be768a3fab6d5201daf5ef6071764746 Mon Sep 17 00:00:00 2001 From: Vasil Dimov Date: Tue, 26 Oct 2021 17:48:05 +0200 Subject: bench: put addrman check ratio in a variable So that it is easy to modify through the file `bench/addrman.cpp`. --- src/bench/addrman.cpp | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/bench/addrman.cpp b/src/bench/addrman.cpp index 2d94e835f0..3ca58b923e 100644 --- a/src/bench/addrman.cpp +++ b/src/bench/addrman.cpp @@ -16,6 +16,9 @@ static constexpr size_t NUM_SOURCES = 64; static constexpr size_t NUM_ADDRESSES_PER_SOURCE = 256; +static const std::vector EMPTY_ASMAP; +static constexpr uint32_t ADDRMAN_CONSISTENCY_CHECK_RATIO{0}; + static std::vector g_sources; static std::vector> g_addresses; @@ -74,14 +77,14 @@ static void AddrManAdd(benchmark::Bench& bench) CreateAddresses(); bench.run([&] { - AddrMan addrman{/* asmap */ std::vector(), /* deterministic */ false, /* consistency_check_ratio */ 0}; + AddrMan addrman{EMPTY_ASMAP, /*deterministic=*/false, ADDRMAN_CONSISTENCY_CHECK_RATIO}; AddAddressesToAddrMan(addrman); }); } static void AddrManSelect(benchmark::Bench& bench) { - AddrMan addrman(/* asmap */ std::vector(), /* deterministic */ false, /* consistency_check_ratio */ 0); + AddrMan addrman{EMPTY_ASMAP, /*deterministic=*/false, ADDRMAN_CONSISTENCY_CHECK_RATIO}; FillAddrMan(addrman); @@ -93,7 +96,7 @@ static void AddrManSelect(benchmark::Bench& bench) static void AddrManGetAddr(benchmark::Bench& bench) { - AddrMan addrman(/* asmap */ std::vector(), /* deterministic */ false, /* consistency_check_ratio */ 0); + AddrMan addrman{EMPTY_ASMAP, /*deterministic=*/false, ADDRMAN_CONSISTENCY_CHECK_RATIO}; FillAddrMan(addrman); @@ -122,7 +125,7 @@ static void AddrManAddThenGood(benchmark::Bench& bench) // // This has some overhead (exactly the result of AddrManAdd benchmark), but that overhead is constant so improvements in // AddrMan::Good() will still be noticeable. - AddrMan addrman(/* asmap */ std::vector(), /* deterministic */ false, /* consistency_check_ratio */ 0); + AddrMan addrman{EMPTY_ASMAP, /*deterministic=*/false, ADDRMAN_CONSISTENCY_CHECK_RATIO}; AddAddressesToAddrMan(addrman); markSomeAsGood(addrman); -- cgit v1.2.3 From 81e4d54d3a95f7bffeb353217a6c32eb2aca8b5c Mon Sep 17 00:00:00 2001 From: Vasil Dimov Date: Tue, 26 Oct 2021 17:51:43 +0200 Subject: test: addrman unit tests: override-able check ratio In addrman unit tests, make it possible to override the check ratio from the command line, without recompiling: ``` test_bitcoin --run_test="addrman_tests/*" -- -checkaddrman=1 ``` Also, make the arguments of the constructor of `AddrManTest` the same as the arguments of `AddrMan`. --- src/test/addrman_tests.cpp | 70 ++++++++++++++++++++++++---------------------- 1 file changed, 37 insertions(+), 33 deletions(-) (limited to 'src') diff --git a/src/test/addrman_tests.cpp b/src/test/addrman_tests.cpp index 752bd0af9e..efc30b6822 100644 --- a/src/test/addrman_tests.cpp +++ b/src/test/addrman_tests.cpp @@ -21,6 +21,15 @@ #include using namespace std::literals; +using node::NodeContext; + +static const std::vector EMPTY_ASMAP; +static const bool DETERMINISTIC{true}; + +static int32_t GetCheckRatio(const NodeContext& node_ctx) +{ + return std::clamp(node_ctx.args->GetIntArg("-checkaddrman", 100), 0, 1000000); +} static CNetAddr ResolveIP(const std::string& ip) { @@ -49,17 +58,11 @@ static std::vector FromBytes(const unsigned char* source, int vector_size) return result; } -/* Utility function to create a deterministic addrman, as used in most tests */ -static std::unique_ptr TestAddrMan(std::vector asmap = std::vector()) -{ - return std::make_unique(asmap, /*deterministic=*/true, /*consistency_check_ratio=*/100); -} - BOOST_FIXTURE_TEST_SUITE(addrman_tests, BasicTestingSetup) BOOST_AUTO_TEST_CASE(addrman_simple) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); CNetAddr source = ResolveIP("252.2.2.2"); @@ -93,7 +96,7 @@ BOOST_AUTO_TEST_CASE(addrman_simple) BOOST_CHECK(addrman->size() >= 1); // Test: reset addrman and test AddrMan::Add multiple addresses works as expected - addrman = TestAddrMan(); + addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); std::vector vAddr; vAddr.push_back(CAddress(ResolveService("250.1.1.3", 8333), NODE_NONE)); vAddr.push_back(CAddress(ResolveService("250.1.1.4", 8333), NODE_NONE)); @@ -103,7 +106,7 @@ BOOST_AUTO_TEST_CASE(addrman_simple) BOOST_AUTO_TEST_CASE(addrman_ports) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); CNetAddr source = ResolveIP("252.2.2.2"); @@ -132,7 +135,7 @@ BOOST_AUTO_TEST_CASE(addrman_ports) BOOST_AUTO_TEST_CASE(addrman_select) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); CNetAddr source = ResolveIP("252.2.2.2"); @@ -191,7 +194,7 @@ BOOST_AUTO_TEST_CASE(addrman_select) BOOST_AUTO_TEST_CASE(addrman_new_collisions) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); CNetAddr source = ResolveIP("252.2.2.2"); @@ -220,7 +223,7 @@ BOOST_AUTO_TEST_CASE(addrman_new_collisions) BOOST_AUTO_TEST_CASE(addrman_new_multiplicity) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); CAddress addr{CAddress(ResolveService("253.3.3.3", 8333), NODE_NONE)}; int64_t start_time{GetAdjustedTime()}; addr.nTime = start_time; @@ -252,7 +255,7 @@ BOOST_AUTO_TEST_CASE(addrman_new_multiplicity) BOOST_AUTO_TEST_CASE(addrman_tried_collisions) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); CNetAddr source = ResolveIP("252.2.2.2"); @@ -283,7 +286,7 @@ BOOST_AUTO_TEST_CASE(addrman_tried_collisions) BOOST_AUTO_TEST_CASE(addrman_getaddr) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); // Test: Sanity check, GetAddr should never return anything if addrman // is empty. @@ -604,9 +607,11 @@ BOOST_AUTO_TEST_CASE(addrman_serialization) { std::vector asmap1 = FromBytes(asmap_raw, sizeof(asmap_raw) * 8); - auto addrman_asmap1 = TestAddrMan(asmap1); - auto addrman_asmap1_dup = TestAddrMan(asmap1); - auto addrman_noasmap = TestAddrMan(); + const auto ratio = GetCheckRatio(m_node); + auto addrman_asmap1 = std::make_unique(asmap1, DETERMINISTIC, ratio); + auto addrman_asmap1_dup = std::make_unique(asmap1, DETERMINISTIC, ratio); + auto addrman_noasmap = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, ratio); + CDataStream stream(SER_NETWORK, PROTOCOL_VERSION); CAddress addr = CAddress(ResolveService("250.1.1.1"), NODE_NONE); @@ -634,8 +639,8 @@ BOOST_AUTO_TEST_CASE(addrman_serialization) BOOST_CHECK(addr_pos1.position != addr_pos3.position); // deserializing non-asmaped peers.dat to asmaped addrman - addrman_asmap1 = TestAddrMan(asmap1); - addrman_noasmap = TestAddrMan(); + addrman_asmap1 = std::make_unique(asmap1, DETERMINISTIC, ratio); + addrman_noasmap = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, ratio); addrman_noasmap->Add({addr}, default_source); stream << *addrman_noasmap; stream >> *addrman_asmap1; @@ -646,8 +651,8 @@ BOOST_AUTO_TEST_CASE(addrman_serialization) BOOST_CHECK(addr_pos4 == addr_pos2); // used to map to different buckets, now maps to the same bucket. - addrman_asmap1 = TestAddrMan(asmap1); - addrman_noasmap = TestAddrMan(); + addrman_asmap1 = std::make_unique(asmap1, DETERMINISTIC, ratio); + addrman_noasmap = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, ratio); CAddress addr1 = CAddress(ResolveService("250.1.1.1"), NODE_NONE); CAddress addr2 = CAddress(ResolveService("250.2.1.1"), NODE_NONE); addrman_noasmap->Add({addr, addr2}, default_source); @@ -666,7 +671,7 @@ BOOST_AUTO_TEST_CASE(remove_invalid) { // Confirm that invalid addresses are ignored in unserialization. - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); CDataStream stream(SER_NETWORK, PROTOCOL_VERSION); const CAddress new1{ResolveService("5.5.5.5"), NODE_NONE}; @@ -698,14 +703,14 @@ BOOST_AUTO_TEST_CASE(remove_invalid) BOOST_REQUIRE(pos + sizeof(tried2_raw_replacement) <= stream.size()); memcpy(stream.data() + pos, tried2_raw_replacement, sizeof(tried2_raw_replacement)); - addrman = TestAddrMan(); + addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); stream >> *addrman; BOOST_CHECK_EQUAL(addrman->size(), 2); } BOOST_AUTO_TEST_CASE(addrman_selecttriedcollision) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); BOOST_CHECK(addrman->size() == 0); @@ -738,7 +743,7 @@ BOOST_AUTO_TEST_CASE(addrman_selecttriedcollision) BOOST_AUTO_TEST_CASE(addrman_noevict) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); // Add 35 addresses. CNetAddr source = ResolveIP("252.2.2.2"); @@ -790,7 +795,7 @@ BOOST_AUTO_TEST_CASE(addrman_noevict) BOOST_AUTO_TEST_CASE(addrman_evictionworks) { - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); BOOST_CHECK(addrman->size() == 0); @@ -860,8 +865,7 @@ static CDataStream AddrmanToStream(const AddrMan& addrman) BOOST_AUTO_TEST_CASE(load_addrman) { - AddrMan addrman{/*asmap=*/ std::vector(), /*deterministic=*/ true, - /*consistency_check_ratio=*/ 100}; + AddrMan addrman{EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)}; CService addr1, addr2, addr3; BOOST_CHECK(Lookup("250.7.1.1", addr1, 8333, false)); @@ -880,7 +884,7 @@ BOOST_AUTO_TEST_CASE(load_addrman) // Test that the de-serialization does not throw an exception. CDataStream ssPeers1 = AddrmanToStream(addrman); bool exceptionThrown = false; - AddrMan addrman1(/*asmap=*/std::vector(), /*deterministic=*/false, /*consistency_check_ratio=*/100); + AddrMan addrman1{EMPTY_ASMAP, !DETERMINISTIC, GetCheckRatio(m_node)}; BOOST_CHECK(addrman1.size() == 0); try { @@ -897,7 +901,7 @@ BOOST_AUTO_TEST_CASE(load_addrman) // Test that ReadFromStream creates an addrman with the correct number of addrs. CDataStream ssPeers2 = AddrmanToStream(addrman); - AddrMan addrman2(/*asmap=*/std::vector(), /*deterministic=*/false, /*consistency_check_ratio=*/100); + AddrMan addrman2{EMPTY_ASMAP, !DETERMINISTIC, GetCheckRatio(m_node)}; BOOST_CHECK(addrman2.size() == 0); ReadFromStream(addrman2, ssPeers2); BOOST_CHECK(addrman2.size() == 3); @@ -935,7 +939,7 @@ BOOST_AUTO_TEST_CASE(load_addrman_corrupted) // Test that the de-serialization of corrupted peers.dat throws an exception. CDataStream ssPeers1 = MakeCorruptPeersDat(); bool exceptionThrown = false; - AddrMan addrman1(/*asmap=*/std::vector(), /*deterministic=*/false, /*consistency_check_ratio=*/100); + AddrMan addrman1{EMPTY_ASMAP, !DETERMINISTIC, GetCheckRatio(m_node)}; BOOST_CHECK(addrman1.size() == 0); try { unsigned char pchMsgTmp[4]; @@ -951,7 +955,7 @@ BOOST_AUTO_TEST_CASE(load_addrman_corrupted) // Test that ReadFromStream fails if peers.dat is corrupt CDataStream ssPeers2 = MakeCorruptPeersDat(); - AddrMan addrman2(/*asmap=*/std::vector(), /*deterministic=*/false, /*consistency_check_ratio=*/100); + AddrMan addrman2{EMPTY_ASMAP, !DETERMINISTIC, GetCheckRatio(m_node)}; BOOST_CHECK(addrman2.size() == 0); BOOST_CHECK_THROW(ReadFromStream(addrman2, ssPeers2), std::ios_base::failure); } @@ -959,7 +963,7 @@ BOOST_AUTO_TEST_CASE(load_addrman_corrupted) BOOST_AUTO_TEST_CASE(addrman_update_address) { // Tests updating nTime via Connected() and nServices via SetServices() - auto addrman = TestAddrMan(); + auto addrman = std::make_unique(EMPTY_ASMAP, DETERMINISTIC, GetCheckRatio(m_node)); CNetAddr source{ResolveIP("252.2.2.2")}; CAddress addr{CAddress(ResolveService("250.1.1.1", 8333), NODE_NONE)}; -- cgit v1.2.3 From 46b0fe78298c8f416a91dec9d4e0f3f4cb1e68b0 Mon Sep 17 00:00:00 2001 From: Vasil Dimov Date: Tue, 26 Oct 2021 17:56:19 +0200 Subject: test: non-addrman unit tests: override-able check ratio Make it possible to override from the command line (without recompiling) the addrman check ratio in the common `TestingSetup::m_node::addrman` (used by all unit tests) instead of hardcoding it to 0: ``` test_bitcoin --run_test="transaction_tests/tx_valid" -- -checkaddrman=1 ``` --- src/test/util/setup_common.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/test/util/setup_common.cpp b/src/test/util/setup_common.cpp index b41c2aa12f..c968e4d124 100644 --- a/src/test/util/setup_common.cpp +++ b/src/test/util/setup_common.cpp @@ -223,7 +223,9 @@ TestingSetup::TestingSetup(const std::string& chainName, const std::vector(/*asmap=*/std::vector(), /*deterministic=*/false, /*consistency_check_ratio=*/0); + m_node.addrman = std::make_unique(/*asmap=*/std::vector(), + /*deterministic=*/false, + m_node.args->GetIntArg("-checkaddrman", 0)); m_node.banman = std::make_unique(m_args.GetDataDirBase() / "banlist", nullptr, DEFAULT_MISBEHAVING_BANTIME); m_node.connman = std::make_unique(0x1337, 0x1337, *m_node.addrman); // Deterministic randomness for tests. m_node.peerman = PeerManager::make(chainparams, *m_node.connman, *m_node.addrman, -- cgit v1.2.3 From 3bd83e273d104e9474af8f1bdf4f969163e33ade Mon Sep 17 00:00:00 2001 From: Vasil Dimov Date: Tue, 26 Oct 2021 18:07:21 +0200 Subject: fuzz: addrman fuzz tests: override-able check ratio Make it possible to override from the command line (without recompiling) the addrman check ratio in addrman fuzz tests instead of hardcoding it to 0: ``` FUZZ=addrman ./src/test/fuzz/fuzz --checkaddrman=5 ``` --- src/test/fuzz/addrman.cpp | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/test/fuzz/addrman.cpp b/src/test/fuzz/addrman.cpp index 9c85c20e2b..3699abb597 100644 --- a/src/test/fuzz/addrman.cpp +++ b/src/test/fuzz/addrman.cpp @@ -11,8 +11,10 @@ #include #include #include +#include #include #include +#include #include #include @@ -20,16 +22,26 @@ #include #include +namespace { +const BasicTestingSetup* g_setup; + +int32_t GetCheckRatio() +{ + return std::clamp(g_setup->m_node.args->GetIntArg("-checkaddrman", 0), 0, 1000000); +} +} // namespace + void initialize_addrman() { - SelectParams(CBaseChainParams::REGTEST); + static const auto testing_setup = MakeNoLogFileContext<>(CBaseChainParams::REGTEST); + g_setup = testing_setup.get(); } FUZZ_TARGET_INIT(data_stream_addr_man, initialize_addrman) { FuzzedDataProvider fuzzed_data_provider{buffer.data(), buffer.size()}; CDataStream data_stream = ConsumeDataStream(fuzzed_data_provider); - AddrMan addr_man(/*asmap=*/std::vector(), /*deterministic=*/false, /*consistency_check_ratio=*/0); + AddrMan addr_man{/*asmap=*/std::vector(), /*deterministic=*/false, GetCheckRatio()}; try { ReadFromStream(addr_man, data_stream); } catch (const std::exception&) { @@ -113,7 +125,7 @@ class AddrManDeterministic : public AddrMan { public: explicit AddrManDeterministic(std::vector asmap, FuzzedDataProvider& fuzzed_data_provider) - : AddrMan(std::move(asmap), /*deterministic=*/true, /*consistency_check_ratio=*/0) + : AddrMan{std::move(asmap), /*deterministic=*/true, GetCheckRatio()} { WITH_LOCK(m_impl->cs, m_impl->insecure_rand = FastRandomContext{ConsumeUInt256(fuzzed_data_provider)}); } -- cgit v1.2.3 From 7f122a4188af7130be9251611e41136a17c814f1 Mon Sep 17 00:00:00 2001 From: Vasil Dimov Date: Tue, 26 Oct 2021 18:10:54 +0200 Subject: fuzz: non-addrman fuzz tests: override-able check ratio Make it possible to override from the command line (without recompiling) the addrman check ratio in non-addrman fuzz tests (connman and deserialize) instead of hardcoding it to 0: ``` FUZZ=connman ./src/test/fuzz/fuzz --checkaddrman=5 ``` --- src/test/fuzz/connman.cpp | 10 +++++++++- src/test/fuzz/deserialize.cpp | 13 ++++++++++++- 2 files changed, 21 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/test/fuzz/connman.cpp b/src/test/fuzz/connman.cpp index f87b6f1503..240274664a 100644 --- a/src/test/fuzz/connman.cpp +++ b/src/test/fuzz/connman.cpp @@ -12,21 +12,29 @@ #include #include #include +#include #include #include #include +namespace { +const BasicTestingSetup* g_setup; +} // namespace + void initialize_connman() { static const auto testing_setup = MakeNoLogFileContext<>(); + g_setup = testing_setup.get(); } FUZZ_TARGET_INIT(connman, initialize_connman) { FuzzedDataProvider fuzzed_data_provider{buffer.data(), buffer.size()}; SetMockTime(ConsumeTime(fuzzed_data_provider)); - AddrMan addrman(/*asmap=*/std::vector(), /*deterministic=*/false, /*consistency_check_ratio=*/0); + AddrMan addrman(/*asmap=*/std::vector(), + /*deterministic=*/false, + g_setup->m_node.args->GetIntArg("-checkaddrman", 0)); CConnman connman{fuzzed_data_provider.ConsumeIntegral(), fuzzed_data_provider.ConsumeIntegral(), addrman, fuzzed_data_provider.ConsumeBool()}; CNetAddr random_netaddr; CNode random_node = ConsumeNode(fuzzed_data_provider); diff --git a/src/test/fuzz/deserialize.cpp b/src/test/fuzz/deserialize.cpp index 8b4faf2f5f..ed6f172a2a 100644 --- a/src/test/fuzz/deserialize.cpp +++ b/src/test/fuzz/deserialize.cpp @@ -22,7 +22,9 @@ #include #include