1 //===-- Block.h -------------------------------------------------*- C++ -*-===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 #ifndef liblldb_Block_h_
11 #define liblldb_Block_h_
17 // Other libraries and framework includes
19 #include "lldb/Core/AddressRange.h"
20 #include "lldb/Core/RangeMap.h"
21 #include "lldb/Core/Stream.h"
22 #include "lldb/Core/UserID.h"
23 #include "lldb/Symbol/CompilerType.h"
24 #include "lldb/Symbol/LineEntry.h"
25 #include "lldb/Symbol/SymbolContext.h"
26 #include "lldb/lldb-private.h"
28 namespace lldb_private {
30 //----------------------------------------------------------------------
31 /// @class Block Block.h "lldb/Symbol/Block.h"
32 /// @brief A class that describes a single lexical block.
34 /// A Function object owns a BlockList object which owns one or more
35 /// Block objects. The BlockList object contains a section offset
36 /// address range, and Block objects contain one or more ranges
37 /// which are offsets into that range. Blocks are can have discontiguous
38 /// ranges within the BlockList address range, and each block can
39 /// contain child blocks each with their own sets of ranges.
41 /// Each block has a variable list that represents local, argument, and
42 /// static variables that are scoped to the block.
44 /// Inlined functions are represented by attaching a
45 /// InlineFunctionInfo shared pointer object to a block. Inlined
46 /// functions are represented as named blocks.
47 //----------------------------------------------------------------------
48 class Block : public UserID, public SymbolContextScope {
50 typedef RangeArray<uint32_t, uint32_t, 1> RangeList;
51 typedef RangeList::Entry Range;
53 //------------------------------------------------------------------
54 /// Construct with a User ID \a uid, \a depth.
56 /// Initialize this block with the specified UID \a uid. The
57 /// \a depth in the \a block_list is used to represent the parent,
58 /// sibling, and child block information and also allows for partial
59 /// parsing at the block level.
62 /// The UID for a given block. This value is given by the
63 /// SymbolFile plug-in and can be any value that helps the
64 /// SymbolFile plug-in to match this block back to the debug
65 /// information data that it parses for further or more in
66 /// depth parsing. Common values would be the index into a
67 /// table, or an offset into the debug information.
70 /// The integer depth of this block in the block list hierarchy.
72 /// @param[in] block_list
73 /// The block list that this object belongs to.
76 //------------------------------------------------------------------
77 Block(lldb::user_id_t uid);
79 //------------------------------------------------------------------
81 //------------------------------------------------------------------
84 //------------------------------------------------------------------
85 /// Add a child to this object.
87 /// @param[in] child_block_sp
88 /// A shared pointer to a child block that will get added to
90 //------------------------------------------------------------------
91 void AddChild(const lldb::BlockSP &child_block_sp);
93 //------------------------------------------------------------------
94 /// Add a new offset range to this block.
96 /// @param[in] start_offset
97 /// An offset into this Function's address range that
98 /// describes the start address of a range for this block.
100 /// @param[in] end_offset
101 /// An offset into this Function's address range that
102 /// describes the end address of a range for this block.
103 //------------------------------------------------------------------
104 void AddRange(const Range &range);
106 void FinalizeRanges();
108 //------------------------------------------------------------------
109 /// @copydoc SymbolContextScope::CalculateSymbolContext(SymbolContext*)
111 /// @see SymbolContextScope
112 //------------------------------------------------------------------
113 void CalculateSymbolContext(SymbolContext *sc) override;
115 lldb::ModuleSP CalculateSymbolContextModule() override;
117 CompileUnit *CalculateSymbolContextCompileUnit() override;
119 Function *CalculateSymbolContextFunction() override;
121 Block *CalculateSymbolContextBlock() override;
123 //------------------------------------------------------------------
124 /// Check if an offset is in one of the block offset ranges.
126 /// @param[in] range_offset
127 /// An offset into the Function's address range.
130 /// Returns \b true if \a range_offset falls in one of this
131 /// block's ranges, \b false otherwise.
132 //------------------------------------------------------------------
133 bool Contains(lldb::addr_t range_offset) const;
135 //------------------------------------------------------------------
136 /// Check if a offset range is in one of the block offset ranges.
139 /// An offset range into the Function's address range.
142 /// Returns \b true if \a range falls in one of this
143 /// block's ranges, \b false otherwise.
144 //------------------------------------------------------------------
145 bool Contains(const Range &range) const;
147 //------------------------------------------------------------------
148 /// Check if this object contains "block" as a child block at any
152 /// A potential child block.
155 /// Returns \b true if \a block is a child of this block, \b
157 //------------------------------------------------------------------
158 bool Contains(const Block *block) const;
160 //------------------------------------------------------------------
161 /// Dump the block contents.
164 /// The stream to which to dump the object description.
166 /// @param[in] base_addr
167 /// The resolved start address of the Function's address
168 /// range. This should be resolved as the file or load address
169 /// prior to passing the value into this function for dumping.
172 /// Limit the number of levels deep that this function should
173 /// print as this block can contain child blocks. Specify
174 /// INT_MAX to dump all child blocks.
176 /// @param[in] show_context
177 /// If \b true, variables will dump their context information.
178 //------------------------------------------------------------------
179 void Dump(Stream *s, lldb::addr_t base_addr, int32_t depth,
180 bool show_context) const;
182 //------------------------------------------------------------------
183 /// @copydoc SymbolContextScope::DumpSymbolContext(Stream*)
185 /// @see SymbolContextScope
186 //------------------------------------------------------------------
187 void DumpSymbolContext(Stream *s) override;
189 void DumpAddressRanges(Stream *s, lldb::addr_t base_addr);
191 void GetDescription(Stream *s, Function *function,
192 lldb::DescriptionLevel level, Target *target) const;
194 //------------------------------------------------------------------
195 /// Get the parent block.
198 /// The parent block pointer, or nullptr if this block has no
200 //------------------------------------------------------------------
201 Block *GetParent() const;
203 //------------------------------------------------------------------
204 /// Get the inlined block that contains this block.
207 /// If this block contains inlined function info, it will return
208 /// this block, else parent blocks will be searched to see if
209 /// any contain this block. nullptr will be returned if this block
210 /// nor any parent blocks are inlined function blocks.
211 //------------------------------------------------------------------
212 Block *GetContainingInlinedBlock();
214 //------------------------------------------------------------------
215 /// Get the inlined parent block for this block.
218 /// The parent block pointer, or nullptr if this block has no
220 //------------------------------------------------------------------
221 Block *GetInlinedParent();
223 //------------------------------------------------------------------
224 /// Get the sibling block for this block.
227 /// The sibling block pointer, or nullptr if this block has no
229 //------------------------------------------------------------------
230 Block *GetSibling() const;
232 //------------------------------------------------------------------
233 /// Get the first child block.
236 /// The first child block pointer, or nullptr if this block has no
238 //------------------------------------------------------------------
239 Block *GetFirstChild() const {
240 return (m_children.empty() ? nullptr : m_children.front().get());
243 //------------------------------------------------------------------
244 /// Get the variable list for this block only.
246 /// @param[in] can_create
247 /// If \b true, the variables can be parsed if they already
248 /// haven't been, else the current state of the block will be
252 /// A variable list shared pointer that contains all variables
254 //------------------------------------------------------------------
255 lldb::VariableListSP GetBlockVariableList(bool can_create);
257 //------------------------------------------------------------------
258 /// Get the variable list for this block and optionally all child
259 /// blocks if \a get_child_variables is \b true.
261 /// @param[in] get_child_variables
262 /// If \b true, all variables from all child blocks will be
263 /// added to the variable list.
265 /// @param[in] can_create
266 /// If \b true, the variables can be parsed if they already
267 /// haven't been, else the current state of the block will be
268 /// returned. Passing \b true for this parameter can be used
269 /// to see the current state of what has been parsed up to this
272 /// @param[in] add_inline_child_block_variables
273 /// If this is \b false, no child variables of child blocks
274 /// that are inlined functions will be gotten. If \b true then
275 /// all child variables will be added regardless of whether they
276 /// come from inlined functions or not.
279 /// A variable list shared pointer that contains all variables
281 //------------------------------------------------------------------
282 uint32_t AppendBlockVariables(bool can_create, bool get_child_block_variables,
283 bool stop_if_child_block_is_inlined_function,
284 const std::function<bool(Variable *)> &filter,
285 VariableList *variable_list);
287 //------------------------------------------------------------------
288 /// Appends the variables from this block, and optionally from all
289 /// parent blocks, to \a variable_list.
291 /// @param[in] can_create
292 /// If \b true, the variables can be parsed if they already
293 /// haven't been, else the current state of the block will be
294 /// returned. Passing \b true for this parameter can be used
295 /// to see the current state of what has been parsed up to this
298 /// @param[in] get_parent_variables
299 /// If \b true, all variables from all parent blocks will be
300 /// added to the variable list.
302 /// @param[in] stop_if_block_is_inlined_function
303 /// If \b true, all variables from all parent blocks will be
304 /// added to the variable list until there are no parent blocks
305 /// or the parent block has inlined function info.
307 /// @param[in,out] variable_list
308 /// All variables in this block, and optionally all parent
309 /// blocks will be added to this list.
312 /// The number of variable that were appended to \a
314 //------------------------------------------------------------------
315 uint32_t AppendVariables(bool can_create, bool get_parent_variables,
316 bool stop_if_block_is_inlined_function,
317 const std::function<bool(Variable *)> &filter,
318 VariableList *variable_list);
320 //------------------------------------------------------------------
321 /// Get const accessor for any inlined function information.
324 /// A const pointer to any inlined function information, or nullptr
325 /// if this is a regular block.
326 //------------------------------------------------------------------
327 const InlineFunctionInfo *GetInlinedFunctionInfo() const {
328 return m_inlineInfoSP.get();
331 CompilerDeclContext GetDeclContext();
333 //------------------------------------------------------------------
334 /// Get the memory cost of this object.
336 /// Returns the cost of this object plus any owned objects from the
337 /// ranges, variables, and inline function information.
340 /// The number of bytes that this object occupies in memory.
341 //------------------------------------------------------------------
342 size_t MemorySize() const;
344 //------------------------------------------------------------------
345 /// Set accessor for any inlined function information.
348 /// The method name for the inlined function. This value should
351 /// @param[in] mangled
352 /// The mangled method name for the inlined function. This can
353 /// be nullptr if there is no mangled name for an inlined function
354 /// or if the name is the same as \a name.
356 /// @param[in] decl_ptr
357 /// A optional pointer to declaration information for the
358 /// inlined function information. This value can be nullptr to
359 /// indicate that no declaration information is available.
361 /// @param[in] call_decl_ptr
362 /// Optional calling location declaration information that
363 /// describes from where this inlined function was called.
364 //------------------------------------------------------------------
365 void SetInlinedFunctionInfo(const char *name, const char *mangled,
366 const Declaration *decl_ptr,
367 const Declaration *call_decl_ptr);
369 void SetParentScope(SymbolContextScope *parent_scope) {
370 m_parent_scope = parent_scope;
373 //------------------------------------------------------------------
374 /// Set accessor for the variable list.
376 /// Called by the SymbolFile plug-ins after they have parsed the
377 /// variable lists and are ready to hand ownership of the list over
380 /// @param[in] variable_list_sp
381 /// A shared pointer to a VariableList.
382 //------------------------------------------------------------------
383 void SetVariableList(lldb::VariableListSP &variable_list_sp) {
384 m_variable_list_sp = variable_list_sp;
387 bool BlockInfoHasBeenParsed() const { return m_parsed_block_info; }
389 void SetBlockInfoHasBeenParsed(bool b, bool set_children);
391 Block *FindBlockByID(lldb::user_id_t block_id);
393 size_t GetNumRanges() const { return m_ranges.GetSize(); }
395 bool GetRangeContainingOffset(const lldb::addr_t offset, Range &range);
397 bool GetRangeContainingAddress(const Address &addr, AddressRange &range);
399 bool GetRangeContainingLoadAddress(lldb::addr_t load_addr, Target &target,
400 AddressRange &range);
402 uint32_t GetRangeIndexContainingAddress(const Address &addr);
404 //------------------------------------------------------------------
405 // Since blocks might have multiple discontiguous address ranges,
406 // we need to be able to get at any of the address ranges in a block.
407 //------------------------------------------------------------------
408 bool GetRangeAtIndex(uint32_t range_idx, AddressRange &range);
410 bool GetStartAddress(Address &addr);
412 void SetDidParseVariables(bool b, bool set_children);
415 typedef std::vector<lldb::BlockSP> collection;
416 //------------------------------------------------------------------
418 //------------------------------------------------------------------
419 SymbolContextScope *m_parent_scope;
420 collection m_children;
422 lldb::InlineFunctionInfoSP m_inlineInfoSP; ///< Inlined function information.
423 lldb::VariableListSP m_variable_list_sp; ///< The variable list for all local,
424 ///static and parameter variables
425 ///scoped to this block.
426 bool m_parsed_block_info : 1, ///< Set to true if this block and it's children
427 ///have all been parsed
428 m_parsed_block_variables : 1, m_parsed_child_blocks : 1;
430 // A parent of child blocks can be asked to find a sibling block given
431 // one of its child blocks
432 Block *GetSiblingForChild(const Block *child_block) const;
435 DISALLOW_COPY_AND_ASSIGN(Block);
438 } // namespace lldb_private
440 #endif // liblldb_Block_h_