[libc-commits] [PATCH] D133370: [libc] Return correct values for hypot when overflowed.
Tue Ly via Phabricator via libc-commits
libc-commits at lists.llvm.org
Wed Sep 7 16:23:39 PDT 2022
This revision was automatically updated to reflect the committed changes.
Closed by commit rGbb6966aa5340: [libc] Return correct values for hypot when overflowed. (authored by lntue).
Repository:
rG LLVM Github Monorepo
CHANGES SINCE LAST ACTION
https://reviews.llvm.org/D133370/new/
https://reviews.llvm.org/D133370
Files:
libc/src/__support/FPUtil/Hypot.h
libc/test/src/math/HypotTest.h
Index: libc/test/src/math/HypotTest.h
===================================================================
--- libc/test/src/math/HypotTest.h
+++ libc/test/src/math/HypotTest.h
@@ -24,24 +24,38 @@
using Func = T (*)(T, T);
using FPBits = __llvm_libc::fputil::FPBits<T>;
using UIntType = typename FPBits::UIntType;
- const T nan = T(__llvm_libc::fputil::FPBits<T>::build_nan(1));
- const T inf = T(__llvm_libc::fputil::FPBits<T>::inf());
- const T neg_inf = T(__llvm_libc::fputil::FPBits<T>::neg_inf());
- const T zero = T(__llvm_libc::fputil::FPBits<T>::zero());
- const T neg_zero = T(__llvm_libc::fputil::FPBits<T>::neg_zero());
+ const T nan = T(FPBits::build_nan(1));
+ const T inf = T(FPBits::inf());
+ const T neg_inf = T(FPBits::neg_inf());
+ const T zero = T(FPBits::zero());
+ const T neg_zero = T(FPBits::neg_zero());
+ const T max_normal = T(FPBits(FPBits::MAX_NORMAL));
+ const T min_normal = T(FPBits(FPBits::MIN_NORMAL));
+ const T max_subnormal = T(FPBits(FPBits::MAX_SUBNORMAL));
+ const T min_subnormal = T(FPBits(FPBits::MIN_SUBNORMAL));
public:
void test_special_numbers(Func func) {
+ constexpr int N = 13;
+ const T SpecialInputs[N] = {inf, neg_inf, zero,
+ neg_zero, max_normal, min_normal,
+ max_subnormal, min_subnormal, -max_normal,
+ -min_normal, -max_subnormal, -min_subnormal};
+
EXPECT_FP_EQ(func(inf, nan), inf);
EXPECT_FP_EQ(func(nan, neg_inf), inf);
- EXPECT_FP_EQ(func(zero, inf), inf);
- EXPECT_FP_EQ(func(neg_inf, neg_zero), inf);
-
EXPECT_FP_EQ(func(nan, nan), nan);
EXPECT_FP_EQ(func(nan, zero), nan);
EXPECT_FP_EQ(func(neg_zero, nan), nan);
- EXPECT_FP_EQ(func(neg_zero, zero), zero);
+ for (int i = 0; i < N; ++i) {
+ for (int j = 0; j < N; ++j) {
+ mpfr::BinaryInput<T> input{SpecialInputs[i], SpecialInputs[j]};
+ EXPECT_MPFR_MATCH_ALL_ROUNDING(mpfr::Operation::Hypot, input,
+ func(SpecialInputs[i], SpecialInputs[j]),
+ 0.5);
+ }
+ }
}
void test_subnormal_range(Func func) {
Index: libc/src/__support/FPUtil/Hypot.h
===================================================================
--- libc/src/__support/FPUtil/Hypot.h
+++ libc/src/__support/FPUtil/Hypot.h
@@ -189,7 +189,10 @@
sum >>= 2;
++out_exp;
if (out_exp >= FPBits_t::MAX_EXPONENT) {
- return T(FPBits_t::inf());
+ if (int round_mode = get_round();
+ round_mode == FE_TONEAREST || round_mode == FE_UPWARD)
+ return T(FPBits_t::inf());
+ return T(FPBits_t(FPBits_t::MAX_NORMAL));
}
} else {
// For denormal result, we simply move the leading bit of the result to
@@ -227,7 +230,8 @@
y_new >>= 1;
// Round to the nearest, tie to even.
- switch (get_round()) {
+ int round_mode = get_round();
+ switch (round_mode) {
case FE_TONEAREST:
// Round to nearest, ties to even
if (round_bit && (lsb || sticky_bits || (r != 0)))
@@ -243,7 +247,9 @@
y_new -= ONE >> 1;
++out_exp;
if (out_exp >= FPBits_t::MAX_EXPONENT) {
- return T(FPBits_t::inf());
+ if (round_mode == FE_TONEAREST || round_mode == FE_UPWARD)
+ return T(FPBits_t::inf());
+ return T(FPBits_t(FPBits_t::MAX_NORMAL));
}
}
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D133370.458595.patch
Type: text/x-patch
Size: 3437 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/libc-commits/attachments/20220907/55d85fdb/attachment.bin>
More information about the libc-commits
mailing list