[PATCH] D12950: [SCEV] Teach isLoopBackedgeGuardedByCond to exploit trip counts.

Sanjoy Das via llvm-commits llvm-commits at lists.llvm.org
Wed Sep 23 17:18:58 PDT 2015


sanjoy updated this revision to Diff 35577.
sanjoy added a comment.

- address hal's review.  Making the loop counter `<nw>` and `<nuw>` changed the output of an existing test case (`zext-wrap.ll`) -- an induction variable is now reported as `<nw>` when it wasn't before.  This inference is correct, so I didn't actually bother trying to verify further.


http://reviews.llvm.org/D12950

Files:
  lib/Analysis/ScalarEvolution.cpp
  test/Analysis/ScalarEvolution/zext-wrap.ll
  test/Transforms/IndVarSimplify/eliminate-comparison.ll

Index: test/Transforms/IndVarSimplify/eliminate-comparison.ll
===================================================================
--- test/Transforms/IndVarSimplify/eliminate-comparison.ll
+++ test/Transforms/IndVarSimplify/eliminate-comparison.ll
@@ -356,5 +356,42 @@
   ret void
 }
 
-!0 = !{i32 0, i32 2147483647}
+define i1 @func_18(i16* %tmp20, i32* %len.addr) {
+; CHECK-LABEL: @func_18(
+entry:
+  %len = load i32, i32* %len.addr, !range !0
+  %tmp18 = icmp eq i32 %len, 0
+  br i1 %tmp18, label %bb2, label %bb0.preheader
+
+bb0.preheader:
+  br label %bb0
+
+bb0:
+; CHECK: bb0:
+  %var_0.in = phi i32 [ %var_0, %bb1 ], [ %len, %bb0.preheader ]
+  %var_1 = phi i32 [ %tmp30, %bb1 ], [ 0, %bb0.preheader ]
+  %var_0 = add nsw i32 %var_0.in, -1
+  %tmp23 = icmp ult i32 %var_1, %len
+; CHECK: br i1 true, label %stay, label %bb2.loopexit
+  br i1 %tmp23, label %stay, label %bb2
+
+stay:
+; CHECK: stay:
+  %tmp25 = getelementptr inbounds i16, i16* %tmp20, i32 %var_1
+  %tmp26 = load i16, i16* %tmp25
+  %tmp29 = icmp eq i16 %tmp26, 0
+  br i1 %tmp29, label %bb1, label %bb2
+
+bb1:
+  %tmp30 = add i32 %var_1, 1
+  %tmp31 = icmp eq i32 %var_0, 0
+  br i1 %tmp31, label %bb3, label %bb0
+
+bb2:
+  ret i1 false
+
+bb3:
+  ret i1 true
+}
 
+!0 = !{i32 0, i32 2147483647}
Index: test/Analysis/ScalarEvolution/zext-wrap.ll
===================================================================
--- test/Analysis/ScalarEvolution/zext-wrap.ll
+++ test/Analysis/ScalarEvolution/zext-wrap.ll
@@ -10,7 +10,7 @@
 
 ; This cast shouldn't be folded into the addrec.
 ; CHECK: %tmp = zext i8 %l_95.0.i1 to i16
-; CHECK: -->  (zext i8 {0,+,-1}<%bb.i> to i16){{ U: [^ ]+ S: [^ ]+}}{{ *}}Exits: 2
+; CHECK: -->  (zext i8 {0,+,-1}<nw><%bb.i> to i16){{ U: [^ ]+ S: [^ ]+}}{{ *}}Exits: 2
 
         %tmp = zext i8 %l_95.0.i1 to i16
 
Index: lib/Analysis/ScalarEvolution.cpp
===================================================================
--- lib/Analysis/ScalarEvolution.cpp
+++ lib/Analysis/ScalarEvolution.cpp
@@ -6994,6 +6994,22 @@
 
   SaveAndRestore<bool> ClearOnExit(WalkingBEDominatingConds, true);
 
+  // See if we can exploit a trip count to prove the predicate.
+  const auto &BETakenInfo = getBackedgeTakenInfo(L);
+  const SCEV *LatchBECount = BETakenInfo.getExact(Latch, this);
+  if (LatchBECount != getCouldNotCompute()) {
+    // We know that Latch branches back to the loop header exactly
+    // LatchBECount times.  This means the backdege condition at Latch is
+    // equivalent to  "{0,+,1} u< LatchBECount".
+    Type *Ty = LatchBECount->getType();
+    auto NoWrapFlags = SCEV::NoWrapFlags(SCEV::FlagNUW | SCEV::FlagNW);
+    const SCEV *LoopCounter =
+      getAddRecExpr(getZero(Ty), getOne(Ty), L, NoWrapFlags);
+    if (isImpliedCond(Pred, LHS, RHS, ICmpInst::ICMP_ULT, LoopCounter,
+                      LatchBECount))
+      return true;
+  }
+
   // Check conditions due to any @llvm.assume intrinsics.
   for (auto &AssumeVH : AC.assumptions()) {
     if (!AssumeVH)


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D12950.35577.patch
Type: text/x-patch
Size: 2992 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20150924/cab550cd/attachment.bin>


More information about the llvm-commits mailing list