It's easy to handle SLE/SGE when the loop has a unit stride.
authorNick Lewycky <nicholas@mxc.ca>
Tue, 9 Dec 2008 07:25:04 +0000 (07:25 +0000)
committerNick Lewycky <nicholas@mxc.ca>
Tue, 9 Dec 2008 07:25:04 +0000 (07:25 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@60748 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Analysis/ScalarEvolution.cpp
test/Analysis/ScalarEvolution/2008-12-08-FiniteSGE.ll [new file with mode: 0644]

index 2b714de3b3fac130bb8c2edb6d2c4fced74a79fa..c9af6de79d9e35d1e685ea6d4eeb7a7ac591af9b 100644 (file)
@@ -2924,8 +2924,12 @@ bool ScalarEvolutionsImpl::potentialInfiniteLoop(SCEV *Stride, SCEV *RHS,
   if (!R)
     return true;
 
-  if (isSigned)
+  if (isSigned) {
+    if (SC->getValue()->isOne())
+      return R->getValue()->isMaxValue(true);
+
     return true;  // XXX: because we don't have an sdiv scev.
+  }
 
   // If negative, it wraps around every iteration, but we don't care about that.
   APInt S = SC->getValue()->getValue().abs();
diff --git a/test/Analysis/ScalarEvolution/2008-12-08-FiniteSGE.ll b/test/Analysis/ScalarEvolution/2008-12-08-FiniteSGE.ll
new file mode 100644 (file)
index 0000000..a9a7c05
--- /dev/null
@@ -0,0 +1,24 @@
+; RUN: llvm-as < %s | opt -analyze -scalar-evolution | grep {255 iterations}
+
+define i32 @foo(i32 %x, i32 %y, i32* %lam, i32* %alp) nounwind {
+bb1.thread:
+       br label %bb1
+
+bb1:           ; preds = %bb1, %bb1.thread
+       %indvar = phi i32 [ 0, %bb1.thread ], [ %indvar.next, %bb1 ]            ; <i32> [#uses=4]
+       %i.0.reg2mem.0 = sub i32 255, %indvar           ; <i32> [#uses=2]
+       %0 = getelementptr i32* %alp, i32 %i.0.reg2mem.0                ; <i32*> [#uses=1]
+       %1 = load i32* %0, align 4              ; <i32> [#uses=1]
+       %2 = getelementptr i32* %lam, i32 %i.0.reg2mem.0                ; <i32*> [#uses=1]
+       store i32 %1, i32* %2, align 4
+       %3 = sub i32 254, %indvar               ; <i32> [#uses=1]
+       %4 = icmp slt i32 %3, 0         ; <i1> [#uses=1]
+       %indvar.next = add i32 %indvar, 1               ; <i32> [#uses=1]
+       br i1 %4, label %bb2, label %bb1
+
+bb2:           ; preds = %bb1
+       %tmp10 = mul i32 %indvar, %x            ; <i32> [#uses=1]
+       %z.0.reg2mem.0 = add i32 %tmp10, %y             ; <i32> [#uses=1]
+       %5 = add i32 %z.0.reg2mem.0, %x         ; <i32> [#uses=1]
+       ret i32 %5
+}