[polly] r205971 - only delinearize when the access function is not affine

Sebastian Pop spop at codeaurora.org
Thu Apr 10 09:08:11 PDT 2014


Author: spop
Date: Thu Apr 10 11:08:11 2014
New Revision: 205971

URL: http://llvm.org/viewvc/llvm-project?rev=205971&view=rev
Log:
only delinearize when the access function is not affine

Modified:
    polly/trunk/lib/Analysis/ScopDetection.cpp
    polly/trunk/lib/Analysis/TempScopInfo.cpp
    polly/trunk/test/Isl/Ast/OpenMP/nested_loop_both_parallel_parametric.ll
    polly/trunk/test/ScopInfo/constant_start_integer.ll

Modified: polly/trunk/lib/Analysis/ScopDetection.cpp
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/Analysis/ScopDetection.cpp?rev=205971&r1=205970&r2=205971&view=diff
==============================================================================
--- polly/trunk/lib/Analysis/ScopDetection.cpp (original)
+++ polly/trunk/lib/Analysis/ScopDetection.cpp Thu Apr 10 11:08:11 2014
@@ -364,12 +364,19 @@ bool ScopDetection::isValidMemoryAccess(
     return invalid<ReportVariantBasePtr>(Context, /*Assert=*/false, BaseValue);
 
   AccessFunction = SE->getMinusSCEV(AccessFunction, BasePointer);
-  const SCEVAddRecExpr *AF = dyn_cast<SCEVAddRecExpr>(AccessFunction);
 
   if (AllowNonAffine) {
     // Do not check whether AccessFunction is affine.
-  } else if (PollyDelinearize && AF) {
-    // Try to delinearize AccessFunction.
+  } else if (!isAffineExpr(&Context.CurRegion, AccessFunction, *SE,
+                           BaseValue)) {
+    const SCEVAddRecExpr *AF = dyn_cast<SCEVAddRecExpr>(AccessFunction);
+    if (!PollyDelinearize || !AF)
+      return invalid<ReportNonAffineAccess>(Context, /*Assert=*/true,
+                                            AccessFunction);
+
+    // Try to delinearize AccessFunction only when the expression is known to
+    // not be affine: as all affine functions can be represented without
+    // problems in Polly, we do not have to delinearize them.
     SmallVector<const SCEV *, 4> Subscripts, Sizes;
     AF->delinearize(*SE, Subscripts, Sizes);
     int size = Subscripts.size();
@@ -378,10 +385,6 @@ bool ScopDetection::isValidMemoryAccess(
       if (!isAffineExpr(&Context.CurRegion, Subscripts[i], *SE, BaseValue))
         return invalid<ReportNonAffineAccess>(Context, /*Assert=*/true,
                                               AccessFunction);
-  } else if (!isAffineExpr(&Context.CurRegion, AccessFunction, *SE,
-                           BaseValue)) {
-    return invalid<ReportNonAffineAccess>(Context, /*Assert=*/true,
-                                          AccessFunction);
   }
 
   // FIXME: Alias Analysis thinks IntToPtrInst aliases with alloca instructions

Modified: polly/trunk/lib/Analysis/TempScopInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/Analysis/TempScopInfo.cpp?rev=205971&r1=205970&r2=205971&view=diff
==============================================================================
--- polly/trunk/lib/Analysis/TempScopInfo.cpp (original)
+++ polly/trunk/lib/Analysis/TempScopInfo.cpp Thu Apr 10 11:08:11 2014
@@ -167,30 +167,32 @@ IRAccess TempScopInfo::buildIRAccess(Ins
   AccessFunction = SE->getMinusSCEV(AccessFunction, BasePointer);
   SmallVector<const SCEV *, 4> Subscripts, Sizes;
 
-  bool IsAffine = true;
+  bool IsAffine = isAffineExpr(R, AccessFunction, *SE, BasePointer->getValue());
   const SCEVAddRecExpr *AF = dyn_cast<SCEVAddRecExpr>(AccessFunction);
 
-  if (PollyDelinearize && AF) {
+  if (!IsAffine && PollyDelinearize && AF) {
     const SCEV *Remainder = AF->delinearize(*SE, Subscripts, Sizes);
     int NSubs = Subscripts.size();
 
-    // Normalize the last dimension: integrate the size of the "scalar
-    // dimension" and the remainder of the delinearization.
-    Subscripts[NSubs - 1] =
-        SE->getMulExpr(Subscripts[NSubs - 1], Sizes[NSubs - 1]);
-    Subscripts[NSubs - 1] = SE->getAddExpr(Subscripts[NSubs - 1], Remainder);
-
-    for (int i = 0; i < NSubs; ++i)
-      if (!isAffineExpr(R, Subscripts[i], *SE, BasePointer->getValue())) {
-        IsAffine = false;
-        break;
-      }
+    if (NSubs > 0) {
+      // Normalize the last dimension: integrate the size of the "scalar
+      // dimension" and the remainder of the delinearization.
+      Subscripts[NSubs - 1] =
+          SE->getMulExpr(Subscripts[NSubs - 1], Sizes[NSubs - 1]);
+      Subscripts[NSubs - 1] = SE->getAddExpr(Subscripts[NSubs - 1], Remainder);
+
+      IsAffine = true;
+      for (int i = 0; i < NSubs; ++i)
+        if (!isAffineExpr(R, Subscripts[i], *SE, BasePointer->getValue())) {
+          IsAffine = false;
+          break;
+        }
+    }
   }
 
   if (Subscripts.size() == 0) {
     Subscripts.push_back(AccessFunction);
     Sizes.push_back(SE->getConstant(ZeroOffset->getType(), Size));
-    IsAffine = isAffineExpr(R, AccessFunction, *SE, BasePointer->getValue());
   }
 
   return IRAccess(Type, BasePointer->getValue(), AccessFunction, Size, IsAffine,

Modified: polly/trunk/test/Isl/Ast/OpenMP/nested_loop_both_parallel_parametric.ll
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/test/Isl/Ast/OpenMP/nested_loop_both_parallel_parametric.ll?rev=205971&r1=205970&r2=205971&view=diff
==============================================================================
--- polly/trunk/test/Isl/Ast/OpenMP/nested_loop_both_parallel_parametric.ll (original)
+++ polly/trunk/test/Isl/Ast/OpenMP/nested_loop_both_parallel_parametric.ll Thu Apr 10 11:08:11 2014
@@ -1,11 +1,12 @@
 ; RUN: opt %loadPolly -polly-ast -polly-ast-detect-parallel -analyze -polly-delinearize < %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-n8:16:32:64"
 target triple = "x86_64-pc-linux-gnu"
-
-; for (i = 0; i < n; i++)
-;   for (j = 0; j < n; j++)
-;     A[i][j] = 1;
-
+; int A[1024][1024];
+; void bar(int n) {
+;   for (i = 0; i < n; i++)
+;     for (j = 0; j < n; j++)
+;       A[i][j] = 1;
+; }
 @A = common global [1024 x [1024 x i32]] zeroinitializer
 define void @bar(i64 %n) {
 start:
@@ -40,17 +41,21 @@ ret:
   ret void
 }
 
-; At the first look both loops seem parallel, however due to the delinearization
-; we get the following dependences:
+; At the first look both loops seem parallel, however due to the linearization
+; of memory access functions, we get the following dependences:
 ;    [n] -> { loop_body[i0, i1] -> loop_body[1024 + i0, -1 + i1]:
 ;                                           0 <= i0 < n - 1024  and 1 <= i1 < n}
 ; They cause the outer loop to be non-parallel.  We can only prove their
 ; absence, if we know that n < 1024. This information is currently not available
 ; to polly. However, we should be able to obtain it due to the out of bounds
 ; memory accesses, that would happen if n >= 1024.
+
+; Note that we do not delinearize this access function because it is considered
+; to already be affine: {{0,+,4}<%loop.i>,+,4096}<%loop.j>.
+
 ;
-; CHECK: #pragma omp parallel for
 ; CHECK: for (int c1 = 0; c1 < n; c1 += 1)
 ; CHECK:   #pragma simd
+; CHECK:   #pragma omp parallel for
 ; CHECK:   for (int c3 = 0; c3 < n; c3 += 1)
 ; CHECK:     Stmt_loop_body(c1, c3);

Modified: polly/trunk/test/ScopInfo/constant_start_integer.ll
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/test/ScopInfo/constant_start_integer.ll?rev=205971&r1=205970&r2=205971&view=diff
==============================================================================
--- polly/trunk/test/ScopInfo/constant_start_integer.ll (original)
+++ polly/trunk/test/ScopInfo/constant_start_integer.ll Thu Apr 10 11:08:11 2014
@@ -16,9 +16,9 @@ target triple = "x86_64-unknown-linux-gn
 ; CHECK-NOT: p1
 
 ; CHECK: ReadAccess
-; CHECK:   [p_0] -> { Stmt_for_body3[i0] -> MemRef_input[p_0, 1 + i0] };
+; CHECK:   [p_0] -> { Stmt_for_body3[i0] -> MemRef_input[o0] : 4o0 = 4 + p_0 + 4i0 };
 ; CHECK: MustWriteAccess
-; CHECK:   [p_0] -> { Stmt_for_body3[i0] -> MemRef_input[p_0, i0] };
+; CHECK:   [p_0] -> { Stmt_for_body3[i0] -> MemRef_input[o0] : 4o0 = p_0 + 4i0 };
 
 define void @foo(float* nocapture %input) {
 entry:





More information about the llvm-commits mailing list