LineTable.h revision 296417
1//===-- LineTable.h ---------------------------------------------*- C++ -*-===//
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#ifndef liblldb_LineTable_h_
11#define liblldb_LineTable_h_
12
13// C Includes
14// C++ Includes
15#include <vector>
16
17// Other libraries and framework includes
18// Project includes
19#include "lldb/lldb-private.h"
20#include "lldb/Symbol/LineEntry.h"
21#include "lldb/Core/ModuleChild.h"
22#include "lldb/Core/Section.h"
23#include "lldb/Core/RangeMap.h"
24
25namespace lldb_private {
26
27//----------------------------------------------------------------------
28/// @class LineSequence LineTable.h "lldb/Symbol/LineTable.h"
29/// @brief An abstract base class used during symbol table creation.
30//----------------------------------------------------------------------
31class LineSequence
32{
33public:
34    LineSequence ();
35
36    virtual
37    ~LineSequence() = default;
38
39    virtual void
40    Clear() = 0;
41
42private:
43    DISALLOW_COPY_AND_ASSIGN (LineSequence);
44};
45
46//----------------------------------------------------------------------
47/// @class LineTable LineTable.h "lldb/Symbol/LineTable.h"
48/// @brief A line table class.
49//----------------------------------------------------------------------
50class LineTable
51{
52public:
53    //------------------------------------------------------------------
54    /// Construct with compile unit.
55    ///
56    /// @param[in] comp_unit
57    ///     The compile unit to which this line table belongs.
58    //------------------------------------------------------------------
59    LineTable (CompileUnit* comp_unit);
60
61    //------------------------------------------------------------------
62    /// Destructor.
63    //------------------------------------------------------------------
64    ~LineTable ();
65
66    //------------------------------------------------------------------
67    /// Adds a new line entry to this line table.
68    ///
69    /// All line entries are maintained in file address order.
70    ///
71    /// @param[in] line_entry
72    ///     A const reference to a new line_entry to add to this line
73    ///     table.
74    ///
75    /// @see Address::DumpStyle
76    //------------------------------------------------------------------
77//  void
78//  AddLineEntry (const LineEntry& line_entry);
79
80    // Called when you can't guarantee the addresses are in increasing order
81    void
82    InsertLineEntry (lldb::addr_t file_addr,
83                     uint32_t line,
84                     uint16_t column,
85                     uint16_t file_idx,
86                     bool is_start_of_statement,
87                     bool is_start_of_basic_block,
88                     bool is_prologue_end,
89                     bool is_epilogue_begin,
90                     bool is_terminal_entry);
91
92    // Used to instantiate the LineSequence helper class
93    LineSequence*
94    CreateLineSequenceContainer ();
95
96    // Append an entry to a caller-provided collection that will later be
97    // inserted in this line table.
98    void
99    AppendLineEntryToSequence (LineSequence* sequence,
100                               lldb::addr_t file_addr,
101                               uint32_t line,
102                               uint16_t column,
103                               uint16_t file_idx,
104                               bool is_start_of_statement,
105                               bool is_start_of_basic_block,
106                               bool is_prologue_end,
107                               bool is_epilogue_begin,
108                               bool is_terminal_entry);
109
110    // Insert a sequence of entries into this line table.
111    void
112    InsertSequence (LineSequence* sequence);
113
114    //------------------------------------------------------------------
115    /// Dump all line entries in this line table to the stream \a s.
116    ///
117    /// @param[in] s
118    ///     The stream to which to dump the object description.
119    ///
120    /// @param[in] style
121    ///     The display style for the address.
122    ///
123    /// @see Address::DumpStyle
124    //------------------------------------------------------------------
125    void
126    Dump (Stream *s, Target *target,
127          Address::DumpStyle style,
128          Address::DumpStyle fallback_style,
129          bool show_line_ranges);
130
131    void
132    GetDescription (Stream *s,
133                    Target *target,
134                    lldb::DescriptionLevel level);
135
136    //------------------------------------------------------------------
137    /// Find a line entry that contains the section offset address \a
138    /// so_addr.
139    ///
140    /// @param[in] so_addr
141    ///     A section offset address object containing the address we
142    ///     are searching for.
143    ///
144    /// @param[out] line_entry
145    ///     A copy of the line entry that was found if \b true is
146    ///     returned, otherwise \a entry is left unmodified.
147    ///
148    /// @param[out] index_ptr
149    ///     A pointer to a 32 bit integer that will get the actual line
150    ///     entry index if it is not nullptr.
151    ///
152    /// @return
153    ///     Returns \b true if \a so_addr is contained in a line entry
154    ///     in this line table, \b false otherwise.
155    //------------------------------------------------------------------
156    bool
157    FindLineEntryByAddress(const Address &so_addr, LineEntry& line_entry, uint32_t *index_ptr = nullptr);
158
159    //------------------------------------------------------------------
160    /// Find a line entry index that has a matching file index and
161    /// source line number.
162    ///
163    /// Finds the next line entry that has a matching \a file_idx and
164    /// source line number \a line starting at the \a start_idx entries
165    /// into the line entry collection.
166    ///
167    /// @param[in] start_idx
168    ///     The number of entries to skip when starting the search.
169    ///
170    /// @param[out] file_idx
171    ///     The file index to search for that should be found prior
172    ///     to calling this function using the following functions:
173    ///     CompileUnit::GetSupportFiles()
174    ///     FileSpecList::FindFileIndex (uint32_t, const FileSpec &) const
175    ///
176    /// @param[in] line
177    ///     The source line to match.
178    ///
179    /// @param[in] exact
180    ///     If true, match only if you find a line entry exactly matching \a line.
181    ///     If false, return the closest line entry greater than \a line.
182    ///
183    /// @param[out] line_entry
184    ///     A reference to a line entry object that will get a copy of
185    ///     the line entry if \b true is returned, otherwise \a
186    ///     line_entry is left untouched.
187    ///
188    /// @return
189    ///     Returns \b true if a matching line entry is found in this
190    ///     line table, \b false otherwise.
191    ///
192    /// @see CompileUnit::GetSupportFiles()
193    /// @see FileSpecList::FindFileIndex (uint32_t, const FileSpec &) const
194    //------------------------------------------------------------------
195    uint32_t
196    FindLineEntryIndexByFileIndex (uint32_t start_idx,
197                                   uint32_t file_idx,
198                                   uint32_t line,
199                                   bool exact,
200                                   LineEntry* line_entry_ptr);
201
202    uint32_t
203    FindLineEntryIndexByFileIndex (uint32_t start_idx,
204                                   const std::vector<uint32_t> &file_indexes,
205                                   uint32_t line,
206                                   bool exact,
207                                   LineEntry* line_entry_ptr);
208
209    size_t
210    FineLineEntriesForFileIndex (uint32_t file_idx,
211                                 bool append,
212                                 SymbolContextList &sc_list);
213
214    //------------------------------------------------------------------
215    /// Get the line entry from the line table at index \a idx.
216    ///
217    /// @param[in] idx
218    ///     An index into the line table entry collection.
219    ///
220    /// @return
221    ///     A valid line entry if \a idx is a valid index, or an invalid
222    ///     line entry if \a idx is not valid.
223    ///
224    /// @see LineTable::GetSize()
225    /// @see LineEntry::IsValid() const
226    //------------------------------------------------------------------
227    bool
228    GetLineEntryAtIndex(uint32_t idx, LineEntry& line_entry);
229
230    //------------------------------------------------------------------
231    /// Gets the size of the line table in number of line table entries.
232    ///
233    /// @return
234    ///     The number of line table entries in this line table.
235    //------------------------------------------------------------------
236    uint32_t
237    GetSize () const;
238
239    typedef lldb_private::RangeArray<lldb::addr_t, lldb::addr_t, 32> FileAddressRanges;
240
241    //------------------------------------------------------------------
242    /// Gets all contiguous file address ranges for the entire line table.
243    ///
244    /// @param[out] file_ranges
245    ///     A collection of file address ranges that will be filled in
246    ///     by this function.
247    ///
248    /// @param[out] append
249    ///     If \b true, then append to \a file_ranges, otherwise clear
250    ///     \a file_ranges prior to adding any ranges.
251    ///
252    /// @return
253    ///     The number of address ranges added to \a file_ranges
254    //------------------------------------------------------------------
255    size_t
256    GetContiguousFileAddressRanges (FileAddressRanges &file_ranges, bool append);
257
258    //------------------------------------------------------------------
259    /// Given a file range link map, relink the current line table
260    /// and return a fixed up line table.
261    ///
262    /// @param[out] file_range_map
263    ///     A collection of file ranges that maps to new file ranges
264    ///     that will be used when linking the line table.
265    ///
266    /// @return
267    ///     A new line table if at least one line table entry was able
268    ///     to be mapped.
269    //------------------------------------------------------------------
270    typedef RangeDataVector<lldb::addr_t, lldb::addr_t, lldb::addr_t> FileRangeMap;
271
272    LineTable *
273    LinkLineTable (const FileRangeMap &file_range_map);
274
275protected:
276    struct Entry
277    {
278        Entry () :
279            file_addr (LLDB_INVALID_ADDRESS),
280            line (0),
281            column (0),
282            file_idx (0),
283            is_start_of_statement (false),
284            is_start_of_basic_block (false),
285            is_prologue_end (false),
286            is_epilogue_begin (false),
287            is_terminal_entry (false)
288        {
289        }
290
291        Entry ( lldb::addr_t _file_addr,
292                uint32_t _line,
293                uint16_t _column,
294                uint16_t _file_idx,
295                bool _is_start_of_statement,
296                bool _is_start_of_basic_block,
297                bool _is_prologue_end,
298                bool _is_epilogue_begin,
299                bool _is_terminal_entry) :
300            file_addr (_file_addr),
301            line (_line),
302            column (_column),
303            file_idx (_file_idx),
304            is_start_of_statement (_is_start_of_statement),
305            is_start_of_basic_block (_is_start_of_basic_block),
306            is_prologue_end (_is_prologue_end),
307            is_epilogue_begin (_is_epilogue_begin),
308            is_terminal_entry (_is_terminal_entry)
309        {
310        }
311
312        int
313        bsearch_compare (const void *key, const void *arrmem);
314
315        void
316        Clear ()
317        {
318            file_addr = LLDB_INVALID_ADDRESS;
319            line = 0;
320            column = 0;
321            file_idx = 0;
322            is_start_of_statement = false;
323            is_start_of_basic_block = false;
324            is_prologue_end = false;
325            is_epilogue_begin = false;
326            is_terminal_entry = false;
327        }
328
329        static int
330        Compare (const Entry& lhs, const Entry& rhs)
331        {
332            // Compare the sections before calling
333            #define SCALAR_COMPARE(a,b) if (a < b) return -1; if (a > b) return +1
334            SCALAR_COMPARE (lhs.file_addr, rhs.file_addr);
335            SCALAR_COMPARE (lhs.line, rhs.line);
336            SCALAR_COMPARE (lhs.column, rhs.column);
337            SCALAR_COMPARE (lhs.is_start_of_statement, rhs.is_start_of_statement);
338            SCALAR_COMPARE (lhs.is_start_of_basic_block, rhs.is_start_of_basic_block);
339            // rhs and lhs reversed on purpose below.
340            SCALAR_COMPARE (rhs.is_prologue_end, lhs.is_prologue_end);
341            SCALAR_COMPARE (lhs.is_epilogue_begin, rhs.is_epilogue_begin);
342            // rhs and lhs reversed on purpose below.
343            SCALAR_COMPARE (rhs.is_terminal_entry, lhs.is_terminal_entry);
344            SCALAR_COMPARE (lhs.file_idx, rhs.file_idx);
345            #undef SCALAR_COMPARE
346            return 0;
347        }
348
349        class LessThanBinaryPredicate
350        {
351        public:
352            LessThanBinaryPredicate(LineTable *line_table);
353            bool operator() (const LineTable::Entry&, const LineTable::Entry&) const;
354
355        protected:
356            LineTable *m_line_table;
357        };
358
359        static bool EntryAddressLessThan (const Entry& lhs, const Entry& rhs)
360        {
361            return lhs.file_addr < rhs.file_addr;
362        }
363
364        //------------------------------------------------------------------
365        // Member variables.
366        //------------------------------------------------------------------
367        lldb::addr_t file_addr;                 ///< The file address for this line entry
368        uint32_t    line;                       ///< The source line number, or zero if there is no line number information.
369        uint16_t    column;                     ///< The column number of the source line, or zero if there is no column information.
370        uint16_t    file_idx:11,                ///< The file index into CompileUnit's file table, or zero if there is no file information.
371                    is_start_of_statement:1,    ///< Indicates this entry is the beginning of a statement.
372                    is_start_of_basic_block:1,  ///< Indicates this entry is the beginning of a basic block.
373                    is_prologue_end:1,          ///< Indicates this entry is one (of possibly many) where execution should be suspended for an entry breakpoint of a function.
374                    is_epilogue_begin:1,        ///< Indicates this entry is one (of possibly many) where execution should be suspended for an exit breakpoint of a function.
375                    is_terminal_entry:1;        ///< Indicates this entry is that of the first byte after the end of a sequence of target machine instructions.
376    };
377
378    struct EntrySearchInfo
379    {
380        LineTable* line_table;
381        lldb_private::Section *a_section;
382        Entry *a_entry;
383    };
384
385    //------------------------------------------------------------------
386    // Types
387    //------------------------------------------------------------------
388    typedef std::vector<lldb_private::Section*> section_collection; ///< The collection type for the sections.
389    typedef std::vector<Entry>                  entry_collection;   ///< The collection type for the line entries.
390    //------------------------------------------------------------------
391    // Member variables.
392    //------------------------------------------------------------------
393    CompileUnit* m_comp_unit;   ///< The compile unit that this line table belongs to.
394    entry_collection m_entries; ///< The collection of line entries in this line table.
395
396    //------------------------------------------------------------------
397    // Helper class
398    //------------------------------------------------------------------
399    class LineSequenceImpl : public LineSequence
400    {
401    public:
402        LineSequenceImpl() = default;
403
404        ~LineSequenceImpl() override = default;
405
406        void
407        Clear() override;
408
409        entry_collection m_entries; ///< The collection of line entries in this sequence.
410    };
411
412    bool
413    ConvertEntryAtIndexToLineEntry (uint32_t idx, LineEntry &line_entry);
414
415private:
416    DISALLOW_COPY_AND_ASSIGN (LineTable);
417};
418
419} // namespace lldb_private
420
421#endif // liblldb_LineTable_h_
422