PR18060 - When we RAUW values with ExtractElement instructions in some cases

we generate PHI nodes with multiple entries from the same basic block but
with different values. Enabling CSE on ExtractElement instructions make sure
that all of the RAUWed instructions are the same.



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@195773 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Nadav Rotem 2013-11-26 17:29:19 +00:00
parent 15f7d261b5
commit bba8da2ba0
2 changed files with 55 additions and 0 deletions

View File

@ -1591,6 +1591,8 @@ Value *BoUpSLP::vectorizeTree() {
if (PHINode *PN = dyn_cast<PHINode>(Vec)) {
Builder.SetInsertPoint(PN->getParent()->getFirstInsertionPt());
Value *Ex = Builder.CreateExtractElement(Vec, Lane);
if (Instruction *Ins = dyn_cast<Instruction>(Ex))
GatherSeq.insert(Ins);
User->replaceUsesOfWith(Scalar, Ex);
} else if (isa<Instruction>(Vec)){
if (PHINode *PH = dyn_cast<PHINode>(User)) {
@ -1598,17 +1600,23 @@ Value *BoUpSLP::vectorizeTree() {
if (PH->getIncomingValue(i) == Scalar) {
Builder.SetInsertPoint(PH->getIncomingBlock(i)->getTerminator());
Value *Ex = Builder.CreateExtractElement(Vec, Lane);
if (Instruction *Ins = dyn_cast<Instruction>(Ex))
GatherSeq.insert(Ins);
PH->setOperand(i, Ex);
}
}
} else {
Builder.SetInsertPoint(cast<Instruction>(User));
Value *Ex = Builder.CreateExtractElement(Vec, Lane);
if (Instruction *Ins = dyn_cast<Instruction>(Ex))
GatherSeq.insert(Ins);
User->replaceUsesOfWith(Scalar, Ex);
}
} else {
Builder.SetInsertPoint(F->getEntryBlock().begin());
Value *Ex = Builder.CreateExtractElement(Vec, Lane);
if (Instruction *Ins = dyn_cast<Instruction>(Ex))
GatherSeq.insert(Ins);
User->replaceUsesOfWith(Scalar, Ex);
}

View File

@ -0,0 +1,47 @@
; RUN: opt < %s -basicaa -slp-vectorizer -dce -S -mtriple=x86_64-apple-macosx10.8.0 -mcpu=corei7
target datalayout = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-a0:0:64-f80:32:32-n8:16:32-S128"
target triple = "i386-pc-linux"
; Function Attrs: nounwind
define i32 @_Z16adjustFixupValueyj(i64 %Value, i32 %Kind) {
entry:
%extract.t = trunc i64 %Value to i32
%extract = lshr i64 %Value, 12
%extract.t6 = trunc i64 %extract to i32
switch i32 %Kind, label %sw.default [
i32 0, label %return
i32 1, label %return
i32 129, label %sw.bb1
i32 130, label %sw.bb2
]
sw.default: ; preds = %entry
call void @_Z25llvm_unreachable_internalv()
unreachable
sw.bb1: ; preds = %entry
%shr = lshr i64 %Value, 16
%extract.t5 = trunc i64 %shr to i32
%extract7 = lshr i64 %Value, 28
%extract.t8 = trunc i64 %extract7 to i32
br label %sw.bb2
sw.bb2: ; preds = %sw.bb1, %entry
%Value.addr.0.off0 = phi i32 [ %extract.t, %entry ], [ %extract.t5, %sw.bb1 ]
%Value.addr.0.off12 = phi i32 [ %extract.t6, %entry ], [ %extract.t8, %sw.bb1 ]
%conv6 = and i32 %Value.addr.0.off0, 4095
%conv4 = shl i32 %Value.addr.0.off12, 16
%shl = and i32 %conv4, 983040
%or = or i32 %shl, %conv6
%or11 = or i32 %or, 8388608
br label %return
return: ; preds = %sw.bb2, %entry, %entry
%retval.0 = phi i32 [ %or11, %sw.bb2 ], [ %extract.t, %entry ], [ %extract.t, %entry ]
ret i32 %retval.0
}
; Function Attrs: noreturn
declare void @_Z25llvm_unreachable_internalv()