38#define DEBUG_TYPE "instcombine"
42using namespace PatternMatch;
52 if (!V->hasOneUse())
return nullptr;
54 bool MadeChange =
false;
58 Value *
A =
nullptr, *
B =
nullptr, *One =
nullptr;
68 if (
I &&
I->isLogicalShift() &&
77 if (
I->getOpcode() == Instruction::LShr && !
I->isExact()) {
82 if (
I->getOpcode() == Instruction::Shl && !
I->hasNoUnsignedWrap()) {
83 I->setHasNoUnsignedWrap();
92 return MadeChange ? V :
nullptr;
108 bool HasAnyNoWrap =
I.hasNoSignedWrap() ||
I.hasNoUnsignedWrap();
116 bool HasAnyNoWrap =
I.hasNoSignedWrap() ||
I.hasNoUnsignedWrap();
154 bool PropagateNSW = HasNSW && cast<ShlOperator>(
Y)->hasNoSignedWrap();
169 Value *Shl = Builder.
CreateShl(FrX, Z,
"mulshl", HasNUW, PropagateNSW);
190 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
208 Type *Ty =
I.getType();
210 const bool HasNSW =
I.hasNoSignedWrap();
211 const bool HasNUW =
I.hasNoUnsignedWrap();
230 assert(Shl &&
"Constant folding of immediate constants failed");
233 if (HasNUW &&
Mul->hasNoUnsignedWrap())
249 if (
match(NewCst,
m_APInt(V)) && *V != V->getBitWidth() - 1)
263 auto *Op1C = cast<Constant>(Op1);
267 HasNSW && Op1C->isNotMinSignedValue()));
276 const APInt *NegPow2C;
280 unsigned SrcWidth =
X->getType()->getScalarSizeInBits();
282 if (ShiftAmt >=
BitWidth - SrcWidth) {
285 return BinaryOperator::CreateShl(Z, ConstantInt::get(Ty, ShiftAmt));
306 auto *BOp0 = cast<BinaryOperator>(Op0);
308 (BOp0->getOpcode() == Instruction::Or || BOp0->hasNoUnsignedWrap());
310 auto *BO = BinaryOperator::CreateAdd(NewMul, NewC);
311 if (HasNUW && Op0NUW) {
313 if (
auto *NewMulBO = dyn_cast<BinaryOperator>(NewMul))
314 NewMulBO->setHasNoUnsignedWrap();
315 BO->setHasNoUnsignedWrap();
323 if (Op0 == Op1 &&
match(Op0, m_Intrinsic<Intrinsic::abs>(
m_Value(
X))))
324 return BinaryOperator::CreateMul(
X,
X);
329 if (
I.hasNoSignedWrap() &&
347 auto *NewMul = BinaryOperator::CreateMul(
X,
Y);
348 if (HasNSW && cast<OverflowingBinaryOperator>(Op0)->
hasNoSignedWrap() &&
350 NewMul->setHasNoSignedWrap();
363 return BinaryOperator::CreateMul(NegOp0,
X);
371 auto UDivCheck = [&C1](
const APInt &
C) {
return C.urem(*C1).isZero(); };
372 auto SDivCheck = [&C1](
const APInt &
C) {
380 auto BOpc = cast<BinaryOperator>(Op0)->getOpcode();
393 if (!Div || (Div->
getOpcode() != Instruction::UDiv &&
394 Div->
getOpcode() != Instruction::SDiv)) {
396 Div = dyn_cast<BinaryOperator>(Op1);
398 Value *Neg = dyn_castNegVal(
Y);
401 (Div->
getOpcode() == Instruction::UDiv ||
402 Div->
getOpcode() == Instruction::SDiv)) {
412 auto RemOpc = Div->
getOpcode() == Instruction::UDiv ? Instruction::URem
420 return BinaryOperator::CreateSub(XFreeze, Rem);
421 return BinaryOperator::CreateSub(Rem, XFreeze);
433 return BinaryOperator::CreateAnd(Op0, Op1);
445 X->getType()->isIntOrIntVectorTy(1) &&
X->getType() ==
Y->getType() &&
446 (Op0->
hasOneUse() || Op1->hasOneUse() ||
X ==
Y)) {
455 X->getType()->isIntOrIntVectorTy(1) &&
X->getType() ==
Y->getType() &&
456 (Op0->
hasOneUse() || Op1->hasOneUse())) {
471 X->getType()->isIntOrIntVectorTy(1))
486 *
C ==
C->getBitWidth() - 1) {
498 *
C ==
C->getBitWidth() - 1) {
545 bool Changed =
false;
546 if (!HasNSW && willNotOverflowSignedMul(Op0, Op1,
I)) {
548 I.setHasNoSignedWrap(
true);
551 if (!HasNUW && willNotOverflowUnsignedMul(Op0, Op1,
I,
I.hasNoSignedWrap())) {
553 I.setHasNoUnsignedWrap(
true);
556 return Changed ? &
I :
nullptr;
561 assert((Opcode == Instruction::FMul || Opcode == Instruction::FDiv) &&
562 "Expected fmul or fdiv");
564 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
580 (Op0->
hasOneUse() || Op1->hasOneUse())) {
596 Intrinsic::powi, {
X->getType(), YZ->
getType()}, {
X, YZ}, &
I);
602 unsigned Opcode =
I.getOpcode();
603 assert((Opcode == Instruction::FMul || Opcode == Instruction::FDiv) &&
604 "Unexpected opcode");
611 Constant *One = ConstantInt::get(
Y->getType(), 1);
612 if (willNotOverflowSignedAdd(
Y, One,
I)) {
619 Value *Op0 =
I.getOperand(0);
620 Value *Op1 =
I.getOperand(1);
621 if (Opcode == Instruction::FMul &&
I.isOnlyUserOfAnyOperand() &&
626 Y->getType() == Z->getType()) {
631 if (Opcode == Instruction::FDiv &&
I.hasAllowReassoc() &&
I.hasNoNaNs()) {
638 willNotOverflowSignedSub(
Y, ConstantInt::get(
Y->getType(), 1),
I)) {
640 Instruction *NewPow = createPowiExpr(
I, *
this, Op1,
Y, NegOne);
651 willNotOverflowSignedSub(
Y, ConstantInt::get(
Y->getType(), 1),
I)) {
653 auto *NewPow = createPowiExpr(
I, *
this,
X,
Y, NegOne);
685 return !R1.
empty() && !
R2.empty();
710 CallInst *FSqrt = cast<CallInst>(
X->getOperand(1));
719 if (!
X->hasAllowReassoc() || !
X->hasAllowReciprocal() || !
X->hasNoInfs())
726 if (BBx != BBr1 && BBx != BBr2)
735 return (
I->getParent() != BBr1 || !
I->hasAllowReassoc());
745 return (
I->getParent() == BBr2 &&
I->hasAllowReassoc());
750 Value *Op0 =
I.getOperand(0);
751 Value *Op1 =
I.getOperand(1);
811 BinaryOperator *DivOp = cast<BinaryOperator>(((Z == Op0) ? Op1 : Op0));
836 if (
I.hasNoSignedZeros() &&
840 if (
I.hasNoSignedZeros() &&
847 if (
I.hasNoNaNs() &&
I.hasNoSignedZeros() && Op0 == Op1 && Op0->
hasNUses(2)) {
874 if (
I.isOnlyUserOfAnyOperand()) {
928 I.getFastMathFlags(),
954 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
969 {
I.getType()}, {Op1, Op0}, &
I);
980 if (
I.hasNoNaNs() &&
I.hasNoSignedZeros()) {
985 X->getType()->isIntOrIntVectorTy(1)) {
987 SI->copyFastMathFlags(
I.getFastMathFlags());
991 X->getType()->isIntOrIntVectorTy(1)) {
993 SI->copyFastMathFlags(
I.getFastMathFlags());
1002 if (
I.hasAllowReassoc())
1011 Log2 = cast<IntrinsicInst>(Op0);
1016 Log2 = cast<IntrinsicInst>(Op1);
1030 Value *Start =
nullptr, *Step =
nullptr;
1044 if (!Result->hasNoNaNs())
1045 Result->setHasNoInfs(
false);
1056 SelectInst *SI = dyn_cast<SelectInst>(
I.getOperand(1));
1081 Value *SelectCond = SI->getCondition();
1082 if (SI->use_empty() && SelectCond->
hasOneUse())
1088 while (BBI != BBFront) {
1096 for (
Use &
Op : BBI->operands()) {
1100 }
else if (
Op == SelectCond) {
1110 if (&*BBI == SelectCond)
1111 SelectCond =
nullptr;
1114 if (!SelectCond && !SI)
1125 Product = IsSigned ? C1.
smul_ov(C2, Overflow) : C1.
umul_ov(C2, Overflow);
1152 assert((
I.getOpcode() == Instruction::SDiv ||
1153 I.getOpcode() == Instruction::UDiv) &&
1154 "Expected integer divide");
1156 bool IsSigned =
I.getOpcode() == Instruction::SDiv;
1157 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
1158 Type *Ty =
I.getType();
1167 auto *
Mul = cast<OverflowingBinaryOperator>(Op0);
1168 auto *Shl = cast<OverflowingBinaryOperator>(Op1);
1169 bool HasNUW =
Mul->hasNoUnsignedWrap() && Shl->hasNoUnsignedWrap();
1170 bool HasNSW =
Mul->hasNoSignedWrap() && Shl->hasNoSignedWrap();
1173 if (!IsSigned && HasNUW)
1177 if (IsSigned && HasNSW && (Op0->
hasOneUse() || Op1->hasOneUse())) {
1187 auto *Shl0 = cast<OverflowingBinaryOperator>(Op0);
1188 auto *Shl1 = cast<OverflowingBinaryOperator>(Op1);
1194 ((Shl0->hasNoUnsignedWrap() && Shl1->hasNoUnsignedWrap()) ||
1195 (Shl0->hasNoUnsignedWrap() && Shl0->hasNoSignedWrap() &&
1196 Shl1->hasNoSignedWrap())))
1201 if (IsSigned && Shl0->hasNoSignedWrap() && Shl1->hasNoSignedWrap() &&
1202 Shl1->hasNoUnsignedWrap())
1210 auto *Shl0 = cast<OverflowingBinaryOperator>(Op0);
1211 auto *Shl1 = cast<OverflowingBinaryOperator>(Op1);
1213 if (IsSigned ? (Shl0->hasNoSignedWrap() && Shl1->hasNoSignedWrap())
1214 : (Shl0->hasNoUnsignedWrap() && Shl1->hasNoUnsignedWrap())) {
1215 Constant *One = ConstantInt::get(
X->getType(), 1);
1219 One,
Y,
"shl.dividend",
1222 IsSigned ? (Shl0->hasNoUnsignedWrap() || Shl1->hasNoUnsignedWrap())
1223 : Shl0->hasNoSignedWrap());
1224 return Builder.
CreateLShr(Dividend, Z,
"",
I.isExact());
1233 assert(
I.isIntDivRem() &&
"Unexpected instruction");
1234 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
1238 auto *Op1C = dyn_cast<Constant>(Op1);
1239 Type *Ty =
I.getType();
1240 auto *VTy = dyn_cast<FixedVectorType>(Ty);
1242 unsigned NumElts = VTy->getNumElements();
1243 for (
unsigned i = 0; i != NumElts; ++i) {
1245 if (Elt && (Elt->
isNullValue() || isa<UndefValue>(Elt)))
1283 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
1284 bool IsSigned =
I.getOpcode() == Instruction::SDiv;
1285 Type *Ty =
I.getType();
1298 ConstantInt::get(Ty, Product));
1306 if (
isMultiple(*C2, *C1, Quotient, IsSigned)) {
1308 ConstantInt::get(Ty, Quotient));
1309 NewDiv->setIsExact(
I.isExact());
1314 if (
isMultiple(*C1, *C2, Quotient, IsSigned)) {
1316 ConstantInt::get(Ty, Quotient));
1317 auto *OBO = cast<OverflowingBinaryOperator>(Op0);
1318 Mul->setHasNoUnsignedWrap(!IsSigned && OBO->hasNoUnsignedWrap());
1319 Mul->setHasNoSignedWrap(OBO->hasNoSignedWrap());
1332 if (
isMultiple(*C2, C1Shifted, Quotient, IsSigned)) {
1334 ConstantInt::get(Ty, Quotient));
1335 BO->setIsExact(
I.isExact());
1340 if (
isMultiple(C1Shifted, *C2, Quotient, IsSigned)) {
1342 ConstantInt::get(Ty, Quotient));
1343 auto *OBO = cast<OverflowingBinaryOperator>(Op0);
1344 Mul->setHasNoUnsignedWrap(!IsSigned && OBO->hasNoUnsignedWrap());
1345 Mul->setHasNoSignedWrap(OBO->hasNoSignedWrap());
1358 return BinaryOperator::CreateNSWAdd(
X, ConstantInt::get(Ty, Quotient));
1363 return BinaryOperator::CreateNUWAdd(
X,
1364 ConstantInt::get(Ty, C1->
udiv(*C2)));
1405 return BinaryOperator::CreateNSWShl(ConstantInt::get(Ty, 1),
Y);
1407 return BinaryOperator::CreateNUWShl(ConstantInt::get(Ty, 1),
Y);
1411 bool HasNSW = cast<OverflowingBinaryOperator>(Op1)->hasNoSignedWrap();
1412 bool HasNUW = cast<OverflowingBinaryOperator>(Op1)->hasNoUnsignedWrap();
1413 if ((IsSigned && HasNSW) || (!IsSigned && HasNUW)) {
1422 if (!IsSigned && Op1->hasOneUse() &&
1440 auto *InnerDiv = cast<PossiblyExactOperator>(Op0);
1441 auto *
Mul = cast<OverflowingBinaryOperator>(InnerDiv->getOperand(0));
1443 if (!IsSigned &&
Mul->hasNoUnsignedWrap())
1444 NewDiv = BinaryOperator::CreateUDiv(
X,
Y);
1445 else if (IsSigned &&
Mul->hasNoSignedWrap())
1446 NewDiv = BinaryOperator::CreateSDiv(
X,
Y);
1450 NewDiv->
setIsExact(
I.isExact() && InnerDiv->isExact());
1457 auto OB0HasNSW = cast<OverflowingBinaryOperator>(Op0)->
hasNoSignedWrap();
1458 auto OB0HasNUW = cast<OverflowingBinaryOperator>(Op0)->hasNoUnsignedWrap();
1461 auto OB1HasNSW = cast<OverflowingBinaryOperator>(Op1)->
hasNoSignedWrap();
1463 cast<OverflowingBinaryOperator>(Op1)->hasNoUnsignedWrap();
1464 const APInt *C1, *C2;
1465 if (IsSigned && OB0HasNSW) {
1467 return BinaryOperator::CreateSDiv(
A,
B);
1469 if (!IsSigned && OB0HasNUW) {
1471 return BinaryOperator::CreateUDiv(
A,
B);
1473 return BinaryOperator::CreateUDiv(
A,
B);
1479 if (
auto *Val = CreateDivOrNull(
Y, Z))
1483 if (
auto *Val = CreateDivOrNull(
X, Z))
1494 return reinterpret_cast<Value *
>(-1);
1502 return IfFold([&]() {
1523 auto *TI = cast<TruncInst>(
Op);
1524 if (AssumeNonZero || TI->hasNoUnsignedWrap())
1526 return IfFold([&]() {
1528 TI->hasNoUnsignedWrap());
1535 auto *BO = cast<OverflowingBinaryOperator>(
Op);
1537 if (AssumeNonZero || BO->hasNoUnsignedWrap() || BO->hasNoSignedWrap())
1545 auto *PEO = cast<PossiblyExactOperator>(
Op);
1546 if (AssumeNonZero || PEO->isExact())
1555 return IfFold([&]() {
return LogX; });
1557 return IfFold([&]() {
return LogY; });
1566 return IfFold([&]() {
1572 auto *
MinMax = dyn_cast<MinMaxIntrinsic>(
Op);
1580 return IfFold([&]() {
1596 Type *Ty =
I.getType();
1599 X->getType() ==
Y->getType() && (
N->hasOneUse() ||
D->hasOneUse())) {
1645 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
1647 const APInt *C1, *C2;
1655 X, ConstantInt::get(
X->getType(), C2ShlC1));
1664 Type *Ty =
I.getType();
1685 if (
I.isExact() && cast<PossiblyExactOperator>(Op0)->isExact())
1690 auto GetShiftableDenom = [&](
Value *Denom) ->
Value * {
1706 if (
auto *Res = GetShiftableDenom(Op1))
1725 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
1726 Type *Ty =
I.getType();
1742 return BinaryOperator::CreateExactAShr(Op0,
C);
1748 return BinaryOperator::CreateExactAShr(Op0, ShAmt);
1783 Constant *NegC = ConstantInt::get(Ty, -(*Op1C));
1817 auto *BO = BinaryOperator::CreateUDiv(Op0, Op1,
I.getName());
1818 BO->setIsExact(
I.isExact());
1836 auto *BO = BinaryOperator::CreateUDiv(Op0, Op1,
I.getName());
1837 BO->setIsExact(
I.isExact());
1867 if (
I.hasNoNaNs() &&
1872 Intrinsic::copysign, {
C->getType()},
1881 if (!(
C->hasExactInverseFP() || (
I.hasAllowReciprocal() &&
C->isNormalFP())))
1889 Instruction::FDiv, ConstantFP::get(
I.getType(), 1.0),
C,
DL);
1890 if (!RecipC || !RecipC->isNormalFP())
1910 if (!
I.hasAllowReassoc() || !
I.hasAllowReciprocal())
1935 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
1936 auto *
II = dyn_cast<IntrinsicInst>(Op1);
1937 if (!
II || !
II->hasOneUse() || !
I.hasAllowReassoc() ||
1938 !
I.hasAllowReciprocal())
1948 case Intrinsic::pow:
1949 Args.push_back(
II->getArgOperand(0));
1952 case Intrinsic::powi: {
1960 Args.push_back(
II->getArgOperand(0));
1961 Args.push_back(Builder.
CreateNeg(
II->getArgOperand(1)));
1962 Type *Tys[] = {
I.getType(),
II->getArgOperand(1)->getType()};
1966 case Intrinsic::exp:
1967 case Intrinsic::exp2:
1982 if (!
I.hasAllowReassoc() || !
I.hasAllowReciprocal())
1984 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
1985 auto *
II = dyn_cast<IntrinsicInst>(Op1);
1986 if (!
II ||
II->getIntrinsicID() != Intrinsic::sqrt || !
II->hasOneUse() ||
1987 !
II->hasAllowReassoc() || !
II->hasAllowReciprocal())
1991 auto *DivOp = dyn_cast<Instruction>(
II->getOperand(0));
1996 if (!DivOp->hasAllowReassoc() || !
I.hasAllowReciprocal() ||
1997 !DivOp->hasOneUse())
2024 B.SetInsertPoint(
X);
2029 auto *FDiv = cast<Instruction>(
2030 B.CreateFDiv(ConstantFP::get(
X->getType(), 1.0), SqrtOp));
2031 auto *R1FPMathMDNode = (*R1.
begin())->getMetadata(LLVMContext::MD_fpmath);
2035 R1FPMathMDNode,
I->getMetadata(LLVMContext::MD_fpmath));
2036 R1FMF &=
I->getFastMathFlags();
2040 FDiv->
setMetadata(LLVMContext::MD_fpmath, R1FPMathMDNode);
2041 FDiv->copyFastMathFlags(R1FMF);
2046 auto *FSqrt = cast<CallInst>(CI->
clone());
2047 FSqrt->insertBefore(CI);
2048 auto *R2FPMathMDNode = (*
R2.begin())->getMetadata(LLVMContext::MD_fpmath);
2052 R2FPMathMDNode,
I->getMetadata(LLVMContext::MD_fpmath));
2053 R2FMF &=
I->getFastMathFlags();
2057 FSqrt->
setMetadata(LLVMContext::MD_fpmath, R2FPMathMDNode);
2058 FSqrt->copyFastMathFlags(R2FMF);
2064 FMul = cast<Instruction>(
B.CreateFNeg(
Mul));
2066 FMul = cast<Instruction>(
B.CreateFMul(FDiv, FSqrt));
2067 FMul->copyMetadata(*
X);
2078 I.getFastMathFlags(),
2097 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
2111 CallInst *CI = cast<CallInst>(
I.getOperand(1));
2116 if (isa<Constant>(Op0))
2117 if (
SelectInst *SI = dyn_cast<SelectInst>(Op1))
2121 if (isa<Constant>(Op1))
2122 if (
SelectInst *SI = dyn_cast<SelectInst>(Op0))
2126 if (
I.hasAllowReassoc() &&
I.hasAllowReciprocal()) {
2129 (!isa<Constant>(
Y) || !isa<Constant>(Op1))) {
2135 (!isa<Constant>(
Y) || !isa<Constant>(Op0))) {
2150 if (
I.hasAllowReassoc() && Op0->
hasOneUse() && Op1->hasOneUse()) {
2154 bool IsTan =
match(Op0, m_Intrinsic<Intrinsic::sin>(
m_Value(
X))) &&
2157 !IsTan &&
match(Op0, m_Intrinsic<Intrinsic::cos>(
m_Value(
X))) &&
2160 if ((IsTan || IsCot) &&
hasFloatFn(M, &
TLI,
I.getType(), LibFunc_tan,
2161 LibFunc_tanf, LibFunc_tanl)) {
2164 B.setFastMathFlags(
I.getFastMathFlags());
2166 cast<CallBase>(Op0)->getCalledFunction()->getAttributes();
2168 LibFunc_tanl,
B, Attrs);
2170 Res =
B.CreateFDiv(ConstantFP::get(
I.getType(), 1.0), Res);
2179 if (
I.hasNoNaNs() &&
I.hasAllowReassoc() &&
2188 if (
I.hasNoNaNs() &&
I.hasNoInfs() &&
2192 Intrinsic::copysign, ConstantFP::get(
I.getType(), 1.0),
X, &
I);
2203 if (
I.hasAllowReassoc() &&
2226 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1), *
X =
nullptr;
2228 bool ShiftByX =
false;
2232 bool &PreserveNSW) ->
bool {
2233 const APInt *Tmp =
nullptr;
2252 const APInt *Tmp =
nullptr;
2264 bool Op0PreserveNSW =
true, Op1PreserveNSW =
true;
2265 if (MatchShiftOrMulXC(Op0,
X,
Y, Op0PreserveNSW) &&
2266 MatchShiftOrMulXC(Op1,
X, Z, Op1PreserveNSW)) {
2268 }
else if (MatchShiftCX(Op0,
Y,
X) && MatchShiftCX(Op1, Z,
X)) {
2274 bool IsSRem =
I.getOpcode() == Instruction::SRem;
2281 bool BO0NoWrap = IsSRem ? BO0HasNSW : BO0HasNUW;
2283 APInt RemYZ = IsSRem ?
Y.srem(Z) :
Y.urem(Z);
2287 if (RemYZ.
isZero() && BO0NoWrap)
2293 auto CreateMulOrShift =
2295 Value *RemSimplification =
2296 ConstantInt::get(
I.getType(), RemSimplificationC);
2297 return ShiftByX ? BinaryOperator::CreateShl(RemSimplification,
X)
2298 : BinaryOperator::CreateMul(
X, RemSimplification);
2304 bool BO1NoWrap = IsSRem ? BO1HasNSW : BO1HasNUW;
2308 if (RemYZ ==
Y && BO1NoWrap) {
2319 if (
Y.uge(Z) && (IsSRem ? (BO0HasNSW && BO1HasNSW) : BO0HasNUW)) {
2337 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
2339 if (isa<Constant>(Op1)) {
2340 if (
Instruction *Op0I = dyn_cast<Instruction>(Op0)) {
2341 if (
SelectInst *SI = dyn_cast<SelectInst>(Op0I)) {
2344 }
else if (
auto *PN = dyn_cast<PHINode>(Op0I)) {
2345 const APInt *Op1Int;
2347 (
I.getOpcode() == Instruction::URem ||
2384 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
2385 Type *Ty =
I.getType();
2391 return BinaryOperator::CreateAnd(Op0,
Add);
2417 Value *FrozenOp0 = Op0;
2430 Value *FrozenOp0 = Op0;
2453 Value *Op0 =
I.getOperand(0), *Op1 =
I.getOperand(1);
2472 return BinaryOperator::CreateURem(Op0, Op1,
I.getName());
2476 if (isa<ConstantVector>(Op1) || isa<ConstantDataVector>(Op1)) {
2478 unsigned VWidth = cast<FixedVectorType>(
C->getType())->getNumElements();
2480 bool hasNegative =
false;
2481 bool hasMissing =
false;
2482 for (
unsigned i = 0; i != VWidth; ++i) {
2483 Constant *Elt =
C->getAggregateElement(i);
2490 if (
RHS->isNegative())
2494 if (hasNegative && !hasMissing) {
2496 for (
unsigned i = 0; i != VWidth; ++i) {
2497 Elts[i] =
C->getAggregateElement(i);
2499 if (
RHS->isNegative())
2515 I.getFastMathFlags(),
This file implements a class to represent arbitrary precision integral constant values and operations...
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static const Function * getParent(const Value *V)
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< StatepointGC > D("statepoint-example", "an example strategy for statepoint")
This file contains the declarations for the subclasses of Constant, which represent the different fla...
static GCMetadataPrinterRegistry::Add< ErlangGCPrinter > X("erlang", "erlang-compatible garbage collector")
This file provides internal interfaces used to implement the InstCombine.
static Instruction * convertFSqrtDivIntoFMul(CallInst *CI, Instruction *X, const SmallPtrSetImpl< Instruction * > &R1, const SmallPtrSetImpl< Instruction * > &R2, InstCombiner::BuilderTy &B, InstCombinerImpl *IC)
static Instruction * simplifyIRemMulShl(BinaryOperator &I, InstCombinerImpl &IC)
static Instruction * narrowUDivURem(BinaryOperator &I, InstCombinerImpl &IC)
If we have zero-extended operands of an unsigned div or rem, we may be able to narrow the operation (...
static Value * simplifyValueKnownNonZero(Value *V, InstCombinerImpl &IC, Instruction &CxtI)
The specific integer value is used in a context where it is known to be non-zero.
static bool getFSqrtDivOptPattern(Instruction *Div, SmallPtrSetImpl< Instruction * > &R1, SmallPtrSetImpl< Instruction * > &R2)
static Value * foldMulSelectToNegate(BinaryOperator &I, InstCombiner::BuilderTy &Builder)
static bool isFSqrtDivToFMulLegal(Instruction *X, SmallPtrSetImpl< Instruction * > &R1, SmallPtrSetImpl< Instruction * > &R2)
static Instruction * foldFDivPowDivisor(BinaryOperator &I, InstCombiner::BuilderTy &Builder)
Negate the exponent of pow/exp to fold division-by-pow() into multiply.
static bool multiplyOverflows(const APInt &C1, const APInt &C2, APInt &Product, bool IsSigned)
True if the multiply can not be expressed in an int this size.
static Value * foldMulShl1(BinaryOperator &Mul, bool CommuteOperands, InstCombiner::BuilderTy &Builder)
Reduce integer multiplication patterns that contain a (+/-1 << Z) factor.
static bool isMultiple(const APInt &C1, const APInt &C2, APInt &Quotient, bool IsSigned)
True if C1 is a multiple of C2. Quotient contains C1/C2.
static Instruction * foldFDivSqrtDivisor(BinaryOperator &I, InstCombiner::BuilderTy &Builder)
Convert div to mul if we have an sqrt divisor iff sqrt's operand is a fdiv instruction.
static Instruction * foldFDivConstantDividend(BinaryOperator &I)
Remove negation and try to reassociate constant math.
static Value * foldIDivShl(BinaryOperator &I, InstCombiner::BuilderTy &Builder)
This file provides the interface for the instcombine pass implementation.
static bool hasNoSignedWrap(BinaryOperator &I)
static bool hasNoUnsignedWrap(BinaryOperator &I)
uint64_t IntrinsicInst * II
static GCMetadataPrinterRegistry::Add< OcamlGCMetadataPrinter > Y("ocaml", "ocaml 3.10-compatible collector")
const SmallVectorImpl< MachineOperand > & Cond
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
This file defines the SmallPtrSet class.
This file defines the SmallVector class.
Class for arbitrary precision integers.
APInt umul_ov(const APInt &RHS, bool &Overflow) const
APInt udiv(const APInt &RHS) const
Unsigned division operation.
static void udivrem(const APInt &LHS, const APInt &RHS, APInt &Quotient, APInt &Remainder)
Dual division/remainder interface.
static APInt getSignMask(unsigned BitWidth)
Get the SignMask for a specific bit width.
bool isMinSignedValue() const
Determine if this is the smallest signed value.
uint64_t getZExtValue() const
Get zero extended value.
static void sdivrem(const APInt &LHS, const APInt &RHS, APInt &Quotient, APInt &Remainder)
bool isAllOnes() const
Determine if all bits are set. This is true for zero-width values.
bool isZero() const
Determine if this value is zero, i.e. all bits are clear.
unsigned getBitWidth() const
Return the number of bits in the APInt.
bool ult(const APInt &RHS) const
Unsigned less than comparison.
bool isMinValue() const
Determine if this is the smallest unsigned value.
unsigned countr_zero() const
Count the number of trailing zero bits.
static APInt getSignedMinValue(unsigned numBits)
Gets minimum signed value of APInt for a specific bit width.
APInt ushl_ov(const APInt &Amt, bool &Overflow) const
unsigned getSignificantBits() const
Get the minimum bit size for this signed APInt.
APInt smul_ov(const APInt &RHS, bool &Overflow) const
bool ule(const APInt &RHS) const
Unsigned less or equal comparison.
static APInt getOneBitSet(unsigned numBits, unsigned BitNo)
Return an APInt with exactly one bit set in the result.
LLVM Basic Block Representation.
InstListType::iterator iterator
Instruction iterators...
static BinaryOperator * CreateFAddFMF(Value *V1, Value *V2, FastMathFlags FMF, const Twine &Name="")
static BinaryOperator * CreateNeg(Value *Op, const Twine &Name="", InsertPosition InsertBefore=nullptr)
Helper functions to construct and inspect unary operations (NEG and NOT) via binary operators SUB and...
BinaryOps getOpcode() const
static BinaryOperator * CreateExact(BinaryOps Opc, Value *V1, Value *V2, const Twine &Name="")
static BinaryOperator * Create(BinaryOps Op, Value *S1, Value *S2, const Twine &Name=Twine(), InsertPosition InsertBefore=nullptr)
Construct a binary instruction, given the opcode and the two operands.
static BinaryOperator * CreateFMulFMF(Value *V1, Value *V2, FastMathFlags FMF, const Twine &Name="")
static BinaryOperator * CreateFDivFMF(Value *V1, Value *V2, FastMathFlags FMF, const Twine &Name="")
static BinaryOperator * CreateFSubFMF(Value *V1, Value *V2, FastMathFlags FMF, const Twine &Name="")
static BinaryOperator * CreateWithCopiedFlags(BinaryOps Opc, Value *V1, Value *V2, Value *CopyO, const Twine &Name="", InsertPosition InsertBefore=nullptr)
static BinaryOperator * CreateNSWNeg(Value *Op, const Twine &Name="", InsertPosition InsertBefore=nullptr)
Value * getArgOperand(unsigned i) const
This class represents a function call, abstracting a target machine's calling convention.
static CastInst * CreateZExtOrBitCast(Value *S, Type *Ty, const Twine &Name="", InsertPosition InsertBefore=nullptr)
Create a ZExt or BitCast cast instruction.
static CastInst * Create(Instruction::CastOps, Value *S, Type *Ty, const Twine &Name="", InsertPosition InsertBefore=nullptr)
Provides a way to construct any of the CastInst subclasses using an opcode instead of the subclass's ...
static Type * makeCmpResultType(Type *opnd_type)
Create a result type for fcmp/icmp.
@ ICMP_ULT
unsigned less than
static Constant * getNeg(Constant *C, bool HasNSW=false)
static Constant * getTrunc(Constant *C, Type *Ty, bool OnlyIfReduced=false)
static Constant * getExactLogBase2(Constant *C)
If C is a scalar/fixed width vector of known powers of 2, then this function returns a new scalar/fix...
static Constant * getInfinity(Type *Ty, bool Negative=false)
This is the shared class of boolean and integer constants.
static ConstantInt * getTrue(LLVMContext &Context)
static ConstantInt * getFalse(LLVMContext &Context)
static ConstantInt * getBool(LLVMContext &Context, bool V)
static Constant * get(ArrayRef< Constant * > V)
This is an important base class in LLVM.
static Constant * getAllOnesValue(Type *Ty)
bool isNormalFP() const
Return true if this is a normal (as opposed to denormal, infinity, nan, or zero) floating-point scala...
static Constant * getNullValue(Type *Ty)
Constructor to create a '0' constant of arbitrary type.
Constant * getAggregateElement(unsigned Elt) const
For aggregates (struct/array/vector) return the constant that corresponds to the specified element if...
bool isNotMinSignedValue() const
Return true if the value is not the smallest signed value, or, for vectors, does not contain smallest...
bool isNullValue() const
Return true if this is the value that would be returned by getNullValue.
This class represents an Operation in the Expression.
A parsed version of the target data layout string in and methods for querying it.
Convenience struct for specifying and reasoning about fast-math flags.
static FastMathFlags intersectRewrite(FastMathFlags LHS, FastMathFlags RHS)
Intersect rewrite-based flags.
static FastMathFlags unionValue(FastMathFlags LHS, FastMathFlags RHS)
Union value flags.
bool allowReassoc() const
Flag queries.
Value * CreateICmpULT(Value *LHS, Value *RHS, const Twine &Name="")
Value * CreateSRem(Value *LHS, Value *RHS, const Twine &Name="")
Value * CreateSelectFMF(Value *C, Value *True, Value *False, FMFSource FMFSource, const Twine &Name="", Instruction *MDFrom=nullptr)
ConstantInt * getTrue()
Get the constant value for i1 true.
Value * CreateSelect(Value *C, Value *True, Value *False, const Twine &Name="", Instruction *MDFrom=nullptr)
Value * CreateFreeze(Value *V, const Twine &Name="")
Value * CreateLShr(Value *LHS, Value *RHS, const Twine &Name="", bool isExact=false)
Value * CreateIsNotNeg(Value *Arg, const Twine &Name="")
Return a boolean value testing if Arg > -1.
Value * CreateNSWMul(Value *LHS, Value *RHS, const Twine &Name="")
Value * CreateUDiv(Value *LHS, Value *RHS, const Twine &Name="", bool isExact=false)
Value * CreateICmpNE(Value *LHS, Value *RHS, const Twine &Name="")
Value * CreateNeg(Value *V, const Twine &Name="", bool HasNSW=false)
Value * CreateBinaryIntrinsic(Intrinsic::ID ID, Value *LHS, Value *RHS, FMFSource FMFSource={}, const Twine &Name="")
Create a call to intrinsic ID with 2 operands which is mangled on the first type.
CallInst * CreateIntrinsic(Intrinsic::ID ID, ArrayRef< Type * > Types, ArrayRef< Value * > Args, FMFSource FMFSource={}, const Twine &Name="")
Create a call to intrinsic ID with Args, mangled using Types.
Value * CreateICmpEQ(Value *LHS, Value *RHS, const Twine &Name="")
Value * CreateBinOpFMF(Instruction::BinaryOps Opc, Value *LHS, Value *RHS, FMFSource FMFSource, const Twine &Name="", MDNode *FPMathTag=nullptr)
Value * CreateIsNeg(Value *Arg, const Twine &Name="")
Return a boolean value testing if Arg < 0.
Value * CreateSub(Value *LHS, Value *RHS, const Twine &Name="", bool HasNUW=false, bool HasNSW=false)
CallInst * CreateUnaryIntrinsic(Intrinsic::ID ID, Value *V, FMFSource FMFSource={}, const Twine &Name="")
Create a call to intrinsic ID with 1 operand which is mangled on its type.
Value * CreateShl(Value *LHS, Value *RHS, const Twine &Name="", bool HasNUW=false, bool HasNSW=false)
Value * CreateZExt(Value *V, Type *DestTy, const Twine &Name="", bool IsNonNeg=false)
Value * CreateAnd(Value *LHS, Value *RHS, const Twine &Name="")
Value * CreateAdd(Value *LHS, Value *RHS, const Twine &Name="", bool HasNUW=false, bool HasNSW=false)
Value * CreateSDiv(Value *LHS, Value *RHS, const Twine &Name="", bool isExact=false)
Value * CreateTrunc(Value *V, Type *DestTy, const Twine &Name="", bool IsNUW=false, bool IsNSW=false)
Value * CreateBinOp(Instruction::BinaryOps Opc, Value *LHS, Value *RHS, const Twine &Name="", MDNode *FPMathTag=nullptr)
Value * CreateICmpUGE(Value *LHS, Value *RHS, const Twine &Name="")
Value * CreateFAddFMF(Value *L, Value *R, FMFSource FMFSource, const Twine &Name="", MDNode *FPMD=nullptr)
Value * CreateAShr(Value *LHS, Value *RHS, const Twine &Name="", bool isExact=false)
Value * CreateFNegFMF(Value *V, FMFSource FMFSource, const Twine &Name="", MDNode *FPMathTag=nullptr)
Value * CreateFDivFMF(Value *L, Value *R, FMFSource FMFSource, const Twine &Name="", MDNode *FPMD=nullptr)
Value * CreateFMulFMF(Value *L, Value *R, FMFSource FMFSource, const Twine &Name="", MDNode *FPMD=nullptr)
Value * CreateMul(Value *LHS, Value *RHS, const Twine &Name="", bool HasNUW=false, bool HasNSW=false)
Instruction * visitMul(BinaryOperator &I)
Instruction * FoldOpIntoSelect(Instruction &Op, SelectInst *SI, bool FoldWithMultiUse=false)
Given an instruction with a select as one operand and a constant as the other operand,...
Instruction * foldBinOpOfSelectAndCastOfSelectCondition(BinaryOperator &I)
Tries to simplify binops of select and cast of the select condition.
Instruction * foldBinOpIntoSelectOrPhi(BinaryOperator &I)
This is a convenience wrapper function for the above two functions.
Instruction * visitUDiv(BinaryOperator &I)
bool SimplifyAssociativeOrCommutative(BinaryOperator &I)
Performs a few simplifications for operators which are associative or commutative.
Value * foldUsingDistributiveLaws(BinaryOperator &I)
Tries to simplify binary operations which some other binary operation distributes over.
Instruction * visitURem(BinaryOperator &I)
Instruction * foldOpIntoPhi(Instruction &I, PHINode *PN, bool AllowMultipleUses=false)
Given a binary operator, cast instruction, or select which has a PHI node as operand #0,...
Value * takeLog2(Value *Op, unsigned Depth, bool AssumeNonZero, bool DoFold)
Take the exact integer log2 of the value.
Instruction * visitSRem(BinaryOperator &I)
Instruction * visitFDiv(BinaryOperator &I)
bool simplifyDivRemOfSelectWithZeroOp(BinaryOperator &I)
Fold a divide or remainder with a select instruction divisor when one of the select operands is zero.
Constant * getLosslessUnsignedTrunc(Constant *C, Type *TruncTy)
Instruction * eraseInstFromFunction(Instruction &I) override
Combiner aware instruction erasure.
Instruction * commonIDivRemTransforms(BinaryOperator &I)
Common integer divide/remainder transforms.
Value * tryGetLog2(Value *Op, bool AssumeNonZero)
Instruction * commonIDivTransforms(BinaryOperator &I)
This function implements the transforms common to both integer division instructions (udiv and sdiv).
Instruction * foldBinopWithPhiOperands(BinaryOperator &BO)
For a binary operator with 2 phi operands, try to hoist the binary operation before the phi.
Instruction * visitFRem(BinaryOperator &I)
bool SimplifyDemandedInstructionBits(Instruction &Inst)
Tries to simplify operands to an integer instruction based on its demanded bits.
Instruction * visitFMul(BinaryOperator &I)
Instruction * foldFMulReassoc(BinaryOperator &I)
Instruction * foldVectorBinop(BinaryOperator &Inst)
Canonicalize the position of binops relative to shufflevector.
Value * SimplifySelectsFeedingBinaryOp(BinaryOperator &I, Value *LHS, Value *RHS)
Instruction * foldPowiReassoc(BinaryOperator &I)
Instruction * visitSDiv(BinaryOperator &I)
Instruction * commonIRemTransforms(BinaryOperator &I)
This function implements the transforms common to both integer remainder instructions (urem and srem)...
bool isKnownToBeAPowerOfTwo(const Value *V, bool OrZero=false, unsigned Depth=0, const Instruction *CxtI=nullptr)
Instruction * replaceInstUsesWith(Instruction &I, Value *V)
A combiner-aware RAUW-like routine.
void replaceUse(Use &U, Value *NewValue)
Replace use and add the previously used value to the worklist.
InstructionWorklist & Worklist
A worklist of the instructions that need to be simplified.
Instruction * replaceOperand(Instruction &I, unsigned OpNum, Value *V)
Replace operand of instruction and add old operand to the worklist.
void computeKnownBits(const Value *V, KnownBits &Known, unsigned Depth, const Instruction *CxtI) const
bool MaskedValueIsZero(const Value *V, const APInt &Mask, unsigned Depth=0, const Instruction *CxtI=nullptr) const
void push(Instruction *I)
Push the instruction onto the worklist stack.
Instruction * clone() const
Create a copy of 'this' instruction that is identical in all ways except the following:
void setHasNoUnsignedWrap(bool b=true)
Set or clear the nuw flag on this instruction, which must be an operator which supports this flag.
bool hasNoNaNs() const LLVM_READONLY
Determine whether the no-NaNs flag is set.
bool hasNoUnsignedWrap() const LLVM_READONLY
Determine whether the no unsigned wrap flag is set.
bool hasNoInfs() const LLVM_READONLY
Determine whether the no-infs flag is set.
bool hasNoSignedZeros() const LLVM_READONLY
Determine whether the no-signed-zeros flag is set.
bool hasNoSignedWrap() const LLVM_READONLY
Determine whether the no signed wrap flag is set.
void setHasNoSignedWrap(bool b=true)
Set or clear the nsw flag on this instruction, which must be an operator which supports this flag.
bool isExact() const LLVM_READONLY
Determine whether the exact flag is set.
void setMetadata(unsigned KindID, MDNode *Node)
Set the metadata of the specified kind to the specified node.
FastMathFlags getFastMathFlags() const LLVM_READONLY
Convenience function for getting all the fast-math flags, which must be an operator which supports th...
void setIsExact(bool b=true)
Set or clear the exact flag on this instruction, which must be an operator which supports this flag.
bool hasAllowReassoc() const LLVM_READONLY
Determine whether the allow-reassociation flag is set.
A wrapper class for inspecting calls to intrinsic functions.
static MDNode * getMostGenericFPMath(MDNode *A, MDNode *B)
A Module instance is used to store all the information related to an LLVM module.
static Value * Negate(bool LHSIsZero, bool IsNSW, Value *Root, InstCombinerImpl &IC)
Attempt to negate Root.
Utility class for integer operators which may exhibit overflow - Add, Sub, Mul, and Shl.
bool hasNoSignedWrap() const
Test whether this operation is known to never undergo signed overflow, aka the nsw property.
bool hasNoUnsignedWrap() const
Test whether this operation is known to never undergo unsigned overflow, aka the nuw property.
static PoisonValue * get(Type *T)
Static factory methods - Return an 'poison' object of the specified type.
This class represents a sign extension of integer types.
This class represents the LLVM 'select' instruction.
static SelectInst * Create(Value *C, Value *S1, Value *S2, const Twine &NameStr="", InsertPosition InsertBefore=nullptr, Instruction *MDFrom=nullptr)
A templated base class for SmallPtrSet which provides the typesafe interface that is common across al...
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
The instances of the Type class are immutable: once they are created, they are never changed.
bool isIntOrIntVectorTy() const
Return true if this is an integer type or a vector of integer types.
unsigned getScalarSizeInBits() const LLVM_READONLY
If this is a vector type, return the getPrimitiveSizeInBits value for the element type.
static UnaryOperator * CreateFNegFMF(Value *Op, Instruction *FMFSource, const Twine &Name="", InsertPosition InsertBefore=nullptr)
A Use represents the edge between a Value definition and its users.
Value * getOperand(unsigned i) const
LLVM Value Representation.
Type * getType() const
All values are typed, get the type of this value.
bool hasOneUse() const
Return true if there is exactly one use of this value.
iterator_range< user_iterator > users()
bool hasNUses(unsigned N) const
Return true if this Value has exactly N uses.
StringRef getName() const
Return a constant reference to the value's name.
void takeName(Value *V)
Transfer the name from V to this value.
This class represents zero extension of integer types.
An efficient, type-erasing, non-owning reference to a callable.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
@ C
The default llvm calling convention, compatible with C.
cst_pred_ty< is_all_ones > m_AllOnes()
Match an integer or vector with all bits set.
BinaryOp_match< LHS, RHS, Instruction::And > m_And(const LHS &L, const RHS &R)
cst_pred_ty< is_negative > m_Negative()
Match an integer or vector of negative values.
BinaryOp_match< LHS, RHS, Instruction::Add > m_Add(const LHS &L, const RHS &R)
class_match< BinaryOperator > m_BinOp()
Match an arbitrary binary operation and ignore it.
BinaryOp_match< LHS, RHS, Instruction::FMul, true > m_c_FMul(const LHS &L, const RHS &R)
Matches FMul with LHS and RHS in either order.
cst_pred_ty< is_sign_mask > m_SignMask()
Match an integer or vector with only the sign bit(s) set.
BinaryOp_match< LHS, RHS, Instruction::AShr > m_AShr(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::FSub > m_FSub(const LHS &L, const RHS &R)
cst_pred_ty< is_power2 > m_Power2()
Match an integer or vector power-of-2.
BinaryOp_match< LHS, RHS, Instruction::URem > m_URem(const LHS &L, const RHS &R)
class_match< Constant > m_Constant()
Match an arbitrary Constant and ignore it.
AllowReassoc_match< T > m_AllowReassoc(const T &SubPattern)
CastInst_match< OpTy, TruncInst > m_Trunc(const OpTy &Op)
Matches Trunc.
specific_intval< false > m_SpecificInt(const APInt &V)
Match a specific integer value or vector with all elements equal to the value.
BinaryOp_match< LHS, RHS, Instruction::FMul > m_FMul(const LHS &L, const RHS &R)
bool match(Val *V, const Pattern &P)
cstfp_pred_ty< is_any_zero_fp > m_AnyZeroFP()
Match a floating-point negative zero or positive zero.
specificval_ty m_Specific(const Value *V)
Match if we have a specific specified value.
specific_intval< true > m_SpecificIntAllowPoison(const APInt &V)
OverflowingBinaryOp_match< cst_pred_ty< is_zero_int >, ValTy, Instruction::Sub, OverflowingBinaryOperator::NoSignedWrap > m_NSWNeg(const ValTy &V)
Matches a 'Neg' as 'sub nsw 0, V'.
cst_pred_ty< is_nonnegative > m_NonNegative()
Match an integer or vector of non-negative values.
cst_pred_ty< is_one > m_One()
Match an integer 1 or a vector with all elements equal to 1.
ThreeOps_match< Cond, LHS, RHS, Instruction::Select > m_Select(const Cond &C, const LHS &L, const RHS &R)
Matches SelectInst.
specific_fpval m_SpecificFP(double V)
Match a specific floating point value or vector with all elements equal to the value.
m_Intrinsic_Ty< Opnd0 >::Ty m_Sqrt(const Opnd0 &Op0)
BinaryOp_match< LHS, RHS, Instruction::FAdd > m_FAdd(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::Mul > m_Mul(const LHS &L, const RHS &R)
deferredval_ty< Value > m_Deferred(Value *const &V)
Like m_Specific(), but works if the specific value to match is determined as part of the same match()...
apint_match m_APIntAllowPoison(const APInt *&Res)
Match APInt while allowing poison in splat vector constants.
OneUse_match< T > m_OneUse(const T &SubPattern)
BinaryOp_match< cst_pred_ty< is_zero_int >, ValTy, Instruction::Sub > m_Neg(const ValTy &V)
Matches a 'Neg' as 'sub 0, V'.
match_combine_and< class_match< Constant >, match_unless< constantexpr_match > > m_ImmConstant()
Match an arbitrary immediate Constant and ignore it.
OverflowingBinaryOp_match< LHS, RHS, Instruction::Shl, OverflowingBinaryOperator::NoSignedWrap > m_NSWShl(const LHS &L, const RHS &R)
CastInst_match< OpTy, ZExtInst > m_ZExt(const OpTy &Op)
Matches ZExt.
OverflowingBinaryOp_match< LHS, RHS, Instruction::Shl, OverflowingBinaryOperator::NoUnsignedWrap > m_NUWShl(const LHS &L, const RHS &R)
OverflowingBinaryOp_match< LHS, RHS, Instruction::Mul, OverflowingBinaryOperator::NoUnsignedWrap > m_NUWMul(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::UDiv > m_UDiv(const LHS &L, const RHS &R)
cst_pred_ty< is_negated_power2 > m_NegatedPower2()
Match a integer or vector negated power-of-2.
cst_pred_ty< custom_checkfn< APInt > > m_CheckedInt(function_ref< bool(const APInt &)> CheckFn)
Match an integer or vector where CheckFn(ele) for each element is true.
specific_fpval m_FPOne()
Match a float 1.0 or vector with all elements equal to 1.0.
apfloat_match m_APFloatAllowPoison(const APFloat *&Res)
Match APFloat while allowing poison in splat vector constants.
match_combine_or< BinaryOp_match< LHS, RHS, Instruction::Add >, DisjointOr_match< LHS, RHS > > m_AddLike(const LHS &L, const RHS &R)
Match either "add" or "or disjoint".
CastInst_match< OpTy, UIToFPInst > m_UIToFP(const OpTy &Op)
BinaryOp_match< LHS, RHS, Instruction::SDiv > m_SDiv(const LHS &L, const RHS &R)
apint_match m_APInt(const APInt *&Res)
Match a ConstantInt or splatted ConstantVector, binding the specified pointer to the contained APInt.
match_combine_or< OverflowingBinaryOp_match< LHS, RHS, Instruction::Add, OverflowingBinaryOperator::NoSignedWrap >, DisjointOr_match< LHS, RHS > > m_NSWAddLike(const LHS &L, const RHS &R)
Match either "add nsw" or "or disjoint".
class_match< Value > m_Value()
Match an arbitrary value and ignore it.
AnyBinaryOp_match< LHS, RHS, true > m_c_BinOp(const LHS &L, const RHS &R)
Matches a BinaryOperator with LHS and RHS in either order.
BinaryOp_match< LHS, RHS, Instruction::LShr > m_LShr(const LHS &L, const RHS &R)
match_combine_or< CastInst_match< OpTy, ZExtInst >, CastInst_match< OpTy, SExtInst > > m_ZExtOrSExt(const OpTy &Op)
Exact_match< T > m_Exact(const T &SubPattern)
FNeg_match< OpTy > m_FNeg(const OpTy &X)
Match 'fneg X' as 'fsub -0.0, X'.
cstfp_pred_ty< is_pos_zero_fp > m_PosZeroFP()
Match a floating-point positive zero.
BinaryOp_match< LHS, RHS, Instruction::Shl > m_Shl(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::FDiv > m_FDiv(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::SRem > m_SRem(const LHS &L, const RHS &R)
BinaryOp_match< cst_pred_ty< is_all_ones >, ValTy, Instruction::Xor, true > m_Not(const ValTy &V)
Matches a 'Not' as 'xor V, -1' or 'xor -1, V'.
BinaryOp_match< LHS, RHS, Instruction::Or > m_Or(const LHS &L, const RHS &R)
CastInst_match< OpTy, SExtInst > m_SExt(const OpTy &Op)
Matches SExt.
is_zero m_Zero()
Match any null constant or a vector with all elements equal to 0.
match_combine_or< OverflowingBinaryOp_match< LHS, RHS, Instruction::Add, OverflowingBinaryOperator::NoUnsignedWrap >, DisjointOr_match< LHS, RHS > > m_NUWAddLike(const LHS &L, const RHS &R)
Match either "add nuw" or "or disjoint".
m_Intrinsic_Ty< Opnd0 >::Ty m_FAbs(const Opnd0 &Op0)
BinaryOp_match< LHS, RHS, Instruction::Mul, true > m_c_Mul(const LHS &L, const RHS &R)
Matches a Mul with LHS and RHS in either order.
OverflowingBinaryOp_match< LHS, RHS, Instruction::Mul, OverflowingBinaryOperator::NoSignedWrap > m_NSWMul(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::Sub > m_Sub(const LHS &L, const RHS &R)
This is an optimization pass for GlobalISel generic memory operations.
Value * emitUnaryFloatFnCall(Value *Op, const TargetLibraryInfo *TLI, StringRef Name, IRBuilderBase &B, const AttributeList &Attrs)
Emit a call to the unary function named 'Name' (e.g.
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly.
Value * simplifyFMulInst(Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q, fp::ExceptionBehavior ExBehavior=fp::ebIgnore, RoundingMode Rounding=RoundingMode::NearestTiesToEven)
Given operands for an FMul, fold the result or return null.
Value * simplifySDivInst(Value *LHS, Value *RHS, bool IsExact, const SimplifyQuery &Q)
Given operands for an SDiv, fold the result or return null.
Value * simplifyMulInst(Value *LHS, Value *RHS, bool IsNSW, bool IsNUW, const SimplifyQuery &Q)
Given operands for a Mul, fold the result or return null.
bool hasFloatFn(const Module *M, const TargetLibraryInfo *TLI, Type *Ty, LibFunc DoubleFn, LibFunc FloatFn, LibFunc LongDoubleFn)
Check whether the overloaded floating point function corresponding to Ty is available.
bool isGuaranteedNotToBeUndef(const Value *V, AssumptionCache *AC=nullptr, const Instruction *CtxI=nullptr, const DominatorTree *DT=nullptr, unsigned Depth=0)
Returns true if V cannot be undef, but may be poison.
bool matchSimpleRecurrence(const PHINode *P, BinaryOperator *&BO, Value *&Start, Value *&Step)
Attempt to match a simple first order recurrence cycle of the form: iv = phi Ty [Start,...
bool any_of(R &&range, UnaryPredicate P)
Provide wrappers to std::any_of which take ranges instead of having to pass begin/end explicitly.
constexpr unsigned MaxAnalysisRecursionDepth
Constant * ConstantFoldUnaryOpOperand(unsigned Opcode, Constant *Op, const DataLayout &DL)
Attempt to constant fold a unary operation with the specified operand.
Value * simplifyFRemInst(Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q, fp::ExceptionBehavior ExBehavior=fp::ebIgnore, RoundingMode Rounding=RoundingMode::NearestTiesToEven)
Given operands for an FRem, fold the result or return null.
Value * simplifyICmpInst(CmpPredicate Pred, Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for an ICmpInst, fold the result or return null.
Constant * ConstantFoldBinaryOpOperands(unsigned Opcode, Constant *LHS, Constant *RHS, const DataLayout &DL)
Attempt to constant fold a binary operation with the specified operands.
Value * simplifyFDivInst(Value *LHS, Value *RHS, FastMathFlags FMF, const SimplifyQuery &Q, fp::ExceptionBehavior ExBehavior=fp::ebIgnore, RoundingMode Rounding=RoundingMode::NearestTiesToEven)
Given operands for an FDiv, fold the result or return null.
@ Mul
Product of integers.
@ And
Bitwise or logical AND of integers.
Value * simplifyUDivInst(Value *LHS, Value *RHS, bool IsExact, const SimplifyQuery &Q)
Given operands for a UDiv, fold the result or return null.
DWARFExpression::Operation Op
constexpr unsigned BitWidth
bool isGuaranteedToTransferExecutionToSuccessor(const Instruction *I)
Return true if this function can prove that the instruction I will always transfer execution to one o...
Value * simplifySRemInst(Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for an SRem, fold the result or return null.
unsigned Log2(Align A)
Returns the log2 of the alignment.
bool isKnownNeverNaN(const Value *V, unsigned Depth, const SimplifyQuery &SQ)
Return true if the floating-point scalar value is not a NaN or if the floating-point vector value has...
bool isKnownNegation(const Value *X, const Value *Y, bool NeedNSW=false, bool AllowPoison=true)
Return true if the two given values are negation.
bool isKnownNonNegative(const Value *V, const SimplifyQuery &SQ, unsigned Depth=0)
Returns true if the give value is known to be non-negative.
Value * simplifyURemInst(Value *LHS, Value *RHS, const SimplifyQuery &Q)
Given operands for a URem, fold the result or return null.
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
bool isNonNegative() const
Returns true if this value is known to be non-negative.
unsigned countMinTrailingZeros() const
Returns the minimum number of trailing zero bits.
SimplifyQuery getWithInstruction(const Instruction *I) const