[llvm-commits] CVS: llvm/lib/Transforms/Scalar/PredicateSimplifier.cpp
Nick Lewycky
nicholas at mxc.ca
Wed Mar 21 19:03:11 PDT 2007
Changes in directory llvm/lib/Transforms/Scalar:
PredicateSimplifier.cpp updated: 1.60 -> 1.61
---
Log message:
Fix broken optimization disabled by a logic bug.
Analyze GEPs. If the indices are all zero, transfer whether the pointer is
known to be not null through the GEP.
Add a few more cases for xor and shift instructions.
---
Diffs of the changes: (+51 -10)
PredicateSimplifier.cpp | 61 ++++++++++++++++++++++++++++++++++++++++--------
1 files changed, 51 insertions(+), 10 deletions(-)
Index: llvm/lib/Transforms/Scalar/PredicateSimplifier.cpp
diff -u llvm/lib/Transforms/Scalar/PredicateSimplifier.cpp:1.60 llvm/lib/Transforms/Scalar/PredicateSimplifier.cpp:1.61
--- llvm/lib/Transforms/Scalar/PredicateSimplifier.cpp:1.60 Sun Mar 18 17:58:46 2007
+++ llvm/lib/Transforms/Scalar/PredicateSimplifier.cpp Wed Mar 21 21:02:51 2007
@@ -1516,13 +1516,27 @@
add(SI->getCondition(), ConstantInt::getFalse(),
ICmpInst::ICMP_EQ, NewContext);
}
+ } else if (GetElementPtrInst *GEPI = dyn_cast<GetElementPtrInst>(I)) {
+ for (GetElementPtrInst::op_iterator OI = GEPI->idx_begin(),
+ OE = GEPI->idx_end(); OI != OE; ++OI) {
+ ConstantInt *Op = dyn_cast<ConstantInt>(IG.canonicalize(*OI, Top));
+ if (!Op || !Op->isZero()) return;
+ }
+ // TODO: The GEPI indices are all zero. Copy from definition to operand,
+ // jumping the type plane as needed.
+ if (isRelatedBy(GEPI, Constant::getNullValue(GEPI->getType()),
+ ICmpInst::ICMP_NE)) {
+ Value *Ptr = GEPI->getPointerOperand();
+ add(Ptr, Constant::getNullValue(Ptr->getType()), ICmpInst::ICMP_NE,
+ NewContext);
+ }
}
// TODO: CastInst "%a = cast ... %b" where %a is EQ or NE a constant.
}
/// opsToDef - A new relationship was discovered involving one of this
/// instruction's operands. Find any new relationship involving the
- /// definition.
+ /// definition, or another operand.
void opsToDef(Instruction *I) {
Instruction *NewContext = below(I) ? I : TopInst;
@@ -1551,6 +1565,9 @@
switch (Opcode) {
default: break;
+ case Instruction::LShr:
+ case Instruction::AShr:
+ case Instruction::Shl:
case Instruction::Sub:
if (Op1 == Zero) {
add(BO, Op0, ICmpInst::ICMP_EQ, NewContext);
@@ -1562,6 +1579,7 @@
add(BO, AllOnes, ICmpInst::ICMP_EQ, NewContext);
return;
} // fall-through
+ case Instruction::Xor:
case Instruction::Add:
if (Op0 == Zero) {
add(BO, Op1, ICmpInst::ICMP_EQ, NewContext);
@@ -1589,25 +1607,32 @@
}
// "%x = add i32 %y, %z" and %x EQ %y then %z EQ 0
- // "%x = mul i32 %y, %z" and %x EQ %y then %z EQ 1
- // 1. Repeat all of the above, with order of operands reversed.
+ // "%x = add i32 %y, %z" and %x EQ %z then %y EQ 0
+ // "%x = shl i32 %y, %z" and %x EQ %y and %y NE 0 then %z EQ 0
// "%x = udiv i32 %y, %z" and %x EQ %y then %z EQ 1
- Value *Known = Op0, *Unknown = Op1;
- if (Known != BO) std::swap(Known, Unknown);
- if (Known == BO) {
+ Value *Known = Op0, *Unknown = Op1,
+ *TheBO = IG.canonicalize(BO, Top);
+ if (Known != TheBO) std::swap(Known, Unknown);
+ if (Known == TheBO) {
switch (Opcode) {
default: break;
+ case Instruction::LShr:
+ case Instruction::AShr:
+ case Instruction::Shl:
+ if (!isRelatedBy(Known, Zero, ICmpInst::ICMP_NE)) break;
+ // otherwise, fall-through.
+ case Instruction::Sub:
+ if (Unknown == Op1) break;
+ // otherwise, fall-through.
case Instruction::Xor:
case Instruction::Add:
- case Instruction::Sub:
add(Unknown, Zero, ICmpInst::ICMP_EQ, NewContext);
break;
case Instruction::UDiv:
case Instruction::SDiv:
- if (Unknown == Op0) break; // otherwise, fallthrough
- case Instruction::Mul:
- if (isa<ConstantInt>(Unknown)) {
+ if (Unknown == Op1) break;
+ if (isRelatedBy(Known, Zero, ICmpInst::ICMP_NE)) {
Constant *One = ConstantInt::get(Ty, 1);
add(Unknown, One, ICmpInst::ICMP_EQ, NewContext);
}
@@ -1633,6 +1658,8 @@
}
} else if (SelectInst *SI = dyn_cast<SelectInst>(I)) {
+ if (I->getType()->isFPOrFPVector()) return;
+
// Given: "%a = select i1 %x, i32 %b, i32 %c"
// %x EQ true then %a EQ %b
// %x EQ false then %a EQ %c
@@ -1658,6 +1685,20 @@
}
// TODO: "%a = cast ... %b" where %b is NE/LT/GT a constant.
+ } else if (GetElementPtrInst *GEPI = dyn_cast<GetElementPtrInst>(I)) {
+ for (GetElementPtrInst::op_iterator OI = GEPI->idx_begin(),
+ OE = GEPI->idx_end(); OI != OE; ++OI) {
+ ConstantInt *Op = dyn_cast<ConstantInt>(IG.canonicalize(*OI, Top));
+ if (!Op || !Op->isZero()) return;
+ }
+ // TODO: The GEPI indices are all zero. Copy from operand to definition,
+ // jumping the type plane as needed.
+ Value *Ptr = GEPI->getPointerOperand();
+ if (isRelatedBy(Ptr, Constant::getNullValue(Ptr->getType()),
+ ICmpInst::ICMP_NE)) {
+ add(GEPI, Constant::getNullValue(GEPI->getType()), ICmpInst::ICMP_NE,
+ NewContext);
+ }
}
}
More information about the llvm-commits
mailing list