util_tests.cpp raw

   1  // Copyright (c) 2011-present 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 <clientversion.h>
   6  #include <common/signmessage.h>
   7  #include <hash.h>
   8  #include <key.h>
   9  #include <script/parsing.h>
  10  #include <span.h>
  11  #include <sync.h>
  12  #include <test/util/common.h>
  13  #include <test/util/random.h>
  14  #include <test/util/setup_common.h>
  15  #include <test/util/time.h>
  16  #include <uint256.h>
  17  #include <univalue.h>
  18  #include <util/bitdeque.h>
  19  #include <util/byte_units.h>
  20  #include <util/fs.h>
  21  #include <util/fs_helpers.h>
  22  #include <util/moneystr.h>
  23  #include <util/overflow.h>
  24  #include <util/readwritefile.h>
  25  #include <util/strencodings.h>
  26  #include <util/string.h>
  27  #include <util/time.h>
  28  #include <util/vector.h>
  29  
  30  #include <array>
  31  #include <cmath>
  32  #include <cstdint>
  33  #include <cstring>
  34  #include <fstream>
  35  #include <limits>
  36  #include <map>
  37  #include <optional>
  38  #include <string>
  39  #include <thread>
  40  #include <type_traits>
  41  #include <utility>
  42  #include <vector>
  43  
  44  #include <sys/types.h>
  45  
  46  #ifndef WIN32
  47  #include <sys/wait.h>
  48  #endif
  49  
  50  #include <boost/test/unit_test.hpp>
  51  
  52  using namespace std::literals;
  53  using namespace util::hex_literals;
  54  using util::ConstevalHexDigit;
  55  using util::Join;
  56  using util::RemovePrefix;
  57  using util::RemovePrefixView;
  58  using util::ReplaceAll;
  59  using util::Split;
  60  using util::SplitString;
  61  using util::TrimString;
  62  using util::TrimStringView;
  63  
  64  static const std::string STRING_WITH_EMBEDDED_NULL_CHAR{"1"s "\0" "1"s};
  65  
  66  /* defined in logging.cpp */
  67  namespace BCLog {
  68      std::string LogEscapeMessage(std::string_view str);
  69  }
  70  
  71  BOOST_FIXTURE_TEST_SUITE(util_tests, BasicTestingSetup)
  72  
  73  namespace {
  74  class NoCopyOrMove
  75  {
  76  public:
  77      int i;
  78      explicit NoCopyOrMove(int i) : i{i} { }
  79  
  80      NoCopyOrMove() = delete;
  81      NoCopyOrMove(const NoCopyOrMove&) = delete;
  82      NoCopyOrMove(NoCopyOrMove&&) = delete;
  83      NoCopyOrMove& operator=(const NoCopyOrMove&) = delete;
  84      NoCopyOrMove& operator=(NoCopyOrMove&&) = delete;
  85  
  86      operator bool() const { return i != 0; }
  87  
  88      int get_ip1() { return i + 1; }
  89      bool test()
  90      {
  91          // Check that Assume can be used within a lambda and still call methods
  92          [&]() { Assume(get_ip1()); }();
  93          return Assume(get_ip1() != 5);
  94      }
  95  };
  96  } // namespace
  97  
  98  BOOST_AUTO_TEST_CASE(util_check)
  99  {
 100      // Check that Assert can forward
 101      const std::unique_ptr<int> p_two = Assert(std::make_unique<int>(2));
 102      // Check that Assert works on lvalues and rvalues
 103      const int two = *Assert(p_two);
 104      Assert(two == 2);
 105      Assert(true);
 106      // Check that Assume can be used as unary expression
 107      const bool result{Assume(two == 2)};
 108      Assert(result);
 109  
 110      // Check that Assert doesn't require copy/move
 111      NoCopyOrMove x{9};
 112      Assert(x).i += 3;
 113      Assert(x).test();
 114  
 115      // Check nested Asserts
 116      BOOST_CHECK_EQUAL(Assert((Assert(x).test() ? 3 : 0)), 3);
 117  
 118      // Check -Wdangling-gsl does not trigger when copying the int. (It would
 119      // trigger on "const int&")
 120      const int nine{*Assert(std::optional<int>{9})};
 121      BOOST_CHECK_EQUAL(9, nine);
 122  }
 123  
 124  BOOST_AUTO_TEST_CASE(util_criticalsection)
 125  {
 126      RecursiveMutex cs;
 127  
 128      do {
 129          LOCK(cs);
 130          break;
 131  
 132          BOOST_ERROR("break was swallowed!");
 133      } while(0);
 134  
 135      do {
 136          TRY_LOCK(cs, lockTest);
 137          if (lockTest) {
 138              BOOST_CHECK(true); // Needed to suppress "Test case [...] did not check any assertions"
 139              break;
 140          }
 141  
 142          BOOST_ERROR("break was swallowed!");
 143      } while(0);
 144  }
 145  
 146  constexpr char HEX_PARSE_INPUT[] = "04678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5f";
 147  constexpr uint8_t HEX_PARSE_OUTPUT[] = {
 148      0x04, 0x67, 0x8a, 0xfd, 0xb0, 0xfe, 0x55, 0x48, 0x27, 0x19, 0x67, 0xf1, 0xa6, 0x71, 0x30, 0xb7,
 149      0x10, 0x5c, 0xd6, 0xa8, 0x28, 0xe0, 0x39, 0x09, 0xa6, 0x79, 0x62, 0xe0, 0xea, 0x1f, 0x61, 0xde,
 150      0xb6, 0x49, 0xf6, 0xbc, 0x3f, 0x4c, 0xef, 0x38, 0xc4, 0xf3, 0x55, 0x04, 0xe5, 0x1e, 0xc1, 0x12,
 151      0xde, 0x5c, 0x38, 0x4d, 0xf7, 0xba, 0x0b, 0x8d, 0x57, 0x8a, 0x4c, 0x70, 0x2b, 0x6b, 0xf1, 0x1d,
 152      0x5f
 153  };
 154  static_assert((sizeof(HEX_PARSE_INPUT) - 1) == 2 * sizeof(HEX_PARSE_OUTPUT));
 155  BOOST_AUTO_TEST_CASE(parse_hex)
 156  {
 157      std::vector<unsigned char> result;
 158  
 159      // Basic test vector
 160      std::vector<unsigned char> expected(std::begin(HEX_PARSE_OUTPUT), std::end(HEX_PARSE_OUTPUT));
 161      constexpr std::array<std::byte, 65> hex_literal_array{operator""_hex<util::detail::Hex(HEX_PARSE_INPUT)>()};
 162      auto hex_literal_span{MakeUCharSpan(hex_literal_array)};
 163      BOOST_CHECK_EQUAL_COLLECTIONS(hex_literal_span.begin(), hex_literal_span.end(), expected.begin(), expected.end());
 164  
 165      const std::vector<std::byte> hex_literal_vector{operator""_hex_v<util::detail::Hex(HEX_PARSE_INPUT)>()};
 166      auto hex_literal_vec_span = MakeUCharSpan(hex_literal_vector);
 167      BOOST_CHECK_EQUAL_COLLECTIONS(hex_literal_vec_span.begin(), hex_literal_vec_span.end(), expected.begin(), expected.end());
 168  
 169      constexpr std::array<uint8_t, 65> hex_literal_array_uint8{operator""_hex_u8<util::detail::Hex(HEX_PARSE_INPUT)>()};
 170      BOOST_CHECK_EQUAL_COLLECTIONS(hex_literal_array_uint8.begin(), hex_literal_array_uint8.end(), expected.begin(), expected.end());
 171  
 172      result = operator""_hex_v_u8<util::detail::Hex(HEX_PARSE_INPUT)>();
 173      BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
 174  
 175      result = ParseHex(HEX_PARSE_INPUT);
 176      BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
 177  
 178      result = TryParseHex<uint8_t>(HEX_PARSE_INPUT).value();
 179      BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
 180  
 181      // Spaces between bytes must be supported
 182      expected = {0x12, 0x34, 0x56, 0x78};
 183      result = ParseHex("12 34 56 78");
 184      BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
 185      result = TryParseHex<uint8_t>("12 34 56 78").value();
 186      BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
 187  
 188      // Leading space must be supported
 189      expected = {0x89, 0x34, 0x56, 0x78};
 190      result = ParseHex(" 89 34 56 78");
 191      BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
 192      result = TryParseHex<uint8_t>(" 89 34 56 78").value();
 193      BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
 194  
 195      // Mixed case and spaces are supported
 196      expected = {0xff, 0xaa};
 197      result = ParseHex("     Ff        aA    ");
 198      BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
 199      result = TryParseHex<uint8_t>("     Ff        aA    ").value();
 200      BOOST_CHECK_EQUAL_COLLECTIONS(result.begin(), result.end(), expected.begin(), expected.end());
 201  
 202      // Empty string is supported
 203      static_assert(""_hex.empty());
 204      static_assert(""_hex_u8.empty());
 205      BOOST_CHECK_EQUAL(""_hex_v.size(), 0);
 206      BOOST_CHECK_EQUAL(""_hex_v_u8.size(), 0);
 207      BOOST_CHECK_EQUAL(ParseHex("").size(), 0);
 208      BOOST_CHECK_EQUAL(TryParseHex<uint8_t>("").value().size(), 0);
 209  
 210      // Spaces between nibbles is treated as invalid
 211      BOOST_CHECK_EQUAL(ParseHex("AAF F").size(), 0);
 212      BOOST_CHECK(!TryParseHex("AAF F").has_value());
 213  
 214      // Embedded null is treated as invalid
 215      const std::string with_embedded_null{" 11 "s
 216                                           " \0 "
 217                                           " 22 "s};
 218      BOOST_CHECK_EQUAL(with_embedded_null.size(), 11);
 219      BOOST_CHECK_EQUAL(ParseHex(with_embedded_null).size(), 0);
 220      BOOST_CHECK(!TryParseHex(with_embedded_null).has_value());
 221  
 222      // Non-hex is treated as invalid
 223      BOOST_CHECK_EQUAL(ParseHex("1234 invalid 1234").size(), 0);
 224      BOOST_CHECK(!TryParseHex("1234 invalid 1234").has_value());
 225  
 226      // Truncated input is treated as invalid
 227      BOOST_CHECK_EQUAL(ParseHex("12 3").size(), 0);
 228      BOOST_CHECK(!TryParseHex("12 3").has_value());
 229  }
 230  
 231  BOOST_AUTO_TEST_CASE(consteval_hex_digit)
 232  {
 233      BOOST_CHECK_EQUAL(ConstevalHexDigit('0'), 0);
 234      BOOST_CHECK_EQUAL(ConstevalHexDigit('9'), 9);
 235      BOOST_CHECK_EQUAL(ConstevalHexDigit('a'), 0xa);
 236      BOOST_CHECK_EQUAL(ConstevalHexDigit('f'), 0xf);
 237  }
 238  
 239  BOOST_AUTO_TEST_CASE(util_HexStr)
 240  {
 241      BOOST_CHECK_EQUAL(HexStr(HEX_PARSE_OUTPUT), HEX_PARSE_INPUT);
 242      BOOST_CHECK_EQUAL(HexStr(std::span{HEX_PARSE_OUTPUT}.last(0)), "");
 243      BOOST_CHECK_EQUAL(HexStr(std::span{HEX_PARSE_OUTPUT}.first(0)), "");
 244  
 245      {
 246          constexpr std::string_view out_exp{"04678afdb0"};
 247          constexpr std::span in_s{HEX_PARSE_OUTPUT, out_exp.size() / 2};
 248          const std::span<const uint8_t> in_u{MakeUCharSpan(in_s)};
 249          const std::span<const std::byte> in_b{MakeByteSpan(in_s)};
 250  
 251          BOOST_CHECK_EQUAL(HexStr(in_u), out_exp);
 252          BOOST_CHECK_EQUAL(HexStr(in_s), out_exp);
 253          BOOST_CHECK_EQUAL(HexStr(in_b), out_exp);
 254      }
 255  
 256      {
 257          auto input = std::string();
 258          for (size_t i=0; i<256; ++i) {
 259              input.push_back(static_cast<char>(i));
 260          }
 261  
 262          auto hex = HexStr(input);
 263          BOOST_TEST_REQUIRE(hex.size() == 512);
 264          static constexpr auto hexmap = std::string_view("0123456789abcdef");
 265          for (size_t i = 0; i < 256; ++i) {
 266              auto upper = hexmap.find(hex[i * 2]);
 267              auto lower = hexmap.find(hex[i * 2 + 1]);
 268              BOOST_TEST_REQUIRE(upper != std::string_view::npos);
 269              BOOST_TEST_REQUIRE(lower != std::string_view::npos);
 270              BOOST_TEST_REQUIRE(i == upper*16 + lower);
 271          }
 272      }
 273  }
 274  
 275  BOOST_AUTO_TEST_CASE(span_write_bytes)
 276  {
 277      std::array mut_arr{uint8_t{0xaa}, uint8_t{0xbb}};
 278      const auto mut_bytes{MakeWritableByteSpan(mut_arr)};
 279      mut_bytes[1] = std::byte{0x11};
 280      BOOST_CHECK_EQUAL(mut_arr.at(0), 0xaa);
 281      BOOST_CHECK_EQUAL(mut_arr.at(1), 0x11);
 282  }
 283  
 284  BOOST_AUTO_TEST_CASE(util_Join)
 285  {
 286      // Normal version
 287      BOOST_CHECK_EQUAL(Join(std::vector<std::string>{}, ", "), "");
 288      BOOST_CHECK_EQUAL(Join(std::vector<std::string>{"foo"}, ", "), "foo");
 289      BOOST_CHECK_EQUAL(Join(std::vector<std::string>{"foo", "bar"}, ", "), "foo, bar");
 290  
 291      // Version with unary operator
 292      const auto op_upper = [](const std::string& s) { return ToUpper(s); };
 293      BOOST_CHECK_EQUAL(Join(std::list<std::string>{}, ", ", op_upper), "");
 294      BOOST_CHECK_EQUAL(Join(std::list<std::string>{"foo"}, ", ", op_upper), "FOO");
 295      BOOST_CHECK_EQUAL(Join(std::list<std::string>{"foo", "bar"}, ", ", op_upper), "FOO, BAR");
 296  }
 297  
 298  BOOST_AUTO_TEST_CASE(util_ReplaceAll)
 299  {
 300      const std::string original("A test \"%s\" string '%s'.");
 301      auto test_replaceall = [&original](const std::string& search, const std::string& substitute, const std::string& expected) {
 302          auto test = original;
 303          ReplaceAll(test, search, substitute);
 304          BOOST_CHECK_EQUAL(test, expected);
 305      };
 306  
 307      test_replaceall("", "foo", original);
 308      test_replaceall(original, "foo", "foo");
 309      test_replaceall("%s", "foo", "A test \"foo\" string 'foo'.");
 310      test_replaceall("\"", "foo", "A test foo%sfoo string '%s'.");
 311      test_replaceall("'", "foo", "A test \"%s\" string foo%sfoo.");
 312  }
 313  
 314  BOOST_AUTO_TEST_CASE(util_TrimString)
 315  {
 316      BOOST_CHECK_EQUAL(TrimString(" foo bar "), "foo bar");
 317      BOOST_CHECK_EQUAL(TrimStringView("\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");
 318      BOOST_CHECK_EQUAL(TrimString("\t \n foo \n\tbar\t \n "), "foo \n\tbar");
 319      BOOST_CHECK_EQUAL(TrimStringView("\t \n foo \n\tbar\t \n ", "fobar"), "\t \n foo \n\tbar\t \n ");
 320      BOOST_CHECK_EQUAL(TrimString("foo bar"), "foo bar");
 321      BOOST_CHECK_EQUAL(TrimStringView("foo bar", "fobar"), " ");
 322      BOOST_CHECK_EQUAL(TrimString(std::string("\0 foo \0 ", 8)), std::string("\0 foo \0", 7));
 323      BOOST_CHECK_EQUAL(TrimStringView(std::string(" foo ", 5)), std::string("foo", 3));
 324      BOOST_CHECK_EQUAL(TrimString(std::string("\t\t\0\0\n\n", 6)), std::string("\0\0", 2));
 325      BOOST_CHECK_EQUAL(TrimStringView(std::string("\x05\x04\x03\x02\x01\x00", 6)), std::string("\x05\x04\x03\x02\x01\x00", 6));
 326      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));
 327      BOOST_CHECK_EQUAL(TrimStringView(std::string("\x05\x04\x03\x02\x01\x00", 6), std::string("\x05\x04\x03\x02\x01\x00", 6)), "");
 328  }
 329  
 330  BOOST_AUTO_TEST_CASE(util_ParseISO8601DateTime)
 331  {
 332      BOOST_CHECK_EQUAL(ParseISO8601DateTime("1969-12-31T23:59:59Z").value(), -1);
 333      BOOST_CHECK_EQUAL(ParseISO8601DateTime("1970-01-01T00:00:00Z").value(), 0);
 334      BOOST_CHECK_EQUAL(ParseISO8601DateTime("1970-01-01T00:00:01Z").value(), 1);
 335      BOOST_CHECK_EQUAL(ParseISO8601DateTime("2000-01-01T00:00:01Z").value(), 946684801);
 336      BOOST_CHECK_EQUAL(ParseISO8601DateTime("2011-09-30T23:36:17Z").value(), 1317425777);
 337      BOOST_CHECK_EQUAL(ParseISO8601DateTime("2100-12-31T23:59:59Z").value(), 4133980799);
 338      BOOST_CHECK_EQUAL(ParseISO8601DateTime("9999-12-31T23:59:59Z").value(), 253402300799);
 339  
 340      // Accept edge-cases, where the time overflows. They are not produced by
 341      // FormatISO8601DateTime, so this can be changed in the future, if needed.
 342      // For now, keep compatibility with the previous implementation.
 343      BOOST_CHECK_EQUAL(ParseISO8601DateTime("2000-01-01T99:00:00Z").value(), 947041200);
 344      BOOST_CHECK_EQUAL(ParseISO8601DateTime("2000-01-01T00:99:00Z").value(), 946690740);
 345      BOOST_CHECK_EQUAL(ParseISO8601DateTime("2000-01-01T00:00:99Z").value(), 946684899);
 346      BOOST_CHECK_EQUAL(ParseISO8601DateTime("2000-01-01T99:99:99Z").value(), 947047239);
 347  
 348      // Reject date overflows.
 349      BOOST_CHECK(!ParseISO8601DateTime("2000-99-01T00:00:00Z"));
 350      BOOST_CHECK(!ParseISO8601DateTime("2000-01-99T00:00:00Z"));
 351  
 352      // Reject out-of-range years
 353      BOOST_CHECK(!ParseISO8601DateTime("32768-12-31T23:59:59Z"));
 354      BOOST_CHECK(!ParseISO8601DateTime("32767-12-31T23:59:59Z"));
 355      BOOST_CHECK(!ParseISO8601DateTime("32767-12-31T00:00:00Z"));
 356      BOOST_CHECK(!ParseISO8601DateTime("999-12-31T00:00:00Z"));
 357  
 358      // Reject invalid format
 359      const std::string valid{"2000-01-01T00:00:01Z"};
 360      BOOST_CHECK(ParseISO8601DateTime(valid).has_value());
 361      for (auto mut{0U}; mut < valid.size(); ++mut) {
 362          std::string invalid{valid};
 363          invalid[mut] = 'a';
 364          BOOST_CHECK(!ParseISO8601DateTime(invalid));
 365      }
 366  }
 367  
 368  BOOST_AUTO_TEST_CASE(util_FormatISO8601DateTime)
 369  {
 370      BOOST_CHECK_EQUAL(FormatISO8601DateTime(971890963199), "32767-12-31T23:59:59Z");
 371      BOOST_CHECK_EQUAL(FormatISO8601DateTime(971890876800), "32767-12-31T00:00:00Z");
 372  
 373      BOOST_CHECK_EQUAL(FormatISO8601DateTime(-1), "1969-12-31T23:59:59Z");
 374      BOOST_CHECK_EQUAL(FormatISO8601DateTime(0), "1970-01-01T00:00:00Z");
 375      BOOST_CHECK_EQUAL(FormatISO8601DateTime(1), "1970-01-01T00:00:01Z");
 376      BOOST_CHECK_EQUAL(FormatISO8601DateTime(946684801), "2000-01-01T00:00:01Z");
 377      BOOST_CHECK_EQUAL(FormatISO8601DateTime(1317425777), "2011-09-30T23:36:17Z");
 378      BOOST_CHECK_EQUAL(FormatISO8601DateTime(4133980799), "2100-12-31T23:59:59Z");
 379      BOOST_CHECK_EQUAL(FormatISO8601DateTime(253402300799), "9999-12-31T23:59:59Z");
 380  }
 381  
 382  BOOST_AUTO_TEST_CASE(util_FormatISO8601Date)
 383  {
 384      BOOST_CHECK_EQUAL(FormatISO8601Date(971890963199), "32767-12-31");
 385      BOOST_CHECK_EQUAL(FormatISO8601Date(971890876800), "32767-12-31");
 386  
 387      BOOST_CHECK_EQUAL(FormatISO8601Date(0), "1970-01-01");
 388      BOOST_CHECK_EQUAL(FormatISO8601Date(1317425777), "2011-09-30");
 389  }
 390  
 391  
 392  BOOST_AUTO_TEST_CASE(util_FormatRFC1123DateTime)
 393  {
 394      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(std::numeric_limits<int64_t>::max()), "");
 395      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(253402300800), "");
 396      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(253402300799), "Fri, 31 Dec 9999 23:59:59 GMT");
 397      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(253402214400), "Fri, 31 Dec 9999 00:00:00 GMT");
 398      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(1717429609), "Mon, 03 Jun 2024 15:46:49 GMT");
 399      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(0), "Thu, 01 Jan 1970 00:00:00 GMT");
 400      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(-1), "Wed, 31 Dec 1969 23:59:59 GMT");
 401      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(-1717429609), "Sat, 31 Jul 1915 08:13:11 GMT");
 402      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(-62167219200), "Sat, 01 Jan 0000 00:00:00 GMT");
 403      BOOST_CHECK_EQUAL(FormatRFC1123DateTime(-62167219201), "");
 404  }
 405  
 406  BOOST_AUTO_TEST_CASE(util_FormatMoney)
 407  {
 408      BOOST_CHECK_EQUAL(FormatMoney(0), "0.00");
 409      BOOST_CHECK_EQUAL(FormatMoney((COIN/10000)*123456789), "12345.6789");
 410      BOOST_CHECK_EQUAL(FormatMoney(-COIN), "-1.00");
 411  
 412      BOOST_CHECK_EQUAL(FormatMoney(COIN*100000000), "100000000.00");
 413      BOOST_CHECK_EQUAL(FormatMoney(COIN*10000000), "10000000.00");
 414      BOOST_CHECK_EQUAL(FormatMoney(COIN*1000000), "1000000.00");
 415      BOOST_CHECK_EQUAL(FormatMoney(COIN*100000), "100000.00");
 416      BOOST_CHECK_EQUAL(FormatMoney(COIN*10000), "10000.00");
 417      BOOST_CHECK_EQUAL(FormatMoney(COIN*1000), "1000.00");
 418      BOOST_CHECK_EQUAL(FormatMoney(COIN*100), "100.00");
 419      BOOST_CHECK_EQUAL(FormatMoney(COIN*10), "10.00");
 420      BOOST_CHECK_EQUAL(FormatMoney(COIN), "1.00");
 421      BOOST_CHECK_EQUAL(FormatMoney(COIN/10), "0.10");
 422      BOOST_CHECK_EQUAL(FormatMoney(COIN/100), "0.01");
 423      BOOST_CHECK_EQUAL(FormatMoney(COIN/1000), "0.001");
 424      BOOST_CHECK_EQUAL(FormatMoney(COIN/10000), "0.0001");
 425      BOOST_CHECK_EQUAL(FormatMoney(COIN/100000), "0.00001");
 426      BOOST_CHECK_EQUAL(FormatMoney(COIN/1000000), "0.000001");
 427      BOOST_CHECK_EQUAL(FormatMoney(COIN/10000000), "0.0000001");
 428      BOOST_CHECK_EQUAL(FormatMoney(COIN/100000000), "0.00000001");
 429  
 430      BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::max()), "92233720368.54775807");
 431      BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::max() - 1), "92233720368.54775806");
 432      BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::max() - 2), "92233720368.54775805");
 433      BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::max() - 3), "92233720368.54775804");
 434      // ...
 435      BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::min() + 3), "-92233720368.54775805");
 436      BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::min() + 2), "-92233720368.54775806");
 437      BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::min() + 1), "-92233720368.54775807");
 438      BOOST_CHECK_EQUAL(FormatMoney(std::numeric_limits<CAmount>::min()), "-92233720368.54775808");
 439  }
 440  
 441  BOOST_AUTO_TEST_CASE(util_ParseMoney)
 442  {
 443      BOOST_CHECK_EQUAL(ParseMoney("0.0").value(), 0);
 444      BOOST_CHECK_EQUAL(ParseMoney(".").value(), 0);
 445      BOOST_CHECK_EQUAL(ParseMoney("0.").value(), 0);
 446      BOOST_CHECK_EQUAL(ParseMoney(".0").value(), 0);
 447      BOOST_CHECK_EQUAL(ParseMoney(".6789").value(), 6789'0000);
 448      BOOST_CHECK_EQUAL(ParseMoney("12345.").value(), COIN * 12345);
 449  
 450      BOOST_CHECK_EQUAL(ParseMoney("12345.6789").value(), (COIN/10000)*123456789);
 451  
 452      BOOST_CHECK_EQUAL(ParseMoney("10000000.00").value(), COIN*10000000);
 453      BOOST_CHECK_EQUAL(ParseMoney("1000000.00").value(), COIN*1000000);
 454      BOOST_CHECK_EQUAL(ParseMoney("100000.00").value(), COIN*100000);
 455      BOOST_CHECK_EQUAL(ParseMoney("10000.00").value(), COIN*10000);
 456      BOOST_CHECK_EQUAL(ParseMoney("1000.00").value(), COIN*1000);
 457      BOOST_CHECK_EQUAL(ParseMoney("100.00").value(), COIN*100);
 458      BOOST_CHECK_EQUAL(ParseMoney("10.00").value(), COIN*10);
 459      BOOST_CHECK_EQUAL(ParseMoney("1.00").value(), COIN);
 460      BOOST_CHECK_EQUAL(ParseMoney("1").value(), COIN);
 461      BOOST_CHECK_EQUAL(ParseMoney("   1").value(), COIN);
 462      BOOST_CHECK_EQUAL(ParseMoney("1   ").value(), COIN);
 463      BOOST_CHECK_EQUAL(ParseMoney("  1 ").value(), COIN);
 464      BOOST_CHECK_EQUAL(ParseMoney("0.1").value(), COIN/10);
 465      BOOST_CHECK_EQUAL(ParseMoney("0.01").value(), COIN/100);
 466      BOOST_CHECK_EQUAL(ParseMoney("0.001").value(), COIN/1000);
 467      BOOST_CHECK_EQUAL(ParseMoney("0.0001").value(), COIN/10000);
 468      BOOST_CHECK_EQUAL(ParseMoney("0.00001").value(), COIN/100000);
 469      BOOST_CHECK_EQUAL(ParseMoney("0.000001").value(), COIN/1000000);
 470      BOOST_CHECK_EQUAL(ParseMoney("0.0000001").value(), COIN/10000000);
 471      BOOST_CHECK_EQUAL(ParseMoney("0.00000001").value(), COIN/100000000);
 472      BOOST_CHECK_EQUAL(ParseMoney(" 0.00000001 ").value(), COIN/100000000);
 473      BOOST_CHECK_EQUAL(ParseMoney("0.00000001 ").value(), COIN/100000000);
 474      BOOST_CHECK_EQUAL(ParseMoney(" 0.00000001").value(), COIN/100000000);
 475  
 476      // Parsing amount that cannot be represented should fail
 477      BOOST_CHECK(!ParseMoney("100000000.00"));
 478      BOOST_CHECK(!ParseMoney("0.000000001"));
 479  
 480      // Parsing empty string should fail
 481      BOOST_CHECK(!ParseMoney(""));
 482      BOOST_CHECK(!ParseMoney(" "));
 483      BOOST_CHECK(!ParseMoney("  "));
 484  
 485      // Parsing two numbers should fail
 486      BOOST_CHECK(!ParseMoney(".."));
 487      BOOST_CHECK(!ParseMoney("0..0"));
 488      BOOST_CHECK(!ParseMoney("1 2"));
 489      BOOST_CHECK(!ParseMoney(" 1 2 "));
 490      BOOST_CHECK(!ParseMoney(" 1.2 3 "));
 491      BOOST_CHECK(!ParseMoney(" 1 2.3 "));
 492  
 493      // Embedded whitespace should fail
 494      BOOST_CHECK(!ParseMoney(" -1 .2  "));
 495      BOOST_CHECK(!ParseMoney("  1 .2  "));
 496      BOOST_CHECK(!ParseMoney(" +1 .2  "));
 497  
 498      // Attempted 63 bit overflow should fail
 499      BOOST_CHECK(!ParseMoney("92233720368.54775808"));
 500  
 501      // Parsing negative amounts must fail
 502      BOOST_CHECK(!ParseMoney("-1"));
 503  
 504      // Parsing strings with embedded NUL characters should fail
 505      BOOST_CHECK(!ParseMoney("\0-1"s));
 506      BOOST_CHECK(!ParseMoney(STRING_WITH_EMBEDDED_NULL_CHAR));
 507      BOOST_CHECK(!ParseMoney("1\0"s));
 508  }
 509  
 510  BOOST_AUTO_TEST_CASE(util_IsHex)
 511  {
 512      BOOST_CHECK(IsHex("00"));
 513      BOOST_CHECK(IsHex("00112233445566778899aabbccddeeffAABBCCDDEEFF"));
 514      BOOST_CHECK(IsHex("ff"));
 515      BOOST_CHECK(IsHex("FF"));
 516  
 517      BOOST_CHECK(!IsHex(""));
 518      BOOST_CHECK(!IsHex("0"));
 519      BOOST_CHECK(!IsHex("a"));
 520      BOOST_CHECK(!IsHex("eleven"));
 521      BOOST_CHECK(!IsHex("00xx00"));
 522      BOOST_CHECK(!IsHex("0x0000"));
 523  }
 524  
 525  BOOST_AUTO_TEST_CASE(util_seed_insecure_rand)
 526  {
 527      SeedRandomForTest(SeedRand::ZEROS);
 528      for (int mod=2;mod<11;mod++)
 529      {
 530          int mask = 1;
 531          // Really rough binomial confidence approximation.
 532          int err = 30*10000./mod*sqrt((1./mod*(1-1./mod))/10000.);
 533          //mask is 2^ceil(log2(mod))-1
 534          while(mask<mod-1)mask=(mask<<1)+1;
 535  
 536          int count = 0;
 537          //How often does it get a zero from the uniform range [0,mod)?
 538          for (int i = 0; i < 10000; i++) {
 539              uint32_t rval;
 540              do{
 541                  rval=m_rng.rand32()&mask;
 542              }while(rval>=(uint32_t)mod);
 543              count += rval==0;
 544          }
 545          BOOST_CHECK(count<=10000/mod+err);
 546          BOOST_CHECK(count>=10000/mod-err);
 547      }
 548  }
 549  
 550  BOOST_AUTO_TEST_CASE(util_TimingResistantEqual)
 551  {
 552      BOOST_CHECK(TimingResistantEqual(std::string(""), std::string("")));
 553      BOOST_CHECK(!TimingResistantEqual(std::string("abc"), std::string("")));
 554      BOOST_CHECK(!TimingResistantEqual(std::string(""), std::string("abc")));
 555      BOOST_CHECK(!TimingResistantEqual(std::string("a"), std::string("aa")));
 556      BOOST_CHECK(!TimingResistantEqual(std::string("aa"), std::string("a")));
 557      BOOST_CHECK(TimingResistantEqual(std::string("abc"), std::string("abc")));
 558      BOOST_CHECK(!TimingResistantEqual(std::string("abc"), std::string("aba")));
 559  }
 560  
 561  /* Test strprintf formatting directives.
 562   * Put a string before and after to ensure sanity of element sizes on stack. */
 563  #define B "check_prefix"
 564  #define E "check_postfix"
 565  BOOST_AUTO_TEST_CASE(strprintf_numbers)
 566  {
 567      int64_t s64t = -9223372036854775807LL; /* signed 64 bit test value */
 568      uint64_t u64t = 18446744073709551615ULL; /* unsigned 64 bit test value */
 569      BOOST_CHECK(strprintf("%s %d %s", B, s64t, E) == B" -9223372036854775807 " E);
 570      BOOST_CHECK(strprintf("%s %u %s", B, u64t, E) == B" 18446744073709551615 " E);
 571      BOOST_CHECK(strprintf("%s %x %s", B, u64t, E) == B" ffffffffffffffff " E);
 572  
 573      size_t st = 12345678; /* unsigned size_t test value */
 574      ssize_t sst = -12345678; /* signed size_t test value */
 575      BOOST_CHECK(strprintf("%s %d %s", B, sst, E) == B" -12345678 " E);
 576      BOOST_CHECK(strprintf("%s %u %s", B, st, E) == B" 12345678 " E);
 577      BOOST_CHECK(strprintf("%s %x %s", B, st, E) == B" bc614e " E);
 578  
 579      ptrdiff_t pt = 87654321; /* positive ptrdiff_t test value */
 580      ptrdiff_t spt = -87654321; /* negative ptrdiff_t test value */
 581      BOOST_CHECK(strprintf("%s %d %s", B, spt, E) == B" -87654321 " E);
 582      BOOST_CHECK(strprintf("%s %u %s", B, pt, E) == B" 87654321 " E);
 583      BOOST_CHECK(strprintf("%s %x %s", B, pt, E) == B" 5397fb1 " E);
 584  }
 585  #undef B
 586  #undef E
 587  
 588  BOOST_AUTO_TEST_CASE(util_mocktime)
 589  {
 590      FakeNodeClock clock{111s};
 591      // Check that mock time does not change after a sleep
 592      for (const auto& num_sleep : {0ms, 1ms}) {
 593          UninterruptibleSleep(num_sleep);
 594          BOOST_CHECK_EQUAL(111, GetTime()); // Deprecated time getter
 595          BOOST_CHECK_EQUAL(111, Now<NodeSeconds>().time_since_epoch().count());
 596          BOOST_CHECK_EQUAL(111, TicksSinceEpoch<std::chrono::seconds>(NodeClock::now()));
 597          BOOST_CHECK_EQUAL(111, TicksSinceEpoch<SecondsDouble>(Now<NodeSeconds>()));
 598          BOOST_CHECK_EQUAL(111, GetTime<std::chrono::seconds>().count());
 599          BOOST_CHECK_EQUAL(111000, GetTime<std::chrono::milliseconds>().count());
 600          BOOST_CHECK_EQUAL(111000, TicksSinceEpoch<std::chrono::milliseconds>(NodeClock::now()));
 601          BOOST_CHECK_EQUAL(111000000, GetTime<std::chrono::microseconds>().count());
 602      }
 603  }
 604  
 605  BOOST_AUTO_TEST_CASE(util_ticksseconds)
 606  {
 607      BOOST_CHECK_EQUAL(TicksSeconds(0s), 0);
 608      BOOST_CHECK_EQUAL(TicksSeconds(1s), 1);
 609      BOOST_CHECK_EQUAL(TicksSeconds(999ms), 0);
 610      BOOST_CHECK_EQUAL(TicksSeconds(1000ms), 1);
 611      BOOST_CHECK_EQUAL(TicksSeconds(1500ms), 1);
 612  }
 613  
 614  BOOST_AUTO_TEST_CASE(test_IsDigit)
 615  {
 616      BOOST_CHECK_EQUAL(IsDigit('0'), true);
 617      BOOST_CHECK_EQUAL(IsDigit('1'), true);
 618      BOOST_CHECK_EQUAL(IsDigit('8'), true);
 619      BOOST_CHECK_EQUAL(IsDigit('9'), true);
 620  
 621      BOOST_CHECK_EQUAL(IsDigit('0' - 1), false);
 622      BOOST_CHECK_EQUAL(IsDigit('9' + 1), false);
 623      BOOST_CHECK_EQUAL(IsDigit(0), false);
 624      BOOST_CHECK_EQUAL(IsDigit(1), false);
 625      BOOST_CHECK_EQUAL(IsDigit(8), false);
 626      BOOST_CHECK_EQUAL(IsDigit(9), false);
 627  }
 628  
 629  /* Check for overflow */
 630  template <typename T>
 631  static void TestAddMatrixOverflow()
 632  {
 633      constexpr T MAXI{std::numeric_limits<T>::max()};
 634      BOOST_CHECK(!CheckedAdd(T{1}, MAXI));
 635      BOOST_CHECK(!CheckedAdd(MAXI, MAXI));
 636      BOOST_CHECK_EQUAL(MAXI, SaturatingAdd(T{1}, MAXI));
 637      BOOST_CHECK_EQUAL(MAXI, SaturatingAdd(MAXI, MAXI));
 638  
 639      BOOST_CHECK_EQUAL(0, CheckedAdd(T{0}, T{0}).value());
 640      BOOST_CHECK_EQUAL(MAXI, CheckedAdd(T{0}, MAXI).value());
 641      BOOST_CHECK_EQUAL(MAXI, CheckedAdd(T{1}, MAXI - 1).value());
 642      BOOST_CHECK_EQUAL(MAXI - 1, CheckedAdd(T{1}, MAXI - 2).value());
 643      BOOST_CHECK_EQUAL(0, SaturatingAdd(T{0}, T{0}));
 644      BOOST_CHECK_EQUAL(MAXI, SaturatingAdd(T{0}, MAXI));
 645      BOOST_CHECK_EQUAL(MAXI, SaturatingAdd(T{1}, MAXI - 1));
 646      BOOST_CHECK_EQUAL(MAXI - 1, SaturatingAdd(T{1}, MAXI - 2));
 647  }
 648  
 649  /* Check for overflow or underflow */
 650  template <typename T>
 651  static void TestAddMatrix()
 652  {
 653      TestAddMatrixOverflow<T>();
 654      constexpr T MINI{std::numeric_limits<T>::min()};
 655      constexpr T MAXI{std::numeric_limits<T>::max()};
 656      BOOST_CHECK(!CheckedAdd(T{-1}, MINI));
 657      BOOST_CHECK(!CheckedAdd(MINI, MINI));
 658      BOOST_CHECK_EQUAL(MINI, SaturatingAdd(T{-1}, MINI));
 659      BOOST_CHECK_EQUAL(MINI, SaturatingAdd(MINI, MINI));
 660  
 661      BOOST_CHECK_EQUAL(MINI, CheckedAdd(T{0}, MINI).value());
 662      BOOST_CHECK_EQUAL(MINI, CheckedAdd(T{-1}, MINI + 1).value());
 663      BOOST_CHECK_EQUAL(-1, CheckedAdd(MINI, MAXI).value());
 664      BOOST_CHECK_EQUAL(MINI + 1, CheckedAdd(T{-1}, MINI + 2).value());
 665      BOOST_CHECK_EQUAL(MINI, SaturatingAdd(T{0}, MINI));
 666      BOOST_CHECK_EQUAL(MINI, SaturatingAdd(T{-1}, MINI + 1));
 667      BOOST_CHECK_EQUAL(MINI + 1, SaturatingAdd(T{-1}, MINI + 2));
 668      BOOST_CHECK_EQUAL(-1, SaturatingAdd(MINI, MAXI));
 669  }
 670  
 671  BOOST_AUTO_TEST_CASE(util_overflow)
 672  {
 673      TestAddMatrixOverflow<unsigned>();
 674      TestAddMatrix<signed>();
 675  }
 676  
 677  template <typename T>
 678  static void RunToIntegralTests()
 679  {
 680      BOOST_CHECK(!ToIntegral<T>(STRING_WITH_EMBEDDED_NULL_CHAR));
 681      BOOST_CHECK(!ToIntegral<T>(" 1"));
 682      BOOST_CHECK(!ToIntegral<T>("1 "));
 683      BOOST_CHECK(!ToIntegral<T>("1a"));
 684      BOOST_CHECK(!ToIntegral<T>("1.1"));
 685      BOOST_CHECK(!ToIntegral<T>("1.9"));
 686      BOOST_CHECK(!ToIntegral<T>("+01.9"));
 687      BOOST_CHECK(!ToIntegral<T>("-"));
 688      BOOST_CHECK(!ToIntegral<T>("+"));
 689      BOOST_CHECK(!ToIntegral<T>(" -1"));
 690      BOOST_CHECK(!ToIntegral<T>("-1 "));
 691      BOOST_CHECK(!ToIntegral<T>(" -1 "));
 692      BOOST_CHECK(!ToIntegral<T>("+1"));
 693      BOOST_CHECK(!ToIntegral<T>(" +1"));
 694      BOOST_CHECK(!ToIntegral<T>(" +1 "));
 695      BOOST_CHECK(!ToIntegral<T>("+-1"));
 696      BOOST_CHECK(!ToIntegral<T>("-+1"));
 697      BOOST_CHECK(!ToIntegral<T>("++1"));
 698      BOOST_CHECK(!ToIntegral<T>("--1"));
 699      BOOST_CHECK(!ToIntegral<T>(""));
 700      BOOST_CHECK(!ToIntegral<T>("aap"));
 701      BOOST_CHECK(!ToIntegral<T>("0x1"));
 702      BOOST_CHECK(!ToIntegral<T>("-32482348723847471234"));
 703      BOOST_CHECK(!ToIntegral<T>("32482348723847471234"));
 704  }
 705  
 706  BOOST_AUTO_TEST_CASE(test_ToIntegral)
 707  {
 708      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("1234").value(), 1'234);
 709      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("0").value(), 0);
 710      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("01234").value(), 1'234);
 711      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("00000000000000001234").value(), 1'234);
 712      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-00000000000000001234").value(), -1'234);
 713      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("00000000000000000000").value(), 0);
 714      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-00000000000000000000").value(), 0);
 715      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-1234").value(), -1'234);
 716      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-1").value(), -1);
 717  
 718      RunToIntegralTests<uint64_t>();
 719      RunToIntegralTests<int64_t>();
 720      RunToIntegralTests<uint32_t>();
 721      RunToIntegralTests<int32_t>();
 722      RunToIntegralTests<uint16_t>();
 723      RunToIntegralTests<int16_t>();
 724      RunToIntegralTests<uint8_t>();
 725      RunToIntegralTests<int8_t>();
 726  
 727      BOOST_CHECK(!ToIntegral<int64_t>("-9223372036854775809"));
 728      BOOST_CHECK_EQUAL(ToIntegral<int64_t>("-9223372036854775808").value(), -9'223'372'036'854'775'807LL - 1LL);
 729      BOOST_CHECK_EQUAL(ToIntegral<int64_t>("9223372036854775807").value(), 9'223'372'036'854'775'807);
 730      BOOST_CHECK(!ToIntegral<int64_t>("9223372036854775808"));
 731  
 732      BOOST_CHECK(!ToIntegral<uint64_t>("-1"));
 733      BOOST_CHECK_EQUAL(ToIntegral<uint64_t>("0").value(), 0U);
 734      BOOST_CHECK_EQUAL(ToIntegral<uint64_t>("18446744073709551615").value(), 18'446'744'073'709'551'615ULL);
 735      BOOST_CHECK(!ToIntegral<uint64_t>("18446744073709551616"));
 736  
 737      BOOST_CHECK(!ToIntegral<int32_t>("-2147483649"));
 738      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("-2147483648").value(), -2'147'483'648LL);
 739      BOOST_CHECK_EQUAL(ToIntegral<int32_t>("2147483647").value(), 2'147'483'647);
 740      BOOST_CHECK(!ToIntegral<int32_t>("2147483648"));
 741  
 742      BOOST_CHECK(!ToIntegral<uint32_t>("-1"));
 743      BOOST_CHECK_EQUAL(ToIntegral<uint32_t>("0").value(), 0U);
 744      BOOST_CHECK_EQUAL(ToIntegral<uint32_t>("4294967295").value(), 4'294'967'295U);
 745      BOOST_CHECK(!ToIntegral<uint32_t>("4294967296"));
 746  
 747      BOOST_CHECK(!ToIntegral<int16_t>("-32769"));
 748      BOOST_CHECK_EQUAL(ToIntegral<int16_t>("-32768").value(), -32'768);
 749      BOOST_CHECK_EQUAL(ToIntegral<int16_t>("32767").value(), 32'767);
 750      BOOST_CHECK(!ToIntegral<int16_t>("32768"));
 751  
 752      BOOST_CHECK(!ToIntegral<uint16_t>("-1"));
 753      BOOST_CHECK_EQUAL(ToIntegral<uint16_t>("0").value(), 0U);
 754      BOOST_CHECK_EQUAL(ToIntegral<uint16_t>("65535").value(), 65'535U);
 755      BOOST_CHECK(!ToIntegral<uint16_t>("65536"));
 756  
 757      BOOST_CHECK(!ToIntegral<int8_t>("-129"));
 758      BOOST_CHECK_EQUAL(ToIntegral<int8_t>("-128").value(), -128);
 759      BOOST_CHECK_EQUAL(ToIntegral<int8_t>("127").value(), 127);
 760      BOOST_CHECK(!ToIntegral<int8_t>("128"));
 761  
 762      BOOST_CHECK(!ToIntegral<uint8_t>("-1"));
 763      BOOST_CHECK_EQUAL(ToIntegral<uint8_t>("0").value(), 0U);
 764      BOOST_CHECK_EQUAL(ToIntegral<uint8_t>("255").value(), 255U);
 765      BOOST_CHECK(!ToIntegral<uint8_t>("256"));
 766  }
 767  
 768  int64_t atoi64_legacy(const std::string& str)
 769  {
 770      return strtoll(str.c_str(), nullptr, 10);
 771  }
 772  
 773  BOOST_AUTO_TEST_CASE(test_LocaleIndependentAtoi)
 774  {
 775      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1234"), 1'234);
 776      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("0"), 0);
 777      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("01234"), 1'234);
 778      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-1234"), -1'234);
 779      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" 1"), 1);
 780      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1 "), 1);
 781      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1a"), 1);
 782      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1.1"), 1);
 783      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("1.9"), 1);
 784      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("+01.9"), 1);
 785      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-1"), -1);
 786      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" -1"), -1);
 787      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-1 "), -1);
 788      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" -1 "), -1);
 789      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("+1"), 1);
 790      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" +1"), 1);
 791      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(" +1 "), 1);
 792  
 793      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("+-1"), 0);
 794      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-+1"), 0);
 795      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("++1"), 0);
 796      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("--1"), 0);
 797      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>(""), 0);
 798      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("aap"), 0);
 799      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("0x1"), 0);
 800      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-32482348723847471234"), -2'147'483'647 - 1);
 801      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("32482348723847471234"), 2'147'483'647);
 802  
 803      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>("-9223372036854775809"), -9'223'372'036'854'775'807LL - 1LL);
 804      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>("-9223372036854775808"), -9'223'372'036'854'775'807LL - 1LL);
 805      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>("9223372036854775807"), 9'223'372'036'854'775'807);
 806      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>("9223372036854775808"), 9'223'372'036'854'775'807);
 807  
 808      std::map<std::string, int64_t> atoi64_test_pairs = {
 809          {"-9223372036854775809", std::numeric_limits<int64_t>::min()},
 810          {"-9223372036854775808", -9'223'372'036'854'775'807LL - 1LL},
 811          {"9223372036854775807", 9'223'372'036'854'775'807},
 812          {"9223372036854775808", std::numeric_limits<int64_t>::max()},
 813          {"+-", 0},
 814          {"0x1", 0},
 815          {"ox1", 0},
 816          {"", 0},
 817      };
 818  
 819      for (const auto& pair : atoi64_test_pairs) {
 820          BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>(pair.first), pair.second);
 821      }
 822  
 823      // Ensure legacy compatibility with previous versions of Bitcoin Core's atoi64
 824      for (const auto& pair : atoi64_test_pairs) {
 825          BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int64_t>(pair.first), atoi64_legacy(pair.first));
 826      }
 827  
 828      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint64_t>("-1"), 0U);
 829      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint64_t>("0"), 0U);
 830      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint64_t>("18446744073709551615"), 18'446'744'073'709'551'615ULL);
 831      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint64_t>("18446744073709551616"), 18'446'744'073'709'551'615ULL);
 832  
 833      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-2147483649"), -2'147'483'648LL);
 834      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("-2147483648"), -2'147'483'648LL);
 835      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("2147483647"), 2'147'483'647);
 836      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int32_t>("2147483648"), 2'147'483'647);
 837  
 838      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint32_t>("-1"), 0U);
 839      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint32_t>("0"), 0U);
 840      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint32_t>("4294967295"), 4'294'967'295U);
 841      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint32_t>("4294967296"), 4'294'967'295U);
 842  
 843      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int16_t>("-32769"), -32'768);
 844      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int16_t>("-32768"), -32'768);
 845      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int16_t>("32767"), 32'767);
 846      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int16_t>("32768"), 32'767);
 847  
 848      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint16_t>("-1"), 0U);
 849      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint16_t>("0"), 0U);
 850      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint16_t>("65535"), 65'535U);
 851      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint16_t>("65536"), 65'535U);
 852  
 853      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int8_t>("-129"), -128);
 854      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int8_t>("-128"), -128);
 855      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int8_t>("127"), 127);
 856      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<int8_t>("128"), 127);
 857  
 858      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint8_t>("-1"), 0U);
 859      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint8_t>("0"), 0U);
 860      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint8_t>("255"), 255U);
 861      BOOST_CHECK_EQUAL(LocaleIndependentAtoi<uint8_t>("256"), 255U);
 862  }
 863  
 864  BOOST_AUTO_TEST_CASE(test_ToIntegralHex)
 865  {
 866      std::optional<uint64_t> n;
 867      // Valid values
 868      n = ToIntegral<uint64_t>("1234", 16);
 869      BOOST_CHECK_EQUAL(*n, 0x1234);
 870      n = ToIntegral<uint64_t>("a", 16);
 871      BOOST_CHECK_EQUAL(*n, 0xA);
 872      n = ToIntegral<uint64_t>("0000000a", 16);
 873      BOOST_CHECK_EQUAL(*n, 0xA);
 874      n = ToIntegral<uint64_t>("100", 16);
 875      BOOST_CHECK_EQUAL(*n, 0x100);
 876      n = ToIntegral<uint64_t>("DEADbeef", 16);
 877      BOOST_CHECK_EQUAL(*n, 0xDEADbeef);
 878      n = ToIntegral<uint64_t>("FfFfFfFf", 16);
 879      BOOST_CHECK_EQUAL(*n, 0xFfFfFfFf);
 880      n = ToIntegral<uint64_t>("123456789", 16);
 881      BOOST_CHECK_EQUAL(*n, 0x123456789ULL);
 882      n = ToIntegral<uint64_t>("0", 16);
 883      BOOST_CHECK_EQUAL(*n, 0);
 884      n = ToIntegral<uint64_t>("FfFfFfFfFfFfFfFf", 16);
 885      BOOST_CHECK_EQUAL(*n, 0xFfFfFfFfFfFfFfFfULL);
 886      BOOST_CHECK_EQUAL(*ToIntegral<int64_t>("-1", 16), -1);
 887      // Invalid values
 888      BOOST_CHECK(!ToIntegral<uint64_t>("", 16));
 889      BOOST_CHECK(!ToIntegral<uint64_t>("-1", 16));
 890      BOOST_CHECK(!ToIntegral<uint64_t>("10 00", 16));
 891      BOOST_CHECK(!ToIntegral<uint64_t>("1 ", 16));
 892      BOOST_CHECK(!ToIntegral<uint64_t>("0xAB", 16));
 893      BOOST_CHECK(!ToIntegral<uint64_t>("FfFfFfFfFfFfFfFf0", 16));
 894  }
 895  
 896  BOOST_AUTO_TEST_CASE(test_FormatParagraph)
 897  {
 898      BOOST_CHECK_EQUAL(FormatParagraph("", 79, 0), "");
 899      BOOST_CHECK_EQUAL(FormatParagraph("test", 79, 0), "test");
 900      BOOST_CHECK_EQUAL(FormatParagraph(" test", 79, 0), " test");
 901      BOOST_CHECK_EQUAL(FormatParagraph("test test", 79, 0), "test test");
 902      BOOST_CHECK_EQUAL(FormatParagraph("test test", 4, 0), "test\ntest");
 903      BOOST_CHECK_EQUAL(FormatParagraph("testerde test", 4, 0), "testerde\ntest");
 904      BOOST_CHECK_EQUAL(FormatParagraph("test test", 4, 4), "test\n    test");
 905  
 906      // Make sure we don't indent a fully-new line following a too-long line ending
 907      BOOST_CHECK_EQUAL(FormatParagraph("test test\nabc", 4, 4), "test\n    test\nabc");
 908  
 909      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");
 910  
 911      // Test wrap length is exact
 912      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");
 913      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");
 914      // Indent should be included in length of lines
 915      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");
 916  
 917      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.");
 918      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.");
 919      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.");
 920      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.");
 921  }
 922  
 923  BOOST_AUTO_TEST_CASE(test_FormatSubVersion)
 924  {
 925      std::vector<std::string> comments;
 926      comments.emplace_back("comment1");
 927      std::vector<std::string> comments2;
 928      comments2.emplace_back("comment1");
 929      comments2.push_back(SanitizeString(std::string("Comment2; .,_?@-; !\"#$%&'()*+/<=>[]\\^`{|}~"), SAFE_CHARS_UA_COMMENT)); // Semicolon is discouraged but not forbidden by BIP-0014
 930      BOOST_CHECK_EQUAL(FormatSubVersion("Test", 99900, std::vector<std::string>()),std::string("/Test:9.99.0/"));
 931      BOOST_CHECK_EQUAL(FormatSubVersion("Test", 99900, comments),std::string("/Test:9.99.0(comment1)/"));
 932      BOOST_CHECK_EQUAL(FormatSubVersion("Test", 99900, comments2),std::string("/Test:9.99.0(comment1; Comment2; .,_?@-; )/"));
 933  }
 934  
 935  BOOST_AUTO_TEST_CASE(test_ParseFixedPoint)
 936  {
 937      int64_t amount = 0;
 938      BOOST_CHECK(ParseFixedPoint("0", 8, &amount));
 939      BOOST_CHECK_EQUAL(amount, 0LL);
 940      BOOST_CHECK(ParseFixedPoint("1", 8, &amount));
 941      BOOST_CHECK_EQUAL(amount, 100000000LL);
 942      BOOST_CHECK(ParseFixedPoint("0.0", 8, &amount));
 943      BOOST_CHECK_EQUAL(amount, 0LL);
 944      BOOST_CHECK(ParseFixedPoint("-0.1", 8, &amount));
 945      BOOST_CHECK_EQUAL(amount, -10000000LL);
 946      BOOST_CHECK(ParseFixedPoint("1.1", 8, &amount));
 947      BOOST_CHECK_EQUAL(amount, 110000000LL);
 948      BOOST_CHECK(ParseFixedPoint("1.10000000000000000", 8, &amount));
 949      BOOST_CHECK_EQUAL(amount, 110000000LL);
 950      BOOST_CHECK(ParseFixedPoint("1.1e1", 8, &amount));
 951      BOOST_CHECK_EQUAL(amount, 1100000000LL);
 952      BOOST_CHECK(ParseFixedPoint("1.1e-1", 8, &amount));
 953      BOOST_CHECK_EQUAL(amount, 11000000LL);
 954      BOOST_CHECK(ParseFixedPoint("1000", 8, &amount));
 955      BOOST_CHECK_EQUAL(amount, 100000000000LL);
 956      BOOST_CHECK(ParseFixedPoint("-1000", 8, &amount));
 957      BOOST_CHECK_EQUAL(amount, -100000000000LL);
 958      BOOST_CHECK(ParseFixedPoint("0.00000001", 8, &amount));
 959      BOOST_CHECK_EQUAL(amount, 1LL);
 960      BOOST_CHECK(ParseFixedPoint("0.0000000100000000", 8, &amount));
 961      BOOST_CHECK_EQUAL(amount, 1LL);
 962      BOOST_CHECK(ParseFixedPoint("-0.00000001", 8, &amount));
 963      BOOST_CHECK_EQUAL(amount, -1LL);
 964      BOOST_CHECK(ParseFixedPoint("1000000000.00000001", 8, &amount));
 965      BOOST_CHECK_EQUAL(amount, 100000000000000001LL);
 966      BOOST_CHECK(ParseFixedPoint("9999999999.99999999", 8, &amount));
 967      BOOST_CHECK_EQUAL(amount, 999999999999999999LL);
 968      BOOST_CHECK(ParseFixedPoint("-9999999999.99999999", 8, &amount));
 969      BOOST_CHECK_EQUAL(amount, -999999999999999999LL);
 970  
 971      BOOST_CHECK(!ParseFixedPoint("", 8, &amount));
 972      BOOST_CHECK(!ParseFixedPoint("-", 8, &amount));
 973      BOOST_CHECK(!ParseFixedPoint("a-1000", 8, &amount));
 974      BOOST_CHECK(!ParseFixedPoint("-a1000", 8, &amount));
 975      BOOST_CHECK(!ParseFixedPoint("-1000a", 8, &amount));
 976      BOOST_CHECK(!ParseFixedPoint("-01000", 8, &amount));
 977      BOOST_CHECK(!ParseFixedPoint("00.1", 8, &amount));
 978      BOOST_CHECK(!ParseFixedPoint(".1", 8, &amount));
 979      BOOST_CHECK(!ParseFixedPoint("--0.1", 8, &amount));
 980      BOOST_CHECK(!ParseFixedPoint("0.000000001", 8, &amount));
 981      BOOST_CHECK(!ParseFixedPoint("-0.000000001", 8, &amount));
 982      BOOST_CHECK(!ParseFixedPoint("0.00000001000000001", 8, &amount));
 983      BOOST_CHECK(!ParseFixedPoint("-10000000000.00000000", 8, &amount));
 984      BOOST_CHECK(!ParseFixedPoint("10000000000.00000000", 8, &amount));
 985      BOOST_CHECK(!ParseFixedPoint("-10000000000.00000001", 8, &amount));
 986      BOOST_CHECK(!ParseFixedPoint("10000000000.00000001", 8, &amount));
 987      BOOST_CHECK(!ParseFixedPoint("-10000000000.00000009", 8, &amount));
 988      BOOST_CHECK(!ParseFixedPoint("10000000000.00000009", 8, &amount));
 989      BOOST_CHECK(!ParseFixedPoint("-99999999999.99999999", 8, &amount));
 990      BOOST_CHECK(!ParseFixedPoint("99999909999.09999999", 8, &amount));
 991      BOOST_CHECK(!ParseFixedPoint("92233720368.54775807", 8, &amount));
 992      BOOST_CHECK(!ParseFixedPoint("92233720368.54775808", 8, &amount));
 993      BOOST_CHECK(!ParseFixedPoint("-92233720368.54775808", 8, &amount));
 994      BOOST_CHECK(!ParseFixedPoint("-92233720368.54775809", 8, &amount));
 995      BOOST_CHECK(!ParseFixedPoint("1.1e", 8, &amount));
 996      BOOST_CHECK(!ParseFixedPoint("1.1e-", 8, &amount));
 997      BOOST_CHECK(!ParseFixedPoint("1.", 8, &amount));
 998  
 999      // Test with 3 decimal places for fee rates in sat/vB.
1000      BOOST_CHECK(ParseFixedPoint("0.001", 3, &amount));
1001      BOOST_CHECK_EQUAL(amount, CAmount{1});
1002      BOOST_CHECK(!ParseFixedPoint("0.0009", 3, &amount));
1003      BOOST_CHECK(!ParseFixedPoint("31.00100001", 3, &amount));
1004      BOOST_CHECK(!ParseFixedPoint("31.0011", 3, &amount));
1005      BOOST_CHECK(!ParseFixedPoint("31.99999999", 3, &amount));
1006      BOOST_CHECK(!ParseFixedPoint("31.999999999999999999999", 3, &amount));
1007  }
1008  
1009  #ifndef WIN32 // Cannot do this test on WIN32 due to lack of fork()
1010  static constexpr char LockCommand = 'L';
1011  static constexpr char UnlockCommand = 'U';
1012  static constexpr char ExitCommand = 'X';
1013  enum : char {
1014      ResSuccess = 2, // Start with 2 to avoid accidental collision with common values 0 and 1
1015      ResErrorWrite,
1016      ResErrorLock,
1017      ResUnlockSuccess,
1018  };
1019  
1020  [[noreturn]] static void TestOtherProcess(fs::path dirname, fs::path lockname, int fd)
1021  {
1022      char ch;
1023      while (true) {
1024          int rv = read(fd, &ch, 1); // Wait for command
1025          assert(rv == 1);
1026          switch (ch) {
1027          case LockCommand:
1028              ch = [&] {
1029                  switch (util::LockDirectory(dirname, lockname)) {
1030                  case util::LockResult::Success: return ResSuccess;
1031                  case util::LockResult::ErrorWrite: return ResErrorWrite;
1032                  case util::LockResult::ErrorLock: return ResErrorLock;
1033                  } // no default case, so the compiler can warn about missing cases
1034                  assert(false);
1035              }();
1036              rv = write(fd, &ch, 1);
1037              assert(rv == 1);
1038              break;
1039          case UnlockCommand:
1040              ReleaseDirectoryLocks();
1041              ch = ResUnlockSuccess; // Always succeeds
1042              rv = write(fd, &ch, 1);
1043              assert(rv == 1);
1044              break;
1045          case ExitCommand:
1046              close(fd);
1047              exit(0);
1048          default:
1049              assert(0);
1050          }
1051      }
1052  }
1053  #endif
1054  
1055  BOOST_AUTO_TEST_CASE(test_LockDirectory)
1056  {
1057      fs::path dirname = m_args.GetDataDirBase() / "lock_dir";
1058      const fs::path lockname = ".lock";
1059  #ifndef WIN32
1060      // Fork another process for testing before creating the lock, so that we
1061      // won't fork while holding the lock (which might be undefined, and is not
1062      // relevant as test case as that is avoided with -daemonize).
1063      int fd[2];
1064      BOOST_CHECK_EQUAL(socketpair(AF_UNIX, SOCK_STREAM, 0, fd), 0);
1065      pid_t pid = fork();
1066      if (!pid) {
1067          BOOST_CHECK_EQUAL(close(fd[1]), 0); // Child: close parent end
1068          TestOtherProcess(dirname, lockname, fd[0]);
1069      }
1070      BOOST_CHECK_EQUAL(close(fd[0]), 0); // Parent: close child end
1071  
1072      char ch;
1073      // Lock on non-existent directory should fail
1074      BOOST_CHECK_EQUAL(write(fd[1], &LockCommand, 1), 1);
1075      BOOST_CHECK_EQUAL(read(fd[1], &ch, 1), 1);
1076      BOOST_CHECK_EQUAL(ch, ResErrorWrite);
1077  #endif
1078      // Lock on non-existent directory should fail
1079      BOOST_CHECK_EQUAL(util::LockDirectory(dirname, lockname), util::LockResult::ErrorWrite);
1080  
1081      fs::create_directories(dirname);
1082  
1083      // Probing lock on new directory should succeed
1084      BOOST_CHECK_EQUAL(util::LockDirectory(dirname, lockname, true), util::LockResult::Success);
1085  
1086      // Persistent lock on new directory should succeed
1087      BOOST_CHECK_EQUAL(util::LockDirectory(dirname, lockname), util::LockResult::Success);
1088  
1089      // Another lock on the directory from the same thread should succeed
1090      BOOST_CHECK_EQUAL(util::LockDirectory(dirname, lockname), util::LockResult::Success);
1091  
1092      // Another lock on the directory from a different thread within the same process should succeed
1093      util::LockResult threadresult;
1094      std::thread thr([&] { threadresult = util::LockDirectory(dirname, lockname); });
1095      thr.join();
1096      BOOST_CHECK_EQUAL(threadresult, util::LockResult::Success);
1097  #ifndef WIN32
1098      // Try to acquire lock in child process while we're holding it, this should fail.
1099      BOOST_CHECK_EQUAL(write(fd[1], &LockCommand, 1), 1);
1100      BOOST_CHECK_EQUAL(read(fd[1], &ch, 1), 1);
1101      BOOST_CHECK_EQUAL(ch, ResErrorLock);
1102  
1103      // Give up our lock
1104      ReleaseDirectoryLocks();
1105      // Probing lock from our side now should succeed, but not hold on to the lock.
1106      BOOST_CHECK_EQUAL(util::LockDirectory(dirname, lockname, true), util::LockResult::Success);
1107  
1108      // Try to acquire the lock in the child process, this should be successful.
1109      BOOST_CHECK_EQUAL(write(fd[1], &LockCommand, 1), 1);
1110      BOOST_CHECK_EQUAL(read(fd[1], &ch, 1), 1);
1111      BOOST_CHECK_EQUAL(ch, ResSuccess);
1112  
1113      // When we try to probe the lock now, it should fail.
1114      BOOST_CHECK_EQUAL(util::LockDirectory(dirname, lockname, true), util::LockResult::ErrorLock);
1115  
1116      // Unlock the lock in the child process
1117      BOOST_CHECK_EQUAL(write(fd[1], &UnlockCommand, 1), 1);
1118      BOOST_CHECK_EQUAL(read(fd[1], &ch, 1), 1);
1119      BOOST_CHECK_EQUAL(ch, ResUnlockSuccess);
1120  
1121      // When we try to probe the lock now, it should succeed.
1122      BOOST_CHECK_EQUAL(util::LockDirectory(dirname, lockname, true), util::LockResult::Success);
1123  
1124      // Re-lock the lock in the child process, then wait for it to exit, check
1125      // successful return. After that, we check that exiting the process
1126      // has released the lock as we would expect by probing it.
1127      int processstatus;
1128      BOOST_CHECK_EQUAL(write(fd[1], &LockCommand, 1), 1);
1129      // The following line invokes the ~CNetCleanup dtor without
1130      // a paired SetupNetworking call. This is acceptable as long as
1131      // ~CNetCleanup is a no-op for non-Windows platforms.
1132      BOOST_CHECK_EQUAL(write(fd[1], &ExitCommand, 1), 1);
1133      BOOST_CHECK_EQUAL(waitpid(pid, &processstatus, 0), pid);
1134      BOOST_CHECK_EQUAL(processstatus, 0);
1135      BOOST_CHECK_EQUAL(util::LockDirectory(dirname, lockname, true), util::LockResult::Success);
1136  
1137      BOOST_CHECK_EQUAL(close(fd[1]), 0); // Close our side of the socketpair
1138  #endif
1139      // Clean up
1140      ReleaseDirectoryLocks();
1141      fs::remove(dirname / lockname);
1142      fs::remove(dirname);
1143  }
1144  
1145  BOOST_AUTO_TEST_CASE(test_ToLower)
1146  {
1147      BOOST_CHECK_EQUAL(ToLower('@'), '@');
1148      BOOST_CHECK_EQUAL(ToLower('A'), 'a');
1149      BOOST_CHECK_EQUAL(ToLower('Z'), 'z');
1150      BOOST_CHECK_EQUAL(ToLower('['), '[');
1151      BOOST_CHECK_EQUAL(ToLower(0), 0);
1152      BOOST_CHECK_EQUAL(ToLower('\xff'), '\xff');
1153  
1154      BOOST_CHECK_EQUAL(ToLower(""), "");
1155      BOOST_CHECK_EQUAL(ToLower("#HODL"), "#hodl");
1156      BOOST_CHECK_EQUAL(ToLower("\x00\xfe\xff"), "\x00\xfe\xff");
1157  }
1158  
1159  BOOST_AUTO_TEST_CASE(test_ToUpper)
1160  {
1161      BOOST_CHECK_EQUAL(ToUpper('`'), '`');
1162      BOOST_CHECK_EQUAL(ToUpper('a'), 'A');
1163      BOOST_CHECK_EQUAL(ToUpper('z'), 'Z');
1164      BOOST_CHECK_EQUAL(ToUpper('{'), '{');
1165      BOOST_CHECK_EQUAL(ToUpper(0), 0);
1166      BOOST_CHECK_EQUAL(ToUpper('\xff'), '\xff');
1167  
1168      BOOST_CHECK_EQUAL(ToUpper(""), "");
1169      BOOST_CHECK_EQUAL(ToUpper("#hodl"), "#HODL");
1170      BOOST_CHECK_EQUAL(ToUpper("\x00\xfe\xff"), "\x00\xfe\xff");
1171  }
1172  
1173  BOOST_AUTO_TEST_CASE(test_Capitalize)
1174  {
1175      BOOST_CHECK_EQUAL(Capitalize(""), "");
1176      BOOST_CHECK_EQUAL(Capitalize("bitcoin"), "Bitcoin");
1177      BOOST_CHECK_EQUAL(Capitalize("\x00\xfe\xff"), "\x00\xfe\xff");
1178  }
1179  
1180  static std::string SpanToStr(const std::span<const char>& span)
1181  {
1182      return std::string(span.begin(), span.end());
1183  }
1184  
1185  BOOST_AUTO_TEST_CASE(test_script_parsing)
1186  {
1187      using namespace script;
1188      std::string input;
1189      std::span<const char> sp;
1190      bool success;
1191  
1192      // Const(...): parse a constant, update span to skip it if successful
1193      input = "MilkToastHoney";
1194      sp = input;
1195      success = Const("", sp); // empty
1196      BOOST_CHECK(success);
1197      BOOST_CHECK_EQUAL(SpanToStr(sp), "MilkToastHoney");
1198  
1199      success = Const("Milk", sp, /*skip=*/false);
1200      BOOST_CHECK(success);
1201      BOOST_CHECK_EQUAL(SpanToStr(sp), "MilkToastHoney");
1202  
1203      success = Const("Milk", sp);
1204      BOOST_CHECK(success);
1205      BOOST_CHECK_EQUAL(SpanToStr(sp), "ToastHoney");
1206  
1207      success = Const("Bread", sp, /*skip=*/false);
1208      BOOST_CHECK(!success);
1209  
1210      success = Const("Bread", sp);
1211      BOOST_CHECK(!success);
1212  
1213      success = Const("Toast", sp, /*skip=*/false);
1214      BOOST_CHECK(success);
1215      BOOST_CHECK_EQUAL(SpanToStr(sp), "ToastHoney");
1216  
1217      success = Const("Toast", sp);
1218      BOOST_CHECK(success);
1219      BOOST_CHECK_EQUAL(SpanToStr(sp), "Honey");
1220  
1221      success = Const("Honeybadger", sp);
1222      BOOST_CHECK(!success);
1223  
1224      success = Const("Honey", sp, /*skip=*/false);
1225      BOOST_CHECK(success);
1226      BOOST_CHECK_EQUAL(SpanToStr(sp), "Honey");
1227  
1228      success = Const("Honey", sp);
1229      BOOST_CHECK(success);
1230      BOOST_CHECK_EQUAL(SpanToStr(sp), "");
1231      // Func(...): parse a function call, update span to argument if successful
1232      input = "Foo(Bar(xy,z()))";
1233      sp = input;
1234  
1235      success = Func("FooBar", sp);
1236      BOOST_CHECK(!success);
1237  
1238      success = Func("Foo(", sp);
1239      BOOST_CHECK(!success);
1240  
1241      success = Func("Foo", sp);
1242      BOOST_CHECK(success);
1243      BOOST_CHECK_EQUAL(SpanToStr(sp), "Bar(xy,z())");
1244  
1245      success = Func("Bar", sp);
1246      BOOST_CHECK(success);
1247      BOOST_CHECK_EQUAL(SpanToStr(sp), "xy,z()");
1248  
1249      success = Func("xy", sp);
1250      BOOST_CHECK(!success);
1251  
1252      // Expr(...): return expression that span begins with, update span to skip it
1253      std::span<const char> result;
1254  
1255      input = "(n*(n-1))/2";
1256      sp = input;
1257      result = Expr(sp);
1258      BOOST_CHECK_EQUAL(SpanToStr(result), "(n*(n-1))/2");
1259      BOOST_CHECK_EQUAL(SpanToStr(sp), "");
1260  
1261      input = "foo,bar";
1262      sp = input;
1263      result = Expr(sp);
1264      BOOST_CHECK_EQUAL(SpanToStr(result), "foo");
1265      BOOST_CHECK_EQUAL(SpanToStr(sp), ",bar");
1266  
1267      input = "(aaaaa,bbbbb()),c";
1268      sp = input;
1269      result = Expr(sp);
1270      BOOST_CHECK_EQUAL(SpanToStr(result), "(aaaaa,bbbbb())");
1271      BOOST_CHECK_EQUAL(SpanToStr(sp), ",c");
1272  
1273      input = "xyz)foo";
1274      sp = input;
1275      result = Expr(sp);
1276      BOOST_CHECK_EQUAL(SpanToStr(result), "xyz");
1277      BOOST_CHECK_EQUAL(SpanToStr(sp), ")foo");
1278  
1279      input = "((a),(b),(c)),xxx";
1280      sp = input;
1281      result = Expr(sp);
1282      BOOST_CHECK_EQUAL(SpanToStr(result), "((a),(b),(c))");
1283      BOOST_CHECK_EQUAL(SpanToStr(sp), ",xxx");
1284  
1285      // Split(...): split a string on every instance of sep, return vector
1286      std::vector<std::span<const char>> results;
1287  
1288      input = "xxx";
1289      results = Split(input, 'x');
1290      BOOST_CHECK_EQUAL(results.size(), 4U);
1291      BOOST_CHECK_EQUAL(SpanToStr(results[0]), "");
1292      BOOST_CHECK_EQUAL(SpanToStr(results[1]), "");
1293      BOOST_CHECK_EQUAL(SpanToStr(results[2]), "");
1294      BOOST_CHECK_EQUAL(SpanToStr(results[3]), "");
1295  
1296      input = "one#two#three";
1297      results = Split(input, '-');
1298      BOOST_CHECK_EQUAL(results.size(), 1U);
1299      BOOST_CHECK_EQUAL(SpanToStr(results[0]), "one#two#three");
1300  
1301      input = "one#two#three";
1302      results = Split(input, '#');
1303      BOOST_CHECK_EQUAL(results.size(), 3U);
1304      BOOST_CHECK_EQUAL(SpanToStr(results[0]), "one");
1305      BOOST_CHECK_EQUAL(SpanToStr(results[1]), "two");
1306      BOOST_CHECK_EQUAL(SpanToStr(results[2]), "three");
1307  
1308      results = Split(input, '#', /*include_sep=*/true);
1309      BOOST_CHECK_EQUAL(results.size(), 3U);
1310      BOOST_CHECK_EQUAL(SpanToStr(results[0]), "one#");
1311      BOOST_CHECK_EQUAL(SpanToStr(results[1]), "two#");
1312      BOOST_CHECK_EQUAL(SpanToStr(results[2]), "three");
1313  
1314      input = "*foo*bar*";
1315      results = Split(input, '*');
1316      BOOST_CHECK_EQUAL(results.size(), 4U);
1317      BOOST_CHECK_EQUAL(SpanToStr(results[0]), "");
1318      BOOST_CHECK_EQUAL(SpanToStr(results[1]), "foo");
1319      BOOST_CHECK_EQUAL(SpanToStr(results[2]), "bar");
1320      BOOST_CHECK_EQUAL(SpanToStr(results[3]), "");
1321  
1322      results = Split(input, '*', /*include_sep=*/true);
1323      BOOST_CHECK_EQUAL(results.size(), 4U);
1324      BOOST_CHECK_EQUAL(SpanToStr(results[0]), "*");
1325      BOOST_CHECK_EQUAL(SpanToStr(results[1]), "foo*");
1326      BOOST_CHECK_EQUAL(SpanToStr(results[2]), "bar*");
1327      BOOST_CHECK_EQUAL(SpanToStr(results[3]), "");
1328  }
1329  
1330  BOOST_AUTO_TEST_CASE(test_SplitString)
1331  {
1332      // Empty string.
1333      {
1334          std::vector<std::string> result = SplitString("", '-');
1335          BOOST_CHECK_EQUAL(result.size(), 1);
1336          BOOST_CHECK_EQUAL(result[0], "");
1337      }
1338  
1339      // Empty items.
1340      {
1341          std::vector<std::string> result = SplitString("-", '-');
1342          BOOST_CHECK_EQUAL(result.size(), 2);
1343          BOOST_CHECK_EQUAL(result[0], "");
1344          BOOST_CHECK_EQUAL(result[1], "");
1345      }
1346  
1347      // More empty items.
1348      {
1349          std::vector<std::string> result = SplitString("--", '-');
1350          BOOST_CHECK_EQUAL(result.size(), 3);
1351          BOOST_CHECK_EQUAL(result[0], "");
1352          BOOST_CHECK_EQUAL(result[1], "");
1353          BOOST_CHECK_EQUAL(result[2], "");
1354      }
1355  
1356      // Separator is not present.
1357      {
1358          std::vector<std::string> result = SplitString("abc", '-');
1359          BOOST_CHECK_EQUAL(result.size(), 1);
1360          BOOST_CHECK_EQUAL(result[0], "abc");
1361      }
1362  
1363      // Basic behavior.
1364      {
1365          std::vector<std::string> result = SplitString("a-b", '-');
1366          BOOST_CHECK_EQUAL(result.size(), 2);
1367          BOOST_CHECK_EQUAL(result[0], "a");
1368          BOOST_CHECK_EQUAL(result[1], "b");
1369      }
1370  
1371      // Case-sensitivity of the separator.
1372      {
1373          std::vector<std::string> result = SplitString("AAA", 'a');
1374          BOOST_CHECK_EQUAL(result.size(), 1);
1375          BOOST_CHECK_EQUAL(result[0], "AAA");
1376      }
1377  
1378      // multiple split characters
1379      {
1380          using V = std::vector<std::string>;
1381          BOOST_TEST(SplitString("a,b.c:d;e", ",;") == V({"a", "b.c:d", "e"}));
1382          BOOST_TEST(SplitString("a,b.c:d;e", ",;:.") == V({"a", "b", "c", "d", "e"}));
1383          BOOST_TEST(SplitString("a,b.c:d;e", "") == V({"a,b.c:d;e"}));
1384          BOOST_TEST(SplitString("aaa", "bcdefg") == V({"aaa"}));
1385          BOOST_TEST(SplitString("x\0a,b"s, "\0"s) == V({"x", "a,b"}));
1386          BOOST_TEST(SplitString("x\0a,b"s, '\0') == V({"x", "a,b"}));
1387          BOOST_TEST(SplitString("x\0a,b"s, "\0,"s) == V({"x", "a", "b"}));
1388          BOOST_TEST(SplitString("abcdefg", "bcd") == V({"a", "", "", "efg"}));
1389      }
1390  }
1391  
1392  BOOST_AUTO_TEST_CASE(test_LogEscapeMessage)
1393  {
1394      // ASCII and UTF-8 must pass through unaltered.
1395      BOOST_CHECK_EQUAL(BCLog::LogEscapeMessage("Valid log message貓"), "Valid log message貓");
1396      // Newlines must pass through unaltered.
1397      BOOST_CHECK_EQUAL(BCLog::LogEscapeMessage("Message\n with newlines\n"), "Message\n with newlines\n");
1398      // Other control characters are escaped in C syntax.
1399      BOOST_CHECK_EQUAL(BCLog::LogEscapeMessage("\x01\x7f Corrupted log message\x0d"), R"(\x01\x7f Corrupted log message\x0d)");
1400      // Embedded NULL characters are escaped too.
1401      const std::string NUL("O\x00O", 3);
1402      BOOST_CHECK_EQUAL(BCLog::LogEscapeMessage(NUL), R"(O\x00O)");
1403  }
1404  
1405  namespace {
1406  
1407  struct Tracker
1408  {
1409      //! Points to the original object (possibly itself) we moved/copied from
1410      const Tracker* origin;
1411      //! How many copies where involved between the original object and this one (moves are not counted)
1412      int copies{0};
1413  
1414      Tracker() noexcept : origin(this) {}
1415      Tracker(const Tracker& t) noexcept : origin(t.origin), copies(t.copies + 1) {}
1416      Tracker(Tracker&& t) noexcept : origin(t.origin), copies(t.copies) {}
1417      Tracker& operator=(const Tracker& t) noexcept
1418      {
1419          if (this != &t) {
1420              origin = t.origin;
1421              copies = t.copies + 1;
1422          }
1423          return *this;
1424      }
1425  };
1426  
1427  }
1428  
1429  BOOST_AUTO_TEST_CASE(test_tracked_vector)
1430  {
1431      Tracker t1;
1432      Tracker t2;
1433      Tracker t3;
1434  
1435      BOOST_CHECK(t1.origin == &t1);
1436      BOOST_CHECK(t2.origin == &t2);
1437      BOOST_CHECK(t3.origin == &t3);
1438  
1439      auto v1 = Vector(t1);
1440      BOOST_CHECK_EQUAL(v1.size(), 1U);
1441      BOOST_CHECK(v1[0].origin == &t1);
1442      BOOST_CHECK_EQUAL(v1[0].copies, 1);
1443  
1444      auto v2 = Vector(std::move(t2));
1445      BOOST_CHECK_EQUAL(v2.size(), 1U);
1446      BOOST_CHECK(v2[0].origin == &t2); // NOLINT(*-use-after-move)
1447      BOOST_CHECK_EQUAL(v2[0].copies, 0);
1448  
1449      auto v3 = Vector(t1, std::move(t2));
1450      BOOST_CHECK_EQUAL(v3.size(), 2U);
1451      BOOST_CHECK(v3[0].origin == &t1);
1452      BOOST_CHECK(v3[1].origin == &t2); // NOLINT(*-use-after-move)
1453      BOOST_CHECK_EQUAL(v3[0].copies, 1);
1454      BOOST_CHECK_EQUAL(v3[1].copies, 0);
1455  
1456      auto v4 = Vector(std::move(v3[0]), v3[1], std::move(t3));
1457      BOOST_CHECK_EQUAL(v4.size(), 3U);
1458      BOOST_CHECK(v4[0].origin == &t1);
1459      BOOST_CHECK(v4[1].origin == &t2);
1460      BOOST_CHECK(v4[2].origin == &t3); // NOLINT(*-use-after-move)
1461      BOOST_CHECK_EQUAL(v4[0].copies, 1);
1462      BOOST_CHECK_EQUAL(v4[1].copies, 1);
1463      BOOST_CHECK_EQUAL(v4[2].copies, 0);
1464  
1465      auto v5 = Cat(v1, v4);
1466      BOOST_CHECK_EQUAL(v5.size(), 4U);
1467      BOOST_CHECK(v5[0].origin == &t1);
1468      BOOST_CHECK(v5[1].origin == &t1);
1469      BOOST_CHECK(v5[2].origin == &t2);
1470      BOOST_CHECK(v5[3].origin == &t3);
1471      BOOST_CHECK_EQUAL(v5[0].copies, 2);
1472      BOOST_CHECK_EQUAL(v5[1].copies, 2);
1473      BOOST_CHECK_EQUAL(v5[2].copies, 2);
1474      BOOST_CHECK_EQUAL(v5[3].copies, 1);
1475  
1476      auto v6 = Cat(std::move(v1), v3);
1477      BOOST_CHECK_EQUAL(v6.size(), 3U);
1478      BOOST_CHECK(v6[0].origin == &t1);
1479      BOOST_CHECK(v6[1].origin == &t1);
1480      BOOST_CHECK(v6[2].origin == &t2);
1481      BOOST_CHECK_EQUAL(v6[0].copies, 1);
1482      BOOST_CHECK_EQUAL(v6[1].copies, 2);
1483      BOOST_CHECK_EQUAL(v6[2].copies, 1);
1484  
1485      auto v7 = Cat(v2, std::move(v4));
1486      BOOST_CHECK_EQUAL(v7.size(), 4U);
1487      BOOST_CHECK(v7[0].origin == &t2);
1488      BOOST_CHECK(v7[1].origin == &t1);
1489      BOOST_CHECK(v7[2].origin == &t2);
1490      BOOST_CHECK(v7[3].origin == &t3);
1491      BOOST_CHECK_EQUAL(v7[0].copies, 1);
1492      BOOST_CHECK_EQUAL(v7[1].copies, 1);
1493      BOOST_CHECK_EQUAL(v7[2].copies, 1);
1494      BOOST_CHECK_EQUAL(v7[3].copies, 0);
1495  
1496      auto v8 = Cat(std::move(v2), std::move(v3));
1497      BOOST_CHECK_EQUAL(v8.size(), 3U);
1498      BOOST_CHECK(v8[0].origin == &t2);
1499      BOOST_CHECK(v8[1].origin == &t1);
1500      BOOST_CHECK(v8[2].origin == &t2);
1501      BOOST_CHECK_EQUAL(v8[0].copies, 0);
1502      BOOST_CHECK_EQUAL(v8[1].copies, 1);
1503      BOOST_CHECK_EQUAL(v8[2].copies, 0);
1504  }
1505  
1506  BOOST_AUTO_TEST_CASE(message_sign)
1507  {
1508      const std::array<unsigned char, 32> privkey_bytes = {
1509          // just some random data
1510          // derived address from this private key: 15CRxFdyRpGZLW9w8HnHvVduizdL5jKNbs
1511          0xD9, 0x7F, 0x51, 0x08, 0xF1, 0x1C, 0xDA, 0x6E,
1512          0xEE, 0xBA, 0xAA, 0x42, 0x0F, 0xEF, 0x07, 0x26,
1513          0xB1, 0xF8, 0x98, 0x06, 0x0B, 0x98, 0x48, 0x9F,
1514          0xA3, 0x09, 0x84, 0x63, 0xC0, 0x03, 0x28, 0x66
1515      };
1516  
1517      const std::string message = "Trust no one";
1518  
1519      const std::string expected_signature =
1520          "IPojfrX2dfPnH26UegfbGQQLrdK844DlHq5157/P6h57WyuS/Qsl+h/WSVGDF4MUi4rWSswW38oimDYfNNUBUOk=";
1521  
1522      CKey privkey;
1523      std::string generated_signature;
1524  
1525      BOOST_REQUIRE_MESSAGE(!privkey.IsValid(),
1526          "Confirm the private key is invalid");
1527  
1528      BOOST_CHECK_MESSAGE(!MessageSign(privkey, message, generated_signature),
1529          "Sign with an invalid private key");
1530  
1531      privkey.Set(privkey_bytes.begin(), privkey_bytes.end(), true);
1532  
1533      BOOST_REQUIRE_MESSAGE(privkey.IsValid(),
1534          "Confirm the private key is valid");
1535  
1536      BOOST_CHECK_MESSAGE(MessageSign(privkey, message, generated_signature),
1537          "Sign with a valid private key");
1538  
1539      BOOST_CHECK_EQUAL(expected_signature, generated_signature);
1540  }
1541  
1542  BOOST_AUTO_TEST_CASE(message_verify)
1543  {
1544      BOOST_CHECK_EQUAL(
1545          MessageVerify(
1546              "invalid address",
1547              "signature should be irrelevant",
1548              "message too"),
1549          MessageVerificationResult::ERR_INVALID_ADDRESS);
1550  
1551      BOOST_CHECK_EQUAL(
1552          MessageVerify(
1553              "3B5fQsEXEaV8v6U3ejYc8XaKXAkyQj2MjV",
1554              "signature should be irrelevant",
1555              "message too"),
1556          MessageVerificationResult::ERR_ADDRESS_NO_KEY);
1557  
1558      BOOST_CHECK_EQUAL(
1559          MessageVerify(
1560              "1KqbBpLy5FARmTPD4VZnDDpYjkUvkr82Pm",
1561              "invalid signature, not in base64 encoding",
1562              "message should be irrelevant"),
1563          MessageVerificationResult::ERR_MALFORMED_SIGNATURE);
1564  
1565      BOOST_CHECK_EQUAL(
1566          MessageVerify(
1567              "1KqbBpLy5FARmTPD4VZnDDpYjkUvkr82Pm",
1568              "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=",
1569              "message should be irrelevant"),
1570          MessageVerificationResult::ERR_PUBKEY_NOT_RECOVERED);
1571  
1572      BOOST_CHECK_EQUAL(
1573          MessageVerify(
1574              "15CRxFdyRpGZLW9w8HnHvVduizdL5jKNbs",
1575              "IPojfrX2dfPnH26UegfbGQQLrdK844DlHq5157/P6h57WyuS/Qsl+h/WSVGDF4MUi4rWSswW38oimDYfNNUBUOk=",
1576              "I never signed this"),
1577          MessageVerificationResult::ERR_NOT_SIGNED);
1578  
1579      BOOST_CHECK_EQUAL(
1580          MessageVerify(
1581              "15CRxFdyRpGZLW9w8HnHvVduizdL5jKNbs",
1582              "IPojfrX2dfPnH26UegfbGQQLrdK844DlHq5157/P6h57WyuS/Qsl+h/WSVGDF4MUi4rWSswW38oimDYfNNUBUOk=",
1583              "Trust no one"),
1584          MessageVerificationResult::OK);
1585  
1586      BOOST_CHECK_EQUAL(
1587          MessageVerify(
1588              "11canuhp9X2NocwCq7xNrQYTmUgZAnLK3",
1589              "IIcaIENoYW5jZWxsb3Igb24gYnJpbmsgb2Ygc2Vjb25kIGJhaWxvdXQgZm9yIGJhbmtzIAaHRtbCeDZINyavx14=",
1590              "Trust me"),
1591          MessageVerificationResult::OK);
1592  }
1593  
1594  BOOST_AUTO_TEST_CASE(message_hash)
1595  {
1596      const std::string unsigned_tx = "...";
1597      const std::string prefixed_message =
1598          std::string(1, (char)MESSAGE_MAGIC.length()) +
1599          MESSAGE_MAGIC +
1600          std::string(1, (char)unsigned_tx.length()) +
1601          unsigned_tx;
1602  
1603      const uint256 signature_hash = Hash(unsigned_tx);
1604      const uint256 message_hash1 = Hash(prefixed_message);
1605      const uint256 message_hash2 = MessageHash(unsigned_tx);
1606  
1607      BOOST_CHECK_EQUAL(message_hash1, message_hash2);
1608      BOOST_CHECK_NE(message_hash1, signature_hash);
1609  }
1610  
1611  BOOST_AUTO_TEST_CASE(remove_prefix)
1612  {
1613      BOOST_CHECK_EQUAL(RemovePrefix("./common/system.h", "./"), "common/system.h");
1614      BOOST_CHECK_EQUAL(RemovePrefixView("foo", "foo"), "");
1615      BOOST_CHECK_EQUAL(RemovePrefix("foo", "fo"), "o");
1616      BOOST_CHECK_EQUAL(RemovePrefixView("foo", "f"), "oo");
1617      BOOST_CHECK_EQUAL(RemovePrefix("foo", ""), "foo");
1618      BOOST_CHECK_EQUAL(RemovePrefixView("fo", "foo"), "fo");
1619      BOOST_CHECK_EQUAL(RemovePrefix("f", "foo"), "f");
1620      BOOST_CHECK_EQUAL(RemovePrefixView("", "foo"), "");
1621      BOOST_CHECK_EQUAL(RemovePrefix("", ""), "");
1622  }
1623  
1624  BOOST_AUTO_TEST_CASE(util_ParseByteUnits)
1625  {
1626      auto noop = ByteUnit::NOOP;
1627  
1628      // no multiplier
1629      BOOST_CHECK_EQUAL(ParseByteUnits("1", noop).value(), 1);
1630      BOOST_CHECK_EQUAL(ParseByteUnits("0", noop).value(), 0);
1631  
1632      BOOST_CHECK_EQUAL(ParseByteUnits("1k", noop).value(), 1000ULL);
1633      BOOST_CHECK_EQUAL(ParseByteUnits("1K", noop).value(), 1ULL << 10);
1634  
1635      BOOST_CHECK_EQUAL(ParseByteUnits("2m", noop).value(), 2'000'000ULL);
1636      BOOST_CHECK_EQUAL(ParseByteUnits("2M", noop).value(), 2_MiB);
1637  
1638      BOOST_CHECK_EQUAL(ParseByteUnits("3g", noop).value(), 3'000'000'000ULL);
1639      BOOST_CHECK_EQUAL(ParseByteUnits("3G", noop).value(), 3_GiB);
1640  
1641      BOOST_CHECK_EQUAL(ParseByteUnits("4t", noop).value(), 4'000'000'000'000ULL);
1642      BOOST_CHECK_EQUAL(ParseByteUnits("4T", noop).value(), 4ULL << 40);
1643  
1644      // check default multiplier
1645      BOOST_CHECK_EQUAL(ParseByteUnits("5", ByteUnit::K).value(), 5ULL << 10);
1646  
1647      // NaN
1648      BOOST_CHECK(!ParseByteUnits("", noop));
1649      BOOST_CHECK(!ParseByteUnits("foo", noop));
1650  
1651      // whitespace
1652      BOOST_CHECK(!ParseByteUnits("123m ", noop));
1653      BOOST_CHECK(!ParseByteUnits(" 123m", noop));
1654  
1655      // no +-
1656      BOOST_CHECK(!ParseByteUnits("-123m", noop));
1657      BOOST_CHECK(!ParseByteUnits("+123m", noop));
1658  
1659      // zero padding
1660      BOOST_CHECK_EQUAL(ParseByteUnits("020M", noop).value(), 20_MiB);
1661  
1662      // fractions not allowed
1663      BOOST_CHECK(!ParseByteUnits("0.5T", noop));
1664  
1665      // overflow
1666      BOOST_CHECK(!ParseByteUnits("18446744073709551615g", noop));
1667  
1668      // invalid unit
1669      BOOST_CHECK(!ParseByteUnits("1x", noop));
1670  }
1671  
1672  BOOST_AUTO_TEST_CASE(util_ReadBinaryFile)
1673  {
1674      fs::path tmpfolder = m_args.GetDataDirBase();
1675      fs::path tmpfile = tmpfolder / "read_binary.dat";
1676      std::string expected_text;
1677      for (int i = 0; i < 30; i++) {
1678          expected_text += "0123456789";
1679      }
1680      {
1681          std::ofstream file{tmpfile.std_path()};
1682          file << expected_text;
1683      }
1684      {
1685          // read all contents in file
1686          auto [valid, text] = ReadBinaryFile(tmpfile);
1687          BOOST_CHECK(valid);
1688          BOOST_CHECK_EQUAL(text, expected_text);
1689      }
1690      {
1691          // read half contents in file
1692          auto [valid, text] = ReadBinaryFile(tmpfile, expected_text.size() / 2);
1693          BOOST_CHECK(valid);
1694          BOOST_CHECK_EQUAL(text, expected_text.substr(0, expected_text.size() / 2));
1695      }
1696      {
1697          // read from non-existent file
1698          fs::path invalid_file = tmpfolder / "invalid_binary.dat";
1699          auto [valid, text] = ReadBinaryFile(invalid_file);
1700          BOOST_CHECK(!valid);
1701          BOOST_CHECK(text.empty());
1702      }
1703  }
1704  
1705  BOOST_AUTO_TEST_CASE(util_WriteBinaryFile)
1706  {
1707      fs::path tmpfolder = m_args.GetDataDirBase();
1708      fs::path tmpfile = tmpfolder / "write_binary.dat";
1709      std::string expected_text = "bitcoin";
1710      auto valid = WriteBinaryFile(tmpfile, expected_text);
1711      std::string actual_text;
1712      std::ifstream file{tmpfile.std_path()};
1713      file >> actual_text;
1714      BOOST_CHECK(valid);
1715      BOOST_CHECK_EQUAL(actual_text, expected_text);
1716  }
1717  
1718  BOOST_AUTO_TEST_CASE(clearshrink_test)
1719  {
1720      {
1721          std::vector<uint8_t> v = {1, 2, 3};
1722          ClearShrink(v);
1723          BOOST_CHECK_EQUAL(v.size(), 0);
1724          BOOST_CHECK_EQUAL(v.capacity(), 0);
1725      }
1726  
1727      {
1728          std::vector<bool> v = {false, true, false, false, true, true};
1729          ClearShrink(v);
1730          BOOST_CHECK_EQUAL(v.size(), 0);
1731          BOOST_CHECK_EQUAL(v.capacity(), 0);
1732      }
1733  
1734      {
1735          std::deque<int> v = {1, 3, 3, 7};
1736          ClearShrink(v);
1737          BOOST_CHECK_EQUAL(v.size(), 0);
1738          // std::deque has no capacity() we can observe.
1739      }
1740  }
1741  
1742  template <typename T>
1743  void TestCheckedLeftShift()
1744  {
1745      constexpr auto MAX{std::numeric_limits<T>::max()};
1746  
1747      // Basic operations
1748      BOOST_CHECK_EQUAL(CheckedLeftShift<T>(0, 1), 0);
1749      BOOST_CHECK_EQUAL(CheckedLeftShift<T>(0, 127), 0);
1750      BOOST_CHECK_EQUAL(CheckedLeftShift<T>(1, 1), 2);
1751      BOOST_CHECK_EQUAL(CheckedLeftShift<T>(2, 2), 8);
1752      BOOST_CHECK_EQUAL(CheckedLeftShift<T>(MAX >> 1, 1), MAX - 1);
1753  
1754      // Max left shift
1755      BOOST_CHECK_EQUAL(CheckedLeftShift<T>(1, std::numeric_limits<T>::digits - 1), MAX / 2 + 1);
1756  
1757      // Overflow cases
1758      BOOST_CHECK(!CheckedLeftShift<T>((MAX >> 1) + 1, 1));
1759      BOOST_CHECK(!CheckedLeftShift<T>(MAX, 1));
1760      BOOST_CHECK(!CheckedLeftShift<T>(1, std::numeric_limits<T>::digits));
1761      BOOST_CHECK(!CheckedLeftShift<T>(1, std::numeric_limits<T>::digits + 1));
1762  
1763      if constexpr (std::is_signed_v<T>) {
1764          constexpr auto MIN{std::numeric_limits<T>::min()};
1765          // Negative input
1766          BOOST_CHECK_EQUAL(CheckedLeftShift<T>(-1, 1), -2);
1767          BOOST_CHECK_EQUAL(CheckedLeftShift<T>((MIN >> 2), 1), MIN / 2);
1768          BOOST_CHECK_EQUAL(CheckedLeftShift<T>((MIN >> 1) + 1, 1), MIN + 2);
1769          BOOST_CHECK_EQUAL(CheckedLeftShift<T>(MIN >> 1, 1), MIN);
1770          // Overflow negative
1771          BOOST_CHECK(!CheckedLeftShift<T>((MIN >> 1) - 1, 1));
1772          BOOST_CHECK(!CheckedLeftShift<T>(MIN >> 1, 2));
1773          BOOST_CHECK(!CheckedLeftShift<T>(-1, 100));
1774      }
1775  }
1776  
1777  template <typename T>
1778  void TestSaturatingLeftShift()
1779  {
1780      constexpr auto MAX{std::numeric_limits<T>::max()};
1781  
1782      // Basic operations
1783      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(0, 1), 0);
1784      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(0, 127), 0);
1785      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(1, 1), 2);
1786      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(2, 2), 8);
1787      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(MAX >> 1, 1), MAX - 1);
1788  
1789      // Max left shift
1790      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(1, std::numeric_limits<T>::digits - 1), MAX / 2 + 1);
1791  
1792      // Saturation cases
1793      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>((MAX >> 1) + 1, 1), MAX);
1794      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(MAX, 1), MAX);
1795      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(1, std::numeric_limits<T>::digits), MAX);
1796      BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(1, std::numeric_limits<T>::digits + 1), MAX);
1797  
1798      if constexpr (std::is_signed_v<T>) {
1799          constexpr auto MIN{std::numeric_limits<T>::min()};
1800          // Negative input
1801          BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(-1, 1), -2);
1802          BOOST_CHECK_EQUAL(SaturatingLeftShift<T>((MIN >> 2), 1), MIN / 2);
1803          BOOST_CHECK_EQUAL(SaturatingLeftShift<T>((MIN >> 1) + 1, 1), MIN + 2);
1804          BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(MIN >> 1, 1), MIN);
1805          // Saturation negative
1806          BOOST_CHECK_EQUAL(SaturatingLeftShift<T>((MIN >> 1) - 1, 1), MIN);
1807          BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(MIN >> 1, 2), MIN);
1808          BOOST_CHECK_EQUAL(SaturatingLeftShift<T>(-1, 100), MIN);
1809      }
1810  }
1811  
1812  BOOST_AUTO_TEST_CASE(checked_left_shift_test)
1813  {
1814      TestCheckedLeftShift<uint8_t>();
1815      TestCheckedLeftShift<int8_t>();
1816      TestCheckedLeftShift<size_t>();
1817      TestCheckedLeftShift<uint64_t>();
1818      TestCheckedLeftShift<int64_t>();
1819  }
1820  
1821  BOOST_AUTO_TEST_CASE(saturating_left_shift_test)
1822  {
1823      TestSaturatingLeftShift<uint8_t>();
1824      TestSaturatingLeftShift<int8_t>();
1825      TestSaturatingLeftShift<size_t>();
1826      TestSaturatingLeftShift<uint64_t>();
1827      TestSaturatingLeftShift<int64_t>();
1828  }
1829  
1830  template <class Int, auto bytes>
1831  concept BraceInitializesTo = requires { Int{bytes}; };
1832  
1833  BOOST_AUTO_TEST_CASE(mib_string_literal_test)
1834  {
1835      // Basic equivalences and simple arithmetic operations
1836      BOOST_CHECK_EQUAL(0_MiB, 0);
1837      BOOST_CHECK_EQUAL(1_MiB, 1 << 20);
1838      BOOST_CHECK_EQUAL(1_MiB, 1024 * 1024);
1839      BOOST_CHECK_EQUAL(1_MiB, 0x100000U);
1840      BOOST_CHECK_EQUAL(1_MiB, 1048576U);
1841      BOOST_CHECK_EQUAL(2ULL * 1_MiB, 2ULL << 20);
1842      BOOST_CHECK_EQUAL((3_MiB + 123) / double(1_MiB), (3_MiB + 123) / 1024.0 / 1024.0);
1843  
1844      // Specific codebase values
1845      BOOST_CHECK_EQUAL(4_MiB, 1 << 22);
1846      BOOST_CHECK_EQUAL(8_MiB, 1 << 23);
1847      BOOST_CHECK_EQUAL(16_MiB, 0x1000000U);
1848      BOOST_CHECK_EQUAL(16_MiB, 1 << 24);
1849      BOOST_CHECK_EQUAL(32_MiB, 0x2000000U);
1850      BOOST_CHECK_EQUAL(32_MiB, 32U << 20);
1851      BOOST_CHECK_EQUAL(50_MiB / 1_MiB, 50U);
1852      BOOST_CHECK_EQUAL(50_MiB, 52428800U);
1853      BOOST_CHECK_EQUAL(128_MiB, 0x8000000U);
1854      BOOST_CHECK_EQUAL(550_MiB, 550ULL * 1024 * 1024);
1855  
1856      // 4095 MiB fits in uint32_t bytes. 4096 MiB requires the uint64_t return type.
1857      static_assert(BraceInitializesTo<uint32_t, 4095_MiB>);
1858      static_assert(!BraceInitializesTo<uint32_t, 4096_MiB>);
1859      static_assert(BraceInitializesTo<uint64_t, 4096_MiB>);
1860      BOOST_CHECK_EQUAL(4095_MiB, uint32_t{4095} << 20);
1861      BOOST_CHECK_EQUAL(4096_MiB, uint64_t{4096} << 20);
1862  }
1863  
1864  BOOST_AUTO_TEST_CASE(ceil_div_test)
1865  {
1866      // Type combinations used by current CeilDiv callsites.
1867      BOOST_CHECK((std::is_same_v<decltype(CeilDiv(uint32_t{0}, 8u)), uint32_t>));
1868      BOOST_CHECK((std::is_same_v<decltype(CeilDiv(size_t{0}, 8u)), size_t>));
1869      BOOST_CHECK((std::is_same_v<decltype(CeilDiv(unsigned{0}, size_t{1})), size_t>));
1870  
1871      // `common/bloom.cpp` and `cuckoocache.h` patterns.
1872      BOOST_CHECK_EQUAL(CeilDiv(uint32_t{3}, 2u), uint32_t{2});
1873      BOOST_CHECK_EQUAL(CeilDiv(uint32_t{65}, 64u), uint32_t{2});
1874      BOOST_CHECK_EQUAL(CeilDiv(uint32_t{9}, 8u), uint32_t{2});
1875  
1876      // `key_io.cpp`, `rest.cpp`, `merkleblock.cpp`, `strencodings.cpp` patterns.
1877      BOOST_CHECK_EQUAL(CeilDiv(size_t{9}, 8u), size_t{2});
1878      BOOST_CHECK_EQUAL(CeilDiv(size_t{10}, 3u), size_t{4});
1879      BOOST_CHECK_EQUAL(CeilDiv(size_t{11}, 5u), size_t{3});
1880      BOOST_CHECK_EQUAL(CeilDiv(size_t{41} * 8, 5u), size_t{66});
1881  
1882      // `flatfile.cpp` mixed unsigned/size_t pattern.
1883      BOOST_CHECK_EQUAL(CeilDiv(unsigned{10}, size_t{4}), size_t{3});
1884  
1885      // `util/feefrac.h` fast-path rounding-up pattern.
1886      constexpr int64_t fee{12345};
1887      constexpr int32_t at_size{67};
1888      constexpr int32_t size{10};
1889      BOOST_CHECK_EQUAL(CeilDiv(uint64_t(fee) * at_size, uint32_t(size)),
1890                        (uint64_t(fee) * at_size + uint32_t(size) - 1) / uint32_t(size));
1891  
1892      // `bitset.h` template parameter pattern.
1893      constexpr unsigned bits{129};
1894      constexpr size_t digits{std::numeric_limits<size_t>::digits};
1895      BOOST_CHECK_EQUAL(CeilDiv(bits, digits), (bits + digits - 1) / digits);
1896  
1897      // `serialize.h` varint scratch-buffer pattern.
1898      BOOST_CHECK_EQUAL(CeilDiv(sizeof(uint64_t) * 8, 7u), (sizeof(uint64_t) * 8 + 6) / 7);
1899  }
1900  
1901  BOOST_AUTO_TEST_CASE(gib_string_literal_test)
1902  {
1903      // Basic equivalences and simple arithmetic operations
1904      BOOST_CHECK_EQUAL(0_GiB, 0);
1905      BOOST_CHECK_EQUAL(1_GiB, 1 << 30);
1906      BOOST_CHECK_EQUAL(1_GiB, 1024 * 1024 * 1024);
1907      BOOST_CHECK_EQUAL(1_GiB, 0x40000000U);
1908      BOOST_CHECK_EQUAL(1_GiB, 1073741824U);
1909      BOOST_CHECK_EQUAL(1_GiB, 1_MiB * 1024);
1910      BOOST_CHECK_EQUAL(1_GiB, 1024_MiB);
1911      BOOST_CHECK_EQUAL((1_GiB + 123) / double(1_GiB), (1_GiB + 123) / 1024.0 / 1024.0 / 1024.0);
1912      BOOST_CHECK_EQUAL(2ULL * 1_GiB, 2ULL << 30);
1913      BOOST_CHECK_EQUAL(4 * uint64_t{1_GiB}, uint64_t{4} << 30);
1914      BOOST_CHECK_EQUAL(2_GiB, 2048_MiB);
1915      BOOST_CHECK_EQUAL(3_GiB / 1_GiB, 3U);
1916      BOOST_CHECK_EQUAL(3_GiB, 3U << 30);
1917  
1918      // 3 GiB fits in uint32_t bytes. 4 GiB requires the uint64_t return type.
1919      static_assert(BraceInitializesTo<uint32_t, 3_GiB>);
1920      static_assert(!BraceInitializesTo<uint32_t, 4_GiB>);
1921      static_assert(BraceInitializesTo<uint64_t, 4_GiB>);
1922      BOOST_CHECK_EQUAL(3_GiB, uint32_t{3} << 30);
1923      BOOST_CHECK_EQUAL(4_GiB, uint64_t{4} << 30);
1924  
1925      // Specific codebase values
1926      BOOST_CHECK_EQUAL(4_GiB, 4096_MiB);
1927      BOOST_CHECK_EQUAL(8_GiB, 8192_MiB);
1928      BOOST_CHECK_EQUAL(16_GiB, 16384_MiB);
1929      BOOST_CHECK_EQUAL(32_GiB, 32768_MiB);
1930  }
1931  
1932  BOOST_AUTO_TEST_SUITE_END()
1933