summaryrefslogtreecommitdiff
path: root/llvm/lib/Analysis/ValueTracking.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/lib/Analysis/ValueTracking.cpp')
-rw-r--r--llvm/lib/Analysis/ValueTracking.cpp55
1 files changed, 27 insertions, 28 deletions
diff --git a/llvm/lib/Analysis/ValueTracking.cpp b/llvm/lib/Analysis/ValueTracking.cpp
index 6f602da569e8..37414de4c240 100644
--- a/llvm/lib/Analysis/ValueTracking.cpp
+++ b/llvm/lib/Analysis/ValueTracking.cpp
@@ -4912,43 +4912,42 @@ void computeKnownFPClass(const Value *V, const APInt &DemandedElts,
break;
}
- case Intrinsic::trunc: {
+ case Intrinsic::trunc:
+ case Intrinsic::floor:
+ case Intrinsic::ceil:
+ case Intrinsic::rint:
+ case Intrinsic::nearbyint:
+ case Intrinsic::round:
+ case Intrinsic::roundeven: {
KnownFPClass KnownSrc;
-
FPClassTest InterestedSrcs = InterestedClasses;
- if (InterestedClasses & fcZero)
- InterestedClasses |= fcNormal | fcSubnormal;
-
- computeKnownFPClass(II->getArgOperand(0), DemandedElts, InterestedSrcs,
- KnownSrc, Depth + 1, Q, TLI);
+ if (InterestedSrcs & fcPosFinite)
+ InterestedSrcs |= fcPosFinite;
+ if (InterestedSrcs & fcNegFinite)
+ InterestedSrcs |= fcNegFinite;
+ computeKnownFPClass(II->getArgOperand(0), DemandedElts,
+ InterestedSrcs, KnownSrc, Depth + 1, Q, TLI);
// Integer results cannot be subnormal.
Known.knownNot(fcSubnormal);
- // trunc passes through infinities.
- if (KnownSrc.isKnownNeverPosInfinity())
- Known.knownNot(fcPosInf);
- if (KnownSrc.isKnownNeverNegInfinity())
- Known.knownNot(fcNegInf);
-
- // Non-constrained intrinsics do not guarantee signaling nan quieting.
- if (KnownSrc.isKnownNeverNaN())
- Known.knownNot(fcNan);
-
- if (KnownSrc.isKnownNever(fcPosNormal))
- Known.knownNot(fcPosNormal);
-
- if (KnownSrc.isKnownNever(fcNegNormal))
- Known.knownNot(fcNegNormal);
+ Known.propagateNaN(KnownSrc, true);
- if (KnownSrc.isKnownNever(fcPosZero | fcPosSubnormal | fcPosNormal))
- Known.knownNot(fcPosZero);
+ // Pass through infinities, except PPC_FP128 is a special case for
+ // intrinsics other than trunc.
+ if (IID == Intrinsic::trunc || !V->getType()->isMultiUnitFPType()) {
+ if (KnownSrc.isKnownNeverPosInfinity())
+ Known.knownNot(fcPosInf);
+ if (KnownSrc.isKnownNeverNegInfinity())
+ Known.knownNot(fcNegInf);
+ }
- if (KnownSrc.isKnownNever(fcNegZero | fcNegSubnormal | fcNegNormal))
- Known.knownNot(fcNegZero);
+ // Negative round ups to 0 produce -0
+ if (KnownSrc.isKnownNever(fcPosFinite))
+ Known.knownNot(fcPosFinite);
+ if (KnownSrc.isKnownNever(fcNegFinite))
+ Known.knownNot(fcNegFinite);
- // Sign should be preserved
- Known.SignBit = KnownSrc.SignBit;
break;
}
case Intrinsic::exp: