1//===-- Unittests for powf ------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "hdr/math_macros.h"
10#include "src/__support/FPUtil/FPBits.h"
11#include "src/math/powf.h"
12#include "test/UnitTest/FPMatcher.h"
13#include "test/UnitTest/Test.h"
14
15#include <stdint.h>
16
17using LlvmLibcPowfTest = LIBC_NAMESPACE::testing::FPTest<float>;
18using LIBC_NAMESPACE::fputil::testing::ForceRoundingMode;
19using LIBC_NAMESPACE::fputil::testing::RoundingMode;
20
21TEST_F(LlvmLibcPowfTest, SpecialNumbers) {
22 constexpr float neg_odd_integer = -3.0f;
23 constexpr float neg_even_integer = -6.0f;
24 constexpr float neg_non_integer = -1.1f;
25 constexpr float pos_odd_integer = 5.0f;
26 constexpr float pos_even_integer = 8.0f;
27 constexpr float pos_non_integer = 1.3f;
28 constexpr float one_half = 0.5f;
29
30 for (int i = 0; i < N_ROUNDING_MODES; ++i) {
31 ForceRoundingMode __r(ROUNDING_MODES[i]);
32 if (!__r.success)
33 continue;
34
35 // pow( sNaN, exponent)
36 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(sNaN, sNaN),
37 FE_INVALID);
38 EXPECT_FP_EQ_WITH_EXCEPTION(
39 aNaN, LIBC_NAMESPACE::powf(sNaN, neg_odd_integer), FE_INVALID);
40 EXPECT_FP_EQ_WITH_EXCEPTION(
41 aNaN, LIBC_NAMESPACE::powf(sNaN, neg_even_integer), FE_INVALID);
42 EXPECT_FP_EQ_WITH_EXCEPTION(
43 aNaN, LIBC_NAMESPACE::powf(sNaN, pos_odd_integer), FE_INVALID);
44 EXPECT_FP_EQ_WITH_EXCEPTION(
45 aNaN, LIBC_NAMESPACE::powf(sNaN, pos_even_integer), FE_INVALID);
46 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(sNaN, one_half),
47 FE_INVALID);
48 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(sNaN, zero),
49 FE_INVALID);
50 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(sNaN, neg_zero),
51 FE_INVALID);
52 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(sNaN, inf),
53 FE_INVALID);
54 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(sNaN, neg_inf),
55 FE_INVALID);
56 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(sNaN, aNaN),
57 FE_INVALID);
58
59 // pow( 0.0f, exponent )
60 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(zero, sNaN),
61 FE_INVALID);
62 EXPECT_FP_EQ_WITH_EXCEPTION(
63 inf, LIBC_NAMESPACE::powf(zero, neg_odd_integer), FE_DIVBYZERO);
64 EXPECT_FP_EQ_WITH_EXCEPTION(
65 inf, LIBC_NAMESPACE::powf(zero, neg_even_integer), FE_DIVBYZERO);
66 EXPECT_FP_EQ_WITH_EXCEPTION(
67 inf, LIBC_NAMESPACE::powf(zero, neg_non_integer), FE_DIVBYZERO);
68 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(zero, pos_odd_integer));
69 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(zero, pos_even_integer));
70 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(zero, pos_non_integer));
71 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(zero, one_half));
72 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(zero, zero));
73 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(zero, neg_zero));
74 EXPECT_FP_EQ(0.0f, LIBC_NAMESPACE::powf(zero, inf));
75 EXPECT_FP_EQ_WITH_EXCEPTION(inf, LIBC_NAMESPACE::powf(zero, neg_inf),
76 FE_DIVBYZERO);
77 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(zero, aNaN));
78
79 // pow( -0.0f, exponent )
80 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(neg_zero, sNaN),
81 FE_INVALID);
82 EXPECT_FP_EQ_WITH_EXCEPTION(
83 neg_inf, LIBC_NAMESPACE::powf(neg_zero, neg_odd_integer), FE_DIVBYZERO);
84 EXPECT_FP_EQ_WITH_EXCEPTION(
85 inf, LIBC_NAMESPACE::powf(neg_zero, neg_even_integer), FE_DIVBYZERO);
86 EXPECT_FP_EQ_WITH_EXCEPTION(
87 inf, LIBC_NAMESPACE::powf(neg_zero, neg_non_integer), FE_DIVBYZERO);
88 EXPECT_FP_EQ(neg_zero, LIBC_NAMESPACE::powf(neg_zero, pos_odd_integer));
89 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(neg_zero, pos_even_integer));
90 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(neg_zero, pos_non_integer));
91 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(neg_zero, one_half));
92 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(neg_zero, zero));
93 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(neg_zero, neg_zero));
94 EXPECT_FP_EQ(0.0f, LIBC_NAMESPACE::powf(neg_zero, inf));
95 EXPECT_FP_EQ_WITH_EXCEPTION(inf, LIBC_NAMESPACE::powf(neg_zero, neg_inf),
96 FE_DIVBYZERO);
97 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(neg_zero, aNaN));
98
99 // pow( 1.0f, exponent )
100 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(1.0f, sNaN),
101 FE_INVALID);
102 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, zero));
103 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, neg_zero));
104 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, 1.0f));
105 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, -1.0f));
106 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, neg_odd_integer));
107 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, neg_even_integer));
108 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, neg_non_integer));
109 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, pos_odd_integer));
110 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, pos_even_integer));
111 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, pos_non_integer));
112 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, inf));
113 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, neg_inf));
114 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(1.0f, aNaN));
115
116 // pow( -1.0f, exponent )
117 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(-1.0f, sNaN),
118 FE_INVALID);
119 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(-1.0f, zero));
120 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(-1.0f, neg_zero));
121 EXPECT_FP_EQ(-1.0f, LIBC_NAMESPACE::powf(-1.0f, 1.0f));
122 EXPECT_FP_EQ(-1.0f, LIBC_NAMESPACE::powf(-1.0f, -1.0f));
123 EXPECT_FP_EQ(-1.0f, LIBC_NAMESPACE::powf(-1.0f, neg_odd_integer));
124 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(-1.0f, neg_even_integer));
125 EXPECT_FP_IS_NAN_WITH_EXCEPTION(
126 LIBC_NAMESPACE::powf(-1.0f, neg_non_integer), FE_INVALID);
127 EXPECT_FP_EQ(-1.0f, LIBC_NAMESPACE::powf(-1.0f, pos_odd_integer));
128 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(-1.0f, pos_even_integer));
129 EXPECT_FP_IS_NAN_WITH_EXCEPTION(
130 LIBC_NAMESPACE::powf(-1.0f, pos_non_integer), FE_INVALID);
131 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(-1.0f, inf));
132 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(-1.0f, neg_inf));
133 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(-1.0f, aNaN));
134
135 // pow( inf, exponent )
136 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(inf, sNaN),
137 FE_INVALID);
138 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(inf, zero));
139 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(inf, neg_zero));
140 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(inf, 1.0f));
141 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(inf, -1.0f));
142 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(inf, neg_odd_integer));
143 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(inf, neg_even_integer));
144 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(inf, neg_non_integer));
145 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(inf, pos_odd_integer));
146 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(inf, pos_even_integer));
147 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(inf, pos_non_integer));
148 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(inf, one_half));
149 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(inf, inf));
150 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(inf, neg_inf));
151 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(inf, aNaN));
152
153 // pow( -inf, exponent )
154 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(neg_inf, sNaN),
155 FE_INVALID);
156 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(neg_inf, zero));
157 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(neg_inf, neg_zero));
158 EXPECT_FP_EQ(neg_inf, LIBC_NAMESPACE::powf(neg_inf, 1.0f));
159 EXPECT_FP_EQ(neg_zero, LIBC_NAMESPACE::powf(neg_inf, -1.0f));
160 EXPECT_FP_EQ(neg_zero, LIBC_NAMESPACE::powf(neg_inf, neg_odd_integer));
161 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(neg_inf, neg_even_integer));
162 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(neg_inf, neg_non_integer));
163 EXPECT_FP_EQ(neg_inf, LIBC_NAMESPACE::powf(neg_inf, pos_odd_integer));
164 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(neg_inf, pos_even_integer));
165 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(neg_inf, pos_non_integer));
166 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(neg_inf, one_half));
167 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(neg_inf, inf));
168 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(neg_inf, neg_inf));
169 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(neg_inf, aNaN));
170
171 // pow ( aNaN, exponent )
172 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(aNaN, sNaN),
173 FE_INVALID);
174 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(aNaN, zero));
175 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(aNaN, neg_zero));
176 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, 1.0f));
177 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, -1.0f));
178 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, neg_odd_integer));
179 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, neg_even_integer));
180 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, neg_non_integer));
181 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, pos_odd_integer));
182 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, pos_even_integer));
183 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, pos_non_integer));
184 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, inf));
185 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, neg_inf));
186 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(aNaN, aNaN));
187
188 // pow ( base, inf )
189 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(0.1f, inf));
190 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(-0.1f, inf));
191 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(1.1f, inf));
192 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(-1.1f, inf));
193
194 // pow ( base, -inf )
195 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(0.1f, neg_inf));
196 EXPECT_FP_EQ(inf, LIBC_NAMESPACE::powf(-0.1f, neg_inf));
197 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(1.1f, neg_inf));
198 EXPECT_FP_EQ(zero, LIBC_NAMESPACE::powf(-1.1f, neg_inf));
199
200 // Exact powers of 2:
201 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(2.0f, sNaN),
202 FE_INVALID);
203 EXPECT_FP_EQ(0x1.0p15f, LIBC_NAMESPACE::powf(2.0f, 15.0f));
204 EXPECT_FP_EQ(0x1.0p126f, LIBC_NAMESPACE::powf(2.0f, 126.0f));
205 EXPECT_FP_EQ(0x1.0p-45f, LIBC_NAMESPACE::powf(2.0f, -45.0f));
206 EXPECT_FP_EQ(0x1.0p-126f, LIBC_NAMESPACE::powf(2.0f, -126.0f));
207 EXPECT_FP_EQ(0x1.0p-149f, LIBC_NAMESPACE::powf(2.0f, -149.0f));
208
209 // Exact powers of 10:
210 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(10.0f, 0.0f));
211 EXPECT_FP_EQ(10.0f, LIBC_NAMESPACE::powf(10.0f, 1.0f));
212 EXPECT_FP_EQ(100.0f, LIBC_NAMESPACE::powf(10.0f, 2.0f));
213 EXPECT_FP_EQ(1000.0f, LIBC_NAMESPACE::powf(10.0f, 3.0f));
214 EXPECT_FP_EQ(10000.0f, LIBC_NAMESPACE::powf(10.0f, 4.0f));
215 EXPECT_FP_EQ(100000.0f, LIBC_NAMESPACE::powf(10.0f, 5.0f));
216 EXPECT_FP_EQ(1000000.0f, LIBC_NAMESPACE::powf(10.0f, 6.0f));
217 EXPECT_FP_EQ(10000000.0f, LIBC_NAMESPACE::powf(10.0f, 7.0f));
218 EXPECT_FP_EQ(100000000.0f, LIBC_NAMESPACE::powf(10.0f, 8.0f));
219 EXPECT_FP_EQ(1000000000.0f, LIBC_NAMESPACE::powf(10.0f, 9.0f));
220 EXPECT_FP_EQ(10000000000.0f, LIBC_NAMESPACE::powf(10.0f, 10.0f));
221 EXPECT_FP_EQ_WITH_EXCEPTION(aNaN, LIBC_NAMESPACE::powf(10.0f, sNaN),
222 FE_INVALID);
223
224 // Overflow / Underflow:
225 if (ROUNDING_MODES[i] != RoundingMode::Downward &&
226 ROUNDING_MODES[i] != RoundingMode::TowardZero) {
227 EXPECT_FP_EQ_WITH_EXCEPTION(inf, LIBC_NAMESPACE::powf(3.1f, 201.0f),
228 FE_OVERFLOW);
229 }
230 if (ROUNDING_MODES[i] != RoundingMode::Upward) {
231 EXPECT_FP_EQ_WITH_EXCEPTION(0.0f, LIBC_NAMESPACE::powf(3.1f, -201.0f),
232 FE_UNDERFLOW);
233 }
234 }
235
236 EXPECT_FP_EQ(-0.0f, LIBC_NAMESPACE::powf(-0.015625f, 25.0f));
237 EXPECT_FP_EQ(0.0f, LIBC_NAMESPACE::powf(-0.015625f, 26.0f));
238}
239
240#ifdef LIBC_TEST_FTZ_DAZ
241
242using namespace LIBC_NAMESPACE::testing;
243
244TEST_F(LlvmLibcPowfTest, FTZMode) {
245 ModifyMXCSR mxcsr(FTZ);
246
247 EXPECT_FP_IS_NAN(LIBC_NAMESPACE::powf(-min_denormal, 0.5f));
248 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(2.0f, min_denormal));
249}
250
251TEST_F(LlvmLibcPowfTest, DAZMode) {
252 ModifyMXCSR mxcsr(DAZ);
253
254 EXPECT_FP_EQ(0.0f, LIBC_NAMESPACE::powf(-min_denormal, 0.5f));
255 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(2.0f, min_denormal));
256}
257
258TEST_F(LlvmLibcPowfTest, FTZDAZMode) {
259 ModifyMXCSR mxcsr(FTZ | DAZ);
260
261 EXPECT_FP_EQ(0.0f, LIBC_NAMESPACE::powf(-min_denormal, 0.5f));
262 EXPECT_FP_EQ(1.0f, LIBC_NAMESPACE::powf(2.0f, min_denormal));
263}
264
265#endif
266

Provided by KDAB

Privacy Policy
Learn to use CMake with our Intro Training
Find out more

source code of libc/test/src/math/smoke/powf_test.cpp