Do not incorrectly set the inverted flag.
authorHongbin Zheng <etherzhhb@gmail.com>
Fri, 28 Nov 2014 03:26:06 +0000 (03:26 +0000)
committerHongbin Zheng <etherzhhb@gmail.com>
Fri, 28 Nov 2014 03:26:06 +0000 (03:26 +0000)
In TempScopInfo::buildCondition we extract the conditions to guard the
BB *in addition of* loop bounds. This means we should only consider the
conditions in the paths (in CFG) that do not contain cycles (loops).

At the same time, we set the invert flag if the FalseBB of the current
branch dominates our target BB to indicate that we reach the target BB
with an inverted condition from the current branch.

In this case, the path from the FalseBB contains a cycle if the FalseBB
is the target of a backedge. The conditions implied by such a path should
not be consider. We can identify such a case by checking if the TrueBB
also dominates our target BB, which means we can also reach our target
BB from the TrueBB, without going through the backedge.

llvm-svn: 222907

polly/lib/Analysis/TempScopInfo.cpp
polly/test/TempScop/nested-loops.ll [new file with mode: 0644]

index b7ab549..6f7a9d9 100644 (file)
@@ -282,8 +282,23 @@ void TempScopInfo::buildCondition(BasicBlock *BB, BasicBlock *RegionEntry) {
     if (Br->isUnconditional())
       continue;
 
+    BasicBlock *TrueBB = Br->getSuccessor(0), *FalseBB = Br->getSuccessor(1);
+
     // Is BB on the ELSE side of the branch?
-    bool inverted = DT->dominates(Br->getSuccessor(1), BB);
+    bool inverted = DT->dominates(FalseBB, BB);
+
+    // If both TrueBB and FalseBB dominate BB, one of them must be the target of
+    // a back-edge, i.e. a loop header.
+    if (inverted && DT->dominates(TrueBB, BB)) {
+      assert(
+          (DT->dominates(TrueBB, FalseBB) || DT->dominates(FalseBB, TrueBB)) &&
+          "One of the successors should be the loop header and dominate the"
+          "other!");
+
+      // It is not an invert if the FalseBB is the header.
+      if (DT->dominates(FalseBB, TrueBB))
+        inverted = false;
+    }
 
     Comparison *Cmp;
     buildAffineCondition(*(Br->getCondition()), inverted, &Cmp);
diff --git a/polly/test/TempScop/nested-loops.ll b/polly/test/TempScop/nested-loops.ll
new file mode 100644 (file)
index 0000000..318b5b8
--- /dev/null
@@ -0,0 +1,33 @@
+; RUN: opt %loadPolly -polly-scops -analyze < %s | FileCheck %s
+
+target datalayout = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-s0:64:64-f80:128:128"
+target triple = "x86_64-unknown-linux-gnu"
+
+define void @f(i64* nocapture %a) nounwind {
+entry:
+  br label %for.i
+
+for.i:
+  %i = phi i64 [ 0, %entry ], [ %i.inc, %for.j ]
+  %i.inc = add nsw i64 %i, 1
+  %exitcond.i = icmp sge i64 %i.inc, 2048
+  br i1 %exitcond.i, label %return, label %for.j
+
+for.j:
+  %j = phi i64 [ 0, %for.i ], [ %j.inc, %body ]
+  %j.inc = add nsw i64 %j, 1
+  %exitcond.j = icmp slt i64 %j.inc, 1024
+  br i1 %exitcond.j, label %body, label %for.i
+
+body:
+  %scevgep = getelementptr i64* %a, i64 %j
+  store i64 %j, i64* %scevgep
+  br label %for.j
+
+return:
+  ret void
+}
+
+; CHECK: body
+; CHECK:        Domain :=
+; CHECK:           { Stmt_body[i0, i1] : i0 >= 0 and i0 <= 2046 and i1 >= 0 and i1 <= 1022 }