blob: 69da089f172b464fba89dd05fc86f0a7222c11b8 [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
Serguei Katkov3a46eb42017-04-21 02:52:17 +000030static std::string convertToString(double d, unsigned Prec, unsigned Pad,
31 bool Tr = true) {
John McCall29b5c282009-12-24 08:56:26 +000032 llvm::SmallVector<char, 100> Buffer;
33 llvm::APFloat F(d);
Serguei Katkov3a46eb42017-04-21 02:52:17 +000034 F.toString(Buffer, Prec, Pad, Tr);
John McCall29b5c282009-12-24 08:56:26 +000035 return std::string(Buffer.data(), Buffer.size());
36}
37
Erick Tryzelaar19f63b22009-08-16 23:36:19 +000038namespace {
39
Michael Gottesman0c622ea2013-05-30 18:07:13 +000040TEST(APFloatTest, isSignaling) {
41 // We test qNaN, -qNaN, +sNaN, -sNaN with and without payloads. *NOTE* The
42 // positive/negative distinction is included only since the getQNaN/getSNaN
43 // API provides the option.
44 APInt payload = APInt::getOneBitSet(4, 2);
Stephan Bergmann17c7f702016-12-14 11:57:17 +000045 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), false).isSignaling());
46 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), true).isSignaling());
47 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), false, &payload).isSignaling());
48 EXPECT_FALSE(APFloat::getQNaN(APFloat::IEEEsingle(), true, &payload).isSignaling());
49 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isSignaling());
50 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isSignaling());
51 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false, &payload).isSignaling());
52 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true, &payload).isSignaling());
Michael Gottesman0c622ea2013-05-30 18:07:13 +000053}
54
55TEST(APFloatTest, next) {
56
Stephan Bergmann17c7f702016-12-14 11:57:17 +000057 APFloat test(APFloat::IEEEquad(), APFloat::uninitialized);
58 APFloat expected(APFloat::IEEEquad(), APFloat::uninitialized);
Michael Gottesman0c622ea2013-05-30 18:07:13 +000059
60 // 1. Test Special Cases Values.
61 //
62 // Test all special values for nextUp and nextDown perscribed by IEEE-754R
63 // 2008. These are:
64 // 1. +inf
65 // 2. -inf
66 // 3. getLargest()
67 // 4. -getLargest()
68 // 5. getSmallest()
69 // 6. -getSmallest()
70 // 7. qNaN
71 // 8. sNaN
72 // 9. +0
73 // 10. -0
74
75 // nextUp(+inf) = +inf.
Stephan Bergmann17c7f702016-12-14 11:57:17 +000076 test = APFloat::getInf(APFloat::IEEEquad(), false);
77 expected = APFloat::getInf(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +000078 EXPECT_EQ(test.next(false), APFloat::opOK);
79 EXPECT_TRUE(test.isInfinity());
80 EXPECT_TRUE(!test.isNegative());
81 EXPECT_TRUE(test.bitwiseIsEqual(expected));
82
83 // nextDown(+inf) = -nextUp(-inf) = -(-getLargest()) = getLargest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +000084 test = APFloat::getInf(APFloat::IEEEquad(), false);
85 expected = APFloat::getLargest(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +000086 EXPECT_EQ(test.next(true), APFloat::opOK);
87 EXPECT_TRUE(!test.isNegative());
88 EXPECT_TRUE(test.bitwiseIsEqual(expected));
89
90 // nextUp(-inf) = -getLargest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +000091 test = APFloat::getInf(APFloat::IEEEquad(), true);
92 expected = APFloat::getLargest(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +000093 EXPECT_EQ(test.next(false), APFloat::opOK);
94 EXPECT_TRUE(test.isNegative());
95 EXPECT_TRUE(test.bitwiseIsEqual(expected));
96
97 // nextDown(-inf) = -nextUp(+inf) = -(+inf) = -inf.
Stephan Bergmann17c7f702016-12-14 11:57:17 +000098 test = APFloat::getInf(APFloat::IEEEquad(), true);
99 expected = APFloat::getInf(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000100 EXPECT_EQ(test.next(true), APFloat::opOK);
101 EXPECT_TRUE(test.isInfinity() && test.isNegative());
102 EXPECT_TRUE(test.bitwiseIsEqual(expected));
103
104 // nextUp(getLargest()) = +inf
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000105 test = APFloat::getLargest(APFloat::IEEEquad(), false);
106 expected = APFloat::getInf(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000107 EXPECT_EQ(test.next(false), APFloat::opOK);
108 EXPECT_TRUE(test.isInfinity() && !test.isNegative());
109 EXPECT_TRUE(test.bitwiseIsEqual(expected));
110
111 // nextDown(getLargest()) = -nextUp(-getLargest())
112 // = -(-getLargest() + inc)
113 // = getLargest() - inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000114 test = APFloat::getLargest(APFloat::IEEEquad(), false);
115 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000116 "0x1.fffffffffffffffffffffffffffep+16383");
117 EXPECT_EQ(test.next(true), APFloat::opOK);
118 EXPECT_TRUE(!test.isInfinity() && !test.isNegative());
119 EXPECT_TRUE(test.bitwiseIsEqual(expected));
120
121 // nextUp(-getLargest()) = -getLargest() + inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000122 test = APFloat::getLargest(APFloat::IEEEquad(), true);
123 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000124 "-0x1.fffffffffffffffffffffffffffep+16383");
125 EXPECT_EQ(test.next(false), APFloat::opOK);
126 EXPECT_TRUE(test.bitwiseIsEqual(expected));
127
128 // nextDown(-getLargest()) = -nextUp(getLargest()) = -(inf) = -inf.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000129 test = APFloat::getLargest(APFloat::IEEEquad(), true);
130 expected = APFloat::getInf(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000131 EXPECT_EQ(test.next(true), APFloat::opOK);
132 EXPECT_TRUE(test.isInfinity() && test.isNegative());
133 EXPECT_TRUE(test.bitwiseIsEqual(expected));
134
135 // nextUp(getSmallest()) = getSmallest() + inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000136 test = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
137 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000138 "0x0.0000000000000000000000000002p-16382");
139 EXPECT_EQ(test.next(false), APFloat::opOK);
140 EXPECT_TRUE(test.bitwiseIsEqual(expected));
141
142 // nextDown(getSmallest()) = -nextUp(-getSmallest()) = -(-0) = +0.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000143 test = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
144 expected = APFloat::getZero(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000145 EXPECT_EQ(test.next(true), APFloat::opOK);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +0000146 EXPECT_TRUE(test.isPosZero());
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000147 EXPECT_TRUE(test.bitwiseIsEqual(expected));
148
149 // nextUp(-getSmallest()) = -0.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000150 test = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
151 expected = APFloat::getZero(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000152 EXPECT_EQ(test.next(false), APFloat::opOK);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +0000153 EXPECT_TRUE(test.isNegZero());
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000154 EXPECT_TRUE(test.bitwiseIsEqual(expected));
155
156 // nextDown(-getSmallest()) = -nextUp(getSmallest()) = -getSmallest() - inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000157 test = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
158 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000159 "-0x0.0000000000000000000000000002p-16382");
160 EXPECT_EQ(test.next(true), APFloat::opOK);
161 EXPECT_TRUE(test.bitwiseIsEqual(expected));
162
163 // nextUp(qNaN) = qNaN
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000164 test = APFloat::getQNaN(APFloat::IEEEquad(), false);
165 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000166 EXPECT_EQ(test.next(false), APFloat::opOK);
167 EXPECT_TRUE(test.bitwiseIsEqual(expected));
168
169 // nextDown(qNaN) = qNaN
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000170 test = APFloat::getQNaN(APFloat::IEEEquad(), false);
171 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000172 EXPECT_EQ(test.next(true), APFloat::opOK);
173 EXPECT_TRUE(test.bitwiseIsEqual(expected));
174
175 // nextUp(sNaN) = qNaN
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000176 test = APFloat::getSNaN(APFloat::IEEEquad(), false);
177 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000178 EXPECT_EQ(test.next(false), APFloat::opInvalidOp);
179 EXPECT_TRUE(test.bitwiseIsEqual(expected));
180
181 // nextDown(sNaN) = qNaN
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000182 test = APFloat::getSNaN(APFloat::IEEEquad(), false);
183 expected = APFloat::getQNaN(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000184 EXPECT_EQ(test.next(true), APFloat::opInvalidOp);
185 EXPECT_TRUE(test.bitwiseIsEqual(expected));
186
187 // nextUp(+0) = +getSmallest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000188 test = APFloat::getZero(APFloat::IEEEquad(), false);
189 expected = APFloat::getSmallest(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000190 EXPECT_EQ(test.next(false), APFloat::opOK);
191 EXPECT_TRUE(test.bitwiseIsEqual(expected));
192
193 // nextDown(+0) = -nextUp(-0) = -getSmallest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000194 test = APFloat::getZero(APFloat::IEEEquad(), false);
195 expected = APFloat::getSmallest(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000196 EXPECT_EQ(test.next(true), APFloat::opOK);
197 EXPECT_TRUE(test.bitwiseIsEqual(expected));
198
199 // nextUp(-0) = +getSmallest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000200 test = APFloat::getZero(APFloat::IEEEquad(), true);
201 expected = APFloat::getSmallest(APFloat::IEEEquad(), false);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000202 EXPECT_EQ(test.next(false), APFloat::opOK);
203 EXPECT_TRUE(test.bitwiseIsEqual(expected));
204
205 // nextDown(-0) = -nextUp(0) = -getSmallest()
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000206 test = APFloat::getZero(APFloat::IEEEquad(), true);
207 expected = APFloat::getSmallest(APFloat::IEEEquad(), true);
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000208 EXPECT_EQ(test.next(true), APFloat::opOK);
209 EXPECT_TRUE(test.bitwiseIsEqual(expected));
210
211 // 2. Binade Boundary Tests.
212
213 // 2a. Test denormal <-> normal binade boundaries.
214 // * nextUp(+Largest Denormal) -> +Smallest Normal.
215 // * nextDown(-Largest Denormal) -> -Smallest Normal.
216 // * nextUp(-Smallest Normal) -> -Largest Denormal.
217 // * nextDown(+Smallest Normal) -> +Largest Denormal.
218
219 // nextUp(+Largest Denormal) -> +Smallest Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000220 test = APFloat(APFloat::IEEEquad(), "0x0.ffffffffffffffffffffffffffffp-16382");
221 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000222 "0x1.0000000000000000000000000000p-16382");
223 EXPECT_EQ(test.next(false), APFloat::opOK);
224 EXPECT_FALSE(test.isDenormal());
225 EXPECT_TRUE(test.bitwiseIsEqual(expected));
226
227 // nextDown(-Largest Denormal) -> -Smallest Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000228 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000229 "-0x0.ffffffffffffffffffffffffffffp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000230 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000231 "-0x1.0000000000000000000000000000p-16382");
232 EXPECT_EQ(test.next(true), APFloat::opOK);
233 EXPECT_FALSE(test.isDenormal());
234 EXPECT_TRUE(test.bitwiseIsEqual(expected));
235
236 // nextUp(-Smallest Normal) -> -LargestDenormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000237 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000238 "-0x1.0000000000000000000000000000p-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000239 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000240 "-0x0.ffffffffffffffffffffffffffffp-16382");
241 EXPECT_EQ(test.next(false), APFloat::opOK);
242 EXPECT_TRUE(test.isDenormal());
243 EXPECT_TRUE(test.bitwiseIsEqual(expected));
244
245 // nextDown(+Smallest Normal) -> +Largest Denormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000246 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000247 "+0x1.0000000000000000000000000000p-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000248 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000249 "+0x0.ffffffffffffffffffffffffffffp-16382");
250 EXPECT_EQ(test.next(true), APFloat::opOK);
251 EXPECT_TRUE(test.isDenormal());
252 EXPECT_TRUE(test.bitwiseIsEqual(expected));
253
254 // 2b. Test normal <-> normal binade boundaries.
255 // * nextUp(-Normal Binade Boundary) -> -Normal Binade Boundary + 1.
256 // * nextDown(+Normal Binade Boundary) -> +Normal Binade Boundary - 1.
257 // * nextUp(+Normal Binade Boundary - 1) -> +Normal Binade Boundary.
258 // * nextDown(-Normal Binade Boundary + 1) -> -Normal Binade Boundary.
259
260 // nextUp(-Normal Binade Boundary) -> -Normal Binade Boundary + 1.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000261 test = APFloat(APFloat::IEEEquad(), "-0x1p+1");
262 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000263 "-0x1.ffffffffffffffffffffffffffffp+0");
264 EXPECT_EQ(test.next(false), APFloat::opOK);
265 EXPECT_TRUE(test.bitwiseIsEqual(expected));
266
267 // nextDown(+Normal Binade Boundary) -> +Normal Binade Boundary - 1.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000268 test = APFloat(APFloat::IEEEquad(), "0x1p+1");
269 expected = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp+0");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000270 EXPECT_EQ(test.next(true), APFloat::opOK);
271 EXPECT_TRUE(test.bitwiseIsEqual(expected));
272
273 // nextUp(+Normal Binade Boundary - 1) -> +Normal Binade Boundary.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000274 test = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp+0");
275 expected = APFloat(APFloat::IEEEquad(), "0x1p+1");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000276 EXPECT_EQ(test.next(false), APFloat::opOK);
277 EXPECT_TRUE(test.bitwiseIsEqual(expected));
278
279 // nextDown(-Normal Binade Boundary + 1) -> -Normal Binade Boundary.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000280 test = APFloat(APFloat::IEEEquad(), "-0x1.ffffffffffffffffffffffffffffp+0");
281 expected = APFloat(APFloat::IEEEquad(), "-0x1p+1");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000282 EXPECT_EQ(test.next(true), APFloat::opOK);
283 EXPECT_TRUE(test.bitwiseIsEqual(expected));
284
285 // 2c. Test using next at binade boundaries with a direction away from the
286 // binade boundary. Away from denormal <-> normal boundaries.
287 //
288 // This is to make sure that even though we are at a binade boundary, since
289 // we are rounding away, we do not trigger the binade boundary code. Thus we
290 // test:
291 // * nextUp(-Largest Denormal) -> -Largest Denormal + inc.
292 // * nextDown(+Largest Denormal) -> +Largest Denormal - inc.
293 // * nextUp(+Smallest Normal) -> +Smallest Normal + inc.
294 // * nextDown(-Smallest Normal) -> -Smallest Normal - inc.
295
296 // nextUp(-Largest Denormal) -> -Largest Denormal + inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000297 test = APFloat(APFloat::IEEEquad(), "-0x0.ffffffffffffffffffffffffffffp-16382");
298 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000299 "-0x0.fffffffffffffffffffffffffffep-16382");
300 EXPECT_EQ(test.next(false), APFloat::opOK);
301 EXPECT_TRUE(test.isDenormal());
302 EXPECT_TRUE(test.isNegative());
303 EXPECT_TRUE(test.bitwiseIsEqual(expected));
304
305 // nextDown(+Largest Denormal) -> +Largest Denormal - inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000306 test = APFloat(APFloat::IEEEquad(), "0x0.ffffffffffffffffffffffffffffp-16382");
307 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000308 "0x0.fffffffffffffffffffffffffffep-16382");
309 EXPECT_EQ(test.next(true), APFloat::opOK);
310 EXPECT_TRUE(test.isDenormal());
311 EXPECT_TRUE(!test.isNegative());
312 EXPECT_TRUE(test.bitwiseIsEqual(expected));
313
314 // nextUp(+Smallest Normal) -> +Smallest Normal + inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000315 test = APFloat(APFloat::IEEEquad(), "0x1.0000000000000000000000000000p-16382");
316 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000317 "0x1.0000000000000000000000000001p-16382");
318 EXPECT_EQ(test.next(false), APFloat::opOK);
319 EXPECT_TRUE(!test.isDenormal());
320 EXPECT_TRUE(!test.isNegative());
321 EXPECT_TRUE(test.bitwiseIsEqual(expected));
322
323 // nextDown(-Smallest Normal) -> -Smallest Normal - inc.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000324 test = APFloat(APFloat::IEEEquad(), "-0x1.0000000000000000000000000000p-16382");
325 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000326 "-0x1.0000000000000000000000000001p-16382");
327 EXPECT_EQ(test.next(true), APFloat::opOK);
328 EXPECT_TRUE(!test.isDenormal());
329 EXPECT_TRUE(test.isNegative());
330 EXPECT_TRUE(test.bitwiseIsEqual(expected));
331
332 // 2d. Test values which cause our exponent to go to min exponent. This
333 // is to ensure that guards in the code to check for min exponent
334 // trigger properly.
335 // * nextUp(-0x1p-16381) -> -0x1.ffffffffffffffffffffffffffffp-16382
336 // * nextDown(-0x1.ffffffffffffffffffffffffffffp-16382) ->
337 // -0x1p-16381
338 // * nextUp(0x1.ffffffffffffffffffffffffffffp-16382) -> 0x1p-16382
339 // * nextDown(0x1p-16382) -> 0x1.ffffffffffffffffffffffffffffp-16382
340
341 // nextUp(-0x1p-16381) -> -0x1.ffffffffffffffffffffffffffffp-16382
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000342 test = APFloat(APFloat::IEEEquad(), "-0x1p-16381");
343 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000344 "-0x1.ffffffffffffffffffffffffffffp-16382");
345 EXPECT_EQ(test.next(false), APFloat::opOK);
346 EXPECT_TRUE(test.bitwiseIsEqual(expected));
347
348 // nextDown(-0x1.ffffffffffffffffffffffffffffp-16382) ->
349 // -0x1p-16381
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000350 test = APFloat(APFloat::IEEEquad(), "-0x1.ffffffffffffffffffffffffffffp-16382");
351 expected = APFloat(APFloat::IEEEquad(), "-0x1p-16381");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000352 EXPECT_EQ(test.next(true), APFloat::opOK);
353 EXPECT_TRUE(test.bitwiseIsEqual(expected));
354
355 // nextUp(0x1.ffffffffffffffffffffffffffffp-16382) -> 0x1p-16381
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000356 test = APFloat(APFloat::IEEEquad(), "0x1.ffffffffffffffffffffffffffffp-16382");
357 expected = APFloat(APFloat::IEEEquad(), "0x1p-16381");
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000358 EXPECT_EQ(test.next(false), APFloat::opOK);
359 EXPECT_TRUE(test.bitwiseIsEqual(expected));
360
361 // nextDown(0x1p-16381) -> 0x1.ffffffffffffffffffffffffffffp-16382
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000362 test = APFloat(APFloat::IEEEquad(), "0x1p-16381");
363 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000364 "0x1.ffffffffffffffffffffffffffffp-16382");
365 EXPECT_EQ(test.next(true), APFloat::opOK);
366 EXPECT_TRUE(test.bitwiseIsEqual(expected));
367
368 // 3. Now we test both denormal/normal computation which will not cause us
369 // to go across binade boundaries. Specifically we test:
370 // * nextUp(+Denormal) -> +Denormal.
371 // * nextDown(+Denormal) -> +Denormal.
372 // * nextUp(-Denormal) -> -Denormal.
373 // * nextDown(-Denormal) -> -Denormal.
374 // * nextUp(+Normal) -> +Normal.
375 // * nextDown(+Normal) -> +Normal.
376 // * nextUp(-Normal) -> -Normal.
377 // * nextDown(-Normal) -> -Normal.
378
379 // nextUp(+Denormal) -> +Denormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000380 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000381 "0x0.ffffffffffffffffffffffff000cp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000382 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000383 "0x0.ffffffffffffffffffffffff000dp-16382");
384 EXPECT_EQ(test.next(false), APFloat::opOK);
385 EXPECT_TRUE(test.isDenormal());
386 EXPECT_TRUE(!test.isNegative());
387 EXPECT_TRUE(test.bitwiseIsEqual(expected));
388
389 // nextDown(+Denormal) -> +Denormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000390 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000391 "0x0.ffffffffffffffffffffffff000cp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000392 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000393 "0x0.ffffffffffffffffffffffff000bp-16382");
394 EXPECT_EQ(test.next(true), APFloat::opOK);
395 EXPECT_TRUE(test.isDenormal());
396 EXPECT_TRUE(!test.isNegative());
397 EXPECT_TRUE(test.bitwiseIsEqual(expected));
398
399 // nextUp(-Denormal) -> -Denormal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000400 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000401 "-0x0.ffffffffffffffffffffffff000cp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000402 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000403 "-0x0.ffffffffffffffffffffffff000bp-16382");
404 EXPECT_EQ(test.next(false), APFloat::opOK);
405 EXPECT_TRUE(test.isDenormal());
406 EXPECT_TRUE(test.isNegative());
407 EXPECT_TRUE(test.bitwiseIsEqual(expected));
408
409 // nextDown(-Denormal) -> -Denormal
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000410 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000411 "-0x0.ffffffffffffffffffffffff000cp-16382");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000412 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000413 "-0x0.ffffffffffffffffffffffff000dp-16382");
414 EXPECT_EQ(test.next(true), APFloat::opOK);
415 EXPECT_TRUE(test.isDenormal());
416 EXPECT_TRUE(test.isNegative());
417 EXPECT_TRUE(test.bitwiseIsEqual(expected));
418
419 // nextUp(+Normal) -> +Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000420 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000421 "0x1.ffffffffffffffffffffffff000cp-16000");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000422 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000423 "0x1.ffffffffffffffffffffffff000dp-16000");
424 EXPECT_EQ(test.next(false), APFloat::opOK);
425 EXPECT_TRUE(!test.isDenormal());
426 EXPECT_TRUE(!test.isNegative());
427 EXPECT_TRUE(test.bitwiseIsEqual(expected));
428
429 // nextDown(+Normal) -> +Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000430 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000431 "0x1.ffffffffffffffffffffffff000cp-16000");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000432 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000433 "0x1.ffffffffffffffffffffffff000bp-16000");
434 EXPECT_EQ(test.next(true), APFloat::opOK);
435 EXPECT_TRUE(!test.isDenormal());
436 EXPECT_TRUE(!test.isNegative());
437 EXPECT_TRUE(test.bitwiseIsEqual(expected));
438
439 // nextUp(-Normal) -> -Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000440 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000441 "-0x1.ffffffffffffffffffffffff000cp-16000");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000442 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000443 "-0x1.ffffffffffffffffffffffff000bp-16000");
444 EXPECT_EQ(test.next(false), APFloat::opOK);
445 EXPECT_TRUE(!test.isDenormal());
446 EXPECT_TRUE(test.isNegative());
447 EXPECT_TRUE(test.bitwiseIsEqual(expected));
448
449 // nextDown(-Normal) -> -Normal.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000450 test = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000451 "-0x1.ffffffffffffffffffffffff000cp-16000");
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000452 expected = APFloat(APFloat::IEEEquad(),
Michael Gottesman0c622ea2013-05-30 18:07:13 +0000453 "-0x1.ffffffffffffffffffffffff000dp-16000");
454 EXPECT_EQ(test.next(true), APFloat::opOK);
455 EXPECT_TRUE(!test.isDenormal());
456 EXPECT_TRUE(test.isNegative());
457 EXPECT_TRUE(test.bitwiseIsEqual(expected));
458}
459
Shuxin Yangbbddbac2013-05-13 18:03:12 +0000460TEST(APFloatTest, FMA) {
461 APFloat::roundingMode rdmd = APFloat::rmNearestTiesToEven;
462
463 {
464 APFloat f1(14.5f);
465 APFloat f2(-14.5f);
466 APFloat f3(225.0f);
467 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
468 EXPECT_EQ(14.75f, f1.convertToFloat());
469 }
470
471 {
472 APFloat Val2(2.0f);
473 APFloat f1((float)1.17549435e-38F);
474 APFloat f2((float)1.17549435e-38F);
475 f1.divide(Val2, rdmd);
476 f2.divide(Val2, rdmd);
477 APFloat f3(12.0f);
478 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
479 EXPECT_EQ(12.0f, f1.convertToFloat());
480 }
Lang Hames56c0eb22014-11-19 19:15:41 +0000481
Lang Hames12b12e82015-01-04 01:20:55 +0000482 // Test for correct zero sign when answer is exactly zero.
483 // fma(1.0, -1.0, 1.0) -> +ve 0.
484 {
485 APFloat f1(1.0);
486 APFloat f2(-1.0);
487 APFloat f3(1.0);
488 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
489 EXPECT_TRUE(!f1.isNegative() && f1.isZero());
490 }
491
492 // Test for correct zero sign when answer is exactly zero and rounding towards
493 // negative.
494 // fma(1.0, -1.0, 1.0) -> +ve 0.
495 {
496 APFloat f1(1.0);
497 APFloat f2(-1.0);
498 APFloat f3(1.0);
499 f1.fusedMultiplyAdd(f2, f3, APFloat::rmTowardNegative);
500 EXPECT_TRUE(f1.isNegative() && f1.isZero());
501 }
502
503 // Test for correct (in this case -ve) sign when adding like signed zeros.
504 // Test fma(0.0, -0.0, -0.0) -> -ve 0.
505 {
506 APFloat f1(0.0);
507 APFloat f2(-0.0);
508 APFloat f3(-0.0);
509 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
510 EXPECT_TRUE(f1.isNegative() && f1.isZero());
511 }
512
513 // Test -ve sign preservation when small negative results underflow.
514 {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000515 APFloat f1(APFloat::IEEEdouble(), "-0x1p-1074");
516 APFloat f2(APFloat::IEEEdouble(), "+0x1p-1074");
Lang Hames12b12e82015-01-04 01:20:55 +0000517 APFloat f3(0.0);
518 f1.fusedMultiplyAdd(f2, f3, APFloat::rmNearestTiesToEven);
519 EXPECT_TRUE(f1.isNegative() && f1.isZero());
520 }
521
522 // Test x87 extended precision case from http://llvm.org/PR20728.
Lang Hames56c0eb22014-11-19 19:15:41 +0000523 {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000524 APFloat M1(APFloat::x87DoubleExtended(), 1.0);
525 APFloat M2(APFloat::x87DoubleExtended(), 1.0);
526 APFloat A(APFloat::x87DoubleExtended(), 3.0);
Lang Hames56c0eb22014-11-19 19:15:41 +0000527
528 bool losesInfo = false;
529 M1.fusedMultiplyAdd(M1, A, APFloat::rmNearestTiesToEven);
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000530 M1.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
Lang Hames56c0eb22014-11-19 19:15:41 +0000531 EXPECT_FALSE(losesInfo);
532 EXPECT_EQ(4.0f, M1.convertToFloat());
533 }
Shuxin Yangbbddbac2013-05-13 18:03:12 +0000534}
535
Matt Arsenault5ccdb982014-10-10 05:21:32 +0000536TEST(APFloatTest, MinNum) {
537 APFloat f1(1.0);
538 APFloat f2(2.0);
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000539 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
Matt Arsenault5ccdb982014-10-10 05:21:32 +0000540
541 EXPECT_EQ(1.0, minnum(f1, f2).convertToDouble());
542 EXPECT_EQ(1.0, minnum(f2, f1).convertToDouble());
543 EXPECT_EQ(1.0, minnum(f1, nan).convertToDouble());
544 EXPECT_EQ(1.0, minnum(nan, f1).convertToDouble());
545}
546
547TEST(APFloatTest, MaxNum) {
548 APFloat f1(1.0);
549 APFloat f2(2.0);
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000550 APFloat nan = APFloat::getNaN(APFloat::IEEEdouble());
Matt Arsenault5ccdb982014-10-10 05:21:32 +0000551
552 EXPECT_EQ(2.0, maxnum(f1, f2).convertToDouble());
553 EXPECT_EQ(2.0, maxnum(f2, f1).convertToDouble());
554 EXPECT_EQ(1.0, maxnum(f1, nan).convertToDouble());
Chandler Carruthf3598e82017-07-10 05:41:14 +0000555 EXPECT_EQ(1.0, maxnum(nan, f1).convertToDouble());
Matt Arsenault5ccdb982014-10-10 05:21:32 +0000556}
557
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000558TEST(APFloatTest, Denormal) {
559 APFloat::roundingMode rdmd = APFloat::rmNearestTiesToEven;
560
561 // Test single precision
562 {
563 const char *MinNormalStr = "1.17549435082228750797e-38";
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000564 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), MinNormalStr).isDenormal());
565 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), 0.0).isDenormal());
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000566
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000567 APFloat Val2(APFloat::IEEEsingle(), 2.0e0);
568 APFloat T(APFloat::IEEEsingle(), MinNormalStr);
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000569 T.divide(Val2, rdmd);
570 EXPECT_TRUE(T.isDenormal());
571 }
572
573 // Test double precision
574 {
575 const char *MinNormalStr = "2.22507385850720138309e-308";
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000576 EXPECT_FALSE(APFloat(APFloat::IEEEdouble(), MinNormalStr).isDenormal());
577 EXPECT_FALSE(APFloat(APFloat::IEEEdouble(), 0.0).isDenormal());
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000578
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000579 APFloat Val2(APFloat::IEEEdouble(), 2.0e0);
580 APFloat T(APFloat::IEEEdouble(), MinNormalStr);
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000581 T.divide(Val2, rdmd);
582 EXPECT_TRUE(T.isDenormal());
583 }
584
585 // Test Intel double-ext
586 {
587 const char *MinNormalStr = "3.36210314311209350626e-4932";
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000588 EXPECT_FALSE(APFloat(APFloat::x87DoubleExtended(), MinNormalStr).isDenormal());
589 EXPECT_FALSE(APFloat(APFloat::x87DoubleExtended(), 0.0).isDenormal());
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000590
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000591 APFloat Val2(APFloat::x87DoubleExtended(), 2.0e0);
592 APFloat T(APFloat::x87DoubleExtended(), MinNormalStr);
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000593 T.divide(Val2, rdmd);
594 EXPECT_TRUE(T.isDenormal());
595 }
596
597 // Test quadruple precision
598 {
599 const char *MinNormalStr = "3.36210314311209350626267781732175260e-4932";
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000600 EXPECT_FALSE(APFloat(APFloat::IEEEquad(), MinNormalStr).isDenormal());
601 EXPECT_FALSE(APFloat(APFloat::IEEEquad(), 0.0).isDenormal());
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000602
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000603 APFloat Val2(APFloat::IEEEquad(), 2.0e0);
604 APFloat T(APFloat::IEEEquad(), MinNormalStr);
Shuxin Yang4fb504f2013-01-07 18:59:35 +0000605 T.divide(Val2, rdmd);
606 EXPECT_TRUE(T.isDenormal());
607 }
608}
609
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000610TEST(APFloatTest, Zero) {
Matt Beaumont-Gaya421ee12011-08-29 17:54:20 +0000611 EXPECT_EQ(0.0f, APFloat(0.0f).convertToFloat());
612 EXPECT_EQ(-0.0f, APFloat(-0.0f).convertToFloat());
613 EXPECT_TRUE(APFloat(-0.0f).isNegative());
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000614
Matt Beaumont-Gaya421ee12011-08-29 17:54:20 +0000615 EXPECT_EQ(0.0, APFloat(0.0).convertToDouble());
616 EXPECT_EQ(-0.0, APFloat(-0.0).convertToDouble());
617 EXPECT_TRUE(APFloat(-0.0).isNegative());
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000618}
619
Michael Gottesman228156c2013-07-01 23:54:08 +0000620TEST(APFloatTest, DecimalStringsWithoutNullTerminators) {
621 // Make sure that we can parse strings without null terminators.
622 // rdar://14323230.
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000623 APFloat Val(APFloat::IEEEdouble());
Michael Gottesman228156c2013-07-01 23:54:08 +0000624 Val.convertFromString(StringRef("0.00", 3),
625 llvm::APFloat::rmNearestTiesToEven);
626 EXPECT_EQ(Val.convertToDouble(), 0.0);
627 Val.convertFromString(StringRef("0.01", 3),
628 llvm::APFloat::rmNearestTiesToEven);
629 EXPECT_EQ(Val.convertToDouble(), 0.0);
630 Val.convertFromString(StringRef("0.09", 3),
631 llvm::APFloat::rmNearestTiesToEven);
632 EXPECT_EQ(Val.convertToDouble(), 0.0);
633 Val.convertFromString(StringRef("0.095", 4),
634 llvm::APFloat::rmNearestTiesToEven);
635 EXPECT_EQ(Val.convertToDouble(), 0.09);
636 Val.convertFromString(StringRef("0.00e+3", 7),
637 llvm::APFloat::rmNearestTiesToEven);
638 EXPECT_EQ(Val.convertToDouble(), 0.00);
639 Val.convertFromString(StringRef("0e+3", 4),
640 llvm::APFloat::rmNearestTiesToEven);
641 EXPECT_EQ(Val.convertToDouble(), 0.00);
642
643}
644
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000645TEST(APFloatTest, fromZeroDecimalString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000646 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0").convertToDouble());
647 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0").convertToDouble());
648 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000649
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000650 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.").convertToDouble());
651 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.").convertToDouble());
652 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000653
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000654 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0").convertToDouble());
655 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0").convertToDouble());
656 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000657
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000658 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0").convertToDouble());
659 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0").convertToDouble());
660 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000661
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000662 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "00000.").convertToDouble());
663 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+00000.").convertToDouble());
664 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-00000.").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000665
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000666 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), ".00000").convertToDouble());
667 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.00000").convertToDouble());
668 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.00000").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000669
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000670 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0000.00000").convertToDouble());
671 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0000.00000").convertToDouble());
672 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0000.00000").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000673}
674
675TEST(APFloatTest, fromZeroDecimalSingleExponentString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000676 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e1").convertToDouble());
677 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e1").convertToDouble());
678 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000679
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000680 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e+1").convertToDouble());
681 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e+1").convertToDouble());
682 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000683
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000684 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e-1").convertToDouble());
685 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e-1").convertToDouble());
686 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000687
688
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000689 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e1").convertToDouble());
690 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e1").convertToDouble());
691 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000692
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000693 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e+1").convertToDouble());
694 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e+1").convertToDouble());
695 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000696
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000697 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.e-1").convertToDouble());
698 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.e-1").convertToDouble());
699 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.e-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000700
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000701 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e1").convertToDouble());
702 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e1").convertToDouble());
703 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000704
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000705 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e+1").convertToDouble());
706 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e+1").convertToDouble());
707 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000708
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000709 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), ".0e-1").convertToDouble());
710 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+.0e-1").convertToDouble());
711 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-.0e-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000712
713
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000714 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e1").convertToDouble());
715 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e1").convertToDouble());
716 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000717
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000718 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e+1").convertToDouble());
719 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e+1").convertToDouble());
720 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000721
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000722 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0.0e-1").convertToDouble());
723 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0.0e-1").convertToDouble());
724 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0.0e-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000725
726
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000727 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "000.0000e1").convertToDouble());
728 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+000.0000e+1").convertToDouble());
729 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-000.0000e+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000730}
731
732TEST(APFloatTest, fromZeroDecimalLargeExponentString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000733 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e1234").convertToDouble());
734 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e1234").convertToDouble());
735 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e1234").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000736
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000737 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e+1234").convertToDouble());
738 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e+1234").convertToDouble());
739 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e+1234").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000740
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000741 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0e-1234").convertToDouble());
742 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0e-1234").convertToDouble());
743 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0e-1234").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000744
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000745 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), "000.0000e1234").convertToDouble());
746 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), "000.0000e-1234").convertToDouble());
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000747
Chandler Carruth170e6cc2017-07-09 07:37:47 +0000748 EXPECT_EQ(0.0, APFloat(APFloat::IEEEdouble(), StringRef("0e1234" "\0" "2", 6)).convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000749}
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000750
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000751TEST(APFloatTest, fromZeroHexadecimalString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000752 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p1").convertToDouble());
753 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p1").convertToDouble());
754 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000755
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000756 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p+1").convertToDouble());
757 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p+1").convertToDouble());
758 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000759
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000760 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p-1").convertToDouble());
761 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0p-1").convertToDouble());
762 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000763
764
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000765 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1").convertToDouble());
766 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p1").convertToDouble());
767 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000768
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000769 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p+1").convertToDouble());
770 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p+1").convertToDouble());
771 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000772
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000773 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p-1").convertToDouble());
774 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.p-1").convertToDouble());
775 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000776
777
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000778 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p1").convertToDouble());
779 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p1").convertToDouble());
780 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000781
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000782 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p+1").convertToDouble());
783 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p+1").convertToDouble());
784 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000785
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000786 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.0p-1").convertToDouble());
787 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x.0p-1").convertToDouble());
788 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x.0p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000789
790
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000791 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p1").convertToDouble());
792 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p1").convertToDouble());
793 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000794
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000795 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p+1").convertToDouble());
796 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p+1").convertToDouble());
797 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000798
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000799 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.0p-1").convertToDouble());
800 EXPECT_EQ(+0.0, APFloat(APFloat::IEEEdouble(), "+0x0.0p-1").convertToDouble());
801 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0.0p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000802
803
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000804 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x00000.p1").convertToDouble());
805 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0000.00000p1").convertToDouble());
806 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.00000p1").convertToDouble());
807 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1").convertToDouble());
808 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0p1234").convertToDouble());
809 EXPECT_EQ(-0.0, APFloat(APFloat::IEEEdouble(), "-0x0p1234").convertToDouble());
810 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x00000.p1234").convertToDouble());
811 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0000.00000p1234").convertToDouble());
812 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x.00000p1234").convertToDouble());
813 EXPECT_EQ( 0.0, APFloat(APFloat::IEEEdouble(), "0x0.p1234").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000814}
815
816TEST(APFloatTest, fromDecimalString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000817 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1").convertToDouble());
818 EXPECT_EQ(2.0, APFloat(APFloat::IEEEdouble(), "2.").convertToDouble());
819 EXPECT_EQ(0.5, APFloat(APFloat::IEEEdouble(), ".5").convertToDouble());
820 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "1.0").convertToDouble());
821 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-2").convertToDouble());
822 EXPECT_EQ(-4.0, APFloat(APFloat::IEEEdouble(), "-4.").convertToDouble());
823 EXPECT_EQ(-0.5, APFloat(APFloat::IEEEdouble(), "-.5").convertToDouble());
824 EXPECT_EQ(-1.5, APFloat(APFloat::IEEEdouble(), "-1.5").convertToDouble());
825 EXPECT_EQ(1.25e12, APFloat(APFloat::IEEEdouble(), "1.25e12").convertToDouble());
826 EXPECT_EQ(1.25e+12, APFloat(APFloat::IEEEdouble(), "1.25e+12").convertToDouble());
827 EXPECT_EQ(1.25e-12, APFloat(APFloat::IEEEdouble(), "1.25e-12").convertToDouble());
828 EXPECT_EQ(1024.0, APFloat(APFloat::IEEEdouble(), "1024.").convertToDouble());
829 EXPECT_EQ(1024.05, APFloat(APFloat::IEEEdouble(), "1024.05000").convertToDouble());
830 EXPECT_EQ(0.05, APFloat(APFloat::IEEEdouble(), ".05000").convertToDouble());
831 EXPECT_EQ(2.0, APFloat(APFloat::IEEEdouble(), "2.").convertToDouble());
832 EXPECT_EQ(2.0e2, APFloat(APFloat::IEEEdouble(), "2.e2").convertToDouble());
833 EXPECT_EQ(2.0e+2, APFloat(APFloat::IEEEdouble(), "2.e+2").convertToDouble());
834 EXPECT_EQ(2.0e-2, APFloat(APFloat::IEEEdouble(), "2.e-2").convertToDouble());
835 EXPECT_EQ(2.05e2, APFloat(APFloat::IEEEdouble(), "002.05000e2").convertToDouble());
836 EXPECT_EQ(2.05e+2, APFloat(APFloat::IEEEdouble(), "002.05000e+2").convertToDouble());
837 EXPECT_EQ(2.05e-2, APFloat(APFloat::IEEEdouble(), "002.05000e-2").convertToDouble());
838 EXPECT_EQ(2.05e12, APFloat(APFloat::IEEEdouble(), "002.05000e12").convertToDouble());
839 EXPECT_EQ(2.05e+12, APFloat(APFloat::IEEEdouble(), "002.05000e+12").convertToDouble());
840 EXPECT_EQ(2.05e-12, APFloat(APFloat::IEEEdouble(), "002.05000e-12").convertToDouble());
John McCallb42cc682010-02-26 22:20:41 +0000841
842 // These are "carefully selected" to overflow the fast log-base
843 // calculations in APFloat.cpp
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000844 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "99e99999").isInfinity());
845 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-99e99999").isInfinity());
846 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "1e-99999").isPosZero());
847 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-1e-99999").isNegZero());
Eli Friedmand2eb07a2013-07-17 22:17:29 +0000848
849 EXPECT_EQ(2.71828, convertToDoubleFromString("2.71828"));
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000850}
851
852TEST(APFloatTest, fromHexadecimalString) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000853 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p0").convertToDouble());
854 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p0").convertToDouble());
855 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000856
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000857 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p+0").convertToDouble());
858 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p+0").convertToDouble());
859 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p+0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000860
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000861 EXPECT_EQ( 1.0, APFloat(APFloat::IEEEdouble(), "0x1p-0").convertToDouble());
862 EXPECT_EQ(+1.0, APFloat(APFloat::IEEEdouble(), "+0x1p-0").convertToDouble());
863 EXPECT_EQ(-1.0, APFloat(APFloat::IEEEdouble(), "-0x1p-0").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000864
865
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000866 EXPECT_EQ( 2.0, APFloat(APFloat::IEEEdouble(), "0x1p1").convertToDouble());
867 EXPECT_EQ(+2.0, APFloat(APFloat::IEEEdouble(), "+0x1p1").convertToDouble());
868 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-0x1p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000869
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000870 EXPECT_EQ( 2.0, APFloat(APFloat::IEEEdouble(), "0x1p+1").convertToDouble());
871 EXPECT_EQ(+2.0, APFloat(APFloat::IEEEdouble(), "+0x1p+1").convertToDouble());
872 EXPECT_EQ(-2.0, APFloat(APFloat::IEEEdouble(), "-0x1p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000873
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000874 EXPECT_EQ( 0.5, APFloat(APFloat::IEEEdouble(), "0x1p-1").convertToDouble());
875 EXPECT_EQ(+0.5, APFloat(APFloat::IEEEdouble(), "+0x1p-1").convertToDouble());
876 EXPECT_EQ(-0.5, APFloat(APFloat::IEEEdouble(), "-0x1p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000877
878
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000879 EXPECT_EQ( 3.0, APFloat(APFloat::IEEEdouble(), "0x1.8p1").convertToDouble());
880 EXPECT_EQ(+3.0, APFloat(APFloat::IEEEdouble(), "+0x1.8p1").convertToDouble());
881 EXPECT_EQ(-3.0, APFloat(APFloat::IEEEdouble(), "-0x1.8p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000882
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000883 EXPECT_EQ( 3.0, APFloat(APFloat::IEEEdouble(), "0x1.8p+1").convertToDouble());
884 EXPECT_EQ(+3.0, APFloat(APFloat::IEEEdouble(), "+0x1.8p+1").convertToDouble());
885 EXPECT_EQ(-3.0, APFloat(APFloat::IEEEdouble(), "-0x1.8p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000886
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000887 EXPECT_EQ( 0.75, APFloat(APFloat::IEEEdouble(), "0x1.8p-1").convertToDouble());
888 EXPECT_EQ(+0.75, APFloat(APFloat::IEEEdouble(), "+0x1.8p-1").convertToDouble());
889 EXPECT_EQ(-0.75, APFloat(APFloat::IEEEdouble(), "-0x1.8p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000890
891
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000892 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p1").convertToDouble());
893 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p1").convertToDouble());
894 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000895
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000896 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p+1").convertToDouble());
897 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p+1").convertToDouble());
898 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000899
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000900 EXPECT_EQ( 2048.0, APFloat(APFloat::IEEEdouble(), "0x1000.000p-1").convertToDouble());
901 EXPECT_EQ(+2048.0, APFloat(APFloat::IEEEdouble(), "+0x1000.000p-1").convertToDouble());
902 EXPECT_EQ(-2048.0, APFloat(APFloat::IEEEdouble(), "-0x1000.000p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000903
904
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000905 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000p1").convertToDouble());
906 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000p1").convertToDouble());
907 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000p1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000908
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000909 EXPECT_EQ( 8192.0, APFloat(APFloat::IEEEdouble(), "0x1000p+1").convertToDouble());
910 EXPECT_EQ(+8192.0, APFloat(APFloat::IEEEdouble(), "+0x1000p+1").convertToDouble());
911 EXPECT_EQ(-8192.0, APFloat(APFloat::IEEEdouble(), "-0x1000p+1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000912
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000913 EXPECT_EQ( 2048.0, APFloat(APFloat::IEEEdouble(), "0x1000p-1").convertToDouble());
914 EXPECT_EQ(+2048.0, APFloat(APFloat::IEEEdouble(), "+0x1000p-1").convertToDouble());
915 EXPECT_EQ(-2048.0, APFloat(APFloat::IEEEdouble(), "-0x1000p-1").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000916
917
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000918 EXPECT_EQ( 16384.0, APFloat(APFloat::IEEEdouble(), "0x10p10").convertToDouble());
919 EXPECT_EQ(+16384.0, APFloat(APFloat::IEEEdouble(), "+0x10p10").convertToDouble());
920 EXPECT_EQ(-16384.0, APFloat(APFloat::IEEEdouble(), "-0x10p10").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000921
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000922 EXPECT_EQ( 16384.0, APFloat(APFloat::IEEEdouble(), "0x10p+10").convertToDouble());
923 EXPECT_EQ(+16384.0, APFloat(APFloat::IEEEdouble(), "+0x10p+10").convertToDouble());
924 EXPECT_EQ(-16384.0, APFloat(APFloat::IEEEdouble(), "-0x10p+10").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000925
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000926 EXPECT_EQ( 0.015625, APFloat(APFloat::IEEEdouble(), "0x10p-10").convertToDouble());
927 EXPECT_EQ(+0.015625, APFloat(APFloat::IEEEdouble(), "+0x10p-10").convertToDouble());
928 EXPECT_EQ(-0.015625, APFloat(APFloat::IEEEdouble(), "-0x10p-10").convertToDouble());
Erick Tryzelaarda666c82009-08-20 23:30:43 +0000929
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000930 EXPECT_EQ(1.0625, APFloat(APFloat::IEEEdouble(), "0x1.1p0").convertToDouble());
931 EXPECT_EQ(1.0, APFloat(APFloat::IEEEdouble(), "0x1p0").convertToDouble());
Daniel Dunbarbc52e4f2009-09-03 22:57:02 +0000932
Eli Friedmand2eb07a2013-07-17 22:17:29 +0000933 EXPECT_EQ(convertToDoubleFromString("0x1p-150"),
934 convertToDoubleFromString("+0x800000000000000001.p-221"));
935 EXPECT_EQ(2251799813685248.5,
936 convertToDoubleFromString("0x80000000000004000000.010p-28"));
Erick Tryzelaar19f63b22009-08-16 23:36:19 +0000937}
938
John McCall29b5c282009-12-24 08:56:26 +0000939TEST(APFloatTest, toString) {
940 ASSERT_EQ("10", convertToString(10.0, 6, 3));
941 ASSERT_EQ("1.0E+1", convertToString(10.0, 6, 0));
942 ASSERT_EQ("10100", convertToString(1.01E+4, 5, 2));
943 ASSERT_EQ("1.01E+4", convertToString(1.01E+4, 4, 2));
944 ASSERT_EQ("1.01E+4", convertToString(1.01E+4, 5, 1));
945 ASSERT_EQ("0.0101", convertToString(1.01E-2, 5, 2));
John McCalldd5044a2009-12-24 23:18:09 +0000946 ASSERT_EQ("0.0101", convertToString(1.01E-2, 4, 2));
John McCall29b5c282009-12-24 08:56:26 +0000947 ASSERT_EQ("1.01E-2", convertToString(1.01E-2, 5, 1));
Eli Friedmane72f1322013-08-29 23:44:34 +0000948 ASSERT_EQ("0.78539816339744828", convertToString(0.78539816339744830961, 0, 3));
949 ASSERT_EQ("4.9406564584124654E-324", convertToString(4.9406564584124654e-324, 0, 3));
950 ASSERT_EQ("873.18340000000001", convertToString(873.1834, 0, 1));
951 ASSERT_EQ("8.7318340000000001E+2", convertToString(873.1834, 0, 0));
952 ASSERT_EQ("1.7976931348623157E+308", convertToString(1.7976931348623157E+308, 0, 0));
Serguei Katkov3a46eb42017-04-21 02:52:17 +0000953 ASSERT_EQ("10", convertToString(10.0, 6, 3, false));
954 ASSERT_EQ("1.000000e+01", convertToString(10.0, 6, 0, false));
955 ASSERT_EQ("10100", convertToString(1.01E+4, 5, 2, false));
956 ASSERT_EQ("1.0100e+04", convertToString(1.01E+4, 4, 2, false));
957 ASSERT_EQ("1.01000e+04", convertToString(1.01E+4, 5, 1, false));
958 ASSERT_EQ("0.0101", convertToString(1.01E-2, 5, 2, false));
959 ASSERT_EQ("0.0101", convertToString(1.01E-2, 4, 2, false));
960 ASSERT_EQ("1.01000e-02", convertToString(1.01E-2, 5, 1, false));
961 ASSERT_EQ("0.78539816339744828",
962 convertToString(0.78539816339744830961, 0, 3, false));
963 ASSERT_EQ("4.94065645841246540e-324",
964 convertToString(4.9406564584124654e-324, 0, 3, false));
965 ASSERT_EQ("873.18340000000001", convertToString(873.1834, 0, 1, false));
966 ASSERT_EQ("8.73183400000000010e+02", convertToString(873.1834, 0, 0, false));
967 ASSERT_EQ("1.79769313486231570e+308",
968 convertToString(1.7976931348623157E+308, 0, 0, false));
John McCall29b5c282009-12-24 08:56:26 +0000969}
970
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000971TEST(APFloatTest, toInteger) {
972 bool isExact = false;
973 APSInt result(5, /*isUnsigned=*/true);
974
975 EXPECT_EQ(APFloat::opOK,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000976 APFloat(APFloat::IEEEdouble(), "10")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000977 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
978 EXPECT_TRUE(isExact);
979 EXPECT_EQ(APSInt(APInt(5, 10), true), result);
980
981 EXPECT_EQ(APFloat::opInvalidOp,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000982 APFloat(APFloat::IEEEdouble(), "-10")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000983 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
984 EXPECT_FALSE(isExact);
985 EXPECT_EQ(APSInt::getMinValue(5, true), result);
986
987 EXPECT_EQ(APFloat::opInvalidOp,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000988 APFloat(APFloat::IEEEdouble(), "32")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000989 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
990 EXPECT_FALSE(isExact);
991 EXPECT_EQ(APSInt::getMaxValue(5, true), result);
992
993 EXPECT_EQ(APFloat::opInexact,
Stephan Bergmann17c7f702016-12-14 11:57:17 +0000994 APFloat(APFloat::IEEEdouble(), "7.9")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +0000995 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
996 EXPECT_FALSE(isExact);
997 EXPECT_EQ(APSInt(APInt(5, 7), true), result);
998
999 result.setIsUnsigned(false);
1000 EXPECT_EQ(APFloat::opOK,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001001 APFloat(APFloat::IEEEdouble(), "-10")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +00001002 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1003 EXPECT_TRUE(isExact);
1004 EXPECT_EQ(APSInt(APInt(5, -10, true), false), result);
1005
1006 EXPECT_EQ(APFloat::opInvalidOp,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001007 APFloat(APFloat::IEEEdouble(), "-17")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +00001008 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1009 EXPECT_FALSE(isExact);
1010 EXPECT_EQ(APSInt::getMinValue(5, false), result);
1011
1012 EXPECT_EQ(APFloat::opInvalidOp,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001013 APFloat(APFloat::IEEEdouble(), "16")
Jeffrey Yasskin03b81a22011-07-15 07:04:56 +00001014 .convertToInteger(result, APFloat::rmTowardZero, &isExact));
1015 EXPECT_FALSE(isExact);
1016 EXPECT_EQ(APSInt::getMaxValue(5, false), result);
1017}
1018
John McCalldcb9a7a2010-02-28 02:51:25 +00001019static APInt nanbits(const fltSemantics &Sem,
1020 bool SNaN, bool Negative, uint64_t fill) {
1021 APInt apfill(64, fill);
1022 if (SNaN)
1023 return APFloat::getSNaN(Sem, Negative, &apfill).bitcastToAPInt();
1024 else
1025 return APFloat::getQNaN(Sem, Negative, &apfill).bitcastToAPInt();
1026}
1027
1028TEST(APFloatTest, makeNaN) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001029 ASSERT_EQ(0x7fc00000, nanbits(APFloat::IEEEsingle(), false, false, 0));
1030 ASSERT_EQ(0xffc00000, nanbits(APFloat::IEEEsingle(), false, true, 0));
1031 ASSERT_EQ(0x7fc0ae72, nanbits(APFloat::IEEEsingle(), false, false, 0xae72));
1032 ASSERT_EQ(0x7fffae72, nanbits(APFloat::IEEEsingle(), false, false, 0xffffae72));
1033 ASSERT_EQ(0x7fa00000, nanbits(APFloat::IEEEsingle(), true, false, 0));
1034 ASSERT_EQ(0xffa00000, nanbits(APFloat::IEEEsingle(), true, true, 0));
1035 ASSERT_EQ(0x7f80ae72, nanbits(APFloat::IEEEsingle(), true, false, 0xae72));
1036 ASSERT_EQ(0x7fbfae72, nanbits(APFloat::IEEEsingle(), true, false, 0xffffae72));
John McCalldcb9a7a2010-02-28 02:51:25 +00001037
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001038 ASSERT_EQ(0x7ff8000000000000ULL, nanbits(APFloat::IEEEdouble(), false, false, 0));
1039 ASSERT_EQ(0xfff8000000000000ULL, nanbits(APFloat::IEEEdouble(), false, true, 0));
1040 ASSERT_EQ(0x7ff800000000ae72ULL, nanbits(APFloat::IEEEdouble(), false, false, 0xae72));
1041 ASSERT_EQ(0x7fffffffffffae72ULL, nanbits(APFloat::IEEEdouble(), false, false, 0xffffffffffffae72ULL));
1042 ASSERT_EQ(0x7ff4000000000000ULL, nanbits(APFloat::IEEEdouble(), true, false, 0));
1043 ASSERT_EQ(0xfff4000000000000ULL, nanbits(APFloat::IEEEdouble(), true, true, 0));
1044 ASSERT_EQ(0x7ff000000000ae72ULL, nanbits(APFloat::IEEEdouble(), true, false, 0xae72));
1045 ASSERT_EQ(0x7ff7ffffffffae72ULL, nanbits(APFloat::IEEEdouble(), true, false, 0xffffffffffffae72ULL));
John McCalldcb9a7a2010-02-28 02:51:25 +00001046}
1047
Erick Tryzelaar927191f2009-08-17 00:55:33 +00001048#ifdef GTEST_HAS_DEATH_TEST
Jeffrey Yasskinb5cd0132010-03-17 01:18:45 +00001049#ifndef NDEBUG
Erick Tryzelaar927191f2009-08-17 00:55:33 +00001050TEST(APFloatTest, SemanticsDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001051 EXPECT_DEATH(APFloat(APFloat::IEEEsingle(), 0.0f).convertToDouble(), "Float semantics are not IEEEdouble");
1052 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), 0.0 ).convertToFloat(), "Float semantics are not IEEEsingle");
Erick Tryzelaar927191f2009-08-17 00:55:33 +00001053}
1054
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001055TEST(APFloatTest, StringDecimalDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001056 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ""), "Invalid string length");
1057 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+"), "String has no digits");
1058 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-"), "String has no digits");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001059
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001060 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("\0", 1)), "Invalid character in significand");
1061 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1\0", 2)), "Invalid character in significand");
Chandler Carruth170e6cc2017-07-09 07:37:47 +00001062 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1" "\0" "2", 3)), "Invalid character in significand");
1063 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1" "\0" "2e1", 5)), "Invalid character in significand");
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001064 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1e\0", 3)), "Invalid character in exponent");
1065 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1e1\0", 4)), "Invalid character in exponent");
Chandler Carruth170e6cc2017-07-09 07:37:47 +00001066 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("1e1" "\0" "2", 5)), "Invalid character in exponent");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001067
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001068 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0f"), "Invalid character in significand");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001069
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001070 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".."), "String contains multiple dots");
1071 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "..0"), "String contains multiple dots");
1072 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0.0"), "String contains multiple dots");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001073}
1074
1075TEST(APFloatTest, StringDecimalSignificandDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001076 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "."), "Significand has no digits");
1077 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+."), "Significand has no digits");
1078 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-."), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001079
1080
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001081 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "e"), "Significand has no digits");
1082 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+e"), "Significand has no digits");
1083 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-e"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001084
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001085 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "e1"), "Significand has no digits");
1086 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+e1"), "Significand has no digits");
1087 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-e1"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001088
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001089 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".e1"), "Significand has no digits");
1090 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+.e1"), "Significand has no digits");
1091 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-.e1"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001092
1093
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001094 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".e"), "Significand has no digits");
1095 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+.e"), "Significand has no digits");
1096 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-.e"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001097}
1098
1099TEST(APFloatTest, StringDecimalExponentDeath) {
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");
1102 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-1e"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001103
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001104 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.e"), "Exponent has no digits");
1105 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+1.e"), "Exponent has no digits");
1106 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-1.e"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001107
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001108 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".1e"), "Exponent has no digits");
1109 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+.1e"), "Exponent has no digits");
1110 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-.1e"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001111
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001112 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.1e"), "Exponent has no digits");
1113 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+1.1e"), "Exponent has no digits");
1114 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-1.1e"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001115
1116
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001117 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1e+"), "Exponent has no digits");
1118 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1e-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001119
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001120 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".1e"), "Exponent has no digits");
1121 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".1e+"), "Exponent has no digits");
1122 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), ".1e-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001123
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001124 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0e"), "Exponent has no digits");
1125 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0e+"), "Exponent has no digits");
1126 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "1.0e-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001127}
1128
1129TEST(APFloatTest, StringHexadecimalDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001130 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x"), "Invalid string");
1131 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x"), "Invalid string");
1132 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x"), "Invalid string");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001133
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001134 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x0"), "Hex strings require an exponent");
1135 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x0"), "Hex strings require an exponent");
1136 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x0"), "Hex strings require an exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001137
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001138 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x0."), "Hex strings require an exponent");
1139 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x0."), "Hex strings require an exponent");
1140 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x0."), "Hex strings require an exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001141
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001142 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.0"), "Hex strings require an exponent");
1143 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.0"), "Hex strings require an exponent");
1144 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.0"), "Hex strings require an exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001145
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001146 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x0.0"), "Hex strings require an exponent");
1147 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x0.0"), "Hex strings require an exponent");
1148 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x0.0"), "Hex strings require an exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001149
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001150 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x\0", 3)), "Invalid character in significand");
1151 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1\0", 4)), "Invalid character in significand");
Chandler Carruth170e6cc2017-07-09 07:37:47 +00001152 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1" "\0" "2", 5)), "Invalid character in significand");
1153 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1" "\0" "2p1", 7)), "Invalid character in significand");
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001154 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1p\0", 5)), "Invalid character in exponent");
1155 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1p1\0", 6)), "Invalid character in exponent");
Chandler Carruth170e6cc2017-07-09 07:37:47 +00001156 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), StringRef("0x1p1" "\0" "2", 7)), "Invalid character in exponent");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001157
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001158 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1p0f"), "Invalid character in exponent");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001159
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001160 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x..p1"), "String contains multiple dots");
1161 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x..0p1"), "String contains multiple dots");
1162 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.0.0p1"), "String contains multiple dots");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001163}
1164
1165TEST(APFloatTest, StringHexadecimalSignificandDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001166 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x."), "Significand has no digits");
1167 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x."), "Significand has no digits");
1168 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x."), "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(), "0xp"), "Significand has no digits");
1171 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0xp"), "Significand has no digits");
1172 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0xp"), "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(), "0xp+"), "Significand has no digits");
1175 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0xp+"), "Significand has no digits");
1176 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0xp+"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001177
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001178 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0xp-"), "Significand has no digits");
1179 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0xp-"), "Significand has no digits");
1180 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0xp-"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001181
1182
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001183 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.p"), "Significand has no digits");
1184 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.p"), "Significand has no digits");
1185 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.p"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001186
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001187 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.p+"), "Significand has no digits");
1188 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.p+"), "Significand has no digits");
1189 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.p+"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001190
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001191 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.p-"), "Significand has no digits");
1192 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.p-"), "Significand has no digits");
1193 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.p-"), "Significand has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001194}
1195
1196TEST(APFloatTest, StringHexadecimalExponentDeath) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001197 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1p"), "Exponent has no digits");
1198 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1p"), "Exponent has no digits");
1199 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1p"), "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(), "0x1p+"), "Exponent has no digits");
1202 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1p+"), "Exponent has no digits");
1203 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1p+"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001204
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001205 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1p-"), "Exponent has no digits");
1206 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1p-"), "Exponent has no digits");
1207 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1p-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001208
1209
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001210 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.p"), "Exponent has no digits");
1211 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.p"), "Exponent has no digits");
1212 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.p"), "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(), "0x1.p+"), "Exponent has no digits");
1215 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.p+"), "Exponent has no digits");
1216 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.p+"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001217
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001218 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.p-"), "Exponent has no digits");
1219 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.p-"), "Exponent has no digits");
1220 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.p-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001221
1222
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001223 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.1p"), "Exponent has no digits");
1224 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.1p"), "Exponent has no digits");
1225 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.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(), "0x.1p+"), "Exponent has no digits");
1228 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.1p+"), "Exponent has no digits");
1229 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.1p+"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001230
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001231 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x.1p-"), "Exponent has no digits");
1232 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x.1p-"), "Exponent has no digits");
1233 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x.1p-"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001234
1235
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001236 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.1p"), "Exponent has no digits");
1237 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.1p"), "Exponent has no digits");
1238 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.1p"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001239
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001240 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.1p+"), "Exponent has no digits");
1241 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.1p+"), "Exponent has no digits");
1242 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.1p+"), "Exponent has no digits");
Erick Tryzelaarda666c82009-08-20 23:30:43 +00001243
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001244 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "0x1.1p-"), "Exponent has no digits");
1245 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "+0x1.1p-"), "Exponent has no digits");
1246 EXPECT_DEATH(APFloat(APFloat::IEEEdouble(), "-0x1.1p-"), "Exponent has no digits");
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001247}
Erick Tryzelaar927191f2009-08-17 00:55:33 +00001248#endif
Jeffrey Yasskinb5cd0132010-03-17 01:18:45 +00001249#endif
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00001250
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001251TEST(APFloatTest, exactInverse) {
1252 APFloat inv(0.0f);
1253
1254 // Trivial operation.
1255 EXPECT_TRUE(APFloat(2.0).getExactInverse(&inv));
1256 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(0.5)));
1257 EXPECT_TRUE(APFloat(2.0f).getExactInverse(&inv));
1258 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(0.5f)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001259 EXPECT_TRUE(APFloat(APFloat::IEEEquad(), "2.0").getExactInverse(&inv));
1260 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::IEEEquad(), "0.5")));
1261 EXPECT_TRUE(APFloat(APFloat::PPCDoubleDouble(), "2.0").getExactInverse(&inv));
1262 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::PPCDoubleDouble(), "0.5")));
1263 EXPECT_TRUE(APFloat(APFloat::x87DoubleExtended(), "2.0").getExactInverse(&inv));
1264 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(APFloat::x87DoubleExtended(), "0.5")));
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001265
1266 // FLT_MIN
1267 EXPECT_TRUE(APFloat(1.17549435e-38f).getExactInverse(&inv));
1268 EXPECT_TRUE(inv.bitwiseIsEqual(APFloat(8.5070592e+37f)));
1269
Benjamin Krameraf0ed952011-03-30 17:02:54 +00001270 // Large float, inverse is a denormal.
Craig Topper66f09ad2014-06-08 22:29:17 +00001271 EXPECT_FALSE(APFloat(1.7014118e38f).getExactInverse(nullptr));
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001272 // Zero
Craig Topper66f09ad2014-06-08 22:29:17 +00001273 EXPECT_FALSE(APFloat(0.0).getExactInverse(nullptr));
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001274 // Denormalized float
Craig Topper66f09ad2014-06-08 22:29:17 +00001275 EXPECT_FALSE(APFloat(1.40129846e-45f).getExactInverse(nullptr));
Benjamin Kramer03fd6722011-03-30 15:42:27 +00001276}
1277
Owen Anderson1ff74b02012-08-15 05:39:46 +00001278TEST(APFloatTest, roundToIntegral) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001279 APFloat T(-0.5), S(3.14), R(APFloat::getLargest(APFloat::IEEEdouble())), P(0.0);
Owen Anderson1ff74b02012-08-15 05:39:46 +00001280
1281 P = T;
1282 P.roundToIntegral(APFloat::rmTowardZero);
1283 EXPECT_EQ(-0.0, P.convertToDouble());
1284 P = T;
1285 P.roundToIntegral(APFloat::rmTowardNegative);
1286 EXPECT_EQ(-1.0, P.convertToDouble());
1287 P = T;
1288 P.roundToIntegral(APFloat::rmTowardPositive);
1289 EXPECT_EQ(-0.0, P.convertToDouble());
1290 P = T;
1291 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1292 EXPECT_EQ(-0.0, P.convertToDouble());
1293
1294 P = S;
1295 P.roundToIntegral(APFloat::rmTowardZero);
1296 EXPECT_EQ(3.0, P.convertToDouble());
1297 P = S;
1298 P.roundToIntegral(APFloat::rmTowardNegative);
1299 EXPECT_EQ(3.0, P.convertToDouble());
1300 P = S;
1301 P.roundToIntegral(APFloat::rmTowardPositive);
1302 EXPECT_EQ(4.0, P.convertToDouble());
1303 P = S;
1304 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1305 EXPECT_EQ(3.0, P.convertToDouble());
Owen Anderson352dfff2012-08-15 18:28:45 +00001306
1307 P = R;
1308 P.roundToIntegral(APFloat::rmTowardZero);
1309 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1310 P = R;
1311 P.roundToIntegral(APFloat::rmTowardNegative);
1312 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1313 P = R;
1314 P.roundToIntegral(APFloat::rmTowardPositive);
1315 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
1316 P = R;
1317 P.roundToIntegral(APFloat::rmNearestTiesToEven);
1318 EXPECT_EQ(R.convertToDouble(), P.convertToDouble());
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001319
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001320 P = APFloat::getZero(APFloat::IEEEdouble());
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001321 P.roundToIntegral(APFloat::rmTowardZero);
1322 EXPECT_EQ(0.0, P.convertToDouble());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001323 P = APFloat::getZero(APFloat::IEEEdouble(), true);
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001324 P.roundToIntegral(APFloat::rmTowardZero);
1325 EXPECT_EQ(-0.0, P.convertToDouble());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001326 P = APFloat::getNaN(APFloat::IEEEdouble());
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001327 P.roundToIntegral(APFloat::rmTowardZero);
Benjamin Kramer37dce442015-03-09 18:35:18 +00001328 EXPECT_TRUE(std::isnan(P.convertToDouble()));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001329 P = APFloat::getInf(APFloat::IEEEdouble());
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001330 P.roundToIntegral(APFloat::rmTowardZero);
Benjamin Kramer37dce442015-03-09 18:35:18 +00001331 EXPECT_TRUE(std::isinf(P.convertToDouble()) && P.convertToDouble() > 0.0);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001332 P = APFloat::getInf(APFloat::IEEEdouble(), true);
Benjamin Kramerc38fab22012-09-26 14:06:58 +00001333 P.roundToIntegral(APFloat::rmTowardZero);
Benjamin Kramer37dce442015-03-09 18:35:18 +00001334 EXPECT_TRUE(std::isinf(P.convertToDouble()) && P.convertToDouble() < 0.0);
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001335}
Matt Arsenaultc25a7112016-03-21 16:49:16 +00001336
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001337TEST(APFloatTest, isInteger) {
1338 APFloat T(-0.0);
1339 EXPECT_TRUE(T.isInteger());
1340 T = APFloat(3.14159);
1341 EXPECT_FALSE(T.isInteger());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001342 T = APFloat::getNaN(APFloat::IEEEdouble());
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001343 EXPECT_FALSE(T.isInteger());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001344 T = APFloat::getInf(APFloat::IEEEdouble());
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001345 EXPECT_FALSE(T.isInteger());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001346 T = APFloat::getInf(APFloat::IEEEdouble(), true);
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001347 EXPECT_FALSE(T.isInteger());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001348 T = APFloat::getLargest(APFloat::IEEEdouble());
Stephen Canon1bfc89b2015-11-16 21:52:48 +00001349 EXPECT_TRUE(T.isInteger());
Owen Anderson1ff74b02012-08-15 05:39:46 +00001350}
1351
Eli Friedmanc5322012011-10-12 21:51:36 +00001352TEST(APFloatTest, getLargest) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001353 EXPECT_EQ(3.402823466e+38f, APFloat::getLargest(APFloat::IEEEsingle()).convertToFloat());
1354 EXPECT_EQ(1.7976931348623158e+308, APFloat::getLargest(APFloat::IEEEdouble()).convertToDouble());
Eli Friedmanc5322012011-10-12 21:51:36 +00001355}
1356
Michael Gottesman63e6d212013-05-29 23:58:29 +00001357TEST(APFloatTest, getSmallest) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001358 APFloat test = APFloat::getSmallest(APFloat::IEEEsingle(), false);
1359 APFloat expected = APFloat(APFloat::IEEEsingle(), "0x0.000002p-126");
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001360 EXPECT_FALSE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001361 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001362 EXPECT_TRUE(test.isDenormal());
Michael Gottesman63e6d212013-05-29 23:58:29 +00001363 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1364
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001365 test = APFloat::getSmallest(APFloat::IEEEsingle(), true);
1366 expected = APFloat(APFloat::IEEEsingle(), "-0x0.000002p-126");
Michael Gottesman63e6d212013-05-29 23:58:29 +00001367 EXPECT_TRUE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001368 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001369 EXPECT_TRUE(test.isDenormal());
Michael Gottesman63e6d212013-05-29 23:58:29 +00001370 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1371
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001372 test = APFloat::getSmallest(APFloat::IEEEquad(), false);
1373 expected = APFloat(APFloat::IEEEquad(), "0x0.0000000000000000000000000001p-16382");
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001374 EXPECT_FALSE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001375 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001376 EXPECT_TRUE(test.isDenormal());
Michael Gottesman63e6d212013-05-29 23:58:29 +00001377 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1378
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001379 test = APFloat::getSmallest(APFloat::IEEEquad(), true);
1380 expected = APFloat(APFloat::IEEEquad(), "-0x0.0000000000000000000000000001p-16382");
Michael Gottesman63e6d212013-05-29 23:58:29 +00001381 EXPECT_TRUE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001382 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman5455d5b2013-05-30 00:18:44 +00001383 EXPECT_TRUE(test.isDenormal());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001384 EXPECT_TRUE(test.bitwiseIsEqual(expected));
Michael Gottesman63e6d212013-05-29 23:58:29 +00001385}
1386
Michael Gottesman0db7c272013-05-30 00:18:47 +00001387TEST(APFloatTest, getSmallestNormalized) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001388 APFloat test = APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
1389 APFloat expected = APFloat(APFloat::IEEEsingle(), "0x1p-126");
Michael Gottesman0db7c272013-05-30 00:18:47 +00001390 EXPECT_FALSE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001391 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman0db7c272013-05-30 00:18:47 +00001392 EXPECT_FALSE(test.isDenormal());
1393 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1394
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001395 test = APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
1396 expected = APFloat(APFloat::IEEEsingle(), "-0x1p-126");
Michael Gottesman0db7c272013-05-30 00:18:47 +00001397 EXPECT_TRUE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001398 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman0db7c272013-05-30 00:18:47 +00001399 EXPECT_FALSE(test.isDenormal());
1400 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1401
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001402 test = APFloat::getSmallestNormalized(APFloat::IEEEquad(), false);
1403 expected = APFloat(APFloat::IEEEquad(), "0x1p-16382");
Michael Gottesman0db7c272013-05-30 00:18:47 +00001404 EXPECT_FALSE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001405 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman0db7c272013-05-30 00:18:47 +00001406 EXPECT_FALSE(test.isDenormal());
1407 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1408
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001409 test = APFloat::getSmallestNormalized(APFloat::IEEEquad(), true);
1410 expected = APFloat(APFloat::IEEEquad(), "-0x1p-16382");
Michael Gottesman0db7c272013-05-30 00:18:47 +00001411 EXPECT_TRUE(test.isNegative());
Michael Gottesmanb5101ab2013-06-19 21:53:45 +00001412 EXPECT_TRUE(test.isFiniteNonZero());
Michael Gottesman0db7c272013-05-30 00:18:47 +00001413 EXPECT_FALSE(test.isDenormal());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001414 EXPECT_TRUE(test.bitwiseIsEqual(expected));
Michael Gottesman0db7c272013-05-30 00:18:47 +00001415}
1416
Michael Gottesmanfc718c92013-05-31 18:43:34 +00001417TEST(APFloatTest, getZero) {
1418 struct {
1419 const fltSemantics *semantics;
1420 const bool sign;
1421 const unsigned long long bitPattern[2];
1422 const unsigned bitPatternLength;
Benjamin Kramer0bb474f2013-06-01 22:29:41 +00001423 } const GetZeroTest[] = {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001424 { &APFloat::IEEEhalf(), false, {0, 0}, 1},
1425 { &APFloat::IEEEhalf(), true, {0x8000ULL, 0}, 1},
1426 { &APFloat::IEEEsingle(), false, {0, 0}, 1},
1427 { &APFloat::IEEEsingle(), true, {0x80000000ULL, 0}, 1},
1428 { &APFloat::IEEEdouble(), false, {0, 0}, 1},
1429 { &APFloat::IEEEdouble(), true, {0x8000000000000000ULL, 0}, 1},
1430 { &APFloat::IEEEquad(), false, {0, 0}, 2},
1431 { &APFloat::IEEEquad(), true, {0, 0x8000000000000000ULL}, 2},
1432 { &APFloat::PPCDoubleDouble(), false, {0, 0}, 2},
1433 { &APFloat::PPCDoubleDouble(), true, {0x8000000000000000ULL, 0}, 2},
1434 { &APFloat::x87DoubleExtended(), false, {0, 0}, 2},
1435 { &APFloat::x87DoubleExtended(), true, {0, 0x8000ULL}, 2},
Michael Gottesmanfc718c92013-05-31 18:43:34 +00001436 };
1437 const unsigned NumGetZeroTests = 12;
1438 for (unsigned i = 0; i < NumGetZeroTests; ++i) {
1439 APFloat test = APFloat::getZero(*GetZeroTest[i].semantics,
1440 GetZeroTest[i].sign);
1441 const char *pattern = GetZeroTest[i].sign? "-0x0p+0" : "0x0p+0";
1442 APFloat expected = APFloat(*GetZeroTest[i].semantics,
1443 pattern);
1444 EXPECT_TRUE(test.isZero());
1445 EXPECT_TRUE(GetZeroTest[i].sign? test.isNegative() : !test.isNegative());
1446 EXPECT_TRUE(test.bitwiseIsEqual(expected));
1447 for (unsigned j = 0, je = GetZeroTest[i].bitPatternLength; j < je; ++j) {
1448 EXPECT_EQ(GetZeroTest[i].bitPattern[j],
1449 test.bitcastToAPInt().getRawData()[j]);
1450 }
1451 }
1452}
1453
Chandler Carruthdf782e42014-10-09 23:26:15 +00001454TEST(APFloatTest, copySign) {
1455 EXPECT_TRUE(APFloat(-42.0).bitwiseIsEqual(
1456 APFloat::copySign(APFloat(42.0), APFloat(-1.0))));
1457 EXPECT_TRUE(APFloat(42.0).bitwiseIsEqual(
1458 APFloat::copySign(APFloat(-42.0), APFloat(1.0))));
1459 EXPECT_TRUE(APFloat(-42.0).bitwiseIsEqual(
1460 APFloat::copySign(APFloat(-42.0), APFloat(-1.0))));
1461 EXPECT_TRUE(APFloat(42.0).bitwiseIsEqual(
1462 APFloat::copySign(APFloat(42.0), APFloat(1.0))));
1463}
1464
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001465TEST(APFloatTest, convert) {
1466 bool losesInfo;
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001467 APFloat test(APFloat::IEEEdouble(), "1.0");
1468 test.convert(APFloat::IEEEsingle(), APFloat::rmNearestTiesToEven, &losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001469 EXPECT_EQ(1.0f, test.convertToFloat());
1470 EXPECT_FALSE(losesInfo);
1471
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001472 test = APFloat(APFloat::x87DoubleExtended(), "0x1p-53");
1473 test.add(APFloat(APFloat::x87DoubleExtended(), "1.0"), APFloat::rmNearestTiesToEven);
1474 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001475 EXPECT_EQ(1.0, test.convertToDouble());
1476 EXPECT_TRUE(losesInfo);
1477
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001478 test = APFloat(APFloat::IEEEquad(), "0x1p-53");
1479 test.add(APFloat(APFloat::IEEEquad(), "1.0"), APFloat::rmNearestTiesToEven);
1480 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001481 EXPECT_EQ(1.0, test.convertToDouble());
1482 EXPECT_TRUE(losesInfo);
1483
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001484 test = APFloat(APFloat::x87DoubleExtended(), "0xf.fffffffp+28");
1485 test.convert(APFloat::IEEEdouble(), APFloat::rmNearestTiesToEven, &losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001486 EXPECT_EQ(4294967295.0, test.convertToDouble());
1487 EXPECT_FALSE(losesInfo);
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001488
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001489 test = APFloat::getSNaN(APFloat::IEEEsingle());
1490 APFloat X87SNaN = APFloat::getSNaN(APFloat::x87DoubleExtended());
1491 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001492 &losesInfo);
1493 EXPECT_TRUE(test.bitwiseIsEqual(X87SNaN));
1494 EXPECT_FALSE(losesInfo);
1495
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001496 test = APFloat::getQNaN(APFloat::IEEEsingle());
1497 APFloat X87QNaN = APFloat::getQNaN(APFloat::x87DoubleExtended());
1498 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001499 &losesInfo);
1500 EXPECT_TRUE(test.bitwiseIsEqual(X87QNaN));
1501 EXPECT_FALSE(losesInfo);
1502
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001503 test = APFloat::getSNaN(APFloat::x87DoubleExtended());
1504 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001505 &losesInfo);
1506 EXPECT_TRUE(test.bitwiseIsEqual(X87SNaN));
1507 EXPECT_FALSE(losesInfo);
1508
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001509 test = APFloat::getQNaN(APFloat::x87DoubleExtended());
1510 test.convert(APFloat::x87DoubleExtended(), APFloat::rmNearestTiesToEven,
Benjamin Kramerb361adb2013-01-25 17:01:00 +00001511 &losesInfo);
1512 EXPECT_TRUE(test.bitwiseIsEqual(X87QNaN));
1513 EXPECT_FALSE(losesInfo);
Eli Friedmana84ad7d2011-11-26 03:38:02 +00001514}
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001515
1516TEST(APFloatTest, PPCDoubleDouble) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001517 APFloat test(APFloat::PPCDoubleDouble(), "1.0");
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001518 EXPECT_EQ(0x3ff0000000000000ull, test.bitcastToAPInt().getRawData()[0]);
1519 EXPECT_EQ(0x0000000000000000ull, test.bitcastToAPInt().getRawData()[1]);
1520
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001521 // LDBL_MAX
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001522 test = APFloat(APFloat::PPCDoubleDouble(), "1.79769313486231580793728971405301e+308");
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001523 EXPECT_EQ(0x7fefffffffffffffull, test.bitcastToAPInt().getRawData()[0]);
1524 EXPECT_EQ(0x7c8ffffffffffffeull, test.bitcastToAPInt().getRawData()[1]);
1525
1526 // LDBL_MIN
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001527 test = APFloat(APFloat::PPCDoubleDouble(), "2.00416836000897277799610805135016e-292");
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001528 EXPECT_EQ(0x0360000000000000ull, test.bitcastToAPInt().getRawData()[0]);
1529 EXPECT_EQ(0x0000000000000000ull, test.bitcastToAPInt().getRawData()[1]);
1530
Tim Shen398f90f2016-11-06 07:38:37 +00001531 // PR30869
1532 {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001533 auto Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") +
1534 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1535 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001536
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001537 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") -
1538 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1539 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001540
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001541 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") *
1542 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1543 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001544
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001545 Result = APFloat(APFloat::PPCDoubleDouble(), "1.0") /
1546 APFloat(APFloat::PPCDoubleDouble(), "1.0");
1547 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001548
1549 int Exp;
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001550 Result = frexp(APFloat(APFloat::PPCDoubleDouble(), "1.0"), Exp,
Tim Shen398f90f2016-11-06 07:38:37 +00001551 APFloat::rmNearestTiesToEven);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001552 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001553
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001554 Result = scalbn(APFloat(APFloat::PPCDoubleDouble(), "1.0"), 1,
Tim Shen398f90f2016-11-06 07:38:37 +00001555 APFloat::rmNearestTiesToEven);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001556 EXPECT_EQ(&APFloat::PPCDoubleDouble(), &Result.getSemantics());
Tim Shen398f90f2016-11-06 07:38:37 +00001557 }
Ulrich Weigandd9f7e252012-10-29 18:09:01 +00001558}
Michael Gottesman3acedb62013-06-04 03:46:25 +00001559
1560TEST(APFloatTest, isNegative) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001561 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesman3acedb62013-06-04 03:46:25 +00001562 EXPECT_FALSE(t.isNegative());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001563 t = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
Michael Gottesman3acedb62013-06-04 03:46:25 +00001564 EXPECT_TRUE(t.isNegative());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001565
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001566 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNegative());
1567 EXPECT_TRUE(APFloat::getInf(APFloat::IEEEsingle(), true).isNegative());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001568
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001569 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNegative());
1570 EXPECT_TRUE(APFloat::getZero(APFloat::IEEEsingle(), true).isNegative());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001571
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001572 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNegative());
1573 EXPECT_TRUE(APFloat::getNaN(APFloat::IEEEsingle(), true).isNegative());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001574
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001575 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNegative());
1576 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isNegative());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001577}
1578
Michael Gottesman120c92882013-06-20 18:34:38 +00001579TEST(APFloatTest, isNormal) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001580 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesman120c92882013-06-20 18:34:38 +00001581 EXPECT_TRUE(t.isNormal());
Michael Gottesmanf9899292013-06-24 09:58:09 +00001582
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001583 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNormal());
1584 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNormal());
1585 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNormal());
1586 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNormal());
1587 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isNormal());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001588}
1589
1590TEST(APFloatTest, isFinite) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001591 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesmanf9899292013-06-24 09:58:09 +00001592 EXPECT_TRUE(t.isFinite());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001593 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isFinite());
1594 EXPECT_TRUE(APFloat::getZero(APFloat::IEEEsingle(), false).isFinite());
1595 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isFinite());
1596 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isFinite());
1597 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isFinite());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001598}
1599
1600TEST(APFloatTest, isInfinity) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001601 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesman3acedb62013-06-04 03:46:25 +00001602 EXPECT_FALSE(t.isInfinity());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001603 EXPECT_TRUE(APFloat::getInf(APFloat::IEEEsingle(), false).isInfinity());
1604 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isInfinity());
1605 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isInfinity());
1606 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isInfinity());
1607 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isInfinity());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001608}
1609
1610TEST(APFloatTest, isNaN) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001611 APFloat t(APFloat::IEEEsingle(), "0x1p+0");
Michael Gottesmanf9899292013-06-24 09:58:09 +00001612 EXPECT_FALSE(t.isNaN());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001613 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isNaN());
1614 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isNaN());
1615 EXPECT_TRUE(APFloat::getNaN(APFloat::IEEEsingle(), false).isNaN());
1616 EXPECT_TRUE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isNaN());
1617 EXPECT_FALSE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isNaN());
Michael Gottesman3acedb62013-06-04 03:46:25 +00001618}
1619
Michael Gottesmand95d4472013-06-19 21:00:17 +00001620TEST(APFloatTest, isFiniteNonZero) {
1621 // Test positive/negative normal value.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001622 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p+0").isFiniteNonZero());
1623 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p+0").isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001624
1625 // Test positive/negative denormal value.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001626 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "0x1p-149").isFiniteNonZero());
1627 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p-149").isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001628
1629 // Test +/- Infinity.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001630 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), false).isFiniteNonZero());
1631 EXPECT_FALSE(APFloat::getInf(APFloat::IEEEsingle(), true).isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001632
1633 // Test +/- Zero.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001634 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), false).isFiniteNonZero());
1635 EXPECT_FALSE(APFloat::getZero(APFloat::IEEEsingle(), true).isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001636
1637 // Test +/- qNaN. +/- dont mean anything with qNaN but paranoia can't hurt in
1638 // this instance.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001639 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), false).isFiniteNonZero());
1640 EXPECT_FALSE(APFloat::getNaN(APFloat::IEEEsingle(), true).isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001641
1642 // Test +/- sNaN. +/- dont mean anything with sNaN but paranoia can't hurt in
1643 // this instance.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001644 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), false).isFiniteNonZero());
1645 EXPECT_FALSE(APFloat::getSNaN(APFloat::IEEEsingle(), true).isFiniteNonZero());
Michael Gottesmand95d4472013-06-19 21:00:17 +00001646}
1647
Michael Gottesmane45b1082013-06-24 09:58:07 +00001648TEST(APFloatTest, add) {
1649 // Test Special Cases against each other and normal values.
1650
1651 // TODOS/NOTES:
1652 // 1. Since we perform only default exception handling all operations with
1653 // signaling NaNs should have a result that is a quiet NaN. Currently they
1654 // return sNaN.
Michael Gottesmane45b1082013-06-24 09:58:07 +00001655
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001656 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
1657 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
1658 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
1659 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
1660 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
1661 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
1662 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
1663 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
1664 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
1665 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
1666 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
1667 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Michael Gottesmane45b1082013-06-24 09:58:07 +00001668 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001669 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Michael Gottesmane45b1082013-06-24 09:58:07 +00001670 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001671 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Michael Gottesmane45b1082013-06-24 09:58:07 +00001672
1673 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
1674
1675 const unsigned NumTests = 169;
1676 struct {
1677 APFloat x;
1678 APFloat y;
1679 const char *result;
1680 int status;
1681 int category;
1682 } SpecialCaseTests[NumTests] = {
1683 { PInf, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1684 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1685 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
1686 { PInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
1687 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1688#if 0
1689 // See Note 1.
1690 { PInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1691#endif
1692 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1693 { PInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1694 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1695 { PInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1696 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1697 { PInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1698 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
1699 { PInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
1700 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1701 { MInf, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1702 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
1703 { MInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001704 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001705#if 0
1706 // See Note 1.
1707 { MInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1708#endif
1709 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1710 { MInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1711 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1712 { MInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1713 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1714 { MInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1715 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
1716 { MInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
1717 { PZero, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1718 { PZero, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1719 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1720 { PZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1721 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1722#if 0
1723 // See Note 1.
1724 { PZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1725#endif
1726 { PZero, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
1727 { PZero, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
1728 { PZero, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1729 { PZero, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1730 { PZero, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
1731 { PZero, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
1732 { PZero, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
1733 { PZero, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
1734 { MZero, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1735 { MZero, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1736 { MZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1737 { MZero, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001738 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001739#if 0
1740 // See Note 1.
1741 { MZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1742#endif
1743 { MZero, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
1744 { MZero, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
1745 { MZero, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1746 { MZero, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1747 { MZero, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
1748 { MZero, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
1749 { MZero, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
1750 { MZero, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
1751 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
1752 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
1753 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
1754 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
1755 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1756#if 0
1757 // See Note 1.
1758 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1759#endif
1760 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
1761 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
1762 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
1763 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
1764 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
1765 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
1766 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
1767 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
1768#if 0
1769 // See Note 1.
1770 { SNaN, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1771 { SNaN, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1772 { SNaN, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1773 { SNaN, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1774 { SNaN, QNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1775 { SNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1776 { SNaN, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1777 { SNaN, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1778 { SNaN, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1779 { SNaN, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1780 { SNaN, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1781 { SNaN, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1782 { SNaN, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1783 { SNaN, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1784#endif
1785 { PNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1786 { PNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1787 { PNormalValue, PZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
1788 { PNormalValue, MZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
1789 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1790#if 0
1791 // See Note 1.
1792 { PNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1793#endif
1794 { PNormalValue, PNormalValue, "0x1p+1", APFloat::opOK, APFloat::fcNormal },
1795 { PNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1796 { PNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1797 { PNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1798 { PNormalValue, PSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1799 { PNormalValue, MSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1800 { PNormalValue, PSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1801 { PNormalValue, MSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1802 { MNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1803 { MNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1804 { MNormalValue, PZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
1805 { MNormalValue, MZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001806 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001807#if 0
1808 // See Note 1.
1809 { MNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1810#endif
1811 { MNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1812 { MNormalValue, MNormalValue, "-0x1p+1", APFloat::opOK, APFloat::fcNormal },
1813 { MNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1814 { MNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1815 { MNormalValue, PSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1816 { MNormalValue, MSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1817 { MNormalValue, PSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1818 { MNormalValue, MSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1819 { PLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1820 { PLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1821 { PLargestValue, PZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1822 { PLargestValue, MZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1823 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1824#if 0
1825 // See Note 1.
1826 { PLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1827#endif
1828 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1829 { PLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1830 { PLargestValue, PLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
1831 { PLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1832 { PLargestValue, PSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1833 { PLargestValue, MSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1834 { PLargestValue, PSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1835 { PLargestValue, MSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1836 { MLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1837 { MLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1838 { MLargestValue, PZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
1839 { MLargestValue, MZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001840 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001841#if 0
1842 // See Note 1.
1843 { MLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1844#endif
1845 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1846 { MLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1847 { MLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1848 { MLargestValue, MLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
1849 { MLargestValue, PSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1850 { MLargestValue, MSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1851 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1852 { MLargestValue, MSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1853 { PSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1854 { PSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1855 { PSmallestValue, PZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
1856 { PSmallestValue, MZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
1857 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1858#if 0
1859 // See Note 1.
1860 { PSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1861#endif
1862 { PSmallestValue, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1863 { PSmallestValue, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1864 { PSmallestValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1865 { PSmallestValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1866 { PSmallestValue, PSmallestValue, "0x1p-148", APFloat::opOK, APFloat::fcNormal },
1867 { PSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1868 { PSmallestValue, PSmallestNormalized, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
1869 { PSmallestValue, MSmallestNormalized, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
1870 { MSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1871 { MSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1872 { MSmallestValue, PZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
1873 { MSmallestValue, MZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001874 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001875#if 0
1876 // See Note 1.
1877 { MSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1878#endif
1879 { MSmallestValue, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1880 { MSmallestValue, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1881 { MSmallestValue, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1882 { MSmallestValue, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1883 { MSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1884 { MSmallestValue, MSmallestValue, "-0x1p-148", APFloat::opOK, APFloat::fcNormal },
1885 { MSmallestValue, PSmallestNormalized, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
1886 { MSmallestValue, MSmallestNormalized, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
1887 { PSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1888 { PSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1889 { PSmallestNormalized, PZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
1890 { PSmallestNormalized, MZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
1891 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
1892#if 0
1893// See Note 1.
1894 { PSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1895#endif
1896 { PSmallestNormalized, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1897 { PSmallestNormalized, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1898 { PSmallestNormalized, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1899 { PSmallestNormalized, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1900 { PSmallestNormalized, PSmallestValue, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
1901 { PSmallestNormalized, MSmallestValue, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
1902 { PSmallestNormalized, PSmallestNormalized, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
1903 { PSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1904 { MSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1905 { MSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1906 { MSmallestNormalized, PZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
1907 { MSmallestNormalized, MZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00001908 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmane45b1082013-06-24 09:58:07 +00001909#if 0
1910 // See Note 1.
1911 { MSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1912#endif
1913 { MSmallestNormalized, PNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1914 { MSmallestNormalized, MNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
1915 { MSmallestNormalized, PLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1916 { MSmallestNormalized, MLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
1917 { MSmallestNormalized, PSmallestValue, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
1918 { MSmallestNormalized, MSmallestValue, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
1919 { MSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
1920 { MSmallestNormalized, MSmallestNormalized, "-0x1p-125", APFloat::opOK, APFloat::fcNormal }
1921 };
1922
1923 for (size_t i = 0; i < NumTests; ++i) {
1924 APFloat x(SpecialCaseTests[i].x);
1925 APFloat y(SpecialCaseTests[i].y);
1926 APFloat::opStatus status = x.add(y, APFloat::rmNearestTiesToEven);
1927
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001928 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
Michael Gottesmane45b1082013-06-24 09:58:07 +00001929
Michael Gottesmane45b1082013-06-24 09:58:07 +00001930 EXPECT_TRUE(result.bitwiseIsEqual(x));
1931 EXPECT_TRUE((int)status == SpecialCaseTests[i].status);
1932 EXPECT_TRUE((int)x.getCategory() == SpecialCaseTests[i].category);
1933 }
1934}
1935
Michael Gottesman9368a532013-06-26 23:55:23 +00001936TEST(APFloatTest, subtract) {
1937 // Test Special Cases against each other and normal values.
1938
1939 // TODOS/NOTES:
1940 // 1. Since we perform only default exception handling all operations with
1941 // signaling NaNs should have a result that is a quiet NaN. Currently they
1942 // return sNaN.
Michael Gottesman9368a532013-06-26 23:55:23 +00001943
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001944 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
1945 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
1946 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
1947 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
1948 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
1949 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
1950 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
1951 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
1952 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
1953 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
1954 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
1955 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Michael Gottesman9368a532013-06-26 23:55:23 +00001956 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001957 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Michael Gottesman9368a532013-06-26 23:55:23 +00001958 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00001959 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Michael Gottesman9368a532013-06-26 23:55:23 +00001960
1961 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
1962
1963 const unsigned NumTests = 169;
1964 struct {
1965 APFloat x;
1966 APFloat y;
1967 const char *result;
1968 int status;
1969 int category;
1970 } SpecialCaseTests[NumTests] = {
1971 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1972 { PInf, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
1973 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
1974 { PInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
Stephen Canond3278282014-06-08 16:53:31 +00001975 { PInf, 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 { PInf, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00001979#endif
1980 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1981 { PInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1982 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1983 { PInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1984 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1985 { PInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
1986 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
1987 { PInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
1988 { MInf, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
1989 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
1990 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
1991 { MInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
Stephen Canond3278282014-06-08 16:53:31 +00001992 { MInf, 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 { MInf, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00001996#endif
1997 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1998 { MInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
1999 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2000 { MInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2001 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2002 { MInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2003 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2004 { MInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2005 { PZero, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2006 { PZero, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2007 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2008 { PZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Stephen Canond3278282014-06-08 16:53:31 +00002009 { PZero, 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 { PZero, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002013#endif
2014 { PZero, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2015 { PZero, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2016 { PZero, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2017 { PZero, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2018 { PZero, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2019 { PZero, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2020 { PZero, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2021 { PZero, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2022 { MZero, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2023 { MZero, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2024 { MZero, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2025 { MZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Stephen Canond3278282014-06-08 16:53:31 +00002026 { MZero, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002027#if 0
2028// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002029 { MZero, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002030#endif
2031 { MZero, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2032 { MZero, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2033 { MZero, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2034 { MZero, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2035 { MZero, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2036 { MZero, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2037 { MZero, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2038 { MZero, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2039 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
2040 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
2041 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
2042 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
2043 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2044#if 0
2045// See Note 1.
2046 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2047#endif
2048 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2049 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
2050 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2051 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2052 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2053 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
2054 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2055 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
2056#if 0
2057// See Note 1.
2058 { SNaN, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2059 { SNaN, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2060 { SNaN, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2061 { SNaN, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2062 { SNaN, QNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2063 { SNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2064 { SNaN, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2065 { SNaN, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2066 { SNaN, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2067 { SNaN, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2068 { SNaN, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2069 { SNaN, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2070 { SNaN, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2071 { SNaN, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2072#endif
2073 { PNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2074 { PNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2075 { PNormalValue, PZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2076 { PNormalValue, MZero, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002077 { PNormalValue, 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 { PNormalValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002081#endif
2082 { PNormalValue, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2083 { PNormalValue, MNormalValue, "0x1p+1", APFloat::opOK, APFloat::fcNormal },
2084 { PNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2085 { PNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2086 { PNormalValue, PSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2087 { PNormalValue, MSmallestValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2088 { PNormalValue, PSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2089 { PNormalValue, MSmallestNormalized, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2090 { MNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2091 { MNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2092 { MNormalValue, PZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2093 { MNormalValue, MZero, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002094 { MNormalValue, 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 { MNormalValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002098#endif
2099 { MNormalValue, PNormalValue, "-0x1p+1", APFloat::opOK, APFloat::fcNormal },
2100 { MNormalValue, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2101 { MNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2102 { MNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2103 { MNormalValue, PSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2104 { MNormalValue, MSmallestValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2105 { MNormalValue, PSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2106 { MNormalValue, MSmallestNormalized, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2107 { PLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2108 { PLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2109 { PLargestValue, PZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2110 { PLargestValue, MZero, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002111 { PLargestValue, 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 { PLargestValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002115#endif
2116 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2117 { PLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2118 { PLargestValue, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2119 { PLargestValue, MLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2120 { PLargestValue, PSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2121 { PLargestValue, MSmallestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2122 { PLargestValue, PSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2123 { PLargestValue, MSmallestNormalized, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2124 { MLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2125 { MLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2126 { MLargestValue, PZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2127 { MLargestValue, MZero, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002128 { MLargestValue, 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 { MLargestValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002132#endif
2133 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2134 { MLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2135 { MLargestValue, PLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2136 { MLargestValue, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2137 { MLargestValue, PSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2138 { MLargestValue, MSmallestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2139 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2140 { MLargestValue, MSmallestNormalized, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2141 { PSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2142 { PSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2143 { PSmallestValue, PZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2144 { PSmallestValue, MZero, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002145 { PSmallestValue, 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 { PSmallestValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002149#endif
2150 { PSmallestValue, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2151 { PSmallestValue, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2152 { PSmallestValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2153 { PSmallestValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2154 { PSmallestValue, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2155 { PSmallestValue, MSmallestValue, "0x1p-148", APFloat::opOK, APFloat::fcNormal },
2156 { PSmallestValue, PSmallestNormalized, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2157 { PSmallestValue, MSmallestNormalized, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2158 { MSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2159 { MSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2160 { MSmallestValue, PZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2161 { MSmallestValue, MZero, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002162 { MSmallestValue, 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 { MSmallestValue, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002166#endif
2167 { MSmallestValue, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2168 { MSmallestValue, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2169 { MSmallestValue, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2170 { MSmallestValue, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2171 { MSmallestValue, PSmallestValue, "-0x1p-148", APFloat::opOK, APFloat::fcNormal },
2172 { MSmallestValue, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2173 { MSmallestValue, PSmallestNormalized, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2174 { MSmallestValue, MSmallestNormalized, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2175 { PSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2176 { PSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2177 { PSmallestNormalized, PZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2178 { PSmallestNormalized, MZero, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002179 { PSmallestNormalized, 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 { PSmallestNormalized, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002183#endif
2184 { PSmallestNormalized, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2185 { PSmallestNormalized, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2186 { PSmallestNormalized, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2187 { PSmallestNormalized, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2188 { PSmallestNormalized, PSmallestValue, "0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2189 { PSmallestNormalized, MSmallestValue, "0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2190 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2191 { PSmallestNormalized, MSmallestNormalized, "0x1p-125", APFloat::opOK, APFloat::fcNormal },
2192 { MSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2193 { MSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2194 { MSmallestNormalized, PZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2195 { MSmallestNormalized, MZero, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
Stephen Canond3278282014-06-08 16:53:31 +00002196 { MSmallestNormalized, QNaN, "-nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002197#if 0
2198// See Note 1.
Stephen Canond3278282014-06-08 16:53:31 +00002199 { MSmallestNormalized, SNaN, "-nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesman9368a532013-06-26 23:55:23 +00002200#endif
2201 { MSmallestNormalized, PNormalValue, "-0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2202 { MSmallestNormalized, MNormalValue, "0x1p+0", APFloat::opInexact, APFloat::fcNormal },
2203 { MSmallestNormalized, PLargestValue, "-0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2204 { MSmallestNormalized, MLargestValue, "0x1.fffffep+127", APFloat::opInexact, APFloat::fcNormal },
2205 { MSmallestNormalized, PSmallestValue, "-0x1.000002p-126", APFloat::opOK, APFloat::fcNormal },
2206 { MSmallestNormalized, MSmallestValue, "-0x1.fffffcp-127", APFloat::opOK, APFloat::fcNormal },
2207 { MSmallestNormalized, PSmallestNormalized, "-0x1p-125", APFloat::opOK, APFloat::fcNormal },
2208 { MSmallestNormalized, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero }
2209 };
2210
2211 for (size_t i = 0; i < NumTests; ++i) {
2212 APFloat x(SpecialCaseTests[i].x);
2213 APFloat y(SpecialCaseTests[i].y);
2214 APFloat::opStatus status = x.subtract(y, APFloat::rmNearestTiesToEven);
2215
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002216 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
Michael Gottesman9368a532013-06-26 23:55:23 +00002217
Michael Gottesman9368a532013-06-26 23:55:23 +00002218 EXPECT_TRUE(result.bitwiseIsEqual(x));
2219 EXPECT_TRUE((int)status == SpecialCaseTests[i].status);
2220 EXPECT_TRUE((int)x.getCategory() == SpecialCaseTests[i].category);
2221 }
2222}
2223
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002224TEST(APFloatTest, multiply) {
2225 // Test Special Cases against each other and normal values.
2226
2227 // TODOS/NOTES:
2228 // 1. Since we perform only default exception handling all operations with
2229 // signaling NaNs should have a result that is a quiet NaN. Currently they
2230 // return sNaN.
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002231
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002232 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2233 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2234 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2235 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2236 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2237 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
2238 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2239 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2240 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2241 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2242 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2243 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002244 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002245 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002246 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002247 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002248
2249 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2250 const int UnderflowStatus = APFloat::opUnderflow | APFloat::opInexact;
2251
2252 const unsigned NumTests = 169;
2253 struct {
2254 APFloat x;
2255 APFloat y;
2256 const char *result;
2257 int status;
2258 int category;
2259 } SpecialCaseTests[NumTests] = {
2260 { PInf, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2261 { PInf, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2262 { PInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2263 { PInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2264 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2265#if 0
2266// See Note 1.
2267 { PInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2268#endif
2269 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2270 { PInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2271 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2272 { PInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2273 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2274 { PInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2275 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2276 { PInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2277 { MInf, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2278 { MInf, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2279 { MInf, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2280 { MInf, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002281 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002282#if 0
2283// See Note 1.
2284 { MInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2285#endif
2286 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2287 { MInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2288 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2289 { MInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2290 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2291 { MInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2292 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2293 { MInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2294 { PZero, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2295 { PZero, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2296 { PZero, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2297 { PZero, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2298 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2299#if 0
2300// See Note 1.
2301 { PZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2302#endif
2303 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2304 { PZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2305 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2306 { PZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2307 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2308 { PZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2309 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2310 { PZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2311 { MZero, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2312 { MZero, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2313 { MZero, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2314 { MZero, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002315 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002316#if 0
2317// See Note 1.
2318 { MZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2319#endif
2320 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2321 { MZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2322 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2323 { MZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2324 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2325 { MZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2326 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2327 { MZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2328 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002329 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002330 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002331 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002332 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2333#if 0
2334// See Note 1.
2335 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2336#endif
2337 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002338 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002339 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002340 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002341 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002342 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002343 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002344 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002345#if 0
2346// See Note 1.
2347 { SNaN, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2348 { SNaN, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2349 { SNaN, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2350 { SNaN, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2351 { SNaN, QNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2352 { SNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2353 { SNaN, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2354 { SNaN, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2355 { SNaN, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2356 { SNaN, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2357 { SNaN, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2358 { SNaN, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2359 { SNaN, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2360 { SNaN, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2361#endif
2362 { PNormalValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2363 { PNormalValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2364 { PNormalValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2365 { PNormalValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2366 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2367#if 0
2368// See Note 1.
2369 { PNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2370#endif
2371 { PNormalValue, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2372 { PNormalValue, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2373 { PNormalValue, PLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2374 { PNormalValue, MLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2375 { PNormalValue, PSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2376 { PNormalValue, MSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2377 { PNormalValue, PSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2378 { PNormalValue, MSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2379 { MNormalValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2380 { MNormalValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2381 { MNormalValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2382 { MNormalValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002383 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002384#if 0
2385// See Note 1.
2386 { MNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2387#endif
2388 { MNormalValue, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2389 { MNormalValue, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2390 { MNormalValue, PLargestValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2391 { MNormalValue, MLargestValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2392 { MNormalValue, PSmallestValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2393 { MNormalValue, MSmallestValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2394 { MNormalValue, PSmallestNormalized, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2395 { MNormalValue, MSmallestNormalized, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2396 { PLargestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2397 { PLargestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2398 { PLargestValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2399 { PLargestValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2400 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2401#if 0
2402// See Note 1.
2403 { PLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2404#endif
2405 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2406 { PLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2407 { PLargestValue, PLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2408 { PLargestValue, MLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2409 { PLargestValue, PSmallestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2410 { PLargestValue, MSmallestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2411 { PLargestValue, PSmallestNormalized, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2412 { PLargestValue, MSmallestNormalized, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2413 { MLargestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2414 { MLargestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2415 { MLargestValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2416 { MLargestValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002417 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002418#if 0
2419// See Note 1.
2420 { MLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2421#endif
2422 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2423 { MLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2424 { MLargestValue, PLargestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2425 { MLargestValue, MLargestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2426 { MLargestValue, PSmallestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2427 { MLargestValue, MSmallestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2428 { MLargestValue, PSmallestNormalized, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2429 { MLargestValue, MSmallestNormalized, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2430 { PSmallestValue, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2431 { PSmallestValue, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2432 { PSmallestValue, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2433 { PSmallestValue, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2434 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2435#if 0
2436// See Note 1.
2437 { PSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2438#endif
2439 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2440 { PSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2441 { PSmallestValue, PLargestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2442 { PSmallestValue, MLargestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2443 { PSmallestValue, PSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2444 { PSmallestValue, MSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2445 { PSmallestValue, PSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2446 { PSmallestValue, MSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2447 { MSmallestValue, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2448 { MSmallestValue, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2449 { MSmallestValue, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2450 { MSmallestValue, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002451 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002452#if 0
2453// See Note 1.
2454 { MSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2455#endif
2456 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2457 { MSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2458 { MSmallestValue, PLargestValue, "-0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2459 { MSmallestValue, MLargestValue, "0x1.fffffep-22", APFloat::opOK, APFloat::fcNormal },
2460 { MSmallestValue, PSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2461 { MSmallestValue, MSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2462 { MSmallestValue, PSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2463 { MSmallestValue, MSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2464 { PSmallestNormalized, PInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2465 { PSmallestNormalized, MInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2466 { PSmallestNormalized, PZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2467 { PSmallestNormalized, MZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2468 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2469#if 0
2470// See Note 1.
2471 { PSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2472#endif
2473 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2474 { PSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2475 { PSmallestNormalized, PLargestValue, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2476 { PSmallestNormalized, MLargestValue, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2477 { PSmallestNormalized, PSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2478 { PSmallestNormalized, MSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2479 { PSmallestNormalized, PSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2480 { PSmallestNormalized, MSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2481 { MSmallestNormalized, PInf, "-inf", APFloat::opOK, APFloat::fcInfinity },
2482 { MSmallestNormalized, MInf, "inf", APFloat::opOK, APFloat::fcInfinity },
2483 { MSmallestNormalized, PZero, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2484 { MSmallestNormalized, MZero, "0x0p+0", APFloat::opOK, APFloat::fcZero },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002485 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002486#if 0
2487// See Note 1.
2488 { MSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2489#endif
2490 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2491 { MSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2492 { MSmallestNormalized, PLargestValue, "-0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2493 { MSmallestNormalized, MLargestValue, "0x1.fffffep+1", APFloat::opOK, APFloat::fcNormal },
2494 { MSmallestNormalized, PSmallestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2495 { MSmallestNormalized, MSmallestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2496 { MSmallestNormalized, PSmallestNormalized, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2497 { MSmallestNormalized, MSmallestNormalized, "0x0p+0", UnderflowStatus, APFloat::fcZero }
2498 };
2499
2500 for (size_t i = 0; i < NumTests; ++i) {
2501 APFloat x(SpecialCaseTests[i].x);
2502 APFloat y(SpecialCaseTests[i].y);
2503 APFloat::opStatus status = x.multiply(y, APFloat::rmNearestTiesToEven);
2504
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002505 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002506
Michael Gottesman9debdfd2013-06-26 23:55:26 +00002507 EXPECT_TRUE(result.bitwiseIsEqual(x));
2508 EXPECT_TRUE((int)status == SpecialCaseTests[i].status);
2509 EXPECT_TRUE((int)x.getCategory() == SpecialCaseTests[i].category);
2510 }
2511}
Michael Gottesman9368a532013-06-26 23:55:23 +00002512
Michael Gottesman3eacb582013-06-27 00:42:00 +00002513TEST(APFloatTest, divide) {
2514 // Test Special Cases against each other and normal values.
2515
2516 // TODOS/NOTES:
2517 // 1. Since we perform only default exception handling all operations with
2518 // signaling NaNs should have a result that is a quiet NaN. Currently they
2519 // return sNaN.
Michael Gottesman3eacb582013-06-27 00:42:00 +00002520
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002521 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2522 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2523 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2524 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2525 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2526 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
2527 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2528 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2529 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2530 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2531 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2532 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Michael Gottesman3eacb582013-06-27 00:42:00 +00002533 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002534 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Michael Gottesman3eacb582013-06-27 00:42:00 +00002535 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002536 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Michael Gottesman3eacb582013-06-27 00:42:00 +00002537
2538 const int OverflowStatus = APFloat::opOverflow | APFloat::opInexact;
2539 const int UnderflowStatus = APFloat::opUnderflow | APFloat::opInexact;
2540
2541 const unsigned NumTests = 169;
2542 struct {
2543 APFloat x;
2544 APFloat y;
2545 const char *result;
2546 int status;
2547 int category;
2548 } SpecialCaseTests[NumTests] = {
2549 { PInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2550 { PInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2551 { PInf, PZero, "inf", APFloat::opOK, APFloat::fcInfinity },
2552 { PInf, MZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2553 { PInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2554#if 0
2555// See Note 1.
2556 { PInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2557#endif
2558 { PInf, PNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2559 { PInf, MNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2560 { PInf, PLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2561 { PInf, MLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2562 { PInf, PSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2563 { PInf, MSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2564 { PInf, PSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2565 { PInf, MSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2566 { MInf, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2567 { MInf, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2568 { MInf, PZero, "-inf", APFloat::opOK, APFloat::fcInfinity },
2569 { MInf, MZero, "inf", APFloat::opOK, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002570 { MInf, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002571#if 0
2572// See Note 1.
2573 { MInf, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2574#endif
2575 { MInf, PNormalValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2576 { MInf, MNormalValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2577 { MInf, PLargestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2578 { MInf, MLargestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2579 { MInf, PSmallestValue, "-inf", APFloat::opOK, APFloat::fcInfinity },
2580 { MInf, MSmallestValue, "inf", APFloat::opOK, APFloat::fcInfinity },
2581 { MInf, PSmallestNormalized, "-inf", APFloat::opOK, APFloat::fcInfinity },
2582 { MInf, MSmallestNormalized, "inf", APFloat::opOK, APFloat::fcInfinity },
2583 { PZero, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2584 { PZero, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2585 { PZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2586 { PZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2587 { PZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2588#if 0
2589// See Note 1.
2590 { PZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2591#endif
2592 { PZero, PNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2593 { PZero, MNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2594 { PZero, PLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2595 { PZero, MLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2596 { PZero, PSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2597 { PZero, MSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2598 { PZero, PSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2599 { PZero, MSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2600 { MZero, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2601 { MZero, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2602 { MZero, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2603 { MZero, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002604 { MZero, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002605#if 0
2606// See Note 1.
2607 { MZero, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2608#endif
2609 { MZero, PNormalValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2610 { MZero, MNormalValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2611 { MZero, PLargestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2612 { MZero, MLargestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2613 { MZero, PSmallestValue, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2614 { MZero, MSmallestValue, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2615 { MZero, PSmallestNormalized, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2616 { MZero, MSmallestNormalized, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2617 { QNaN, PInf, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002618 { QNaN, MInf, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002619 { QNaN, PZero, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002620 { QNaN, MZero, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002621 { QNaN, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2622#if 0
2623// See Note 1.
2624 { QNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2625#endif
2626 { QNaN, PNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002627 { QNaN, MNormalValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002628 { QNaN, PLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002629 { QNaN, MLargestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002630 { QNaN, PSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002631 { QNaN, MSmallestValue, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002632 { QNaN, PSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002633 { QNaN, MSmallestNormalized, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002634#if 0
2635// See Note 1.
2636 { SNaN, PInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2637 { SNaN, MInf, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2638 { SNaN, PZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2639 { SNaN, MZero, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2640 { SNaN, QNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2641 { SNaN, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2642 { SNaN, PNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2643 { SNaN, MNormalValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2644 { SNaN, PLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2645 { SNaN, MLargestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2646 { SNaN, PSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2647 { SNaN, MSmallestValue, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2648 { SNaN, PSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2649 { SNaN, MSmallestNormalized, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2650#endif
2651 { PNormalValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2652 { PNormalValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2653 { PNormalValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2654 { PNormalValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2655 { PNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2656#if 0
2657// See Note 1.
2658 { PNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2659#endif
2660 { PNormalValue, PNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2661 { PNormalValue, MNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2662 { PNormalValue, PLargestValue, "0x1p-128", UnderflowStatus, APFloat::fcNormal },
2663 { PNormalValue, MLargestValue, "-0x1p-128", UnderflowStatus, APFloat::fcNormal },
2664 { PNormalValue, PSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2665 { PNormalValue, MSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2666 { PNormalValue, PSmallestNormalized, "0x1p+126", APFloat::opOK, APFloat::fcNormal },
2667 { PNormalValue, MSmallestNormalized, "-0x1p+126", APFloat::opOK, APFloat::fcNormal },
2668 { MNormalValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2669 { MNormalValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2670 { MNormalValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2671 { MNormalValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002672 { MNormalValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002673#if 0
2674// See Note 1.
2675 { MNormalValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2676#endif
2677 { MNormalValue, PNormalValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2678 { MNormalValue, MNormalValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2679 { MNormalValue, PLargestValue, "-0x1p-128", UnderflowStatus, APFloat::fcNormal },
2680 { MNormalValue, MLargestValue, "0x1p-128", UnderflowStatus, APFloat::fcNormal },
2681 { MNormalValue, PSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2682 { MNormalValue, MSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2683 { MNormalValue, PSmallestNormalized, "-0x1p+126", APFloat::opOK, APFloat::fcNormal },
2684 { MNormalValue, MSmallestNormalized, "0x1p+126", APFloat::opOK, APFloat::fcNormal },
2685 { PLargestValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2686 { PLargestValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2687 { PLargestValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2688 { PLargestValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2689 { PLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2690#if 0
2691// See Note 1.
2692 { PLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2693#endif
2694 { PLargestValue, PNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2695 { PLargestValue, MNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2696 { PLargestValue, PLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2697 { PLargestValue, MLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2698 { PLargestValue, PSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2699 { PLargestValue, MSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2700 { PLargestValue, PSmallestNormalized, "inf", OverflowStatus, APFloat::fcInfinity },
2701 { PLargestValue, MSmallestNormalized, "-inf", OverflowStatus, APFloat::fcInfinity },
2702 { MLargestValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2703 { MLargestValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2704 { MLargestValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2705 { MLargestValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002706 { MLargestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002707#if 0
2708// See Note 1.
2709 { MLargestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2710#endif
2711 { MLargestValue, PNormalValue, "-0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2712 { MLargestValue, MNormalValue, "0x1.fffffep+127", APFloat::opOK, APFloat::fcNormal },
2713 { MLargestValue, PLargestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2714 { MLargestValue, MLargestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2715 { MLargestValue, PSmallestValue, "-inf", OverflowStatus, APFloat::fcInfinity },
2716 { MLargestValue, MSmallestValue, "inf", OverflowStatus, APFloat::fcInfinity },
2717 { MLargestValue, PSmallestNormalized, "-inf", OverflowStatus, APFloat::fcInfinity },
2718 { MLargestValue, MSmallestNormalized, "inf", OverflowStatus, APFloat::fcInfinity },
2719 { PSmallestValue, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2720 { PSmallestValue, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2721 { PSmallestValue, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2722 { PSmallestValue, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2723 { PSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2724#if 0
2725// See Note 1.
2726 { PSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2727#endif
2728 { PSmallestValue, PNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2729 { PSmallestValue, MNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2730 { PSmallestValue, PLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2731 { PSmallestValue, MLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2732 { PSmallestValue, PSmallestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2733 { PSmallestValue, MSmallestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2734 { PSmallestValue, PSmallestNormalized, "0x1p-23", APFloat::opOK, APFloat::fcNormal },
2735 { PSmallestValue, MSmallestNormalized, "-0x1p-23", APFloat::opOK, APFloat::fcNormal },
2736 { MSmallestValue, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2737 { MSmallestValue, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2738 { MSmallestValue, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2739 { MSmallestValue, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002740 { MSmallestValue, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002741#if 0
2742// See Note 1.
2743 { MSmallestValue, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2744#endif
2745 { MSmallestValue, PNormalValue, "-0x1p-149", APFloat::opOK, APFloat::fcNormal },
2746 { MSmallestValue, MNormalValue, "0x1p-149", APFloat::opOK, APFloat::fcNormal },
2747 { MSmallestValue, PLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2748 { MSmallestValue, MLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2749 { MSmallestValue, PSmallestValue, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2750 { MSmallestValue, MSmallestValue, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2751 { MSmallestValue, PSmallestNormalized, "-0x1p-23", APFloat::opOK, APFloat::fcNormal },
2752 { MSmallestValue, MSmallestNormalized, "0x1p-23", APFloat::opOK, APFloat::fcNormal },
2753 { PSmallestNormalized, PInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2754 { PSmallestNormalized, MInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2755 { PSmallestNormalized, PZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
2756 { PSmallestNormalized, MZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2757 { PSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
2758#if 0
2759// See Note 1.
2760 { PSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2761#endif
2762 { PSmallestNormalized, PNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2763 { PSmallestNormalized, MNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2764 { PSmallestNormalized, PLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2765 { PSmallestNormalized, MLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2766 { PSmallestNormalized, PSmallestValue, "0x1p+23", APFloat::opOK, APFloat::fcNormal },
2767 { PSmallestNormalized, MSmallestValue, "-0x1p+23", APFloat::opOK, APFloat::fcNormal },
2768 { PSmallestNormalized, PSmallestNormalized, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2769 { PSmallestNormalized, MSmallestNormalized, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2770 { MSmallestNormalized, PInf, "-0x0p+0", APFloat::opOK, APFloat::fcZero },
2771 { MSmallestNormalized, MInf, "0x0p+0", APFloat::opOK, APFloat::fcZero },
2772 { MSmallestNormalized, PZero, "-inf", APFloat::opDivByZero, APFloat::fcInfinity },
2773 { MSmallestNormalized, MZero, "inf", APFloat::opDivByZero, APFloat::fcInfinity },
Michael Gottesmanb0e688e2013-07-27 21:49:25 +00002774 { MSmallestNormalized, QNaN, "nan", APFloat::opOK, APFloat::fcNaN },
Michael Gottesman3eacb582013-06-27 00:42:00 +00002775#if 0
2776// See Note 1.
2777 { MSmallestNormalized, SNaN, "nan", APFloat::opInvalidOp, APFloat::fcNaN },
2778#endif
2779 { MSmallestNormalized, PNormalValue, "-0x1p-126", APFloat::opOK, APFloat::fcNormal },
2780 { MSmallestNormalized, MNormalValue, "0x1p-126", APFloat::opOK, APFloat::fcNormal },
2781 { MSmallestNormalized, PLargestValue, "-0x0p+0", UnderflowStatus, APFloat::fcZero },
2782 { MSmallestNormalized, MLargestValue, "0x0p+0", UnderflowStatus, APFloat::fcZero },
2783 { MSmallestNormalized, PSmallestValue, "-0x1p+23", APFloat::opOK, APFloat::fcNormal },
2784 { MSmallestNormalized, MSmallestValue, "0x1p+23", APFloat::opOK, APFloat::fcNormal },
2785 { MSmallestNormalized, PSmallestNormalized, "-0x1p+0", APFloat::opOK, APFloat::fcNormal },
2786 { MSmallestNormalized, MSmallestNormalized, "0x1p+0", APFloat::opOK, APFloat::fcNormal },
2787 };
2788
2789 for (size_t i = 0; i < NumTests; ++i) {
2790 APFloat x(SpecialCaseTests[i].x);
2791 APFloat y(SpecialCaseTests[i].y);
2792 APFloat::opStatus status = x.divide(y, APFloat::rmNearestTiesToEven);
2793
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002794 APFloat result(APFloat::IEEEsingle(), SpecialCaseTests[i].result);
Michael Gottesman3eacb582013-06-27 00:42:00 +00002795
2796 EXPECT_TRUE(result.bitwiseIsEqual(x));
2797 EXPECT_TRUE((int)status == SpecialCaseTests[i].status);
2798 EXPECT_TRUE((int)x.getCategory() == SpecialCaseTests[i].category);
2799 }
2800}
2801
Chandler Carruthdf782e42014-10-09 23:26:15 +00002802TEST(APFloatTest, operatorOverloads) {
2803 // This is mostly testing that these operator overloads compile.
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002804 APFloat One = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2805 APFloat Two = APFloat(APFloat::IEEEsingle(), "0x2p+0");
Chandler Carruthdf782e42014-10-09 23:26:15 +00002806 EXPECT_TRUE(Two.bitwiseIsEqual(One + One));
2807 EXPECT_TRUE(One.bitwiseIsEqual(Two - One));
2808 EXPECT_TRUE(Two.bitwiseIsEqual(One * Two));
2809 EXPECT_TRUE(One.bitwiseIsEqual(Two / Two));
2810}
Chandler Carruth7468b062014-10-10 04:17:04 +00002811
Chandler Carruthafe56ae2014-10-10 08:27:22 +00002812TEST(APFloatTest, abs) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002813 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2814 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2815 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2816 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2817 APFloat PQNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2818 APFloat MQNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
2819 APFloat PSNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
2820 APFloat MSNaN = APFloat::getSNaN(APFloat::IEEEsingle(), true);
2821 APFloat PNormalValue = APFloat(APFloat::IEEEsingle(), "0x1p+0");
2822 APFloat MNormalValue = APFloat(APFloat::IEEEsingle(), "-0x1p+0");
2823 APFloat PLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), false);
2824 APFloat MLargestValue = APFloat::getLargest(APFloat::IEEEsingle(), true);
2825 APFloat PSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), false);
2826 APFloat MSmallestValue = APFloat::getSmallest(APFloat::IEEEsingle(), true);
Chandler Carruthafe56ae2014-10-10 08:27:22 +00002827 APFloat PSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002828 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false);
Chandler Carruthafe56ae2014-10-10 08:27:22 +00002829 APFloat MSmallestNormalized =
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002830 APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true);
Chandler Carruthafe56ae2014-10-10 08:27:22 +00002831
2832 EXPECT_TRUE(PInf.bitwiseIsEqual(abs(PInf)));
2833 EXPECT_TRUE(PInf.bitwiseIsEqual(abs(MInf)));
2834 EXPECT_TRUE(PZero.bitwiseIsEqual(abs(PZero)));
2835 EXPECT_TRUE(PZero.bitwiseIsEqual(abs(MZero)));
2836 EXPECT_TRUE(PQNaN.bitwiseIsEqual(abs(PQNaN)));
2837 EXPECT_TRUE(PQNaN.bitwiseIsEqual(abs(MQNaN)));
2838 EXPECT_TRUE(PSNaN.bitwiseIsEqual(abs(PSNaN)));
2839 EXPECT_TRUE(PSNaN.bitwiseIsEqual(abs(MSNaN)));
2840 EXPECT_TRUE(PNormalValue.bitwiseIsEqual(abs(PNormalValue)));
2841 EXPECT_TRUE(PNormalValue.bitwiseIsEqual(abs(MNormalValue)));
2842 EXPECT_TRUE(PLargestValue.bitwiseIsEqual(abs(PLargestValue)));
2843 EXPECT_TRUE(PLargestValue.bitwiseIsEqual(abs(MLargestValue)));
2844 EXPECT_TRUE(PSmallestValue.bitwiseIsEqual(abs(PSmallestValue)));
2845 EXPECT_TRUE(PSmallestValue.bitwiseIsEqual(abs(MSmallestValue)));
2846 EXPECT_TRUE(PSmallestNormalized.bitwiseIsEqual(abs(PSmallestNormalized)));
2847 EXPECT_TRUE(PSmallestNormalized.bitwiseIsEqual(abs(MSmallestNormalized)));
2848}
2849
Matt Arsenault8a27aee2017-01-25 04:54:34 +00002850TEST(APFloatTest, neg) {
2851 APFloat One = APFloat(APFloat::IEEEsingle(), "1.0");
2852 APFloat NegOne = APFloat(APFloat::IEEEsingle(), "-1.0");
2853 APFloat Zero = APFloat::getZero(APFloat::IEEEsingle(), false);
2854 APFloat NegZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2855 APFloat Inf = APFloat::getInf(APFloat::IEEEsingle(), false);
2856 APFloat NegInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2857 APFloat QNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2858 APFloat NegQNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
2859
2860 EXPECT_TRUE(NegOne.bitwiseIsEqual(neg(One)));
2861 EXPECT_TRUE(One.bitwiseIsEqual(neg(NegOne)));
2862 EXPECT_TRUE(NegZero.bitwiseIsEqual(neg(Zero)));
2863 EXPECT_TRUE(Zero.bitwiseIsEqual(neg(NegZero)));
2864 EXPECT_TRUE(NegInf.bitwiseIsEqual(neg(Inf)));
2865 EXPECT_TRUE(Inf.bitwiseIsEqual(neg(NegInf)));
2866 EXPECT_TRUE(NegInf.bitwiseIsEqual(neg(Inf)));
2867 EXPECT_TRUE(Inf.bitwiseIsEqual(neg(NegInf)));
2868 EXPECT_TRUE(NegQNaN.bitwiseIsEqual(neg(QNaN)));
2869 EXPECT_TRUE(QNaN.bitwiseIsEqual(neg(NegQNaN)));
2870}
2871
Chandler Carruthca067142014-10-10 05:14:12 +00002872TEST(APFloatTest, ilogb) {
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002873 EXPECT_EQ(-1074, ilogb(APFloat::getSmallest(APFloat::IEEEdouble(), false)));
2874 EXPECT_EQ(-1074, ilogb(APFloat::getSmallest(APFloat::IEEEdouble(), true)));
2875 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1024")));
2876 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023")));
2877 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023")));
2878 EXPECT_EQ(-51, ilogb(APFloat(APFloat::IEEEdouble(), "0x1p-51")));
2879 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1023")));
2880 EXPECT_EQ(-2, ilogb(APFloat(APFloat::IEEEdouble(), "0x0.ffffp-1")));
2881 EXPECT_EQ(-1023, ilogb(APFloat(APFloat::IEEEdouble(), "0x1.fffep-1023")));
2882 EXPECT_EQ(1023, ilogb(APFloat::getLargest(APFloat::IEEEdouble(), false)));
2883 EXPECT_EQ(1023, ilogb(APFloat::getLargest(APFloat::IEEEdouble(), true)));
Matt Arsenault69fdf9b2016-03-13 05:12:32 +00002884
2885
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002886 EXPECT_EQ(0, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p+0")));
2887 EXPECT_EQ(0, ilogb(APFloat(APFloat::IEEEsingle(), "-0x1p+0")));
2888 EXPECT_EQ(42, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p+42")));
2889 EXPECT_EQ(-42, ilogb(APFloat(APFloat::IEEEsingle(), "0x1p-42")));
Chandler Carruth7468b062014-10-10 04:17:04 +00002890
Chandler Carruthca067142014-10-10 05:14:12 +00002891 EXPECT_EQ(APFloat::IEK_Inf,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002892 ilogb(APFloat::getInf(APFloat::IEEEsingle(), false)));
Chandler Carruthca067142014-10-10 05:14:12 +00002893 EXPECT_EQ(APFloat::IEK_Inf,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002894 ilogb(APFloat::getInf(APFloat::IEEEsingle(), true)));
Chandler Carruthca067142014-10-10 05:14:12 +00002895 EXPECT_EQ(APFloat::IEK_Zero,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002896 ilogb(APFloat::getZero(APFloat::IEEEsingle(), false)));
Chandler Carruthca067142014-10-10 05:14:12 +00002897 EXPECT_EQ(APFloat::IEK_Zero,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002898 ilogb(APFloat::getZero(APFloat::IEEEsingle(), true)));
Chandler Carruthca067142014-10-10 05:14:12 +00002899 EXPECT_EQ(APFloat::IEK_NaN,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002900 ilogb(APFloat::getNaN(APFloat::IEEEsingle(), false)));
Chandler Carruthca067142014-10-10 05:14:12 +00002901 EXPECT_EQ(APFloat::IEK_NaN,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002902 ilogb(APFloat::getSNaN(APFloat::IEEEsingle(), false)));
Chandler Carruth7468b062014-10-10 04:17:04 +00002903
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002904 EXPECT_EQ(127, ilogb(APFloat::getLargest(APFloat::IEEEsingle(), false)));
2905 EXPECT_EQ(127, ilogb(APFloat::getLargest(APFloat::IEEEsingle(), true)));
Matt Arsenault69fdf9b2016-03-13 05:12:32 +00002906
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002907 EXPECT_EQ(-149, ilogb(APFloat::getSmallest(APFloat::IEEEsingle(), false)));
2908 EXPECT_EQ(-149, ilogb(APFloat::getSmallest(APFloat::IEEEsingle(), true)));
Chandler Carruthca067142014-10-10 05:14:12 +00002909 EXPECT_EQ(-126,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002910 ilogb(APFloat::getSmallestNormalized(APFloat::IEEEsingle(), false)));
Chandler Carruthca067142014-10-10 05:14:12 +00002911 EXPECT_EQ(-126,
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002912 ilogb(APFloat::getSmallestNormalized(APFloat::IEEEsingle(), true)));
Chandler Carruth7468b062014-10-10 04:17:04 +00002913}
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002914
2915TEST(APFloatTest, scalbn) {
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002916
2917 const APFloat::roundingMode RM = APFloat::rmNearestTiesToEven;
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002918 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002919 APFloat(APFloat::IEEEsingle(), "0x1p+0")
2920 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 0, RM)));
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002921 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002922 APFloat(APFloat::IEEEsingle(), "0x1p+42")
2923 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 42, RM)));
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002924 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002925 APFloat(APFloat::IEEEsingle(), "0x1p-42")
2926 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), -42, RM)));
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002927
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002928 APFloat PInf = APFloat::getInf(APFloat::IEEEsingle(), false);
2929 APFloat MInf = APFloat::getInf(APFloat::IEEEsingle(), true);
2930 APFloat PZero = APFloat::getZero(APFloat::IEEEsingle(), false);
2931 APFloat MZero = APFloat::getZero(APFloat::IEEEsingle(), true);
2932 APFloat QPNaN = APFloat::getNaN(APFloat::IEEEsingle(), false);
2933 APFloat QMNaN = APFloat::getNaN(APFloat::IEEEsingle(), true);
2934 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEsingle(), false);
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00002935
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002936 EXPECT_TRUE(PInf.bitwiseIsEqual(scalbn(PInf, 0, RM)));
2937 EXPECT_TRUE(MInf.bitwiseIsEqual(scalbn(MInf, 0, RM)));
2938 EXPECT_TRUE(PZero.bitwiseIsEqual(scalbn(PZero, 0, RM)));
2939 EXPECT_TRUE(MZero.bitwiseIsEqual(scalbn(MZero, 0, RM)));
2940 EXPECT_TRUE(QPNaN.bitwiseIsEqual(scalbn(QPNaN, 0, RM)));
2941 EXPECT_TRUE(QMNaN.bitwiseIsEqual(scalbn(QMNaN, 0, RM)));
Matt Arsenaultea00b492016-03-23 23:51:45 +00002942 EXPECT_FALSE(scalbn(SNaN, 0, RM).isSignaling());
2943
2944 APFloat ScalbnSNaN = scalbn(SNaN, 1, RM);
2945 EXPECT_TRUE(ScalbnSNaN.isNaN() && !ScalbnSNaN.isSignaling());
2946
2947 // Make sure highest bit of payload is preserved.
2948 const APInt Payload(64, (UINT64_C(1) << 50) |
2949 (UINT64_C(1) << 49) |
2950 (UINT64_C(1234) << 32) |
2951 1);
2952
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002953 APFloat SNaNWithPayload = APFloat::getSNaN(APFloat::IEEEdouble(), false,
Matt Arsenaultea00b492016-03-23 23:51:45 +00002954 &Payload);
2955 APFloat QuietPayload = scalbn(SNaNWithPayload, 1, RM);
2956 EXPECT_TRUE(QuietPayload.isNaN() && !QuietPayload.isSignaling());
2957 EXPECT_EQ(Payload, QuietPayload.bitcastToAPInt().getLoBits(51));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002958
2959 EXPECT_TRUE(PInf.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002960 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+0"), 128, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002961 EXPECT_TRUE(MInf.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002962 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p+0"), 128, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002963 EXPECT_TRUE(PInf.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002964 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p+127"), 1, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002965 EXPECT_TRUE(PZero.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002966 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p-127"), -127, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002967 EXPECT_TRUE(MZero.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002968 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p-127"), -127, RM)));
2969 EXPECT_TRUE(APFloat(APFloat::IEEEsingle(), "-0x1p-149").bitwiseIsEqual(
2970 scalbn(APFloat(APFloat::IEEEsingle(), "-0x1p-127"), -22, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002971 EXPECT_TRUE(PZero.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002972 scalbn(APFloat(APFloat::IEEEsingle(), "0x1p-126"), -24, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002973
2974
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002975 APFloat SmallestF64 = APFloat::getSmallest(APFloat::IEEEdouble(), false);
2976 APFloat NegSmallestF64 = APFloat::getSmallest(APFloat::IEEEdouble(), true);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002977
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002978 APFloat LargestF64 = APFloat::getLargest(APFloat::IEEEdouble(), false);
2979 APFloat NegLargestF64 = APFloat::getLargest(APFloat::IEEEdouble(), true);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002980
2981 APFloat SmallestNormalizedF64
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002982 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002983 APFloat NegSmallestNormalizedF64
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002984 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002985
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002986 APFloat LargestDenormalF64(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023");
2987 APFloat NegLargestDenormalF64(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023");
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002988
2989
2990 EXPECT_TRUE(SmallestF64.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002991 scalbn(APFloat(APFloat::IEEEdouble(), "0x1p-1074"), 0, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002992 EXPECT_TRUE(NegSmallestF64.bitwiseIsEqual(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002993 scalbn(APFloat(APFloat::IEEEdouble(), "-0x1p-1074"), 0, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002994
Stephan Bergmann17c7f702016-12-14 11:57:17 +00002995 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1023")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00002996 .bitwiseIsEqual(scalbn(SmallestF64, 2097, RM)));
2997
2998 EXPECT_TRUE(scalbn(SmallestF64, -2097, RM).isPosZero());
2999 EXPECT_TRUE(scalbn(SmallestF64, -2098, RM).isPosZero());
3000 EXPECT_TRUE(scalbn(SmallestF64, -2099, RM).isPosZero());
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003001 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1022")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003002 .bitwiseIsEqual(scalbn(SmallestF64, 2096, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003003 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+1023")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003004 .bitwiseIsEqual(scalbn(SmallestF64, 2097, RM)));
3005 EXPECT_TRUE(scalbn(SmallestF64, 2098, RM).isInfinity());
3006 EXPECT_TRUE(scalbn(SmallestF64, 2099, RM).isInfinity());
3007
3008 // Test for integer overflows when adding to exponent.
3009 EXPECT_TRUE(scalbn(SmallestF64, -INT_MAX, RM).isPosZero());
3010 EXPECT_TRUE(scalbn(LargestF64, INT_MAX, RM).isInfinity());
3011
3012 EXPECT_TRUE(LargestDenormalF64
3013 .bitwiseIsEqual(scalbn(LargestDenormalF64, 0, RM)));
3014 EXPECT_TRUE(NegLargestDenormalF64
3015 .bitwiseIsEqual(scalbn(NegLargestDenormalF64, 0, RM)));
3016
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003017 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1022")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003018 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003019 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1021")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003020 .bitwiseIsEqual(scalbn(NegLargestDenormalF64, 2, RM)));
3021
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003022 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+1")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003023 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1024, RM)));
3024 EXPECT_TRUE(scalbn(LargestDenormalF64, -1023, RM).isPosZero());
3025 EXPECT_TRUE(scalbn(LargestDenormalF64, -1024, RM).isPosZero());
3026 EXPECT_TRUE(scalbn(LargestDenormalF64, -2048, RM).isPosZero());
3027 EXPECT_TRUE(scalbn(LargestDenormalF64, 2047, RM).isInfinity());
3028 EXPECT_TRUE(scalbn(LargestDenormalF64, 2098, RM).isInfinity());
3029 EXPECT_TRUE(scalbn(LargestDenormalF64, 2099, RM).isInfinity());
3030
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003031 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-2")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003032 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1021, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003033 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003034 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1022, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003035 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+0")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003036 .bitwiseIsEqual(scalbn(LargestDenormalF64, 1023, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003037 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep+1023")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003038 .bitwiseIsEqual(scalbn(LargestDenormalF64, 2046, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003039 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p+974")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003040 .bitwiseIsEqual(scalbn(SmallestF64, 2048, RM)));
3041
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003042 APFloat RandomDenormalF64(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+51");
3043 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-972")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003044 .bitwiseIsEqual(scalbn(RandomDenormalF64, -1023, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003045 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003046 .bitwiseIsEqual(scalbn(RandomDenormalF64, -52, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003047 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-2")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003048 .bitwiseIsEqual(scalbn(RandomDenormalF64, -53, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003049 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+0")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003050 .bitwiseIsEqual(scalbn(RandomDenormalF64, -51, RM)));
3051
3052 EXPECT_TRUE(scalbn(RandomDenormalF64, -2097, RM).isPosZero());
3053 EXPECT_TRUE(scalbn(RandomDenormalF64, -2090, RM).isPosZero());
3054
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00003055
3056 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003057 APFloat(APFloat::IEEEdouble(), "-0x1p-1073")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003058 .bitwiseIsEqual(scalbn(NegLargestF64, -2097, RM)));
3059
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00003060 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003061 APFloat(APFloat::IEEEdouble(), "-0x1p-1024")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003062 .bitwiseIsEqual(scalbn(NegLargestF64, -2048, RM)));
3063
3064 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003065 APFloat(APFloat::IEEEdouble(), "0x1p-1073")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003066 .bitwiseIsEqual(scalbn(LargestF64, -2097, RM)));
3067
3068 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003069 APFloat(APFloat::IEEEdouble(), "0x1p-1074")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003070 .bitwiseIsEqual(scalbn(LargestF64, -2098, RM)));
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003071 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1074")
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003072 .bitwiseIsEqual(scalbn(NegLargestF64, -2098, RM)));
3073 EXPECT_TRUE(scalbn(NegLargestF64, -2099, RM).isNegZero());
3074 EXPECT_TRUE(scalbn(LargestF64, 1, RM).isInfinity());
3075
3076
3077 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003078 APFloat(APFloat::IEEEdouble(), "0x1p+0")
3079 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEdouble(), "0x1p+52"), -52, RM)));
Matt Arsenaultafa31cf2016-03-13 05:11:51 +00003080
3081 EXPECT_TRUE(
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003082 APFloat(APFloat::IEEEdouble(), "0x1p-103")
3083 .bitwiseIsEqual(scalbn(APFloat(APFloat::IEEEdouble(), "0x1p-51"), -52, RM)));
Chandler Carruthd9edd1e2014-10-10 04:54:30 +00003084}
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003085
3086TEST(APFloatTest, frexp) {
3087 const APFloat::roundingMode RM = APFloat::rmNearestTiesToEven;
3088
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003089 APFloat PZero = APFloat::getZero(APFloat::IEEEdouble(), false);
3090 APFloat MZero = APFloat::getZero(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003091 APFloat One(1.0);
3092 APFloat MOne(-1.0);
3093 APFloat Two(2.0);
3094 APFloat MTwo(-2.0);
3095
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003096 APFloat LargestDenormal(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1023");
3097 APFloat NegLargestDenormal(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1023");
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003098
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003099 APFloat Smallest = APFloat::getSmallest(APFloat::IEEEdouble(), false);
3100 APFloat NegSmallest = APFloat::getSmallest(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003101
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003102 APFloat Largest = APFloat::getLargest(APFloat::IEEEdouble(), false);
3103 APFloat NegLargest = APFloat::getLargest(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003104
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003105 APFloat PInf = APFloat::getInf(APFloat::IEEEdouble(), false);
3106 APFloat MInf = APFloat::getInf(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003107
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003108 APFloat QPNaN = APFloat::getNaN(APFloat::IEEEdouble(), false);
3109 APFloat QMNaN = APFloat::getNaN(APFloat::IEEEdouble(), true);
3110 APFloat SNaN = APFloat::getSNaN(APFloat::IEEEdouble(), false);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003111
3112 // Make sure highest bit of payload is preserved.
3113 const APInt Payload(64, (UINT64_C(1) << 50) |
3114 (UINT64_C(1) << 49) |
3115 (UINT64_C(1234) << 32) |
3116 1);
3117
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003118 APFloat SNaNWithPayload = APFloat::getSNaN(APFloat::IEEEdouble(), false,
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003119 &Payload);
3120
3121 APFloat SmallestNormalized
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003122 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), false);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003123 APFloat NegSmallestNormalized
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003124 = APFloat::getSmallestNormalized(APFloat::IEEEdouble(), true);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003125
3126 int Exp;
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003127 APFloat Frac(APFloat::IEEEdouble());
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003128
3129
3130 Frac = frexp(PZero, Exp, RM);
3131 EXPECT_EQ(0, Exp);
3132 EXPECT_TRUE(Frac.isPosZero());
3133
3134 Frac = frexp(MZero, Exp, RM);
3135 EXPECT_EQ(0, Exp);
3136 EXPECT_TRUE(Frac.isNegZero());
3137
3138
3139 Frac = frexp(One, Exp, RM);
3140 EXPECT_EQ(1, 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(MOne, Exp, RM);
3144 EXPECT_EQ(1, 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 Frac = frexp(LargestDenormal, Exp, RM);
3148 EXPECT_EQ(-1022, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003149 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.ffffffffffffep-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003150
3151 Frac = frexp(NegLargestDenormal, Exp, RM);
3152 EXPECT_EQ(-1022, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003153 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.ffffffffffffep-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003154
3155
3156 Frac = frexp(Smallest, Exp, RM);
3157 EXPECT_EQ(-1073, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003158 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003159
3160 Frac = frexp(NegSmallest, Exp, RM);
3161 EXPECT_EQ(-1073, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003162 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1p-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003163
3164
3165 Frac = frexp(Largest, Exp, RM);
3166 EXPECT_EQ(1024, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003167 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.fffffffffffffp-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003168
3169 Frac = frexp(NegLargest, Exp, RM);
3170 EXPECT_EQ(1024, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003171 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "-0x1.fffffffffffffp-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003172
3173
3174 Frac = frexp(PInf, Exp, RM);
3175 EXPECT_EQ(INT_MAX, Exp);
3176 EXPECT_TRUE(Frac.isInfinity() && !Frac.isNegative());
3177
3178 Frac = frexp(MInf, Exp, RM);
3179 EXPECT_EQ(INT_MAX, Exp);
3180 EXPECT_TRUE(Frac.isInfinity() && Frac.isNegative());
3181
3182 Frac = frexp(QPNaN, Exp, RM);
3183 EXPECT_EQ(INT_MIN, Exp);
3184 EXPECT_TRUE(Frac.isNaN());
3185
3186 Frac = frexp(QMNaN, Exp, RM);
3187 EXPECT_EQ(INT_MIN, Exp);
3188 EXPECT_TRUE(Frac.isNaN());
3189
3190 Frac = frexp(SNaN, Exp, RM);
3191 EXPECT_EQ(INT_MIN, Exp);
3192 EXPECT_TRUE(Frac.isNaN() && !Frac.isSignaling());
3193
3194 Frac = frexp(SNaNWithPayload, Exp, RM);
3195 EXPECT_EQ(INT_MIN, Exp);
3196 EXPECT_TRUE(Frac.isNaN() && !Frac.isSignaling());
3197 EXPECT_EQ(Payload, Frac.bitcastToAPInt().getLoBits(51));
3198
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003199 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x0.ffffp-1"), Exp, RM);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003200 EXPECT_EQ(-1, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003201 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.fffep-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003202
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003203 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x1p-51"), Exp, RM);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003204 EXPECT_EQ(-50, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003205 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1p-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003206
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003207 Frac = frexp(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp+51"), Exp, RM);
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003208 EXPECT_EQ(52, Exp);
Stephan Bergmann17c7f702016-12-14 11:57:17 +00003209 EXPECT_TRUE(APFloat(APFloat::IEEEdouble(), "0x1.c60f120d9f87cp-1").bitwiseIsEqual(Frac));
Matt Arsenaultc25a7112016-03-21 16:49:16 +00003210}
Tim Shen44bde892016-12-12 21:59:30 +00003211
Stephen Canon157c8692017-03-31 20:31:33 +00003212TEST(APFloatTest, mod) {
3213 {
3214 APFloat f1(APFloat::IEEEdouble(), "1.5");
3215 APFloat f2(APFloat::IEEEdouble(), "1.0");
3216 APFloat expected(APFloat::IEEEdouble(), "0.5");
3217 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3218 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3219 }
3220 {
3221 APFloat f1(APFloat::IEEEdouble(), "0.5");
3222 APFloat f2(APFloat::IEEEdouble(), "1.0");
3223 APFloat expected(APFloat::IEEEdouble(), "0.5");
3224 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3225 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3226 }
3227 {
3228 APFloat f1(APFloat::IEEEdouble(), "0x1.3333333333333p-2"); // 0.3
3229 APFloat f2(APFloat::IEEEdouble(), "0x1.47ae147ae147bp-7"); // 0.01
3230 APFloat expected(APFloat::IEEEdouble(),
3231 "0x1.47ae147ae1471p-7"); // 0.009999999999999983
3232 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3233 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3234 }
3235 {
3236 APFloat f1(APFloat::IEEEdouble(), "0x1p64"); // 1.8446744073709552e19
3237 APFloat f2(APFloat::IEEEdouble(), "1.5");
3238 APFloat expected(APFloat::IEEEdouble(), "1.0");
3239 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3240 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3241 }
3242 {
3243 APFloat f1(APFloat::IEEEdouble(), "0x1p1000");
3244 APFloat f2(APFloat::IEEEdouble(), "0x1p-1000");
3245 APFloat expected(APFloat::IEEEdouble(), "0.0");
3246 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3247 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3248 }
3249 {
3250 APFloat f1(APFloat::IEEEdouble(), "0.0");
3251 APFloat f2(APFloat::IEEEdouble(), "1.0");
3252 APFloat expected(APFloat::IEEEdouble(), "0.0");
3253 EXPECT_EQ(f1.mod(f2), APFloat::opOK);
3254 EXPECT_TRUE(f1.bitwiseIsEqual(expected));
3255 }
3256 {
3257 APFloat f1(APFloat::IEEEdouble(), "1.0");
3258 APFloat f2(APFloat::IEEEdouble(), "0.0");
3259 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3260 EXPECT_TRUE(f1.isNaN());
3261 }
3262 {
3263 APFloat f1(APFloat::IEEEdouble(), "0.0");
3264 APFloat f2(APFloat::IEEEdouble(), "0.0");
3265 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3266 EXPECT_TRUE(f1.isNaN());
3267 }
3268 {
3269 APFloat f1 = APFloat::getInf(APFloat::IEEEdouble(), false);
3270 APFloat f2(APFloat::IEEEdouble(), "1.0");
3271 EXPECT_EQ(f1.mod(f2), APFloat::opInvalidOp);
3272 EXPECT_TRUE(f1.isNaN());
3273 }
3274}
3275
Tim Shen44bde892016-12-12 21:59:30 +00003276TEST(APFloatTest, PPCDoubleDoubleAddSpecial) {
3277 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t,
Stephen Canon29a9ba22017-03-31 20:35:02 +00003278 APFloat::fltCategory, APFloat::roundingMode>;
3279 DataType Data[] = {
Tim Shen44bde892016-12-12 21:59:30 +00003280 // (1 + 0) + (-1 + 0) = fcZero
Tim Shen18e7ae62016-12-12 22:16:08 +00003281 std::make_tuple(0x3ff0000000000000ull, 0, 0xbff0000000000000ull, 0,
3282 APFloat::fcZero, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003283 // LDBL_MAX + (1.1 >> (1023 - 106) + 0)) = fcInfinity
Tim Shen18e7ae62016-12-12 22:16:08 +00003284 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3285 0x7948000000000000ull, 0ull, APFloat::fcInfinity,
3286 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003287 // TODO: change the 4th 0x75effffffffffffe to 0x75efffffffffffff when
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003288 // semPPCDoubleDoubleLegacy is gone.
Tim Shen44bde892016-12-12 21:59:30 +00003289 // LDBL_MAX + (1.011111... >> (1023 - 106) + (1.1111111...0 >> (1023 -
3290 // 160))) = fcNormal
Tim Shen18e7ae62016-12-12 22:16:08 +00003291 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3292 0x7947ffffffffffffull, 0x75effffffffffffeull,
3293 APFloat::fcNormal, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003294 // LDBL_MAX + (1.1 >> (1023 - 106) + 0)) = fcInfinity
Tim Shen18e7ae62016-12-12 22:16:08 +00003295 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3296 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3297 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003298 // NaN + (1 + 0) = fcNaN
Tim Shen18e7ae62016-12-12 22:16:08 +00003299 std::make_tuple(0x7ff8000000000000ull, 0, 0x3ff0000000000000ull, 0,
3300 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003301 };
3302
3303 for (auto Tp : Data) {
3304 uint64_t Op1[2], Op2[2];
3305 APFloat::fltCategory Expected;
3306 APFloat::roundingMode RM;
3307 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected, RM) = Tp;
3308
Tim Shen7f127622017-01-24 00:19:45 +00003309 {
3310 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3311 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3312 A1.add(A2, RM);
Tim Shen44bde892016-12-12 21:59:30 +00003313
Tim Shen7f127622017-01-24 00:19:45 +00003314 EXPECT_EQ(Expected, A1.getCategory())
3315 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
3316 Op2[0], Op2[1])
3317 .str();
3318 }
3319 {
3320 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3321 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3322 A2.add(A1, RM);
3323
3324 EXPECT_EQ(Expected, A2.getCategory())
3325 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
3326 Op1[0], Op1[1])
3327 .str();
3328 }
Tim Shen44bde892016-12-12 21:59:30 +00003329 }
3330}
3331
3332TEST(APFloatTest, PPCDoubleDoubleAdd) {
3333 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
3334 uint64_t, APFloat::roundingMode>;
3335 DataType Data[] = {
3336 // (1 + 0) + (1e-105 + 0) = (1 + 1e-105)
Tim Shen18e7ae62016-12-12 22:16:08 +00003337 std::make_tuple(0x3ff0000000000000ull, 0, 0x3960000000000000ull, 0,
3338 0x3ff0000000000000ull, 0x3960000000000000ull,
3339 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003340 // (1 + 0) + (1e-106 + 0) = (1 + 1e-106)
Tim Shen18e7ae62016-12-12 22:16:08 +00003341 std::make_tuple(0x3ff0000000000000ull, 0, 0x3950000000000000ull, 0,
3342 0x3ff0000000000000ull, 0x3950000000000000ull,
3343 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003344 // (1 + 1e-106) + (1e-106 + 0) = (1 + 1e-105)
Tim Shen18e7ae62016-12-12 22:16:08 +00003345 std::make_tuple(0x3ff0000000000000ull, 0x3950000000000000ull,
3346 0x3950000000000000ull, 0, 0x3ff0000000000000ull,
3347 0x3960000000000000ull, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003348 // (1 + 0) + (epsilon + 0) = (1 + epsilon)
Tim Shen18e7ae62016-12-12 22:16:08 +00003349 std::make_tuple(0x3ff0000000000000ull, 0, 0x0000000000000001ull, 0,
3350 0x3ff0000000000000ull, 0x0000000000000001ull,
3351 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003352 // TODO: change 0xf950000000000000 to 0xf940000000000000, when
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003353 // semPPCDoubleDoubleLegacy is gone.
Tim Shen44bde892016-12-12 21:59:30 +00003354 // (DBL_MAX - 1 << (1023 - 105)) + (1 << (1023 - 53) + 0) = DBL_MAX +
3355 // 1.11111... << (1023 - 52)
Tim Shen18e7ae62016-12-12 22:16:08 +00003356 std::make_tuple(0x7fefffffffffffffull, 0xf950000000000000ull,
3357 0x7c90000000000000ull, 0, 0x7fefffffffffffffull,
3358 0x7c8ffffffffffffeull, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003359 // TODO: change 0xf950000000000000 to 0xf940000000000000, when
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003360 // semPPCDoubleDoubleLegacy is gone.
Tim Shen44bde892016-12-12 21:59:30 +00003361 // (1 << (1023 - 53) + 0) + (DBL_MAX - 1 << (1023 - 105)) = DBL_MAX +
3362 // 1.11111... << (1023 - 52)
Tim Shen18e7ae62016-12-12 22:16:08 +00003363 std::make_tuple(0x7c90000000000000ull, 0, 0x7fefffffffffffffull,
3364 0xf950000000000000ull, 0x7fefffffffffffffull,
3365 0x7c8ffffffffffffeull, APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003366 };
3367
3368 for (auto Tp : Data) {
3369 uint64_t Op1[2], Op2[2], Expected[2];
3370 APFloat::roundingMode RM;
3371 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
3372
Tim Shen7f127622017-01-24 00:19:45 +00003373 {
3374 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3375 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3376 A1.add(A2, RM);
Tim Shen44bde892016-12-12 21:59:30 +00003377
Tim Shen7f127622017-01-24 00:19:45 +00003378 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3379 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
3380 Op2[0], Op2[1])
3381 .str();
3382 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3383 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op1[0], Op1[1],
3384 Op2[0], Op2[1])
3385 .str();
3386 }
3387 {
3388 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3389 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3390 A2.add(A1, RM);
3391
3392 EXPECT_EQ(Expected[0], A2.bitcastToAPInt().getRawData()[0])
3393 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
3394 Op1[0], Op1[1])
3395 .str();
3396 EXPECT_EQ(Expected[1], A2.bitcastToAPInt().getRawData()[1])
3397 << formatv("({0:x} + {1:x}) + ({2:x} + {3:x})", Op2[0], Op2[1],
3398 Op1[0], Op1[1])
3399 .str();
3400 }
Tim Shen44bde892016-12-12 21:59:30 +00003401 }
3402}
3403
3404TEST(APFloatTest, PPCDoubleDoubleSubtract) {
3405 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
3406 uint64_t, APFloat::roundingMode>;
3407 DataType Data[] = {
3408 // (1 + 0) - (-1e-105 + 0) = (1 + 1e-105)
Tim Shen18e7ae62016-12-12 22:16:08 +00003409 std::make_tuple(0x3ff0000000000000ull, 0, 0xb960000000000000ull, 0,
3410 0x3ff0000000000000ull, 0x3960000000000000ull,
3411 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003412 // (1 + 0) - (-1e-106 + 0) = (1 + 1e-106)
Tim Shen18e7ae62016-12-12 22:16:08 +00003413 std::make_tuple(0x3ff0000000000000ull, 0, 0xb950000000000000ull, 0,
3414 0x3ff0000000000000ull, 0x3950000000000000ull,
3415 APFloat::rmNearestTiesToEven),
Tim Shen44bde892016-12-12 21:59:30 +00003416 };
3417
3418 for (auto Tp : Data) {
3419 uint64_t Op1[2], Op2[2], Expected[2];
3420 APFloat::roundingMode RM;
3421 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
3422
Stephan Bergmann7d94d542016-12-14 12:11:35 +00003423 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3424 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
Tim Shen44bde892016-12-12 21:59:30 +00003425 A1.subtract(A2, RM);
3426
Tim Shen53f14c72016-12-16 00:47:17 +00003427 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3428 << formatv("({0:x} + {1:x}) - ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
3429 Op2[1])
3430 .str();
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003431 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
Tim Shen53f14c72016-12-16 00:47:17 +00003432 << formatv("({0:x} + {1:x}) - ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
3433 Op2[1])
3434 .str();
Tim Shen44bde892016-12-12 21:59:30 +00003435 }
3436}
Tim Shen1594e062017-01-05 22:57:54 +00003437
Tim Shen7f127622017-01-24 00:19:45 +00003438TEST(APFloatTest, PPCDoubleDoubleMultiplySpecial) {
3439 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t,
3440 APFloat::fltCategory, APFloat::roundingMode>;
3441 DataType Data[] = {
3442 // fcNaN * fcNaN = fcNaN
3443 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0,
3444 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
3445 // fcNaN * fcZero = fcNaN
3446 std::make_tuple(0x7ff8000000000000ull, 0, 0, 0, APFloat::fcNaN,
3447 APFloat::rmNearestTiesToEven),
3448 // fcNaN * fcInfinity = fcNaN
3449 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff0000000000000ull, 0,
3450 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
3451 // fcNaN * fcNormal = fcNaN
3452 std::make_tuple(0x7ff8000000000000ull, 0, 0x3ff0000000000000ull, 0,
3453 APFloat::fcNaN, APFloat::rmNearestTiesToEven),
3454 // fcInfinity * fcInfinity = fcInfinity
3455 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0,
3456 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
3457 // fcInfinity * fcZero = fcNaN
3458 std::make_tuple(0x7ff0000000000000ull, 0, 0, 0, APFloat::fcNaN,
3459 APFloat::rmNearestTiesToEven),
3460 // fcInfinity * fcNormal = fcInfinity
3461 std::make_tuple(0x7ff0000000000000ull, 0, 0x3ff0000000000000ull, 0,
3462 APFloat::fcInfinity, APFloat::rmNearestTiesToEven),
3463 // fcZero * fcZero = fcZero
3464 std::make_tuple(0, 0, 0, 0, APFloat::fcZero,
3465 APFloat::rmNearestTiesToEven),
3466 // fcZero * fcNormal = fcZero
3467 std::make_tuple(0, 0, 0x3ff0000000000000ull, 0, APFloat::fcZero,
3468 APFloat::rmNearestTiesToEven),
3469 };
3470
3471 for (auto Tp : Data) {
3472 uint64_t Op1[2], Op2[2];
3473 APFloat::fltCategory Expected;
3474 APFloat::roundingMode RM;
3475 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected, RM) = Tp;
3476
3477 {
3478 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3479 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3480 A1.multiply(A2, RM);
3481
3482 EXPECT_EQ(Expected, A1.getCategory())
3483 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
3484 Op2[0], Op2[1])
3485 .str();
3486 }
3487 {
3488 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3489 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3490 A2.multiply(A1, RM);
3491
3492 EXPECT_EQ(Expected, A2.getCategory())
3493 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
3494 Op1[0], Op1[1])
3495 .str();
3496 }
3497 }
3498}
3499
Tim Shen1594e062017-01-05 22:57:54 +00003500TEST(APFloatTest, PPCDoubleDoubleMultiply) {
3501 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
3502 uint64_t, APFloat::roundingMode>;
Tim Shen1594e062017-01-05 22:57:54 +00003503 DataType Data[] = {
3504 // 1/3 * 3 = 1.0
3505 std::make_tuple(0x3fd5555555555555ull, 0x3c75555555555556ull,
3506 0x4008000000000000ull, 0, 0x3ff0000000000000ull, 0,
3507 APFloat::rmNearestTiesToEven),
Tim Shen7f127622017-01-24 00:19:45 +00003508 // (1 + epsilon) * (1 + 0) = fcZero
3509 std::make_tuple(0x3ff0000000000000ull, 0x0000000000000001ull,
3510 0x3ff0000000000000ull, 0, 0x3ff0000000000000ull,
3511 0x0000000000000001ull, APFloat::rmNearestTiesToEven),
3512 // (1 + epsilon) * (1 + epsilon) = 1 + 2 * epsilon
3513 std::make_tuple(0x3ff0000000000000ull, 0x0000000000000001ull,
3514 0x3ff0000000000000ull, 0x0000000000000001ull,
3515 0x3ff0000000000000ull, 0x0000000000000002ull,
3516 APFloat::rmNearestTiesToEven),
3517 // -(1 + epsilon) * (1 + epsilon) = -1
3518 std::make_tuple(0xbff0000000000000ull, 0x0000000000000001ull,
3519 0x3ff0000000000000ull, 0x0000000000000001ull,
3520 0xbff0000000000000ull, 0, APFloat::rmNearestTiesToEven),
3521 // (0.5 + 0) * (1 + 2 * epsilon) = 0.5 + epsilon
3522 std::make_tuple(0x3fe0000000000000ull, 0, 0x3ff0000000000000ull,
3523 0x0000000000000002ull, 0x3fe0000000000000ull,
3524 0x0000000000000001ull, APFloat::rmNearestTiesToEven),
3525 // (0.5 + 0) * (1 + epsilon) = 0.5
3526 std::make_tuple(0x3fe0000000000000ull, 0, 0x3ff0000000000000ull,
3527 0x0000000000000001ull, 0x3fe0000000000000ull, 0,
3528 APFloat::rmNearestTiesToEven),
3529 // __LDBL_MAX__ * (1 + 1 << 106) = inf
3530 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3531 0x3ff0000000000000ull, 0x3950000000000000ull,
3532 0x7ff0000000000000ull, 0, APFloat::rmNearestTiesToEven),
3533 // __LDBL_MAX__ * (1 + 1 << 107) > __LDBL_MAX__, but not inf, yes =_=|||
3534 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3535 0x3ff0000000000000ull, 0x3940000000000000ull,
3536 0x7fefffffffffffffull, 0x7c8fffffffffffffull,
3537 APFloat::rmNearestTiesToEven),
3538 // __LDBL_MAX__ * (1 + 1 << 108) = __LDBL_MAX__
3539 std::make_tuple(0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3540 0x3ff0000000000000ull, 0x3930000000000000ull,
3541 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3542 APFloat::rmNearestTiesToEven),
Tim Shen1594e062017-01-05 22:57:54 +00003543 };
3544
3545 for (auto Tp : Data) {
3546 uint64_t Op1[2], Op2[2], Expected[2];
3547 APFloat::roundingMode RM;
3548 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
3549
Tim Shen7f127622017-01-24 00:19:45 +00003550 {
3551 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3552 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3553 A1.multiply(A2, RM);
Tim Shen1594e062017-01-05 22:57:54 +00003554
Tim Shen7f127622017-01-24 00:19:45 +00003555 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3556 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
3557 Op2[0], Op2[1])
3558 .str();
3559 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3560 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op1[0], Op1[1],
3561 Op2[0], Op2[1])
3562 .str();
3563 }
3564 {
3565 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3566 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3567 A2.multiply(A1, RM);
3568
3569 EXPECT_EQ(Expected[0], A2.bitcastToAPInt().getRawData()[0])
3570 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
3571 Op1[0], Op1[1])
3572 .str();
3573 EXPECT_EQ(Expected[1], A2.bitcastToAPInt().getRawData()[1])
3574 << formatv("({0:x} + {1:x}) * ({2:x} + {3:x})", Op2[0], Op2[1],
3575 Op1[0], Op1[1])
3576 .str();
3577 }
Tim Shen1594e062017-01-05 22:57:54 +00003578 }
3579}
3580
3581TEST(APFloatTest, PPCDoubleDoubleDivide) {
3582 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t,
3583 uint64_t, APFloat::roundingMode>;
3584 // TODO: Only a sanity check for now. Add more edge cases when the
3585 // double-double algorithm is implemented.
3586 DataType Data[] = {
3587 // 1 / 3 = 1/3
3588 std::make_tuple(0x3ff0000000000000ull, 0, 0x4008000000000000ull, 0,
3589 0x3fd5555555555555ull, 0x3c75555555555556ull,
3590 APFloat::rmNearestTiesToEven),
3591 };
3592
3593 for (auto Tp : Data) {
3594 uint64_t Op1[2], Op2[2], Expected[2];
3595 APFloat::roundingMode RM;
3596 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1], RM) = Tp;
3597
3598 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3599 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3600 A1.divide(A2, RM);
3601
3602 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3603 << formatv("({0:x} + {1:x}) / ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
3604 Op2[1])
3605 .str();
3606 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3607 << formatv("({0:x} + {1:x}) / ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
3608 Op2[1])
3609 .str();
3610 }
3611}
3612
3613TEST(APFloatTest, PPCDoubleDoubleRemainder) {
3614 using DataType =
3615 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t, uint64_t>;
3616 DataType Data[] = {
3617 // remainder(3.0 + 3.0 << 53, 1.25 + 1.25 << 53) = (0.5 + 0.5 << 53)
3618 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
3619 0x3ff4000000000000ull, 0x3ca4000000000000ull,
3620 0x3fe0000000000000ull, 0x3c90000000000000ull),
3621 // remainder(3.0 + 3.0 << 53, 1.75 + 1.75 << 53) = (-0.5 - 0.5 << 53)
3622 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
3623 0x3ffc000000000000ull, 0x3cac000000000000ull,
3624 0xbfe0000000000000ull, 0xbc90000000000000ull),
3625 };
3626
3627 for (auto Tp : Data) {
3628 uint64_t Op1[2], Op2[2], Expected[2];
3629 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1]) = Tp;
3630
3631 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3632 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3633 A1.remainder(A2);
3634
3635 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3636 << formatv("remainder({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
3637 Op2[0], Op2[1])
3638 .str();
3639 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3640 << formatv("remainder(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0],
3641 Op1[1], Op2[0], Op2[1])
3642 .str();
3643 }
3644}
3645
3646TEST(APFloatTest, PPCDoubleDoubleMod) {
3647 using DataType =
3648 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, uint64_t, uint64_t>;
3649 DataType Data[] = {
3650 // mod(3.0 + 3.0 << 53, 1.25 + 1.25 << 53) = (0.5 + 0.5 << 53)
3651 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
3652 0x3ff4000000000000ull, 0x3ca4000000000000ull,
3653 0x3fe0000000000000ull, 0x3c90000000000000ull),
3654 // mod(3.0 + 3.0 << 53, 1.75 + 1.75 << 53) = (1.25 + 1.25 << 53)
3655 // 0xbc98000000000000 doesn't seem right, but it's what we currently have.
3656 // TODO: investigate
3657 std::make_tuple(0x4008000000000000ull, 0x3cb8000000000000ull,
3658 0x3ffc000000000000ull, 0x3cac000000000000ull,
3659 0x3ff4000000000001ull, 0xbc98000000000000ull),
3660 };
3661
3662 for (auto Tp : Data) {
3663 uint64_t Op1[2], Op2[2], Expected[2];
3664 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected[0], Expected[1]) = Tp;
3665
3666 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3667 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3668 A1.mod(A2);
3669
3670 EXPECT_EQ(Expected[0], A1.bitcastToAPInt().getRawData()[0])
3671 << formatv("fmod(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
3672 Op2[0], Op2[1])
3673 .str();
3674 EXPECT_EQ(Expected[1], A1.bitcastToAPInt().getRawData()[1])
3675 << formatv("fmod(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
3676 Op2[0], Op2[1])
3677 .str();
3678 }
3679}
3680
3681TEST(APFloatTest, PPCDoubleDoubleFMA) {
3682 // Sanity check for now.
3683 APFloat A(APFloat::PPCDoubleDouble(), "2");
3684 A.fusedMultiplyAdd(APFloat(APFloat::PPCDoubleDouble(), "3"),
3685 APFloat(APFloat::PPCDoubleDouble(), "4"),
3686 APFloat::rmNearestTiesToEven);
3687 EXPECT_EQ(APFloat::cmpEqual,
3688 APFloat(APFloat::PPCDoubleDouble(), "10").compare(A));
3689}
3690
3691TEST(APFloatTest, PPCDoubleDoubleRoundToIntegral) {
3692 {
3693 APFloat A(APFloat::PPCDoubleDouble(), "1.5");
3694 A.roundToIntegral(APFloat::rmNearestTiesToEven);
3695 EXPECT_EQ(APFloat::cmpEqual,
3696 APFloat(APFloat::PPCDoubleDouble(), "2").compare(A));
3697 }
3698 {
3699 APFloat A(APFloat::PPCDoubleDouble(), "2.5");
3700 A.roundToIntegral(APFloat::rmNearestTiesToEven);
3701 EXPECT_EQ(APFloat::cmpEqual,
3702 APFloat(APFloat::PPCDoubleDouble(), "2").compare(A));
3703 }
3704}
3705
3706TEST(APFloatTest, PPCDoubleDoubleCompare) {
3707 using DataType =
3708 std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, APFloat::cmpResult>;
3709
3710 DataType Data[] = {
3711 // (1 + 0) = (1 + 0)
3712 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000000ull, 0,
3713 APFloat::cmpEqual),
3714 // (1 + 0) < (1.00...1 + 0)
3715 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull, 0,
3716 APFloat::cmpLessThan),
3717 // (1.00...1 + 0) > (1 + 0)
3718 std::make_tuple(0x3ff0000000000001ull, 0, 0x3ff0000000000000ull, 0,
3719 APFloat::cmpGreaterThan),
3720 // (1 + 0) < (1 + epsilon)
3721 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull,
3722 0x0000000000000001ull, APFloat::cmpLessThan),
3723 // NaN != NaN
3724 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0,
3725 APFloat::cmpUnordered),
3726 // (1 + 0) != NaN
3727 std::make_tuple(0x3ff0000000000000ull, 0, 0x7ff8000000000000ull, 0,
3728 APFloat::cmpUnordered),
3729 // Inf = Inf
3730 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0,
3731 APFloat::cmpEqual),
3732 };
3733
3734 for (auto Tp : Data) {
3735 uint64_t Op1[2], Op2[2];
3736 APFloat::cmpResult Expected;
3737 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected) = Tp;
3738
3739 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3740 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3741 EXPECT_EQ(Expected, A1.compare(A2))
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003742 << formatv("compare(({0:x} + {1:x}), ({2:x} + {3:x}))", Op1[0], Op1[1],
3743 Op2[0], Op2[1])
3744 .str();
3745 }
3746}
3747
3748TEST(APFloatTest, PPCDoubleDoubleBitwiseIsEqual) {
3749 using DataType = std::tuple<uint64_t, uint64_t, uint64_t, uint64_t, bool>;
3750
3751 DataType Data[] = {
3752 // (1 + 0) = (1 + 0)
3753 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000000ull, 0, true),
3754 // (1 + 0) != (1.00...1 + 0)
3755 std::make_tuple(0x3ff0000000000000ull, 0, 0x3ff0000000000001ull, 0,
3756 false),
3757 // NaN = NaN
3758 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull, 0, true),
3759 // NaN != NaN with a different bit pattern
3760 std::make_tuple(0x7ff8000000000000ull, 0, 0x7ff8000000000000ull,
3761 0x3ff0000000000000ull, false),
3762 // Inf = Inf
3763 std::make_tuple(0x7ff0000000000000ull, 0, 0x7ff0000000000000ull, 0, true),
3764 };
3765
3766 for (auto Tp : Data) {
3767 uint64_t Op1[2], Op2[2];
3768 bool Expected;
3769 std::tie(Op1[0], Op1[1], Op2[0], Op2[1], Expected) = Tp;
3770
3771 APFloat A1(APFloat::PPCDoubleDouble(), APInt(128, 2, Op1));
3772 APFloat A2(APFloat::PPCDoubleDouble(), APInt(128, 2, Op2));
3773 EXPECT_EQ(Expected, A1.bitwiseIsEqual(A2))
3774 << formatv("({0:x} + {1:x}) = ({2:x} + {3:x})", Op1[0], Op1[1], Op2[0],
Tim Shen1594e062017-01-05 22:57:54 +00003775 Op2[1])
3776 .str();
3777 }
3778}
3779
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003780TEST(APFloatTest, PPCDoubleDoubleHashValue) {
3781 uint64_t Data1[] = {0x3ff0000000000001ull, 0x0000000000000001ull};
3782 uint64_t Data2[] = {0x3ff0000000000001ull, 0};
3783 // The hash values are *hopefully* different.
3784 EXPECT_NE(
3785 hash_value(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data1))),
3786 hash_value(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data2))));
3787}
3788
Tim Shen1594e062017-01-05 22:57:54 +00003789TEST(APFloatTest, PPCDoubleDoubleChangeSign) {
3790 uint64_t Data[] = {
3791 0x400f000000000000ull, 0xbcb0000000000000ull,
3792 };
3793 APFloat Float(APFloat::PPCDoubleDouble(), APInt(128, 2, Data));
3794 {
3795 APFloat Actual =
3796 APFloat::copySign(Float, APFloat(APFloat::IEEEdouble(), "1"));
3797 EXPECT_EQ(0x400f000000000000ull, Actual.bitcastToAPInt().getRawData()[0]);
3798 EXPECT_EQ(0xbcb0000000000000ull, Actual.bitcastToAPInt().getRawData()[1]);
3799 }
3800 {
3801 APFloat Actual =
3802 APFloat::copySign(Float, APFloat(APFloat::IEEEdouble(), "-1"));
3803 EXPECT_EQ(0xc00f000000000000ull, Actual.bitcastToAPInt().getRawData()[0]);
3804 EXPECT_EQ(0x3cb0000000000000ull, Actual.bitcastToAPInt().getRawData()[1]);
3805 }
3806}
3807
3808TEST(APFloatTest, PPCDoubleDoubleFactories) {
3809 {
3810 uint64_t Data[] = {
3811 0, 0,
3812 };
3813 EXPECT_EQ(APInt(128, 2, Data),
3814 APFloat::getZero(APFloat::PPCDoubleDouble()).bitcastToAPInt());
3815 }
3816 {
3817 uint64_t Data[] = {
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003818 0x7fefffffffffffffull, 0x7c8ffffffffffffeull,
3819 };
3820 EXPECT_EQ(APInt(128, 2, Data),
3821 APFloat::getLargest(APFloat::PPCDoubleDouble()).bitcastToAPInt());
3822 }
3823 {
3824 uint64_t Data[] = {
Tim Shen1594e062017-01-05 22:57:54 +00003825 0x0000000000000001ull, 0,
3826 };
3827 EXPECT_EQ(
3828 APInt(128, 2, Data),
3829 APFloat::getSmallest(APFloat::PPCDoubleDouble()).bitcastToAPInt());
3830 }
3831 {
3832 uint64_t Data[] = {0x0360000000000000ull, 0};
3833 EXPECT_EQ(APInt(128, 2, Data),
3834 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble())
3835 .bitcastToAPInt());
3836 }
3837 {
3838 uint64_t Data[] = {
3839 0x8000000000000000ull, 0x0000000000000000ull,
3840 };
3841 EXPECT_EQ(
3842 APInt(128, 2, Data),
3843 APFloat::getZero(APFloat::PPCDoubleDouble(), true).bitcastToAPInt());
3844 }
3845 {
3846 uint64_t Data[] = {
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003847 0xffefffffffffffffull, 0xfc8ffffffffffffeull,
3848 };
3849 EXPECT_EQ(
3850 APInt(128, 2, Data),
3851 APFloat::getLargest(APFloat::PPCDoubleDouble(), true).bitcastToAPInt());
3852 }
3853 {
3854 uint64_t Data[] = {
Tim Shen1594e062017-01-05 22:57:54 +00003855 0x8000000000000001ull, 0x0000000000000000ull,
3856 };
3857 EXPECT_EQ(APInt(128, 2, Data),
3858 APFloat::getSmallest(APFloat::PPCDoubleDouble(), true)
3859 .bitcastToAPInt());
3860 }
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003861 {
3862 uint64_t Data[] = {
3863 0x8360000000000000ull, 0x0000000000000000ull,
3864 };
3865 EXPECT_EQ(APInt(128, 2, Data),
3866 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble(), true)
3867 .bitcastToAPInt());
3868 }
Tim Shen1594e062017-01-05 22:57:54 +00003869 EXPECT_TRUE(APFloat::getSmallest(APFloat::PPCDoubleDouble()).isSmallest());
3870 EXPECT_TRUE(APFloat::getLargest(APFloat::PPCDoubleDouble()).isLargest());
3871}
Tim Shenfd1e5aa2017-01-23 22:39:35 +00003872
3873TEST(APFloatTest, PPCDoubleDoubleIsDenormal) {
3874 EXPECT_TRUE(APFloat::getSmallest(APFloat::PPCDoubleDouble()).isDenormal());
3875 EXPECT_FALSE(APFloat::getLargest(APFloat::PPCDoubleDouble()).isDenormal());
3876 EXPECT_FALSE(
3877 APFloat::getSmallestNormalized(APFloat::PPCDoubleDouble()).isDenormal());
3878 {
3879 // (4 + 3) is not normalized
3880 uint64_t Data[] = {
3881 0x4010000000000000ull, 0x4008000000000000ull,
3882 };
3883 EXPECT_TRUE(
3884 APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Data)).isDenormal());
3885 }
3886}
3887
3888TEST(APFloatTest, PPCDoubleDoubleScalbn) {
3889 // 3.0 + 3.0 << 53
3890 uint64_t Input[] = {
3891 0x4008000000000000ull, 0x3cb8000000000000ull,
3892 };
3893 APFloat Result =
3894 scalbn(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Input)), 1,
3895 APFloat::rmNearestTiesToEven);
3896 // 6.0 + 6.0 << 53
3897 EXPECT_EQ(0x4018000000000000ull, Result.bitcastToAPInt().getRawData()[0]);
3898 EXPECT_EQ(0x3cc8000000000000ull, Result.bitcastToAPInt().getRawData()[1]);
3899}
3900
3901TEST(APFloatTest, PPCDoubleDoubleFrexp) {
3902 // 3.0 + 3.0 << 53
3903 uint64_t Input[] = {
3904 0x4008000000000000ull, 0x3cb8000000000000ull,
3905 };
3906 int Exp;
3907 // 0.75 + 0.75 << 53
3908 APFloat Result =
3909 frexp(APFloat(APFloat::PPCDoubleDouble(), APInt(128, 2, Input)), Exp,
3910 APFloat::rmNearestTiesToEven);
3911 EXPECT_EQ(2, Exp);
3912 EXPECT_EQ(0x3fe8000000000000ull, Result.bitcastToAPInt().getRawData()[0]);
3913 EXPECT_EQ(0x3c98000000000000ull, Result.bitcastToAPInt().getRawData()[1]);
3914}
Erick Tryzelaar19f63b22009-08-16 23:36:19 +00003915}