forked from OSchip/llvm-project
				
			[IslNodeBuilder] [NFC] Refactor creation of loop induction variables of loops outside scops.
This logic is duplicated, so we refactor it into a separate function. This will be used in a later patch to teach PPCGCodeGen code generation for loops that are outside the scop. Differential Revision: https://reviews.llvm.org/D36310 llvm-svn: 310192
This commit is contained in:
		
							parent
							
								
									9d8e9ff620
								
							
						
					
					
						commit
						0caed1fbe6
					
				| 
						 | 
				
			
			@ -412,6 +412,16 @@ private:
 | 
			
		|||
  ///                    ids to new access expressions.
 | 
			
		||||
  void generateCopyStmt(ScopStmt *Stmt,
 | 
			
		||||
                        __isl_keep isl_id_to_ast_expr *NewAccesses);
 | 
			
		||||
 | 
			
		||||
  /// Materialize a canonical loop induction variable for `L`, which is a loop
 | 
			
		||||
  /// that is *not* present in the Scop.
 | 
			
		||||
  ///
 | 
			
		||||
  /// Note that this is materialized at the point where the `Builder` is
 | 
			
		||||
  /// currently pointing.
 | 
			
		||||
  /// We also populate the `OutsideLoopIterations` map with `L`s SCEV to keep
 | 
			
		||||
  /// track of the induction variable.
 | 
			
		||||
  /// See [Code generation of induction variables of loops outside Scops]
 | 
			
		||||
  Value *materializeNonScopLoopInductionVariable(const Loop *L);
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#endif // POLLY_ISL_NODE_BUILDER_H
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -309,9 +309,17 @@ void IslNodeBuilder::getReferencesInSubtree(__isl_keep isl_ast_node *For,
 | 
			
		|||
 | 
			
		||||
  Values.remove_if([](const Value *V) { return isa<GlobalValue>(V); });
 | 
			
		||||
 | 
			
		||||
  /// Note: Code generation of induction variables of loops outside Scops
 | 
			
		||||
  ///
 | 
			
		||||
  /// Remove loops that contain the scop or that are part of the scop, as they
 | 
			
		||||
  /// are considered local. This leaves only loops that are before the scop, but
 | 
			
		||||
  /// do not contain the scop itself.
 | 
			
		||||
  /// We ignore loops perfectly contained in the Scop because these are already
 | 
			
		||||
  /// generated at `IslNodeBuilder::addParameters`. These `Loops` are loops
 | 
			
		||||
  /// whose induction variables are referred to by the Scop, but the Scop is not
 | 
			
		||||
  /// fully contained in these Loops. Since there can be many of these,
 | 
			
		||||
  /// we choose to codegen these on-demand.
 | 
			
		||||
  /// @see IslNodeBuilder::materializeNonScopLoopInductionVariable.
 | 
			
		||||
  Loops.remove_if([this](const Loop *L) {
 | 
			
		||||
    return S.contains(L) || L->contains(S.getEntry());
 | 
			
		||||
  });
 | 
			
		||||
| 
						 | 
				
			
			@ -627,13 +635,10 @@ void IslNodeBuilder::createForParallel(__isl_take isl_ast_node *For) {
 | 
			
		|||
  // Create for all loops we depend on values that contain the current loop
 | 
			
		||||
  // iteration. These values are necessary to generate code for SCEVs that
 | 
			
		||||
  // depend on such loops. As a result we need to pass them to the subfunction.
 | 
			
		||||
  // See [Code generation of induction variables of loops outside Scops]
 | 
			
		||||
  for (const Loop *L : Loops) {
 | 
			
		||||
    const SCEV *OuterLIV = SE.getAddRecExpr(SE.getUnknown(Builder.getInt64(0)),
 | 
			
		||||
                                            SE.getUnknown(Builder.getInt64(1)),
 | 
			
		||||
                                            L, SCEV::FlagAnyWrap);
 | 
			
		||||
    Value *V = generateSCEV(OuterLIV);
 | 
			
		||||
    OutsideLoopIterations[L] = SE.getUnknown(V);
 | 
			
		||||
    SubtreeValues.insert(V);
 | 
			
		||||
    Value *LoopInductionVar = materializeNonScopLoopInductionVariable(L);
 | 
			
		||||
    SubtreeValues.insert(LoopInductionVar);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  ValueMapT NewValues;
 | 
			
		||||
| 
						 | 
				
			
			@ -896,6 +901,17 @@ void IslNodeBuilder::generateCopyStmt(
 | 
			
		|||
  Builder.CreateStore(LoadValue, StoreAddr);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
Value *IslNodeBuilder::materializeNonScopLoopInductionVariable(const Loop *L) {
 | 
			
		||||
  assert(OutsideLoopIterations.find(L) == OutsideLoopIterations.end() &&
 | 
			
		||||
         "trying to materialize loop induction variable twice");
 | 
			
		||||
  const SCEV *OuterLIV = SE.getAddRecExpr(SE.getUnknown(Builder.getInt64(0)),
 | 
			
		||||
                                          SE.getUnknown(Builder.getInt64(1)), L,
 | 
			
		||||
                                          SCEV::FlagAnyWrap);
 | 
			
		||||
  Value *V = generateSCEV(OuterLIV);
 | 
			
		||||
  OutsideLoopIterations[L] = SE.getUnknown(V);
 | 
			
		||||
  return V;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void IslNodeBuilder::createUser(__isl_take isl_ast_node *User) {
 | 
			
		||||
  LoopToScevMapT LTS;
 | 
			
		||||
  isl_id *Id;
 | 
			
		||||
| 
						 | 
				
			
			@ -1484,11 +1500,7 @@ void IslNodeBuilder::addParameters(__isl_take isl_set *Context) {
 | 
			
		|||
    L = L->getParentLoop();
 | 
			
		||||
 | 
			
		||||
  while (L != nullptr) {
 | 
			
		||||
    const SCEV *OuterLIV = SE.getAddRecExpr(SE.getUnknown(Builder.getInt64(0)),
 | 
			
		||||
                                            SE.getUnknown(Builder.getInt64(1)),
 | 
			
		||||
                                            L, SCEV::FlagAnyWrap);
 | 
			
		||||
    Value *V = generateSCEV(OuterLIV);
 | 
			
		||||
    OutsideLoopIterations[L] = SE.getUnknown(V);
 | 
			
		||||
    materializeNonScopLoopInductionVariable(L);
 | 
			
		||||
    L = L->getParentLoop();
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in New Issue