diff --git a/llvm/test/tools/llvm-profdata/c-general.test b/llvm/test/tools/llvm-profdata/c-general.test index 7c48f7b04a05c..ab4849fac034f 100644 --- a/llvm/test/tools/llvm-profdata/c-general.test +++ b/llvm/test/tools/llvm-profdata/c-general.test @@ -22,6 +22,6 @@ SWITCHES-LABEL: Functions shown: 1 CHECK-LABEL: Total functions: 12 CHECK-NEXT: Maximum function count: 1 CHECK-NEXT: Maximum internal block count: 100 -TOPN: boolean_operators, max count = 100 -TOPN-NEXT: simple_loops, max count = 100 -TOPN-NEXT: conditionals, max count = 100 +TOPN: simple_loops, max count = 100 +TOPN-NEXT: conditionals, max count = 100 +TOPN-NEXT: boolean_operators, max count = 100 diff --git a/llvm/test/tools/llvm-profdata/show-hot.proftext b/llvm/test/tools/llvm-profdata/show-hot.proftext new file mode 100644 index 0000000000000..5c9bd61c20d28 --- /dev/null +++ b/llvm/test/tools/llvm-profdata/show-hot.proftext @@ -0,0 +1,35 @@ +# RUN: llvm-profdata show %s --hot-func-list | FileCheck %s + +# CHECK: # Hot count threshold: 101 +# CHECK: hot_b +# CHECK: hot_a +# CHECK: hot_c + +:ir +hot_a +# Func Hash: +0x1234 +# Num Counters: +1 +# Counter Values: +101 + +hot_b +0x5678 +1 +202 + +hot_c +0x5678 +1 +101 + +cold_d +0xabcd +1 +1 + +cold_e +0xefff +1 +0 diff --git a/llvm/tools/llvm-profdata/llvm-profdata.cpp b/llvm/tools/llvm-profdata/llvm-profdata.cpp index 5efabd5f2a7c6..96d135b9746ff 100644 --- a/llvm/tools/llvm-profdata/llvm-profdata.cpp +++ b/llvm/tools/llvm-profdata/llvm-profdata.cpp @@ -46,7 +46,6 @@ #include #include #include -#include using namespace llvm; using ProfCorrelatorKind = InstrProfCorrelator::ProfCorrelatorKind; @@ -2846,9 +2845,8 @@ static int showInstrProfile(ShowFormat SFormat, raw_fd_ostream &OS) { auto FS = vfs::getRealFileSystem(); auto ReaderOrErr = InstrProfReader::create(Filename, *FS); std::vector Cutoffs = std::move(DetailedSummaryCutoffs); - if (ShowDetailedSummary && Cutoffs.empty()) { + if (Cutoffs.empty() && (ShowDetailedSummary || ShowHotFuncList)) Cutoffs = ProfileSummaryBuilder::DefaultCutoffs; - } InstrProfSummaryBuilder Builder(std::move(Cutoffs)); if (Error E = ReaderOrErr.takeError()) exitWithError(std::move(E), Filename); @@ -2860,15 +2858,7 @@ static int showInstrProfile(ShowFormat SFormat, raw_fd_ostream &OS) { int NumVPKind = IPVK_Last - IPVK_First + 1; std::vector VPStats(NumVPKind); - auto MinCmp = [](const std::pair &v1, - const std::pair &v2) { - return v1.second > v2.second; - }; - - std::priority_queue, - std::vector>, - decltype(MinCmp)> - HottestFuncs(MinCmp); + std::vector> NameAndMaxCount; if (!TextFormat && OnlyListBelow) { OS << "The list of functions with the maximum counter less than " @@ -2942,15 +2932,8 @@ static int showInstrProfile(ShowFormat SFormat, raw_fd_ostream &OS) { if (OnlyListBelow) continue; - if (TopNFunctions) { - if (HottestFuncs.size() == TopNFunctions) { - if (HottestFuncs.top().second < FuncMax) { - HottestFuncs.pop(); - HottestFuncs.emplace(std::make_pair(std::string(Func.Name), FuncMax)); - } - } else - HottestFuncs.emplace(std::make_pair(std::string(Func.Name), FuncMax)); - } + if (TopNFunctions || ShowHotFuncList) + NameAndMaxCount.emplace_back(Func.Name, FuncMax); if (Show) { if (!ShownFunctions) @@ -3029,16 +3012,27 @@ static int showInstrProfile(ShowFormat SFormat, raw_fd_ostream &OS) { << "): " << PS->getNumFunctions() - BelowCutoffFunctions << "\n"; } + // Sort by MaxCount in decreasing order + llvm::stable_sort(NameAndMaxCount, [](const auto &L, const auto &R) { + return L.second > R.second; + }); if (TopNFunctions) { - std::vector> SortedHottestFuncs; - while (!HottestFuncs.empty()) { - SortedHottestFuncs.emplace_back(HottestFuncs.top()); - HottestFuncs.pop(); - } OS << "Top " << TopNFunctions << " functions with the largest internal block counts: \n"; - for (auto &hotfunc : llvm::reverse(SortedHottestFuncs)) - OS << " " << hotfunc.first << ", max count = " << hotfunc.second << "\n"; + auto TopFuncs = ArrayRef(NameAndMaxCount).take_front(TopNFunctions); + for (auto [Name, MaxCount] : TopFuncs) + OS << " " << Name << ", max count = " << MaxCount << "\n"; + } + + if (ShowHotFuncList) { + auto HotCountThreshold = + ProfileSummaryBuilder::getHotCountThreshold(PS->getDetailedSummary()); + OS << "# Hot count threshold: " << HotCountThreshold << "\n"; + for (auto [Name, MaxCount] : NameAndMaxCount) { + if (MaxCount < HotCountThreshold) + break; + OS << Name << "\n"; + } } if (ShownFunctions && ShowIndirectCallTargets) {