Run DCE after a LoopFlatten test to reduce spurious output [nfc]
[llvm-project.git] / llvm / unittests / ADT / APFloatTest.cpp
blobbaf055e503b7e7a83679a02f5cfbd6f64d71e236
1 //===- llvm/unittest/ADT/APFloat.cpp - APFloat unit tests ---------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
9 #include "llvm/ADT/APFloat.h"
10 #include "llvm/ADT/APSInt.h"
11 #include "llvm/ADT/Hashing.h"
12 #include "llvm/ADT/SmallString.h"
13 #include "llvm/ADT/SmallVector.h"
14 #include "llvm/ADT/StringExtras.h"
15 #include "llvm/Support/Error.h"
16 #include "llvm/Support/FormatVariadic.h"
17 #include "gtest/gtest.h"
18 #include <cmath>
19 #include <ostream>
20 #include <string>
21 #include <tuple>
23 using namespace llvm;
25 static std::string convertToErrorFromString(StringRef Str) {
26 llvm::APFloat F(0.0);
27 auto StatusOrErr =
28 F.convertFromString(Str, llvm::APFloat::rmNearestTiesToEven);
29 EXPECT_TRUE(!StatusOrErr);
30 return toString(StatusOrErr.takeError());
33 static double convertToDoubleFromString(StringRef Str) {
34 llvm::APFloat F(0.0);
35 auto StatusOrErr =
36 F.convertFromString(Str, llvm::APFloat::rmNearestTiesToEven);
37 EXPECT_FALSE(!StatusOrErr);
38 consumeError(StatusOrErr.takeError());
39 return F.convertToDouble();
42 static std::string convertToString(double d, unsigned Prec, unsigned Pad,
43 bool Tr = true) {
44 llvm::SmallVector<char, 100> Buffer;
45 llvm::APFloat F(d);
46 F.toString(Buffer, Prec, Pad, Tr);
47 return std::string(Buffer.data(), Buffer.size());
50 namespace {
52 TEST(APFloatTest, isSignaling) {
53 // We test qNaN, -qNaN, +sNaN, -sNaN with and without payloads. *NOTE* The
54 // positive/negative distinction is included only since the getQNaN/getSNaN
55 // API provides the option.
56 APInt payload = APInt::getOneBitSet(4, 2);
57 APFloat QNan = APFloat::getQNaN(APFloat::IEEEsingle(), false);
58 EXPECT_FALSE(QNan.isSignaling());
59 EXPECT_EQ(fcQNan, QNan.classify());
61 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), true).isSignaling());
62 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), false, &payload).isSignaling());
63 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), true, &payload).isSignaling());
65 APFloat SNan = APFloat::getSNaN(APFloat::IEEEsingle(), false);
66 EXPECT_TRUE(SNan.isSignaling());
67 EXPECT_EQ(fcSNan, SNan.classify());
69 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isSignaling());
70 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false, &payload).isSignaling());
71 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true, &payload).isSignaling());
74 TEST(APFloatTest, next) {
76 APFloat test(APFloat::IEEEquad(), APFloat::uninitialized);
77 APFloat expected(APFloat::IEEEquad(), APFloat::uninitialized);
79 // 1. Test Special Cases Values.
81 // Test all special values for nextUp and nextDown perscribed by IEEE-754R
82 // 2008. These are:
83 // 1. +inf
84 // 2. -inf
85 // 3. getLargest()
86 // 4. -getLargest()
87 // 5. getSmallest()
88 // 6. -getSmallest()
89 // 7. qNaN
90 // 8. sNaN
91 // 9. +0
92 // 10. -0
94 // nextUp(+inf) = +inf.
95 test = APFloat::getInf(APFloat::IEEEquad(), false);
96 expected = APFloat::getInf(APFloat::IEEEquad(), false);
97 EXPECT_EQ(test.next(false), APFloat::opOK);
98 EXPECT_TRUE(test.isInfinity());
99 EXPECT_TRUE(!test.isNegative());
100 EXPECT_TRUE(test.bitwiseIsEqual(expected));
102 // nextDown(+inf) = -nextUp(-inf) = -(-getLargest()) = getLargest()
103 test = APFloat::getInf(APFloat::IEEEquad(), false);
104 expected = APFloat::getLargest(APFloat::IEEEquad(), false);
105 EXPECT_EQ(test.next(true), APFloat::opOK);
106 EXPECT_TRUE(!test.isNegative());
107 EXPECT_TRUE(test.bitwiseIsEqual(expected));
109 // nextUp(-inf) = -getLargest()
110 test = APFloat::getInf(APFloat::IEEEquad(), true);
111 expected = APFloat::getLargest(APFloat::IEEEquad(), true);
112 EXPECT_EQ(test.next(false), APFloat::opOK);
113 EXPECT_TRUE(test.isNegative());
114 EXPECT_TRUE(test.bitwiseIsEqual(expected));
116 // nextDown(-inf) = -nextUp(+inf) = -(+inf) = -inf.
117 test = APFloat::getInf(APFloat::IEEEquad(), true);
118 expected = APFloat::getInf(APFloat::IEEEquad(), true);
119 EXPECT_EQ(test.next(true), APFloat::opOK);
120 EXPECT_TRUE(test.isInfinity() && test.isNegative());
121 EXPECT_TRUE(test.bitwiseIsEqual(expected));
123 // nextUp(getLargest()) = +inf
124 test = APFloat::getLargest(APFloat::IEEEquad(), false);
125 expected = APFloat::getInf(APFloat::IEEEquad(), false);
126 EXPECT_EQ(test.next(false), APFloat::opOK);
127 EXPECT_TRUE(test.isInfinity() && !test.isNegative());
128 EXPECT_TRUE(test.bitwiseIsEqual(expected));
130 // nextDown(getLargest()) = -nextUp(-getLargest())
131 // = -(-getLargest() + inc)
132 // = getLargest() - inc.
133 test = APFloat::getLargest(APFloat::IEEEquad(), false);
134 expected = APFloat(APFloat::IEEEquad(),
135 "0x1.fffffffffffffffffffffffffffep+16383");
136 EXPECT_EQ(test.next(true), APFloat::opOK);
137 EXPECT_TRUE(!test.isInfinity() && !test.isNegative());
138 EXPECT_TRUE(test.bitwiseIsEqual(expected));
140 // nextUp(-getLargest()) = -getLargest() + inc.
141 test = APFloat::getLargest(APFloat::IEEEquad(), true);
142 expected = APFloat(APFloat::IEEEquad(),
143 "-0x1.fffffffffffffffffffffffffffep+16383");
144 EXPECT_EQ(test.next(false), APFloat::opOK);
145 EXPECT_TRUE(test.bitwiseIsEqual(expected));
147 // nextDown(-getLargest()) = -nextUp(getLargest()) = -(inf) = -inf.
148 test = APFloat::getLargest(APFloat::IEEEquad(), true);
149 expected = APFloat::getInf(APFloat::IEEEquad(), true);
150 EXPECT_EQ(test.next(true), APFloat::opOK);
151 EXPECT_TRUE(test.isInfinity() && test.isNegative());
152 EXPECT_TRUE(test.bitwiseIsEqual(expected));
154 // nextUp(getSmallest()) = getSmallest() + inc.
155 test = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
156 expected = APFloat(APFloat::IEEEquad(),
157 "0x0.0000000000000000000000000002p-16382");
158 EXPECT_EQ(test.next(false), APFloat::opOK);
159 EXPECT_TRUE(test.bitwiseIsEqual(expected));
161 // nextDown(getSmallest()) = -nextUp(-getSmallest()) = -(-0) = +0.
162 test = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
163 expected = APFloat::getZero(APFloat::IEEEquad(), false);
164 EXPECT_EQ(test.next(true), APFloat::opOK);
165 EXPECT_TRUE(test.isPosZero());
166 EXPECT_TRUE(test.bitwiseIsEqual(expected));
168 // nextUp(-getSmallest()) = -0.
169 test = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
170 expected = APFloat::getZero(APFloat::IEEEquad(), true);
171 EXPECT_EQ(test.next(false), APFloat::opOK);
172 EXPECT_TRUE(test.isNegZero());
173 EXPECT_TRUE(test.bitwiseIsEqual(expected));
175 // nextDown(-getSmallest()) = -nextUp(getSmallest()) = -getSmallest() - inc.
176 test = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
177 expected = APFloat(APFloat::IEEEquad(),
178 "-0x0.0000000000000000000000000002p-16382");
179 EXPECT_EQ(test.next(true), APFloat::opOK);
180 EXPECT_TRUE(test.bitwiseIsEqual(expected));
182 // nextUp(qNaN) = qNaN
183 test = APFloat::getQNaN(APFloat::IEEEquad(), false);
184 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
185 EXPECT_EQ(test.next(false), APFloat::opOK);
186 EXPECT_TRUE(test.bitwiseIsEqual(expected));
188 // nextDown(qNaN) = qNaN
189 test = APFloat::getQNaN(APFloat::IEEEquad(), false);
190 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
191 EXPECT_EQ(test.next(true), APFloat::opOK);
192 EXPECT_TRUE(test.bitwiseIsEqual(expected));
194 // nextUp(sNaN) = qNaN
195 test = APFloat::getSNaN(APFloat::IEEEquad(), false);
196 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
197 EXPECT_EQ(test.next(false), APFloat::opInvalidOp);
198 EXPECT_TRUE(test.bitwiseIsEqual(expected));
200 // nextDown(sNaN) = qNaN
201 test = APFloat::getSNaN(APFloat::IEEEquad(), false);
202 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
203 EXPECT_EQ(test.next(true), APFloat::opInvalidOp);
204 EXPECT_TRUE(test.bitwiseIsEqual(expected));
206 // nextUp(+0) = +getSmallest()
207 test = APFloat::getZero(APFloat::IEEEquad(), false);
208 expected = APFloat::getSmallest(APFloat::IEEEquad(), false);
209 EXPECT_EQ(test.next(false), APFloat::opOK);
210 EXPECT_TRUE(test.bitwiseIsEqual(expected));
212 // nextDown(+0) = -nextUp(-0) = -getSmallest()
213 test = APFloat::getZero(APFloat::IEEEquad(), false);
214 expected = APFloat::getSmallest(APFloat::IEEEquad(), true);
215 EXPECT_EQ(test.next(true), APFloat::opOK);
216 EXPECT_TRUE(test.bitwiseIsEqual(expected));
218 // nextUp(-0) = +getSmallest()
219 test = APFloat::getZero(APFloat::IEEEquad(), true);
220 expected = APFloat::getSmallest(APFloat::IEEEquad(), false);
221 EXPECT_EQ(test.next(false), APFloat::opOK);
222 EXPECT_TRUE(test.bitwiseIsEqual(expected));
224 // nextDown(-0) = -nextUp(0) = -getSmallest()
225 test = APFloat::getZero(APFloat::IEEEquad(), true);
226 expected = APFloat::getSmallest(APFloat::IEEEquad(), true);
227 EXPECT_EQ(test.next(true), APFloat::opOK);
228 EXPECT_TRUE(test.bitwiseIsEqual(expected));
230 // 2. Binade Boundary Tests.
232 // 2a. Test denormal <-> normal binade boundaries.
233 // * nextUp(+Largest Denormal) -> +Smallest Normal.
234 // * nextDown(-Largest Denormal) -> -Smallest Normal.
235 // * nextUp(-Smallest Normal) -> -Largest Denormal.
236 // * nextDown(+Smallest Normal) -> +Largest Denormal.
238 // nextUp(+Largest Denormal) -> +Smallest Normal.
239 test = APFloat(APFloat::IEEEquad(), "0x0.ffffffffffffffffffffffffffffp-16382");
240 expected = APFloat(APFloat::IEEEquad(),
241 "0x1.0000000000000000000000000000p-16382");
242 EXPECT_EQ(test.next(false), APFloat::opOK);
243 EXPECT_FALSE(test.isDenormal());
244 EXPECT_TRUE(test.bitwiseIsEqual(expected));
246 // nextDown(-Largest Denormal) -> -Smallest Normal.
247 test = APFloat(APFloat::IEEEquad(),
248 "-0x0.ffffffffffffffffffffffffffffp-16382");
249 expected = APFloat(APFloat::IEEEquad(),
250 "-0x1.0000000000000000000000000000p-16382");
251 EXPECT_EQ(test.next(true), APFloat::opOK);
252 EXPECT_FALSE(test.isDenormal());
253 EXPECT_TRUE(test.bitwiseIsEqual(expected));
255 // nextUp(-Smallest Normal) -> -LargestDenormal.
256 test = APFloat(APFloat::IEEEquad(),
257 "-0x1.0000000000000000000000000000p-16382");
258 expected = APFloat(APFloat::IEEEquad(),
259 "-0x0.ffffffffffffffffffffffffffffp-16382");
260 EXPECT_EQ(test.next(false), APFloat::opOK);
261 EXPECT_TRUE(test.isDenormal());
262 EXPECT_TRUE(test.bitwiseIsEqual(expected));
264 // nextDown(+Smallest Normal) -> +Largest Denormal.
265 test = APFloat(APFloat::IEEEquad(),
266 "+0x1.0000000000000000000000000000p-16382");
267 expected = APFloat(APFloat::IEEEquad(),
268 "+0x0.ffffffffffffffffffffffffffffp-16382");
269 EXPECT_EQ(test.next(true), APFloat::opOK);
270 EXPECT_TRUE(test.isDenormal());
271 EXPECT_TRUE(test.bitwiseIsEqual(expected));
273 // 2b. Test normal <-> normal binade boundaries.
274 // * nextUp(-Normal Binade Boundary) -> -Normal Binade Boundary + 1.
275 // * nextDown(+Normal Binade Boundary) -> +Normal Binade Boundary - 1.
276 // * nextUp(+Normal Binade Boundary - 1) -> +Normal Binade Boundary.
277 // * nextDown(-Normal Binade Boundary + 1) -> -Normal Binade Boundary.
279 // nextUp(-Normal Binade Boundary) -> -Normal Binade Boundary + 1.
280 test = APFloat(APFloat::IEEEquad(), "-0x1p+1");
281 expected = APFloat(APFloat::IEEEquad(),
282 "-0x1.ffffffffffffffffffffffffffffp+0");
283 EXPECT_EQ(test.next(false), APFloat::opOK);
284 EXPECT_TRUE(test.bitwiseIsEqual(expected));
286 // nextDown(+Normal Binade Boundary) -> +Normal Binade Boundary - 1.
287 test = APFloat(APFloat::IEEEquad(), "0x1p+1");
288 expected = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp+0");
289 EXPECT_EQ(test.next(true), APFloat::opOK);
290 EXPECT_TRUE(test.bitwiseIsEqual(expected));
292 // nextUp(+Normal Binade Boundary - 1) -> +Normal Binade Boundary.
293 test = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp+0");
294 expected = APFloat(APFloat::IEEEquad(), "0x1p+1");
295 EXPECT_EQ(test.next(false), APFloat::opOK);
296 EXPECT_TRUE(test.bitwiseIsEqual(expected));
298 // nextDown(-Normal Binade Boundary + 1) -> -Normal Binade Boundary.
299 test = APFloat(APFloat::IEEEquad(), "-0x1.ffffffffffffffffffffffffffffp+0");
300 expected = APFloat(APFloat::IEEEquad(), "-0x1p+1");
301 EXPECT_EQ(test.next(true), APFloat::opOK);
302 EXPECT_TRUE(test.bitwiseIsEqual(expected));
304 // 2c. Test using next at binade boundaries with a direction away from the
305 // binade boundary. Away from denormal <-> normal boundaries.
307 // This is to make sure that even though we are at a binade boundary, since
308 // we are rounding away, we do not trigger the binade boundary code. Thus we
309 // test:
310 // * nextUp(-Largest Denormal) -> -Largest Denormal + inc.
311 // * nextDown(+Largest Denormal) -> +Largest Denormal - inc.
312 // * nextUp(+Smallest Normal) -> +Smallest Normal + inc.
313 // * nextDown(-Smallest Normal) -> -Smallest Normal - inc.
315 // nextUp(-Largest Denormal) -> -Largest Denormal + inc.
316 test = APFloat(APFloat::IEEEquad(), "-0x0.ffffffffffffffffffffffffffffp-16382");
317 expected = APFloat(APFloat::IEEEquad(),
318 "-0x0.fffffffffffffffffffffffffffep-16382");
319 EXPECT_EQ(test.next(false), APFloat::opOK);
320 EXPECT_TRUE(test.isDenormal());
321 EXPECT_TRUE(test.isNegative());
322 EXPECT_TRUE(test.bitwiseIsEqual(expected));
324 // nextDown(+Largest Denormal) -> +Largest Denormal - inc.
325 test = APFloat(APFloat::IEEEquad(), "0x0.ffffffffffffffffffffffffffffp-16382");
326 expected = APFloat(APFloat::IEEEquad(),
327 "0x0.fffffffffffffffffffffffffffep-16382");
328 EXPECT_EQ(test.next(true), APFloat::opOK);
329 EXPECT_TRUE(test.isDenormal());
330 EXPECT_TRUE(!test.isNegative());
331 EXPECT_TRUE(test.bitwiseIsEqual(expected));
333 // nextUp(+Smallest Normal) -> +Smallest Normal + inc.
334 test = APFloat(APFloat::IEEEquad(), "0x1.0000000000000000000000000000p-16382");
335 expected = APFloat(APFloat::IEEEquad(),
336 "0x1.0000000000000000000000000001p-16382");
337 EXPECT_EQ(test.next(false), APFloat::opOK);
338 EXPECT_TRUE(!test.isDenormal());
339 EXPECT_TRUE(!test.isNegative());
340 EXPECT_TRUE(test.bitwiseIsEqual(expected));
342 // nextDown(-Smallest Normal) -> -Smallest Normal - inc.
343 test = APFloat(APFloat::IEEEquad(), "-0x1.0000000000000000000000000000p-16382");
344 expected = APFloat(APFloat::IEEEquad(),
345 "-0x1.0000000000000000000000000001p-16382");
346 EXPECT_EQ(test.next(true), APFloat::opOK);
347 EXPECT_TRUE(!test.isDenormal());
348 EXPECT_TRUE(test.isNegative());
349 EXPECT_TRUE(test.bitwiseIsEqual(expected));
351 // 2d. Test values which cause our exponent to go to min exponent. This
352 // is to ensure that guards in the code to check for min exponent
353 // trigger properly.
354 // * nextUp(-0x1p-16381) -> -0x1.ffffffffffffffffffffffffffffp-16382
355 // * nextDown(-0x1.ffffffffffffffffffffffffffffp-16382) ->
356 // -0x1p-16381
357 // * nextUp(0x1.ffffffffffffffffffffffffffffp-16382) -> 0x1p-16382
358 // * nextDown(0x1p-16382) -> 0x1.ffffffffffffffffffffffffffffp-16382
360 // nextUp(-0x1p-16381) -> -0x1.ffffffffffffffffffffffffffffp-16382
361 test = APFloat(APFloat::IEEEquad(), "-0x1p-16381");
362 expected = APFloat(APFloat::IEEEquad(),
363 "-0x1.ffffffffffffffffffffffffffffp-16382");
364 EXPECT_EQ(test.next(false), APFloat::opOK);
365 EXPECT_TRUE(test.bitwiseIsEqual(expected));
367 // nextDown(-0x1.ffffffffffffffffffffffffffffp-16382) ->
368 // -0x1p-16381
369 test = APFloat(APFloat::IEEEquad(), "-0x1.ffffffffffffffffffffffffffffp-16382");
370 expected = APFloat(APFloat::IEEEquad(), "-0x1p-16381");
371 EXPECT_EQ(test.next(true), APFloat::opOK);
372 EXPECT_TRUE(test.bitwiseIsEqual(expected));
374 // nextUp(0x1.ffffffffffffffffffffffffffffp-16382) -> 0x1p-16381
375 test = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp-16382");
376 expected = APFloat(APFloat::IEEEquad(), "0x1p-16381");
377 EXPECT_EQ(test.next(false), APFloat::opOK);
378 EXPECT_TRUE(test.bitwiseIsEqual(expected));
380 // nextDown(0x1p-16381) -> 0x1.ffffffffffffffffffffffffffffp-16382
381 test = APFloat(APFloat::IEEEquad(), "0x1p-16381");
382 expected = APFloat(APFloat::IEEEquad(),
383 "0x1.ffffffffffffffffffffffffffffp-16382");
384 EXPECT_EQ(test.next(true), APFloat::opOK);
385 EXPECT_TRUE(test.bitwiseIsEqual(expected));
387 // 3. Now we test both denormal/normal computation which will not cause us
388 // to go across binade boundaries. Specifically we test:
389 // * nextUp(+Denormal) -> +Denormal.
390 // * nextDown(+Denormal) -> +Denormal.
391 // * nextUp(-Denormal) -> -Denormal.
392 // * nextDown(-Denormal) -> -Denormal.
393 // * nextUp(+Normal) -> +Normal.
394 // * nextDown(+Normal) -> +Normal.
395 // * nextUp(-Normal) -> -Normal.
396 // * nextDown(-Normal) -> -Normal.
398 // nextUp(+Denormal) -> +Denormal.
399 test = APFloat(APFloat::IEEEquad(),
400 "0x0.ffffffffffffffffffffffff000cp-16382");
401 expected = APFloat(APFloat::IEEEquad(),
402 "0x0.ffffffffffffffffffffffff000dp-16382");
403 EXPECT_EQ(test.next(false), APFloat::opOK);
404 EXPECT_TRUE(test.isDenormal());
405 EXPECT_TRUE(!test.isNegative());
406 EXPECT_TRUE(test.bitwiseIsEqual(expected));
408 // nextDown(+Denormal) -> +Denormal.
409 test = APFloat(APFloat::IEEEquad(),
410 "0x0.ffffffffffffffffffffffff000cp-16382");
411 expected = APFloat(APFloat::IEEEquad(),
412 "0x0.ffffffffffffffffffffffff000bp-16382");
413 EXPECT_EQ(test.next(true), APFloat::opOK);
414 EXPECT_TRUE(test.isDenormal());
415 EXPECT_TRUE(!test.isNegative());
416 EXPECT_TRUE(test.bitwiseIsEqual(expected));
418 // nextUp(-Denormal) -> -Denormal.
419 test = APFloat(APFloat::IEEEquad(),
420 "-0x0.ffffffffffffffffffffffff000cp-16382");
421 expected = APFloat(APFloat::IEEEquad(),
422 "-0x0.ffffffffffffffffffffffff000bp-16382");
423 EXPECT_EQ(test.next(false), APFloat::opOK);
424 EXPECT_TRUE(test.isDenormal());
425 EXPECT_TRUE(test.isNegative());
426 EXPECT_TRUE(test.bitwiseIsEqual(expected));
428 // nextDown(-Denormal) -> -Denormal
429 test = APFloat(APFloat::IEEEquad(),
430 "-0x0.ffffffffffffffffffffffff000cp-16382");
431 expected = APFloat(APFloat::IEEEquad(),
432 "-0x0.ffffffffffffffffffffffff000dp-16382");
433 EXPECT_EQ(test.next(true), APFloat::opOK);
434 EXPECT_TRUE(test.isDenormal());
435 EXPECT_TRUE(test.isNegative());
436 EXPECT_TRUE(test.bitwiseIsEqual(expected));
438 // nextUp(+Normal) -> +Normal.
439 test = APFloat(APFloat::IEEEquad(),
440 "0x1.ffffffffffffffffffffffff000cp-16000");
441 expected = APFloat(APFloat::IEEEquad(),
442 "0x1.ffffffffffffffffffffffff000dp-16000");
443 EXPECT_EQ(test.next(false), APFloat::opOK);
444 EXPECT_TRUE(!test.isDenormal());
445 EXPECT_TRUE(!test.isNegative());
446 EXPECT_TRUE(test.bitwiseIsEqual(expected));
448 // nextDown(+Normal) -> +Normal.
449 test = APFloat(APFloat::IEEEquad(),
450 "0x1.ffffffffffffffffffffffff000cp-16000");
451 expected = APFloat(APFloat::IEEEquad(),
452 "0x1.ffffffffffffffffffffffff000bp-16000");
453 EXPECT_EQ(test.next(true), APFloat::opOK);
454 EXPECT_TRUE(!test.isDenormal());
455 EXPECT_TRUE(!test.isNegative());
456 EXPECT_TRUE(test.bitwiseIsEqual(expected));
458 // nextUp(-Normal) -> -Normal.
459 test = APFloat(APFloat::IEEEquad(),
460 "-0x1.ffffffffffffffffffffffff000cp-16000");
461 expected = APFloat(APFloat::IEEEquad(),
462 "-0x1.ffffffffffffffffffffffff000bp-16000");
463 EXPECT_EQ(test.next(false), APFloat::opOK);
464 EXPECT_TRUE(!test.isDenormal());
465 EXPECT_TRUE(test.isNegative());
466 EXPECT_TRUE(test.bitwiseIsEqual(expected));
468 // nextDown(-Normal) -> -Normal.
469 test = APFloat(APFloat::IEEEquad(),
470 "-0x1.ffffffffffffffffffffffff000cp-16000");
471 expected = APFloat(APFloat::IEEEquad(),
472 "-0x1.ffffffffffffffffffffffff000dp-16000");
473 EXPECT_EQ(test.next(true), APFloat::opOK);
474 EXPECT_TRUE(!test.isDenormal());
475 EXPECT_TRUE(test.isNegative());
476 EXPECT_TRUE(test.bitwiseIsEqual(expected));
479 TEST(APFloatTest, FMA) {
480 APFloat::roundingMode rdmd = APFloat::rmNearestTiesToEven;
483 APFloat f1(14.5f);
484 APFloat f2(-14.5f);
485 APFloat f3(225.0f);
486 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
487 EXPECT_EQ(14.75f, f1.convertToFloat());
491 APFloat Val2(2.0f);
492 APFloat f1((float)1.17549435e-38F);
493 APFloat f2((float)1.17549435e-38F);
494 f1.divide(Val2, rdmd);
495 f2.divide(Val2, rdmd);
496 APFloat f3(12.0f);
497 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
498 EXPECT_EQ(12.0f, f1.convertToFloat());
501 // Test for correct zero sign when answer is exactly zero.
502 // fma(1.0, -1.0, 1.0) -> +ve 0.
504 APFloat f1(1.0);
505 APFloat f2(-1.0);
506 APFloat f3(1.0);
507 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
508 EXPECT_TRUE(!f1.isNegative() && f1.isZero());
511 // Test for correct zero sign when answer is exactly zero and rounding towards
512 // negative.
513 // fma(1.0, -1.0, 1.0) -> +ve 0.
515 APFloat f1(1.0);
516 APFloat f2(-1.0);
517 APFloat f3(1.0);
518 f1.fusedMultiplyAdd(f2, f3, APFloat::rmTowardNegative);
519 EXPECT_TRUE(f1.isNegative() && f1.isZero());
522 // Test for correct (in this case -ve) sign when adding like signed zeros.
523 // Test fma(0.0, -0.0, -0.0) -> -ve 0.
525 APFloat f1(0.0);
526 APFloat f2(-0.0);
527 APFloat f3(-0.0);
528 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
529 EXPECT_TRUE(f1.isNegative() && f1.isZero());
532 // Test -ve sign preservation when small negative results underflow.
534 APFloat f1(APFloat::IEEEdouble(), "-0x1p-1074");
535 APFloat f2(APFloat::IEEEdouble(), "+0x1p-1074");
536 APFloat f3(0.0);
537 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
538 EXPECT_TRUE(f1.isNegative() && f1.isZero());
541 // Test x87 extended precision case from http://llvm.org/PR20728.
543 APFloat M1(APFloat::x87DoubleExtended(), 1);
544 APFloat M2(APFloat::x87DoubleExtended(), 1);
545 APFloat A(APFloat::x87DoubleExtended(), 3);
547 bool losesInfo = false;
548 M1.fusedMultiplyAdd(M1, A, APFloat::rmNearestTiesToEven);
549 M1.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
550 EXPECT_FALSE(losesInfo);
551 EXPECT_EQ(4.0f, M1.convertToFloat());
554 // Regression test that failed an assertion.
556 APFloat f1(-8.85242279E-41f);
557 APFloat f2(2.0f);
558 APFloat f3(8.85242279E-41f);
559 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
560 EXPECT_EQ(-8.85242279E-41f, f1.convertToFloat());
563 // Test using only a single instance of APFloat.
565 APFloat F(1.5);
567 F.fusedMultiplyAdd(F, F, APFloat::rmNearestTiesToEven);
568 EXPECT_EQ(3.75, F.convertToDouble());
572 TEST(APFloatTest, MinNum) {
573 APFloat f1(1.0);
574 APFloat f2(2.0);
575 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
577 EXPECT_EQ(1.0, minnum(f1, f2).convertToDouble());
578 EXPECT_EQ(1.0, minnum(f2, f1).convertToDouble());
579 EXPECT_EQ(1.0, minnum(f1, nan).convertToDouble());
580 EXPECT_EQ(1.0, minnum(nan, f1).convertToDouble());
583 TEST(APFloatTest, MaxNum) {
584 APFloat f1(1.0);
585 APFloat f2(2.0);
586 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
588 EXPECT_EQ(2.0, maxnum(f1, f2).convertToDouble());
589 EXPECT_EQ(2.0, maxnum(f2, f1).convertToDouble());
590 EXPECT_EQ(1.0, maxnum(f1, nan).convertToDouble());
591 EXPECT_EQ(1.0, maxnum(nan, f1).convertToDouble());
594 TEST(APFloatTest, Minimum) {
595 APFloat f1(1.0);
596 APFloat f2(2.0);
597 APFloat zp(0.0);
598 APFloat zn(-0.0);
599 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
601 EXPECT_EQ(1.0, minimum(f1, f2).convertToDouble());
602 EXPECT_EQ(1.0, minimum(f2, f1).convertToDouble());
603 EXPECT_EQ(-0.0, minimum(zp, zn).convertToDouble());
604 EXPECT_EQ(-0.0, minimum(zn, zp).convertToDouble());
605 EXPECT_TRUE(std::isnan(minimum(f1, nan).convertToDouble()));
606 EXPECT_TRUE(std::isnan(minimum(nan, f1).convertToDouble()));
609 TEST(APFloatTest, Maximum) {
610 APFloat f1(1.0);
611 APFloat f2(2.0);
612 APFloat zp(0.0);
613 APFloat zn(-0.0);
614 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
616 EXPECT_EQ(2.0, maximum(f1, f2).convertToDouble());
617 EXPECT_EQ(2.0, maximum(f2, f1).convertToDouble());
618 EXPECT_EQ(0.0, maximum(zp, zn).convertToDouble());
619 EXPECT_EQ(0.0, maximum(zn, zp).convertToDouble());
620 EXPECT_TRUE(std::isnan(maximum(f1, nan).convertToDouble()));
621 EXPECT_TRUE(std::isnan(maximum(nan, f1).convertToDouble()));
624 TEST(APFloatTest, Denormal) {
625 APFloat::roundingMode rdmd = APFloat::rmNearestTiesToEven;
627 // Test single precision
629 const char *MinNormalStr = "1.17549435082228750797e-38";
630 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), MinNormalStr).isDenormal());
631 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), 0).isDenormal());
633 APFloat Val2(APFloat::IEEEsingle(), 2);
634 APFloat T(APFloat::IEEEsingle(), MinNormalStr);
635 T.divide(Val2, rdmd);
636 EXPECT_TRUE(T.isDenormal());
637 EXPECT_EQ(fcPosSubnormal, T.classify());
640 const char *NegMinNormalStr = "-1.17549435082228750797e-38";
641 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), NegMinNormalStr).isDenormal());
642 APFloat NegT(APFloat::IEEEsingle(), NegMinNormalStr);
643 NegT.divide(Val2, rdmd);
644 EXPECT_TRUE(NegT.isDenormal());
645 EXPECT_EQ(fcNegSubnormal, NegT.classify());
648 // Test double precision
650 const char *MinNormalStr = "2.22507385850720138309e-308";
651 EXPECT_FALSE(APFloat(APFloat::IEEEdouble(), MinNormalStr).isDenormal());
652 EXPECT_FALSE(APFloat(APFloat::IEEEdouble(), 0).isDenormal());
654 APFloat Val2(APFloat::IEEEdouble(), 2);
655 APFloat T(APFloat::IEEEdouble(), MinNormalStr);
656 T.divide(Val2, rdmd);
657 EXPECT_TRUE(T.isDenormal());
658 EXPECT_EQ(fcPosSubnormal, T.classify());
661 // Test Intel double-ext
663 const char *MinNormalStr = "3.36210314311209350626e-4932";
664 EXPECT_FALSE(APFloat(APFloat::x87DoubleExtended(), MinNormalStr).isDenormal());
665 EXPECT_FALSE(APFloat(APFloat::x87DoubleExtended(), 0).isDenormal());
667 APFloat Val2(APFloat::x87DoubleExtended(), 2);
668 APFloat T(APFloat::x87DoubleExtended(), MinNormalStr);
669 T.divide(Val2, rdmd);
670 EXPECT_TRUE(T.isDenormal());
671 EXPECT_EQ(fcPosSubnormal, T.classify());
674 // Test quadruple precision
676 const char *MinNormalStr = "3.36210314311209350626267781732175260e-4932";
677 EXPECT_FALSE(APFloat(APFloat::IEEEquad(), MinNormalStr).isDenormal());
678 EXPECT_FALSE(APFloat(APFloat::IEEEquad(), 0).isDenormal());
680 APFloat Val2(APFloat::IEEEquad(), 2);
681 APFloat T(APFloat::IEEEquad(), MinNormalStr);
682 T.divide(Val2, rdmd);
683 EXPECT_TRUE(T.isDenormal());
684 EXPECT_EQ(fcPosSubnormal, T.classify());
687 // Test TF32
689 const char *MinNormalStr = "1.17549435082228750797e-38";
690 EXPECT_FALSE(APFloat(APFloat::FloatTF32(), MinNormalStr).isDenormal());
691 EXPECT_FALSE(APFloat(APFloat::FloatTF32(), 0).isDenormal());
693 APFloat Val2(APFloat::FloatTF32(), 2);
694 APFloat T(APFloat::FloatTF32(), MinNormalStr);
695 T.divide(Val2, rdmd);
696 EXPECT_TRUE(T.isDenormal());
697 EXPECT_EQ(fcPosSubnormal, T.classify());
699 const char *NegMinNormalStr = "-1.17549435082228750797e-38";
700 EXPECT_FALSE(APFloat(APFloat::FloatTF32(), NegMinNormalStr).isDenormal());
701 APFloat NegT(APFloat::FloatTF32(), NegMinNormalStr);
702 NegT.divide(Val2, rdmd);
703 EXPECT_TRUE(NegT.isDenormal());
704 EXPECT_EQ(fcNegSubnormal, NegT.classify());
708 TEST(APFloatTest, IsSmallestNormalized) {
709 for (unsigned I = 0; I != APFloat::S_MaxSemantics + 1; ++I) {
710 const fltSemantics &Semantics =
711 APFloat::EnumToSemantics(static_cast<APFloat::Semantics>(I));
713 EXPECT_FALSE(APFloat::getZero(Semantics, false).isSmallestNormalized());
714 EXPECT_FALSE(APFloat::getZero(Semantics, true).isSmallestNormalized());
716 EXPECT_FALSE(APFloat::getInf(Semantics, false).isSmallestNormalized());
717 EXPECT_FALSE(APFloat::getInf(Semantics, true).isSmallestNormalized());
719 EXPECT_FALSE(APFloat::getQNaN(Semantics).isSmallestNormalized());
720 EXPECT_FALSE(APFloat::getSNaN(Semantics).isSmallestNormalized());
722 EXPECT_FALSE(APFloat::getLargest(Semantics).isSmallestNormalized());
723 EXPECT_FALSE(APFloat::getLargest(Semantics, true).isSmallestNormalized());
725 EXPECT_FALSE(APFloat::getSmallest(Semantics).isSmallestNormalized());
726 EXPECT_FALSE(APFloat::getSmallest(Semantics, true).isSmallestNormalized());
728 EXPECT_FALSE(APFloat::getAllOnesValue(Semantics).isSmallestNormalized());
730 APFloat PosSmallestNormalized =
731 APFloat::getSmallestNormalized(Semantics, false);
732 APFloat NegSmallestNormalized =
733 APFloat::getSmallestNormalized(Semantics, true);
734 EXPECT_TRUE(PosSmallestNormalized.isSmallestNormalized());
735 EXPECT_TRUE(NegSmallestNormalized.isSmallestNormalized());
736 EXPECT_EQ(fcPosNormal, PosSmallestNormalized.classify());
737 EXPECT_EQ(fcNegNormal, NegSmallestNormalized.classify());
739 for (APFloat *Val : {&PosSmallestNormalized, &NegSmallestNormalized}) {
740 bool OldSign = Val->isNegative();
742 // Step down, make sure it's still not smallest normalized.
743 EXPECT_EQ(APFloat::opOK, Val->next(false));
744 EXPECT_EQ(OldSign, Val->isNegative());
745 EXPECT_FALSE(Val->isSmallestNormalized());
746 EXPECT_EQ(OldSign, Val->isNegative());
748 // Step back up should restore it to being smallest normalized.
749 EXPECT_EQ(APFloat::opOK, Val->next(true));
750 EXPECT_TRUE(Val->isSmallestNormalized());
751 EXPECT_EQ(OldSign, Val->isNegative());
753 // Step beyond should no longer smallest normalized.
754 EXPECT_EQ(APFloat::opOK, Val->next(true));
755 EXPECT_FALSE(Val->isSmallestNormalized());
756 EXPECT_EQ(OldSign, Val->isNegative());
761 TEST(APFloatTest, Zero) {
762 EXPECT_EQ(0.0f, APFloat(0.0f).convertToFloat());
763 EXPECT_EQ(-0.0f, APFloat(-0.0f).convertToFloat());
764 EXPECT_TRUE(APFloat(-0.0f).isNegative());
766 EXPECT_EQ(0.0, APFloat(0.0).convertToDouble());
767 EXPECT_EQ(-0.0, APFloat(-0.0).convertToDouble());
768 EXPECT_TRUE(APFloat(-0.0).isNegative());
770 EXPECT_EQ(fcPosZero, APFloat(0.0).classify());
771 EXPECT_EQ(fcNegZero, APFloat(-0.0).classify());
774 TEST(APFloatTest, DecimalStringsWithoutNullTerminators) {
775 // Make sure that we can parse strings without null terminators.
776 // rdar://14323230.
777 EXPECT_EQ(convertToDoubleFromString(StringRef("0.00", 3)), 0.0);
778 EXPECT_EQ(convertToDoubleFromString(StringRef("0.01", 3)), 0.0);
779 EXPECT_EQ(convertToDoubleFromString(StringRef("0.09", 3)), 0.0);
780 EXPECT_EQ(convertToDoubleFromString(StringRef("0.095", 4)), 0.09);
781 EXPECT_EQ(convertToDoubleFromString(StringRef("0.00e+3", 7)), 0.00);
782 EXPECT_EQ(convertToDoubleFromString(StringRef("0e+3", 4)), 0.00);
785 TEST(APFloatTest, fromZeroDecimalString) {
786 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0").convertToDouble());
787 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0").convertToDouble());
788 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0").convertToDouble());
790 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.").convertToDouble());
791 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.").convertToDouble());
792 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.").convertToDouble());
794 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0").convertToDouble());
795 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0").convertToDouble());
796 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0").convertToDouble());
798 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0").convertToDouble());
799 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0").convertToDouble());
800 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0").convertToDouble());
802 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "00000.").convertToDouble());
803 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+00000.").convertToDouble());
804 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-00000.").convertToDouble());
806 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), ".00000").convertToDouble());
807 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.00000").convertToDouble());
808 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.00000").convertToDouble());
810 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0000.00000").convertToDouble());
811 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0000.00000").convertToDouble());
812 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0000.00000").convertToDouble());
815 TEST(APFloatTest, fromZeroDecimalSingleExponentString) {
816 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e1").convertToDouble());
817 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e1").convertToDouble());
818 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e1").convertToDouble());
820 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e+1").convertToDouble());
821 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e+1").convertToDouble());
822 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e+1").convertToDouble());
824 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e-1").convertToDouble());
825 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e-1").convertToDouble());
826 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e-1").convertToDouble());
829 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e1").convertToDouble());
830 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e1").convertToDouble());
831 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e1").convertToDouble());
833 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e+1").convertToDouble());
834 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e+1").convertToDouble());
835 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e+1").convertToDouble());
837 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e-1").convertToDouble());
838 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e-1").convertToDouble());
839 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e-1").convertToDouble());
841 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e1").convertToDouble());
842 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e1").convertToDouble());
843 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e1").convertToDouble());
845 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e+1").convertToDouble());
846 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e+1").convertToDouble());
847 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e+1").convertToDouble());
849 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e-1").convertToDouble());
850 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e-1").convertToDouble());
851 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e-1").convertToDouble());
854 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e1").convertToDouble());
855 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e1").convertToDouble());
856 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e1").convertToDouble());
858 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e+1").convertToDouble());
859 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e+1").convertToDouble());
860 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e+1").convertToDouble());
862 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e-1").convertToDouble());
863 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e-1").convertToDouble());
864 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e-1").convertToDouble());
867 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "000.0000e1").convertToDouble());
868 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+000.0000e+1").convertToDouble());
869 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-000.0000e+1").convertToDouble());
872 TEST(APFloatTest, fromZeroDecimalLargeExponentString) {
873 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e1234").convertToDouble());
874 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e1234").convertToDouble());
875 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e1234").convertToDouble());
877 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e+1234").convertToDouble());
878 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e+1234").convertToDouble());
879 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e+1234").convertToDouble());
881 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e-1234").convertToDouble());
882 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e-1234").convertToDouble());
883 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e-1234").convertToDouble());
885 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), "000.0000e1234").convertToDouble());
886 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), "000.0000e-1234").convertToDouble());
888 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), StringRef("0e1234" "\0" "2", 6)).convertToDouble());
891 TEST(APFloatTest, fromZeroHexadecimalString) {
892 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p1").convertToDouble());
893 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p1").convertToDouble());
894 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p1").convertToDouble());
896 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p+1").convertToDouble());
897 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p+1").convertToDouble());
898 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p+1").convertToDouble());
900 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p-1").convertToDouble());
901 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p-1").convertToDouble());
902 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p-1").convertToDouble());
905 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1").convertToDouble());
906 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p1").convertToDouble());
907 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p1").convertToDouble());
909 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p+1").convertToDouble());
910 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p+1").convertToDouble());
911 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p+1").convertToDouble());
913 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p-1").convertToDouble());
914 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p-1").convertToDouble());
915 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p-1").convertToDouble());
918 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p1").convertToDouble());
919 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p1").convertToDouble());
920 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p1").convertToDouble());
922 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p+1").convertToDouble());
923 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p+1").convertToDouble());
924 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p+1").convertToDouble());
926 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p-1").convertToDouble());
927 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p-1").convertToDouble());
928 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p-1").convertToDouble());
931 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p1").convertToDouble());
932 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p1").convertToDouble());
933 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p1").convertToDouble());
935 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p+1").convertToDouble());
936 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p+1").convertToDouble());
937 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p+1").convertToDouble());
939 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p-1").convertToDouble());
940 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p-1").convertToDouble());
941 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p-1").convertToDouble());
944 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x00000.p1").convertToDouble());
945 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0000.00000p1").convertToDouble());
946 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.00000p1").convertToDouble());
947 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1").convertToDouble());
948 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p1234").convertToDouble());
949 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p1234").convertToDouble());
950 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x00000.p1234").convertToDouble());
951 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0000.00000p1234").convertToDouble());
952 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.00000p1234").convertToDouble());
953 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1234").convertToDouble());
956 TEST(APFloatTest, fromDecimalString) {
957 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1").convertToDouble());
958 EXPECT_EQ(2.0, APFloat(APFloat::IEEEdouble(), "2.").convertToDouble());
959 EXPECT_EQ(0.5, APFloat(APFloat::IEEEdouble(), ".5").convertToDouble());
960 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0").convertToDouble());
961 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-2").convertToDouble());
962 EXPECT_EQ(-4.0, APFloat(APFloat::IEEEdouble(), "-4.").convertToDouble());
963 EXPECT_EQ(-0.5, APFloat(APFloat::IEEEdouble(), "-.5").convertToDouble());
964 EXPECT_EQ(-1.5, APFloat(APFloat::IEEEdouble(), "-1.5").convertToDouble());
965 EXPECT_EQ(1.25e12, APFloat(APFloat::IEEEdouble(), "1.25e12").convertToDouble());
966 EXPECT_EQ(1.25e+12, APFloat(APFloat::IEEEdouble(), "1.25e+12").convertToDouble());
967 EXPECT_EQ(1.25e-12, APFloat(APFloat::IEEEdouble(), "1.25e-12").convertToDouble());
968 EXPECT_EQ(1024.0, APFloat(APFloat::IEEEdouble(), "1024.").convertToDouble());
969 EXPECT_EQ(1024.05, APFloat(APFloat::IEEEdouble(), "1024.05000").convertToDouble());
970 EXPECT_EQ(0.05, APFloat(APFloat::IEEEdouble(), ".05000").convertToDouble());
971 EXPECT_EQ(2.0, APFloat(APFloat::IEEEdouble(), "2.").convertToDouble());
972 EXPECT_EQ(2.0e2, APFloat(APFloat::IEEEdouble(), "2.e2").convertToDouble());
973 EXPECT_EQ(2.0e+2, APFloat(APFloat::IEEEdouble(), "2.e+2").convertToDouble());
974 EXPECT_EQ(2.0e-2, APFloat(APFloat::IEEEdouble(), "2.e-2").convertToDouble());
975 EXPECT_EQ(2.05e2, APFloat(APFloat::IEEEdouble(), "002.05000e2").convertToDouble());
976 EXPECT_EQ(2.05e+2, APFloat(APFloat::IEEEdouble(), "002.05000e+2").convertToDouble());
977 EXPECT_EQ(2.05e-2, APFloat(APFloat::IEEEdouble(), "002.05000e-2").convertToDouble());
978 EXPECT_EQ(2.05e12, APFloat(APFloat::IEEEdouble(), "002.05000e12").convertToDouble());
979 EXPECT_EQ(2.05e+12, APFloat(APFloat::IEEEdouble(), "002.05000e+12").convertToDouble());
980 EXPECT_EQ(2.05e-12, APFloat(APFloat::IEEEdouble(), "002.05000e-12").convertToDouble());
982 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1e").convertToDouble());
983 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "+1e").convertToDouble());
984 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-1e").convertToDouble());
986 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.e").convertToDouble());
987 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "+1.e").convertToDouble());
988 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-1.e").convertToDouble());
990 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), ".1e").convertToDouble());
991 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), "+.1e").convertToDouble());
992 EXPECT_EQ(-0.1, APFloat(APFloat::IEEEdouble(), "-.1e").convertToDouble());
994 EXPECT_EQ(1.1, APFloat(APFloat::IEEEdouble(), "1.1e").convertToDouble());
995 EXPECT_EQ(1.1, APFloat(APFloat::IEEEdouble(), "+1.1e").convertToDouble());
996 EXPECT_EQ(-1.1, APFloat(APFloat::IEEEdouble(), "-1.1e").convertToDouble());
998 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1e+").convertToDouble());
999 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1e-").convertToDouble());
1001 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), ".1e").convertToDouble());
1002 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), ".1e+").convertToDouble());
1003 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), ".1e-").convertToDouble());
1005 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0e").convertToDouble());
1006 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0e+").convertToDouble());
1007 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0e-").convertToDouble());
1009 // These are "carefully selected" to overflow the fast log-base
1010 // calculations in APFloat.cpp
1011 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "99e99999").isInfinity());
1012 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-99e99999").isInfinity());
1013 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "1e-99999").isPosZero());
1014 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-1e-99999").isNegZero());
1016 EXPECT_EQ(2.71828, convertToDoubleFromString("2.71828"));
1019 TEST(APFloatTest, fromStringSpecials) {
1020 const fltSemantics &Sem = APFloat::IEEEdouble();
1021 const unsigned Precision = 53;
1022 const unsigned PayloadBits = Precision - 2;
1023 uint64_t PayloadMask = (uint64_t(1) << PayloadBits) - uint64_t(1);
1025 uint64_t NaNPayloads[] = {
1028 123,
1029 0xDEADBEEF,
1030 uint64_t(-2),
1031 uint64_t(1) << PayloadBits, // overflow bit
1032 uint64_t(1) << (PayloadBits - 1), // signaling bit
1033 uint64_t(1) << (PayloadBits - 2) // highest possible bit
1036 // Convert payload integer to decimal string representation.
1037 std::string NaNPayloadDecStrings[std::size(NaNPayloads)];
1038 for (size_t I = 0; I < std::size(NaNPayloads); ++I)
1039 NaNPayloadDecStrings[I] = utostr(NaNPayloads[I]);
1041 // Convert payload integer to hexadecimal string representation.
1042 std::string NaNPayloadHexStrings[std::size(NaNPayloads)];
1043 for (size_t I = 0; I < std::size(NaNPayloads); ++I)
1044 NaNPayloadHexStrings[I] = "0x" + utohexstr(NaNPayloads[I]);
1046 // Fix payloads to expected result.
1047 for (uint64_t &Payload : NaNPayloads)
1048 Payload &= PayloadMask;
1050 // Signaling NaN must have a non-zero payload. In case a zero payload is
1051 // requested, a default arbitrary payload is set instead. Save this payload
1052 // for testing.
1053 const uint64_t SNaNDefaultPayload =
1054 APFloat::getSNaN(Sem).bitcastToAPInt().getZExtValue() & PayloadMask;
1056 // Negative sign prefix (or none - for positive).
1057 const char Signs[] = {0, '-'};
1059 // "Signaling" prefix (or none - for "Quiet").
1060 const char NaNTypes[] = {0, 's', 'S'};
1062 const StringRef NaNStrings[] = {"nan", "NaN"};
1063 for (StringRef NaNStr : NaNStrings)
1064 for (char TypeChar : NaNTypes) {
1065 bool Signaling = (TypeChar == 's' || TypeChar == 'S');
1067 for (size_t J = 0; J < std::size(NaNPayloads); ++J) {
1068 uint64_t Payload = (Signaling && !NaNPayloads[J]) ? SNaNDefaultPayload
1069 : NaNPayloads[J];
1070 std::string &PayloadDec = NaNPayloadDecStrings[J];
1071 std::string &PayloadHex = NaNPayloadHexStrings[J];
1073 for (char SignChar : Signs) {
1074 bool Negative = (SignChar == '-');
1076 std::string TestStrings[5];
1077 size_t NumTestStrings = 0;
1079 std::string Prefix;
1080 if (SignChar)
1081 Prefix += SignChar;
1082 if (TypeChar)
1083 Prefix += TypeChar;
1084 Prefix += NaNStr;
1086 // Test without any paylod.
1087 if (!Payload)
1088 TestStrings[NumTestStrings++] = Prefix;
1090 // Test with the payload as a suffix.
1091 TestStrings[NumTestStrings++] = Prefix + PayloadDec;
1092 TestStrings[NumTestStrings++] = Prefix + PayloadHex;
1094 // Test with the payload inside parentheses.
1095 TestStrings[NumTestStrings++] = Prefix + '(' + PayloadDec + ')';
1096 TestStrings[NumTestStrings++] = Prefix + '(' + PayloadHex + ')';
1098 for (size_t K = 0; K < NumTestStrings; ++K) {
1099 StringRef TestStr = TestStrings[K];
1101 APFloat F(Sem);
1102 bool HasError = !F.convertFromString(
1103 TestStr, llvm::APFloat::rmNearestTiesToEven);
1104 EXPECT_FALSE(HasError);
1105 EXPECT_TRUE(F.isNaN());
1106 EXPECT_EQ(Signaling, F.isSignaling());
1107 EXPECT_EQ(Negative, F.isNegative());
1108 uint64_t PayloadResult =
1109 F.bitcastToAPInt().getZExtValue() & PayloadMask;
1110 EXPECT_EQ(Payload, PayloadResult);
1116 const StringRef InfStrings[] = {"inf", "INFINITY", "+Inf",
1117 "-inf", "-INFINITY", "-Inf"};
1118 for (StringRef InfStr : InfStrings) {
1119 bool Negative = InfStr.front() == '-';
1121 APFloat F(Sem);
1122 bool HasError =
1123 !F.convertFromString(InfStr, llvm::APFloat::rmNearestTiesToEven);
1124 EXPECT_FALSE(HasError);
1125 EXPECT_TRUE(F.isInfinity());
1126 EXPECT_EQ(Negative, F.isNegative());
1127 uint64_t PayloadResult = F.bitcastToAPInt().getZExtValue() & PayloadMask;
1128 EXPECT_EQ(UINT64_C(0), PayloadResult);
1132 TEST(APFloatTest, fromToStringSpecials) {
1133 auto expects = [] (const char *first, const char *second) {
1134 std::string roundtrip = convertToString(convertToDoubleFromString(second), 0, 3);
1135 EXPECT_STREQ(first, roundtrip.c_str());
1137 expects("+Inf", "+Inf");
1138 expects("+Inf", "INFINITY");
1139 expects("+Inf", "inf");
1140 expects("-Inf", "-Inf");
1141 expects("-Inf", "-INFINITY");
1142 expects("-Inf", "-inf");
1143 expects("NaN", "NaN");
1144 expects("NaN", "nan");
1145 expects("NaN", "-NaN");
1146 expects("NaN", "-nan");
1149 TEST(APFloatTest, fromHexadecimalString) {
1150 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p0").convertToDouble());
1151 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p0").convertToDouble());
1152 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p0").convertToDouble());
1154 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p+0").convertToDouble());
1155 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p+0").convertToDouble());
1156 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p+0").convertToDouble());
1158 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p-0").convertToDouble());
1159 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p-0").convertToDouble());
1160 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p-0").convertToDouble());
1163 EXPECT_EQ( 2.0, APFloat(APFloat::IEEEdouble(), "0x1p1").convertToDouble());
1164 EXPECT_EQ(+2.0, APFloat(APFloat::IEEEdouble(), "+0x1p1").convertToDouble());
1165 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-0x1p1").convertToDouble());
1167 EXPECT_EQ( 2.0, APFloat(APFloat::IEEEdouble(), "0x1p+1").convertToDouble());
1168 EXPECT_EQ(+2.0, APFloat(APFloat::IEEEdouble(), "+0x1p+1").convertToDouble());
1169 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-0x1p+1").convertToDouble());
1171 EXPECT_EQ( 0.5, APFloat(APFloat::IEEEdouble(), "0x1p-1").convertToDouble());
1172 EXPECT_EQ(+0.5, APFloat(APFloat::IEEEdouble(), "+0x1p-1").convertToDouble());
1173 EXPECT_EQ(-0.5, APFloat(APFloat::IEEEdouble(), "-0x1p-1").convertToDouble());
1176 EXPECT_EQ( 3.0, APFloat(APFloat::IEEEdouble(), "0x1.8p1").convertToDouble());
1177 EXPECT_EQ(+3.0, APFloat(APFloat::IEEEdouble(), "+0x1.8p1").convertToDouble());
1178 EXPECT_EQ(-3.0, APFloat(APFloat::IEEEdouble(), "-0x1.8p1").convertToDouble());
1180 EXPECT_EQ( 3.0, APFloat(APFloat::IEEEdouble(), "0x1.8p+1").convertToDouble());
1181 EXPECT_EQ(+3.0, APFloat(APFloat::IEEEdouble(), "+0x1.8p+1").convertToDouble());
1182 EXPECT_EQ(-3.0, APFloat(APFloat::IEEEdouble(), "-0x1.8p+1").convertToDouble());
1184 EXPECT_EQ( 0.75, APFloat(APFloat::IEEEdouble(), "0x1.8p-1").convertToDouble());
1185 EXPECT_EQ(+0.75, APFloat(APFloat::IEEEdouble(), "+0x1.8p-1").convertToDouble());
1186 EXPECT_EQ(-0.75, APFloat(APFloat::IEEEdouble(), "-0x1.8p-1").convertToDouble());
1189 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p1").convertToDouble());
1190 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p1").convertToDouble());
1191 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p1").convertToDouble());
1193 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p+1").convertToDouble());
1194 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p+1").convertToDouble());
1195 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p+1").convertToDouble());
1197 EXPECT_EQ( 2048.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p-1").convertToDouble());
1198 EXPECT_EQ(+2048.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p-1").convertToDouble());
1199 EXPECT_EQ(-2048.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p-1").convertToDouble());
1202 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000p1").convertToDouble());
1203 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000p1").convertToDouble());
1204 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000p1").convertToDouble());
1206 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000p+1").convertToDouble());
1207 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000p+1").convertToDouble());
1208 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000p+1").convertToDouble());
1210 EXPECT_EQ( 2048.0, APFloat(APFloat::IEEEdouble(), "0x1000p-1").convertToDouble());
1211 EXPECT_EQ(+2048.0, APFloat(APFloat::IEEEdouble(), "+0x1000p-1").convertToDouble());
1212 EXPECT_EQ(-2048.0, APFloat(APFloat::IEEEdouble(), "-0x1000p-1").convertToDouble());
1215 EXPECT_EQ( 16384.0, APFloat(APFloat::IEEEdouble(), "0x10p10").convertToDouble());
1216 EXPECT_EQ(+16384.0, APFloat(APFloat::IEEEdouble(), "+0x10p10").convertToDouble());
1217 EXPECT_EQ(-16384.0, APFloat(APFloat::IEEEdouble(), "-0x10p10").convertToDouble());
1219 EXPECT_EQ( 16384.0, APFloat(APFloat::IEEEdouble(), "0x10p+10").convertToDouble());
1220 EXPECT_EQ(+16384.0, APFloat(APFloat::IEEEdouble(), "+0x10p+10").convertToDouble());
1221 EXPECT_EQ(-16384.0, APFloat(APFloat::IEEEdouble(), "-0x10p+10").convertToDouble());
1223 EXPECT_EQ( 0.015625, APFloat(APFloat::IEEEdouble(), "0x10p-10").convertToDouble());
1224 EXPECT_EQ(+0.015625, APFloat(APFloat::IEEEdouble(), "+0x10p-10").convertToDouble());
1225 EXPECT_EQ(-0.015625, APFloat(APFloat::IEEEdouble(), "-0x10p-10").convertToDouble());
1227 EXPECT_EQ(1.0625, APFloat(APFloat::IEEEdouble(), "0x1.1p0").convertToDouble());
1228 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "0x1p0").convertToDouble());
1230 EXPECT_EQ(convertToDoubleFromString("0x1p-150"),
1231 convertToDoubleFromString("+0x800000000000000001.p-221"));
1232 EXPECT_EQ(2251799813685248.5,
1233 convertToDoubleFromString("0x80000000000004000000.010p-28"));
1236 TEST(APFloatTest, toString) {
1237 ASSERT_EQ("10", convertToString(10.0, 6, 3));
1238 ASSERT_EQ("1.0E+1", convertToString(10.0, 6, 0));
1239 ASSERT_EQ("10100", convertToString(1.01E+4, 5, 2));
1240 ASSERT_EQ("1.01E+4", convertToString(1.01E+4, 4, 2));
1241 ASSERT_EQ("1.01E+4", convertToString(1.01E+4, 5, 1));
1242 ASSERT_EQ("0.0101", convertToString(1.01E-2, 5, 2));
1243 ASSERT_EQ("0.0101", convertToString(1.01E-2, 4, 2));
1244 ASSERT_EQ("1.01E-2", convertToString(1.01E-2, 5, 1));
1245 ASSERT_EQ("0.78539816339744828", convertToString(0.78539816339744830961, 0, 3));
1246 ASSERT_EQ("4.9406564584124654E-324", convertToString(4.9406564584124654e-324, 0, 3));
1247 ASSERT_EQ("873.18340000000001", convertToString(873.1834, 0, 1));
1248 ASSERT_EQ("8.7318340000000001E+2", convertToString(873.1834, 0, 0));
1249 ASSERT_EQ("1.7976931348623157E+308", convertToString(1.7976931348623157E+308, 0, 0));
1250 ASSERT_EQ("10", convertToString(10.0, 6, 3, false));
1251 ASSERT_EQ("1.000000e+01", convertToString(10.0, 6, 0, false));
1252 ASSERT_EQ("10100", convertToString(1.01E+4, 5, 2, false));
1253 ASSERT_EQ("1.0100e+04", convertToString(1.01E+4, 4, 2, false));
1254 ASSERT_EQ("1.01000e+04", convertToString(1.01E+4, 5, 1, false));
1255 ASSERT_EQ("0.0101", convertToString(1.01E-2, 5, 2, false));
1256 ASSERT_EQ("0.0101", convertToString(1.01E-2, 4, 2, false));
1257 ASSERT_EQ("1.01000e-02", convertToString(1.01E-2, 5, 1, false));
1258 ASSERT_EQ("0.78539816339744828",
1259 convertToString(0.78539816339744830961, 0, 3, false));
1260 ASSERT_EQ("4.94065645841246540e-324",
1261 convertToString(4.9406564584124654e-324, 0, 3, false));
1262 ASSERT_EQ("873.18340000000001", convertToString(873.1834, 0, 1, false));
1263 ASSERT_EQ("8.73183400000000010e+02", convertToString(873.1834, 0, 0, false));
1264 ASSERT_EQ("1.79769313486231570e+308",
1265 convertToString(1.7976931348623157E+308, 0, 0, false));
1268 SmallString<64> Str;
1269 APFloat UnnormalZero(APFloat::x87DoubleExtended(), APInt(80, {0, 1}));
1270 UnnormalZero.toString(Str);
1271 ASSERT_EQ("NaN", Str);
1275 TEST(APFloatTest, toInteger) {
1276 bool isExact = false;
1277 APSInt result(5, /*isUnsigned=*/true);
1279 EXPECT_EQ(APFloat::opOK,
1280 APFloat(APFloat::IEEEdouble(), "10")
1281 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1282 EXPECT_TRUE(isExact);
1283 EXPECT_EQ(APSInt(APInt(5, 10), true), result);
1285 EXPECT_EQ(APFloat::opInvalidOp,
1286 APFloat(APFloat::IEEEdouble(), "-10")
1287 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1288 EXPECT_FALSE(isExact);
1289 EXPECT_EQ(APSInt::getMinValue(5, true), result);
1291 EXPECT_EQ(APFloat::opInvalidOp,
1292 APFloat(APFloat::IEEEdouble(), "32")
1293 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1294 EXPECT_FALSE(isExact);
1295 EXPECT_EQ(APSInt::getMaxValue(5, true), result);
1297 EXPECT_EQ(APFloat::opInexact,
1298 APFloat(APFloat::IEEEdouble(), "7.9")
1299 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1300 EXPECT_FALSE(isExact);
1301 EXPECT_EQ(APSInt(APInt(5, 7), true), result);
1303 result.setIsUnsigned(false);
1304 EXPECT_EQ(APFloat::opOK,
1305 APFloat(APFloat::IEEEdouble(), "-10")
1306 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1307 EXPECT_TRUE(isExact);
1308 EXPECT_EQ(APSInt(APInt(5, -10, true), false), result);
1310 EXPECT_EQ(APFloat::opInvalidOp,
1311 APFloat(APFloat::IEEEdouble(), "-17")
1312 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1313 EXPECT_FALSE(isExact);
1314 EXPECT_EQ(APSInt::getMinValue(5, false), result);
1316 EXPECT_EQ(APFloat::opInvalidOp,
1317 APFloat(APFloat::IEEEdouble(), "16")
1318 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1319 EXPECT_FALSE(isExact);
1320 EXPECT_EQ(APSInt::getMaxValue(5, false), result);
1323 static APInt nanbitsFromAPInt(const fltSemantics &Sem, bool SNaN, bool Negative,
1324 uint64_t payload) {
1325 APInt appayload(64, payload);
1326 if (SNaN)
1327 return APFloat::getSNaN(Sem, Negative, &appayload).bitcastToAPInt();
1328 else
1329 return APFloat::getQNaN(Sem, Negative, &appayload).bitcastToAPInt();
1332 TEST(APFloatTest, makeNaN) {
1333 const struct {
1334 uint64_t expected;
1335 const fltSemantics &semantics;
1336 bool SNaN;
1337 bool Negative;
1338 uint64_t payload;
1339 } tests[] = {
1340 // clang-format off
1341 /* expected semantics SNaN Neg payload */
1342 { 0x7fc00000ULL, APFloat::IEEEsingle(), false, false, 0x00000000ULL },
1343 { 0xffc00000ULL, APFloat::IEEEsingle(), false, true, 0x00000000ULL },
1344 { 0x7fc0ae72ULL, APFloat::IEEEsingle(), false, false, 0x0000ae72ULL },
1345 { 0x7fffae72ULL, APFloat::IEEEsingle(), false, false, 0xffffae72ULL },
1346 { 0x7fdaae72ULL, APFloat::IEEEsingle(), false, false, 0x00daae72ULL },
1347 { 0x7fa00000ULL, APFloat::IEEEsingle(), true, false, 0x00000000ULL },
1348 { 0xffa00000ULL, APFloat::IEEEsingle(), true, true, 0x00000000ULL },
1349 { 0x7f80ae72ULL, APFloat::IEEEsingle(), true, false, 0x0000ae72ULL },
1350 { 0x7fbfae72ULL, APFloat::IEEEsingle(), true, false, 0xffffae72ULL },
1351 { 0x7f9aae72ULL, APFloat::IEEEsingle(), true, false, 0x001aae72ULL },
1352 { 0x7ff8000000000000ULL, APFloat::IEEEdouble(), false, false, 0x0000000000000000ULL },
1353 { 0xfff8000000000000ULL, APFloat::IEEEdouble(), false, true, 0x0000000000000000ULL },
1354 { 0x7ff800000000ae72ULL, APFloat::IEEEdouble(), false, false, 0x000000000000ae72ULL },
1355 { 0x7fffffffffffae72ULL, APFloat::IEEEdouble(), false, false, 0xffffffffffffae72ULL },
1356 { 0x7ffdaaaaaaaaae72ULL, APFloat::IEEEdouble(), false, false, 0x000daaaaaaaaae72ULL },
1357 { 0x7ff4000000000000ULL, APFloat::IEEEdouble(), true, false, 0x0000000000000000ULL },
1358 { 0xfff4000000000000ULL, APFloat::IEEEdouble(), true, true, 0x0000000000000000ULL },
1359 { 0x7ff000000000ae72ULL, APFloat::IEEEdouble(), true, false, 0x000000000000ae72ULL },
1360 { 0x7ff7ffffffffae72ULL, APFloat::IEEEdouble(), true, false, 0xffffffffffffae72ULL },
1361 { 0x7ff1aaaaaaaaae72ULL, APFloat::IEEEdouble(), true, false, 0x0001aaaaaaaaae72ULL },
1362 { 0x80ULL, APFloat::Float8E5M2FNUZ(), false, false, 0xaaULL },
1363 { 0x80ULL, APFloat::Float8E5M2FNUZ(), false, true, 0xaaULL },
1364 { 0x80ULL, APFloat::Float8E5M2FNUZ(), true, false, 0xaaULL },
1365 { 0x80ULL, APFloat::Float8E5M2FNUZ(), true, true, 0xaaULL },
1366 { 0x80ULL, APFloat::Float8E4M3FNUZ(), false, false, 0xaaULL },
1367 { 0x80ULL, APFloat::Float8E4M3FNUZ(), false, true, 0xaaULL },
1368 { 0x80ULL, APFloat::Float8E4M3FNUZ(), true, false, 0xaaULL },
1369 { 0x80ULL, APFloat::Float8E4M3FNUZ(), true, true, 0xaaULL },
1370 { 0x80ULL, APFloat::Float8E4M3B11FNUZ(), false, false, 0xaaULL },
1371 { 0x80ULL, APFloat::Float8E4M3B11FNUZ(), false, true, 0xaaULL },
1372 { 0x80ULL, APFloat::Float8E4M3B11FNUZ(), true, false, 0xaaULL },
1373 { 0x80ULL, APFloat::Float8E4M3B11FNUZ(), true, true, 0xaaULL },
1374 { 0x3fe00ULL, APFloat::FloatTF32(), false, false, 0x00000000ULL },
1375 { 0x7fe00ULL, APFloat::FloatTF32(), false, true, 0x00000000ULL },
1376 { 0x3feaaULL, APFloat::FloatTF32(), false, false, 0xaaULL },
1377 { 0x3ffaaULL, APFloat::FloatTF32(), false, false, 0xdaaULL },
1378 { 0x3ffaaULL, APFloat::FloatTF32(), false, false, 0xfdaaULL },
1379 { 0x3fd00ULL, APFloat::FloatTF32(), true, false, 0x00000000ULL },
1380 { 0x7fd00ULL, APFloat::FloatTF32(), true, true, 0x00000000ULL },
1381 { 0x3fcaaULL, APFloat::FloatTF32(), true, false, 0xaaULL },
1382 { 0x3fdaaULL, APFloat::FloatTF32(), true, false, 0xfaaULL },
1383 { 0x3fdaaULL, APFloat::FloatTF32(), true, false, 0x1aaULL },
1384 // clang-format on
1387 for (const auto &t : tests) {
1388 ASSERT_EQ(t.expected, nanbitsFromAPInt(t.semantics, t.SNaN, t.Negative, t.payload));
1392 #ifdef GTEST_HAS_DEATH_TEST
1393 #ifndef NDEBUG
1394 TEST(APFloatTest, SemanticsDeath) {
1395 EXPECT_DEATH(APFloat(APFloat::IEEEquad(), 0).convertToDouble(),
1396 "Float semantics is not representable by IEEEdouble");
1397 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), 0).convertToFloat(),
1398 "Float semantics is not representable by IEEEsingle");
1400 #endif
1401 #endif
1403 TEST(APFloatTest, StringDecimalError) {
1404 EXPECT_EQ("Invalid string length", convertToErrorFromString(""));
1405 EXPECT_EQ("String has no digits", convertToErrorFromString("+"));
1406 EXPECT_EQ("String has no digits", convertToErrorFromString("-"));
1408 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("\0", 1)));
1409 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("1\0", 2)));
1410 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("1" "\0" "2", 3)));
1411 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("1" "\0" "2e1", 5)));
1412 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("1e\0", 3)));
1413 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("1e1\0", 4)));
1414 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("1e1" "\0" "2", 5)));
1416 EXPECT_EQ("Invalid character in significand", convertToErrorFromString("1.0f"));
1418 EXPECT_EQ("String contains multiple dots", convertToErrorFromString(".."));
1419 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("..0"));
1420 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("1.0.0"));
1423 TEST(APFloatTest, StringDecimalSignificandError) {
1424 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "."));
1425 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+."));
1426 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-."));
1429 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "e"));
1430 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+e"));
1431 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-e"));
1433 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "e1"));
1434 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+e1"));
1435 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-e1"));
1437 EXPECT_EQ("Significand has no digits", convertToErrorFromString( ".e1"));
1438 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+.e1"));
1439 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-.e1"));
1442 EXPECT_EQ("Significand has no digits", convertToErrorFromString( ".e"));
1443 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+.e"));
1444 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-.e"));
1447 TEST(APFloatTest, StringHexadecimalError) {
1448 EXPECT_EQ("Invalid string", convertToErrorFromString( "0x"));
1449 EXPECT_EQ("Invalid string", convertToErrorFromString("+0x"));
1450 EXPECT_EQ("Invalid string", convertToErrorFromString("-0x"));
1452 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString( "0x0"));
1453 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("+0x0"));
1454 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("-0x0"));
1456 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString( "0x0."));
1457 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("+0x0."));
1458 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("-0x0."));
1460 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString( "0x.0"));
1461 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("+0x.0"));
1462 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("-0x.0"));
1464 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString( "0x0.0"));
1465 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("+0x0.0"));
1466 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("-0x0.0"));
1468 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("0x\0", 3)));
1469 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("0x1\0", 4)));
1470 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("0x1" "\0" "2", 5)));
1471 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("0x1" "\0" "2p1", 7)));
1472 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("0x1p\0", 5)));
1473 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("0x1p1\0", 6)));
1474 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("0x1p1" "\0" "2", 7)));
1476 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString("0x1p0f"));
1478 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("0x..p1"));
1479 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("0x..0p1"));
1480 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("0x1.0.0p1"));
1483 TEST(APFloatTest, StringHexadecimalSignificandError) {
1484 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0x."));
1485 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0x."));
1486 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0x."));
1488 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0xp"));
1489 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0xp"));
1490 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0xp"));
1492 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0xp+"));
1493 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0xp+"));
1494 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0xp+"));
1496 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0xp-"));
1497 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0xp-"));
1498 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0xp-"));
1501 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0x.p"));
1502 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0x.p"));
1503 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0x.p"));
1505 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0x.p+"));
1506 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0x.p+"));
1507 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0x.p+"));
1509 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0x.p-"));
1510 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0x.p-"));
1511 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0x.p-"));
1514 TEST(APFloatTest, StringHexadecimalExponentError) {
1515 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1p"));
1516 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1p"));
1517 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1p"));
1519 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1p+"));
1520 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1p+"));
1521 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1p+"));
1523 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1p-"));
1524 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1p-"));
1525 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1p-"));
1528 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.p"));
1529 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.p"));
1530 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.p"));
1532 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.p+"));
1533 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.p+"));
1534 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.p+"));
1536 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.p-"));
1537 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.p-"));
1538 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.p-"));
1541 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x.1p"));
1542 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x.1p"));
1543 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x.1p"));
1545 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x.1p+"));
1546 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x.1p+"));
1547 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x.1p+"));
1549 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x.1p-"));
1550 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x.1p-"));
1551 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x.1p-"));
1554 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.1p"));
1555 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.1p"));
1556 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.1p"));
1558 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.1p+"));
1559 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.1p+"));
1560 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.1p+"));
1562 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.1p-"));
1563 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.1p-"));
1564 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.1p-"));
1567 TEST(APFloatTest, exactInverse) {
1568 APFloat inv(0.0f);
1570 // Trivial operation.
1571 EXPECT_TRUE(APFloat(2.0).getExactInverse(&inv));
1572 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(0.5)));
1573 EXPECT_TRUE(APFloat(2.0f).getExactInverse(&inv));
1574 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(0.5f)));
1575 EXPECT_TRUE(APFloat(APFloat::IEEEquad(), "2.0").getExactInverse(&inv));
1576 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::IEEEquad(), "0.5")));
1577 EXPECT_TRUE(APFloat(APFloat::PPCDoubleDouble(), "2.0").getExactInverse(&inv));
1578 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::PPCDoubleDouble(), "0.5")));
1579 EXPECT_TRUE(APFloat(APFloat::x87DoubleExtended(), "2.0").getExactInverse(&inv));
1580 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::x87DoubleExtended(), "0.5")));
1582 // FLT_MIN
1583 EXPECT_TRUE(APFloat(1.17549435e-38f).getExactInverse(&inv));
1584 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(8.5070592e+37f)));
1586 // Large float, inverse is a denormal.
1587 EXPECT_FALSE(APFloat(1.7014118e38f).getExactInverse(nullptr));
1588 // Zero
1589 EXPECT_FALSE(APFloat(0.0).getExactInverse(nullptr));
1590 // Denormalized float
1591 EXPECT_FALSE(APFloat(1.40129846e-45f).getExactInverse(nullptr));
1594 TEST(APFloatTest, roundToIntegral) {
1595 APFloat T(-0.5), S(3.14), R(APFloat::getLargest(APFloat::IEEEdouble())), P(0.0);
1597 P = T;
1598 P.roundToIntegral(APFloat::rmTowardZero);
1599 EXPECT_EQ(-0.0, P.convertToDouble());
1600 P = T;
1601 P.roundToIntegral(APFloat::rmTowardNegative);
1602 EXPECT_EQ(-1.0, P.convertToDouble());
1603 P = T;
1604 P.roundToIntegral(APFloat::rmTowardPositive);
1605 EXPECT_EQ(-0.0, P.convertToDouble());
1606 P = T;
1607 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1608 EXPECT_EQ(-0.0, P.convertToDouble());
1610 P = S;
1611 P.roundToIntegral(APFloat::rmTowardZero);
1612 EXPECT_EQ(3.0, P.convertToDouble());
1613 P = S;
1614 P.roundToIntegral(APFloat::rmTowardNegative);
1615 EXPECT_EQ(3.0, P.convertToDouble());
1616 P = S;
1617 P.roundToIntegral(APFloat::rmTowardPositive);
1618 EXPECT_EQ(4.0, P.convertToDouble());
1619 P = S;
1620 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1621 EXPECT_EQ(3.0, P.convertToDouble());
1623 P = R;
1624 P.roundToIntegral(APFloat::rmTowardZero);
1625 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1626 P = R;
1627 P.roundToIntegral(APFloat::rmTowardNegative);
1628 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1629 P = R;
1630 P.roundToIntegral(APFloat::rmTowardPositive);
1631 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1632 P = R;
1633 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1634 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1636 P = APFloat::getZero(APFloat::IEEEdouble());
1637 P.roundToIntegral(APFloat::rmTowardZero);
1638 EXPECT_EQ(0.0, P.convertToDouble());
1639 P = APFloat::getZero(APFloat::IEEEdouble(), true);
1640 P.roundToIntegral(APFloat::rmTowardZero);
1641 EXPECT_EQ(-0.0, P.convertToDouble());
1642 P = APFloat::getNaN(APFloat::IEEEdouble());
1643 P.roundToIntegral(APFloat::rmTowardZero);
1644 EXPECT_TRUE(std::isnan(P.convertToDouble()));
1645 P = APFloat::getInf(APFloat::IEEEdouble());
1646 P.roundToIntegral(APFloat::rmTowardZero);
1647 EXPECT_TRUE(std::isinf(P.convertToDouble()) && P.convertToDouble() > 0.0);
1648 P = APFloat::getInf(APFloat::IEEEdouble(), true);
1649 P.roundToIntegral(APFloat::rmTowardZero);
1650 EXPECT_TRUE(std::isinf(P.convertToDouble()) && P.convertToDouble() < 0.0);
1652 APFloat::opStatus St;
1654 P = APFloat::getNaN(APFloat::IEEEdouble());
1655 St = P.roundToIntegral(APFloat::rmTowardZero);
1656 EXPECT_TRUE(P.isNaN());
1657 EXPECT_FALSE(P.isNegative());
1658 EXPECT_EQ(APFloat::opOK, St);
1660 P = APFloat::getNaN(APFloat::IEEEdouble(), true);
1661 St = P.roundToIntegral(APFloat::rmTowardZero);
1662 EXPECT_TRUE(P.isNaN());
1663 EXPECT_TRUE(P.isNegative());
1664 EXPECT_EQ(APFloat::opOK, St);
1666 P = APFloat::getSNaN(APFloat::IEEEdouble());
1667 St = P.roundToIntegral(APFloat::rmTowardZero);
1668 EXPECT_TRUE(P.isNaN());
1669 EXPECT_FALSE(P.isSignaling());
1670 EXPECT_FALSE(P.isNegative());
1671 EXPECT_EQ(APFloat::opInvalidOp, St);
1673 P = APFloat::getSNaN(APFloat::IEEEdouble(), true);
1674 St = P.roundToIntegral(APFloat::rmTowardZero);
1675 EXPECT_TRUE(P.isNaN());
1676 EXPECT_FALSE(P.isSignaling());
1677 EXPECT_TRUE(P.isNegative());
1678 EXPECT_EQ(APFloat::opInvalidOp, St);
1680 P = APFloat::getInf(APFloat::IEEEdouble());
1681 St = P.roundToIntegral(APFloat::rmTowardZero);
1682 EXPECT_TRUE(P.isInfinity());
1683 EXPECT_FALSE(P.isNegative());
1684 EXPECT_EQ(APFloat::opOK, St);
1686 P = APFloat::getInf(APFloat::IEEEdouble(), true);
1687 St = P.roundToIntegral(APFloat::rmTowardZero);
1688 EXPECT_TRUE(P.isInfinity());
1689 EXPECT_TRUE(P.isNegative());
1690 EXPECT_EQ(APFloat::opOK, St);
1692 P = APFloat::getZero(APFloat::IEEEdouble(), false);
1693 St = P.roundToIntegral(APFloat::rmTowardZero);
1694 EXPECT_TRUE(P.isZero());
1695 EXPECT_FALSE(P.isNegative());
1696 EXPECT_EQ(APFloat::opOK, St);
1698 P = APFloat::getZero(APFloat::IEEEdouble(), false);
1699 St = P.roundToIntegral(APFloat::rmTowardNegative);
1700 EXPECT_TRUE(P.isZero());
1701 EXPECT_FALSE(P.isNegative());
1702 EXPECT_EQ(APFloat::opOK, St);
1704 P = APFloat::getZero(APFloat::IEEEdouble(), true);
1705 St = P.roundToIntegral(APFloat::rmTowardZero);
1706 EXPECT_TRUE(P.isZero());
1707 EXPECT_TRUE(P.isNegative());
1708 EXPECT_EQ(APFloat::opOK, St);
1710 P = APFloat::getZero(APFloat::IEEEdouble(), true);
1711 St = P.roundToIntegral(APFloat::rmTowardNegative);
1712 EXPECT_TRUE(P.isZero());
1713 EXPECT_TRUE(P.isNegative());
1714 EXPECT_EQ(APFloat::opOK, St);
1716 P = APFloat(1E-100);
1717 St = P.roundToIntegral(APFloat::rmTowardNegative);
1718 EXPECT_TRUE(P.isZero());
1719 EXPECT_FALSE(P.isNegative());
1720 EXPECT_EQ(APFloat::opInexact, St);
1722 P = APFloat(1E-100);
1723 St = P.roundToIntegral(APFloat::rmTowardPositive);
1724 EXPECT_EQ(1.0, P.convertToDouble());
1725 EXPECT_FALSE(P.isNegative());
1726 EXPECT_EQ(APFloat::opInexact, St);
1728 P = APFloat(-1E-100);
1729 St = P.roundToIntegral(APFloat::rmTowardNegative);
1730 EXPECT_TRUE(P.isNegative());
1731 EXPECT_EQ(-1.0, P.convertToDouble());
1732 EXPECT_EQ(APFloat::opInexact, St);
1734 P = APFloat(-1E-100);
1735 St = P.roundToIntegral(APFloat::rmTowardPositive);
1736 EXPECT_TRUE(P.isZero());
1737 EXPECT_TRUE(P.isNegative());
1738 EXPECT_EQ(APFloat::opInexact, St);
1740 P = APFloat(10.0);
1741 St = P.roundToIntegral(APFloat::rmTowardZero);
1742 EXPECT_EQ(10.0, P.convertToDouble());
1743 EXPECT_EQ(APFloat::opOK, St);
1745 P = APFloat(10.5);
1746 St = P.roundToIntegral(APFloat::rmTowardZero);
1747 EXPECT_EQ(10.0, P.convertToDouble());
1748 EXPECT_EQ(APFloat::opInexact, St);
1750 P = APFloat(10.5);
1751 St = P.roundToIntegral(APFloat::rmTowardPositive);
1752 EXPECT_EQ(11.0, P.convertToDouble());
1753 EXPECT_EQ(APFloat::opInexact, St);
1755 P = APFloat(10.5);
1756 St = P.roundToIntegral(APFloat::rmTowardNegative);
1757 EXPECT_EQ(10.0, P.convertToDouble());
1758 EXPECT_EQ(APFloat::opInexact, St);
1760 P = APFloat(10.5);
1761 St = P.roundToIntegral(APFloat::rmNearestTiesToAway);
1762 EXPECT_EQ(11.0, P.convertToDouble());
1763 EXPECT_EQ(APFloat::opInexact, St);
1765 P = APFloat(10.5);
1766 St = P.roundToIntegral(APFloat::rmNearestTiesToEven);
1767 EXPECT_EQ(10.0, P.convertToDouble());
1768 EXPECT_EQ(APFloat::opInexact, St);
1771 TEST(APFloatTest, isInteger) {
1772 APFloat T(-0.0);
1773 EXPECT_TRUE(T.isInteger());
1774 T = APFloat(3.14159);
1775 EXPECT_FALSE(T.isInteger());
1776 T = APFloat::getNaN(APFloat::IEEEdouble());
1777 EXPECT_FALSE(T.isInteger());
1778 T = APFloat::getInf(APFloat::IEEEdouble());
1779 EXPECT_FALSE(T.isInteger());
1780 T = APFloat::getInf(APFloat::IEEEdouble(), true);
1781 EXPECT_FALSE(T.isInteger());
1782 T = APFloat::getLargest(APFloat::IEEEdouble());
1783 EXPECT_TRUE(T.isInteger());
1786 TEST(DoubleAPFloatTest, isInteger) {
1787 APFloat F1(-0.0);
1788 APFloat F2(-0.0);
1789 llvm::detail::DoubleAPFloat T(APFloat::PPCDoubleDouble(), std::move(F1),
1790 std::move(F2));
1791 EXPECT_TRUE(T.isInteger());
1792 APFloat F3(3.14159);
1793 APFloat F4(-0.0);
1794 llvm::detail::DoubleAPFloat T2(APFloat::PPCDoubleDouble(), std::move(F3),
1795 std::move(F4));
1796 EXPECT_FALSE(T2.isInteger());
1797 APFloat F5(-0.0);
1798 APFloat F6(3.14159);
1799 llvm::detail::DoubleAPFloat T3(APFloat::PPCDoubleDouble(), std::move(F5),
1800 std::move(F6));
1801 EXPECT_FALSE(T3.isInteger());
1804 TEST(APFloatTest, getLargest) {
1805 EXPECT_EQ(3.402823466e+38f, APFloat::getLargest(APFloat::IEEEsingle()).convertToFloat());
1806 EXPECT_EQ(1.7976931348623158e+308, APFloat::getLargest(APFloat::IEEEdouble()).convertToDouble());
1807 EXPECT_EQ(448, APFloat::getLargest(APFloat::Float8E4M3FN()).convertToDouble());
1808 EXPECT_EQ(240,
1809 APFloat::getLargest(APFloat::Float8E4M3FNUZ()).convertToDouble());
1810 EXPECT_EQ(57344,
1811 APFloat::getLargest(APFloat::Float8E5M2FNUZ()).convertToDouble());
1812 EXPECT_EQ(
1813 30, APFloat::getLargest(APFloat::Float8E4M3B11FNUZ()).convertToDouble());
1814 EXPECT_EQ(3.40116213421e+38f,
1815 APFloat::getLargest(APFloat::FloatTF32()).convertToFloat());
1818 TEST(APFloatTest, getSmallest) {
1819 APFloat test = APFloat::getSmallest(APFloat::IEEEsingle(), false);
1820 APFloat expected = APFloat(APFloat::IEEEsingle(), "0x0.000002p-126");
1821 EXPECT_FALSE(test.isNegative());
1822 EXPECT_TRUE(test.isFiniteNonZero());
1823 EXPECT_TRUE(test.isDenormal());
1824 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1826 test = APFloat::getSmallest(APFloat::IEEEsingle(), true);
1827 expected = APFloat(APFloat::IEEEsingle(), "-0x0.000002p-126");
1828 EXPECT_TRUE(test.isNegative());
1829 EXPECT_TRUE(test.isFiniteNonZero());
1830 EXPECT_TRUE(test.isDenormal());
1831 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1833 test = APFloat::getSmallest(APFloat::IEEEquad(), false);
1834 expected = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
1835 EXPECT_FALSE(test.isNegative());
1836 EXPECT_TRUE(test.isFiniteNonZero());
1837 EXPECT_TRUE(test.isDenormal());
1838 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1840 test = APFloat::getSmallest(APFloat::IEEEquad(), true);
1841 expected = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
1842 EXPECT_TRUE(test.isNegative());
1843 EXPECT_TRUE(test.isFiniteNonZero());
1844 EXPECT_TRUE(test.isDenormal());
1845 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1847 test = APFloat::getSmallest(APFloat::Float8E5M2FNUZ(), false);
1848 expected = APFloat(APFloat::Float8E5M2FNUZ(), "0x0.4p-15");
1849 EXPECT_FALSE(test.isNegative());
1850 EXPECT_TRUE(test.isFiniteNonZero());
1851 EXPECT_TRUE(test.isDenormal());
1852 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1854 test = APFloat::getSmallest(APFloat::Float8E4M3FNUZ(), false);
1855 expected = APFloat(APFloat::Float8E4M3FNUZ(), "0x0.2p-7");
1856 EXPECT_FALSE(test.isNegative());
1857 EXPECT_TRUE(test.isFiniteNonZero());
1858 EXPECT_TRUE(test.isDenormal());
1859 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1861 test = APFloat::getSmallest(APFloat::Float8E4M3B11FNUZ(), false);
1862 expected = APFloat(APFloat::Float8E4M3B11FNUZ(), "0x0.2p-10");
1863 EXPECT_FALSE(test.isNegative());
1864 EXPECT_TRUE(test.isFiniteNonZero());
1865 EXPECT_TRUE(test.isDenormal());
1866 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1868 test = APFloat::getSmallest(APFloat::FloatTF32(), true);
1869 expected = APFloat(APFloat::FloatTF32(), "-0x0.004p-126");
1870 EXPECT_TRUE(test.isNegative());
1871 EXPECT_TRUE(test.isFiniteNonZero());
1872 EXPECT_TRUE(test.isDenormal());
1873 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1876 TEST(APFloatTest, getSmallestNormalized) {
1877 APFloat test = APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
1878 APFloat expected = APFloat(APFloat::IEEEsingle(), "0x1p-126");
1879 EXPECT_FALSE(test.isNegative());
1880 EXPECT_TRUE(test.isFiniteNonZero());
1881 EXPECT_FALSE(test.isDenormal());
1882 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1883 EXPECT_TRUE(test.isSmallestNormalized());
1885 test = APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
1886 expected = APFloat(APFloat::IEEEsingle(), "-0x1p-126");
1887 EXPECT_TRUE(test.isNegative());
1888 EXPECT_TRUE(test.isFiniteNonZero());
1889 EXPECT_FALSE(test.isDenormal());
1890 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1891 EXPECT_TRUE(test.isSmallestNormalized());
1893 test = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
1894 expected = APFloat(APFloat::IEEEdouble(), "0x1p-1022");
1895 EXPECT_FALSE(test.isNegative());
1896 EXPECT_TRUE(test.isFiniteNonZero());
1897 EXPECT_FALSE(test.isDenormal());
1898 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1899 EXPECT_TRUE(test.isSmallestNormalized());
1901 test = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
1902 expected = APFloat(APFloat::IEEEdouble(), "-0x1p-1022");
1903 EXPECT_TRUE(test.isNegative());
1904 EXPECT_TRUE(test.isFiniteNonZero());
1905 EXPECT_FALSE(test.isDenormal());
1906 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1907 EXPECT_TRUE(test.isSmallestNormalized());
1909 test = APFloat::getSmallestNormalized(APFloat::IEEEquad(), false);
1910 expected = APFloat(APFloat::IEEEquad(), "0x1p-16382");
1911 EXPECT_FALSE(test.isNegative());
1912 EXPECT_TRUE(test.isFiniteNonZero());
1913 EXPECT_FALSE(test.isDenormal());
1914 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1915 EXPECT_TRUE(test.isSmallestNormalized());
1917 test = APFloat::getSmallestNormalized(APFloat::IEEEquad(), true);
1918 expected = APFloat(APFloat::IEEEquad(), "-0x1p-16382");
1919 EXPECT_TRUE(test.isNegative());
1920 EXPECT_TRUE(test.isFiniteNonZero());
1921 EXPECT_FALSE(test.isDenormal());
1922 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1923 EXPECT_TRUE(test.isSmallestNormalized());
1925 test = APFloat::getSmallestNormalized(APFloat::Float8E5M2FNUZ(), false);
1926 expected = APFloat(APFloat::Float8E5M2FNUZ(), "0x1.0p-15");
1927 EXPECT_FALSE(test.isNegative());
1928 EXPECT_TRUE(test.isFiniteNonZero());
1929 EXPECT_FALSE(test.isDenormal());
1930 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1931 EXPECT_TRUE(test.isSmallestNormalized());
1933 test = APFloat::getSmallestNormalized(APFloat::Float8E4M3FNUZ(), false);
1934 expected = APFloat(APFloat::Float8E4M3FNUZ(), "0x1.0p-7");
1935 EXPECT_FALSE(test.isNegative());
1936 EXPECT_TRUE(test.isFiniteNonZero());
1937 EXPECT_FALSE(test.isDenormal());
1938 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1939 EXPECT_TRUE(test.isSmallestNormalized());
1941 test = APFloat::getSmallestNormalized(APFloat::Float8E4M3B11FNUZ(), false);
1942 expected = APFloat(APFloat::Float8E4M3B11FNUZ(), "0x1.0p-10");
1943 EXPECT_FALSE(test.isNegative());
1944 EXPECT_TRUE(test.isFiniteNonZero());
1945 EXPECT_FALSE(test.isDenormal());
1946 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1947 EXPECT_TRUE(test.isSmallestNormalized());
1949 test = APFloat::getSmallestNormalized(APFloat::FloatTF32(), false);
1950 expected = APFloat(APFloat::FloatTF32(), "0x1p-126");
1951 EXPECT_FALSE(test.isNegative());
1952 EXPECT_TRUE(test.isFiniteNonZero());
1953 EXPECT_FALSE(test.isDenormal());
1954 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1955 EXPECT_TRUE(test.isSmallestNormalized());
1958 TEST(APFloatTest, getZero) {
1959 struct {
1960 const fltSemantics *semantics;
1961 const bool sign;
1962 const bool signedZero;
1963 const unsigned long long bitPattern[2];
1964 const unsigned bitPatternLength;
1965 } const GetZeroTest[] = {
1966 {&APFloat::IEEEhalf(), false, true, {0, 0}, 1},
1967 {&APFloat::IEEEhalf(), true, true, {0x8000ULL, 0}, 1},
1968 {&APFloat::IEEEsingle(), false, true, {0, 0}, 1},
1969 {&APFloat::IEEEsingle(), true, true, {0x80000000ULL, 0}, 1},
1970 {&APFloat::IEEEdouble(), false, true, {0, 0}, 1},
1971 {&APFloat::IEEEdouble(), true, true, {0x8000000000000000ULL, 0}, 1},
1972 {&APFloat::IEEEquad(), false, true, {0, 0}, 2},
1973 {&APFloat::IEEEquad(), true, true, {0, 0x8000000000000000ULL}, 2},
1974 {&APFloat::PPCDoubleDouble(), false, true, {0, 0}, 2},
1975 {&APFloat::PPCDoubleDouble(), true, true, {0x8000000000000000ULL, 0}, 2},
1976 {&APFloat::x87DoubleExtended(), false, true, {0, 0}, 2},
1977 {&APFloat::x87DoubleExtended(), true, true, {0, 0x8000ULL}, 2},
1978 {&APFloat::Float8E5M2(), false, true, {0, 0}, 1},
1979 {&APFloat::Float8E5M2(), true, true, {0x80ULL, 0}, 1},
1980 {&APFloat::Float8E5M2FNUZ(), false, false, {0, 0}, 1},
1981 {&APFloat::Float8E5M2FNUZ(), true, false, {0, 0}, 1},
1982 {&APFloat::Float8E4M3FN(), false, true, {0, 0}, 1},
1983 {&APFloat::Float8E4M3FN(), true, true, {0x80ULL, 0}, 1},
1984 {&APFloat::Float8E4M3FNUZ(), false, false, {0, 0}, 1},
1985 {&APFloat::Float8E4M3FNUZ(), true, false, {0, 0}, 1},
1986 {&APFloat::Float8E4M3B11FNUZ(), false, false, {0, 0}, 1},
1987 {&APFloat::Float8E4M3B11FNUZ(), true, false, {0, 0}, 1},
1988 {&APFloat::FloatTF32(), false, true, {0, 0}, 1},
1989 {&APFloat::FloatTF32(), true, true, {0x40000ULL, 0}, 1}};
1990 const unsigned NumGetZeroTests = std::size(GetZeroTest);
1991 for (unsigned i = 0; i < NumGetZeroTests; ++i) {
1992 APFloat test = APFloat::getZero(*GetZeroTest[i].semantics,
1993 GetZeroTest[i].sign);
1994 const char *pattern = GetZeroTest[i].sign? "-0x0p+0" : "0x0p+0";
1995 APFloat expected = APFloat(*GetZeroTest[i].semantics,
1996 pattern);
1997 EXPECT_TRUE(test.isZero());
1998 if (GetZeroTest[i].signedZero)
1999 EXPECT_TRUE(GetZeroTest[i].sign ? test.isNegative() : !test.isNegative());
2000 else
2001 EXPECT_TRUE(!test.isNegative());
2002 EXPECT_TRUE(test.bitwiseIsEqual(expected));
2003 for (unsigned j = 0, je = GetZeroTest[i].bitPatternLength; j < je; ++j) {
2004 EXPECT_EQ(GetZeroTest[i].bitPattern[j],
2005 test.bitcastToAPInt().getRawData()[j]);
2010 TEST(APFloatTest, copySign) {
2011 EXPECT_TRUE(APFloat(-42.0).bitwiseIsEqual(
2012 APFloat::copySign(APFloat(42.0), APFloat(-1.0))));
2013 EXPECT_TRUE(APFloat(42.0).bitwiseIsEqual(
2014 APFloat::copySign(APFloat(-42.0), APFloat(1.0))));
2015 EXPECT_TRUE(APFloat(-42.0).bitwiseIsEqual(
2016 APFloat::copySign(APFloat(-42.0), APFloat(-1.0))));
2017 EXPECT_TRUE(APFloat(42.0).bitwiseIsEqual(
2018 APFloat::copySign(APFloat(42.0), APFloat(1.0))));
2019 // For floating-point formats with unsigned 0, copySign() to a zero is a noop
2020 for (APFloat::Semantics S :
2021 {APFloat::S_Float8E4M3FNUZ, APFloat::S_Float8E4M3B11FNUZ}) {
2022 const llvm::fltSemantics &Sem = APFloat::EnumToSemantics(S);
2023 EXPECT_TRUE(APFloat::getZero(Sem).bitwiseIsEqual(
2024 APFloat::copySign(APFloat::getZero(Sem), APFloat(-1.0))));
2025 EXPECT_TRUE(APFloat::getNaN(Sem, true).bitwiseIsEqual(
2026 APFloat::copySign(APFloat::getNaN(Sem, true), APFloat(1.0))));
2030 TEST(APFloatTest, convert) {
2031 bool losesInfo;
2032 APFloat test(APFloat::IEEEdouble(), "1.0");
2033 test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
2034 EXPECT_EQ(1.0f, test.convertToFloat());
2035 EXPECT_FALSE(losesInfo);
2037 test = APFloat(APFloat::x87DoubleExtended(), "0x1p-53");
2038 test.add(APFloat(APFloat::x87DoubleExtended(), "1.0"), APFloat::rmNearestTiesToEven);
2039 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
2040 EXPECT_EQ(1.0, test.convertToDouble());
2041 EXPECT_TRUE(losesInfo);
2043 test = APFloat(APFloat::IEEEquad(), "0x1p-53");
2044 test.add(APFloat(APFloat::IEEEquad(), "1.0"), APFloat::rmNearestTiesToEven);
2045 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
2046 EXPECT_EQ(1.0, test.convertToDouble());
2047 EXPECT_TRUE(losesInfo);
2049 test = APFloat(APFloat::x87DoubleExtended(), "0xf.fffffffp+28");
2050 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
2051 EXPECT_EQ(4294967295.0, test.convertToDouble());
2052 EXPECT_FALSE(losesInfo);
2054 test = APFloat::getSNaN(APFloat::IEEEsingle());
2055 APFloat::opStatus status = test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven, &losesInfo);
2056 // Conversion quiets the SNAN, so now 2 bits of the 64-bit significand should be set.
2057 APInt topTwoBits(64, 0x6000000000000000);
2058 EXPECT_TRUE(test.bitwiseIsEqual(APFloat::getQNaN(APFloat::x87DoubleExtended(), false, &topTwoBits)));
2059 EXPECT_FALSE(losesInfo);
2060 EXPECT_EQ(status, APFloat::opInvalidOp);
2062 test = APFloat::getQNaN(APFloat::IEEEsingle());
2063 APFloat X87QNaN = APFloat::getQNaN(APFloat::x87DoubleExtended());
2064 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
2065 &losesInfo);
2066 EXPECT_TRUE(test.bitwiseIsEqual(X87QNaN));
2067 EXPECT_FALSE(losesInfo);
2069 test = APFloat::getSNaN(APFloat::x87DoubleExtended());
2070 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
2071 &losesInfo);
2072 APFloat X87SNaN = APFloat::getSNaN(APFloat::x87DoubleExtended());
2073 EXPECT_TRUE(test.bitwiseIsEqual(X87SNaN));
2074 EXPECT_FALSE(losesInfo);
2076 test = APFloat::getQNaN(APFloat::x87DoubleExtended());
2077 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
2078 &losesInfo);
2079 EXPECT_TRUE(test.bitwiseIsEqual(X87QNaN));
2080 EXPECT_FALSE(losesInfo);
2082 // The payload is lost in truncation, but we retain NaN by setting the quiet bit.
2083 APInt payload(52, 1);
2084 test = APFloat::getSNaN(APFloat::IEEEdouble(), false, &payload);
2085 status = test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
2086 EXPECT_EQ(0x7fc00000, test.bitcastToAPInt());
2087 EXPECT_TRUE(losesInfo);
2088 EXPECT_EQ(status, APFloat::opInvalidOp);
2090 // The payload is lost in truncation. QNaN remains QNaN.
2091 test = APFloat::getQNaN(APFloat::IEEEdouble(), false, &payload);
2092 status = test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
2093 EXPECT_EQ(0x7fc00000, test.bitcastToAPInt());
2094 EXPECT_TRUE(losesInfo);
2095 EXPECT_EQ(status, APFloat::opOK);
2097 // Test that subnormals are handled correctly in double to float conversion
2098 test = APFloat(APFloat::IEEEdouble(), "0x0.0000010000000p-1022");
2099 test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
2100 EXPECT_EQ(0.0f, test.convertToFloat());
2101 EXPECT_TRUE(losesInfo);
2103 test = APFloat(APFloat::IEEEdouble(), "0x0.0000010000001p-1022");
2104 test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
2105 EXPECT_EQ(0.0f, test.convertToFloat());
2106 EXPECT_TRUE(losesInfo);
2108 test = APFloat(APFloat::IEEEdouble(), "-0x0.0000010000001p-1022");
2109 test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
2110 EXPECT_EQ(0.0f, test.convertToFloat());
2111 EXPECT_TRUE(losesInfo);
2113 test = APFloat(APFloat::IEEEdouble(), "0x0.0000020000000p-1022");
2114 test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
2115 EXPECT_EQ(0.0f, test.convertToFloat());
2116 EXPECT_TRUE(losesInfo);
2118 test = APFloat(APFloat::IEEEdouble(), "0x0.0000020000001p-1022");
2119 test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
2120 EXPECT_EQ(0.0f, test.convertToFloat());
2121 EXPECT_TRUE(losesInfo);
2123 // Test subnormal conversion to bfloat
2124 test = APFloat(APFloat::IEEEsingle(), "0x0.01p-126");
2125 test.convert(APFloat::BFloat(), APFloat::rmNearestTiesToEven, &losesInfo);
2126 EXPECT_EQ(0.0f, test.convertToFloat());
2127 EXPECT_TRUE(losesInfo);
2129 test = APFloat(APFloat::IEEEsingle(), "0x0.02p-126");
2130 test.convert(APFloat::BFloat(), APFloat::rmNearestTiesToEven, &losesInfo);
2131 EXPECT_EQ(0x01, test.bitcastToAPInt());
2132 EXPECT_FALSE(losesInfo);
2134 test = APFloat(APFloat::IEEEsingle(), "0x0.01p-126");
2135 test.convert(APFloat::BFloat(), APFloat::rmNearestTiesToAway, &losesInfo);
2136 EXPECT_EQ(0x01, test.bitcastToAPInt());
2137 EXPECT_TRUE(losesInfo);
2140 TEST(APFloatTest, Float8UZConvert) {
2141 bool losesInfo = false;
2142 std::pair<APFloat, APFloat::opStatus> toNaNTests[] = {
2143 {APFloat::getQNaN(APFloat::IEEEsingle(), false), APFloat::opOK},
2144 {APFloat::getQNaN(APFloat::IEEEsingle(), true), APFloat::opOK},
2145 {APFloat::getSNaN(APFloat::IEEEsingle(), false), APFloat::opInvalidOp},
2146 {APFloat::getSNaN(APFloat::IEEEsingle(), true), APFloat::opInvalidOp},
2147 {APFloat::getInf(APFloat::IEEEsingle(), false), APFloat::opInexact},
2148 {APFloat::getInf(APFloat::IEEEsingle(), true), APFloat::opInexact}};
2149 for (APFloat::Semantics S :
2150 {APFloat::S_Float8E5M2FNUZ, APFloat::S_Float8E4M3FNUZ,
2151 APFloat::S_Float8E4M3B11FNUZ}) {
2152 const llvm::fltSemantics &Sem = APFloat::EnumToSemantics(S);
2153 SCOPED_TRACE("Semantics = " + std::to_string(S));
2154 for (auto [toTest, expectedRes] : toNaNTests) {
2155 llvm::SmallString<16> value;
2156 toTest.toString(value);
2157 SCOPED_TRACE("toTest = " + value);
2158 losesInfo = false;
2159 APFloat test = toTest;
2160 EXPECT_EQ(test.convert(Sem, APFloat::rmNearestTiesToAway, &losesInfo),
2161 expectedRes);
2162 EXPECT_TRUE(test.isNaN());
2163 EXPECT_TRUE(test.isNegative());
2164 EXPECT_FALSE(test.isSignaling());
2165 EXPECT_FALSE(test.isInfinity());
2166 EXPECT_EQ(0x80, test.bitcastToAPInt());
2167 EXPECT_TRUE(losesInfo);
2170 // Negative zero conversions are information losing.
2171 losesInfo = false;
2172 APFloat test = APFloat::getZero(APFloat::IEEEsingle(), true);
2173 EXPECT_EQ(test.convert(Sem, APFloat::rmNearestTiesToAway, &losesInfo),
2174 APFloat::opInexact);
2175 EXPECT_TRUE(test.isZero());
2176 EXPECT_FALSE(test.isNegative());
2177 EXPECT_TRUE(losesInfo);
2178 EXPECT_EQ(0x0, test.bitcastToAPInt());
2180 losesInfo = true;
2181 test = APFloat::getZero(APFloat::IEEEsingle(), false);
2182 EXPECT_EQ(test.convert(Sem, APFloat::rmNearestTiesToAway, &losesInfo),
2183 APFloat::opOK);
2184 EXPECT_TRUE(test.isZero());
2185 EXPECT_FALSE(test.isNegative());
2186 EXPECT_FALSE(losesInfo);
2187 EXPECT_EQ(0x0, test.bitcastToAPInt());
2189 // Except in casts between ourselves.
2190 losesInfo = true;
2191 test = APFloat::getZero(Sem);
2192 EXPECT_EQ(test.convert(Sem, APFloat::rmNearestTiesToAway, &losesInfo),
2193 APFloat::opOK);
2194 EXPECT_FALSE(losesInfo);
2195 EXPECT_EQ(0x0, test.bitcastToAPInt());
2199 TEST(APFloatTest, PPCDoubleDouble) {
2200 APFloat test(APFloat::PPCDoubleDouble(), "1.0");
2201 EXPECT_EQ(0x3ff0000000000000ull, test.bitcastToAPInt().getRawData()[0]);
2202 EXPECT_EQ(0x0000000000000000ull, test.bitcastToAPInt().getRawData()[1]);
2204 // LDBL_MAX
2205 test = APFloat(APFloat::PPCDoubleDouble(), "1.79769313486231580793728971405301e+308");
2206 EXPECT_EQ(0x7fefffffffffffffull, test.bitcastToAPInt().getRawData()[0]);
2207 EXPECT_EQ(0x7c8ffffffffffffeull, test.bitcastToAPInt().getRawData()[1]);
2209 // LDBL_MIN
2210 test = APFloat(APFloat::PPCDoubleDouble(), "2.00416836000897277799610805135016e-292");
2211 EXPECT_EQ(0x0360000000000000ull, test.bitcastToAPInt().getRawData()[0]);
2212 EXPECT_EQ(0x0000000000000000ull, test.bitcastToAPInt().getRawData()[1]);
2214 // PR30869
2216 auto Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") +
2217 APFloat(APFloat::PPCDoubleDouble(), "1.0");
2218 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
2220 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") -
2221 APFloat(APFloat::PPCDoubleDouble(), "1.0");
2222 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
2224 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") *
2225 APFloat(APFloat::PPCDoubleDouble(), "1.0");
2226 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
2228 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") /
2229 APFloat(APFloat::PPCDoubleDouble(), "1.0");
2230 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
2232 int Exp;
2233 Result = frexp(APFloat(APFloat::PPCDoubleDouble(), "1.0"), Exp,
2234 APFloat::rmNearestTiesToEven);
2235 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
2237 Result = scalbn(APFloat(APFloat::PPCDoubleDouble(), "1.0"), 1,
2238 APFloat::rmNearestTiesToEven);
2239 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
2243 TEST(APFloatTest, isNegative) {
2244 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
2245 EXPECT_FALSE(t.isNegative());
2246 t = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2247 EXPECT_TRUE(t.isNegative());
2249 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNegative());
2250 EXPECT_TRUE(APFloat::getInf(APFloat::IEEEsingle(), true).isNegative());
2252 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNegative());
2253 EXPECT_TRUE(APFloat::getZero(APFloat::IEEEsingle(), true).isNegative());
2255 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNegative());
2256 EXPECT_TRUE(APFloat::getNaN(APFloat::IEEEsingle(), true).isNegative());
2258 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNegative());
2259 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isNegative());
2262 TEST(APFloatTest, isNormal) {
2263 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
2264 EXPECT_TRUE(t.isNormal());
2266 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNormal());
2267 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNormal());
2268 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNormal());
2269 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNormal());
2270 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isNormal());
2273 TEST(APFloatTest, isFinite) {
2274 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
2275 EXPECT_TRUE(t.isFinite());
2276 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isFinite());
2277 EXPECT_TRUE(APFloat::getZero(APFloat::IEEEsingle(), false).isFinite());
2278 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isFinite());
2279 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isFinite());
2280 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isFinite());
2283 TEST(APFloatTest, isInfinity) {
2284 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
2285 EXPECT_FALSE(t.isInfinity());
2287 APFloat PosInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2288 APFloat NegInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2290 EXPECT_TRUE(PosInf.isInfinity());
2291 EXPECT_TRUE(PosInf.isPosInfinity());
2292 EXPECT_FALSE(PosInf.isNegInfinity());
2293 EXPECT_EQ(fcPosInf, PosInf.classify());
2295 EXPECT_TRUE(NegInf.isInfinity());
2296 EXPECT_FALSE(NegInf.isPosInfinity());
2297 EXPECT_TRUE(NegInf.isNegInfinity());
2298 EXPECT_EQ(fcNegInf, NegInf.classify());
2300 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isInfinity());
2301 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isInfinity());
2302 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isInfinity());
2303 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isInfinity());
2306 TEST(APFloatTest, isNaN) {
2307 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
2308 EXPECT_FALSE(t.isNaN());
2309 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNaN());
2310 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNaN());
2311 EXPECT_TRUE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNaN());
2312 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNaN());
2313 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isNaN());
2316 TEST(APFloatTest, isFiniteNonZero) {
2317 // Test positive/negative normal value.
2318 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p+0").isFiniteNonZero());
2319 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p+0").isFiniteNonZero());
2321 // Test positive/negative denormal value.
2322 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isFiniteNonZero());
2323 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p-149").isFiniteNonZero());
2325 // Test +/- Infinity.
2326 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isFiniteNonZero());
2327 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), true).isFiniteNonZero());
2329 // Test +/- Zero.
2330 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isFiniteNonZero());
2331 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), true).isFiniteNonZero());
2333 // Test +/- qNaN. +/- dont mean anything with qNaN but paranoia can't hurt in
2334 // this instance.
2335 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isFiniteNonZero());
2336 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), true).isFiniteNonZero());
2338 // Test +/- sNaN. +/- dont mean anything with sNaN but paranoia can't hurt in
2339 // this instance.
2340 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isFiniteNonZero());
2341 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isFiniteNonZero());
2344 TEST(APFloatTest, add) {
2345 // Test Special Cases against each other and normal values.
2347 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2348 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2349 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2350 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2351 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2352 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
2353 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2354 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2355 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2356 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2357 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2358 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
2359 APFloat PSmallestNormalized =
2360 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
2361 APFloat MSmallestNormalized =
2362 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
2364 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2366 struct {
2367 APFloat x;
2368 APFloat y;
2369 const char *result;
2370 int status;
2371 int category;
2372 } SpecialCaseTests[] = {
2373 { PInf, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2374 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2375 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2376 { PInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2377 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2378 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2379 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2380 { PInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2381 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2382 { PInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2383 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2384 { PInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2385 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2386 { PInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2387 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2388 { MInf, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2389 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2390 { MInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2391 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2392 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2393 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2394 { MInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2395 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2396 { MInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2397 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2398 { MInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2399 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2400 { MInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2401 { PZero, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2402 { PZero, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2403 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2404 { PZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2405 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2406 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2407 { PZero, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2408 { PZero, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2409 { PZero, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2410 { PZero, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2411 { PZero, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2412 { PZero, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2413 { PZero, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2414 { PZero, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2415 { MZero, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2416 { MZero, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2417 { MZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2418 { MZero, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2419 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2420 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2421 { MZero, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2422 { MZero, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2423 { MZero, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2424 { MZero, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2425 { MZero, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2426 { MZero, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2427 { MZero, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2428 { MZero, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2429 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
2430 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
2431 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
2432 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
2433 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2434 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2435 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2436 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2437 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2438 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2439 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2440 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2441 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2442 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2443 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2444 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2445 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2446 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2447 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2448 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2449 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2450 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2451 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2452 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2453 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2454 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2455 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2456 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2457 { PNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2458 { PNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2459 { PNormalValue, PZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2460 { PNormalValue, MZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2461 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2462 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2463 { PNormalValue, PNormalValue, "0x1p+1", APFloat::opOK, APFloat::fcNormal },
2464 { PNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2465 { PNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2466 { PNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2467 { PNormalValue, PSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2468 { PNormalValue, MSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2469 { PNormalValue, PSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2470 { PNormalValue, MSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2471 { MNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2472 { MNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2473 { MNormalValue, PZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2474 { MNormalValue, MZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2475 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2476 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2477 { MNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2478 { MNormalValue, MNormalValue, "-0x1p+1", APFloat::opOK, APFloat::fcNormal },
2479 { MNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2480 { MNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2481 { MNormalValue, PSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2482 { MNormalValue, MSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2483 { MNormalValue, PSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2484 { MNormalValue, MSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2485 { PLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2486 { PLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2487 { PLargestValue, PZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2488 { PLargestValue, MZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2489 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2490 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2491 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2492 { PLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2493 { PLargestValue, PLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2494 { PLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2495 { PLargestValue, PSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2496 { PLargestValue, MSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2497 { PLargestValue, PSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2498 { PLargestValue, MSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2499 { MLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2500 { MLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2501 { MLargestValue, PZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2502 { MLargestValue, MZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2503 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2504 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2505 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2506 { MLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2507 { MLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2508 { MLargestValue, MLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2509 { MLargestValue, PSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2510 { MLargestValue, MSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2511 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2512 { MLargestValue, MSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2513 { PSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2514 { PSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2515 { PSmallestValue, PZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2516 { PSmallestValue, MZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2517 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2518 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2519 { PSmallestValue, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2520 { PSmallestValue, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2521 { PSmallestValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2522 { PSmallestValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2523 { PSmallestValue, PSmallestValue, "0x1p-148", APFloat::opOK, APFloat::fcNormal },
2524 { PSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2525 { PSmallestValue, PSmallestNormalized, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2526 { PSmallestValue, MSmallestNormalized, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2527 { MSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2528 { MSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2529 { MSmallestValue, PZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2530 { MSmallestValue, MZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2531 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2532 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2533 { MSmallestValue, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2534 { MSmallestValue, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2535 { MSmallestValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2536 { MSmallestValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2537 { MSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2538 { MSmallestValue, MSmallestValue, "-0x1p-148", APFloat::opOK, APFloat::fcNormal },
2539 { MSmallestValue, PSmallestNormalized, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2540 { MSmallestValue, MSmallestNormalized, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2541 { PSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2542 { PSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2543 { PSmallestNormalized, PZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2544 { PSmallestNormalized, MZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2545 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2546 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2547 { PSmallestNormalized, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2548 { PSmallestNormalized, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2549 { PSmallestNormalized, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2550 { PSmallestNormalized, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2551 { PSmallestNormalized, PSmallestValue, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2552 { PSmallestNormalized, MSmallestValue, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2553 { PSmallestNormalized, PSmallestNormalized, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
2554 { PSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2555 { MSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2556 { MSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2557 { MSmallestNormalized, PZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2558 { MSmallestNormalized, MZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2559 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2560 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2561 { MSmallestNormalized, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2562 { MSmallestNormalized, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2563 { MSmallestNormalized, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2564 { MSmallestNormalized, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2565 { MSmallestNormalized, PSmallestValue, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2566 { MSmallestNormalized, MSmallestValue, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2567 { MSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2568 { MSmallestNormalized, MSmallestNormalized, "-0x1p-125", APFloat::opOK, APFloat::fcNormal }
2571 for (size_t i = 0; i < std::size(SpecialCaseTests); ++i) {
2572 APFloat x(SpecialCaseTests[i].x);
2573 APFloat y(SpecialCaseTests[i].y);
2574 APFloat::opStatus status = x.add(y, APFloat::rmNearestTiesToEven);
2576 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
2578 EXPECT_TRUE(result.bitwiseIsEqual(x));
2579 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
2580 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
2584 TEST(APFloatTest, subtract) {
2585 // Test Special Cases against each other and normal values.
2587 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2588 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2589 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2590 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2591 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2592 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
2593 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2594 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2595 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2596 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2597 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2598 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
2599 APFloat PSmallestNormalized =
2600 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
2601 APFloat MSmallestNormalized =
2602 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
2604 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2606 struct {
2607 APFloat x;
2608 APFloat y;
2609 const char *result;
2610 int status;
2611 int category;
2612 } SpecialCaseTests[] = {
2613 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2614 { PInf, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2615 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2616 { PInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2617 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2618 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2619 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2620 { PInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2621 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2622 { PInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2623 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2624 { PInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2625 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2626 { PInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2627 { MInf, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2628 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2629 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2630 { MInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2631 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2632 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2633 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2634 { MInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2635 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2636 { MInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2637 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2638 { MInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2639 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2640 { MInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2641 { PZero, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2642 { PZero, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2643 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2644 { PZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2645 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2646 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2647 { PZero, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2648 { PZero, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2649 { PZero, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2650 { PZero, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2651 { PZero, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2652 { PZero, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2653 { PZero, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2654 { PZero, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2655 { MZero, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2656 { MZero, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2657 { MZero, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2658 { MZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2659 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2660 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2661 { MZero, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2662 { MZero, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2663 { MZero, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2664 { MZero, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2665 { MZero, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2666 { MZero, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2667 { MZero, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2668 { MZero, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2669 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
2670 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
2671 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
2672 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
2673 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2674 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2675 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2676 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2677 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2678 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2679 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2680 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2681 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2682 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2683 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2684 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2685 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2686 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2687 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2688 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2689 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2690 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2691 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2692 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2693 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2694 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2695 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2696 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2697 { PNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2698 { PNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2699 { PNormalValue, PZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2700 { PNormalValue, MZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2701 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2702 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2703 { PNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2704 { PNormalValue, MNormalValue, "0x1p+1", APFloat::opOK, APFloat::fcNormal },
2705 { PNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2706 { PNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2707 { PNormalValue, PSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2708 { PNormalValue, MSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2709 { PNormalValue, PSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2710 { PNormalValue, MSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2711 { MNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2712 { MNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2713 { MNormalValue, PZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2714 { MNormalValue, MZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2715 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2716 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2717 { MNormalValue, PNormalValue, "-0x1p+1", APFloat::opOK, APFloat::fcNormal },
2718 { MNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2719 { MNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2720 { MNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2721 { MNormalValue, PSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2722 { MNormalValue, MSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2723 { MNormalValue, PSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2724 { MNormalValue, MSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2725 { PLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2726 { PLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2727 { PLargestValue, PZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2728 { PLargestValue, MZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2729 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2730 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2731 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2732 { PLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2733 { PLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2734 { PLargestValue, MLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2735 { PLargestValue, PSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2736 { PLargestValue, MSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2737 { PLargestValue, PSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2738 { PLargestValue, MSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2739 { MLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2740 { MLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2741 { MLargestValue, PZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2742 { MLargestValue, MZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2743 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2744 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2745 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2746 { MLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2747 { MLargestValue, PLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2748 { MLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2749 { MLargestValue, PSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2750 { MLargestValue, MSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2751 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2752 { MLargestValue, MSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2753 { PSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2754 { PSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2755 { PSmallestValue, PZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2756 { PSmallestValue, MZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2757 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2758 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2759 { PSmallestValue, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2760 { PSmallestValue, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2761 { PSmallestValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2762 { PSmallestValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2763 { PSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2764 { PSmallestValue, MSmallestValue, "0x1p-148", APFloat::opOK, APFloat::fcNormal },
2765 { PSmallestValue, PSmallestNormalized, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2766 { PSmallestValue, MSmallestNormalized, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2767 { MSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2768 { MSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2769 { MSmallestValue, PZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2770 { MSmallestValue, MZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2771 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2772 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2773 { MSmallestValue, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2774 { MSmallestValue, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2775 { MSmallestValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2776 { MSmallestValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2777 { MSmallestValue, PSmallestValue, "-0x1p-148", APFloat::opOK, APFloat::fcNormal },
2778 { MSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2779 { MSmallestValue, PSmallestNormalized, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2780 { MSmallestValue, MSmallestNormalized, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2781 { PSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2782 { PSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2783 { PSmallestNormalized, PZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2784 { PSmallestNormalized, MZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2785 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2786 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2787 { PSmallestNormalized, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2788 { PSmallestNormalized, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2789 { PSmallestNormalized, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2790 { PSmallestNormalized, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2791 { PSmallestNormalized, PSmallestValue, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2792 { PSmallestNormalized, MSmallestValue, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2793 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2794 { PSmallestNormalized, MSmallestNormalized, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
2795 { MSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2796 { MSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2797 { MSmallestNormalized, PZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2798 { MSmallestNormalized, MZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2799 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2800 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2801 { MSmallestNormalized, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2802 { MSmallestNormalized, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2803 { MSmallestNormalized, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2804 { MSmallestNormalized, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2805 { MSmallestNormalized, PSmallestValue, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2806 { MSmallestNormalized, MSmallestValue, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2807 { MSmallestNormalized, PSmallestNormalized, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
2808 { MSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero }
2811 for (size_t i = 0; i < std::size(SpecialCaseTests); ++i) {
2812 APFloat x(SpecialCaseTests[i].x);
2813 APFloat y(SpecialCaseTests[i].y);
2814 APFloat::opStatus status = x.subtract(y, APFloat::rmNearestTiesToEven);
2816 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
2818 EXPECT_TRUE(result.bitwiseIsEqual(x));
2819 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
2820 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
2824 TEST(APFloatTest, multiply) {
2825 // Test Special Cases against each other and normal values.
2827 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2828 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2829 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2830 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2831 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2832 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
2833 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2834 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2835 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2836 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2837 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2838 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
2839 APFloat PSmallestNormalized =
2840 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
2841 APFloat MSmallestNormalized =
2842 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
2844 APFloat MaxQuad(APFloat::IEEEquad(),
2845 "0x1.ffffffffffffffffffffffffffffp+16383");
2846 APFloat MinQuad(APFloat::IEEEquad(),
2847 "0x0.0000000000000000000000000001p-16382");
2848 APFloat NMinQuad(APFloat::IEEEquad(),
2849 "-0x0.0000000000000000000000000001p-16382");
2851 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2852 const int UnderflowStatus = APFloat::opUnderflow | APFloat::opInexact;
2854 struct {
2855 APFloat x;
2856 APFloat y;
2857 const char *result;
2858 int status;
2859 int category;
2860 APFloat::roundingMode roundingMode = APFloat::rmNearestTiesToEven;
2861 } SpecialCaseTests[] = {
2862 { PInf, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2863 { PInf, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2864 { PInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2865 { PInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2866 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2867 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2868 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2869 { PInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2870 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2871 { PInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2872 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2873 { PInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2874 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2875 { PInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2876 { MInf, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2877 { MInf, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2878 { MInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2879 { MInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2880 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2881 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2882 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2883 { MInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2884 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2885 { MInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2886 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2887 { MInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2888 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2889 { MInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2890 { PZero, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2891 { PZero, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2892 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2893 { PZero, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2894 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2895 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2896 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2897 { PZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2898 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2899 { PZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2900 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2901 { PZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2902 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2903 { PZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2904 { MZero, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2905 { MZero, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2906 { MZero, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2907 { MZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2908 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2909 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2910 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2911 { MZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2912 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2913 { MZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2914 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2915 { MZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2916 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2917 { MZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2918 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
2919 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
2920 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
2921 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
2922 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2923 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2924 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2925 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2926 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2927 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2928 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2929 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2930 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2931 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2932 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2933 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2934 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2935 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2936 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2937 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2938 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2939 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2940 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2941 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2942 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2943 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2944 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2945 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2946 { PNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2947 { PNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2948 { PNormalValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2949 { PNormalValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2950 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2951 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2952 { PNormalValue, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2953 { PNormalValue, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2954 { PNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2955 { PNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2956 { PNormalValue, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2957 { PNormalValue, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2958 { PNormalValue, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2959 { PNormalValue, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2960 { MNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2961 { MNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2962 { MNormalValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2963 { MNormalValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2964 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2965 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2966 { MNormalValue, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2967 { MNormalValue, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2968 { MNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2969 { MNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2970 { MNormalValue, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2971 { MNormalValue, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2972 { MNormalValue, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2973 { MNormalValue, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2974 { PLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2975 { PLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2976 { PLargestValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2977 { PLargestValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2978 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2979 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2980 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2981 { PLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2982 { PLargestValue, PLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2983 { PLargestValue, MLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2984 { PLargestValue, PSmallestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2985 { PLargestValue, MSmallestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2986 { PLargestValue, PSmallestNormalized, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2987 { PLargestValue, MSmallestNormalized, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2988 { MLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2989 { MLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2990 { MLargestValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2991 { MLargestValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2992 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2993 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2994 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2995 { MLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2996 { MLargestValue, PLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2997 { MLargestValue, MLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2998 { MLargestValue, PSmallestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2999 { MLargestValue, MSmallestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
3000 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
3001 { MLargestValue, MSmallestNormalized, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
3002 { PSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
3003 { PSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
3004 { PSmallestValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3005 { PSmallestValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3006 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3007 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3008 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3009 { PSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3010 { PSmallestValue, PLargestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
3011 { PSmallestValue, MLargestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
3012 { PSmallestValue, PSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3013 { PSmallestValue, MSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3014 { PSmallestValue, PSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3015 { PSmallestValue, MSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3016 { MSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
3017 { MSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
3018 { MSmallestValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3019 { MSmallestValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3020 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3021 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3022 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3023 { MSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3024 { MSmallestValue, PLargestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
3025 { MSmallestValue, MLargestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
3026 { MSmallestValue, PSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3027 { MSmallestValue, MSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3028 { MSmallestValue, PSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3029 { MSmallestValue, MSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3030 { PSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
3031 { PSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
3032 { PSmallestNormalized, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3033 { PSmallestNormalized, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3034 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3035 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3036 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3037 { PSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3038 { PSmallestNormalized, PLargestValue, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
3039 { PSmallestNormalized, MLargestValue, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
3040 { PSmallestNormalized, PSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3041 { PSmallestNormalized, MSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3042 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3043 { PSmallestNormalized, MSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3044 { MSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
3045 { MSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
3046 { MSmallestNormalized, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3047 { MSmallestNormalized, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3048 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3049 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3050 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3051 { MSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3052 { MSmallestNormalized, PLargestValue, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
3053 { MSmallestNormalized, MLargestValue, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
3054 { MSmallestNormalized, PSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3055 { MSmallestNormalized, MSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3056 { MSmallestNormalized, PSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3057 { MSmallestNormalized, MSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3059 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3060 APFloat::fcNormal, APFloat::rmNearestTiesToEven},
3061 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3062 APFloat::fcNormal, APFloat::rmTowardPositive},
3063 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3064 APFloat::fcNormal, APFloat::rmTowardNegative},
3065 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3066 APFloat::fcNormal, APFloat::rmTowardZero},
3067 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3068 APFloat::fcNormal, APFloat::rmNearestTiesToAway},
3070 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3071 APFloat::fcNormal, APFloat::rmNearestTiesToEven},
3072 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3073 APFloat::fcNormal, APFloat::rmTowardPositive},
3074 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3075 APFloat::fcNormal, APFloat::rmTowardNegative},
3076 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3077 APFloat::fcNormal, APFloat::rmTowardZero},
3078 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
3079 APFloat::fcNormal, APFloat::rmNearestTiesToAway},
3081 {MaxQuad, MaxQuad, "inf", OverflowStatus, APFloat::fcInfinity,
3082 APFloat::rmNearestTiesToEven},
3083 {MaxQuad, MaxQuad, "inf", OverflowStatus, APFloat::fcInfinity,
3084 APFloat::rmTowardPositive},
3085 {MaxQuad, MaxQuad, "0x1.ffffffffffffffffffffffffffffp+16383",
3086 APFloat::opInexact, APFloat::fcNormal, APFloat::rmTowardNegative},
3087 {MaxQuad, MaxQuad, "0x1.ffffffffffffffffffffffffffffp+16383",
3088 APFloat::opInexact, APFloat::fcNormal, APFloat::rmTowardZero},
3089 {MaxQuad, MaxQuad, "inf", OverflowStatus, APFloat::fcInfinity,
3090 APFloat::rmNearestTiesToAway},
3092 {MinQuad, MinQuad, "0", UnderflowStatus, APFloat::fcZero,
3093 APFloat::rmNearestTiesToEven},
3094 {MinQuad, MinQuad, "0x0.0000000000000000000000000001p-16382",
3095 UnderflowStatus, APFloat::fcNormal, APFloat::rmTowardPositive},
3096 {MinQuad, MinQuad, "0", UnderflowStatus, APFloat::fcZero,
3097 APFloat::rmTowardNegative},
3098 {MinQuad, MinQuad, "0", UnderflowStatus, APFloat::fcZero,
3099 APFloat::rmTowardZero},
3100 {MinQuad, MinQuad, "0", UnderflowStatus, APFloat::fcZero,
3101 APFloat::rmNearestTiesToAway},
3103 {MinQuad, NMinQuad, "-0", UnderflowStatus, APFloat::fcZero,
3104 APFloat::rmNearestTiesToEven},
3105 {MinQuad, NMinQuad, "-0", UnderflowStatus, APFloat::fcZero,
3106 APFloat::rmTowardPositive},
3107 {MinQuad, NMinQuad, "-0x0.0000000000000000000000000001p-16382",
3108 UnderflowStatus, APFloat::fcNormal, APFloat::rmTowardNegative},
3109 {MinQuad, NMinQuad, "-0", UnderflowStatus, APFloat::fcZero,
3110 APFloat::rmTowardZero},
3111 {MinQuad, NMinQuad, "-0", UnderflowStatus, APFloat::fcZero,
3112 APFloat::rmNearestTiesToAway},
3115 for (size_t i = 0; i < std::size(SpecialCaseTests); ++i) {
3116 APFloat x(SpecialCaseTests[i].x);
3117 APFloat y(SpecialCaseTests[i].y);
3118 APFloat::opStatus status = x.multiply(y, SpecialCaseTests[i].roundingMode);
3120 APFloat result(x.getSemantics(), SpecialCaseTests[i].result);
3122 EXPECT_TRUE(result.bitwiseIsEqual(x));
3123 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
3124 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
3128 TEST(APFloatTest, divide) {
3129 // Test Special Cases against each other and normal values.
3131 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
3132 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
3133 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
3134 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
3135 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
3136 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
3137 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
3138 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
3139 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
3140 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
3141 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
3142 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
3143 APFloat PSmallestNormalized =
3144 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
3145 APFloat MSmallestNormalized =
3146 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
3148 APFloat MaxQuad(APFloat::IEEEquad(),
3149 "0x1.ffffffffffffffffffffffffffffp+16383");
3150 APFloat MinQuad(APFloat::IEEEquad(),
3151 "0x0.0000000000000000000000000001p-16382");
3152 APFloat NMinQuad(APFloat::IEEEquad(),
3153 "-0x0.0000000000000000000000000001p-16382");
3155 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
3156 const int UnderflowStatus = APFloat::opUnderflow | APFloat::opInexact;
3158 struct {
3159 APFloat x;
3160 APFloat y;
3161 const char *result;
3162 int status;
3163 int category;
3164 APFloat::roundingMode roundingMode = APFloat::rmNearestTiesToEven;
3165 } SpecialCaseTests[] = {
3166 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3167 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3168 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
3169 { PInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
3170 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3171 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3172 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
3173 { PInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
3174 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
3175 { PInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
3176 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
3177 { PInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
3178 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
3179 { PInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
3180 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3181 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3182 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
3183 { MInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
3184 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3185 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3186 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
3187 { MInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
3188 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
3189 { MInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
3190 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
3191 { MInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
3192 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
3193 { MInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
3194 { PZero, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3195 { PZero, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3196 { PZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3197 { PZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3198 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3199 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3200 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3201 { PZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3202 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3203 { PZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3204 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3205 { PZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3206 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3207 { PZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3208 { MZero, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3209 { MZero, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3210 { MZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3211 { MZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3212 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3213 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3214 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3215 { MZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3216 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3217 { MZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3218 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3219 { MZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3220 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3221 { MZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3222 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
3223 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
3224 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
3225 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
3226 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3227 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3228 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
3229 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
3230 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
3231 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
3232 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
3233 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
3234 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
3235 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
3236 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3237 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3238 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3239 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3240 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3241 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3242 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3243 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3244 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3245 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3246 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3247 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3248 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3249 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3250 { PNormalValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3251 { PNormalValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3252 { PNormalValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
3253 { PNormalValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
3254 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3255 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3256 { PNormalValue, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3257 { PNormalValue, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3258 { PNormalValue, PLargestValue, "0x1p-128", UnderflowStatus, APFloat::fcNormal },
3259 { PNormalValue, MLargestValue, "-0x1p-128", UnderflowStatus, APFloat::fcNormal },
3260 { PNormalValue, PSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
3261 { PNormalValue, MSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
3262 { PNormalValue, PSmallestNormalized, "0x1p+126", APFloat::opOK, APFloat::fcNormal },
3263 { PNormalValue, MSmallestNormalized, "-0x1p+126", APFloat::opOK, APFloat::fcNormal },
3264 { MNormalValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3265 { MNormalValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3266 { MNormalValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
3267 { MNormalValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
3268 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3269 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3270 { MNormalValue, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3271 { MNormalValue, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3272 { MNormalValue, PLargestValue, "-0x1p-128", UnderflowStatus, APFloat::fcNormal },
3273 { MNormalValue, MLargestValue, "0x1p-128", UnderflowStatus, APFloat::fcNormal },
3274 { MNormalValue, PSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
3275 { MNormalValue, MSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
3276 { MNormalValue, PSmallestNormalized, "-0x1p+126", APFloat::opOK, APFloat::fcNormal },
3277 { MNormalValue, MSmallestNormalized, "0x1p+126", APFloat::opOK, APFloat::fcNormal },
3278 { PLargestValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3279 { PLargestValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3280 { PLargestValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
3281 { PLargestValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
3282 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3283 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3284 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
3285 { PLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
3286 { PLargestValue, PLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3287 { PLargestValue, MLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3288 { PLargestValue, PSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
3289 { PLargestValue, MSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
3290 { PLargestValue, PSmallestNormalized, "inf", OverflowStatus, APFloat::fcInfinity },
3291 { PLargestValue, MSmallestNormalized, "-inf", OverflowStatus, APFloat::fcInfinity },
3292 { MLargestValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3293 { MLargestValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3294 { MLargestValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
3295 { MLargestValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
3296 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3297 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3298 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
3299 { MLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
3300 { MLargestValue, PLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3301 { MLargestValue, MLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3302 { MLargestValue, PSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
3303 { MLargestValue, MSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
3304 { MLargestValue, PSmallestNormalized, "-inf", OverflowStatus, APFloat::fcInfinity },
3305 { MLargestValue, MSmallestNormalized, "inf", OverflowStatus, APFloat::fcInfinity },
3306 { PSmallestValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3307 { PSmallestValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3308 { PSmallestValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
3309 { PSmallestValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
3310 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3311 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3312 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3313 { PSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3314 { PSmallestValue, PLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3315 { PSmallestValue, MLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3316 { PSmallestValue, PSmallestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3317 { PSmallestValue, MSmallestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3318 { PSmallestValue, PSmallestNormalized, "0x1p-23", APFloat::opOK, APFloat::fcNormal },
3319 { PSmallestValue, MSmallestNormalized, "-0x1p-23", APFloat::opOK, APFloat::fcNormal },
3320 { MSmallestValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3321 { MSmallestValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3322 { MSmallestValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
3323 { MSmallestValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
3324 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3325 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3326 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3327 { MSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3328 { MSmallestValue, PLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3329 { MSmallestValue, MLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3330 { MSmallestValue, PSmallestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3331 { MSmallestValue, MSmallestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3332 { MSmallestValue, PSmallestNormalized, "-0x1p-23", APFloat::opOK, APFloat::fcNormal },
3333 { MSmallestValue, MSmallestNormalized, "0x1p-23", APFloat::opOK, APFloat::fcNormal },
3334 { PSmallestNormalized, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3335 { PSmallestNormalized, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3336 { PSmallestNormalized, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
3337 { PSmallestNormalized, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
3338 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3339 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3340 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3341 { PSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3342 { PSmallestNormalized, PLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3343 { PSmallestNormalized, MLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3344 { PSmallestNormalized, PSmallestValue, "0x1p+23", APFloat::opOK, APFloat::fcNormal },
3345 { PSmallestNormalized, MSmallestValue, "-0x1p+23", APFloat::opOK, APFloat::fcNormal },
3346 { PSmallestNormalized, PSmallestNormalized, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3347 { PSmallestNormalized, MSmallestNormalized, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3348 { MSmallestNormalized, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3349 { MSmallestNormalized, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3350 { MSmallestNormalized, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
3351 { MSmallestNormalized, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
3352 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3353 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3354 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3355 { MSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3356 { MSmallestNormalized, PLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3357 { MSmallestNormalized, MLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3358 { MSmallestNormalized, PSmallestValue, "-0x1p+23", APFloat::opOK, APFloat::fcNormal },
3359 { MSmallestNormalized, MSmallestValue, "0x1p+23", APFloat::opOK, APFloat::fcNormal },
3360 { MSmallestNormalized, PSmallestNormalized, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3361 { MSmallestNormalized, MSmallestNormalized, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3363 {MaxQuad, NMinQuad, "-inf", OverflowStatus, APFloat::fcInfinity,
3364 APFloat::rmNearestTiesToEven},
3365 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp+16383",
3366 APFloat::opInexact, APFloat::fcNormal, APFloat::rmTowardPositive},
3367 {MaxQuad, NMinQuad, "-inf", OverflowStatus, APFloat::fcInfinity,
3368 APFloat::rmTowardNegative},
3369 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp+16383",
3370 APFloat::opInexact, APFloat::fcNormal, APFloat::rmTowardZero},
3371 {MaxQuad, NMinQuad, "-inf", OverflowStatus, APFloat::fcInfinity,
3372 APFloat::rmNearestTiesToAway},
3374 {MinQuad, MaxQuad, "0", UnderflowStatus, APFloat::fcZero,
3375 APFloat::rmNearestTiesToEven},
3376 {MinQuad, MaxQuad, "0x0.0000000000000000000000000001p-16382",
3377 UnderflowStatus, APFloat::fcNormal, APFloat::rmTowardPositive},
3378 {MinQuad, MaxQuad, "0", UnderflowStatus, APFloat::fcZero,
3379 APFloat::rmTowardNegative},
3380 {MinQuad, MaxQuad, "0", UnderflowStatus, APFloat::fcZero,
3381 APFloat::rmTowardZero},
3382 {MinQuad, MaxQuad, "0", UnderflowStatus, APFloat::fcZero,
3383 APFloat::rmNearestTiesToAway},
3385 {NMinQuad, MaxQuad, "-0", UnderflowStatus, APFloat::fcZero,
3386 APFloat::rmNearestTiesToEven},
3387 {NMinQuad, MaxQuad, "-0", UnderflowStatus, APFloat::fcZero,
3388 APFloat::rmTowardPositive},
3389 {NMinQuad, MaxQuad, "-0x0.0000000000000000000000000001p-16382",
3390 UnderflowStatus, APFloat::fcNormal, APFloat::rmTowardNegative},
3391 {NMinQuad, MaxQuad, "-0", UnderflowStatus, APFloat::fcZero,
3392 APFloat::rmTowardZero},
3393 {NMinQuad, MaxQuad, "-0", UnderflowStatus, APFloat::fcZero,
3394 APFloat::rmNearestTiesToAway},
3397 for (size_t i = 0; i < std::size(SpecialCaseTests); ++i) {
3398 APFloat x(SpecialCaseTests[i].x);
3399 APFloat y(SpecialCaseTests[i].y);
3400 APFloat::opStatus status = x.divide(y, SpecialCaseTests[i].roundingMode);
3402 APFloat result(x.getSemantics(), SpecialCaseTests[i].result);
3404 EXPECT_TRUE(result.bitwiseIsEqual(x));
3405 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
3406 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
3410 TEST(APFloatTest, operatorOverloads) {
3411 // This is mostly testing that these operator overloads compile.
3412 APFloat One = APFloat(APFloat::IEEEsingle(), "0x1p+0");
3413 APFloat Two = APFloat(APFloat::IEEEsingle(), "0x2p+0");
3414 EXPECT_TRUE(Two.bitwiseIsEqual(One + One));
3415 EXPECT_TRUE(One.bitwiseIsEqual(Two - One));
3416 EXPECT_TRUE(Two.bitwiseIsEqual(One * Two));
3417 EXPECT_TRUE(One.bitwiseIsEqual(Two / Two));
3420 TEST(APFloatTest, Comparisons) {
3421 enum {MNan, MInf, MBig, MOne, MZer, PZer, POne, PBig, PInf, PNan, NumVals};
3422 APFloat Vals[NumVals] = {
3423 APFloat::getNaN(APFloat::IEEEsingle(), true),
3424 APFloat::getInf(APFloat::IEEEsingle(), true),
3425 APFloat::getLargest(APFloat::IEEEsingle(), true),
3426 APFloat(APFloat::IEEEsingle(), "-0x1p+0"),
3427 APFloat::getZero(APFloat::IEEEsingle(), true),
3428 APFloat::getZero(APFloat::IEEEsingle(), false),
3429 APFloat(APFloat::IEEEsingle(), "0x1p+0"),
3430 APFloat::getLargest(APFloat::IEEEsingle(), false),
3431 APFloat::getInf(APFloat::IEEEsingle(), false),
3432 APFloat::getNaN(APFloat::IEEEsingle(), false),
3434 using Relation = void (*)(const APFloat &, const APFloat &);
3435 Relation LT = [](const APFloat &LHS, const APFloat &RHS) {
3436 EXPECT_FALSE(LHS == RHS);
3437 EXPECT_TRUE(LHS != RHS);
3438 EXPECT_TRUE(LHS < RHS);
3439 EXPECT_FALSE(LHS > RHS);
3440 EXPECT_TRUE(LHS <= RHS);
3441 EXPECT_FALSE(LHS >= RHS);
3443 Relation EQ = [](const APFloat &LHS, const APFloat &RHS) {
3444 EXPECT_TRUE(LHS == RHS);
3445 EXPECT_FALSE(LHS != RHS);
3446 EXPECT_FALSE(LHS < RHS);
3447 EXPECT_FALSE(LHS > RHS);
3448 EXPECT_TRUE(LHS <= RHS);
3449 EXPECT_TRUE(LHS >= RHS);
3451 Relation GT = [](const APFloat &LHS, const APFloat &RHS) {
3452 EXPECT_FALSE(LHS == RHS);
3453 EXPECT_TRUE(LHS != RHS);
3454 EXPECT_FALSE(LHS < RHS);
3455 EXPECT_TRUE(LHS > RHS);
3456 EXPECT_FALSE(LHS <= RHS);
3457 EXPECT_TRUE(LHS >= RHS);
3459 Relation UN = [](const APFloat &LHS, const APFloat &RHS) {
3460 EXPECT_FALSE(LHS == RHS);
3461 EXPECT_TRUE(LHS != RHS);
3462 EXPECT_FALSE(LHS < RHS);
3463 EXPECT_FALSE(LHS > RHS);
3464 EXPECT_FALSE(LHS <= RHS);
3465 EXPECT_FALSE(LHS >= RHS);
3467 Relation Relations[NumVals][NumVals] = {
3468 // -N -I -B -1 -0 +0 +1 +B +I +N
3469 /* MNan */ {UN, UN, UN, UN, UN, UN, UN, UN, UN, UN},
3470 /* MInf */ {UN, EQ, LT, LT, LT, LT, LT, LT, LT, UN},
3471 /* MBig */ {UN, GT, EQ, LT, LT, LT, LT, LT, LT, UN},
3472 /* MOne */ {UN, GT, GT, EQ, LT, LT, LT, LT, LT, UN},
3473 /* MZer */ {UN, GT, GT, GT, EQ, EQ, LT, LT, LT, UN},
3474 /* PZer */ {UN, GT, GT, GT, EQ, EQ, LT, LT, LT, UN},
3475 /* POne */ {UN, GT, GT, GT, GT, GT, EQ, LT, LT, UN},
3476 /* PBig */ {UN, GT, GT, GT, GT, GT, GT, EQ, LT, UN},
3477 /* PInf */ {UN, GT, GT, GT, GT, GT, GT, GT, EQ, UN},
3478 /* PNan */ {UN, UN, UN, UN, UN, UN, UN, UN, UN, UN},
3480 for (unsigned I = 0; I < NumVals; ++I)
3481 for (unsigned J = 0; J < NumVals; ++J)
3482 Relations[I][J](Vals[I], Vals[J]);
3485 TEST(APFloatTest, abs) {
3486 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
3487 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
3488 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
3489 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
3490 APFloat PQNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
3491 APFloat MQNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
3492 APFloat PSNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
3493 APFloat MSNaN = APFloat::getSNaN(APFloat::IEEEsingle(), true);
3494 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
3495 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
3496 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
3497 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
3498 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
3499 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
3500 APFloat PSmallestNormalized =
3501 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
3502 APFloat MSmallestNormalized =
3503 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
3505 EXPECT_TRUE(PInf.bitwiseIsEqual(abs(PInf)));
3506 EXPECT_TRUE(PInf.bitwiseIsEqual(abs(MInf)));
3507 EXPECT_TRUE(PZero.bitwiseIsEqual(abs(PZero)));
3508 EXPECT_TRUE(PZero.bitwiseIsEqual(abs(MZero)));
3509 EXPECT_TRUE(PQNaN.bitwiseIsEqual(abs(PQNaN)));
3510 EXPECT_TRUE(PQNaN.bitwiseIsEqual(abs(MQNaN)));
3511 EXPECT_TRUE(PSNaN.bitwiseIsEqual(abs(PSNaN)));
3512 EXPECT_TRUE(PSNaN.bitwiseIsEqual(abs(MSNaN)));
3513 EXPECT_TRUE(PNormalValue.bitwiseIsEqual(abs(PNormalValue)));
3514 EXPECT_TRUE(PNormalValue.bitwiseIsEqual(abs(MNormalValue)));
3515 EXPECT_TRUE(PLargestValue.bitwiseIsEqual(abs(PLargestValue)));
3516 EXPECT_TRUE(PLargestValue.bitwiseIsEqual(abs(MLargestValue)));
3517 EXPECT_TRUE(PSmallestValue.bitwiseIsEqual(abs(PSmallestValue)));
3518 EXPECT_TRUE(PSmallestValue.bitwiseIsEqual(abs(MSmallestValue)));
3519 EXPECT_TRUE(PSmallestNormalized.bitwiseIsEqual(abs(PSmallestNormalized)));
3520 EXPECT_TRUE(PSmallestNormalized.bitwiseIsEqual(abs(MSmallestNormalized)));
3523 TEST(APFloatTest, neg) {
3524 APFloat One = APFloat(APFloat::IEEEsingle(), "1.0");
3525 APFloat NegOne = APFloat(APFloat::IEEEsingle(), "-1.0");
3526 APFloat Zero = APFloat::getZero(APFloat::IEEEsingle(), false);
3527 APFloat NegZero = APFloat::getZero(APFloat::IEEEsingle(), true);
3528 APFloat Inf = APFloat::getInf(APFloat::IEEEsingle(), false);
3529 APFloat NegInf = APFloat::getInf(APFloat::IEEEsingle(), true);
3530 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
3531 APFloat NegQNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
3533 EXPECT_TRUE(NegOne.bitwiseIsEqual(neg(One)));
3534 EXPECT_TRUE(One.bitwiseIsEqual(neg(NegOne)));
3535 EXPECT_TRUE(NegZero.bitwiseIsEqual(neg(Zero)));
3536 EXPECT_TRUE(Zero.bitwiseIsEqual(neg(NegZero)));
3537 EXPECT_TRUE(NegInf.bitwiseIsEqual(neg(Inf)));
3538 EXPECT_TRUE(Inf.bitwiseIsEqual(neg(NegInf)));
3539 EXPECT_TRUE(NegInf.bitwiseIsEqual(neg(Inf)));
3540 EXPECT_TRUE(Inf.bitwiseIsEqual(neg(NegInf)));
3541 EXPECT_TRUE(NegQNaN.bitwiseIsEqual(neg(QNaN)));
3542 EXPECT_TRUE(QNaN.bitwiseIsEqual(neg(NegQNaN)));
3544 EXPECT_TRUE(NegOne.bitwiseIsEqual(-One));
3545 EXPECT_TRUE(One.bitwiseIsEqual(-NegOne));
3546 EXPECT_TRUE(NegZero.bitwiseIsEqual(-Zero));
3547 EXPECT_TRUE(Zero.bitwiseIsEqual(-NegZero));
3548 EXPECT_TRUE(NegInf.bitwiseIsEqual(-Inf));
3549 EXPECT_TRUE(Inf.bitwiseIsEqual(-NegInf));
3550 EXPECT_TRUE(NegInf.bitwiseIsEqual(-Inf));
3551 EXPECT_TRUE(Inf.bitwiseIsEqual(-NegInf));
3552 EXPECT_TRUE(NegQNaN.bitwiseIsEqual(-QNaN));
3553 EXPECT_TRUE(QNaN.bitwiseIsEqual(-NegQNaN));
3556 TEST(APFloatTest, ilogb) {
3557 EXPECT_EQ(-1074, ilogb(APFloat::getSmallest(APFloat::IEEEdouble(), false)));
3558 EXPECT_EQ(-1074, ilogb(APFloat::getSmallest(APFloat::IEEEdouble(), true)));
3559 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1024")));
3560 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023")));
3561 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023")));
3562 EXPECT_EQ(-51, ilogb(APFloat(APFloat::IEEEdouble(), "0x1p-51")));
3563 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1023")));
3564 EXPECT_EQ(-2, ilogb(APFloat(APFloat::IEEEdouble(), "0x0.ffffp-1")));
3565 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.fffep-1023")));
3566 EXPECT_EQ(1023, ilogb(APFloat::getLargest(APFloat::IEEEdouble(), false)));
3567 EXPECT_EQ(1023, ilogb(APFloat::getLargest(APFloat::IEEEdouble(), true)));
3570 EXPECT_EQ(0, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p+0")));
3571 EXPECT_EQ(0, ilogb(APFloat(APFloat::IEEEsingle(), "-0x1p+0")));
3572 EXPECT_EQ(42, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p+42")));
3573 EXPECT_EQ(-42, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p-42")));
3575 EXPECT_EQ(APFloat::IEK_Inf,
3576 ilogb(APFloat::getInf(APFloat::IEEEsingle(), false)));
3577 EXPECT_EQ(APFloat::IEK_Inf,
3578 ilogb(APFloat::getInf(APFloat::IEEEsingle(), true)));
3579 EXPECT_EQ(APFloat::IEK_Zero,
3580 ilogb(APFloat::getZero(APFloat::IEEEsingle(), false)));
3581 EXPECT_EQ(APFloat::IEK_Zero,
3582 ilogb(APFloat::getZero(APFloat::IEEEsingle(), true)));
3583 EXPECT_EQ(APFloat::IEK_NaN,
3584 ilogb(APFloat::getNaN(APFloat::IEEEsingle(), false)));
3585 EXPECT_EQ(APFloat::IEK_NaN,
3586 ilogb(APFloat::getSNaN(APFloat::IEEEsingle(), false)));
3588 EXPECT_EQ(127, ilogb(APFloat::getLargest(APFloat::IEEEsingle(), false)));
3589 EXPECT_EQ(127, ilogb(APFloat::getLargest(APFloat::IEEEsingle(), true)));
3591 EXPECT_EQ(-149, ilogb(APFloat::getSmallest(APFloat::IEEEsingle(), false)));
3592 EXPECT_EQ(-149, ilogb(APFloat::getSmallest(APFloat::IEEEsingle(), true)));
3593 EXPECT_EQ(-126,
3594 ilogb(APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false)));
3595 EXPECT_EQ(-126,
3596 ilogb(APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true)));
3599 TEST(APFloatTest, scalbn) {
3601 const APFloat::roundingMode RM = APFloat::rmNearestTiesToEven;
3602 EXPECT_TRUE(
3603 APFloat(APFloat::IEEEsingle(), "0x1p+0")
3604 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 0, RM)));
3605 EXPECT_TRUE(
3606 APFloat(APFloat::IEEEsingle(), "0x1p+42")
3607 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 42, RM)));
3608 EXPECT_TRUE(
3609 APFloat(APFloat::IEEEsingle(), "0x1p-42")
3610 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), -42, RM)));
3612 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
3613 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
3614 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
3615 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
3616 APFloat QPNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
3617 APFloat QMNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
3618 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
3620 EXPECT_TRUE(PInf.bitwiseIsEqual(scalbn(PInf, 0, RM)));
3621 EXPECT_TRUE(MInf.bitwiseIsEqual(scalbn(MInf, 0, RM)));
3622 EXPECT_TRUE(PZero.bitwiseIsEqual(scalbn(PZero, 0, RM)));
3623 EXPECT_TRUE(MZero.bitwiseIsEqual(scalbn(MZero, 0, RM)));
3624 EXPECT_TRUE(QPNaN.bitwiseIsEqual(scalbn(QPNaN, 0, RM)));
3625 EXPECT_TRUE(QMNaN.bitwiseIsEqual(scalbn(QMNaN, 0, RM)));
3626 EXPECT_FALSE(scalbn(SNaN, 0, RM).isSignaling());
3628 APFloat ScalbnSNaN = scalbn(SNaN, 1, RM);
3629 EXPECT_TRUE(ScalbnSNaN.isNaN() && !ScalbnSNaN.isSignaling());
3631 // Make sure highest bit of payload is preserved.
3632 const APInt Payload(64, (UINT64_C(1) << 50) |
3633 (UINT64_C(1) << 49) |
3634 (UINT64_C(1234) << 32) |
3637 APFloat SNaNWithPayload = APFloat::getSNaN(APFloat::IEEEdouble(), false,
3638 &Payload);
3639 APFloat QuietPayload = scalbn(SNaNWithPayload, 1, RM);
3640 EXPECT_TRUE(QuietPayload.isNaN() && !QuietPayload.isSignaling());
3641 EXPECT_EQ(Payload, QuietPayload.bitcastToAPInt().getLoBits(51));
3643 EXPECT_TRUE(PInf.bitwiseIsEqual(
3644 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 128, RM)));
3645 EXPECT_TRUE(MInf.bitwiseIsEqual(
3646 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p+0"), 128, RM)));
3647 EXPECT_TRUE(PInf.bitwiseIsEqual(
3648 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+127"), 1, RM)));
3649 EXPECT_TRUE(PZero.bitwiseIsEqual(
3650 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p-127"), -127, RM)));
3651 EXPECT_TRUE(MZero.bitwiseIsEqual(
3652 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p-127"), -127, RM)));
3653 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p-149").bitwiseIsEqual(
3654 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p-127"), -22, RM)));
3655 EXPECT_TRUE(PZero.bitwiseIsEqual(
3656 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p-126"), -24, RM)));
3659 APFloat SmallestF64 = APFloat::getSmallest(APFloat::IEEEdouble(), false);
3660 APFloat NegSmallestF64 = APFloat::getSmallest(APFloat::IEEEdouble(), true);
3662 APFloat LargestF64 = APFloat::getLargest(APFloat::IEEEdouble(), false);
3663 APFloat NegLargestF64 = APFloat::getLargest(APFloat::IEEEdouble(), true);
3665 APFloat SmallestNormalizedF64
3666 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
3667 APFloat NegSmallestNormalizedF64
3668 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
3670 APFloat LargestDenormalF64(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023");
3671 APFloat NegLargestDenormalF64(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023");
3674 EXPECT_TRUE(SmallestF64.bitwiseIsEqual(
3675 scalbn(APFloat(APFloat::IEEEdouble(), "0x1p-1074"), 0, RM)));
3676 EXPECT_TRUE(NegSmallestF64.bitwiseIsEqual(
3677 scalbn(APFloat(APFloat::IEEEdouble(), "-0x1p-1074"), 0, RM)));
3679 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1023")
3680 .bitwiseIsEqual(scalbn(SmallestF64, 2097, RM)));
3682 EXPECT_TRUE(scalbn(SmallestF64, -2097, RM).isPosZero());
3683 EXPECT_TRUE(scalbn(SmallestF64, -2098, RM).isPosZero());
3684 EXPECT_TRUE(scalbn(SmallestF64, -2099, RM).isPosZero());
3685 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1022")
3686 .bitwiseIsEqual(scalbn(SmallestF64, 2096, RM)));
3687 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1023")
3688 .bitwiseIsEqual(scalbn(SmallestF64, 2097, RM)));
3689 EXPECT_TRUE(scalbn(SmallestF64, 2098, RM).isInfinity());
3690 EXPECT_TRUE(scalbn(SmallestF64, 2099, RM).isInfinity());
3692 // Test for integer overflows when adding to exponent.
3693 EXPECT_TRUE(scalbn(SmallestF64, -INT_MAX, RM).isPosZero());
3694 EXPECT_TRUE(scalbn(LargestF64, INT_MAX, RM).isInfinity());
3696 EXPECT_TRUE(LargestDenormalF64
3697 .bitwiseIsEqual(scalbn(LargestDenormalF64, 0, RM)));
3698 EXPECT_TRUE(NegLargestDenormalF64
3699 .bitwiseIsEqual(scalbn(NegLargestDenormalF64, 0, RM)));
3701 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1022")
3702 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1, RM)));
3703 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1021")
3704 .bitwiseIsEqual(scalbn(NegLargestDenormalF64, 2, RM)));
3706 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+1")
3707 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1024, RM)));
3708 EXPECT_TRUE(scalbn(LargestDenormalF64, -1023, RM).isPosZero());
3709 EXPECT_TRUE(scalbn(LargestDenormalF64, -1024, RM).isPosZero());
3710 EXPECT_TRUE(scalbn(LargestDenormalF64, -2048, RM).isPosZero());
3711 EXPECT_TRUE(scalbn(LargestDenormalF64, 2047, RM).isInfinity());
3712 EXPECT_TRUE(scalbn(LargestDenormalF64, 2098, RM).isInfinity());
3713 EXPECT_TRUE(scalbn(LargestDenormalF64, 2099, RM).isInfinity());
3715 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-2")
3716 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1021, RM)));
3717 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1")
3718 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1022, RM)));
3719 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+0")
3720 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1023, RM)));
3721 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+1023")
3722 .bitwiseIsEqual(scalbn(LargestDenormalF64, 2046, RM)));
3723 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+974")
3724 .bitwiseIsEqual(scalbn(SmallestF64, 2048, RM)));
3726 APFloat RandomDenormalF64(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+51");
3727 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-972")
3728 .bitwiseIsEqual(scalbn(RandomDenormalF64, -1023, RM)));
3729 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1")
3730 .bitwiseIsEqual(scalbn(RandomDenormalF64, -52, RM)));
3731 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-2")
3732 .bitwiseIsEqual(scalbn(RandomDenormalF64, -53, RM)));
3733 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+0")
3734 .bitwiseIsEqual(scalbn(RandomDenormalF64, -51, RM)));
3736 EXPECT_TRUE(scalbn(RandomDenormalF64, -2097, RM).isPosZero());
3737 EXPECT_TRUE(scalbn(RandomDenormalF64, -2090, RM).isPosZero());
3740 EXPECT_TRUE(
3741 APFloat(APFloat::IEEEdouble(), "-0x1p-1073")
3742 .bitwiseIsEqual(scalbn(NegLargestF64, -2097, RM)));
3744 EXPECT_TRUE(
3745 APFloat(APFloat::IEEEdouble(), "-0x1p-1024")
3746 .bitwiseIsEqual(scalbn(NegLargestF64, -2048, RM)));
3748 EXPECT_TRUE(
3749 APFloat(APFloat::IEEEdouble(), "0x1p-1073")
3750 .bitwiseIsEqual(scalbn(LargestF64, -2097, RM)));
3752 EXPECT_TRUE(
3753 APFloat(APFloat::IEEEdouble(), "0x1p-1074")
3754 .bitwiseIsEqual(scalbn(LargestF64, -2098, RM)));
3755 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1074")
3756 .bitwiseIsEqual(scalbn(NegLargestF64, -2098, RM)));
3757 EXPECT_TRUE(scalbn(NegLargestF64, -2099, RM).isNegZero());
3758 EXPECT_TRUE(scalbn(LargestF64, 1, RM).isInfinity());
3761 EXPECT_TRUE(
3762 APFloat(APFloat::IEEEdouble(), "0x1p+0")
3763 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEdouble(), "0x1p+52"), -52, RM)));
3765 EXPECT_TRUE(
3766 APFloat(APFloat::IEEEdouble(), "0x1p-103")
3767 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEdouble(), "0x1p-51"), -52, RM)));
3770 TEST(APFloatTest, frexp) {
3771 const APFloat::roundingMode RM = APFloat::rmNearestTiesToEven;
3773 APFloat PZero = APFloat::getZero(APFloat::IEEEdouble(), false);
3774 APFloat MZero = APFloat::getZero(APFloat::IEEEdouble(), true);
3775 APFloat One(1.0);
3776 APFloat MOne(-1.0);
3777 APFloat Two(2.0);
3778 APFloat MTwo(-2.0);
3780 APFloat LargestDenormal(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023");
3781 APFloat NegLargestDenormal(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023");
3783 APFloat Smallest = APFloat::getSmallest(APFloat::IEEEdouble(), false);
3784 APFloat NegSmallest = APFloat::getSmallest(APFloat::IEEEdouble(), true);
3786 APFloat Largest = APFloat::getLargest(APFloat::IEEEdouble(), false);
3787 APFloat NegLargest = APFloat::getLargest(APFloat::IEEEdouble(), true);
3789 APFloat PInf = APFloat::getInf(APFloat::IEEEdouble(), false);
3790 APFloat MInf = APFloat::getInf(APFloat::IEEEdouble(), true);
3792 APFloat QPNaN = APFloat::getNaN(APFloat::IEEEdouble(), false);
3793 APFloat QMNaN = APFloat::getNaN(APFloat::IEEEdouble(), true);
3794 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEdouble(), false);
3796 // Make sure highest bit of payload is preserved.
3797 const APInt Payload(64, (UINT64_C(1) << 50) |
3798 (UINT64_C(1) << 49) |
3799 (UINT64_C(1234) << 32) |
3802 APFloat SNaNWithPayload = APFloat::getSNaN(APFloat::IEEEdouble(), false,
3803 &Payload);
3805 APFloat SmallestNormalized
3806 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
3807 APFloat NegSmallestNormalized
3808 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
3810 int Exp;
3811 APFloat Frac(APFloat::IEEEdouble());
3814 Frac = frexp(PZero, Exp, RM);
3815 EXPECT_EQ(0, Exp);
3816 EXPECT_TRUE(Frac.isPosZero());
3818 Frac = frexp(MZero, Exp, RM);
3819 EXPECT_EQ(0, Exp);
3820 EXPECT_TRUE(Frac.isNegZero());
3823 Frac = frexp(One, Exp, RM);
3824 EXPECT_EQ(1, Exp);
3825 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
3827 Frac = frexp(MOne, Exp, RM);
3828 EXPECT_EQ(1, Exp);
3829 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1").bitwiseIsEqual(Frac));
3831 Frac = frexp(LargestDenormal, Exp, RM);
3832 EXPECT_EQ(-1022, Exp);
3833 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1").bitwiseIsEqual(Frac));
3835 Frac = frexp(NegLargestDenormal, Exp, RM);
3836 EXPECT_EQ(-1022, Exp);
3837 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1").bitwiseIsEqual(Frac));
3840 Frac = frexp(Smallest, Exp, RM);
3841 EXPECT_EQ(-1073, Exp);
3842 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
3844 Frac = frexp(NegSmallest, Exp, RM);
3845 EXPECT_EQ(-1073, Exp);
3846 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1").bitwiseIsEqual(Frac));
3849 Frac = frexp(Largest, Exp, RM);
3850 EXPECT_EQ(1024, Exp);
3851 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.fffffffffffffp-1").bitwiseIsEqual(Frac));
3853 Frac = frexp(NegLargest, Exp, RM);
3854 EXPECT_EQ(1024, Exp);
3855 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.fffffffffffffp-1").bitwiseIsEqual(Frac));
3858 Frac = frexp(PInf, Exp, RM);
3859 EXPECT_EQ(INT_MAX, Exp);
3860 EXPECT_TRUE(Frac.isInfinity() && !Frac.isNegative());
3862 Frac = frexp(MInf, Exp, RM);
3863 EXPECT_EQ(INT_MAX, Exp);
3864 EXPECT_TRUE(Frac.isInfinity() && Frac.isNegative());
3866 Frac = frexp(QPNaN, Exp, RM);
3867 EXPECT_EQ(INT_MIN, Exp);
3868 EXPECT_TRUE(Frac.isNaN());
3870 Frac = frexp(QMNaN, Exp, RM);
3871 EXPECT_EQ(INT_MIN, Exp);
3872 EXPECT_TRUE(Frac.isNaN());
3874 Frac = frexp(SNaN, Exp, RM);
3875 EXPECT_EQ(INT_MIN, Exp);
3876 EXPECT_TRUE(Frac.isNaN() && !Frac.isSignaling());
3878 Frac = frexp(SNaNWithPayload, Exp, RM);
3879 EXPECT_EQ(INT_MIN, Exp);
3880 EXPECT_TRUE(Frac.isNaN() && !Frac.isSignaling());
3881 EXPECT_EQ(Payload, Frac.bitcastToAPInt().getLoBits(51));
3883 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x0.ffffp-1"), Exp, RM);
3884 EXPECT_EQ(-1, Exp);
3885 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.fffep-1").bitwiseIsEqual(Frac));
3887 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x1p-51"), Exp, RM);
3888 EXPECT_EQ(-50, Exp);
3889 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
3891 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+51"), Exp, RM);
3892 EXPECT_EQ(52, Exp);
3893 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1").bitwiseIsEqual(Frac));
3896 TEST(APFloatTest, mod) {
3898 APFloat f1(APFloat::IEEEdouble(), "1.5");
3899 APFloat f2(APFloat::IEEEdouble(), "1.0");
3900 APFloat expected(APFloat::IEEEdouble(), "0.5");
3901 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3902 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3905 APFloat f1(APFloat::IEEEdouble(), "0.5");
3906 APFloat f2(APFloat::IEEEdouble(), "1.0");
3907 APFloat expected(APFloat::IEEEdouble(), "0.5");
3908 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3909 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3912 APFloat f1(APFloat::IEEEdouble(), "0x1.3333333333333p-2"); // 0.3
3913 APFloat f2(APFloat::IEEEdouble(), "0x1.47ae147ae147bp-7"); // 0.01
3914 APFloat expected(APFloat::IEEEdouble(),
3915 "0x1.47ae147ae1471p-7"); // 0.009999999999999983
3916 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3917 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3920 APFloat f1(APFloat::IEEEdouble(), "0x1p64"); // 1.8446744073709552e19
3921 APFloat f2(APFloat::IEEEdouble(), "1.5");
3922 APFloat expected(APFloat::IEEEdouble(), "1.0");
3923 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3924 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3927 APFloat f1(APFloat::IEEEdouble(), "0x1p1000");
3928 APFloat f2(APFloat::IEEEdouble(), "0x1p-1000");
3929 APFloat expected(APFloat::IEEEdouble(), "0.0");
3930 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3931 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3934 APFloat f1(APFloat::IEEEdouble(), "0.0");
3935 APFloat f2(APFloat::IEEEdouble(), "1.0");
3936 APFloat expected(APFloat::IEEEdouble(), "0.0");
3937 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3938 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3941 APFloat f1(APFloat::IEEEdouble(), "1.0");
3942 APFloat f2(APFloat::IEEEdouble(), "0.0");
3943 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3944 EXPECT_TRUE(f1.isNaN());
3947 APFloat f1(APFloat::IEEEdouble(), "0.0");
3948 APFloat f2(APFloat::IEEEdouble(), "0.0");
3949 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3950 EXPECT_TRUE(f1.isNaN());
3953 APFloat f1 = APFloat::getInf(APFloat::IEEEdouble(), false);
3954 APFloat f2(APFloat::IEEEdouble(), "1.0");
3955 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3956 EXPECT_TRUE(f1.isNaN());
3959 APFloat f1(APFloat::IEEEdouble(), "-4.0");
3960 APFloat f2(APFloat::IEEEdouble(), "-2.0");
3961 APFloat expected(APFloat::IEEEdouble(), "-0.0");
3962 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3963 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3966 APFloat f1(APFloat::IEEEdouble(), "-4.0");
3967 APFloat f2(APFloat::IEEEdouble(), "2.0");
3968 APFloat expected(APFloat::IEEEdouble(), "-0.0");
3969 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3970 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3973 // Test E4M3FN mod where the LHS exponent is maxExponent (8) and the RHS is
3974 // the max value whose exponent is minExponent (-6). This requires special
3975 // logic in the mod implementation to prevent overflow to NaN.
3976 APFloat f1(APFloat::Float8E4M3FN(), "0x1p8"); // 256
3977 APFloat f2(APFloat::Float8E4M3FN(), "0x1.ep-6"); // 0.029296875
3978 APFloat expected(APFloat::Float8E4M3FN(), "0x1p-8"); // 0.00390625
3979 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3980 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3984 TEST(APFloatTest, remainder) {
3985 // Test Special Cases against each other and normal values.
3987 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
3988 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
3989 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
3990 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
3991 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
3992 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
3993 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
3994 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
3995 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
3996 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
3997 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
3998 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
3999 APFloat PSmallestNormalized =
4000 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
4001 APFloat MSmallestNormalized =
4002 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
4004 APFloat PVal1(APFloat::IEEEsingle(), "0x1.fffffep+126");
4005 APFloat MVal1(APFloat::IEEEsingle(), "-0x1.fffffep+126");
4006 APFloat PVal2(APFloat::IEEEsingle(), "0x1.fffffep-126");
4007 APFloat MVal2(APFloat::IEEEsingle(), "-0x1.fffffep-126");
4008 APFloat PVal3(APFloat::IEEEsingle(), "0x1p-125");
4009 APFloat MVal3(APFloat::IEEEsingle(), "-0x1p-125");
4010 APFloat PVal4(APFloat::IEEEsingle(), "0x1p+127");
4011 APFloat MVal4(APFloat::IEEEsingle(), "-0x1p+127");
4012 APFloat PVal5(APFloat::IEEEsingle(), "1.5");
4013 APFloat MVal5(APFloat::IEEEsingle(), "-1.5");
4014 APFloat PVal6(APFloat::IEEEsingle(), "1");
4015 APFloat MVal6(APFloat::IEEEsingle(), "-1");
4017 struct {
4018 APFloat x;
4019 APFloat y;
4020 const char *result;
4021 int status;
4022 int category;
4023 } SpecialCaseTests[] = {
4024 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4025 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4026 { PInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4027 { PInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4028 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4029 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4030 { PInf, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4031 { PInf, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4032 { PInf, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4033 { PInf, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4034 { PInf, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4035 { PInf, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4036 { PInf, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4037 { PInf, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4038 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4039 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4040 { MInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4041 { MInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4042 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4043 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4044 { MInf, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4045 { MInf, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4046 { MInf, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4047 { MInf, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4048 { MInf, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4049 { MInf, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4050 { MInf, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4051 { MInf, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4052 { PZero, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4053 { PZero, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4054 { PZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4055 { PZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4056 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4057 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4058 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4059 { PZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4060 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4061 { PZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4062 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4063 { PZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4064 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4065 { PZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4066 { MZero, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4067 { MZero, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4068 { MZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4069 { MZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4070 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4071 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4072 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4073 { MZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4074 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4075 { MZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4076 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4077 { MZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4078 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4079 { MZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4080 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
4081 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
4082 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
4083 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
4084 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4085 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4086 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
4087 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
4088 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
4089 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
4090 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
4091 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
4092 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
4093 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
4094 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4095 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4096 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4097 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4098 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4099 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4100 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4101 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4102 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4103 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4104 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4105 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4106 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4107 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4108 { PNormalValue, PInf, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
4109 { PNormalValue, MInf, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
4110 { PNormalValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4111 { PNormalValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4112 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4113 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4114 { PNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4115 { PNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4116 { PNormalValue, PLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
4117 { PNormalValue, MLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
4118 { PNormalValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4119 { PNormalValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4120 { PNormalValue, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4121 { PNormalValue, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4122 { MNormalValue, PInf, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4123 { MNormalValue, MInf, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4124 { MNormalValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4125 { MNormalValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4126 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4127 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4128 { MNormalValue, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4129 { MNormalValue, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4130 { MNormalValue, PLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4131 { MNormalValue, MLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4132 { MNormalValue, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4133 { MNormalValue, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4134 { MNormalValue, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4135 { MNormalValue, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4136 { PLargestValue, PInf, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
4137 { PLargestValue, MInf, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
4138 { PLargestValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4139 { PLargestValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4140 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4141 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4142 { PLargestValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4143 { PLargestValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4144 { PLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4145 { PLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4146 { PLargestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4147 { PLargestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4148 { PLargestValue, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4149 { PLargestValue, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4150 { MLargestValue, PInf, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
4151 { MLargestValue, MInf, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
4152 { MLargestValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4153 { MLargestValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4154 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4155 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4156 { MLargestValue, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4157 { MLargestValue, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4158 { MLargestValue, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4159 { MLargestValue, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4160 { MLargestValue, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4161 { MLargestValue, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4162 { MLargestValue, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4163 { MLargestValue, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4164 { PSmallestValue, PInf, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
4165 { PSmallestValue, MInf, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
4166 { PSmallestValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4167 { PSmallestValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4168 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4169 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4170 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
4171 { PSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
4172 { PSmallestValue, PLargestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
4173 { PSmallestValue, MLargestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
4174 { PSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4175 { PSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4176 { PSmallestValue, PSmallestNormalized, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
4177 { PSmallestValue, MSmallestNormalized, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
4178 { MSmallestValue, PInf, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
4179 { MSmallestValue, MInf, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
4180 { MSmallestValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4181 { MSmallestValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4182 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4183 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4184 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
4185 { MSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
4186 { MSmallestValue, PLargestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
4187 { MSmallestValue, MLargestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
4188 { MSmallestValue, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4189 { MSmallestValue, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4190 { MSmallestValue, PSmallestNormalized, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
4191 { MSmallestValue, MSmallestNormalized, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
4192 { PSmallestNormalized, PInf, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
4193 { PSmallestNormalized, MInf, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
4194 { PSmallestNormalized, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4195 { PSmallestNormalized, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4196 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4197 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4198 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
4199 { PSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
4200 { PSmallestNormalized, PLargestValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
4201 { PSmallestNormalized, MLargestValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
4202 { PSmallestNormalized, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4203 { PSmallestNormalized, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4204 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4205 { PSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4206 { MSmallestNormalized, PInf, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
4207 { MSmallestNormalized, MInf, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
4208 { MSmallestNormalized, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4209 { MSmallestNormalized, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
4210 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
4211 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
4212 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
4213 { MSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
4214 { MSmallestNormalized, PLargestValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
4215 { MSmallestNormalized, MLargestValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
4216 { MSmallestNormalized, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4217 { MSmallestNormalized, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4218 { MSmallestNormalized, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4219 { MSmallestNormalized, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4221 { PVal1, PVal1, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4222 { PVal1, MVal1, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4223 { PVal1, PVal2, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4224 { PVal1, MVal2, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4225 { PVal1, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4226 { PVal1, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4227 { PVal1, PVal4, "-0x1p+103", APFloat::opOK, APFloat::fcNormal },
4228 { PVal1, MVal4, "-0x1p+103", APFloat::opOK, APFloat::fcNormal },
4229 { PVal1, PVal5, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4230 { PVal1, MVal5, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4231 { PVal1, PVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4232 { PVal1, MVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4233 { MVal1, PVal1, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4234 { MVal1, MVal1, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4235 { MVal1, PVal2, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4236 { MVal1, MVal2, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4237 { MVal1, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4238 { MVal1, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4239 { MVal1, PVal4, "0x1p+103", APFloat::opOK, APFloat::fcNormal },
4240 { MVal1, MVal4, "0x1p+103", APFloat::opOK, APFloat::fcNormal },
4241 { MVal1, PVal5, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4242 { MVal1, MVal5, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4243 { MVal1, PVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4244 { MVal1, MVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4245 { PVal2, PVal1, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4246 { PVal2, MVal1, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4247 { PVal2, PVal2, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4248 { PVal2, MVal2, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4249 { PVal2, PVal3, "-0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
4250 { PVal2, MVal3, "-0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
4251 { PVal2, PVal4, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4252 { PVal2, MVal4, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4253 { PVal2, PVal5, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4254 { PVal2, MVal5, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4255 { PVal2, PVal6, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4256 { PVal2, MVal6, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4257 { MVal2, PVal1, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4258 { MVal2, MVal1, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4259 { MVal2, PVal2, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4260 { MVal2, MVal2, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4261 { MVal2, PVal3, "0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
4262 { MVal2, MVal3, "0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
4263 { MVal2, PVal4, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4264 { MVal2, MVal4, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4265 { MVal2, PVal5, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4266 { MVal2, MVal5, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4267 { MVal2, PVal6, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4268 { MVal2, MVal6, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
4269 { PVal3, PVal1, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
4270 { PVal3, MVal1, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
4271 { PVal3, PVal2, "0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
4272 { PVal3, MVal2, "0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
4273 { PVal3, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4274 { PVal3, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4275 { PVal3, PVal4, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
4276 { PVal3, MVal4, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
4277 { PVal3, PVal5, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
4278 { PVal3, MVal5, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
4279 { PVal3, PVal6, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
4280 { PVal3, MVal6, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
4281 { MVal3, PVal1, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
4282 { MVal3, MVal1, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
4283 { MVal3, PVal2, "-0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
4284 { MVal3, MVal2, "-0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
4285 { MVal3, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4286 { MVal3, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4287 { MVal3, PVal4, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
4288 { MVal3, MVal4, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
4289 { MVal3, PVal5, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
4290 { MVal3, MVal5, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
4291 { MVal3, PVal6, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
4292 { MVal3, MVal6, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
4293 { PVal4, PVal1, "0x1p+103", APFloat::opOK, APFloat::fcNormal },
4294 { PVal4, MVal1, "0x1p+103", APFloat::opOK, APFloat::fcNormal },
4295 { PVal4, PVal2, "0x0.002p-126", APFloat::opOK, APFloat::fcNormal },
4296 { PVal4, MVal2, "0x0.002p-126", APFloat::opOK, APFloat::fcNormal },
4297 { PVal4, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4298 { PVal4, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4299 { PVal4, PVal4, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4300 { PVal4, MVal4, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4301 { PVal4, PVal5, "0.5", APFloat::opOK, APFloat::fcNormal },
4302 { PVal4, MVal5, "0.5", APFloat::opOK, APFloat::fcNormal },
4303 { PVal4, PVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4304 { PVal4, MVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4305 { MVal4, PVal1, "-0x1p+103", APFloat::opOK, APFloat::fcNormal },
4306 { MVal4, MVal1, "-0x1p+103", APFloat::opOK, APFloat::fcNormal },
4307 { MVal4, PVal2, "-0x0.002p-126", APFloat::opOK, APFloat::fcNormal },
4308 { MVal4, MVal2, "-0x0.002p-126", APFloat::opOK, APFloat::fcNormal },
4309 { MVal4, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4310 { MVal4, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4311 { MVal4, PVal4, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4312 { MVal4, MVal4, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4313 { MVal4, PVal5, "-0.5", APFloat::opOK, APFloat::fcNormal },
4314 { MVal4, MVal5, "-0.5", APFloat::opOK, APFloat::fcNormal },
4315 { MVal4, PVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4316 { MVal4, MVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4317 { PVal5, PVal1, "1.5", APFloat::opOK, APFloat::fcNormal },
4318 { PVal5, MVal1, "1.5", APFloat::opOK, APFloat::fcNormal },
4319 { PVal5, PVal2, "0x0.00006p-126", APFloat::opOK, APFloat::fcNormal },
4320 { PVal5, MVal2, "0x0.00006p-126", APFloat::opOK, APFloat::fcNormal },
4321 { PVal5, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4322 { PVal5, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4323 { PVal5, PVal4, "1.5", APFloat::opOK, APFloat::fcNormal },
4324 { PVal5, MVal4, "1.5", APFloat::opOK, APFloat::fcNormal },
4325 { PVal5, PVal5, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4326 { PVal5, MVal5, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4327 { PVal5, PVal6, "-0.5", APFloat::opOK, APFloat::fcNormal },
4328 { PVal5, MVal6, "-0.5", APFloat::opOK, APFloat::fcNormal },
4329 { MVal5, PVal1, "-1.5", APFloat::opOK, APFloat::fcNormal },
4330 { MVal5, MVal1, "-1.5", APFloat::opOK, APFloat::fcNormal },
4331 { MVal5, PVal2, "-0x0.00006p-126", APFloat::opOK, APFloat::fcNormal },
4332 { MVal5, MVal2, "-0x0.00006p-126", APFloat::opOK, APFloat::fcNormal },
4333 { MVal5, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4334 { MVal5, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4335 { MVal5, PVal4, "-1.5", APFloat::opOK, APFloat::fcNormal },
4336 { MVal5, MVal4, "-1.5", APFloat::opOK, APFloat::fcNormal },
4337 { MVal5, PVal5, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4338 { MVal5, MVal5, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4339 { MVal5, PVal6, "0.5", APFloat::opOK, APFloat::fcNormal },
4340 { MVal5, MVal6, "0.5", APFloat::opOK, APFloat::fcNormal },
4341 { PVal6, PVal1, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
4342 { PVal6, MVal1, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
4343 { PVal6, PVal2, "0x0.00004p-126", APFloat::opOK, APFloat::fcNormal },
4344 { PVal6, MVal2, "0x0.00004p-126", APFloat::opOK, APFloat::fcNormal },
4345 { PVal6, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4346 { PVal6, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4347 { PVal6, PVal4, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
4348 { PVal6, MVal4, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
4349 { PVal6, PVal5, "-0.5", APFloat::opOK, APFloat::fcNormal },
4350 { PVal6, MVal5, "-0.5", APFloat::opOK, APFloat::fcNormal },
4351 { PVal6, PVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4352 { PVal6, MVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
4353 { MVal6, PVal1, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4354 { MVal6, MVal1, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4355 { MVal6, PVal2, "-0x0.00004p-126", APFloat::opOK, APFloat::fcNormal },
4356 { MVal6, MVal2, "-0x0.00004p-126", APFloat::opOK, APFloat::fcNormal },
4357 { MVal6, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4358 { MVal6, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4359 { MVal6, PVal4, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4360 { MVal6, MVal4, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4361 { MVal6, PVal5, "0.5", APFloat::opOK, APFloat::fcNormal },
4362 { MVal6, MVal5, "0.5", APFloat::opOK, APFloat::fcNormal },
4363 { MVal6, PVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4364 { MVal6, MVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4367 for (size_t i = 0; i < std::size(SpecialCaseTests); ++i) {
4368 APFloat x(SpecialCaseTests[i].x);
4369 APFloat y(SpecialCaseTests[i].y);
4370 APFloat::opStatus status = x.remainder(y);
4372 APFloat result(x.getSemantics(), SpecialCaseTests[i].result);
4374 EXPECT_TRUE(result.bitwiseIsEqual(x));
4375 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
4376 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
4380 APFloat f1(APFloat::IEEEdouble(), "0x1.3333333333333p-2"); // 0.3
4381 APFloat f2(APFloat::IEEEdouble(), "0x1.47ae147ae147bp-7"); // 0.01
4382 APFloat expected(APFloat::IEEEdouble(), "-0x1.4p-56");
4383 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4384 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4387 APFloat f1(APFloat::IEEEdouble(), "0x1p64"); // 1.8446744073709552e19
4388 APFloat f2(APFloat::IEEEdouble(), "1.5");
4389 APFloat expected(APFloat::IEEEdouble(), "-0.5");
4390 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4391 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4394 APFloat f1(APFloat::IEEEdouble(), "0x1p1000");
4395 APFloat f2(APFloat::IEEEdouble(), "0x1p-1000");
4396 APFloat expected(APFloat::IEEEdouble(), "0.0");
4397 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4398 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4401 APFloat f1 = APFloat::getInf(APFloat::IEEEdouble(), false);
4402 APFloat f2(APFloat::IEEEdouble(), "1.0");
4403 EXPECT_EQ(f1.remainder(f2), APFloat::opInvalidOp);
4404 EXPECT_TRUE(f1.isNaN());
4407 APFloat f1(APFloat::IEEEdouble(), "-4.0");
4408 APFloat f2(APFloat::IEEEdouble(), "-2.0");
4409 APFloat expected(APFloat::IEEEdouble(), "-0.0");
4410 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4411 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4414 APFloat f1(APFloat::IEEEdouble(), "-4.0");
4415 APFloat f2(APFloat::IEEEdouble(), "2.0");
4416 APFloat expected(APFloat::IEEEdouble(), "-0.0");
4417 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4418 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4422 TEST(APFloatTest, PPCDoubleDoubleAddSpecial) {
4423 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t,
4424 APFloat::fltCategory, APFloat::roundingMode>;
4425 DataType Data[] = {
4426 // (1 + 0) + (-1 + 0) = fcZero
4427 std::make_tuple(0x3ff0000000000000ull, 0, 0xbff0000000000000ull, 0,
4428 APFloat::fcZero, APFloat::rmNearestTiesToEven),
4429 // LDBL_MAX + (1.1 >> (1023 - 106) + 0)) = fcInfinity
4430 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4431 0x7948000000000000ull, 0ull, APFloat::fcInfinity,
4432 APFloat::rmNearestTiesToEven),
4433 // TODO: change the 4th 0x75effffffffffffe to 0x75efffffffffffff when
4434 // semPPCDoubleDoubleLegacy is gone.
4435 // LDBL_MAX + (1.011111... >> (1023 - 106) + (1.1111111...0 >> (1023 -
4436 // 160))) = fcNormal
4437 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4438 0x7947ffffffffffffull, 0x75effffffffffffeull,
4439 APFloat::fcNormal, APFloat::rmNearestTiesToEven),
4440 // LDBL_MAX + (1.1 >> (1023 - 106) + 0)) = fcInfinity
4441 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4442 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4443 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
4444 // NaN + (1 + 0) = fcNaN
4445 std::make_tuple(0x7ff8000000000000ull, 0, 0x3ff0000000000000ull, 0,
4446 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
4449 for (auto Tp : Data) {
4450 uint64_t Op1[2], Op2[2];
4451 APFloat::fltCategory Expected;
4452 APFloat::roundingMode RM;
4453 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected, RM) = Tp;
4456 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4457 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4458 A1.add(A2, RM);
4460 EXPECT_EQ(Expected, A1.getCategory())
4461 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
4462 Op2[0], Op2[1])
4463 .str();
4466 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4467 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4468 A2.add(A1, RM);
4470 EXPECT_EQ(Expected, A2.getCategory())
4471 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
4472 Op1[0], Op1[1])
4473 .str();
4478 TEST(APFloatTest, PPCDoubleDoubleAdd) {
4479 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
4480 uint64_t, APFloat::roundingMode>;
4481 DataType Data[] = {
4482 // (1 + 0) + (1e-105 + 0) = (1 + 1e-105)
4483 std::make_tuple(0x3ff0000000000000ull, 0, 0x3960000000000000ull, 0,
4484 0x3ff0000000000000ull, 0x3960000000000000ull,
4485 APFloat::rmNearestTiesToEven),
4486 // (1 + 0) + (1e-106 + 0) = (1 + 1e-106)
4487 std::make_tuple(0x3ff0000000000000ull, 0, 0x3950000000000000ull, 0,
4488 0x3ff0000000000000ull, 0x3950000000000000ull,
4489 APFloat::rmNearestTiesToEven),
4490 // (1 + 1e-106) + (1e-106 + 0) = (1 + 1e-105)
4491 std::make_tuple(0x3ff0000000000000ull, 0x3950000000000000ull,
4492 0x3950000000000000ull, 0, 0x3ff0000000000000ull,
4493 0x3960000000000000ull, APFloat::rmNearestTiesToEven),
4494 // (1 + 0) + (epsilon + 0) = (1 + epsilon)
4495 std::make_tuple(0x3ff0000000000000ull, 0, 0x0000000000000001ull, 0,
4496 0x3ff0000000000000ull, 0x0000000000000001ull,
4497 APFloat::rmNearestTiesToEven),
4498 // TODO: change 0xf950000000000000 to 0xf940000000000000, when
4499 // semPPCDoubleDoubleLegacy is gone.
4500 // (DBL_MAX - 1 << (1023 - 105)) + (1 << (1023 - 53) + 0) = DBL_MAX +
4501 // 1.11111... << (1023 - 52)
4502 std::make_tuple(0x7fefffffffffffffull, 0xf950000000000000ull,
4503 0x7c90000000000000ull, 0, 0x7fefffffffffffffull,
4504 0x7c8ffffffffffffeull, APFloat::rmNearestTiesToEven),
4505 // TODO: change 0xf950000000000000 to 0xf940000000000000, when
4506 // semPPCDoubleDoubleLegacy is gone.
4507 // (1 << (1023 - 53) + 0) + (DBL_MAX - 1 << (1023 - 105)) = DBL_MAX +
4508 // 1.11111... << (1023 - 52)
4509 std::make_tuple(0x7c90000000000000ull, 0, 0x7fefffffffffffffull,
4510 0xf950000000000000ull, 0x7fefffffffffffffull,
4511 0x7c8ffffffffffffeull, APFloat::rmNearestTiesToEven),
4514 for (auto Tp : Data) {
4515 uint64_t Op1[2], Op2[2], Expected[2];
4516 APFloat::roundingMode RM;
4517 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
4520 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4521 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4522 A1.add(A2, RM);
4524 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4525 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
4526 Op2[0], Op2[1])
4527 .str();
4528 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4529 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
4530 Op2[0], Op2[1])
4531 .str();
4534 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4535 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4536 A2.add(A1, RM);
4538 EXPECT_EQ(Expected[0], A2.bitcastToAPInt().getRawData()[0])
4539 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
4540 Op1[0], Op1[1])
4541 .str();
4542 EXPECT_EQ(Expected[1], A2.bitcastToAPInt().getRawData()[1])
4543 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
4544 Op1[0], Op1[1])
4545 .str();
4550 TEST(APFloatTest, PPCDoubleDoubleSubtract) {
4551 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
4552 uint64_t, APFloat::roundingMode>;
4553 DataType Data[] = {
4554 // (1 + 0) - (-1e-105 + 0) = (1 + 1e-105)
4555 std::make_tuple(0x3ff0000000000000ull, 0, 0xb960000000000000ull, 0,
4556 0x3ff0000000000000ull, 0x3960000000000000ull,
4557 APFloat::rmNearestTiesToEven),
4558 // (1 + 0) - (-1e-106 + 0) = (1 + 1e-106)
4559 std::make_tuple(0x3ff0000000000000ull, 0, 0xb950000000000000ull, 0,
4560 0x3ff0000000000000ull, 0x3950000000000000ull,
4561 APFloat::rmNearestTiesToEven),
4564 for (auto Tp : Data) {
4565 uint64_t Op1[2], Op2[2], Expected[2];
4566 APFloat::roundingMode RM;
4567 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
4569 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4570 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4571 A1.subtract(A2, RM);
4573 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4574 << formatv("({0:x} + {1:x}) - ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4575 Op2[1])
4576 .str();
4577 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4578 << formatv("({0:x} + {1:x}) - ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4579 Op2[1])
4580 .str();
4584 TEST(APFloatTest, PPCDoubleDoubleMultiplySpecial) {
4585 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t,
4586 APFloat::fltCategory, APFloat::roundingMode>;
4587 DataType Data[] = {
4588 // fcNaN * fcNaN = fcNaN
4589 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0,
4590 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
4591 // fcNaN * fcZero = fcNaN
4592 std::make_tuple(0x7ff8000000000000ull, 0, 0, 0, APFloat::fcNaN,
4593 APFloat::rmNearestTiesToEven),
4594 // fcNaN * fcInfinity = fcNaN
4595 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff0000000000000ull, 0,
4596 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
4597 // fcNaN * fcNormal = fcNaN
4598 std::make_tuple(0x7ff8000000000000ull, 0, 0x3ff0000000000000ull, 0,
4599 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
4600 // fcInfinity * fcInfinity = fcInfinity
4601 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0,
4602 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
4603 // fcInfinity * fcZero = fcNaN
4604 std::make_tuple(0x7ff0000000000000ull, 0, 0, 0, APFloat::fcNaN,
4605 APFloat::rmNearestTiesToEven),
4606 // fcInfinity * fcNormal = fcInfinity
4607 std::make_tuple(0x7ff0000000000000ull, 0, 0x3ff0000000000000ull, 0,
4608 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
4609 // fcZero * fcZero = fcZero
4610 std::make_tuple(0, 0, 0, 0, APFloat::fcZero,
4611 APFloat::rmNearestTiesToEven),
4612 // fcZero * fcNormal = fcZero
4613 std::make_tuple(0, 0, 0x3ff0000000000000ull, 0, APFloat::fcZero,
4614 APFloat::rmNearestTiesToEven),
4617 for (auto Tp : Data) {
4618 uint64_t Op1[2], Op2[2];
4619 APFloat::fltCategory Expected;
4620 APFloat::roundingMode RM;
4621 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected, RM) = Tp;
4624 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4625 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4626 A1.multiply(A2, RM);
4628 EXPECT_EQ(Expected, A1.getCategory())
4629 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
4630 Op2[0], Op2[1])
4631 .str();
4634 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4635 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4636 A2.multiply(A1, RM);
4638 EXPECT_EQ(Expected, A2.getCategory())
4639 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
4640 Op1[0], Op1[1])
4641 .str();
4646 TEST(APFloatTest, PPCDoubleDoubleMultiply) {
4647 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
4648 uint64_t, APFloat::roundingMode>;
4649 DataType Data[] = {
4650 // 1/3 * 3 = 1.0
4651 std::make_tuple(0x3fd5555555555555ull, 0x3c75555555555556ull,
4652 0x4008000000000000ull, 0, 0x3ff0000000000000ull, 0,
4653 APFloat::rmNearestTiesToEven),
4654 // (1 + epsilon) * (1 + 0) = fcZero
4655 std::make_tuple(0x3ff0000000000000ull, 0x0000000000000001ull,
4656 0x3ff0000000000000ull, 0, 0x3ff0000000000000ull,
4657 0x0000000000000001ull, APFloat::rmNearestTiesToEven),
4658 // (1 + epsilon) * (1 + epsilon) = 1 + 2 * epsilon
4659 std::make_tuple(0x3ff0000000000000ull, 0x0000000000000001ull,
4660 0x3ff0000000000000ull, 0x0000000000000001ull,
4661 0x3ff0000000000000ull, 0x0000000000000002ull,
4662 APFloat::rmNearestTiesToEven),
4663 // -(1 + epsilon) * (1 + epsilon) = -1
4664 std::make_tuple(0xbff0000000000000ull, 0x0000000000000001ull,
4665 0x3ff0000000000000ull, 0x0000000000000001ull,
4666 0xbff0000000000000ull, 0, APFloat::rmNearestTiesToEven),
4667 // (0.5 + 0) * (1 + 2 * epsilon) = 0.5 + epsilon
4668 std::make_tuple(0x3fe0000000000000ull, 0, 0x3ff0000000000000ull,
4669 0x0000000000000002ull, 0x3fe0000000000000ull,
4670 0x0000000000000001ull, APFloat::rmNearestTiesToEven),
4671 // (0.5 + 0) * (1 + epsilon) = 0.5
4672 std::make_tuple(0x3fe0000000000000ull, 0, 0x3ff0000000000000ull,
4673 0x0000000000000001ull, 0x3fe0000000000000ull, 0,
4674 APFloat::rmNearestTiesToEven),
4675 // __LDBL_MAX__ * (1 + 1 << 106) = inf
4676 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4677 0x3ff0000000000000ull, 0x3950000000000000ull,
4678 0x7ff0000000000000ull, 0, APFloat::rmNearestTiesToEven),
4679 // __LDBL_MAX__ * (1 + 1 << 107) > __LDBL_MAX__, but not inf, yes =_=|||
4680 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4681 0x3ff0000000000000ull, 0x3940000000000000ull,
4682 0x7fefffffffffffffull, 0x7c8fffffffffffffull,
4683 APFloat::rmNearestTiesToEven),
4684 // __LDBL_MAX__ * (1 + 1 << 108) = __LDBL_MAX__
4685 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4686 0x3ff0000000000000ull, 0x3930000000000000ull,
4687 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4688 APFloat::rmNearestTiesToEven),
4691 for (auto Tp : Data) {
4692 uint64_t Op1[2], Op2[2], Expected[2];
4693 APFloat::roundingMode RM;
4694 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
4697 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4698 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4699 A1.multiply(A2, RM);
4701 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4702 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
4703 Op2[0], Op2[1])
4704 .str();
4705 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4706 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
4707 Op2[0], Op2[1])
4708 .str();
4711 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4712 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4713 A2.multiply(A1, RM);
4715 EXPECT_EQ(Expected[0], A2.bitcastToAPInt().getRawData()[0])
4716 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
4717 Op1[0], Op1[1])
4718 .str();
4719 EXPECT_EQ(Expected[1], A2.bitcastToAPInt().getRawData()[1])
4720 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
4721 Op1[0], Op1[1])
4722 .str();
4727 TEST(APFloatTest, PPCDoubleDoubleDivide) {
4728 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
4729 uint64_t, APFloat::roundingMode>;
4730 // TODO: Only a sanity check for now. Add more edge cases when the
4731 // double-double algorithm is implemented.
4732 DataType Data[] = {
4733 // 1 / 3 = 1/3
4734 std::make_tuple(0x3ff0000000000000ull, 0, 0x4008000000000000ull, 0,
4735 0x3fd5555555555555ull, 0x3c75555555555556ull,
4736 APFloat::rmNearestTiesToEven),
4739 for (auto Tp : Data) {
4740 uint64_t Op1[2], Op2[2], Expected[2];
4741 APFloat::roundingMode RM;
4742 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
4744 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4745 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4746 A1.divide(A2, RM);
4748 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4749 << formatv("({0:x} + {1:x}) / ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4750 Op2[1])
4751 .str();
4752 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4753 << formatv("({0:x} + {1:x}) / ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4754 Op2[1])
4755 .str();
4759 TEST(APFloatTest, PPCDoubleDoubleRemainder) {
4760 using DataType =
4761 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t, uint64_t>;
4762 DataType Data[] = {
4763 // remainder(3.0 + 3.0 << 53, 1.25 + 1.25 << 53) = (0.5 + 0.5 << 53)
4764 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
4765 0x3ff4000000000000ull, 0x3ca4000000000000ull,
4766 0x3fe0000000000000ull, 0x3c90000000000000ull),
4767 // remainder(3.0 + 3.0 << 53, 1.75 + 1.75 << 53) = (-0.5 - 0.5 << 53)
4768 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
4769 0x3ffc000000000000ull, 0x3cac000000000000ull,
4770 0xbfe0000000000000ull, 0xbc90000000000000ull),
4773 for (auto Tp : Data) {
4774 uint64_t Op1[2], Op2[2], Expected[2];
4775 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1]) = Tp;
4777 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4778 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4779 A1.remainder(A2);
4781 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4782 << formatv("remainder({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
4783 Op2[0], Op2[1])
4784 .str();
4785 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4786 << formatv("remainder(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0],
4787 Op1[1], Op2[0], Op2[1])
4788 .str();
4792 TEST(APFloatTest, PPCDoubleDoubleMod) {
4793 using DataType =
4794 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t, uint64_t>;
4795 DataType Data[] = {
4796 // mod(3.0 + 3.0 << 53, 1.25 + 1.25 << 53) = (0.5 + 0.5 << 53)
4797 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
4798 0x3ff4000000000000ull, 0x3ca4000000000000ull,
4799 0x3fe0000000000000ull, 0x3c90000000000000ull),
4800 // mod(3.0 + 3.0 << 53, 1.75 + 1.75 << 53) = (1.25 + 1.25 << 53)
4801 // 0xbc98000000000000 doesn't seem right, but it's what we currently have.
4802 // TODO: investigate
4803 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
4804 0x3ffc000000000000ull, 0x3cac000000000000ull,
4805 0x3ff4000000000001ull, 0xbc98000000000000ull),
4808 for (auto Tp : Data) {
4809 uint64_t Op1[2], Op2[2], Expected[2];
4810 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1]) = Tp;
4812 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4813 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4814 A1.mod(A2);
4816 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4817 << formatv("fmod(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
4818 Op2[0], Op2[1])
4819 .str();
4820 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4821 << formatv("fmod(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
4822 Op2[0], Op2[1])
4823 .str();
4827 TEST(APFloatTest, PPCDoubleDoubleFMA) {
4828 // Sanity check for now.
4829 APFloat A(APFloat::PPCDoubleDouble(), "2");
4830 A.fusedMultiplyAdd(APFloat(APFloat::PPCDoubleDouble(), "3"),
4831 APFloat(APFloat::PPCDoubleDouble(), "4"),
4832 APFloat::rmNearestTiesToEven);
4833 EXPECT_EQ(APFloat::cmpEqual,
4834 APFloat(APFloat::PPCDoubleDouble(), "10").compare(A));
4837 TEST(APFloatTest, PPCDoubleDoubleRoundToIntegral) {
4839 APFloat A(APFloat::PPCDoubleDouble(), "1.5");
4840 A.roundToIntegral(APFloat::rmNearestTiesToEven);
4841 EXPECT_EQ(APFloat::cmpEqual,
4842 APFloat(APFloat::PPCDoubleDouble(), "2").compare(A));
4845 APFloat A(APFloat::PPCDoubleDouble(), "2.5");
4846 A.roundToIntegral(APFloat::rmNearestTiesToEven);
4847 EXPECT_EQ(APFloat::cmpEqual,
4848 APFloat(APFloat::PPCDoubleDouble(), "2").compare(A));
4852 TEST(APFloatTest, PPCDoubleDoubleCompare) {
4853 using DataType =
4854 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, APFloat::cmpResult>;
4856 DataType Data[] = {
4857 // (1 + 0) = (1 + 0)
4858 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000000ull, 0,
4859 APFloat::cmpEqual),
4860 // (1 + 0) < (1.00...1 + 0)
4861 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull, 0,
4862 APFloat::cmpLessThan),
4863 // (1.00...1 + 0) > (1 + 0)
4864 std::make_tuple(0x3ff0000000000001ull, 0, 0x3ff0000000000000ull, 0,
4865 APFloat::cmpGreaterThan),
4866 // (1 + 0) < (1 + epsilon)
4867 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull,
4868 0x0000000000000001ull, APFloat::cmpLessThan),
4869 // NaN != NaN
4870 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0,
4871 APFloat::cmpUnordered),
4872 // (1 + 0) != NaN
4873 std::make_tuple(0x3ff0000000000000ull, 0, 0x7ff8000000000000ull, 0,
4874 APFloat::cmpUnordered),
4875 // Inf = Inf
4876 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0,
4877 APFloat::cmpEqual),
4880 for (auto Tp : Data) {
4881 uint64_t Op1[2], Op2[2];
4882 APFloat::cmpResult Expected;
4883 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected) = Tp;
4885 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4886 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4887 EXPECT_EQ(Expected, A1.compare(A2))
4888 << formatv("compare(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
4889 Op2[0], Op2[1])
4890 .str();
4894 TEST(APFloatTest, PPCDoubleDoubleBitwiseIsEqual) {
4895 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, bool>;
4897 DataType Data[] = {
4898 // (1 + 0) = (1 + 0)
4899 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000000ull, 0, true),
4900 // (1 + 0) != (1.00...1 + 0)
4901 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull, 0,
4902 false),
4903 // NaN = NaN
4904 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0, true),
4905 // NaN != NaN with a different bit pattern
4906 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull,
4907 0x3ff0000000000000ull, false),
4908 // Inf = Inf
4909 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0, true),
4912 for (auto Tp : Data) {
4913 uint64_t Op1[2], Op2[2];
4914 bool Expected;
4915 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected) = Tp;
4917 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4918 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4919 EXPECT_EQ(Expected, A1.bitwiseIsEqual(A2))
4920 << formatv("({0:x} + {1:x}) = ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4921 Op2[1])
4922 .str();
4926 TEST(APFloatTest, PPCDoubleDoubleHashValue) {
4927 uint64_t Data1[] = {0x3ff0000000000001ull, 0x0000000000000001ull};
4928 uint64_t Data2[] = {0x3ff0000000000001ull, 0};
4929 // The hash values are *hopefully* different.
4930 EXPECT_NE(
4931 hash_value(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data1))),
4932 hash_value(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data2))));
4935 TEST(APFloatTest, PPCDoubleDoubleChangeSign) {
4936 uint64_t Data[] = {
4937 0x400f000000000000ull, 0xbcb0000000000000ull,
4939 APFloat Float(APFloat::PPCDoubleDouble(), APInt(128, 2, Data));
4941 APFloat Actual =
4942 APFloat::copySign(Float, APFloat(APFloat::IEEEdouble(), "1"));
4943 EXPECT_EQ(0x400f000000000000ull, Actual.bitcastToAPInt().getRawData()[0]);
4944 EXPECT_EQ(0xbcb0000000000000ull, Actual.bitcastToAPInt().getRawData()[1]);
4947 APFloat Actual =
4948 APFloat::copySign(Float, APFloat(APFloat::IEEEdouble(), "-1"));
4949 EXPECT_EQ(0xc00f000000000000ull, Actual.bitcastToAPInt().getRawData()[0]);
4950 EXPECT_EQ(0x3cb0000000000000ull, Actual.bitcastToAPInt().getRawData()[1]);
4954 TEST(APFloatTest, PPCDoubleDoubleFactories) {
4956 uint64_t Data[] = {
4957 0, 0,
4959 EXPECT_EQ(APInt(128, 2, Data),
4960 APFloat::getZero(APFloat::PPCDoubleDouble()).bitcastToAPInt());
4963 uint64_t Data[] = {
4964 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4966 EXPECT_EQ(APInt(128, 2, Data),
4967 APFloat::getLargest(APFloat::PPCDoubleDouble()).bitcastToAPInt());
4970 uint64_t Data[] = {
4971 0x0000000000000001ull, 0,
4973 EXPECT_EQ(
4974 APInt(128, 2, Data),
4975 APFloat::getSmallest(APFloat::PPCDoubleDouble()).bitcastToAPInt());
4978 uint64_t Data[] = {0x0360000000000000ull, 0};
4979 EXPECT_EQ(APInt(128, 2, Data),
4980 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble())
4981 .bitcastToAPInt());
4984 uint64_t Data[] = {
4985 0x8000000000000000ull, 0x0000000000000000ull,
4987 EXPECT_EQ(
4988 APInt(128, 2, Data),
4989 APFloat::getZero(APFloat::PPCDoubleDouble(), true).bitcastToAPInt());
4992 uint64_t Data[] = {
4993 0xffefffffffffffffull, 0xfc8ffffffffffffeull,
4995 EXPECT_EQ(
4996 APInt(128, 2, Data),
4997 APFloat::getLargest(APFloat::PPCDoubleDouble(), true).bitcastToAPInt());
5000 uint64_t Data[] = {
5001 0x8000000000000001ull, 0x0000000000000000ull,
5003 EXPECT_EQ(APInt(128, 2, Data),
5004 APFloat::getSmallest(APFloat::PPCDoubleDouble(), true)
5005 .bitcastToAPInt());
5008 uint64_t Data[] = {
5009 0x8360000000000000ull, 0x0000000000000000ull,
5011 EXPECT_EQ(APInt(128, 2, Data),
5012 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble(), true)
5013 .bitcastToAPInt());
5015 EXPECT_TRUE(APFloat::getSmallest(APFloat::PPCDoubleDouble()).isSmallest());
5016 EXPECT_TRUE(APFloat::getLargest(APFloat::PPCDoubleDouble()).isLargest());
5019 TEST(APFloatTest, PPCDoubleDoubleIsDenormal) {
5020 EXPECT_TRUE(APFloat::getSmallest(APFloat::PPCDoubleDouble()).isDenormal());
5021 EXPECT_FALSE(APFloat::getLargest(APFloat::PPCDoubleDouble()).isDenormal());
5022 EXPECT_FALSE(
5023 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble()).isDenormal());
5025 // (4 + 3) is not normalized
5026 uint64_t Data[] = {
5027 0x4010000000000000ull, 0x4008000000000000ull,
5029 EXPECT_TRUE(
5030 APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data)).isDenormal());
5034 TEST(APFloatTest, PPCDoubleDoubleScalbn) {
5035 // 3.0 + 3.0 << 53
5036 uint64_t Input[] = {
5037 0x4008000000000000ull, 0x3cb8000000000000ull,
5039 APFloat Result =
5040 scalbn(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Input)), 1,
5041 APFloat::rmNearestTiesToEven);
5042 // 6.0 + 6.0 << 53
5043 EXPECT_EQ(0x4018000000000000ull, Result.bitcastToAPInt().getRawData()[0]);
5044 EXPECT_EQ(0x3cc8000000000000ull, Result.bitcastToAPInt().getRawData()[1]);
5047 TEST(APFloatTest, PPCDoubleDoubleFrexp) {
5048 // 3.0 + 3.0 << 53
5049 uint64_t Input[] = {
5050 0x4008000000000000ull, 0x3cb8000000000000ull,
5052 int Exp;
5053 // 0.75 + 0.75 << 53
5054 APFloat Result =
5055 frexp(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Input)), Exp,
5056 APFloat::rmNearestTiesToEven);
5057 EXPECT_EQ(2, Exp);
5058 EXPECT_EQ(0x3fe8000000000000ull, Result.bitcastToAPInt().getRawData()[0]);
5059 EXPECT_EQ(0x3c98000000000000ull, Result.bitcastToAPInt().getRawData()[1]);
5062 TEST(APFloatTest, x87Largest) {
5063 APFloat MaxX87Val = APFloat::getLargest(APFloat::x87DoubleExtended());
5064 EXPECT_TRUE(MaxX87Val.isLargest());
5067 TEST(APFloatTest, x87Next) {
5068 APFloat F(APFloat::x87DoubleExtended(), "-1.0");
5069 F.next(false);
5070 EXPECT_TRUE(ilogb(F) == -1);
5073 TEST(APFloatTest, Float8ExhaustivePair) {
5074 // Test each pair of 8-bit floats with non-standard semantics
5075 for (APFloat::Semantics Sem :
5076 {APFloat::S_Float8E4M3FN, APFloat::S_Float8E5M2FNUZ,
5077 APFloat::S_Float8E4M3FNUZ, APFloat::S_Float8E4M3B11FNUZ}) {
5078 const llvm::fltSemantics &S = APFloat::EnumToSemantics(Sem);
5079 for (int i = 0; i < 256; i++) {
5080 for (int j = 0; j < 256; j++) {
5081 SCOPED_TRACE("sem=" + std::to_string(Sem) + ",i=" + std::to_string(i) +
5082 ",j=" + std::to_string(j));
5083 APFloat x(S, APInt(8, i));
5084 APFloat y(S, APInt(8, j));
5086 bool losesInfo;
5087 APFloat x16 = x;
5088 x16.convert(APFloat::IEEEhalf(), APFloat::rmNearestTiesToEven,
5089 &losesInfo);
5090 EXPECT_FALSE(losesInfo);
5091 APFloat y16 = y;
5092 y16.convert(APFloat::IEEEhalf(), APFloat::rmNearestTiesToEven,
5093 &losesInfo);
5094 EXPECT_FALSE(losesInfo);
5096 // Add
5097 APFloat z = x;
5098 z.add(y, APFloat::rmNearestTiesToEven);
5099 APFloat z16 = x16;
5100 z16.add(y16, APFloat::rmNearestTiesToEven);
5101 z16.convert(S, APFloat::rmNearestTiesToEven, &losesInfo);
5102 EXPECT_TRUE(z.bitwiseIsEqual(z16))
5103 << "sem=" << Sem << ", i=" << i << ", j=" << j;
5105 // Subtract
5106 z = x;
5107 z.subtract(y, APFloat::rmNearestTiesToEven);
5108 z16 = x16;
5109 z16.subtract(y16, APFloat::rmNearestTiesToEven);
5110 z16.convert(S, APFloat::rmNearestTiesToEven, &losesInfo);
5111 EXPECT_TRUE(z.bitwiseIsEqual(z16))
5112 << "sem=" << Sem << ", i=" << i << ", j=" << j;
5114 // Multiply
5115 z = x;
5116 z.multiply(y, APFloat::rmNearestTiesToEven);
5117 z16 = x16;
5118 z16.multiply(y16, APFloat::rmNearestTiesToEven);
5119 z16.convert(S, APFloat::rmNearestTiesToEven, &losesInfo);
5120 EXPECT_TRUE(z.bitwiseIsEqual(z16))
5121 << "sem=" << Sem << ", i=" << i << ", j=" << j;
5123 // Divide
5124 z = x;
5125 z.divide(y, APFloat::rmNearestTiesToEven);
5126 z16 = x16;
5127 z16.divide(y16, APFloat::rmNearestTiesToEven);
5128 z16.convert(S, APFloat::rmNearestTiesToEven, &losesInfo);
5129 EXPECT_TRUE(z.bitwiseIsEqual(z16))
5130 << "sem=" << Sem << ", i=" << i << ", j=" << j;
5132 // Mod
5133 z = x;
5134 z.mod(y);
5135 z16 = x16;
5136 z16.mod(y16);
5137 z16.convert(S, APFloat::rmNearestTiesToEven, &losesInfo);
5138 EXPECT_TRUE(z.bitwiseIsEqual(z16))
5139 << "sem=" << Sem << ", i=" << i << ", j=" << j;
5141 // Remainder
5142 z = x;
5143 z.remainder(y);
5144 z16 = x16;
5145 z16.remainder(y16);
5146 z16.convert(S, APFloat::rmNearestTiesToEven, &losesInfo);
5147 EXPECT_TRUE(z.bitwiseIsEqual(z16))
5148 << "sem=" << Sem << ", i=" << i << ", j=" << j;
5154 TEST(APFloatTest, ConvertE4M3FNToE5M2) {
5155 bool losesInfo;
5156 APFloat test(APFloat::Float8E4M3FN(), "1.0");
5157 APFloat::opStatus status = test.convert(
5158 APFloat::Float8E5M2(), APFloat::rmNearestTiesToEven, &losesInfo);
5159 EXPECT_EQ(1.0f, test.convertToFloat());
5160 EXPECT_FALSE(losesInfo);
5161 EXPECT_EQ(status, APFloat::opOK);
5163 test = APFloat(APFloat::Float8E4M3FN(), "0.0");
5164 status = test.convert(APFloat::Float8E5M2(), APFloat::rmNearestTiesToEven,
5165 &losesInfo);
5166 EXPECT_EQ(0.0f, test.convertToFloat());
5167 EXPECT_FALSE(losesInfo);
5168 EXPECT_EQ(status, APFloat::opOK);
5170 test = APFloat(APFloat::Float8E4M3FN(), "0x1.2p0"); // 1.125
5171 status = test.convert(APFloat::Float8E5M2(), APFloat::rmNearestTiesToEven,
5172 &losesInfo);
5173 EXPECT_EQ(0x1.0p0 /* 1.0 */, test.convertToFloat());
5174 EXPECT_TRUE(losesInfo);
5175 EXPECT_EQ(status, APFloat::opInexact);
5177 test = APFloat(APFloat::Float8E4M3FN(), "0x1.6p0"); // 1.375
5178 status = test.convert(APFloat::Float8E5M2(), APFloat::rmNearestTiesToEven,
5179 &losesInfo);
5180 EXPECT_EQ(0x1.8p0 /* 1.5 */, test.convertToFloat());
5181 EXPECT_TRUE(losesInfo);
5182 EXPECT_EQ(status, APFloat::opInexact);
5184 // Convert E4M3 denormal to E5M2 normal. Should not be truncated, despite the
5185 // destination format having one fewer significand bit
5186 test = APFloat(APFloat::Float8E4M3FN(), "0x1.Cp-7");
5187 status = test.convert(APFloat::Float8E5M2(), APFloat::rmNearestTiesToEven,
5188 &losesInfo);
5189 EXPECT_EQ(0x1.Cp-7, test.convertToFloat());
5190 EXPECT_FALSE(losesInfo);
5191 EXPECT_EQ(status, APFloat::opOK);
5193 // Test convert from NaN
5194 test = APFloat(APFloat::Float8E4M3FN(), "nan");
5195 status = test.convert(APFloat::Float8E5M2(), APFloat::rmNearestTiesToEven,
5196 &losesInfo);
5197 EXPECT_TRUE(std::isnan(test.convertToFloat()));
5198 EXPECT_FALSE(losesInfo);
5199 EXPECT_EQ(status, APFloat::opOK);
5202 TEST(APFloatTest, ConvertE5M2ToE4M3FN) {
5203 bool losesInfo;
5204 APFloat test(APFloat::Float8E5M2(), "1.0");
5205 APFloat::opStatus status = test.convert(
5206 APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven, &losesInfo);
5207 EXPECT_EQ(1.0f, test.convertToFloat());
5208 EXPECT_FALSE(losesInfo);
5209 EXPECT_EQ(status, APFloat::opOK);
5211 test = APFloat(APFloat::Float8E5M2(), "0.0");
5212 status = test.convert(APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven,
5213 &losesInfo);
5214 EXPECT_EQ(0.0f, test.convertToFloat());
5215 EXPECT_FALSE(losesInfo);
5216 EXPECT_EQ(status, APFloat::opOK);
5218 test = APFloat(APFloat::Float8E5M2(), "0x1.Cp8"); // 448
5219 status = test.convert(APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven,
5220 &losesInfo);
5221 EXPECT_EQ(0x1.Cp8 /* 448 */, test.convertToFloat());
5222 EXPECT_FALSE(losesInfo);
5223 EXPECT_EQ(status, APFloat::opOK);
5225 // Test overflow
5226 test = APFloat(APFloat::Float8E5M2(), "0x1.0p9"); // 512
5227 status = test.convert(APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven,
5228 &losesInfo);
5229 EXPECT_TRUE(std::isnan(test.convertToFloat()));
5230 EXPECT_TRUE(losesInfo);
5231 EXPECT_EQ(status, APFloat::opOverflow | APFloat::opInexact);
5233 // Test underflow
5234 test = APFloat(APFloat::Float8E5M2(), "0x1.0p-10");
5235 status = test.convert(APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven,
5236 &losesInfo);
5237 EXPECT_EQ(0., test.convertToFloat());
5238 EXPECT_TRUE(losesInfo);
5239 EXPECT_EQ(status, APFloat::opUnderflow | APFloat::opInexact);
5241 // Test rounding up to smallest denormal number
5242 test = APFloat(APFloat::Float8E5M2(), "0x1.8p-10");
5243 status = test.convert(APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven,
5244 &losesInfo);
5245 EXPECT_EQ(0x1.0p-9, test.convertToFloat());
5246 EXPECT_TRUE(losesInfo);
5247 EXPECT_EQ(status, APFloat::opUnderflow | APFloat::opInexact);
5249 // Testing inexact rounding to denormal number
5250 test = APFloat(APFloat::Float8E5M2(), "0x1.8p-9");
5251 status = test.convert(APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven,
5252 &losesInfo);
5253 EXPECT_EQ(0x1.0p-8, test.convertToFloat());
5254 EXPECT_TRUE(losesInfo);
5255 EXPECT_EQ(status, APFloat::opUnderflow | APFloat::opInexact);
5257 APFloat nan = APFloat(APFloat::Float8E4M3FN(), "nan");
5259 // Testing convert from Inf
5260 test = APFloat(APFloat::Float8E5M2(), "inf");
5261 status = test.convert(APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven,
5262 &losesInfo);
5263 EXPECT_TRUE(std::isnan(test.convertToFloat()));
5264 EXPECT_TRUE(losesInfo);
5265 EXPECT_EQ(status, APFloat::opInexact);
5266 EXPECT_TRUE(test.bitwiseIsEqual(nan));
5268 // Testing convert from quiet NaN
5269 test = APFloat(APFloat::Float8E5M2(), "nan");
5270 status = test.convert(APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven,
5271 &losesInfo);
5272 EXPECT_TRUE(std::isnan(test.convertToFloat()));
5273 EXPECT_TRUE(losesInfo);
5274 EXPECT_EQ(status, APFloat::opOK);
5275 EXPECT_TRUE(test.bitwiseIsEqual(nan));
5277 // Testing convert from signaling NaN
5278 test = APFloat(APFloat::Float8E5M2(), "snan");
5279 status = test.convert(APFloat::Float8E4M3FN(), APFloat::rmNearestTiesToEven,
5280 &losesInfo);
5281 EXPECT_TRUE(std::isnan(test.convertToFloat()));
5282 EXPECT_TRUE(losesInfo);
5283 EXPECT_EQ(status, APFloat::opInvalidOp);
5284 EXPECT_TRUE(test.bitwiseIsEqual(nan));
5287 TEST(APFloatTest, Float8E4M3FNGetInf) {
5288 APFloat t = APFloat::getInf(APFloat::Float8E4M3FN());
5289 EXPECT_TRUE(t.isNaN());
5290 EXPECT_FALSE(t.isInfinity());
5293 TEST(APFloatTest, Float8E4M3FNFromString) {
5294 // Exactly representable
5295 EXPECT_EQ(448, APFloat(APFloat::Float8E4M3FN(), "448").convertToDouble());
5296 // Round down to maximum value
5297 EXPECT_EQ(448, APFloat(APFloat::Float8E4M3FN(), "464").convertToDouble());
5298 // Round up, causing overflow to NaN
5299 EXPECT_TRUE(APFloat(APFloat::Float8E4M3FN(), "465").isNaN());
5300 // Overflow without rounding
5301 EXPECT_TRUE(APFloat(APFloat::Float8E4M3FN(), "480").isNaN());
5302 // Inf converted to NaN
5303 EXPECT_TRUE(APFloat(APFloat::Float8E4M3FN(), "inf").isNaN());
5304 // NaN converted to NaN
5305 EXPECT_TRUE(APFloat(APFloat::Float8E4M3FN(), "nan").isNaN());
5308 TEST(APFloatTest, Float8E4M3FNAdd) {
5309 APFloat QNaN = APFloat::getNaN(APFloat::Float8E4M3FN(), false);
5311 auto FromStr = [](StringRef S) {
5312 return APFloat(APFloat::Float8E4M3FN(), S);
5315 struct {
5316 APFloat x;
5317 APFloat y;
5318 const char *result;
5319 int status;
5320 int category;
5321 APFloat::roundingMode roundingMode = APFloat::rmNearestTiesToEven;
5322 } AdditionTests[] = {
5323 // Test addition operations involving NaN, overflow, and the max E4M3
5324 // value (448) because E4M3 differs from IEEE-754 types in these regards
5325 {FromStr("448"), FromStr("16"), "448", APFloat::opInexact,
5326 APFloat::fcNormal},
5327 {FromStr("448"), FromStr("18"), "NaN",
5328 APFloat::opOverflow | APFloat::opInexact, APFloat::fcNaN},
5329 {FromStr("448"), FromStr("32"), "NaN",
5330 APFloat::opOverflow | APFloat::opInexact, APFloat::fcNaN},
5331 {FromStr("-448"), FromStr("-32"), "-NaN",
5332 APFloat::opOverflow | APFloat::opInexact, APFloat::fcNaN},
5333 {QNaN, FromStr("-448"), "NaN", APFloat::opOK, APFloat::fcNaN},
5334 {FromStr("448"), FromStr("-32"), "416", APFloat::opOK, APFloat::fcNormal},
5335 {FromStr("448"), FromStr("0"), "448", APFloat::opOK, APFloat::fcNormal},
5336 {FromStr("448"), FromStr("32"), "448", APFloat::opInexact,
5337 APFloat::fcNormal, APFloat::rmTowardZero},
5338 {FromStr("448"), FromStr("448"), "448", APFloat::opInexact,
5339 APFloat::fcNormal, APFloat::rmTowardZero},
5342 for (size_t i = 0; i < std::size(AdditionTests); ++i) {
5343 APFloat x(AdditionTests[i].x);
5344 APFloat y(AdditionTests[i].y);
5345 APFloat::opStatus status = x.add(y, AdditionTests[i].roundingMode);
5347 APFloat result(APFloat::Float8E4M3FN(), AdditionTests[i].result);
5349 EXPECT_TRUE(result.bitwiseIsEqual(x));
5350 EXPECT_EQ(AdditionTests[i].status, (int)status);
5351 EXPECT_EQ(AdditionTests[i].category, (int)x.getCategory());
5355 TEST(APFloatTest, Float8E4M3FNDivideByZero) {
5356 APFloat x(APFloat::Float8E4M3FN(), "1");
5357 APFloat zero(APFloat::Float8E4M3FN(), "0");
5358 EXPECT_EQ(x.divide(zero, APFloat::rmNearestTiesToEven), APFloat::opDivByZero);
5359 EXPECT_TRUE(x.isNaN());
5362 TEST(APFloatTest, Float8E4M3FNNext) {
5363 APFloat test(APFloat::Float8E4M3FN(), APFloat::uninitialized);
5364 APFloat expected(APFloat::Float8E4M3FN(), APFloat::uninitialized);
5366 // nextUp on positive numbers
5367 for (int i = 0; i < 127; i++) {
5368 test = APFloat(APFloat::Float8E4M3FN(), APInt(8, i));
5369 expected = APFloat(APFloat::Float8E4M3FN(), APInt(8, i + 1));
5370 EXPECT_EQ(test.next(false), APFloat::opOK);
5371 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5374 // nextUp on negative zero
5375 test = APFloat::getZero(APFloat::Float8E4M3FN(), true);
5376 expected = APFloat::getSmallest(APFloat::Float8E4M3FN(), false);
5377 EXPECT_EQ(test.next(false), APFloat::opOK);
5378 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5380 // nextUp on negative nonzero numbers
5381 for (int i = 129; i < 255; i++) {
5382 test = APFloat(APFloat::Float8E4M3FN(), APInt(8, i));
5383 expected = APFloat(APFloat::Float8E4M3FN(), APInt(8, i - 1));
5384 EXPECT_EQ(test.next(false), APFloat::opOK);
5385 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5388 // nextUp on NaN
5389 test = APFloat::getQNaN(APFloat::Float8E4M3FN(), false);
5390 expected = APFloat::getQNaN(APFloat::Float8E4M3FN(), false);
5391 EXPECT_EQ(test.next(false), APFloat::opOK);
5392 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5394 // nextDown on positive nonzero finite numbers
5395 for (int i = 1; i < 127; i++) {
5396 test = APFloat(APFloat::Float8E4M3FN(), APInt(8, i));
5397 expected = APFloat(APFloat::Float8E4M3FN(), APInt(8, i - 1));
5398 EXPECT_EQ(test.next(true), APFloat::opOK);
5399 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5402 // nextDown on positive zero
5403 test = APFloat::getZero(APFloat::Float8E4M3FN(), true);
5404 expected = APFloat::getSmallest(APFloat::Float8E4M3FN(), true);
5405 EXPECT_EQ(test.next(true), APFloat::opOK);
5406 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5408 // nextDown on negative finite numbers
5409 for (int i = 128; i < 255; i++) {
5410 test = APFloat(APFloat::Float8E4M3FN(), APInt(8, i));
5411 expected = APFloat(APFloat::Float8E4M3FN(), APInt(8, i + 1));
5412 EXPECT_EQ(test.next(true), APFloat::opOK);
5413 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5416 // nextDown on NaN
5417 test = APFloat::getQNaN(APFloat::Float8E4M3FN(), false);
5418 expected = APFloat::getQNaN(APFloat::Float8E4M3FN(), false);
5419 EXPECT_EQ(test.next(true), APFloat::opOK);
5420 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5423 TEST(APFloatTest, Float8E4M3FNExhaustive) {
5424 // Test each of the 256 Float8E4M3FN values.
5425 for (int i = 0; i < 256; i++) {
5426 APFloat test(APFloat::Float8E4M3FN(), APInt(8, i));
5427 SCOPED_TRACE("i=" + std::to_string(i));
5429 // isLargest
5430 if (i == 126 || i == 254) {
5431 EXPECT_TRUE(test.isLargest());
5432 EXPECT_EQ(abs(test).convertToDouble(), 448.);
5433 } else {
5434 EXPECT_FALSE(test.isLargest());
5437 // isSmallest
5438 if (i == 1 || i == 129) {
5439 EXPECT_TRUE(test.isSmallest());
5440 EXPECT_EQ(abs(test).convertToDouble(), 0x1p-9);
5441 } else {
5442 EXPECT_FALSE(test.isSmallest());
5445 // convert to BFloat
5446 APFloat test2 = test;
5447 bool losesInfo;
5448 APFloat::opStatus status = test2.convert(
5449 APFloat::BFloat(), APFloat::rmNearestTiesToEven, &losesInfo);
5450 EXPECT_EQ(status, APFloat::opOK);
5451 EXPECT_FALSE(losesInfo);
5452 if (i == 127 || i == 255)
5453 EXPECT_TRUE(test2.isNaN());
5454 else
5455 EXPECT_EQ(test.convertToFloat(), test2.convertToFloat());
5457 // bitcastToAPInt
5458 EXPECT_EQ(i, test.bitcastToAPInt());
5462 TEST(APFloatTest, Float8E5M2FNUZNext) {
5463 APFloat test(APFloat::Float8E5M2FNUZ(), APFloat::uninitialized);
5464 APFloat expected(APFloat::Float8E5M2FNUZ(), APFloat::uninitialized);
5466 // 1. NextUp of largest bit pattern is nan
5467 test = APFloat::getLargest(APFloat::Float8E5M2FNUZ());
5468 expected = APFloat::getNaN(APFloat::Float8E5M2FNUZ());
5469 EXPECT_EQ(test.next(false), APFloat::opOK);
5470 EXPECT_FALSE(test.isInfinity());
5471 EXPECT_FALSE(test.isZero());
5472 EXPECT_TRUE(test.isNaN());
5473 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5475 // 2. NextUp of smallest negative denormal is +0
5476 test = APFloat::getSmallest(APFloat::Float8E5M2FNUZ(), true);
5477 expected = APFloat::getZero(APFloat::Float8E5M2FNUZ(), false);
5478 EXPECT_EQ(test.next(false), APFloat::opOK);
5479 EXPECT_FALSE(test.isNegZero());
5480 EXPECT_TRUE(test.isPosZero());
5481 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5483 // 3. nextDown of negative of largest value is NaN
5484 test = APFloat::getLargest(APFloat::Float8E5M2FNUZ(), true);
5485 expected = APFloat::getNaN(APFloat::Float8E5M2FNUZ());
5486 EXPECT_EQ(test.next(true), APFloat::opOK);
5487 EXPECT_FALSE(test.isInfinity());
5488 EXPECT_FALSE(test.isZero());
5489 EXPECT_TRUE(test.isNaN());
5490 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5492 // 4. nextDown of +0 is smallest negative denormal
5493 test = APFloat::getZero(APFloat::Float8E5M2FNUZ(), false);
5494 expected = APFloat::getSmallest(APFloat::Float8E5M2FNUZ(), true);
5495 EXPECT_EQ(test.next(true), APFloat::opOK);
5496 EXPECT_FALSE(test.isZero());
5497 EXPECT_TRUE(test.isDenormal());
5498 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5500 // 5. nextUp of NaN is NaN
5501 test = APFloat::getNaN(APFloat::Float8E5M2FNUZ(), false);
5502 expected = APFloat::getNaN(APFloat::Float8E5M2FNUZ(), true);
5503 EXPECT_EQ(test.next(false), APFloat::opOK);
5504 EXPECT_TRUE(test.isNaN());
5506 // 6. nextDown of NaN is NaN
5507 test = APFloat::getNaN(APFloat::Float8E5M2FNUZ(), false);
5508 expected = APFloat::getNaN(APFloat::Float8E5M2FNUZ(), true);
5509 EXPECT_EQ(test.next(true), APFloat::opOK);
5510 EXPECT_TRUE(test.isNaN());
5513 TEST(APFloatTest, Float8E5M2FNUZChangeSign) {
5514 APFloat test = APFloat(APFloat::Float8E5M2FNUZ(), "1.0");
5515 APFloat expected = APFloat(APFloat::Float8E5M2FNUZ(), "-1.0");
5516 test.changeSign();
5517 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5519 test = APFloat::getZero(APFloat::Float8E5M2FNUZ());
5520 expected = test;
5521 test.changeSign();
5522 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5524 test = APFloat::getNaN(APFloat::Float8E5M2FNUZ());
5525 expected = test;
5526 test.changeSign();
5527 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5530 TEST(APFloatTest, Float8E5M2FNUZFromString) {
5531 // Exactly representable
5532 EXPECT_EQ(57344,
5533 APFloat(APFloat::Float8E5M2FNUZ(), "57344").convertToDouble());
5534 // Round down to maximum value
5535 EXPECT_EQ(57344,
5536 APFloat(APFloat::Float8E5M2FNUZ(), "59392").convertToDouble());
5537 // Round up, causing overflow to NaN
5538 EXPECT_TRUE(APFloat(APFloat::Float8E5M2FNUZ(), "61440").isNaN());
5539 // Overflow without rounding
5540 EXPECT_TRUE(APFloat(APFloat::Float8E5M2FNUZ(), "131072").isNaN());
5541 // Inf converted to NaN
5542 EXPECT_TRUE(APFloat(APFloat::Float8E5M2FNUZ(), "inf").isNaN());
5543 // NaN converted to NaN
5544 EXPECT_TRUE(APFloat(APFloat::Float8E5M2FNUZ(), "nan").isNaN());
5545 // Negative zero converted to positive zero
5546 EXPECT_TRUE(APFloat(APFloat::Float8E5M2FNUZ(), "-0").isPosZero());
5549 TEST(APFloatTest, UnsignedZeroArithmeticSpecial) {
5550 // Float semantics with only unsigned zero (ex. Float8E4M3FNUZ) violate the
5551 // IEEE rules about signs in arithmetic operations when producing zeros,
5552 // because they only have one zero. Most of the rest of the complexities of
5553 // arithmetic on these values are covered by the other Float8 types' test
5554 // cases and so are not repeated here.
5556 // The IEEE round towards negative rule doesn't apply
5557 for (APFloat::Semantics S :
5558 {APFloat::S_Float8E4M3FNUZ, APFloat::S_Float8E4M3B11FNUZ}) {
5559 const llvm::fltSemantics &Sem = APFloat::EnumToSemantics(S);
5560 APFloat test = APFloat::getSmallest(Sem);
5561 APFloat rhs = test;
5562 EXPECT_EQ(test.subtract(rhs, APFloat::rmTowardNegative), APFloat::opOK);
5563 EXPECT_TRUE(test.isZero());
5564 EXPECT_FALSE(test.isNegative());
5566 // Multiplication of (small) * (-small) is +0
5567 test = APFloat::getSmallestNormalized(Sem);
5568 rhs = -test;
5569 EXPECT_EQ(test.multiply(rhs, APFloat::rmNearestTiesToAway),
5570 APFloat::opInexact | APFloat::opUnderflow);
5571 EXPECT_TRUE(test.isZero());
5572 EXPECT_FALSE(test.isNegative());
5574 // Dividing the negatize float_min by anything gives +0
5575 test = APFloat::getSmallest(Sem, true);
5576 rhs = APFloat(Sem, "2.0");
5577 EXPECT_EQ(test.divide(rhs, APFloat::rmNearestTiesToEven),
5578 APFloat::opInexact | APFloat::opUnderflow);
5579 EXPECT_TRUE(test.isZero());
5580 EXPECT_FALSE(test.isNegative());
5582 // Remainder can't copy sign because there's only one zero
5583 test = APFloat(Sem, "-4.0");
5584 rhs = APFloat(Sem, "2.0");
5585 EXPECT_EQ(test.remainder(rhs), APFloat::opOK);
5586 EXPECT_TRUE(test.isZero());
5587 EXPECT_FALSE(test.isNegative());
5589 // And same for mod
5590 test = APFloat(Sem, "-4.0");
5591 rhs = APFloat(Sem, "2.0");
5592 EXPECT_EQ(test.mod(rhs), APFloat::opOK);
5593 EXPECT_TRUE(test.isZero());
5594 EXPECT_FALSE(test.isNegative());
5596 // FMA correctly handles both the multiply and add parts of all this
5597 test = APFloat(Sem, "2.0");
5598 rhs = test;
5599 APFloat addend = APFloat(Sem, "-4.0");
5600 EXPECT_EQ(test.fusedMultiplyAdd(rhs, addend, APFloat::rmTowardNegative),
5601 APFloat::opOK);
5602 EXPECT_TRUE(test.isZero());
5603 EXPECT_FALSE(test.isNegative());
5607 TEST(APFloatTest, Float8E5M2FNUZAdd) {
5608 APFloat QNaN = APFloat::getNaN(APFloat::Float8E5M2FNUZ(), false);
5610 auto FromStr = [](StringRef S) {
5611 return APFloat(APFloat::Float8E5M2FNUZ(), S);
5614 struct {
5615 APFloat x;
5616 APFloat y;
5617 const char *result;
5618 int status;
5619 int category;
5620 APFloat::roundingMode roundingMode = APFloat::rmNearestTiesToEven;
5621 } AdditionTests[] = {
5622 // Test addition operations involving NaN, overflow, and the max E5M2FNUZ
5623 // value (57344) because E5M2FNUZ differs from IEEE-754 types in these
5624 // regards
5625 {FromStr("57344"), FromStr("2048"), "57344", APFloat::opInexact,
5626 APFloat::fcNormal},
5627 {FromStr("57344"), FromStr("4096"), "NaN",
5628 APFloat::opOverflow | APFloat::opInexact, APFloat::fcNaN},
5629 {FromStr("-57344"), FromStr("-4096"), "NaN",
5630 APFloat::opOverflow | APFloat::opInexact, APFloat::fcNaN},
5631 {QNaN, FromStr("-57344"), "NaN", APFloat::opOK, APFloat::fcNaN},
5632 {FromStr("57344"), FromStr("-8192"), "49152", APFloat::opOK,
5633 APFloat::fcNormal},
5634 {FromStr("57344"), FromStr("0"), "57344", APFloat::opOK,
5635 APFloat::fcNormal},
5636 {FromStr("57344"), FromStr("4096"), "57344", APFloat::opInexact,
5637 APFloat::fcNormal, APFloat::rmTowardZero},
5638 {FromStr("57344"), FromStr("57344"), "57344", APFloat::opInexact,
5639 APFloat::fcNormal, APFloat::rmTowardZero},
5642 for (size_t i = 0; i < std::size(AdditionTests); ++i) {
5643 APFloat x(AdditionTests[i].x);
5644 APFloat y(AdditionTests[i].y);
5645 APFloat::opStatus status = x.add(y, AdditionTests[i].roundingMode);
5647 APFloat result(APFloat::Float8E5M2FNUZ(), AdditionTests[i].result);
5649 EXPECT_TRUE(result.bitwiseIsEqual(x));
5650 EXPECT_EQ(AdditionTests[i].status, (int)status);
5651 EXPECT_EQ(AdditionTests[i].category, (int)x.getCategory());
5655 TEST(APFloatTest, Float8E5M2FNUZDivideByZero) {
5656 APFloat x(APFloat::Float8E5M2FNUZ(), "1");
5657 APFloat zero(APFloat::Float8E5M2FNUZ(), "0");
5658 EXPECT_EQ(x.divide(zero, APFloat::rmNearestTiesToEven), APFloat::opDivByZero);
5659 EXPECT_TRUE(x.isNaN());
5662 TEST(APFloatTest, Float8UnsignedZeroExhaustive) {
5663 struct {
5664 const fltSemantics *semantics;
5665 const double largest;
5666 const double smallest;
5667 } const exhaustiveTests[] = {{&APFloat::Float8E5M2FNUZ(), 57344., 0x1.0p-17},
5668 {&APFloat::Float8E4M3FNUZ(), 240., 0x1.0p-10},
5669 {&APFloat::Float8E4M3B11FNUZ(), 30., 0x1.0p-13}};
5670 for (const auto &testInfo : exhaustiveTests) {
5671 const fltSemantics &sem = *testInfo.semantics;
5672 SCOPED_TRACE("Semantics=" + std::to_string(APFloat::SemanticsToEnum(sem)));
5673 // Test each of the 256 values.
5674 for (int i = 0; i < 256; i++) {
5675 SCOPED_TRACE("i=" + std::to_string(i));
5676 APFloat test(sem, APInt(8, i));
5678 // isLargest
5679 if (i == 127 || i == 255) {
5680 EXPECT_TRUE(test.isLargest());
5681 EXPECT_EQ(abs(test).convertToDouble(), testInfo.largest);
5682 } else {
5683 EXPECT_FALSE(test.isLargest());
5686 // isSmallest
5687 if (i == 1 || i == 129) {
5688 EXPECT_TRUE(test.isSmallest());
5689 EXPECT_EQ(abs(test).convertToDouble(), testInfo.smallest);
5690 } else {
5691 EXPECT_FALSE(test.isSmallest());
5694 // convert to BFloat
5695 APFloat test2 = test;
5696 bool losesInfo;
5697 APFloat::opStatus status = test2.convert(
5698 APFloat::BFloat(), APFloat::rmNearestTiesToEven, &losesInfo);
5699 EXPECT_EQ(status, APFloat::opOK);
5700 EXPECT_FALSE(losesInfo);
5701 if (i == 128)
5702 EXPECT_TRUE(test2.isNaN());
5703 else
5704 EXPECT_EQ(test.convertToFloat(), test2.convertToFloat());
5706 // bitcastToAPInt
5707 EXPECT_EQ(i, test.bitcastToAPInt());
5712 TEST(APFloatTest, Float8E4M3FNUZNext) {
5713 for (APFloat::Semantics S :
5714 {APFloat::S_Float8E4M3FNUZ, APFloat::S_Float8E4M3B11FNUZ}) {
5715 const llvm::fltSemantics &Sem = APFloat::EnumToSemantics(S);
5716 APFloat test(Sem, APFloat::uninitialized);
5717 APFloat expected(Sem, APFloat::uninitialized);
5719 // 1. NextUp of largest bit pattern is nan
5720 test = APFloat::getLargest(Sem);
5721 expected = APFloat::getNaN(Sem);
5722 EXPECT_EQ(test.next(false), APFloat::opOK);
5723 EXPECT_FALSE(test.isInfinity());
5724 EXPECT_FALSE(test.isZero());
5725 EXPECT_TRUE(test.isNaN());
5726 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5728 // 2. NextUp of smallest negative denormal is +0
5729 test = APFloat::getSmallest(Sem, true);
5730 expected = APFloat::getZero(Sem, false);
5731 EXPECT_EQ(test.next(false), APFloat::opOK);
5732 EXPECT_FALSE(test.isNegZero());
5733 EXPECT_TRUE(test.isPosZero());
5734 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5736 // 3. nextDown of negative of largest value is NaN
5737 test = APFloat::getLargest(Sem, true);
5738 expected = APFloat::getNaN(Sem);
5739 EXPECT_EQ(test.next(true), APFloat::opOK);
5740 EXPECT_FALSE(test.isInfinity());
5741 EXPECT_FALSE(test.isZero());
5742 EXPECT_TRUE(test.isNaN());
5743 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5745 // 4. nextDown of +0 is smallest negative denormal
5746 test = APFloat::getZero(Sem, false);
5747 expected = APFloat::getSmallest(Sem, true);
5748 EXPECT_EQ(test.next(true), APFloat::opOK);
5749 EXPECT_FALSE(test.isZero());
5750 EXPECT_TRUE(test.isDenormal());
5751 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5753 // 5. nextUp of NaN is NaN
5754 test = APFloat::getNaN(Sem, false);
5755 expected = APFloat::getNaN(Sem, true);
5756 EXPECT_EQ(test.next(false), APFloat::opOK);
5757 EXPECT_TRUE(test.isNaN());
5759 // 6. nextDown of NaN is NaN
5760 test = APFloat::getNaN(Sem, false);
5761 expected = APFloat::getNaN(Sem, true);
5762 EXPECT_EQ(test.next(true), APFloat::opOK);
5763 EXPECT_TRUE(test.isNaN());
5767 TEST(APFloatTest, Float8E4M3FNUZChangeSign) {
5768 for (APFloat::Semantics S :
5769 {APFloat::S_Float8E4M3FNUZ, APFloat::S_Float8E4M3B11FNUZ}) {
5770 const llvm::fltSemantics &Sem = APFloat::EnumToSemantics(S);
5771 APFloat test = APFloat(Sem, "1.0");
5772 APFloat expected = APFloat(Sem, "-1.0");
5773 test.changeSign();
5774 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5776 test = APFloat::getZero(Sem);
5777 expected = test;
5778 test.changeSign();
5779 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5781 test = APFloat::getNaN(Sem);
5782 expected = test;
5783 test.changeSign();
5784 EXPECT_TRUE(test.bitwiseIsEqual(expected));
5788 TEST(APFloatTest, Float8E4M3FNUZFromString) {
5789 // Exactly representable
5790 EXPECT_EQ(240, APFloat(APFloat::Float8E4M3FNUZ(), "240").convertToDouble());
5791 // Round down to maximum value
5792 EXPECT_EQ(240, APFloat(APFloat::Float8E4M3FNUZ(), "247").convertToDouble());
5793 // Round up, causing overflow to NaN
5794 EXPECT_TRUE(APFloat(APFloat::Float8E4M3FNUZ(), "248").isNaN());
5795 // Overflow without rounding
5796 EXPECT_TRUE(APFloat(APFloat::Float8E4M3FNUZ(), "480").isNaN());
5797 // Inf converted to NaN
5798 EXPECT_TRUE(APFloat(APFloat::Float8E4M3FNUZ(), "inf").isNaN());
5799 // NaN converted to NaN
5800 EXPECT_TRUE(APFloat(APFloat::Float8E4M3FNUZ(), "nan").isNaN());
5801 // Negative zero converted to positive zero
5802 EXPECT_TRUE(APFloat(APFloat::Float8E4M3FNUZ(), "-0").isPosZero());
5805 TEST(APFloatTest, Float8E4M3FNUZAdd) {
5806 APFloat QNaN = APFloat::getNaN(APFloat::Float8E4M3FNUZ(), false);
5808 auto FromStr = [](StringRef S) {
5809 return APFloat(APFloat::Float8E4M3FNUZ(), S);
5812 struct {
5813 APFloat x;
5814 APFloat y;
5815 const char *result;
5816 int status;
5817 int category;
5818 APFloat::roundingMode roundingMode = APFloat::rmNearestTiesToEven;
5819 } AdditionTests[] = {
5820 // Test addition operations involving NaN, overflow, and the max E4M3FNUZ
5821 // value (240) because E4M3FNUZ differs from IEEE-754 types in these
5822 // regards
5823 {FromStr("240"), FromStr("4"), "240", APFloat::opInexact,
5824 APFloat::fcNormal},
5825 {FromStr("240"), FromStr("8"), "NaN",
5826 APFloat::opOverflow | APFloat::opInexact, APFloat::fcNaN},
5827 {FromStr("240"), FromStr("16"), "NaN",
5828 APFloat::opOverflow | APFloat::opInexact, APFloat::fcNaN},
5829 {FromStr("-240"), FromStr("-16"), "NaN",
5830 APFloat::opOverflow | APFloat::opInexact, APFloat::fcNaN},
5831 {QNaN, FromStr("-240"), "NaN", APFloat::opOK, APFloat::fcNaN},
5832 {FromStr("240"), FromStr("-16"), "224", APFloat::opOK, APFloat::fcNormal},
5833 {FromStr("240"), FromStr("0"), "240", APFloat::opOK, APFloat::fcNormal},
5834 {FromStr("240"), FromStr("32"), "240", APFloat::opInexact,
5835 APFloat::fcNormal, APFloat::rmTowardZero},
5836 {FromStr("240"), FromStr("240"), "240", APFloat::opInexact,
5837 APFloat::fcNormal, APFloat::rmTowardZero},
5840 for (size_t i = 0; i < std::size(AdditionTests); ++i) {
5841 APFloat x(AdditionTests[i].x);
5842 APFloat y(AdditionTests[i].y);
5843 APFloat::opStatus status = x.add(y, AdditionTests[i].roundingMode);
5845 APFloat result(APFloat::Float8E4M3FNUZ(), AdditionTests[i].result);
5847 EXPECT_TRUE(result.bitwiseIsEqual(x));
5848 EXPECT_EQ(AdditionTests[i].status, (int)status);
5849 EXPECT_EQ(AdditionTests[i].category, (int)x.getCategory());
5853 TEST(APFloatTest, Float8E4M3FNUZDivideByZero) {
5854 APFloat x(APFloat::Float8E4M3FNUZ(), "1");
5855 APFloat zero(APFloat::Float8E4M3FNUZ(), "0");
5856 EXPECT_EQ(x.divide(zero, APFloat::rmNearestTiesToEven), APFloat::opDivByZero);
5857 EXPECT_TRUE(x.isNaN());
5860 TEST(APFloatTest, ConvertE5M2FNUZToE4M3FNUZ) {
5861 bool losesInfo;
5862 APFloat test(APFloat::Float8E5M2FNUZ(), "1.0");
5863 APFloat::opStatus status = test.convert(
5864 APFloat::Float8E4M3FNUZ(), APFloat::rmNearestTiesToEven, &losesInfo);
5865 EXPECT_EQ(1.0f, test.convertToFloat());
5866 EXPECT_FALSE(losesInfo);
5867 EXPECT_EQ(status, APFloat::opOK);
5869 losesInfo = true;
5870 test = APFloat(APFloat::Float8E5M2FNUZ(), "0.0");
5871 status = test.convert(APFloat::Float8E4M3FNUZ(), APFloat::rmNearestTiesToEven,
5872 &losesInfo);
5873 EXPECT_EQ(0.0f, test.convertToFloat());
5874 EXPECT_FALSE(losesInfo);
5875 EXPECT_EQ(status, APFloat::opOK);
5877 losesInfo = true;
5878 test = APFloat(APFloat::Float8E5M2FNUZ(), "0x1.Cp7"); // 224
5879 status = test.convert(APFloat::Float8E4M3FNUZ(), APFloat::rmNearestTiesToEven,
5880 &losesInfo);
5881 EXPECT_EQ(0x1.Cp7 /* 224 */, test.convertToFloat());
5882 EXPECT_FALSE(losesInfo);
5883 EXPECT_EQ(status, APFloat::opOK);
5885 // Test overflow
5886 losesInfo = false;
5887 test = APFloat(APFloat::Float8E5M2FNUZ(), "0x1.0p8"); // 256
5888 status = test.convert(APFloat::Float8E4M3FNUZ(), APFloat::rmNearestTiesToEven,
5889 &losesInfo);
5890 EXPECT_TRUE(std::isnan(test.convertToFloat()));
5891 EXPECT_TRUE(losesInfo);
5892 EXPECT_EQ(status, APFloat::opOverflow | APFloat::opInexact);
5894 // Test underflow
5895 test = APFloat(APFloat::Float8E5M2FNUZ(), "0x1.0p-11");
5896 status = test.convert(APFloat::Float8E4M3FNUZ(), APFloat::rmNearestTiesToEven,
5897 &losesInfo);
5898 EXPECT_EQ(0., test.convertToFloat());
5899 EXPECT_TRUE(losesInfo);
5900 EXPECT_EQ(status, APFloat::opUnderflow | APFloat::opInexact);
5902 // Test rounding up to smallest denormal number
5903 losesInfo = false;
5904 test = APFloat(APFloat::Float8E5M2FNUZ(), "0x1.8p-11");
5905 status = test.convert(APFloat::Float8E4M3FNUZ(), APFloat::rmNearestTiesToEven,
5906 &losesInfo);
5907 EXPECT_EQ(0x1.0p-10, test.convertToFloat());
5908 EXPECT_TRUE(losesInfo);
5909 EXPECT_EQ(status, APFloat::opUnderflow | APFloat::opInexact);
5911 // Testing inexact rounding to denormal number
5912 losesInfo = false;
5913 test = APFloat(APFloat::Float8E5M2FNUZ(), "0x1.8p-10");
5914 status = test.convert(APFloat::Float8E4M3FNUZ(), APFloat::rmNearestTiesToEven,
5915 &losesInfo);
5916 EXPECT_EQ(0x1.0p-9, test.convertToFloat());
5917 EXPECT_TRUE(losesInfo);
5918 EXPECT_EQ(status, APFloat::opUnderflow | APFloat::opInexact);
5921 TEST(APFloatTest, ConvertE4M3FNUZToE5M2FNUZ) {
5922 bool losesInfo;
5923 APFloat test(APFloat::Float8E4M3FNUZ(), "1.0");
5924 APFloat::opStatus status = test.convert(
5925 APFloat::Float8E5M2FNUZ(), APFloat::rmNearestTiesToEven, &losesInfo);
5926 EXPECT_EQ(1.0f, test.convertToFloat());
5927 EXPECT_FALSE(losesInfo);
5928 EXPECT_EQ(status, APFloat::opOK);
5930 losesInfo = true;
5931 test = APFloat(APFloat::Float8E4M3FNUZ(), "0.0");
5932 status = test.convert(APFloat::Float8E5M2FNUZ(), APFloat::rmNearestTiesToEven,
5933 &losesInfo);
5934 EXPECT_EQ(0.0f, test.convertToFloat());
5935 EXPECT_FALSE(losesInfo);
5936 EXPECT_EQ(status, APFloat::opOK);
5938 losesInfo = false;
5939 test = APFloat(APFloat::Float8E4M3FNUZ(), "0x1.2p0"); // 1.125
5940 status = test.convert(APFloat::Float8E5M2FNUZ(), APFloat::rmNearestTiesToEven,
5941 &losesInfo);
5942 EXPECT_EQ(0x1.0p0 /* 1.0 */, test.convertToFloat());
5943 EXPECT_TRUE(losesInfo);
5944 EXPECT_EQ(status, APFloat::opInexact);
5946 losesInfo = false;
5947 test = APFloat(APFloat::Float8E4M3FNUZ(), "0x1.6p0"); // 1.375
5948 status = test.convert(APFloat::Float8E5M2FNUZ(), APFloat::rmNearestTiesToEven,
5949 &losesInfo);
5950 EXPECT_EQ(0x1.8p0 /* 1.5 */, test.convertToFloat());
5951 EXPECT_TRUE(losesInfo);
5952 EXPECT_EQ(status, APFloat::opInexact);
5954 // Convert E4M3 denormal to E5M2 normal. Should not be truncated, despite the
5955 // destination format having one fewer significand bit
5956 losesInfo = true;
5957 test = APFloat(APFloat::Float8E4M3FNUZ(), "0x1.Cp-8");
5958 status = test.convert(APFloat::Float8E5M2FNUZ(), APFloat::rmNearestTiesToEven,
5959 &losesInfo);
5960 EXPECT_EQ(0x1.Cp-8, test.convertToFloat());
5961 EXPECT_FALSE(losesInfo);
5962 EXPECT_EQ(status, APFloat::opOK);
5965 TEST(APFloatTest, F8ToString) {
5966 for (APFloat::Semantics S :
5967 {APFloat::S_Float8E5M2, APFloat::S_Float8E4M3FN,
5968 APFloat::S_Float8E5M2FNUZ, APFloat::S_Float8E4M3FNUZ,
5969 APFloat::S_Float8E4M3B11FNUZ}) {
5970 SCOPED_TRACE("Semantics=" + std::to_string(S));
5971 for (int i = 0; i < 256; i++) {
5972 SCOPED_TRACE("i=" + std::to_string(i));
5973 APFloat test(APFloat::EnumToSemantics(S), APInt(8, i));
5974 llvm::SmallString<128> str;
5975 test.toString(str);
5977 if (test.isNaN()) {
5978 EXPECT_EQ(str, "NaN");
5979 } else {
5980 APFloat test2(APFloat::EnumToSemantics(S), str);
5981 EXPECT_TRUE(test.bitwiseIsEqual(test2));
5987 TEST(APFloatTest, BitsToF8ToBits) {
5988 for (APFloat::Semantics S :
5989 {APFloat::S_Float8E5M2, APFloat::S_Float8E4M3FN,
5990 APFloat::S_Float8E5M2FNUZ, APFloat::S_Float8E4M3FNUZ,
5991 APFloat::S_Float8E4M3B11FNUZ}) {
5992 SCOPED_TRACE("Semantics=" + std::to_string(S));
5993 for (int i = 0; i < 256; i++) {
5994 SCOPED_TRACE("i=" + std::to_string(i));
5995 APInt bits_in = APInt(8, i);
5996 APFloat test(APFloat::EnumToSemantics(S), bits_in);
5997 APInt bits_out = test.bitcastToAPInt();
5998 EXPECT_EQ(bits_in, bits_out);
6003 TEST(APFloatTest, F8ToBitsToF8) {
6004 for (APFloat::Semantics S :
6005 {APFloat::S_Float8E5M2, APFloat::S_Float8E4M3FN,
6006 APFloat::S_Float8E5M2FNUZ, APFloat::S_Float8E4M3FNUZ,
6007 APFloat::S_Float8E4M3B11FNUZ}) {
6008 SCOPED_TRACE("Semantics=" + std::to_string(S));
6009 auto &Sem = APFloat::EnumToSemantics(S);
6010 for (bool negative : {false, true}) {
6011 SCOPED_TRACE("negative=" + std::to_string(negative));
6012 APFloat test = APFloat::getZero(Sem, /*Negative=*/negative);
6013 for (int i = 0; i < 128; i++, test.next(/*nextDown=*/negative)) {
6014 SCOPED_TRACE("i=" + std::to_string(i));
6015 APInt bits = test.bitcastToAPInt();
6016 APFloat test2 = APFloat(Sem, bits);
6017 if (test.isNaN()) {
6018 EXPECT_TRUE(test2.isNaN());
6019 } else {
6020 EXPECT_TRUE(test.bitwiseIsEqual(test2));
6027 TEST(APFloatTest, IEEEdoubleToDouble) {
6028 APFloat DPosZero(0.0);
6029 APFloat DPosZeroToDouble(DPosZero.convertToDouble());
6030 EXPECT_TRUE(DPosZeroToDouble.isPosZero());
6031 APFloat DNegZero(-0.0);
6032 APFloat DNegZeroToDouble(DNegZero.convertToDouble());
6033 EXPECT_TRUE(DNegZeroToDouble.isNegZero());
6035 APFloat DOne(1.0);
6036 EXPECT_EQ(1.0, DOne.convertToDouble());
6037 APFloat DPosLargest = APFloat::getLargest(APFloat::IEEEdouble(), false);
6038 EXPECT_EQ(std::numeric_limits<double>::max(), DPosLargest.convertToDouble());
6039 APFloat DNegLargest = APFloat::getLargest(APFloat::IEEEdouble(), true);
6040 EXPECT_EQ(-std::numeric_limits<double>::max(), DNegLargest.convertToDouble());
6041 APFloat DPosSmallest =
6042 APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
6043 EXPECT_EQ(std::numeric_limits<double>::min(), DPosSmallest.convertToDouble());
6044 APFloat DNegSmallest =
6045 APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
6046 EXPECT_EQ(-std::numeric_limits<double>::min(),
6047 DNegSmallest.convertToDouble());
6049 APFloat DSmallestDenorm = APFloat::getSmallest(APFloat::IEEEdouble(), false);
6050 EXPECT_EQ(std::numeric_limits<double>::denorm_min(),
6051 DSmallestDenorm.convertToDouble());
6052 APFloat DLargestDenorm(APFloat::IEEEdouble(), "0x0.FFFFFFFFFFFFFp-1022");
6053 EXPECT_EQ(/*0x0.FFFFFFFFFFFFFp-1022*/ 2.225073858507201e-308,
6054 DLargestDenorm.convertToDouble());
6056 APFloat DPosInf = APFloat::getInf(APFloat::IEEEdouble());
6057 EXPECT_EQ(std::numeric_limits<double>::infinity(), DPosInf.convertToDouble());
6058 APFloat DNegInf = APFloat::getInf(APFloat::IEEEdouble(), true);
6059 EXPECT_EQ(-std::numeric_limits<double>::infinity(),
6060 DNegInf.convertToDouble());
6061 APFloat DQNaN = APFloat::getQNaN(APFloat::IEEEdouble());
6062 EXPECT_TRUE(std::isnan(DQNaN.convertToDouble()));
6065 TEST(APFloatTest, IEEEsingleToDouble) {
6066 APFloat FPosZero(0.0F);
6067 APFloat FPosZeroToDouble(FPosZero.convertToDouble());
6068 EXPECT_TRUE(FPosZeroToDouble.isPosZero());
6069 APFloat FNegZero(-0.0F);
6070 APFloat FNegZeroToDouble(FNegZero.convertToDouble());
6071 EXPECT_TRUE(FNegZeroToDouble.isNegZero());
6073 APFloat FOne(1.0F);
6074 EXPECT_EQ(1.0, FOne.convertToDouble());
6075 APFloat FPosLargest = APFloat::getLargest(APFloat::IEEEsingle(), false);
6076 EXPECT_EQ(std::numeric_limits<float>::max(), FPosLargest.convertToDouble());
6077 APFloat FNegLargest = APFloat::getLargest(APFloat::IEEEsingle(), true);
6078 EXPECT_EQ(-std::numeric_limits<float>::max(), FNegLargest.convertToDouble());
6079 APFloat FPosSmallest =
6080 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
6081 EXPECT_EQ(std::numeric_limits<float>::min(), FPosSmallest.convertToDouble());
6082 APFloat FNegSmallest =
6083 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
6084 EXPECT_EQ(-std::numeric_limits<float>::min(), FNegSmallest.convertToDouble());
6086 APFloat FSmallestDenorm = APFloat::getSmallest(APFloat::IEEEsingle(), false);
6087 EXPECT_EQ(std::numeric_limits<float>::denorm_min(),
6088 FSmallestDenorm.convertToDouble());
6089 APFloat FLargestDenorm(APFloat::IEEEdouble(), "0x0.FFFFFEp-126");
6090 EXPECT_EQ(/*0x0.FFFFFEp-126*/ 1.1754942106924411e-38,
6091 FLargestDenorm.convertToDouble());
6093 APFloat FPosInf = APFloat::getInf(APFloat::IEEEsingle());
6094 EXPECT_EQ(std::numeric_limits<double>::infinity(), FPosInf.convertToDouble());
6095 APFloat FNegInf = APFloat::getInf(APFloat::IEEEsingle(), true);
6096 EXPECT_EQ(-std::numeric_limits<double>::infinity(),
6097 FNegInf.convertToDouble());
6098 APFloat FQNaN = APFloat::getQNaN(APFloat::IEEEsingle());
6099 EXPECT_TRUE(std::isnan(FQNaN.convertToDouble()));
6102 TEST(APFloatTest, IEEEhalfToDouble) {
6103 APFloat HPosZero = APFloat::getZero(APFloat::IEEEhalf());
6104 APFloat HPosZeroToDouble(HPosZero.convertToDouble());
6105 EXPECT_TRUE(HPosZeroToDouble.isPosZero());
6106 APFloat HNegZero = APFloat::getZero(APFloat::IEEEhalf(), true);
6107 APFloat HNegZeroToDouble(HNegZero.convertToDouble());
6108 EXPECT_TRUE(HNegZeroToDouble.isNegZero());
6110 APFloat HOne(APFloat::IEEEhalf(), "1.0");
6111 EXPECT_EQ(1.0, HOne.convertToDouble());
6112 APFloat HPosLargest = APFloat::getLargest(APFloat::IEEEhalf(), false);
6113 EXPECT_EQ(65504.0, HPosLargest.convertToDouble());
6114 APFloat HNegLargest = APFloat::getLargest(APFloat::IEEEhalf(), true);
6115 EXPECT_EQ(-65504.0, HNegLargest.convertToDouble());
6116 APFloat HPosSmallest =
6117 APFloat::getSmallestNormalized(APFloat::IEEEhalf(), false);
6118 EXPECT_EQ(/*0x1.p-14*/ 6.103515625e-05, HPosSmallest.convertToDouble());
6119 APFloat HNegSmallest =
6120 APFloat::getSmallestNormalized(APFloat::IEEEhalf(), true);
6121 EXPECT_EQ(/*-0x1.p-14*/ -6.103515625e-05, HNegSmallest.convertToDouble());
6123 APFloat HSmallestDenorm = APFloat::getSmallest(APFloat::IEEEhalf(), false);
6124 EXPECT_EQ(/*0x1.p-24*/ 5.960464477539063e-08,
6125 HSmallestDenorm.convertToDouble());
6126 APFloat HLargestDenorm(APFloat::IEEEhalf(), "0x1.FFCp-14");
6127 EXPECT_EQ(/*0x1.FFCp-14*/ 0.00012201070785522461,
6128 HLargestDenorm.convertToDouble());
6130 APFloat HPosInf = APFloat::getInf(APFloat::IEEEhalf());
6131 EXPECT_EQ(std::numeric_limits<double>::infinity(), HPosInf.convertToDouble());
6132 APFloat HNegInf = APFloat::getInf(APFloat::IEEEhalf(), true);
6133 EXPECT_EQ(-std::numeric_limits<double>::infinity(),
6134 HNegInf.convertToDouble());
6135 APFloat HQNaN = APFloat::getQNaN(APFloat::IEEEhalf());
6136 EXPECT_TRUE(std::isnan(HQNaN.convertToDouble()));
6138 APFloat BPosZero = APFloat::getZero(APFloat::IEEEhalf());
6139 APFloat BPosZeroToDouble(BPosZero.convertToDouble());
6140 EXPECT_TRUE(BPosZeroToDouble.isPosZero());
6141 APFloat BNegZero = APFloat::getZero(APFloat::IEEEhalf(), true);
6142 APFloat BNegZeroToDouble(BNegZero.convertToDouble());
6143 EXPECT_TRUE(BNegZeroToDouble.isNegZero());
6146 TEST(APFloatTest, BFloatToDouble) {
6147 APFloat BOne(APFloat::BFloat(), "1.0");
6148 EXPECT_EQ(1.0, BOne.convertToDouble());
6149 APFloat BPosLargest = APFloat::getLargest(APFloat::BFloat(), false);
6150 EXPECT_EQ(/*0x1.FEp127*/ 3.3895313892515355e+38,
6151 BPosLargest.convertToDouble());
6152 APFloat BNegLargest = APFloat::getLargest(APFloat::BFloat(), true);
6153 EXPECT_EQ(/*-0x1.FEp127*/ -3.3895313892515355e+38,
6154 BNegLargest.convertToDouble());
6155 APFloat BPosSmallest =
6156 APFloat::getSmallestNormalized(APFloat::BFloat(), false);
6157 EXPECT_EQ(/*0x1.p-126*/ 1.1754943508222875e-38,
6158 BPosSmallest.convertToDouble());
6159 APFloat BNegSmallest =
6160 APFloat::getSmallestNormalized(APFloat::BFloat(), true);
6161 EXPECT_EQ(/*-0x1.p-126*/ -1.1754943508222875e-38,
6162 BNegSmallest.convertToDouble());
6164 APFloat BSmallestDenorm = APFloat::getSmallest(APFloat::BFloat(), false);
6165 EXPECT_EQ(/*0x1.p-133*/ 9.183549615799121e-41,
6166 BSmallestDenorm.convertToDouble());
6167 APFloat BLargestDenorm(APFloat::BFloat(), "0x1.FCp-127");
6168 EXPECT_EQ(/*0x1.FCp-127*/ 1.1663108012064884e-38,
6169 BLargestDenorm.convertToDouble());
6171 APFloat BPosInf = APFloat::getInf(APFloat::BFloat());
6172 EXPECT_EQ(std::numeric_limits<double>::infinity(), BPosInf.convertToDouble());
6173 APFloat BNegInf = APFloat::getInf(APFloat::BFloat(), true);
6174 EXPECT_EQ(-std::numeric_limits<double>::infinity(),
6175 BNegInf.convertToDouble());
6176 APFloat BQNaN = APFloat::getQNaN(APFloat::BFloat());
6177 EXPECT_TRUE(std::isnan(BQNaN.convertToDouble()));
6180 TEST(APFloatTest, Float8E5M2ToDouble) {
6181 APFloat One(APFloat::Float8E5M2(), "1.0");
6182 EXPECT_EQ(1.0, One.convertToDouble());
6183 APFloat Two(APFloat::Float8E5M2(), "2.0");
6184 EXPECT_EQ(2.0, Two.convertToDouble());
6185 APFloat PosLargest = APFloat::getLargest(APFloat::Float8E5M2(), false);
6186 EXPECT_EQ(5.734400e+04, PosLargest.convertToDouble());
6187 APFloat NegLargest = APFloat::getLargest(APFloat::Float8E5M2(), true);
6188 EXPECT_EQ(-5.734400e+04, NegLargest.convertToDouble());
6189 APFloat PosSmallest =
6190 APFloat::getSmallestNormalized(APFloat::Float8E5M2(), false);
6191 EXPECT_EQ(0x1.p-14, PosSmallest.convertToDouble());
6192 APFloat NegSmallest =
6193 APFloat::getSmallestNormalized(APFloat::Float8E5M2(), true);
6194 EXPECT_EQ(-0x1.p-14, NegSmallest.convertToDouble());
6196 APFloat SmallestDenorm = APFloat::getSmallest(APFloat::Float8E5M2(), false);
6197 EXPECT_TRUE(SmallestDenorm.isDenormal());
6198 EXPECT_EQ(0x1p-16, SmallestDenorm.convertToDouble());
6200 APFloat PosInf = APFloat::getInf(APFloat::Float8E5M2());
6201 EXPECT_EQ(std::numeric_limits<double>::infinity(), PosInf.convertToDouble());
6202 APFloat NegInf = APFloat::getInf(APFloat::Float8E5M2(), true);
6203 EXPECT_EQ(-std::numeric_limits<double>::infinity(), NegInf.convertToDouble());
6204 APFloat QNaN = APFloat::getQNaN(APFloat::Float8E5M2());
6205 EXPECT_TRUE(std::isnan(QNaN.convertToDouble()));
6208 TEST(APFloatTest, Float8E4M3FNToDouble) {
6209 APFloat One(APFloat::Float8E4M3FN(), "1.0");
6210 EXPECT_EQ(1.0, One.convertToDouble());
6211 APFloat Two(APFloat::Float8E4M3FN(), "2.0");
6212 EXPECT_EQ(2.0, Two.convertToDouble());
6213 APFloat PosLargest = APFloat::getLargest(APFloat::Float8E4M3FN(), false);
6214 EXPECT_EQ(448., PosLargest.convertToDouble());
6215 APFloat NegLargest = APFloat::getLargest(APFloat::Float8E4M3FN(), true);
6216 EXPECT_EQ(-448., NegLargest.convertToDouble());
6217 APFloat PosSmallest =
6218 APFloat::getSmallestNormalized(APFloat::Float8E4M3FN(), false);
6219 EXPECT_EQ(0x1.p-6, PosSmallest.convertToDouble());
6220 APFloat NegSmallest =
6221 APFloat::getSmallestNormalized(APFloat::Float8E4M3FN(), true);
6222 EXPECT_EQ(-0x1.p-6, NegSmallest.convertToDouble());
6224 APFloat SmallestDenorm = APFloat::getSmallest(APFloat::Float8E4M3FN(), false);
6225 EXPECT_TRUE(SmallestDenorm.isDenormal());
6226 EXPECT_EQ(0x1p-9, SmallestDenorm.convertToDouble());
6228 APFloat QNaN = APFloat::getQNaN(APFloat::Float8E4M3FN());
6229 EXPECT_TRUE(std::isnan(QNaN.convertToDouble()));
6232 TEST(APFloatTest, Float8E5M2FNUZToDouble) {
6233 APFloat One(APFloat::Float8E5M2FNUZ(), "1.0");
6234 EXPECT_EQ(1.0, One.convertToDouble());
6235 APFloat Two(APFloat::Float8E5M2FNUZ(), "2.0");
6236 EXPECT_EQ(2.0, Two.convertToDouble());
6237 APFloat PosLargest = APFloat::getLargest(APFloat::Float8E5M2FNUZ(), false);
6238 EXPECT_EQ(57344., PosLargest.convertToDouble());
6239 APFloat NegLargest = APFloat::getLargest(APFloat::Float8E5M2FNUZ(), true);
6240 EXPECT_EQ(-57344., NegLargest.convertToDouble());
6241 APFloat PosSmallest =
6242 APFloat::getSmallestNormalized(APFloat::Float8E5M2FNUZ(), false);
6243 EXPECT_EQ(0x1.p-15, PosSmallest.convertToDouble());
6244 APFloat NegSmallest =
6245 APFloat::getSmallestNormalized(APFloat::Float8E5M2FNUZ(), true);
6246 EXPECT_EQ(-0x1.p-15, NegSmallest.convertToDouble());
6248 APFloat SmallestDenorm =
6249 APFloat::getSmallest(APFloat::Float8E5M2FNUZ(), false);
6250 EXPECT_TRUE(SmallestDenorm.isDenormal());
6251 EXPECT_EQ(0x1p-17, SmallestDenorm.convertToDouble());
6253 APFloat QNaN = APFloat::getQNaN(APFloat::Float8E5M2FNUZ());
6254 EXPECT_TRUE(std::isnan(QNaN.convertToDouble()));
6257 TEST(APFloatTest, Float8E4M3FNUZToDouble) {
6258 APFloat One(APFloat::Float8E4M3FNUZ(), "1.0");
6259 EXPECT_EQ(1.0, One.convertToDouble());
6260 APFloat Two(APFloat::Float8E4M3FNUZ(), "2.0");
6261 EXPECT_EQ(2.0, Two.convertToDouble());
6262 APFloat PosLargest = APFloat::getLargest(APFloat::Float8E4M3FNUZ(), false);
6263 EXPECT_EQ(240., PosLargest.convertToDouble());
6264 APFloat NegLargest = APFloat::getLargest(APFloat::Float8E4M3FNUZ(), true);
6265 EXPECT_EQ(-240., NegLargest.convertToDouble());
6266 APFloat PosSmallest =
6267 APFloat::getSmallestNormalized(APFloat::Float8E4M3FNUZ(), false);
6268 EXPECT_EQ(0x1.p-7, PosSmallest.convertToDouble());
6269 APFloat NegSmallest =
6270 APFloat::getSmallestNormalized(APFloat::Float8E4M3FNUZ(), true);
6271 EXPECT_EQ(-0x1.p-7, NegSmallest.convertToDouble());
6273 APFloat SmallestDenorm =
6274 APFloat::getSmallest(APFloat::Float8E4M3FNUZ(), false);
6275 EXPECT_TRUE(SmallestDenorm.isDenormal());
6276 EXPECT_EQ(0x1p-10, SmallestDenorm.convertToDouble());
6278 APFloat QNaN = APFloat::getQNaN(APFloat::Float8E4M3FNUZ());
6279 EXPECT_TRUE(std::isnan(QNaN.convertToDouble()));
6282 TEST(APFloatTest, FloatTF32ToDouble) {
6283 APFloat One(APFloat::FloatTF32(), "1.0");
6284 EXPECT_EQ(1.0, One.convertToDouble());
6285 APFloat PosLargest = APFloat::getLargest(APFloat::FloatTF32(), false);
6286 EXPECT_EQ(3.401162134214653489792616e+38, PosLargest.convertToDouble());
6287 APFloat NegLargest = APFloat::getLargest(APFloat::FloatTF32(), true);
6288 EXPECT_EQ(-3.401162134214653489792616e+38, NegLargest.convertToDouble());
6289 APFloat PosSmallest =
6290 APFloat::getSmallestNormalized(APFloat::FloatTF32(), false);
6291 EXPECT_EQ(1.1754943508222875079687e-38, PosSmallest.convertToDouble());
6292 APFloat NegSmallest =
6293 APFloat::getSmallestNormalized(APFloat::FloatTF32(), true);
6294 EXPECT_EQ(-1.1754943508222875079687e-38, NegSmallest.convertToDouble());
6296 APFloat SmallestDenorm = APFloat::getSmallest(APFloat::FloatTF32(), false);
6297 EXPECT_EQ(1.1479437019748901445007e-41, SmallestDenorm.convertToDouble());
6298 APFloat LargestDenorm(APFloat::FloatTF32(), "0x1.FF8p-127");
6299 EXPECT_EQ(/*0x1.FF8p-127*/ 1.1743464071203126178242e-38,
6300 LargestDenorm.convertToDouble());
6302 APFloat PosInf = APFloat::getInf(APFloat::FloatTF32());
6303 EXPECT_EQ(std::numeric_limits<double>::infinity(), PosInf.convertToDouble());
6304 APFloat NegInf = APFloat::getInf(APFloat::FloatTF32(), true);
6305 EXPECT_EQ(-std::numeric_limits<double>::infinity(), NegInf.convertToDouble());
6306 APFloat QNaN = APFloat::getQNaN(APFloat::FloatTF32());
6307 EXPECT_TRUE(std::isnan(QNaN.convertToDouble()));
6310 TEST(APFloatTest, Float8E5M2FNUZToFloat) {
6311 APFloat PosZero = APFloat::getZero(APFloat::Float8E5M2FNUZ());
6312 APFloat PosZeroToFloat(PosZero.convertToFloat());
6313 EXPECT_TRUE(PosZeroToFloat.isPosZero());
6314 // Negative zero is not supported
6315 APFloat NegZero = APFloat::getZero(APFloat::Float8E5M2FNUZ(), true);
6316 APFloat NegZeroToFloat(NegZero.convertToFloat());
6317 EXPECT_TRUE(NegZeroToFloat.isPosZero());
6318 APFloat One(APFloat::Float8E5M2FNUZ(), "1.0");
6319 EXPECT_EQ(1.0F, One.convertToFloat());
6320 APFloat Two(APFloat::Float8E5M2FNUZ(), "2.0");
6321 EXPECT_EQ(2.0F, Two.convertToFloat());
6322 APFloat PosLargest = APFloat::getLargest(APFloat::Float8E5M2FNUZ(), false);
6323 EXPECT_EQ(57344.F, PosLargest.convertToFloat());
6324 APFloat NegLargest = APFloat::getLargest(APFloat::Float8E5M2FNUZ(), true);
6325 EXPECT_EQ(-57344.F, NegLargest.convertToFloat());
6326 APFloat PosSmallest =
6327 APFloat::getSmallestNormalized(APFloat::Float8E5M2FNUZ(), false);
6328 EXPECT_EQ(0x1.p-15F, PosSmallest.convertToFloat());
6329 APFloat NegSmallest =
6330 APFloat::getSmallestNormalized(APFloat::Float8E5M2FNUZ(), true);
6331 EXPECT_EQ(-0x1.p-15F, NegSmallest.convertToFloat());
6333 APFloat SmallestDenorm =
6334 APFloat::getSmallest(APFloat::Float8E5M2FNUZ(), false);
6335 EXPECT_TRUE(SmallestDenorm.isDenormal());
6336 EXPECT_EQ(0x1p-17F, SmallestDenorm.convertToFloat());
6338 APFloat QNaN = APFloat::getQNaN(APFloat::Float8E5M2FNUZ());
6339 EXPECT_TRUE(std::isnan(QNaN.convertToFloat()));
6342 TEST(APFloatTest, Float8E4M3FNUZToFloat) {
6343 APFloat PosZero = APFloat::getZero(APFloat::Float8E4M3FNUZ());
6344 APFloat PosZeroToFloat(PosZero.convertToFloat());
6345 EXPECT_TRUE(PosZeroToFloat.isPosZero());
6346 // Negative zero is not supported
6347 APFloat NegZero = APFloat::getZero(APFloat::Float8E4M3FNUZ(), true);
6348 APFloat NegZeroToFloat(NegZero.convertToFloat());
6349 EXPECT_TRUE(NegZeroToFloat.isPosZero());
6350 APFloat One(APFloat::Float8E4M3FNUZ(), "1.0");
6351 EXPECT_EQ(1.0F, One.convertToFloat());
6352 APFloat Two(APFloat::Float8E4M3FNUZ(), "2.0");
6353 EXPECT_EQ(2.0F, Two.convertToFloat());
6354 APFloat PosLargest = APFloat::getLargest(APFloat::Float8E4M3FNUZ(), false);
6355 EXPECT_EQ(240.F, PosLargest.convertToFloat());
6356 APFloat NegLargest = APFloat::getLargest(APFloat::Float8E4M3FNUZ(), true);
6357 EXPECT_EQ(-240.F, NegLargest.convertToFloat());
6358 APFloat PosSmallest =
6359 APFloat::getSmallestNormalized(APFloat::Float8E4M3FNUZ(), false);
6360 EXPECT_EQ(0x1.p-7F, PosSmallest.convertToFloat());
6361 APFloat NegSmallest =
6362 APFloat::getSmallestNormalized(APFloat::Float8E4M3FNUZ(), true);
6363 EXPECT_EQ(-0x1.p-7F, NegSmallest.convertToFloat());
6365 APFloat SmallestDenorm =
6366 APFloat::getSmallest(APFloat::Float8E4M3FNUZ(), false);
6367 EXPECT_TRUE(SmallestDenorm.isDenormal());
6368 EXPECT_EQ(0x1p-10F, SmallestDenorm.convertToFloat());
6370 APFloat QNaN = APFloat::getQNaN(APFloat::Float8E4M3FNUZ());
6371 EXPECT_TRUE(std::isnan(QNaN.convertToFloat()));
6374 TEST(APFloatTest, IEEEsingleToFloat) {
6375 APFloat FPosZero(0.0F);
6376 APFloat FPosZeroToFloat(FPosZero.convertToFloat());
6377 EXPECT_TRUE(FPosZeroToFloat.isPosZero());
6378 APFloat FNegZero(-0.0F);
6379 APFloat FNegZeroToFloat(FNegZero.convertToFloat());
6380 EXPECT_TRUE(FNegZeroToFloat.isNegZero());
6382 APFloat FOne(1.0F);
6383 EXPECT_EQ(1.0F, FOne.convertToFloat());
6384 APFloat FPosLargest = APFloat::getLargest(APFloat::IEEEsingle(), false);
6385 EXPECT_EQ(std::numeric_limits<float>::max(), FPosLargest.convertToFloat());
6386 APFloat FNegLargest = APFloat::getLargest(APFloat::IEEEsingle(), true);
6387 EXPECT_EQ(-std::numeric_limits<float>::max(), FNegLargest.convertToFloat());
6388 APFloat FPosSmallest =
6389 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
6390 EXPECT_EQ(std::numeric_limits<float>::min(), FPosSmallest.convertToFloat());
6391 APFloat FNegSmallest =
6392 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
6393 EXPECT_EQ(-std::numeric_limits<float>::min(), FNegSmallest.convertToFloat());
6395 APFloat FSmallestDenorm = APFloat::getSmallest(APFloat::IEEEsingle(), false);
6396 EXPECT_EQ(std::numeric_limits<float>::denorm_min(),
6397 FSmallestDenorm.convertToFloat());
6398 APFloat FLargestDenorm(APFloat::IEEEsingle(), "0x1.FFFFFEp-126");
6399 EXPECT_EQ(/*0x1.FFFFFEp-126*/ 2.3509885615147286e-38F,
6400 FLargestDenorm.convertToFloat());
6402 APFloat FPosInf = APFloat::getInf(APFloat::IEEEsingle());
6403 EXPECT_EQ(std::numeric_limits<float>::infinity(), FPosInf.convertToFloat());
6404 APFloat FNegInf = APFloat::getInf(APFloat::IEEEsingle(), true);
6405 EXPECT_EQ(-std::numeric_limits<float>::infinity(), FNegInf.convertToFloat());
6406 APFloat FQNaN = APFloat::getQNaN(APFloat::IEEEsingle());
6407 EXPECT_TRUE(std::isnan(FQNaN.convertToFloat()));
6410 TEST(APFloatTest, IEEEhalfToFloat) {
6411 APFloat HPosZero = APFloat::getZero(APFloat::IEEEhalf());
6412 APFloat HPosZeroToFloat(HPosZero.convertToFloat());
6413 EXPECT_TRUE(HPosZeroToFloat.isPosZero());
6414 APFloat HNegZero = APFloat::getZero(APFloat::IEEEhalf(), true);
6415 APFloat HNegZeroToFloat(HNegZero.convertToFloat());
6416 EXPECT_TRUE(HNegZeroToFloat.isNegZero());
6418 APFloat HOne(APFloat::IEEEhalf(), "1.0");
6419 EXPECT_EQ(1.0F, HOne.convertToFloat());
6420 APFloat HPosLargest = APFloat::getLargest(APFloat::IEEEhalf(), false);
6421 EXPECT_EQ(/*0x1.FFCp15*/ 65504.0F, HPosLargest.convertToFloat());
6422 APFloat HNegLargest = APFloat::getLargest(APFloat::IEEEhalf(), true);
6423 EXPECT_EQ(/*-0x1.FFCp15*/ -65504.0F, HNegLargest.convertToFloat());
6424 APFloat HPosSmallest =
6425 APFloat::getSmallestNormalized(APFloat::IEEEhalf(), false);
6426 EXPECT_EQ(/*0x1.p-14*/ 6.103515625e-05F, HPosSmallest.convertToFloat());
6427 APFloat HNegSmallest =
6428 APFloat::getSmallestNormalized(APFloat::IEEEhalf(), true);
6429 EXPECT_EQ(/*-0x1.p-14*/ -6.103515625e-05F, HNegSmallest.convertToFloat());
6431 APFloat HSmallestDenorm = APFloat::getSmallest(APFloat::IEEEhalf(), false);
6432 EXPECT_EQ(/*0x1.p-24*/ 5.960464477539063e-08F,
6433 HSmallestDenorm.convertToFloat());
6434 APFloat HLargestDenorm(APFloat::IEEEhalf(), "0x1.FFCp-14");
6435 EXPECT_EQ(/*0x1.FFCp-14*/ 0.00012201070785522461F,
6436 HLargestDenorm.convertToFloat());
6438 APFloat HPosInf = APFloat::getInf(APFloat::IEEEhalf());
6439 EXPECT_EQ(std::numeric_limits<float>::infinity(), HPosInf.convertToFloat());
6440 APFloat HNegInf = APFloat::getInf(APFloat::IEEEhalf(), true);
6441 EXPECT_EQ(-std::numeric_limits<float>::infinity(), HNegInf.convertToFloat());
6442 APFloat HQNaN = APFloat::getQNaN(APFloat::IEEEhalf());
6443 EXPECT_TRUE(std::isnan(HQNaN.convertToFloat()));
6446 TEST(APFloatTest, BFloatToFloat) {
6447 APFloat BPosZero = APFloat::getZero(APFloat::BFloat());
6448 APFloat BPosZeroToDouble(BPosZero.convertToFloat());
6449 EXPECT_TRUE(BPosZeroToDouble.isPosZero());
6450 APFloat BNegZero = APFloat::getZero(APFloat::BFloat(), true);
6451 APFloat BNegZeroToDouble(BNegZero.convertToFloat());
6452 EXPECT_TRUE(BNegZeroToDouble.isNegZero());
6454 APFloat BOne(APFloat::BFloat(), "1.0");
6455 EXPECT_EQ(1.0F, BOne.convertToFloat());
6456 APFloat BPosLargest = APFloat::getLargest(APFloat::BFloat(), false);
6457 EXPECT_EQ(/*0x1.FEp127*/ 3.3895313892515355e+38F,
6458 BPosLargest.convertToFloat());
6459 APFloat BNegLargest = APFloat::getLargest(APFloat::BFloat(), true);
6460 EXPECT_EQ(/*-0x1.FEp127*/ -3.3895313892515355e+38F,
6461 BNegLargest.convertToFloat());
6462 APFloat BPosSmallest =
6463 APFloat::getSmallestNormalized(APFloat::BFloat(), false);
6464 EXPECT_EQ(/*0x1.p-126*/ 1.1754943508222875e-38F,
6465 BPosSmallest.convertToFloat());
6466 APFloat BNegSmallest =
6467 APFloat::getSmallestNormalized(APFloat::BFloat(), true);
6468 EXPECT_EQ(/*-0x1.p-126*/ -1.1754943508222875e-38F,
6469 BNegSmallest.convertToFloat());
6471 APFloat BSmallestDenorm = APFloat::getSmallest(APFloat::BFloat(), false);
6472 EXPECT_EQ(/*0x1.p-133*/ 9.183549615799121e-41F,
6473 BSmallestDenorm.convertToFloat());
6474 APFloat BLargestDenorm(APFloat::BFloat(), "0x1.FCp-127");
6475 EXPECT_EQ(/*0x1.FCp-127*/ 1.1663108012064884e-38F,
6476 BLargestDenorm.convertToFloat());
6478 APFloat BPosInf = APFloat::getInf(APFloat::BFloat());
6479 EXPECT_EQ(std::numeric_limits<float>::infinity(), BPosInf.convertToFloat());
6480 APFloat BNegInf = APFloat::getInf(APFloat::BFloat(), true);
6481 EXPECT_EQ(-std::numeric_limits<float>::infinity(), BNegInf.convertToFloat());
6482 APFloat BQNaN = APFloat::getQNaN(APFloat::BFloat());
6483 EXPECT_TRUE(std::isnan(BQNaN.convertToFloat()));
6486 TEST(APFloatTest, Float8E5M2ToFloat) {
6487 APFloat PosZero = APFloat::getZero(APFloat::Float8E5M2());
6488 APFloat PosZeroToFloat(PosZero.convertToFloat());
6489 EXPECT_TRUE(PosZeroToFloat.isPosZero());
6490 APFloat NegZero = APFloat::getZero(APFloat::Float8E5M2(), true);
6491 APFloat NegZeroToFloat(NegZero.convertToFloat());
6492 EXPECT_TRUE(NegZeroToFloat.isNegZero());
6494 APFloat One(APFloat::Float8E5M2(), "1.0");
6495 EXPECT_EQ(1.0F, One.convertToFloat());
6496 APFloat Two(APFloat::Float8E5M2(), "2.0");
6497 EXPECT_EQ(2.0F, Two.convertToFloat());
6499 APFloat PosLargest = APFloat::getLargest(APFloat::Float8E5M2(), false);
6500 EXPECT_EQ(5.734400e+04, PosLargest.convertToFloat());
6501 APFloat NegLargest = APFloat::getLargest(APFloat::Float8E5M2(), true);
6502 EXPECT_EQ(-5.734400e+04, NegLargest.convertToFloat());
6503 APFloat PosSmallest =
6504 APFloat::getSmallestNormalized(APFloat::Float8E5M2(), false);
6505 EXPECT_EQ(0x1.p-14, PosSmallest.convertToFloat());
6506 APFloat NegSmallest =
6507 APFloat::getSmallestNormalized(APFloat::Float8E5M2(), true);
6508 EXPECT_EQ(-0x1.p-14, NegSmallest.convertToFloat());
6510 APFloat SmallestDenorm = APFloat::getSmallest(APFloat::Float8E5M2(), false);
6511 EXPECT_TRUE(SmallestDenorm.isDenormal());
6512 EXPECT_EQ(0x1.p-16, SmallestDenorm.convertToFloat());
6514 APFloat PosInf = APFloat::getInf(APFloat::Float8E5M2());
6515 EXPECT_EQ(std::numeric_limits<float>::infinity(), PosInf.convertToFloat());
6516 APFloat NegInf = APFloat::getInf(APFloat::Float8E5M2(), true);
6517 EXPECT_EQ(-std::numeric_limits<float>::infinity(), NegInf.convertToFloat());
6518 APFloat QNaN = APFloat::getQNaN(APFloat::Float8E5M2());
6519 EXPECT_TRUE(std::isnan(QNaN.convertToFloat()));
6522 TEST(APFloatTest, Float8E4M3FNToFloat) {
6523 APFloat PosZero = APFloat::getZero(APFloat::Float8E4M3FN());
6524 APFloat PosZeroToFloat(PosZero.convertToFloat());
6525 EXPECT_TRUE(PosZeroToFloat.isPosZero());
6526 APFloat NegZero = APFloat::getZero(APFloat::Float8E4M3FN(), true);
6527 APFloat NegZeroToFloat(NegZero.convertToFloat());
6528 EXPECT_TRUE(NegZeroToFloat.isNegZero());
6530 APFloat One(APFloat::Float8E4M3FN(), "1.0");
6531 EXPECT_EQ(1.0F, One.convertToFloat());
6532 APFloat Two(APFloat::Float8E4M3FN(), "2.0");
6533 EXPECT_EQ(2.0F, Two.convertToFloat());
6535 APFloat PosLargest = APFloat::getLargest(APFloat::Float8E4M3FN(), false);
6536 EXPECT_EQ(448., PosLargest.convertToFloat());
6537 APFloat NegLargest = APFloat::getLargest(APFloat::Float8E4M3FN(), true);
6538 EXPECT_EQ(-448, NegLargest.convertToFloat());
6539 APFloat PosSmallest =
6540 APFloat::getSmallestNormalized(APFloat::Float8E4M3FN(), false);
6541 EXPECT_EQ(0x1.p-6, PosSmallest.convertToFloat());
6542 APFloat NegSmallest =
6543 APFloat::getSmallestNormalized(APFloat::Float8E4M3FN(), true);
6544 EXPECT_EQ(-0x1.p-6, NegSmallest.convertToFloat());
6546 APFloat SmallestDenorm = APFloat::getSmallest(APFloat::Float8E4M3FN(), false);
6547 EXPECT_TRUE(SmallestDenorm.isDenormal());
6548 EXPECT_EQ(0x1.p-9, SmallestDenorm.convertToFloat());
6550 APFloat QNaN = APFloat::getQNaN(APFloat::Float8E4M3FN());
6551 EXPECT_TRUE(std::isnan(QNaN.convertToFloat()));
6554 TEST(APFloatTest, FloatTF32ToFloat) {
6555 APFloat PosZero = APFloat::getZero(APFloat::FloatTF32());
6556 APFloat PosZeroToFloat(PosZero.convertToFloat());
6557 EXPECT_TRUE(PosZeroToFloat.isPosZero());
6558 APFloat NegZero = APFloat::getZero(APFloat::FloatTF32(), true);
6559 APFloat NegZeroToFloat(NegZero.convertToFloat());
6560 EXPECT_TRUE(NegZeroToFloat.isNegZero());
6562 APFloat One(APFloat::FloatTF32(), "1.0");
6563 EXPECT_EQ(1.0F, One.convertToFloat());
6564 APFloat Two(APFloat::FloatTF32(), "2.0");
6565 EXPECT_EQ(2.0F, Two.convertToFloat());
6567 APFloat PosLargest = APFloat::getLargest(APFloat::FloatTF32(), false);
6568 EXPECT_EQ(3.40116213421e+38F, PosLargest.convertToFloat());
6570 APFloat NegLargest = APFloat::getLargest(APFloat::FloatTF32(), true);
6571 EXPECT_EQ(-3.40116213421e+38F, NegLargest.convertToFloat());
6573 APFloat PosSmallest =
6574 APFloat::getSmallestNormalized(APFloat::FloatTF32(), false);
6575 EXPECT_EQ(/*0x1.p-126*/ 1.1754943508222875e-38F,
6576 PosSmallest.convertToFloat());
6577 APFloat NegSmallest =
6578 APFloat::getSmallestNormalized(APFloat::FloatTF32(), true);
6579 EXPECT_EQ(/*-0x1.p-126*/ -1.1754943508222875e-38F,
6580 NegSmallest.convertToFloat());
6582 APFloat SmallestDenorm = APFloat::getSmallest(APFloat::FloatTF32(), false);
6583 EXPECT_TRUE(SmallestDenorm.isDenormal());
6584 EXPECT_EQ(0x0.004p-126, SmallestDenorm.convertToFloat());
6586 APFloat QNaN = APFloat::getQNaN(APFloat::FloatTF32());
6587 EXPECT_TRUE(std::isnan(QNaN.convertToFloat()));
6590 TEST(APFloatTest, getExactLog2) {
6591 for (unsigned I = 0; I != APFloat::S_MaxSemantics + 1; ++I) {
6592 auto SemEnum = static_cast<APFloat::Semantics>(I);
6593 const fltSemantics &Semantics = APFloat::EnumToSemantics(SemEnum);
6595 APFloat One(Semantics, "1.0");
6597 if (I == APFloat::S_PPCDoubleDouble) {
6598 // Not implemented
6599 EXPECT_EQ(INT_MIN, One.getExactLog2());
6600 EXPECT_EQ(INT_MIN, One.getExactLog2Abs());
6601 continue;
6604 int MinExp = APFloat::semanticsMinExponent(Semantics);
6605 int MaxExp = APFloat::semanticsMaxExponent(Semantics);
6606 int Precision = APFloat::semanticsPrecision(Semantics);
6608 EXPECT_EQ(0, One.getExactLog2());
6609 EXPECT_EQ(INT_MIN, APFloat(Semantics, "3.0").getExactLog2());
6610 EXPECT_EQ(INT_MIN, APFloat(Semantics, "-3.0").getExactLog2());
6611 EXPECT_EQ(INT_MIN, APFloat(Semantics, "3.0").getExactLog2Abs());
6612 EXPECT_EQ(INT_MIN, APFloat(Semantics, "-3.0").getExactLog2Abs());
6613 EXPECT_EQ(3, APFloat(Semantics, "8.0").getExactLog2());
6614 EXPECT_EQ(INT_MIN, APFloat(Semantics, "-8.0").getExactLog2());
6615 EXPECT_EQ(-2, APFloat(Semantics, "0.25").getExactLog2());
6616 EXPECT_EQ(-2, APFloat(Semantics, "0.25").getExactLog2Abs());
6617 EXPECT_EQ(INT_MIN, APFloat(Semantics, "-0.25").getExactLog2());
6618 EXPECT_EQ(-2, APFloat(Semantics, "-0.25").getExactLog2Abs());
6619 EXPECT_EQ(3, APFloat(Semantics, "8.0").getExactLog2Abs());
6620 EXPECT_EQ(3, APFloat(Semantics, "-8.0").getExactLog2Abs());
6622 EXPECT_EQ(INT_MIN, APFloat::getZero(Semantics, false).getExactLog2());
6623 EXPECT_EQ(INT_MIN, APFloat::getZero(Semantics, true).getExactLog2());
6624 EXPECT_EQ(INT_MIN, APFloat::getInf(Semantics).getExactLog2());
6625 EXPECT_EQ(INT_MIN, APFloat::getInf(Semantics, true).getExactLog2());
6626 EXPECT_EQ(INT_MIN, APFloat::getNaN(Semantics, false).getExactLog2());
6627 EXPECT_EQ(INT_MIN, APFloat::getNaN(Semantics, true).getExactLog2());
6629 EXPECT_EQ(INT_MIN, APFloat::getZero(Semantics, false).getExactLog2Abs());
6630 EXPECT_EQ(INT_MIN, APFloat::getZero(Semantics, true).getExactLog2Abs());
6631 EXPECT_EQ(INT_MIN, APFloat::getInf(Semantics).getExactLog2Abs());
6632 EXPECT_EQ(INT_MIN, APFloat::getInf(Semantics, true).getExactLog2Abs());
6633 EXPECT_EQ(INT_MIN, APFloat::getNaN(Semantics, false).getExactLog2Abs());
6634 EXPECT_EQ(INT_MIN, APFloat::getNaN(Semantics, true).getExactLog2Abs());
6636 EXPECT_EQ(INT_MIN,
6637 scalbn(One, MinExp - Precision - 1, APFloat::rmNearestTiesToEven)
6638 .getExactLog2());
6639 EXPECT_EQ(INT_MIN,
6640 scalbn(One, MinExp - Precision, APFloat::rmNearestTiesToEven)
6641 .getExactLog2());
6643 EXPECT_EQ(
6644 INT_MIN,
6645 scalbn(One, MaxExp + 1, APFloat::rmNearestTiesToEven).getExactLog2());
6647 for (int i = MinExp - Precision + 1; i <= MaxExp; ++i) {
6648 EXPECT_EQ(i, scalbn(One, i, APFloat::rmNearestTiesToEven).getExactLog2());
6653 } // namespace