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 //===----------------------------------------------------------------------===//
8
9 #include "llvm/ADT/APFloat.h"
10 #include "llvm/ADT/APSInt.h"
11 #include "llvm/ADT/Hashing.h"
12 #include "llvm/ADT/SmallVector.h"
13 #include "llvm/Support/Error.h"
14 #include "llvm/Support/FormatVariadic.h"
15 #include "gtest/gtest.h"
16 #include <cmath>
17 #include <ostream>
18 #include <string>
19 #include <tuple>
20
21 using namespace llvm;
22
convertToErrorFromString(StringRef Str)23 static std::string convertToErrorFromString(StringRef Str) {
24 llvm::APFloat F(0.0);
25 auto StatusOrErr =
26 F.convertFromString(Str, llvm::APFloat::rmNearestTiesToEven);
27 EXPECT_TRUE(!StatusOrErr);
28 return toString(StatusOrErr.takeError());
29 }
30
convertToDoubleFromString(StringRef Str)31 static double convertToDoubleFromString(StringRef Str) {
32 llvm::APFloat F(0.0);
33 auto StatusOrErr =
34 F.convertFromString(Str, llvm::APFloat::rmNearestTiesToEven);
35 EXPECT_FALSE(!StatusOrErr);
36 consumeError(StatusOrErr.takeError());
37 return F.convertToDouble();
38 }
39
convertToString(double d,unsigned Prec,unsigned Pad,bool Tr=true)40 static std::string convertToString(double d, unsigned Prec, unsigned Pad,
41 bool Tr = true) {
42 llvm::SmallVector<char, 100> Buffer;
43 llvm::APFloat F(d);
44 F.toString(Buffer, Prec, Pad, Tr);
45 return std::string(Buffer.data(), Buffer.size());
46 }
47
48 namespace {
49
TEST(APFloatTest,isSignaling)50 TEST(APFloatTest, isSignaling) {
51 // We test qNaN, -qNaN, +sNaN, -sNaN with and without payloads. *NOTE* The
52 // positive/negative distinction is included only since the getQNaN/getSNaN
53 // API provides the option.
54 APInt payload = APInt::getOneBitSet(4, 2);
55 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), false).isSignaling());
56 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), true).isSignaling());
57 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), false, &payload).isSignaling());
58 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), true, &payload).isSignaling());
59 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isSignaling());
60 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isSignaling());
61 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false, &payload).isSignaling());
62 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true, &payload).isSignaling());
63 }
64
TEST(APFloatTest,next)65 TEST(APFloatTest, next) {
66
67 APFloat test(APFloat::IEEEquad(), APFloat::uninitialized);
68 APFloat expected(APFloat::IEEEquad(), APFloat::uninitialized);
69
70 // 1. Test Special Cases Values.
71 //
72 // Test all special values for nextUp and nextDown perscribed by IEEE-754R
73 // 2008. These are:
74 // 1. +inf
75 // 2. -inf
76 // 3. getLargest()
77 // 4. -getLargest()
78 // 5. getSmallest()
79 // 6. -getSmallest()
80 // 7. qNaN
81 // 8. sNaN
82 // 9. +0
83 // 10. -0
84
85 // nextUp(+inf) = +inf.
86 test = APFloat::getInf(APFloat::IEEEquad(), false);
87 expected = APFloat::getInf(APFloat::IEEEquad(), false);
88 EXPECT_EQ(test.next(false), APFloat::opOK);
89 EXPECT_TRUE(test.isInfinity());
90 EXPECT_TRUE(!test.isNegative());
91 EXPECT_TRUE(test.bitwiseIsEqual(expected));
92
93 // nextDown(+inf) = -nextUp(-inf) = -(-getLargest()) = getLargest()
94 test = APFloat::getInf(APFloat::IEEEquad(), false);
95 expected = APFloat::getLargest(APFloat::IEEEquad(), false);
96 EXPECT_EQ(test.next(true), APFloat::opOK);
97 EXPECT_TRUE(!test.isNegative());
98 EXPECT_TRUE(test.bitwiseIsEqual(expected));
99
100 // nextUp(-inf) = -getLargest()
101 test = APFloat::getInf(APFloat::IEEEquad(), true);
102 expected = APFloat::getLargest(APFloat::IEEEquad(), true);
103 EXPECT_EQ(test.next(false), APFloat::opOK);
104 EXPECT_TRUE(test.isNegative());
105 EXPECT_TRUE(test.bitwiseIsEqual(expected));
106
107 // nextDown(-inf) = -nextUp(+inf) = -(+inf) = -inf.
108 test = APFloat::getInf(APFloat::IEEEquad(), true);
109 expected = APFloat::getInf(APFloat::IEEEquad(), true);
110 EXPECT_EQ(test.next(true), APFloat::opOK);
111 EXPECT_TRUE(test.isInfinity() && test.isNegative());
112 EXPECT_TRUE(test.bitwiseIsEqual(expected));
113
114 // nextUp(getLargest()) = +inf
115 test = APFloat::getLargest(APFloat::IEEEquad(), false);
116 expected = APFloat::getInf(APFloat::IEEEquad(), false);
117 EXPECT_EQ(test.next(false), APFloat::opOK);
118 EXPECT_TRUE(test.isInfinity() && !test.isNegative());
119 EXPECT_TRUE(test.bitwiseIsEqual(expected));
120
121 // nextDown(getLargest()) = -nextUp(-getLargest())
122 // = -(-getLargest() + inc)
123 // = getLargest() - inc.
124 test = APFloat::getLargest(APFloat::IEEEquad(), false);
125 expected = APFloat(APFloat::IEEEquad(),
126 "0x1.fffffffffffffffffffffffffffep+16383");
127 EXPECT_EQ(test.next(true), APFloat::opOK);
128 EXPECT_TRUE(!test.isInfinity() && !test.isNegative());
129 EXPECT_TRUE(test.bitwiseIsEqual(expected));
130
131 // nextUp(-getLargest()) = -getLargest() + inc.
132 test = APFloat::getLargest(APFloat::IEEEquad(), true);
133 expected = APFloat(APFloat::IEEEquad(),
134 "-0x1.fffffffffffffffffffffffffffep+16383");
135 EXPECT_EQ(test.next(false), APFloat::opOK);
136 EXPECT_TRUE(test.bitwiseIsEqual(expected));
137
138 // nextDown(-getLargest()) = -nextUp(getLargest()) = -(inf) = -inf.
139 test = APFloat::getLargest(APFloat::IEEEquad(), true);
140 expected = APFloat::getInf(APFloat::IEEEquad(), true);
141 EXPECT_EQ(test.next(true), APFloat::opOK);
142 EXPECT_TRUE(test.isInfinity() && test.isNegative());
143 EXPECT_TRUE(test.bitwiseIsEqual(expected));
144
145 // nextUp(getSmallest()) = getSmallest() + inc.
146 test = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
147 expected = APFloat(APFloat::IEEEquad(),
148 "0x0.0000000000000000000000000002p-16382");
149 EXPECT_EQ(test.next(false), APFloat::opOK);
150 EXPECT_TRUE(test.bitwiseIsEqual(expected));
151
152 // nextDown(getSmallest()) = -nextUp(-getSmallest()) = -(-0) = +0.
153 test = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
154 expected = APFloat::getZero(APFloat::IEEEquad(), false);
155 EXPECT_EQ(test.next(true), APFloat::opOK);
156 EXPECT_TRUE(test.isPosZero());
157 EXPECT_TRUE(test.bitwiseIsEqual(expected));
158
159 // nextUp(-getSmallest()) = -0.
160 test = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
161 expected = APFloat::getZero(APFloat::IEEEquad(), true);
162 EXPECT_EQ(test.next(false), APFloat::opOK);
163 EXPECT_TRUE(test.isNegZero());
164 EXPECT_TRUE(test.bitwiseIsEqual(expected));
165
166 // nextDown(-getSmallest()) = -nextUp(getSmallest()) = -getSmallest() - inc.
167 test = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
168 expected = APFloat(APFloat::IEEEquad(),
169 "-0x0.0000000000000000000000000002p-16382");
170 EXPECT_EQ(test.next(true), APFloat::opOK);
171 EXPECT_TRUE(test.bitwiseIsEqual(expected));
172
173 // nextUp(qNaN) = qNaN
174 test = APFloat::getQNaN(APFloat::IEEEquad(), false);
175 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
176 EXPECT_EQ(test.next(false), APFloat::opOK);
177 EXPECT_TRUE(test.bitwiseIsEqual(expected));
178
179 // nextDown(qNaN) = qNaN
180 test = APFloat::getQNaN(APFloat::IEEEquad(), false);
181 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
182 EXPECT_EQ(test.next(true), APFloat::opOK);
183 EXPECT_TRUE(test.bitwiseIsEqual(expected));
184
185 // nextUp(sNaN) = qNaN
186 test = APFloat::getSNaN(APFloat::IEEEquad(), false);
187 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
188 EXPECT_EQ(test.next(false), APFloat::opInvalidOp);
189 EXPECT_TRUE(test.bitwiseIsEqual(expected));
190
191 // nextDown(sNaN) = qNaN
192 test = APFloat::getSNaN(APFloat::IEEEquad(), false);
193 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
194 EXPECT_EQ(test.next(true), APFloat::opInvalidOp);
195 EXPECT_TRUE(test.bitwiseIsEqual(expected));
196
197 // nextUp(+0) = +getSmallest()
198 test = APFloat::getZero(APFloat::IEEEquad(), false);
199 expected = APFloat::getSmallest(APFloat::IEEEquad(), false);
200 EXPECT_EQ(test.next(false), APFloat::opOK);
201 EXPECT_TRUE(test.bitwiseIsEqual(expected));
202
203 // nextDown(+0) = -nextUp(-0) = -getSmallest()
204 test = APFloat::getZero(APFloat::IEEEquad(), false);
205 expected = APFloat::getSmallest(APFloat::IEEEquad(), true);
206 EXPECT_EQ(test.next(true), APFloat::opOK);
207 EXPECT_TRUE(test.bitwiseIsEqual(expected));
208
209 // nextUp(-0) = +getSmallest()
210 test = APFloat::getZero(APFloat::IEEEquad(), true);
211 expected = APFloat::getSmallest(APFloat::IEEEquad(), false);
212 EXPECT_EQ(test.next(false), APFloat::opOK);
213 EXPECT_TRUE(test.bitwiseIsEqual(expected));
214
215 // nextDown(-0) = -nextUp(0) = -getSmallest()
216 test = APFloat::getZero(APFloat::IEEEquad(), true);
217 expected = APFloat::getSmallest(APFloat::IEEEquad(), true);
218 EXPECT_EQ(test.next(true), APFloat::opOK);
219 EXPECT_TRUE(test.bitwiseIsEqual(expected));
220
221 // 2. Binade Boundary Tests.
222
223 // 2a. Test denormal <-> normal binade boundaries.
224 // * nextUp(+Largest Denormal) -> +Smallest Normal.
225 // * nextDown(-Largest Denormal) -> -Smallest Normal.
226 // * nextUp(-Smallest Normal) -> -Largest Denormal.
227 // * nextDown(+Smallest Normal) -> +Largest Denormal.
228
229 // nextUp(+Largest Denormal) -> +Smallest Normal.
230 test = APFloat(APFloat::IEEEquad(), "0x0.ffffffffffffffffffffffffffffp-16382");
231 expected = APFloat(APFloat::IEEEquad(),
232 "0x1.0000000000000000000000000000p-16382");
233 EXPECT_EQ(test.next(false), APFloat::opOK);
234 EXPECT_FALSE(test.isDenormal());
235 EXPECT_TRUE(test.bitwiseIsEqual(expected));
236
237 // nextDown(-Largest Denormal) -> -Smallest Normal.
238 test = APFloat(APFloat::IEEEquad(),
239 "-0x0.ffffffffffffffffffffffffffffp-16382");
240 expected = APFloat(APFloat::IEEEquad(),
241 "-0x1.0000000000000000000000000000p-16382");
242 EXPECT_EQ(test.next(true), APFloat::opOK);
243 EXPECT_FALSE(test.isDenormal());
244 EXPECT_TRUE(test.bitwiseIsEqual(expected));
245
246 // nextUp(-Smallest Normal) -> -LargestDenormal.
247 test = APFloat(APFloat::IEEEquad(),
248 "-0x1.0000000000000000000000000000p-16382");
249 expected = APFloat(APFloat::IEEEquad(),
250 "-0x0.ffffffffffffffffffffffffffffp-16382");
251 EXPECT_EQ(test.next(false), APFloat::opOK);
252 EXPECT_TRUE(test.isDenormal());
253 EXPECT_TRUE(test.bitwiseIsEqual(expected));
254
255 // nextDown(+Smallest Normal) -> +Largest Denormal.
256 test = APFloat(APFloat::IEEEquad(),
257 "+0x1.0000000000000000000000000000p-16382");
258 expected = APFloat(APFloat::IEEEquad(),
259 "+0x0.ffffffffffffffffffffffffffffp-16382");
260 EXPECT_EQ(test.next(true), APFloat::opOK);
261 EXPECT_TRUE(test.isDenormal());
262 EXPECT_TRUE(test.bitwiseIsEqual(expected));
263
264 // 2b. Test normal <-> normal binade boundaries.
265 // * nextUp(-Normal Binade Boundary) -> -Normal Binade Boundary + 1.
266 // * nextDown(+Normal Binade Boundary) -> +Normal Binade Boundary - 1.
267 // * nextUp(+Normal Binade Boundary - 1) -> +Normal Binade Boundary.
268 // * nextDown(-Normal Binade Boundary + 1) -> -Normal Binade Boundary.
269
270 // nextUp(-Normal Binade Boundary) -> -Normal Binade Boundary + 1.
271 test = APFloat(APFloat::IEEEquad(), "-0x1p+1");
272 expected = APFloat(APFloat::IEEEquad(),
273 "-0x1.ffffffffffffffffffffffffffffp+0");
274 EXPECT_EQ(test.next(false), APFloat::opOK);
275 EXPECT_TRUE(test.bitwiseIsEqual(expected));
276
277 // nextDown(+Normal Binade Boundary) -> +Normal Binade Boundary - 1.
278 test = APFloat(APFloat::IEEEquad(), "0x1p+1");
279 expected = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp+0");
280 EXPECT_EQ(test.next(true), APFloat::opOK);
281 EXPECT_TRUE(test.bitwiseIsEqual(expected));
282
283 // nextUp(+Normal Binade Boundary - 1) -> +Normal Binade Boundary.
284 test = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp+0");
285 expected = APFloat(APFloat::IEEEquad(), "0x1p+1");
286 EXPECT_EQ(test.next(false), APFloat::opOK);
287 EXPECT_TRUE(test.bitwiseIsEqual(expected));
288
289 // nextDown(-Normal Binade Boundary + 1) -> -Normal Binade Boundary.
290 test = APFloat(APFloat::IEEEquad(), "-0x1.ffffffffffffffffffffffffffffp+0");
291 expected = APFloat(APFloat::IEEEquad(), "-0x1p+1");
292 EXPECT_EQ(test.next(true), APFloat::opOK);
293 EXPECT_TRUE(test.bitwiseIsEqual(expected));
294
295 // 2c. Test using next at binade boundaries with a direction away from the
296 // binade boundary. Away from denormal <-> normal boundaries.
297 //
298 // This is to make sure that even though we are at a binade boundary, since
299 // we are rounding away, we do not trigger the binade boundary code. Thus we
300 // test:
301 // * nextUp(-Largest Denormal) -> -Largest Denormal + inc.
302 // * nextDown(+Largest Denormal) -> +Largest Denormal - inc.
303 // * nextUp(+Smallest Normal) -> +Smallest Normal + inc.
304 // * nextDown(-Smallest Normal) -> -Smallest Normal - inc.
305
306 // nextUp(-Largest Denormal) -> -Largest Denormal + inc.
307 test = APFloat(APFloat::IEEEquad(), "-0x0.ffffffffffffffffffffffffffffp-16382");
308 expected = APFloat(APFloat::IEEEquad(),
309 "-0x0.fffffffffffffffffffffffffffep-16382");
310 EXPECT_EQ(test.next(false), APFloat::opOK);
311 EXPECT_TRUE(test.isDenormal());
312 EXPECT_TRUE(test.isNegative());
313 EXPECT_TRUE(test.bitwiseIsEqual(expected));
314
315 // nextDown(+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(true), APFloat::opOK);
320 EXPECT_TRUE(test.isDenormal());
321 EXPECT_TRUE(!test.isNegative());
322 EXPECT_TRUE(test.bitwiseIsEqual(expected));
323
324 // nextUp(+Smallest Normal) -> +Smallest Normal + inc.
325 test = APFloat(APFloat::IEEEquad(), "0x1.0000000000000000000000000000p-16382");
326 expected = APFloat(APFloat::IEEEquad(),
327 "0x1.0000000000000000000000000001p-16382");
328 EXPECT_EQ(test.next(false), APFloat::opOK);
329 EXPECT_TRUE(!test.isDenormal());
330 EXPECT_TRUE(!test.isNegative());
331 EXPECT_TRUE(test.bitwiseIsEqual(expected));
332
333 // nextDown(-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(true), APFloat::opOK);
338 EXPECT_TRUE(!test.isDenormal());
339 EXPECT_TRUE(test.isNegative());
340 EXPECT_TRUE(test.bitwiseIsEqual(expected));
341
342 // 2d. Test values which cause our exponent to go to min exponent. This
343 // is to ensure that guards in the code to check for min exponent
344 // trigger properly.
345 // * nextUp(-0x1p-16381) -> -0x1.ffffffffffffffffffffffffffffp-16382
346 // * nextDown(-0x1.ffffffffffffffffffffffffffffp-16382) ->
347 // -0x1p-16381
348 // * nextUp(0x1.ffffffffffffffffffffffffffffp-16382) -> 0x1p-16382
349 // * nextDown(0x1p-16382) -> 0x1.ffffffffffffffffffffffffffffp-16382
350
351 // nextUp(-0x1p-16381) -> -0x1.ffffffffffffffffffffffffffffp-16382
352 test = APFloat(APFloat::IEEEquad(), "-0x1p-16381");
353 expected = APFloat(APFloat::IEEEquad(),
354 "-0x1.ffffffffffffffffffffffffffffp-16382");
355 EXPECT_EQ(test.next(false), APFloat::opOK);
356 EXPECT_TRUE(test.bitwiseIsEqual(expected));
357
358 // nextDown(-0x1.ffffffffffffffffffffffffffffp-16382) ->
359 // -0x1p-16381
360 test = APFloat(APFloat::IEEEquad(), "-0x1.ffffffffffffffffffffffffffffp-16382");
361 expected = APFloat(APFloat::IEEEquad(), "-0x1p-16381");
362 EXPECT_EQ(test.next(true), APFloat::opOK);
363 EXPECT_TRUE(test.bitwiseIsEqual(expected));
364
365 // nextUp(0x1.ffffffffffffffffffffffffffffp-16382) -> 0x1p-16381
366 test = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp-16382");
367 expected = APFloat(APFloat::IEEEquad(), "0x1p-16381");
368 EXPECT_EQ(test.next(false), APFloat::opOK);
369 EXPECT_TRUE(test.bitwiseIsEqual(expected));
370
371 // nextDown(0x1p-16381) -> 0x1.ffffffffffffffffffffffffffffp-16382
372 test = APFloat(APFloat::IEEEquad(), "0x1p-16381");
373 expected = APFloat(APFloat::IEEEquad(),
374 "0x1.ffffffffffffffffffffffffffffp-16382");
375 EXPECT_EQ(test.next(true), APFloat::opOK);
376 EXPECT_TRUE(test.bitwiseIsEqual(expected));
377
378 // 3. Now we test both denormal/normal computation which will not cause us
379 // to go across binade boundaries. Specifically we test:
380 // * nextUp(+Denormal) -> +Denormal.
381 // * nextDown(+Denormal) -> +Denormal.
382 // * nextUp(-Denormal) -> -Denormal.
383 // * nextDown(-Denormal) -> -Denormal.
384 // * nextUp(+Normal) -> +Normal.
385 // * nextDown(+Normal) -> +Normal.
386 // * nextUp(-Normal) -> -Normal.
387 // * nextDown(-Normal) -> -Normal.
388
389 // nextUp(+Denormal) -> +Denormal.
390 test = APFloat(APFloat::IEEEquad(),
391 "0x0.ffffffffffffffffffffffff000cp-16382");
392 expected = APFloat(APFloat::IEEEquad(),
393 "0x0.ffffffffffffffffffffffff000dp-16382");
394 EXPECT_EQ(test.next(false), APFloat::opOK);
395 EXPECT_TRUE(test.isDenormal());
396 EXPECT_TRUE(!test.isNegative());
397 EXPECT_TRUE(test.bitwiseIsEqual(expected));
398
399 // nextDown(+Denormal) -> +Denormal.
400 test = APFloat(APFloat::IEEEquad(),
401 "0x0.ffffffffffffffffffffffff000cp-16382");
402 expected = APFloat(APFloat::IEEEquad(),
403 "0x0.ffffffffffffffffffffffff000bp-16382");
404 EXPECT_EQ(test.next(true), APFloat::opOK);
405 EXPECT_TRUE(test.isDenormal());
406 EXPECT_TRUE(!test.isNegative());
407 EXPECT_TRUE(test.bitwiseIsEqual(expected));
408
409 // nextUp(-Denormal) -> -Denormal.
410 test = APFloat(APFloat::IEEEquad(),
411 "-0x0.ffffffffffffffffffffffff000cp-16382");
412 expected = APFloat(APFloat::IEEEquad(),
413 "-0x0.ffffffffffffffffffffffff000bp-16382");
414 EXPECT_EQ(test.next(false), APFloat::opOK);
415 EXPECT_TRUE(test.isDenormal());
416 EXPECT_TRUE(test.isNegative());
417 EXPECT_TRUE(test.bitwiseIsEqual(expected));
418
419 // nextDown(-Denormal) -> -Denormal
420 test = APFloat(APFloat::IEEEquad(),
421 "-0x0.ffffffffffffffffffffffff000cp-16382");
422 expected = APFloat(APFloat::IEEEquad(),
423 "-0x0.ffffffffffffffffffffffff000dp-16382");
424 EXPECT_EQ(test.next(true), APFloat::opOK);
425 EXPECT_TRUE(test.isDenormal());
426 EXPECT_TRUE(test.isNegative());
427 EXPECT_TRUE(test.bitwiseIsEqual(expected));
428
429 // nextUp(+Normal) -> +Normal.
430 test = APFloat(APFloat::IEEEquad(),
431 "0x1.ffffffffffffffffffffffff000cp-16000");
432 expected = APFloat(APFloat::IEEEquad(),
433 "0x1.ffffffffffffffffffffffff000dp-16000");
434 EXPECT_EQ(test.next(false), APFloat::opOK);
435 EXPECT_TRUE(!test.isDenormal());
436 EXPECT_TRUE(!test.isNegative());
437 EXPECT_TRUE(test.bitwiseIsEqual(expected));
438
439 // nextDown(+Normal) -> +Normal.
440 test = APFloat(APFloat::IEEEquad(),
441 "0x1.ffffffffffffffffffffffff000cp-16000");
442 expected = APFloat(APFloat::IEEEquad(),
443 "0x1.ffffffffffffffffffffffff000bp-16000");
444 EXPECT_EQ(test.next(true), APFloat::opOK);
445 EXPECT_TRUE(!test.isDenormal());
446 EXPECT_TRUE(!test.isNegative());
447 EXPECT_TRUE(test.bitwiseIsEqual(expected));
448
449 // nextUp(-Normal) -> -Normal.
450 test = APFloat(APFloat::IEEEquad(),
451 "-0x1.ffffffffffffffffffffffff000cp-16000");
452 expected = APFloat(APFloat::IEEEquad(),
453 "-0x1.ffffffffffffffffffffffff000bp-16000");
454 EXPECT_EQ(test.next(false), APFloat::opOK);
455 EXPECT_TRUE(!test.isDenormal());
456 EXPECT_TRUE(test.isNegative());
457 EXPECT_TRUE(test.bitwiseIsEqual(expected));
458
459 // nextDown(-Normal) -> -Normal.
460 test = APFloat(APFloat::IEEEquad(),
461 "-0x1.ffffffffffffffffffffffff000cp-16000");
462 expected = APFloat(APFloat::IEEEquad(),
463 "-0x1.ffffffffffffffffffffffff000dp-16000");
464 EXPECT_EQ(test.next(true), APFloat::opOK);
465 EXPECT_TRUE(!test.isDenormal());
466 EXPECT_TRUE(test.isNegative());
467 EXPECT_TRUE(test.bitwiseIsEqual(expected));
468 }
469
TEST(APFloatTest,FMA)470 TEST(APFloatTest, FMA) {
471 APFloat::roundingMode rdmd = APFloat::rmNearestTiesToEven;
472
473 {
474 APFloat f1(14.5f);
475 APFloat f2(-14.5f);
476 APFloat f3(225.0f);
477 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
478 EXPECT_EQ(14.75f, f1.convertToFloat());
479 }
480
481 {
482 APFloat Val2(2.0f);
483 APFloat f1((float)1.17549435e-38F);
484 APFloat f2((float)1.17549435e-38F);
485 f1.divide(Val2, rdmd);
486 f2.divide(Val2, rdmd);
487 APFloat f3(12.0f);
488 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
489 EXPECT_EQ(12.0f, f1.convertToFloat());
490 }
491
492 // Test for correct zero sign when answer is exactly zero.
493 // fma(1.0, -1.0, 1.0) -> +ve 0.
494 {
495 APFloat f1(1.0);
496 APFloat f2(-1.0);
497 APFloat f3(1.0);
498 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
499 EXPECT_TRUE(!f1.isNegative() && f1.isZero());
500 }
501
502 // Test for correct zero sign when answer is exactly zero and rounding towards
503 // negative.
504 // fma(1.0, -1.0, 1.0) -> +ve 0.
505 {
506 APFloat f1(1.0);
507 APFloat f2(-1.0);
508 APFloat f3(1.0);
509 f1.fusedMultiplyAdd(f2, f3, APFloat::rmTowardNegative);
510 EXPECT_TRUE(f1.isNegative() && f1.isZero());
511 }
512
513 // Test for correct (in this case -ve) sign when adding like signed zeros.
514 // Test fma(0.0, -0.0, -0.0) -> -ve 0.
515 {
516 APFloat f1(0.0);
517 APFloat f2(-0.0);
518 APFloat f3(-0.0);
519 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
520 EXPECT_TRUE(f1.isNegative() && f1.isZero());
521 }
522
523 // Test -ve sign preservation when small negative results underflow.
524 {
525 APFloat f1(APFloat::IEEEdouble(), "-0x1p-1074");
526 APFloat f2(APFloat::IEEEdouble(), "+0x1p-1074");
527 APFloat f3(0.0);
528 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
529 EXPECT_TRUE(f1.isNegative() && f1.isZero());
530 }
531
532 // Test x87 extended precision case from http://llvm.org/PR20728.
533 {
534 APFloat M1(APFloat::x87DoubleExtended(), 1);
535 APFloat M2(APFloat::x87DoubleExtended(), 1);
536 APFloat A(APFloat::x87DoubleExtended(), 3);
537
538 bool losesInfo = false;
539 M1.fusedMultiplyAdd(M1, A, APFloat::rmNearestTiesToEven);
540 M1.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
541 EXPECT_FALSE(losesInfo);
542 EXPECT_EQ(4.0f, M1.convertToFloat());
543 }
544
545 // Regression test that failed an assertion.
546 {
547 APFloat f1(-8.85242279E-41f);
548 APFloat f2(2.0f);
549 APFloat f3(8.85242279E-41f);
550 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
551 EXPECT_EQ(-8.85242279E-41f, f1.convertToFloat());
552 }
553
554 // Test using only a single instance of APFloat.
555 {
556 APFloat F(1.5);
557
558 F.fusedMultiplyAdd(F, F, APFloat::rmNearestTiesToEven);
559 EXPECT_EQ(3.75, F.convertToDouble());
560 }
561 }
562
TEST(APFloatTest,MinNum)563 TEST(APFloatTest, MinNum) {
564 APFloat f1(1.0);
565 APFloat f2(2.0);
566 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
567
568 EXPECT_EQ(1.0, minnum(f1, f2).convertToDouble());
569 EXPECT_EQ(1.0, minnum(f2, f1).convertToDouble());
570 EXPECT_EQ(1.0, minnum(f1, nan).convertToDouble());
571 EXPECT_EQ(1.0, minnum(nan, f1).convertToDouble());
572 }
573
TEST(APFloatTest,MaxNum)574 TEST(APFloatTest, MaxNum) {
575 APFloat f1(1.0);
576 APFloat f2(2.0);
577 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
578
579 EXPECT_EQ(2.0, maxnum(f1, f2).convertToDouble());
580 EXPECT_EQ(2.0, maxnum(f2, f1).convertToDouble());
581 EXPECT_EQ(1.0, maxnum(f1, nan).convertToDouble());
582 EXPECT_EQ(1.0, maxnum(nan, f1).convertToDouble());
583 }
584
TEST(APFloatTest,Minimum)585 TEST(APFloatTest, Minimum) {
586 APFloat f1(1.0);
587 APFloat f2(2.0);
588 APFloat zp(0.0);
589 APFloat zn(-0.0);
590 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
591
592 EXPECT_EQ(1.0, minimum(f1, f2).convertToDouble());
593 EXPECT_EQ(1.0, minimum(f2, f1).convertToDouble());
594 EXPECT_EQ(-0.0, minimum(zp, zn).convertToDouble());
595 EXPECT_EQ(-0.0, minimum(zn, zp).convertToDouble());
596 EXPECT_TRUE(std::isnan(minimum(f1, nan).convertToDouble()));
597 EXPECT_TRUE(std::isnan(minimum(nan, f1).convertToDouble()));
598 }
599
TEST(APFloatTest,Maximum)600 TEST(APFloatTest, Maximum) {
601 APFloat f1(1.0);
602 APFloat f2(2.0);
603 APFloat zp(0.0);
604 APFloat zn(-0.0);
605 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
606
607 EXPECT_EQ(2.0, maximum(f1, f2).convertToDouble());
608 EXPECT_EQ(2.0, maximum(f2, f1).convertToDouble());
609 EXPECT_EQ(0.0, maximum(zp, zn).convertToDouble());
610 EXPECT_EQ(0.0, maximum(zn, zp).convertToDouble());
611 EXPECT_TRUE(std::isnan(maximum(f1, nan).convertToDouble()));
612 EXPECT_TRUE(std::isnan(maximum(nan, f1).convertToDouble()));
613 }
614
TEST(APFloatTest,Denormal)615 TEST(APFloatTest, Denormal) {
616 APFloat::roundingMode rdmd = APFloat::rmNearestTiesToEven;
617
618 // Test single precision
619 {
620 const char *MinNormalStr = "1.17549435082228750797e-38";
621 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), MinNormalStr).isDenormal());
622 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), 0).isDenormal());
623
624 APFloat Val2(APFloat::IEEEsingle(), 2);
625 APFloat T(APFloat::IEEEsingle(), MinNormalStr);
626 T.divide(Val2, rdmd);
627 EXPECT_TRUE(T.isDenormal());
628 }
629
630 // Test double precision
631 {
632 const char *MinNormalStr = "2.22507385850720138309e-308";
633 EXPECT_FALSE(APFloat(APFloat::IEEEdouble(), MinNormalStr).isDenormal());
634 EXPECT_FALSE(APFloat(APFloat::IEEEdouble(), 0).isDenormal());
635
636 APFloat Val2(APFloat::IEEEdouble(), 2);
637 APFloat T(APFloat::IEEEdouble(), MinNormalStr);
638 T.divide(Val2, rdmd);
639 EXPECT_TRUE(T.isDenormal());
640 }
641
642 // Test Intel double-ext
643 {
644 const char *MinNormalStr = "3.36210314311209350626e-4932";
645 EXPECT_FALSE(APFloat(APFloat::x87DoubleExtended(), MinNormalStr).isDenormal());
646 EXPECT_FALSE(APFloat(APFloat::x87DoubleExtended(), 0).isDenormal());
647
648 APFloat Val2(APFloat::x87DoubleExtended(), 2);
649 APFloat T(APFloat::x87DoubleExtended(), MinNormalStr);
650 T.divide(Val2, rdmd);
651 EXPECT_TRUE(T.isDenormal());
652 }
653
654 // Test quadruple precision
655 {
656 const char *MinNormalStr = "3.36210314311209350626267781732175260e-4932";
657 EXPECT_FALSE(APFloat(APFloat::IEEEquad(), MinNormalStr).isDenormal());
658 EXPECT_FALSE(APFloat(APFloat::IEEEquad(), 0).isDenormal());
659
660 APFloat Val2(APFloat::IEEEquad(), 2);
661 APFloat T(APFloat::IEEEquad(), MinNormalStr);
662 T.divide(Val2, rdmd);
663 EXPECT_TRUE(T.isDenormal());
664 }
665 }
666
TEST(APFloatTest,Zero)667 TEST(APFloatTest, Zero) {
668 EXPECT_EQ(0.0f, APFloat(0.0f).convertToFloat());
669 EXPECT_EQ(-0.0f, APFloat(-0.0f).convertToFloat());
670 EXPECT_TRUE(APFloat(-0.0f).isNegative());
671
672 EXPECT_EQ(0.0, APFloat(0.0).convertToDouble());
673 EXPECT_EQ(-0.0, APFloat(-0.0).convertToDouble());
674 EXPECT_TRUE(APFloat(-0.0).isNegative());
675 }
676
TEST(APFloatTest,DecimalStringsWithoutNullTerminators)677 TEST(APFloatTest, DecimalStringsWithoutNullTerminators) {
678 // Make sure that we can parse strings without null terminators.
679 // rdar://14323230.
680 EXPECT_EQ(convertToDoubleFromString(StringRef("0.00", 3)), 0.0);
681 EXPECT_EQ(convertToDoubleFromString(StringRef("0.01", 3)), 0.0);
682 EXPECT_EQ(convertToDoubleFromString(StringRef("0.09", 3)), 0.0);
683 EXPECT_EQ(convertToDoubleFromString(StringRef("0.095", 4)), 0.09);
684 EXPECT_EQ(convertToDoubleFromString(StringRef("0.00e+3", 7)), 0.00);
685 EXPECT_EQ(convertToDoubleFromString(StringRef("0e+3", 4)), 0.00);
686 }
687
TEST(APFloatTest,fromZeroDecimalString)688 TEST(APFloatTest, fromZeroDecimalString) {
689 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0").convertToDouble());
690 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0").convertToDouble());
691 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0").convertToDouble());
692
693 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.").convertToDouble());
694 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.").convertToDouble());
695 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.").convertToDouble());
696
697 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0").convertToDouble());
698 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0").convertToDouble());
699 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0").convertToDouble());
700
701 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0").convertToDouble());
702 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0").convertToDouble());
703 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0").convertToDouble());
704
705 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "00000.").convertToDouble());
706 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+00000.").convertToDouble());
707 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-00000.").convertToDouble());
708
709 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), ".00000").convertToDouble());
710 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.00000").convertToDouble());
711 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.00000").convertToDouble());
712
713 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0000.00000").convertToDouble());
714 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0000.00000").convertToDouble());
715 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0000.00000").convertToDouble());
716 }
717
TEST(APFloatTest,fromZeroDecimalSingleExponentString)718 TEST(APFloatTest, fromZeroDecimalSingleExponentString) {
719 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e1").convertToDouble());
720 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e1").convertToDouble());
721 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e1").convertToDouble());
722
723 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e+1").convertToDouble());
724 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e+1").convertToDouble());
725 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e+1").convertToDouble());
726
727 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e-1").convertToDouble());
728 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e-1").convertToDouble());
729 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e-1").convertToDouble());
730
731
732 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e1").convertToDouble());
733 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e1").convertToDouble());
734 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e1").convertToDouble());
735
736 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e+1").convertToDouble());
737 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e+1").convertToDouble());
738 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e+1").convertToDouble());
739
740 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e-1").convertToDouble());
741 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e-1").convertToDouble());
742 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e-1").convertToDouble());
743
744 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e1").convertToDouble());
745 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e1").convertToDouble());
746 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e1").convertToDouble());
747
748 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e+1").convertToDouble());
749 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e+1").convertToDouble());
750 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e+1").convertToDouble());
751
752 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e-1").convertToDouble());
753 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e-1").convertToDouble());
754 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e-1").convertToDouble());
755
756
757 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e1").convertToDouble());
758 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e1").convertToDouble());
759 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e1").convertToDouble());
760
761 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e+1").convertToDouble());
762 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e+1").convertToDouble());
763 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e+1").convertToDouble());
764
765 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e-1").convertToDouble());
766 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e-1").convertToDouble());
767 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e-1").convertToDouble());
768
769
770 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "000.0000e1").convertToDouble());
771 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+000.0000e+1").convertToDouble());
772 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-000.0000e+1").convertToDouble());
773 }
774
TEST(APFloatTest,fromZeroDecimalLargeExponentString)775 TEST(APFloatTest, fromZeroDecimalLargeExponentString) {
776 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e1234").convertToDouble());
777 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e1234").convertToDouble());
778 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e1234").convertToDouble());
779
780 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e+1234").convertToDouble());
781 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e+1234").convertToDouble());
782 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e+1234").convertToDouble());
783
784 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e-1234").convertToDouble());
785 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e-1234").convertToDouble());
786 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e-1234").convertToDouble());
787
788 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), "000.0000e1234").convertToDouble());
789 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), "000.0000e-1234").convertToDouble());
790
791 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), StringRef("0e1234" "\0" "2", 6)).convertToDouble());
792 }
793
TEST(APFloatTest,fromZeroHexadecimalString)794 TEST(APFloatTest, fromZeroHexadecimalString) {
795 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p1").convertToDouble());
796 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p1").convertToDouble());
797 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p1").convertToDouble());
798
799 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p+1").convertToDouble());
800 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p+1").convertToDouble());
801 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p+1").convertToDouble());
802
803 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p-1").convertToDouble());
804 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p-1").convertToDouble());
805 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p-1").convertToDouble());
806
807
808 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1").convertToDouble());
809 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p1").convertToDouble());
810 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p1").convertToDouble());
811
812 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p+1").convertToDouble());
813 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p+1").convertToDouble());
814 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p+1").convertToDouble());
815
816 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p-1").convertToDouble());
817 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p-1").convertToDouble());
818 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p-1").convertToDouble());
819
820
821 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p1").convertToDouble());
822 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p1").convertToDouble());
823 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p1").convertToDouble());
824
825 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p+1").convertToDouble());
826 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p+1").convertToDouble());
827 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p+1").convertToDouble());
828
829 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p-1").convertToDouble());
830 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p-1").convertToDouble());
831 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p-1").convertToDouble());
832
833
834 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p1").convertToDouble());
835 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p1").convertToDouble());
836 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p1").convertToDouble());
837
838 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p+1").convertToDouble());
839 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p+1").convertToDouble());
840 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p+1").convertToDouble());
841
842 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p-1").convertToDouble());
843 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p-1").convertToDouble());
844 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p-1").convertToDouble());
845
846
847 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x00000.p1").convertToDouble());
848 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0000.00000p1").convertToDouble());
849 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.00000p1").convertToDouble());
850 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1").convertToDouble());
851 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p1234").convertToDouble());
852 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p1234").convertToDouble());
853 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x00000.p1234").convertToDouble());
854 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0000.00000p1234").convertToDouble());
855 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.00000p1234").convertToDouble());
856 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1234").convertToDouble());
857 }
858
TEST(APFloatTest,fromDecimalString)859 TEST(APFloatTest, fromDecimalString) {
860 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1").convertToDouble());
861 EXPECT_EQ(2.0, APFloat(APFloat::IEEEdouble(), "2.").convertToDouble());
862 EXPECT_EQ(0.5, APFloat(APFloat::IEEEdouble(), ".5").convertToDouble());
863 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0").convertToDouble());
864 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-2").convertToDouble());
865 EXPECT_EQ(-4.0, APFloat(APFloat::IEEEdouble(), "-4.").convertToDouble());
866 EXPECT_EQ(-0.5, APFloat(APFloat::IEEEdouble(), "-.5").convertToDouble());
867 EXPECT_EQ(-1.5, APFloat(APFloat::IEEEdouble(), "-1.5").convertToDouble());
868 EXPECT_EQ(1.25e12, APFloat(APFloat::IEEEdouble(), "1.25e12").convertToDouble());
869 EXPECT_EQ(1.25e+12, APFloat(APFloat::IEEEdouble(), "1.25e+12").convertToDouble());
870 EXPECT_EQ(1.25e-12, APFloat(APFloat::IEEEdouble(), "1.25e-12").convertToDouble());
871 EXPECT_EQ(1024.0, APFloat(APFloat::IEEEdouble(), "1024.").convertToDouble());
872 EXPECT_EQ(1024.05, APFloat(APFloat::IEEEdouble(), "1024.05000").convertToDouble());
873 EXPECT_EQ(0.05, APFloat(APFloat::IEEEdouble(), ".05000").convertToDouble());
874 EXPECT_EQ(2.0, APFloat(APFloat::IEEEdouble(), "2.").convertToDouble());
875 EXPECT_EQ(2.0e2, APFloat(APFloat::IEEEdouble(), "2.e2").convertToDouble());
876 EXPECT_EQ(2.0e+2, APFloat(APFloat::IEEEdouble(), "2.e+2").convertToDouble());
877 EXPECT_EQ(2.0e-2, APFloat(APFloat::IEEEdouble(), "2.e-2").convertToDouble());
878 EXPECT_EQ(2.05e2, APFloat(APFloat::IEEEdouble(), "002.05000e2").convertToDouble());
879 EXPECT_EQ(2.05e+2, APFloat(APFloat::IEEEdouble(), "002.05000e+2").convertToDouble());
880 EXPECT_EQ(2.05e-2, APFloat(APFloat::IEEEdouble(), "002.05000e-2").convertToDouble());
881 EXPECT_EQ(2.05e12, APFloat(APFloat::IEEEdouble(), "002.05000e12").convertToDouble());
882 EXPECT_EQ(2.05e+12, APFloat(APFloat::IEEEdouble(), "002.05000e+12").convertToDouble());
883 EXPECT_EQ(2.05e-12, APFloat(APFloat::IEEEdouble(), "002.05000e-12").convertToDouble());
884
885 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1e").convertToDouble());
886 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "+1e").convertToDouble());
887 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-1e").convertToDouble());
888
889 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.e").convertToDouble());
890 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "+1.e").convertToDouble());
891 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-1.e").convertToDouble());
892
893 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), ".1e").convertToDouble());
894 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), "+.1e").convertToDouble());
895 EXPECT_EQ(-0.1, APFloat(APFloat::IEEEdouble(), "-.1e").convertToDouble());
896
897 EXPECT_EQ(1.1, APFloat(APFloat::IEEEdouble(), "1.1e").convertToDouble());
898 EXPECT_EQ(1.1, APFloat(APFloat::IEEEdouble(), "+1.1e").convertToDouble());
899 EXPECT_EQ(-1.1, APFloat(APFloat::IEEEdouble(), "-1.1e").convertToDouble());
900
901 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1e+").convertToDouble());
902 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1e-").convertToDouble());
903
904 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), ".1e").convertToDouble());
905 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), ".1e+").convertToDouble());
906 EXPECT_EQ(0.1, APFloat(APFloat::IEEEdouble(), ".1e-").convertToDouble());
907
908 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0e").convertToDouble());
909 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0e+").convertToDouble());
910 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0e-").convertToDouble());
911
912 // These are "carefully selected" to overflow the fast log-base
913 // calculations in APFloat.cpp
914 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "99e99999").isInfinity());
915 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-99e99999").isInfinity());
916 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "1e-99999").isPosZero());
917 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-1e-99999").isNegZero());
918
919 EXPECT_EQ(2.71828, convertToDoubleFromString("2.71828"));
920 }
921
TEST(APFloatTest,fromStringSpecials)922 TEST(APFloatTest, fromStringSpecials) {
923 const fltSemantics &Sem = APFloat::IEEEdouble();
924 const unsigned Precision = 53;
925 const unsigned PayloadBits = Precision - 2;
926 uint64_t PayloadMask = (uint64_t(1) << PayloadBits) - uint64_t(1);
927
928 uint64_t NaNPayloads[] = {
929 0,
930 1,
931 123,
932 0xDEADBEEF,
933 uint64_t(-2),
934 uint64_t(1) << PayloadBits, // overflow bit
935 uint64_t(1) << (PayloadBits - 1), // signaling bit
936 uint64_t(1) << (PayloadBits - 2) // highest possible bit
937 };
938
939 // Convert payload integer to decimal string representation.
940 std::string NaNPayloadDecStrings[array_lengthof(NaNPayloads)];
941 for (size_t I = 0; I < array_lengthof(NaNPayloads); ++I)
942 NaNPayloadDecStrings[I] = utostr(NaNPayloads[I]);
943
944 // Convert payload integer to hexadecimal string representation.
945 std::string NaNPayloadHexStrings[array_lengthof(NaNPayloads)];
946 for (size_t I = 0; I < array_lengthof(NaNPayloads); ++I)
947 NaNPayloadHexStrings[I] = "0x" + utohexstr(NaNPayloads[I]);
948
949 // Fix payloads to expected result.
950 for (uint64_t &Payload : NaNPayloads)
951 Payload &= PayloadMask;
952
953 // Signaling NaN must have a non-zero payload. In case a zero payload is
954 // requested, a default arbitrary payload is set instead. Save this payload
955 // for testing.
956 const uint64_t SNaNDefaultPayload =
957 APFloat::getSNaN(Sem).bitcastToAPInt().getZExtValue() & PayloadMask;
958
959 // Negative sign prefix (or none - for positive).
960 const char Signs[] = {0, '-'};
961
962 // "Signaling" prefix (or none - for "Quiet").
963 const char NaNTypes[] = {0, 's', 'S'};
964
965 const StringRef NaNStrings[] = {"nan", "NaN"};
966 for (StringRef NaNStr : NaNStrings)
967 for (char TypeChar : NaNTypes) {
968 bool Signaling = (TypeChar == 's' || TypeChar == 'S');
969
970 for (size_t J = 0; J < array_lengthof(NaNPayloads); ++J) {
971 uint64_t Payload = (Signaling && !NaNPayloads[J]) ? SNaNDefaultPayload
972 : NaNPayloads[J];
973 std::string &PayloadDec = NaNPayloadDecStrings[J];
974 std::string &PayloadHex = NaNPayloadHexStrings[J];
975
976 for (char SignChar : Signs) {
977 bool Negative = (SignChar == '-');
978
979 std::string TestStrings[5];
980 size_t NumTestStrings = 0;
981
982 std::string Prefix;
983 if (SignChar)
984 Prefix += SignChar;
985 if (TypeChar)
986 Prefix += TypeChar;
987 Prefix += NaNStr;
988
989 // Test without any paylod.
990 if (!Payload)
991 TestStrings[NumTestStrings++] = Prefix;
992
993 // Test with the payload as a suffix.
994 TestStrings[NumTestStrings++] = Prefix + PayloadDec;
995 TestStrings[NumTestStrings++] = Prefix + PayloadHex;
996
997 // Test with the payload inside parentheses.
998 TestStrings[NumTestStrings++] = Prefix + '(' + PayloadDec + ')';
999 TestStrings[NumTestStrings++] = Prefix + '(' + PayloadHex + ')';
1000
1001 for (size_t K = 0; K < NumTestStrings; ++K) {
1002 StringRef TestStr = TestStrings[K];
1003
1004 APFloat F(Sem);
1005 bool HasError = !F.convertFromString(
1006 TestStr, llvm::APFloat::rmNearestTiesToEven);
1007 EXPECT_FALSE(HasError);
1008 EXPECT_TRUE(F.isNaN());
1009 EXPECT_EQ(Signaling, F.isSignaling());
1010 EXPECT_EQ(Negative, F.isNegative());
1011 uint64_t PayloadResult =
1012 F.bitcastToAPInt().getZExtValue() & PayloadMask;
1013 EXPECT_EQ(Payload, PayloadResult);
1014 }
1015 }
1016 }
1017 }
1018
1019 const StringRef InfStrings[] = {"inf", "INFINITY", "+Inf",
1020 "-inf", "-INFINITY", "-Inf"};
1021 for (StringRef InfStr : InfStrings) {
1022 bool Negative = InfStr.front() == '-';
1023
1024 APFloat F(Sem);
1025 bool HasError =
1026 !F.convertFromString(InfStr, llvm::APFloat::rmNearestTiesToEven);
1027 EXPECT_FALSE(HasError);
1028 EXPECT_TRUE(F.isInfinity());
1029 EXPECT_EQ(Negative, F.isNegative());
1030 uint64_t PayloadResult = F.bitcastToAPInt().getZExtValue() & PayloadMask;
1031 EXPECT_EQ(UINT64_C(0), PayloadResult);
1032 }
1033 }
1034
TEST(APFloatTest,fromToStringSpecials)1035 TEST(APFloatTest, fromToStringSpecials) {
1036 auto expects = [] (const char *first, const char *second) {
1037 std::string roundtrip = convertToString(convertToDoubleFromString(second), 0, 3);
1038 EXPECT_STREQ(first, roundtrip.c_str());
1039 };
1040 expects("+Inf", "+Inf");
1041 expects("+Inf", "INFINITY");
1042 expects("+Inf", "inf");
1043 expects("-Inf", "-Inf");
1044 expects("-Inf", "-INFINITY");
1045 expects("-Inf", "-inf");
1046 expects("NaN", "NaN");
1047 expects("NaN", "nan");
1048 expects("NaN", "-NaN");
1049 expects("NaN", "-nan");
1050 }
1051
TEST(APFloatTest,fromHexadecimalString)1052 TEST(APFloatTest, fromHexadecimalString) {
1053 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p0").convertToDouble());
1054 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p0").convertToDouble());
1055 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p0").convertToDouble());
1056
1057 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p+0").convertToDouble());
1058 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p+0").convertToDouble());
1059 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p+0").convertToDouble());
1060
1061 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p-0").convertToDouble());
1062 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p-0").convertToDouble());
1063 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p-0").convertToDouble());
1064
1065
1066 EXPECT_EQ( 2.0, APFloat(APFloat::IEEEdouble(), "0x1p1").convertToDouble());
1067 EXPECT_EQ(+2.0, APFloat(APFloat::IEEEdouble(), "+0x1p1").convertToDouble());
1068 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-0x1p1").convertToDouble());
1069
1070 EXPECT_EQ( 2.0, APFloat(APFloat::IEEEdouble(), "0x1p+1").convertToDouble());
1071 EXPECT_EQ(+2.0, APFloat(APFloat::IEEEdouble(), "+0x1p+1").convertToDouble());
1072 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-0x1p+1").convertToDouble());
1073
1074 EXPECT_EQ( 0.5, APFloat(APFloat::IEEEdouble(), "0x1p-1").convertToDouble());
1075 EXPECT_EQ(+0.5, APFloat(APFloat::IEEEdouble(), "+0x1p-1").convertToDouble());
1076 EXPECT_EQ(-0.5, APFloat(APFloat::IEEEdouble(), "-0x1p-1").convertToDouble());
1077
1078
1079 EXPECT_EQ( 3.0, APFloat(APFloat::IEEEdouble(), "0x1.8p1").convertToDouble());
1080 EXPECT_EQ(+3.0, APFloat(APFloat::IEEEdouble(), "+0x1.8p1").convertToDouble());
1081 EXPECT_EQ(-3.0, APFloat(APFloat::IEEEdouble(), "-0x1.8p1").convertToDouble());
1082
1083 EXPECT_EQ( 3.0, APFloat(APFloat::IEEEdouble(), "0x1.8p+1").convertToDouble());
1084 EXPECT_EQ(+3.0, APFloat(APFloat::IEEEdouble(), "+0x1.8p+1").convertToDouble());
1085 EXPECT_EQ(-3.0, APFloat(APFloat::IEEEdouble(), "-0x1.8p+1").convertToDouble());
1086
1087 EXPECT_EQ( 0.75, APFloat(APFloat::IEEEdouble(), "0x1.8p-1").convertToDouble());
1088 EXPECT_EQ(+0.75, APFloat(APFloat::IEEEdouble(), "+0x1.8p-1").convertToDouble());
1089 EXPECT_EQ(-0.75, APFloat(APFloat::IEEEdouble(), "-0x1.8p-1").convertToDouble());
1090
1091
1092 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p1").convertToDouble());
1093 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p1").convertToDouble());
1094 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p1").convertToDouble());
1095
1096 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p+1").convertToDouble());
1097 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p+1").convertToDouble());
1098 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p+1").convertToDouble());
1099
1100 EXPECT_EQ( 2048.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p-1").convertToDouble());
1101 EXPECT_EQ(+2048.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p-1").convertToDouble());
1102 EXPECT_EQ(-2048.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p-1").convertToDouble());
1103
1104
1105 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000p1").convertToDouble());
1106 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000p1").convertToDouble());
1107 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000p1").convertToDouble());
1108
1109 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000p+1").convertToDouble());
1110 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000p+1").convertToDouble());
1111 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000p+1").convertToDouble());
1112
1113 EXPECT_EQ( 2048.0, APFloat(APFloat::IEEEdouble(), "0x1000p-1").convertToDouble());
1114 EXPECT_EQ(+2048.0, APFloat(APFloat::IEEEdouble(), "+0x1000p-1").convertToDouble());
1115 EXPECT_EQ(-2048.0, APFloat(APFloat::IEEEdouble(), "-0x1000p-1").convertToDouble());
1116
1117
1118 EXPECT_EQ( 16384.0, APFloat(APFloat::IEEEdouble(), "0x10p10").convertToDouble());
1119 EXPECT_EQ(+16384.0, APFloat(APFloat::IEEEdouble(), "+0x10p10").convertToDouble());
1120 EXPECT_EQ(-16384.0, APFloat(APFloat::IEEEdouble(), "-0x10p10").convertToDouble());
1121
1122 EXPECT_EQ( 16384.0, APFloat(APFloat::IEEEdouble(), "0x10p+10").convertToDouble());
1123 EXPECT_EQ(+16384.0, APFloat(APFloat::IEEEdouble(), "+0x10p+10").convertToDouble());
1124 EXPECT_EQ(-16384.0, APFloat(APFloat::IEEEdouble(), "-0x10p+10").convertToDouble());
1125
1126 EXPECT_EQ( 0.015625, APFloat(APFloat::IEEEdouble(), "0x10p-10").convertToDouble());
1127 EXPECT_EQ(+0.015625, APFloat(APFloat::IEEEdouble(), "+0x10p-10").convertToDouble());
1128 EXPECT_EQ(-0.015625, APFloat(APFloat::IEEEdouble(), "-0x10p-10").convertToDouble());
1129
1130 EXPECT_EQ(1.0625, APFloat(APFloat::IEEEdouble(), "0x1.1p0").convertToDouble());
1131 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "0x1p0").convertToDouble());
1132
1133 EXPECT_EQ(convertToDoubleFromString("0x1p-150"),
1134 convertToDoubleFromString("+0x800000000000000001.p-221"));
1135 EXPECT_EQ(2251799813685248.5,
1136 convertToDoubleFromString("0x80000000000004000000.010p-28"));
1137 }
1138
TEST(APFloatTest,toString)1139 TEST(APFloatTest, toString) {
1140 ASSERT_EQ("10", convertToString(10.0, 6, 3));
1141 ASSERT_EQ("1.0E+1", convertToString(10.0, 6, 0));
1142 ASSERT_EQ("10100", convertToString(1.01E+4, 5, 2));
1143 ASSERT_EQ("1.01E+4", convertToString(1.01E+4, 4, 2));
1144 ASSERT_EQ("1.01E+4", convertToString(1.01E+4, 5, 1));
1145 ASSERT_EQ("0.0101", convertToString(1.01E-2, 5, 2));
1146 ASSERT_EQ("0.0101", convertToString(1.01E-2, 4, 2));
1147 ASSERT_EQ("1.01E-2", convertToString(1.01E-2, 5, 1));
1148 ASSERT_EQ("0.78539816339744828", convertToString(0.78539816339744830961, 0, 3));
1149 ASSERT_EQ("4.9406564584124654E-324", convertToString(4.9406564584124654e-324, 0, 3));
1150 ASSERT_EQ("873.18340000000001", convertToString(873.1834, 0, 1));
1151 ASSERT_EQ("8.7318340000000001E+2", convertToString(873.1834, 0, 0));
1152 ASSERT_EQ("1.7976931348623157E+308", convertToString(1.7976931348623157E+308, 0, 0));
1153 ASSERT_EQ("10", convertToString(10.0, 6, 3, false));
1154 ASSERT_EQ("1.000000e+01", convertToString(10.0, 6, 0, false));
1155 ASSERT_EQ("10100", convertToString(1.01E+4, 5, 2, false));
1156 ASSERT_EQ("1.0100e+04", convertToString(1.01E+4, 4, 2, false));
1157 ASSERT_EQ("1.01000e+04", convertToString(1.01E+4, 5, 1, false));
1158 ASSERT_EQ("0.0101", convertToString(1.01E-2, 5, 2, false));
1159 ASSERT_EQ("0.0101", convertToString(1.01E-2, 4, 2, false));
1160 ASSERT_EQ("1.01000e-02", convertToString(1.01E-2, 5, 1, false));
1161 ASSERT_EQ("0.78539816339744828",
1162 convertToString(0.78539816339744830961, 0, 3, false));
1163 ASSERT_EQ("4.94065645841246540e-324",
1164 convertToString(4.9406564584124654e-324, 0, 3, false));
1165 ASSERT_EQ("873.18340000000001", convertToString(873.1834, 0, 1, false));
1166 ASSERT_EQ("8.73183400000000010e+02", convertToString(873.1834, 0, 0, false));
1167 ASSERT_EQ("1.79769313486231570e+308",
1168 convertToString(1.7976931348623157E+308, 0, 0, false));
1169
1170 {
1171 SmallString<64> Str;
1172 APFloat UnnormalZero(APFloat::x87DoubleExtended(), APInt(80, {0, 1}));
1173 UnnormalZero.toString(Str);
1174 ASSERT_EQ("NaN", Str);
1175 }
1176 }
1177
TEST(APFloatTest,toInteger)1178 TEST(APFloatTest, toInteger) {
1179 bool isExact = false;
1180 APSInt result(5, /*isUnsigned=*/true);
1181
1182 EXPECT_EQ(APFloat::opOK,
1183 APFloat(APFloat::IEEEdouble(), "10")
1184 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1185 EXPECT_TRUE(isExact);
1186 EXPECT_EQ(APSInt(APInt(5, 10), true), result);
1187
1188 EXPECT_EQ(APFloat::opInvalidOp,
1189 APFloat(APFloat::IEEEdouble(), "-10")
1190 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1191 EXPECT_FALSE(isExact);
1192 EXPECT_EQ(APSInt::getMinValue(5, true), result);
1193
1194 EXPECT_EQ(APFloat::opInvalidOp,
1195 APFloat(APFloat::IEEEdouble(), "32")
1196 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1197 EXPECT_FALSE(isExact);
1198 EXPECT_EQ(APSInt::getMaxValue(5, true), result);
1199
1200 EXPECT_EQ(APFloat::opInexact,
1201 APFloat(APFloat::IEEEdouble(), "7.9")
1202 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1203 EXPECT_FALSE(isExact);
1204 EXPECT_EQ(APSInt(APInt(5, 7), true), result);
1205
1206 result.setIsUnsigned(false);
1207 EXPECT_EQ(APFloat::opOK,
1208 APFloat(APFloat::IEEEdouble(), "-10")
1209 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1210 EXPECT_TRUE(isExact);
1211 EXPECT_EQ(APSInt(APInt(5, -10, true), false), result);
1212
1213 EXPECT_EQ(APFloat::opInvalidOp,
1214 APFloat(APFloat::IEEEdouble(), "-17")
1215 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1216 EXPECT_FALSE(isExact);
1217 EXPECT_EQ(APSInt::getMinValue(5, false), result);
1218
1219 EXPECT_EQ(APFloat::opInvalidOp,
1220 APFloat(APFloat::IEEEdouble(), "16")
1221 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1222 EXPECT_FALSE(isExact);
1223 EXPECT_EQ(APSInt::getMaxValue(5, false), result);
1224 }
1225
nanbitsFromAPInt(const fltSemantics & Sem,bool SNaN,bool Negative,uint64_t payload)1226 static APInt nanbitsFromAPInt(const fltSemantics &Sem, bool SNaN, bool Negative,
1227 uint64_t payload) {
1228 APInt appayload(64, payload);
1229 if (SNaN)
1230 return APFloat::getSNaN(Sem, Negative, &appayload).bitcastToAPInt();
1231 else
1232 return APFloat::getQNaN(Sem, Negative, &appayload).bitcastToAPInt();
1233 }
1234
TEST(APFloatTest,makeNaN)1235 TEST(APFloatTest, makeNaN) {
1236 const struct {
1237 uint64_t expected;
1238 const fltSemantics &semantics;
1239 bool SNaN;
1240 bool Negative;
1241 uint64_t payload;
1242 } tests[] = {
1243 /* expected semantics SNaN Neg payload */
1244 { 0x7fc00000ULL, APFloat::IEEEsingle(), false, false, 0x00000000ULL },
1245 { 0xffc00000ULL, APFloat::IEEEsingle(), false, true, 0x00000000ULL },
1246 { 0x7fc0ae72ULL, APFloat::IEEEsingle(), false, false, 0x0000ae72ULL },
1247 { 0x7fffae72ULL, APFloat::IEEEsingle(), false, false, 0xffffae72ULL },
1248 { 0x7fdaae72ULL, APFloat::IEEEsingle(), false, false, 0x00daae72ULL },
1249 { 0x7fa00000ULL, APFloat::IEEEsingle(), true, false, 0x00000000ULL },
1250 { 0xffa00000ULL, APFloat::IEEEsingle(), true, true, 0x00000000ULL },
1251 { 0x7f80ae72ULL, APFloat::IEEEsingle(), true, false, 0x0000ae72ULL },
1252 { 0x7fbfae72ULL, APFloat::IEEEsingle(), true, false, 0xffffae72ULL },
1253 { 0x7f9aae72ULL, APFloat::IEEEsingle(), true, false, 0x001aae72ULL },
1254 { 0x7ff8000000000000ULL, APFloat::IEEEdouble(), false, false, 0x0000000000000000ULL },
1255 { 0xfff8000000000000ULL, APFloat::IEEEdouble(), false, true, 0x0000000000000000ULL },
1256 { 0x7ff800000000ae72ULL, APFloat::IEEEdouble(), false, false, 0x000000000000ae72ULL },
1257 { 0x7fffffffffffae72ULL, APFloat::IEEEdouble(), false, false, 0xffffffffffffae72ULL },
1258 { 0x7ffdaaaaaaaaae72ULL, APFloat::IEEEdouble(), false, false, 0x000daaaaaaaaae72ULL },
1259 { 0x7ff4000000000000ULL, APFloat::IEEEdouble(), true, false, 0x0000000000000000ULL },
1260 { 0xfff4000000000000ULL, APFloat::IEEEdouble(), true, true, 0x0000000000000000ULL },
1261 { 0x7ff000000000ae72ULL, APFloat::IEEEdouble(), true, false, 0x000000000000ae72ULL },
1262 { 0x7ff7ffffffffae72ULL, APFloat::IEEEdouble(), true, false, 0xffffffffffffae72ULL },
1263 { 0x7ff1aaaaaaaaae72ULL, APFloat::IEEEdouble(), true, false, 0x0001aaaaaaaaae72ULL },
1264 };
1265
1266 for (const auto &t : tests) {
1267 ASSERT_EQ(t.expected, nanbitsFromAPInt(t.semantics, t.SNaN, t.Negative, t.payload));
1268 }
1269 }
1270
1271 #ifdef GTEST_HAS_DEATH_TEST
1272 #ifndef NDEBUG
TEST(APFloatTest,SemanticsDeath)1273 TEST(APFloatTest, SemanticsDeath) {
1274 EXPECT_DEATH(APFloat(APFloat::IEEEsingle(), 0).convertToDouble(), "Float semantics are not IEEEdouble");
1275 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), 0).convertToFloat(), "Float semantics are not IEEEsingle");
1276 }
1277 #endif
1278 #endif
1279
TEST(APFloatTest,StringDecimalError)1280 TEST(APFloatTest, StringDecimalError) {
1281 EXPECT_EQ("Invalid string length", convertToErrorFromString(""));
1282 EXPECT_EQ("String has no digits", convertToErrorFromString("+"));
1283 EXPECT_EQ("String has no digits", convertToErrorFromString("-"));
1284
1285 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("\0", 1)));
1286 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("1\0", 2)));
1287 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("1" "\0" "2", 3)));
1288 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("1" "\0" "2e1", 5)));
1289 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("1e\0", 3)));
1290 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("1e1\0", 4)));
1291 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("1e1" "\0" "2", 5)));
1292
1293 EXPECT_EQ("Invalid character in significand", convertToErrorFromString("1.0f"));
1294
1295 EXPECT_EQ("String contains multiple dots", convertToErrorFromString(".."));
1296 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("..0"));
1297 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("1.0.0"));
1298 }
1299
TEST(APFloatTest,StringDecimalSignificandError)1300 TEST(APFloatTest, StringDecimalSignificandError) {
1301 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "."));
1302 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+."));
1303 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-."));
1304
1305
1306 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "e"));
1307 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+e"));
1308 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-e"));
1309
1310 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "e1"));
1311 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+e1"));
1312 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-e1"));
1313
1314 EXPECT_EQ("Significand has no digits", convertToErrorFromString( ".e1"));
1315 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+.e1"));
1316 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-.e1"));
1317
1318
1319 EXPECT_EQ("Significand has no digits", convertToErrorFromString( ".e"));
1320 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+.e"));
1321 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-.e"));
1322 }
1323
TEST(APFloatTest,StringHexadecimalError)1324 TEST(APFloatTest, StringHexadecimalError) {
1325 EXPECT_EQ("Invalid string", convertToErrorFromString( "0x"));
1326 EXPECT_EQ("Invalid string", convertToErrorFromString("+0x"));
1327 EXPECT_EQ("Invalid string", convertToErrorFromString("-0x"));
1328
1329 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString( "0x0"));
1330 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("+0x0"));
1331 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("-0x0"));
1332
1333 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString( "0x0."));
1334 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("+0x0."));
1335 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("-0x0."));
1336
1337 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString( "0x.0"));
1338 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("+0x.0"));
1339 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("-0x.0"));
1340
1341 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString( "0x0.0"));
1342 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("+0x0.0"));
1343 EXPECT_EQ("Hex strings require an exponent", convertToErrorFromString("-0x0.0"));
1344
1345 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("0x\0", 3)));
1346 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("0x1\0", 4)));
1347 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("0x1" "\0" "2", 5)));
1348 EXPECT_EQ("Invalid character in significand", convertToErrorFromString(StringRef("0x1" "\0" "2p1", 7)));
1349 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("0x1p\0", 5)));
1350 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("0x1p1\0", 6)));
1351 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString(StringRef("0x1p1" "\0" "2", 7)));
1352
1353 EXPECT_EQ("Invalid character in exponent", convertToErrorFromString("0x1p0f"));
1354
1355 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("0x..p1"));
1356 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("0x..0p1"));
1357 EXPECT_EQ("String contains multiple dots", convertToErrorFromString("0x1.0.0p1"));
1358 }
1359
TEST(APFloatTest,StringHexadecimalSignificandError)1360 TEST(APFloatTest, StringHexadecimalSignificandError) {
1361 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0x."));
1362 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0x."));
1363 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0x."));
1364
1365 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0xp"));
1366 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0xp"));
1367 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0xp"));
1368
1369 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0xp+"));
1370 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0xp+"));
1371 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0xp+"));
1372
1373 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0xp-"));
1374 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0xp-"));
1375 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0xp-"));
1376
1377
1378 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0x.p"));
1379 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0x.p"));
1380 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0x.p"));
1381
1382 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0x.p+"));
1383 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0x.p+"));
1384 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0x.p+"));
1385
1386 EXPECT_EQ("Significand has no digits", convertToErrorFromString( "0x.p-"));
1387 EXPECT_EQ("Significand has no digits", convertToErrorFromString("+0x.p-"));
1388 EXPECT_EQ("Significand has no digits", convertToErrorFromString("-0x.p-"));
1389 }
1390
TEST(APFloatTest,StringHexadecimalExponentError)1391 TEST(APFloatTest, StringHexadecimalExponentError) {
1392 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1p"));
1393 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1p"));
1394 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1p"));
1395
1396 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1p+"));
1397 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1p+"));
1398 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1p+"));
1399
1400 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1p-"));
1401 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1p-"));
1402 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1p-"));
1403
1404
1405 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.p"));
1406 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.p"));
1407 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.p"));
1408
1409 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.p+"));
1410 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.p+"));
1411 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.p+"));
1412
1413 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.p-"));
1414 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.p-"));
1415 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.p-"));
1416
1417
1418 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x.1p"));
1419 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x.1p"));
1420 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x.1p"));
1421
1422 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x.1p+"));
1423 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x.1p+"));
1424 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x.1p+"));
1425
1426 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x.1p-"));
1427 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x.1p-"));
1428 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x.1p-"));
1429
1430
1431 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.1p"));
1432 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.1p"));
1433 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.1p"));
1434
1435 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.1p+"));
1436 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.1p+"));
1437 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.1p+"));
1438
1439 EXPECT_EQ("Exponent has no digits", convertToErrorFromString( "0x1.1p-"));
1440 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("+0x1.1p-"));
1441 EXPECT_EQ("Exponent has no digits", convertToErrorFromString("-0x1.1p-"));
1442 }
1443
TEST(APFloatTest,exactInverse)1444 TEST(APFloatTest, exactInverse) {
1445 APFloat inv(0.0f);
1446
1447 // Trivial operation.
1448 EXPECT_TRUE(APFloat(2.0).getExactInverse(&inv));
1449 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(0.5)));
1450 EXPECT_TRUE(APFloat(2.0f).getExactInverse(&inv));
1451 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(0.5f)));
1452 EXPECT_TRUE(APFloat(APFloat::IEEEquad(), "2.0").getExactInverse(&inv));
1453 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::IEEEquad(), "0.5")));
1454 EXPECT_TRUE(APFloat(APFloat::PPCDoubleDouble(), "2.0").getExactInverse(&inv));
1455 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::PPCDoubleDouble(), "0.5")));
1456 EXPECT_TRUE(APFloat(APFloat::x87DoubleExtended(), "2.0").getExactInverse(&inv));
1457 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::x87DoubleExtended(), "0.5")));
1458
1459 // FLT_MIN
1460 EXPECT_TRUE(APFloat(1.17549435e-38f).getExactInverse(&inv));
1461 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(8.5070592e+37f)));
1462
1463 // Large float, inverse is a denormal.
1464 EXPECT_FALSE(APFloat(1.7014118e38f).getExactInverse(nullptr));
1465 // Zero
1466 EXPECT_FALSE(APFloat(0.0).getExactInverse(nullptr));
1467 // Denormalized float
1468 EXPECT_FALSE(APFloat(1.40129846e-45f).getExactInverse(nullptr));
1469 }
1470
TEST(APFloatTest,roundToIntegral)1471 TEST(APFloatTest, roundToIntegral) {
1472 APFloat T(-0.5), S(3.14), R(APFloat::getLargest(APFloat::IEEEdouble())), P(0.0);
1473
1474 P = T;
1475 P.roundToIntegral(APFloat::rmTowardZero);
1476 EXPECT_EQ(-0.0, P.convertToDouble());
1477 P = T;
1478 P.roundToIntegral(APFloat::rmTowardNegative);
1479 EXPECT_EQ(-1.0, P.convertToDouble());
1480 P = T;
1481 P.roundToIntegral(APFloat::rmTowardPositive);
1482 EXPECT_EQ(-0.0, P.convertToDouble());
1483 P = T;
1484 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1485 EXPECT_EQ(-0.0, P.convertToDouble());
1486
1487 P = S;
1488 P.roundToIntegral(APFloat::rmTowardZero);
1489 EXPECT_EQ(3.0, P.convertToDouble());
1490 P = S;
1491 P.roundToIntegral(APFloat::rmTowardNegative);
1492 EXPECT_EQ(3.0, P.convertToDouble());
1493 P = S;
1494 P.roundToIntegral(APFloat::rmTowardPositive);
1495 EXPECT_EQ(4.0, P.convertToDouble());
1496 P = S;
1497 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1498 EXPECT_EQ(3.0, P.convertToDouble());
1499
1500 P = R;
1501 P.roundToIntegral(APFloat::rmTowardZero);
1502 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1503 P = R;
1504 P.roundToIntegral(APFloat::rmTowardNegative);
1505 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1506 P = R;
1507 P.roundToIntegral(APFloat::rmTowardPositive);
1508 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1509 P = R;
1510 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1511 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1512
1513 P = APFloat::getZero(APFloat::IEEEdouble());
1514 P.roundToIntegral(APFloat::rmTowardZero);
1515 EXPECT_EQ(0.0, P.convertToDouble());
1516 P = APFloat::getZero(APFloat::IEEEdouble(), true);
1517 P.roundToIntegral(APFloat::rmTowardZero);
1518 EXPECT_EQ(-0.0, P.convertToDouble());
1519 P = APFloat::getNaN(APFloat::IEEEdouble());
1520 P.roundToIntegral(APFloat::rmTowardZero);
1521 EXPECT_TRUE(std::isnan(P.convertToDouble()));
1522 P = APFloat::getInf(APFloat::IEEEdouble());
1523 P.roundToIntegral(APFloat::rmTowardZero);
1524 EXPECT_TRUE(std::isinf(P.convertToDouble()) && P.convertToDouble() > 0.0);
1525 P = APFloat::getInf(APFloat::IEEEdouble(), true);
1526 P.roundToIntegral(APFloat::rmTowardZero);
1527 EXPECT_TRUE(std::isinf(P.convertToDouble()) && P.convertToDouble() < 0.0);
1528
1529 APFloat::opStatus St;
1530
1531 P = APFloat::getNaN(APFloat::IEEEdouble());
1532 St = P.roundToIntegral(APFloat::rmTowardZero);
1533 EXPECT_TRUE(P.isNaN());
1534 EXPECT_FALSE(P.isNegative());
1535 EXPECT_EQ(APFloat::opOK, St);
1536
1537 P = APFloat::getNaN(APFloat::IEEEdouble(), true);
1538 St = P.roundToIntegral(APFloat::rmTowardZero);
1539 EXPECT_TRUE(P.isNaN());
1540 EXPECT_TRUE(P.isNegative());
1541 EXPECT_EQ(APFloat::opOK, St);
1542
1543 P = APFloat::getSNaN(APFloat::IEEEdouble());
1544 St = P.roundToIntegral(APFloat::rmTowardZero);
1545 EXPECT_TRUE(P.isNaN());
1546 EXPECT_FALSE(P.isSignaling());
1547 EXPECT_FALSE(P.isNegative());
1548 EXPECT_EQ(APFloat::opInvalidOp, St);
1549
1550 P = APFloat::getSNaN(APFloat::IEEEdouble(), true);
1551 St = P.roundToIntegral(APFloat::rmTowardZero);
1552 EXPECT_TRUE(P.isNaN());
1553 EXPECT_FALSE(P.isSignaling());
1554 EXPECT_TRUE(P.isNegative());
1555 EXPECT_EQ(APFloat::opInvalidOp, St);
1556
1557 P = APFloat::getInf(APFloat::IEEEdouble());
1558 St = P.roundToIntegral(APFloat::rmTowardZero);
1559 EXPECT_TRUE(P.isInfinity());
1560 EXPECT_FALSE(P.isNegative());
1561 EXPECT_EQ(APFloat::opOK, St);
1562
1563 P = APFloat::getInf(APFloat::IEEEdouble(), true);
1564 St = P.roundToIntegral(APFloat::rmTowardZero);
1565 EXPECT_TRUE(P.isInfinity());
1566 EXPECT_TRUE(P.isNegative());
1567 EXPECT_EQ(APFloat::opOK, St);
1568
1569 P = APFloat::getZero(APFloat::IEEEdouble(), false);
1570 St = P.roundToIntegral(APFloat::rmTowardZero);
1571 EXPECT_TRUE(P.isZero());
1572 EXPECT_FALSE(P.isNegative());
1573 EXPECT_EQ(APFloat::opOK, St);
1574
1575 P = APFloat::getZero(APFloat::IEEEdouble(), false);
1576 St = P.roundToIntegral(APFloat::rmTowardNegative);
1577 EXPECT_TRUE(P.isZero());
1578 EXPECT_FALSE(P.isNegative());
1579 EXPECT_EQ(APFloat::opOK, St);
1580
1581 P = APFloat::getZero(APFloat::IEEEdouble(), true);
1582 St = P.roundToIntegral(APFloat::rmTowardZero);
1583 EXPECT_TRUE(P.isZero());
1584 EXPECT_TRUE(P.isNegative());
1585 EXPECT_EQ(APFloat::opOK, St);
1586
1587 P = APFloat::getZero(APFloat::IEEEdouble(), true);
1588 St = P.roundToIntegral(APFloat::rmTowardNegative);
1589 EXPECT_TRUE(P.isZero());
1590 EXPECT_TRUE(P.isNegative());
1591 EXPECT_EQ(APFloat::opOK, St);
1592
1593 P = APFloat(1E-100);
1594 St = P.roundToIntegral(APFloat::rmTowardNegative);
1595 EXPECT_TRUE(P.isZero());
1596 EXPECT_FALSE(P.isNegative());
1597 EXPECT_EQ(APFloat::opInexact, St);
1598
1599 P = APFloat(1E-100);
1600 St = P.roundToIntegral(APFloat::rmTowardPositive);
1601 EXPECT_EQ(1.0, P.convertToDouble());
1602 EXPECT_FALSE(P.isNegative());
1603 EXPECT_EQ(APFloat::opInexact, St);
1604
1605 P = APFloat(-1E-100);
1606 St = P.roundToIntegral(APFloat::rmTowardNegative);
1607 EXPECT_TRUE(P.isNegative());
1608 EXPECT_EQ(-1.0, P.convertToDouble());
1609 EXPECT_EQ(APFloat::opInexact, St);
1610
1611 P = APFloat(-1E-100);
1612 St = P.roundToIntegral(APFloat::rmTowardPositive);
1613 EXPECT_TRUE(P.isZero());
1614 EXPECT_TRUE(P.isNegative());
1615 EXPECT_EQ(APFloat::opInexact, St);
1616
1617 P = APFloat(10.0);
1618 St = P.roundToIntegral(APFloat::rmTowardZero);
1619 EXPECT_EQ(10.0, P.convertToDouble());
1620 EXPECT_EQ(APFloat::opOK, St);
1621
1622 P = APFloat(10.5);
1623 St = P.roundToIntegral(APFloat::rmTowardZero);
1624 EXPECT_EQ(10.0, P.convertToDouble());
1625 EXPECT_EQ(APFloat::opInexact, St);
1626
1627 P = APFloat(10.5);
1628 St = P.roundToIntegral(APFloat::rmTowardPositive);
1629 EXPECT_EQ(11.0, P.convertToDouble());
1630 EXPECT_EQ(APFloat::opInexact, St);
1631
1632 P = APFloat(10.5);
1633 St = P.roundToIntegral(APFloat::rmTowardNegative);
1634 EXPECT_EQ(10.0, P.convertToDouble());
1635 EXPECT_EQ(APFloat::opInexact, St);
1636
1637 P = APFloat(10.5);
1638 St = P.roundToIntegral(APFloat::rmNearestTiesToAway);
1639 EXPECT_EQ(11.0, P.convertToDouble());
1640 EXPECT_EQ(APFloat::opInexact, St);
1641
1642 P = APFloat(10.5);
1643 St = P.roundToIntegral(APFloat::rmNearestTiesToEven);
1644 EXPECT_EQ(10.0, P.convertToDouble());
1645 EXPECT_EQ(APFloat::opInexact, St);
1646 }
1647
TEST(APFloatTest,isInteger)1648 TEST(APFloatTest, isInteger) {
1649 APFloat T(-0.0);
1650 EXPECT_TRUE(T.isInteger());
1651 T = APFloat(3.14159);
1652 EXPECT_FALSE(T.isInteger());
1653 T = APFloat::getNaN(APFloat::IEEEdouble());
1654 EXPECT_FALSE(T.isInteger());
1655 T = APFloat::getInf(APFloat::IEEEdouble());
1656 EXPECT_FALSE(T.isInteger());
1657 T = APFloat::getInf(APFloat::IEEEdouble(), true);
1658 EXPECT_FALSE(T.isInteger());
1659 T = APFloat::getLargest(APFloat::IEEEdouble());
1660 EXPECT_TRUE(T.isInteger());
1661 }
1662
TEST(DoubleAPFloatTest,isInteger)1663 TEST(DoubleAPFloatTest, isInteger) {
1664 APFloat F1(-0.0);
1665 APFloat F2(-0.0);
1666 llvm::detail::DoubleAPFloat T(APFloat::PPCDoubleDouble(), std::move(F1),
1667 std::move(F2));
1668 EXPECT_TRUE(T.isInteger());
1669 APFloat F3(3.14159);
1670 APFloat F4(-0.0);
1671 llvm::detail::DoubleAPFloat T2(APFloat::PPCDoubleDouble(), std::move(F3),
1672 std::move(F4));
1673 EXPECT_FALSE(T2.isInteger());
1674 APFloat F5(-0.0);
1675 APFloat F6(3.14159);
1676 llvm::detail::DoubleAPFloat T3(APFloat::PPCDoubleDouble(), std::move(F5),
1677 std::move(F6));
1678 EXPECT_FALSE(T3.isInteger());
1679 }
1680
TEST(APFloatTest,getLargest)1681 TEST(APFloatTest, getLargest) {
1682 EXPECT_EQ(3.402823466e+38f, APFloat::getLargest(APFloat::IEEEsingle()).convertToFloat());
1683 EXPECT_EQ(1.7976931348623158e+308, APFloat::getLargest(APFloat::IEEEdouble()).convertToDouble());
1684 }
1685
TEST(APFloatTest,getSmallest)1686 TEST(APFloatTest, getSmallest) {
1687 APFloat test = APFloat::getSmallest(APFloat::IEEEsingle(), false);
1688 APFloat expected = APFloat(APFloat::IEEEsingle(), "0x0.000002p-126");
1689 EXPECT_FALSE(test.isNegative());
1690 EXPECT_TRUE(test.isFiniteNonZero());
1691 EXPECT_TRUE(test.isDenormal());
1692 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1693
1694 test = APFloat::getSmallest(APFloat::IEEEsingle(), true);
1695 expected = APFloat(APFloat::IEEEsingle(), "-0x0.000002p-126");
1696 EXPECT_TRUE(test.isNegative());
1697 EXPECT_TRUE(test.isFiniteNonZero());
1698 EXPECT_TRUE(test.isDenormal());
1699 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1700
1701 test = APFloat::getSmallest(APFloat::IEEEquad(), false);
1702 expected = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
1703 EXPECT_FALSE(test.isNegative());
1704 EXPECT_TRUE(test.isFiniteNonZero());
1705 EXPECT_TRUE(test.isDenormal());
1706 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1707
1708 test = APFloat::getSmallest(APFloat::IEEEquad(), true);
1709 expected = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
1710 EXPECT_TRUE(test.isNegative());
1711 EXPECT_TRUE(test.isFiniteNonZero());
1712 EXPECT_TRUE(test.isDenormal());
1713 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1714 }
1715
TEST(APFloatTest,getSmallestNormalized)1716 TEST(APFloatTest, getSmallestNormalized) {
1717 APFloat test = APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
1718 APFloat expected = APFloat(APFloat::IEEEsingle(), "0x1p-126");
1719 EXPECT_FALSE(test.isNegative());
1720 EXPECT_TRUE(test.isFiniteNonZero());
1721 EXPECT_FALSE(test.isDenormal());
1722 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1723
1724 test = APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
1725 expected = APFloat(APFloat::IEEEsingle(), "-0x1p-126");
1726 EXPECT_TRUE(test.isNegative());
1727 EXPECT_TRUE(test.isFiniteNonZero());
1728 EXPECT_FALSE(test.isDenormal());
1729 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1730
1731 test = APFloat::getSmallestNormalized(APFloat::IEEEquad(), false);
1732 expected = APFloat(APFloat::IEEEquad(), "0x1p-16382");
1733 EXPECT_FALSE(test.isNegative());
1734 EXPECT_TRUE(test.isFiniteNonZero());
1735 EXPECT_FALSE(test.isDenormal());
1736 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1737
1738 test = APFloat::getSmallestNormalized(APFloat::IEEEquad(), true);
1739 expected = APFloat(APFloat::IEEEquad(), "-0x1p-16382");
1740 EXPECT_TRUE(test.isNegative());
1741 EXPECT_TRUE(test.isFiniteNonZero());
1742 EXPECT_FALSE(test.isDenormal());
1743 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1744 }
1745
TEST(APFloatTest,getZero)1746 TEST(APFloatTest, getZero) {
1747 struct {
1748 const fltSemantics *semantics;
1749 const bool sign;
1750 const unsigned long long bitPattern[2];
1751 const unsigned bitPatternLength;
1752 } const GetZeroTest[] = {
1753 { &APFloat::IEEEhalf(), false, {0, 0}, 1},
1754 { &APFloat::IEEEhalf(), true, {0x8000ULL, 0}, 1},
1755 { &APFloat::IEEEsingle(), false, {0, 0}, 1},
1756 { &APFloat::IEEEsingle(), true, {0x80000000ULL, 0}, 1},
1757 { &APFloat::IEEEdouble(), false, {0, 0}, 1},
1758 { &APFloat::IEEEdouble(), true, {0x8000000000000000ULL, 0}, 1},
1759 { &APFloat::IEEEquad(), false, {0, 0}, 2},
1760 { &APFloat::IEEEquad(), true, {0, 0x8000000000000000ULL}, 2},
1761 { &APFloat::PPCDoubleDouble(), false, {0, 0}, 2},
1762 { &APFloat::PPCDoubleDouble(), true, {0x8000000000000000ULL, 0}, 2},
1763 { &APFloat::x87DoubleExtended(), false, {0, 0}, 2},
1764 { &APFloat::x87DoubleExtended(), true, {0, 0x8000ULL}, 2},
1765 };
1766 const unsigned NumGetZeroTests = 12;
1767 for (unsigned i = 0; i < NumGetZeroTests; ++i) {
1768 APFloat test = APFloat::getZero(*GetZeroTest[i].semantics,
1769 GetZeroTest[i].sign);
1770 const char *pattern = GetZeroTest[i].sign? "-0x0p+0" : "0x0p+0";
1771 APFloat expected = APFloat(*GetZeroTest[i].semantics,
1772 pattern);
1773 EXPECT_TRUE(test.isZero());
1774 EXPECT_TRUE(GetZeroTest[i].sign? test.isNegative() : !test.isNegative());
1775 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1776 for (unsigned j = 0, je = GetZeroTest[i].bitPatternLength; j < je; ++j) {
1777 EXPECT_EQ(GetZeroTest[i].bitPattern[j],
1778 test.bitcastToAPInt().getRawData()[j]);
1779 }
1780 }
1781 }
1782
TEST(APFloatTest,copySign)1783 TEST(APFloatTest, copySign) {
1784 EXPECT_TRUE(APFloat(-42.0).bitwiseIsEqual(
1785 APFloat::copySign(APFloat(42.0), APFloat(-1.0))));
1786 EXPECT_TRUE(APFloat(42.0).bitwiseIsEqual(
1787 APFloat::copySign(APFloat(-42.0), APFloat(1.0))));
1788 EXPECT_TRUE(APFloat(-42.0).bitwiseIsEqual(
1789 APFloat::copySign(APFloat(-42.0), APFloat(-1.0))));
1790 EXPECT_TRUE(APFloat(42.0).bitwiseIsEqual(
1791 APFloat::copySign(APFloat(42.0), APFloat(1.0))));
1792 }
1793
TEST(APFloatTest,convert)1794 TEST(APFloatTest, convert) {
1795 bool losesInfo;
1796 APFloat test(APFloat::IEEEdouble(), "1.0");
1797 test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
1798 EXPECT_EQ(1.0f, test.convertToFloat());
1799 EXPECT_FALSE(losesInfo);
1800
1801 test = APFloat(APFloat::x87DoubleExtended(), "0x1p-53");
1802 test.add(APFloat(APFloat::x87DoubleExtended(), "1.0"), APFloat::rmNearestTiesToEven);
1803 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
1804 EXPECT_EQ(1.0, test.convertToDouble());
1805 EXPECT_TRUE(losesInfo);
1806
1807 test = APFloat(APFloat::IEEEquad(), "0x1p-53");
1808 test.add(APFloat(APFloat::IEEEquad(), "1.0"), APFloat::rmNearestTiesToEven);
1809 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
1810 EXPECT_EQ(1.0, test.convertToDouble());
1811 EXPECT_TRUE(losesInfo);
1812
1813 test = APFloat(APFloat::x87DoubleExtended(), "0xf.fffffffp+28");
1814 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
1815 EXPECT_EQ(4294967295.0, test.convertToDouble());
1816 EXPECT_FALSE(losesInfo);
1817
1818 test = APFloat::getSNaN(APFloat::IEEEsingle());
1819 APFloat::opStatus status = test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven, &losesInfo);
1820 // Conversion quiets the SNAN, so now 2 bits of the 64-bit significand should be set.
1821 APInt topTwoBits(64, 0x6000000000000000);
1822 EXPECT_TRUE(test.bitwiseIsEqual(APFloat::getQNaN(APFloat::x87DoubleExtended(), false, &topTwoBits)));
1823 EXPECT_FALSE(losesInfo);
1824 EXPECT_EQ(status, APFloat::opInvalidOp);
1825
1826 test = APFloat::getQNaN(APFloat::IEEEsingle());
1827 APFloat X87QNaN = APFloat::getQNaN(APFloat::x87DoubleExtended());
1828 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
1829 &losesInfo);
1830 EXPECT_TRUE(test.bitwiseIsEqual(X87QNaN));
1831 EXPECT_FALSE(losesInfo);
1832
1833 test = APFloat::getSNaN(APFloat::x87DoubleExtended());
1834 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
1835 &losesInfo);
1836 APFloat X87SNaN = APFloat::getSNaN(APFloat::x87DoubleExtended());
1837 EXPECT_TRUE(test.bitwiseIsEqual(X87SNaN));
1838 EXPECT_FALSE(losesInfo);
1839
1840 test = APFloat::getQNaN(APFloat::x87DoubleExtended());
1841 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
1842 &losesInfo);
1843 EXPECT_TRUE(test.bitwiseIsEqual(X87QNaN));
1844 EXPECT_FALSE(losesInfo);
1845
1846 // The payload is lost in truncation, but we retain NaN by setting the quiet bit.
1847 APInt payload(52, 1);
1848 test = APFloat::getSNaN(APFloat::IEEEdouble(), false, &payload);
1849 status = test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
1850 EXPECT_EQ(0x7fc00000, test.bitcastToAPInt());
1851 EXPECT_TRUE(losesInfo);
1852 EXPECT_EQ(status, APFloat::opInvalidOp);
1853
1854 // The payload is lost in truncation. QNaN remains QNaN.
1855 test = APFloat::getQNaN(APFloat::IEEEdouble(), false, &payload);
1856 status = test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
1857 EXPECT_EQ(0x7fc00000, test.bitcastToAPInt());
1858 EXPECT_TRUE(losesInfo);
1859 EXPECT_EQ(status, APFloat::opOK);
1860 }
1861
TEST(APFloatTest,PPCDoubleDouble)1862 TEST(APFloatTest, PPCDoubleDouble) {
1863 APFloat test(APFloat::PPCDoubleDouble(), "1.0");
1864 EXPECT_EQ(0x3ff0000000000000ull, test.bitcastToAPInt().getRawData()[0]);
1865 EXPECT_EQ(0x0000000000000000ull, test.bitcastToAPInt().getRawData()[1]);
1866
1867 // LDBL_MAX
1868 test = APFloat(APFloat::PPCDoubleDouble(), "1.79769313486231580793728971405301e+308");
1869 EXPECT_EQ(0x7fefffffffffffffull, test.bitcastToAPInt().getRawData()[0]);
1870 EXPECT_EQ(0x7c8ffffffffffffeull, test.bitcastToAPInt().getRawData()[1]);
1871
1872 // LDBL_MIN
1873 test = APFloat(APFloat::PPCDoubleDouble(), "2.00416836000897277799610805135016e-292");
1874 EXPECT_EQ(0x0360000000000000ull, test.bitcastToAPInt().getRawData()[0]);
1875 EXPECT_EQ(0x0000000000000000ull, test.bitcastToAPInt().getRawData()[1]);
1876
1877 // PR30869
1878 {
1879 auto Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") +
1880 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1881 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
1882
1883 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") -
1884 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1885 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
1886
1887 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") *
1888 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1889 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
1890
1891 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") /
1892 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1893 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
1894
1895 int Exp;
1896 Result = frexp(APFloat(APFloat::PPCDoubleDouble(), "1.0"), Exp,
1897 APFloat::rmNearestTiesToEven);
1898 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
1899
1900 Result = scalbn(APFloat(APFloat::PPCDoubleDouble(), "1.0"), 1,
1901 APFloat::rmNearestTiesToEven);
1902 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
1903 }
1904 }
1905
TEST(APFloatTest,isNegative)1906 TEST(APFloatTest, isNegative) {
1907 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
1908 EXPECT_FALSE(t.isNegative());
1909 t = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
1910 EXPECT_TRUE(t.isNegative());
1911
1912 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNegative());
1913 EXPECT_TRUE(APFloat::getInf(APFloat::IEEEsingle(), true).isNegative());
1914
1915 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNegative());
1916 EXPECT_TRUE(APFloat::getZero(APFloat::IEEEsingle(), true).isNegative());
1917
1918 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNegative());
1919 EXPECT_TRUE(APFloat::getNaN(APFloat::IEEEsingle(), true).isNegative());
1920
1921 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNegative());
1922 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isNegative());
1923 }
1924
TEST(APFloatTest,isNormal)1925 TEST(APFloatTest, isNormal) {
1926 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
1927 EXPECT_TRUE(t.isNormal());
1928
1929 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNormal());
1930 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNormal());
1931 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNormal());
1932 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNormal());
1933 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isNormal());
1934 }
1935
TEST(APFloatTest,isFinite)1936 TEST(APFloatTest, isFinite) {
1937 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
1938 EXPECT_TRUE(t.isFinite());
1939 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isFinite());
1940 EXPECT_TRUE(APFloat::getZero(APFloat::IEEEsingle(), false).isFinite());
1941 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isFinite());
1942 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isFinite());
1943 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isFinite());
1944 }
1945
TEST(APFloatTest,isInfinity)1946 TEST(APFloatTest, isInfinity) {
1947 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
1948 EXPECT_FALSE(t.isInfinity());
1949 EXPECT_TRUE(APFloat::getInf(APFloat::IEEEsingle(), false).isInfinity());
1950 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isInfinity());
1951 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isInfinity());
1952 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isInfinity());
1953 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isInfinity());
1954 }
1955
TEST(APFloatTest,isNaN)1956 TEST(APFloatTest, isNaN) {
1957 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
1958 EXPECT_FALSE(t.isNaN());
1959 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNaN());
1960 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNaN());
1961 EXPECT_TRUE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNaN());
1962 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNaN());
1963 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isNaN());
1964 }
1965
TEST(APFloatTest,isFiniteNonZero)1966 TEST(APFloatTest, isFiniteNonZero) {
1967 // Test positive/negative normal value.
1968 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p+0").isFiniteNonZero());
1969 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p+0").isFiniteNonZero());
1970
1971 // Test positive/negative denormal value.
1972 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isFiniteNonZero());
1973 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p-149").isFiniteNonZero());
1974
1975 // Test +/- Infinity.
1976 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isFiniteNonZero());
1977 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), true).isFiniteNonZero());
1978
1979 // Test +/- Zero.
1980 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isFiniteNonZero());
1981 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), true).isFiniteNonZero());
1982
1983 // Test +/- qNaN. +/- dont mean anything with qNaN but paranoia can't hurt in
1984 // this instance.
1985 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isFiniteNonZero());
1986 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), true).isFiniteNonZero());
1987
1988 // Test +/- sNaN. +/- dont mean anything with sNaN but paranoia can't hurt in
1989 // this instance.
1990 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isFiniteNonZero());
1991 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isFiniteNonZero());
1992 }
1993
TEST(APFloatTest,add)1994 TEST(APFloatTest, add) {
1995 // Test Special Cases against each other and normal values.
1996
1997 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
1998 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
1999 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2000 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2001 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2002 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
2003 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2004 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2005 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2006 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2007 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2008 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
2009 APFloat PSmallestNormalized =
2010 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
2011 APFloat MSmallestNormalized =
2012 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
2013
2014 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2015
2016 struct {
2017 APFloat x;
2018 APFloat y;
2019 const char *result;
2020 int status;
2021 int category;
2022 } SpecialCaseTests[] = {
2023 { PInf, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2024 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2025 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2026 { PInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2027 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2028 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2029 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2030 { PInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2031 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2032 { PInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2033 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2034 { PInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2035 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2036 { PInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2037 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2038 { MInf, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2039 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2040 { MInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2041 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2042 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2043 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2044 { MInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2045 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2046 { MInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2047 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2048 { MInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2049 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2050 { MInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2051 { PZero, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2052 { PZero, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2053 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2054 { PZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2055 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2056 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2057 { PZero, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2058 { PZero, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2059 { PZero, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2060 { PZero, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2061 { PZero, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2062 { PZero, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2063 { PZero, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2064 { PZero, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2065 { MZero, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2066 { MZero, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2067 { MZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2068 { MZero, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2069 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2070 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2071 { MZero, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2072 { MZero, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2073 { MZero, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2074 { MZero, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2075 { MZero, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2076 { MZero, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2077 { MZero, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2078 { MZero, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2079 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
2080 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
2081 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
2082 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
2083 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2084 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2085 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2086 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2087 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2088 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2089 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2090 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2091 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2092 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2093 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2094 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2095 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2096 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2097 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2098 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2099 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2100 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2101 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2102 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2103 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2104 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2105 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2106 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2107 { PNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2108 { PNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2109 { PNormalValue, PZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2110 { PNormalValue, MZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2111 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2112 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2113 { PNormalValue, PNormalValue, "0x1p+1", APFloat::opOK, APFloat::fcNormal },
2114 { PNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2115 { PNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2116 { PNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2117 { PNormalValue, PSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2118 { PNormalValue, MSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2119 { PNormalValue, PSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2120 { PNormalValue, MSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2121 { MNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2122 { MNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2123 { MNormalValue, PZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2124 { MNormalValue, MZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2125 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2126 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2127 { MNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2128 { MNormalValue, MNormalValue, "-0x1p+1", APFloat::opOK, APFloat::fcNormal },
2129 { MNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2130 { MNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2131 { MNormalValue, PSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2132 { MNormalValue, MSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2133 { MNormalValue, PSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2134 { MNormalValue, MSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2135 { PLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2136 { PLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2137 { PLargestValue, PZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2138 { PLargestValue, MZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2139 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2140 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2141 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2142 { PLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2143 { PLargestValue, PLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2144 { PLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2145 { PLargestValue, PSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2146 { PLargestValue, MSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2147 { PLargestValue, PSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2148 { PLargestValue, MSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2149 { MLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2150 { MLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2151 { MLargestValue, PZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2152 { MLargestValue, MZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2153 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2154 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2155 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2156 { MLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2157 { MLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2158 { MLargestValue, MLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2159 { MLargestValue, PSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2160 { MLargestValue, MSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2161 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2162 { MLargestValue, MSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2163 { PSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2164 { PSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2165 { PSmallestValue, PZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2166 { PSmallestValue, MZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2167 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2168 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2169 { PSmallestValue, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2170 { PSmallestValue, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2171 { PSmallestValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2172 { PSmallestValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2173 { PSmallestValue, PSmallestValue, "0x1p-148", APFloat::opOK, APFloat::fcNormal },
2174 { PSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2175 { PSmallestValue, PSmallestNormalized, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2176 { PSmallestValue, MSmallestNormalized, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2177 { MSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2178 { MSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2179 { MSmallestValue, PZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2180 { MSmallestValue, MZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2181 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2182 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2183 { MSmallestValue, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2184 { MSmallestValue, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2185 { MSmallestValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2186 { MSmallestValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2187 { MSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2188 { MSmallestValue, MSmallestValue, "-0x1p-148", APFloat::opOK, APFloat::fcNormal },
2189 { MSmallestValue, PSmallestNormalized, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2190 { MSmallestValue, MSmallestNormalized, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2191 { PSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2192 { PSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2193 { PSmallestNormalized, PZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2194 { PSmallestNormalized, MZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2195 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2196 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2197 { PSmallestNormalized, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2198 { PSmallestNormalized, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2199 { PSmallestNormalized, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2200 { PSmallestNormalized, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2201 { PSmallestNormalized, PSmallestValue, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2202 { PSmallestNormalized, MSmallestValue, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2203 { PSmallestNormalized, PSmallestNormalized, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
2204 { PSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2205 { MSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2206 { MSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2207 { MSmallestNormalized, PZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2208 { MSmallestNormalized, MZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2209 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2210 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2211 { MSmallestNormalized, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2212 { MSmallestNormalized, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2213 { MSmallestNormalized, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2214 { MSmallestNormalized, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2215 { MSmallestNormalized, PSmallestValue, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2216 { MSmallestNormalized, MSmallestValue, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2217 { MSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2218 { MSmallestNormalized, MSmallestNormalized, "-0x1p-125", APFloat::opOK, APFloat::fcNormal }
2219 };
2220
2221 for (size_t i = 0; i < array_lengthof(SpecialCaseTests); ++i) {
2222 APFloat x(SpecialCaseTests[i].x);
2223 APFloat y(SpecialCaseTests[i].y);
2224 APFloat::opStatus status = x.add(y, APFloat::rmNearestTiesToEven);
2225
2226 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
2227
2228 EXPECT_TRUE(result.bitwiseIsEqual(x));
2229 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
2230 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
2231 }
2232 }
2233
TEST(APFloatTest,subtract)2234 TEST(APFloatTest, subtract) {
2235 // Test Special Cases against each other and normal values.
2236
2237 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2238 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2239 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2240 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2241 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2242 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
2243 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2244 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2245 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2246 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2247 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2248 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
2249 APFloat PSmallestNormalized =
2250 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
2251 APFloat MSmallestNormalized =
2252 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
2253
2254 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2255
2256 struct {
2257 APFloat x;
2258 APFloat y;
2259 const char *result;
2260 int status;
2261 int category;
2262 } SpecialCaseTests[] = {
2263 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2264 { PInf, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2265 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2266 { PInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2267 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2268 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2269 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2270 { PInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2271 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2272 { PInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2273 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2274 { PInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2275 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2276 { PInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2277 { MInf, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2278 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2279 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2280 { MInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2281 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2282 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2283 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2284 { MInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2285 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2286 { MInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2287 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2288 { MInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2289 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2290 { MInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2291 { PZero, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2292 { PZero, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2293 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2294 { PZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2295 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2296 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2297 { PZero, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2298 { PZero, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2299 { PZero, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2300 { PZero, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2301 { PZero, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2302 { PZero, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2303 { PZero, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2304 { PZero, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2305 { MZero, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2306 { MZero, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2307 { MZero, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2308 { MZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2309 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2310 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2311 { MZero, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2312 { MZero, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2313 { MZero, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2314 { MZero, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2315 { MZero, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2316 { MZero, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2317 { MZero, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2318 { MZero, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2319 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
2320 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
2321 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
2322 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
2323 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2324 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2325 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2326 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2327 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2328 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2329 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2330 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2331 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2332 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2333 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2334 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2335 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2336 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2337 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2338 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2339 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2340 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2341 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2342 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2343 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2344 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2345 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2346 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2347 { PNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2348 { PNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2349 { PNormalValue, PZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2350 { PNormalValue, MZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2351 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2352 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2353 { PNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2354 { PNormalValue, MNormalValue, "0x1p+1", APFloat::opOK, APFloat::fcNormal },
2355 { PNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2356 { PNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2357 { PNormalValue, PSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2358 { PNormalValue, MSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2359 { PNormalValue, PSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2360 { PNormalValue, MSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2361 { MNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2362 { MNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2363 { MNormalValue, PZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2364 { MNormalValue, MZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2365 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2366 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2367 { MNormalValue, PNormalValue, "-0x1p+1", APFloat::opOK, APFloat::fcNormal },
2368 { MNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2369 { MNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2370 { MNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2371 { MNormalValue, PSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2372 { MNormalValue, MSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2373 { MNormalValue, PSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2374 { MNormalValue, MSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2375 { PLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2376 { PLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2377 { PLargestValue, PZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2378 { PLargestValue, MZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2379 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2380 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2381 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2382 { PLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2383 { PLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2384 { PLargestValue, MLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2385 { PLargestValue, PSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2386 { PLargestValue, MSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2387 { PLargestValue, PSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2388 { PLargestValue, MSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2389 { MLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2390 { MLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2391 { MLargestValue, PZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2392 { MLargestValue, MZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2393 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2394 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2395 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2396 { MLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2397 { MLargestValue, PLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2398 { MLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2399 { MLargestValue, PSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2400 { MLargestValue, MSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2401 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2402 { MLargestValue, MSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2403 { PSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2404 { PSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2405 { PSmallestValue, PZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2406 { PSmallestValue, MZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2407 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2408 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2409 { PSmallestValue, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2410 { PSmallestValue, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2411 { PSmallestValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2412 { PSmallestValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2413 { PSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2414 { PSmallestValue, MSmallestValue, "0x1p-148", APFloat::opOK, APFloat::fcNormal },
2415 { PSmallestValue, PSmallestNormalized, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2416 { PSmallestValue, MSmallestNormalized, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2417 { MSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2418 { MSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2419 { MSmallestValue, PZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2420 { MSmallestValue, MZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2421 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2422 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2423 { MSmallestValue, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2424 { MSmallestValue, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2425 { MSmallestValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2426 { MSmallestValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2427 { MSmallestValue, PSmallestValue, "-0x1p-148", APFloat::opOK, APFloat::fcNormal },
2428 { MSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2429 { MSmallestValue, PSmallestNormalized, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2430 { MSmallestValue, MSmallestNormalized, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2431 { PSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2432 { PSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2433 { PSmallestNormalized, PZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2434 { PSmallestNormalized, MZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2435 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2436 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2437 { PSmallestNormalized, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2438 { PSmallestNormalized, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2439 { PSmallestNormalized, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2440 { PSmallestNormalized, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2441 { PSmallestNormalized, PSmallestValue, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2442 { PSmallestNormalized, MSmallestValue, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2443 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2444 { PSmallestNormalized, MSmallestNormalized, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
2445 { MSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2446 { MSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2447 { MSmallestNormalized, PZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2448 { MSmallestNormalized, MZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2449 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2450 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2451 { MSmallestNormalized, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2452 { MSmallestNormalized, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2453 { MSmallestNormalized, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2454 { MSmallestNormalized, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2455 { MSmallestNormalized, PSmallestValue, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2456 { MSmallestNormalized, MSmallestValue, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2457 { MSmallestNormalized, PSmallestNormalized, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
2458 { MSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero }
2459 };
2460
2461 for (size_t i = 0; i < array_lengthof(SpecialCaseTests); ++i) {
2462 APFloat x(SpecialCaseTests[i].x);
2463 APFloat y(SpecialCaseTests[i].y);
2464 APFloat::opStatus status = x.subtract(y, APFloat::rmNearestTiesToEven);
2465
2466 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
2467
2468 EXPECT_TRUE(result.bitwiseIsEqual(x));
2469 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
2470 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
2471 }
2472 }
2473
TEST(APFloatTest,multiply)2474 TEST(APFloatTest, multiply) {
2475 // Test Special Cases against each other and normal values.
2476
2477 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2478 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2479 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2480 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2481 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2482 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
2483 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2484 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2485 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2486 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2487 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2488 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
2489 APFloat PSmallestNormalized =
2490 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
2491 APFloat MSmallestNormalized =
2492 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
2493
2494 APFloat MaxQuad(APFloat::IEEEquad(),
2495 "0x1.ffffffffffffffffffffffffffffp+16383");
2496 APFloat MinQuad(APFloat::IEEEquad(),
2497 "0x0.0000000000000000000000000001p-16382");
2498 APFloat NMinQuad(APFloat::IEEEquad(),
2499 "-0x0.0000000000000000000000000001p-16382");
2500
2501 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2502 const int UnderflowStatus = APFloat::opUnderflow | APFloat::opInexact;
2503
2504 struct {
2505 APFloat x;
2506 APFloat y;
2507 const char *result;
2508 int status;
2509 int category;
2510 APFloat::roundingMode roundingMode = APFloat::rmNearestTiesToEven;
2511 } SpecialCaseTests[] = {
2512 { PInf, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2513 { PInf, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2514 { PInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2515 { PInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2516 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2517 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2518 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2519 { PInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2520 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2521 { PInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2522 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2523 { PInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2524 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2525 { PInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2526 { MInf, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2527 { MInf, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2528 { MInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2529 { MInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2530 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2531 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2532 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2533 { MInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2534 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2535 { MInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2536 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2537 { MInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2538 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2539 { MInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2540 { PZero, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2541 { PZero, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2542 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2543 { PZero, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2544 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2545 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2546 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2547 { PZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2548 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2549 { PZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2550 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2551 { PZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2552 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2553 { PZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2554 { MZero, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2555 { MZero, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2556 { MZero, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2557 { MZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2558 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2559 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2560 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2561 { MZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2562 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2563 { MZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2564 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2565 { MZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2566 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2567 { MZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2568 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
2569 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
2570 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
2571 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
2572 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2573 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2574 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2575 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2576 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2577 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2578 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2579 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2580 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2581 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2582 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2583 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2584 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2585 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2586 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2587 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2588 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2589 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2590 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2591 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2592 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2593 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2594 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2595 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2596 { PNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2597 { PNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2598 { PNormalValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2599 { PNormalValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2600 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2601 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2602 { PNormalValue, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2603 { PNormalValue, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2604 { PNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2605 { PNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2606 { PNormalValue, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2607 { PNormalValue, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2608 { PNormalValue, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2609 { PNormalValue, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2610 { MNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2611 { MNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2612 { MNormalValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2613 { MNormalValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2614 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2615 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2616 { MNormalValue, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2617 { MNormalValue, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2618 { MNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2619 { MNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2620 { MNormalValue, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2621 { MNormalValue, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2622 { MNormalValue, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2623 { MNormalValue, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2624 { PLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2625 { PLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2626 { PLargestValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2627 { PLargestValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2628 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2629 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2630 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2631 { PLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2632 { PLargestValue, PLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2633 { PLargestValue, MLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2634 { PLargestValue, PSmallestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2635 { PLargestValue, MSmallestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2636 { PLargestValue, PSmallestNormalized, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2637 { PLargestValue, MSmallestNormalized, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2638 { MLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2639 { MLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2640 { MLargestValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2641 { MLargestValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2642 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2643 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2644 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2645 { MLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2646 { MLargestValue, PLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2647 { MLargestValue, MLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2648 { MLargestValue, PSmallestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2649 { MLargestValue, MSmallestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2650 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2651 { MLargestValue, MSmallestNormalized, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2652 { PSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2653 { PSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2654 { PSmallestValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2655 { PSmallestValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2656 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2657 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2658 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2659 { PSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2660 { PSmallestValue, PLargestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2661 { PSmallestValue, MLargestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2662 { PSmallestValue, PSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2663 { PSmallestValue, MSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2664 { PSmallestValue, PSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2665 { PSmallestValue, MSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2666 { MSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2667 { MSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2668 { MSmallestValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2669 { MSmallestValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2670 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2671 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2672 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2673 { MSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2674 { MSmallestValue, PLargestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2675 { MSmallestValue, MLargestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2676 { MSmallestValue, PSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2677 { MSmallestValue, MSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2678 { MSmallestValue, PSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2679 { MSmallestValue, MSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2680 { PSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2681 { PSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2682 { PSmallestNormalized, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2683 { PSmallestNormalized, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2684 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2685 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2686 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2687 { PSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2688 { PSmallestNormalized, PLargestValue, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2689 { PSmallestNormalized, MLargestValue, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2690 { PSmallestNormalized, PSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2691 { PSmallestNormalized, MSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2692 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2693 { PSmallestNormalized, MSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2694 { MSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2695 { MSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2696 { MSmallestNormalized, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2697 { MSmallestNormalized, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2698 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2699 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2700 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2701 { MSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2702 { MSmallestNormalized, PLargestValue, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2703 { MSmallestNormalized, MLargestValue, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2704 { MSmallestNormalized, PSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2705 { MSmallestNormalized, MSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2706 { MSmallestNormalized, PSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2707 { MSmallestNormalized, MSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2708
2709 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2710 APFloat::fcNormal, APFloat::rmNearestTiesToEven},
2711 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2712 APFloat::fcNormal, APFloat::rmTowardPositive},
2713 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2714 APFloat::fcNormal, APFloat::rmTowardNegative},
2715 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2716 APFloat::fcNormal, APFloat::rmTowardZero},
2717 {MaxQuad, MinQuad, "0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2718 APFloat::fcNormal, APFloat::rmNearestTiesToAway},
2719
2720 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2721 APFloat::fcNormal, APFloat::rmNearestTiesToEven},
2722 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2723 APFloat::fcNormal, APFloat::rmTowardPositive},
2724 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2725 APFloat::fcNormal, APFloat::rmTowardNegative},
2726 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2727 APFloat::fcNormal, APFloat::rmTowardZero},
2728 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp-111", APFloat::opOK,
2729 APFloat::fcNormal, APFloat::rmNearestTiesToAway},
2730
2731 {MaxQuad, MaxQuad, "inf", OverflowStatus, APFloat::fcInfinity,
2732 APFloat::rmNearestTiesToEven},
2733 {MaxQuad, MaxQuad, "inf", OverflowStatus, APFloat::fcInfinity,
2734 APFloat::rmTowardPositive},
2735 {MaxQuad, MaxQuad, "0x1.ffffffffffffffffffffffffffffp+16383",
2736 APFloat::opInexact, APFloat::fcNormal, APFloat::rmTowardNegative},
2737 {MaxQuad, MaxQuad, "0x1.ffffffffffffffffffffffffffffp+16383",
2738 APFloat::opInexact, APFloat::fcNormal, APFloat::rmTowardZero},
2739 {MaxQuad, MaxQuad, "inf", OverflowStatus, APFloat::fcInfinity,
2740 APFloat::rmNearestTiesToAway},
2741
2742 {MinQuad, MinQuad, "0", UnderflowStatus, APFloat::fcZero,
2743 APFloat::rmNearestTiesToEven},
2744 {MinQuad, MinQuad, "0x0.0000000000000000000000000001p-16382",
2745 UnderflowStatus, APFloat::fcNormal, APFloat::rmTowardPositive},
2746 {MinQuad, MinQuad, "0", UnderflowStatus, APFloat::fcZero,
2747 APFloat::rmTowardNegative},
2748 {MinQuad, MinQuad, "0", UnderflowStatus, APFloat::fcZero,
2749 APFloat::rmTowardZero},
2750 {MinQuad, MinQuad, "0", UnderflowStatus, APFloat::fcZero,
2751 APFloat::rmNearestTiesToAway},
2752
2753 {MinQuad, NMinQuad, "-0", UnderflowStatus, APFloat::fcZero,
2754 APFloat::rmNearestTiesToEven},
2755 {MinQuad, NMinQuad, "-0", UnderflowStatus, APFloat::fcZero,
2756 APFloat::rmTowardPositive},
2757 {MinQuad, NMinQuad, "-0x0.0000000000000000000000000001p-16382",
2758 UnderflowStatus, APFloat::fcNormal, APFloat::rmTowardNegative},
2759 {MinQuad, NMinQuad, "-0", UnderflowStatus, APFloat::fcZero,
2760 APFloat::rmTowardZero},
2761 {MinQuad, NMinQuad, "-0", UnderflowStatus, APFloat::fcZero,
2762 APFloat::rmNearestTiesToAway},
2763 };
2764
2765 for (size_t i = 0; i < array_lengthof(SpecialCaseTests); ++i) {
2766 APFloat x(SpecialCaseTests[i].x);
2767 APFloat y(SpecialCaseTests[i].y);
2768 APFloat::opStatus status = x.multiply(y, SpecialCaseTests[i].roundingMode);
2769
2770 APFloat result(x.getSemantics(), SpecialCaseTests[i].result);
2771
2772 EXPECT_TRUE(result.bitwiseIsEqual(x));
2773 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
2774 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
2775 }
2776 }
2777
TEST(APFloatTest,divide)2778 TEST(APFloatTest, divide) {
2779 // Test Special Cases against each other and normal values.
2780
2781 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2782 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2783 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2784 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2785 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2786 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
2787 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2788 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2789 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2790 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2791 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2792 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
2793 APFloat PSmallestNormalized =
2794 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
2795 APFloat MSmallestNormalized =
2796 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
2797
2798 APFloat MaxQuad(APFloat::IEEEquad(),
2799 "0x1.ffffffffffffffffffffffffffffp+16383");
2800 APFloat MinQuad(APFloat::IEEEquad(),
2801 "0x0.0000000000000000000000000001p-16382");
2802 APFloat NMinQuad(APFloat::IEEEquad(),
2803 "-0x0.0000000000000000000000000001p-16382");
2804
2805 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2806 const int UnderflowStatus = APFloat::opUnderflow | APFloat::opInexact;
2807
2808 struct {
2809 APFloat x;
2810 APFloat y;
2811 const char *result;
2812 int status;
2813 int category;
2814 APFloat::roundingMode roundingMode = APFloat::rmNearestTiesToEven;
2815 } SpecialCaseTests[] = {
2816 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2817 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2818 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2819 { PInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2820 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2821 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2822 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2823 { PInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2824 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2825 { PInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2826 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2827 { PInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2828 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2829 { PInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2830 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2831 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2832 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2833 { MInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2834 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2835 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2836 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2837 { MInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2838 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2839 { MInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2840 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2841 { MInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2842 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2843 { MInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2844 { PZero, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2845 { PZero, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2846 { PZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2847 { PZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2848 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2849 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2850 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2851 { PZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2852 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2853 { PZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2854 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2855 { PZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2856 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2857 { PZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2858 { MZero, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2859 { MZero, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2860 { MZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2861 { MZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2862 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2863 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2864 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2865 { MZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2866 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2867 { MZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2868 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2869 { MZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2870 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2871 { MZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2872 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
2873 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
2874 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
2875 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
2876 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2877 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2878 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2879 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2880 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2881 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2882 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2883 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2884 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2885 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2886 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2887 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2888 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2889 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2890 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2891 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2892 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2893 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2894 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2895 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2896 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2897 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2898 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2899 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2900 { PNormalValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2901 { PNormalValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2902 { PNormalValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2903 { PNormalValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2904 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2905 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2906 { PNormalValue, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2907 { PNormalValue, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2908 { PNormalValue, PLargestValue, "0x1p-128", UnderflowStatus, APFloat::fcNormal },
2909 { PNormalValue, MLargestValue, "-0x1p-128", UnderflowStatus, APFloat::fcNormal },
2910 { PNormalValue, PSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2911 { PNormalValue, MSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2912 { PNormalValue, PSmallestNormalized, "0x1p+126", APFloat::opOK, APFloat::fcNormal },
2913 { PNormalValue, MSmallestNormalized, "-0x1p+126", APFloat::opOK, APFloat::fcNormal },
2914 { MNormalValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2915 { MNormalValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2916 { MNormalValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2917 { MNormalValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2918 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2919 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2920 { MNormalValue, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2921 { MNormalValue, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2922 { MNormalValue, PLargestValue, "-0x1p-128", UnderflowStatus, APFloat::fcNormal },
2923 { MNormalValue, MLargestValue, "0x1p-128", UnderflowStatus, APFloat::fcNormal },
2924 { MNormalValue, PSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2925 { MNormalValue, MSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2926 { MNormalValue, PSmallestNormalized, "-0x1p+126", APFloat::opOK, APFloat::fcNormal },
2927 { MNormalValue, MSmallestNormalized, "0x1p+126", APFloat::opOK, APFloat::fcNormal },
2928 { PLargestValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2929 { PLargestValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2930 { PLargestValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2931 { PLargestValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2932 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2933 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2934 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2935 { PLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2936 { PLargestValue, PLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2937 { PLargestValue, MLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2938 { PLargestValue, PSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2939 { PLargestValue, MSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2940 { PLargestValue, PSmallestNormalized, "inf", OverflowStatus, APFloat::fcInfinity },
2941 { PLargestValue, MSmallestNormalized, "-inf", OverflowStatus, APFloat::fcInfinity },
2942 { MLargestValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2943 { MLargestValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2944 { MLargestValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2945 { MLargestValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2946 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2947 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2948 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2949 { MLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2950 { MLargestValue, PLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2951 { MLargestValue, MLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2952 { MLargestValue, PSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2953 { MLargestValue, MSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2954 { MLargestValue, PSmallestNormalized, "-inf", OverflowStatus, APFloat::fcInfinity },
2955 { MLargestValue, MSmallestNormalized, "inf", OverflowStatus, APFloat::fcInfinity },
2956 { PSmallestValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2957 { PSmallestValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2958 { PSmallestValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2959 { PSmallestValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2960 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2961 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2962 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2963 { PSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2964 { PSmallestValue, PLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2965 { PSmallestValue, MLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2966 { PSmallestValue, PSmallestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2967 { PSmallestValue, MSmallestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2968 { PSmallestValue, PSmallestNormalized, "0x1p-23", APFloat::opOK, APFloat::fcNormal },
2969 { PSmallestValue, MSmallestNormalized, "-0x1p-23", APFloat::opOK, APFloat::fcNormal },
2970 { MSmallestValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2971 { MSmallestValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2972 { MSmallestValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2973 { MSmallestValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2974 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2975 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2976 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2977 { MSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2978 { MSmallestValue, PLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2979 { MSmallestValue, MLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2980 { MSmallestValue, PSmallestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2981 { MSmallestValue, MSmallestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2982 { MSmallestValue, PSmallestNormalized, "-0x1p-23", APFloat::opOK, APFloat::fcNormal },
2983 { MSmallestValue, MSmallestNormalized, "0x1p-23", APFloat::opOK, APFloat::fcNormal },
2984 { PSmallestNormalized, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2985 { PSmallestNormalized, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2986 { PSmallestNormalized, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2987 { PSmallestNormalized, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2988 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2989 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
2990 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2991 { PSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2992 { PSmallestNormalized, PLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2993 { PSmallestNormalized, MLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2994 { PSmallestNormalized, PSmallestValue, "0x1p+23", APFloat::opOK, APFloat::fcNormal },
2995 { PSmallestNormalized, MSmallestValue, "-0x1p+23", APFloat::opOK, APFloat::fcNormal },
2996 { PSmallestNormalized, PSmallestNormalized, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2997 { PSmallestNormalized, MSmallestNormalized, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2998 { MSmallestNormalized, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2999 { MSmallestNormalized, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3000 { MSmallestNormalized, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
3001 { MSmallestNormalized, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
3002 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3003 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3004 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3005 { MSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3006 { MSmallestNormalized, PLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
3007 { MSmallestNormalized, MLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
3008 { MSmallestNormalized, PSmallestValue, "-0x1p+23", APFloat::opOK, APFloat::fcNormal },
3009 { MSmallestNormalized, MSmallestValue, "0x1p+23", APFloat::opOK, APFloat::fcNormal },
3010 { MSmallestNormalized, PSmallestNormalized, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3011 { MSmallestNormalized, MSmallestNormalized, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3012
3013 {MaxQuad, NMinQuad, "-inf", OverflowStatus, APFloat::fcInfinity,
3014 APFloat::rmNearestTiesToEven},
3015 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp+16383",
3016 APFloat::opInexact, APFloat::fcNormal, APFloat::rmTowardPositive},
3017 {MaxQuad, NMinQuad, "-inf", OverflowStatus, APFloat::fcInfinity,
3018 APFloat::rmTowardNegative},
3019 {MaxQuad, NMinQuad, "-0x1.ffffffffffffffffffffffffffffp+16383",
3020 APFloat::opInexact, APFloat::fcNormal, APFloat::rmTowardZero},
3021 {MaxQuad, NMinQuad, "-inf", OverflowStatus, APFloat::fcInfinity,
3022 APFloat::rmNearestTiesToAway},
3023
3024 {MinQuad, MaxQuad, "0", UnderflowStatus, APFloat::fcZero,
3025 APFloat::rmNearestTiesToEven},
3026 {MinQuad, MaxQuad, "0x0.0000000000000000000000000001p-16382",
3027 UnderflowStatus, APFloat::fcNormal, APFloat::rmTowardPositive},
3028 {MinQuad, MaxQuad, "0", UnderflowStatus, APFloat::fcZero,
3029 APFloat::rmTowardNegative},
3030 {MinQuad, MaxQuad, "0", UnderflowStatus, APFloat::fcZero,
3031 APFloat::rmTowardZero},
3032 {MinQuad, MaxQuad, "0", UnderflowStatus, APFloat::fcZero,
3033 APFloat::rmNearestTiesToAway},
3034
3035 {NMinQuad, MaxQuad, "-0", UnderflowStatus, APFloat::fcZero,
3036 APFloat::rmNearestTiesToEven},
3037 {NMinQuad, MaxQuad, "-0", UnderflowStatus, APFloat::fcZero,
3038 APFloat::rmTowardPositive},
3039 {NMinQuad, MaxQuad, "-0x0.0000000000000000000000000001p-16382",
3040 UnderflowStatus, APFloat::fcNormal, APFloat::rmTowardNegative},
3041 {NMinQuad, MaxQuad, "-0", UnderflowStatus, APFloat::fcZero,
3042 APFloat::rmTowardZero},
3043 {NMinQuad, MaxQuad, "-0", UnderflowStatus, APFloat::fcZero,
3044 APFloat::rmNearestTiesToAway},
3045 };
3046
3047 for (size_t i = 0; i < array_lengthof(SpecialCaseTests); ++i) {
3048 APFloat x(SpecialCaseTests[i].x);
3049 APFloat y(SpecialCaseTests[i].y);
3050 APFloat::opStatus status = x.divide(y, SpecialCaseTests[i].roundingMode);
3051
3052 APFloat result(x.getSemantics(), SpecialCaseTests[i].result);
3053
3054 EXPECT_TRUE(result.bitwiseIsEqual(x));
3055 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
3056 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
3057 }
3058 }
3059
TEST(APFloatTest,operatorOverloads)3060 TEST(APFloatTest, operatorOverloads) {
3061 // This is mostly testing that these operator overloads compile.
3062 APFloat One = APFloat(APFloat::IEEEsingle(), "0x1p+0");
3063 APFloat Two = APFloat(APFloat::IEEEsingle(), "0x2p+0");
3064 EXPECT_TRUE(Two.bitwiseIsEqual(One + One));
3065 EXPECT_TRUE(One.bitwiseIsEqual(Two - One));
3066 EXPECT_TRUE(Two.bitwiseIsEqual(One * Two));
3067 EXPECT_TRUE(One.bitwiseIsEqual(Two / Two));
3068 }
3069
TEST(APFloatTest,Comparisons)3070 TEST(APFloatTest, Comparisons) {
3071 enum {MNan, MInf, MBig, MOne, MZer, PZer, POne, PBig, PInf, PNan, NumVals};
3072 APFloat Vals[NumVals] = {
3073 APFloat::getNaN(APFloat::IEEEsingle(), true),
3074 APFloat::getInf(APFloat::IEEEsingle(), true),
3075 APFloat::getLargest(APFloat::IEEEsingle(), true),
3076 APFloat(APFloat::IEEEsingle(), "-0x1p+0"),
3077 APFloat::getZero(APFloat::IEEEsingle(), true),
3078 APFloat::getZero(APFloat::IEEEsingle(), false),
3079 APFloat(APFloat::IEEEsingle(), "0x1p+0"),
3080 APFloat::getLargest(APFloat::IEEEsingle(), false),
3081 APFloat::getInf(APFloat::IEEEsingle(), false),
3082 APFloat::getNaN(APFloat::IEEEsingle(), false),
3083 };
3084 using Relation = void (*)(const APFloat &, const APFloat &);
3085 Relation LT = [](const APFloat &LHS, const APFloat &RHS) {
3086 EXPECT_FALSE(LHS == RHS);
3087 EXPECT_TRUE(LHS != RHS);
3088 EXPECT_TRUE(LHS < RHS);
3089 EXPECT_FALSE(LHS > RHS);
3090 EXPECT_TRUE(LHS <= RHS);
3091 EXPECT_FALSE(LHS >= RHS);
3092 };
3093 Relation EQ = [](const APFloat &LHS, const APFloat &RHS) {
3094 EXPECT_TRUE(LHS == RHS);
3095 EXPECT_FALSE(LHS != RHS);
3096 EXPECT_FALSE(LHS < RHS);
3097 EXPECT_FALSE(LHS > RHS);
3098 EXPECT_TRUE(LHS <= RHS);
3099 EXPECT_TRUE(LHS >= RHS);
3100 };
3101 Relation GT = [](const APFloat &LHS, const APFloat &RHS) {
3102 EXPECT_FALSE(LHS == RHS);
3103 EXPECT_TRUE(LHS != RHS);
3104 EXPECT_FALSE(LHS < RHS);
3105 EXPECT_TRUE(LHS > RHS);
3106 EXPECT_FALSE(LHS <= RHS);
3107 EXPECT_TRUE(LHS >= RHS);
3108 };
3109 Relation UN = [](const APFloat &LHS, const APFloat &RHS) {
3110 EXPECT_FALSE(LHS == RHS);
3111 EXPECT_TRUE(LHS != RHS);
3112 EXPECT_FALSE(LHS < RHS);
3113 EXPECT_FALSE(LHS > RHS);
3114 EXPECT_FALSE(LHS <= RHS);
3115 EXPECT_FALSE(LHS >= RHS);
3116 };
3117 Relation Relations[NumVals][NumVals] = {
3118 // -N -I -B -1 -0 +0 +1 +B +I +N
3119 /* MNan */ {UN, UN, UN, UN, UN, UN, UN, UN, UN, UN},
3120 /* MInf */ {UN, EQ, LT, LT, LT, LT, LT, LT, LT, UN},
3121 /* MBig */ {UN, GT, EQ, LT, LT, LT, LT, LT, LT, UN},
3122 /* MOne */ {UN, GT, GT, EQ, LT, LT, LT, LT, LT, UN},
3123 /* MZer */ {UN, GT, GT, GT, EQ, EQ, LT, LT, LT, UN},
3124 /* PZer */ {UN, GT, GT, GT, EQ, EQ, LT, LT, LT, UN},
3125 /* POne */ {UN, GT, GT, GT, GT, GT, EQ, LT, LT, UN},
3126 /* PBig */ {UN, GT, GT, GT, GT, GT, GT, EQ, LT, UN},
3127 /* PInf */ {UN, GT, GT, GT, GT, GT, GT, GT, EQ, UN},
3128 /* PNan */ {UN, UN, UN, UN, UN, UN, UN, UN, UN, UN},
3129 };
3130 for (unsigned I = 0; I < NumVals; ++I)
3131 for (unsigned J = 0; J < NumVals; ++J)
3132 Relations[I][J](Vals[I], Vals[J]);
3133 }
3134
TEST(APFloatTest,abs)3135 TEST(APFloatTest, abs) {
3136 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
3137 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
3138 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
3139 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
3140 APFloat PQNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
3141 APFloat MQNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
3142 APFloat PSNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
3143 APFloat MSNaN = APFloat::getSNaN(APFloat::IEEEsingle(), true);
3144 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
3145 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
3146 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
3147 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
3148 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
3149 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
3150 APFloat PSmallestNormalized =
3151 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
3152 APFloat MSmallestNormalized =
3153 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
3154
3155 EXPECT_TRUE(PInf.bitwiseIsEqual(abs(PInf)));
3156 EXPECT_TRUE(PInf.bitwiseIsEqual(abs(MInf)));
3157 EXPECT_TRUE(PZero.bitwiseIsEqual(abs(PZero)));
3158 EXPECT_TRUE(PZero.bitwiseIsEqual(abs(MZero)));
3159 EXPECT_TRUE(PQNaN.bitwiseIsEqual(abs(PQNaN)));
3160 EXPECT_TRUE(PQNaN.bitwiseIsEqual(abs(MQNaN)));
3161 EXPECT_TRUE(PSNaN.bitwiseIsEqual(abs(PSNaN)));
3162 EXPECT_TRUE(PSNaN.bitwiseIsEqual(abs(MSNaN)));
3163 EXPECT_TRUE(PNormalValue.bitwiseIsEqual(abs(PNormalValue)));
3164 EXPECT_TRUE(PNormalValue.bitwiseIsEqual(abs(MNormalValue)));
3165 EXPECT_TRUE(PLargestValue.bitwiseIsEqual(abs(PLargestValue)));
3166 EXPECT_TRUE(PLargestValue.bitwiseIsEqual(abs(MLargestValue)));
3167 EXPECT_TRUE(PSmallestValue.bitwiseIsEqual(abs(PSmallestValue)));
3168 EXPECT_TRUE(PSmallestValue.bitwiseIsEqual(abs(MSmallestValue)));
3169 EXPECT_TRUE(PSmallestNormalized.bitwiseIsEqual(abs(PSmallestNormalized)));
3170 EXPECT_TRUE(PSmallestNormalized.bitwiseIsEqual(abs(MSmallestNormalized)));
3171 }
3172
TEST(APFloatTest,neg)3173 TEST(APFloatTest, neg) {
3174 APFloat One = APFloat(APFloat::IEEEsingle(), "1.0");
3175 APFloat NegOne = APFloat(APFloat::IEEEsingle(), "-1.0");
3176 APFloat Zero = APFloat::getZero(APFloat::IEEEsingle(), false);
3177 APFloat NegZero = APFloat::getZero(APFloat::IEEEsingle(), true);
3178 APFloat Inf = APFloat::getInf(APFloat::IEEEsingle(), false);
3179 APFloat NegInf = APFloat::getInf(APFloat::IEEEsingle(), true);
3180 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
3181 APFloat NegQNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
3182
3183 EXPECT_TRUE(NegOne.bitwiseIsEqual(neg(One)));
3184 EXPECT_TRUE(One.bitwiseIsEqual(neg(NegOne)));
3185 EXPECT_TRUE(NegZero.bitwiseIsEqual(neg(Zero)));
3186 EXPECT_TRUE(Zero.bitwiseIsEqual(neg(NegZero)));
3187 EXPECT_TRUE(NegInf.bitwiseIsEqual(neg(Inf)));
3188 EXPECT_TRUE(Inf.bitwiseIsEqual(neg(NegInf)));
3189 EXPECT_TRUE(NegInf.bitwiseIsEqual(neg(Inf)));
3190 EXPECT_TRUE(Inf.bitwiseIsEqual(neg(NegInf)));
3191 EXPECT_TRUE(NegQNaN.bitwiseIsEqual(neg(QNaN)));
3192 EXPECT_TRUE(QNaN.bitwiseIsEqual(neg(NegQNaN)));
3193
3194 EXPECT_TRUE(NegOne.bitwiseIsEqual(-One));
3195 EXPECT_TRUE(One.bitwiseIsEqual(-NegOne));
3196 EXPECT_TRUE(NegZero.bitwiseIsEqual(-Zero));
3197 EXPECT_TRUE(Zero.bitwiseIsEqual(-NegZero));
3198 EXPECT_TRUE(NegInf.bitwiseIsEqual(-Inf));
3199 EXPECT_TRUE(Inf.bitwiseIsEqual(-NegInf));
3200 EXPECT_TRUE(NegInf.bitwiseIsEqual(-Inf));
3201 EXPECT_TRUE(Inf.bitwiseIsEqual(-NegInf));
3202 EXPECT_TRUE(NegQNaN.bitwiseIsEqual(-QNaN));
3203 EXPECT_TRUE(QNaN.bitwiseIsEqual(-NegQNaN));
3204 }
3205
TEST(APFloatTest,ilogb)3206 TEST(APFloatTest, ilogb) {
3207 EXPECT_EQ(-1074, ilogb(APFloat::getSmallest(APFloat::IEEEdouble(), false)));
3208 EXPECT_EQ(-1074, ilogb(APFloat::getSmallest(APFloat::IEEEdouble(), true)));
3209 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1024")));
3210 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023")));
3211 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023")));
3212 EXPECT_EQ(-51, ilogb(APFloat(APFloat::IEEEdouble(), "0x1p-51")));
3213 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1023")));
3214 EXPECT_EQ(-2, ilogb(APFloat(APFloat::IEEEdouble(), "0x0.ffffp-1")));
3215 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.fffep-1023")));
3216 EXPECT_EQ(1023, ilogb(APFloat::getLargest(APFloat::IEEEdouble(), false)));
3217 EXPECT_EQ(1023, ilogb(APFloat::getLargest(APFloat::IEEEdouble(), true)));
3218
3219
3220 EXPECT_EQ(0, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p+0")));
3221 EXPECT_EQ(0, ilogb(APFloat(APFloat::IEEEsingle(), "-0x1p+0")));
3222 EXPECT_EQ(42, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p+42")));
3223 EXPECT_EQ(-42, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p-42")));
3224
3225 EXPECT_EQ(APFloat::IEK_Inf,
3226 ilogb(APFloat::getInf(APFloat::IEEEsingle(), false)));
3227 EXPECT_EQ(APFloat::IEK_Inf,
3228 ilogb(APFloat::getInf(APFloat::IEEEsingle(), true)));
3229 EXPECT_EQ(APFloat::IEK_Zero,
3230 ilogb(APFloat::getZero(APFloat::IEEEsingle(), false)));
3231 EXPECT_EQ(APFloat::IEK_Zero,
3232 ilogb(APFloat::getZero(APFloat::IEEEsingle(), true)));
3233 EXPECT_EQ(APFloat::IEK_NaN,
3234 ilogb(APFloat::getNaN(APFloat::IEEEsingle(), false)));
3235 EXPECT_EQ(APFloat::IEK_NaN,
3236 ilogb(APFloat::getSNaN(APFloat::IEEEsingle(), false)));
3237
3238 EXPECT_EQ(127, ilogb(APFloat::getLargest(APFloat::IEEEsingle(), false)));
3239 EXPECT_EQ(127, ilogb(APFloat::getLargest(APFloat::IEEEsingle(), true)));
3240
3241 EXPECT_EQ(-149, ilogb(APFloat::getSmallest(APFloat::IEEEsingle(), false)));
3242 EXPECT_EQ(-149, ilogb(APFloat::getSmallest(APFloat::IEEEsingle(), true)));
3243 EXPECT_EQ(-126,
3244 ilogb(APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false)));
3245 EXPECT_EQ(-126,
3246 ilogb(APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true)));
3247 }
3248
TEST(APFloatTest,scalbn)3249 TEST(APFloatTest, scalbn) {
3250
3251 const APFloat::roundingMode RM = APFloat::rmNearestTiesToEven;
3252 EXPECT_TRUE(
3253 APFloat(APFloat::IEEEsingle(), "0x1p+0")
3254 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 0, RM)));
3255 EXPECT_TRUE(
3256 APFloat(APFloat::IEEEsingle(), "0x1p+42")
3257 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 42, RM)));
3258 EXPECT_TRUE(
3259 APFloat(APFloat::IEEEsingle(), "0x1p-42")
3260 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), -42, RM)));
3261
3262 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
3263 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
3264 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
3265 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
3266 APFloat QPNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
3267 APFloat QMNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
3268 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
3269
3270 EXPECT_TRUE(PInf.bitwiseIsEqual(scalbn(PInf, 0, RM)));
3271 EXPECT_TRUE(MInf.bitwiseIsEqual(scalbn(MInf, 0, RM)));
3272 EXPECT_TRUE(PZero.bitwiseIsEqual(scalbn(PZero, 0, RM)));
3273 EXPECT_TRUE(MZero.bitwiseIsEqual(scalbn(MZero, 0, RM)));
3274 EXPECT_TRUE(QPNaN.bitwiseIsEqual(scalbn(QPNaN, 0, RM)));
3275 EXPECT_TRUE(QMNaN.bitwiseIsEqual(scalbn(QMNaN, 0, RM)));
3276 EXPECT_FALSE(scalbn(SNaN, 0, RM).isSignaling());
3277
3278 APFloat ScalbnSNaN = scalbn(SNaN, 1, RM);
3279 EXPECT_TRUE(ScalbnSNaN.isNaN() && !ScalbnSNaN.isSignaling());
3280
3281 // Make sure highest bit of payload is preserved.
3282 const APInt Payload(64, (UINT64_C(1) << 50) |
3283 (UINT64_C(1) << 49) |
3284 (UINT64_C(1234) << 32) |
3285 1);
3286
3287 APFloat SNaNWithPayload = APFloat::getSNaN(APFloat::IEEEdouble(), false,
3288 &Payload);
3289 APFloat QuietPayload = scalbn(SNaNWithPayload, 1, RM);
3290 EXPECT_TRUE(QuietPayload.isNaN() && !QuietPayload.isSignaling());
3291 EXPECT_EQ(Payload, QuietPayload.bitcastToAPInt().getLoBits(51));
3292
3293 EXPECT_TRUE(PInf.bitwiseIsEqual(
3294 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 128, RM)));
3295 EXPECT_TRUE(MInf.bitwiseIsEqual(
3296 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p+0"), 128, RM)));
3297 EXPECT_TRUE(PInf.bitwiseIsEqual(
3298 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+127"), 1, RM)));
3299 EXPECT_TRUE(PZero.bitwiseIsEqual(
3300 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p-127"), -127, RM)));
3301 EXPECT_TRUE(MZero.bitwiseIsEqual(
3302 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p-127"), -127, RM)));
3303 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p-149").bitwiseIsEqual(
3304 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p-127"), -22, RM)));
3305 EXPECT_TRUE(PZero.bitwiseIsEqual(
3306 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p-126"), -24, RM)));
3307
3308
3309 APFloat SmallestF64 = APFloat::getSmallest(APFloat::IEEEdouble(), false);
3310 APFloat NegSmallestF64 = APFloat::getSmallest(APFloat::IEEEdouble(), true);
3311
3312 APFloat LargestF64 = APFloat::getLargest(APFloat::IEEEdouble(), false);
3313 APFloat NegLargestF64 = APFloat::getLargest(APFloat::IEEEdouble(), true);
3314
3315 APFloat SmallestNormalizedF64
3316 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
3317 APFloat NegSmallestNormalizedF64
3318 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
3319
3320 APFloat LargestDenormalF64(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023");
3321 APFloat NegLargestDenormalF64(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023");
3322
3323
3324 EXPECT_TRUE(SmallestF64.bitwiseIsEqual(
3325 scalbn(APFloat(APFloat::IEEEdouble(), "0x1p-1074"), 0, RM)));
3326 EXPECT_TRUE(NegSmallestF64.bitwiseIsEqual(
3327 scalbn(APFloat(APFloat::IEEEdouble(), "-0x1p-1074"), 0, RM)));
3328
3329 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1023")
3330 .bitwiseIsEqual(scalbn(SmallestF64, 2097, RM)));
3331
3332 EXPECT_TRUE(scalbn(SmallestF64, -2097, RM).isPosZero());
3333 EXPECT_TRUE(scalbn(SmallestF64, -2098, RM).isPosZero());
3334 EXPECT_TRUE(scalbn(SmallestF64, -2099, RM).isPosZero());
3335 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1022")
3336 .bitwiseIsEqual(scalbn(SmallestF64, 2096, RM)));
3337 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1023")
3338 .bitwiseIsEqual(scalbn(SmallestF64, 2097, RM)));
3339 EXPECT_TRUE(scalbn(SmallestF64, 2098, RM).isInfinity());
3340 EXPECT_TRUE(scalbn(SmallestF64, 2099, RM).isInfinity());
3341
3342 // Test for integer overflows when adding to exponent.
3343 EXPECT_TRUE(scalbn(SmallestF64, -INT_MAX, RM).isPosZero());
3344 EXPECT_TRUE(scalbn(LargestF64, INT_MAX, RM).isInfinity());
3345
3346 EXPECT_TRUE(LargestDenormalF64
3347 .bitwiseIsEqual(scalbn(LargestDenormalF64, 0, RM)));
3348 EXPECT_TRUE(NegLargestDenormalF64
3349 .bitwiseIsEqual(scalbn(NegLargestDenormalF64, 0, RM)));
3350
3351 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1022")
3352 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1, RM)));
3353 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1021")
3354 .bitwiseIsEqual(scalbn(NegLargestDenormalF64, 2, RM)));
3355
3356 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+1")
3357 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1024, RM)));
3358 EXPECT_TRUE(scalbn(LargestDenormalF64, -1023, RM).isPosZero());
3359 EXPECT_TRUE(scalbn(LargestDenormalF64, -1024, RM).isPosZero());
3360 EXPECT_TRUE(scalbn(LargestDenormalF64, -2048, RM).isPosZero());
3361 EXPECT_TRUE(scalbn(LargestDenormalF64, 2047, RM).isInfinity());
3362 EXPECT_TRUE(scalbn(LargestDenormalF64, 2098, RM).isInfinity());
3363 EXPECT_TRUE(scalbn(LargestDenormalF64, 2099, RM).isInfinity());
3364
3365 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-2")
3366 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1021, RM)));
3367 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1")
3368 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1022, RM)));
3369 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+0")
3370 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1023, RM)));
3371 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+1023")
3372 .bitwiseIsEqual(scalbn(LargestDenormalF64, 2046, RM)));
3373 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+974")
3374 .bitwiseIsEqual(scalbn(SmallestF64, 2048, RM)));
3375
3376 APFloat RandomDenormalF64(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+51");
3377 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-972")
3378 .bitwiseIsEqual(scalbn(RandomDenormalF64, -1023, RM)));
3379 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1")
3380 .bitwiseIsEqual(scalbn(RandomDenormalF64, -52, RM)));
3381 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-2")
3382 .bitwiseIsEqual(scalbn(RandomDenormalF64, -53, RM)));
3383 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+0")
3384 .bitwiseIsEqual(scalbn(RandomDenormalF64, -51, RM)));
3385
3386 EXPECT_TRUE(scalbn(RandomDenormalF64, -2097, RM).isPosZero());
3387 EXPECT_TRUE(scalbn(RandomDenormalF64, -2090, RM).isPosZero());
3388
3389
3390 EXPECT_TRUE(
3391 APFloat(APFloat::IEEEdouble(), "-0x1p-1073")
3392 .bitwiseIsEqual(scalbn(NegLargestF64, -2097, RM)));
3393
3394 EXPECT_TRUE(
3395 APFloat(APFloat::IEEEdouble(), "-0x1p-1024")
3396 .bitwiseIsEqual(scalbn(NegLargestF64, -2048, RM)));
3397
3398 EXPECT_TRUE(
3399 APFloat(APFloat::IEEEdouble(), "0x1p-1073")
3400 .bitwiseIsEqual(scalbn(LargestF64, -2097, RM)));
3401
3402 EXPECT_TRUE(
3403 APFloat(APFloat::IEEEdouble(), "0x1p-1074")
3404 .bitwiseIsEqual(scalbn(LargestF64, -2098, RM)));
3405 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1074")
3406 .bitwiseIsEqual(scalbn(NegLargestF64, -2098, RM)));
3407 EXPECT_TRUE(scalbn(NegLargestF64, -2099, RM).isNegZero());
3408 EXPECT_TRUE(scalbn(LargestF64, 1, RM).isInfinity());
3409
3410
3411 EXPECT_TRUE(
3412 APFloat(APFloat::IEEEdouble(), "0x1p+0")
3413 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEdouble(), "0x1p+52"), -52, RM)));
3414
3415 EXPECT_TRUE(
3416 APFloat(APFloat::IEEEdouble(), "0x1p-103")
3417 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEdouble(), "0x1p-51"), -52, RM)));
3418 }
3419
TEST(APFloatTest,frexp)3420 TEST(APFloatTest, frexp) {
3421 const APFloat::roundingMode RM = APFloat::rmNearestTiesToEven;
3422
3423 APFloat PZero = APFloat::getZero(APFloat::IEEEdouble(), false);
3424 APFloat MZero = APFloat::getZero(APFloat::IEEEdouble(), true);
3425 APFloat One(1.0);
3426 APFloat MOne(-1.0);
3427 APFloat Two(2.0);
3428 APFloat MTwo(-2.0);
3429
3430 APFloat LargestDenormal(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023");
3431 APFloat NegLargestDenormal(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023");
3432
3433 APFloat Smallest = APFloat::getSmallest(APFloat::IEEEdouble(), false);
3434 APFloat NegSmallest = APFloat::getSmallest(APFloat::IEEEdouble(), true);
3435
3436 APFloat Largest = APFloat::getLargest(APFloat::IEEEdouble(), false);
3437 APFloat NegLargest = APFloat::getLargest(APFloat::IEEEdouble(), true);
3438
3439 APFloat PInf = APFloat::getInf(APFloat::IEEEdouble(), false);
3440 APFloat MInf = APFloat::getInf(APFloat::IEEEdouble(), true);
3441
3442 APFloat QPNaN = APFloat::getNaN(APFloat::IEEEdouble(), false);
3443 APFloat QMNaN = APFloat::getNaN(APFloat::IEEEdouble(), true);
3444 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEdouble(), false);
3445
3446 // Make sure highest bit of payload is preserved.
3447 const APInt Payload(64, (UINT64_C(1) << 50) |
3448 (UINT64_C(1) << 49) |
3449 (UINT64_C(1234) << 32) |
3450 1);
3451
3452 APFloat SNaNWithPayload = APFloat::getSNaN(APFloat::IEEEdouble(), false,
3453 &Payload);
3454
3455 APFloat SmallestNormalized
3456 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
3457 APFloat NegSmallestNormalized
3458 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
3459
3460 int Exp;
3461 APFloat Frac(APFloat::IEEEdouble());
3462
3463
3464 Frac = frexp(PZero, Exp, RM);
3465 EXPECT_EQ(0, Exp);
3466 EXPECT_TRUE(Frac.isPosZero());
3467
3468 Frac = frexp(MZero, Exp, RM);
3469 EXPECT_EQ(0, Exp);
3470 EXPECT_TRUE(Frac.isNegZero());
3471
3472
3473 Frac = frexp(One, Exp, RM);
3474 EXPECT_EQ(1, Exp);
3475 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
3476
3477 Frac = frexp(MOne, Exp, RM);
3478 EXPECT_EQ(1, Exp);
3479 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1").bitwiseIsEqual(Frac));
3480
3481 Frac = frexp(LargestDenormal, Exp, RM);
3482 EXPECT_EQ(-1022, Exp);
3483 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1").bitwiseIsEqual(Frac));
3484
3485 Frac = frexp(NegLargestDenormal, Exp, RM);
3486 EXPECT_EQ(-1022, Exp);
3487 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1").bitwiseIsEqual(Frac));
3488
3489
3490 Frac = frexp(Smallest, Exp, RM);
3491 EXPECT_EQ(-1073, Exp);
3492 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
3493
3494 Frac = frexp(NegSmallest, Exp, RM);
3495 EXPECT_EQ(-1073, Exp);
3496 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1").bitwiseIsEqual(Frac));
3497
3498
3499 Frac = frexp(Largest, Exp, RM);
3500 EXPECT_EQ(1024, Exp);
3501 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.fffffffffffffp-1").bitwiseIsEqual(Frac));
3502
3503 Frac = frexp(NegLargest, Exp, RM);
3504 EXPECT_EQ(1024, Exp);
3505 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.fffffffffffffp-1").bitwiseIsEqual(Frac));
3506
3507
3508 Frac = frexp(PInf, Exp, RM);
3509 EXPECT_EQ(INT_MAX, Exp);
3510 EXPECT_TRUE(Frac.isInfinity() && !Frac.isNegative());
3511
3512 Frac = frexp(MInf, Exp, RM);
3513 EXPECT_EQ(INT_MAX, Exp);
3514 EXPECT_TRUE(Frac.isInfinity() && Frac.isNegative());
3515
3516 Frac = frexp(QPNaN, Exp, RM);
3517 EXPECT_EQ(INT_MIN, Exp);
3518 EXPECT_TRUE(Frac.isNaN());
3519
3520 Frac = frexp(QMNaN, Exp, RM);
3521 EXPECT_EQ(INT_MIN, Exp);
3522 EXPECT_TRUE(Frac.isNaN());
3523
3524 Frac = frexp(SNaN, Exp, RM);
3525 EXPECT_EQ(INT_MIN, Exp);
3526 EXPECT_TRUE(Frac.isNaN() && !Frac.isSignaling());
3527
3528 Frac = frexp(SNaNWithPayload, Exp, RM);
3529 EXPECT_EQ(INT_MIN, Exp);
3530 EXPECT_TRUE(Frac.isNaN() && !Frac.isSignaling());
3531 EXPECT_EQ(Payload, Frac.bitcastToAPInt().getLoBits(51));
3532
3533 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x0.ffffp-1"), Exp, RM);
3534 EXPECT_EQ(-1, Exp);
3535 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.fffep-1").bitwiseIsEqual(Frac));
3536
3537 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x1p-51"), Exp, RM);
3538 EXPECT_EQ(-50, Exp);
3539 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
3540
3541 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+51"), Exp, RM);
3542 EXPECT_EQ(52, Exp);
3543 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1").bitwiseIsEqual(Frac));
3544 }
3545
TEST(APFloatTest,mod)3546 TEST(APFloatTest, mod) {
3547 {
3548 APFloat f1(APFloat::IEEEdouble(), "1.5");
3549 APFloat f2(APFloat::IEEEdouble(), "1.0");
3550 APFloat expected(APFloat::IEEEdouble(), "0.5");
3551 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3552 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3553 }
3554 {
3555 APFloat f1(APFloat::IEEEdouble(), "0.5");
3556 APFloat f2(APFloat::IEEEdouble(), "1.0");
3557 APFloat expected(APFloat::IEEEdouble(), "0.5");
3558 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3559 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3560 }
3561 {
3562 APFloat f1(APFloat::IEEEdouble(), "0x1.3333333333333p-2"); // 0.3
3563 APFloat f2(APFloat::IEEEdouble(), "0x1.47ae147ae147bp-7"); // 0.01
3564 APFloat expected(APFloat::IEEEdouble(),
3565 "0x1.47ae147ae1471p-7"); // 0.009999999999999983
3566 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3567 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3568 }
3569 {
3570 APFloat f1(APFloat::IEEEdouble(), "0x1p64"); // 1.8446744073709552e19
3571 APFloat f2(APFloat::IEEEdouble(), "1.5");
3572 APFloat expected(APFloat::IEEEdouble(), "1.0");
3573 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3574 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3575 }
3576 {
3577 APFloat f1(APFloat::IEEEdouble(), "0x1p1000");
3578 APFloat f2(APFloat::IEEEdouble(), "0x1p-1000");
3579 APFloat expected(APFloat::IEEEdouble(), "0.0");
3580 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3581 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3582 }
3583 {
3584 APFloat f1(APFloat::IEEEdouble(), "0.0");
3585 APFloat f2(APFloat::IEEEdouble(), "1.0");
3586 APFloat expected(APFloat::IEEEdouble(), "0.0");
3587 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3588 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3589 }
3590 {
3591 APFloat f1(APFloat::IEEEdouble(), "1.0");
3592 APFloat f2(APFloat::IEEEdouble(), "0.0");
3593 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3594 EXPECT_TRUE(f1.isNaN());
3595 }
3596 {
3597 APFloat f1(APFloat::IEEEdouble(), "0.0");
3598 APFloat f2(APFloat::IEEEdouble(), "0.0");
3599 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3600 EXPECT_TRUE(f1.isNaN());
3601 }
3602 {
3603 APFloat f1 = APFloat::getInf(APFloat::IEEEdouble(), false);
3604 APFloat f2(APFloat::IEEEdouble(), "1.0");
3605 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3606 EXPECT_TRUE(f1.isNaN());
3607 }
3608 {
3609 APFloat f1(APFloat::IEEEdouble(), "-4.0");
3610 APFloat f2(APFloat::IEEEdouble(), "-2.0");
3611 APFloat expected(APFloat::IEEEdouble(), "-0.0");
3612 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3613 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3614 }
3615 {
3616 APFloat f1(APFloat::IEEEdouble(), "-4.0");
3617 APFloat f2(APFloat::IEEEdouble(), "2.0");
3618 APFloat expected(APFloat::IEEEdouble(), "-0.0");
3619 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3620 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3621 }
3622 }
3623
TEST(APFloatTest,remainder)3624 TEST(APFloatTest, remainder) {
3625 // Test Special Cases against each other and normal values.
3626
3627 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
3628 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
3629 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
3630 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
3631 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
3632 APFloat SNaN = APFloat(APFloat::IEEEsingle(), "snan123");
3633 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
3634 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
3635 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
3636 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
3637 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
3638 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
3639 APFloat PSmallestNormalized =
3640 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
3641 APFloat MSmallestNormalized =
3642 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
3643
3644 APFloat PVal1(APFloat::IEEEsingle(), "0x1.fffffep+126");
3645 APFloat MVal1(APFloat::IEEEsingle(), "-0x1.fffffep+126");
3646 APFloat PVal2(APFloat::IEEEsingle(), "0x1.fffffep-126");
3647 APFloat MVal2(APFloat::IEEEsingle(), "-0x1.fffffep-126");
3648 APFloat PVal3(APFloat::IEEEsingle(), "0x1p-125");
3649 APFloat MVal3(APFloat::IEEEsingle(), "-0x1p-125");
3650 APFloat PVal4(APFloat::IEEEsingle(), "0x1p+127");
3651 APFloat MVal4(APFloat::IEEEsingle(), "-0x1p+127");
3652 APFloat PVal5(APFloat::IEEEsingle(), "1.5");
3653 APFloat MVal5(APFloat::IEEEsingle(), "-1.5");
3654 APFloat PVal6(APFloat::IEEEsingle(), "1");
3655 APFloat MVal6(APFloat::IEEEsingle(), "-1");
3656
3657 struct {
3658 APFloat x;
3659 APFloat y;
3660 const char *result;
3661 int status;
3662 int category;
3663 } SpecialCaseTests[] = {
3664 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3665 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3666 { PInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3667 { PInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3668 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3669 { PInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3670 { PInf, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3671 { PInf, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3672 { PInf, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3673 { PInf, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3674 { PInf, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3675 { PInf, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3676 { PInf, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3677 { PInf, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3678 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3679 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3680 { MInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3681 { MInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3682 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3683 { MInf, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3684 { MInf, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3685 { MInf, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3686 { MInf, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3687 { MInf, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3688 { MInf, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3689 { MInf, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3690 { MInf, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3691 { MInf, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3692 { PZero, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3693 { PZero, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3694 { PZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3695 { PZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3696 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3697 { PZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3698 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3699 { PZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3700 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3701 { PZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3702 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3703 { PZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3704 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3705 { PZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3706 { MZero, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3707 { MZero, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3708 { MZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3709 { MZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3710 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3711 { MZero, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3712 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3713 { MZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3714 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3715 { MZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3716 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3717 { MZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3718 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3719 { MZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3720 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
3721 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
3722 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
3723 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
3724 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3725 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3726 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
3727 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
3728 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
3729 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
3730 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
3731 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
3732 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
3733 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
3734 { SNaN, PInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3735 { SNaN, MInf, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3736 { SNaN, PZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3737 { SNaN, MZero, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3738 { SNaN, QNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3739 { SNaN, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3740 { SNaN, PNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3741 { SNaN, MNormalValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3742 { SNaN, PLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3743 { SNaN, MLargestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3744 { SNaN, PSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3745 { SNaN, MSmallestValue, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3746 { SNaN, PSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3747 { SNaN, MSmallestNormalized, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3748 { PNormalValue, PInf, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3749 { PNormalValue, MInf, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3750 { PNormalValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3751 { PNormalValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3752 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3753 { PNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3754 { PNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3755 { PNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3756 { PNormalValue, PLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3757 { PNormalValue, MLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3758 { PNormalValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3759 { PNormalValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3760 { PNormalValue, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3761 { PNormalValue, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3762 { MNormalValue, PInf, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3763 { MNormalValue, MInf, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3764 { MNormalValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3765 { MNormalValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3766 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3767 { MNormalValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3768 { MNormalValue, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3769 { MNormalValue, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3770 { MNormalValue, PLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3771 { MNormalValue, MLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3772 { MNormalValue, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3773 { MNormalValue, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3774 { MNormalValue, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3775 { MNormalValue, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3776 { PLargestValue, PInf, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
3777 { PLargestValue, MInf, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
3778 { PLargestValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3779 { PLargestValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3780 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3781 { PLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3782 { PLargestValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3783 { PLargestValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3784 { PLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3785 { PLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3786 { PLargestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3787 { PLargestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3788 { PLargestValue, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3789 { PLargestValue, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3790 { MLargestValue, PInf, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
3791 { MLargestValue, MInf, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
3792 { MLargestValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3793 { MLargestValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3794 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3795 { MLargestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3796 { MLargestValue, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3797 { MLargestValue, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3798 { MLargestValue, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3799 { MLargestValue, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3800 { MLargestValue, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3801 { MLargestValue, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3802 { MLargestValue, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3803 { MLargestValue, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3804 { PSmallestValue, PInf, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3805 { PSmallestValue, MInf, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3806 { PSmallestValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3807 { PSmallestValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3808 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3809 { PSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3810 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3811 { PSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3812 { PSmallestValue, PLargestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3813 { PSmallestValue, MLargestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3814 { PSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3815 { PSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3816 { PSmallestValue, PSmallestNormalized, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3817 { PSmallestValue, MSmallestNormalized, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
3818 { MSmallestValue, PInf, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3819 { MSmallestValue, MInf, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3820 { MSmallestValue, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3821 { MSmallestValue, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3822 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3823 { MSmallestValue, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3824 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3825 { MSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3826 { MSmallestValue, PLargestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3827 { MSmallestValue, MLargestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3828 { MSmallestValue, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3829 { MSmallestValue, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3830 { MSmallestValue, PSmallestNormalized, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3831 { MSmallestValue, MSmallestNormalized, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
3832 { PSmallestNormalized, PInf, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3833 { PSmallestNormalized, MInf, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3834 { PSmallestNormalized, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3835 { PSmallestNormalized, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3836 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3837 { PSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3838 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3839 { PSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3840 { PSmallestNormalized, PLargestValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3841 { PSmallestNormalized, MLargestValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
3842 { PSmallestNormalized, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3843 { PSmallestNormalized, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3844 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3845 { PSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3846 { MSmallestNormalized, PInf, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3847 { MSmallestNormalized, MInf, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3848 { MSmallestNormalized, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3849 { MSmallestNormalized, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
3850 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
3851 { MSmallestNormalized, SNaN, "nan123", APFloat::opInvalidOp, APFloat::fcNaN },
3852 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3853 { MSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3854 { MSmallestNormalized, PLargestValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3855 { MSmallestNormalized, MLargestValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
3856 { MSmallestNormalized, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3857 { MSmallestNormalized, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3858 { MSmallestNormalized, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3859 { MSmallestNormalized, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3860
3861 { PVal1, PVal1, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3862 { PVal1, MVal1, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3863 { PVal1, PVal2, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3864 { PVal1, MVal2, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3865 { PVal1, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3866 { PVal1, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3867 { PVal1, PVal4, "-0x1p+103", APFloat::opOK, APFloat::fcNormal },
3868 { PVal1, MVal4, "-0x1p+103", APFloat::opOK, APFloat::fcNormal },
3869 { PVal1, PVal5, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3870 { PVal1, MVal5, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3871 { PVal1, PVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3872 { PVal1, MVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3873 { MVal1, PVal1, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3874 { MVal1, MVal1, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3875 { MVal1, PVal2, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3876 { MVal1, MVal2, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3877 { MVal1, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3878 { MVal1, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3879 { MVal1, PVal4, "0x1p+103", APFloat::opOK, APFloat::fcNormal },
3880 { MVal1, MVal4, "0x1p+103", APFloat::opOK, APFloat::fcNormal },
3881 { MVal1, PVal5, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3882 { MVal1, MVal5, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3883 { MVal1, PVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3884 { MVal1, MVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3885 { PVal2, PVal1, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3886 { PVal2, MVal1, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3887 { PVal2, PVal2, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3888 { PVal2, MVal2, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3889 { PVal2, PVal3, "-0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
3890 { PVal2, MVal3, "-0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
3891 { PVal2, PVal4, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3892 { PVal2, MVal4, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3893 { PVal2, PVal5, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3894 { PVal2, MVal5, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3895 { PVal2, PVal6, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3896 { PVal2, MVal6, "0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3897 { MVal2, PVal1, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3898 { MVal2, MVal1, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3899 { MVal2, PVal2, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3900 { MVal2, MVal2, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3901 { MVal2, PVal3, "0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
3902 { MVal2, MVal3, "0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
3903 { MVal2, PVal4, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3904 { MVal2, MVal4, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3905 { MVal2, PVal5, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3906 { MVal2, MVal5, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3907 { MVal2, PVal6, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3908 { MVal2, MVal6, "-0x1.fffffep-126", APFloat::opOK, APFloat::fcNormal },
3909 { PVal3, PVal1, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
3910 { PVal3, MVal1, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
3911 { PVal3, PVal2, "0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
3912 { PVal3, MVal2, "0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
3913 { PVal3, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3914 { PVal3, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3915 { PVal3, PVal4, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
3916 { PVal3, MVal4, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
3917 { PVal3, PVal5, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
3918 { PVal3, MVal5, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
3919 { PVal3, PVal6, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
3920 { PVal3, MVal6, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
3921 { MVal3, PVal1, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
3922 { MVal3, MVal1, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
3923 { MVal3, PVal2, "-0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
3924 { MVal3, MVal2, "-0x0.000002p-126", APFloat::opOK, APFloat::fcNormal },
3925 { MVal3, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3926 { MVal3, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3927 { MVal3, PVal4, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
3928 { MVal3, MVal4, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
3929 { MVal3, PVal5, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
3930 { MVal3, MVal5, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
3931 { MVal3, PVal6, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
3932 { MVal3, MVal6, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
3933 { PVal4, PVal1, "0x1p+103", APFloat::opOK, APFloat::fcNormal },
3934 { PVal4, MVal1, "0x1p+103", APFloat::opOK, APFloat::fcNormal },
3935 { PVal4, PVal2, "0x0.002p-126", APFloat::opOK, APFloat::fcNormal },
3936 { PVal4, MVal2, "0x0.002p-126", APFloat::opOK, APFloat::fcNormal },
3937 { PVal4, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3938 { PVal4, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3939 { PVal4, PVal4, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3940 { PVal4, MVal4, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3941 { PVal4, PVal5, "0.5", APFloat::opOK, APFloat::fcNormal },
3942 { PVal4, MVal5, "0.5", APFloat::opOK, APFloat::fcNormal },
3943 { PVal4, PVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3944 { PVal4, MVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3945 { MVal4, PVal1, "-0x1p+103", APFloat::opOK, APFloat::fcNormal },
3946 { MVal4, MVal1, "-0x1p+103", APFloat::opOK, APFloat::fcNormal },
3947 { MVal4, PVal2, "-0x0.002p-126", APFloat::opOK, APFloat::fcNormal },
3948 { MVal4, MVal2, "-0x0.002p-126", APFloat::opOK, APFloat::fcNormal },
3949 { MVal4, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3950 { MVal4, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3951 { MVal4, PVal4, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3952 { MVal4, MVal4, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3953 { MVal4, PVal5, "-0.5", APFloat::opOK, APFloat::fcNormal },
3954 { MVal4, MVal5, "-0.5", APFloat::opOK, APFloat::fcNormal },
3955 { MVal4, PVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3956 { MVal4, MVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3957 { PVal5, PVal1, "1.5", APFloat::opOK, APFloat::fcNormal },
3958 { PVal5, MVal1, "1.5", APFloat::opOK, APFloat::fcNormal },
3959 { PVal5, PVal2, "0x0.00006p-126", APFloat::opOK, APFloat::fcNormal },
3960 { PVal5, MVal2, "0x0.00006p-126", APFloat::opOK, APFloat::fcNormal },
3961 { PVal5, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3962 { PVal5, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3963 { PVal5, PVal4, "1.5", APFloat::opOK, APFloat::fcNormal },
3964 { PVal5, MVal4, "1.5", APFloat::opOK, APFloat::fcNormal },
3965 { PVal5, PVal5, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3966 { PVal5, MVal5, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3967 { PVal5, PVal6, "-0.5", APFloat::opOK, APFloat::fcNormal },
3968 { PVal5, MVal6, "-0.5", APFloat::opOK, APFloat::fcNormal },
3969 { MVal5, PVal1, "-1.5", APFloat::opOK, APFloat::fcNormal },
3970 { MVal5, MVal1, "-1.5", APFloat::opOK, APFloat::fcNormal },
3971 { MVal5, PVal2, "-0x0.00006p-126", APFloat::opOK, APFloat::fcNormal },
3972 { MVal5, MVal2, "-0x0.00006p-126", APFloat::opOK, APFloat::fcNormal },
3973 { MVal5, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3974 { MVal5, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3975 { MVal5, PVal4, "-1.5", APFloat::opOK, APFloat::fcNormal },
3976 { MVal5, MVal4, "-1.5", APFloat::opOK, APFloat::fcNormal },
3977 { MVal5, PVal5, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3978 { MVal5, MVal5, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3979 { MVal5, PVal6, "0.5", APFloat::opOK, APFloat::fcNormal },
3980 { MVal5, MVal6, "0.5", APFloat::opOK, APFloat::fcNormal },
3981 { PVal6, PVal1, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3982 { PVal6, MVal1, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3983 { PVal6, PVal2, "0x0.00004p-126", APFloat::opOK, APFloat::fcNormal },
3984 { PVal6, MVal2, "0x0.00004p-126", APFloat::opOK, APFloat::fcNormal },
3985 { PVal6, PVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3986 { PVal6, MVal3, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3987 { PVal6, PVal4, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3988 { PVal6, MVal4, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
3989 { PVal6, PVal5, "-0.5", APFloat::opOK, APFloat::fcNormal },
3990 { PVal6, MVal5, "-0.5", APFloat::opOK, APFloat::fcNormal },
3991 { PVal6, PVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3992 { PVal6, MVal6, "0x0p+0", APFloat::opOK, APFloat::fcZero },
3993 { MVal6, PVal1, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3994 { MVal6, MVal1, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
3995 { MVal6, PVal2, "-0x0.00004p-126", APFloat::opOK, APFloat::fcNormal },
3996 { MVal6, MVal2, "-0x0.00004p-126", APFloat::opOK, APFloat::fcNormal },
3997 { MVal6, PVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3998 { MVal6, MVal3, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
3999 { MVal6, PVal4, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4000 { MVal6, MVal4, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
4001 { MVal6, PVal5, "0.5", APFloat::opOK, APFloat::fcNormal },
4002 { MVal6, MVal5, "0.5", APFloat::opOK, APFloat::fcNormal },
4003 { MVal6, PVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4004 { MVal6, MVal6, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
4005 };
4006
4007 for (size_t i = 0; i < array_lengthof(SpecialCaseTests); ++i) {
4008 APFloat x(SpecialCaseTests[i].x);
4009 APFloat y(SpecialCaseTests[i].y);
4010 APFloat::opStatus status = x.remainder(y);
4011
4012 APFloat result(x.getSemantics(), SpecialCaseTests[i].result);
4013
4014 EXPECT_TRUE(result.bitwiseIsEqual(x));
4015 EXPECT_EQ(SpecialCaseTests[i].status, (int)status);
4016 EXPECT_EQ(SpecialCaseTests[i].category, (int)x.getCategory());
4017 }
4018
4019 {
4020 APFloat f1(APFloat::IEEEdouble(), "0x1.3333333333333p-2"); // 0.3
4021 APFloat f2(APFloat::IEEEdouble(), "0x1.47ae147ae147bp-7"); // 0.01
4022 APFloat expected(APFloat::IEEEdouble(), "-0x1.4p-56");
4023 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4024 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4025 }
4026 {
4027 APFloat f1(APFloat::IEEEdouble(), "0x1p64"); // 1.8446744073709552e19
4028 APFloat f2(APFloat::IEEEdouble(), "1.5");
4029 APFloat expected(APFloat::IEEEdouble(), "-0.5");
4030 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4031 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4032 }
4033 {
4034 APFloat f1(APFloat::IEEEdouble(), "0x1p1000");
4035 APFloat f2(APFloat::IEEEdouble(), "0x1p-1000");
4036 APFloat expected(APFloat::IEEEdouble(), "0.0");
4037 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4038 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4039 }
4040 {
4041 APFloat f1 = APFloat::getInf(APFloat::IEEEdouble(), false);
4042 APFloat f2(APFloat::IEEEdouble(), "1.0");
4043 EXPECT_EQ(f1.remainder(f2), APFloat::opInvalidOp);
4044 EXPECT_TRUE(f1.isNaN());
4045 }
4046 {
4047 APFloat f1(APFloat::IEEEdouble(), "-4.0");
4048 APFloat f2(APFloat::IEEEdouble(), "-2.0");
4049 APFloat expected(APFloat::IEEEdouble(), "-0.0");
4050 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4051 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4052 }
4053 {
4054 APFloat f1(APFloat::IEEEdouble(), "-4.0");
4055 APFloat f2(APFloat::IEEEdouble(), "2.0");
4056 APFloat expected(APFloat::IEEEdouble(), "-0.0");
4057 EXPECT_EQ(APFloat::opOK, f1.remainder(f2));
4058 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
4059 }
4060 }
4061
TEST(APFloatTest,PPCDoubleDoubleAddSpecial)4062 TEST(APFloatTest, PPCDoubleDoubleAddSpecial) {
4063 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t,
4064 APFloat::fltCategory, APFloat::roundingMode>;
4065 DataType Data[] = {
4066 // (1 + 0) + (-1 + 0) = fcZero
4067 std::make_tuple(0x3ff0000000000000ull, 0, 0xbff0000000000000ull, 0,
4068 APFloat::fcZero, APFloat::rmNearestTiesToEven),
4069 // LDBL_MAX + (1.1 >> (1023 - 106) + 0)) = fcInfinity
4070 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4071 0x7948000000000000ull, 0ull, APFloat::fcInfinity,
4072 APFloat::rmNearestTiesToEven),
4073 // TODO: change the 4th 0x75effffffffffffe to 0x75efffffffffffff when
4074 // semPPCDoubleDoubleLegacy is gone.
4075 // LDBL_MAX + (1.011111... >> (1023 - 106) + (1.1111111...0 >> (1023 -
4076 // 160))) = fcNormal
4077 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4078 0x7947ffffffffffffull, 0x75effffffffffffeull,
4079 APFloat::fcNormal, APFloat::rmNearestTiesToEven),
4080 // LDBL_MAX + (1.1 >> (1023 - 106) + 0)) = fcInfinity
4081 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4082 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4083 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
4084 // NaN + (1 + 0) = fcNaN
4085 std::make_tuple(0x7ff8000000000000ull, 0, 0x3ff0000000000000ull, 0,
4086 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
4087 };
4088
4089 for (auto Tp : Data) {
4090 uint64_t Op1[2], Op2[2];
4091 APFloat::fltCategory Expected;
4092 APFloat::roundingMode RM;
4093 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected, RM) = Tp;
4094
4095 {
4096 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4097 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4098 A1.add(A2, RM);
4099
4100 EXPECT_EQ(Expected, A1.getCategory())
4101 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
4102 Op2[0], Op2[1])
4103 .str();
4104 }
4105 {
4106 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4107 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4108 A2.add(A1, RM);
4109
4110 EXPECT_EQ(Expected, A2.getCategory())
4111 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
4112 Op1[0], Op1[1])
4113 .str();
4114 }
4115 }
4116 }
4117
TEST(APFloatTest,PPCDoubleDoubleAdd)4118 TEST(APFloatTest, PPCDoubleDoubleAdd) {
4119 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
4120 uint64_t, APFloat::roundingMode>;
4121 DataType Data[] = {
4122 // (1 + 0) + (1e-105 + 0) = (1 + 1e-105)
4123 std::make_tuple(0x3ff0000000000000ull, 0, 0x3960000000000000ull, 0,
4124 0x3ff0000000000000ull, 0x3960000000000000ull,
4125 APFloat::rmNearestTiesToEven),
4126 // (1 + 0) + (1e-106 + 0) = (1 + 1e-106)
4127 std::make_tuple(0x3ff0000000000000ull, 0, 0x3950000000000000ull, 0,
4128 0x3ff0000000000000ull, 0x3950000000000000ull,
4129 APFloat::rmNearestTiesToEven),
4130 // (1 + 1e-106) + (1e-106 + 0) = (1 + 1e-105)
4131 std::make_tuple(0x3ff0000000000000ull, 0x3950000000000000ull,
4132 0x3950000000000000ull, 0, 0x3ff0000000000000ull,
4133 0x3960000000000000ull, APFloat::rmNearestTiesToEven),
4134 // (1 + 0) + (epsilon + 0) = (1 + epsilon)
4135 std::make_tuple(0x3ff0000000000000ull, 0, 0x0000000000000001ull, 0,
4136 0x3ff0000000000000ull, 0x0000000000000001ull,
4137 APFloat::rmNearestTiesToEven),
4138 // TODO: change 0xf950000000000000 to 0xf940000000000000, when
4139 // semPPCDoubleDoubleLegacy is gone.
4140 // (DBL_MAX - 1 << (1023 - 105)) + (1 << (1023 - 53) + 0) = DBL_MAX +
4141 // 1.11111... << (1023 - 52)
4142 std::make_tuple(0x7fefffffffffffffull, 0xf950000000000000ull,
4143 0x7c90000000000000ull, 0, 0x7fefffffffffffffull,
4144 0x7c8ffffffffffffeull, APFloat::rmNearestTiesToEven),
4145 // TODO: change 0xf950000000000000 to 0xf940000000000000, when
4146 // semPPCDoubleDoubleLegacy is gone.
4147 // (1 << (1023 - 53) + 0) + (DBL_MAX - 1 << (1023 - 105)) = DBL_MAX +
4148 // 1.11111... << (1023 - 52)
4149 std::make_tuple(0x7c90000000000000ull, 0, 0x7fefffffffffffffull,
4150 0xf950000000000000ull, 0x7fefffffffffffffull,
4151 0x7c8ffffffffffffeull, APFloat::rmNearestTiesToEven),
4152 };
4153
4154 for (auto Tp : Data) {
4155 uint64_t Op1[2], Op2[2], Expected[2];
4156 APFloat::roundingMode RM;
4157 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
4158
4159 {
4160 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4161 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4162 A1.add(A2, RM);
4163
4164 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4165 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
4166 Op2[0], Op2[1])
4167 .str();
4168 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4169 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
4170 Op2[0], Op2[1])
4171 .str();
4172 }
4173 {
4174 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4175 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4176 A2.add(A1, RM);
4177
4178 EXPECT_EQ(Expected[0], A2.bitcastToAPInt().getRawData()[0])
4179 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
4180 Op1[0], Op1[1])
4181 .str();
4182 EXPECT_EQ(Expected[1], A2.bitcastToAPInt().getRawData()[1])
4183 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
4184 Op1[0], Op1[1])
4185 .str();
4186 }
4187 }
4188 }
4189
TEST(APFloatTest,PPCDoubleDoubleSubtract)4190 TEST(APFloatTest, PPCDoubleDoubleSubtract) {
4191 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
4192 uint64_t, APFloat::roundingMode>;
4193 DataType Data[] = {
4194 // (1 + 0) - (-1e-105 + 0) = (1 + 1e-105)
4195 std::make_tuple(0x3ff0000000000000ull, 0, 0xb960000000000000ull, 0,
4196 0x3ff0000000000000ull, 0x3960000000000000ull,
4197 APFloat::rmNearestTiesToEven),
4198 // (1 + 0) - (-1e-106 + 0) = (1 + 1e-106)
4199 std::make_tuple(0x3ff0000000000000ull, 0, 0xb950000000000000ull, 0,
4200 0x3ff0000000000000ull, 0x3950000000000000ull,
4201 APFloat::rmNearestTiesToEven),
4202 };
4203
4204 for (auto Tp : Data) {
4205 uint64_t Op1[2], Op2[2], Expected[2];
4206 APFloat::roundingMode RM;
4207 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
4208
4209 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4210 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4211 A1.subtract(A2, RM);
4212
4213 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4214 << formatv("({0:x} + {1:x}) - ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4215 Op2[1])
4216 .str();
4217 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4218 << formatv("({0:x} + {1:x}) - ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4219 Op2[1])
4220 .str();
4221 }
4222 }
4223
TEST(APFloatTest,PPCDoubleDoubleMultiplySpecial)4224 TEST(APFloatTest, PPCDoubleDoubleMultiplySpecial) {
4225 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t,
4226 APFloat::fltCategory, APFloat::roundingMode>;
4227 DataType Data[] = {
4228 // fcNaN * fcNaN = fcNaN
4229 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0,
4230 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
4231 // fcNaN * fcZero = fcNaN
4232 std::make_tuple(0x7ff8000000000000ull, 0, 0, 0, APFloat::fcNaN,
4233 APFloat::rmNearestTiesToEven),
4234 // fcNaN * fcInfinity = fcNaN
4235 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff0000000000000ull, 0,
4236 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
4237 // fcNaN * fcNormal = fcNaN
4238 std::make_tuple(0x7ff8000000000000ull, 0, 0x3ff0000000000000ull, 0,
4239 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
4240 // fcInfinity * fcInfinity = fcInfinity
4241 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0,
4242 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
4243 // fcInfinity * fcZero = fcNaN
4244 std::make_tuple(0x7ff0000000000000ull, 0, 0, 0, APFloat::fcNaN,
4245 APFloat::rmNearestTiesToEven),
4246 // fcInfinity * fcNormal = fcInfinity
4247 std::make_tuple(0x7ff0000000000000ull, 0, 0x3ff0000000000000ull, 0,
4248 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
4249 // fcZero * fcZero = fcZero
4250 std::make_tuple(0, 0, 0, 0, APFloat::fcZero,
4251 APFloat::rmNearestTiesToEven),
4252 // fcZero * fcNormal = fcZero
4253 std::make_tuple(0, 0, 0x3ff0000000000000ull, 0, APFloat::fcZero,
4254 APFloat::rmNearestTiesToEven),
4255 };
4256
4257 for (auto Tp : Data) {
4258 uint64_t Op1[2], Op2[2];
4259 APFloat::fltCategory Expected;
4260 APFloat::roundingMode RM;
4261 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected, RM) = Tp;
4262
4263 {
4264 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4265 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4266 A1.multiply(A2, RM);
4267
4268 EXPECT_EQ(Expected, A1.getCategory())
4269 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
4270 Op2[0], Op2[1])
4271 .str();
4272 }
4273 {
4274 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4275 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4276 A2.multiply(A1, RM);
4277
4278 EXPECT_EQ(Expected, A2.getCategory())
4279 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
4280 Op1[0], Op1[1])
4281 .str();
4282 }
4283 }
4284 }
4285
TEST(APFloatTest,PPCDoubleDoubleMultiply)4286 TEST(APFloatTest, PPCDoubleDoubleMultiply) {
4287 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
4288 uint64_t, APFloat::roundingMode>;
4289 DataType Data[] = {
4290 // 1/3 * 3 = 1.0
4291 std::make_tuple(0x3fd5555555555555ull, 0x3c75555555555556ull,
4292 0x4008000000000000ull, 0, 0x3ff0000000000000ull, 0,
4293 APFloat::rmNearestTiesToEven),
4294 // (1 + epsilon) * (1 + 0) = fcZero
4295 std::make_tuple(0x3ff0000000000000ull, 0x0000000000000001ull,
4296 0x3ff0000000000000ull, 0, 0x3ff0000000000000ull,
4297 0x0000000000000001ull, APFloat::rmNearestTiesToEven),
4298 // (1 + epsilon) * (1 + epsilon) = 1 + 2 * epsilon
4299 std::make_tuple(0x3ff0000000000000ull, 0x0000000000000001ull,
4300 0x3ff0000000000000ull, 0x0000000000000001ull,
4301 0x3ff0000000000000ull, 0x0000000000000002ull,
4302 APFloat::rmNearestTiesToEven),
4303 // -(1 + epsilon) * (1 + epsilon) = -1
4304 std::make_tuple(0xbff0000000000000ull, 0x0000000000000001ull,
4305 0x3ff0000000000000ull, 0x0000000000000001ull,
4306 0xbff0000000000000ull, 0, APFloat::rmNearestTiesToEven),
4307 // (0.5 + 0) * (1 + 2 * epsilon) = 0.5 + epsilon
4308 std::make_tuple(0x3fe0000000000000ull, 0, 0x3ff0000000000000ull,
4309 0x0000000000000002ull, 0x3fe0000000000000ull,
4310 0x0000000000000001ull, APFloat::rmNearestTiesToEven),
4311 // (0.5 + 0) * (1 + epsilon) = 0.5
4312 std::make_tuple(0x3fe0000000000000ull, 0, 0x3ff0000000000000ull,
4313 0x0000000000000001ull, 0x3fe0000000000000ull, 0,
4314 APFloat::rmNearestTiesToEven),
4315 // __LDBL_MAX__ * (1 + 1 << 106) = inf
4316 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4317 0x3ff0000000000000ull, 0x3950000000000000ull,
4318 0x7ff0000000000000ull, 0, APFloat::rmNearestTiesToEven),
4319 // __LDBL_MAX__ * (1 + 1 << 107) > __LDBL_MAX__, but not inf, yes =_=|||
4320 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4321 0x3ff0000000000000ull, 0x3940000000000000ull,
4322 0x7fefffffffffffffull, 0x7c8fffffffffffffull,
4323 APFloat::rmNearestTiesToEven),
4324 // __LDBL_MAX__ * (1 + 1 << 108) = __LDBL_MAX__
4325 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4326 0x3ff0000000000000ull, 0x3930000000000000ull,
4327 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4328 APFloat::rmNearestTiesToEven),
4329 };
4330
4331 for (auto Tp : Data) {
4332 uint64_t Op1[2], Op2[2], Expected[2];
4333 APFloat::roundingMode RM;
4334 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
4335
4336 {
4337 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4338 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4339 A1.multiply(A2, RM);
4340
4341 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4342 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
4343 Op2[0], Op2[1])
4344 .str();
4345 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4346 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
4347 Op2[0], Op2[1])
4348 .str();
4349 }
4350 {
4351 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4352 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4353 A2.multiply(A1, RM);
4354
4355 EXPECT_EQ(Expected[0], A2.bitcastToAPInt().getRawData()[0])
4356 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
4357 Op1[0], Op1[1])
4358 .str();
4359 EXPECT_EQ(Expected[1], A2.bitcastToAPInt().getRawData()[1])
4360 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
4361 Op1[0], Op1[1])
4362 .str();
4363 }
4364 }
4365 }
4366
TEST(APFloatTest,PPCDoubleDoubleDivide)4367 TEST(APFloatTest, PPCDoubleDoubleDivide) {
4368 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
4369 uint64_t, APFloat::roundingMode>;
4370 // TODO: Only a sanity check for now. Add more edge cases when the
4371 // double-double algorithm is implemented.
4372 DataType Data[] = {
4373 // 1 / 3 = 1/3
4374 std::make_tuple(0x3ff0000000000000ull, 0, 0x4008000000000000ull, 0,
4375 0x3fd5555555555555ull, 0x3c75555555555556ull,
4376 APFloat::rmNearestTiesToEven),
4377 };
4378
4379 for (auto Tp : Data) {
4380 uint64_t Op1[2], Op2[2], Expected[2];
4381 APFloat::roundingMode RM;
4382 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
4383
4384 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4385 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4386 A1.divide(A2, RM);
4387
4388 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4389 << formatv("({0:x} + {1:x}) / ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4390 Op2[1])
4391 .str();
4392 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4393 << formatv("({0:x} + {1:x}) / ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4394 Op2[1])
4395 .str();
4396 }
4397 }
4398
TEST(APFloatTest,PPCDoubleDoubleRemainder)4399 TEST(APFloatTest, PPCDoubleDoubleRemainder) {
4400 using DataType =
4401 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t, uint64_t>;
4402 DataType Data[] = {
4403 // remainder(3.0 + 3.0 << 53, 1.25 + 1.25 << 53) = (0.5 + 0.5 << 53)
4404 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
4405 0x3ff4000000000000ull, 0x3ca4000000000000ull,
4406 0x3fe0000000000000ull, 0x3c90000000000000ull),
4407 // remainder(3.0 + 3.0 << 53, 1.75 + 1.75 << 53) = (-0.5 - 0.5 << 53)
4408 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
4409 0x3ffc000000000000ull, 0x3cac000000000000ull,
4410 0xbfe0000000000000ull, 0xbc90000000000000ull),
4411 };
4412
4413 for (auto Tp : Data) {
4414 uint64_t Op1[2], Op2[2], Expected[2];
4415 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1]) = Tp;
4416
4417 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4418 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4419 A1.remainder(A2);
4420
4421 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4422 << formatv("remainder({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
4423 Op2[0], Op2[1])
4424 .str();
4425 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4426 << formatv("remainder(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0],
4427 Op1[1], Op2[0], Op2[1])
4428 .str();
4429 }
4430 }
4431
TEST(APFloatTest,PPCDoubleDoubleMod)4432 TEST(APFloatTest, PPCDoubleDoubleMod) {
4433 using DataType =
4434 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t, uint64_t>;
4435 DataType Data[] = {
4436 // mod(3.0 + 3.0 << 53, 1.25 + 1.25 << 53) = (0.5 + 0.5 << 53)
4437 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
4438 0x3ff4000000000000ull, 0x3ca4000000000000ull,
4439 0x3fe0000000000000ull, 0x3c90000000000000ull),
4440 // mod(3.0 + 3.0 << 53, 1.75 + 1.75 << 53) = (1.25 + 1.25 << 53)
4441 // 0xbc98000000000000 doesn't seem right, but it's what we currently have.
4442 // TODO: investigate
4443 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
4444 0x3ffc000000000000ull, 0x3cac000000000000ull,
4445 0x3ff4000000000001ull, 0xbc98000000000000ull),
4446 };
4447
4448 for (auto Tp : Data) {
4449 uint64_t Op1[2], Op2[2], Expected[2];
4450 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1]) = Tp;
4451
4452 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4453 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4454 A1.mod(A2);
4455
4456 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
4457 << formatv("fmod(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
4458 Op2[0], Op2[1])
4459 .str();
4460 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
4461 << formatv("fmod(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
4462 Op2[0], Op2[1])
4463 .str();
4464 }
4465 }
4466
TEST(APFloatTest,PPCDoubleDoubleFMA)4467 TEST(APFloatTest, PPCDoubleDoubleFMA) {
4468 // Sanity check for now.
4469 APFloat A(APFloat::PPCDoubleDouble(), "2");
4470 A.fusedMultiplyAdd(APFloat(APFloat::PPCDoubleDouble(), "3"),
4471 APFloat(APFloat::PPCDoubleDouble(), "4"),
4472 APFloat::rmNearestTiesToEven);
4473 EXPECT_EQ(APFloat::cmpEqual,
4474 APFloat(APFloat::PPCDoubleDouble(), "10").compare(A));
4475 }
4476
TEST(APFloatTest,PPCDoubleDoubleRoundToIntegral)4477 TEST(APFloatTest, PPCDoubleDoubleRoundToIntegral) {
4478 {
4479 APFloat A(APFloat::PPCDoubleDouble(), "1.5");
4480 A.roundToIntegral(APFloat::rmNearestTiesToEven);
4481 EXPECT_EQ(APFloat::cmpEqual,
4482 APFloat(APFloat::PPCDoubleDouble(), "2").compare(A));
4483 }
4484 {
4485 APFloat A(APFloat::PPCDoubleDouble(), "2.5");
4486 A.roundToIntegral(APFloat::rmNearestTiesToEven);
4487 EXPECT_EQ(APFloat::cmpEqual,
4488 APFloat(APFloat::PPCDoubleDouble(), "2").compare(A));
4489 }
4490 }
4491
TEST(APFloatTest,PPCDoubleDoubleCompare)4492 TEST(APFloatTest, PPCDoubleDoubleCompare) {
4493 using DataType =
4494 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, APFloat::cmpResult>;
4495
4496 DataType Data[] = {
4497 // (1 + 0) = (1 + 0)
4498 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000000ull, 0,
4499 APFloat::cmpEqual),
4500 // (1 + 0) < (1.00...1 + 0)
4501 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull, 0,
4502 APFloat::cmpLessThan),
4503 // (1.00...1 + 0) > (1 + 0)
4504 std::make_tuple(0x3ff0000000000001ull, 0, 0x3ff0000000000000ull, 0,
4505 APFloat::cmpGreaterThan),
4506 // (1 + 0) < (1 + epsilon)
4507 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull,
4508 0x0000000000000001ull, APFloat::cmpLessThan),
4509 // NaN != NaN
4510 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0,
4511 APFloat::cmpUnordered),
4512 // (1 + 0) != NaN
4513 std::make_tuple(0x3ff0000000000000ull, 0, 0x7ff8000000000000ull, 0,
4514 APFloat::cmpUnordered),
4515 // Inf = Inf
4516 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0,
4517 APFloat::cmpEqual),
4518 };
4519
4520 for (auto Tp : Data) {
4521 uint64_t Op1[2], Op2[2];
4522 APFloat::cmpResult Expected;
4523 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected) = Tp;
4524
4525 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4526 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4527 EXPECT_EQ(Expected, A1.compare(A2))
4528 << formatv("compare(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
4529 Op2[0], Op2[1])
4530 .str();
4531 }
4532 }
4533
TEST(APFloatTest,PPCDoubleDoubleBitwiseIsEqual)4534 TEST(APFloatTest, PPCDoubleDoubleBitwiseIsEqual) {
4535 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, bool>;
4536
4537 DataType Data[] = {
4538 // (1 + 0) = (1 + 0)
4539 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000000ull, 0, true),
4540 // (1 + 0) != (1.00...1 + 0)
4541 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull, 0,
4542 false),
4543 // NaN = NaN
4544 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0, true),
4545 // NaN != NaN with a different bit pattern
4546 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull,
4547 0x3ff0000000000000ull, false),
4548 // Inf = Inf
4549 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0, true),
4550 };
4551
4552 for (auto Tp : Data) {
4553 uint64_t Op1[2], Op2[2];
4554 bool Expected;
4555 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected) = Tp;
4556
4557 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
4558 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
4559 EXPECT_EQ(Expected, A1.bitwiseIsEqual(A2))
4560 << formatv("({0:x} + {1:x}) = ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
4561 Op2[1])
4562 .str();
4563 }
4564 }
4565
TEST(APFloatTest,PPCDoubleDoubleHashValue)4566 TEST(APFloatTest, PPCDoubleDoubleHashValue) {
4567 uint64_t Data1[] = {0x3ff0000000000001ull, 0x0000000000000001ull};
4568 uint64_t Data2[] = {0x3ff0000000000001ull, 0};
4569 // The hash values are *hopefully* different.
4570 EXPECT_NE(
4571 hash_value(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data1))),
4572 hash_value(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data2))));
4573 }
4574
TEST(APFloatTest,PPCDoubleDoubleChangeSign)4575 TEST(APFloatTest, PPCDoubleDoubleChangeSign) {
4576 uint64_t Data[] = {
4577 0x400f000000000000ull, 0xbcb0000000000000ull,
4578 };
4579 APFloat Float(APFloat::PPCDoubleDouble(), APInt(128, 2, Data));
4580 {
4581 APFloat Actual =
4582 APFloat::copySign(Float, APFloat(APFloat::IEEEdouble(), "1"));
4583 EXPECT_EQ(0x400f000000000000ull, Actual.bitcastToAPInt().getRawData()[0]);
4584 EXPECT_EQ(0xbcb0000000000000ull, Actual.bitcastToAPInt().getRawData()[1]);
4585 }
4586 {
4587 APFloat Actual =
4588 APFloat::copySign(Float, APFloat(APFloat::IEEEdouble(), "-1"));
4589 EXPECT_EQ(0xc00f000000000000ull, Actual.bitcastToAPInt().getRawData()[0]);
4590 EXPECT_EQ(0x3cb0000000000000ull, Actual.bitcastToAPInt().getRawData()[1]);
4591 }
4592 }
4593
TEST(APFloatTest,PPCDoubleDoubleFactories)4594 TEST(APFloatTest, PPCDoubleDoubleFactories) {
4595 {
4596 uint64_t Data[] = {
4597 0, 0,
4598 };
4599 EXPECT_EQ(APInt(128, 2, Data),
4600 APFloat::getZero(APFloat::PPCDoubleDouble()).bitcastToAPInt());
4601 }
4602 {
4603 uint64_t Data[] = {
4604 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
4605 };
4606 EXPECT_EQ(APInt(128, 2, Data),
4607 APFloat::getLargest(APFloat::PPCDoubleDouble()).bitcastToAPInt());
4608 }
4609 {
4610 uint64_t Data[] = {
4611 0x0000000000000001ull, 0,
4612 };
4613 EXPECT_EQ(
4614 APInt(128, 2, Data),
4615 APFloat::getSmallest(APFloat::PPCDoubleDouble()).bitcastToAPInt());
4616 }
4617 {
4618 uint64_t Data[] = {0x0360000000000000ull, 0};
4619 EXPECT_EQ(APInt(128, 2, Data),
4620 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble())
4621 .bitcastToAPInt());
4622 }
4623 {
4624 uint64_t Data[] = {
4625 0x8000000000000000ull, 0x0000000000000000ull,
4626 };
4627 EXPECT_EQ(
4628 APInt(128, 2, Data),
4629 APFloat::getZero(APFloat::PPCDoubleDouble(), true).bitcastToAPInt());
4630 }
4631 {
4632 uint64_t Data[] = {
4633 0xffefffffffffffffull, 0xfc8ffffffffffffeull,
4634 };
4635 EXPECT_EQ(
4636 APInt(128, 2, Data),
4637 APFloat::getLargest(APFloat::PPCDoubleDouble(), true).bitcastToAPInt());
4638 }
4639 {
4640 uint64_t Data[] = {
4641 0x8000000000000001ull, 0x0000000000000000ull,
4642 };
4643 EXPECT_EQ(APInt(128, 2, Data),
4644 APFloat::getSmallest(APFloat::PPCDoubleDouble(), true)
4645 .bitcastToAPInt());
4646 }
4647 {
4648 uint64_t Data[] = {
4649 0x8360000000000000ull, 0x0000000000000000ull,
4650 };
4651 EXPECT_EQ(APInt(128, 2, Data),
4652 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble(), true)
4653 .bitcastToAPInt());
4654 }
4655 EXPECT_TRUE(APFloat::getSmallest(APFloat::PPCDoubleDouble()).isSmallest());
4656 EXPECT_TRUE(APFloat::getLargest(APFloat::PPCDoubleDouble()).isLargest());
4657 }
4658
TEST(APFloatTest,PPCDoubleDoubleIsDenormal)4659 TEST(APFloatTest, PPCDoubleDoubleIsDenormal) {
4660 EXPECT_TRUE(APFloat::getSmallest(APFloat::PPCDoubleDouble()).isDenormal());
4661 EXPECT_FALSE(APFloat::getLargest(APFloat::PPCDoubleDouble()).isDenormal());
4662 EXPECT_FALSE(
4663 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble()).isDenormal());
4664 {
4665 // (4 + 3) is not normalized
4666 uint64_t Data[] = {
4667 0x4010000000000000ull, 0x4008000000000000ull,
4668 };
4669 EXPECT_TRUE(
4670 APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data)).isDenormal());
4671 }
4672 }
4673
TEST(APFloatTest,PPCDoubleDoubleScalbn)4674 TEST(APFloatTest, PPCDoubleDoubleScalbn) {
4675 // 3.0 + 3.0 << 53
4676 uint64_t Input[] = {
4677 0x4008000000000000ull, 0x3cb8000000000000ull,
4678 };
4679 APFloat Result =
4680 scalbn(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Input)), 1,
4681 APFloat::rmNearestTiesToEven);
4682 // 6.0 + 6.0 << 53
4683 EXPECT_EQ(0x4018000000000000ull, Result.bitcastToAPInt().getRawData()[0]);
4684 EXPECT_EQ(0x3cc8000000000000ull, Result.bitcastToAPInt().getRawData()[1]);
4685 }
4686
TEST(APFloatTest,PPCDoubleDoubleFrexp)4687 TEST(APFloatTest, PPCDoubleDoubleFrexp) {
4688 // 3.0 + 3.0 << 53
4689 uint64_t Input[] = {
4690 0x4008000000000000ull, 0x3cb8000000000000ull,
4691 };
4692 int Exp;
4693 // 0.75 + 0.75 << 53
4694 APFloat Result =
4695 frexp(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Input)), Exp,
4696 APFloat::rmNearestTiesToEven);
4697 EXPECT_EQ(2, Exp);
4698 EXPECT_EQ(0x3fe8000000000000ull, Result.bitcastToAPInt().getRawData()[0]);
4699 EXPECT_EQ(0x3c98000000000000ull, Result.bitcastToAPInt().getRawData()[1]);
4700 }
4701
TEST(APFloatTest,x87Largest)4702 TEST(APFloatTest, x87Largest) {
4703 APFloat MaxX87Val = APFloat::getLargest(APFloat::x87DoubleExtended());
4704 EXPECT_TRUE(MaxX87Val.isLargest());
4705 }
4706
TEST(APFloatTest,x87Next)4707 TEST(APFloatTest, x87Next) {
4708 APFloat F(APFloat::x87DoubleExtended(), "-1.0");
4709 F.next(false);
4710 EXPECT_TRUE(ilogb(F) == -1);
4711 }
4712 }
4713