Skip to content

Commit f071cac

Browse files
authored
[ConstantFPRange] Add getWithout[NaN|Inf] (#162696)
This patch adds getWithoutNaN/getWithoutInf. We will apply nnan/ninf flags to the range of operands/results for a more precise range.
1 parent 30ccb60 commit f071cac

File tree

3 files changed

+40
-0
lines changed

3 files changed

+40
-0
lines changed

llvm/include/llvm/IR/ConstantFPRange.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -206,6 +206,16 @@ class [[nodiscard]] ConstantFPRange {
206206

207207
/// Calculate range of negated values.
208208
LLVM_ABI ConstantFPRange negate() const;
209+
210+
/// Get the range without NaNs. It is useful when we apply nnan flag to range
211+
/// of operands/results.
212+
ConstantFPRange getWithoutNaN() const {
213+
return ConstantFPRange(Lower, Upper, false, false);
214+
}
215+
216+
/// Get the range without infinities. It is useful when we apply ninf flag to
217+
/// range of operands/results.
218+
LLVM_ABI ConstantFPRange getWithoutInf() const;
209219
};
210220

211221
inline raw_ostream &operator<<(raw_ostream &OS, const ConstantFPRange &CR) {

llvm/lib/IR/ConstantFPRange.cpp

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -411,3 +411,17 @@ ConstantFPRange ConstantFPRange::abs() const {
411411
ConstantFPRange ConstantFPRange::negate() const {
412412
return ConstantFPRange(-Upper, -Lower, MayBeQNaN, MayBeSNaN);
413413
}
414+
415+
ConstantFPRange ConstantFPRange::getWithoutInf() const {
416+
if (isNaNOnly())
417+
return *this;
418+
APFloat NewLower = Lower;
419+
APFloat NewUpper = Upper;
420+
if (Lower.isNegInfinity())
421+
NewLower = APFloat::getLargest(getSemantics(), /*Negative=*/true);
422+
if (Upper.isPosInfinity())
423+
NewUpper = APFloat::getLargest(getSemantics(), /*Negative=*/false);
424+
canonicalizeRange(NewLower, NewUpper);
425+
return ConstantFPRange(std::move(NewLower), std::move(NewUpper), MayBeQNaN,
426+
MayBeSNaN);
427+
}

llvm/unittests/IR/ConstantFPRangeTest.cpp

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -802,4 +802,20 @@ TEST_F(ConstantFPRangeTest, negate) {
802802
ConstantFPRange::getNonNaN(APFloat(-2.0), APFloat(3.0)));
803803
}
804804

805+
TEST_F(ConstantFPRangeTest, getWithout) {
806+
EXPECT_EQ(Full.getWithoutNaN(), ConstantFPRange::getNonNaN(Sem));
807+
EXPECT_EQ(NaN.getWithoutNaN(), Empty);
808+
809+
EXPECT_EQ(NaN.getWithoutInf(), NaN);
810+
EXPECT_EQ(PosInf.getWithoutInf(), Empty);
811+
EXPECT_EQ(NegInf.getWithoutInf(), Empty);
812+
EXPECT_EQ(ConstantFPRange::getNonNaN(Sem).getWithoutInf(), Finite);
813+
EXPECT_EQ(Zero.getWithoutInf(), Zero);
814+
EXPECT_EQ(ConstantFPRange::getNonNaN(APFloat::getInf(Sem, /*Negative=*/true),
815+
APFloat(3.0))
816+
.getWithoutInf(),
817+
ConstantFPRange::getNonNaN(
818+
APFloat::getLargest(Sem, /*Negative=*/true), APFloat(3.0)));
819+
}
820+
805821
} // anonymous namespace

0 commit comments

Comments
 (0)