aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWojciech Matyjewicz <wmatyjewicz@fastmail.fm>2008-06-15 19:07:39 +0000
committerWojciech Matyjewicz <wmatyjewicz@fastmail.fm>2008-06-15 19:07:39 +0000
commit8a08769bad43a22fae2845bb0ba0fd1266cd55c8 (patch)
tree9abb039b6c4ffddfb82d5c4ad11145c2880bbbd7
parent93c534623c4691d255ea6c870347482ff8752313 (diff)
Fix PR2434. When scanning for exising binary operator to reuse don't
take into account the instrucion pointed by InsertPt. Thanks to it, returning the new value of InsertPt to the InsertBinop() caller can be avoided. The bug was, actually, in visitAddRecExpr() method which wasn't correctly handling changes of InsertPt. There shouldn't be any performance regression, as -gvn pass (run after -indvars) removes any redundant binops. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@52291 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--include/llvm/Analysis/ScalarEvolutionExpander.h2
-rw-r--r--lib/Analysis/ScalarEvolutionExpander.cpp30
-rw-r--r--test/Transforms/IndVarsSimplify/2008-06-15-SCEVExpanderBug.ll17
3 files changed, 33 insertions, 16 deletions
diff --git a/include/llvm/Analysis/ScalarEvolutionExpander.h b/include/llvm/Analysis/ScalarEvolutionExpander.h
index daff373348..9a69b24165 100644
--- a/include/llvm/Analysis/ScalarEvolutionExpander.h
+++ b/include/llvm/Analysis/ScalarEvolutionExpander.h
@@ -88,7 +88,7 @@ namespace llvm {
/// InsertBinop - Insert the specified binary operator, doing a small amount
/// of work to avoid inserting an obviously redundant operation.
static Value *InsertBinop(Instruction::BinaryOps Opcode, Value *LHS,
- Value *RHS, Instruction *&InsertPt);
+ Value *RHS, Instruction *InsertPt);
protected:
Value *expand(SCEV *S);
diff --git a/lib/Analysis/ScalarEvolutionExpander.cpp b/lib/Analysis/ScalarEvolutionExpander.cpp
index a241960b37..9872ced519 100644
--- a/lib/Analysis/ScalarEvolutionExpander.cpp
+++ b/lib/Analysis/ScalarEvolutionExpander.cpp
@@ -73,7 +73,7 @@ Value *SCEVExpander::InsertCastOfTo(Instruction::CastOps opcode, Value *V,
/// InsertBinop - Insert the specified binary operator, doing a small amount
/// of work to avoid inserting an obviously redundant operation.
Value *SCEVExpander::InsertBinop(Instruction::BinaryOps Opcode, Value *LHS,
- Value *RHS, Instruction *&InsertPt) {
+ Value *RHS, Instruction *InsertPt) {
// Fold a binop with constant operands.
if (Constant *CLHS = dyn_cast<Constant>(LHS))
if (Constant *CRHS = dyn_cast<Constant>(RHS))
@@ -81,21 +81,21 @@ Value *SCEVExpander::InsertBinop(Instruction::BinaryOps Opcode, Value *LHS,
// Do a quick scan to see if we have this binop nearby. If so, reuse it.
unsigned ScanLimit = 6;
- for (BasicBlock::iterator IP = InsertPt, E = InsertPt->getParent()->begin();
- ScanLimit; --IP, --ScanLimit) {
- if (BinaryOperator *BinOp = dyn_cast<BinaryOperator>(IP))
- if (BinOp->getOpcode() == Opcode && BinOp->getOperand(0) == LHS &&
- BinOp->getOperand(1) == RHS) {
- // If we found the instruction *at* the insert point, insert later
- // instructions after it.
- if (BinOp == InsertPt)
- InsertPt = ++IP;
- return BinOp;
- }
- if (IP == E) break;
+ BasicBlock::iterator BlockBegin = InsertPt->getParent()->begin();
+ if (InsertPt != BlockBegin) {
+ // Scanning starts from the last instruction before InsertPt.
+ BasicBlock::iterator IP = InsertPt;
+ --IP;
+ for (; ScanLimit; --IP, --ScanLimit) {
+ if (BinaryOperator *BinOp = dyn_cast<BinaryOperator>(IP))
+ if (BinOp->getOpcode() == Opcode && BinOp->getOperand(0) == LHS &&
+ BinOp->getOperand(1) == RHS)
+ return BinOp;
+ if (IP == BlockBegin) break;
+ }
}
-
- // If we don't have
+
+ // If we haven't found this binop, insert it.
return BinaryOperator::Create(Opcode, LHS, RHS, "tmp", InsertPt);
}
diff --git a/test/Transforms/IndVarsSimplify/2008-06-15-SCEVExpanderBug.ll b/test/Transforms/IndVarsSimplify/2008-06-15-SCEVExpanderBug.ll
new file mode 100644
index 0000000000..aac8d97894
--- /dev/null
+++ b/test/Transforms/IndVarsSimplify/2008-06-15-SCEVExpanderBug.ll
@@ -0,0 +1,17 @@
+; RUN: llvm-as < %s | opt -indvars -disable-output
+; PR2434
+
+define fastcc void @regcppop() nounwind {
+entry:
+ %tmp61 = add i32 0, -5 ; <i32> [#uses=1]
+ br label %bb
+
+bb: ; preds = %bb, %entry
+ %PL_savestack_ix.tmp.0 = phi i32 [ %tmp61, %entry ], [ %tmp127, %bb ] ; <i32> [#uses=2]
+ %indvar10 = phi i32 [ 0, %entry ], [ %indvar.next11, %bb ] ; <i32> [#uses=2]
+ %tmp13 = mul i32 %indvar10, -4 ; <i32> [#uses=0]
+ %tmp111 = add i32 %PL_savestack_ix.tmp.0, -3 ; <i32> [#uses=0]
+ %tmp127 = add i32 %PL_savestack_ix.tmp.0, -4 ; <i32> [#uses=1]
+ %indvar.next11 = add i32 %indvar10, 1 ; <i32> [#uses=1]
+ br label %bb
+}