Details | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
14 | pmbaty | 1 | //===- Transforms/Instrumentation/InstrProfiling.h --------------*- C++ -*-===// |
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 | /// \file |
||
9 | /// This file provides the interface for LLVM's PGO Instrumentation lowering |
||
10 | /// pass. |
||
11 | //===----------------------------------------------------------------------===// |
||
12 | |||
13 | #ifndef LLVM_TRANSFORMS_INSTRUMENTATION_INSTRPROFILING_H |
||
14 | #define LLVM_TRANSFORMS_INSTRUMENTATION_INSTRPROFILING_H |
||
15 | |||
16 | #include "llvm/ADT/DenseMap.h" |
||
17 | #include "llvm/ADT/StringRef.h" |
||
18 | #include "llvm/IR/IntrinsicInst.h" |
||
19 | #include "llvm/IR/PassManager.h" |
||
20 | #include "llvm/ProfileData/InstrProf.h" |
||
21 | #include "llvm/Transforms/Instrumentation.h" |
||
22 | #include <cstdint> |
||
23 | #include <cstring> |
||
24 | #include <vector> |
||
25 | |||
26 | namespace llvm { |
||
27 | |||
28 | class TargetLibraryInfo; |
||
29 | using LoadStorePair = std::pair<Instruction *, Instruction *>; |
||
30 | |||
31 | /// Instrumentation based profiling lowering pass. This pass lowers |
||
32 | /// the profile instrumented code generated by FE or the IR based |
||
33 | /// instrumentation pass. |
||
34 | class InstrProfiling : public PassInfoMixin<InstrProfiling> { |
||
35 | public: |
||
36 | InstrProfiling() : IsCS(false) {} |
||
37 | InstrProfiling(const InstrProfOptions &Options, bool IsCS = false) |
||
38 | : Options(Options), IsCS(IsCS) {} |
||
39 | |||
40 | PreservedAnalyses run(Module &M, ModuleAnalysisManager &AM); |
||
41 | bool run(Module &M, |
||
42 | std::function<const TargetLibraryInfo &(Function &F)> GetTLI); |
||
43 | |||
44 | private: |
||
45 | InstrProfOptions Options; |
||
46 | Module *M; |
||
47 | Triple TT; |
||
48 | std::function<const TargetLibraryInfo &(Function &F)> GetTLI; |
||
49 | struct PerFunctionProfileData { |
||
50 | uint32_t NumValueSites[IPVK_Last + 1]; |
||
51 | GlobalVariable *RegionCounters = nullptr; |
||
52 | GlobalVariable *DataVar = nullptr; |
||
53 | |||
54 | PerFunctionProfileData() { |
||
55 | memset(NumValueSites, 0, sizeof(uint32_t) * (IPVK_Last + 1)); |
||
56 | } |
||
57 | }; |
||
58 | DenseMap<GlobalVariable *, PerFunctionProfileData> ProfileDataMap; |
||
59 | /// If runtime relocation is enabled, this maps functions to the load |
||
60 | /// instruction that produces the profile relocation bias. |
||
61 | DenseMap<const Function *, LoadInst *> FunctionToProfileBiasMap; |
||
62 | std::vector<GlobalValue *> CompilerUsedVars; |
||
63 | std::vector<GlobalValue *> UsedVars; |
||
64 | std::vector<GlobalVariable *> ReferencedNames; |
||
65 | GlobalVariable *NamesVar; |
||
66 | size_t NamesSize; |
||
67 | |||
68 | // Is this lowering for the context-sensitive instrumentation. |
||
69 | bool IsCS; |
||
70 | |||
71 | // vector of counter load/store pairs to be register promoted. |
||
72 | std::vector<LoadStorePair> PromotionCandidates; |
||
73 | |||
74 | int64_t TotalCountersPromoted = 0; |
||
75 | |||
76 | /// Lower instrumentation intrinsics in the function. Returns true if there |
||
77 | /// any lowering. |
||
78 | bool lowerIntrinsics(Function *F); |
||
79 | |||
80 | /// Register-promote counter loads and stores in loops. |
||
81 | void promoteCounterLoadStores(Function *F); |
||
82 | |||
83 | /// Returns true if relocating counters at runtime is enabled. |
||
84 | bool isRuntimeCounterRelocationEnabled() const; |
||
85 | |||
86 | /// Returns true if profile counter update register promotion is enabled. |
||
87 | bool isCounterPromotionEnabled() const; |
||
88 | |||
89 | /// Count the number of instrumented value sites for the function. |
||
90 | void computeNumValueSiteCounts(InstrProfValueProfileInst *Ins); |
||
91 | |||
92 | /// Replace instrprof.value.profile with a call to runtime library. |
||
93 | void lowerValueProfileInst(InstrProfValueProfileInst *Ins); |
||
94 | |||
95 | /// Replace instrprof.cover with a store instruction to the coverage byte. |
||
96 | void lowerCover(InstrProfCoverInst *Inc); |
||
97 | |||
98 | /// Replace instrprof.increment with an increment of the appropriate value. |
||
99 | void lowerIncrement(InstrProfIncrementInst *Inc); |
||
100 | |||
101 | /// Force emitting of name vars for unused functions. |
||
102 | void lowerCoverageData(GlobalVariable *CoverageNamesVar); |
||
103 | |||
104 | /// Compute the address of the counter value that this profiling instruction |
||
105 | /// acts on. |
||
106 | Value *getCounterAddress(InstrProfInstBase *I); |
||
107 | |||
108 | /// Get the region counters for an increment, creating them if necessary. |
||
109 | /// |
||
110 | /// If the counter array doesn't yet exist, the profile data variables |
||
111 | /// referring to them will also be created. |
||
112 | GlobalVariable *getOrCreateRegionCounters(InstrProfInstBase *Inc); |
||
113 | |||
114 | /// Create the region counters. |
||
115 | GlobalVariable *createRegionCounters(InstrProfInstBase *Inc, StringRef Name, |
||
116 | GlobalValue::LinkageTypes Linkage); |
||
117 | |||
118 | /// Emit the section with compressed function names. |
||
119 | void emitNameData(); |
||
120 | |||
121 | /// Emit value nodes section for value profiling. |
||
122 | void emitVNodes(); |
||
123 | |||
124 | /// Emit runtime registration functions for each profile data variable. |
||
125 | void emitRegistration(); |
||
126 | |||
127 | /// Emit the necessary plumbing to pull in the runtime initialization. |
||
128 | /// Returns true if a change was made. |
||
129 | bool emitRuntimeHook(); |
||
130 | |||
131 | /// Add uses of our data variables and runtime hook. |
||
132 | void emitUses(); |
||
133 | |||
134 | /// Create a static initializer for our data, on platforms that need it, |
||
135 | /// and for any profile output file that was specified. |
||
136 | void emitInitialization(); |
||
137 | }; |
||
138 | |||
139 | } // end namespace llvm |
||
140 | |||
141 | #endif // LLVM_TRANSFORMS_INSTRUMENTATION_INSTRPROFILING_H |