/Users/buildslave/jenkins/sharedspace/clang-stage2-coverage-R@2/llvm/lib/Analysis/IndirectCallPromotionAnalysis.cpp
Line | Count | Source |
1 | | //===-- IndirectCallPromotionAnalysis.cpp - Find promotion candidates ===// |
2 | | // |
3 | | // The LLVM Compiler Infrastructure |
4 | | // |
5 | | // This file is distributed under the University of Illinois Open Source |
6 | | // License. See LICENSE.TXT for details. |
7 | | // |
8 | | //===----------------------------------------------------------------------===// |
9 | | // |
10 | | // Helper methods for identifying profitable indirect call promotion |
11 | | // candidates for an instruction when the indirect-call value profile metadata |
12 | | // is available. |
13 | | // |
14 | | //===----------------------------------------------------------------------===// |
15 | | |
16 | | #include "llvm/Analysis/IndirectCallPromotionAnalysis.h" |
17 | | #include "llvm/ADT/STLExtras.h" |
18 | | #include "llvm/Analysis/IndirectCallSiteVisitor.h" |
19 | | #include "llvm/IR/CallSite.h" |
20 | | #include "llvm/IR/DiagnosticInfo.h" |
21 | | #include "llvm/IR/InstIterator.h" |
22 | | #include "llvm/IR/InstVisitor.h" |
23 | | #include "llvm/IR/Instructions.h" |
24 | | #include "llvm/IR/IntrinsicInst.h" |
25 | | #include "llvm/ProfileData/InstrProf.h" |
26 | | #include "llvm/Support/Debug.h" |
27 | | #include <string> |
28 | | #include <utility> |
29 | | #include <vector> |
30 | | |
31 | | using namespace llvm; |
32 | | |
33 | | #define DEBUG_TYPE "pgo-icall-prom-analysis" |
34 | | |
35 | | // The percent threshold for the direct-call target (this call site vs the |
36 | | // remaining call count) for it to be considered as the promotion target. |
37 | | static cl::opt<unsigned> ICPRemainingPercentThreshold( |
38 | | "icp-remaining-percent-threshold", cl::init(30), cl::Hidden, cl::ZeroOrMore, |
39 | | cl::desc("The percentage threshold against remaining unpromoted indirect " |
40 | | "call count for the promotion")); |
41 | | |
42 | | // The percent threshold for the direct-call target (this call site vs the |
43 | | // total call count) for it to be considered as the promotion target. |
44 | | static cl::opt<unsigned> |
45 | | ICPTotalPercentThreshold("icp-total-percent-threshold", cl::init(5), |
46 | | cl::Hidden, cl::ZeroOrMore, |
47 | | cl::desc("The percentage threshold against total " |
48 | | "count for the promotion")); |
49 | | |
50 | | // Set the maximum number of targets to promote for a single indirect-call |
51 | | // callsite. |
52 | | static cl::opt<unsigned> |
53 | | MaxNumPromotions("icp-max-prom", cl::init(3), cl::Hidden, cl::ZeroOrMore, |
54 | | cl::desc("Max number of promotions for a single indirect " |
55 | | "call callsite")); |
56 | | |
57 | 1.13k | ICallPromotionAnalysis::ICallPromotionAnalysis() { |
58 | 1.13k | ValueDataArray = llvm::make_unique<InstrProfValueData[]>(MaxNumPromotions); |
59 | 1.13k | } |
60 | | |
61 | | bool ICallPromotionAnalysis::isPromotionProfitable(uint64_t Count, |
62 | | uint64_t TotalCount, |
63 | 58 | uint64_t RemainingCount) { |
64 | 58 | return Count * 100 >= ICPRemainingPercentThreshold * RemainingCount && |
65 | 58 | Count * 100 >= ICPTotalPercentThreshold * TotalCount; |
66 | 58 | } |
67 | | |
68 | | // Indirect-call promotion heuristic. The direct targets are sorted based on |
69 | | // the count. Stop at the first target that is not promoted. Returns the |
70 | | // number of candidates deemed profitable. |
71 | | uint32_t ICallPromotionAnalysis::getProfitablePromotionCandidates( |
72 | 43 | const Instruction *Inst, uint32_t NumVals, uint64_t TotalCount) { |
73 | 43 | ArrayRef<InstrProfValueData> ValueDataRef(ValueDataArray.get(), NumVals); |
74 | 43 | |
75 | 43 | DEBUG(dbgs() << " \nWork on callsite " << *Inst << " Num_targets: " << NumVals |
76 | 43 | << "\n"); |
77 | 43 | |
78 | 43 | uint32_t I = 0; |
79 | 43 | uint64_t RemainingCount = TotalCount; |
80 | 97 | for (; I < MaxNumPromotions && 97 I < NumVals95 ; I++54 ) { |
81 | 58 | uint64_t Count = ValueDataRef[I].Count; |
82 | 58 | assert(Count <= RemainingCount); |
83 | 58 | DEBUG(dbgs() << " Candidate " << I << " Count=" << Count |
84 | 58 | << " Target_func: " << ValueDataRef[I].Value << "\n"); |
85 | 58 | |
86 | 58 | if (!isPromotionProfitable(Count, TotalCount, RemainingCount)58 ) { |
87 | 4 | DEBUG(dbgs() << " Not promote: Cold target.\n"); |
88 | 4 | return I; |
89 | 4 | } |
90 | 54 | RemainingCount -= Count; |
91 | 54 | } |
92 | 39 | return I; |
93 | 43 | } |
94 | | |
95 | | ArrayRef<InstrProfValueData> |
96 | | ICallPromotionAnalysis::getPromotionCandidatesForInstruction( |
97 | | const Instruction *I, uint32_t &NumVals, uint64_t &TotalCount, |
98 | 69 | uint32_t &NumCandidates) { |
99 | 69 | bool Res = |
100 | 69 | getValueProfDataFromInst(*I, IPVK_IndirectCallTarget, MaxNumPromotions, |
101 | 69 | ValueDataArray.get(), NumVals, TotalCount); |
102 | 69 | if (!Res69 ) { |
103 | 26 | NumCandidates = 0; |
104 | 26 | return ArrayRef<InstrProfValueData>(); |
105 | 26 | } |
106 | 43 | NumCandidates = getProfitablePromotionCandidates(I, NumVals, TotalCount); |
107 | 43 | return ArrayRef<InstrProfValueData>(ValueDataArray.get(), NumVals); |
108 | 43 | } |