[polly] r269074 - Invalidate unprofitable SCoPs after creation

Johannes Doerfert via llvm-commits llvm-commits at lists.llvm.org
Tue May 10 09:38:10 PDT 2016


Author: jdoerfert
Date: Tue May 10 11:38:09 2016
New Revision: 269074

URL: http://llvm.org/viewvc/llvm-project?rev=269074&view=rev
Log:
Invalidate unprofitable SCoPs after creation

  If a profitable run is performed we will check if the SCoP seems to be
  profitable after creation but before e.g., dependence are computed. This is
  needed as SCoP detection only approximates the actual SCoP representation.
  In the end this should allow us to be less conservative during the SCoP
  detection while keeping the compile time in check.

Modified:
    polly/trunk/include/polly/ScopInfo.h
    polly/trunk/lib/Analysis/ScopInfo.cpp
    polly/trunk/test/ScopInfo/NonAffine/non_affine_loop_used_later.ll

Modified: polly/trunk/include/polly/ScopInfo.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/include/polly/ScopInfo.h?rev=269074&r1=269073&r2=269074&view=diff
==============================================================================
--- polly/trunk/include/polly/ScopInfo.h (original)
+++ polly/trunk/include/polly/ScopInfo.h Tue May 10 11:38:09 2016
@@ -76,6 +76,7 @@ enum AssumptionKind {
   INBOUNDS,
   WRAPPING,
   UNSIGNED,
+  PROFITABLE,
   ERRORBLOCK,
   COMPLEXITY,
   INFINITELOOP,
@@ -2089,6 +2090,9 @@ public:
   /// @brief Align the parameters in the statement to the scop context
   void realignParams();
 
+  /// @brief Return true if this SCoP can be profitably optimized.
+  bool isProfitable() const;
+
   /// @brief Return true if the SCoP contained at least one error block.
   bool hasErrorBlock() const { return HasErrorBlock; }
 

Modified: polly/trunk/lib/Analysis/ScopInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/Analysis/ScopInfo.cpp?rev=269074&r1=269073&r2=269074&view=diff
==============================================================================
--- polly/trunk/lib/Analysis/ScopInfo.cpp (original)
+++ polly/trunk/lib/Analysis/ScopInfo.cpp Tue May 10 11:38:09 2016
@@ -3118,10 +3118,14 @@ void Scop::init(AliasAnalysis &AA, Assum
   for (ScopStmt &Stmt : Stmts)
     Stmt.init(SD);
 
-  buildSchedule(SD, LI);
-
-  if (!hasFeasibleRuntimeContext())
+  // Check early for profitability. Afterwards it cannot change anymore,
+  // only the runtime context could become infeasible.
+  if (!isProfitable()) {
+    invalidate(PROFITABLE, DebugLoc());
     return;
+  }
+
+  buildSchedule(SD, LI);
 
   updateAccessDimensionality();
   realignParams();
@@ -3138,6 +3142,13 @@ void Scop::init(AliasAnalysis &AA, Assum
   hoistInvariantLoads(SD);
   verifyInvariantLoads(SD);
   simplifySCoP(true, DT, LI);
+
+  // Check late for a feasible runtime context because profitability did not
+  // change.
+  if (!hasFeasibleRuntimeContext()) {
+    invalidate(PROFITABLE, DebugLoc());
+    return;
+  }
 }
 
 Scop::~Scop() {
@@ -3571,6 +3582,37 @@ __isl_give isl_set *Scop::getAssumedCont
   return isl_set_copy(AssumedContext);
 }
 
+bool Scop::isProfitable() const {
+  if (PollyProcessUnprofitable)
+    return true;
+
+  if (!hasFeasibleRuntimeContext())
+    return false;
+
+  if (isEmpty())
+    return false;
+
+  unsigned OptimizableStmtsOrLoops = 0;
+  for (auto &Stmt : *this) {
+    if (Stmt.getNumIterators() == 0)
+      continue;
+
+    bool ContainsArrayAccs = false;
+    bool ContainsScalarAccs = false;
+    for (auto *MA : Stmt) {
+      if (MA->isRead())
+        continue;
+      ContainsArrayAccs |= MA->isArrayKind();
+      ContainsScalarAccs |= MA->isScalarKind();
+    }
+
+    if (ContainsArrayAccs && !ContainsScalarAccs)
+      OptimizableStmtsOrLoops += Stmt.getNumIterators();
+  }
+
+  return OptimizableStmtsOrLoops > 1;
+}
+
 bool Scop::hasFeasibleRuntimeContext() const {
   auto *PositiveContext = getAssumedContext();
   auto *NegativeContext = getInvalidContext();
@@ -3604,6 +3646,8 @@ static std::string toString(AssumptionKi
     return "Signed-unsigned";
   case COMPLEXITY:
     return "Low complexity";
+  case PROFITABLE:
+    return "Profitable";
   case ERRORBLOCK:
     return "No-error";
   case INFINITELOOP:
@@ -4873,7 +4917,7 @@ bool ScopInfo::runOnRegion(Region *R, RG
 
   DEBUG(scop->print(dbgs()));
 
-  if (scop->isEmpty() || !scop->hasFeasibleRuntimeContext()) {
+  if (!scop->hasFeasibleRuntimeContext()) {
     Msg = "SCoP ends here but was dismissed.";
     scop.reset();
   } else {

Modified: polly/trunk/test/ScopInfo/NonAffine/non_affine_loop_used_later.ll
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/test/ScopInfo/NonAffine/non_affine_loop_used_later.ll?rev=269074&r1=269073&r2=269074&view=diff
==============================================================================
--- polly/trunk/test/ScopInfo/NonAffine/non_affine_loop_used_later.ll (original)
+++ polly/trunk/test/ScopInfo/NonAffine/non_affine_loop_used_later.ll Tue May 10 11:38:09 2016
@@ -86,9 +86,9 @@
 ; CHECK-NEXT:             [N] -> { Stmt_bb23[i0] -> MemRef_j_0__phi[] };
 ; CHECK-NEXT: }
 ;
-; As we might be able to distribute the outer loop we consider the region profitable for now.
+; Due to the scalar accesses we are not able to distribute the outer loop, thus we do not consider the region profitable.
 ;
-; PROFIT: Statements
+; PROFIT-NOT: Statements
 ;
 ;    void f(int *A, int N, int M) {
 ;      int i = 0, j = 0;




More information about the llvm-commits mailing list