aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/Analysis/ValueTracking.cpp
diff options
context:
space:
mode:
authorgoldsteinn <35538541+goldsteinn@users.noreply.github.com>2025-01-11 15:11:11 -0600
committerGitHub <noreply@github.com>2025-01-11 15:11:11 -0600
commit17ef436e3df231fa45aa6010bf8ed41189380679 (patch)
tree908c5ac33c35e5dbb992321c7019eb058c41cd75 /llvm/lib/Analysis/ValueTracking.cpp
parentcc995ad064ffe22566270fe95e974a368c71ba22 (diff)
downloadllvm-17ef436e3df231fa45aa6010bf8ed41189380679.zip
llvm-17ef436e3df231fa45aa6010bf8ed41189380679.tar.gz
llvm-17ef436e3df231fa45aa6010bf8ed41189380679.tar.bz2
[ValueTracking] Take into account whether zero is poison when computing CR for `ct{t,l}z` (#122548)
Diffstat (limited to 'llvm/lib/Analysis/ValueTracking.cpp')
-rw-r--r--llvm/lib/Analysis/ValueTracking.cpp15
1 files changed, 11 insertions, 4 deletions
diff --git a/llvm/lib/Analysis/ValueTracking.cpp b/llvm/lib/Analysis/ValueTracking.cpp
index 92338d3..53da8d2 100644
--- a/llvm/lib/Analysis/ValueTracking.cpp
+++ b/llvm/lib/Analysis/ValueTracking.cpp
@@ -9897,13 +9897,20 @@ static void setLimitsForBinOp(const BinaryOperator &BO, APInt &Lower,
}
}
-static ConstantRange getRangeForIntrinsic(const IntrinsicInst &II) {
+static ConstantRange getRangeForIntrinsic(const IntrinsicInst &II,
+ bool UseInstrInfo) {
unsigned Width = II.getType()->getScalarSizeInBits();
const APInt *C;
switch (II.getIntrinsicID()) {
- case Intrinsic::ctpop:
case Intrinsic::ctlz:
- case Intrinsic::cttz:
+ case Intrinsic::cttz: {
+ APInt Upper(Width, Width);
+ if (!UseInstrInfo || !match(II.getArgOperand(1), m_One()))
+ Upper += 1;
+ // Maximum of set/clear bits is the bit width.
+ return ConstantRange::getNonEmpty(APInt::getZero(Width), Upper);
+ }
+ case Intrinsic::ctpop:
// Maximum of set/clear bits is the bit width.
return ConstantRange::getNonEmpty(APInt::getZero(Width),
APInt(Width, Width) + 1);
@@ -10094,7 +10101,7 @@ ConstantRange llvm::computeConstantRange(const Value *V, bool ForSigned,
setLimitsForBinOp(*BO, Lower, Upper, IIQ, ForSigned);
CR = ConstantRange::getNonEmpty(Lower, Upper);
} else if (auto *II = dyn_cast<IntrinsicInst>(V))
- CR = getRangeForIntrinsic(*II);
+ CR = getRangeForIntrinsic(*II, UseInstrInfo);
else if (auto *SI = dyn_cast<SelectInst>(V)) {
ConstantRange CRTrue = computeConstantRange(
SI->getTrueValue(), ForSigned, UseInstrInfo, AC, CtxI, DT, Depth + 1);