Movatterモバイル変換


[0]ホーム

URL:


LLVM 20.0.0git
DebugCounter.cpp
Go to the documentation of this file.
1#include "llvm/Support/DebugCounter.h"
2
3#include "DebugOptions.h"
4
5#include "llvm/Support/CommandLine.h"
6#include "llvm/Support/Format.h"
7
8using namespacellvm;
9
10namespacellvm {
11
12voidDebugCounter::Chunk::print(llvm::raw_ostream &OS) {
13if (Begin ==End)
14OS <<Begin;
15else
16OS <<Begin <<"-" <<End;
17}
18
19voidDebugCounter::printChunks(raw_ostream &OS,ArrayRef<Chunk> Chunks) {
20if (Chunks.empty()) {
21OS <<"empty";
22 }else {
23bool IsFirst =true;
24for (auto E : Chunks) {
25if (!IsFirst)
26OS <<':';
27else
28 IsFirst =false;
29 E.print(OS);
30 }
31 }
32}
33
34boolDebugCounter::parseChunks(StringRef Str,SmallVector<Chunk> &Chunks) {
35StringRef Remaining = Str;
36
37auto ConsumeInt = [&]() -> int64_t {
38StringRefNumber =
39 Remaining.take_until([](char c) {return c <'0' || c >'9'; });
40 int64_t Res;
41if (Number.getAsInteger(10, Res)) {
42errs() <<"Failed to parse int at : " << Remaining <<"\n";
43return -1;
44 }
45 Remaining = Remaining.drop_front(Number.size());
46return Res;
47 };
48
49while (1) {
50 int64_t Num = ConsumeInt();
51if (Num == -1)
52returntrue;
53if (!Chunks.empty() && Num <= Chunks[Chunks.size() - 1].End) {
54errs() <<"Expected Chunks to be in increasing order " << Num
55 <<" <= " << Chunks[Chunks.size() - 1].End <<"\n";
56returntrue;
57 }
58if (Remaining.starts_with("-")) {
59 Remaining = Remaining.drop_front();
60 int64_t Num2 = ConsumeInt();
61if (Num2 == -1)
62returntrue;
63if (Num >= Num2) {
64errs() <<"Expected " << Num <<" < " << Num2 <<" in " << Num <<"-"
65 << Num2 <<"\n";
66returntrue;
67 }
68
69 Chunks.push_back({Num, Num2});
70 }else {
71 Chunks.push_back({Num, Num});
72 }
73if (Remaining.starts_with(":")) {
74 Remaining = Remaining.drop_front();
75continue;
76 }
77if (Remaining.empty())
78break;
79errs() <<"Failed to parse at : " << Remaining;
80returntrue;
81 }
82returnfalse;
83}
84
85}// namespace llvm
86
87namespace{
88// This class overrides the default list implementation of printing so we
89// can pretty print the list of debug counter options. This type of
90// dynamic option is pretty rare (basically this and pass lists).
91classDebugCounterList :publiccl::list<std::string, DebugCounter> {
92private:
93usingBase =cl::list<std::string, DebugCounter>;
94
95public:
96template <class... Mods>
97explicit DebugCounterList(Mods &&... Ms) :Base(std::forward<Mods>(Ms)...) {}
98
99private:
100void printOptionInfo(size_t GlobalWidth) const override{
101// This is a variant of from generic_parser_base::printOptionInfo. Sadly,
102// it's not easy to make it more usable. We could get it to print these as
103// options if we were a cl::opt and registered them, but lists don't have
104// options, nor does the parser for std::string. The other mechanisms for
105// options are global and would pollute the global namespace with our
106// counters. Rather than go that route, we have just overridden the
107// printing, which only a few things call anyway.
108outs() <<" -" << ArgStr;
109// All of the other options in CommandLine.cpp use ArgStr.size() + 6 for
110// width, so we do the same.
111 Option::printHelpStr(HelpStr, GlobalWidth, ArgStr.size() + 6);
112constauto &CounterInstance =DebugCounter::instance();
113for (constauto &Name : CounterInstance) {
114constautoInfo =
115 CounterInstance.getCounterInfo(CounterInstance.getCounterId(Name));
116size_t NumSpaces = GlobalWidth -Info.first.size() - 8;
117outs() <<" =" <<Info.first;
118outs().indent(NumSpaces) <<" - " <<Info.second <<'\n';
119 }
120 }
121};
122
123// All global objects associated to the DebugCounter, including the DebugCounter
124// itself, are owned by a single global instance of the DebugCounterOwner
125// struct. This makes it easier to control the order in which constructors and
126// destructors are run.
127structDebugCounterOwner :DebugCounter {
128 DebugCounterList DebugCounterOption{
129"debug-counter",cl::Hidden,
130cl::desc("Comma separated list of debug counter skip and count"),
131cl::CommaSeparated, cl::location<DebugCounter>(*this)};
132cl::opt<bool, true> PrintDebugCounter{
133"print-debug-counter",
134cl::Hidden,
135cl::Optional,
136cl::location(this->ShouldPrintCounter),
137cl::init(false),
138cl::desc("Print out debug counter info after all counters accumulated")};
139cl::opt<bool, true> BreakOnLastCount{
140"debug-counter-break-on-last",
141cl::Hidden,
142cl::Optional,
143cl::location(this->BreakOnLast),
144cl::init(false),
145cl::desc("Insert a break point on the last enabled count of a "
146"chunks list")};
147
148 DebugCounterOwner() {
149// Our destructor uses the debug stream. By referencing it here, we
150// ensure that its destructor runs after our destructor.
151 (void)dbgs();
152 }
153
154// Print information when destroyed, iff command line option is specified.
155 ~DebugCounterOwner() {
156if (ShouldPrintCounter)
157print(dbgs());
158 }
159};
160
161}// anonymous namespace
162
163voidllvm::initDebugCounterOptions() { (void)DebugCounter::instance(); }
164
165DebugCounter &DebugCounter::instance() {
166static DebugCounterOwner O;
167return O;
168}
169
170// This is called by the command line parser when it sees a value for the
171// debug-counter option defined above.
172voidDebugCounter::push_back(const std::string &Val) {
173if (Val.empty())
174return;
175
176// The strings should come in as counter=chunk_list
177auto CounterPair =StringRef(Val).split('=');
178if (CounterPair.second.empty()) {
179errs() <<"DebugCounter Error: " << Val <<" does not have an = in it\n";
180return;
181 }
182StringRef CounterName = CounterPair.first;
183SmallVector<Chunk> Chunks;
184
185if (parseChunks(CounterPair.second, Chunks)) {
186return;
187 }
188
189unsigned CounterID =getCounterId(std::string(CounterName));
190if (!CounterID) {
191errs() <<"DebugCounter Error: " << CounterName
192 <<" is not a registered counter\n";
193return;
194 }
195enableAllCounters();
196
197CounterInfo &Counter =Counters[CounterID];
198 Counter.IsSet =true;
199 Counter.Chunks = std::move(Chunks);
200}
201
202voidDebugCounter::print(raw_ostream &OS) const{
203SmallVector<StringRef, 16> CounterNames(RegisteredCounters.begin(),
204RegisteredCounters.end());
205sort(CounterNames);
206
207auto &Us =instance();
208OS <<"Counters and values:\n";
209for (auto &CounterName : CounterNames) {
210unsigned CounterID =getCounterId(std::string(CounterName));
211OS <<left_justify(RegisteredCounters[CounterID], 32) <<": {"
212 << Us.Counters[CounterID].Count <<",";
213printChunks(OS, Us.Counters[CounterID].Chunks);
214OS <<"}\n";
215 }
216}
217
218boolDebugCounter::shouldExecuteImpl(unsigned CounterName) {
219auto &Us =instance();
220auto Result = Us.Counters.find(CounterName);
221if (Result != Us.Counters.end()) {
222auto &CounterInfo = Result->second;
223 int64_t CurrCount =CounterInfo.Count++;
224uint64_t CurrIdx =CounterInfo.CurrChunkIdx;
225
226if (CounterInfo.Chunks.empty())
227returntrue;
228if (CurrIdx >=CounterInfo.Chunks.size())
229returnfalse;
230
231bool Res =CounterInfo.Chunks[CurrIdx].contains(CurrCount);
232if (Us.BreakOnLast && CurrIdx == (CounterInfo.Chunks.size() - 1) &&
233 CurrCount ==CounterInfo.Chunks[CurrIdx].End) {
234LLVM_BUILTIN_DEBUGTRAP;
235 }
236if (CurrCount >CounterInfo.Chunks[CurrIdx].End) {
237CounterInfo.CurrChunkIdx++;
238
239 /// Handle consecutive blocks.
240if (CounterInfo.CurrChunkIdx <CounterInfo.Chunks.size() &&
241 CurrCount ==CounterInfo.Chunks[CounterInfo.CurrChunkIdx].Begin)
242returntrue;
243 }
244return Res;
245 }
246// Didn't find the counter, should we warn?
247returntrue;
248}
249
250LLVM_DUMP_METHODvoidDebugCounter::dump() const{
251print(dbgs());
252}
print
static void print(raw_ostream &Out, object::Archive::Kind Kind, T Val)
Definition:ArchiveWriter.cpp:205
Info
Analysis containing CSE Info
Definition:CSEInfo.cpp:27
CommandLine.h
LLVM_BUILTIN_DEBUGTRAP
#define LLVM_BUILTIN_DEBUGTRAP
LLVM_BUILTIN_DEBUGTRAP - On compilers which support it, expands to an expression which causes the pro...
Definition:Compiler.h:477
LLVM_DUMP_METHOD
#define LLVM_DUMP_METHOD
Mark debug helper function definitions like dump() that should not be stripped from debug builds.
Definition:Compiler.h:622
DebugCounter.h
This file provides an implementation of debug counters.
DebugOptions.h
Name
std::string Name
Definition:ELFObjHandler.cpp:77
Format.h
OS
raw_pwrite_stream & OS
Definition:SampleProfWriter.cpp:51
llvm::ArrayRef
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition:ArrayRef.h:41
llvm::ArrayRef::empty
bool empty() const
empty - Check if the array is empty.
Definition:ArrayRef.h:163
llvm::DebugCounter
Definition:DebugCounter.h:56
llvm::DebugCounter::printChunks
static void printChunks(raw_ostream &OS, ArrayRef< Chunk >)
Definition:DebugCounter.cpp:19
llvm::DebugCounter::Counters
DenseMap< unsigned, CounterInfo > Counters
Definition:DebugCounter.h:178
llvm::DebugCounter::RegisteredCounters
CounterVector RegisteredCounters
Definition:DebugCounter.h:179
llvm::DebugCounter::push_back
void push_back(const std::string &)
Definition:DebugCounter.cpp:172
llvm::DebugCounter::getCounterId
unsigned getCounterId(const std::string &Name) const
Definition:DebugCounter.h:127
llvm::DebugCounter::shouldExecuteImpl
static bool shouldExecuteImpl(unsigned CounterName)
Definition:DebugCounter.cpp:218
llvm::DebugCounter::enableAllCounters
static void enableAllCounters()
Definition:DebugCounter.h:151
llvm::DebugCounter::parseChunks
static bool parseChunks(StringRef Str, SmallVector< Chunk > &Res)
Return true on parsing error and print the error message on the llvm::errs()
Definition:DebugCounter.cpp:34
llvm::DebugCounter::instance
static DebugCounter & instance()
Returns a reference to the singleton instance.
Definition:DebugCounter.cpp:165
llvm::DebugCounter::print
void print(raw_ostream &OS) const
Definition:DebugCounter.cpp:202
llvm::DebugCounter::dump
LLVM_DUMP_METHOD void dump() const
Definition:DebugCounter.cpp:250
llvm::SmallVectorBase::empty
bool empty() const
Definition:SmallVector.h:81
llvm::SmallVectorBase::size
size_t size() const
Definition:SmallVector.h:78
llvm::SmallVectorTemplateBase::push_back
void push_back(const T &Elt)
Definition:SmallVector.h:413
llvm::SmallVector
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition:SmallVector.h:1196
llvm::StringRef
StringRef - Represent a constant reference to a string, i.e.
Definition:StringRef.h:51
llvm::StringRef::split
std::pair< StringRef, StringRef > split(char Separator) const
Split into two substrings around the first occurrence of a separator character.
Definition:StringRef.h:700
llvm::StringRef::starts_with
bool starts_with(StringRef Prefix) const
Check if this string starts with the given Prefix.
Definition:StringRef.h:265
llvm::StringRef::empty
constexpr bool empty() const
empty - Check if the string is empty.
Definition:StringRef.h:147
llvm::StringRef::drop_front
StringRef drop_front(size_t N=1) const
Return a StringRef equal to 'this' but with the first N elements dropped.
Definition:StringRef.h:609
llvm::StringRef::take_until
StringRef take_until(function_ref< bool(char)> F) const
Return the longest prefix of 'this' such that no character in the prefix satisfies the given predicat...
Definition:StringRef.h:603
llvm::UniqueVector::end
iterator end()
Return an iterator to the end of the vector.
Definition:UniqueVector.h:81
llvm::UniqueVector::begin
iterator begin()
Return an iterator to the start of the vector.
Definition:UniqueVector.h:75
llvm::cl::list
Definition:CommandLine.h:1655
llvm::cl::opt
Definition:CommandLine.h:1423
llvm::raw_ostream
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition:raw_ostream.h:52
llvm::raw_ostream::indent
raw_ostream & indent(unsigned NumSpaces)
indent - Insert 'NumSpaces' spaces.
Definition:raw_ostream.cpp:495
uint64_t
llvm::cl::Optional
@ Optional
Definition:CommandLine.h:113
llvm::cl::Hidden
@ Hidden
Definition:CommandLine.h:137
llvm::cl::init
initializer< Ty > init(const Ty &Val)
Definition:CommandLine.h:443
llvm::cl::CommaSeparated
@ CommaSeparated
Definition:CommandLine.h:163
llvm::cl::location
LocationClass< Ty > location(Ty &L)
Definition:CommandLine.h:463
llvm::sampleprof::Base
@ Base
Definition:Discriminator.h:58
llvm
This is an optimization pass for GlobalISel generic memory operations.
Definition:AddressRanges.h:18
llvm::outs
raw_fd_ostream & outs()
This returns a reference to a raw_fd_ostream for standard output.
Definition:raw_ostream.cpp:895
llvm::initDebugCounterOptions
void initDebugCounterOptions()
Definition:DebugCounter.cpp:163
llvm::sort
void sort(IteratorTy Start, IteratorTy End)
Definition:STLExtras.h:1664
llvm::dbgs
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition:Debug.cpp:163
llvm::errs
raw_fd_ostream & errs()
This returns a reference to a raw_ostream for standard error.
Definition:raw_ostream.cpp:907
llvm::left_justify
FormattedString left_justify(StringRef Str, unsigned Width)
left_justify - append spaces after string so total output is Width characters.
Definition:Format.h:146
llvm::IntegerStyle::Number
@ Number
std
Implement std::hash so that hash_code can be used in STL containers.
Definition:BitVector.h:858
llvm::DebugCounter::Chunk::End
int64_t End
Definition:DebugCounter.h:60
llvm::DebugCounter::Chunk::Begin
int64_t Begin
Definition:DebugCounter.h:59
llvm::DebugCounter::Chunk::print
void print(llvm::raw_ostream &OS)
Definition:DebugCounter.cpp:12
llvm::DebugCounter::CounterInfo
Definition:DebugCounter.h:170
llvm::DebugCounter::CounterInfo::CurrChunkIdx
uint64_t CurrChunkIdx
Definition:DebugCounter.h:172
llvm::DebugCounter::CounterInfo::IsSet
bool IsSet
Definition:DebugCounter.h:173
llvm::DebugCounter::CounterInfo::Count
int64_t Count
Definition:DebugCounter.h:171
llvm::DebugCounter::CounterInfo::Chunks
SmallVector< Chunk > Chunks
Definition:DebugCounter.h:175
llvm::cl::desc
Definition:CommandLine.h:409

Generated on Sun Jul 20 2025 09:49:05 for LLVM by doxygen 1.9.6
[8]ページ先頭

©2009-2025 Movatter.jp