LoopVectorize: Handle single edge PHIs

We might encouter single edge PHIs - handle them with an identity select.

Fixes PR15990.

llvm-svn: 182199
This commit is contained in:
Arnold Schwaighofer 2013-05-18 18:38:34 +00:00
parent 836a4f3643
commit 693a1ca628
2 changed files with 26 additions and 4 deletions

View File

@ -2105,7 +2105,6 @@ InnerLoopVectorizer::vectorizeBlockInLoop(LoopVectorizationLegality *Legal,
// optimizations will clean it up.
unsigned NumIncoming = P->getNumIncomingValues();
assert(NumIncoming > 1 && "Invalid PHI");
// Generate a sequence of selects of the form:
// SELECT(Mask3, In3,
@ -2117,10 +2116,11 @@ InnerLoopVectorizer::vectorizeBlockInLoop(LoopVectorizationLegality *Legal,
VectorParts &In0 = getVectorValue(P->getIncomingValue(In));
for (unsigned part = 0; part < UF; ++part) {
// We don't need to 'select' the first PHI operand because it is
// the default value if all of the other masks don't match.
// We might have single edge PHIs (blocks) - use an identity
// 'select' for the first PHI operand.
if (In == 0)
Entry[part] = In0[part];
Entry[part] = Builder.CreateSelect(Cond[part], In0[part],
In0[part]);
else
// Select between the current value and the previous incoming edge
// based on the incoming mask.

View File

@ -37,3 +37,25 @@ if.end21: ; preds = %lor.lhs.false
if.end25: ; preds = %entry
ret void
}
; PR15990
; We can have basic blocks with single entry PHI nodes.
define void @single_entry_phi(i32* %a, i32 *%b) {
entry:
br label %for.cond1.preheader
for.cond1.preheader:
%inc10 = phi i32 [ 0, %entry ], [ %inc, %for.end ]
br label %for.end
for.end:
%malicious.phi = phi i32 [ 0, %for.cond1.preheader ]
%inc = add nsw i32 %inc10, 1
%tobool = icmp eq i32 %inc, 0
br i1 %tobool, label %for.cond.for.end5, label %for.cond1.preheader
for.cond.for.end5:
%and.lcssa = phi i32 [ %malicious.phi, %for.end ]
store i32 %and.lcssa, i32* %a, align 4
ret void
}