xref: /llvm-project/llvm/tools/llvm-mca/Views/RetireControlUnitStatistics.cpp (revision 14f77576c9c4f502267a92992abe3bdcbeb96b2c)
110aa09f0SMatt Davis //===--------------------- RetireControlUnitStatistics.cpp ------*- C++ -*-===//
210aa09f0SMatt Davis //
32946cd70SChandler Carruth // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
42946cd70SChandler Carruth // See https://llvm.org/LICENSE.txt for license information.
52946cd70SChandler Carruth // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
610aa09f0SMatt Davis //
710aa09f0SMatt Davis //===----------------------------------------------------------------------===//
810aa09f0SMatt Davis /// \file
910aa09f0SMatt Davis ///
1010aa09f0SMatt Davis /// This file implements the RetireControlUnitStatistics interface.
1110aa09f0SMatt Davis ///
1210aa09f0SMatt Davis //===----------------------------------------------------------------------===//
1310aa09f0SMatt Davis 
1410aa09f0SMatt Davis #include "Views/RetireControlUnitStatistics.h"
1510aa09f0SMatt Davis #include "llvm/Support/Format.h"
1610aa09f0SMatt Davis 
175a8fd657SFangrui Song namespace llvm {
1810aa09f0SMatt Davis namespace mca {
1910aa09f0SMatt Davis 
RetireControlUnitStatistics(const MCSchedModel & SM)2007a8255aSAndrea Di Biagio RetireControlUnitStatistics::RetireControlUnitStatistics(const MCSchedModel &SM)
2107a8255aSAndrea Di Biagio     : NumRetired(0), NumCycles(0), EntriesInUse(0), MaxUsedEntries(0),
2207a8255aSAndrea Di Biagio       SumOfUsedEntries(0) {
2307a8255aSAndrea Di Biagio   TotalROBEntries = SM.MicroOpBufferSize;
2407a8255aSAndrea Di Biagio   if (SM.hasExtraProcessorInfo()) {
2507a8255aSAndrea Di Biagio     const MCExtraProcessorInfo &EPI = SM.getExtraProcessorInfo();
2607a8255aSAndrea Di Biagio     if (EPI.ReorderBufferSize)
2707a8255aSAndrea Di Biagio       TotalROBEntries = EPI.ReorderBufferSize;
2807a8255aSAndrea Di Biagio   }
2907a8255aSAndrea Di Biagio }
3007a8255aSAndrea Di Biagio 
onEvent(const HWInstructionEvent & Event)3110aa09f0SMatt Davis void RetireControlUnitStatistics::onEvent(const HWInstructionEvent &Event) {
3207a8255aSAndrea Di Biagio   if (Event.Type == HWInstructionEvent::Dispatched) {
3307a8255aSAndrea Di Biagio     unsigned NumEntries =
3407a8255aSAndrea Di Biagio         static_cast<const HWInstructionDispatchedEvent &>(Event).MicroOpcodes;
3507a8255aSAndrea Di Biagio     EntriesInUse += NumEntries;
3607a8255aSAndrea Di Biagio   }
3707a8255aSAndrea Di Biagio 
3807a8255aSAndrea Di Biagio   if (Event.Type == HWInstructionEvent::Retired) {
3907a8255aSAndrea Di Biagio     unsigned ReleasedEntries = Event.IR.getInstruction()->getDesc().NumMicroOps;
4007a8255aSAndrea Di Biagio     assert(EntriesInUse >= ReleasedEntries && "Invalid internal state!");
4107a8255aSAndrea Di Biagio     EntriesInUse -= ReleasedEntries;
4210aa09f0SMatt Davis     ++NumRetired;
4310aa09f0SMatt Davis   }
4407a8255aSAndrea Di Biagio }
4507a8255aSAndrea Di Biagio 
onCycleEnd()4607a8255aSAndrea Di Biagio void RetireControlUnitStatistics::onCycleEnd() {
4707a8255aSAndrea Di Biagio   // Update histogram
4807a8255aSAndrea Di Biagio   RetiredPerCycle[NumRetired]++;
4907a8255aSAndrea Di Biagio   NumRetired = 0;
5007a8255aSAndrea Di Biagio   ++NumCycles;
5107a8255aSAndrea Di Biagio   MaxUsedEntries = std::max(MaxUsedEntries, EntriesInUse);
5207a8255aSAndrea Di Biagio   SumOfUsedEntries += EntriesInUse;
5307a8255aSAndrea Di Biagio }
5410aa09f0SMatt Davis 
printView(raw_ostream & OS) const55db158be6SAndrea Di Biagio void RetireControlUnitStatistics::printView(raw_ostream &OS) const {
5610aa09f0SMatt Davis   std::string Buffer;
5710aa09f0SMatt Davis   raw_string_ostream TempStream(Buffer);
5810aa09f0SMatt Davis   TempStream << "\n\nRetire Control Unit - "
5910aa09f0SMatt Davis              << "number of cycles where we saw N instructions retired:\n";
6010aa09f0SMatt Davis   TempStream << "[# retired], [# cycles]\n";
6110aa09f0SMatt Davis 
62536c9a60SMark de Wever   for (const std::pair<const unsigned, unsigned> &Entry : RetiredPerCycle) {
6310aa09f0SMatt Davis     TempStream << " " << Entry.first;
6410aa09f0SMatt Davis     if (Entry.first < 10)
6510aa09f0SMatt Davis       TempStream << ",           ";
6610aa09f0SMatt Davis     else
6710aa09f0SMatt Davis       TempStream << ",          ";
6810aa09f0SMatt Davis     TempStream << Entry.second << "  ("
6910aa09f0SMatt Davis                << format("%.1f", ((double)Entry.second / NumCycles) * 100.0)
7010aa09f0SMatt Davis                << "%)\n";
7110aa09f0SMatt Davis   }
7210aa09f0SMatt Davis 
7307a8255aSAndrea Di Biagio   unsigned AvgUsage = (double)SumOfUsedEntries / NumCycles;
74*14f77576SMarcos Horro   double MaxUsagePercentage =
75*14f77576SMarcos Horro       ((double)MaxUsedEntries / TotalROBEntries) * 100.0;
7607a8255aSAndrea Di Biagio   double NormalizedMaxPercentage = floor((MaxUsagePercentage * 10) + 0.5) / 10;
7707a8255aSAndrea Di Biagio   double AvgUsagePercentage = ((double)AvgUsage / TotalROBEntries) * 100.0;
7807a8255aSAndrea Di Biagio   double NormalizedAvgPercentage = floor((AvgUsagePercentage * 10) + 0.5) / 10;
7907a8255aSAndrea Di Biagio 
8007a8255aSAndrea Di Biagio   TempStream << "\nTotal ROB Entries:                " << TotalROBEntries
8107a8255aSAndrea Di Biagio              << "\nMax Used ROB Entries:             " << MaxUsedEntries
8207a8255aSAndrea Di Biagio              << format("  ( %.1f%% )", NormalizedMaxPercentage)
8307a8255aSAndrea Di Biagio              << "\nAverage Used ROB Entries per cy:  " << AvgUsage
8407a8255aSAndrea Di Biagio              << format("  ( %.1f%% )\n", NormalizedAvgPercentage);
8507a8255aSAndrea Di Biagio 
8610aa09f0SMatt Davis   TempStream.flush();
8710aa09f0SMatt Davis   OS << Buffer;
8810aa09f0SMatt Davis }
8910aa09f0SMatt Davis 
9010aa09f0SMatt Davis } // namespace mca
915a8fd657SFangrui Song } // namespace llvm
92