summaryrefslogtreecommitdiffstats
path: root/polly/lib
diff options
context:
space:
mode:
authorJohannes Doerfert <doerfert@cs.uni-saarland.de>2016-05-19 12:34:57 +0000
committerJohannes Doerfert <doerfert@cs.uni-saarland.de>2016-05-19 12:34:57 +0000
commitffd222f2d671d5e15b10d17a19bab21f16891a5d (patch)
treeb2cc1050ce29afaab5a0f3a55a69b8be2fdd47dc /polly/lib
parent60dd9e134688da14357b515258c3194253c9a3eb (diff)
downloadbcm5719-llvm-ffd222f2d671d5e15b10d17a19bab21f16891a5d.tar.gz
bcm5719-llvm-ffd222f2d671d5e15b10d17a19bab21f16891a5d.zip
Propagate the DetectionContext to the SCoP [NFC]
The SCoP now holds a reference to the ScopDetection::DetectionContext which allows to simplify the type of various methods and remove code. llvm-svn: 270053
Diffstat (limited to 'polly/lib')
-rw-r--r--polly/lib/Analysis/ScopDetection.cpp28
-rw-r--r--polly/lib/Analysis/ScopInfo.cpp219
2 files changed, 92 insertions, 155 deletions
diff --git a/polly/lib/Analysis/ScopDetection.cpp b/polly/lib/Analysis/ScopDetection.cpp
index cf71b8905ed..bfc9a99ff86 100644
--- a/polly/lib/Analysis/ScopDetection.cpp
+++ b/polly/lib/Analysis/ScopDetection.cpp
@@ -1493,13 +1493,6 @@ bool ScopDetection::runOnFunction(llvm::Function &F) {
return false;
}
-bool ScopDetection::isNonAffineSubRegion(const Region *SubR,
- const Region *ScopR) const {
- const DetectionContext *DC = getDetectionContext(ScopR);
- assert(DC && "ScopR is no valid region!");
- return DC->NonAffineSubRegionSet.count(SubR);
-}
-
const ScopDetection::DetectionContext *
ScopDetection::getDetectionContext(const Region *R) const {
auto DCMIt = DetectionContextMap.find(getBBPairForRegion(R));
@@ -1508,27 +1501,6 @@ ScopDetection::getDetectionContext(const Region *R) const {
return &DCMIt->second;
}
-const ScopDetection::BoxedLoopsSetTy *
-ScopDetection::getBoxedLoops(const Region *R) const {
- const DetectionContext *DC = getDetectionContext(R);
- assert(DC && "ScopR is no valid region!");
- return &DC->BoxedLoopsSet;
-}
-
-const MapInsnToMemAcc *
-ScopDetection::getInsnToMemAccMap(const Region *R) const {
- const DetectionContext *DC = getDetectionContext(R);
- assert(DC && "ScopR is no valid region!");
- return &DC->InsnToMemAcc;
-}
-
-const InvariantLoadsSetTy *
-ScopDetection::getRequiredInvariantLoads(const Region *R) const {
- const DetectionContext *DC = getDetectionContext(R);
- assert(DC && "ScopR is no valid region!");
- return &DC->RequiredILS;
-}
-
const RejectLog *ScopDetection::lookupRejectionLog(const Region *R) const {
const DetectionContext *DC = getDetectionContext(R);
return DC ? &DC->Log : nullptr;
diff --git a/polly/lib/Analysis/ScopInfo.cpp b/polly/lib/Analysis/ScopInfo.cpp
index b12af38937c..6c2612ae135 100644
--- a/polly/lib/Analysis/ScopInfo.cpp
+++ b/polly/lib/Analysis/ScopInfo.cpp
@@ -1402,15 +1402,14 @@ void ScopStmt::buildDomain() {
Domain = isl_set_set_tuple_id(Domain, Id);
}
-void ScopStmt::deriveAssumptionsFromGEP(GetElementPtrInst *GEP,
- ScopDetection &SD) {
+void ScopStmt::deriveAssumptionsFromGEP(GetElementPtrInst *GEP, LoopInfo &LI) {
isl_ctx *Ctx = Parent.getIslCtx();
isl_local_space *LSpace = isl_local_space_from_space(getDomainSpace());
Type *Ty = GEP->getPointerOperandType();
ScalarEvolution &SE = *Parent.getSE();
// The set of loads that are required to be invariant.
- auto &ScopRIL = *SD.getRequiredInvariantLoads(&Parent.getRegion());
+ auto &ScopRIL = Parent.getRequiredInvariantLoads();
std::vector<const SCEV *> Subscripts;
std::vector<int> Sizes;
@@ -1430,7 +1429,7 @@ void ScopStmt::deriveAssumptionsFromGEP(GetElementPtrInst *GEP,
auto *Expr = Subscripts[i + IndexOffset];
auto Size = Sizes[i];
- auto *Scope = SD.getLI()->getLoopFor(getEntryBlock());
+ auto *Scope = LI.getLoopFor(getEntryBlock());
InvariantLoadsSetTy AccessILS;
if (!isAffineExpr(&Parent.getRegion(), Scope, Expr, SE, &AccessILS))
continue;
@@ -1468,7 +1467,7 @@ void ScopStmt::deriveAssumptionsFromGEP(GetElementPtrInst *GEP,
isl_set_free(NotExecuted);
}
-void ScopStmt::deriveAssumptions(ScopDetection &SD) {
+void ScopStmt::deriveAssumptions(LoopInfo &LI) {
for (auto *MA : *this) {
if (!MA->isArrayKind())
continue;
@@ -1477,7 +1476,7 @@ void ScopStmt::deriveAssumptions(ScopDetection &SD) {
auto *GEP = dyn_cast_or_null<GetElementPtrInst>(Acc.getPointerOperand());
if (GEP)
- deriveAssumptionsFromGEP(GEP, SD);
+ deriveAssumptionsFromGEP(GEP, LI);
}
}
@@ -1503,14 +1502,14 @@ ScopStmt::ScopStmt(Scop &parent, BasicBlock &bb)
BaseName = getIslCompatibleName("Stmt_", &bb, "");
}
-void ScopStmt::init(ScopDetection &SD) {
+void ScopStmt::init(LoopInfo &LI) {
assert(!Domain && "init must be called only once");
buildDomain();
collectSurroundingLoops();
buildAccessRelations();
- deriveAssumptions(SD);
+ deriveAssumptions(LI);
if (DetectReductions)
checkForReductions();
@@ -1996,10 +1995,10 @@ void Scop::addUserContext() {
isl_space_free(Space);
}
-void Scop::buildInvariantEquivalenceClasses(ScopDetection &SD) {
+void Scop::buildInvariantEquivalenceClasses() {
DenseMap<std::pair<const SCEV *, Type *>, LoadInst *> EquivClasses;
- const InvariantLoadsSetTy &RIL = *SD.getRequiredInvariantLoads(&getRegion());
+ const InvariantLoadsSetTy &RIL = getRequiredInvariantLoads();
for (LoadInst *LInst : RIL) {
const SCEV *PointerSCEV = SE->getSCEV(LInst->getPointerOperand());
@@ -2267,10 +2266,9 @@ __isl_give isl_set *Scop::getDomainConditions(BasicBlock *BB) const {
return getDomainConditions(BBR->getEntry());
}
-bool Scop::buildDomains(Region *R, ScopDetection &SD, DominatorTree &DT,
- LoopInfo &LI) {
+bool Scop::buildDomains(Region *R, DominatorTree &DT, LoopInfo &LI) {
- bool IsOnlyNonAffineRegion = SD.isNonAffineSubRegion(R, R);
+ bool IsOnlyNonAffineRegion = isNonAffineSubRegion(R);
auto *EntryBB = R->getEntry();
auto *L = IsOnlyNonAffineRegion ? nullptr : LI.getLoopFor(EntryBB);
int LD = getRelativeLoopDepth(L);
@@ -2290,10 +2288,10 @@ bool Scop::buildDomains(Region *R, ScopDetection &SD, DominatorTree &DT,
if (IsOnlyNonAffineRegion)
return !containsErrorBlock(R->getNode(), *R, LI, DT);
- if (!buildDomainsWithBranchConstraints(R, SD, DT, LI))
+ if (!buildDomainsWithBranchConstraints(R, DT, LI))
return false;
- if (!propagateDomainConstraints(R, SD, DT, LI))
+ if (!propagateDomainConstraints(R, DT, LI))
return false;
// Error blocks and blocks dominated by them have been assumed to never be
@@ -2308,15 +2306,14 @@ bool Scop::buildDomains(Region *R, ScopDetection &SD, DominatorTree &DT,
// with an empty set. Additionally, we will record for each block under which
// parameter combination it would be reached via an error block in its
// InvalidDomain. This information is needed during load hoisting.
- if (!propagateInvalidStmtDomains(R, SD, DT, LI))
+ if (!propagateInvalidStmtDomains(R, DT, LI))
return false;
return true;
}
-static Loop *
-getFirstNonBoxedLoopFor(BasicBlock *BB, LoopInfo &LI,
- const ScopDetection::BoxedLoopsSetTy &BoxedLoops) {
+static Loop *getFirstNonBoxedLoopFor(BasicBlock *BB, LoopInfo &LI,
+ const BoxedLoopsSetTy &BoxedLoops) {
auto *L = LI.getLoopFor(BB);
while (BoxedLoops.count(L))
L = L->getParentLoop();
@@ -2373,9 +2370,9 @@ static __isl_give isl_set *adjustDomainDimensions(Scop &S,
return Dom;
}
-bool Scop::propagateInvalidStmtDomains(Region *R, ScopDetection &SD,
- DominatorTree &DT, LoopInfo &LI) {
- auto &BoxedLoops = *SD.getBoxedLoops(&getRegion());
+bool Scop::propagateInvalidStmtDomains(Region *R, DominatorTree &DT,
+ LoopInfo &LI) {
+ auto &BoxedLoops = getBoxedLoops();
ReversePostOrderTraversal<Region *> RTraversal(R);
for (auto *RN : RTraversal) {
@@ -2384,8 +2381,8 @@ bool Scop::propagateInvalidStmtDomains(Region *R, ScopDetection &SD,
// subregions.
if (RN->isSubRegion()) {
Region *SubRegion = RN->getNodeAs<Region>();
- if (!SD.isNonAffineSubRegion(SubRegion, &getRegion())) {
- propagateInvalidStmtDomains(SubRegion, SD, DT, LI);
+ if (!isNonAffineSubRegion(SubRegion)) {
+ propagateInvalidStmtDomains(SubRegion, DT, LI);
continue;
}
}
@@ -2459,8 +2456,7 @@ bool Scop::propagateInvalidStmtDomains(Region *R, ScopDetection &SD,
void Scop::propagateDomainConstraintsToRegionExit(
BasicBlock *BB, Loop *BBLoop,
- SmallPtrSetImpl<BasicBlock *> &FinishedExitBlocks, ScopDetection &SD,
- LoopInfo &LI) {
+ SmallPtrSetImpl<BasicBlock *> &FinishedExitBlocks, LoopInfo &LI) {
// Check if the block @p BB is the entry of a region. If so we propagate it's
// domain to the exit block of the region. Otherwise we are done.
@@ -2470,7 +2466,7 @@ void Scop::propagateDomainConstraintsToRegionExit(
if (!BBReg || BBReg->getEntry() != BB || !R.contains(ExitBB))
return;
- auto &BoxedLoops = *SD.getBoxedLoops(&getRegion());
+ auto &BoxedLoops = getBoxedLoops();
// Do not propagate the domain if there is a loop backedge inside the region
// that would prevent the exit block from beeing executed.
auto *L = BBLoop;
@@ -2506,10 +2502,8 @@ void Scop::propagateDomainConstraintsToRegionExit(
FinishedExitBlocks.insert(ExitBB);
}
-bool Scop::buildDomainsWithBranchConstraints(Region *R, ScopDetection &SD,
- DominatorTree &DT, LoopInfo &LI) {
- auto &BoxedLoops = *SD.getBoxedLoops(&getRegion());
-
+bool Scop::buildDomainsWithBranchConstraints(Region *R, DominatorTree &DT,
+ LoopInfo &LI) {
// To create the domain for each block in R we iterate over all blocks and
// subregions in R and propagate the conditions under which the current region
// element is executed. To this end we iterate in reverse post order over R as
@@ -2529,8 +2523,8 @@ bool Scop::buildDomainsWithBranchConstraints(Region *R, ScopDetection &SD,
// subregions.
if (RN->isSubRegion()) {
Region *SubRegion = RN->getNodeAs<Region>();
- if (!SD.isNonAffineSubRegion(SubRegion, &getRegion())) {
- if (!buildDomainsWithBranchConstraints(SubRegion, SD, DT, LI))
+ if (!isNonAffineSubRegion(SubRegion)) {
+ if (!buildDomainsWithBranchConstraints(SubRegion, DT, LI))
return false;
continue;
}
@@ -2553,8 +2547,7 @@ bool Scop::buildDomainsWithBranchConstraints(Region *R, ScopDetection &SD,
auto *BBLoop = getRegionNodeLoop(RN, LI);
// Propagate the domain from BB directly to blocks that have a superset
// domain, at the moment only region exit nodes of regions that start in BB.
- propagateDomainConstraintsToRegionExit(BB, BBLoop, FinishedExitBlocks, SD,
- LI);
+ propagateDomainConstraintsToRegionExit(BB, BBLoop, FinishedExitBlocks, LI);
// If all successors of BB have been set a domain through the propagation
// above we do not need to build condition sets but can just skip this
@@ -2607,6 +2600,7 @@ bool Scop::buildDomainsWithBranchConstraints(Region *R, ScopDetection &SD,
continue;
}
+ auto &BoxedLoops = getBoxedLoops();
auto *SuccBBLoop = getFirstNonBoxedLoopFor(SuccBB, LI, BoxedLoops);
CondSet = adjustDomainDimensions(*this, CondSet, BBLoop, SuccBBLoop);
@@ -2640,7 +2634,6 @@ bool Scop::buildDomainsWithBranchConstraints(Region *R, ScopDetection &SD,
__isl_give isl_set *Scop::getPredecessorDomainConstraints(BasicBlock *BB,
isl_set *Domain,
- ScopDetection &SD,
DominatorTree &DT,
LoopInfo &LI) {
// If @p BB is the ScopEntry we are done
@@ -2648,7 +2641,7 @@ __isl_give isl_set *Scop::getPredecessorDomainConstraints(BasicBlock *BB,
return isl_set_universe(isl_set_get_space(Domain));
// The set of boxed loops (loops in non-affine subregions) for this SCoP.
- auto &BoxedLoops = *SD.getBoxedLoops(&getRegion());
+ auto &BoxedLoops = getBoxedLoops();
// The region info of this function.
auto &RI = *R.getRegionInfo();
@@ -2698,8 +2691,8 @@ __isl_give isl_set *Scop::getPredecessorDomainConstraints(BasicBlock *BB,
return PredDom;
}
-bool Scop::propagateDomainConstraints(Region *R, ScopDetection &SD,
- DominatorTree &DT, LoopInfo &LI) {
+bool Scop::propagateDomainConstraints(Region *R, DominatorTree &DT,
+ LoopInfo &LI) {
// Iterate over the region R and propagate the domain constrains from the
// predecessors to the current node. In contrast to the
// buildDomainsWithBranchConstraints function, this one will pull the domain
@@ -2716,8 +2709,8 @@ bool Scop::propagateDomainConstraints(Region *R, ScopDetection &SD,
// subregions.
if (RN->isSubRegion()) {
Region *SubRegion = RN->getNodeAs<Region>();
- if (!SD.isNonAffineSubRegion(SubRegion, &getRegion())) {
- if (!propagateDomainConstraints(SubRegion, SD, DT, LI))
+ if (!isNonAffineSubRegion(SubRegion)) {
+ if (!propagateDomainConstraints(SubRegion, DT, LI))
return false;
continue;
}
@@ -2728,7 +2721,7 @@ bool Scop::propagateDomainConstraints(Region *R, ScopDetection &SD,
assert(Domain);
// Under the union of all predecessor conditions we can reach this block.
- auto *PredDom = getPredecessorDomainConstraints(BB, Domain, SD, DT, LI);
+ auto *PredDom = getPredecessorDomainConstraints(BB, Domain, DT, LI);
Domain = isl_set_coalesce(isl_set_intersect(Domain, PredDom));
Domain = isl_set_align_params(Domain, getParamSpace());
@@ -3058,22 +3051,23 @@ static Loop *getLoopSurroundingRegion(Region &R, LoopInfo &LI) {
return L ? (R.contains(L) ? L->getParentLoop() : L) : nullptr;
}
-Scop::Scop(Region &R, ScalarEvolution &ScalarEvolution, LoopInfo &LI)
+Scop::Scop(Region &R, ScalarEvolution &ScalarEvolution, LoopInfo &LI,
+ const ScopDetection::DetectionContext &DC)
: SE(&ScalarEvolution), R(R), IsOptimized(false),
HasSingleExitEdge(R.getExitingBlock()), HasErrorBlock(false),
- MaxLoopDepth(0), IslCtx(isl_ctx_alloc(), isl_ctx_free), Context(nullptr),
- Affinator(this, LI), AssumedContext(nullptr), InvalidContext(nullptr),
- Schedule(nullptr) {
+ MaxLoopDepth(0), DC(DC), IslCtx(isl_ctx_alloc(), isl_ctx_free),
+ Context(nullptr), Affinator(this, LI), AssumedContext(nullptr),
+ InvalidContext(nullptr), Schedule(nullptr) {
if (IslOnErrorAbort)
isl_options_set_on_error(getIslCtx(), ISL_ON_ERROR_ABORT);
buildContext();
}
-void Scop::init(AliasAnalysis &AA, AssumptionCache &AC, ScopDetection &SD,
- DominatorTree &DT, LoopInfo &LI) {
- buildInvariantEquivalenceClasses(SD);
+void Scop::init(AliasAnalysis &AA, AssumptionCache &AC, DominatorTree &DT,
+ LoopInfo &LI) {
+ buildInvariantEquivalenceClasses();
- if (!buildDomains(&R, SD, DT, LI))
+ if (!buildDomains(&R, DT, LI))
return;
addUserAssumptions(AC, DT, LI);
@@ -3086,7 +3080,7 @@ void Scop::init(AliasAnalysis &AA, AssumptionCache &AC, ScopDetection &SD,
// The ScopStmts now have enough information to initialize themselves.
for (ScopStmt &Stmt : Stmts)
- Stmt.init(SD);
+ Stmt.init(LI);
// Check early for profitability. Afterwards it cannot change anymore,
// only the runtime context could become infeasible.
@@ -3095,7 +3089,7 @@ void Scop::init(AliasAnalysis &AA, AssumptionCache &AC, ScopDetection &SD,
return;
}
- buildSchedule(SD, LI);
+ buildSchedule(LI);
updateAccessDimensionality();
realignParams();
@@ -3109,8 +3103,8 @@ void Scop::init(AliasAnalysis &AA, AssumptionCache &AC, ScopDetection &SD,
simplifyContexts();
buildAliasChecks(AA);
- hoistInvariantLoads(SD);
- verifyInvariantLoads(SD);
+ hoistInvariantLoads();
+ verifyInvariantLoads();
simplifySCoP(true, DT, LI);
// Check late for a feasible runtime context because profitability did not
@@ -3450,8 +3444,8 @@ bool Scop::isHoistableAccess(MemoryAccess *Access,
return true;
}
-void Scop::verifyInvariantLoads(ScopDetection &SD) {
- auto &RIL = *SD.getRequiredInvariantLoads(&getRegion());
+void Scop::verifyInvariantLoads() {
+ auto &RIL = getRequiredInvariantLoads();
for (LoadInst *LI : RIL) {
assert(LI && getRegion().contains(LI));
ScopStmt *Stmt = getStmtFor(LI);
@@ -3462,7 +3456,7 @@ void Scop::verifyInvariantLoads(ScopDetection &SD) {
}
}
-void Scop::hoistInvariantLoads(ScopDetection &SD) {
+void Scop::hoistInvariantLoads() {
if (!PollyInvariantLoadHoisting)
return;
@@ -4041,10 +4035,10 @@ void Scop::addScopStmt(BasicBlock *BB, Region *R) {
}
}
-void Scop::buildSchedule(ScopDetection &SD, LoopInfo &LI) {
+void Scop::buildSchedule(LoopInfo &LI) {
Loop *L = getLoopSurroundingRegion(getRegion(), LI);
LoopStackTy LoopStack({LoopStackElementTy(L, nullptr, 0)});
- buildSchedule(getRegion().getNode(), LoopStack, SD, LI);
+ buildSchedule(getRegion().getNode(), LoopStack, LI);
assert(LoopStack.size() == 1 && LoopStack.back().L == L);
Schedule = LoopStack[0].Schedule;
}
@@ -4073,8 +4067,7 @@ void Scop::buildSchedule(ScopDetection &SD, LoopInfo &LI) {
/// sub-regions or blocks that are outside the last loop on the @p LoopStack.
/// These region-nodes are then queue and only traverse after the all nodes
/// within the current loop have been processed.
-void Scop::buildSchedule(Region *R, LoopStackTy &LoopStack, ScopDetection &SD,
- LoopInfo &LI) {
+void Scop::buildSchedule(Region *R, LoopStackTy &LoopStack, LoopInfo &LI) {
Loop *OuterScopLoop = getLoopSurroundingRegion(getRegion(), LI);
ReversePostOrderTraversal<Region *> RTraversal(R);
@@ -4114,19 +4107,18 @@ void Scop::buildSchedule(Region *R, LoopStackTy &LoopStack, ScopDetection &SD,
}
LoopStack.push_back({L, nullptr, 0});
}
- buildSchedule(RN, LoopStack, SD, LI);
+ buildSchedule(RN, LoopStack, LI);
}
return;
}
-void Scop::buildSchedule(RegionNode *RN, LoopStackTy &LoopStack,
- ScopDetection &SD, LoopInfo &LI) {
+void Scop::buildSchedule(RegionNode *RN, LoopStackTy &LoopStack, LoopInfo &LI) {
if (RN->isSubRegion()) {
auto *LocalRegion = RN->getNodeAs<Region>();
- if (!SD.isNonAffineSubRegion(LocalRegion, &getRegion())) {
- buildSchedule(LocalRegion, LoopStack, SD, LI);
+ if (!isNonAffineSubRegion(LocalRegion)) {
+ buildSchedule(LocalRegion, LoopStack, LI);
return;
}
}
@@ -4270,10 +4262,7 @@ void ScopInfo::buildEscapingDependences(Instruction *Inst) {
}
}
-bool ScopInfo::buildAccessMultiDimFixed(
- MemAccInst Inst, Loop *L, Region *R,
- const ScopDetection::BoxedLoopsSetTy *BoxedLoops,
- const InvariantLoadsSetTy &ScopRIL) {
+bool ScopInfo::buildAccessMultiDimFixed(MemAccInst Inst, Loop *L, Region *R) {
Value *Val = Inst.getValueOperand();
Type *ElementType = Val->getType();
Value *Address = Inst.getPointerOperand();
@@ -4317,6 +4306,7 @@ bool ScopInfo::buildAccessMultiDimFixed(
std::vector<const SCEV *> SizesSCEV;
+ const InvariantLoadsSetTy &ScopRIL = scop->getRequiredInvariantLoads();
for (auto *Subscript : Subscripts) {
InvariantLoadsSetTy AccessILS;
if (!isAffineExpr(R, L, Subscript, *SE, &AccessILS))
@@ -4339,10 +4329,7 @@ bool ScopInfo::buildAccessMultiDimFixed(
return true;
}
-bool ScopInfo::buildAccessMultiDimParam(
- MemAccInst Inst, Loop *L, Region *R,
- const ScopDetection::BoxedLoopsSetTy *BoxedLoops,
- const InvariantLoadsSetTy &ScopRIL, const MapInsnToMemAcc &InsnToMemAcc) {
+bool ScopInfo::buildAccessMultiDimParam(MemAccInst Inst, Loop *L, Region *R) {
if (!PollyDelinearize)
return false;
@@ -4360,6 +4347,7 @@ bool ScopInfo::buildAccessMultiDimParam(
assert(BasePointer && "Could not find base pointer");
AccessFunction = SE->getMinusSCEV(AccessFunction, BasePointer);
+ auto &InsnToMemAcc = scop->getInsnToMemAccMap();
auto AccItr = InsnToMemAcc.find(Inst);
if (AccItr == InsnToMemAcc.end())
return false;
@@ -4384,10 +4372,7 @@ bool ScopInfo::buildAccessMultiDimParam(
return true;
}
-bool ScopInfo::buildAccessMemIntrinsic(
- MemAccInst Inst, Loop *L, Region *R,
- const ScopDetection::BoxedLoopsSetTy *BoxedLoops,
- const InvariantLoadsSetTy &ScopRIL) {
+bool ScopInfo::buildAccessMemIntrinsic(MemAccInst Inst, Loop *L, Region *R) {
auto *MemIntr = dyn_cast_or_null<MemIntrinsic>(Inst);
if (MemIntr == nullptr)
@@ -4398,6 +4383,7 @@ bool ScopInfo::buildAccessMemIntrinsic(
// Check if the length val is actually affine or if we overapproximate it
InvariantLoadsSetTy AccessILS;
+ const InvariantLoadsSetTy &ScopRIL = scop->getRequiredInvariantLoads();
bool LengthIsAffine = isAffineExpr(R, L, LengthVal, *SE, &AccessILS);
for (LoadInst *LInst : AccessILS)
if (!ScopRIL.count(LInst))
@@ -4449,10 +4435,7 @@ bool ScopInfo::buildAccessMemIntrinsic(
return true;
}
-bool ScopInfo::buildAccessCallInst(
- MemAccInst Inst, Loop *L, Region *R,
- const ScopDetection::BoxedLoopsSetTy *BoxedLoops,
- const InvariantLoadsSetTy &ScopRIL) {
+bool ScopInfo::buildAccessCallInst(MemAccInst Inst, Loop *L, Region *R) {
auto *CI = dyn_cast_or_null<CallInst>(Inst);
if (CI == nullptr)
@@ -4495,10 +4478,7 @@ bool ScopInfo::buildAccessCallInst(
return true;
}
-void ScopInfo::buildAccessSingleDim(
- MemAccInst Inst, Loop *L, Region *R,
- const ScopDetection::BoxedLoopsSetTy *BoxedLoops,
- const InvariantLoadsSetTy &ScopRIL) {
+void ScopInfo::buildAccessSingleDim(MemAccInst Inst, Loop *L, Region *R) {
Value *Address = Inst.getPointerOperand();
Value *Val = Inst.getValueOperand();
Type *ElementType = Val->getType();
@@ -4514,18 +4494,18 @@ void ScopInfo::buildAccessSingleDim(
// Check if the access depends on a loop contained in a non-affine subregion.
bool isVariantInNonAffineLoop = false;
- if (BoxedLoops) {
- SetVector<const Loop *> Loops;
- findLoops(AccessFunction, Loops);
- for (const Loop *L : Loops)
- if (BoxedLoops->count(L))
- isVariantInNonAffineLoop = true;
- }
+ SetVector<const Loop *> Loops;
+ auto &BoxedLoops = scop->getBoxedLoops();
+ findLoops(AccessFunction, Loops);
+ for (const Loop *L : Loops)
+ if (BoxedLoops.count(L))
+ isVariantInNonAffineLoop = true;
InvariantLoadsSetTy AccessILS;
bool IsAffine = !isVariantInNonAffineLoop &&
isAffineExpr(R, L, AccessFunction, *SE, &AccessILS);
+ const InvariantLoadsSetTy &ScopRIL = scop->getRequiredInvariantLoads();
for (LoadInst *LInst : AccessILS)
if (!ScopRIL.count(LInst))
IsAffine = false;
@@ -4537,45 +4517,41 @@ void ScopInfo::buildAccessSingleDim(
{AccessFunction}, {}, Val);
}
-void ScopInfo::buildMemoryAccess(
- MemAccInst Inst, Loop *L, Region *R,
- const ScopDetection::BoxedLoopsSetTy *BoxedLoops,
- const InvariantLoadsSetTy &ScopRIL, const MapInsnToMemAcc &InsnToMemAcc) {
+void ScopInfo::buildMemoryAccess(MemAccInst Inst, Loop *L, Region *R) {
- if (buildAccessMemIntrinsic(Inst, L, R, BoxedLoops, ScopRIL))
+ if (buildAccessMemIntrinsic(Inst, L, R))
return;
- if (buildAccessCallInst(Inst, L, R, BoxedLoops, ScopRIL))
+ if (buildAccessCallInst(Inst, L, R))
return;
- if (buildAccessMultiDimFixed(Inst, L, R, BoxedLoops, ScopRIL))
+ if (buildAccessMultiDimFixed(Inst, L, R))
return;
- if (buildAccessMultiDimParam(Inst, L, R, BoxedLoops, ScopRIL, InsnToMemAcc))
+ if (buildAccessMultiDimParam(Inst, L, R))
return;
- buildAccessSingleDim(Inst, L, R, BoxedLoops, ScopRIL);
+ buildAccessSingleDim(Inst, L, R);
}
-void ScopInfo::buildAccessFunctions(Region &R, Region &SR,
- const MapInsnToMemAcc &InsnToMemAcc) {
+void ScopInfo::buildAccessFunctions(Region &R, Region &SR) {
- if (SD->isNonAffineSubRegion(&SR, &R)) {
+ if (scop->isNonAffineSubRegion(&SR)) {
for (BasicBlock *BB : SR.blocks())
- buildAccessFunctions(R, *BB, InsnToMemAcc, &SR);
+ buildAccessFunctions(R, *BB, &SR);
return;
}
for (auto I = SR.element_begin(), E = SR.element_end(); I != E; ++I)
if (I->isSubRegion())
- buildAccessFunctions(R, *I->getNodeAs<Region>(), InsnToMemAcc);
+ buildAccessFunctions(R, *I->getNodeAs<Region>());
else
- buildAccessFunctions(R, *I->getNodeAs<BasicBlock>(), InsnToMemAcc);
+ buildAccessFunctions(R, *I->getNodeAs<BasicBlock>());
}
void ScopInfo::buildStmts(Region &R, Region &SR) {
- if (SD->isNonAffineSubRegion(&SR, &R)) {
+ if (scop->isNonAffineSubRegion(&SR)) {
scop->addScopStmt(nullptr, &SR);
return;
}
@@ -4588,7 +4564,6 @@ void ScopInfo::buildStmts(Region &R, Region &SR) {
}
void ScopInfo::buildAccessFunctions(Region &R, BasicBlock &BB,
- const MapInsnToMemAcc &InsnToMemAcc,
Region *NonAffineSubRegion,
bool IsExitBlock) {
// We do not build access functions for error blocks, as they may contain
@@ -4598,12 +4573,6 @@ void ScopInfo::buildAccessFunctions(Region &R, BasicBlock &BB,
Loop *L = LI->getLoopFor(&BB);
- // The set of loops contained in non-affine subregions that are part of R.
- const ScopDetection::BoxedLoopsSetTy *BoxedLoops = SD->getBoxedLoops(&R);
-
- // The set of loads that are required to be invariant.
- auto &ScopRIL = *SD->getRequiredInvariantLoads(&R);
-
for (Instruction &Inst : BB) {
PHINode *PHI = dyn_cast<PHINode>(&Inst);
if (PHI)
@@ -4613,12 +4582,8 @@ void ScopInfo::buildAccessFunctions(Region &R, BasicBlock &BB,
if (!PHI && IsExitBlock)
break;
- // TODO: At this point we only know that elements of ScopRIL have to be
- // invariant and will be hoisted for the SCoP to be processed. Though,
- // there might be other invariant accesses that will be hoisted and
- // that would allow to make a non-affine access affine.
if (auto MemInst = MemAccInst::dyn_cast(Inst))
- buildMemoryAccess(MemInst, L, &R, BoxedLoops, ScopRIL, InsnToMemAcc);
+ buildMemoryAccess(MemInst, L, &R);
if (isIgnoredIntrinsic(&Inst))
continue;
@@ -4727,8 +4692,8 @@ void ScopInfo::ensureValueRead(Value *V, BasicBlock *UserBB) {
// Do not build scalar dependences for required invariant loads as we will
// hoist them later on anyway or drop the SCoP if we cannot.
- auto *ScopRIL = SD->getRequiredInvariantLoads(&ScopRegion);
- if (ScopRIL->count(dyn_cast<LoadInst>(V)))
+ auto &ScopRIL = scop->getRequiredInvariantLoads();
+ if (ScopRIL.count(dyn_cast<LoadInst>(V)))
return;
// Determine the ScopStmt containing the value's definition and use. There is
@@ -4810,10 +4775,10 @@ void ScopInfo::addPHIReadAccess(PHINode *PHI) {
}
void ScopInfo::buildScop(Region &R, AssumptionCache &AC) {
- scop.reset(new Scop(R, *SE, *LI));
+ scop.reset(new Scop(R, *SE, *LI, *SD->getDetectionContext(&R)));
buildStmts(R, R);
- buildAccessFunctions(R, R, *SD->getInsnToMemAccMap(&R));
+ buildAccessFunctions(R, R);
// In case the region does not have an exiting block we will later (during
// code generation) split the exit block. This will move potential PHI nodes
@@ -4823,7 +4788,7 @@ void ScopInfo::buildScop(Region &R, AssumptionCache &AC) {
// accesses. Note that we do not model anything in the exit block if we have
// an exiting block in the region, as there will not be any splitting later.
if (!R.getExitingBlock())
- buildAccessFunctions(R, *R.getExit(), *SD->getInsnToMemAccMap(&R), nullptr,
+ buildAccessFunctions(R, *R.getExit(), nullptr,
/* IsExitBlock */ true);
// Create memory accesses for global reads since all arrays are now known.
@@ -4833,7 +4798,7 @@ void ScopInfo::buildScop(Region &R, AssumptionCache &AC) {
addArrayAccess(MemAccInst(GlobalRead), MemoryAccess::READ, BP,
BP->getType(), false, {AF}, {}, GlobalRead);
- scop->init(*AA, AC, *SD, *DT, *LI);
+ scop->init(*AA, AC, *DT, *LI);
}
void ScopInfo::print(raw_ostream &OS, const Module *) const {
OpenPOWER on IntegriCloud