diff options
author | Matthias Springer <me@m-sp.org> | 2024-11-15 09:29:54 +0900 |
---|---|---|
committer | GitHub <noreply@github.com> | 2024-11-15 09:29:54 +0900 |
commit | 2f55de4e317ee93cdca839558acf8be2b5ac2b46 (patch) | |
tree | b17ec11d95569389d822fa971868250246e185eb | |
parent | eec21ccee0950d52926a79685573db1996e3ba5b (diff) | |
download | llvm-2f55de4e317ee93cdca839558acf8be2b5ac2b46.zip llvm-2f55de4e317ee93cdca839558acf8be2b5ac2b46.tar.gz llvm-2f55de4e317ee93cdca839558acf8be2b5ac2b46.tar.bz2 |
[llvm] `APFloat`: Query `hasNanOrInf` from semantics (#116158)
Whether a floating point type supports NaN or infinity can be queried
from its semantics. No need to hard-code a list of types.
-rw-r--r-- | llvm/include/llvm/ADT/APFloat.h | 16 | ||||
-rw-r--r-- | llvm/lib/Support/APFloat.cpp | 4 | ||||
-rw-r--r-- | llvm/unittests/ADT/APFloatTest.cpp | 6 |
3 files changed, 9 insertions, 17 deletions
diff --git a/llvm/include/llvm/ADT/APFloat.h b/llvm/include/llvm/ADT/APFloat.h index 97547fb..4b5a859 100644 --- a/llvm/include/llvm/ADT/APFloat.h +++ b/llvm/include/llvm/ADT/APFloat.h @@ -311,6 +311,7 @@ struct APFloatBase { static unsigned int semanticsIntSizeInBits(const fltSemantics&, bool); static bool semanticsHasZero(const fltSemantics &); static bool semanticsHasSignedRepr(const fltSemantics &); + static bool semanticsHasNanOrInf(const fltSemantics &); // Returns true if any number described by \p Src can be precisely represented // by a normal (not subnormal) value in \p Dst. @@ -1127,21 +1128,6 @@ public: /// \param Semantics - type float semantics static APFloat getAllOnesValue(const fltSemantics &Semantics); - /// Returns true if the given semantics supports either NaN or Infinity. - /// - /// \param Sem - type float semantics - static bool hasNanOrInf(const fltSemantics &Sem) { - switch (SemanticsToEnum(Sem)) { - default: - return true; - // Below Semantics do not support {NaN or Inf} - case APFloat::S_Float6E3M2FN: - case APFloat::S_Float6E2M3FN: - case APFloat::S_Float4E2M1FN: - return false; - } - } - /// Returns true if the given semantics has actual significand. /// /// \param Sem - type float semantics diff --git a/llvm/lib/Support/APFloat.cpp b/llvm/lib/Support/APFloat.cpp index c566d48..58bf002 100644 --- a/llvm/lib/Support/APFloat.cpp +++ b/llvm/lib/Support/APFloat.cpp @@ -375,6 +375,10 @@ bool APFloatBase::semanticsHasSignedRepr(const fltSemantics &semantics) { return semantics.hasSignedRepr; } +bool APFloatBase::semanticsHasNanOrInf(const fltSemantics &semantics) { + return semantics.nonFiniteBehavior != fltNonfiniteBehavior::FiniteOnly; +} + bool APFloatBase::isRepresentableAsNormalIn(const fltSemantics &Src, const fltSemantics &Dst) { // Exponent range must be larger. diff --git a/llvm/unittests/ADT/APFloatTest.cpp b/llvm/unittests/ADT/APFloatTest.cpp index 74aaf66..ab9db8e 100644 --- a/llvm/unittests/ADT/APFloatTest.cpp +++ b/llvm/unittests/ADT/APFloatTest.cpp @@ -832,7 +832,8 @@ TEST(APFloatTest, IsSmallestNormalized) { EXPECT_FALSE(APFloat::getZero(Semantics, false).isSmallestNormalized()); EXPECT_FALSE(APFloat::getZero(Semantics, true).isSmallestNormalized()); - if (APFloat::hasNanOrInf(Semantics)) { + if (APFloat::semanticsHasNanOrInf(Semantics)) { + // Types that do not support Inf will return NaN when asked for Inf. EXPECT_FALSE(APFloat::getInf(Semantics, false).isSmallestNormalized()); EXPECT_FALSE(APFloat::getInf(Semantics, true).isSmallestNormalized()); @@ -7344,7 +7345,8 @@ TEST(APFloatTest, getExactLog2) { EXPECT_EQ(INT_MIN, APFloat::getZero(Semantics, false).getExactLog2Abs()); EXPECT_EQ(INT_MIN, APFloat::getZero(Semantics, true).getExactLog2Abs()); - if (APFloat::hasNanOrInf(Semantics)) { + if (APFloat::semanticsHasNanOrInf(Semantics)) { + // Types that do not support Inf will return NaN when asked for Inf. EXPECT_EQ(INT_MIN, APFloat::getInf(Semantics).getExactLog2()); EXPECT_EQ(INT_MIN, APFloat::getInf(Semantics, true).getExactLog2()); EXPECT_EQ(INT_MIN, APFloat::getNaN(Semantics, false).getExactLog2()); |