blob: 60a920bd3f72a5120a0909b70dbf412ef4d2301b [file] [log] [blame]
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001//===- llvm/unittest/ADT/APFloat.cpp - APFloat unit tests ---------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
Erick Tryzelaar19f63b22009-08-16 23:36:19 +000010#include "llvm/ADT/APFloat.h"
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +000011#include "llvm/ADT/APSInt.h"
Tim Shenfd1e5aa2017-01-23 22:39:35 +000012#include "llvm/ADT/Hashing.h"
John McCall29b5c282009-12-24 08:56:26 +000013#include "llvm/ADT/SmallVector.h"
Tim Shen53f14c72016-12-16 00:47:17 +000014#include "llvm/Support/FormatVariadic.h"
Chandler Carruth130cec22012-12-04 10:23:08 +000015#include "llvm/Support/raw_ostream.h"
16#include "gtest/gtest.h"
Benjamin Kramer37dce442015-03-09 18:35:18 +000017#include <cmath>
Chandler Carruth130cec22012-12-04 10:23:08 +000018#include <ostream>
19#include <string>
Tim Shen18e7ae62016-12-12 22:16:08 +000020#include <tuple>
Erick Tryzelaar19f63b22009-08-16 23:36:19 +000021
22using namespace llvm;
23
Daniel Dunbarbc52e4f2009-09-03 22:57:02 +000024static double convertToDoubleFromString(const char *Str) {
25 llvm::APFloat F(0.0);
26 F.convertFromString(Str, llvm::APFloat::rmNearestTiesToEven);
27 return F.convertToDouble();
28}
29
John McCall29b5c282009-12-24 08:56:26 +000030static std::string convertToString(double d, unsigned Prec, unsigned Pad) {
31 llvm::SmallVector<char, 100> Buffer;
32 llvm::APFloat F(d);
33 F.toString(Buffer, Prec, Pad);
34 return std::string(Buffer.data(), Buffer.size());
35}
36
Erick Tryzelaar19f63b22009-08-16 23:36:19 +000037namespace {
38
Michael Gottesman0c622ea2013-05-30 18:07:13 +000039TEST(APFloatTest, isSignaling) {
40 // We test qNaN, -qNaN, +sNaN, -sNaN with and without payloads. *NOTE* The
41 // positive/negative distinction is included only since the getQNaN/getSNaN
42 // API provides the option.
43 APInt payload = APInt::getOneBitSet(4, 2);
Stephan Bergmann17c7f702016-12-14 11:57:17 +000044 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), false).isSignaling());
45 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), true).isSignaling());
46 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), false, &payload).isSignaling());
47 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), true, &payload).isSignaling());
48 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isSignaling());
49 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isSignaling());
50 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false, &payload).isSignaling());
51 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true, &payload).isSignaling());
Michael Gottesman0c622ea2013-05-30 18:07:13 +000052}
53
54TEST(APFloatTest, next) {
55
Stephan Bergmann17c7f702016-12-14 11:57:17 +000056 APFloat test(APFloat::IEEEquad(), APFloat::uninitialized);
57 APFloat expected(APFloat::IEEEquad(), APFloat::uninitialized);
Michael Gottesman0c622ea2013-05-30 18:07:13 +000058
59 // 1. Test Special Cases Values.
60 //
61 // Test all special values for nextUp and nextDown perscribed by IEEE-754R
62 // 2008. These are:
63 // 1. +inf
64 // 2. -inf
65 // 3. getLargest()
66 // 4. -getLargest()
67 // 5. getSmallest()
68 // 6. -getSmallest()
69 // 7. qNaN
70 // 8. sNaN
71 // 9. +0
72 // 10. -0
73
74 // nextUp(+inf) = +inf.
Stephan Bergmann17c7f702016-12-14 11:57:17 +000075 test = APFloat::getInf(APFloat::IEEEquad(), false);
76 expected = APFloat::getInf(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +000077 EXPECT_EQ(test.next(false), APFloat::opOK);
78 EXPECT_TRUE(test.isInfinity());
79 EXPECT_TRUE(!test.isNegative());
80 EXPECT_TRUE(test.bitwiseIsEqual(expected));
81
82 // nextDown(+inf) = -nextUp(-inf) = -(-getLargest()) = getLargest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +000083 test = APFloat::getInf(APFloat::IEEEquad(), false);
84 expected = APFloat::getLargest(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +000085 EXPECT_EQ(test.next(true), APFloat::opOK);
86 EXPECT_TRUE(!test.isNegative());
87 EXPECT_TRUE(test.bitwiseIsEqual(expected));
88
89 // nextUp(-inf) = -getLargest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +000090 test = APFloat::getInf(APFloat::IEEEquad(), true);
91 expected = APFloat::getLargest(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +000092 EXPECT_EQ(test.next(false), APFloat::opOK);
93 EXPECT_TRUE(test.isNegative());
94 EXPECT_TRUE(test.bitwiseIsEqual(expected));
95
96 // nextDown(-inf) = -nextUp(+inf) = -(+inf) = -inf.
Stephan Bergmann17c7f702016-12-14 11:57:17 +000097 test = APFloat::getInf(APFloat::IEEEquad(), true);
98 expected = APFloat::getInf(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +000099 EXPECT_EQ(test.next(true), APFloat::opOK);
100 EXPECT_TRUE(test.isInfinity() && test.isNegative());
101 EXPECT_TRUE(test.bitwiseIsEqual(expected));
102
103 // nextUp(getLargest()) = +inf
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000104 test = APFloat::getLargest(APFloat::IEEEquad(), false);
105 expected = APFloat::getInf(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000106 EXPECT_EQ(test.next(false), APFloat::opOK);
107 EXPECT_TRUE(test.isInfinity() && !test.isNegative());
108 EXPECT_TRUE(test.bitwiseIsEqual(expected));
109
110 // nextDown(getLargest()) = -nextUp(-getLargest())
111 // = -(-getLargest() + inc)
112 // = getLargest() - inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000113 test = APFloat::getLargest(APFloat::IEEEquad(), false);
114 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000115 "0x1.fffffffffffffffffffffffffffep+16383");
116 EXPECT_EQ(test.next(true), APFloat::opOK);
117 EXPECT_TRUE(!test.isInfinity() && !test.isNegative());
118 EXPECT_TRUE(test.bitwiseIsEqual(expected));
119
120 // nextUp(-getLargest()) = -getLargest() + inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000121 test = APFloat::getLargest(APFloat::IEEEquad(), true);
122 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000123 "-0x1.fffffffffffffffffffffffffffep+16383");
124 EXPECT_EQ(test.next(false), APFloat::opOK);
125 EXPECT_TRUE(test.bitwiseIsEqual(expected));
126
127 // nextDown(-getLargest()) = -nextUp(getLargest()) = -(inf) = -inf.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000128 test = APFloat::getLargest(APFloat::IEEEquad(), true);
129 expected = APFloat::getInf(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000130 EXPECT_EQ(test.next(true), APFloat::opOK);
131 EXPECT_TRUE(test.isInfinity() && test.isNegative());
132 EXPECT_TRUE(test.bitwiseIsEqual(expected));
133
134 // nextUp(getSmallest()) = getSmallest() + inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000135 test = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
136 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000137 "0x0.0000000000000000000000000002p-16382");
138 EXPECT_EQ(test.next(false), APFloat::opOK);
139 EXPECT_TRUE(test.bitwiseIsEqual(expected));
140
141 // nextDown(getSmallest()) = -nextUp(-getSmallest()) = -(-0) = +0.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000142 test = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
143 expected = APFloat::getZero(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000144 EXPECT_EQ(test.next(true), APFloat::opOK);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +0000145 EXPECT_TRUE(test.isPosZero());
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000146 EXPECT_TRUE(test.bitwiseIsEqual(expected));
147
148 // nextUp(-getSmallest()) = -0.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000149 test = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
150 expected = APFloat::getZero(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000151 EXPECT_EQ(test.next(false), APFloat::opOK);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +0000152 EXPECT_TRUE(test.isNegZero());
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000153 EXPECT_TRUE(test.bitwiseIsEqual(expected));
154
155 // nextDown(-getSmallest()) = -nextUp(getSmallest()) = -getSmallest() - inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000156 test = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
157 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000158 "-0x0.0000000000000000000000000002p-16382");
159 EXPECT_EQ(test.next(true), APFloat::opOK);
160 EXPECT_TRUE(test.bitwiseIsEqual(expected));
161
162 // nextUp(qNaN) = qNaN
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000163 test = APFloat::getQNaN(APFloat::IEEEquad(), false);
164 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000165 EXPECT_EQ(test.next(false), APFloat::opOK);
166 EXPECT_TRUE(test.bitwiseIsEqual(expected));
167
168 // nextDown(qNaN) = qNaN
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000169 test = APFloat::getQNaN(APFloat::IEEEquad(), false);
170 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000171 EXPECT_EQ(test.next(true), APFloat::opOK);
172 EXPECT_TRUE(test.bitwiseIsEqual(expected));
173
174 // nextUp(sNaN) = qNaN
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000175 test = APFloat::getSNaN(APFloat::IEEEquad(), false);
176 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000177 EXPECT_EQ(test.next(false), APFloat::opInvalidOp);
178 EXPECT_TRUE(test.bitwiseIsEqual(expected));
179
180 // nextDown(sNaN) = qNaN
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000181 test = APFloat::getSNaN(APFloat::IEEEquad(), false);
182 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000183 EXPECT_EQ(test.next(true), APFloat::opInvalidOp);
184 EXPECT_TRUE(test.bitwiseIsEqual(expected));
185
186 // nextUp(+0) = +getSmallest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000187 test = APFloat::getZero(APFloat::IEEEquad(), false);
188 expected = APFloat::getSmallest(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000189 EXPECT_EQ(test.next(false), APFloat::opOK);
190 EXPECT_TRUE(test.bitwiseIsEqual(expected));
191
192 // nextDown(+0) = -nextUp(-0) = -getSmallest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000193 test = APFloat::getZero(APFloat::IEEEquad(), false);
194 expected = APFloat::getSmallest(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000195 EXPECT_EQ(test.next(true), APFloat::opOK);
196 EXPECT_TRUE(test.bitwiseIsEqual(expected));
197
198 // nextUp(-0) = +getSmallest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000199 test = APFloat::getZero(APFloat::IEEEquad(), true);
200 expected = APFloat::getSmallest(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000201 EXPECT_EQ(test.next(false), APFloat::opOK);
202 EXPECT_TRUE(test.bitwiseIsEqual(expected));
203
204 // nextDown(-0) = -nextUp(0) = -getSmallest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000205 test = APFloat::getZero(APFloat::IEEEquad(), true);
206 expected = APFloat::getSmallest(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000207 EXPECT_EQ(test.next(true), APFloat::opOK);
208 EXPECT_TRUE(test.bitwiseIsEqual(expected));
209
210 // 2. Binade Boundary Tests.
211
212 // 2a. Test denormal <-> normal binade boundaries.
213 // * nextUp(+Largest Denormal) -> +Smallest Normal.
214 // * nextDown(-Largest Denormal) -> -Smallest Normal.
215 // * nextUp(-Smallest Normal) -> -Largest Denormal.
216 // * nextDown(+Smallest Normal) -> +Largest Denormal.
217
218 // nextUp(+Largest Denormal) -> +Smallest Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000219 test = APFloat(APFloat::IEEEquad(), "0x0.ffffffffffffffffffffffffffffp-16382");
220 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000221 "0x1.0000000000000000000000000000p-16382");
222 EXPECT_EQ(test.next(false), APFloat::opOK);
223 EXPECT_FALSE(test.isDenormal());
224 EXPECT_TRUE(test.bitwiseIsEqual(expected));
225
226 // nextDown(-Largest Denormal) -> -Smallest Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000227 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000228 "-0x0.ffffffffffffffffffffffffffffp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000229 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000230 "-0x1.0000000000000000000000000000p-16382");
231 EXPECT_EQ(test.next(true), APFloat::opOK);
232 EXPECT_FALSE(test.isDenormal());
233 EXPECT_TRUE(test.bitwiseIsEqual(expected));
234
235 // nextUp(-Smallest Normal) -> -LargestDenormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000236 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000237 "-0x1.0000000000000000000000000000p-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000238 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000239 "-0x0.ffffffffffffffffffffffffffffp-16382");
240 EXPECT_EQ(test.next(false), APFloat::opOK);
241 EXPECT_TRUE(test.isDenormal());
242 EXPECT_TRUE(test.bitwiseIsEqual(expected));
243
244 // nextDown(+Smallest Normal) -> +Largest Denormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000245 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000246 "+0x1.0000000000000000000000000000p-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000247 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000248 "+0x0.ffffffffffffffffffffffffffffp-16382");
249 EXPECT_EQ(test.next(true), APFloat::opOK);
250 EXPECT_TRUE(test.isDenormal());
251 EXPECT_TRUE(test.bitwiseIsEqual(expected));
252
253 // 2b. Test normal <-> normal binade boundaries.
254 // * nextUp(-Normal Binade Boundary) -> -Normal Binade Boundary + 1.
255 // * nextDown(+Normal Binade Boundary) -> +Normal Binade Boundary - 1.
256 // * nextUp(+Normal Binade Boundary - 1) -> +Normal Binade Boundary.
257 // * nextDown(-Normal Binade Boundary + 1) -> -Normal Binade Boundary.
258
259 // nextUp(-Normal Binade Boundary) -> -Normal Binade Boundary + 1.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000260 test = APFloat(APFloat::IEEEquad(), "-0x1p+1");
261 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000262 "-0x1.ffffffffffffffffffffffffffffp+0");
263 EXPECT_EQ(test.next(false), APFloat::opOK);
264 EXPECT_TRUE(test.bitwiseIsEqual(expected));
265
266 // nextDown(+Normal Binade Boundary) -> +Normal Binade Boundary - 1.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000267 test = APFloat(APFloat::IEEEquad(), "0x1p+1");
268 expected = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp+0");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000269 EXPECT_EQ(test.next(true), APFloat::opOK);
270 EXPECT_TRUE(test.bitwiseIsEqual(expected));
271
272 // nextUp(+Normal Binade Boundary - 1) -> +Normal Binade Boundary.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000273 test = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp+0");
274 expected = APFloat(APFloat::IEEEquad(), "0x1p+1");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000275 EXPECT_EQ(test.next(false), APFloat::opOK);
276 EXPECT_TRUE(test.bitwiseIsEqual(expected));
277
278 // nextDown(-Normal Binade Boundary + 1) -> -Normal Binade Boundary.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000279 test = APFloat(APFloat::IEEEquad(), "-0x1.ffffffffffffffffffffffffffffp+0");
280 expected = APFloat(APFloat::IEEEquad(), "-0x1p+1");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000281 EXPECT_EQ(test.next(true), APFloat::opOK);
282 EXPECT_TRUE(test.bitwiseIsEqual(expected));
283
284 // 2c. Test using next at binade boundaries with a direction away from the
285 // binade boundary. Away from denormal <-> normal boundaries.
286 //
287 // This is to make sure that even though we are at a binade boundary, since
288 // we are rounding away, we do not trigger the binade boundary code. Thus we
289 // test:
290 // * nextUp(-Largest Denormal) -> -Largest Denormal + inc.
291 // * nextDown(+Largest Denormal) -> +Largest Denormal - inc.
292 // * nextUp(+Smallest Normal) -> +Smallest Normal + inc.
293 // * nextDown(-Smallest Normal) -> -Smallest Normal - inc.
294
295 // nextUp(-Largest Denormal) -> -Largest Denormal + inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000296 test = APFloat(APFloat::IEEEquad(), "-0x0.ffffffffffffffffffffffffffffp-16382");
297 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000298 "-0x0.fffffffffffffffffffffffffffep-16382");
299 EXPECT_EQ(test.next(false), APFloat::opOK);
300 EXPECT_TRUE(test.isDenormal());
301 EXPECT_TRUE(test.isNegative());
302 EXPECT_TRUE(test.bitwiseIsEqual(expected));
303
304 // nextDown(+Largest Denormal) -> +Largest Denormal - inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000305 test = APFloat(APFloat::IEEEquad(), "0x0.ffffffffffffffffffffffffffffp-16382");
306 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000307 "0x0.fffffffffffffffffffffffffffep-16382");
308 EXPECT_EQ(test.next(true), APFloat::opOK);
309 EXPECT_TRUE(test.isDenormal());
310 EXPECT_TRUE(!test.isNegative());
311 EXPECT_TRUE(test.bitwiseIsEqual(expected));
312
313 // nextUp(+Smallest Normal) -> +Smallest Normal + inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000314 test = APFloat(APFloat::IEEEquad(), "0x1.0000000000000000000000000000p-16382");
315 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000316 "0x1.0000000000000000000000000001p-16382");
317 EXPECT_EQ(test.next(false), APFloat::opOK);
318 EXPECT_TRUE(!test.isDenormal());
319 EXPECT_TRUE(!test.isNegative());
320 EXPECT_TRUE(test.bitwiseIsEqual(expected));
321
322 // nextDown(-Smallest Normal) -> -Smallest Normal - inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000323 test = APFloat(APFloat::IEEEquad(), "-0x1.0000000000000000000000000000p-16382");
324 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000325 "-0x1.0000000000000000000000000001p-16382");
326 EXPECT_EQ(test.next(true), APFloat::opOK);
327 EXPECT_TRUE(!test.isDenormal());
328 EXPECT_TRUE(test.isNegative());
329 EXPECT_TRUE(test.bitwiseIsEqual(expected));
330
331 // 2d. Test values which cause our exponent to go to min exponent. This
332 // is to ensure that guards in the code to check for min exponent
333 // trigger properly.
334 // * nextUp(-0x1p-16381) -> -0x1.ffffffffffffffffffffffffffffp-16382
335 // * nextDown(-0x1.ffffffffffffffffffffffffffffp-16382) ->
336 // -0x1p-16381
337 // * nextUp(0x1.ffffffffffffffffffffffffffffp-16382) -> 0x1p-16382
338 // * nextDown(0x1p-16382) -> 0x1.ffffffffffffffffffffffffffffp-16382
339
340 // nextUp(-0x1p-16381) -> -0x1.ffffffffffffffffffffffffffffp-16382
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000341 test = APFloat(APFloat::IEEEquad(), "-0x1p-16381");
342 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000343 "-0x1.ffffffffffffffffffffffffffffp-16382");
344 EXPECT_EQ(test.next(false), APFloat::opOK);
345 EXPECT_TRUE(test.bitwiseIsEqual(expected));
346
347 // nextDown(-0x1.ffffffffffffffffffffffffffffp-16382) ->
348 // -0x1p-16381
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000349 test = APFloat(APFloat::IEEEquad(), "-0x1.ffffffffffffffffffffffffffffp-16382");
350 expected = APFloat(APFloat::IEEEquad(), "-0x1p-16381");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000351 EXPECT_EQ(test.next(true), APFloat::opOK);
352 EXPECT_TRUE(test.bitwiseIsEqual(expected));
353
354 // nextUp(0x1.ffffffffffffffffffffffffffffp-16382) -> 0x1p-16381
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000355 test = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp-16382");
356 expected = APFloat(APFloat::IEEEquad(), "0x1p-16381");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000357 EXPECT_EQ(test.next(false), APFloat::opOK);
358 EXPECT_TRUE(test.bitwiseIsEqual(expected));
359
360 // nextDown(0x1p-16381) -> 0x1.ffffffffffffffffffffffffffffp-16382
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000361 test = APFloat(APFloat::IEEEquad(), "0x1p-16381");
362 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000363 "0x1.ffffffffffffffffffffffffffffp-16382");
364 EXPECT_EQ(test.next(true), APFloat::opOK);
365 EXPECT_TRUE(test.bitwiseIsEqual(expected));
366
367 // 3. Now we test both denormal/normal computation which will not cause us
368 // to go across binade boundaries. Specifically we test:
369 // * nextUp(+Denormal) -> +Denormal.
370 // * nextDown(+Denormal) -> +Denormal.
371 // * nextUp(-Denormal) -> -Denormal.
372 // * nextDown(-Denormal) -> -Denormal.
373 // * nextUp(+Normal) -> +Normal.
374 // * nextDown(+Normal) -> +Normal.
375 // * nextUp(-Normal) -> -Normal.
376 // * nextDown(-Normal) -> -Normal.
377
378 // nextUp(+Denormal) -> +Denormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000379 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000380 "0x0.ffffffffffffffffffffffff000cp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000381 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000382 "0x0.ffffffffffffffffffffffff000dp-16382");
383 EXPECT_EQ(test.next(false), APFloat::opOK);
384 EXPECT_TRUE(test.isDenormal());
385 EXPECT_TRUE(!test.isNegative());
386 EXPECT_TRUE(test.bitwiseIsEqual(expected));
387
388 // nextDown(+Denormal) -> +Denormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000389 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000390 "0x0.ffffffffffffffffffffffff000cp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000391 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000392 "0x0.ffffffffffffffffffffffff000bp-16382");
393 EXPECT_EQ(test.next(true), APFloat::opOK);
394 EXPECT_TRUE(test.isDenormal());
395 EXPECT_TRUE(!test.isNegative());
396 EXPECT_TRUE(test.bitwiseIsEqual(expected));
397
398 // nextUp(-Denormal) -> -Denormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000399 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000400 "-0x0.ffffffffffffffffffffffff000cp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000401 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000402 "-0x0.ffffffffffffffffffffffff000bp-16382");
403 EXPECT_EQ(test.next(false), APFloat::opOK);
404 EXPECT_TRUE(test.isDenormal());
405 EXPECT_TRUE(test.isNegative());
406 EXPECT_TRUE(test.bitwiseIsEqual(expected));
407
408 // nextDown(-Denormal) -> -Denormal
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000409 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000410 "-0x0.ffffffffffffffffffffffff000cp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000411 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000412 "-0x0.ffffffffffffffffffffffff000dp-16382");
413 EXPECT_EQ(test.next(true), APFloat::opOK);
414 EXPECT_TRUE(test.isDenormal());
415 EXPECT_TRUE(test.isNegative());
416 EXPECT_TRUE(test.bitwiseIsEqual(expected));
417
418 // nextUp(+Normal) -> +Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000419 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000420 "0x1.ffffffffffffffffffffffff000cp-16000");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000421 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000422 "0x1.ffffffffffffffffffffffff000dp-16000");
423 EXPECT_EQ(test.next(false), APFloat::opOK);
424 EXPECT_TRUE(!test.isDenormal());
425 EXPECT_TRUE(!test.isNegative());
426 EXPECT_TRUE(test.bitwiseIsEqual(expected));
427
428 // nextDown(+Normal) -> +Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000429 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000430 "0x1.ffffffffffffffffffffffff000cp-16000");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000431 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000432 "0x1.ffffffffffffffffffffffff000bp-16000");
433 EXPECT_EQ(test.next(true), APFloat::opOK);
434 EXPECT_TRUE(!test.isDenormal());
435 EXPECT_TRUE(!test.isNegative());
436 EXPECT_TRUE(test.bitwiseIsEqual(expected));
437
438 // nextUp(-Normal) -> -Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000439 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000440 "-0x1.ffffffffffffffffffffffff000cp-16000");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000441 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000442 "-0x1.ffffffffffffffffffffffff000bp-16000");
443 EXPECT_EQ(test.next(false), APFloat::opOK);
444 EXPECT_TRUE(!test.isDenormal());
445 EXPECT_TRUE(test.isNegative());
446 EXPECT_TRUE(test.bitwiseIsEqual(expected));
447
448 // nextDown(-Normal) -> -Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000449 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000450 "-0x1.ffffffffffffffffffffffff000cp-16000");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000451 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000452 "-0x1.ffffffffffffffffffffffff000dp-16000");
453 EXPECT_EQ(test.next(true), APFloat::opOK);
454 EXPECT_TRUE(!test.isDenormal());
455 EXPECT_TRUE(test.isNegative());
456 EXPECT_TRUE(test.bitwiseIsEqual(expected));
457}
458
Shuxin Yangbbddbac2013-05-13 18:03:12 +0000459TEST(APFloatTest, FMA) {
460 APFloat::roundingMode rdmd = APFloat::rmNearestTiesToEven;
461
462 {
463 APFloat f1(14.5f);
464 APFloat f2(-14.5f);
465 APFloat f3(225.0f);
466 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
467 EXPECT_EQ(14.75f, f1.convertToFloat());
468 }
469
470 {
471 APFloat Val2(2.0f);
472 APFloat f1((float)1.17549435e-38F);
473 APFloat f2((float)1.17549435e-38F);
474 f1.divide(Val2, rdmd);
475 f2.divide(Val2, rdmd);
476 APFloat f3(12.0f);
477 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
478 EXPECT_EQ(12.0f, f1.convertToFloat());
479 }
Lang Hames56c0eb22014-11-19 19:15:41 +0000480
Lang Hames12b12e82015-01-04 01:20:55 +0000481 // Test for correct zero sign when answer is exactly zero.
482 // fma(1.0, -1.0, 1.0) -> +ve 0.
483 {
484 APFloat f1(1.0);
485 APFloat f2(-1.0);
486 APFloat f3(1.0);
487 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
488 EXPECT_TRUE(!f1.isNegative() && f1.isZero());
489 }
490
491 // Test for correct zero sign when answer is exactly zero and rounding towards
492 // negative.
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::rmTowardNegative);
499 EXPECT_TRUE(f1.isNegative() && f1.isZero());
500 }
501
502 // Test for correct (in this case -ve) sign when adding like signed zeros.
503 // Test fma(0.0, -0.0, -0.0) -> -ve 0.
504 {
505 APFloat f1(0.0);
506 APFloat f2(-0.0);
507 APFloat f3(-0.0);
508 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
509 EXPECT_TRUE(f1.isNegative() && f1.isZero());
510 }
511
512 // Test -ve sign preservation when small negative results underflow.
513 {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000514 APFloat f1(APFloat::IEEEdouble(), "-0x1p-1074");
515 APFloat f2(APFloat::IEEEdouble(), "+0x1p-1074");
Lang Hames12b12e82015-01-04 01:20:55 +0000516 APFloat f3(0.0);
517 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
518 EXPECT_TRUE(f1.isNegative() && f1.isZero());
519 }
520
521 // Test x87 extended precision case from http://llvm.org/PR20728.
Lang Hames56c0eb22014-11-19 19:15:41 +0000522 {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000523 APFloat M1(APFloat::x87DoubleExtended(), 1.0);
524 APFloat M2(APFloat::x87DoubleExtended(), 1.0);
525 APFloat A(APFloat::x87DoubleExtended(), 3.0);
Lang Hames56c0eb22014-11-19 19:15:41 +0000526
527 bool losesInfo = false;
528 M1.fusedMultiplyAdd(M1, A, APFloat::rmNearestTiesToEven);
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000529 M1.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
Lang Hames56c0eb22014-11-19 19:15:41 +0000530 EXPECT_FALSE(losesInfo);
531 EXPECT_EQ(4.0f, M1.convertToFloat());
532 }
Shuxin Yangbbddbac2013-05-13 18:03:12 +0000533}
534
Matt Arsenault5ccdb982014-10-10 05:21:32 +0000535TEST(APFloatTest, MinNum) {
536 APFloat f1(1.0);
537 APFloat f2(2.0);
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000538 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
Matt Arsenault5ccdb982014-10-10 05:21:32 +0000539
540 EXPECT_EQ(1.0, minnum(f1, f2).convertToDouble());
541 EXPECT_EQ(1.0, minnum(f2, f1).convertToDouble());
542 EXPECT_EQ(1.0, minnum(f1, nan).convertToDouble());
543 EXPECT_EQ(1.0, minnum(nan, f1).convertToDouble());
544}
545
546TEST(APFloatTest, MaxNum) {
547 APFloat f1(1.0);
548 APFloat f2(2.0);
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000549 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
Matt Arsenault5ccdb982014-10-10 05:21:32 +0000550
551 EXPECT_EQ(2.0, maxnum(f1, f2).convertToDouble());
552 EXPECT_EQ(2.0, maxnum(f2, f1).convertToDouble());
553 EXPECT_EQ(1.0, maxnum(f1, nan).convertToDouble());
554 EXPECT_EQ(1.0, minnum(nan, f1).convertToDouble());
555}
556
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000557TEST(APFloatTest, Denormal) {
558 APFloat::roundingMode rdmd = APFloat::rmNearestTiesToEven;
559
560 // Test single precision
561 {
562 const char *MinNormalStr = "1.17549435082228750797e-38";
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000563 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), MinNormalStr).isDenormal());
564 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), 0.0).isDenormal());
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000565
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000566 APFloat Val2(APFloat::IEEEsingle(), 2.0e0);
567 APFloat T(APFloat::IEEEsingle(), MinNormalStr);
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000568 T.divide(Val2, rdmd);
569 EXPECT_TRUE(T.isDenormal());
570 }
571
572 // Test double precision
573 {
574 const char *MinNormalStr = "2.22507385850720138309e-308";
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000575 EXPECT_FALSE(APFloat(APFloat::IEEEdouble(), MinNormalStr).isDenormal());
576 EXPECT_FALSE(APFloat(APFloat::IEEEdouble(), 0.0).isDenormal());
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000577
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000578 APFloat Val2(APFloat::IEEEdouble(), 2.0e0);
579 APFloat T(APFloat::IEEEdouble(), MinNormalStr);
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000580 T.divide(Val2, rdmd);
581 EXPECT_TRUE(T.isDenormal());
582 }
583
584 // Test Intel double-ext
585 {
586 const char *MinNormalStr = "3.36210314311209350626e-4932";
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000587 EXPECT_FALSE(APFloat(APFloat::x87DoubleExtended(), MinNormalStr).isDenormal());
588 EXPECT_FALSE(APFloat(APFloat::x87DoubleExtended(), 0.0).isDenormal());
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000589
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000590 APFloat Val2(APFloat::x87DoubleExtended(), 2.0e0);
591 APFloat T(APFloat::x87DoubleExtended(), MinNormalStr);
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000592 T.divide(Val2, rdmd);
593 EXPECT_TRUE(T.isDenormal());
594 }
595
596 // Test quadruple precision
597 {
598 const char *MinNormalStr = "3.36210314311209350626267781732175260e-4932";
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000599 EXPECT_FALSE(APFloat(APFloat::IEEEquad(), MinNormalStr).isDenormal());
600 EXPECT_FALSE(APFloat(APFloat::IEEEquad(), 0.0).isDenormal());
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000601
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000602 APFloat Val2(APFloat::IEEEquad(), 2.0e0);
603 APFloat T(APFloat::IEEEquad(), MinNormalStr);
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000604 T.divide(Val2, rdmd);
605 EXPECT_TRUE(T.isDenormal());
606 }
607}
608
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000609TEST(APFloatTest, Zero) {
Matt Beaumont-Gaya421ee12011-08-29 17:54:20 +0000610 EXPECT_EQ(0.0f, APFloat(0.0f).convertToFloat());
611 EXPECT_EQ(-0.0f, APFloat(-0.0f).convertToFloat());
612 EXPECT_TRUE(APFloat(-0.0f).isNegative());
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000613
Matt Beaumont-Gaya421ee12011-08-29 17:54:20 +0000614 EXPECT_EQ(0.0, APFloat(0.0).convertToDouble());
615 EXPECT_EQ(-0.0, APFloat(-0.0).convertToDouble());
616 EXPECT_TRUE(APFloat(-0.0).isNegative());
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000617}
618
Michael Gottesman228156c2013-07-01 23:54:08 +0000619TEST(APFloatTest, DecimalStringsWithoutNullTerminators) {
620 // Make sure that we can parse strings without null terminators.
621 // rdar://14323230.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000622 APFloat Val(APFloat::IEEEdouble());
Michael Gottesman228156c2013-07-01 23:54:08 +0000623 Val.convertFromString(StringRef("0.00", 3),
624 llvm::APFloat::rmNearestTiesToEven);
625 EXPECT_EQ(Val.convertToDouble(), 0.0);
626 Val.convertFromString(StringRef("0.01", 3),
627 llvm::APFloat::rmNearestTiesToEven);
628 EXPECT_EQ(Val.convertToDouble(), 0.0);
629 Val.convertFromString(StringRef("0.09", 3),
630 llvm::APFloat::rmNearestTiesToEven);
631 EXPECT_EQ(Val.convertToDouble(), 0.0);
632 Val.convertFromString(StringRef("0.095", 4),
633 llvm::APFloat::rmNearestTiesToEven);
634 EXPECT_EQ(Val.convertToDouble(), 0.09);
635 Val.convertFromString(StringRef("0.00e+3", 7),
636 llvm::APFloat::rmNearestTiesToEven);
637 EXPECT_EQ(Val.convertToDouble(), 0.00);
638 Val.convertFromString(StringRef("0e+3", 4),
639 llvm::APFloat::rmNearestTiesToEven);
640 EXPECT_EQ(Val.convertToDouble(), 0.00);
641
642}
643
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000644TEST(APFloatTest, fromZeroDecimalString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000645 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0").convertToDouble());
646 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0").convertToDouble());
647 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000648
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000649 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.").convertToDouble());
650 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.").convertToDouble());
651 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000652
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000653 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0").convertToDouble());
654 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0").convertToDouble());
655 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000656
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000657 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0").convertToDouble());
658 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0").convertToDouble());
659 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000660
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000661 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "00000.").convertToDouble());
662 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+00000.").convertToDouble());
663 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-00000.").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000664
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000665 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), ".00000").convertToDouble());
666 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.00000").convertToDouble());
667 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.00000").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000668
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000669 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0000.00000").convertToDouble());
670 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0000.00000").convertToDouble());
671 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0000.00000").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000672}
673
674TEST(APFloatTest, fromZeroDecimalSingleExponentString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000675 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e1").convertToDouble());
676 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e1").convertToDouble());
677 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000678
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000679 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e+1").convertToDouble());
680 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e+1").convertToDouble());
681 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000682
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000683 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e-1").convertToDouble());
684 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e-1").convertToDouble());
685 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000686
687
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000688 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e1").convertToDouble());
689 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e1").convertToDouble());
690 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000691
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000692 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e+1").convertToDouble());
693 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e+1").convertToDouble());
694 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000695
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000696 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e-1").convertToDouble());
697 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e-1").convertToDouble());
698 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000699
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000700 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e1").convertToDouble());
701 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e1").convertToDouble());
702 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000703
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000704 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e+1").convertToDouble());
705 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e+1").convertToDouble());
706 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000707
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000708 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e-1").convertToDouble());
709 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e-1").convertToDouble());
710 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000711
712
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000713 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e1").convertToDouble());
714 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e1").convertToDouble());
715 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000716
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000717 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e+1").convertToDouble());
718 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e+1").convertToDouble());
719 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000720
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000721 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e-1").convertToDouble());
722 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e-1").convertToDouble());
723 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000724
725
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000726 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "000.0000e1").convertToDouble());
727 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+000.0000e+1").convertToDouble());
728 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-000.0000e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000729}
730
731TEST(APFloatTest, fromZeroDecimalLargeExponentString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000732 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e1234").convertToDouble());
733 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e1234").convertToDouble());
734 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e1234").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000735
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000736 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e+1234").convertToDouble());
737 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e+1234").convertToDouble());
738 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e+1234").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000739
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000740 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e-1234").convertToDouble());
741 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e-1234").convertToDouble());
742 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e-1234").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000743
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000744 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), "000.0000e1234").convertToDouble());
745 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), "000.0000e-1234").convertToDouble());
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000746
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000747 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), StringRef("0e1234\02", 6)).convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000748}
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000749
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000750TEST(APFloatTest, fromZeroHexadecimalString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000751 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p1").convertToDouble());
752 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p1").convertToDouble());
753 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000754
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000755 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p+1").convertToDouble());
756 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p+1").convertToDouble());
757 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000758
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000759 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p-1").convertToDouble());
760 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p-1").convertToDouble());
761 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000762
763
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000764 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1").convertToDouble());
765 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p1").convertToDouble());
766 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000767
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000768 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p+1").convertToDouble());
769 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p+1").convertToDouble());
770 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000771
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000772 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p-1").convertToDouble());
773 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p-1").convertToDouble());
774 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000775
776
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000777 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p1").convertToDouble());
778 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p1").convertToDouble());
779 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000780
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000781 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p+1").convertToDouble());
782 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p+1").convertToDouble());
783 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000784
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000785 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p-1").convertToDouble());
786 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p-1").convertToDouble());
787 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000788
789
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000790 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p1").convertToDouble());
791 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p1").convertToDouble());
792 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000793
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000794 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p+1").convertToDouble());
795 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p+1").convertToDouble());
796 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000797
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000798 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p-1").convertToDouble());
799 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p-1").convertToDouble());
800 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000801
802
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000803 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x00000.p1").convertToDouble());
804 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0000.00000p1").convertToDouble());
805 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.00000p1").convertToDouble());
806 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1").convertToDouble());
807 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p1234").convertToDouble());
808 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p1234").convertToDouble());
809 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x00000.p1234").convertToDouble());
810 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0000.00000p1234").convertToDouble());
811 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.00000p1234").convertToDouble());
812 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1234").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000813}
814
815TEST(APFloatTest, fromDecimalString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000816 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1").convertToDouble());
817 EXPECT_EQ(2.0, APFloat(APFloat::IEEEdouble(), "2.").convertToDouble());
818 EXPECT_EQ(0.5, APFloat(APFloat::IEEEdouble(), ".5").convertToDouble());
819 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0").convertToDouble());
820 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-2").convertToDouble());
821 EXPECT_EQ(-4.0, APFloat(APFloat::IEEEdouble(), "-4.").convertToDouble());
822 EXPECT_EQ(-0.5, APFloat(APFloat::IEEEdouble(), "-.5").convertToDouble());
823 EXPECT_EQ(-1.5, APFloat(APFloat::IEEEdouble(), "-1.5").convertToDouble());
824 EXPECT_EQ(1.25e12, APFloat(APFloat::IEEEdouble(), "1.25e12").convertToDouble());
825 EXPECT_EQ(1.25e+12, APFloat(APFloat::IEEEdouble(), "1.25e+12").convertToDouble());
826 EXPECT_EQ(1.25e-12, APFloat(APFloat::IEEEdouble(), "1.25e-12").convertToDouble());
827 EXPECT_EQ(1024.0, APFloat(APFloat::IEEEdouble(), "1024.").convertToDouble());
828 EXPECT_EQ(1024.05, APFloat(APFloat::IEEEdouble(), "1024.05000").convertToDouble());
829 EXPECT_EQ(0.05, APFloat(APFloat::IEEEdouble(), ".05000").convertToDouble());
830 EXPECT_EQ(2.0, APFloat(APFloat::IEEEdouble(), "2.").convertToDouble());
831 EXPECT_EQ(2.0e2, APFloat(APFloat::IEEEdouble(), "2.e2").convertToDouble());
832 EXPECT_EQ(2.0e+2, APFloat(APFloat::IEEEdouble(), "2.e+2").convertToDouble());
833 EXPECT_EQ(2.0e-2, APFloat(APFloat::IEEEdouble(), "2.e-2").convertToDouble());
834 EXPECT_EQ(2.05e2, APFloat(APFloat::IEEEdouble(), "002.05000e2").convertToDouble());
835 EXPECT_EQ(2.05e+2, APFloat(APFloat::IEEEdouble(), "002.05000e+2").convertToDouble());
836 EXPECT_EQ(2.05e-2, APFloat(APFloat::IEEEdouble(), "002.05000e-2").convertToDouble());
837 EXPECT_EQ(2.05e12, APFloat(APFloat::IEEEdouble(), "002.05000e12").convertToDouble());
838 EXPECT_EQ(2.05e+12, APFloat(APFloat::IEEEdouble(), "002.05000e+12").convertToDouble());
839 EXPECT_EQ(2.05e-12, APFloat(APFloat::IEEEdouble(), "002.05000e-12").convertToDouble());
John McCallb42cc682010-02-26 22:20:41 +0000840
841 // These are "carefully selected" to overflow the fast log-base
842 // calculations in APFloat.cpp
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000843 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "99e99999").isInfinity());
844 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-99e99999").isInfinity());
845 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "1e-99999").isPosZero());
846 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-1e-99999").isNegZero());
Eli Friedmand2eb07a2013-07-17 22:17:29 +0000847
848 EXPECT_EQ(2.71828, convertToDoubleFromString("2.71828"));
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000849}
850
851TEST(APFloatTest, fromHexadecimalString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000852 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p0").convertToDouble());
853 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p0").convertToDouble());
854 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000855
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000856 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p+0").convertToDouble());
857 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p+0").convertToDouble());
858 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p+0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000859
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000860 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p-0").convertToDouble());
861 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p-0").convertToDouble());
862 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p-0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000863
864
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000865 EXPECT_EQ( 2.0, APFloat(APFloat::IEEEdouble(), "0x1p1").convertToDouble());
866 EXPECT_EQ(+2.0, APFloat(APFloat::IEEEdouble(), "+0x1p1").convertToDouble());
867 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-0x1p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000868
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000869 EXPECT_EQ( 2.0, APFloat(APFloat::IEEEdouble(), "0x1p+1").convertToDouble());
870 EXPECT_EQ(+2.0, APFloat(APFloat::IEEEdouble(), "+0x1p+1").convertToDouble());
871 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-0x1p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000872
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000873 EXPECT_EQ( 0.5, APFloat(APFloat::IEEEdouble(), "0x1p-1").convertToDouble());
874 EXPECT_EQ(+0.5, APFloat(APFloat::IEEEdouble(), "+0x1p-1").convertToDouble());
875 EXPECT_EQ(-0.5, APFloat(APFloat::IEEEdouble(), "-0x1p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000876
877
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000878 EXPECT_EQ( 3.0, APFloat(APFloat::IEEEdouble(), "0x1.8p1").convertToDouble());
879 EXPECT_EQ(+3.0, APFloat(APFloat::IEEEdouble(), "+0x1.8p1").convertToDouble());
880 EXPECT_EQ(-3.0, APFloat(APFloat::IEEEdouble(), "-0x1.8p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000881
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000882 EXPECT_EQ( 3.0, APFloat(APFloat::IEEEdouble(), "0x1.8p+1").convertToDouble());
883 EXPECT_EQ(+3.0, APFloat(APFloat::IEEEdouble(), "+0x1.8p+1").convertToDouble());
884 EXPECT_EQ(-3.0, APFloat(APFloat::IEEEdouble(), "-0x1.8p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000885
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000886 EXPECT_EQ( 0.75, APFloat(APFloat::IEEEdouble(), "0x1.8p-1").convertToDouble());
887 EXPECT_EQ(+0.75, APFloat(APFloat::IEEEdouble(), "+0x1.8p-1").convertToDouble());
888 EXPECT_EQ(-0.75, APFloat(APFloat::IEEEdouble(), "-0x1.8p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000889
890
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000891 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p1").convertToDouble());
892 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p1").convertToDouble());
893 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000894
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000895 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p+1").convertToDouble());
896 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p+1").convertToDouble());
897 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000898
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000899 EXPECT_EQ( 2048.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p-1").convertToDouble());
900 EXPECT_EQ(+2048.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p-1").convertToDouble());
901 EXPECT_EQ(-2048.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000902
903
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000904 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000p1").convertToDouble());
905 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000p1").convertToDouble());
906 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000907
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000908 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000p+1").convertToDouble());
909 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000p+1").convertToDouble());
910 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000911
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000912 EXPECT_EQ( 2048.0, APFloat(APFloat::IEEEdouble(), "0x1000p-1").convertToDouble());
913 EXPECT_EQ(+2048.0, APFloat(APFloat::IEEEdouble(), "+0x1000p-1").convertToDouble());
914 EXPECT_EQ(-2048.0, APFloat(APFloat::IEEEdouble(), "-0x1000p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000915
916
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000917 EXPECT_EQ( 16384.0, APFloat(APFloat::IEEEdouble(), "0x10p10").convertToDouble());
918 EXPECT_EQ(+16384.0, APFloat(APFloat::IEEEdouble(), "+0x10p10").convertToDouble());
919 EXPECT_EQ(-16384.0, APFloat(APFloat::IEEEdouble(), "-0x10p10").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000920
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000921 EXPECT_EQ( 16384.0, APFloat(APFloat::IEEEdouble(), "0x10p+10").convertToDouble());
922 EXPECT_EQ(+16384.0, APFloat(APFloat::IEEEdouble(), "+0x10p+10").convertToDouble());
923 EXPECT_EQ(-16384.0, APFloat(APFloat::IEEEdouble(), "-0x10p+10").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000924
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000925 EXPECT_EQ( 0.015625, APFloat(APFloat::IEEEdouble(), "0x10p-10").convertToDouble());
926 EXPECT_EQ(+0.015625, APFloat(APFloat::IEEEdouble(), "+0x10p-10").convertToDouble());
927 EXPECT_EQ(-0.015625, APFloat(APFloat::IEEEdouble(), "-0x10p-10").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000928
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000929 EXPECT_EQ(1.0625, APFloat(APFloat::IEEEdouble(), "0x1.1p0").convertToDouble());
930 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "0x1p0").convertToDouble());
Daniel Dunbarbc52e4f2009-09-03 22:57:02 +0000931
Eli Friedmand2eb07a2013-07-17 22:17:29 +0000932 EXPECT_EQ(convertToDoubleFromString("0x1p-150"),
933 convertToDoubleFromString("+0x800000000000000001.p-221"));
934 EXPECT_EQ(2251799813685248.5,
935 convertToDoubleFromString("0x80000000000004000000.010p-28"));
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000936}
937
John McCall29b5c282009-12-24 08:56:26 +0000938TEST(APFloatTest, toString) {
939 ASSERT_EQ("10", convertToString(10.0, 6, 3));
940 ASSERT_EQ("1.0E+1", convertToString(10.0, 6, 0));
941 ASSERT_EQ("10100", convertToString(1.01E+4, 5, 2));
942 ASSERT_EQ("1.01E+4", convertToString(1.01E+4, 4, 2));
943 ASSERT_EQ("1.01E+4", convertToString(1.01E+4, 5, 1));
944 ASSERT_EQ("0.0101", convertToString(1.01E-2, 5, 2));
John McCalldd5044a2009-12-24 23:18:09 +0000945 ASSERT_EQ("0.0101", convertToString(1.01E-2, 4, 2));
John McCall29b5c282009-12-24 08:56:26 +0000946 ASSERT_EQ("1.01E-2", convertToString(1.01E-2, 5, 1));
Eli Friedmane72f1322013-08-29 23:44:34 +0000947 ASSERT_EQ("0.78539816339744828", convertToString(0.78539816339744830961, 0, 3));
948 ASSERT_EQ("4.9406564584124654E-324", convertToString(4.9406564584124654e-324, 0, 3));
949 ASSERT_EQ("873.18340000000001", convertToString(873.1834, 0, 1));
950 ASSERT_EQ("8.7318340000000001E+2", convertToString(873.1834, 0, 0));
951 ASSERT_EQ("1.7976931348623157E+308", convertToString(1.7976931348623157E+308, 0, 0));
John McCall29b5c282009-12-24 08:56:26 +0000952}
953
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000954TEST(APFloatTest, toInteger) {
955 bool isExact = false;
956 APSInt result(5, /*isUnsigned=*/true);
957
958 EXPECT_EQ(APFloat::opOK,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000959 APFloat(APFloat::IEEEdouble(), "10")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000960 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
961 EXPECT_TRUE(isExact);
962 EXPECT_EQ(APSInt(APInt(5, 10), true), result);
963
964 EXPECT_EQ(APFloat::opInvalidOp,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000965 APFloat(APFloat::IEEEdouble(), "-10")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000966 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
967 EXPECT_FALSE(isExact);
968 EXPECT_EQ(APSInt::getMinValue(5, true), result);
969
970 EXPECT_EQ(APFloat::opInvalidOp,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000971 APFloat(APFloat::IEEEdouble(), "32")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000972 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
973 EXPECT_FALSE(isExact);
974 EXPECT_EQ(APSInt::getMaxValue(5, true), result);
975
976 EXPECT_EQ(APFloat::opInexact,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000977 APFloat(APFloat::IEEEdouble(), "7.9")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000978 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
979 EXPECT_FALSE(isExact);
980 EXPECT_EQ(APSInt(APInt(5, 7), true), result);
981
982 result.setIsUnsigned(false);
983 EXPECT_EQ(APFloat::opOK,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000984 APFloat(APFloat::IEEEdouble(), "-10")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000985 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
986 EXPECT_TRUE(isExact);
987 EXPECT_EQ(APSInt(APInt(5, -10, true), false), result);
988
989 EXPECT_EQ(APFloat::opInvalidOp,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000990 APFloat(APFloat::IEEEdouble(), "-17")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000991 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
992 EXPECT_FALSE(isExact);
993 EXPECT_EQ(APSInt::getMinValue(5, false), result);
994
995 EXPECT_EQ(APFloat::opInvalidOp,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000996 APFloat(APFloat::IEEEdouble(), "16")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000997 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
998 EXPECT_FALSE(isExact);
999 EXPECT_EQ(APSInt::getMaxValue(5, false), result);
1000}
1001
John McCalldcb9a7a2010-02-28 02:51:25 +00001002static APInt nanbits(const fltSemantics &Sem,
1003 bool SNaN, bool Negative, uint64_t fill) {
1004 APInt apfill(64, fill);
1005 if (SNaN)
1006 return APFloat::getSNaN(Sem, Negative, &apfill).bitcastToAPInt();
1007 else
1008 return APFloat::getQNaN(Sem, Negative, &apfill).bitcastToAPInt();
1009}
1010
1011TEST(APFloatTest, makeNaN) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001012 ASSERT_EQ(0x7fc00000, nanbits(APFloat::IEEEsingle(), false, false, 0));
1013 ASSERT_EQ(0xffc00000, nanbits(APFloat::IEEEsingle(), false, true, 0));
1014 ASSERT_EQ(0x7fc0ae72, nanbits(APFloat::IEEEsingle(), false, false, 0xae72));
1015 ASSERT_EQ(0x7fffae72, nanbits(APFloat::IEEEsingle(), false, false, 0xffffae72));
1016 ASSERT_EQ(0x7fa00000, nanbits(APFloat::IEEEsingle(), true, false, 0));
1017 ASSERT_EQ(0xffa00000, nanbits(APFloat::IEEEsingle(), true, true, 0));
1018 ASSERT_EQ(0x7f80ae72, nanbits(APFloat::IEEEsingle(), true, false, 0xae72));
1019 ASSERT_EQ(0x7fbfae72, nanbits(APFloat::IEEEsingle(), true, false, 0xffffae72));
John McCalldcb9a7a2010-02-28 02:51:25 +00001020
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001021 ASSERT_EQ(0x7ff8000000000000ULL, nanbits(APFloat::IEEEdouble(), false, false, 0));
1022 ASSERT_EQ(0xfff8000000000000ULL, nanbits(APFloat::IEEEdouble(), false, true, 0));
1023 ASSERT_EQ(0x7ff800000000ae72ULL, nanbits(APFloat::IEEEdouble(), false, false, 0xae72));
1024 ASSERT_EQ(0x7fffffffffffae72ULL, nanbits(APFloat::IEEEdouble(), false, false, 0xffffffffffffae72ULL));
1025 ASSERT_EQ(0x7ff4000000000000ULL, nanbits(APFloat::IEEEdouble(), true, false, 0));
1026 ASSERT_EQ(0xfff4000000000000ULL, nanbits(APFloat::IEEEdouble(), true, true, 0));
1027 ASSERT_EQ(0x7ff000000000ae72ULL, nanbits(APFloat::IEEEdouble(), true, false, 0xae72));
1028 ASSERT_EQ(0x7ff7ffffffffae72ULL, nanbits(APFloat::IEEEdouble(), true, false, 0xffffffffffffae72ULL));
John McCalldcb9a7a2010-02-28 02:51:25 +00001029}
1030
Erick Tryzelaar927191f2009-08-17 00:55:33 +00001031#ifdef GTEST_HAS_DEATH_TEST
Jeffrey Yasskinb5cd0132010-03-17 01:18:45 +00001032#ifndef NDEBUG
Erick Tryzelaar927191f2009-08-17 00:55:33 +00001033TEST(APFloatTest, SemanticsDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001034 EXPECT_DEATH(APFloat(APFloat::IEEEsingle(), 0.0f).convertToDouble(), "Float semantics are not IEEEdouble");
1035 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), 0.0 ).convertToFloat(), "Float semantics are not IEEEsingle");
Erick Tryzelaar927191f2009-08-17 00:55:33 +00001036}
1037
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001038TEST(APFloatTest, StringDecimalDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001039 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ""), "Invalid string length");
1040 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+"), "String has no digits");
1041 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-"), "String has no digits");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001042
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001043 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("\0", 1)), "Invalid character in significand");
1044 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1\0", 2)), "Invalid character in significand");
1045 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1\02", 3)), "Invalid character in significand");
1046 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1\02e1", 5)), "Invalid character in significand");
1047 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1e\0", 3)), "Invalid character in exponent");
1048 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1e1\0", 4)), "Invalid character in exponent");
1049 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1e1\02", 5)), "Invalid character in exponent");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001050
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001051 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0f"), "Invalid character in significand");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001052
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001053 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".."), "String contains multiple dots");
1054 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "..0"), "String contains multiple dots");
1055 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0.0"), "String contains multiple dots");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001056}
1057
1058TEST(APFloatTest, StringDecimalSignificandDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001059 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "."), "Significand has no digits");
1060 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+."), "Significand has no digits");
1061 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-."), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001062
1063
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001064 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "e"), "Significand has no digits");
1065 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+e"), "Significand has no digits");
1066 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-e"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001067
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001068 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "e1"), "Significand has no digits");
1069 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+e1"), "Significand has no digits");
1070 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-e1"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001071
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001072 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".e1"), "Significand has no digits");
1073 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+.e1"), "Significand has no digits");
1074 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-.e1"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001075
1076
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001077 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".e"), "Significand has no digits");
1078 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+.e"), "Significand has no digits");
1079 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-.e"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001080}
1081
1082TEST(APFloatTest, StringDecimalExponentDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001083 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1e"), "Exponent has no digits");
1084 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+1e"), "Exponent has no digits");
1085 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-1e"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001086
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001087 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.e"), "Exponent has no digits");
1088 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+1.e"), "Exponent has no digits");
1089 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-1.e"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001090
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001091 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".1e"), "Exponent has no digits");
1092 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+.1e"), "Exponent has no digits");
1093 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-.1e"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001094
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001095 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.1e"), "Exponent has no digits");
1096 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+1.1e"), "Exponent has no digits");
1097 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-1.1e"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001098
1099
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001100 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1e+"), "Exponent has no digits");
1101 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1e-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001102
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001103 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".1e"), "Exponent has no digits");
1104 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".1e+"), "Exponent has no digits");
1105 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".1e-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001106
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001107 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0e"), "Exponent has no digits");
1108 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0e+"), "Exponent has no digits");
1109 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0e-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001110}
1111
1112TEST(APFloatTest, StringHexadecimalDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001113 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x"), "Invalid string");
1114 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x"), "Invalid string");
1115 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x"), "Invalid string");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001116
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001117 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x0"), "Hex strings require an exponent");
1118 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x0"), "Hex strings require an exponent");
1119 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x0"), "Hex strings require an exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001120
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001121 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x0."), "Hex strings require an exponent");
1122 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x0."), "Hex strings require an exponent");
1123 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x0."), "Hex strings require an exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001124
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001125 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.0"), "Hex strings require an exponent");
1126 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.0"), "Hex strings require an exponent");
1127 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.0"), "Hex strings require an exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001128
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001129 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x0.0"), "Hex strings require an exponent");
1130 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x0.0"), "Hex strings require an exponent");
1131 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x0.0"), "Hex strings require an exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001132
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001133 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x\0", 3)), "Invalid character in significand");
1134 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1\0", 4)), "Invalid character in significand");
1135 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1\02", 5)), "Invalid character in significand");
1136 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1\02p1", 7)), "Invalid character in significand");
1137 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1p\0", 5)), "Invalid character in exponent");
1138 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1p1\0", 6)), "Invalid character in exponent");
1139 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1p1\02", 7)), "Invalid character in exponent");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001140
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001141 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1p0f"), "Invalid character in exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001142
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001143 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x..p1"), "String contains multiple dots");
1144 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x..0p1"), "String contains multiple dots");
1145 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.0.0p1"), "String contains multiple dots");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001146}
1147
1148TEST(APFloatTest, StringHexadecimalSignificandDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001149 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x."), "Significand has no digits");
1150 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x."), "Significand has no digits");
1151 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x."), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001152
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001153 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0xp"), "Significand has no digits");
1154 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0xp"), "Significand has no digits");
1155 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0xp"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001156
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001157 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0xp+"), "Significand has no digits");
1158 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0xp+"), "Significand has no digits");
1159 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0xp+"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001160
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001161 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0xp-"), "Significand has no digits");
1162 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0xp-"), "Significand has no digits");
1163 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0xp-"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001164
1165
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001166 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.p"), "Significand has no digits");
1167 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.p"), "Significand has no digits");
1168 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.p"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001169
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001170 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.p+"), "Significand has no digits");
1171 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.p+"), "Significand has no digits");
1172 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.p+"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001173
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001174 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.p-"), "Significand has no digits");
1175 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.p-"), "Significand has no digits");
1176 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.p-"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001177}
1178
1179TEST(APFloatTest, StringHexadecimalExponentDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001180 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1p"), "Exponent has no digits");
1181 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1p"), "Exponent has no digits");
1182 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1p"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001183
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001184 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1p+"), "Exponent has no digits");
1185 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1p+"), "Exponent has no digits");
1186 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1p+"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001187
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001188 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1p-"), "Exponent has no digits");
1189 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1p-"), "Exponent has no digits");
1190 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1p-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001191
1192
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001193 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.p"), "Exponent has no digits");
1194 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.p"), "Exponent has no digits");
1195 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.p"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001196
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001197 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.p+"), "Exponent has no digits");
1198 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.p+"), "Exponent has no digits");
1199 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.p+"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001200
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001201 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.p-"), "Exponent has no digits");
1202 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.p-"), "Exponent has no digits");
1203 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.p-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001204
1205
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001206 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.1p"), "Exponent has no digits");
1207 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.1p"), "Exponent has no digits");
1208 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.1p"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001209
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001210 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.1p+"), "Exponent has no digits");
1211 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.1p+"), "Exponent has no digits");
1212 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.1p+"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001213
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001214 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.1p-"), "Exponent has no digits");
1215 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.1p-"), "Exponent has no digits");
1216 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.1p-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001217
1218
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001219 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.1p"), "Exponent has no digits");
1220 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.1p"), "Exponent has no digits");
1221 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.1p"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001222
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001223 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.1p+"), "Exponent has no digits");
1224 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.1p+"), "Exponent has no digits");
1225 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.1p+"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001226
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001227 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.1p-"), "Exponent has no digits");
1228 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.1p-"), "Exponent has no digits");
1229 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.1p-"), "Exponent has no digits");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001230}
Erick Tryzelaar927191f2009-08-17 00:55:33 +00001231#endif
Jeffrey Yasskinb5cd0132010-03-17 01:18:45 +00001232#endif
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001233
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001234TEST(APFloatTest, exactInverse) {
1235 APFloat inv(0.0f);
1236
1237 // Trivial operation.
1238 EXPECT_TRUE(APFloat(2.0).getExactInverse(&inv));
1239 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(0.5)));
1240 EXPECT_TRUE(APFloat(2.0f).getExactInverse(&inv));
1241 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(0.5f)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001242 EXPECT_TRUE(APFloat(APFloat::IEEEquad(), "2.0").getExactInverse(&inv));
1243 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::IEEEquad(), "0.5")));
1244 EXPECT_TRUE(APFloat(APFloat::PPCDoubleDouble(), "2.0").getExactInverse(&inv));
1245 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::PPCDoubleDouble(), "0.5")));
1246 EXPECT_TRUE(APFloat(APFloat::x87DoubleExtended(), "2.0").getExactInverse(&inv));
1247 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::x87DoubleExtended(), "0.5")));
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001248
1249 // FLT_MIN
1250 EXPECT_TRUE(APFloat(1.17549435e-38f).getExactInverse(&inv));
1251 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(8.5070592e+37f)));
1252
Benjamin Krameraf0ed952011-03-30 17:02:54 +00001253 // Large float, inverse is a denormal.
Craig Topper66f09ad2014-06-08 22:29:17 +00001254 EXPECT_FALSE(APFloat(1.7014118e38f).getExactInverse(nullptr));
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001255 // Zero
Craig Topper66f09ad2014-06-08 22:29:17 +00001256 EXPECT_FALSE(APFloat(0.0).getExactInverse(nullptr));
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001257 // Denormalized float
Craig Topper66f09ad2014-06-08 22:29:17 +00001258 EXPECT_FALSE(APFloat(1.40129846e-45f).getExactInverse(nullptr));
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001259}
1260
Owen Anderson1ff74b02012-08-15 05:39:46 +00001261TEST(APFloatTest, roundToIntegral) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001262 APFloat T(-0.5), S(3.14), R(APFloat::getLargest(APFloat::IEEEdouble())), P(0.0);
Owen Anderson1ff74b02012-08-15 05:39:46 +00001263
1264 P = T;
1265 P.roundToIntegral(APFloat::rmTowardZero);
1266 EXPECT_EQ(-0.0, P.convertToDouble());
1267 P = T;
1268 P.roundToIntegral(APFloat::rmTowardNegative);
1269 EXPECT_EQ(-1.0, P.convertToDouble());
1270 P = T;
1271 P.roundToIntegral(APFloat::rmTowardPositive);
1272 EXPECT_EQ(-0.0, P.convertToDouble());
1273 P = T;
1274 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1275 EXPECT_EQ(-0.0, P.convertToDouble());
1276
1277 P = S;
1278 P.roundToIntegral(APFloat::rmTowardZero);
1279 EXPECT_EQ(3.0, P.convertToDouble());
1280 P = S;
1281 P.roundToIntegral(APFloat::rmTowardNegative);
1282 EXPECT_EQ(3.0, P.convertToDouble());
1283 P = S;
1284 P.roundToIntegral(APFloat::rmTowardPositive);
1285 EXPECT_EQ(4.0, P.convertToDouble());
1286 P = S;
1287 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1288 EXPECT_EQ(3.0, P.convertToDouble());
Owen Anderson352dfff2012-08-15 18:28:45 +00001289
1290 P = R;
1291 P.roundToIntegral(APFloat::rmTowardZero);
1292 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1293 P = R;
1294 P.roundToIntegral(APFloat::rmTowardNegative);
1295 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1296 P = R;
1297 P.roundToIntegral(APFloat::rmTowardPositive);
1298 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1299 P = R;
1300 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1301 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001302
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001303 P = APFloat::getZero(APFloat::IEEEdouble());
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001304 P.roundToIntegral(APFloat::rmTowardZero);
1305 EXPECT_EQ(0.0, P.convertToDouble());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001306 P = APFloat::getZero(APFloat::IEEEdouble(), true);
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001307 P.roundToIntegral(APFloat::rmTowardZero);
1308 EXPECT_EQ(-0.0, P.convertToDouble());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001309 P = APFloat::getNaN(APFloat::IEEEdouble());
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001310 P.roundToIntegral(APFloat::rmTowardZero);
Benjamin Kramer37dce442015-03-09 18:35:18 +00001311 EXPECT_TRUE(std::isnan(P.convertToDouble()));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001312 P = APFloat::getInf(APFloat::IEEEdouble());
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001313 P.roundToIntegral(APFloat::rmTowardZero);
Benjamin Kramer37dce442015-03-09 18:35:18 +00001314 EXPECT_TRUE(std::isinf(P.convertToDouble()) && P.convertToDouble() > 0.0);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001315 P = APFloat::getInf(APFloat::IEEEdouble(), true);
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001316 P.roundToIntegral(APFloat::rmTowardZero);
Benjamin Kramer37dce442015-03-09 18:35:18 +00001317 EXPECT_TRUE(std::isinf(P.convertToDouble()) && P.convertToDouble() < 0.0);
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001318}
Matt Arsenaultc25a7112016-03-21 16:49:16 +00001319
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001320TEST(APFloatTest, isInteger) {
1321 APFloat T(-0.0);
1322 EXPECT_TRUE(T.isInteger());
1323 T = APFloat(3.14159);
1324 EXPECT_FALSE(T.isInteger());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001325 T = APFloat::getNaN(APFloat::IEEEdouble());
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001326 EXPECT_FALSE(T.isInteger());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001327 T = APFloat::getInf(APFloat::IEEEdouble());
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001328 EXPECT_FALSE(T.isInteger());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001329 T = APFloat::getInf(APFloat::IEEEdouble(), true);
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001330 EXPECT_FALSE(T.isInteger());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001331 T = APFloat::getLargest(APFloat::IEEEdouble());
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001332 EXPECT_TRUE(T.isInteger());
Owen Anderson1ff74b02012-08-15 05:39:46 +00001333}
1334
Eli Friedmanc5322012011-10-12 21:51:36 +00001335TEST(APFloatTest, getLargest) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001336 EXPECT_EQ(3.402823466e+38f, APFloat::getLargest(APFloat::IEEEsingle()).convertToFloat());
1337 EXPECT_EQ(1.7976931348623158e+308, APFloat::getLargest(APFloat::IEEEdouble()).convertToDouble());
Eli Friedmanc5322012011-10-12 21:51:36 +00001338}
1339
Michael Gottesman63e6d212013-05-29 23:58:29 +00001340TEST(APFloatTest, getSmallest) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001341 APFloat test = APFloat::getSmallest(APFloat::IEEEsingle(), false);
1342 APFloat expected = APFloat(APFloat::IEEEsingle(), "0x0.000002p-126");
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001343 EXPECT_FALSE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001344 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001345 EXPECT_TRUE(test.isDenormal());
Michael Gottesman63e6d212013-05-29 23:58:29 +00001346 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1347
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001348 test = APFloat::getSmallest(APFloat::IEEEsingle(), true);
1349 expected = APFloat(APFloat::IEEEsingle(), "-0x0.000002p-126");
Michael Gottesman63e6d212013-05-29 23:58:29 +00001350 EXPECT_TRUE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001351 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001352 EXPECT_TRUE(test.isDenormal());
Michael Gottesman63e6d212013-05-29 23:58:29 +00001353 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1354
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001355 test = APFloat::getSmallest(APFloat::IEEEquad(), false);
1356 expected = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001357 EXPECT_FALSE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001358 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001359 EXPECT_TRUE(test.isDenormal());
Michael Gottesman63e6d212013-05-29 23:58:29 +00001360 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1361
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001362 test = APFloat::getSmallest(APFloat::IEEEquad(), true);
1363 expected = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
Michael Gottesman63e6d212013-05-29 23:58:29 +00001364 EXPECT_TRUE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001365 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001366 EXPECT_TRUE(test.isDenormal());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001367 EXPECT_TRUE(test.bitwiseIsEqual(expected));
Michael Gottesman63e6d212013-05-29 23:58:29 +00001368}
1369
Michael Gottesman0db7c272013-05-30 00:18:47 +00001370TEST(APFloatTest, getSmallestNormalized) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001371 APFloat test = APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
1372 APFloat expected = APFloat(APFloat::IEEEsingle(), "0x1p-126");
Michael Gottesman0db7c272013-05-30 00:18:47 +00001373 EXPECT_FALSE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001374 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman0db7c272013-05-30 00:18:47 +00001375 EXPECT_FALSE(test.isDenormal());
1376 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1377
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001378 test = APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
1379 expected = APFloat(APFloat::IEEEsingle(), "-0x1p-126");
Michael Gottesman0db7c272013-05-30 00:18:47 +00001380 EXPECT_TRUE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001381 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman0db7c272013-05-30 00:18:47 +00001382 EXPECT_FALSE(test.isDenormal());
1383 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1384
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001385 test = APFloat::getSmallestNormalized(APFloat::IEEEquad(), false);
1386 expected = APFloat(APFloat::IEEEquad(), "0x1p-16382");
Michael Gottesman0db7c272013-05-30 00:18:47 +00001387 EXPECT_FALSE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001388 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman0db7c272013-05-30 00:18:47 +00001389 EXPECT_FALSE(test.isDenormal());
1390 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1391
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001392 test = APFloat::getSmallestNormalized(APFloat::IEEEquad(), true);
1393 expected = APFloat(APFloat::IEEEquad(), "-0x1p-16382");
Michael Gottesman0db7c272013-05-30 00:18:47 +00001394 EXPECT_TRUE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001395 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman0db7c272013-05-30 00:18:47 +00001396 EXPECT_FALSE(test.isDenormal());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001397 EXPECT_TRUE(test.bitwiseIsEqual(expected));
Michael Gottesman0db7c272013-05-30 00:18:47 +00001398}
1399
Michael Gottesmanfc718c92013-05-31 18:43:34 +00001400TEST(APFloatTest, getZero) {
1401 struct {
1402 const fltSemantics *semantics;
1403 const bool sign;
1404 const unsigned long long bitPattern[2];
1405 const unsigned bitPatternLength;
Benjamin Kramer0bb474f2013-06-01 22:29:41 +00001406 } const GetZeroTest[] = {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001407 { &APFloat::IEEEhalf(), false, {0, 0}, 1},
1408 { &APFloat::IEEEhalf(), true, {0x8000ULL, 0}, 1},
1409 { &APFloat::IEEEsingle(), false, {0, 0}, 1},
1410 { &APFloat::IEEEsingle(), true, {0x80000000ULL, 0}, 1},
1411 { &APFloat::IEEEdouble(), false, {0, 0}, 1},
1412 { &APFloat::IEEEdouble(), true, {0x8000000000000000ULL, 0}, 1},
1413 { &APFloat::IEEEquad(), false, {0, 0}, 2},
1414 { &APFloat::IEEEquad(), true, {0, 0x8000000000000000ULL}, 2},
1415 { &APFloat::PPCDoubleDouble(), false, {0, 0}, 2},
1416 { &APFloat::PPCDoubleDouble(), true, {0x8000000000000000ULL, 0}, 2},
1417 { &APFloat::x87DoubleExtended(), false, {0, 0}, 2},
1418 { &APFloat::x87DoubleExtended(), true, {0, 0x8000ULL}, 2},
Michael Gottesmanfc718c92013-05-31 18:43:34 +00001419 };
1420 const unsigned NumGetZeroTests = 12;
1421 for (unsigned i = 0; i < NumGetZeroTests; ++i) {
1422 APFloat test = APFloat::getZero(*GetZeroTest[i].semantics,
1423 GetZeroTest[i].sign);
1424 const char *pattern = GetZeroTest[i].sign? "-0x0p+0" : "0x0p+0";
1425 APFloat expected = APFloat(*GetZeroTest[i].semantics,
1426 pattern);
1427 EXPECT_TRUE(test.isZero());
1428 EXPECT_TRUE(GetZeroTest[i].sign? test.isNegative() : !test.isNegative());
1429 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1430 for (unsigned j = 0, je = GetZeroTest[i].bitPatternLength; j < je; ++j) {
1431 EXPECT_EQ(GetZeroTest[i].bitPattern[j],
1432 test.bitcastToAPInt().getRawData()[j]);
1433 }
1434 }
1435}
1436
Chandler Carruthdf782e42014-10-09 23:26:15 +00001437TEST(APFloatTest, copySign) {
1438 EXPECT_TRUE(APFloat(-42.0).bitwiseIsEqual(
1439 APFloat::copySign(APFloat(42.0), APFloat(-1.0))));
1440 EXPECT_TRUE(APFloat(42.0).bitwiseIsEqual(
1441 APFloat::copySign(APFloat(-42.0), APFloat(1.0))));
1442 EXPECT_TRUE(APFloat(-42.0).bitwiseIsEqual(
1443 APFloat::copySign(APFloat(-42.0), APFloat(-1.0))));
1444 EXPECT_TRUE(APFloat(42.0).bitwiseIsEqual(
1445 APFloat::copySign(APFloat(42.0), APFloat(1.0))));
1446}
1447
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001448TEST(APFloatTest, convert) {
1449 bool losesInfo;
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001450 APFloat test(APFloat::IEEEdouble(), "1.0");
1451 test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001452 EXPECT_EQ(1.0f, test.convertToFloat());
1453 EXPECT_FALSE(losesInfo);
1454
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001455 test = APFloat(APFloat::x87DoubleExtended(), "0x1p-53");
1456 test.add(APFloat(APFloat::x87DoubleExtended(), "1.0"), APFloat::rmNearestTiesToEven);
1457 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001458 EXPECT_EQ(1.0, test.convertToDouble());
1459 EXPECT_TRUE(losesInfo);
1460
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001461 test = APFloat(APFloat::IEEEquad(), "0x1p-53");
1462 test.add(APFloat(APFloat::IEEEquad(), "1.0"), APFloat::rmNearestTiesToEven);
1463 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001464 EXPECT_EQ(1.0, test.convertToDouble());
1465 EXPECT_TRUE(losesInfo);
1466
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001467 test = APFloat(APFloat::x87DoubleExtended(), "0xf.fffffffp+28");
1468 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001469 EXPECT_EQ(4294967295.0, test.convertToDouble());
1470 EXPECT_FALSE(losesInfo);
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001471
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001472 test = APFloat::getSNaN(APFloat::IEEEsingle());
1473 APFloat X87SNaN = APFloat::getSNaN(APFloat::x87DoubleExtended());
1474 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001475 &losesInfo);
1476 EXPECT_TRUE(test.bitwiseIsEqual(X87SNaN));
1477 EXPECT_FALSE(losesInfo);
1478
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001479 test = APFloat::getQNaN(APFloat::IEEEsingle());
1480 APFloat X87QNaN = APFloat::getQNaN(APFloat::x87DoubleExtended());
1481 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001482 &losesInfo);
1483 EXPECT_TRUE(test.bitwiseIsEqual(X87QNaN));
1484 EXPECT_FALSE(losesInfo);
1485
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001486 test = APFloat::getSNaN(APFloat::x87DoubleExtended());
1487 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001488 &losesInfo);
1489 EXPECT_TRUE(test.bitwiseIsEqual(X87SNaN));
1490 EXPECT_FALSE(losesInfo);
1491
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001492 test = APFloat::getQNaN(APFloat::x87DoubleExtended());
1493 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001494 &losesInfo);
1495 EXPECT_TRUE(test.bitwiseIsEqual(X87QNaN));
1496 EXPECT_FALSE(losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001497}
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001498
1499TEST(APFloatTest, PPCDoubleDouble) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001500 APFloat test(APFloat::PPCDoubleDouble(), "1.0");
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001501 EXPECT_EQ(0x3ff0000000000000ull, test.bitcastToAPInt().getRawData()[0]);
1502 EXPECT_EQ(0x0000000000000000ull, test.bitcastToAPInt().getRawData()[1]);
1503
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001504 // LDBL_MAX
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001505 test = APFloat(APFloat::PPCDoubleDouble(), "1.79769313486231580793728971405301e+308");
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001506 EXPECT_EQ(0x7fefffffffffffffull, test.bitcastToAPInt().getRawData()[0]);
1507 EXPECT_EQ(0x7c8ffffffffffffeull, test.bitcastToAPInt().getRawData()[1]);
1508
1509 // LDBL_MIN
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001510 test = APFloat(APFloat::PPCDoubleDouble(), "2.00416836000897277799610805135016e-292");
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001511 EXPECT_EQ(0x0360000000000000ull, test.bitcastToAPInt().getRawData()[0]);
1512 EXPECT_EQ(0x0000000000000000ull, test.bitcastToAPInt().getRawData()[1]);
1513
Tim Shen398f90f2016-11-06 07:38:37 +00001514 // PR30869
1515 {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001516 auto Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") +
1517 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1518 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001519
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001520 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") -
1521 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1522 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001523
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001524 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") *
1525 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1526 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001527
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001528 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") /
1529 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1530 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001531
1532 int Exp;
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001533 Result = frexp(APFloat(APFloat::PPCDoubleDouble(), "1.0"), Exp,
Tim Shen398f90f2016-11-06 07:38:37 +00001534 APFloat::rmNearestTiesToEven);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001535 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001536
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001537 Result = scalbn(APFloat(APFloat::PPCDoubleDouble(), "1.0"), 1,
Tim Shen398f90f2016-11-06 07:38:37 +00001538 APFloat::rmNearestTiesToEven);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001539 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001540 }
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001541}
Michael Gottesman3acedb62013-06-04 03:46:25 +00001542
1543TEST(APFloatTest, isNegative) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001544 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesman3acedb62013-06-04 03:46:25 +00001545 EXPECT_FALSE(t.isNegative());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001546 t = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
Michael Gottesman3acedb62013-06-04 03:46:25 +00001547 EXPECT_TRUE(t.isNegative());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001548
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001549 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNegative());
1550 EXPECT_TRUE(APFloat::getInf(APFloat::IEEEsingle(), true).isNegative());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001551
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001552 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNegative());
1553 EXPECT_TRUE(APFloat::getZero(APFloat::IEEEsingle(), true).isNegative());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001554
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001555 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNegative());
1556 EXPECT_TRUE(APFloat::getNaN(APFloat::IEEEsingle(), true).isNegative());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001557
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001558 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNegative());
1559 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isNegative());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001560}
1561
Michael Gottesman120c92882013-06-20 18:34:38 +00001562TEST(APFloatTest, isNormal) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001563 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesman120c92882013-06-20 18:34:38 +00001564 EXPECT_TRUE(t.isNormal());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001565
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001566 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNormal());
1567 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNormal());
1568 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNormal());
1569 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNormal());
1570 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isNormal());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001571}
1572
1573TEST(APFloatTest, isFinite) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001574 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesmanf9899292013-06-24 09:58:09 +00001575 EXPECT_TRUE(t.isFinite());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001576 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isFinite());
1577 EXPECT_TRUE(APFloat::getZero(APFloat::IEEEsingle(), false).isFinite());
1578 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isFinite());
1579 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isFinite());
1580 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isFinite());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001581}
1582
1583TEST(APFloatTest, isInfinity) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001584 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesman3acedb62013-06-04 03:46:25 +00001585 EXPECT_FALSE(t.isInfinity());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001586 EXPECT_TRUE(APFloat::getInf(APFloat::IEEEsingle(), false).isInfinity());
1587 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isInfinity());
1588 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isInfinity());
1589 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isInfinity());
1590 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isInfinity());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001591}
1592
1593TEST(APFloatTest, isNaN) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001594 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesmanf9899292013-06-24 09:58:09 +00001595 EXPECT_FALSE(t.isNaN());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001596 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNaN());
1597 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNaN());
1598 EXPECT_TRUE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNaN());
1599 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNaN());
1600 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isNaN());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001601}
1602
Michael Gottesmand95d4472013-06-19 21:00:17 +00001603TEST(APFloatTest, isFiniteNonZero) {
1604 // Test positive/negative normal value.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001605 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p+0").isFiniteNonZero());
1606 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p+0").isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001607
1608 // Test positive/negative denormal value.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001609 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isFiniteNonZero());
1610 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p-149").isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001611
1612 // Test +/- Infinity.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001613 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isFiniteNonZero());
1614 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), true).isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001615
1616 // Test +/- Zero.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001617 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isFiniteNonZero());
1618 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), true).isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001619
1620 // Test +/- qNaN. +/- dont mean anything with qNaN but paranoia can't hurt in
1621 // this instance.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001622 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isFiniteNonZero());
1623 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), true).isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001624
1625 // Test +/- sNaN. +/- dont mean anything with sNaN but paranoia can't hurt in
1626 // this instance.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001627 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isFiniteNonZero());
1628 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001629}
1630
Michael Gottesmane45b1082013-06-24 09:58:07 +00001631TEST(APFloatTest, add) {
1632 // Test Special Cases against each other and normal values.
1633
1634 // TODOS/NOTES:
1635 // 1. Since we perform only default exception handling all operations with
1636 // signaling NaNs should have a result that is a quiet NaN. Currently they
1637 // return sNaN.
Michael Gottesmane45b1082013-06-24 09:58:07 +00001638
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001639 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
1640 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
1641 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
1642 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
1643 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
1644 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
1645 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
1646 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
1647 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
1648 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
1649 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
1650 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Michael Gottesmane45b1082013-06-24 09:58:07 +00001651 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001652 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Michael Gottesmane45b1082013-06-24 09:58:07 +00001653 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001654 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Michael Gottesmane45b1082013-06-24 09:58:07 +00001655
1656 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
1657
1658 const unsigned NumTests = 169;
1659 struct {
1660 APFloat x;
1661 APFloat y;
1662 const char *result;
1663 int status;
1664 int category;
1665 } SpecialCaseTests[NumTests] = {
1666 { PInf, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1667 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1668 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
1669 { PInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
1670 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1671#if 0
1672 // See Note 1.
1673 { PInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1674#endif
1675 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1676 { PInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1677 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1678 { PInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1679 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1680 { PInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1681 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
1682 { PInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
1683 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1684 { MInf, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1685 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
1686 { MInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001687 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001688#if 0
1689 // See Note 1.
1690 { MInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1691#endif
1692 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1693 { MInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1694 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1695 { MInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1696 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1697 { MInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1698 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
1699 { MInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
1700 { PZero, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1701 { PZero, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1702 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1703 { PZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1704 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1705#if 0
1706 // See Note 1.
1707 { PZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1708#endif
1709 { PZero, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
1710 { PZero, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
1711 { PZero, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1712 { PZero, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1713 { PZero, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
1714 { PZero, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
1715 { PZero, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
1716 { PZero, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
1717 { MZero, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1718 { MZero, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1719 { MZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1720 { MZero, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001721 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001722#if 0
1723 // See Note 1.
1724 { MZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1725#endif
1726 { MZero, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
1727 { MZero, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
1728 { MZero, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1729 { MZero, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1730 { MZero, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
1731 { MZero, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
1732 { MZero, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
1733 { MZero, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
1734 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
1735 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
1736 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
1737 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
1738 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1739#if 0
1740 // See Note 1.
1741 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1742#endif
1743 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
1744 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
1745 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
1746 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
1747 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
1748 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
1749 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
1750 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
1751#if 0
1752 // See Note 1.
1753 { SNaN, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1754 { SNaN, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1755 { SNaN, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1756 { SNaN, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1757 { SNaN, QNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1758 { SNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1759 { SNaN, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1760 { SNaN, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1761 { SNaN, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1762 { SNaN, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1763 { SNaN, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1764 { SNaN, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1765 { SNaN, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1766 { SNaN, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1767#endif
1768 { PNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1769 { PNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1770 { PNormalValue, PZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
1771 { PNormalValue, MZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
1772 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1773#if 0
1774 // See Note 1.
1775 { PNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1776#endif
1777 { PNormalValue, PNormalValue, "0x1p+1", APFloat::opOK, APFloat::fcNormal },
1778 { PNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1779 { PNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1780 { PNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1781 { PNormalValue, PSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1782 { PNormalValue, MSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1783 { PNormalValue, PSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1784 { PNormalValue, MSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1785 { MNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1786 { MNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1787 { MNormalValue, PZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
1788 { MNormalValue, MZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001789 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001790#if 0
1791 // See Note 1.
1792 { MNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1793#endif
1794 { MNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1795 { MNormalValue, MNormalValue, "-0x1p+1", APFloat::opOK, APFloat::fcNormal },
1796 { MNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1797 { MNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1798 { MNormalValue, PSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1799 { MNormalValue, MSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1800 { MNormalValue, PSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1801 { MNormalValue, MSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1802 { PLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1803 { PLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1804 { PLargestValue, PZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1805 { PLargestValue, MZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1806 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1807#if 0
1808 // See Note 1.
1809 { PLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1810#endif
1811 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1812 { PLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1813 { PLargestValue, PLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
1814 { PLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1815 { PLargestValue, PSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1816 { PLargestValue, MSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1817 { PLargestValue, PSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1818 { PLargestValue, MSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1819 { MLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1820 { MLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1821 { MLargestValue, PZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1822 { MLargestValue, MZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001823 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001824#if 0
1825 // See Note 1.
1826 { MLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1827#endif
1828 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1829 { MLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1830 { MLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1831 { MLargestValue, MLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
1832 { MLargestValue, PSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1833 { MLargestValue, MSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1834 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1835 { MLargestValue, MSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1836 { PSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1837 { PSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1838 { PSmallestValue, PZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
1839 { PSmallestValue, MZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
1840 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1841#if 0
1842 // See Note 1.
1843 { PSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1844#endif
1845 { PSmallestValue, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1846 { PSmallestValue, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1847 { PSmallestValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1848 { PSmallestValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1849 { PSmallestValue, PSmallestValue, "0x1p-148", APFloat::opOK, APFloat::fcNormal },
1850 { PSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1851 { PSmallestValue, PSmallestNormalized, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
1852 { PSmallestValue, MSmallestNormalized, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
1853 { MSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1854 { MSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1855 { MSmallestValue, PZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
1856 { MSmallestValue, MZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001857 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001858#if 0
1859 // See Note 1.
1860 { MSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1861#endif
1862 { MSmallestValue, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1863 { MSmallestValue, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1864 { MSmallestValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1865 { MSmallestValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1866 { MSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1867 { MSmallestValue, MSmallestValue, "-0x1p-148", APFloat::opOK, APFloat::fcNormal },
1868 { MSmallestValue, PSmallestNormalized, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
1869 { MSmallestValue, MSmallestNormalized, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
1870 { PSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1871 { PSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1872 { PSmallestNormalized, PZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
1873 { PSmallestNormalized, MZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
1874 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1875#if 0
1876// See Note 1.
1877 { PSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1878#endif
1879 { PSmallestNormalized, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1880 { PSmallestNormalized, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1881 { PSmallestNormalized, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1882 { PSmallestNormalized, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1883 { PSmallestNormalized, PSmallestValue, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
1884 { PSmallestNormalized, MSmallestValue, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
1885 { PSmallestNormalized, PSmallestNormalized, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
1886 { PSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1887 { MSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1888 { MSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1889 { MSmallestNormalized, PZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
1890 { MSmallestNormalized, MZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001891 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001892#if 0
1893 // See Note 1.
1894 { MSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1895#endif
1896 { MSmallestNormalized, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1897 { MSmallestNormalized, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1898 { MSmallestNormalized, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1899 { MSmallestNormalized, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1900 { MSmallestNormalized, PSmallestValue, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
1901 { MSmallestNormalized, MSmallestValue, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
1902 { MSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1903 { MSmallestNormalized, MSmallestNormalized, "-0x1p-125", APFloat::opOK, APFloat::fcNormal }
1904 };
1905
1906 for (size_t i = 0; i < NumTests; ++i) {
1907 APFloat x(SpecialCaseTests[i].x);
1908 APFloat y(SpecialCaseTests[i].y);
1909 APFloat::opStatus status = x.add(y, APFloat::rmNearestTiesToEven);
1910
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001911 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
Michael Gottesmane45b1082013-06-24 09:58:07 +00001912
Michael Gottesmane45b1082013-06-24 09:58:07 +00001913 EXPECT_TRUE(result.bitwiseIsEqual(x));
1914 EXPECT_TRUE((int)status == SpecialCaseTests[i].status);
1915 EXPECT_TRUE((int)x.getCategory() == SpecialCaseTests[i].category);
1916 }
1917}
1918
Michael Gottesman9368a532013-06-26 23:55:23 +00001919TEST(APFloatTest, subtract) {
1920 // Test Special Cases against each other and normal values.
1921
1922 // TODOS/NOTES:
1923 // 1. Since we perform only default exception handling all operations with
1924 // signaling NaNs should have a result that is a quiet NaN. Currently they
1925 // return sNaN.
Michael Gottesman9368a532013-06-26 23:55:23 +00001926
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001927 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
1928 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
1929 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
1930 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
1931 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
1932 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
1933 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
1934 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
1935 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
1936 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
1937 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
1938 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Michael Gottesman9368a532013-06-26 23:55:23 +00001939 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001940 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Michael Gottesman9368a532013-06-26 23:55:23 +00001941 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001942 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Michael Gottesman9368a532013-06-26 23:55:23 +00001943
1944 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
1945
1946 const unsigned NumTests = 169;
1947 struct {
1948 APFloat x;
1949 APFloat y;
1950 const char *result;
1951 int status;
1952 int category;
1953 } SpecialCaseTests[NumTests] = {
1954 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1955 { PInf, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1956 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
1957 { PInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
Stephen Canond3278282014-06-08 16:53:31 +00001958 { PInf, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00001959#if 0
1960// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00001961 { PInf, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00001962#endif
1963 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1964 { PInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1965 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1966 { PInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1967 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1968 { PInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1969 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
1970 { PInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
1971 { MInf, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1972 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1973 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
1974 { MInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
Stephen Canond3278282014-06-08 16:53:31 +00001975 { MInf, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00001976#if 0
1977// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00001978 { MInf, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00001979#endif
1980 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1981 { MInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1982 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1983 { MInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1984 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1985 { MInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1986 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
1987 { MInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
1988 { PZero, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1989 { PZero, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1990 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1991 { PZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Stephen Canond3278282014-06-08 16:53:31 +00001992 { PZero, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00001993#if 0
1994// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00001995 { PZero, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00001996#endif
1997 { PZero, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
1998 { PZero, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
1999 { PZero, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2000 { PZero, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2001 { PZero, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2002 { PZero, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2003 { PZero, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2004 { PZero, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2005 { MZero, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2006 { MZero, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2007 { MZero, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2008 { MZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Stephen Canond3278282014-06-08 16:53:31 +00002009 { MZero, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002010#if 0
2011// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002012 { MZero, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002013#endif
2014 { MZero, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2015 { MZero, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2016 { MZero, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2017 { MZero, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2018 { MZero, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2019 { MZero, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2020 { MZero, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2021 { MZero, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2022 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
2023 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
2024 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
2025 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
2026 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2027#if 0
2028// See Note 1.
2029 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2030#endif
2031 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2032 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2033 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2034 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2035 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2036 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2037 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2038 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2039#if 0
2040// See Note 1.
2041 { SNaN, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2042 { SNaN, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2043 { SNaN, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2044 { SNaN, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2045 { SNaN, QNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2046 { SNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2047 { SNaN, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2048 { SNaN, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2049 { SNaN, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2050 { SNaN, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2051 { SNaN, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2052 { SNaN, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2053 { SNaN, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2054 { SNaN, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2055#endif
2056 { PNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2057 { PNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2058 { PNormalValue, PZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2059 { PNormalValue, MZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002060 { PNormalValue, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002061#if 0
2062// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002063 { PNormalValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002064#endif
2065 { PNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2066 { PNormalValue, MNormalValue, "0x1p+1", APFloat::opOK, APFloat::fcNormal },
2067 { PNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2068 { PNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2069 { PNormalValue, PSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2070 { PNormalValue, MSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2071 { PNormalValue, PSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2072 { PNormalValue, MSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2073 { MNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2074 { MNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2075 { MNormalValue, PZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2076 { MNormalValue, MZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002077 { MNormalValue, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002078#if 0
2079// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002080 { MNormalValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002081#endif
2082 { MNormalValue, PNormalValue, "-0x1p+1", APFloat::opOK, APFloat::fcNormal },
2083 { MNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2084 { MNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2085 { MNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2086 { MNormalValue, PSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2087 { MNormalValue, MSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2088 { MNormalValue, PSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2089 { MNormalValue, MSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2090 { PLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2091 { PLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2092 { PLargestValue, PZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2093 { PLargestValue, MZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002094 { PLargestValue, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002095#if 0
2096// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002097 { PLargestValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002098#endif
2099 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2100 { PLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2101 { PLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2102 { PLargestValue, MLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2103 { PLargestValue, PSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2104 { PLargestValue, MSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2105 { PLargestValue, PSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2106 { PLargestValue, MSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2107 { MLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2108 { MLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2109 { MLargestValue, PZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2110 { MLargestValue, MZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002111 { MLargestValue, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002112#if 0
2113// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002114 { MLargestValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002115#endif
2116 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2117 { MLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2118 { MLargestValue, PLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2119 { MLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2120 { MLargestValue, PSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2121 { MLargestValue, MSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2122 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2123 { MLargestValue, MSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2124 { PSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2125 { PSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2126 { PSmallestValue, PZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2127 { PSmallestValue, MZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002128 { PSmallestValue, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002129#if 0
2130// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002131 { PSmallestValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002132#endif
2133 { PSmallestValue, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2134 { PSmallestValue, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2135 { PSmallestValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2136 { PSmallestValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2137 { PSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2138 { PSmallestValue, MSmallestValue, "0x1p-148", APFloat::opOK, APFloat::fcNormal },
2139 { PSmallestValue, PSmallestNormalized, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2140 { PSmallestValue, MSmallestNormalized, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2141 { MSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2142 { MSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2143 { MSmallestValue, PZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2144 { MSmallestValue, MZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002145 { MSmallestValue, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002146#if 0
2147// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002148 { MSmallestValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002149#endif
2150 { MSmallestValue, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2151 { MSmallestValue, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2152 { MSmallestValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2153 { MSmallestValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2154 { MSmallestValue, PSmallestValue, "-0x1p-148", APFloat::opOK, APFloat::fcNormal },
2155 { MSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2156 { MSmallestValue, PSmallestNormalized, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2157 { MSmallestValue, MSmallestNormalized, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2158 { PSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2159 { PSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2160 { PSmallestNormalized, PZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2161 { PSmallestNormalized, MZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002162 { PSmallestNormalized, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002163#if 0
2164// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002165 { PSmallestNormalized, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002166#endif
2167 { PSmallestNormalized, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2168 { PSmallestNormalized, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2169 { PSmallestNormalized, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2170 { PSmallestNormalized, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2171 { PSmallestNormalized, PSmallestValue, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2172 { PSmallestNormalized, MSmallestValue, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2173 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2174 { PSmallestNormalized, MSmallestNormalized, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
2175 { MSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2176 { MSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2177 { MSmallestNormalized, PZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2178 { MSmallestNormalized, MZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002179 { MSmallestNormalized, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002180#if 0
2181// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002182 { MSmallestNormalized, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002183#endif
2184 { MSmallestNormalized, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2185 { MSmallestNormalized, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2186 { MSmallestNormalized, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2187 { MSmallestNormalized, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2188 { MSmallestNormalized, PSmallestValue, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2189 { MSmallestNormalized, MSmallestValue, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2190 { MSmallestNormalized, PSmallestNormalized, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
2191 { MSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero }
2192 };
2193
2194 for (size_t i = 0; i < NumTests; ++i) {
2195 APFloat x(SpecialCaseTests[i].x);
2196 APFloat y(SpecialCaseTests[i].y);
2197 APFloat::opStatus status = x.subtract(y, APFloat::rmNearestTiesToEven);
2198
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002199 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
Michael Gottesman9368a532013-06-26 23:55:23 +00002200
Michael Gottesman9368a532013-06-26 23:55:23 +00002201 EXPECT_TRUE(result.bitwiseIsEqual(x));
2202 EXPECT_TRUE((int)status == SpecialCaseTests[i].status);
2203 EXPECT_TRUE((int)x.getCategory() == SpecialCaseTests[i].category);
2204 }
2205}
2206
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002207TEST(APFloatTest, multiply) {
2208 // Test Special Cases against each other and normal values.
2209
2210 // TODOS/NOTES:
2211 // 1. Since we perform only default exception handling all operations with
2212 // signaling NaNs should have a result that is a quiet NaN. Currently they
2213 // return sNaN.
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002214
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002215 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2216 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2217 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2218 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2219 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2220 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
2221 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2222 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2223 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2224 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2225 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2226 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002227 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002228 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002229 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002230 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002231
2232 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2233 const int UnderflowStatus = APFloat::opUnderflow | APFloat::opInexact;
2234
2235 const unsigned NumTests = 169;
2236 struct {
2237 APFloat x;
2238 APFloat y;
2239 const char *result;
2240 int status;
2241 int category;
2242 } SpecialCaseTests[NumTests] = {
2243 { PInf, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2244 { PInf, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2245 { PInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2246 { PInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2247 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2248#if 0
2249// See Note 1.
2250 { PInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2251#endif
2252 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2253 { PInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2254 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2255 { PInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2256 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2257 { PInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2258 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2259 { PInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2260 { MInf, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2261 { MInf, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2262 { MInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2263 { MInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002264 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002265#if 0
2266// See Note 1.
2267 { MInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2268#endif
2269 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2270 { MInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2271 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2272 { MInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2273 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2274 { MInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2275 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2276 { MInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2277 { PZero, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2278 { PZero, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2279 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2280 { PZero, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2281 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2282#if 0
2283// See Note 1.
2284 { PZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2285#endif
2286 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2287 { PZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2288 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2289 { PZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2290 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2291 { PZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2292 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2293 { PZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2294 { MZero, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2295 { MZero, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2296 { MZero, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2297 { MZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002298 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002299#if 0
2300// See Note 1.
2301 { MZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2302#endif
2303 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2304 { MZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2305 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2306 { MZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2307 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2308 { MZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2309 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2310 { MZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2311 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002312 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002313 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002314 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002315 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2316#if 0
2317// See Note 1.
2318 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2319#endif
2320 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002321 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002322 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002323 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002324 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002325 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002326 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002327 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002328#if 0
2329// See Note 1.
2330 { SNaN, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2331 { SNaN, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2332 { SNaN, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2333 { SNaN, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2334 { SNaN, QNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2335 { SNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2336 { SNaN, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2337 { SNaN, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2338 { SNaN, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2339 { SNaN, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2340 { SNaN, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2341 { SNaN, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2342 { SNaN, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2343 { SNaN, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2344#endif
2345 { PNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2346 { PNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2347 { PNormalValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2348 { PNormalValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2349 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2350#if 0
2351// See Note 1.
2352 { PNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2353#endif
2354 { PNormalValue, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2355 { PNormalValue, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2356 { PNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2357 { PNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2358 { PNormalValue, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2359 { PNormalValue, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2360 { PNormalValue, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2361 { PNormalValue, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2362 { MNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2363 { MNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2364 { MNormalValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2365 { MNormalValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002366 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002367#if 0
2368// See Note 1.
2369 { MNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2370#endif
2371 { MNormalValue, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2372 { MNormalValue, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2373 { MNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2374 { MNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2375 { MNormalValue, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2376 { MNormalValue, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2377 { MNormalValue, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2378 { MNormalValue, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2379 { PLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2380 { PLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2381 { PLargestValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2382 { PLargestValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2383 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2384#if 0
2385// See Note 1.
2386 { PLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2387#endif
2388 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2389 { PLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2390 { PLargestValue, PLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2391 { PLargestValue, MLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2392 { PLargestValue, PSmallestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2393 { PLargestValue, MSmallestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2394 { PLargestValue, PSmallestNormalized, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2395 { PLargestValue, MSmallestNormalized, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2396 { MLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2397 { MLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2398 { MLargestValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2399 { MLargestValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002400 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002401#if 0
2402// See Note 1.
2403 { MLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2404#endif
2405 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2406 { MLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2407 { MLargestValue, PLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2408 { MLargestValue, MLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2409 { MLargestValue, PSmallestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2410 { MLargestValue, MSmallestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2411 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2412 { MLargestValue, MSmallestNormalized, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2413 { PSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2414 { PSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2415 { PSmallestValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2416 { PSmallestValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2417 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2418#if 0
2419// See Note 1.
2420 { PSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2421#endif
2422 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2423 { PSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2424 { PSmallestValue, PLargestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2425 { PSmallestValue, MLargestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2426 { PSmallestValue, PSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2427 { PSmallestValue, MSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2428 { PSmallestValue, PSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2429 { PSmallestValue, MSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2430 { MSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2431 { MSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2432 { MSmallestValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2433 { MSmallestValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002434 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002435#if 0
2436// See Note 1.
2437 { MSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2438#endif
2439 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2440 { MSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2441 { MSmallestValue, PLargestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2442 { MSmallestValue, MLargestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2443 { MSmallestValue, PSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2444 { MSmallestValue, MSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2445 { MSmallestValue, PSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2446 { MSmallestValue, MSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2447 { PSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2448 { PSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2449 { PSmallestNormalized, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2450 { PSmallestNormalized, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2451 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2452#if 0
2453// See Note 1.
2454 { PSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2455#endif
2456 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2457 { PSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2458 { PSmallestNormalized, PLargestValue, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2459 { PSmallestNormalized, MLargestValue, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2460 { PSmallestNormalized, PSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2461 { PSmallestNormalized, MSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2462 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2463 { PSmallestNormalized, MSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2464 { MSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2465 { MSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2466 { MSmallestNormalized, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2467 { MSmallestNormalized, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002468 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002469#if 0
2470// See Note 1.
2471 { MSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2472#endif
2473 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2474 { MSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2475 { MSmallestNormalized, PLargestValue, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2476 { MSmallestNormalized, MLargestValue, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2477 { MSmallestNormalized, PSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2478 { MSmallestNormalized, MSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2479 { MSmallestNormalized, PSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2480 { MSmallestNormalized, MSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero }
2481 };
2482
2483 for (size_t i = 0; i < NumTests; ++i) {
2484 APFloat x(SpecialCaseTests[i].x);
2485 APFloat y(SpecialCaseTests[i].y);
2486 APFloat::opStatus status = x.multiply(y, APFloat::rmNearestTiesToEven);
2487
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002488 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002489
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002490 EXPECT_TRUE(result.bitwiseIsEqual(x));
2491 EXPECT_TRUE((int)status == SpecialCaseTests[i].status);
2492 EXPECT_TRUE((int)x.getCategory() == SpecialCaseTests[i].category);
2493 }
2494}
Michael Gottesman9368a532013-06-26 23:55:23 +00002495
Michael Gottesman3eacb582013-06-27 00:42:00 +00002496TEST(APFloatTest, divide) {
2497 // Test Special Cases against each other and normal values.
2498
2499 // TODOS/NOTES:
2500 // 1. Since we perform only default exception handling all operations with
2501 // signaling NaNs should have a result that is a quiet NaN. Currently they
2502 // return sNaN.
Michael Gottesman3eacb582013-06-27 00:42:00 +00002503
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002504 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2505 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2506 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2507 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2508 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2509 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
2510 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2511 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2512 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2513 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2514 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2515 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Michael Gottesman3eacb582013-06-27 00:42:00 +00002516 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002517 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Michael Gottesman3eacb582013-06-27 00:42:00 +00002518 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002519 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Michael Gottesman3eacb582013-06-27 00:42:00 +00002520
2521 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2522 const int UnderflowStatus = APFloat::opUnderflow | APFloat::opInexact;
2523
2524 const unsigned NumTests = 169;
2525 struct {
2526 APFloat x;
2527 APFloat y;
2528 const char *result;
2529 int status;
2530 int category;
2531 } SpecialCaseTests[NumTests] = {
2532 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2533 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2534 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2535 { PInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2536 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2537#if 0
2538// See Note 1.
2539 { PInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2540#endif
2541 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2542 { PInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2543 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2544 { PInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2545 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2546 { PInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2547 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2548 { PInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2549 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2550 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2551 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2552 { MInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002553 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002554#if 0
2555// See Note 1.
2556 { MInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2557#endif
2558 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2559 { MInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2560 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2561 { MInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2562 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2563 { MInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2564 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2565 { MInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2566 { PZero, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2567 { PZero, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2568 { PZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2569 { PZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2570 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2571#if 0
2572// See Note 1.
2573 { PZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2574#endif
2575 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2576 { PZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2577 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2578 { PZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2579 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2580 { PZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2581 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2582 { PZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2583 { MZero, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2584 { MZero, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2585 { MZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2586 { MZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002587 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002588#if 0
2589// See Note 1.
2590 { MZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2591#endif
2592 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2593 { MZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2594 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2595 { MZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2596 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2597 { MZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2598 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2599 { MZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2600 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002601 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002602 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002603 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002604 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2605#if 0
2606// See Note 1.
2607 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2608#endif
2609 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002610 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002611 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002612 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002613 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002614 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002615 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002616 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002617#if 0
2618// See Note 1.
2619 { SNaN, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2620 { SNaN, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2621 { SNaN, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2622 { SNaN, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2623 { SNaN, QNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2624 { SNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2625 { SNaN, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2626 { SNaN, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2627 { SNaN, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2628 { SNaN, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2629 { SNaN, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2630 { SNaN, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2631 { SNaN, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2632 { SNaN, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2633#endif
2634 { PNormalValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2635 { PNormalValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2636 { PNormalValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2637 { PNormalValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2638 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2639#if 0
2640// See Note 1.
2641 { PNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2642#endif
2643 { PNormalValue, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2644 { PNormalValue, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2645 { PNormalValue, PLargestValue, "0x1p-128", UnderflowStatus, APFloat::fcNormal },
2646 { PNormalValue, MLargestValue, "-0x1p-128", UnderflowStatus, APFloat::fcNormal },
2647 { PNormalValue, PSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2648 { PNormalValue, MSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2649 { PNormalValue, PSmallestNormalized, "0x1p+126", APFloat::opOK, APFloat::fcNormal },
2650 { PNormalValue, MSmallestNormalized, "-0x1p+126", APFloat::opOK, APFloat::fcNormal },
2651 { MNormalValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2652 { MNormalValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2653 { MNormalValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2654 { MNormalValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002655 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002656#if 0
2657// See Note 1.
2658 { MNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2659#endif
2660 { MNormalValue, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2661 { MNormalValue, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2662 { MNormalValue, PLargestValue, "-0x1p-128", UnderflowStatus, APFloat::fcNormal },
2663 { MNormalValue, MLargestValue, "0x1p-128", UnderflowStatus, APFloat::fcNormal },
2664 { MNormalValue, PSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2665 { MNormalValue, MSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2666 { MNormalValue, PSmallestNormalized, "-0x1p+126", APFloat::opOK, APFloat::fcNormal },
2667 { MNormalValue, MSmallestNormalized, "0x1p+126", APFloat::opOK, APFloat::fcNormal },
2668 { PLargestValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2669 { PLargestValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2670 { PLargestValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2671 { PLargestValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2672 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2673#if 0
2674// See Note 1.
2675 { PLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2676#endif
2677 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2678 { PLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2679 { PLargestValue, PLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2680 { PLargestValue, MLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2681 { PLargestValue, PSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2682 { PLargestValue, MSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2683 { PLargestValue, PSmallestNormalized, "inf", OverflowStatus, APFloat::fcInfinity },
2684 { PLargestValue, MSmallestNormalized, "-inf", OverflowStatus, APFloat::fcInfinity },
2685 { MLargestValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2686 { MLargestValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2687 { MLargestValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2688 { MLargestValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002689 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002690#if 0
2691// See Note 1.
2692 { MLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2693#endif
2694 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2695 { MLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2696 { MLargestValue, PLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2697 { MLargestValue, MLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2698 { MLargestValue, PSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2699 { MLargestValue, MSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2700 { MLargestValue, PSmallestNormalized, "-inf", OverflowStatus, APFloat::fcInfinity },
2701 { MLargestValue, MSmallestNormalized, "inf", OverflowStatus, APFloat::fcInfinity },
2702 { PSmallestValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2703 { PSmallestValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2704 { PSmallestValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2705 { PSmallestValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2706 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2707#if 0
2708// See Note 1.
2709 { PSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2710#endif
2711 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2712 { PSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2713 { PSmallestValue, PLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2714 { PSmallestValue, MLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2715 { PSmallestValue, PSmallestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2716 { PSmallestValue, MSmallestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2717 { PSmallestValue, PSmallestNormalized, "0x1p-23", APFloat::opOK, APFloat::fcNormal },
2718 { PSmallestValue, MSmallestNormalized, "-0x1p-23", APFloat::opOK, APFloat::fcNormal },
2719 { MSmallestValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2720 { MSmallestValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2721 { MSmallestValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2722 { MSmallestValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002723 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002724#if 0
2725// See Note 1.
2726 { MSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2727#endif
2728 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2729 { MSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2730 { MSmallestValue, PLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2731 { MSmallestValue, MLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2732 { MSmallestValue, PSmallestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2733 { MSmallestValue, MSmallestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2734 { MSmallestValue, PSmallestNormalized, "-0x1p-23", APFloat::opOK, APFloat::fcNormal },
2735 { MSmallestValue, MSmallestNormalized, "0x1p-23", APFloat::opOK, APFloat::fcNormal },
2736 { PSmallestNormalized, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2737 { PSmallestNormalized, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2738 { PSmallestNormalized, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2739 { PSmallestNormalized, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2740 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2741#if 0
2742// See Note 1.
2743 { PSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2744#endif
2745 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2746 { PSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2747 { PSmallestNormalized, PLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2748 { PSmallestNormalized, MLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2749 { PSmallestNormalized, PSmallestValue, "0x1p+23", APFloat::opOK, APFloat::fcNormal },
2750 { PSmallestNormalized, MSmallestValue, "-0x1p+23", APFloat::opOK, APFloat::fcNormal },
2751 { PSmallestNormalized, PSmallestNormalized, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2752 { PSmallestNormalized, MSmallestNormalized, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2753 { MSmallestNormalized, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2754 { MSmallestNormalized, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2755 { MSmallestNormalized, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2756 { MSmallestNormalized, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002757 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002758#if 0
2759// See Note 1.
2760 { MSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2761#endif
2762 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2763 { MSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2764 { MSmallestNormalized, PLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2765 { MSmallestNormalized, MLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2766 { MSmallestNormalized, PSmallestValue, "-0x1p+23", APFloat::opOK, APFloat::fcNormal },
2767 { MSmallestNormalized, MSmallestValue, "0x1p+23", APFloat::opOK, APFloat::fcNormal },
2768 { MSmallestNormalized, PSmallestNormalized, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2769 { MSmallestNormalized, MSmallestNormalized, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2770 };
2771
2772 for (size_t i = 0; i < NumTests; ++i) {
2773 APFloat x(SpecialCaseTests[i].x);
2774 APFloat y(SpecialCaseTests[i].y);
2775 APFloat::opStatus status = x.divide(y, APFloat::rmNearestTiesToEven);
2776
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002777 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
Michael Gottesman3eacb582013-06-27 00:42:00 +00002778
2779 EXPECT_TRUE(result.bitwiseIsEqual(x));
2780 EXPECT_TRUE((int)status == SpecialCaseTests[i].status);
2781 EXPECT_TRUE((int)x.getCategory() == SpecialCaseTests[i].category);
2782 }
2783}
2784
Chandler Carruthdf782e42014-10-09 23:26:15 +00002785TEST(APFloatTest, operatorOverloads) {
2786 // This is mostly testing that these operator overloads compile.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002787 APFloat One = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2788 APFloat Two = APFloat(APFloat::IEEEsingle(), "0x2p+0");
Chandler Carruthdf782e42014-10-09 23:26:15 +00002789 EXPECT_TRUE(Two.bitwiseIsEqual(One + One));
2790 EXPECT_TRUE(One.bitwiseIsEqual(Two - One));
2791 EXPECT_TRUE(Two.bitwiseIsEqual(One * Two));
2792 EXPECT_TRUE(One.bitwiseIsEqual(Two / Two));
2793}
Chandler Carruth7468b062014-10-10 04:17:04 +00002794
Chandler Carruthafe56ae2014-10-10 08:27:22 +00002795TEST(APFloatTest, abs) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002796 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2797 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2798 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2799 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2800 APFloat PQNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2801 APFloat MQNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
2802 APFloat PSNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
2803 APFloat MSNaN = APFloat::getSNaN(APFloat::IEEEsingle(), true);
2804 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2805 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2806 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2807 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2808 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2809 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Chandler Carruthafe56ae2014-10-10 08:27:22 +00002810 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002811 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Chandler Carruthafe56ae2014-10-10 08:27:22 +00002812 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002813 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Chandler Carruthafe56ae2014-10-10 08:27:22 +00002814
2815 EXPECT_TRUE(PInf.bitwiseIsEqual(abs(PInf)));
2816 EXPECT_TRUE(PInf.bitwiseIsEqual(abs(MInf)));
2817 EXPECT_TRUE(PZero.bitwiseIsEqual(abs(PZero)));
2818 EXPECT_TRUE(PZero.bitwiseIsEqual(abs(MZero)));
2819 EXPECT_TRUE(PQNaN.bitwiseIsEqual(abs(PQNaN)));
2820 EXPECT_TRUE(PQNaN.bitwiseIsEqual(abs(MQNaN)));
2821 EXPECT_TRUE(PSNaN.bitwiseIsEqual(abs(PSNaN)));
2822 EXPECT_TRUE(PSNaN.bitwiseIsEqual(abs(MSNaN)));
2823 EXPECT_TRUE(PNormalValue.bitwiseIsEqual(abs(PNormalValue)));
2824 EXPECT_TRUE(PNormalValue.bitwiseIsEqual(abs(MNormalValue)));
2825 EXPECT_TRUE(PLargestValue.bitwiseIsEqual(abs(PLargestValue)));
2826 EXPECT_TRUE(PLargestValue.bitwiseIsEqual(abs(MLargestValue)));
2827 EXPECT_TRUE(PSmallestValue.bitwiseIsEqual(abs(PSmallestValue)));
2828 EXPECT_TRUE(PSmallestValue.bitwiseIsEqual(abs(MSmallestValue)));
2829 EXPECT_TRUE(PSmallestNormalized.bitwiseIsEqual(abs(PSmallestNormalized)));
2830 EXPECT_TRUE(PSmallestNormalized.bitwiseIsEqual(abs(MSmallestNormalized)));
2831}
2832
Matt Arsenault8a27aee2017-01-25 04:54:34 +00002833TEST(APFloatTest, neg) {
2834 APFloat One = APFloat(APFloat::IEEEsingle(), "1.0");
2835 APFloat NegOne = APFloat(APFloat::IEEEsingle(), "-1.0");
2836 APFloat Zero = APFloat::getZero(APFloat::IEEEsingle(), false);
2837 APFloat NegZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2838 APFloat Inf = APFloat::getInf(APFloat::IEEEsingle(), false);
2839 APFloat NegInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2840 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2841 APFloat NegQNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
2842
2843 EXPECT_TRUE(NegOne.bitwiseIsEqual(neg(One)));
2844 EXPECT_TRUE(One.bitwiseIsEqual(neg(NegOne)));
2845 EXPECT_TRUE(NegZero.bitwiseIsEqual(neg(Zero)));
2846 EXPECT_TRUE(Zero.bitwiseIsEqual(neg(NegZero)));
2847 EXPECT_TRUE(NegInf.bitwiseIsEqual(neg(Inf)));
2848 EXPECT_TRUE(Inf.bitwiseIsEqual(neg(NegInf)));
2849 EXPECT_TRUE(NegInf.bitwiseIsEqual(neg(Inf)));
2850 EXPECT_TRUE(Inf.bitwiseIsEqual(neg(NegInf)));
2851 EXPECT_TRUE(NegQNaN.bitwiseIsEqual(neg(QNaN)));
2852 EXPECT_TRUE(QNaN.bitwiseIsEqual(neg(NegQNaN)));
2853}
2854
Chandler Carruthca067142014-10-10 05:14:12 +00002855TEST(APFloatTest, ilogb) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002856 EXPECT_EQ(-1074, ilogb(APFloat::getSmallest(APFloat::IEEEdouble(), false)));
2857 EXPECT_EQ(-1074, ilogb(APFloat::getSmallest(APFloat::IEEEdouble(), true)));
2858 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1024")));
2859 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023")));
2860 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023")));
2861 EXPECT_EQ(-51, ilogb(APFloat(APFloat::IEEEdouble(), "0x1p-51")));
2862 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1023")));
2863 EXPECT_EQ(-2, ilogb(APFloat(APFloat::IEEEdouble(), "0x0.ffffp-1")));
2864 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.fffep-1023")));
2865 EXPECT_EQ(1023, ilogb(APFloat::getLargest(APFloat::IEEEdouble(), false)));
2866 EXPECT_EQ(1023, ilogb(APFloat::getLargest(APFloat::IEEEdouble(), true)));
Matt Arsenault69fdf9b2016-03-13 05:12:32 +00002867
2868
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002869 EXPECT_EQ(0, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p+0")));
2870 EXPECT_EQ(0, ilogb(APFloat(APFloat::IEEEsingle(), "-0x1p+0")));
2871 EXPECT_EQ(42, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p+42")));
2872 EXPECT_EQ(-42, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p-42")));
Chandler Carruth7468b062014-10-10 04:17:04 +00002873
Chandler Carruthca067142014-10-10 05:14:12 +00002874 EXPECT_EQ(APFloat::IEK_Inf,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002875 ilogb(APFloat::getInf(APFloat::IEEEsingle(), false)));
Chandler Carruthca067142014-10-10 05:14:12 +00002876 EXPECT_EQ(APFloat::IEK_Inf,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002877 ilogb(APFloat::getInf(APFloat::IEEEsingle(), true)));
Chandler Carruthca067142014-10-10 05:14:12 +00002878 EXPECT_EQ(APFloat::IEK_Zero,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002879 ilogb(APFloat::getZero(APFloat::IEEEsingle(), false)));
Chandler Carruthca067142014-10-10 05:14:12 +00002880 EXPECT_EQ(APFloat::IEK_Zero,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002881 ilogb(APFloat::getZero(APFloat::IEEEsingle(), true)));
Chandler Carruthca067142014-10-10 05:14:12 +00002882 EXPECT_EQ(APFloat::IEK_NaN,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002883 ilogb(APFloat::getNaN(APFloat::IEEEsingle(), false)));
Chandler Carruthca067142014-10-10 05:14:12 +00002884 EXPECT_EQ(APFloat::IEK_NaN,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002885 ilogb(APFloat::getSNaN(APFloat::IEEEsingle(), false)));
Chandler Carruth7468b062014-10-10 04:17:04 +00002886
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002887 EXPECT_EQ(127, ilogb(APFloat::getLargest(APFloat::IEEEsingle(), false)));
2888 EXPECT_EQ(127, ilogb(APFloat::getLargest(APFloat::IEEEsingle(), true)));
Matt Arsenault69fdf9b2016-03-13 05:12:32 +00002889
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002890 EXPECT_EQ(-149, ilogb(APFloat::getSmallest(APFloat::IEEEsingle(), false)));
2891 EXPECT_EQ(-149, ilogb(APFloat::getSmallest(APFloat::IEEEsingle(), true)));
Chandler Carruthca067142014-10-10 05:14:12 +00002892 EXPECT_EQ(-126,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002893 ilogb(APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false)));
Chandler Carruthca067142014-10-10 05:14:12 +00002894 EXPECT_EQ(-126,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002895 ilogb(APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true)));
Chandler Carruth7468b062014-10-10 04:17:04 +00002896}
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002897
2898TEST(APFloatTest, scalbn) {
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002899
2900 const APFloat::roundingMode RM = APFloat::rmNearestTiesToEven;
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002901 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002902 APFloat(APFloat::IEEEsingle(), "0x1p+0")
2903 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 0, RM)));
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002904 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002905 APFloat(APFloat::IEEEsingle(), "0x1p+42")
2906 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 42, RM)));
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002907 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002908 APFloat(APFloat::IEEEsingle(), "0x1p-42")
2909 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), -42, RM)));
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002910
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002911 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2912 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2913 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2914 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2915 APFloat QPNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2916 APFloat QMNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
2917 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002918
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002919 EXPECT_TRUE(PInf.bitwiseIsEqual(scalbn(PInf, 0, RM)));
2920 EXPECT_TRUE(MInf.bitwiseIsEqual(scalbn(MInf, 0, RM)));
2921 EXPECT_TRUE(PZero.bitwiseIsEqual(scalbn(PZero, 0, RM)));
2922 EXPECT_TRUE(MZero.bitwiseIsEqual(scalbn(MZero, 0, RM)));
2923 EXPECT_TRUE(QPNaN.bitwiseIsEqual(scalbn(QPNaN, 0, RM)));
2924 EXPECT_TRUE(QMNaN.bitwiseIsEqual(scalbn(QMNaN, 0, RM)));
Matt Arsenaultea00b492016-03-23 23:51:45 +00002925 EXPECT_FALSE(scalbn(SNaN, 0, RM).isSignaling());
2926
2927 APFloat ScalbnSNaN = scalbn(SNaN, 1, RM);
2928 EXPECT_TRUE(ScalbnSNaN.isNaN() && !ScalbnSNaN.isSignaling());
2929
2930 // Make sure highest bit of payload is preserved.
2931 const APInt Payload(64, (UINT64_C(1) << 50) |
2932 (UINT64_C(1) << 49) |
2933 (UINT64_C(1234) << 32) |
2934 1);
2935
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002936 APFloat SNaNWithPayload = APFloat::getSNaN(APFloat::IEEEdouble(), false,
Matt Arsenaultea00b492016-03-23 23:51:45 +00002937 &Payload);
2938 APFloat QuietPayload = scalbn(SNaNWithPayload, 1, RM);
2939 EXPECT_TRUE(QuietPayload.isNaN() && !QuietPayload.isSignaling());
2940 EXPECT_EQ(Payload, QuietPayload.bitcastToAPInt().getLoBits(51));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002941
2942 EXPECT_TRUE(PInf.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002943 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 128, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002944 EXPECT_TRUE(MInf.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002945 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p+0"), 128, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002946 EXPECT_TRUE(PInf.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002947 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+127"), 1, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002948 EXPECT_TRUE(PZero.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002949 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p-127"), -127, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002950 EXPECT_TRUE(MZero.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002951 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p-127"), -127, RM)));
2952 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p-149").bitwiseIsEqual(
2953 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p-127"), -22, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002954 EXPECT_TRUE(PZero.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002955 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p-126"), -24, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002956
2957
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002958 APFloat SmallestF64 = APFloat::getSmallest(APFloat::IEEEdouble(), false);
2959 APFloat NegSmallestF64 = APFloat::getSmallest(APFloat::IEEEdouble(), true);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002960
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002961 APFloat LargestF64 = APFloat::getLargest(APFloat::IEEEdouble(), false);
2962 APFloat NegLargestF64 = APFloat::getLargest(APFloat::IEEEdouble(), true);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002963
2964 APFloat SmallestNormalizedF64
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002965 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002966 APFloat NegSmallestNormalizedF64
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002967 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002968
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002969 APFloat LargestDenormalF64(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023");
2970 APFloat NegLargestDenormalF64(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023");
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002971
2972
2973 EXPECT_TRUE(SmallestF64.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002974 scalbn(APFloat(APFloat::IEEEdouble(), "0x1p-1074"), 0, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002975 EXPECT_TRUE(NegSmallestF64.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002976 scalbn(APFloat(APFloat::IEEEdouble(), "-0x1p-1074"), 0, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002977
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002978 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1023")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002979 .bitwiseIsEqual(scalbn(SmallestF64, 2097, RM)));
2980
2981 EXPECT_TRUE(scalbn(SmallestF64, -2097, RM).isPosZero());
2982 EXPECT_TRUE(scalbn(SmallestF64, -2098, RM).isPosZero());
2983 EXPECT_TRUE(scalbn(SmallestF64, -2099, RM).isPosZero());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002984 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1022")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002985 .bitwiseIsEqual(scalbn(SmallestF64, 2096, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002986 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1023")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002987 .bitwiseIsEqual(scalbn(SmallestF64, 2097, RM)));
2988 EXPECT_TRUE(scalbn(SmallestF64, 2098, RM).isInfinity());
2989 EXPECT_TRUE(scalbn(SmallestF64, 2099, RM).isInfinity());
2990
2991 // Test for integer overflows when adding to exponent.
2992 EXPECT_TRUE(scalbn(SmallestF64, -INT_MAX, RM).isPosZero());
2993 EXPECT_TRUE(scalbn(LargestF64, INT_MAX, RM).isInfinity());
2994
2995 EXPECT_TRUE(LargestDenormalF64
2996 .bitwiseIsEqual(scalbn(LargestDenormalF64, 0, RM)));
2997 EXPECT_TRUE(NegLargestDenormalF64
2998 .bitwiseIsEqual(scalbn(NegLargestDenormalF64, 0, RM)));
2999
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003000 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1022")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003001 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003002 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1021")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003003 .bitwiseIsEqual(scalbn(NegLargestDenormalF64, 2, RM)));
3004
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003005 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+1")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003006 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1024, RM)));
3007 EXPECT_TRUE(scalbn(LargestDenormalF64, -1023, RM).isPosZero());
3008 EXPECT_TRUE(scalbn(LargestDenormalF64, -1024, RM).isPosZero());
3009 EXPECT_TRUE(scalbn(LargestDenormalF64, -2048, RM).isPosZero());
3010 EXPECT_TRUE(scalbn(LargestDenormalF64, 2047, RM).isInfinity());
3011 EXPECT_TRUE(scalbn(LargestDenormalF64, 2098, RM).isInfinity());
3012 EXPECT_TRUE(scalbn(LargestDenormalF64, 2099, RM).isInfinity());
3013
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003014 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-2")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003015 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1021, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003016 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003017 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1022, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003018 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+0")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003019 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1023, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003020 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+1023")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003021 .bitwiseIsEqual(scalbn(LargestDenormalF64, 2046, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003022 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+974")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003023 .bitwiseIsEqual(scalbn(SmallestF64, 2048, RM)));
3024
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003025 APFloat RandomDenormalF64(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+51");
3026 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-972")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003027 .bitwiseIsEqual(scalbn(RandomDenormalF64, -1023, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003028 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003029 .bitwiseIsEqual(scalbn(RandomDenormalF64, -52, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003030 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-2")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003031 .bitwiseIsEqual(scalbn(RandomDenormalF64, -53, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003032 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+0")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003033 .bitwiseIsEqual(scalbn(RandomDenormalF64, -51, RM)));
3034
3035 EXPECT_TRUE(scalbn(RandomDenormalF64, -2097, RM).isPosZero());
3036 EXPECT_TRUE(scalbn(RandomDenormalF64, -2090, RM).isPosZero());
3037
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00003038
3039 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003040 APFloat(APFloat::IEEEdouble(), "-0x1p-1073")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003041 .bitwiseIsEqual(scalbn(NegLargestF64, -2097, RM)));
3042
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00003043 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003044 APFloat(APFloat::IEEEdouble(), "-0x1p-1024")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003045 .bitwiseIsEqual(scalbn(NegLargestF64, -2048, RM)));
3046
3047 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003048 APFloat(APFloat::IEEEdouble(), "0x1p-1073")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003049 .bitwiseIsEqual(scalbn(LargestF64, -2097, RM)));
3050
3051 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003052 APFloat(APFloat::IEEEdouble(), "0x1p-1074")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003053 .bitwiseIsEqual(scalbn(LargestF64, -2098, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003054 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1074")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003055 .bitwiseIsEqual(scalbn(NegLargestF64, -2098, RM)));
3056 EXPECT_TRUE(scalbn(NegLargestF64, -2099, RM).isNegZero());
3057 EXPECT_TRUE(scalbn(LargestF64, 1, RM).isInfinity());
3058
3059
3060 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003061 APFloat(APFloat::IEEEdouble(), "0x1p+0")
3062 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEdouble(), "0x1p+52"), -52, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003063
3064 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003065 APFloat(APFloat::IEEEdouble(), "0x1p-103")
3066 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEdouble(), "0x1p-51"), -52, RM)));
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00003067}
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003068
3069TEST(APFloatTest, frexp) {
3070 const APFloat::roundingMode RM = APFloat::rmNearestTiesToEven;
3071
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003072 APFloat PZero = APFloat::getZero(APFloat::IEEEdouble(), false);
3073 APFloat MZero = APFloat::getZero(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003074 APFloat One(1.0);
3075 APFloat MOne(-1.0);
3076 APFloat Two(2.0);
3077 APFloat MTwo(-2.0);
3078
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003079 APFloat LargestDenormal(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023");
3080 APFloat NegLargestDenormal(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023");
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003081
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003082 APFloat Smallest = APFloat::getSmallest(APFloat::IEEEdouble(), false);
3083 APFloat NegSmallest = APFloat::getSmallest(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003084
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003085 APFloat Largest = APFloat::getLargest(APFloat::IEEEdouble(), false);
3086 APFloat NegLargest = APFloat::getLargest(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003087
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003088 APFloat PInf = APFloat::getInf(APFloat::IEEEdouble(), false);
3089 APFloat MInf = APFloat::getInf(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003090
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003091 APFloat QPNaN = APFloat::getNaN(APFloat::IEEEdouble(), false);
3092 APFloat QMNaN = APFloat::getNaN(APFloat::IEEEdouble(), true);
3093 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEdouble(), false);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003094
3095 // Make sure highest bit of payload is preserved.
3096 const APInt Payload(64, (UINT64_C(1) << 50) |
3097 (UINT64_C(1) << 49) |
3098 (UINT64_C(1234) << 32) |
3099 1);
3100
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003101 APFloat SNaNWithPayload = APFloat::getSNaN(APFloat::IEEEdouble(), false,
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003102 &Payload);
3103
3104 APFloat SmallestNormalized
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003105 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003106 APFloat NegSmallestNormalized
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003107 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003108
3109 int Exp;
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003110 APFloat Frac(APFloat::IEEEdouble());
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003111
3112
3113 Frac = frexp(PZero, Exp, RM);
3114 EXPECT_EQ(0, Exp);
3115 EXPECT_TRUE(Frac.isPosZero());
3116
3117 Frac = frexp(MZero, Exp, RM);
3118 EXPECT_EQ(0, Exp);
3119 EXPECT_TRUE(Frac.isNegZero());
3120
3121
3122 Frac = frexp(One, Exp, RM);
3123 EXPECT_EQ(1, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003124 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003125
3126 Frac = frexp(MOne, Exp, RM);
3127 EXPECT_EQ(1, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003128 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003129
3130 Frac = frexp(LargestDenormal, Exp, RM);
3131 EXPECT_EQ(-1022, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003132 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003133
3134 Frac = frexp(NegLargestDenormal, Exp, RM);
3135 EXPECT_EQ(-1022, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003136 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003137
3138
3139 Frac = frexp(Smallest, Exp, RM);
3140 EXPECT_EQ(-1073, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003141 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003142
3143 Frac = frexp(NegSmallest, Exp, RM);
3144 EXPECT_EQ(-1073, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003145 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003146
3147
3148 Frac = frexp(Largest, Exp, RM);
3149 EXPECT_EQ(1024, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003150 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.fffffffffffffp-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003151
3152 Frac = frexp(NegLargest, Exp, RM);
3153 EXPECT_EQ(1024, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003154 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.fffffffffffffp-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003155
3156
3157 Frac = frexp(PInf, Exp, RM);
3158 EXPECT_EQ(INT_MAX, Exp);
3159 EXPECT_TRUE(Frac.isInfinity() && !Frac.isNegative());
3160
3161 Frac = frexp(MInf, Exp, RM);
3162 EXPECT_EQ(INT_MAX, Exp);
3163 EXPECT_TRUE(Frac.isInfinity() && Frac.isNegative());
3164
3165 Frac = frexp(QPNaN, Exp, RM);
3166 EXPECT_EQ(INT_MIN, Exp);
3167 EXPECT_TRUE(Frac.isNaN());
3168
3169 Frac = frexp(QMNaN, Exp, RM);
3170 EXPECT_EQ(INT_MIN, Exp);
3171 EXPECT_TRUE(Frac.isNaN());
3172
3173 Frac = frexp(SNaN, Exp, RM);
3174 EXPECT_EQ(INT_MIN, Exp);
3175 EXPECT_TRUE(Frac.isNaN() && !Frac.isSignaling());
3176
3177 Frac = frexp(SNaNWithPayload, Exp, RM);
3178 EXPECT_EQ(INT_MIN, Exp);
3179 EXPECT_TRUE(Frac.isNaN() && !Frac.isSignaling());
3180 EXPECT_EQ(Payload, Frac.bitcastToAPInt().getLoBits(51));
3181
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003182 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x0.ffffp-1"), Exp, RM);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003183 EXPECT_EQ(-1, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003184 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.fffep-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003185
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003186 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x1p-51"), Exp, RM);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003187 EXPECT_EQ(-50, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003188 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003189
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003190 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+51"), Exp, RM);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003191 EXPECT_EQ(52, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003192 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003193}
Tim Shen44bde892016-12-12 21:59:30 +00003194
Stephen Canon157c8692017-03-31 20:31:33 +00003195TEST(APFloatTest, mod) {
3196 {
3197 APFloat f1(APFloat::IEEEdouble(), "1.5");
3198 APFloat f2(APFloat::IEEEdouble(), "1.0");
3199 APFloat expected(APFloat::IEEEdouble(), "0.5");
3200 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3201 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3202 }
3203 {
3204 APFloat f1(APFloat::IEEEdouble(), "0.5");
3205 APFloat f2(APFloat::IEEEdouble(), "1.0");
3206 APFloat expected(APFloat::IEEEdouble(), "0.5");
3207 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3208 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3209 }
3210 {
3211 APFloat f1(APFloat::IEEEdouble(), "0x1.3333333333333p-2"); // 0.3
3212 APFloat f2(APFloat::IEEEdouble(), "0x1.47ae147ae147bp-7"); // 0.01
3213 APFloat expected(APFloat::IEEEdouble(),
3214 "0x1.47ae147ae1471p-7"); // 0.009999999999999983
3215 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3216 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3217 }
3218 {
3219 APFloat f1(APFloat::IEEEdouble(), "0x1p64"); // 1.8446744073709552e19
3220 APFloat f2(APFloat::IEEEdouble(), "1.5");
3221 APFloat expected(APFloat::IEEEdouble(), "1.0");
3222 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3223 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3224 }
3225 {
3226 APFloat f1(APFloat::IEEEdouble(), "0x1p1000");
3227 APFloat f2(APFloat::IEEEdouble(), "0x1p-1000");
3228 APFloat expected(APFloat::IEEEdouble(), "0.0");
3229 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3230 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3231 }
3232 {
3233 APFloat f1(APFloat::IEEEdouble(), "0.0");
3234 APFloat f2(APFloat::IEEEdouble(), "1.0");
3235 APFloat expected(APFloat::IEEEdouble(), "0.0");
3236 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3237 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3238 }
3239 {
3240 APFloat f1(APFloat::IEEEdouble(), "1.0");
3241 APFloat f2(APFloat::IEEEdouble(), "0.0");
3242 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3243 EXPECT_TRUE(f1.isNaN());
3244 }
3245 {
3246 APFloat f1(APFloat::IEEEdouble(), "0.0");
3247 APFloat f2(APFloat::IEEEdouble(), "0.0");
3248 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3249 EXPECT_TRUE(f1.isNaN());
3250 }
3251 {
3252 APFloat f1 = APFloat::getInf(APFloat::IEEEdouble(), false);
3253 APFloat f2(APFloat::IEEEdouble(), "1.0");
3254 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3255 EXPECT_TRUE(f1.isNaN());
3256 }
3257}
3258
Tim Shen44bde892016-12-12 21:59:30 +00003259TEST(APFloatTest, PPCDoubleDoubleAddSpecial) {
3260 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t,
Stephen Canon157c8692017-03-31 20:31:33 +00003261 APFloat::fltCategory, APFloat::roundingMode>; DataType Data[] = {
Tim Shen44bde892016-12-12 21:59:30 +00003262 // (1 + 0) + (-1 + 0) = fcZero
Tim Shen18e7ae62016-12-12 22:16:08 +00003263 std::make_tuple(0x3ff0000000000000ull, 0, 0xbff0000000000000ull, 0,
3264 APFloat::fcZero, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003265 // LDBL_MAX + (1.1 >> (1023 - 106) + 0)) = fcInfinity
Tim Shen18e7ae62016-12-12 22:16:08 +00003266 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3267 0x7948000000000000ull, 0ull, APFloat::fcInfinity,
3268 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003269 // TODO: change the 4th 0x75effffffffffffe to 0x75efffffffffffff when
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003270 // semPPCDoubleDoubleLegacy is gone.
Tim Shen44bde892016-12-12 21:59:30 +00003271 // LDBL_MAX + (1.011111... >> (1023 - 106) + (1.1111111...0 >> (1023 -
3272 // 160))) = fcNormal
Tim Shen18e7ae62016-12-12 22:16:08 +00003273 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3274 0x7947ffffffffffffull, 0x75effffffffffffeull,
3275 APFloat::fcNormal, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003276 // LDBL_MAX + (1.1 >> (1023 - 106) + 0)) = fcInfinity
Tim Shen18e7ae62016-12-12 22:16:08 +00003277 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3278 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3279 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003280 // NaN + (1 + 0) = fcNaN
Tim Shen18e7ae62016-12-12 22:16:08 +00003281 std::make_tuple(0x7ff8000000000000ull, 0, 0x3ff0000000000000ull, 0,
3282 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003283 };
3284
3285 for (auto Tp : Data) {
3286 uint64_t Op1[2], Op2[2];
3287 APFloat::fltCategory Expected;
3288 APFloat::roundingMode RM;
3289 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected, RM) = Tp;
3290
Tim Shen7f127622017-01-24 00:19:45 +00003291 {
3292 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3293 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3294 A1.add(A2, RM);
Tim Shen44bde892016-12-12 21:59:30 +00003295
Tim Shen7f127622017-01-24 00:19:45 +00003296 EXPECT_EQ(Expected, A1.getCategory())
3297 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
3298 Op2[0], Op2[1])
3299 .str();
3300 }
3301 {
3302 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3303 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3304 A2.add(A1, RM);
3305
3306 EXPECT_EQ(Expected, A2.getCategory())
3307 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
3308 Op1[0], Op1[1])
3309 .str();
3310 }
Tim Shen44bde892016-12-12 21:59:30 +00003311 }
3312}
3313
3314TEST(APFloatTest, PPCDoubleDoubleAdd) {
3315 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
3316 uint64_t, APFloat::roundingMode>;
3317 DataType Data[] = {
3318 // (1 + 0) + (1e-105 + 0) = (1 + 1e-105)
Tim Shen18e7ae62016-12-12 22:16:08 +00003319 std::make_tuple(0x3ff0000000000000ull, 0, 0x3960000000000000ull, 0,
3320 0x3ff0000000000000ull, 0x3960000000000000ull,
3321 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003322 // (1 + 0) + (1e-106 + 0) = (1 + 1e-106)
Tim Shen18e7ae62016-12-12 22:16:08 +00003323 std::make_tuple(0x3ff0000000000000ull, 0, 0x3950000000000000ull, 0,
3324 0x3ff0000000000000ull, 0x3950000000000000ull,
3325 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003326 // (1 + 1e-106) + (1e-106 + 0) = (1 + 1e-105)
Tim Shen18e7ae62016-12-12 22:16:08 +00003327 std::make_tuple(0x3ff0000000000000ull, 0x3950000000000000ull,
3328 0x3950000000000000ull, 0, 0x3ff0000000000000ull,
3329 0x3960000000000000ull, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003330 // (1 + 0) + (epsilon + 0) = (1 + epsilon)
Tim Shen18e7ae62016-12-12 22:16:08 +00003331 std::make_tuple(0x3ff0000000000000ull, 0, 0x0000000000000001ull, 0,
3332 0x3ff0000000000000ull, 0x0000000000000001ull,
3333 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003334 // TODO: change 0xf950000000000000 to 0xf940000000000000, when
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003335 // semPPCDoubleDoubleLegacy is gone.
Tim Shen44bde892016-12-12 21:59:30 +00003336 // (DBL_MAX - 1 << (1023 - 105)) + (1 << (1023 - 53) + 0) = DBL_MAX +
3337 // 1.11111... << (1023 - 52)
Tim Shen18e7ae62016-12-12 22:16:08 +00003338 std::make_tuple(0x7fefffffffffffffull, 0xf950000000000000ull,
3339 0x7c90000000000000ull, 0, 0x7fefffffffffffffull,
3340 0x7c8ffffffffffffeull, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003341 // TODO: change 0xf950000000000000 to 0xf940000000000000, when
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003342 // semPPCDoubleDoubleLegacy is gone.
Tim Shen44bde892016-12-12 21:59:30 +00003343 // (1 << (1023 - 53) + 0) + (DBL_MAX - 1 << (1023 - 105)) = DBL_MAX +
3344 // 1.11111... << (1023 - 52)
Tim Shen18e7ae62016-12-12 22:16:08 +00003345 std::make_tuple(0x7c90000000000000ull, 0, 0x7fefffffffffffffull,
3346 0xf950000000000000ull, 0x7fefffffffffffffull,
3347 0x7c8ffffffffffffeull, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003348 };
3349
3350 for (auto Tp : Data) {
3351 uint64_t Op1[2], Op2[2], Expected[2];
3352 APFloat::roundingMode RM;
3353 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
3354
Tim Shen7f127622017-01-24 00:19:45 +00003355 {
3356 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3357 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3358 A1.add(A2, RM);
Tim Shen44bde892016-12-12 21:59:30 +00003359
Tim Shen7f127622017-01-24 00:19:45 +00003360 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3361 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
3362 Op2[0], Op2[1])
3363 .str();
3364 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3365 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
3366 Op2[0], Op2[1])
3367 .str();
3368 }
3369 {
3370 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3371 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3372 A2.add(A1, RM);
3373
3374 EXPECT_EQ(Expected[0], A2.bitcastToAPInt().getRawData()[0])
3375 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
3376 Op1[0], Op1[1])
3377 .str();
3378 EXPECT_EQ(Expected[1], A2.bitcastToAPInt().getRawData()[1])
3379 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
3380 Op1[0], Op1[1])
3381 .str();
3382 }
Tim Shen44bde892016-12-12 21:59:30 +00003383 }
3384}
3385
3386TEST(APFloatTest, PPCDoubleDoubleSubtract) {
3387 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
3388 uint64_t, APFloat::roundingMode>;
3389 DataType Data[] = {
3390 // (1 + 0) - (-1e-105 + 0) = (1 + 1e-105)
Tim Shen18e7ae62016-12-12 22:16:08 +00003391 std::make_tuple(0x3ff0000000000000ull, 0, 0xb960000000000000ull, 0,
3392 0x3ff0000000000000ull, 0x3960000000000000ull,
3393 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003394 // (1 + 0) - (-1e-106 + 0) = (1 + 1e-106)
Tim Shen18e7ae62016-12-12 22:16:08 +00003395 std::make_tuple(0x3ff0000000000000ull, 0, 0xb950000000000000ull, 0,
3396 0x3ff0000000000000ull, 0x3950000000000000ull,
3397 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003398 };
3399
3400 for (auto Tp : Data) {
3401 uint64_t Op1[2], Op2[2], Expected[2];
3402 APFloat::roundingMode RM;
3403 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
3404
Stephan Bergmann7d94d542016-12-14 12:11:35 +00003405 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3406 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
Tim Shen44bde892016-12-12 21:59:30 +00003407 A1.subtract(A2, RM);
3408
Tim Shen53f14c72016-12-16 00:47:17 +00003409 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3410 << formatv("({0:x} + {1:x}) - ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
3411 Op2[1])
3412 .str();
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003413 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
Tim Shen53f14c72016-12-16 00:47:17 +00003414 << formatv("({0:x} + {1:x}) - ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
3415 Op2[1])
3416 .str();
Tim Shen44bde892016-12-12 21:59:30 +00003417 }
3418}
Tim Shen1594e062017-01-05 22:57:54 +00003419
Tim Shen7f127622017-01-24 00:19:45 +00003420TEST(APFloatTest, PPCDoubleDoubleMultiplySpecial) {
3421 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t,
3422 APFloat::fltCategory, APFloat::roundingMode>;
3423 DataType Data[] = {
3424 // fcNaN * fcNaN = fcNaN
3425 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0,
3426 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
3427 // fcNaN * fcZero = fcNaN
3428 std::make_tuple(0x7ff8000000000000ull, 0, 0, 0, APFloat::fcNaN,
3429 APFloat::rmNearestTiesToEven),
3430 // fcNaN * fcInfinity = fcNaN
3431 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff0000000000000ull, 0,
3432 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
3433 // fcNaN * fcNormal = fcNaN
3434 std::make_tuple(0x7ff8000000000000ull, 0, 0x3ff0000000000000ull, 0,
3435 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
3436 // fcInfinity * fcInfinity = fcInfinity
3437 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0,
3438 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
3439 // fcInfinity * fcZero = fcNaN
3440 std::make_tuple(0x7ff0000000000000ull, 0, 0, 0, APFloat::fcNaN,
3441 APFloat::rmNearestTiesToEven),
3442 // fcInfinity * fcNormal = fcInfinity
3443 std::make_tuple(0x7ff0000000000000ull, 0, 0x3ff0000000000000ull, 0,
3444 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
3445 // fcZero * fcZero = fcZero
3446 std::make_tuple(0, 0, 0, 0, APFloat::fcZero,
3447 APFloat::rmNearestTiesToEven),
3448 // fcZero * fcNormal = fcZero
3449 std::make_tuple(0, 0, 0x3ff0000000000000ull, 0, APFloat::fcZero,
3450 APFloat::rmNearestTiesToEven),
3451 };
3452
3453 for (auto Tp : Data) {
3454 uint64_t Op1[2], Op2[2];
3455 APFloat::fltCategory Expected;
3456 APFloat::roundingMode RM;
3457 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected, RM) = Tp;
3458
3459 {
3460 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3461 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3462 A1.multiply(A2, RM);
3463
3464 EXPECT_EQ(Expected, A1.getCategory())
3465 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
3466 Op2[0], Op2[1])
3467 .str();
3468 }
3469 {
3470 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3471 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3472 A2.multiply(A1, RM);
3473
3474 EXPECT_EQ(Expected, A2.getCategory())
3475 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
3476 Op1[0], Op1[1])
3477 .str();
3478 }
3479 }
3480}
3481
Tim Shen1594e062017-01-05 22:57:54 +00003482TEST(APFloatTest, PPCDoubleDoubleMultiply) {
3483 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
3484 uint64_t, APFloat::roundingMode>;
Tim Shen1594e062017-01-05 22:57:54 +00003485 DataType Data[] = {
3486 // 1/3 * 3 = 1.0
3487 std::make_tuple(0x3fd5555555555555ull, 0x3c75555555555556ull,
3488 0x4008000000000000ull, 0, 0x3ff0000000000000ull, 0,
3489 APFloat::rmNearestTiesToEven),
Tim Shen7f127622017-01-24 00:19:45 +00003490 // (1 + epsilon) * (1 + 0) = fcZero
3491 std::make_tuple(0x3ff0000000000000ull, 0x0000000000000001ull,
3492 0x3ff0000000000000ull, 0, 0x3ff0000000000000ull,
3493 0x0000000000000001ull, APFloat::rmNearestTiesToEven),
3494 // (1 + epsilon) * (1 + epsilon) = 1 + 2 * epsilon
3495 std::make_tuple(0x3ff0000000000000ull, 0x0000000000000001ull,
3496 0x3ff0000000000000ull, 0x0000000000000001ull,
3497 0x3ff0000000000000ull, 0x0000000000000002ull,
3498 APFloat::rmNearestTiesToEven),
3499 // -(1 + epsilon) * (1 + epsilon) = -1
3500 std::make_tuple(0xbff0000000000000ull, 0x0000000000000001ull,
3501 0x3ff0000000000000ull, 0x0000000000000001ull,
3502 0xbff0000000000000ull, 0, APFloat::rmNearestTiesToEven),
3503 // (0.5 + 0) * (1 + 2 * epsilon) = 0.5 + epsilon
3504 std::make_tuple(0x3fe0000000000000ull, 0, 0x3ff0000000000000ull,
3505 0x0000000000000002ull, 0x3fe0000000000000ull,
3506 0x0000000000000001ull, APFloat::rmNearestTiesToEven),
3507 // (0.5 + 0) * (1 + epsilon) = 0.5
3508 std::make_tuple(0x3fe0000000000000ull, 0, 0x3ff0000000000000ull,
3509 0x0000000000000001ull, 0x3fe0000000000000ull, 0,
3510 APFloat::rmNearestTiesToEven),
3511 // __LDBL_MAX__ * (1 + 1 << 106) = inf
3512 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3513 0x3ff0000000000000ull, 0x3950000000000000ull,
3514 0x7ff0000000000000ull, 0, APFloat::rmNearestTiesToEven),
3515 // __LDBL_MAX__ * (1 + 1 << 107) > __LDBL_MAX__, but not inf, yes =_=|||
3516 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3517 0x3ff0000000000000ull, 0x3940000000000000ull,
3518 0x7fefffffffffffffull, 0x7c8fffffffffffffull,
3519 APFloat::rmNearestTiesToEven),
3520 // __LDBL_MAX__ * (1 + 1 << 108) = __LDBL_MAX__
3521 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3522 0x3ff0000000000000ull, 0x3930000000000000ull,
3523 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3524 APFloat::rmNearestTiesToEven),
Tim Shen1594e062017-01-05 22:57:54 +00003525 };
3526
3527 for (auto Tp : Data) {
3528 uint64_t Op1[2], Op2[2], Expected[2];
3529 APFloat::roundingMode RM;
3530 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
3531
Tim Shen7f127622017-01-24 00:19:45 +00003532 {
3533 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3534 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3535 A1.multiply(A2, RM);
Tim Shen1594e062017-01-05 22:57:54 +00003536
Tim Shen7f127622017-01-24 00:19:45 +00003537 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3538 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
3539 Op2[0], Op2[1])
3540 .str();
3541 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3542 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
3543 Op2[0], Op2[1])
3544 .str();
3545 }
3546 {
3547 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3548 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3549 A2.multiply(A1, RM);
3550
3551 EXPECT_EQ(Expected[0], A2.bitcastToAPInt().getRawData()[0])
3552 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
3553 Op1[0], Op1[1])
3554 .str();
3555 EXPECT_EQ(Expected[1], A2.bitcastToAPInt().getRawData()[1])
3556 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
3557 Op1[0], Op1[1])
3558 .str();
3559 }
Tim Shen1594e062017-01-05 22:57:54 +00003560 }
3561}
3562
3563TEST(APFloatTest, PPCDoubleDoubleDivide) {
3564 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
3565 uint64_t, APFloat::roundingMode>;
3566 // TODO: Only a sanity check for now. Add more edge cases when the
3567 // double-double algorithm is implemented.
3568 DataType Data[] = {
3569 // 1 / 3 = 1/3
3570 std::make_tuple(0x3ff0000000000000ull, 0, 0x4008000000000000ull, 0,
3571 0x3fd5555555555555ull, 0x3c75555555555556ull,
3572 APFloat::rmNearestTiesToEven),
3573 };
3574
3575 for (auto Tp : Data) {
3576 uint64_t Op1[2], Op2[2], Expected[2];
3577 APFloat::roundingMode RM;
3578 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
3579
3580 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3581 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3582 A1.divide(A2, RM);
3583
3584 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3585 << formatv("({0:x} + {1:x}) / ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
3586 Op2[1])
3587 .str();
3588 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3589 << formatv("({0:x} + {1:x}) / ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
3590 Op2[1])
3591 .str();
3592 }
3593}
3594
3595TEST(APFloatTest, PPCDoubleDoubleRemainder) {
3596 using DataType =
3597 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t, uint64_t>;
3598 DataType Data[] = {
3599 // remainder(3.0 + 3.0 << 53, 1.25 + 1.25 << 53) = (0.5 + 0.5 << 53)
3600 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
3601 0x3ff4000000000000ull, 0x3ca4000000000000ull,
3602 0x3fe0000000000000ull, 0x3c90000000000000ull),
3603 // remainder(3.0 + 3.0 << 53, 1.75 + 1.75 << 53) = (-0.5 - 0.5 << 53)
3604 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
3605 0x3ffc000000000000ull, 0x3cac000000000000ull,
3606 0xbfe0000000000000ull, 0xbc90000000000000ull),
3607 };
3608
3609 for (auto Tp : Data) {
3610 uint64_t Op1[2], Op2[2], Expected[2];
3611 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1]) = Tp;
3612
3613 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3614 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3615 A1.remainder(A2);
3616
3617 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3618 << formatv("remainder({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
3619 Op2[0], Op2[1])
3620 .str();
3621 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3622 << formatv("remainder(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0],
3623 Op1[1], Op2[0], Op2[1])
3624 .str();
3625 }
3626}
3627
3628TEST(APFloatTest, PPCDoubleDoubleMod) {
3629 using DataType =
3630 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t, uint64_t>;
3631 DataType Data[] = {
3632 // mod(3.0 + 3.0 << 53, 1.25 + 1.25 << 53) = (0.5 + 0.5 << 53)
3633 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
3634 0x3ff4000000000000ull, 0x3ca4000000000000ull,
3635 0x3fe0000000000000ull, 0x3c90000000000000ull),
3636 // mod(3.0 + 3.0 << 53, 1.75 + 1.75 << 53) = (1.25 + 1.25 << 53)
3637 // 0xbc98000000000000 doesn't seem right, but it's what we currently have.
3638 // TODO: investigate
3639 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
3640 0x3ffc000000000000ull, 0x3cac000000000000ull,
3641 0x3ff4000000000001ull, 0xbc98000000000000ull),
3642 };
3643
3644 for (auto Tp : Data) {
3645 uint64_t Op1[2], Op2[2], Expected[2];
3646 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1]) = Tp;
3647
3648 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3649 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3650 A1.mod(A2);
3651
3652 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3653 << formatv("fmod(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
3654 Op2[0], Op2[1])
3655 .str();
3656 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3657 << formatv("fmod(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
3658 Op2[0], Op2[1])
3659 .str();
3660 }
3661}
3662
3663TEST(APFloatTest, PPCDoubleDoubleFMA) {
3664 // Sanity check for now.
3665 APFloat A(APFloat::PPCDoubleDouble(), "2");
3666 A.fusedMultiplyAdd(APFloat(APFloat::PPCDoubleDouble(), "3"),
3667 APFloat(APFloat::PPCDoubleDouble(), "4"),
3668 APFloat::rmNearestTiesToEven);
3669 EXPECT_EQ(APFloat::cmpEqual,
3670 APFloat(APFloat::PPCDoubleDouble(), "10").compare(A));
3671}
3672
3673TEST(APFloatTest, PPCDoubleDoubleRoundToIntegral) {
3674 {
3675 APFloat A(APFloat::PPCDoubleDouble(), "1.5");
3676 A.roundToIntegral(APFloat::rmNearestTiesToEven);
3677 EXPECT_EQ(APFloat::cmpEqual,
3678 APFloat(APFloat::PPCDoubleDouble(), "2").compare(A));
3679 }
3680 {
3681 APFloat A(APFloat::PPCDoubleDouble(), "2.5");
3682 A.roundToIntegral(APFloat::rmNearestTiesToEven);
3683 EXPECT_EQ(APFloat::cmpEqual,
3684 APFloat(APFloat::PPCDoubleDouble(), "2").compare(A));
3685 }
3686}
3687
3688TEST(APFloatTest, PPCDoubleDoubleCompare) {
3689 using DataType =
3690 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, APFloat::cmpResult>;
3691
3692 DataType Data[] = {
3693 // (1 + 0) = (1 + 0)
3694 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000000ull, 0,
3695 APFloat::cmpEqual),
3696 // (1 + 0) < (1.00...1 + 0)
3697 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull, 0,
3698 APFloat::cmpLessThan),
3699 // (1.00...1 + 0) > (1 + 0)
3700 std::make_tuple(0x3ff0000000000001ull, 0, 0x3ff0000000000000ull, 0,
3701 APFloat::cmpGreaterThan),
3702 // (1 + 0) < (1 + epsilon)
3703 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull,
3704 0x0000000000000001ull, APFloat::cmpLessThan),
3705 // NaN != NaN
3706 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0,
3707 APFloat::cmpUnordered),
3708 // (1 + 0) != NaN
3709 std::make_tuple(0x3ff0000000000000ull, 0, 0x7ff8000000000000ull, 0,
3710 APFloat::cmpUnordered),
3711 // Inf = Inf
3712 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0,
3713 APFloat::cmpEqual),
3714 };
3715
3716 for (auto Tp : Data) {
3717 uint64_t Op1[2], Op2[2];
3718 APFloat::cmpResult Expected;
3719 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected) = Tp;
3720
3721 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3722 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3723 EXPECT_EQ(Expected, A1.compare(A2))
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003724 << formatv("compare(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
3725 Op2[0], Op2[1])
3726 .str();
3727 }
3728}
3729
3730TEST(APFloatTest, PPCDoubleDoubleBitwiseIsEqual) {
3731 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, bool>;
3732
3733 DataType Data[] = {
3734 // (1 + 0) = (1 + 0)
3735 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000000ull, 0, true),
3736 // (1 + 0) != (1.00...1 + 0)
3737 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull, 0,
3738 false),
3739 // NaN = NaN
3740 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0, true),
3741 // NaN != NaN with a different bit pattern
3742 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull,
3743 0x3ff0000000000000ull, false),
3744 // Inf = Inf
3745 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0, true),
3746 };
3747
3748 for (auto Tp : Data) {
3749 uint64_t Op1[2], Op2[2];
3750 bool Expected;
3751 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected) = Tp;
3752
3753 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3754 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3755 EXPECT_EQ(Expected, A1.bitwiseIsEqual(A2))
3756 << formatv("({0:x} + {1:x}) = ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
Tim Shen1594e062017-01-05 22:57:54 +00003757 Op2[1])
3758 .str();
3759 }
3760}
3761
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003762TEST(APFloatTest, PPCDoubleDoubleHashValue) {
3763 uint64_t Data1[] = {0x3ff0000000000001ull, 0x0000000000000001ull};
3764 uint64_t Data2[] = {0x3ff0000000000001ull, 0};
3765 // The hash values are *hopefully* different.
3766 EXPECT_NE(
3767 hash_value(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data1))),
3768 hash_value(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data2))));
3769}
3770
Tim Shen1594e062017-01-05 22:57:54 +00003771TEST(APFloatTest, PPCDoubleDoubleChangeSign) {
3772 uint64_t Data[] = {
3773 0x400f000000000000ull, 0xbcb0000000000000ull,
3774 };
3775 APFloat Float(APFloat::PPCDoubleDouble(), APInt(128, 2, Data));
3776 {
3777 APFloat Actual =
3778 APFloat::copySign(Float, APFloat(APFloat::IEEEdouble(), "1"));
3779 EXPECT_EQ(0x400f000000000000ull, Actual.bitcastToAPInt().getRawData()[0]);
3780 EXPECT_EQ(0xbcb0000000000000ull, Actual.bitcastToAPInt().getRawData()[1]);
3781 }
3782 {
3783 APFloat Actual =
3784 APFloat::copySign(Float, APFloat(APFloat::IEEEdouble(), "-1"));
3785 EXPECT_EQ(0xc00f000000000000ull, Actual.bitcastToAPInt().getRawData()[0]);
3786 EXPECT_EQ(0x3cb0000000000000ull, Actual.bitcastToAPInt().getRawData()[1]);
3787 }
3788}
3789
3790TEST(APFloatTest, PPCDoubleDoubleFactories) {
3791 {
3792 uint64_t Data[] = {
3793 0, 0,
3794 };
3795 EXPECT_EQ(APInt(128, 2, Data),
3796 APFloat::getZero(APFloat::PPCDoubleDouble()).bitcastToAPInt());
3797 }
3798 {
3799 uint64_t Data[] = {
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003800 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3801 };
3802 EXPECT_EQ(APInt(128, 2, Data),
3803 APFloat::getLargest(APFloat::PPCDoubleDouble()).bitcastToAPInt());
3804 }
3805 {
3806 uint64_t Data[] = {
Tim Shen1594e062017-01-05 22:57:54 +00003807 0x0000000000000001ull, 0,
3808 };
3809 EXPECT_EQ(
3810 APInt(128, 2, Data),
3811 APFloat::getSmallest(APFloat::PPCDoubleDouble()).bitcastToAPInt());
3812 }
3813 {
3814 uint64_t Data[] = {0x0360000000000000ull, 0};
3815 EXPECT_EQ(APInt(128, 2, Data),
3816 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble())
3817 .bitcastToAPInt());
3818 }
3819 {
3820 uint64_t Data[] = {
3821 0x8000000000000000ull, 0x0000000000000000ull,
3822 };
3823 EXPECT_EQ(
3824 APInt(128, 2, Data),
3825 APFloat::getZero(APFloat::PPCDoubleDouble(), true).bitcastToAPInt());
3826 }
3827 {
3828 uint64_t Data[] = {
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003829 0xffefffffffffffffull, 0xfc8ffffffffffffeull,
3830 };
3831 EXPECT_EQ(
3832 APInt(128, 2, Data),
3833 APFloat::getLargest(APFloat::PPCDoubleDouble(), true).bitcastToAPInt());
3834 }
3835 {
3836 uint64_t Data[] = {
Tim Shen1594e062017-01-05 22:57:54 +00003837 0x8000000000000001ull, 0x0000000000000000ull,
3838 };
3839 EXPECT_EQ(APInt(128, 2, Data),
3840 APFloat::getSmallest(APFloat::PPCDoubleDouble(), true)
3841 .bitcastToAPInt());
3842 }
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003843 {
3844 uint64_t Data[] = {
3845 0x8360000000000000ull, 0x0000000000000000ull,
3846 };
3847 EXPECT_EQ(APInt(128, 2, Data),
3848 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble(), true)
3849 .bitcastToAPInt());
3850 }
Tim Shen1594e062017-01-05 22:57:54 +00003851 EXPECT_TRUE(APFloat::getSmallest(APFloat::PPCDoubleDouble()).isSmallest());
3852 EXPECT_TRUE(APFloat::getLargest(APFloat::PPCDoubleDouble()).isLargest());
3853}
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003854
3855TEST(APFloatTest, PPCDoubleDoubleIsDenormal) {
3856 EXPECT_TRUE(APFloat::getSmallest(APFloat::PPCDoubleDouble()).isDenormal());
3857 EXPECT_FALSE(APFloat::getLargest(APFloat::PPCDoubleDouble()).isDenormal());
3858 EXPECT_FALSE(
3859 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble()).isDenormal());
3860 {
3861 // (4 + 3) is not normalized
3862 uint64_t Data[] = {
3863 0x4010000000000000ull, 0x4008000000000000ull,
3864 };
3865 EXPECT_TRUE(
3866 APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data)).isDenormal());
3867 }
3868}
3869
3870TEST(APFloatTest, PPCDoubleDoubleScalbn) {
3871 // 3.0 + 3.0 << 53
3872 uint64_t Input[] = {
3873 0x4008000000000000ull, 0x3cb8000000000000ull,
3874 };
3875 APFloat Result =
3876 scalbn(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Input)), 1,
3877 APFloat::rmNearestTiesToEven);
3878 // 6.0 + 6.0 << 53
3879 EXPECT_EQ(0x4018000000000000ull, Result.bitcastToAPInt().getRawData()[0]);
3880 EXPECT_EQ(0x3cc8000000000000ull, Result.bitcastToAPInt().getRawData()[1]);
3881}
3882
3883TEST(APFloatTest, PPCDoubleDoubleFrexp) {
3884 // 3.0 + 3.0 << 53
3885 uint64_t Input[] = {
3886 0x4008000000000000ull, 0x3cb8000000000000ull,
3887 };
3888 int Exp;
3889 // 0.75 + 0.75 << 53
3890 APFloat Result =
3891 frexp(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Input)), Exp,
3892 APFloat::rmNearestTiesToEven);
3893 EXPECT_EQ(2, Exp);
3894 EXPECT_EQ(0x3fe8000000000000ull, Result.bitcastToAPInt().getRawData()[0]);
3895 EXPECT_EQ(0x3c98000000000000ull, Result.bitcastToAPInt().getRawData()[1]);
3896}
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00003897}