diff options
author | Chris Lattner <sabre@nondot.org> | 2006-02-24 18:05:58 +0000 |
---|---|---|
committer | Chris Lattner <sabre@nondot.org> | 2006-02-24 18:05:58 +0000 |
commit | 97f37a439c8025ac1a7a3cdbc4cc8a0aa2c65cf2 (patch) | |
tree | ec0b3c082d2a69e9a774056bc9cde609661f5777 | |
parent | 6990600f93c212bd73623d523eb8f53ae0b6eee5 (diff) |
Fix a problem that Nate noticed that boils down to an over conservative check
in the code that does "select C, (X+Y), (X-Y) --> (X+(select C, Y, (-Y)))".
We now compile this loop:
LBB1_1: ; no_exit
add r6, r2, r3
subf r3, r2, r3
cmpwi cr0, r2, 0
addi r7, r5, 4
lwz r2, 0(r5)
addi r4, r4, 1
blt cr0, LBB1_4 ; no_exit
LBB1_3: ; no_exit
mr r3, r6
LBB1_4: ; no_exit
cmpwi cr0, r4, 16
mr r5, r7
bne cr0, LBB1_1 ; no_exit
into this instead:
LBB1_1: ; no_exit
srawi r6, r2, 31
add r2, r2, r6
xor r6, r2, r6
addi r7, r5, 4
lwz r2, 0(r5)
addi r4, r4, 1
add r3, r3, r6
cmpwi cr0, r4, 16
mr r5, r7
bne cr0, LBB1_1 ; no_exit
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@26356 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | lib/Transforms/Scalar/InstructionCombining.cpp | 39 |
1 files changed, 17 insertions, 22 deletions
diff --git a/lib/Transforms/Scalar/InstructionCombining.cpp b/lib/Transforms/Scalar/InstructionCombining.cpp index 7b01531fb2..b98228c092 100644 --- a/lib/Transforms/Scalar/InstructionCombining.cpp +++ b/lib/Transforms/Scalar/InstructionCombining.cpp @@ -5074,30 +5074,25 @@ Instruction *InstCombiner::visitSelectInst(SelectInst &SI) { } if (OtherAddOp) { - // So at this point we know we have: - // select C, (add X, Y), (sub X, ?) - // We can do the transform profitably if either 'Y' = '?' or '?' is - // a constant. - if (SubOp->getOperand(1) == AddOp || - isa<Constant>(SubOp->getOperand(1))) { - Value *NegVal; - if (Constant *C = dyn_cast<Constant>(SubOp->getOperand(1))) { - NegVal = ConstantExpr::getNeg(C); - } else { - NegVal = InsertNewInstBefore( - BinaryOperator::createNeg(SubOp->getOperand(1)), SI); - } + // So at this point we know we have (Y -> OtherAddOp): + // select C, (add X, Y), (sub X, Z) + Value *NegVal; // Compute -Z + if (Constant *C = dyn_cast<Constant>(SubOp->getOperand(1))) { + NegVal = ConstantExpr::getNeg(C); + } else { + NegVal = InsertNewInstBefore( + BinaryOperator::createNeg(SubOp->getOperand(1), "tmp"), SI); + } - Value *NewTrueOp = OtherAddOp; - Value *NewFalseOp = NegVal; - if (AddOp != TI) - std::swap(NewTrueOp, NewFalseOp); - Instruction *NewSel = - new SelectInst(CondVal, NewTrueOp,NewFalseOp,SI.getName()+".p"); + Value *NewTrueOp = OtherAddOp; + Value *NewFalseOp = NegVal; + if (AddOp != TI) + std::swap(NewTrueOp, NewFalseOp); + Instruction *NewSel = + new SelectInst(CondVal, NewTrueOp,NewFalseOp,SI.getName()+".p"); - NewSel = InsertNewInstBefore(NewSel, SI); - return BinaryOperator::createAdd(SubOp->getOperand(0), NewSel); - } + NewSel = InsertNewInstBefore(NewSel, SI); + return BinaryOperator::createAdd(SubOp->getOperand(0), NewSel); } } } |