[polly] r295431 - [ScopInfo] Add statistics to count loops after scop modeling
Tobias Grosser via llvm-commits
llvm-commits at lists.llvm.org
Fri Feb 17 00:12:37 PST 2017
Author: grosser
Date: Fri Feb 17 02:12:36 2017
New Revision: 295431
URL: http://llvm.org/viewvc/llvm-project?rev=295431&view=rev
Log:
[ScopInfo] Add statistics to count loops after scop modeling
Added:
polly/trunk/test/ScopInfo/statistics.ll
Modified:
polly/trunk/include/polly/ScopDetection.h
polly/trunk/lib/Analysis/ScopDetection.cpp
polly/trunk/lib/Analysis/ScopInfo.cpp
Modified: polly/trunk/include/polly/ScopDetection.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/include/polly/ScopDetection.h?rev=295431&r1=295430&r2=295431&view=diff
==============================================================================
--- polly/trunk/include/polly/ScopDetection.h (original)
+++ polly/trunk/include/polly/ScopDetection.h Fri Feb 17 02:12:36 2017
@@ -487,20 +487,9 @@ private:
/// a loop is assumed to be profitable and
/// consequently is counted.
/// returns A tuple of number of loops and their maximal depth.
- ScopDetection::LoopStats
+ static ScopDetection::LoopStats
countBeneficialSubLoops(Loop *L, ScalarEvolution &SE,
- unsigned MinProfitableTrips) const;
-
- /// Count the number of loops and the maximal loop depth in @p R.
- ///
- /// @param R The region to check
- /// @param SE The scalar evolution analysis.
- /// @param MinProfitableTrips The minimum number of trip counts from which
- /// a loop is assumed to be profitable and
- /// consequently is counted.
- /// returns A tuple of number of loops and their maximal depth.
- ScopDetection::LoopStats
- countBeneficialLoops(Region *R, unsigned MinProfitableTrips) const;
+ unsigned MinProfitableTrips);
/// Check if the function @p F is marked as invalid.
///
@@ -615,6 +604,18 @@ public:
virtual bool runOnFunction(Function &F);
virtual void print(raw_ostream &OS, const Module *) const;
//@}
+
+ /// Count the number of loops and the maximal loop depth in @p R.
+ ///
+ /// @param R The region to check
+ /// @param SE The scalar evolution analysis.
+ /// @param MinProfitableTrips The minimum number of trip counts from which
+ /// a loop is assumed to be profitable and
+ /// consequently is counted.
+ /// returns A tuple of number of loops and their maximal depth.
+ static ScopDetection::LoopStats
+ countBeneficialLoops(Region *R, ScalarEvolution &SE, LoopInfo &LI,
+ unsigned MinProfitableTrips);
};
} // end namespace polly
Modified: polly/trunk/lib/Analysis/ScopDetection.cpp
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/Analysis/ScopDetection.cpp?rev=295431&r1=295430&r2=295431&view=diff
==============================================================================
--- polly/trunk/lib/Analysis/ScopDetection.cpp (original)
+++ polly/trunk/lib/Analysis/ScopDetection.cpp Fri Feb 17 02:12:36 2017
@@ -1132,7 +1132,7 @@ bool ScopDetection::isValidLoop(Loop *L,
/// count that is not known to be less than @MinProfitableTrips.
ScopDetection::LoopStats
ScopDetection::countBeneficialSubLoops(Loop *L, ScalarEvolution &SE,
- unsigned MinProfitableTrips) const {
+ unsigned MinProfitableTrips) {
auto *TripCount = SE.getBackedgeTakenCount(L);
int NumLoops = 1;
@@ -1152,22 +1152,22 @@ ScopDetection::countBeneficialSubLoops(L
}
ScopDetection::LoopStats
-ScopDetection::countBeneficialLoops(Region *R,
- unsigned MinProfitableTrips) const {
+ScopDetection::countBeneficialLoops(Region *R, ScalarEvolution &SE,
+ LoopInfo &LI, unsigned MinProfitableTrips) {
int LoopNum = 0;
int MaxLoopDepth = 0;
- auto L = LI->getLoopFor(R->getEntry());
+ auto L = LI.getLoopFor(R->getEntry());
L = L ? R->outermostLoopInRegion(L) : nullptr;
L = L ? L->getParentLoop() : nullptr;
auto SubLoops =
- L ? L->getSubLoopsVector() : std::vector<Loop *>(LI->begin(), LI->end());
+ L ? L->getSubLoopsVector() : std::vector<Loop *>(LI.begin(), LI.end());
for (auto &SubLoop : SubLoops)
if (R->contains(SubLoop)) {
LoopStats Stats =
- countBeneficialSubLoops(SubLoop, *SE, MinProfitableTrips);
+ countBeneficialSubLoops(SubLoop, SE, MinProfitableTrips);
LoopNum += Stats.NumLoops;
MaxLoopDepth = std::max(MaxLoopDepth, Stats.MaxDepth);
}
@@ -1388,7 +1388,8 @@ bool ScopDetection::isProfitableRegion(D
if (!Context.hasStores || !Context.hasLoads)
return invalid<ReportUnprofitable>(Context, /*Assert=*/true, &CurRegion);
- int NumLoops = countBeneficialLoops(&CurRegion, MIN_LOOP_TRIP_COUNT).NumLoops;
+ int NumLoops =
+ countBeneficialLoops(&CurRegion, *SE, *LI, MIN_LOOP_TRIP_COUNT).NumLoops;
int NumAffineLoops = NumLoops - Context.BoxedLoopsSet.size();
// Scops with at least two loops may allow either loop fusion or tiling and
@@ -1616,7 +1617,7 @@ bool ScopDetection::runOnFunction(llvm::
continue;
if (!ValidRegions.count(&DC.CurRegion))
continue;
- LoopStats Stats = countBeneficialLoops(&DC.CurRegion, 0);
+ LoopStats Stats = countBeneficialLoops(&DC.CurRegion, *SE, *LI, 0);
updateLoopCountStatistic(Stats, false /* OnlyProfitable */);
if (isProfitableRegion(DC)) {
updateLoopCountStatistic(Stats, true /* OnlyProfitable */);
@@ -1627,7 +1628,7 @@ bool ScopDetection::runOnFunction(llvm::
}
NumProfScopRegions += ValidRegions.size();
- NumLoopsOverall += countBeneficialLoops(TopRegion, 0).NumLoops;
+ NumLoopsOverall += countBeneficialLoops(TopRegion, *SE, *LI, 0).NumLoops;
// Only makes sense when we tracked errors.
if (PollyTrackFailures)
Modified: polly/trunk/lib/Analysis/ScopInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/Analysis/ScopInfo.cpp?rev=295431&r1=295430&r2=295431&view=diff
==============================================================================
--- polly/trunk/lib/Analysis/ScopInfo.cpp (original)
+++ polly/trunk/lib/Analysis/ScopInfo.cpp Fri Feb 17 02:12:36 2017
@@ -74,6 +74,16 @@ STATISTIC(AssumptionsInvariantLoad,
STATISTIC(AssumptionsDelinearization,
"Number of delinearization assumptions taken.");
+STATISTIC(NumLoopsInScop, "Number of loops in scops");
+STATISTIC(NumScopsDepthOne, "Number of scops with maximal loop depth 1");
+STATISTIC(NumScopsDepthTwo, "Number of scops with maximal loop depth 2");
+STATISTIC(NumScopsDepthThree, "Number of scops with maximal loop depth 3");
+STATISTIC(NumScopsDepthFour, "Number of scops with maximal loop depth 4");
+STATISTIC(NumScopsDepthFive, "Number of scops with maximal loop depth 5");
+STATISTIC(NumScopsDepthLarger,
+ "Number of scops with maximal loop depth 6 and larger");
+STATISTIC(MaxNumLoopsInScop, "Maximal number of loops in scops");
+
// The maximal number of basic sets we allow during domain construction to
// be created. More complex scops will result in very high compile time and
// are also unlikely to result in good code
@@ -4539,6 +4549,26 @@ void ScopInfoRegionPass::getAnalysisUsag
AU.setPreservesAll();
}
+void updateLoopCountStatistic(ScopDetection::LoopStats Stats) {
+ NumLoopsInScop += Stats.NumLoops;
+ MaxNumLoopsInScop =
+ std::max(MaxNumLoopsInScop.getValue(), (unsigned)Stats.NumLoops);
+
+ errs() << "MaxLoopDepth: " << Stats.MaxDepth << "\n";
+ if (Stats.MaxDepth == 1)
+ NumScopsDepthOne++;
+ else if (Stats.MaxDepth == 2)
+ NumScopsDepthTwo++;
+ else if (Stats.MaxDepth == 3)
+ NumScopsDepthThree++;
+ else if (Stats.MaxDepth == 4)
+ NumScopsDepthFour++;
+ else if (Stats.MaxDepth == 5)
+ NumScopsDepthFive++;
+ else
+ NumScopsDepthLarger++;
+}
+
bool ScopInfoRegionPass::runOnRegion(Region *R, RGPassManager &RGM) {
auto &SD = getAnalysis<ScopDetection>();
@@ -4554,6 +4584,13 @@ bool ScopInfoRegionPass::runOnRegion(Reg
ScopBuilder SB(R, AA, DL, DT, LI, SD, SE);
S = SB.getScop(); // take ownership of scop object
+
+ if (S) {
+ ScopDetection::LoopStats Stats =
+ ScopDetection::countBeneficialLoops(&S->getRegion(), SE, LI, 0);
+ updateLoopCountStatistic(Stats);
+ }
+
return false;
}
Added: polly/trunk/test/ScopInfo/statistics.ll
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/test/ScopInfo/statistics.ll?rev=295431&view=auto
==============================================================================
--- polly/trunk/test/ScopInfo/statistics.ll (added)
+++ polly/trunk/test/ScopInfo/statistics.ll Fri Feb 17 02:12:36 2017
@@ -0,0 +1,241 @@
+; RUN: opt %loadPolly -polly-scops -stats -analyze < %s 2>&1 | FileCheck %s
+; REQUIRES: asserts
+
+; CHECK-DAG: 4 polly-scops - Maximal number of loops in scops
+; CHECK-DAG: 10 polly-scops - Number of loops in scops
+; CHECK-DAG: 1 polly-scops - Number of scops with maximal loop depth 4
+; CHECK-DAG: 1 polly-scops - Number of scops with maximal loop depth 1
+; CHECK-DAG: 1 polly-scops - Number of scops with maximal loop depth 3
+; CHECK-DAG: 1 polly-scops - Number of scops with maximal loop depth 2
+; CHECK-DAG: 4 polly-scops - Number of Scops containing a loop
+; CHECK-DAG: 4 polly-scops - Number of valid Scops
+;
+; void foo_1d(float *A) {
+; for (long i = 0; i < 1024; i++)
+; A[i] += i;
+; }
+;
+; void foo_2d(float *A) {
+; for (long i = 0; i < 1024; i++)
+; for (long j = 0; j < 1024; j++)
+; A[i + j] += i + j;
+; }
+;
+; void foo_3d(float *A) {
+; for (long i = 0; i < 1024; i++)
+; for (long j = 0; j < 1024; j++)
+; for (long k = 0; k < 1024; k++)
+; A[i + j + k] += i + j + k;
+; }
+;
+; void foo_4d(float *A) {
+; for (long i = 0; i < 1024; i++)
+; for (long j = 0; j < 1024; j++)
+; for (long k = 0; k < 1024; k++)
+; for (long l = 0; l < 1024; l++)
+; A[i + j + k + l] += i + j + k + l;
+; }
+;
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
+
+define void @foo_1d(float* %A) {
+bb:
+ br label %bb1
+
+bb1: ; preds = %bb6, %bb
+ %i.0 = phi i64 [ 0, %bb ], [ %tmp7, %bb6 ]
+ %exitcond = icmp ne i64 %i.0, 1024
+ br i1 %exitcond, label %bb2, label %bb8
+
+bb2: ; preds = %bb1
+ %tmp = sitofp i64 %i.0 to float
+ %tmp3 = getelementptr inbounds float, float* %A, i64 %i.0
+ %tmp4 = load float, float* %tmp3, align 4
+ %tmp5 = fadd float %tmp4, %tmp
+ store float %tmp5, float* %tmp3, align 4
+ br label %bb6
+
+bb6: ; preds = %bb2
+ %tmp7 = add nuw nsw i64 %i.0, 1
+ br label %bb1
+
+bb8: ; preds = %bb1
+ ret void
+}
+
+define void @foo_2d(float* %A) {
+bb:
+ br label %bb2
+
+bb2: ; preds = %bb14, %bb
+ %i.0 = phi i64 [ 0, %bb ], [ %tmp15, %bb14 ]
+ %exitcond1 = icmp ne i64 %i.0, 1024
+ br i1 %exitcond1, label %bb3, label %bb16
+
+bb3: ; preds = %bb2
+ br label %bb4
+
+bb4: ; preds = %bb11, %bb3
+ %j.0 = phi i64 [ 0, %bb3 ], [ %tmp12, %bb11 ]
+ %exitcond = icmp ne i64 %j.0, 1024
+ br i1 %exitcond, label %bb5, label %bb13
+
+bb5: ; preds = %bb4
+ %tmp = add nuw nsw i64 %i.0, %j.0
+ %tmp6 = sitofp i64 %tmp to float
+ %tmp7 = add nuw nsw i64 %i.0, %j.0
+ %tmp8 = getelementptr inbounds float, float* %A, i64 %tmp7
+ %tmp9 = load float, float* %tmp8, align 4
+ %tmp10 = fadd float %tmp9, %tmp6
+ store float %tmp10, float* %tmp8, align 4
+ br label %bb11
+
+bb11: ; preds = %bb5
+ %tmp12 = add nuw nsw i64 %j.0, 1
+ br label %bb4
+
+bb13: ; preds = %bb4
+ br label %bb14
+
+bb14: ; preds = %bb13
+ %tmp15 = add nuw nsw i64 %i.0, 1
+ br label %bb2
+
+bb16: ; preds = %bb2
+ ret void
+}
+
+define void @foo_3d(float* %A) {
+bb:
+ br label %bb3
+
+bb3: ; preds = %bb22, %bb
+ %i.0 = phi i64 [ 0, %bb ], [ %tmp23, %bb22 ]
+ %exitcond2 = icmp ne i64 %i.0, 1024
+ br i1 %exitcond2, label %bb4, label %bb24
+
+bb4: ; preds = %bb3
+ br label %bb5
+
+bb5: ; preds = %bb19, %bb4
+ %j.0 = phi i64 [ 0, %bb4 ], [ %tmp20, %bb19 ]
+ %exitcond1 = icmp ne i64 %j.0, 1024
+ br i1 %exitcond1, label %bb6, label %bb21
+
+bb6: ; preds = %bb5
+ br label %bb7
+
+bb7: ; preds = %bb16, %bb6
+ %k.0 = phi i64 [ 0, %bb6 ], [ %tmp17, %bb16 ]
+ %exitcond = icmp ne i64 %k.0, 1024
+ br i1 %exitcond, label %bb8, label %bb18
+
+bb8: ; preds = %bb7
+ %tmp = add nuw nsw i64 %i.0, %j.0
+ %tmp9 = add nuw nsw i64 %tmp, %k.0
+ %tmp10 = sitofp i64 %tmp9 to float
+ %tmp11 = add nuw nsw i64 %i.0, %j.0
+ %tmp12 = add nuw nsw i64 %tmp11, %k.0
+ %tmp13 = getelementptr inbounds float, float* %A, i64 %tmp12
+ %tmp14 = load float, float* %tmp13, align 4
+ %tmp15 = fadd float %tmp14, %tmp10
+ store float %tmp15, float* %tmp13, align 4
+ br label %bb16
+
+bb16: ; preds = %bb8
+ %tmp17 = add nuw nsw i64 %k.0, 1
+ br label %bb7
+
+bb18: ; preds = %bb7
+ br label %bb19
+
+bb19: ; preds = %bb18
+ %tmp20 = add nuw nsw i64 %j.0, 1
+ br label %bb5
+
+bb21: ; preds = %bb5
+ br label %bb22
+
+bb22: ; preds = %bb21
+ %tmp23 = add nuw nsw i64 %i.0, 1
+ br label %bb3
+
+bb24: ; preds = %bb3
+ ret void
+}
+
+define void @foo_4d(float* %A) {
+bb:
+ br label %bb4
+
+bb4: ; preds = %bb30, %bb
+ %i.0 = phi i64 [ 0, %bb ], [ %tmp31, %bb30 ]
+ %exitcond3 = icmp ne i64 %i.0, 1024
+ br i1 %exitcond3, label %bb5, label %bb32
+
+bb5: ; preds = %bb4
+ br label %bb6
+
+bb6: ; preds = %bb27, %bb5
+ %j.0 = phi i64 [ 0, %bb5 ], [ %tmp28, %bb27 ]
+ %exitcond2 = icmp ne i64 %j.0, 1024
+ br i1 %exitcond2, label %bb7, label %bb29
+
+bb7: ; preds = %bb6
+ br label %bb8
+
+bb8: ; preds = %bb24, %bb7
+ %k.0 = phi i64 [ 0, %bb7 ], [ %tmp25, %bb24 ]
+ %exitcond1 = icmp ne i64 %k.0, 1024
+ br i1 %exitcond1, label %bb9, label %bb26
+
+bb9: ; preds = %bb8
+ br label %bb10
+
+bb10: ; preds = %bb21, %bb9
+ %l.0 = phi i64 [ 0, %bb9 ], [ %tmp22, %bb21 ]
+ %exitcond = icmp ne i64 %l.0, 1024
+ br i1 %exitcond, label %bb11, label %bb23
+
+bb11: ; preds = %bb10
+ %tmp = add nuw nsw i64 %i.0, %j.0
+ %tmp12 = add nuw nsw i64 %tmp, %k.0
+ %tmp13 = add nuw nsw i64 %tmp12, %l.0
+ %tmp14 = sitofp i64 %tmp13 to float
+ %tmp15 = add nuw nsw i64 %i.0, %j.0
+ %tmp16 = add nuw nsw i64 %tmp15, %k.0
+ %tmp17 = add nuw nsw i64 %tmp16, %l.0
+ %tmp18 = getelementptr inbounds float, float* %A, i64 %tmp17
+ %tmp19 = load float, float* %tmp18, align 4
+ %tmp20 = fadd float %tmp19, %tmp14
+ store float %tmp20, float* %tmp18, align 4
+ br label %bb21
+
+bb21: ; preds = %bb11
+ %tmp22 = add nuw nsw i64 %l.0, 1
+ br label %bb10
+
+bb23: ; preds = %bb10
+ br label %bb24
+
+bb24: ; preds = %bb23
+ %tmp25 = add nuw nsw i64 %k.0, 1
+ br label %bb8
+
+bb26: ; preds = %bb8
+ br label %bb27
+
+bb27: ; preds = %bb26
+ %tmp28 = add nuw nsw i64 %j.0, 1
+ br label %bb6
+
+bb29: ; preds = %bb6
+ br label %bb30
+
+bb30: ; preds = %bb29
+ %tmp31 = add nuw nsw i64 %i.0, 1
+ br label %bb4
+
+bb32: ; preds = %bb4
+ ret void
+}
More information about the llvm-commits
mailing list