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 22 namespace lldb_private { 23 24 class 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. 33 class SymbolContext { 34 public: 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, bool show_function_name, 154 bool show_inline_callsite_line_info = true) 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 327 class SymbolContextSpecifier { 328 public: 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 357 private: 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. 378 class SymbolContextList { 379 public: 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 463 protected: 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 470 public: 471 typedef AdaptedIterable<collection, SymbolContext, vector_adapter> 472 SymbolContextIterable; SymbolContexts()473 SymbolContextIterable SymbolContexts() { 474 return SymbolContextIterable(m_symbol_contexts); 475 } 476 }; 477 478 bool operator==(const SymbolContext &lhs, const SymbolContext &rhs); 479 bool operator!=(const SymbolContext &lhs, const SymbolContext &rhs); 480 481 bool operator==(const SymbolContextList &lhs, const SymbolContextList &rhs); 482 bool operator!=(const SymbolContextList &lhs, const SymbolContextList &rhs); 483 484 } // namespace lldb_private 485 486 #endif // LLDB_SYMBOL_SYMBOLCONTEXT_H 487