rippled
Loading...
Searching...
No Matches
IOUAmount_test.cpp
1//------------------------------------------------------------------------------
2/*
3 This file is part of rippled: https://github.com/ripple/rippled
4 Copyright (c) 2012, 2013 Ripple Labs Inc.
5
6 Permission to use, copy, modify, and/or distribute this software for any
7 purpose with or without fee is hereby granted, provided that the above
8 copyright notice and this permission notice appear in all copies.
9
10 THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11 WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12 MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13 ANY SPECIAL , DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14 WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15 ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16 OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17*/
18//==============================================================================
19
20#include <xrpl/beast/unit_test.h>
21#include <xrpl/protocol/IOUAmount.h>
22
23namespace ripple {
24
26{
27public:
28 void
30 {
31 testcase("zero");
32
33 IOUAmount const z(0, 0);
34
35 BEAST_EXPECT(z.mantissa() == 0);
36 BEAST_EXPECT(z.exponent() == -100);
37 BEAST_EXPECT(!z);
38 BEAST_EXPECT(z.signum() == 0);
39 BEAST_EXPECT(z == beast::zero);
40
41 BEAST_EXPECT((z + z) == z);
42 BEAST_EXPECT((z - z) == z);
43 BEAST_EXPECT(z == -z);
44
45 IOUAmount const zz(beast::zero);
46 BEAST_EXPECT(z == zz);
47 }
48
49 void
51 {
52 testcase("signum");
53
54 IOUAmount const neg(-1, 0);
55 BEAST_EXPECT(neg.signum() < 0);
56
57 IOUAmount const zer(0, 0);
58 BEAST_EXPECT(zer.signum() == 0);
59
60 IOUAmount const pos(1, 0);
61 BEAST_EXPECT(pos.signum() > 0);
62 }
63
64 void
66 {
67 testcase("beast::Zero Comparisons");
68
69 using beast::zero;
70
71 {
72 IOUAmount z(zero);
73 BEAST_EXPECT(z == zero);
74 BEAST_EXPECT(z >= zero);
75 BEAST_EXPECT(z <= zero);
76 unexpected(z != zero);
77 unexpected(z > zero);
78 unexpected(z < zero);
79 }
80
81 {
82 IOUAmount const neg(-2, 0);
83 BEAST_EXPECT(neg < zero);
84 BEAST_EXPECT(neg <= zero);
85 BEAST_EXPECT(neg != zero);
86 unexpected(neg == zero);
87 }
88
89 {
90 IOUAmount const pos(2, 0);
91 BEAST_EXPECT(pos > zero);
92 BEAST_EXPECT(pos >= zero);
93 BEAST_EXPECT(pos != zero);
94 unexpected(pos == zero);
95 }
96 }
97
98 void
100 {
101 testcase("IOU Comparisons");
102
103 IOUAmount const n(-2, 0);
104 IOUAmount const z(0, 0);
105 IOUAmount const p(2, 0);
106
107 BEAST_EXPECT(z == z);
108 BEAST_EXPECT(z >= z);
109 BEAST_EXPECT(z <= z);
110 BEAST_EXPECT(z == -z);
111 unexpected(z > z);
112 unexpected(z < z);
113 unexpected(z != z);
114 unexpected(z != -z);
115
116 BEAST_EXPECT(n < z);
117 BEAST_EXPECT(n <= z);
118 BEAST_EXPECT(n != z);
119 unexpected(n > z);
120 unexpected(n >= z);
121 unexpected(n == z);
122
123 BEAST_EXPECT(p > z);
124 BEAST_EXPECT(p >= z);
125 BEAST_EXPECT(p != z);
126 unexpected(p < z);
127 unexpected(p <= z);
128 unexpected(p == z);
129
130 BEAST_EXPECT(n < p);
131 BEAST_EXPECT(n <= p);
132 BEAST_EXPECT(n != p);
133 unexpected(n > p);
134 unexpected(n >= p);
135 unexpected(n == p);
136
137 BEAST_EXPECT(p > n);
138 BEAST_EXPECT(p >= n);
139 BEAST_EXPECT(p != n);
140 unexpected(p < n);
141 unexpected(p <= n);
142 unexpected(p == n);
143
144 BEAST_EXPECT(p > -p);
145 BEAST_EXPECT(p >= -p);
146 BEAST_EXPECT(p != -p);
147
148 BEAST_EXPECT(n < -n);
149 BEAST_EXPECT(n <= -n);
150 BEAST_EXPECT(n != -n);
151 }
152
153 void
155 {
156 testcase("IOU strings");
157
158 BEAST_EXPECT(to_string(IOUAmount(-2, 0)) == "-2");
159 BEAST_EXPECT(to_string(IOUAmount(0, 0)) == "0");
160 BEAST_EXPECT(to_string(IOUAmount(2, 0)) == "2");
161 BEAST_EXPECT(to_string(IOUAmount(25, -3)) == "0.025");
162 BEAST_EXPECT(to_string(IOUAmount(-25, -3)) == "-0.025");
163 BEAST_EXPECT(to_string(IOUAmount(25, 1)) == "250");
164 BEAST_EXPECT(to_string(IOUAmount(-25, 1)) == "-250");
165 BEAST_EXPECT(to_string(IOUAmount(2, 20)) == "2000000000000000e5");
166 BEAST_EXPECT(to_string(IOUAmount(-2, -20)) == "-2000000000000000e-35");
167 }
168
169 void
171 {
172 testcase("mulRatio");
173
174 /* The range for the mantissa when normalized */
175 constexpr std::int64_t minMantissa = 1000000000000000ull;
176 constexpr std::int64_t maxMantissa = 9999999999999999ull;
177 // log(2,maxMantissa) ~ 53.15
178 /* The range for the exponent when normalized */
179 constexpr int minExponent = -96;
180 constexpr int maxExponent = 80;
181 constexpr auto maxUInt = std::numeric_limits<std::uint32_t>::max();
182
183 {
184 // multiply by a number that would overflow the mantissa, then
185 // divide by the same number, and check we didn't lose any value
186 IOUAmount bigMan(maxMantissa, 0);
187 BEAST_EXPECT(bigMan == mulRatio(bigMan, maxUInt, maxUInt, true));
188 // rounding mode shouldn't matter as the result is exact
189 BEAST_EXPECT(bigMan == mulRatio(bigMan, maxUInt, maxUInt, false));
190 }
191 {
192 // Similar test as above, but for negative values
193 IOUAmount bigMan(-maxMantissa, 0);
194 BEAST_EXPECT(bigMan == mulRatio(bigMan, maxUInt, maxUInt, true));
195 // rounding mode shouldn't matter as the result is exact
196 BEAST_EXPECT(bigMan == mulRatio(bigMan, maxUInt, maxUInt, false));
197 }
198
199 {
200 // small amounts
202 // Round up should give the smallest allowable number
203 BEAST_EXPECT(tiny == mulRatio(tiny, 1, maxUInt, true));
204 BEAST_EXPECT(tiny == mulRatio(tiny, maxUInt - 1, maxUInt, true));
205 // rounding down should be zero
206 BEAST_EXPECT(beast::zero == mulRatio(tiny, 1, maxUInt, false));
207 BEAST_EXPECT(
208 beast::zero == mulRatio(tiny, maxUInt - 1, maxUInt, false));
209
210 // tiny negative numbers
212 // Round up should give zero
213 BEAST_EXPECT(beast::zero == mulRatio(tinyNeg, 1, maxUInt, true));
214 BEAST_EXPECT(
215 beast::zero == mulRatio(tinyNeg, maxUInt - 1, maxUInt, true));
216 // rounding down should be tiny
217 BEAST_EXPECT(tinyNeg == mulRatio(tinyNeg, 1, maxUInt, false));
218 BEAST_EXPECT(
219 tinyNeg == mulRatio(tinyNeg, maxUInt - 1, maxUInt, false));
220 }
221
222 { // rounding
223 {
224 IOUAmount one(1, 0);
225 auto const rup = mulRatio(one, maxUInt - 1, maxUInt, true);
226 auto const rdown = mulRatio(one, maxUInt - 1, maxUInt, false);
227 BEAST_EXPECT(rup.mantissa() - rdown.mantissa() == 1);
228 }
229 {
231 auto const rup = mulRatio(big, maxUInt - 1, maxUInt, true);
232 auto const rdown = mulRatio(big, maxUInt - 1, maxUInt, false);
233 BEAST_EXPECT(rup.mantissa() - rdown.mantissa() == 1);
234 }
235
236 {
237 IOUAmount negOne(-1, 0);
238 auto const rup = mulRatio(negOne, maxUInt - 1, maxUInt, true);
239 auto const rdown =
240 mulRatio(negOne, maxUInt - 1, maxUInt, false);
241 BEAST_EXPECT(rup.mantissa() - rdown.mantissa() == 1);
242 }
243 }
244
245 {
246 // division by zero
247 IOUAmount one(1, 0);
248 except([&] { mulRatio(one, 1, 0, true); });
249 }
250
251 {
252 // overflow
254 except([&] { mulRatio(big, 2, 0, true); });
255 }
256 } // namespace ripple
257
258 //--------------------------------------------------------------------------
259
260 void
261 run() override
262 {
263 testZero();
264 testSigNum();
267 testToString();
268 testMulRatio();
269 }
270};
271
272BEAST_DEFINE_TESTSUITE(IOUAmount, protocol, ripple);
273
274} // namespace ripple
A testsuite class.
Definition: suite.h:55
bool unexpected(Condition shouldBeFalse, String const &reason)
Definition: suite.h:499
testcase_t testcase
Memberspace for declaring test cases.
Definition: suite.h:155
bool except(F &&f, String const &reason)
Definition: suite.h:448
void run() override
Runs the suite.
Floating point representation of amounts with high dynamic range.
Definition: IOUAmount.h:47
int exponent() const noexcept
Definition: IOUAmount.h:167
int signum() const noexcept
Return the sign of the amount.
Definition: IOUAmount.h:161
std::int64_t mantissa() const noexcept
Definition: IOUAmount.h:173
T max(T... args)
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
Definition: algorithm.h:26
constexpr Number one
Definition: Number.cpp:175
static int constexpr maxExponent
Definition: IOUAmount.cpp:66
static int constexpr minExponent
Definition: IOUAmount.cpp:65
static std::int64_t constexpr maxMantissa
Definition: IOUAmount.cpp:63
static std::int64_t constexpr minMantissa
Definition: IOUAmount.cpp:62
IOUAmount mulRatio(IOUAmount const &amt, std::uint32_t num, std::uint32_t den, bool roundUp)
Definition: IOUAmount.cpp:190
std::string to_string(base_uint< Bits, Tag > const &a)
Definition: base_uint.h:630