dev-arm: Fix WalkCache stats
The WalkCache stats are wrongly using the legacy framework.
With this patch we are registering those to the hierarchical structure.
As we need to pass the Stats::Group parent at construction time,
we are replacing 2d arrays with Vector2d for count stats and using a flat
vector of pointers for the Formula stats
Signed-off-by: Giacomo Travaglini <giacomo.travaglini@arm.com>
Change-Id: I8992bc262a376e4e81a4d608c11dff6902e0a01d
Reviewed-on: https://gem5-review.googlesource.com/c/public/gem5/+/42984
Maintainer: Jason Lowe-Power <power.jg@gmail.com>
Reviewed-by: Jason Lowe-Power <power.jg@gmail.com>
Tested-by: kokoro <noreply+kokoro@google.com>
diff --git a/src/dev/arm/smmu_v3_caches.cc b/src/dev/arm/smmu_v3_caches.cc
index 59f5aca..b09fb31 100644
--- a/src/dev/arm/smmu_v3_caches.cc
+++ b/src/dev/arm/smmu_v3_caches.cc
@@ -1228,68 +1228,105 @@
WalkCache::
WalkCacheStats::WalkCacheStats(Stats::Group *parent)
- : Stats::Group(parent)
+ : Stats::Group(parent),
+ ADD_STAT(totalLookupsByStageLevel, UNIT_COUNT,
+ "Total number of lookups"),
+ ADD_STAT(totalMissesByStageLevel, UNIT_COUNT,
+ "Total number of misses"),
+ ADD_STAT(totalUpdatesByStageLevel, UNIT_COUNT,
+ "Total number of updates"),
+ ADD_STAT(insertionsByStageLevel, UNIT_COUNT,
+ "Number of insertions (not replacements)")
{
using namespace Stats;
+ totalLookupsByStageLevel
+ .init(2, WALK_CACHE_LEVELS)
+ .flags(pdf);
+ totalMissesByStageLevel
+ .init(2, WALK_CACHE_LEVELS)
+ .flags(pdf);
+ totalUpdatesByStageLevel
+ .init(2, WALK_CACHE_LEVELS)
+ .flags(pdf);
+ insertionsByStageLevel
+ .init(2, WALK_CACHE_LEVELS)
+ .flags(pdf);
+
for (int s = 0; s < 2; s++) {
+ totalLookupsByStageLevel.subname(s, csprintf("S%d", s + 1));
+ totalMissesByStageLevel.subname(s, csprintf("S%d", s + 1));
+ totalUpdatesByStageLevel.subname(s, csprintf("S%d", s + 1));
+ insertionsByStageLevel.subname(s, csprintf("S%d", s + 1));
+
for (int l = 0; l < WALK_CACHE_LEVELS; l++) {
- averageLookupsByStageLevel[s][l]
- .name(csprintf("averageLookupsS%dL%d", s+1, l))
- .desc("Average number lookups per second")
- .flags(pdf);
+ totalLookupsByStageLevel.ysubname(l, csprintf("L%d", l));
+ totalMissesByStageLevel.ysubname(l, csprintf("L%d", l));
+ totalUpdatesByStageLevel.ysubname(l, csprintf("L%d", l));
+ insertionsByStageLevel.ysubname(l, csprintf("L%d", l));
- totalLookupsByStageLevel[s][l]
- .name(csprintf("totalLookupsS%dL%d", s+1, l))
- .desc("Total number of lookups")
- .flags(pdf);
+ auto avg_lookup = new Stats::Formula(
+ this,
+ csprintf("averageLookups_S%dL%d", s+1, l).c_str(),
+ UNIT_RATE(Stats::Units::Count, Stats::Units::Second),
+ "Average number lookups per second");
+ avg_lookup->flags(pdf);
+ averageLookupsByStageLevel.push_back(avg_lookup);
- averageLookupsByStageLevel[s][l] =
+ *avg_lookup =
totalLookupsByStageLevel[s][l] / simSeconds;
+ auto avg_misses = new Stats::Formula(
+ this,
+ csprintf("averageMisses_S%dL%d", s+1, l).c_str(),
+ UNIT_RATE(Stats::Units::Count, Stats::Units::Second),
+ "Average number misses per second");
+ avg_misses->flags(pdf);
+ averageMissesByStageLevel.push_back(avg_misses);
- averageMissesByStageLevel[s][l]
- .name(csprintf("averageMissesS%dL%d", s+1, l))
- .desc("Average number misses per second")
- .flags(pdf);
-
- totalMissesByStageLevel[s][l]
- .name(csprintf("totalMissesS%dL%d", s+1, l))
- .desc("Total number of misses")
- .flags(pdf);
-
- averageMissesByStageLevel[s][l] =
+ *avg_misses =
totalMissesByStageLevel[s][l] / simSeconds;
+ auto avg_updates = new Stats::Formula(
+ this,
+ csprintf("averageUpdates_S%dL%d", s+1, l).c_str(),
+ UNIT_RATE(Stats::Units::Count, Stats::Units::Second),
+ "Average number updates per second");
+ avg_updates->flags(pdf);
+ averageUpdatesByStageLevel.push_back(avg_updates);
- averageUpdatesByStageLevel[s][l]
- .name(csprintf("averageUpdatesS%dL%d", s+1, l))
- .desc("Average number updates per second")
- .flags(pdf);
-
- totalUpdatesByStageLevel[s][l]
- .name(csprintf("totalUpdatesS%dL%d", s+1, l))
- .desc("Total number of updates")
- .flags(pdf);
-
- averageUpdatesByStageLevel[s][l] =
+ *avg_updates =
totalUpdatesByStageLevel[s][l] / simSeconds;
+ auto avg_hitrate = new Stats::Formula(
+ this,
+ csprintf("averageHitRate_S%dL%d", s+1, l).c_str(),
+ UNIT_RATIO,
+ "Average hit rate");
+ avg_hitrate->flags(pdf);
+ averageHitRateByStageLevel.push_back(avg_hitrate);
- averageHitRateByStageLevel[s][l]
- .name(csprintf("averageHitRateS%dL%d", s+1, l))
- .desc("Average hit rate")
- .flags(pdf);
-
- averageHitRateByStageLevel[s][l] =
+ *avg_hitrate =
(totalLookupsByStageLevel[s][l] -
totalMissesByStageLevel[s][l])
/ totalLookupsByStageLevel[s][l];
- insertionsByStageLevel[s][l]
- .name(csprintf("insertionsS%dL%d", s+1, l))
- .desc("Number of insertions (not replacements)")
- .flags(pdf);
}
}
}
+
+WalkCache::
+WalkCacheStats::~WalkCacheStats()
+{
+ for (auto avg_lookup : averageLookupsByStageLevel)
+ delete avg_lookup;
+
+ for (auto avg_miss : averageMissesByStageLevel)
+ delete avg_miss;
+
+ for (auto avg_update : averageUpdatesByStageLevel)
+ delete avg_update;
+
+ for (auto avg_hitrate : averageHitRateByStageLevel)
+ delete avg_hitrate;
+}
diff --git a/src/dev/arm/smmu_v3_caches.hh b/src/dev/arm/smmu_v3_caches.hh
index dee09f2..07c6242 100644
--- a/src/dev/arm/smmu_v3_caches.hh
+++ b/src/dev/arm/smmu_v3_caches.hh
@@ -325,22 +325,23 @@
struct WalkCacheStats : public Stats::Group
{
WalkCacheStats(Stats::Group *parent);
+ ~WalkCacheStats();
unsigned int lookupsByStageLevel[2][WALK_CACHE_LEVELS];
- Stats::Formula averageLookupsByStageLevel[2][WALK_CACHE_LEVELS];
- Stats::Scalar totalLookupsByStageLevel[2][WALK_CACHE_LEVELS];
+ std::vector<Stats::Formula*> averageLookupsByStageLevel;
+ Stats::Vector2d totalLookupsByStageLevel;
unsigned int missesByStageLevel[2][WALK_CACHE_LEVELS];
- Stats::Formula averageMissesByStageLevel[2][WALK_CACHE_LEVELS];
- Stats::Scalar totalMissesByStageLevel[2][WALK_CACHE_LEVELS];
+ std::vector<Stats::Formula*> averageMissesByStageLevel;
+ Stats::Vector2d totalMissesByStageLevel;
unsigned int updatesByStageLevel[2][WALK_CACHE_LEVELS];
- Stats::Formula averageUpdatesByStageLevel[2][WALK_CACHE_LEVELS];
- Stats::Scalar totalUpdatesByStageLevel[2][WALK_CACHE_LEVELS];
+ std::vector<Stats::Formula*> averageUpdatesByStageLevel;
+ Stats::Vector2d totalUpdatesByStageLevel;
- Stats::Formula averageHitRateByStageLevel[2][WALK_CACHE_LEVELS];
+ std::vector<Stats::Formula*> averageHitRateByStageLevel;
- Stats::Scalar insertionsByStageLevel[2][WALK_CACHE_LEVELS];
+ Stats::Vector2d insertionsByStageLevel;
} walkCacheStats;
private:
typedef std::vector<Entry> Set;