1//===-- SymbolContext.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
9#ifndef LLDB_SYMBOL_SYMBOLCONTEXT_H
10#define LLDB_SYMBOL_SYMBOLCONTEXT_H
11
12#include <memory>
13#include <string>
14#include <vector>
15
16#include "lldb/Core/Address.h"
17#include "lldb/Core/Mangled.h"
18#include "lldb/Symbol/LineEntry.h"
19#include "lldb/Utility/Iterable.h"
20#include "lldb/lldb-private.h"
21
22namespace lldb_private {
23
24class SymbolContextScope;
25
26/// \class SymbolContext SymbolContext.h "lldb/Symbol/SymbolContext.h" Defines
27/// a symbol context baton that can be handed other debug core functions.
28///
29/// Many debugger functions require a context when doing lookups. This class
30/// provides a common structure that can be used as the result of a query that
31/// can contain a single result. Examples of such queries include
32/// \li Looking up a load address.
33class SymbolContext {
34public:
35 /// Default constructor.
36 ///
37 /// Initialize all pointer members to nullptr and all struct members to
38 /// their default state.
39 SymbolContext();
40
41 /// Construct with an object that knows how to reconstruct its symbol
42 /// context.
43 ///
44 /// \param[in] sc_scope
45 /// A symbol context scope object that knows how to reconstruct
46 /// it's context.
47 explicit SymbolContext(SymbolContextScope *sc_scope);
48
49 /// Construct with module, and optional compile unit, function, block, line
50 /// table, line entry and symbol.
51 ///
52 /// Initialize all pointer to the specified values.
53 ///
54 /// \param[in] module_sp
55 /// A Module pointer to the module for this context.
56 ///
57 /// \param[in] comp_unit
58 /// A CompileUnit pointer to the compile unit for this context.
59 ///
60 /// \param[in] function
61 /// A Function pointer to the function for this context.
62 ///
63 /// \param[in] block
64 /// A Block pointer to the deepest block for this context.
65 ///
66 /// \param[in] line_entry
67 /// A LineEntry pointer to the line entry for this context.
68 ///
69 /// \param[in] symbol
70 /// A Symbol pointer to the symbol for this context.
71 explicit SymbolContext(const lldb::TargetSP &target_sp,
72 const lldb::ModuleSP &module_sp,
73 CompileUnit *comp_unit = nullptr,
74 Function *function = nullptr, Block *block = nullptr,
75 LineEntry *line_entry = nullptr,
76 Symbol *symbol = nullptr);
77
78 // This version sets the target to a NULL TargetSP if you don't know it.
79 explicit SymbolContext(const lldb::ModuleSP &module_sp,
80 CompileUnit *comp_unit = nullptr,
81 Function *function = nullptr, Block *block = nullptr,
82 LineEntry *line_entry = nullptr,
83 Symbol *symbol = nullptr);
84
85 ~SymbolContext();
86
87 /// Clear the object's state.
88 ///
89 /// Resets all pointer members to nullptr, and clears any class objects to
90 /// their default state.
91 void Clear(bool clear_target);
92
93 /// Dump a description of this object to a Stream.
94 ///
95 /// Dump a description of the contents of this object to the supplied stream
96 /// \a s.
97 ///
98 /// \param[in] s
99 /// The stream to which to dump the object description.
100 void Dump(Stream *s, Target *target) const;
101
102 /// Dump the stop context in this object to a Stream.
103 ///
104 /// Dump the best description of this object to the stream. The information
105 /// displayed depends on the amount and quality of the information in this
106 /// context. If a module, function, file and line number are available, they
107 /// will be dumped. If only a module and function or symbol name with offset
108 /// is available, that will be output. Else just the address at which the
109 /// target was stopped will be displayed.
110 ///
111 /// \param[in] s
112 /// The stream to which to dump the object description.
113 ///
114 /// \param[in] so_addr
115 /// The resolved section offset address.
116 ///
117 /// \param[in] show_fullpaths
118 /// When printing file paths (with the Module), whether the
119 /// base name of the Module should be printed or the full path.
120 ///
121 /// \param[in] show_module
122 /// Whether the module name should be printed followed by a
123 /// grave accent "`" character.
124 ///
125 /// \param[in] show_inlined_frames
126 /// If a given pc is in inlined function(s), whether the inlined
127 /// functions should be printed on separate lines in addition to
128 /// the concrete function containing the pc.
129 ///
130 /// \param[in] show_function_arguments
131 /// If false, this method will try to elide the function argument
132 /// types when printing the function name. This may be ambiguous
133 /// for languages that have function overloading - but it may
134 /// make the "function name" too long to include all the argument
135 /// types.
136 ///
137 /// \param[in] show_function_name
138 /// Normally this should be true - the function/symbol name should
139 /// be printed. In disassembly formatting, where we want a format
140 /// like "<*+36>", this should be false and "*" will be printed
141 /// instead.
142 ///
143 /// \param[in] show_inline_callsite_line_info
144 /// When processing an inline block, the line info of the callsite
145 /// is dumped if this flag is \b true, otherwise the line info
146 /// of the actual inlined function is dumped.
147 ///
148 /// \return
149 /// \b true if some text was dumped, \b false otherwise.
150 bool DumpStopContext(Stream *s, ExecutionContextScope *exe_scope,
151 const Address &so_addr, bool show_fullpaths,
152 bool show_module, bool show_inlined_frames,
153 bool show_function_arguments,
154 bool show_function_name) const;
155
156 /// Get the address range contained within a symbol context.
157 ///
158 /// Address range priority is as follows:
159 /// - line_entry address range if line_entry is valid and
160 /// eSymbolContextLineEntry is set in \a scope
161 /// - block address range if block is not nullptr and eSymbolContextBlock
162 /// is set in \a scope
163 /// - function address range if function is not nullptr and
164 /// eSymbolContextFunction is set in \a scope
165 /// - symbol address range if symbol is not nullptr and
166 /// eSymbolContextSymbol is set in \a scope
167 ///
168 /// \param[in] scope
169 /// A mask of symbol context bits telling this function which
170 /// address ranges it can use when trying to extract one from
171 /// the valid (non-nullptr) symbol context classes.
172 ///
173 /// \param[in] range_idx
174 /// The address range index to grab. Since many functions and
175 /// blocks are not always contiguous, they may have more than
176 /// one address range.
177 ///
178 /// \param[in] use_inline_block_range
179 /// If \a scope has the eSymbolContextBlock bit set, and there
180 /// is a valid block in the symbol context, return the block
181 /// address range for the containing inline function block, not
182 /// the deepest most block. This allows us to extract information
183 /// for the address range of the inlined function block, not
184 /// the deepest lexical block.
185 ///
186 /// \param[out] range
187 /// An address range object that will be filled in if \b true
188 /// is returned.
189 ///
190 /// \return
191 /// \b True if this symbol context contains items that describe
192 /// an address range, \b false otherwise.
193 bool GetAddressRange(uint32_t scope, uint32_t range_idx,
194 bool use_inline_block_range, AddressRange &range) const;
195
196 bool GetAddressRangeFromHereToEndLine(uint32_t end_line, AddressRange &range,
197 Status &error);
198
199 /// Find the best global data symbol visible from this context.
200 ///
201 /// Symbol priority is:
202 /// - extern symbol in the current module if there is one
203 /// - non-extern symbol in the current module if there is one
204 /// - extern symbol in the target
205 /// - non-extern symbol in the target
206 /// It is an error if the highest-priority result is ambiguous.
207 ///
208 /// \param[in] name
209 /// The name of the symbol to search for.
210 ///
211 /// \param[out] error
212 /// An error that will be populated with a message if there was an
213 /// ambiguous result. The error will not be populated if no result
214 /// was found.
215 ///
216 /// \return
217 /// The symbol that was found, or \b nullptr if none was found.
218 const Symbol *FindBestGlobalDataSymbol(ConstString name, Status &error);
219
220 void GetDescription(Stream *s, lldb::DescriptionLevel level,
221 Target *target) const;
222
223 uint32_t GetResolvedMask() const;
224
225 lldb::LanguageType GetLanguage() const;
226
227 /// Find a block that defines the function represented by this symbol
228 /// context.
229 ///
230 /// If this symbol context points to a block that is an inlined function, or
231 /// is contained within an inlined function, the block that defines the
232 /// inlined function is returned.
233 ///
234 /// If this symbol context has no block in it, or the block is not itself an
235 /// inlined function block or contained within one, we return the top level
236 /// function block.
237 ///
238 /// This is a handy function to call when you want to get the block whose
239 /// variable list will include the arguments for the function that is
240 /// represented by this symbol context (whether the function is an inline
241 /// function or not).
242 ///
243 /// \return
244 /// The block object pointer that defines the function that is
245 /// represented by this symbol context object, nullptr otherwise.
246 Block *GetFunctionBlock();
247
248 /// If this symbol context represents a function that is a method, return
249 /// true and provide information about the method.
250 ///
251 /// \param[out] language
252 /// If \b true is returned, the language for the method.
253 ///
254 /// \param[out] is_instance_method
255 /// If \b true is returned, \b true if this is a instance method,
256 /// \b false if this is a static/class function.
257 ///
258 /// \param[out] language_object_name
259 /// If \b true is returned, the name of the artificial variable
260 /// for the language ("this" for C++, "self" for ObjC).
261 ///
262 /// \return
263 /// \b True if this symbol context represents a function that
264 /// is a method of a class, \b false otherwise.
265 bool GetFunctionMethodInfo(lldb::LanguageType &language,
266 bool &is_instance_method,
267 ConstString &language_object_name);
268
269 /// Sorts the types in TypeMap according to SymbolContext to TypeList
270 ///
271 void SortTypeList(TypeMap &type_map, TypeList &type_list) const;
272
273 /// Find a name of the innermost function for the symbol context.
274 ///
275 /// For instance, if the symbol context contains an inlined block, it will
276 /// return the inlined function name.
277 ///
278 /// \return
279 /// The name of the function represented by this symbol context.
280 ConstString GetFunctionName(
281 Mangled::NamePreference preference = Mangled::ePreferDemangled) const;
282
283 /// Get the line entry that corresponds to the function.
284 ///
285 /// If the symbol context contains an inlined block, the line entry for the
286 /// start address of the inlined function will be returned, otherwise the
287 /// line entry for the start address of the function will be returned. This
288 /// can be used after doing a Module::FindFunctions(...) or
289 /// ModuleList::FindFunctions(...) call in order to get the correct line
290 /// table information for the symbol context. it will return the inlined
291 /// function name.
292 LineEntry GetFunctionStartLineEntry() const;
293
294 /// Find the block containing the inlined block that contains this block.
295 ///
296 /// For instance, if the symbol context contains an inlined block, it will
297 /// return the inlined function name.
298 ///
299 /// \param[in] curr_frame_pc
300 /// The address within the block of this object.
301 ///
302 /// \param[out] next_frame_sc
303 /// A new symbol context that does what the title says it does.
304 ///
305 /// \param[out] inlined_frame_addr
306 /// This is what you should report as the PC in \a next_frame_sc.
307 ///
308 /// \return
309 /// \b true if this SymbolContext specifies a block contained in an
310 /// inlined block. If this returns \b true, \a next_frame_sc and
311 /// \a inlined_frame_addr will be filled in correctly.
312 bool GetParentOfInlinedScope(const Address &curr_frame_pc,
313 SymbolContext &next_frame_sc,
314 Address &inlined_frame_addr) const;
315
316 // Member variables
317 lldb::TargetSP target_sp; ///< The Target for a given query
318 lldb::ModuleSP module_sp; ///< The Module for a given query
319 CompileUnit *comp_unit; ///< The CompileUnit for a given query
320 Function *function; ///< The Function for a given query
321 Block *block; ///< The Block for a given query
322 LineEntry line_entry; ///< The LineEntry for a given query
323 Symbol *symbol; ///< The Symbol for a given query
324 Variable *variable; ///< The global variable matching the given query
325};
326
327class SymbolContextSpecifier {
328public:
329 enum SpecificationType {
330 eNothingSpecified = 0,
331 eModuleSpecified = 1 << 0,
332 eFileSpecified = 1 << 1,
333 eLineStartSpecified = 1 << 2,
334 eLineEndSpecified = 1 << 3,
335 eFunctionSpecified = 1 << 4,
336 eClassOrNamespaceSpecified = 1 << 5,
337 eAddressRangeSpecified = 1 << 6
338 };
339
340 // This one produces a specifier that matches everything...
341 SymbolContextSpecifier(const lldb::TargetSP &target_sp);
342
343 ~SymbolContextSpecifier();
344
345 bool AddSpecification(const char *spec_string, SpecificationType type);
346
347 bool AddLineSpecification(uint32_t line_no, SpecificationType type);
348
349 void Clear();
350
351 bool SymbolContextMatches(const SymbolContext &sc);
352
353 bool AddressMatches(lldb::addr_t addr);
354
355 void GetDescription(Stream *s, lldb::DescriptionLevel level) const;
356
357private:
358 lldb::TargetSP m_target_sp;
359 std::string m_module_spec;
360 lldb::ModuleSP m_module_sp;
361 std::unique_ptr<FileSpec> m_file_spec_up;
362 size_t m_start_line;
363 size_t m_end_line;
364 std::string m_function_spec;
365 std::string m_class_name;
366 std::unique_ptr<AddressRange> m_address_range_up;
367 uint32_t m_type; // Or'ed bits from SpecificationType
368};
369
370/// \class SymbolContextList SymbolContext.h "lldb/Symbol/SymbolContext.h"
371/// Defines a list of symbol context objects.
372///
373/// This class provides a common structure that can be used to contain the
374/// result of a query that can contain a multiple results. Examples of such
375/// queries include:
376/// \li Looking up a function by name.
377/// \li Finding all addresses for a specified file and line number.
378class SymbolContextList {
379public:
380 /// Default constructor.
381 ///
382 /// Initialize with an empty list.
383 SymbolContextList();
384
385 /// Destructor.
386 ~SymbolContextList();
387
388 /// Append a new symbol context to the list.
389 ///
390 /// \param[in] sc
391 /// A symbol context to append to the list.
392 void Append(const SymbolContext &sc);
393
394 void Append(const SymbolContextList &sc_list);
395
396 bool AppendIfUnique(const SymbolContext &sc, bool merge_symbol_into_function);
397
398 uint32_t AppendIfUnique(const SymbolContextList &sc_list,
399 bool merge_symbol_into_function);
400
401 /// Clear the object's state.
402 ///
403 /// Clears the symbol context list.
404 void Clear();
405
406 /// Dump a description of this object to a Stream.
407 ///
408 /// Dump a description of the contents of each symbol context in the list to
409 /// the supplied stream \a s.
410 ///
411 /// \param[in] s
412 /// The stream to which to dump the object description.
413 void Dump(Stream *s, Target *target) const;
414
415 /// Get accessor for a symbol context at index \a idx.
416 ///
417 /// Dump a description of the contents of each symbol context in the list to
418 /// the supplied stream \a s.
419 ///
420 /// \param[in] idx
421 /// The zero based index into the symbol context list.
422 ///
423 /// \param[out] sc
424 /// A reference to the symbol context to fill in.
425 ///
426 /// \return
427 /// Returns \b true if \a idx was a valid index into this
428 /// symbol context list and \a sc was filled in, \b false
429 /// otherwise.
430 bool GetContextAtIndex(size_t idx, SymbolContext &sc) const;
431
432 /// Direct reference accessor for a symbol context at index \a idx.
433 ///
434 /// The index \a idx must be a valid index, no error checking will be done
435 /// to ensure that it is valid.
436 ///
437 /// \param[in] idx
438 /// The zero based index into the symbol context list.
439 ///
440 /// \return
441 /// A const reference to the symbol context to fill in.
442 SymbolContext &operator[](size_t idx) { return m_symbol_contexts[idx]; }
443
444 const SymbolContext &operator[](size_t idx) const {
445 return m_symbol_contexts[idx];
446 }
447
448 bool RemoveContextAtIndex(size_t idx);
449
450 /// Get accessor for a symbol context list size.
451 ///
452 /// \return
453 /// Returns the number of symbol context objects in the list.
454 uint32_t GetSize() const;
455
456 bool IsEmpty() const;
457
458 uint32_t NumLineEntriesWithLine(uint32_t line) const;
459
460 void GetDescription(Stream *s, lldb::DescriptionLevel level,
461 Target *target) const;
462
463protected:
464 typedef std::vector<SymbolContext>
465 collection; ///< The collection type for the list.
466
467 // Member variables.
468 collection m_symbol_contexts; ///< The list of symbol contexts.
469
470public:
471 typedef AdaptedIterable<collection, SymbolContext, vector_adapter>
472 SymbolContextIterable;
473 SymbolContextIterable SymbolContexts() {
474 return SymbolContextIterable(m_symbol_contexts);
475 }
476};
477
478bool operator==(const SymbolContext &lhs, const SymbolContext &rhs);
479bool operator!=(const SymbolContext &lhs, const SymbolContext &rhs);
480
481bool operator==(const SymbolContextList &lhs, const SymbolContextList &rhs);
482bool operator!=(const SymbolContextList &lhs, const SymbolContextList &rhs);
483
484} // namespace lldb_private
485
486#endif // LLDB_SYMBOL_SYMBOLCONTEXT_H
487