/ src / test / amount_tests.cpp
amount_tests.cpp
  1  // Copyright (c) 2016-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 <consensus/amount.h>
  6  #include <policy/feerate.h>
  7  
  8  #include <limits>
  9  
 10  #include <boost/test/unit_test.hpp>
 11  
 12  BOOST_AUTO_TEST_SUITE(amount_tests)
 13  
 14  BOOST_AUTO_TEST_CASE(MoneyRangeTest)
 15  {
 16      BOOST_CHECK_EQUAL(MoneyRange(CAmount(-1)), false);
 17      BOOST_CHECK_EQUAL(MoneyRange(CAmount(0)), true);
 18      BOOST_CHECK_EQUAL(MoneyRange(CAmount(1)), true);
 19      BOOST_CHECK_EQUAL(MoneyRange(MAX_MONEY), true);
 20      BOOST_CHECK_EQUAL(MoneyRange(MAX_MONEY + CAmount(1)), false);
 21  }
 22  
 23  BOOST_AUTO_TEST_CASE(GetFeeTest)
 24  {
 25      CFeeRate feeRate, altFeeRate;
 26  
 27      feeRate = CFeeRate(0);
 28      // Must always return 0
 29      BOOST_CHECK_EQUAL(feeRate.GetFee(0), CAmount(0));
 30      BOOST_CHECK_EQUAL(feeRate.GetFee(1e5), CAmount(0));
 31  
 32      feeRate = CFeeRate(1000);
 33      // Must always just return the arg
 34      BOOST_CHECK_EQUAL(feeRate.GetFee(0), CAmount(0));
 35      BOOST_CHECK_EQUAL(feeRate.GetFee(1), CAmount(1));
 36      BOOST_CHECK_EQUAL(feeRate.GetFee(121), CAmount(121));
 37      BOOST_CHECK_EQUAL(feeRate.GetFee(999), CAmount(999));
 38      BOOST_CHECK_EQUAL(feeRate.GetFee(1e3), CAmount(1e3));
 39      BOOST_CHECK_EQUAL(feeRate.GetFee(9e3), CAmount(9e3));
 40  
 41      feeRate = CFeeRate(-1000);
 42      // Must always just return -1 * arg
 43      BOOST_CHECK_EQUAL(feeRate.GetFee(0), CAmount(0));
 44      BOOST_CHECK_EQUAL(feeRate.GetFee(1), CAmount(-1));
 45      BOOST_CHECK_EQUAL(feeRate.GetFee(121), CAmount(-121));
 46      BOOST_CHECK_EQUAL(feeRate.GetFee(999), CAmount(-999));
 47      BOOST_CHECK_EQUAL(feeRate.GetFee(1e3), CAmount(-1e3));
 48      BOOST_CHECK_EQUAL(feeRate.GetFee(9e3), CAmount(-9e3));
 49  
 50      feeRate = CFeeRate(123);
 51      // Rounds up the result, if not integer
 52      BOOST_CHECK_EQUAL(feeRate.GetFee(0), CAmount(0));
 53      BOOST_CHECK_EQUAL(feeRate.GetFee(8), CAmount(1)); // Special case: returns 1 instead of 0
 54      BOOST_CHECK_EQUAL(feeRate.GetFee(9), CAmount(2));
 55      BOOST_CHECK_EQUAL(feeRate.GetFee(121), CAmount(15));
 56      BOOST_CHECK_EQUAL(feeRate.GetFee(122), CAmount(16));
 57      BOOST_CHECK_EQUAL(feeRate.GetFee(999), CAmount(123));
 58      BOOST_CHECK_EQUAL(feeRate.GetFee(1e3), CAmount(123));
 59      BOOST_CHECK_EQUAL(feeRate.GetFee(9e3), CAmount(1107));
 60  
 61      feeRate = CFeeRate(-123);
 62      // Truncates the result, if not integer
 63      BOOST_CHECK_EQUAL(feeRate.GetFee(0), CAmount(0));
 64      BOOST_CHECK_EQUAL(feeRate.GetFee(8), CAmount(-1)); // Special case: returns -1 instead of 0
 65      BOOST_CHECK_EQUAL(feeRate.GetFee(9), CAmount(-1));
 66  
 67      // check alternate constructor
 68      feeRate = CFeeRate(1000);
 69      altFeeRate = CFeeRate(feeRate);
 70      BOOST_CHECK_EQUAL(feeRate.GetFee(100), altFeeRate.GetFee(100));
 71  
 72      // Check full constructor
 73      BOOST_CHECK(CFeeRate(CAmount(-1), 0) == CFeeRate(0));
 74      BOOST_CHECK(CFeeRate(CAmount(0), 0) == CFeeRate(0));
 75      BOOST_CHECK(CFeeRate(CAmount(1), 0) == CFeeRate(0));
 76      BOOST_CHECK(CFeeRate(CAmount(1), -1000) == CFeeRate(0));
 77      // default value
 78      BOOST_CHECK(CFeeRate(CAmount(-1), 1000) == CFeeRate(-1));
 79      BOOST_CHECK(CFeeRate(CAmount(0), 1000) == CFeeRate(0));
 80      BOOST_CHECK(CFeeRate(CAmount(1), 1000) == CFeeRate(1));
 81      // Previously, precision was limited to three decimal digits
 82      // due to only supporting satoshis per kB, so CFeeRate(CAmount(1), 1001) was equal to CFeeRate(0)
 83      // Since #32750, higher precision is maintained.
 84      BOOST_CHECK(CFeeRate(CAmount(1), 1001) > CFeeRate(0) && CFeeRate(CAmount(1), 1001) < CFeeRate(1));
 85      BOOST_CHECK(CFeeRate(CAmount(2), 1001) > CFeeRate(1) && CFeeRate(CAmount(2), 1001) < CFeeRate(2));
 86      // some more integer checks
 87      BOOST_CHECK(CFeeRate(CAmount(26), 789) > CFeeRate(32) && CFeeRate(CAmount(26), 789) < CFeeRate(33));
 88      BOOST_CHECK(CFeeRate(CAmount(27), 789) > CFeeRate(34) && CFeeRate(CAmount(27), 789) < CFeeRate(35));
 89      // Maximum size in bytes, should not crash
 90      CFeeRate(MAX_MONEY, std::numeric_limits<int32_t>::max()).GetFeePerK();
 91  
 92      // check multiplication operator
 93      // check multiplying by zero
 94      feeRate = CFeeRate(1000);
 95      BOOST_CHECK(0 * feeRate == CFeeRate(0));
 96      BOOST_CHECK(feeRate * 0 == CFeeRate(0));
 97      // check multiplying by a positive integer
 98      BOOST_CHECK(3 * feeRate == CFeeRate(3000));
 99      BOOST_CHECK(feeRate * 3 == CFeeRate(3000));
100      // check multiplying by a negative integer
101      BOOST_CHECK(-3 * feeRate == CFeeRate(-3000));
102      BOOST_CHECK(feeRate * -3 == CFeeRate(-3000));
103      // check commutativity
104      BOOST_CHECK(2 * feeRate == feeRate * 2);
105      // check with large numbers
106      int largeNumber = 1000000;
107      BOOST_CHECK(largeNumber * feeRate == feeRate * largeNumber);
108      // check boundary values
109      int maxInt = std::numeric_limits<int>::max();
110      feeRate = CFeeRate(maxInt);
111      BOOST_CHECK(feeRate * 2 == CFeeRate(static_cast<int64_t>(maxInt) * 2));
112      BOOST_CHECK(2 * feeRate == CFeeRate(static_cast<int64_t>(maxInt) * 2));
113      // check with zero fee rate
114      feeRate = CFeeRate(0);
115      BOOST_CHECK(feeRate * 5 == CFeeRate(0));
116      BOOST_CHECK(5 * feeRate == CFeeRate(0));
117  }
118  
119  BOOST_AUTO_TEST_CASE(BinaryOperatorTest)
120  {
121      CFeeRate a, b;
122      a = CFeeRate(1);
123      b = CFeeRate(2);
124      BOOST_CHECK(a < b);
125      BOOST_CHECK(b > a);
126      BOOST_CHECK(a == a);
127      BOOST_CHECK(a <= b);
128      BOOST_CHECK(a <= a);
129      BOOST_CHECK(b >= a);
130      BOOST_CHECK(b >= b);
131      // a should be 0.00000002 BTC/kvB now
132      a += a;
133      BOOST_CHECK(a == b);
134  }
135  
136  BOOST_AUTO_TEST_CASE(ToStringTest)
137  {
138      CFeeRate feeRate;
139      feeRate = CFeeRate(1);
140      BOOST_CHECK_EQUAL(feeRate.ToString(), "0.00000001 BTC/kvB");
141      BOOST_CHECK_EQUAL(feeRate.ToString(FeeRateFormat::BTC_KVB), "0.00000001 BTC/kvB");
142      BOOST_CHECK_EQUAL(feeRate.ToString(FeeRateFormat::SAT_VB), "0.001 sat/vB");
143  }
144  
145  BOOST_AUTO_TEST_SUITE_END()