diff options
-rw-r--r-- | llvm/lib/Transforms/Scalar/IndVarSimplify.cpp | 16 | ||||
-rw-r--r-- | llvm/test/Transforms/IndVarSimplify/eliminate-comparison.ll | 3 | ||||
-rw-r--r-- | llvm/test/Transforms/IndVarSimplify/eliminate-trunc.ll | 4 |
3 files changed, 17 insertions, 6 deletions
diff --git a/llvm/lib/Transforms/Scalar/IndVarSimplify.cpp b/llvm/lib/Transforms/Scalar/IndVarSimplify.cpp index 69dd973c114..57f246373f0 100644 --- a/llvm/lib/Transforms/Scalar/IndVarSimplify.cpp +++ b/llvm/lib/Transforms/Scalar/IndVarSimplify.cpp @@ -2724,9 +2724,21 @@ bool IndVarSimplify::run(Loop *L) { if (isa<SCEVCouldNotCompute>(ExitCount)) continue; - // Better to fold to true (TODO: do so!) - if (ExitCount->isZero()) + // If we know we'd exit on the first iteration, rewrite the exit to + // reflect this. This does not imply the loop must exit through this + // exit; there may be an earlier one taken on the first iteration. + // TODO: Given we know the backedge can't be taken, we should go ahead + // and break it. Or at least, kill all the header phis and simplify. + if (ExitCount->isZero()) { + auto *BI = cast<BranchInst>(ExitingBB->getTerminator()); + bool ExitIfTrue = !L->contains(*succ_begin(ExitingBB)); + auto *NewCond = ExitIfTrue ? + ConstantInt::getTrue(BI->getCondition()->getType()) : + ConstantInt::getFalse(BI->getCondition()->getType()); + BI->setCondition(NewCond); + Changed = true; continue; + } PHINode *IndVar = FindLoopCounter(L, ExitingBB, ExitCount, SE, DT); if (!IndVar) diff --git a/llvm/test/Transforms/IndVarSimplify/eliminate-comparison.ll b/llvm/test/Transforms/IndVarSimplify/eliminate-comparison.ll index cd639f8d731..49088601125 100644 --- a/llvm/test/Transforms/IndVarSimplify/eliminate-comparison.ll +++ b/llvm/test/Transforms/IndVarSimplify/eliminate-comparison.ll @@ -284,7 +284,7 @@ define i32 @func_12() nounwind uwtable { ; CHECK-NEXT: [[SEXT21:%.*]] = shl i32 [[TMP57]], 16 ; CHECK-NEXT: [[TMP76:%.*]] = icmp ne i32 [[SEXT34]], [[SEXT21]] ; CHECK-NEXT: [[TMP81]] = add nuw nsw i32 [[__KEY8_0]], 1 -; CHECK-NEXT: br i1 [[TMP76]], label [[FORCOND38]], label [[ASSERT77:%.*]] +; CHECK-NEXT: br i1 false, label [[FORCOND38]], label [[ASSERT77:%.*]] ; CHECK: assert77: ; CHECK-NEXT: tail call void @llvm.trap() ; CHECK-NEXT: unreachable @@ -897,5 +897,4 @@ leave: ret void } - !0 = !{i32 0, i32 2147483647} diff --git a/llvm/test/Transforms/IndVarSimplify/eliminate-trunc.ll b/llvm/test/Transforms/IndVarSimplify/eliminate-trunc.ll index f152c236859..eaa20b5bf6d 100644 --- a/llvm/test/Transforms/IndVarSimplify/eliminate-trunc.ll +++ b/llvm/test/Transforms/IndVarSimplify/eliminate-trunc.ll @@ -174,7 +174,7 @@ define void @test_06(i32 %n) { ; CHECK-NEXT: [[IV_NEXT]] = add nuw nsw i64 [[IV]], 1 ; CHECK-NEXT: [[NARROW_IV:%.*]] = trunc i64 [[IV]] to i32 ; CHECK-NEXT: [[CMP:%.*]] = icmp slt i32 [[NARROW_IV]], [[N:%.*]] -; CHECK-NEXT: br i1 [[CMP]], label [[LOOP]], label [[EXIT:%.*]] +; CHECK-NEXT: br i1 false, label [[LOOP]], label [[EXIT:%.*]] ; CHECK: exit: ; CHECK-NEXT: ret void ; @@ -354,7 +354,7 @@ define void @test_06_unsigned(i32 %n) { ; CHECK-NEXT: [[IV_NEXT]] = add nsw i64 [[IV]], 1 ; CHECK-NEXT: [[NARROW_IV:%.*]] = trunc i64 [[IV]] to i32 ; CHECK-NEXT: [[CMP:%.*]] = icmp ult i32 [[NARROW_IV]], [[N:%.*]] -; CHECK-NEXT: br i1 [[CMP]], label [[LOOP]], label [[EXIT:%.*]] +; CHECK-NEXT: br i1 false, label [[LOOP]], label [[EXIT:%.*]] ; CHECK: exit: ; CHECK-NEXT: ret void ; |