xref: /freebsd/contrib/llvm-project/llvm/include/llvm/Analysis/StaticDataProfileInfo.h (revision 700637cbb5e582861067a11aaca4d053546871d2)
1 #ifndef LLVM_ANALYSIS_STATICDATAPROFILEINFO_H
2 #define LLVM_ANALYSIS_STATICDATAPROFILEINFO_H
3 
4 #include "llvm/ADT/DenseMap.h"
5 #include "llvm/ADT/DenseSet.h"
6 #include "llvm/Analysis/ProfileSummaryInfo.h"
7 #include "llvm/IR/Constant.h"
8 #include "llvm/Pass.h"
9 #include "llvm/Support/Compiler.h"
10 
11 namespace llvm {
12 
13 /// A class that holds the constants that represent static data and their
14 /// profile information and provides methods to operate on them.
15 class StaticDataProfileInfo {
16 public:
17   /// Accummulate the profile count of a constant that will be lowered to static
18   /// data sections.
19   DenseMap<const Constant *, uint64_t> ConstantProfileCounts;
20 
21   /// Keeps track of the constants that are seen at least once without profile
22   /// counts.
23   DenseSet<const Constant *> ConstantWithoutCounts;
24 
25   /// If \p C has a count, return it. Otherwise, return std::nullopt.
26   LLVM_ABI std::optional<uint64_t>
27   getConstantProfileCount(const Constant *C) const;
28 
29 public:
30   StaticDataProfileInfo() = default;
31 
32   /// If \p Count is not nullopt, add it to the profile count of the constant \p
33   /// C in a saturating way, and clamp the count to \p getInstrMaxCountValue if
34   /// the result exceeds it. Otherwise, mark the constant as having no profile
35   /// count.
36   LLVM_ABI void addConstantProfileCount(const Constant *C,
37                                         std::optional<uint64_t> Count);
38 
39   /// Return a section prefix for the constant \p C based on its profile count.
40   /// - If a constant doesn't have a counter, return an empty string.
41   /// - Otherwise,
42   ///   - If it has a hot count, return "hot".
43   ///   - If it is seen by unprofiled function, return an empty string.
44   ///   - If it has a cold count, return "unlikely".
45   ///   - Otherwise (e.g. it's used by lukewarm functions), return an empty
46   ///     string.
47   LLVM_ABI StringRef getConstantSectionPrefix(
48       const Constant *C, const ProfileSummaryInfo *PSI) const;
49 };
50 
51 /// This wraps the StaticDataProfileInfo object as an immutable pass, for a
52 /// backend pass to operate on.
53 class LLVM_ABI StaticDataProfileInfoWrapperPass : public ImmutablePass {
54 public:
55   static char ID;
56   StaticDataProfileInfoWrapperPass();
57   bool doInitialization(Module &M) override;
58   bool doFinalization(Module &M) override;
59 
getStaticDataProfileInfo()60   StaticDataProfileInfo &getStaticDataProfileInfo() { return *Info; }
getStaticDataProfileInfo()61   const StaticDataProfileInfo &getStaticDataProfileInfo() const {
62     return *Info;
63   }
64 
65   /// This pass provides StaticDataProfileInfo for reads/writes but does not
66   /// modify \p M or other analysis. All analysis are preserved.
getAnalysisUsage(AnalysisUsage & AU)67   void getAnalysisUsage(AnalysisUsage &AU) const override {
68     AU.setPreservesAll();
69   }
70 
71 private:
72   std::unique_ptr<StaticDataProfileInfo> Info;
73 };
74 
75 } // namespace llvm
76 
77 #endif // LLVM_ANALYSIS_STATICDATAPROFILEINFO_H
78