38#include <boost/test/unit_test.hpp>
40using namespace std::literals;
78 const std::unique_ptr<int> p_two =
Assert(std::make_unique<int>(2));
80 const int two = *
Assert(p_two);
84 const bool result{
Assume(two == 2)};
96 BOOST_ERROR(
"break was swallowed!");
106 BOOST_ERROR(
"break was swallowed!");
111 0x04, 0x67, 0x8a, 0xfd, 0xb0, 0xfe, 0x55, 0x48, 0x27, 0x19, 0x67, 0xf1, 0xa6, 0x71, 0x30, 0xb7,
112 0x10, 0x5c, 0xd6, 0xa8, 0x28, 0xe0, 0x39, 0x09, 0xa6, 0x79, 0x62, 0xe0, 0xea, 0x1f, 0x61, 0xde,
113 0xb6, 0x49, 0xf6, 0xbc, 0x3f, 0x4c, 0xef, 0x38, 0xc4, 0xf3, 0x55, 0x04, 0xe5, 0x1e, 0xc1, 0x12,
114 0xde, 0x5c, 0x38, 0x4d, 0xf7, 0xba, 0x0b, 0x8d, 0x57, 0x8a, 0x4c, 0x70, 0x2b, 0x6b, 0xf1, 0x1d,
119 std::vector<unsigned char> result;
122 result =
ParseHex(
"04678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5f");
123 BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
127 BOOST_CHECK(result.size() == 4 && result[0] == 0x12 && result[1] == 0x34 && result[2] == 0x56 && result[3] == 0x78);
131 BOOST_CHECK(result.size() == 4 && result[0] == 0x89 && result[1] == 0x34 && result[2] == 0x56 && result[3] == 0x78);
134 result =
ParseHex(
"1234 invalid 1234");
135 BOOST_CHECK(result.size() == 2 && result[0] == 0x12 && result[1] == 0x34);
142 "04678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5f");
170 const auto op_upper = [](
const std::string& s) {
return ToUpper(s); };
173 BOOST_CHECK_EQUAL(Join<std::string>({
"foo",
"bar"},
", ", op_upper),
"FOO, BAR");
188 BOOST_CHECK_EQUAL(
TrimString(std::string(
"\x05\x04\x03\x02\x01\x00", 6), std::string(
"\x05\x04\x03\x02\x01", 5)), std::string(
"\0", 1));
215 std::istringstream streamConfig(str_config);
218 m_settings.ro_config.clear();
219 m_config_sections.clear();
227 m_network_only_args.insert(arg);
229 void SetupArgs(
const std::vector<std::pair<std::string, unsigned int>>& args)
231 for (
const auto& arg : args) {
239 using ArgsManager::m_network;
240 using ArgsManager::m_settings;
273 const char* argv[] = {
"ignored", arg};
279 if (
expect.setting.isNull() ||
expect.setting.isFalse()) {
288 BOOST_CHECK_NE(
error.find(
expect.error), std::string::npos);
294 if (
expect.default_string) {
296 }
else if (
expect.string_value) {
304 }
else if (
expect.int_value) {
310 if (
expect.default_bool) {
313 }
else if (
expect.bool_value) {
321 auto l = test.
GetArgs(
"-value");
322 BOOST_CHECK_EQUAL_COLLECTIONS(l.begin(), l.end(),
expect.list_value->begin(),
expect.list_value->end());
333 CheckValue(M::ALLOW_ANY,
nullptr, Expect{{}}.DefaultString().DefaultInt().DefaultBool().List({}));
334 CheckValue(M::ALLOW_ANY,
"-novalue", Expect{
false}.String(
"0").Int(0).Bool(
false).List({}));
335 CheckValue(M::ALLOW_ANY,
"-novalue=", Expect{
false}.String(
"0").Int(0).Bool(
false).List({}));
336 CheckValue(M::ALLOW_ANY,
"-novalue=0", Expect{
true}.String(
"1").Int(1).Bool(
true).List({
"1"}));
337 CheckValue(M::ALLOW_ANY,
"-novalue=1", Expect{
false}.String(
"0").Int(0).Bool(
false).List({}));
338 CheckValue(M::ALLOW_ANY,
"-novalue=2", Expect{
false}.String(
"0").Int(0).Bool(
false).List({}));
339 CheckValue(M::ALLOW_ANY,
"-novalue=abc", Expect{
true}.String(
"1").Int(1).Bool(
true).List({
"1"}));
340 CheckValue(M::ALLOW_ANY,
"-value", Expect{
""}.String(
"").Int(0).Bool(
true).List({
""}));
341 CheckValue(M::ALLOW_ANY,
"-value=", Expect{
""}.String(
"").Int(0).Bool(
true).List({
""}));
342 CheckValue(M::ALLOW_ANY,
"-value=0", Expect{
"0"}.String(
"0").Int(0).Bool(
false).List({
"0"}));
343 CheckValue(M::ALLOW_ANY,
"-value=1", Expect{
"1"}.String(
"1").Int(1).Bool(
true).List({
"1"}));
344 CheckValue(M::ALLOW_ANY,
"-value=2", Expect{
"2"}.String(
"2").Int(2).Bool(
true).List({
"2"}));
345 CheckValue(M::ALLOW_ANY,
"-value=abc", Expect{
"abc"}.String(
"abc").Int(0).Bool(
false).List({
"abc"}));
353 std::array argv{
"ignored", arg};
363 BOOST_CHECK_EQUAL(
Parse(
"-includeconf"),
"-includeconf cannot be used from commandline; -includeconf=\"\"");
364 BOOST_CHECK_EQUAL(
Parse(
"-includeconf=file"),
"-includeconf cannot be used from commandline; -includeconf=\"file\"");
375 const char *argv_test[] = {
"-ignored",
"-a",
"-b",
"-ccc=argument",
"-ccc=multiple",
"f",
"-d=e"};
381 BOOST_CHECK(testArgs.m_settings.command_line_options.empty() && testArgs.m_settings.ro_config.empty());
384 BOOST_CHECK(testArgs.m_settings.command_line_options.empty() && testArgs.m_settings.ro_config.empty());
390 BOOST_CHECK(testArgs.m_settings.command_line_options.size() == 3 && testArgs.m_settings.ro_config.empty());
393 BOOST_CHECK(testArgs.m_settings.command_line_options.count(
"a") && testArgs.m_settings.command_line_options.count(
"b") && testArgs.m_settings.command_line_options.count(
"ccc")
394 && !testArgs.m_settings.command_line_options.count(
"f") && !testArgs.m_settings.command_line_options.count(
"d"));
396 BOOST_CHECK(testArgs.m_settings.command_line_options[
"a"].size() == 1);
397 BOOST_CHECK(testArgs.m_settings.command_line_options[
"a"].front().get_str() ==
"");
398 BOOST_CHECK(testArgs.m_settings.command_line_options[
"ccc"].size() == 2);
399 BOOST_CHECK(testArgs.m_settings.command_line_options[
"ccc"].front().get_str() ==
"argument");
400 BOOST_CHECK(testArgs.m_settings.command_line_options[
"ccc"].back().get_str() ==
"multiple");
409 const char* argv[] = {
"ignored",
"-registered"};
414 argv[1] =
"-unregistered";
420 argv[1] =
"-test.registered";
425static void TestParse(
const std::string& str,
bool expected_bool, int64_t expected_int)
429 std::string arg =
"-value=" + str;
430 const char* argv[] = {
"ignored", arg.c_str()};
489 const char *argv_test[] = {
490 "ignored",
"-a",
"-nob",
"-c=0",
"-d=1",
"-e=false",
"-f=true"};
497 for (
const char opt :
"abcdef")
501 BOOST_CHECK(testArgs.m_settings.command_line_options.size() == 6 &&
502 testArgs.m_settings.ro_config.empty());
528 const char *argv_test[] = {
"ignored",
"-nofoo",
"-foo",
"-nobar=0"};
542 const char *conf_test =
"nofoo=1\nfoo=1\nnobar=0\n";
556 const char *combo_test_args[] = {
"ignored",
"-nofoo",
"-bar"};
557 const char *combo_test_conf =
"foo=1\nnobar=1\n";
570 && testArgs.
GetArgs(
"-bar").front() ==
"");
575 const char *str_config =
609 test_args.
SetupArgs({a, b, ccc, d, e, fff, ggg, h, i, iii});
615 BOOST_CHECK(test_args.m_settings.command_line_options.empty());
616 BOOST_CHECK(test_args.m_settings.ro_config.size() == 3);
617 BOOST_CHECK(test_args.m_settings.ro_config[
""].size() == 8);
618 BOOST_CHECK(test_args.m_settings.ro_config[
"sec1"].size() == 3);
619 BOOST_CHECK(test_args.m_settings.ro_config[
"sec2"].size() == 2);
621 BOOST_CHECK(test_args.m_settings.ro_config[
""].count(
"a"));
622 BOOST_CHECK(test_args.m_settings.ro_config[
""].count(
"b"));
623 BOOST_CHECK(test_args.m_settings.ro_config[
""].count(
"ccc"));
624 BOOST_CHECK(test_args.m_settings.ro_config[
""].count(
"d"));
625 BOOST_CHECK(test_args.m_settings.ro_config[
""].count(
"fff"));
626 BOOST_CHECK(test_args.m_settings.ro_config[
""].count(
"ggg"));
627 BOOST_CHECK(test_args.m_settings.ro_config[
""].count(
"h"));
628 BOOST_CHECK(test_args.m_settings.ro_config[
""].count(
"i"));
629 BOOST_CHECK(test_args.m_settings.ro_config[
"sec1"].count(
"ccc"));
630 BOOST_CHECK(test_args.m_settings.ro_config[
"sec1"].count(
"h"));
631 BOOST_CHECK(test_args.m_settings.ro_config[
"sec2"].count(
"ccc"));
632 BOOST_CHECK(test_args.m_settings.ro_config[
"sec2"].count(
"iii"));
656 for (
const bool def : {
false,
true}) {
670 && test_args.
GetArgs(
"-a").front() ==
"");
672 && test_args.
GetArgs(
"-b").front() ==
"1");
674 && test_args.
GetArgs(
"-ccc").front() ==
"argument"
675 && test_args.
GetArgs(
"-ccc").back() ==
"multiple");
679 && test_args.
GetArgs(
"-ggg").front() ==
"1");
684 && test_args.
GetArgs(
"-i").front() ==
"1");
715 const std::vector<std::string> sec1_ccc_expected = {
"extend1",
"extend2",
"argument",
"multiple"};
716 const auto& sec1_ccc_res = test_args.
GetArgs(
"-ccc");
717 BOOST_CHECK_EQUAL_COLLECTIONS(sec1_ccc_res.begin(), sec1_ccc_res.end(), sec1_ccc_expected.begin(), sec1_ccc_expected.end());
734 const std::vector<std::string> sec2_ccc_expected = {
"extend3",
"argument",
"multiple"};
735 const auto& sec2_ccc_res = test_args.
GetArgs(
"-ccc");
736 BOOST_CHECK_EQUAL_COLLECTIONS(sec2_ccc_res.begin(), sec2_ccc_res.end(), sec2_ccc_expected.begin(), sec2_ccc_expected.end());
766 testArgs.m_settings.command_line_options.clear();
767 testArgs.m_settings.command_line_options[
"strtest1"] = {
"string..."};
769 testArgs.m_settings.command_line_options[
"inttest1"] = {
"12345"};
770 testArgs.m_settings.command_line_options[
"inttest2"] = {
"81985529216486895"};
772 testArgs.m_settings.command_line_options[
"booltest1"] = {
""};
774 testArgs.m_settings.command_line_options[
"booltest3"] = {
"0"};
775 testArgs.m_settings.command_line_options[
"booltest4"] = {
"1"};
778 testArgs.m_settings.command_line_options[
"pritest1"] = {
"a",
"b"};
779 testArgs.m_settings.ro_config[
""][
"pritest2"] = {
"a",
"b"};
780 testArgs.m_settings.command_line_options[
"pritest3"] = {
"a"};
781 testArgs.m_settings.ro_config[
""][
"pritest3"] = {
"b"};
782 testArgs.m_settings.command_line_options[
"pritest4"] = {
"a",
"b"};
783 testArgs.m_settings.ro_config[
""][
"pritest4"] = {
"c",
"d"};
808 const char* argv_testnet[] = {
"cmd",
"-testnet"};
809 const char* argv_regtest[] = {
"cmd",
"-regtest"};
810 const char* argv_test_no_reg[] = {
"cmd",
"-testnet",
"-noregtest"};
811 const char* argv_both[] = {
"cmd",
"-testnet",
"-regtest"};
815 const char* testnetconf =
"testnet=1\nregtest=0\n[test]\nregtest=1";
909 template <
typename Fn>
917 for (
bool soft_set : {
false,
true}) {
918 for (
bool force_set : {
false,
true}) {
921 for (
bool net_specific : {
false,
true}) {
922 fn(arg_actions, conf_actions, soft_set, force_set, section, network, net_specific);
934 const std::string& section,
935 const std::string&
name,
936 const std::string& value_prefix)
938 std::vector<std::string>
values;
940 for (
Action action : actions) {
941 if (action ==
NONE)
break;
945 for (
int i = 0; i < 2; ++i) {
964 FILE* out_file =
nullptr;
965 if (
const char* out_path = getenv(
"ARGS_MERGE_TEST_OUT")) {
967 if (!out_file)
throw std::system_error(errno, std::generic_category(),
"fopen failed");
970 ForEachMergeSetup([&](
const ActionList& arg_actions,
const ActionList& conf_actions,
bool soft_set,
bool force_set,
971 const std::string& section,
const std::string& network,
bool net_specific) {
975 std::string desc =
"net=";
977 parser.m_network = network;
979 const std::string&
name = net_specific ?
"wallet" :
"server";
980 const std::string key =
"-" +
name;
984 auto args = GetValues(arg_actions, section,
name,
"a");
985 std::vector<const char*> argv = {
"ignored"};
986 for (
auto& arg : args) {
990 argv.push_back(arg.c_str());
997 for (
auto& conf_val : GetValues(conf_actions, section,
name,
"c")) {
1003 std::istringstream conf_stream(conf);
1031 desc += parser.
GetArg(key,
"default");
1033 for (
const auto& arg : parser.
GetArgs(key)) {
1040 if (!ignored.empty()) {
1041 desc +=
" | ignored";
1042 for (
const auto& arg : ignored) {
1052 BOOST_REQUIRE(fwrite(desc.data(), 1, desc.size(), out_file) == desc.size());
1057 if (fclose(out_file))
throw std::system_error(errno, std::generic_category(),
"fclose failed");
1063 std::string out_sha_hex =
HexStr(out_sha_bytes);
1074 BOOST_CHECK_EQUAL(out_sha_hex,
"d1e436c1cd510d0ec44d5205d4b4e3bee6387d316e0075c58206cb16603f3d82");
1085 template <
typename Fn>
1099 FILE* out_file =
nullptr;
1100 if (
const char* out_path = getenv(
"CHAIN_MERGE_TEST_OUT")) {
1102 if (!out_file)
throw std::system_error(errno, std::generic_category(),
"fopen failed");
1105 ForEachMergeSetup([&](
const ActionList& arg_actions,
const ActionList& conf_actions) {
1111 auto arg = [](Action action) {
return action == ENABLE_TEST ?
"-testnet=1" :
1112 action == DISABLE_TEST ?
"-testnet=0" :
1113 action == NEGATE_TEST ?
"-notestnet=1" :
1114 action == ENABLE_REG ?
"-regtest=1" :
1115 action == DISABLE_REG ?
"-regtest=0" :
1116 action == NEGATE_REG ?
"-noregtest=1" :
nullptr; };
1119 std::vector<const char*> argv = {
"ignored"};
1120 for (Action action : arg_actions) {
1121 const char* argstr = arg(action);
1123 argv.push_back(argstr);
1125 desc += argv.back();
1132 for (Action action : conf_actions) {
1133 const char* argstr = arg(action);
1140 std::istringstream conf_stream(conf);
1147 }
catch (
const std::runtime_error& e) {
1155 BOOST_REQUIRE(fwrite(desc.data(), 1, desc.size(), out_file) == desc.size());
1160 if (fclose(out_file))
throw std::system_error(errno, std::generic_category(),
"fclose failed");
1166 std::string out_sha_hex =
HexStr(out_sha_bytes);
1177 BOOST_CHECK_EQUAL(out_sha_hex,
"f263493e300023b6509963887444c41386f44b63bc30047eb8402e8c1144854c");
1351 for (
int mod=2;mod<11;mod++)
1355 int err = 30*10000./mod*sqrt((1./mod*(1-1./mod))/10000.);
1357 while(mask<mod-1)mask=(mask<<1)+1;
1361 for (
int i = 0; i < 10000; i++) {
1365 }
while(rval>=(uint32_t)mod);
1386#define B "check_prefix"
1387#define E "check_postfix"
1390 int64_t s64t = -9223372036854775807LL;
1391 uint64_t u64t = 18446744073709551615ULL;
1396 size_t st = 12345678;
1397 ssize_t sst = -12345678;
1402 ptrdiff_t pt = 87654321;
1403 ptrdiff_t spt = -87654321;
1423 for (
const auto& num_sleep : {0, 1}) {
1433 const auto ms_0 = GetTime<std::chrono::milliseconds>();
1434 const auto us_0 = GetTime<std::chrono::microseconds>();
1436 BOOST_CHECK(ms_0 < GetTime<std::chrono::milliseconds>());
1437 BOOST_CHECK(us_0 < GetTime<std::chrono::microseconds>());
1489template <
typename T>
1514 BOOST_CHECK(!ToIntegral<T>(
"-32482348723847471234"));
1515 BOOST_CHECK(!ToIntegral<T>(
"32482348723847471234"));
1524 BOOST_CHECK_EQUAL(ToIntegral<int32_t>(
"-00000000000000001234").value(), -1'234);
1530 RunToIntegralTests<uint64_t>();
1531 RunToIntegralTests<int64_t>();
1532 RunToIntegralTests<uint32_t>();
1533 RunToIntegralTests<int32_t>();
1534 RunToIntegralTests<uint16_t>();
1535 RunToIntegralTests<int16_t>();
1536 RunToIntegralTests<uint8_t>();
1537 RunToIntegralTests<int8_t>();
1539 BOOST_CHECK(!ToIntegral<int64_t>(
"-9223372036854775809"));
1540 BOOST_CHECK_EQUAL(ToIntegral<int64_t>(
"-9223372036854775808").value(), -9'223'372'036'854'775'807LL - 1LL);
1541 BOOST_CHECK_EQUAL(ToIntegral<int64_t>(
"9223372036854775807").value(), 9'223'372'036'854'775'807);
1542 BOOST_CHECK(!ToIntegral<int64_t>(
"9223372036854775808"));
1546 BOOST_CHECK_EQUAL(ToIntegral<uint64_t>(
"18446744073709551615").value(), 18'446'744'073'709'551'615ULL);
1547 BOOST_CHECK(!ToIntegral<uint64_t>(
"18446744073709551616"));
1550 BOOST_CHECK_EQUAL(ToIntegral<int32_t>(
"-2147483648").value(), -2'147'483'648LL);
1611 BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>(
"-9223372036854775808"), -9'223'372'036'854'775'807LL - 1LL);
1612 BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>(
"9223372036854775807"), 9'223'372'036'854'775'807);
1617 BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint64_t>(
"18446744073709551615"), 18'446'744'073'709'551'615ULL);
1621 BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(
"-2147483648"), -2'147'483'648LL);
1627 BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint32_t>(
"4294967295"), 4'294'967'295U);
1829 BOOST_CHECK_EQUAL(
FormatParagraph(
"This_is_a_very_long_test_string_without_any_spaces_so_it_should_just_get_returned_as_is_despite_the_length until it gets here", 79),
"This_is_a_very_long_test_string_without_any_spaces_so_it_should_just_get_returned_as_is_despite_the_length\nuntil it gets here");
1832 BOOST_CHECK_EQUAL(
FormatParagraph(
"a b c d e f g h i j k l m n o p q r s t u v w x y z 1 2 3 4 5 6 7 8 9 a b c de f g h i j k l m n o p", 79),
"a b c d e f g h i j k l m n o p q r s t u v w x y z 1 2 3 4 5 6 7 8 9 a b c de\nf g h i j k l m n o p");
1833 BOOST_CHECK_EQUAL(
FormatParagraph(
"x\na b c d e f g h i j k l m n o p q r s t u v w x y z 1 2 3 4 5 6 7 8 9 a b c de f g h i j k l m n o p", 79),
"x\na b c d e f g h i j k l m n o p q r s t u v w x y z 1 2 3 4 5 6 7 8 9 a b c de\nf g h i j k l m n o p");
1835 BOOST_CHECK_EQUAL(
FormatParagraph(
"x\na b c d e f g h i j k l m n o p q r s t u v w x y z 1 2 3 4 5 6 7 8 9 a b c de f g h i j k l m n o p q r s t u v w x y z 0 1 2 3 4 5 6 7 8 9 a b c d e fg h i j k", 79, 4),
"x\na b c d e f g h i j k l m n o p q r s t u v w x y z 1 2 3 4 5 6 7 8 9 a b c de\n f g h i j k l m n o p q r s t u v w x y z 0 1 2 3 4 5 6 7 8 9 a b c d e fg\n h i j k");
1837 BOOST_CHECK_EQUAL(
FormatParagraph(
"This is a very long test string. This is a second sentence in the very long test string.", 79),
"This is a very long test string. This is a second sentence in the very long\ntest string.");
1838 BOOST_CHECK_EQUAL(
FormatParagraph(
"This is a very long test string.\nThis is a second sentence in the very long test string. This is a third sentence in the very long test string.", 79),
"This is a very long test string.\nThis is a second sentence in the very long test string. This is a third\nsentence in the very long test string.");
1839 BOOST_CHECK_EQUAL(
FormatParagraph(
"This is a very long test string.\n\nThis is a second sentence in the very long test string. This is a third sentence in the very long test string.", 79),
"This is a very long test string.\n\nThis is a second sentence in the very long test string. This is a third\nsentence in the very long test string.");
1840 BOOST_CHECK_EQUAL(
FormatParagraph(
"Testing that normal newlines do not get indented.\nLike here.", 79),
"Testing that normal newlines do not get indented.\nLike here.");
1845 std::vector<std::string> comments;
1846 comments.push_back(std::string(
"comment1"));
1847 std::vector<std::string> comments2;
1848 comments2.push_back(std::string(
"comment1"));
1943 int rv = read(fd, &ch, 1);
1948 rv = write(fd, &ch, 1);
1954 rv = write(fd, &ch, 1);
1969 fs::path dirname = m_args.GetDataDirBase() /
"lock_dir";
1970 const std::string lockname =
".lock";
1975 void (*old_handler)(int) = signal(SIGCHLD, SIG_DFL);
1992 fs::create_directories(dirname);
2047 signal(SIGCHLD, old_handler);
2052 fs::remove_all(dirname);
2058 fs::path tmpdirname = m_args.GetDataDirBase();
2065 fs::create_directory(tmpdirname);
2068 fs::remove(tmpdirname);
2108 return std::string(span.
begin(), span.
end());
2119 input =
"MilkToastHoney";
2121 success =
Const(
"", sp);
2125 success =
Const(
"Milk", sp);
2129 success =
Const(
"Bread", sp);
2132 success =
Const(
"Toast", sp);
2136 success =
Const(
"Honeybadger", sp);
2139 success =
Const(
"Honey", sp);
2144 input =
"Foo(Bar(xy,z()))";
2147 success =
Func(
"FooBar", sp);
2150 success =
Func(
"Foo(", sp);
2153 success =
Func(
"Foo", sp);
2157 success =
Func(
"Bar", sp);
2161 success =
Func(
"xy", sp);
2167 input =
"(n*(n-1))/2";
2179 input =
"(aaaaa,bbbbb()),c";
2191 input =
"((a),(b),(c)),xxx";
2198 std::vector<Span<const char>> results;
2201 results =
Split(input,
'x');
2208 input =
"one#two#three";
2209 results =
Split(input,
'-');
2213 input =
"one#two#three";
2214 results =
Split(input,
'#');
2220 input =
"*foo*bar*";
2221 results =
Split(input,
'*');
2238 const std::string NUL(
"O\x00O", 3);
2247 const Tracker* origin;
2251 Tracker() noexcept : origin(this), copies(0) {}
2252 Tracker(
const Tracker& t) noexcept : origin(t.origin), copies(t.copies + 1) {}
2253 Tracker(Tracker&& t) noexcept : origin(t.origin), copies(t.copies) {}
2254 Tracker& operator=(
const Tracker& t)
noexcept
2257 copies = t.copies + 1;
2279 auto v2 =
Vector(std::move(t2));
2284 auto v3 =
Vector(t1, std::move(t2));
2291 auto v4 =
Vector(std::move(v3[0]), v3[1], std::move(t3));
2300 auto v5 =
Cat(v1, v4);
2311 auto v6 =
Cat(std::move(v1), v3);
2320 auto v7 =
Cat(v2, std::move(v4));
2331 auto v8 =
Cat(std::move(v2), std::move(v3));
2343 const std::array<unsigned char, 32> privkey_bytes = {
2346 0xD9, 0x7F, 0x51, 0x08, 0xF1, 0x1C, 0xDA, 0x6E,
2347 0xEE, 0xBA, 0xAA, 0x42, 0x0F, 0xEF, 0x07, 0x26,
2348 0xB1, 0xF8, 0x98, 0x06, 0x0B, 0x98, 0x48, 0x9F,
2349 0xA3, 0x09, 0x84, 0x63, 0xC0, 0x03, 0x28, 0x66
2352 const std::string message =
"Trust no one";
2354 const std::string expected_signature =
2355 "IPojfrX2dfPnH26UegfbGQQLrdK844DlHq5157/P6h57WyuS/Qsl+h/WSVGDF4MUi4rWSswW38oimDYfNNUBUOk=";
2358 std::string generated_signature;
2360 BOOST_REQUIRE_MESSAGE(!privkey.
IsValid(),
2361 "Confirm the private key is invalid");
2363 BOOST_CHECK_MESSAGE(!
MessageSign(privkey, message, generated_signature),
2364 "Sign with an invalid private key");
2366 privkey.
Set(privkey_bytes.begin(), privkey_bytes.end(),
true);
2368 BOOST_REQUIRE_MESSAGE(privkey.
IsValid(),
2369 "Confirm the private key is valid");
2371 BOOST_CHECK_MESSAGE(
MessageSign(privkey, message, generated_signature),
2372 "Sign with a valid private key");
2382 "signature should be irrelevant",
2388 "3B5fQsEXEaV8v6U3ejYc8XaKXAkyQj2MjV",
2389 "signature should be irrelevant",
2395 "1KqbBpLy5FARmTPD4VZnDDpYjkUvkr82Pm",
2396 "invalid signature, not in base64 encoding",
2397 "message should be irrelevant"),
2402 "1KqbBpLy5FARmTPD4VZnDDpYjkUvkr82Pm",
2403 "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=",
2404 "message should be irrelevant"),
2409 "15CRxFdyRpGZLW9w8HnHvVduizdL5jKNbs",
2410 "IPojfrX2dfPnH26UegfbGQQLrdK844DlHq5157/P6h57WyuS/Qsl+h/WSVGDF4MUi4rWSswW38oimDYfNNUBUOk=",
2411 "I never signed this"),
2416 "15CRxFdyRpGZLW9w8HnHvVduizdL5jKNbs",
2417 "IPojfrX2dfPnH26UegfbGQQLrdK844DlHq5157/P6h57WyuS/Qsl+h/WSVGDF4MUi4rWSswW38oimDYfNNUBUOk=",
2423 "11canuhp9X2NocwCq7xNrQYTmUgZAnLK3",
2424 "IIcaIENoYW5jZWxsb3Igb24gYnJpbmsgb2Ygc2Vjb25kIGJhaWxvdXQgZm9yIGJhbmtzIAaHRtbCeDZINyavx14=",
2431 const std::string unsigned_tx =
"...";
2432 const std::string prefixed_message =
2435 std::string(1, (
char)unsigned_tx.length()) +
2439 const uint256 message_hash1 =
Hash(prefixed_message);
2443 BOOST_CHECK_NE(message_hash1, signature_hash);
int64_t CAmount
Amount in satoshis (Can be negative)
static constexpr CAmount COIN
The amount of satoshis in one BTC.
#define Assert(val)
Identity function.
#define Assume(val)
Assume is the identity function.
const fs::path & GetDataDirBase() const
Get data directory path.
const std::set< std::string > GetUnsuitableSectionOnlyArgs() const
Log warnings for options in m_section_only_args when they are specified in the default section but no...
bool IsArgNegated(const std::string &strArg) const
Return true if the argument was originally passed as a negated option, i.e.
@ ALLOW_ANY
disable validation
bool ReadSettingsFile(std::vector< std::string > *errors=nullptr)
Read settings file.
void ForceSetArg(const std::string &strArg, const std::string &strValue)
bool WriteSettingsFile(std::vector< std::string > *errors=nullptr) const
Write settings file.
bool ParseParameters(int argc, const char *const argv[], std::string &error)
std::vector< std::string > GetArgs(const std::string &strArg) const
Return a vector of strings of the given argument.
void LockSettings(Fn &&fn)
Access settings with lock held.
bool SoftSetArg(const std::string &strArg, const std::string &strValue)
Set an argument if it doesn't already have a value.
void SelectConfigNetwork(const std::string &network)
Select the network in use.
void ClearPathCache()
Clear cached directory paths.
bool IsArgSet(const std::string &strArg) const
Return true if the given argument has been manually set.
int64_t GetIntArg(const std::string &strArg, int64_t nDefault) const
Return integer argument or default value.
std::vector< util::SettingsValue > GetSettingsList(const std::string &arg) const
Get list of setting values.
std::string GetArg(const std::string &strArg, const std::string &strDefault) const
Return string argument or default value.
util::SettingsValue GetSetting(const std::string &arg) const
Get setting value.
bool ReadConfigStream(std::istream &stream, const std::string &filepath, std::string &error, bool ignore_invalid_keys=false)
bool GetBoolArg(const std::string &strArg, bool fDefault) const
Return boolean argument or default value.
void AddArg(const std::string &name, const std::string &help, unsigned int flags, const OptionsCategory &cat)
Add argument.
std::string GetChainName() const
Returns the appropriate chain name from the program arguments.
static const std::string TESTNET
static const std::string SIGNET
static const std::string MAIN
Chain name strings.
A hasher class for Bitcoin's 256-bit hash (double SHA-256).
void Finalize(Span< unsigned char > output)
CHash256 & Write(Span< const unsigned char > input)
An encapsulated private key.
bool IsValid() const
Check whether this private key is valid.
void Set(const T pbegin, const T pend, bool fCompressedIn)
Initialize using begin and end iterators to byte data.
static const size_t OUTPUT_SIZE
Test GetSetting and GetArg type coercion, negation, and default value handling.
void CheckValue(unsigned int flags, const char *arg, const Expect &expect)
A Span is an object that can refer to a contiguous sequence of objects.
constexpr C * begin() const noexcept
constexpr C * end() const noexcept
std::string write(unsigned int prettyIndent=0, unsigned int indentLevel=0) const
Path class wrapper to prepare application code for transition from boost::filesystem library to std::...
std::string FormatSubVersion(const std::string &name, int nClientVersion, const std::vector< std::string > &comments)
Format the subversion field according to BIP 14 spec (https://github.com/bitcoin/bips/blob/master/bip...
BOOST_AUTO_TEST_SUITE_END()
std::unique_ptr< Descriptor > Parse(const std::string &descriptor, FlatSigningProvider &out, std::string &error, bool require_checksum)
Parse a descriptor string.
fs::path GetUniquePath(const fs::path &base)
Helper function for getting a unique path.
uint256 Hash(const T &in1)
Compute the 256-bit hash of an object.
@ ERR_MALFORMED_SIGNATURE
The provided signature couldn't be parsed (maybe invalid base64).
@ ERR_INVALID_ADDRESS
The provided address is invalid.
@ ERR_ADDRESS_NO_KEY
The provided address is valid but does not refer to a public key.
@ ERR_NOT_SIGNED
The message was not signed with the private key of the provided address.
@ OK
The message verification was successful.
@ ERR_PUBKEY_NOT_RECOVERED
A public key could not be recovered from the provided signature and message.
std::optional< CAmount > ParseMoney(const std::string &money_string)
Parse an amount denoted in full coins.
std::string FormatMoney(const CAmount n)
Money parsing/formatting utilities.
std::string LogEscapeMessage(const std::string &str)
Belts and suspenders: make sure outgoing log messages don't contain potentially suspicious characters...
static std::string PathToString(const path &path)
Convert path object to byte string.
FILE * fopen(const fs::path &p, const char *mode)
std::vector< Span< const char > > Split(const Span< const char > &sp, char sep)
Split a string on every instance of sep, returning a vector.
Span< const char > Expr(Span< const char > &sp)
Extract the expression that sp begins with.
bool Const(const std::string &str, Span< const char > &sp)
Parse a constant.
bool Func(const std::string &str, Span< const char > &sp)
Parse a function call.
#define BOOST_CHECK_THROW(stmt, excMatch)
#define BOOST_FIXTURE_TEST_SUITE(a, b)
#define BOOST_CHECK_EQUAL(v1, v2)
#define BOOST_CHECK(expr)
static const int64_t values[]
A selection of numbers that do not trigger int64_t overflow when added/subtracted.
@ ZEROS
Seed with a compile time constant of zeros.
static void SeedInsecureRand(SeedRand seed=SeedRand::SEED)
static uint32_t InsecureRand32()
constexpr auto MakeUCharSpan(V &&v) -> decltype(UCharSpanCast(MakeSpan(std::forward< V >(v))))
Like MakeSpan, but for (const) unsigned char member types only.
void ForEachNoDup(CharType(&string)[StringLength], CharType min_char, CharType max_char, Fn &&fn)
Iterate over string values and call function for each string without successive duplicate characters.
std::string Capitalize(std::string str)
Capitalizes the first character of the given string.
std::string HexStr(const Span< const uint8_t > s)
Convert a span of bytes to a lower-case hexadecimal string.
std::string FormatParagraph(const std::string &in, size_t width, size_t indent)
Format a paragraph of text to a fixed width, adding spaces for indentation to any added line.
bool ParseUInt16(const std::string &str, uint16_t *out)
Convert decimal string to unsigned 16-bit integer with strict parse error feedback.
std::string ToLower(const std::string &str)
Returns the lowercase equivalent of the given string.
bool ParseUInt64(const std::string &str, uint64_t *out)
Convert decimal string to unsigned 64-bit integer with strict parse error feedback.
std::vector< unsigned char > ParseHex(const char *psz)
bool ParseUInt32(const std::string &str, uint32_t *out)
Convert decimal string to unsigned 32-bit integer with strict parse error feedback.
bool ParseInt32(const std::string &str, int32_t *out)
Convert string to signed 32-bit integer with strict parse error feedback.
bool ParseFixedPoint(const std::string &val, int decimals, int64_t *amount_out)
Parse number as fixed point according to JSON number syntax.
bool IsHex(const std::string &str)
std::string SanitizeString(const std::string &str, int rule)
Remove unsafe chars.
bool IsHexNumber(const std::string &str)
Return true if the string is a hex number, optionally prefixed with "0x".
bool ParseInt64(const std::string &str, int64_t *out)
Convert string to signed 64-bit integer with strict parse error feedback.
std::string ToUpper(const std::string &str)
Returns the uppercase equivalent of the given string.
bool ParseUInt8(const std::string &str, uint8_t *out)
Convert decimal string to unsigned 8-bit integer with strict parse error feedback.
constexpr bool IsDigit(char c)
Tests if the given character is a decimal digit.
bool TimingResistantEqual(const T &a, const T &b)
Timing-attack-resistant comparison.
@ SAFE_CHARS_UA_COMMENT
BIP-0014 subset.
auto Join(const std::vector< T > &list, const BaseType &separator, UnaryOp unary_op) -> decltype(unary_op(list.at(0)))
Join a list of items.
std::string RemovePrefix(const std::string &str, const std::string &prefix)
std::string TrimString(const std::string &str, const std::string &pattern=" \f\n\r\t\v")
std::string ToString(const T &t)
Locale-independent version of std::to_string.
void ForEachMergeSetup(Fn &&fn)
Enumerate all possible test configurations.
static constexpr int MAX_ACTIONS
Max number of actions to sequence together.
std::vector< std::string > GetValues(const ActionList &actions, const std::string §ion, const std::string &name, const std::string &value_prefix)
Translate actions into a list of <key>=setting strings.
Action[MAX_ACTIONS] ActionList
void ForEachMergeSetup(Fn &&fn)
Enumerate all possible test configurations.
Action[MAX_ACTIONS] ActionList
static constexpr int MAX_ACTIONS
Expect & List(std::vector< std::string > m)
Expect(util::SettingsValue s)
Expect & String(const char *s)
std::optional< int64_t > int_value
std::optional< std::vector< std::string > > list_value
Expect & Error(const char *e)
std::optional< bool > bool_value
util::SettingsValue setting
const char * string_value
std::string Parse(const char *arg)
void SetupArgs(const std::vector< std::pair< std::string, unsigned int > > &args)
void SetNetworkOnlyArg(const std::string arg)
void ReadConfigString(const std::string str_config)
std::vector< util::SettingsValue > GetSettingsList(const std::string &arg) const
Get list of setting values.
util::SettingsValue GetSetting(const std::string &arg) const
Get setting value.
bool ReadConfigStream(std::istream &stream, const std::string &filepath, std::string &error, bool ignore_invalid_keys=false)
Testing fixture that pre-creates a 100-block REGTEST-mode block chain.
std::map< std::string, SettingsValue > rw_settings
Map of setting name to read-write file setting value.
#define TRY_LOCK(cs, name)
bool error(const char *fmt, const Args &... args)
#define ASSERT_DEBUG_LOG(message)
void UninterruptibleSleep(const std::chrono::microseconds &n)
int64_t GetTimeSeconds()
Returns the system time (not mockable)
std::string FormatISO8601Date(int64_t nTime)
void SetMockTime(int64_t nMockTimeIn)
DEPRECATED Use SetMockTime with chrono type.
int64_t ParseISO8601DateTime(const std::string &str)
int64_t GetTime()
DEPRECATED Use either GetTimeSeconds (not mockable) or GetTime<T> (mockable)
std::string FormatISO8601DateTime(int64_t nTime)
ISO 8601 formatting is preferred.
uint256 MessageHash(const std::string &message)
Hashes a message for signing and verification in a manner that prevents inadvertently signing a trans...
bool MessageSign(const CKey &privkey, const std::string &message, std::string &signature)
Sign a message.
const std::string MESSAGE_MAGIC
Text used to signify that a signed message follows and to prevent inadvertently signing a transaction...
MessageVerificationResult MessageVerify(const std::string &address, const std::string &signature, const std::string &message)
Verify a signed message.
bool LockDirectory(const fs::path &directory, const std::string lockfile_name, bool probe_only)
bool DirIsWritable(const fs::path &directory)
void ReleaseDirectoryLocks()
Release all directory locks.
BOOST_FIXTURE_TEST_CASE(util_CheckValue, CheckValueTest)
static void TestParse(const std::string &str, bool expected_bool, int64_t expected_int)
static constexpr char ExitCommand
static constexpr char UnlockCommand
static void TestOtherProcess(fs::path dirname, std::string lockname, int fd)
static const unsigned char ParseHex_expected[65]
static void RunToIntegralTests()
static const std::string STRING_WITH_EMBEDDED_NULL_CHAR
static constexpr char LockCommand
BOOST_AUTO_TEST_CASE(util_datadir)
static void TestOtherThread(fs::path dirname, std::string lockname, bool *result)
static std::string SpanToStr(const Span< const char > &span)
V Cat(V v1, V &&v2)
Concatenate two vectors, moving elements.
std::vector< typename std::common_type< Args... >::type > Vector(Args &&... args)
Construct a vector with the specified elements.