[llvm] [InstCombine] Fold Minimum over Trailing/Leading Bits Counts (PR #90402)
Nikita Popov via llvm-commits
llvm-commits at lists.llvm.org
Thu May 2 18:58:22 PDT 2024
================
@@ -1428,6 +1428,40 @@ static Instruction *foldBitOrderCrossLogicOp(Value *V,
return nullptr;
}
+/// Fold an unsigned minimum of trailing or leading zero bits counts:
+/// umin(cttz(CtOp, ZeroUndef), ConstOp) --> cttz(CtOp | (1 << ConstOp))
+/// umin(ctlz(CtOp, ZeroUndef), ConstOp) --> ctlz(CtOp | ((1 << (bitwidth-1))
+/// >> ConstOp))
+template <Intrinsic::ID IntrID>
+static Instruction *foldMinimumOverTrailingOrLeadingZeroCount(
+ Instruction *OrigInst, Value *CtOp, Value *ZeroUndef, Constant *ConstOp,
+ const DataLayout &DL, InstCombiner::BuilderTy &Builder) {
+ static_assert(IntrID == Intrinsic::cttz || IntrID == Intrinsic::ctlz,
+ "This helper only supports cttz and ctlz intrinsics");
+
+ auto BitWidth = ConstOp->getType()->getScalarSizeInBits();
+ auto *Ty = ConstOp->getType();
+
+ Constant *NewConst = ConstantFoldSelectInstruction(
+ ConstantFoldCompareInstOperands(CmpInst::ICMP_ULT, ConstOp,
+ ConstantInt::get(Ty, BitWidth), DL),
+ ConstantFoldBinaryOpOperands(
+ IntrID == Intrinsic::cttz ? Instruction::Shl : Instruction::LShr,
+ IntrID == Intrinsic::cttz
+ ? ConstantInt::get(Ty, 1)
+ : ConstantInt::get(Ty, APInt::getSignedMinValue(BitWidth)),
+ ConstOp, DL),
+ Constant::getNullValue(Ty));
----------------
nikic wrote:
If you go with this implementation, you'll also have to adjust the alive2 proofs in the PR description to be in terms of this implementation rather than assumes.
https://github.com/llvm/llvm-project/pull/90402
More information about the llvm-commits
mailing list