Bitcoin Core  22.99.0
P2P Digital Currency
util_tests.cpp
Go to the documentation of this file.
1 // Copyright (c) 2011-2021 The Bitcoin Core developers
2 // Distributed under the MIT software license, see the accompanying
3 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
4 
5 #include <util/system.h>
6 
7 #include <clientversion.h>
8 #include <fs.h>
9 #include <hash.h> // For Hash()
10 #include <key.h> // For CKey
11 #include <sync.h>
12 #include <test/util/logging.h>
13 #include <test/util/setup_common.h>
14 #include <test/util/str.h>
15 #include <uint256.h>
16 #include <util/getuniquepath.h>
17 #include <util/message.h> // For MessageSign(), MessageVerify(), MESSAGE_MAGIC
18 #include <util/moneystr.h>
19 #include <util/overflow.h>
20 #include <util/spanparsing.h>
21 #include <util/strencodings.h>
22 #include <util/string.h>
23 #include <util/time.h>
24 #include <util/vector.h>
25 
26 #include <array>
27 #include <optional>
28 #include <limits>
29 #include <map>
30 #include <stdint.h>
31 #include <string.h>
32 #include <thread>
33 #include <univalue.h>
34 #include <utility>
35 #include <vector>
36 #ifndef WIN32
37 #include <signal.h>
38 #include <sys/types.h>
39 #include <sys/wait.h>
40 #endif
41 
42 #include <boost/test/unit_test.hpp>
43 
44 using namespace std::literals;
45 static const std::string STRING_WITH_EMBEDDED_NULL_CHAR{"1"s "\0" "1"s};
46 
47 /* defined in logging.cpp */
48 namespace BCLog {
49  std::string LogEscapeMessage(const std::string& str);
50 }
51 
53 
54 BOOST_AUTO_TEST_CASE(util_datadir)
55 {
56  // Use local args variable instead of m_args to avoid making assumptions about test setup
58  args.ForceSetArg("-datadir", fs::PathToString(m_path_root));
59 
60  const fs::path dd_norm = args.GetDataDirBase();
61 
62  args.ForceSetArg("-datadir", fs::PathToString(dd_norm) + "/");
65 
66  args.ForceSetArg("-datadir", fs::PathToString(dd_norm) + "/.");
69 
70  args.ForceSetArg("-datadir", fs::PathToString(dd_norm) + "/./");
73 
74  args.ForceSetArg("-datadir", fs::PathToString(dd_norm) + "/.//");
77 }
78 
80 {
81  // Check that Assert can forward
82  const std::unique_ptr<int> p_two = Assert(std::make_unique<int>(2));
83  // Check that Assert works on lvalues and rvalues
84  const int two = *Assert(p_two);
85  Assert(two == 2);
86  Assert(true);
87  // Check that Assume can be used as unary expression
88  const bool result{Assume(two == 2)};
89  Assert(result);
90 }
91 
92 BOOST_AUTO_TEST_CASE(util_criticalsection)
93 {
95 
96  do {
97  LOCK(cs);
98  break;
99 
100  BOOST_ERROR("break was swallowed!");
101  } while(0);
102 
103  do {
104  TRY_LOCK(cs, lockTest);
105  if (lockTest) {
106  BOOST_CHECK(true); // Needed to suppress "Test case [...] did not check any assertions"
107  break;
108  }
109 
110  BOOST_ERROR("break was swallowed!");
111  } while(0);
112 }
113 
114 static const unsigned char ParseHex_expected[65] = {
115  0x04, 0x67, 0x8a, 0xfd, 0xb0, 0xfe, 0x55, 0x48, 0x27, 0x19, 0x67, 0xf1, 0xa6, 0x71, 0x30, 0xb7,
116  0x10, 0x5c, 0xd6, 0xa8, 0x28, 0xe0, 0x39, 0x09, 0xa6, 0x79, 0x62, 0xe0, 0xea, 0x1f, 0x61, 0xde,
117  0xb6, 0x49, 0xf6, 0xbc, 0x3f, 0x4c, 0xef, 0x38, 0xc4, 0xf3, 0x55, 0x04, 0xe5, 0x1e, 0xc1, 0x12,
118  0xde, 0x5c, 0x38, 0x4d, 0xf7, 0xba, 0x0b, 0x8d, 0x57, 0x8a, 0x4c, 0x70, 0x2b, 0x6b, 0xf1, 0x1d,
119  0x5f
120 };
121 BOOST_AUTO_TEST_CASE(util_ParseHex)
122 {
123  std::vector<unsigned char> result;
124  std::vector<unsigned char> expected(ParseHex_expected, ParseHex_expected + sizeof(ParseHex_expected));
125  // Basic test vector
126  result = ParseHex("04678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5f");
127  BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
128 
129  // Spaces between bytes must be supported
130  result = ParseHex("12 34 56 78");
131  BOOST_CHECK(result.size() == 4 && result[0] == 0x12 && result[1] == 0x34 && result[2] == 0x56 && result[3] == 0x78);
132 
133  // Leading space must be supported (used in BerkeleyEnvironment::Salvage)
134  result = ParseHex(" 89 34 56 78");
135  BOOST_CHECK(result.size() == 4 && result[0] == 0x89 && result[1] == 0x34 && result[2] == 0x56 && result[3] == 0x78);
136 
137  // Stop parsing at invalid value
138  result = ParseHex("1234 invalid 1234");
139  BOOST_CHECK(result.size() == 2 && result[0] == 0x12 && result[1] == 0x34);
140 }
141 
143 {
146  "04678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5f");
147 
149  HexStr(Span{ParseHex_expected}.last(0)),
150  "");
151 
153  HexStr(Span{ParseHex_expected}.first(0)),
154  "");
155 
156  {
157  const std::vector<char> in_s{ParseHex_expected, ParseHex_expected + 5};
158  const Span<const uint8_t> in_u{MakeUCharSpan(in_s)};
159  const Span<const std::byte> in_b{MakeByteSpan(in_s)};
160  const std::string out_exp{"04678afdb0"};
161 
162  BOOST_CHECK_EQUAL(HexStr(in_u), out_exp);
163  BOOST_CHECK_EQUAL(HexStr(in_s), out_exp);
164  BOOST_CHECK_EQUAL(HexStr(in_b), out_exp);
165  }
166 }
167 
168 BOOST_AUTO_TEST_CASE(span_write_bytes)
169 {
170  std::array mut_arr{uint8_t{0xaa}, uint8_t{0xbb}};
171  const auto mut_bytes{MakeWritableByteSpan(mut_arr)};
172  mut_bytes[1] = std::byte{0x11};
173  BOOST_CHECK_EQUAL(mut_arr.at(0), 0xaa);
174  BOOST_CHECK_EQUAL(mut_arr.at(1), 0x11);
175 }
176 
178 {
179  // Normal version
180  BOOST_CHECK_EQUAL(Join({}, ", "), "");
181  BOOST_CHECK_EQUAL(Join({"foo"}, ", "), "foo");
182  BOOST_CHECK_EQUAL(Join({"foo", "bar"}, ", "), "foo, bar");
183 
184  // Version with unary operator
185  const auto op_upper = [](const std::string& s) { return ToUpper(s); };
186  BOOST_CHECK_EQUAL(Join<std::string>({}, ", ", op_upper), "");
187  BOOST_CHECK_EQUAL(Join<std::string>({"foo"}, ", ", op_upper), "FOO");
188  BOOST_CHECK_EQUAL(Join<std::string>({"foo", "bar"}, ", ", op_upper), "FOO, BAR");
189 }
190 
191 BOOST_AUTO_TEST_CASE(util_TrimString)
192 {
193  BOOST_CHECK_EQUAL(TrimString(" foo bar "), "foo bar");
194  BOOST_CHECK_EQUAL(TrimString("\t \n \n \f\n\r\t\v\tfoo \n \f\n\r\t\v\tbar\t \n \f\n\r\t\v\t\n "), "foo \n \f\n\r\t\v\tbar");
195  BOOST_CHECK_EQUAL(TrimString("\t \n foo \n\tbar\t \n "), "foo \n\tbar");
196  BOOST_CHECK_EQUAL(TrimString("\t \n foo \n\tbar\t \n ", "fobar"), "\t \n foo \n\tbar\t \n ");
197  BOOST_CHECK_EQUAL(TrimString("foo bar"), "foo bar");
198  BOOST_CHECK_EQUAL(TrimString("foo bar", "fobar"), " ");
199  BOOST_CHECK_EQUAL(TrimString(std::string("\0 foo \0 ", 8)), std::string("\0 foo \0", 7));
200  BOOST_CHECK_EQUAL(TrimString(std::string(" foo ", 5)), std::string("foo", 3));
201  BOOST_CHECK_EQUAL(TrimString(std::string("\t\t\0\0\n\n", 6)), std::string("\0\0", 2));
202  BOOST_CHECK_EQUAL(TrimString(std::string("\x05\x04\x03\x02\x01\x00", 6)), std::string("\x05\x04\x03\x02\x01\x00", 6));
203  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));
204  BOOST_CHECK_EQUAL(TrimString(std::string("\x05\x04\x03\x02\x01\x00", 6), std::string("\x05\x04\x03\x02\x01\x00", 6)), "");
205 }
206 
207 BOOST_AUTO_TEST_CASE(util_FormatParseISO8601DateTime)
208 {
209  BOOST_CHECK_EQUAL(FormatISO8601DateTime(1317425777), "2011-09-30T23:36:17Z");
210  BOOST_CHECK_EQUAL(FormatISO8601DateTime(0), "1970-01-01T00:00:00Z");
211 
212  BOOST_CHECK_EQUAL(ParseISO8601DateTime("1970-01-01T00:00:00Z"), 0);
213  BOOST_CHECK_EQUAL(ParseISO8601DateTime("1960-01-01T00:00:00Z"), 0);
214  BOOST_CHECK_EQUAL(ParseISO8601DateTime("2011-09-30T23:36:17Z"), 1317425777);
215 
216  auto time = GetTimeSeconds();
218 }
219 
220 BOOST_AUTO_TEST_CASE(util_FormatISO8601Date)
221 {
222  BOOST_CHECK_EQUAL(FormatISO8601Date(1317425777), "2011-09-30");
223 }
224 
226 {
227  TestArgsManager() { m_network_only_args.clear(); }
228  void ReadConfigString(const std::string str_config)
229  {
230  std::istringstream streamConfig(str_config);
231  {
232  LOCK(cs_args);
233  m_settings.ro_config.clear();
234  m_config_sections.clear();
235  }
236  std::string error;
237  BOOST_REQUIRE(ReadConfigStream(streamConfig, "", error));
238  }
239  void SetNetworkOnlyArg(const std::string arg)
240  {
241  LOCK(cs_args);
242  m_network_only_args.insert(arg);
243  }
244  void SetupArgs(const std::vector<std::pair<std::string, unsigned int>>& args)
245  {
246  for (const auto& arg : args) {
247  AddArg(arg.first, "", arg.second, OptionsCategory::OPTIONS);
248  }
249  }
253  using ArgsManager::cs_args;
254  using ArgsManager::m_network;
255  using ArgsManager::m_settings;
256 };
257 
260 {
261 public:
262  struct Expect {
264  bool default_string = false;
265  bool default_int = false;
266  bool default_bool = false;
267  const char* string_value = nullptr;
268  std::optional<int64_t> int_value;
269  std::optional<bool> bool_value;
270  std::optional<std::vector<std::string>> list_value;
271  const char* error = nullptr;
272 
273  explicit Expect(util::SettingsValue s) : setting(std::move(s)) {}
274  Expect& DefaultString() { default_string = true; return *this; }
275  Expect& DefaultInt() { default_int = true; return *this; }
276  Expect& DefaultBool() { default_bool = true; return *this; }
277  Expect& String(const char* s) { string_value = s; return *this; }
278  Expect& Int(int64_t i) { int_value = i; return *this; }
279  Expect& Bool(bool b) { bool_value = b; return *this; }
280  Expect& List(std::vector<std::string> m) { list_value = std::move(m); return *this; }
281  Expect& Error(const char* e) { error = e; return *this; }
282  };
283 
284  void CheckValue(unsigned int flags, const char* arg, const Expect& expect)
285  {
286  TestArgsManager test;
287  test.SetupArgs({{"-value", flags}});
288  const char* argv[] = {"ignored", arg};
289  std::string error;
290  bool success = test.ParseParameters(arg ? 2 : 1, (char**)argv, error);
291 
292  BOOST_CHECK_EQUAL(test.GetSetting("-value").write(), expect.setting.write());
293  auto settings_list = test.GetSettingsList("-value");
294  if (expect.setting.isNull() || expect.setting.isFalse()) {
295  BOOST_CHECK_EQUAL(settings_list.size(), 0U);
296  } else {
297  BOOST_CHECK_EQUAL(settings_list.size(), 1U);
298  BOOST_CHECK_EQUAL(settings_list[0].write(), expect.setting.write());
299  }
300 
301  if (expect.error) {
302  BOOST_CHECK(!success);
303  BOOST_CHECK_NE(error.find(expect.error), std::string::npos);
304  } else {
305  BOOST_CHECK(success);
307  }
308 
309  if (expect.default_string) {
310  BOOST_CHECK_EQUAL(test.GetArg("-value", "zzzzz"), "zzzzz");
311  } else if (expect.string_value) {
312  BOOST_CHECK_EQUAL(test.GetArg("-value", "zzzzz"), expect.string_value);
313  } else {
314  BOOST_CHECK(!success);
315  }
316 
317  if (expect.default_int) {
318  BOOST_CHECK_EQUAL(test.GetIntArg("-value", 99999), 99999);
319  } else if (expect.int_value) {
320  BOOST_CHECK_EQUAL(test.GetIntArg("-value", 99999), *expect.int_value);
321  } else {
322  BOOST_CHECK(!success);
323  }
324 
325  if (expect.default_bool) {
326  BOOST_CHECK_EQUAL(test.GetBoolArg("-value", false), false);
327  BOOST_CHECK_EQUAL(test.GetBoolArg("-value", true), true);
328  } else if (expect.bool_value) {
329  BOOST_CHECK_EQUAL(test.GetBoolArg("-value", false), *expect.bool_value);
330  BOOST_CHECK_EQUAL(test.GetBoolArg("-value", true), *expect.bool_value);
331  } else {
332  BOOST_CHECK(!success);
333  }
334 
335  if (expect.list_value) {
336  auto l = test.GetArgs("-value");
337  BOOST_CHECK_EQUAL_COLLECTIONS(l.begin(), l.end(), expect.list_value->begin(), expect.list_value->end());
338  } else {
339  BOOST_CHECK(!success);
340  }
341  }
342 };
343 
345 {
346  using M = ArgsManager;
347 
348  CheckValue(M::ALLOW_ANY, nullptr, Expect{{}}.DefaultString().DefaultInt().DefaultBool().List({}));
349  CheckValue(M::ALLOW_ANY, "-novalue", Expect{false}.String("0").Int(0).Bool(false).List({}));
350  CheckValue(M::ALLOW_ANY, "-novalue=", Expect{false}.String("0").Int(0).Bool(false).List({}));
351  CheckValue(M::ALLOW_ANY, "-novalue=0", Expect{true}.String("1").Int(1).Bool(true).List({"1"}));
352  CheckValue(M::ALLOW_ANY, "-novalue=1", Expect{false}.String("0").Int(0).Bool(false).List({}));
353  CheckValue(M::ALLOW_ANY, "-novalue=2", Expect{false}.String("0").Int(0).Bool(false).List({}));
354  CheckValue(M::ALLOW_ANY, "-novalue=abc", Expect{true}.String("1").Int(1).Bool(true).List({"1"}));
355  CheckValue(M::ALLOW_ANY, "-value", Expect{""}.String("").Int(0).Bool(true).List({""}));
356  CheckValue(M::ALLOW_ANY, "-value=", Expect{""}.String("").Int(0).Bool(true).List({""}));
357  CheckValue(M::ALLOW_ANY, "-value=0", Expect{"0"}.String("0").Int(0).Bool(false).List({"0"}));
358  CheckValue(M::ALLOW_ANY, "-value=1", Expect{"1"}.String("1").Int(1).Bool(true).List({"1"}));
359  CheckValue(M::ALLOW_ANY, "-value=2", Expect{"2"}.String("2").Int(2).Bool(true).List({"2"}));
360  CheckValue(M::ALLOW_ANY, "-value=abc", Expect{"abc"}.String("abc").Int(0).Bool(false).List({"abc"}));
361 }
362 
364  std::string Parse(const char* arg)
365  {
366  TestArgsManager test;
367  test.SetupArgs({{"-includeconf", ArgsManager::ALLOW_ANY}});
368  std::array argv{"ignored", arg};
369  std::string error;
370  (void)test.ParseParameters(argv.size(), argv.data(), error);
371  return error;
372  }
373 };
374 
376 {
377  BOOST_CHECK_EQUAL(Parse("-noincludeconf"), "");
378  BOOST_CHECK_EQUAL(Parse("-includeconf"), "-includeconf cannot be used from commandline; -includeconf=\"\"");
379  BOOST_CHECK_EQUAL(Parse("-includeconf=file"), "-includeconf cannot be used from commandline; -includeconf=\"file\"");
380 }
381 
382 BOOST_AUTO_TEST_CASE(util_ParseParameters)
383 {
384  TestArgsManager testArgs;
385  const auto a = std::make_pair("-a", ArgsManager::ALLOW_ANY);
386  const auto b = std::make_pair("-b", ArgsManager::ALLOW_ANY);
387  const auto ccc = std::make_pair("-ccc", ArgsManager::ALLOW_ANY);
388  const auto d = std::make_pair("-d", ArgsManager::ALLOW_ANY);
389 
390  const char *argv_test[] = {"-ignored", "-a", "-b", "-ccc=argument", "-ccc=multiple", "f", "-d=e"};
391 
392  std::string error;
393  LOCK(testArgs.cs_args);
394  testArgs.SetupArgs({a, b, ccc, d});
395  BOOST_CHECK(testArgs.ParseParameters(0, (char**)argv_test, error));
396  BOOST_CHECK(testArgs.m_settings.command_line_options.empty() && testArgs.m_settings.ro_config.empty());
397 
398  BOOST_CHECK(testArgs.ParseParameters(1, (char**)argv_test, error));
399  BOOST_CHECK(testArgs.m_settings.command_line_options.empty() && testArgs.m_settings.ro_config.empty());
400 
401  BOOST_CHECK(testArgs.ParseParameters(7, (char**)argv_test, error));
402  // expectation: -ignored is ignored (program name argument),
403  // -a, -b and -ccc end up in map, -d ignored because it is after
404  // a non-option argument (non-GNU option parsing)
405  BOOST_CHECK(testArgs.m_settings.command_line_options.size() == 3 && testArgs.m_settings.ro_config.empty());
406  BOOST_CHECK(testArgs.IsArgSet("-a") && testArgs.IsArgSet("-b") && testArgs.IsArgSet("-ccc")
407  && !testArgs.IsArgSet("f") && !testArgs.IsArgSet("-d"));
408  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")
409  && !testArgs.m_settings.command_line_options.count("f") && !testArgs.m_settings.command_line_options.count("d"));
410 
411  BOOST_CHECK(testArgs.m_settings.command_line_options["a"].size() == 1);
412  BOOST_CHECK(testArgs.m_settings.command_line_options["a"].front().get_str() == "");
413  BOOST_CHECK(testArgs.m_settings.command_line_options["ccc"].size() == 2);
414  BOOST_CHECK(testArgs.m_settings.command_line_options["ccc"].front().get_str() == "argument");
415  BOOST_CHECK(testArgs.m_settings.command_line_options["ccc"].back().get_str() == "multiple");
416  BOOST_CHECK(testArgs.GetArgs("-ccc").size() == 2);
417 }
418 
419 BOOST_AUTO_TEST_CASE(util_ParseInvalidParameters)
420 {
421  TestArgsManager test;
422  test.SetupArgs({{"-registered", ArgsManager::ALLOW_ANY}});
423 
424  const char* argv[] = {"ignored", "-registered"};
425  std::string error;
426  BOOST_CHECK(test.ParseParameters(2, (char**)argv, error));
428 
429  argv[1] = "-unregistered";
430  BOOST_CHECK(!test.ParseParameters(2, (char**)argv, error));
431  BOOST_CHECK_EQUAL(error, "Invalid parameter -unregistered");
432 
433  // Make sure registered parameters prefixed with a chain name trigger errors.
434  // (Previously, they were accepted and ignored.)
435  argv[1] = "-test.registered";
436  BOOST_CHECK(!test.ParseParameters(2, (char**)argv, error));
437  BOOST_CHECK_EQUAL(error, "Invalid parameter -test.registered");
438 }
439 
440 static void TestParse(const std::string& str, bool expected_bool, int64_t expected_int)
441 {
442  TestArgsManager test;
443  test.SetupArgs({{"-value", ArgsManager::ALLOW_ANY}});
444  std::string arg = "-value=" + str;
445  const char* argv[] = {"ignored", arg.c_str()};
446  std::string error;
447  BOOST_CHECK(test.ParseParameters(2, (char**)argv, error));
448  BOOST_CHECK_EQUAL(test.GetBoolArg("-value", false), expected_bool);
449  BOOST_CHECK_EQUAL(test.GetBoolArg("-value", true), expected_bool);
450  BOOST_CHECK_EQUAL(test.GetIntArg("-value", 99998), expected_int);
451  BOOST_CHECK_EQUAL(test.GetIntArg("-value", 99999), expected_int);
452 }
453 
454 // Test bool and int parsing.
455 BOOST_AUTO_TEST_CASE(util_ArgParsing)
456 {
457  // Some of these cases could be ambiguous or surprising to users, and might
458  // be worth triggering errors or warnings in the future. But for now basic
459  // test coverage is useful to avoid breaking backwards compatibility
460  // unintentionally.
461  TestParse("", true, 0);
462  TestParse(" ", false, 0);
463  TestParse("0", false, 0);
464  TestParse("0 ", false, 0);
465  TestParse(" 0", false, 0);
466  TestParse("+0", false, 0);
467  TestParse("-0", false, 0);
468  TestParse("5", true, 5);
469  TestParse("5 ", true, 5);
470  TestParse(" 5", true, 5);
471  TestParse("+5", true, 5);
472  TestParse("-5", true, -5);
473  TestParse("0 5", false, 0);
474  TestParse("5 0", true, 5);
475  TestParse("050", true, 50);
476  TestParse("0.", false, 0);
477  TestParse("5.", true, 5);
478  TestParse("0.0", false, 0);
479  TestParse("0.5", false, 0);
480  TestParse("5.0", true, 5);
481  TestParse("5.5", true, 5);
482  TestParse("x", false, 0);
483  TestParse("x0", false, 0);
484  TestParse("x5", false, 0);
485  TestParse("0x", false, 0);
486  TestParse("5x", true, 5);
487  TestParse("0x5", false, 0);
488  TestParse("false", false, 0);
489  TestParse("true", false, 0);
490  TestParse("yes", false, 0);
491  TestParse("no", false, 0);
492 }
493 
494 BOOST_AUTO_TEST_CASE(util_GetBoolArg)
495 {
496  TestArgsManager testArgs;
497  const auto a = std::make_pair("-a", ArgsManager::ALLOW_ANY);
498  const auto b = std::make_pair("-b", ArgsManager::ALLOW_ANY);
499  const auto c = std::make_pair("-c", ArgsManager::ALLOW_ANY);
500  const auto d = std::make_pair("-d", ArgsManager::ALLOW_ANY);
501  const auto e = std::make_pair("-e", ArgsManager::ALLOW_ANY);
502  const auto f = std::make_pair("-f", ArgsManager::ALLOW_ANY);
503 
504  const char *argv_test[] = {
505  "ignored", "-a", "-nob", "-c=0", "-d=1", "-e=false", "-f=true"};
506  std::string error;
507  LOCK(testArgs.cs_args);
508  testArgs.SetupArgs({a, b, c, d, e, f});
509  BOOST_CHECK(testArgs.ParseParameters(7, (char**)argv_test, error));
510 
511  // Each letter should be set.
512  for (const char opt : "abcdef")
513  BOOST_CHECK(testArgs.IsArgSet({'-', opt}) || !opt);
514 
515  // Nothing else should be in the map
516  BOOST_CHECK(testArgs.m_settings.command_line_options.size() == 6 &&
517  testArgs.m_settings.ro_config.empty());
518 
519  // The -no prefix should get stripped on the way in.
520  BOOST_CHECK(!testArgs.IsArgSet("-nob"));
521 
522  // The -b option is flagged as negated, and nothing else is
523  BOOST_CHECK(testArgs.IsArgNegated("-b"));
524  BOOST_CHECK(!testArgs.IsArgNegated("-a"));
525 
526  // Check expected values.
527  BOOST_CHECK(testArgs.GetBoolArg("-a", false) == true);
528  BOOST_CHECK(testArgs.GetBoolArg("-b", true) == false);
529  BOOST_CHECK(testArgs.GetBoolArg("-c", true) == false);
530  BOOST_CHECK(testArgs.GetBoolArg("-d", false) == true);
531  BOOST_CHECK(testArgs.GetBoolArg("-e", true) == false);
532  BOOST_CHECK(testArgs.GetBoolArg("-f", true) == false);
533 }
534 
535 BOOST_AUTO_TEST_CASE(util_GetBoolArgEdgeCases)
536 {
537  // Test some awful edge cases that hopefully no user will ever exercise.
538  TestArgsManager testArgs;
539 
540  // Params test
541  const auto foo = std::make_pair("-foo", ArgsManager::ALLOW_ANY);
542  const auto bar = std::make_pair("-bar", ArgsManager::ALLOW_ANY);
543  const char *argv_test[] = {"ignored", "-nofoo", "-foo", "-nobar=0"};
544  testArgs.SetupArgs({foo, bar});
545  std::string error;
546  BOOST_CHECK(testArgs.ParseParameters(4, (char**)argv_test, error));
547 
548  // This was passed twice, second one overrides the negative setting.
549  BOOST_CHECK(!testArgs.IsArgNegated("-foo"));
550  BOOST_CHECK(testArgs.GetArg("-foo", "xxx") == "");
551 
552  // A double negative is a positive, and not marked as negated.
553  BOOST_CHECK(!testArgs.IsArgNegated("-bar"));
554  BOOST_CHECK(testArgs.GetArg("-bar", "xxx") == "1");
555 
556  // Config test
557  const char *conf_test = "nofoo=1\nfoo=1\nnobar=0\n";
558  BOOST_CHECK(testArgs.ParseParameters(1, (char**)argv_test, error));
559  testArgs.ReadConfigString(conf_test);
560 
561  // This was passed twice, second one overrides the negative setting,
562  // and the value.
563  BOOST_CHECK(!testArgs.IsArgNegated("-foo"));
564  BOOST_CHECK(testArgs.GetArg("-foo", "xxx") == "1");
565 
566  // A double negative is a positive, and does not count as negated.
567  BOOST_CHECK(!testArgs.IsArgNegated("-bar"));
568  BOOST_CHECK(testArgs.GetArg("-bar", "xxx") == "1");
569 
570  // Combined test
571  const char *combo_test_args[] = {"ignored", "-nofoo", "-bar"};
572  const char *combo_test_conf = "foo=1\nnobar=1\n";
573  BOOST_CHECK(testArgs.ParseParameters(3, (char**)combo_test_args, error));
574  testArgs.ReadConfigString(combo_test_conf);
575 
576  // Command line overrides, but doesn't erase old setting
577  BOOST_CHECK(testArgs.IsArgNegated("-foo"));
578  BOOST_CHECK(testArgs.GetArg("-foo", "xxx") == "0");
579  BOOST_CHECK(testArgs.GetArgs("-foo").size() == 0);
580 
581  // Command line overrides, but doesn't erase old setting
582  BOOST_CHECK(!testArgs.IsArgNegated("-bar"));
583  BOOST_CHECK(testArgs.GetArg("-bar", "xxx") == "");
584  BOOST_CHECK(testArgs.GetArgs("-bar").size() == 1
585  && testArgs.GetArgs("-bar").front() == "");
586 }
587 
588 BOOST_AUTO_TEST_CASE(util_ReadConfigStream)
589 {
590  const char *str_config =
591  "a=\n"
592  "b=1\n"
593  "ccc=argument\n"
594  "ccc=multiple\n"
595  "d=e\n"
596  "nofff=1\n"
597  "noggg=0\n"
598  "h=1\n"
599  "noh=1\n"
600  "noi=1\n"
601  "i=1\n"
602  "sec1.ccc=extend1\n"
603  "\n"
604  "[sec1]\n"
605  "ccc=extend2\n"
606  "d=eee\n"
607  "h=1\n"
608  "[sec2]\n"
609  "ccc=extend3\n"
610  "iii=2\n";
611 
612  TestArgsManager test_args;
613  LOCK(test_args.cs_args);
614  const auto a = std::make_pair("-a", ArgsManager::ALLOW_ANY);
615  const auto b = std::make_pair("-b", ArgsManager::ALLOW_ANY);
616  const auto ccc = std::make_pair("-ccc", ArgsManager::ALLOW_ANY);
617  const auto d = std::make_pair("-d", ArgsManager::ALLOW_ANY);
618  const auto e = std::make_pair("-e", ArgsManager::ALLOW_ANY);
619  const auto fff = std::make_pair("-fff", ArgsManager::ALLOW_ANY);
620  const auto ggg = std::make_pair("-ggg", ArgsManager::ALLOW_ANY);
621  const auto h = std::make_pair("-h", ArgsManager::ALLOW_ANY);
622  const auto i = std::make_pair("-i", ArgsManager::ALLOW_ANY);
623  const auto iii = std::make_pair("-iii", ArgsManager::ALLOW_ANY);
624  test_args.SetupArgs({a, b, ccc, d, e, fff, ggg, h, i, iii});
625 
626  test_args.ReadConfigString(str_config);
627  // expectation: a, b, ccc, d, fff, ggg, h, i end up in map
628  // so do sec1.ccc, sec1.d, sec1.h, sec2.ccc, sec2.iii
629 
630  BOOST_CHECK(test_args.m_settings.command_line_options.empty());
631  BOOST_CHECK(test_args.m_settings.ro_config.size() == 3);
632  BOOST_CHECK(test_args.m_settings.ro_config[""].size() == 8);
633  BOOST_CHECK(test_args.m_settings.ro_config["sec1"].size() == 3);
634  BOOST_CHECK(test_args.m_settings.ro_config["sec2"].size() == 2);
635 
636  BOOST_CHECK(test_args.m_settings.ro_config[""].count("a"));
637  BOOST_CHECK(test_args.m_settings.ro_config[""].count("b"));
638  BOOST_CHECK(test_args.m_settings.ro_config[""].count("ccc"));
639  BOOST_CHECK(test_args.m_settings.ro_config[""].count("d"));
640  BOOST_CHECK(test_args.m_settings.ro_config[""].count("fff"));
641  BOOST_CHECK(test_args.m_settings.ro_config[""].count("ggg"));
642  BOOST_CHECK(test_args.m_settings.ro_config[""].count("h"));
643  BOOST_CHECK(test_args.m_settings.ro_config[""].count("i"));
644  BOOST_CHECK(test_args.m_settings.ro_config["sec1"].count("ccc"));
645  BOOST_CHECK(test_args.m_settings.ro_config["sec1"].count("h"));
646  BOOST_CHECK(test_args.m_settings.ro_config["sec2"].count("ccc"));
647  BOOST_CHECK(test_args.m_settings.ro_config["sec2"].count("iii"));
648 
649  BOOST_CHECK(test_args.IsArgSet("-a"));
650  BOOST_CHECK(test_args.IsArgSet("-b"));
651  BOOST_CHECK(test_args.IsArgSet("-ccc"));
652  BOOST_CHECK(test_args.IsArgSet("-d"));
653  BOOST_CHECK(test_args.IsArgSet("-fff"));
654  BOOST_CHECK(test_args.IsArgSet("-ggg"));
655  BOOST_CHECK(test_args.IsArgSet("-h"));
656  BOOST_CHECK(test_args.IsArgSet("-i"));
657  BOOST_CHECK(!test_args.IsArgSet("-zzz"));
658  BOOST_CHECK(!test_args.IsArgSet("-iii"));
659 
660  BOOST_CHECK_EQUAL(test_args.GetArg("-a", "xxx"), "");
661  BOOST_CHECK_EQUAL(test_args.GetArg("-b", "xxx"), "1");
662  BOOST_CHECK_EQUAL(test_args.GetArg("-ccc", "xxx"), "argument");
663  BOOST_CHECK_EQUAL(test_args.GetArg("-d", "xxx"), "e");
664  BOOST_CHECK_EQUAL(test_args.GetArg("-fff", "xxx"), "0");
665  BOOST_CHECK_EQUAL(test_args.GetArg("-ggg", "xxx"), "1");
666  BOOST_CHECK_EQUAL(test_args.GetArg("-h", "xxx"), "0");
667  BOOST_CHECK_EQUAL(test_args.GetArg("-i", "xxx"), "1");
668  BOOST_CHECK_EQUAL(test_args.GetArg("-zzz", "xxx"), "xxx");
669  BOOST_CHECK_EQUAL(test_args.GetArg("-iii", "xxx"), "xxx");
670 
671  for (const bool def : {false, true}) {
672  BOOST_CHECK(test_args.GetBoolArg("-a", def));
673  BOOST_CHECK(test_args.GetBoolArg("-b", def));
674  BOOST_CHECK(!test_args.GetBoolArg("-ccc", def));
675  BOOST_CHECK(!test_args.GetBoolArg("-d", def));
676  BOOST_CHECK(!test_args.GetBoolArg("-fff", def));
677  BOOST_CHECK(test_args.GetBoolArg("-ggg", def));
678  BOOST_CHECK(!test_args.GetBoolArg("-h", def));
679  BOOST_CHECK(test_args.GetBoolArg("-i", def));
680  BOOST_CHECK(test_args.GetBoolArg("-zzz", def) == def);
681  BOOST_CHECK(test_args.GetBoolArg("-iii", def) == def);
682  }
683 
684  BOOST_CHECK(test_args.GetArgs("-a").size() == 1
685  && test_args.GetArgs("-a").front() == "");
686  BOOST_CHECK(test_args.GetArgs("-b").size() == 1
687  && test_args.GetArgs("-b").front() == "1");
688  BOOST_CHECK(test_args.GetArgs("-ccc").size() == 2
689  && test_args.GetArgs("-ccc").front() == "argument"
690  && test_args.GetArgs("-ccc").back() == "multiple");
691  BOOST_CHECK(test_args.GetArgs("-fff").size() == 0);
692  BOOST_CHECK(test_args.GetArgs("-nofff").size() == 0);
693  BOOST_CHECK(test_args.GetArgs("-ggg").size() == 1
694  && test_args.GetArgs("-ggg").front() == "1");
695  BOOST_CHECK(test_args.GetArgs("-noggg").size() == 0);
696  BOOST_CHECK(test_args.GetArgs("-h").size() == 0);
697  BOOST_CHECK(test_args.GetArgs("-noh").size() == 0);
698  BOOST_CHECK(test_args.GetArgs("-i").size() == 1
699  && test_args.GetArgs("-i").front() == "1");
700  BOOST_CHECK(test_args.GetArgs("-noi").size() == 0);
701  BOOST_CHECK(test_args.GetArgs("-zzz").size() == 0);
702 
703  BOOST_CHECK(!test_args.IsArgNegated("-a"));
704  BOOST_CHECK(!test_args.IsArgNegated("-b"));
705  BOOST_CHECK(!test_args.IsArgNegated("-ccc"));
706  BOOST_CHECK(!test_args.IsArgNegated("-d"));
707  BOOST_CHECK(test_args.IsArgNegated("-fff"));
708  BOOST_CHECK(!test_args.IsArgNegated("-ggg"));
709  BOOST_CHECK(test_args.IsArgNegated("-h")); // last setting takes precedence
710  BOOST_CHECK(!test_args.IsArgNegated("-i")); // last setting takes precedence
711  BOOST_CHECK(!test_args.IsArgNegated("-zzz"));
712 
713  // Test sections work
714  test_args.SelectConfigNetwork("sec1");
715 
716  // same as original
717  BOOST_CHECK_EQUAL(test_args.GetArg("-a", "xxx"), "");
718  BOOST_CHECK_EQUAL(test_args.GetArg("-b", "xxx"), "1");
719  BOOST_CHECK_EQUAL(test_args.GetArg("-fff", "xxx"), "0");
720  BOOST_CHECK_EQUAL(test_args.GetArg("-ggg", "xxx"), "1");
721  BOOST_CHECK_EQUAL(test_args.GetArg("-zzz", "xxx"), "xxx");
722  BOOST_CHECK_EQUAL(test_args.GetArg("-iii", "xxx"), "xxx");
723  // d is overridden
724  BOOST_CHECK(test_args.GetArg("-d", "xxx") == "eee");
725  // section-specific setting
726  BOOST_CHECK(test_args.GetArg("-h", "xxx") == "1");
727  // section takes priority for multiple values
728  BOOST_CHECK(test_args.GetArg("-ccc", "xxx") == "extend1");
729  // check multiple values works
730  const std::vector<std::string> sec1_ccc_expected = {"extend1","extend2","argument","multiple"};
731  const auto& sec1_ccc_res = test_args.GetArgs("-ccc");
732  BOOST_CHECK_EQUAL_COLLECTIONS(sec1_ccc_res.begin(), sec1_ccc_res.end(), sec1_ccc_expected.begin(), sec1_ccc_expected.end());
733 
734  test_args.SelectConfigNetwork("sec2");
735 
736  // same as original
737  BOOST_CHECK(test_args.GetArg("-a", "xxx") == "");
738  BOOST_CHECK(test_args.GetArg("-b", "xxx") == "1");
739  BOOST_CHECK(test_args.GetArg("-d", "xxx") == "e");
740  BOOST_CHECK(test_args.GetArg("-fff", "xxx") == "0");
741  BOOST_CHECK(test_args.GetArg("-ggg", "xxx") == "1");
742  BOOST_CHECK(test_args.GetArg("-zzz", "xxx") == "xxx");
743  BOOST_CHECK(test_args.GetArg("-h", "xxx") == "0");
744  // section-specific setting
745  BOOST_CHECK(test_args.GetArg("-iii", "xxx") == "2");
746  // section takes priority for multiple values
747  BOOST_CHECK(test_args.GetArg("-ccc", "xxx") == "extend3");
748  // check multiple values works
749  const std::vector<std::string> sec2_ccc_expected = {"extend3","argument","multiple"};
750  const auto& sec2_ccc_res = test_args.GetArgs("-ccc");
751  BOOST_CHECK_EQUAL_COLLECTIONS(sec2_ccc_res.begin(), sec2_ccc_res.end(), sec2_ccc_expected.begin(), sec2_ccc_expected.end());
752 
753  // Test section only options
754 
755  test_args.SetNetworkOnlyArg("-d");
756  test_args.SetNetworkOnlyArg("-ccc");
757  test_args.SetNetworkOnlyArg("-h");
758 
760  BOOST_CHECK(test_args.GetArg("-d", "xxx") == "e");
761  BOOST_CHECK(test_args.GetArgs("-ccc").size() == 2);
762  BOOST_CHECK(test_args.GetArg("-h", "xxx") == "0");
763 
764  test_args.SelectConfigNetwork("sec1");
765  BOOST_CHECK(test_args.GetArg("-d", "xxx") == "eee");
766  BOOST_CHECK(test_args.GetArgs("-d").size() == 1);
767  BOOST_CHECK(test_args.GetArgs("-ccc").size() == 2);
768  BOOST_CHECK(test_args.GetArg("-h", "xxx") == "1");
769 
770  test_args.SelectConfigNetwork("sec2");
771  BOOST_CHECK(test_args.GetArg("-d", "xxx") == "xxx");
772  BOOST_CHECK(test_args.GetArgs("-d").size() == 0);
773  BOOST_CHECK(test_args.GetArgs("-ccc").size() == 1);
774  BOOST_CHECK(test_args.GetArg("-h", "xxx") == "0");
775 }
776 
778 {
779  TestArgsManager testArgs;
780  LOCK(testArgs.cs_args);
781  testArgs.m_settings.command_line_options.clear();
782  testArgs.m_settings.command_line_options["strtest1"] = {"string..."};
783  // strtest2 undefined on purpose
784  testArgs.m_settings.command_line_options["inttest1"] = {"12345"};
785  testArgs.m_settings.command_line_options["inttest2"] = {"81985529216486895"};
786  // inttest3 undefined on purpose
787  testArgs.m_settings.command_line_options["booltest1"] = {""};
788  // booltest2 undefined on purpose
789  testArgs.m_settings.command_line_options["booltest3"] = {"0"};
790  testArgs.m_settings.command_line_options["booltest4"] = {"1"};
791 
792  // priorities
793  testArgs.m_settings.command_line_options["pritest1"] = {"a", "b"};
794  testArgs.m_settings.ro_config[""]["pritest2"] = {"a", "b"};
795  testArgs.m_settings.command_line_options["pritest3"] = {"a"};
796  testArgs.m_settings.ro_config[""]["pritest3"] = {"b"};
797  testArgs.m_settings.command_line_options["pritest4"] = {"a","b"};
798  testArgs.m_settings.ro_config[""]["pritest4"] = {"c","d"};
799 
800  BOOST_CHECK_EQUAL(testArgs.GetArg("strtest1", "default"), "string...");
801  BOOST_CHECK_EQUAL(testArgs.GetArg("strtest2", "default"), "default");
802  BOOST_CHECK_EQUAL(testArgs.GetIntArg("inttest1", -1), 12345);
803  BOOST_CHECK_EQUAL(testArgs.GetIntArg("inttest2", -1), 81985529216486895LL);
804  BOOST_CHECK_EQUAL(testArgs.GetIntArg("inttest3", -1), -1);
805  BOOST_CHECK_EQUAL(testArgs.GetBoolArg("booltest1", false), true);
806  BOOST_CHECK_EQUAL(testArgs.GetBoolArg("booltest2", false), false);
807  BOOST_CHECK_EQUAL(testArgs.GetBoolArg("booltest3", false), false);
808  BOOST_CHECK_EQUAL(testArgs.GetBoolArg("booltest4", false), true);
809 
810  BOOST_CHECK_EQUAL(testArgs.GetArg("pritest1", "default"), "b");
811  BOOST_CHECK_EQUAL(testArgs.GetArg("pritest2", "default"), "a");
812  BOOST_CHECK_EQUAL(testArgs.GetArg("pritest3", "default"), "a");
813  BOOST_CHECK_EQUAL(testArgs.GetArg("pritest4", "default"), "b");
814 }
815 
816 BOOST_AUTO_TEST_CASE(util_GetChainName)
817 {
818  TestArgsManager test_args;
819  const auto testnet = std::make_pair("-testnet", ArgsManager::ALLOW_ANY);
820  const auto regtest = std::make_pair("-regtest", ArgsManager::ALLOW_ANY);
821  test_args.SetupArgs({testnet, regtest});
822 
823  const char* argv_testnet[] = {"cmd", "-testnet"};
824  const char* argv_regtest[] = {"cmd", "-regtest"};
825  const char* argv_test_no_reg[] = {"cmd", "-testnet", "-noregtest"};
826  const char* argv_both[] = {"cmd", "-testnet", "-regtest"};
827 
828  // equivalent to "-testnet"
829  // regtest in testnet section is ignored
830  const char* testnetconf = "testnet=1\nregtest=0\n[test]\nregtest=1";
831  std::string error;
832 
833  BOOST_CHECK(test_args.ParseParameters(0, (char**)argv_testnet, error));
834  BOOST_CHECK_EQUAL(test_args.GetChainName(), "main");
835 
836  BOOST_CHECK(test_args.ParseParameters(2, (char**)argv_testnet, error));
837  BOOST_CHECK_EQUAL(test_args.GetChainName(), "test");
838 
839  BOOST_CHECK(test_args.ParseParameters(2, (char**)argv_regtest, error));
840  BOOST_CHECK_EQUAL(test_args.GetChainName(), "regtest");
841 
842  BOOST_CHECK(test_args.ParseParameters(3, (char**)argv_test_no_reg, error));
843  BOOST_CHECK_EQUAL(test_args.GetChainName(), "test");
844 
845  BOOST_CHECK(test_args.ParseParameters(3, (char**)argv_both, error));
846  BOOST_CHECK_THROW(test_args.GetChainName(), std::runtime_error);
847 
848  BOOST_CHECK(test_args.ParseParameters(0, (char**)argv_testnet, error));
849  test_args.ReadConfigString(testnetconf);
850  BOOST_CHECK_EQUAL(test_args.GetChainName(), "test");
851 
852  BOOST_CHECK(test_args.ParseParameters(2, (char**)argv_testnet, error));
853  test_args.ReadConfigString(testnetconf);
854  BOOST_CHECK_EQUAL(test_args.GetChainName(), "test");
855 
856  BOOST_CHECK(test_args.ParseParameters(2, (char**)argv_regtest, error));
857  test_args.ReadConfigString(testnetconf);
858  BOOST_CHECK_THROW(test_args.GetChainName(), std::runtime_error);
859 
860  BOOST_CHECK(test_args.ParseParameters(3, (char**)argv_test_no_reg, error));
861  test_args.ReadConfigString(testnetconf);
862  BOOST_CHECK_EQUAL(test_args.GetChainName(), "test");
863 
864  BOOST_CHECK(test_args.ParseParameters(3, (char**)argv_both, error));
865  test_args.ReadConfigString(testnetconf);
866  BOOST_CHECK_THROW(test_args.GetChainName(), std::runtime_error);
867 
868  // check setting the network to test (and thus making
869  // [test] regtest=1 potentially relevant) doesn't break things
870  test_args.SelectConfigNetwork("test");
871 
872  BOOST_CHECK(test_args.ParseParameters(0, (char**)argv_testnet, error));
873  test_args.ReadConfigString(testnetconf);
874  BOOST_CHECK_EQUAL(test_args.GetChainName(), "test");
875 
876  BOOST_CHECK(test_args.ParseParameters(2, (char**)argv_testnet, error));
877  test_args.ReadConfigString(testnetconf);
878  BOOST_CHECK_EQUAL(test_args.GetChainName(), "test");
879 
880  BOOST_CHECK(test_args.ParseParameters(2, (char**)argv_regtest, error));
881  test_args.ReadConfigString(testnetconf);
882  BOOST_CHECK_THROW(test_args.GetChainName(), std::runtime_error);
883 
884  BOOST_CHECK(test_args.ParseParameters(2, (char**)argv_test_no_reg, error));
885  test_args.ReadConfigString(testnetconf);
886  BOOST_CHECK_EQUAL(test_args.GetChainName(), "test");
887 
888  BOOST_CHECK(test_args.ParseParameters(3, (char**)argv_both, error));
889  test_args.ReadConfigString(testnetconf);
890  BOOST_CHECK_THROW(test_args.GetChainName(), std::runtime_error);
891 }
892 
893 // Test different ways settings can be merged, and verify results. This test can
894 // be used to confirm that updates to settings code don't change behavior
895 // unintentionally.
896 //
897 // The test covers:
898 //
899 // - Combining different setting actions. Possible actions are: configuring a
900 // setting, negating a setting (adding "-no" prefix), and configuring/negating
901 // settings in a network section (adding "main." or "test." prefixes).
902 //
903 // - Combining settings from command line arguments and a config file.
904 //
905 // - Combining SoftSet and ForceSet calls.
906 //
907 // - Testing "main" and "test" network values to make sure settings from network
908 // sections are applied and to check for mainnet-specific behaviors like
909 // inheriting settings from the default section.
910 //
911 // - Testing network-specific settings like "-wallet", that may be ignored
912 // outside a network section, and non-network specific settings like "-server"
913 // that aren't sensitive to the network.
914 //
918  static constexpr int MAX_ACTIONS = 3;
919 
920  enum Action { NONE, SET, NEGATE, SECTION_SET, SECTION_NEGATE };
921  using ActionList = Action[MAX_ACTIONS];
922 
924  template <typename Fn>
925  void ForEachMergeSetup(Fn&& fn)
926  {
927  ActionList arg_actions = {};
928  // command_line_options do not have sections. Only iterate over SET and NEGATE
929  ForEachNoDup(arg_actions, SET, NEGATE, [&] {
930  ActionList conf_actions = {};
931  ForEachNoDup(conf_actions, SET, SECTION_NEGATE, [&] {
932  for (bool soft_set : {false, true}) {
933  for (bool force_set : {false, true}) {
934  for (const std::string& section : {CBaseChainParams::MAIN, CBaseChainParams::TESTNET, CBaseChainParams::SIGNET}) {
935  for (const std::string& network : {CBaseChainParams::MAIN, CBaseChainParams::TESTNET, CBaseChainParams::SIGNET}) {
936  for (bool net_specific : {false, true}) {
937  fn(arg_actions, conf_actions, soft_set, force_set, section, network, net_specific);
938  }
939  }
940  }
941  }
942  }
943  });
944  });
945  }
946 
948  std::vector<std::string> GetValues(const ActionList& actions,
949  const std::string& section,
950  const std::string& name,
951  const std::string& value_prefix)
952  {
953  std::vector<std::string> values;
954  int suffix = 0;
955  for (Action action : actions) {
956  if (action == NONE) break;
957  std::string prefix;
958  if (action == SECTION_SET || action == SECTION_NEGATE) prefix = section + ".";
959  if (action == SET || action == SECTION_SET) {
960  for (int i = 0; i < 2; ++i) {
961  values.push_back(prefix + name + "=" + value_prefix + ToString(++suffix));
962  }
963  }
964  if (action == NEGATE || action == SECTION_NEGATE) {
965  values.push_back(prefix + "no" + name + "=1");
966  }
967  }
968  return values;
969  }
970 };
971 
972 // Regression test covering different ways config settings can be merged. The
973 // test parses and merges settings, representing the results as strings that get
974 // compared against an expected hash. To debug, the result strings can be dumped
975 // to a file (see comments below).
977 {
978  CHash256 out_sha;
979  FILE* out_file = nullptr;
980  if (const char* out_path = getenv("ARGS_MERGE_TEST_OUT")) {
981  out_file = fsbridge::fopen(out_path, "w");
982  if (!out_file) throw std::system_error(errno, std::generic_category(), "fopen failed");
983  }
984 
985  ForEachMergeSetup([&](const ActionList& arg_actions, const ActionList& conf_actions, bool soft_set, bool force_set,
986  const std::string& section, const std::string& network, bool net_specific) {
987  TestArgsManager parser;
988  LOCK(parser.cs_args);
989 
990  std::string desc = "net=";
991  desc += network;
992  parser.m_network = network;
993 
994  const std::string& name = net_specific ? "wallet" : "server";
995  const std::string key = "-" + name;
997  if (net_specific) parser.SetNetworkOnlyArg(key);
998 
999  auto args = GetValues(arg_actions, section, name, "a");
1000  std::vector<const char*> argv = {"ignored"};
1001  for (auto& arg : args) {
1002  arg.insert(0, "-");
1003  desc += " ";
1004  desc += arg;
1005  argv.push_back(arg.c_str());
1006  }
1007  std::string error;
1008  BOOST_CHECK(parser.ParseParameters(argv.size(), argv.data(), error));
1009  BOOST_CHECK_EQUAL(error, "");
1010 
1011  std::string conf;
1012  for (auto& conf_val : GetValues(conf_actions, section, name, "c")) {
1013  desc += " ";
1014  desc += conf_val;
1015  conf += conf_val;
1016  conf += "\n";
1017  }
1018  std::istringstream conf_stream(conf);
1019  BOOST_CHECK(parser.ReadConfigStream(conf_stream, "filepath", error));
1020  BOOST_CHECK_EQUAL(error, "");
1021 
1022  if (soft_set) {
1023  desc += " soft";
1024  parser.SoftSetArg(key, "soft1");
1025  parser.SoftSetArg(key, "soft2");
1026  }
1027 
1028  if (force_set) {
1029  desc += " force";
1030  parser.ForceSetArg(key, "force1");
1031  parser.ForceSetArg(key, "force2");
1032  }
1033 
1034  desc += " || ";
1035 
1036  if (!parser.IsArgSet(key)) {
1037  desc += "unset";
1038  BOOST_CHECK(!parser.IsArgNegated(key));
1039  BOOST_CHECK_EQUAL(parser.GetArg(key, "default"), "default");
1040  BOOST_CHECK(parser.GetArgs(key).empty());
1041  } else if (parser.IsArgNegated(key)) {
1042  desc += "negated";
1043  BOOST_CHECK_EQUAL(parser.GetArg(key, "default"), "0");
1044  BOOST_CHECK(parser.GetArgs(key).empty());
1045  } else {
1046  desc += parser.GetArg(key, "default");
1047  desc += " |";
1048  for (const auto& arg : parser.GetArgs(key)) {
1049  desc += " ";
1050  desc += arg;
1051  }
1052  }
1053 
1054  std::set<std::string> ignored = parser.GetUnsuitableSectionOnlyArgs();
1055  if (!ignored.empty()) {
1056  desc += " | ignored";
1057  for (const auto& arg : ignored) {
1058  desc += " ";
1059  desc += arg;
1060  }
1061  }
1062 
1063  desc += "\n";
1064 
1065  out_sha.Write(MakeUCharSpan(desc));
1066  if (out_file) {
1067  BOOST_REQUIRE(fwrite(desc.data(), 1, desc.size(), out_file) == desc.size());
1068  }
1069  });
1070 
1071  if (out_file) {
1072  if (fclose(out_file)) throw std::system_error(errno, std::generic_category(), "fclose failed");
1073  out_file = nullptr;
1074  }
1075 
1076  unsigned char out_sha_bytes[CSHA256::OUTPUT_SIZE];
1077  out_sha.Finalize(out_sha_bytes);
1078  std::string out_sha_hex = HexStr(out_sha_bytes);
1079 
1080  // If check below fails, should manually dump the results with:
1081  //
1082  // ARGS_MERGE_TEST_OUT=results.txt ./test_bitcoin --run_test=util_tests/util_ArgsMerge
1083  //
1084  // And verify diff against previous results to make sure the changes are expected.
1085  //
1086  // Results file is formatted like:
1087  //
1088  // <input> || <IsArgSet/IsArgNegated/GetArg output> | <GetArgs output> | <GetUnsuitable output>
1089  BOOST_CHECK_EQUAL(out_sha_hex, "d1e436c1cd510d0ec44d5205d4b4e3bee6387d316e0075c58206cb16603f3d82");
1090 }
1091 
1092 // Similar test as above, but for ArgsManager::GetChainName function.
1094  static constexpr int MAX_ACTIONS = 2;
1095 
1096  enum Action { NONE, ENABLE_TEST, DISABLE_TEST, NEGATE_TEST, ENABLE_REG, DISABLE_REG, NEGATE_REG };
1097  using ActionList = Action[MAX_ACTIONS];
1098 
1100  template <typename Fn>
1101  void ForEachMergeSetup(Fn&& fn)
1102  {
1103  ActionList arg_actions = {};
1104  ForEachNoDup(arg_actions, ENABLE_TEST, NEGATE_REG, [&] {
1105  ActionList conf_actions = {};
1106  ForEachNoDup(conf_actions, ENABLE_TEST, NEGATE_REG, [&] { fn(arg_actions, conf_actions); });
1107  });
1108  }
1109 };
1110 
1112 {
1113  CHash256 out_sha;
1114  FILE* out_file = nullptr;
1115  if (const char* out_path = getenv("CHAIN_MERGE_TEST_OUT")) {
1116  out_file = fsbridge::fopen(out_path, "w");
1117  if (!out_file) throw std::system_error(errno, std::generic_category(), "fopen failed");
1118  }
1119 
1120  ForEachMergeSetup([&](const ActionList& arg_actions, const ActionList& conf_actions) {
1121  TestArgsManager parser;
1122  LOCK(parser.cs_args);
1123  parser.AddArg("-regtest", "regtest", ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
1124  parser.AddArg("-testnet", "testnet", ArgsManager::ALLOW_ANY, OptionsCategory::OPTIONS);
1125 
1126  auto arg = [](Action action) { return action == ENABLE_TEST ? "-testnet=1" :
1127  action == DISABLE_TEST ? "-testnet=0" :
1128  action == NEGATE_TEST ? "-notestnet=1" :
1129  action == ENABLE_REG ? "-regtest=1" :
1130  action == DISABLE_REG ? "-regtest=0" :
1131  action == NEGATE_REG ? "-noregtest=1" : nullptr; };
1132 
1133  std::string desc;
1134  std::vector<const char*> argv = {"ignored"};
1135  for (Action action : arg_actions) {
1136  const char* argstr = arg(action);
1137  if (!argstr) break;
1138  argv.push_back(argstr);
1139  desc += " ";
1140  desc += argv.back();
1141  }
1142  std::string error;
1143  BOOST_CHECK(parser.ParseParameters(argv.size(), argv.data(), error));
1144  BOOST_CHECK_EQUAL(error, "");
1145 
1146  std::string conf;
1147  for (Action action : conf_actions) {
1148  const char* argstr = arg(action);
1149  if (!argstr) break;
1150  desc += " ";
1151  desc += argstr + 1;
1152  conf += argstr + 1;
1153  conf += "\n";
1154  }
1155  std::istringstream conf_stream(conf);
1156  BOOST_CHECK(parser.ReadConfigStream(conf_stream, "filepath", error));
1157  BOOST_CHECK_EQUAL(error, "");
1158 
1159  desc += " || ";
1160  try {
1161  desc += parser.GetChainName();
1162  } catch (const std::runtime_error& e) {
1163  desc += "error: ";
1164  desc += e.what();
1165  }
1166  desc += "\n";
1167 
1168  out_sha.Write(MakeUCharSpan(desc));
1169  if (out_file) {
1170  BOOST_REQUIRE(fwrite(desc.data(), 1, desc.size(), out_file) == desc.size());
1171  }
1172  });
1173 
1174  if (out_file) {
1175  if (fclose(out_file)) throw std::system_error(errno, std::generic_category(), "fclose failed");
1176  out_file = nullptr;
1177  }
1178 
1179  unsigned char out_sha_bytes[CSHA256::OUTPUT_SIZE];
1180  out_sha.Finalize(out_sha_bytes);
1181  std::string out_sha_hex = HexStr(out_sha_bytes);
1182 
1183  // If check below fails, should manually dump the results with:
1184  //
1185  // CHAIN_MERGE_TEST_OUT=results.txt ./test_bitcoin --run_test=util_tests/util_ChainMerge
1186  //
1187  // And verify diff against previous results to make sure the changes are expected.
1188  //
1189  // Results file is formatted like:
1190  //
1191  // <input> || <output>
1192  BOOST_CHECK_EQUAL(out_sha_hex, "f263493e300023b6509963887444c41386f44b63bc30047eb8402e8c1144854c");
1193 }
1194 
1195 BOOST_AUTO_TEST_CASE(util_ReadWriteSettings)
1196 {
1197  // Test writing setting.
1198  TestArgsManager args1;
1199  args1.ForceSetArg("-datadir", fs::PathToString(m_path_root));
1200  args1.LockSettings([&](util::Settings& settings) { settings.rw_settings["name"] = "value"; });
1201  args1.WriteSettingsFile();
1202 
1203  // Test reading setting.
1204  TestArgsManager args2;
1205  args2.ForceSetArg("-datadir", fs::PathToString(m_path_root));
1206  args2.ReadSettingsFile();
1207  args2.LockSettings([&](util::Settings& settings) { BOOST_CHECK_EQUAL(settings.rw_settings["name"].get_str(), "value"); });
1208 
1209  // Test error logging, and remove previously written setting.
1210  {
1211  ASSERT_DEBUG_LOG("Failed renaming settings file");
1212  fs::remove(args1.GetDataDirBase() / "settings.json");
1213  fs::create_directory(args1.GetDataDirBase() / "settings.json");
1214  args2.WriteSettingsFile();
1215  fs::remove(args1.GetDataDirBase() / "settings.json");
1216  }
1217 }
1218 
1219 BOOST_AUTO_TEST_CASE(util_FormatMoney)
1220 {
1221  BOOST_CHECK_EQUAL(FormatMoney(0), "0.00");
1222  BOOST_CHECK_EQUAL(FormatMoney((COIN/10000)*123456789), "12345.6789");
1223  BOOST_CHECK_EQUAL(FormatMoney(-COIN), "-1.00");
1224 
1225  BOOST_CHECK_EQUAL(FormatMoney(COIN*100000000), "100000000.00");
1226  BOOST_CHECK_EQUAL(FormatMoney(COIN*10000000), "10000000.00");
1227  BOOST_CHECK_EQUAL(FormatMoney(COIN*1000000), "1000000.00");
1228  BOOST_CHECK_EQUAL(FormatMoney(COIN*100000), "100000.00");
1229  BOOST_CHECK_EQUAL(FormatMoney(COIN*10000), "10000.00");
1230  BOOST_CHECK_EQUAL(FormatMoney(COIN*1000), "1000.00");
1231  BOOST_CHECK_EQUAL(FormatMoney(COIN*100), "100.00");
1232  BOOST_CHECK_EQUAL(FormatMoney(COIN*10), "10.00");
1234  BOOST_CHECK_EQUAL(FormatMoney(COIN/10), "0.10");
1235  BOOST_CHECK_EQUAL(FormatMoney(COIN/100), "0.01");
1236  BOOST_CHECK_EQUAL(FormatMoney(COIN/1000), "0.001");
1237  BOOST_CHECK_EQUAL(FormatMoney(COIN/10000), "0.0001");
1238  BOOST_CHECK_EQUAL(FormatMoney(COIN/100000), "0.00001");
1239  BOOST_CHECK_EQUAL(FormatMoney(COIN/1000000), "0.000001");
1240  BOOST_CHECK_EQUAL(FormatMoney(COIN/10000000), "0.0000001");
1241  BOOST_CHECK_EQUAL(FormatMoney(COIN/100000000), "0.00000001");
1242 
1243  BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::max()), "92233720368.54775807");
1244  BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::max() - 1), "92233720368.54775806");
1245  BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::max() - 2), "92233720368.54775805");
1246  BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::max() - 3), "92233720368.54775804");
1247  // ...
1248  BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::min() + 3), "-92233720368.54775805");
1249  BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::min() + 2), "-92233720368.54775806");
1250  BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::min() + 1), "-92233720368.54775807");
1251  BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::min()), "-92233720368.54775808");
1252 }
1253 
1254 BOOST_AUTO_TEST_CASE(util_ParseMoney)
1255 {
1256  BOOST_CHECK_EQUAL(ParseMoney("0.0").value(), 0);
1257  BOOST_CHECK_EQUAL(ParseMoney(".").value(), 0);
1258  BOOST_CHECK_EQUAL(ParseMoney("0.").value(), 0);
1259  BOOST_CHECK_EQUAL(ParseMoney(".0").value(), 0);
1260  BOOST_CHECK_EQUAL(ParseMoney(".6789").value(), 6789'0000);
1261  BOOST_CHECK_EQUAL(ParseMoney("12345.").value(), COIN * 12345);
1262 
1263  BOOST_CHECK_EQUAL(ParseMoney("12345.6789").value(), (COIN/10000)*123456789);
1264 
1265  BOOST_CHECK_EQUAL(ParseMoney("10000000.00").value(), COIN*10000000);
1266  BOOST_CHECK_EQUAL(ParseMoney("1000000.00").value(), COIN*1000000);
1267  BOOST_CHECK_EQUAL(ParseMoney("100000.00").value(), COIN*100000);
1268  BOOST_CHECK_EQUAL(ParseMoney("10000.00").value(), COIN*10000);
1269  BOOST_CHECK_EQUAL(ParseMoney("1000.00").value(), COIN*1000);
1270  BOOST_CHECK_EQUAL(ParseMoney("100.00").value(), COIN*100);
1271  BOOST_CHECK_EQUAL(ParseMoney("10.00").value(), COIN*10);
1272  BOOST_CHECK_EQUAL(ParseMoney("1.00").value(), COIN);
1273  BOOST_CHECK_EQUAL(ParseMoney("1").value(), COIN);
1274  BOOST_CHECK_EQUAL(ParseMoney(" 1").value(), COIN);
1275  BOOST_CHECK_EQUAL(ParseMoney("1 ").value(), COIN);
1276  BOOST_CHECK_EQUAL(ParseMoney(" 1 ").value(), COIN);
1277  BOOST_CHECK_EQUAL(ParseMoney("0.1").value(), COIN/10);
1278  BOOST_CHECK_EQUAL(ParseMoney("0.01").value(), COIN/100);
1279  BOOST_CHECK_EQUAL(ParseMoney("0.001").value(), COIN/1000);
1280  BOOST_CHECK_EQUAL(ParseMoney("0.0001").value(), COIN/10000);
1281  BOOST_CHECK_EQUAL(ParseMoney("0.00001").value(), COIN/100000);
1282  BOOST_CHECK_EQUAL(ParseMoney("0.000001").value(), COIN/1000000);
1283  BOOST_CHECK_EQUAL(ParseMoney("0.0000001").value(), COIN/10000000);
1284  BOOST_CHECK_EQUAL(ParseMoney("0.00000001").value(), COIN/100000000);
1285  BOOST_CHECK_EQUAL(ParseMoney(" 0.00000001 ").value(), COIN/100000000);
1286  BOOST_CHECK_EQUAL(ParseMoney("0.00000001 ").value(), COIN/100000000);
1287  BOOST_CHECK_EQUAL(ParseMoney(" 0.00000001").value(), COIN/100000000);
1288 
1289  // Parsing amount that can not be represented should fail
1290  BOOST_CHECK(!ParseMoney("100000000.00"));
1291  BOOST_CHECK(!ParseMoney("0.000000001"));
1292 
1293  // Parsing empty string should fail
1294  BOOST_CHECK(!ParseMoney(""));
1295  BOOST_CHECK(!ParseMoney(" "));
1296  BOOST_CHECK(!ParseMoney(" "));
1297 
1298  // Parsing two numbers should fail
1299  BOOST_CHECK(!ParseMoney(".."));
1300  BOOST_CHECK(!ParseMoney("0..0"));
1301  BOOST_CHECK(!ParseMoney("1 2"));
1302  BOOST_CHECK(!ParseMoney(" 1 2 "));
1303  BOOST_CHECK(!ParseMoney(" 1.2 3 "));
1304  BOOST_CHECK(!ParseMoney(" 1 2.3 "));
1305 
1306  // Embedded whitespace should fail
1307  BOOST_CHECK(!ParseMoney(" -1 .2 "));
1308  BOOST_CHECK(!ParseMoney(" 1 .2 "));
1309  BOOST_CHECK(!ParseMoney(" +1 .2 "));
1310 
1311  // Attempted 63 bit overflow should fail
1312  BOOST_CHECK(!ParseMoney("92233720368.54775808"));
1313 
1314  // Parsing negative amounts must fail
1315  BOOST_CHECK(!ParseMoney("-1"));
1316 
1317  // Parsing strings with embedded NUL characters should fail
1318  BOOST_CHECK(!ParseMoney("\0-1"s));
1319  BOOST_CHECK(!ParseMoney(STRING_WITH_EMBEDDED_NULL_CHAR));
1320  BOOST_CHECK(!ParseMoney("1\0"s));
1321 }
1322 
1323 BOOST_AUTO_TEST_CASE(util_IsHex)
1324 {
1325  BOOST_CHECK(IsHex("00"));
1326  BOOST_CHECK(IsHex("00112233445566778899aabbccddeeffAABBCCDDEEFF"));
1327  BOOST_CHECK(IsHex("ff"));
1328  BOOST_CHECK(IsHex("FF"));
1329 
1330  BOOST_CHECK(!IsHex(""));
1331  BOOST_CHECK(!IsHex("0"));
1332  BOOST_CHECK(!IsHex("a"));
1333  BOOST_CHECK(!IsHex("eleven"));
1334  BOOST_CHECK(!IsHex("00xx00"));
1335  BOOST_CHECK(!IsHex("0x0000"));
1336 }
1337 
1338 BOOST_AUTO_TEST_CASE(util_IsHexNumber)
1339 {
1340  BOOST_CHECK(IsHexNumber("0x0"));
1341  BOOST_CHECK(IsHexNumber("0"));
1342  BOOST_CHECK(IsHexNumber("0x10"));
1343  BOOST_CHECK(IsHexNumber("10"));
1344  BOOST_CHECK(IsHexNumber("0xff"));
1345  BOOST_CHECK(IsHexNumber("ff"));
1346  BOOST_CHECK(IsHexNumber("0xFfa"));
1347  BOOST_CHECK(IsHexNumber("Ffa"));
1348  BOOST_CHECK(IsHexNumber("0x00112233445566778899aabbccddeeffAABBCCDDEEFF"));
1349  BOOST_CHECK(IsHexNumber("00112233445566778899aabbccddeeffAABBCCDDEEFF"));
1350 
1351  BOOST_CHECK(!IsHexNumber("")); // empty string not allowed
1352  BOOST_CHECK(!IsHexNumber("0x")); // empty string after prefix not allowed
1353  BOOST_CHECK(!IsHexNumber("0x0 ")); // no spaces at end,
1354  BOOST_CHECK(!IsHexNumber(" 0x0")); // or beginning,
1355  BOOST_CHECK(!IsHexNumber("0x 0")); // or middle,
1356  BOOST_CHECK(!IsHexNumber(" ")); // etc.
1357  BOOST_CHECK(!IsHexNumber("0x0ga")); // invalid character
1358  BOOST_CHECK(!IsHexNumber("x0")); // broken prefix
1359  BOOST_CHECK(!IsHexNumber("0x0x00")); // two prefixes not allowed
1360 
1361 }
1362 
1363 BOOST_AUTO_TEST_CASE(util_seed_insecure_rand)
1364 {
1365  SeedInsecureRand(SeedRand::ZEROS);
1366  for (int mod=2;mod<11;mod++)
1367  {
1368  int mask = 1;
1369  // Really rough binomial confidence approximation.
1370  int err = 30*10000./mod*sqrt((1./mod*(1-1./mod))/10000.);
1371  //mask is 2^ceil(log2(mod))-1
1372  while(mask<mod-1)mask=(mask<<1)+1;
1373 
1374  int count = 0;
1375  //How often does it get a zero from the uniform range [0,mod)?
1376  for (int i = 0; i < 10000; i++) {
1377  uint32_t rval;
1378  do{
1379  rval=InsecureRand32()&mask;
1380  }while(rval>=(uint32_t)mod);
1381  count += rval==0;
1382  }
1383  BOOST_CHECK(count<=10000/mod+err);
1384  BOOST_CHECK(count>=10000/mod-err);
1385  }
1386 }
1387 
1388 BOOST_AUTO_TEST_CASE(util_TimingResistantEqual)
1389 {
1390  BOOST_CHECK(TimingResistantEqual(std::string(""), std::string("")));
1391  BOOST_CHECK(!TimingResistantEqual(std::string("abc"), std::string("")));
1392  BOOST_CHECK(!TimingResistantEqual(std::string(""), std::string("abc")));
1393  BOOST_CHECK(!TimingResistantEqual(std::string("a"), std::string("aa")));
1394  BOOST_CHECK(!TimingResistantEqual(std::string("aa"), std::string("a")));
1395  BOOST_CHECK(TimingResistantEqual(std::string("abc"), std::string("abc")));
1396  BOOST_CHECK(!TimingResistantEqual(std::string("abc"), std::string("aba")));
1397 }
1398 
1399 /* Test strprintf formatting directives.
1400  * Put a string before and after to ensure sanity of element sizes on stack. */
1401 #define B "check_prefix"
1402 #define E "check_postfix"
1403 BOOST_AUTO_TEST_CASE(strprintf_numbers)
1404 {
1405  int64_t s64t = -9223372036854775807LL; /* signed 64 bit test value */
1406  uint64_t u64t = 18446744073709551615ULL; /* unsigned 64 bit test value */
1407  BOOST_CHECK(strprintf("%s %d %s", B, s64t, E) == B" -9223372036854775807 " E);
1408  BOOST_CHECK(strprintf("%s %u %s", B, u64t, E) == B" 18446744073709551615 " E);
1409  BOOST_CHECK(strprintf("%s %x %s", B, u64t, E) == B" ffffffffffffffff " E);
1410 
1411  size_t st = 12345678; /* unsigned size_t test value */
1412  ssize_t sst = -12345678; /* signed size_t test value */
1413  BOOST_CHECK(strprintf("%s %d %s", B, sst, E) == B" -12345678 " E);
1414  BOOST_CHECK(strprintf("%s %u %s", B, st, E) == B" 12345678 " E);
1415  BOOST_CHECK(strprintf("%s %x %s", B, st, E) == B" bc614e " E);
1416 
1417  ptrdiff_t pt = 87654321; /* positive ptrdiff_t test value */
1418  ptrdiff_t spt = -87654321; /* negative ptrdiff_t test value */
1419  BOOST_CHECK(strprintf("%s %d %s", B, spt, E) == B" -87654321 " E);
1420  BOOST_CHECK(strprintf("%s %u %s", B, pt, E) == B" 87654321 " E);
1421  BOOST_CHECK(strprintf("%s %x %s", B, pt, E) == B" 5397fb1 " E);
1422 }
1423 #undef B
1424 #undef E
1425 
1426 /* Check for mingw/wine issue #3494
1427  * Remove this test before time.ctime(0xffffffff) == 'Sun Feb 7 07:28:15 2106'
1428  */
1429 BOOST_AUTO_TEST_CASE(gettime)
1430 {
1431  BOOST_CHECK((GetTime() & ~0xFFFFFFFFLL) == 0);
1432 }
1433 
1434 BOOST_AUTO_TEST_CASE(util_time_GetTime)
1435 {
1436  SetMockTime(111);
1437  // Check that mock time does not change after a sleep
1438  for (const auto& num_sleep : {0, 1}) {
1439  UninterruptibleSleep(std::chrono::milliseconds{num_sleep});
1440  BOOST_CHECK_EQUAL(111, GetTime()); // Deprecated time getter
1441  BOOST_CHECK_EQUAL(111, GetTime<std::chrono::seconds>().count());
1442  BOOST_CHECK_EQUAL(111000, GetTime<std::chrono::milliseconds>().count());
1443  BOOST_CHECK_EQUAL(111000000, GetTime<std::chrono::microseconds>().count());
1444  }
1445 
1446  SetMockTime(0);
1447  // Check that system time changes after a sleep
1448  const auto ms_0 = GetTime<std::chrono::milliseconds>();
1449  const auto us_0 = GetTime<std::chrono::microseconds>();
1450  UninterruptibleSleep(std::chrono::milliseconds{1});
1451  BOOST_CHECK(ms_0 < GetTime<std::chrono::milliseconds>());
1452  BOOST_CHECK(us_0 < GetTime<std::chrono::microseconds>());
1453 }
1454 
1455 BOOST_AUTO_TEST_CASE(test_IsDigit)
1456 {
1457  BOOST_CHECK_EQUAL(IsDigit('0'), true);
1458  BOOST_CHECK_EQUAL(IsDigit('1'), true);
1459  BOOST_CHECK_EQUAL(IsDigit('8'), true);
1460  BOOST_CHECK_EQUAL(IsDigit('9'), true);
1461 
1462  BOOST_CHECK_EQUAL(IsDigit('0' - 1), false);
1463  BOOST_CHECK_EQUAL(IsDigit('9' + 1), false);
1464  BOOST_CHECK_EQUAL(IsDigit(0), false);
1465  BOOST_CHECK_EQUAL(IsDigit(1), false);
1466  BOOST_CHECK_EQUAL(IsDigit(8), false);
1467  BOOST_CHECK_EQUAL(IsDigit(9), false);
1468 }
1469 
1470 /* Check for overflow */
1471 template <typename T>
1472 static void TestAddMatrixOverflow()
1473 {
1474  constexpr T MAXI{std::numeric_limits<T>::max()};
1475  BOOST_CHECK(!CheckedAdd(T{1}, MAXI));
1476  BOOST_CHECK(!CheckedAdd(MAXI, MAXI));
1477  BOOST_CHECK_EQUAL(0, CheckedAdd(T{0}, T{0}).value());
1478  BOOST_CHECK_EQUAL(MAXI, CheckedAdd(T{0}, MAXI).value());
1479  BOOST_CHECK_EQUAL(MAXI, CheckedAdd(T{1}, MAXI - 1).value());
1480 }
1481 
1482 /* Check for overflow or underflow */
1483 template <typename T>
1484 static void TestAddMatrix()
1485 {
1486  TestAddMatrixOverflow<T>();
1487  constexpr T MINI{std::numeric_limits<T>::min()};
1488  constexpr T MAXI{std::numeric_limits<T>::max()};
1489  BOOST_CHECK(!CheckedAdd(T{-1}, MINI));
1490  BOOST_CHECK(!CheckedAdd(MINI, MINI));
1491  BOOST_CHECK_EQUAL(MINI, CheckedAdd(T{0}, MINI).value());
1492  BOOST_CHECK_EQUAL(MINI, CheckedAdd(T{-1}, MINI + 1).value());
1493  BOOST_CHECK_EQUAL(-1, CheckedAdd(MINI, MAXI).value());
1494 }
1495 
1496 BOOST_AUTO_TEST_CASE(util_overflow)
1497 {
1498  TestAddMatrixOverflow<unsigned>();
1499  TestAddMatrix<signed>();
1500 }
1501 
1502 BOOST_AUTO_TEST_CASE(test_ParseInt32)
1503 {
1504  int32_t n;
1505  // Valid values
1506  BOOST_CHECK(ParseInt32("1234", nullptr));
1507  BOOST_CHECK(ParseInt32("0", &n) && n == 0);
1508  BOOST_CHECK(ParseInt32("1234", &n) && n == 1234);
1509  BOOST_CHECK(ParseInt32("01234", &n) && n == 1234); // no octal
1510  BOOST_CHECK(ParseInt32("2147483647", &n) && n == 2147483647);
1511  BOOST_CHECK(ParseInt32("-2147483648", &n) && n == (-2147483647 - 1)); // (-2147483647 - 1) equals INT_MIN
1512  BOOST_CHECK(ParseInt32("-1234", &n) && n == -1234);
1513  BOOST_CHECK(ParseInt32("00000000000000001234", &n) && n == 1234);
1514  BOOST_CHECK(ParseInt32("-00000000000000001234", &n) && n == -1234);
1515  BOOST_CHECK(ParseInt32("00000000000000000000", &n) && n == 0);
1516  BOOST_CHECK(ParseInt32("-00000000000000000000", &n) && n == 0);
1517  // Invalid values
1518  BOOST_CHECK(!ParseInt32("", &n));
1519  BOOST_CHECK(!ParseInt32(" 1", &n)); // no padding inside
1520  BOOST_CHECK(!ParseInt32("1 ", &n));
1521  BOOST_CHECK(!ParseInt32("++1", &n));
1522  BOOST_CHECK(!ParseInt32("+-1", &n));
1523  BOOST_CHECK(!ParseInt32("-+1", &n));
1524  BOOST_CHECK(!ParseInt32("--1", &n));
1525  BOOST_CHECK(!ParseInt32("1a", &n));
1526  BOOST_CHECK(!ParseInt32("aap", &n));
1527  BOOST_CHECK(!ParseInt32("0x1", &n)); // no hex
1528  BOOST_CHECK(!ParseInt32(STRING_WITH_EMBEDDED_NULL_CHAR, &n));
1529  // Overflow and underflow
1530  BOOST_CHECK(!ParseInt32("-2147483649", nullptr));
1531  BOOST_CHECK(!ParseInt32("2147483648", nullptr));
1532  BOOST_CHECK(!ParseInt32("-32482348723847471234", nullptr));
1533  BOOST_CHECK(!ParseInt32("32482348723847471234", nullptr));
1534 }
1535 
1536 template <typename T>
1537 static void RunToIntegralTests()
1538 {
1539  BOOST_CHECK(!ToIntegral<T>(STRING_WITH_EMBEDDED_NULL_CHAR));
1540  BOOST_CHECK(!ToIntegral<T>(" 1"));
1541  BOOST_CHECK(!ToIntegral<T>("1 "));
1542  BOOST_CHECK(!ToIntegral<T>("1a"));
1543  BOOST_CHECK(!ToIntegral<T>("1.1"));
1544  BOOST_CHECK(!ToIntegral<T>("1.9"));
1545  BOOST_CHECK(!ToIntegral<T>("+01.9"));
1546  BOOST_CHECK(!ToIntegral<T>("-"));
1547  BOOST_CHECK(!ToIntegral<T>("+"));
1548  BOOST_CHECK(!ToIntegral<T>(" -1"));
1549  BOOST_CHECK(!ToIntegral<T>("-1 "));
1550  BOOST_CHECK(!ToIntegral<T>(" -1 "));
1551  BOOST_CHECK(!ToIntegral<T>("+1"));
1552  BOOST_CHECK(!ToIntegral<T>(" +1"));
1553  BOOST_CHECK(!ToIntegral<T>(" +1 "));
1554  BOOST_CHECK(!ToIntegral<T>("+-1"));
1555  BOOST_CHECK(!ToIntegral<T>("-+1"));
1556  BOOST_CHECK(!ToIntegral<T>("++1"));
1557  BOOST_CHECK(!ToIntegral<T>("--1"));
1558  BOOST_CHECK(!ToIntegral<T>(""));
1559  BOOST_CHECK(!ToIntegral<T>("aap"));
1560  BOOST_CHECK(!ToIntegral<T>("0x1"));
1561  BOOST_CHECK(!ToIntegral<T>("-32482348723847471234"));
1562  BOOST_CHECK(!ToIntegral<T>("32482348723847471234"));
1563 }
1564 
1565 BOOST_AUTO_TEST_CASE(test_ToIntegral)
1566 {
1567  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("1234").value(), 1'234);
1568  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("0").value(), 0);
1569  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("01234").value(), 1'234);
1570  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("00000000000000001234").value(), 1'234);
1571  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-00000000000000001234").value(), -1'234);
1572  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("00000000000000000000").value(), 0);
1573  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-00000000000000000000").value(), 0);
1574  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-1234").value(), -1'234);
1575  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-1").value(), -1);
1576 
1577  RunToIntegralTests<uint64_t>();
1578  RunToIntegralTests<int64_t>();
1579  RunToIntegralTests<uint32_t>();
1580  RunToIntegralTests<int32_t>();
1581  RunToIntegralTests<uint16_t>();
1582  RunToIntegralTests<int16_t>();
1583  RunToIntegralTests<uint8_t>();
1584  RunToIntegralTests<int8_t>();
1585 
1586  BOOST_CHECK(!ToIntegral<int64_t>("-9223372036854775809"));
1587  BOOST_CHECK_EQUAL(ToIntegral<int64_t>("-9223372036854775808").value(), -9'223'372'036'854'775'807LL - 1LL);
1588  BOOST_CHECK_EQUAL(ToIntegral<int64_t>("9223372036854775807").value(), 9'223'372'036'854'775'807);
1589  BOOST_CHECK(!ToIntegral<int64_t>("9223372036854775808"));
1590 
1591  BOOST_CHECK(!ToIntegral<uint64_t>("-1"));
1592  BOOST_CHECK_EQUAL(ToIntegral<uint64_t>("0").value(), 0U);
1593  BOOST_CHECK_EQUAL(ToIntegral<uint64_t>("18446744073709551615").value(), 18'446'744'073'709'551'615ULL);
1594  BOOST_CHECK(!ToIntegral<uint64_t>("18446744073709551616"));
1595 
1596  BOOST_CHECK(!ToIntegral<int32_t>("-2147483649"));
1597  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-2147483648").value(), -2'147'483'648LL);
1598  BOOST_CHECK_EQUAL(ToIntegral<int32_t>("2147483647").value(), 2'147'483'647);
1599  BOOST_CHECK(!ToIntegral<int32_t>("2147483648"));
1600 
1601  BOOST_CHECK(!ToIntegral<uint32_t>("-1"));
1602  BOOST_CHECK_EQUAL(ToIntegral<uint32_t>("0").value(), 0U);
1603  BOOST_CHECK_EQUAL(ToIntegral<uint32_t>("4294967295").value(), 4'294'967'295U);
1604  BOOST_CHECK(!ToIntegral<uint32_t>("4294967296"));
1605 
1606  BOOST_CHECK(!ToIntegral<int16_t>("-32769"));
1607  BOOST_CHECK_EQUAL(ToIntegral<int16_t>("-32768").value(), -32'768);
1608  BOOST_CHECK_EQUAL(ToIntegral<int16_t>("32767").value(), 32'767);
1609  BOOST_CHECK(!ToIntegral<int16_t>("32768"));
1610 
1611  BOOST_CHECK(!ToIntegral<uint16_t>("-1"));
1612  BOOST_CHECK_EQUAL(ToIntegral<uint16_t>("0").value(), 0U);
1613  BOOST_CHECK_EQUAL(ToIntegral<uint16_t>("65535").value(), 65'535U);
1614  BOOST_CHECK(!ToIntegral<uint16_t>("65536"));
1615 
1616  BOOST_CHECK(!ToIntegral<int8_t>("-129"));
1617  BOOST_CHECK_EQUAL(ToIntegral<int8_t>("-128").value(), -128);
1618  BOOST_CHECK_EQUAL(ToIntegral<int8_t>("127").value(), 127);
1619  BOOST_CHECK(!ToIntegral<int8_t>("128"));
1620 
1621  BOOST_CHECK(!ToIntegral<uint8_t>("-1"));
1622  BOOST_CHECK_EQUAL(ToIntegral<uint8_t>("0").value(), 0U);
1623  BOOST_CHECK_EQUAL(ToIntegral<uint8_t>("255").value(), 255U);
1624  BOOST_CHECK(!ToIntegral<uint8_t>("256"));
1625 }
1626 
1627 int64_t atoi64_legacy(const std::string& str)
1628 {
1629  return strtoll(str.c_str(), nullptr, 10);
1630 }
1631 
1632 BOOST_AUTO_TEST_CASE(test_LocaleIndependentAtoi)
1633 {
1634  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1234"), 1'234);
1635  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("0"), 0);
1636  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("01234"), 1'234);
1637  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-1234"), -1'234);
1638  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" 1"), 1);
1639  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1 "), 1);
1640  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1a"), 1);
1641  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1.1"), 1);
1642  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1.9"), 1);
1643  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("+01.9"), 1);
1644  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-1"), -1);
1645  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" -1"), -1);
1646  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-1 "), -1);
1647  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" -1 "), -1);
1648  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("+1"), 1);
1649  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" +1"), 1);
1650  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" +1 "), 1);
1651 
1652  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("+-1"), 0);
1653  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-+1"), 0);
1654  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("++1"), 0);
1655  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("--1"), 0);
1656  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(""), 0);
1657  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("aap"), 0);
1658  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("0x1"), 0);
1659  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-32482348723847471234"), -2'147'483'647 - 1);
1660  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("32482348723847471234"), 2'147'483'647);
1661 
1662  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>("-9223372036854775809"), -9'223'372'036'854'775'807LL - 1LL);
1663  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>("-9223372036854775808"), -9'223'372'036'854'775'807LL - 1LL);
1664  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>("9223372036854775807"), 9'223'372'036'854'775'807);
1665  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>("9223372036854775808"), 9'223'372'036'854'775'807);
1666 
1667  std::map<std::string, int64_t> atoi64_test_pairs = {
1668  {"-9223372036854775809", std::numeric_limits<int64_t>::min()},
1669  {"-9223372036854775808", -9'223'372'036'854'775'807LL - 1LL},
1670  {"9223372036854775807", 9'223'372'036'854'775'807},
1671  {"9223372036854775808", std::numeric_limits<int64_t>::max()},
1672  {"+-", 0},
1673  {"0x1", 0},
1674  {"ox1", 0},
1675  {"", 0},
1676  };
1677 
1678  for (const auto& pair : atoi64_test_pairs) {
1679  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>(pair.first), pair.second);
1680  }
1681 
1682  // Ensure legacy compatibility with previous versions of Bitcoin Core's atoi64
1683  for (const auto& pair : atoi64_test_pairs) {
1684  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>(pair.first), atoi64_legacy(pair.first));
1685  }
1686 
1687  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint64_t>("-1"), 0U);
1688  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint64_t>("0"), 0U);
1689  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint64_t>("18446744073709551615"), 18'446'744'073'709'551'615ULL);
1690  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint64_t>("18446744073709551616"), 18'446'744'073'709'551'615ULL);
1691 
1692  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-2147483649"), -2'147'483'648LL);
1693  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-2147483648"), -2'147'483'648LL);
1694  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("2147483647"), 2'147'483'647);
1695  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("2147483648"), 2'147'483'647);
1696 
1697  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint32_t>("-1"), 0U);
1698  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint32_t>("0"), 0U);
1699  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint32_t>("4294967295"), 4'294'967'295U);
1700  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint32_t>("4294967296"), 4'294'967'295U);
1701 
1702  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int16_t>("-32769"), -32'768);
1703  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int16_t>("-32768"), -32'768);
1704  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int16_t>("32767"), 32'767);
1705  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int16_t>("32768"), 32'767);
1706 
1707  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint16_t>("-1"), 0U);
1708  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint16_t>("0"), 0U);
1709  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint16_t>("65535"), 65'535U);
1710  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint16_t>("65536"), 65'535U);
1711 
1712  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int8_t>("-129"), -128);
1713  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int8_t>("-128"), -128);
1714  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int8_t>("127"), 127);
1715  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int8_t>("128"), 127);
1716 
1717  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint8_t>("-1"), 0U);
1718  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint8_t>("0"), 0U);
1719  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint8_t>("255"), 255U);
1720  BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint8_t>("256"), 255U);
1721 }
1722 
1723 BOOST_AUTO_TEST_CASE(test_ParseInt64)
1724 {
1725  int64_t n;
1726  // Valid values
1727  BOOST_CHECK(ParseInt64("1234", nullptr));
1728  BOOST_CHECK(ParseInt64("0", &n) && n == 0LL);
1729  BOOST_CHECK(ParseInt64("1234", &n) && n == 1234LL);
1730  BOOST_CHECK(ParseInt64("01234", &n) && n == 1234LL); // no octal
1731  BOOST_CHECK(ParseInt64("2147483647", &n) && n == 2147483647LL);
1732  BOOST_CHECK(ParseInt64("-2147483648", &n) && n == -2147483648LL);
1733  BOOST_CHECK(ParseInt64("9223372036854775807", &n) && n == (int64_t)9223372036854775807);
1734  BOOST_CHECK(ParseInt64("-9223372036854775808", &n) && n == (int64_t)-9223372036854775807-1);
1735  BOOST_CHECK(ParseInt64("-1234", &n) && n == -1234LL);
1736  // Invalid values
1737  BOOST_CHECK(!ParseInt64("", &n));
1738  BOOST_CHECK(!ParseInt64(" 1", &n)); // no padding inside
1739  BOOST_CHECK(!ParseInt64("1 ", &n));
1740  BOOST_CHECK(!ParseInt64("1a", &n));
1741  BOOST_CHECK(!ParseInt64("aap", &n));
1742  BOOST_CHECK(!ParseInt64("0x1", &n)); // no hex
1744  // Overflow and underflow
1745  BOOST_CHECK(!ParseInt64("-9223372036854775809", nullptr));
1746  BOOST_CHECK(!ParseInt64("9223372036854775808", nullptr));
1747  BOOST_CHECK(!ParseInt64("-32482348723847471234", nullptr));
1748  BOOST_CHECK(!ParseInt64("32482348723847471234", nullptr));
1749 }
1750 
1751 BOOST_AUTO_TEST_CASE(test_ParseUInt8)
1752 {
1753  uint8_t n;
1754  // Valid values
1755  BOOST_CHECK(ParseUInt8("255", nullptr));
1756  BOOST_CHECK(ParseUInt8("0", &n) && n == 0);
1757  BOOST_CHECK(ParseUInt8("255", &n) && n == 255);
1758  BOOST_CHECK(ParseUInt8("0255", &n) && n == 255); // no octal
1759  BOOST_CHECK(ParseUInt8("255", &n) && n == static_cast<uint8_t>(255));
1760  BOOST_CHECK(ParseUInt8("+255", &n) && n == 255);
1761  BOOST_CHECK(ParseUInt8("00000000000000000012", &n) && n == 12);
1762  BOOST_CHECK(ParseUInt8("00000000000000000000", &n) && n == 0);
1763  // Invalid values
1764  BOOST_CHECK(!ParseUInt8("-00000000000000000000", &n));
1765  BOOST_CHECK(!ParseUInt8("", &n));
1766  BOOST_CHECK(!ParseUInt8(" 1", &n)); // no padding inside
1767  BOOST_CHECK(!ParseUInt8(" -1", &n));
1768  BOOST_CHECK(!ParseUInt8("++1", &n));
1769  BOOST_CHECK(!ParseUInt8("+-1", &n));
1770  BOOST_CHECK(!ParseUInt8("-+1", &n));
1771  BOOST_CHECK(!ParseUInt8("--1", &n));
1772  BOOST_CHECK(!ParseUInt8("-1", &n));
1773  BOOST_CHECK(!ParseUInt8("1 ", &n));
1774  BOOST_CHECK(!ParseUInt8("1a", &n));
1775  BOOST_CHECK(!ParseUInt8("aap", &n));
1776  BOOST_CHECK(!ParseUInt8("0x1", &n)); // no hex
1778  // Overflow and underflow
1779  BOOST_CHECK(!ParseUInt8("-255", &n));
1780  BOOST_CHECK(!ParseUInt8("256", &n));
1781  BOOST_CHECK(!ParseUInt8("-123", &n));
1782  BOOST_CHECK(!ParseUInt8("-123", nullptr));
1783  BOOST_CHECK(!ParseUInt8("256", nullptr));
1784 }
1785 
1786 BOOST_AUTO_TEST_CASE(test_ParseUInt16)
1787 {
1788  uint16_t n;
1789  // Valid values
1790  BOOST_CHECK(ParseUInt16("1234", nullptr));
1791  BOOST_CHECK(ParseUInt16("0", &n) && n == 0);
1792  BOOST_CHECK(ParseUInt16("1234", &n) && n == 1234);
1793  BOOST_CHECK(ParseUInt16("01234", &n) && n == 1234); // no octal
1794  BOOST_CHECK(ParseUInt16("65535", &n) && n == static_cast<uint16_t>(65535));
1795  BOOST_CHECK(ParseUInt16("+65535", &n) && n == 65535);
1796  BOOST_CHECK(ParseUInt16("00000000000000000012", &n) && n == 12);
1797  BOOST_CHECK(ParseUInt16("00000000000000000000", &n) && n == 0);
1798  // Invalid values
1799  BOOST_CHECK(!ParseUInt16("-00000000000000000000", &n));
1800  BOOST_CHECK(!ParseUInt16("", &n));
1801  BOOST_CHECK(!ParseUInt16(" 1", &n)); // no padding inside
1802  BOOST_CHECK(!ParseUInt16(" -1", &n));
1803  BOOST_CHECK(!ParseUInt16("++1", &n));
1804  BOOST_CHECK(!ParseUInt16("+-1", &n));
1805  BOOST_CHECK(!ParseUInt16("-+1", &n));
1806  BOOST_CHECK(!ParseUInt16("--1", &n));
1807  BOOST_CHECK(!ParseUInt16("-1", &n));
1808  BOOST_CHECK(!ParseUInt16("1 ", &n));
1809  BOOST_CHECK(!ParseUInt16("1a", &n));
1810  BOOST_CHECK(!ParseUInt16("aap", &n));
1811  BOOST_CHECK(!ParseUInt16("0x1", &n)); // no hex
1813  // Overflow and underflow
1814  BOOST_CHECK(!ParseUInt16("-65535", &n));
1815  BOOST_CHECK(!ParseUInt16("65536", &n));
1816  BOOST_CHECK(!ParseUInt16("-123", &n));
1817  BOOST_CHECK(!ParseUInt16("-123", nullptr));
1818  BOOST_CHECK(!ParseUInt16("65536", nullptr));
1819 }
1820 
1821 BOOST_AUTO_TEST_CASE(test_ParseUInt32)
1822 {
1823  uint32_t n;
1824  // Valid values
1825  BOOST_CHECK(ParseUInt32("1234", nullptr));
1826  BOOST_CHECK(ParseUInt32("0", &n) && n == 0);
1827  BOOST_CHECK(ParseUInt32("1234", &n) && n == 1234);
1828  BOOST_CHECK(ParseUInt32("01234", &n) && n == 1234); // no octal
1829  BOOST_CHECK(ParseUInt32("2147483647", &n) && n == 2147483647);
1830  BOOST_CHECK(ParseUInt32("2147483648", &n) && n == (uint32_t)2147483648);
1831  BOOST_CHECK(ParseUInt32("4294967295", &n) && n == (uint32_t)4294967295);
1832  BOOST_CHECK(ParseUInt32("+1234", &n) && n == 1234);
1833  BOOST_CHECK(ParseUInt32("00000000000000001234", &n) && n == 1234);
1834  BOOST_CHECK(ParseUInt32("00000000000000000000", &n) && n == 0);
1835  // Invalid values
1836  BOOST_CHECK(!ParseUInt32("-00000000000000000000", &n));
1837  BOOST_CHECK(!ParseUInt32("", &n));
1838  BOOST_CHECK(!ParseUInt32(" 1", &n)); // no padding inside
1839  BOOST_CHECK(!ParseUInt32(" -1", &n));
1840  BOOST_CHECK(!ParseUInt32("++1", &n));
1841  BOOST_CHECK(!ParseUInt32("+-1", &n));
1842  BOOST_CHECK(!ParseUInt32("-+1", &n));
1843  BOOST_CHECK(!ParseUInt32("--1", &n));
1844  BOOST_CHECK(!ParseUInt32("-1", &n));
1845  BOOST_CHECK(!ParseUInt32("1 ", &n));
1846  BOOST_CHECK(!ParseUInt32("1a", &n));
1847  BOOST_CHECK(!ParseUInt32("aap", &n));
1848  BOOST_CHECK(!ParseUInt32("0x1", &n)); // no hex
1850  // Overflow and underflow
1851  BOOST_CHECK(!ParseUInt32("-2147483648", &n));
1852  BOOST_CHECK(!ParseUInt32("4294967296", &n));
1853  BOOST_CHECK(!ParseUInt32("-1234", &n));
1854  BOOST_CHECK(!ParseUInt32("-32482348723847471234", nullptr));
1855  BOOST_CHECK(!ParseUInt32("32482348723847471234", nullptr));
1856 }
1857 
1858 BOOST_AUTO_TEST_CASE(test_ParseUInt64)
1859 {
1860  uint64_t n;
1861  // Valid values
1862  BOOST_CHECK(ParseUInt64("1234", nullptr));
1863  BOOST_CHECK(ParseUInt64("0", &n) && n == 0LL);
1864  BOOST_CHECK(ParseUInt64("1234", &n) && n == 1234LL);
1865  BOOST_CHECK(ParseUInt64("01234", &n) && n == 1234LL); // no octal
1866  BOOST_CHECK(ParseUInt64("2147483647", &n) && n == 2147483647LL);
1867  BOOST_CHECK(ParseUInt64("9223372036854775807", &n) && n == 9223372036854775807ULL);
1868  BOOST_CHECK(ParseUInt64("9223372036854775808", &n) && n == 9223372036854775808ULL);
1869  BOOST_CHECK(ParseUInt64("18446744073709551615", &n) && n == 18446744073709551615ULL);
1870  // Invalid values
1871  BOOST_CHECK(!ParseUInt64("", &n));
1872  BOOST_CHECK(!ParseUInt64(" 1", &n)); // no padding inside
1873  BOOST_CHECK(!ParseUInt64(" -1", &n));
1874  BOOST_CHECK(!ParseUInt64("1 ", &n));
1875  BOOST_CHECK(!ParseUInt64("1a", &n));
1876  BOOST_CHECK(!ParseUInt64("aap", &n));
1877  BOOST_CHECK(!ParseUInt64("0x1", &n)); // no hex
1879  // Overflow and underflow
1880  BOOST_CHECK(!ParseUInt64("-9223372036854775809", nullptr));
1881  BOOST_CHECK(!ParseUInt64("18446744073709551616", nullptr));
1882  BOOST_CHECK(!ParseUInt64("-32482348723847471234", nullptr));
1883  BOOST_CHECK(!ParseUInt64("-2147483648", &n));
1884  BOOST_CHECK(!ParseUInt64("-9223372036854775808", &n));
1885  BOOST_CHECK(!ParseUInt64("-1234", &n));
1886 }
1887 
1888 BOOST_AUTO_TEST_CASE(test_FormatParagraph)
1889 {
1890  BOOST_CHECK_EQUAL(FormatParagraph("", 79, 0), "");
1891  BOOST_CHECK_EQUAL(FormatParagraph("test", 79, 0), "test");
1892  BOOST_CHECK_EQUAL(FormatParagraph(" test", 79, 0), " test");
1893  BOOST_CHECK_EQUAL(FormatParagraph("test test", 79, 0), "test test");
1894  BOOST_CHECK_EQUAL(FormatParagraph("test test", 4, 0), "test\ntest");
1895  BOOST_CHECK_EQUAL(FormatParagraph("testerde test", 4, 0), "testerde\ntest");
1896  BOOST_CHECK_EQUAL(FormatParagraph("test test", 4, 4), "test\n test");
1897 
1898  // Make sure we don't indent a fully-new line following a too-long line ending
1899  BOOST_CHECK_EQUAL(FormatParagraph("test test\nabc", 4, 4), "test\n test\nabc");
1900 
1901  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");
1902 
1903  // Test wrap length is exact
1904  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");
1905  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");
1906  // Indent should be included in length of lines
1907  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");
1908 
1909  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.");
1910  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.");
1911  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.");
1912  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.");
1913 }
1914 
1915 BOOST_AUTO_TEST_CASE(test_FormatSubVersion)
1916 {
1917  std::vector<std::string> comments;
1918  comments.push_back(std::string("comment1"));
1919  std::vector<std::string> comments2;
1920  comments2.push_back(std::string("comment1"));
1921  comments2.push_back(SanitizeString(std::string("Comment2; .,_?@-; !\"#$%&'()*+/<=>[]\\^`{|}~"), SAFE_CHARS_UA_COMMENT)); // Semicolon is discouraged but not forbidden by BIP-0014
1922  BOOST_CHECK_EQUAL(FormatSubVersion("Test", 99900, std::vector<std::string>()),std::string("/Test:9.99.0/"));
1923  BOOST_CHECK_EQUAL(FormatSubVersion("Test", 99900, comments),std::string("/Test:9.99.0(comment1)/"));
1924  BOOST_CHECK_EQUAL(FormatSubVersion("Test", 99900, comments2),std::string("/Test:9.99.0(comment1; Comment2; .,_?@-; )/"));
1925 }
1926 
1927 BOOST_AUTO_TEST_CASE(test_ParseFixedPoint)
1928 {
1929  int64_t amount = 0;
1930  BOOST_CHECK(ParseFixedPoint("0", 8, &amount));
1931  BOOST_CHECK_EQUAL(amount, 0LL);
1932  BOOST_CHECK(ParseFixedPoint("1", 8, &amount));
1933  BOOST_CHECK_EQUAL(amount, 100000000LL);
1934  BOOST_CHECK(ParseFixedPoint("0.0", 8, &amount));
1935  BOOST_CHECK_EQUAL(amount, 0LL);
1936  BOOST_CHECK(ParseFixedPoint("-0.1", 8, &amount));
1937  BOOST_CHECK_EQUAL(amount, -10000000LL);
1938  BOOST_CHECK(ParseFixedPoint("1.1", 8, &amount));
1939  BOOST_CHECK_EQUAL(amount, 110000000LL);
1940  BOOST_CHECK(ParseFixedPoint("1.10000000000000000", 8, &amount));
1941  BOOST_CHECK_EQUAL(amount, 110000000LL);
1942  BOOST_CHECK(ParseFixedPoint("1.1e1", 8, &amount));
1943  BOOST_CHECK_EQUAL(amount, 1100000000LL);
1944  BOOST_CHECK(ParseFixedPoint("1.1e-1", 8, &amount));
1945  BOOST_CHECK_EQUAL(amount, 11000000LL);
1946  BOOST_CHECK(ParseFixedPoint("1000", 8, &amount));
1947  BOOST_CHECK_EQUAL(amount, 100000000000LL);
1948  BOOST_CHECK(ParseFixedPoint("-1000", 8, &amount));
1949  BOOST_CHECK_EQUAL(amount, -100000000000LL);
1950  BOOST_CHECK(ParseFixedPoint("0.00000001", 8, &amount));
1951  BOOST_CHECK_EQUAL(amount, 1LL);
1952  BOOST_CHECK(ParseFixedPoint("0.0000000100000000", 8, &amount));
1953  BOOST_CHECK_EQUAL(amount, 1LL);
1954  BOOST_CHECK(ParseFixedPoint("-0.00000001", 8, &amount));
1955  BOOST_CHECK_EQUAL(amount, -1LL);
1956  BOOST_CHECK(ParseFixedPoint("1000000000.00000001", 8, &amount));
1957  BOOST_CHECK_EQUAL(amount, 100000000000000001LL);
1958  BOOST_CHECK(ParseFixedPoint("9999999999.99999999", 8, &amount));
1959  BOOST_CHECK_EQUAL(amount, 999999999999999999LL);
1960  BOOST_CHECK(ParseFixedPoint("-9999999999.99999999", 8, &amount));
1961  BOOST_CHECK_EQUAL(amount, -999999999999999999LL);
1962 
1963  BOOST_CHECK(!ParseFixedPoint("", 8, &amount));
1964  BOOST_CHECK(!ParseFixedPoint("-", 8, &amount));
1965  BOOST_CHECK(!ParseFixedPoint("a-1000", 8, &amount));
1966  BOOST_CHECK(!ParseFixedPoint("-a1000", 8, &amount));
1967  BOOST_CHECK(!ParseFixedPoint("-1000a", 8, &amount));
1968  BOOST_CHECK(!ParseFixedPoint("-01000", 8, &amount));
1969  BOOST_CHECK(!ParseFixedPoint("00.1", 8, &amount));
1970  BOOST_CHECK(!ParseFixedPoint(".1", 8, &amount));
1971  BOOST_CHECK(!ParseFixedPoint("--0.1", 8, &amount));
1972  BOOST_CHECK(!ParseFixedPoint("0.000000001", 8, &amount));
1973  BOOST_CHECK(!ParseFixedPoint("-0.000000001", 8, &amount));
1974  BOOST_CHECK(!ParseFixedPoint("0.00000001000000001", 8, &amount));
1975  BOOST_CHECK(!ParseFixedPoint("-10000000000.00000000", 8, &amount));
1976  BOOST_CHECK(!ParseFixedPoint("10000000000.00000000", 8, &amount));
1977  BOOST_CHECK(!ParseFixedPoint("-10000000000.00000001", 8, &amount));
1978  BOOST_CHECK(!ParseFixedPoint("10000000000.00000001", 8, &amount));
1979  BOOST_CHECK(!ParseFixedPoint("-10000000000.00000009", 8, &amount));
1980  BOOST_CHECK(!ParseFixedPoint("10000000000.00000009", 8, &amount));
1981  BOOST_CHECK(!ParseFixedPoint("-99999999999.99999999", 8, &amount));
1982  BOOST_CHECK(!ParseFixedPoint("99999909999.09999999", 8, &amount));
1983  BOOST_CHECK(!ParseFixedPoint("92233720368.54775807", 8, &amount));
1984  BOOST_CHECK(!ParseFixedPoint("92233720368.54775808", 8, &amount));
1985  BOOST_CHECK(!ParseFixedPoint("-92233720368.54775808", 8, &amount));
1986  BOOST_CHECK(!ParseFixedPoint("-92233720368.54775809", 8, &amount));
1987  BOOST_CHECK(!ParseFixedPoint("1.1e", 8, &amount));
1988  BOOST_CHECK(!ParseFixedPoint("1.1e-", 8, &amount));
1989  BOOST_CHECK(!ParseFixedPoint("1.", 8, &amount));
1990 
1991  // Test with 3 decimal places for fee rates in sat/vB.
1992  BOOST_CHECK(ParseFixedPoint("0.001", 3, &amount));
1993  BOOST_CHECK_EQUAL(amount, CAmount{1});
1994  BOOST_CHECK(!ParseFixedPoint("0.0009", 3, &amount));
1995  BOOST_CHECK(!ParseFixedPoint("31.00100001", 3, &amount));
1996  BOOST_CHECK(!ParseFixedPoint("31.0011", 3, &amount));
1997  BOOST_CHECK(!ParseFixedPoint("31.99999999", 3, &amount));
1998  BOOST_CHECK(!ParseFixedPoint("31.999999999999999999999", 3, &amount));
1999 }
2000 
2001 static void TestOtherThread(fs::path dirname, std::string lockname, bool *result)
2002 {
2003  *result = LockDirectory(dirname, lockname);
2004 }
2005 
2006 #ifndef WIN32 // Cannot do this test on WIN32 due to lack of fork()
2007 static constexpr char LockCommand = 'L';
2008 static constexpr char UnlockCommand = 'U';
2009 static constexpr char ExitCommand = 'X';
2010 
2011 [[noreturn]] static void TestOtherProcess(fs::path dirname, std::string lockname, int fd)
2012 {
2013  char ch;
2014  while (true) {
2015  int rv = read(fd, &ch, 1); // Wait for command
2016  assert(rv == 1);
2017  switch(ch) {
2018  case LockCommand:
2019  ch = LockDirectory(dirname, lockname);
2020  rv = write(fd, &ch, 1);
2021  assert(rv == 1);
2022  break;
2023  case UnlockCommand:
2025  ch = true; // Always succeeds
2026  rv = write(fd, &ch, 1);
2027  assert(rv == 1);
2028  break;
2029  case ExitCommand:
2030  close(fd);
2031  exit(0);
2032  default:
2033  assert(0);
2034  }
2035  }
2036 }
2037 #endif
2038 
2039 BOOST_AUTO_TEST_CASE(test_LockDirectory)
2040 {
2041  fs::path dirname = m_args.GetDataDirBase() / "lock_dir";
2042  const std::string lockname = ".lock";
2043 #ifndef WIN32
2044  // Revert SIGCHLD to default, otherwise boost.test will catch and fail on
2045  // it: there is BOOST_TEST_IGNORE_SIGCHLD but that only works when defined
2046  // at build-time of the boost library
2047  void (*old_handler)(int) = signal(SIGCHLD, SIG_DFL);
2048 
2049  // Fork another process for testing before creating the lock, so that we
2050  // won't fork while holding the lock (which might be undefined, and is not
2051  // relevant as test case as that is avoided with -daemonize).
2052  int fd[2];
2053  BOOST_CHECK_EQUAL(socketpair(AF_UNIX, SOCK_STREAM, 0, fd), 0);
2054  pid_t pid = fork();
2055  if (!pid) {
2056  BOOST_CHECK_EQUAL(close(fd[1]), 0); // Child: close parent end
2057  TestOtherProcess(dirname, lockname, fd[0]);
2058  }
2059  BOOST_CHECK_EQUAL(close(fd[0]), 0); // Parent: close child end
2060 #endif
2061  // Lock on non-existent directory should fail
2062  BOOST_CHECK_EQUAL(LockDirectory(dirname, lockname), false);
2063 
2064  fs::create_directories(dirname);
2065 
2066  // Probing lock on new directory should succeed
2067  BOOST_CHECK_EQUAL(LockDirectory(dirname, lockname, true), true);
2068 
2069  // Persistent lock on new directory should succeed
2070  BOOST_CHECK_EQUAL(LockDirectory(dirname, lockname), true);
2071 
2072  // Another lock on the directory from the same thread should succeed
2073  BOOST_CHECK_EQUAL(LockDirectory(dirname, lockname), true);
2074 
2075  // Another lock on the directory from a different thread within the same process should succeed
2076  bool threadresult;
2077  std::thread thr(TestOtherThread, dirname, lockname, &threadresult);
2078  thr.join();
2079  BOOST_CHECK_EQUAL(threadresult, true);
2080 #ifndef WIN32
2081  // Try to acquire lock in child process while we're holding it, this should fail.
2082  char ch;
2083  BOOST_CHECK_EQUAL(write(fd[1], &LockCommand, 1), 1);
2084  BOOST_CHECK_EQUAL(read(fd[1], &ch, 1), 1);
2085  BOOST_CHECK_EQUAL((bool)ch, false);
2086 
2087  // Give up our lock
2089  // Probing lock from our side now should succeed, but not hold on to the lock.
2090  BOOST_CHECK_EQUAL(LockDirectory(dirname, lockname, true), true);
2091 
2092  // Try to acquire the lock in the child process, this should be successful.
2093  BOOST_CHECK_EQUAL(write(fd[1], &LockCommand, 1), 1);
2094  BOOST_CHECK_EQUAL(read(fd[1], &ch, 1), 1);
2095  BOOST_CHECK_EQUAL((bool)ch, true);
2096 
2097  // When we try to probe the lock now, it should fail.
2098  BOOST_CHECK_EQUAL(LockDirectory(dirname, lockname, true), false);
2099 
2100  // Unlock the lock in the child process
2101  BOOST_CHECK_EQUAL(write(fd[1], &UnlockCommand, 1), 1);
2102  BOOST_CHECK_EQUAL(read(fd[1], &ch, 1), 1);
2103  BOOST_CHECK_EQUAL((bool)ch, true);
2104 
2105  // When we try to probe the lock now, it should succeed.
2106  BOOST_CHECK_EQUAL(LockDirectory(dirname, lockname, true), true);
2107 
2108  // Re-lock the lock in the child process, then wait for it to exit, check
2109  // successful return. After that, we check that exiting the process
2110  // has released the lock as we would expect by probing it.
2111  int processstatus;
2112  BOOST_CHECK_EQUAL(write(fd[1], &LockCommand, 1), 1);
2113  BOOST_CHECK_EQUAL(write(fd[1], &ExitCommand, 1), 1);
2114  BOOST_CHECK_EQUAL(waitpid(pid, &processstatus, 0), pid);
2115  BOOST_CHECK_EQUAL(processstatus, 0);
2116  BOOST_CHECK_EQUAL(LockDirectory(dirname, lockname, true), true);
2117 
2118  // Restore SIGCHLD
2119  signal(SIGCHLD, old_handler);
2120  BOOST_CHECK_EQUAL(close(fd[1]), 0); // Close our side of the socketpair
2121 #endif
2122  // Clean up
2124  fs::remove_all(dirname);
2125 }
2126 
2127 BOOST_AUTO_TEST_CASE(test_DirIsWritable)
2128 {
2129  // Should be able to write to the data dir.
2130  fs::path tmpdirname = m_args.GetDataDirBase();
2131  BOOST_CHECK_EQUAL(DirIsWritable(tmpdirname), true);
2132 
2133  // Should not be able to write to a non-existent dir.
2134  tmpdirname = GetUniquePath(tmpdirname);
2135  BOOST_CHECK_EQUAL(DirIsWritable(tmpdirname), false);
2136 
2137  fs::create_directory(tmpdirname);
2138  // Should be able to write to it now.
2139  BOOST_CHECK_EQUAL(DirIsWritable(tmpdirname), true);
2140  fs::remove(tmpdirname);
2141 }
2142 
2144 {
2145  BOOST_CHECK_EQUAL(ToLower('@'), '@');
2146  BOOST_CHECK_EQUAL(ToLower('A'), 'a');
2147  BOOST_CHECK_EQUAL(ToLower('Z'), 'z');
2148  BOOST_CHECK_EQUAL(ToLower('['), '[');
2149  BOOST_CHECK_EQUAL(ToLower(0), 0);
2150  BOOST_CHECK_EQUAL(ToLower('\xff'), '\xff');
2151 
2152  BOOST_CHECK_EQUAL(ToLower(""), "");
2153  BOOST_CHECK_EQUAL(ToLower("#HODL"), "#hodl");
2154  BOOST_CHECK_EQUAL(ToLower("\x00\xfe\xff"), "\x00\xfe\xff");
2155 }
2156 
2158 {
2159  BOOST_CHECK_EQUAL(ToUpper('`'), '`');
2160  BOOST_CHECK_EQUAL(ToUpper('a'), 'A');
2161  BOOST_CHECK_EQUAL(ToUpper('z'), 'Z');
2162  BOOST_CHECK_EQUAL(ToUpper('{'), '{');
2163  BOOST_CHECK_EQUAL(ToUpper(0), 0);
2164  BOOST_CHECK_EQUAL(ToUpper('\xff'), '\xff');
2165 
2166  BOOST_CHECK_EQUAL(ToUpper(""), "");
2167  BOOST_CHECK_EQUAL(ToUpper("#hodl"), "#HODL");
2168  BOOST_CHECK_EQUAL(ToUpper("\x00\xfe\xff"), "\x00\xfe\xff");
2169 }
2170 
2171 BOOST_AUTO_TEST_CASE(test_Capitalize)
2172 {
2173  BOOST_CHECK_EQUAL(Capitalize(""), "");
2174  BOOST_CHECK_EQUAL(Capitalize("bitcoin"), "Bitcoin");
2175  BOOST_CHECK_EQUAL(Capitalize("\x00\xfe\xff"), "\x00\xfe\xff");
2176 }
2177 
2178 static std::string SpanToStr(const Span<const char>& span)
2179 {
2180  return std::string(span.begin(), span.end());
2181 }
2182 
2183 BOOST_AUTO_TEST_CASE(test_spanparsing)
2184 {
2185  using namespace spanparsing;
2186  std::string input;
2187  Span<const char> sp;
2188  bool success;
2189 
2190  // Const(...): parse a constant, update span to skip it if successful
2191  input = "MilkToastHoney";
2192  sp = input;
2193  success = Const("", sp); // empty
2194  BOOST_CHECK(success);
2195  BOOST_CHECK_EQUAL(SpanToStr(sp), "MilkToastHoney");
2196 
2197  success = Const("Milk", sp);
2198  BOOST_CHECK(success);
2199  BOOST_CHECK_EQUAL(SpanToStr(sp), "ToastHoney");
2200 
2201  success = Const("Bread", sp);
2202  BOOST_CHECK(!success);
2203 
2204  success = Const("Toast", sp);
2205  BOOST_CHECK(success);
2206  BOOST_CHECK_EQUAL(SpanToStr(sp), "Honey");
2207 
2208  success = Const("Honeybadger", sp);
2209  BOOST_CHECK(!success);
2210 
2211  success = Const("Honey", sp);
2212  BOOST_CHECK(success);
2213  BOOST_CHECK_EQUAL(SpanToStr(sp), "");
2214 
2215  // Func(...): parse a function call, update span to argument if successful
2216  input = "Foo(Bar(xy,z()))";
2217  sp = input;
2218 
2219  success = Func("FooBar", sp);
2220  BOOST_CHECK(!success);
2221 
2222  success = Func("Foo(", sp);
2223  BOOST_CHECK(!success);
2224 
2225  success = Func("Foo", sp);
2226  BOOST_CHECK(success);
2227  BOOST_CHECK_EQUAL(SpanToStr(sp), "Bar(xy,z())");
2228 
2229  success = Func("Bar", sp);
2230  BOOST_CHECK(success);
2231  BOOST_CHECK_EQUAL(SpanToStr(sp), "xy,z()");
2232 
2233  success = Func("xy", sp);
2234  BOOST_CHECK(!success);
2235 
2236  // Expr(...): return expression that span begins with, update span to skip it
2237  Span<const char> result;
2238 
2239  input = "(n*(n-1))/2";
2240  sp = input;
2241  result = Expr(sp);
2242  BOOST_CHECK_EQUAL(SpanToStr(result), "(n*(n-1))/2");
2243  BOOST_CHECK_EQUAL(SpanToStr(sp), "");
2244 
2245  input = "foo,bar";
2246  sp = input;
2247  result = Expr(sp);
2248  BOOST_CHECK_EQUAL(SpanToStr(result), "foo");
2249  BOOST_CHECK_EQUAL(SpanToStr(sp), ",bar");
2250 
2251  input = "(aaaaa,bbbbb()),c";
2252  sp = input;
2253  result = Expr(sp);
2254  BOOST_CHECK_EQUAL(SpanToStr(result), "(aaaaa,bbbbb())");
2255  BOOST_CHECK_EQUAL(SpanToStr(sp), ",c");
2256 
2257  input = "xyz)foo";
2258  sp = input;
2259  result = Expr(sp);
2260  BOOST_CHECK_EQUAL(SpanToStr(result), "xyz");
2261  BOOST_CHECK_EQUAL(SpanToStr(sp), ")foo");
2262 
2263  input = "((a),(b),(c)),xxx";
2264  sp = input;
2265  result = Expr(sp);
2266  BOOST_CHECK_EQUAL(SpanToStr(result), "((a),(b),(c))");
2267  BOOST_CHECK_EQUAL(SpanToStr(sp), ",xxx");
2268 
2269  // Split(...): split a string on every instance of sep, return vector
2270  std::vector<Span<const char>> results;
2271 
2272  input = "xxx";
2273  results = Split(input, 'x');
2274  BOOST_CHECK_EQUAL(results.size(), 4U);
2275  BOOST_CHECK_EQUAL(SpanToStr(results[0]), "");
2276  BOOST_CHECK_EQUAL(SpanToStr(results[1]), "");
2277  BOOST_CHECK_EQUAL(SpanToStr(results[2]), "");
2278  BOOST_CHECK_EQUAL(SpanToStr(results[3]), "");
2279 
2280  input = "one#two#three";
2281  results = Split(input, '-');
2282  BOOST_CHECK_EQUAL(results.size(), 1U);
2283  BOOST_CHECK_EQUAL(SpanToStr(results[0]), "one#two#three");
2284 
2285  input = "one#two#three";
2286  results = Split(input, '#');
2287  BOOST_CHECK_EQUAL(results.size(), 3U);
2288  BOOST_CHECK_EQUAL(SpanToStr(results[0]), "one");
2289  BOOST_CHECK_EQUAL(SpanToStr(results[1]), "two");
2290  BOOST_CHECK_EQUAL(SpanToStr(results[2]), "three");
2291 
2292  input = "*foo*bar*";
2293  results = Split(input, '*');
2294  BOOST_CHECK_EQUAL(results.size(), 4U);
2295  BOOST_CHECK_EQUAL(SpanToStr(results[0]), "");
2296  BOOST_CHECK_EQUAL(SpanToStr(results[1]), "foo");
2297  BOOST_CHECK_EQUAL(SpanToStr(results[2]), "bar");
2298  BOOST_CHECK_EQUAL(SpanToStr(results[3]), "");
2299 }
2300 
2301 BOOST_AUTO_TEST_CASE(test_LogEscapeMessage)
2302 {
2303  // ASCII and UTF-8 must pass through unaltered.
2304  BOOST_CHECK_EQUAL(BCLog::LogEscapeMessage("Valid log message貓"), "Valid log message貓");
2305  // Newlines must pass through unaltered.
2306  BOOST_CHECK_EQUAL(BCLog::LogEscapeMessage("Message\n with newlines\n"), "Message\n with newlines\n");
2307  // Other control characters are escaped in C syntax.
2308  BOOST_CHECK_EQUAL(BCLog::LogEscapeMessage("\x01\x7f Corrupted log message\x0d"), R"(\x01\x7f Corrupted log message\x0d)");
2309  // Embedded NULL characters are escaped too.
2310  const std::string NUL("O\x00O", 3);
2311  BOOST_CHECK_EQUAL(BCLog::LogEscapeMessage(NUL), R"(O\x00O)");
2312 }
2313 
2314 namespace {
2315 
2316 struct Tracker
2317 {
2319  const Tracker* origin;
2321  int copies;
2322 
2323  Tracker() noexcept : origin(this), copies(0) {}
2324  Tracker(const Tracker& t) noexcept : origin(t.origin), copies(t.copies + 1) {}
2325  Tracker(Tracker&& t) noexcept : origin(t.origin), copies(t.copies) {}
2326  Tracker& operator=(const Tracker& t) noexcept
2327  {
2328  origin = t.origin;
2329  copies = t.copies + 1;
2330  return *this;
2331  }
2332 };
2333 
2334 }
2335 
2336 BOOST_AUTO_TEST_CASE(test_tracked_vector)
2337 {
2338  Tracker t1;
2339  Tracker t2;
2340  Tracker t3;
2341 
2342  BOOST_CHECK(t1.origin == &t1);
2343  BOOST_CHECK(t2.origin == &t2);
2344  BOOST_CHECK(t3.origin == &t3);
2345 
2346  auto v1 = Vector(t1);
2347  BOOST_CHECK_EQUAL(v1.size(), 1U);
2348  BOOST_CHECK(v1[0].origin == &t1);
2349  BOOST_CHECK_EQUAL(v1[0].copies, 1);
2350 
2351  auto v2 = Vector(std::move(t2));
2352  BOOST_CHECK_EQUAL(v2.size(), 1U);
2353  BOOST_CHECK(v2[0].origin == &t2);
2354  BOOST_CHECK_EQUAL(v2[0].copies, 0);
2355 
2356  auto v3 = Vector(t1, std::move(t2));
2357  BOOST_CHECK_EQUAL(v3.size(), 2U);
2358  BOOST_CHECK(v3[0].origin == &t1);
2359  BOOST_CHECK(v3[1].origin == &t2);
2360  BOOST_CHECK_EQUAL(v3[0].copies, 1);
2361  BOOST_CHECK_EQUAL(v3[1].copies, 0);
2362 
2363  auto v4 = Vector(std::move(v3[0]), v3[1], std::move(t3));
2364  BOOST_CHECK_EQUAL(v4.size(), 3U);
2365  BOOST_CHECK(v4[0].origin == &t1);
2366  BOOST_CHECK(v4[1].origin == &t2);
2367  BOOST_CHECK(v4[2].origin == &t3);
2368  BOOST_CHECK_EQUAL(v4[0].copies, 1);
2369  BOOST_CHECK_EQUAL(v4[1].copies, 1);
2370  BOOST_CHECK_EQUAL(v4[2].copies, 0);
2371 
2372  auto v5 = Cat(v1, v4);
2373  BOOST_CHECK_EQUAL(v5.size(), 4U);
2374  BOOST_CHECK(v5[0].origin == &t1);
2375  BOOST_CHECK(v5[1].origin == &t1);
2376  BOOST_CHECK(v5[2].origin == &t2);
2377  BOOST_CHECK(v5[3].origin == &t3);
2378  BOOST_CHECK_EQUAL(v5[0].copies, 2);
2379  BOOST_CHECK_EQUAL(v5[1].copies, 2);
2380  BOOST_CHECK_EQUAL(v5[2].copies, 2);
2381  BOOST_CHECK_EQUAL(v5[3].copies, 1);
2382 
2383  auto v6 = Cat(std::move(v1), v3);
2384  BOOST_CHECK_EQUAL(v6.size(), 3U);
2385  BOOST_CHECK(v6[0].origin == &t1);
2386  BOOST_CHECK(v6[1].origin == &t1);
2387  BOOST_CHECK(v6[2].origin == &t2);
2388  BOOST_CHECK_EQUAL(v6[0].copies, 1);
2389  BOOST_CHECK_EQUAL(v6[1].copies, 2);
2390  BOOST_CHECK_EQUAL(v6[2].copies, 1);
2391 
2392  auto v7 = Cat(v2, std::move(v4));
2393  BOOST_CHECK_EQUAL(v7.size(), 4U);
2394  BOOST_CHECK(v7[0].origin == &t2);
2395  BOOST_CHECK(v7[1].origin == &t1);
2396  BOOST_CHECK(v7[2].origin == &t2);
2397  BOOST_CHECK(v7[3].origin == &t3);
2398  BOOST_CHECK_EQUAL(v7[0].copies, 1);
2399  BOOST_CHECK_EQUAL(v7[1].copies, 1);
2400  BOOST_CHECK_EQUAL(v7[2].copies, 1);
2401  BOOST_CHECK_EQUAL(v7[3].copies, 0);
2402 
2403  auto v8 = Cat(std::move(v2), std::move(v3));
2404  BOOST_CHECK_EQUAL(v8.size(), 3U);
2405  BOOST_CHECK(v8[0].origin == &t2);
2406  BOOST_CHECK(v8[1].origin == &t1);
2407  BOOST_CHECK(v8[2].origin == &t2);
2408  BOOST_CHECK_EQUAL(v8[0].copies, 0);
2409  BOOST_CHECK_EQUAL(v8[1].copies, 1);
2410  BOOST_CHECK_EQUAL(v8[2].copies, 0);
2411 }
2412 
2414 {
2415  const std::array<unsigned char, 32> privkey_bytes = {
2416  // just some random data
2417  // derived address from this private key: 15CRxFdyRpGZLW9w8HnHvVduizdL5jKNbs
2418  0xD9, 0x7F, 0x51, 0x08, 0xF1, 0x1C, 0xDA, 0x6E,
2419  0xEE, 0xBA, 0xAA, 0x42, 0x0F, 0xEF, 0x07, 0x26,
2420  0xB1, 0xF8, 0x98, 0x06, 0x0B, 0x98, 0x48, 0x9F,
2421  0xA3, 0x09, 0x84, 0x63, 0xC0, 0x03, 0x28, 0x66
2422  };
2423 
2424  const std::string message = "Trust no one";
2425 
2426  const std::string expected_signature =
2427  "IPojfrX2dfPnH26UegfbGQQLrdK844DlHq5157/P6h57WyuS/Qsl+h/WSVGDF4MUi4rWSswW38oimDYfNNUBUOk=";
2428 
2429  CKey privkey;
2430  std::string generated_signature;
2431 
2432  BOOST_REQUIRE_MESSAGE(!privkey.IsValid(),
2433  "Confirm the private key is invalid");
2434 
2435  BOOST_CHECK_MESSAGE(!MessageSign(privkey, message, generated_signature),
2436  "Sign with an invalid private key");
2437 
2438  privkey.Set(privkey_bytes.begin(), privkey_bytes.end(), true);
2439 
2440  BOOST_REQUIRE_MESSAGE(privkey.IsValid(),
2441  "Confirm the private key is valid");
2442 
2443  BOOST_CHECK_MESSAGE(MessageSign(privkey, message, generated_signature),
2444  "Sign with a valid private key");
2445 
2446  BOOST_CHECK_EQUAL(expected_signature, generated_signature);
2447 }
2448 
2449 BOOST_AUTO_TEST_CASE(message_verify)
2450 {
2452  MessageVerify(
2453  "invalid address",
2454  "signature should be irrelevant",
2455  "message too"),
2457 
2459  MessageVerify(
2460  "3B5fQsEXEaV8v6U3ejYc8XaKXAkyQj2MjV",
2461  "signature should be irrelevant",
2462  "message too"),
2464 
2466  MessageVerify(
2467  "1KqbBpLy5FARmTPD4VZnDDpYjkUvkr82Pm",
2468  "invalid signature, not in base64 encoding",
2469  "message should be irrelevant"),
2471 
2473  MessageVerify(
2474  "1KqbBpLy5FARmTPD4VZnDDpYjkUvkr82Pm",
2475  "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=",
2476  "message should be irrelevant"),
2478 
2480  MessageVerify(
2481  "15CRxFdyRpGZLW9w8HnHvVduizdL5jKNbs",
2482  "IPojfrX2dfPnH26UegfbGQQLrdK844DlHq5157/P6h57WyuS/Qsl+h/WSVGDF4MUi4rWSswW38oimDYfNNUBUOk=",
2483  "I never signed this"),
2485 
2487  MessageVerify(
2488  "15CRxFdyRpGZLW9w8HnHvVduizdL5jKNbs",
2489  "IPojfrX2dfPnH26UegfbGQQLrdK844DlHq5157/P6h57WyuS/Qsl+h/WSVGDF4MUi4rWSswW38oimDYfNNUBUOk=",
2490  "Trust no one"),
2492 
2494  MessageVerify(
2495  "11canuhp9X2NocwCq7xNrQYTmUgZAnLK3",
2496  "IIcaIENoYW5jZWxsb3Igb24gYnJpbmsgb2Ygc2Vjb25kIGJhaWxvdXQgZm9yIGJhbmtzIAaHRtbCeDZINyavx14=",
2497  "Trust me"),
2499 }
2500 
2502 {
2503  const std::string unsigned_tx = "...";
2504  const std::string prefixed_message =
2505  std::string(1, (char)MESSAGE_MAGIC.length()) +
2506  MESSAGE_MAGIC +
2507  std::string(1, (char)unsigned_tx.length()) +
2508  unsigned_tx;
2509 
2510  const uint256 signature_hash = Hash(unsigned_tx);
2511  const uint256 message_hash1 = Hash(prefixed_message);
2512  const uint256 message_hash2 = MessageHash(unsigned_tx);
2513 
2514  BOOST_CHECK_EQUAL(message_hash1, message_hash2);
2515  BOOST_CHECK_NE(message_hash1, signature_hash);
2516 }
2517 
2518 BOOST_AUTO_TEST_CASE(remove_prefix)
2519 {
2520  BOOST_CHECK_EQUAL(RemovePrefix("./util/system.h", "./"), "util/system.h");
2521  BOOST_CHECK_EQUAL(RemovePrefix("foo", "foo"), "");
2522  BOOST_CHECK_EQUAL(RemovePrefix("foo", "fo"), "o");
2523  BOOST_CHECK_EQUAL(RemovePrefix("foo", "f"), "oo");
2524  BOOST_CHECK_EQUAL(RemovePrefix("foo", ""), "foo");
2525  BOOST_CHECK_EQUAL(RemovePrefix("fo", "foo"), "fo");
2526  BOOST_CHECK_EQUAL(RemovePrefix("f", "foo"), "f");
2527  BOOST_CHECK_EQUAL(RemovePrefix("", "foo"), "");
2528  BOOST_CHECK_EQUAL(RemovePrefix("", ""), "");
2529 }
2530 
2531 BOOST_AUTO_TEST_CASE(util_ParseByteUnits)
2532 {
2533  auto noop = ByteUnit::NOOP;
2534 
2535  // no multiplier
2536  BOOST_CHECK_EQUAL(ParseByteUnits("1", noop).value(), 1);
2537  BOOST_CHECK_EQUAL(ParseByteUnits("0", noop).value(), 0);
2538 
2539  BOOST_CHECK_EQUAL(ParseByteUnits("1k", noop).value(), 1000ULL);
2540  BOOST_CHECK_EQUAL(ParseByteUnits("1K", noop).value(), 1ULL << 10);
2541 
2542  BOOST_CHECK_EQUAL(ParseByteUnits("2m", noop).value(), 2'000'000ULL);
2543  BOOST_CHECK_EQUAL(ParseByteUnits("2M", noop).value(), 2ULL << 20);
2544 
2545  BOOST_CHECK_EQUAL(ParseByteUnits("3g", noop).value(), 3'000'000'000ULL);
2546  BOOST_CHECK_EQUAL(ParseByteUnits("3G", noop).value(), 3ULL << 30);
2547 
2548  BOOST_CHECK_EQUAL(ParseByteUnits("4t", noop).value(), 4'000'000'000'000ULL);
2549  BOOST_CHECK_EQUAL(ParseByteUnits("4T", noop).value(), 4ULL << 40);
2550 
2551  // check default multiplier
2552  BOOST_CHECK_EQUAL(ParseByteUnits("5", ByteUnit::K).value(), 5ULL << 10);
2553 
2554  // NaN
2555  BOOST_CHECK(!ParseByteUnits("", noop));
2556  BOOST_CHECK(!ParseByteUnits("foo", noop));
2557 
2558  // whitespace
2559  BOOST_CHECK(!ParseByteUnits("123m ", noop));
2560  BOOST_CHECK(!ParseByteUnits(" 123m", noop));
2561 
2562  // no +-
2563  BOOST_CHECK(!ParseByteUnits("-123m", noop));
2564  BOOST_CHECK(!ParseByteUnits("+123m", noop));
2565 
2566  // zero padding
2567  BOOST_CHECK_EQUAL(ParseByteUnits("020M", noop).value(), 20ULL << 20);
2568 
2569  // fractions not allowed
2570  BOOST_CHECK(!ParseByteUnits("0.5T", noop));
2571 
2572  // overflow
2573  BOOST_CHECK(!ParseByteUnits("18446744073709551615g", noop));
2574 
2575  // invalid unit
2576  BOOST_CHECK(!ParseByteUnits("1x", noop));
2577 }
2578 
2579 BOOST_AUTO_TEST_SUITE_END()
ForEachNoDup
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.
Definition: str.h:32
ArgsMergeTestingSetup::Action
Action
Definition: util_tests.cpp:920
ChainMergeTestingSetup::ActionList
Action[MAX_ACTIONS] ActionList
Definition: util_tests.cpp:1097
MessageSign
bool MessageSign(const CKey &privkey, const std::string &message, std::string &signature)
Sign a message.
Definition: message.cpp:56
FormatISO8601Date
std::string FormatISO8601Date(int64_t nTime)
Definition: time.cpp:145
MakeByteSpan
Span< const std::byte > MakeByteSpan(V &&v) noexcept
Definition: span.h:264
ParseInt64
bool ParseInt64(const std::string &str, int64_t *out)
Convert string to signed 64-bit integer with strict parse error feedback.
Definition: strencodings.cpp:304
Parse
std::unique_ptr< Descriptor > Parse(const std::string &descriptor, FlatSigningProvider &out, std::string &error, bool require_checksum)
Parse a descriptor string.
Definition: descriptor.cpp:1394
BCLog::LogEscapeMessage
std::string LogEscapeMessage(const std::string &str)
Belts and suspenders: make sure outgoing log messages don't contain potentially suspicious characters...
Definition: logging.cpp:236
str.h
ArgsManager::GetBoolArg
bool GetBoolArg(const std::string &strArg, bool fDefault) const
Return boolean argument or default value.
Definition: system.cpp:600
ArgsManager::ClearPathCache
void ClearPathCache()
Clear cached directory paths.
Definition: system.cpp:456
MessageVerificationResult::ERR_MALFORMED_SIGNATURE
@ ERR_MALFORMED_SIGNATURE
The provided signature couldn't be parsed (maybe invalid base64).
MakeUCharSpan
constexpr auto MakeUCharSpan(V &&v) -> decltype(UCharSpanCast(Span
Like the Span constructor, but for (const) unsigned char member types only.
Definition: span.h:285
ParseHex
std::vector< unsigned char > ParseHex(const char *psz)
Definition: strencodings.cpp:84
ToString
std::string ToString(const T &t)
Locale-independent version of std::to_string.
Definition: string.h:87
CheckValueTest::Expect
Definition: util_tests.cpp:262
ReleaseDirectoryLocks
void ReleaseDirectoryLocks()
Release all directory locks.
Definition: system.cpp:128
assert
assert(!tx.IsCoinBase())
TestArgsManager::TestArgsManager
TestArgsManager()
Definition: util_tests.cpp:227
CheckValueTest::Expect::String
Expect & String(const char *s)
Definition: util_tests.cpp:277
CheckValueTest::Expect::int_value
std::optional< int64_t > int_value
Definition: util_tests.cpp:268
TestArgsManager
Definition: util_tests.cpp:225
ByteUnit::M
@ M
ParseFixedPoint
bool ParseFixedPoint(const std::string &val, int decimals, int64_t *amount_out)
Parse number as fixed point according to JSON number syntax.
Definition: strencodings.cpp:398
util::Settings
Stored settings.
Definition: settings.h:31
DirIsWritable
bool DirIsWritable(const fs::path &directory)
Definition: system.cpp:134
fs.h
CHash256::Write
CHash256 & Write(Span< const unsigned char > input)
Definition: hash.h:37
TestArgsManager::GetSetting
util::SettingsValue GetSetting(const std::string &arg) const
Get setting value.
Definition: system.cpp:1021
fsbridge::fopen
FILE * fopen(const fs::path &p, const char *mode)
Definition: fs.cpp:27
flags
int flags
Definition: bitcoin-tx.cpp:529
CheckValueTest::Expect::List
Expect & List(std::vector< std::string > m)
Definition: util_tests.cpp:280
ArgsManager::GetSetting
util::SettingsValue GetSetting(const std::string &arg) const
Get setting value.
Definition: system.cpp:1021
setup_common.h
ArgsMergeTestingSetup::ForEachMergeSetup
void ForEachMergeSetup(Fn &&fn)
Enumerate all possible test configurations.
Definition: util_tests.cpp:925
moneystr.h
sync.h
Cat
V Cat(V v1, V &&v2)
Concatenate two vectors, moving elements.
Definition: vector.h:31
string.h
ParseISO8601DateTime
int64_t ParseISO8601DateTime(const std::string &str)
Definition: time.cpp:158
uint256.h
ArgsManager::ALLOW_ANY
@ ALLOW_ANY
disable validation
Definition: system.h:172
CKey::Set
void Set(const T pbegin, const T pend, bool fCompressedIn)
Initialize using begin and end iterators to byte data.
Definition: key.h:73
ArgsManager::GetChainName
std::string GetChainName() const
Returns the appropriate chain name from the program arguments.
Definition: system.cpp:987
CheckValueTest
Test GetSetting and GetArg type coercion, negation, and default value handling.
Definition: util_tests.cpp:259
FormatSubVersion
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...
Definition: clientversion.cpp:59
ArgsManager::IsArgSet
bool IsArgSet(const std::string &strArg) const
Return true if the given argument has been manually set.
Definition: system.cpp:494
CheckValueTest::Expect::bool_value
std::optional< bool > bool_value
Definition: util_tests.cpp:269
spanparsing::Split
std::vector< Span< const char > > Split(const Span< const char > &sp, char sep)
Split a string on every instance of sep, returning a vector.
Definition: spanparsing.cpp:51
ArgsMergeTestingSetup
Definition: util_tests.cpp:915
CBaseChainParams::TESTNET
static const std::string TESTNET
Definition: chainparamsbase.h:23
MessageVerify
MessageVerificationResult MessageVerify(const std::string &address, const std::string &signature, const std::string &message)
Verify a signed message.
Definition: message.cpp:24
MessageVerificationResult::ERR_NOT_SIGNED
@ ERR_NOT_SIGNED
The message was not signed with the private key of the provided address.
AnnotatedMixin< std::recursive_mutex >
SAFE_CHARS_UA_COMMENT
@ SAFE_CHARS_UA_COMMENT
BIP-0014 subset.
Definition: strencodings.h:28
spanparsing::Func
bool Func(const std::string &str, Span< const char > &sp)
Parse a function call.
Definition: spanparsing.cpp:23
clientversion.h
expect
#define expect(bit)
Definition: univalue_read.cpp:255
ChainMergeTestingSetup::Action
Action
Definition: util_tests.cpp:1096
ParseHex_expected
static const unsigned char ParseHex_expected[65]
Definition: util_tests.cpp:114
TRY_LOCK
#define TRY_LOCK(cs, name)
Definition: sync.h:230
TrimString
std::string TrimString(const std::string &str, const std::string &pattern=" \f\n\r\t\v")
Definition: string.h:18
TestArgsManager::GetSettingsList
std::vector< util::SettingsValue > GetSettingsList(const std::string &arg) const
Get list of setting values.
Definition: system.cpp:1028
fs::PathToString
static std::string PathToString(const path &path)
Convert path object to a byte string.
Definition: fs.h:112
UniValue::write
std::string write(unsigned int prettyIndent=0, unsigned int indentLevel=0) const
Definition: univalue_write.cpp:28
BOOST_AUTO_TEST_CASE
BOOST_AUTO_TEST_CASE(util_datadir)
Definition: util_tests.cpp:54
BOOST_FIXTURE_TEST_SUITE
#define BOOST_FIXTURE_TEST_SUITE(a, b)
Definition: object.cpp:14
atoi64_legacy
int64_t atoi64_legacy(const std::string &str)
Definition: util_tests.cpp:1627
ParseUInt16
bool ParseUInt16(const std::string &str, uint16_t *out)
Convert decimal string to unsigned 16-bit integer with strict parse error feedback.
Definition: strencodings.cpp:314
FormatISO8601DateTime
std::string FormatISO8601DateTime(int64_t nTime)
ISO 8601 formatting is preferred.
Definition: time.cpp:132
Assert
#define Assert(val)
Identity function.
Definition: check.h:57
TestOtherThread
static void TestOtherThread(fs::path dirname, std::string lockname, bool *result)
Definition: util_tests.cpp:2001
LockDirectory
bool LockDirectory(const fs::path &directory, const std::string lockfile_name, bool probe_only)
Definition: system.cpp:98
UniValue
Definition: univalue.h:17
cs
static void pool cs
Definition: mempool_eviction.cpp:12
TestArgsManager::ReadConfigStream
bool ReadConfigStream(std::istream &stream, const std::string &filepath, std::string &error, bool ignore_invalid_keys=false)
Definition: system.cpp:867
prefix
const char * prefix
Definition: rest.cpp:926
NoIncludeConfTest::Parse
std::string Parse(const char *arg)
Definition: util_tests.cpp:364
ArgsManager::GetDataDirBase
const fs::path & GetDataDirBase() const
Get data directory path.
Definition: system.h:296
CheckValueTest::Expect::DefaultBool
Expect & DefaultBool()
Definition: util_tests.cpp:276
Span
A Span is an object that can refer to a contiguous sequence of objects.
Definition: span.h:96
Assume
#define Assume(val)
Assume is the identity function.
Definition: check.h:72
ChainMergeTestingSetup::ForEachMergeSetup
void ForEachMergeSetup(Fn &&fn)
Enumerate all possible test configurations.
Definition: util_tests.cpp:1101
strencodings.h
ChainMergeTestingSetup
Definition: util_tests.cpp:1093
ArgsManager::cs_args
RecursiveMutex cs_args
Definition: system.h:199
Hash
uint256 Hash(const T &in1)
Compute the 256-bit hash of an object.
Definition: hash.h:75
ASSERT_DEBUG_LOG
#define ASSERT_DEBUG_LOG(message)
Definition: logging.h:39
BOOST_FIXTURE_TEST_CASE
BOOST_FIXTURE_TEST_CASE(util_CheckValue, CheckValueTest)
Definition: util_tests.cpp:344
values
static const int64_t values[]
A selection of numbers that do not trigger int64_t overflow when added/subtracted.
Definition: scriptnum_tests.cpp:17
fs::path
Path class wrapper to block calls to the fs::path(std::string) implicit constructor and the fs::path:...
Definition: fs.h:29
ArgsManager::SoftSetArg
bool SoftSetArg(const std::string &strArg, const std::string &strValue)
Set an argument if it doesn't already have a value.
Definition: system.cpp:606
ExitCommand
static constexpr char ExitCommand
Definition: util_tests.cpp:2009
message.h
ArgsMergeTestingSetup::GetValues
std::vector< std::string > GetValues(const ActionList &actions, const std::string &section, const std::string &name, const std::string &value_prefix)
Translate actions into a list of <key>=setting strings.
Definition: util_tests.cpp:948
ArgsManager::AddArg
void AddArg(const std::string &name, const std::string &help, unsigned int flags, const OptionsCategory &cat)
Add argument.
Definition: system.cpp:640
CheckValueTest::Expect::setting
util::SettingsValue setting
Definition: util_tests.cpp:263
ArgsManager::WriteSettingsFile
bool WriteSettingsFile(std::vector< std::string > *errors=nullptr) const
Write settings file.
Definition: system.cpp:563
univalue.h
TestParse
static void TestParse(const std::string &str, bool expected_bool, int64_t expected_int)
Definition: util_tests.cpp:440
time.h
CKey::IsValid
bool IsValid() const
Check whether this private key is valid.
Definition: key.h:93
ArgsManager::GetUnsuitableSectionOnlyArgs
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...
Definition: system.cpp:255
ArgsManager::ForceSetArg
void ForceSetArg(const std::string &strArg, const std::string &strValue)
Definition: system.cpp:622
ArgsManager::GetArg
std::string GetArg(const std::string &strArg, const std::string &strDefault) const
Return string argument or default value.
Definition: system.cpp:588
MessageVerificationResult::ERR_INVALID_ADDRESS
@ ERR_INVALID_ADDRESS
The provided address is invalid.
CAmount
int64_t CAmount
Amount in satoshis (Can be negative)
Definition: amount.h:12
OptionsCategory::OPTIONS
@ OPTIONS
Span::begin
constexpr C * begin() const noexcept
Definition: span.h:174
CHash256::Finalize
void Finalize(Span< unsigned char > output)
Definition: hash.h:30
BasicTestingSetup
Basic testing setup.
Definition: setup_common.h:83
CheckValueTest::CheckValue
void CheckValue(unsigned int flags, const char *arg, const Expect &expect)
Definition: util_tests.cpp:284
Capitalize
std::string Capitalize(std::string str)
Capitalizes the first character of the given string.
Definition: strencodings.cpp:504
ToUpper
std::string ToUpper(const std::string &str)
Returns the uppercase equivalent of the given string.
Definition: strencodings.cpp:497
LockCommand
static constexpr char LockCommand
Definition: util_tests.cpp:2007
TestChain100Setup
Testing fixture that pre-creates a 100-block REGTEST-mode block chain.
Definition: setup_common.h:124
ArgsManager::ParseParameters
bool ParseParameters(int argc, const char *const argv[], std::string &error)
Definition: system.cpp:297
spanparsing.h
uint256
256-bit opaque blob.
Definition: uint256.h:126
STRING_WITH_EMBEDDED_NULL_CHAR
static const std::string STRING_WITH_EMBEDDED_NULL_CHAR
Definition: util_tests.cpp:45
MessageVerificationResult::ERR_PUBKEY_NOT_RECOVERED
@ ERR_PUBKEY_NOT_RECOVERED
A public key could not be recovered from the provided signature and message.
RemovePrefix
std::string RemovePrefix(const std::string &str, const std::string &prefix)
Definition: string.h:28
spanparsing::Const
bool Const(const std::string &str, Span< const char > &sp)
Parse a constant.
Definition: spanparsing.cpp:14
CheckValueTest::Expect::Bool
Expect & Bool(bool b)
Definition: util_tests.cpp:279
logging.h
TestArgsManager::SetNetworkOnlyArg
void SetNetworkOnlyArg(const std::string arg)
Definition: util_tests.cpp:239
MessageVerificationResult::ERR_ADDRESS_NO_KEY
@ ERR_ADDRESS_NO_KEY
The provided address is valid but does not refer to a public key.
ArgsManager::ReadConfigStream
bool ReadConfigStream(std::istream &stream, const std::string &filepath, std::string &error, bool ignore_invalid_keys=false)
Definition: system.cpp:867
CBaseChainParams::MAIN
static const std::string MAIN
Chain name strings.
Definition: chainparamsbase.h:22
name
const char * name
Definition: rest.cpp:52
CSHA256::OUTPUT_SIZE
static const size_t OUTPUT_SIZE
Definition: sha256.h:21
ArgsManager::ReadSettingsFile
bool ReadSettingsFile(std::vector< std::string > *errors=nullptr)
Read settings file.
Definition: system.cpp:540
CheckValueTest::Expect::DefaultInt
Expect & DefaultInt()
Definition: util_tests.cpp:275
ArgsManager::SelectConfigNetwork
void SelectConfigNetwork(const std::string &network)
Select the network in use.
Definition: system.cpp:291
system.h
ArgsManager::LockSettings
void LockSettings(Fn &&fn)
Access settings with lock held.
Definition: system.h:453
key.h
ParseUInt64
bool ParseUInt64(const std::string &str, uint64_t *out)
Convert decimal string to unsigned 64-bit integer with strict parse error feedback.
Definition: strencodings.cpp:324
ArgsMergeTestingSetup::ActionList
Action[MAX_ACTIONS] ActionList
Definition: util_tests.cpp:921
ArgsManager::GetSettingsList
std::vector< util::SettingsValue > GetSettingsList(const std::string &arg) const
Get list of setting values.
Definition: system.cpp:1028
Join
auto Join(const std::vector< T > &list, const BaseType &separator, UnaryOp unary_op) -> decltype(unary_op(list.at(0)))
Join a list of items.
Definition: string.h:44
CheckValueTest::Expect::Error
Expect & Error(const char *e)
Definition: util_tests.cpp:281
ArgsMergeTestingSetup::SET
@ SET
Definition: util_tests.cpp:920
ArgsManager::IsArgNegated
bool IsArgNegated(const std::string &strArg) const
Return true if the argument was originally passed as a negated option, i.e.
Definition: system.cpp:583
SanitizeString
std::string SanitizeString(const std::string &str, int rule)
Remove unsafe chars.
Definition: strencodings.cpp:27
CheckValueTest::Expect::Expect
Expect(util::SettingsValue s)
Definition: util_tests.cpp:273
CheckValueTest::Expect::Int
Expect & Int(int64_t i)
Definition: util_tests.cpp:278
CheckValueTest::Expect::list_value
std::optional< std::vector< std::string > > list_value
Definition: util_tests.cpp:270
BCLog
Definition: timer.h:18
CKey
An encapsulated private key.
Definition: key.h:26
ArgsManager
Definition: system.h:164
Vector
std::vector< typename std::common_type< Args... >::type > Vector(Args &&... args)
Construct a vector with the specified elements.
Definition: vector.h:20
vector.h
LOCK
#define LOCK(cs)
Definition: sync.h:226
ParseMoney
std::optional< CAmount > ParseMoney(const std::string &money_string)
Parse an amount denoted in full coins.
Definition: moneystr.cpp:41
spanparsing::Expr
Span< const char > Expr(Span< const char > &sp)
Extract the expression that sp begins with.
Definition: spanparsing.cpp:32
std
Definition: setup_common.h:33
fs::create_directories
static bool create_directories(const std::filesystem::path &p)
Create directory (and if necessary its parents), unless the leaf directory already exists or is a sym...
Definition: fs.h:150
ByteUnit::NOOP
@ NOOP
MessageVerificationResult::OK
@ OK
The message verification was successful.
TestArgsManager::ReadConfigString
void ReadConfigString(const std::string str_config)
Definition: util_tests.cpp:228
getuniquepath.h
BOOST_CHECK_THROW
#define BOOST_CHECK_THROW(stmt, excMatch)
Definition: object.cpp:19
NoIncludeConfTest
Definition: util_tests.cpp:363
util::Settings::rw_settings
std::map< std::string, SettingsValue > rw_settings
Map of setting name to read-write file setting value.
Definition: settings.h:37
CHash256
A hasher class for Bitcoin's 256-bit hash (double SHA-256).
Definition: hash.h:24
ParseByteUnits
std::optional< uint64_t > ParseByteUnits(const std::string &str, ByteUnit default_multiplier)
Parse a string with suffix unit [k|K|m|M|g|G|t|T].
Definition: strencodings.cpp:525
SpanToStr
static std::string SpanToStr(const Span< const char > &span)
Definition: util_tests.cpp:2178
TestArgsManager::SetupArgs
void SetupArgs(const std::vector< std::pair< std::string, unsigned int >> &args)
Definition: util_tests.cpp:244
ArgsManager::GetArgs
std::vector< std::string > GetArgs(const std::string &strArg) const
Return a vector of strings of the given argument.
Definition: system.cpp:485
error
bool error(const char *fmt, const Args &... args)
Definition: system.h:49
spanparsing
Definition: spanparsing.cpp:12
COIN
static constexpr CAmount COIN
The amount of satoshis in one BTC.
Definition: amount.h:15
MESSAGE_MAGIC
const std::string MESSAGE_MAGIC
Text used to signify that a signed message follows and to prevent inadvertently signing a transaction...
Definition: message.cpp:22
HexStr
std::string HexStr(const Span< const uint8_t > s)
Convert a span of bytes to a lower-case hexadecimal string.
Definition: strencodings.cpp:511
ArgsManager::GetIntArg
int64_t GetIntArg(const std::string &strArg, int64_t nDefault) const
Return integer argument or default value.
Definition: system.cpp:594
UnlockCommand
static constexpr char UnlockCommand
Definition: util_tests.cpp:2008
ByteUnit::m
@ m
TestArgsManager::cs_args
RecursiveMutex cs_args
Definition: system.h:199
MakeWritableByteSpan
Span< std::byte > MakeWritableByteSpan(V &&v) noexcept
Definition: span.h:269
ParseUInt8
bool ParseUInt8(const std::string &str, uint8_t *out)
Convert decimal string to unsigned 8-bit integer with strict parse error feedback.
Definition: strencodings.cpp:309
overflow.h
GetUniquePath
fs::path GetUniquePath(const fs::path &base)
Helper function for getting a unique path.
Definition: getuniquepath.cpp:9
Span::end
constexpr C * end() const noexcept
Definition: span.h:175
ParseUInt32
bool ParseUInt32(const std::string &str, uint32_t *out)
Convert decimal string to unsigned 32-bit integer with strict parse error feedback.
Definition: strencodings.cpp:319
BOOST_CHECK
#define BOOST_CHECK(expr)
Definition: object.cpp:17
BOOST_CHECK_EQUAL
#define BOOST_CHECK_EQUAL(v1, v2)
Definition: object.cpp:18
FormatParagraph
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.
Definition: strencodings.cpp:329
TestOtherProcess
static void TestOtherProcess(fs::path dirname, std::string lockname, int fd)
Definition: util_tests.cpp:2011
ByteUnit::t
@ t
CheckValueTest::Expect::DefaultString
Expect & DefaultString()
Definition: util_tests.cpp:274
CBaseChainParams::SIGNET
static const std::string SIGNET
Definition: chainparamsbase.h:24
args
ArgsManager args
Definition: notifications.cpp:36
GetTimeSeconds
int64_t GetTimeSeconds()
Returns the system time (not mockable)
Definition: time.cpp:127
ToLower
std::string ToLower(const std::string &str)
Returns the lowercase equivalent of the given string.
Definition: strencodings.cpp:490
FormatMoney
std::string FormatMoney(const CAmount n)
Money parsing/formatting utilities.
Definition: moneystr.cpp:15
MessageHash
uint256 MessageHash(const std::string &message)
Hashes a message for signing and verification in a manner that prevents inadvertently signing a trans...
Definition: message.cpp:72
ChainMergeTestingSetup::NONE
@ NONE
Definition: util_tests.cpp:1096