1 //===-- Unittests for modfff
2 //-----------------------------------------------===//
3 //
4 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
5 // See https://llvm.org/LICENSE.txt for license information.
6 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #include "include/math.h"
11 #include "src/math/modff.h"
12 #include "utils/FPUtil/BitPatterns.h"
13 #include "utils/FPUtil/FloatOperations.h"
14 #include "utils/FPUtil/FloatProperties.h"
15 #include "utils/UnitTest/Test.h"
16 
17 using __llvm_libc::fputil::valueAsBits;
18 using __llvm_libc::fputil::valueFromBits;
19 
20 using BitPatterns = __llvm_libc::fputil::BitPatterns<float>;
21 using Properties = __llvm_libc::fputil::FloatProperties<float>;
22 
23 TEST(ModffTest, SpecialNumbers) {
24   float integral;
25 
26   EXPECT_EQ(BitPatterns::aQuietNaN,
27             valueAsBits(__llvm_libc::modff(
28                 valueFromBits(BitPatterns::aQuietNaN), &integral)));
29   EXPECT_EQ(BitPatterns::aNegativeQuietNaN,
30             valueAsBits(__llvm_libc::modff(
31                 valueFromBits(BitPatterns::aNegativeQuietNaN), &integral)));
32 
33   EXPECT_EQ(BitPatterns::aSignallingNaN,
34             valueAsBits(__llvm_libc::modff(
35                 valueFromBits(BitPatterns::aSignallingNaN), &integral)));
36   EXPECT_EQ(
37       BitPatterns::aNegativeSignallingNaN,
38       valueAsBits(__llvm_libc::modff(
39           valueFromBits(BitPatterns::aNegativeSignallingNaN), &integral)));
40 
41   EXPECT_EQ(BitPatterns::zero,
42             valueAsBits(__llvm_libc::modff(valueFromBits(BitPatterns::inf),
43                                            &integral)));
44   EXPECT_EQ(valueAsBits(integral), BitPatterns::inf);
45 
46   EXPECT_EQ(BitPatterns::negZero,
47             valueAsBits(__llvm_libc::modff(valueFromBits(BitPatterns::negInf),
48                                            &integral)));
49   EXPECT_EQ(valueAsBits(integral), BitPatterns::negInf);
50 
51   EXPECT_EQ(BitPatterns::zero,
52             valueAsBits(__llvm_libc::modff(valueFromBits(BitPatterns::zero),
53                                            &integral)));
54   EXPECT_EQ(valueAsBits(integral), BitPatterns::zero);
55 
56   EXPECT_EQ(BitPatterns::negZero,
57             valueAsBits(__llvm_libc::modff(valueFromBits(BitPatterns::negZero),
58                                            &integral)));
59   EXPECT_EQ(valueAsBits(integral), BitPatterns::negZero);
60 }
61 
62 TEST(ModffTest, Integers) {
63   float integral;
64 
65   EXPECT_EQ(BitPatterns::zero,
66             valueAsBits(__llvm_libc::modff(1.0f, &integral)));
67   EXPECT_EQ(valueAsBits(integral), valueAsBits(1.0f));
68 
69   EXPECT_EQ(BitPatterns::negZero,
70             valueAsBits(__llvm_libc::modff(-1.0f, &integral)));
71   EXPECT_EQ(valueAsBits(integral), valueAsBits(-1.0f));
72 
73   EXPECT_EQ(BitPatterns::zero,
74             valueAsBits(__llvm_libc::modff(10.0f, &integral)));
75   EXPECT_EQ(valueAsBits(integral), valueAsBits(10.0f));
76 
77   EXPECT_EQ(BitPatterns::negZero,
78             valueAsBits(__llvm_libc::modff(-10.0f, &integral)));
79   EXPECT_EQ(valueAsBits(integral), valueAsBits(-10.0f));
80 
81   EXPECT_EQ(BitPatterns::zero,
82             valueAsBits(__llvm_libc::modff(12345.0f, &integral)));
83   EXPECT_EQ(valueAsBits(integral), valueAsBits(12345.0f));
84 
85   EXPECT_EQ(BitPatterns::negZero,
86             valueAsBits(__llvm_libc::modff(-12345.0f, &integral)));
87   EXPECT_EQ(valueAsBits(integral), valueAsBits(-12345.0f));
88 }
89 
90 TEST(ModfTest, Fractions) {
91   float integral;
92 
93   EXPECT_EQ(valueAsBits(0.5f),
94             valueAsBits(__llvm_libc::modff(1.5f, &integral)));
95   EXPECT_EQ(valueAsBits(integral), valueAsBits(1.0f));
96 
97   EXPECT_EQ(valueAsBits(-0.5f),
98             valueAsBits(__llvm_libc::modff(-1.5f, &integral)));
99   EXPECT_EQ(valueAsBits(integral), valueAsBits(-1.0f));
100 
101   EXPECT_EQ(valueAsBits(0.75f),
102             valueAsBits(__llvm_libc::modff(10.75f, &integral)));
103   EXPECT_EQ(valueAsBits(integral), valueAsBits(10.0f));
104 
105   EXPECT_EQ(valueAsBits(-0.75f),
106             valueAsBits(__llvm_libc::modff(-10.75f, &integral)));
107   EXPECT_EQ(valueAsBits(integral), valueAsBits(-10.0f));
108 
109   EXPECT_EQ(valueAsBits(0.125f),
110             valueAsBits(__llvm_libc::modff(100.125f, &integral)));
111   EXPECT_EQ(valueAsBits(integral), valueAsBits(100.0f));
112 
113   EXPECT_EQ(valueAsBits(-0.125f),
114             valueAsBits(__llvm_libc::modff(-100.125f, &integral)));
115   EXPECT_EQ(valueAsBits(integral), valueAsBits(-100.0f));
116 }
117 
118 TEST(ModffTest, InDoubleRange) {
119   using BitsType = Properties::BitsType;
120   constexpr BitsType count = 10000000;
121   constexpr BitsType step = UINT32_MAX / count;
122   for (BitsType i = 0, v = 0; i <= count; ++i, v += step) {
123     float x = valueFromBits(v);
124     if (isnan(x) || isinf(x) || x == 0.0f) {
125       // These conditions have been tested in other tests.
126       continue;
127     }
128 
129     float integral;
130     float frac = __llvm_libc::modff(x, &integral);
131     ASSERT_TRUE(__llvm_libc::fputil::abs(frac) < 1.0f);
132     ASSERT_TRUE(__llvm_libc::fputil::trunc(x) == integral);
133     ASSERT_TRUE(integral + frac == x);
134   }
135 }
136