Update configs. IGNORE BROKEN CHANGESETS CLOSED TREE NO BUG a=release ba=release
[gecko.git] / js / src / jsapi-tests / testNumberToString.cpp
blobd5107327c6e8755cd316da9b45b9da5fae318914
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 * vim: set ts=8 sts=2 et sw=2 tw=80:
3 */
4 /* This Source Code Form is subject to the terms of the Mozilla Public
5 * License, v. 2.0. If a copy of the MPL was not distributed with this
6 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
8 #include "mozilla/FloatingPoint.h" // mozilla::{PositiveInfinity,UnspecifiedNaN}
10 #include <stddef.h> // size_t
11 #include <string.h> // memcmp, memset
13 #include "js/Conversions.h" // JS::NumberToString, JS::MaximumNumberToStringLength
14 #include "jsapi-tests/tests.h" // BEGIN_TEST, CHECK_EQUAL, END_TEST
15 #include "util/Text.h" // js_strlen
17 #define REST(x) x, (js_strlen(x)), __LINE__
19 static const struct NumberToStringTest {
20 double number;
21 const char* expected;
22 size_t expectedLength;
23 size_t lineno;
24 } numberToStringTests[] = {
25 {5e-324, REST("5e-324")}, // 2**-1074
26 {9.5367431640625e-7, REST("9.5367431640625e-7")}, // 2**-20
27 {0.0000010984284297360395, REST("0.0000010984284297360395")},
28 {0.0000019073486328125, REST("0.0000019073486328125")}, // 2**-19
29 {0.000003814697265625, REST("0.000003814697265625")}, // 2**-18
30 {0.0000057220458984375, REST("0.0000057220458984375")}, // 2**-18 + 2**-19
31 {0.000244140625, REST("0.000244140625")}, // 2**-12
32 {0.125, REST("0.125")},
33 {0.25, REST("0.25")},
34 {0.5, REST("0.5")},
35 {1, REST("1")},
36 {1.5, REST("1.5")},
37 {2, REST("2")},
38 {9, REST("9")},
39 {10, REST("10")},
40 {15, REST("15")},
41 {16, REST("16")},
42 {389427, REST("389427")},
43 {1073741823, REST("1073741823")},
44 {1073741824, REST("1073741824")},
45 {1073741825, REST("1073741825")},
46 {2147483647, REST("2147483647")},
47 {2147483648, REST("2147483648")},
48 {2147483649, REST("2147483649")},
49 {4294967294, REST("4294967294")},
50 {4294967295, REST("4294967295")},
51 {4294967296, REST("4294967296")},
52 {999999999999999900000.0, REST("999999999999999900000")},
53 {999999999999999900000.0 + 65535, REST("999999999999999900000")},
54 {999999999999999900000.0 + 65536, REST("1e+21")},
55 {1.7976931348623157e+308, REST("1.7976931348623157e+308")}, // MAX_VALUE
58 static constexpr char PoisonChar = 0x37;
60 struct StorageForNumberToString {
61 char out[JS::MaximumNumberToStringLength];
62 char overflow;
63 } storage;
65 BEGIN_TEST(testNumberToString) {
66 StorageForNumberToString storage;
68 if (!testNormalValues(false, storage)) {
69 return false;
72 if (!testNormalValues(true, storage)) {
73 return false;
76 NumberToStringTest zeroTest = {0.0, REST("0")};
77 if (!testOne(zeroTest, false, storage)) {
78 return false;
80 NumberToStringTest negativeZeroTest = {-0.0, REST("0")};
81 if (!testOne(negativeZeroTest, false, storage)) {
82 return false;
85 NumberToStringTest infTest = {mozilla::PositiveInfinity<double>(),
86 REST("Infinity")};
87 if (!testOne(infTest, false, storage)) {
88 return false;
90 if (!testOne(infTest, true, storage)) {
91 return false;
94 NumberToStringTest nanTest = {mozilla::UnspecifiedNaN<double>(), REST("NaN")};
95 return testOne(nanTest, false, storage);
98 bool testNormalValues(bool hasMinusSign, StorageForNumberToString& storage) {
99 for (const auto& test : numberToStringTests) {
100 if (!testOne(test, hasMinusSign, storage)) {
101 return false;
105 return true;
108 bool testOne(const NumberToStringTest& test, bool hasMinusSign,
109 StorageForNumberToString& storage) {
110 memset(&storage, PoisonChar, sizeof(storage));
112 JS::NumberToString(hasMinusSign ? -test.number : test.number, storage.out);
114 CHECK_EQUAL(storage.overflow, PoisonChar);
116 const char* start = storage.out;
117 if (hasMinusSign) {
118 CHECK_EQUAL(start[0], '-');
119 start++;
122 if (!checkEqual(memcmp(start, test.expected, test.expectedLength), 0, start,
123 test.expected, __FILE__, test.lineno)) {
124 return false;
127 char actualTerminator[] = {start[test.expectedLength], '\0'};
128 return checkEqual(actualTerminator[0], '\0', actualTerminator, "'\\0'",
129 __FILE__, test.lineno);
131 END_TEST(testNumberToString)
133 #undef REST