xref: /freebsd/contrib/llvm-project/llvm/lib/CodeGen/MachineBranchProbabilityInfo.cpp (revision b64c5a0ace59af62eff52bfe110a521dc73c937b)
1 //===- MachineBranchProbabilityInfo.cpp - Machine Branch Probability Info -===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This analysis uses probability info stored in Machine Basic Blocks.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #include "llvm/CodeGen/MachineBranchProbabilityInfo.h"
14 #include "llvm/CodeGen/MachineBasicBlock.h"
15 #include "llvm/InitializePasses.h"
16 #include "llvm/Support/CommandLine.h"
17 #include "llvm/Support/raw_ostream.h"
18 
19 using namespace llvm;
20 
21 INITIALIZE_PASS_BEGIN(MachineBranchProbabilityInfoWrapperPass,
22                       "machine-branch-prob",
23                       "Machine Branch Probability Analysis", false, true)
24 INITIALIZE_PASS_END(MachineBranchProbabilityInfoWrapperPass,
25                     "machine-branch-prob",
26                     "Machine Branch Probability Analysis", false, true)
27 
28 namespace llvm {
29 cl::opt<unsigned>
30     StaticLikelyProb("static-likely-prob",
31                      cl::desc("branch probability threshold in percentage"
32                               "to be considered very likely"),
33                      cl::init(80), cl::Hidden);
34 
35 cl::opt<unsigned> ProfileLikelyProb(
36     "profile-likely-prob",
37     cl::desc("branch probability threshold in percentage to be considered"
38              " very likely when profile is available"),
39     cl::init(51), cl::Hidden);
40 } // namespace llvm
41 
42 MachineBranchProbabilityAnalysis::Result
43 MachineBranchProbabilityAnalysis::run(MachineFunction &,
44                                       MachineFunctionAnalysisManager &) {
45   return MachineBranchProbabilityInfo();
46 }
47 
48 PreservedAnalyses
49 MachineBranchProbabilityPrinterPass::run(MachineFunction &MF,
50                                          MachineFunctionAnalysisManager &MFAM) {
51   OS << "Printing analysis 'Machine Branch Probability Analysis' for machine "
52         "function '"
53      << MF.getName() << "':\n";
54   auto &MBPI = MFAM.getResult<MachineBranchProbabilityAnalysis>(MF);
55   for (const MachineBasicBlock &MBB : MF) {
56     for (const MachineBasicBlock *Succ : MBB.successors())
57       MBPI.printEdgeProbability(OS << "  ", &MBB, Succ);
58   }
59   return PreservedAnalyses::all();
60 }
61 
62 char MachineBranchProbabilityInfoWrapperPass::ID = 0;
63 
64 MachineBranchProbabilityInfoWrapperPass::
65     MachineBranchProbabilityInfoWrapperPass()
66     : ImmutablePass(ID) {
67   PassRegistry &Registry = *PassRegistry::getPassRegistry();
68   initializeMachineBranchProbabilityInfoWrapperPassPass(Registry);
69 }
70 
71 void MachineBranchProbabilityInfoWrapperPass::anchor() {}
72 
73 AnalysisKey MachineBranchProbabilityAnalysis::Key;
74 
75 bool MachineBranchProbabilityInfo::invalidate(
76     MachineFunction &, const PreservedAnalyses &PA,
77     MachineFunctionAnalysisManager::Invalidator &) {
78   auto PAC = PA.getChecker<MachineBranchProbabilityAnalysis>();
79   return !PAC.preservedWhenStateless();
80 }
81 
82 BranchProbability MachineBranchProbabilityInfo::getEdgeProbability(
83     const MachineBasicBlock *Src,
84     MachineBasicBlock::const_succ_iterator Dst) const {
85   return Src->getSuccProbability(Dst);
86 }
87 
88 BranchProbability MachineBranchProbabilityInfo::getEdgeProbability(
89     const MachineBasicBlock *Src, const MachineBasicBlock *Dst) const {
90   // This is a linear search. Try to use the const_succ_iterator version when
91   // possible.
92   return getEdgeProbability(Src, find(Src->successors(), Dst));
93 }
94 
95 bool MachineBranchProbabilityInfo::isEdgeHot(
96     const MachineBasicBlock *Src, const MachineBasicBlock *Dst) const {
97   BranchProbability HotProb(StaticLikelyProb, 100);
98   return getEdgeProbability(Src, Dst) > HotProb;
99 }
100 
101 raw_ostream &MachineBranchProbabilityInfo::printEdgeProbability(
102     raw_ostream &OS, const MachineBasicBlock *Src,
103     const MachineBasicBlock *Dst) const {
104 
105   const BranchProbability Prob = getEdgeProbability(Src, Dst);
106   OS << "edge " << printMBBReference(*Src) << " -> " << printMBBReference(*Dst)
107      << " probability is " << Prob
108      << (isEdgeHot(Src, Dst) ? " [HOT edge]\n" : "\n");
109 
110   return OS;
111 }
112