]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - source/Plugins/SymbolFile/DWARF/DWARFDebugLine.h
Vendor import of lldb trunk r290819:
[FreeBSD/FreeBSD.git] / source / Plugins / SymbolFile / DWARF / DWARFDebugLine.h
1 //===-- DWARFDebugLine.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 SymbolFileDWARF_DWARFDebugLine_h_
11 #define SymbolFileDWARF_DWARFDebugLine_h_
12
13 #include <map>
14 #include <string>
15 #include <vector>
16
17 #include "lldb/lldb-private.h"
18
19 #include "DWARFDataExtractor.h"
20 #include "DWARFDefines.h"
21
22 class SymbolFileDWARF;
23
24 //----------------------------------------------------------------------
25 // DWARFDebugLine
26 //----------------------------------------------------------------------
27 class DWARFDebugLine {
28 public:
29   //------------------------------------------------------------------
30   // FileNameEntry
31   //------------------------------------------------------------------
32   struct FileNameEntry {
33     FileNameEntry() : name(nullptr), dir_idx(0), mod_time(0), length(0) {}
34
35     const char *name;
36     dw_sleb128_t dir_idx;
37     dw_sleb128_t mod_time;
38     dw_sleb128_t length;
39   };
40
41   //------------------------------------------------------------------
42   // Prologue
43   //------------------------------------------------------------------
44   struct Prologue {
45
46     Prologue()
47         : total_length(0), version(0), prologue_length(0), min_inst_length(0),
48           default_is_stmt(0), line_base(0), line_range(0), opcode_base(0),
49           standard_opcode_lengths(), include_directories(), file_names() {}
50
51     typedef std::shared_ptr<Prologue> shared_ptr;
52
53     uint32_t total_length; // The size in bytes of the statement information for
54                            // this compilation unit (not including the
55                            // total_length field itself).
56     uint16_t
57         version; // Version identifier for the statement information format.
58     uint32_t prologue_length; // The number of bytes following the
59                               // prologue_length field to the beginning of the
60                               // first byte of the statement program itself.
61     uint8_t min_inst_length; // The size in bytes of the smallest target machine
62                              // instruction. Statement program opcodes that
63                              // alter the address register first multiply their
64                              // operands by this value.
65     uint8_t maximum_operations_per_instruction; // New in DWARF4. The maximum
66                                                 // number of individual
67                                                 // operations that may be
68                                                 // encoded in an instruction.
69     uint8_t default_is_stmt; // The initial value of theis_stmtregister.
70     int8_t line_base;    // This parameter affects the meaning of the special
71                          // opcodes. See below.
72     uint8_t line_range;  // This parameter affects the meaning of the special
73                          // opcodes. See below.
74     uint8_t opcode_base; // The number assigned to the first special opcode.
75     std::vector<uint8_t> standard_opcode_lengths;
76     std::vector<const char *> include_directories;
77     std::vector<FileNameEntry> file_names;
78
79     int32_t MaxLineIncrementForSpecialOpcode() const {
80       return line_base + (int8_t)line_range - 1;
81     }
82     bool IsValid() const;
83     //      void Append(BinaryStreamBuf& buff) const;
84     void Dump(lldb_private::Log *log);
85     void Clear() {
86       total_length = version = prologue_length = min_inst_length = line_base =
87           line_range = opcode_base = 0;
88       line_base = 0;
89       standard_opcode_lengths.clear();
90       include_directories.clear();
91       file_names.clear();
92     }
93     bool GetFile(uint32_t file_idx, const char *comp_dir,
94                  lldb_private::FileSpec &file) const;
95   };
96
97   // Standard .debug_line state machine structure
98   struct Row {
99     typedef std::vector<Row> collection;
100     typedef collection::iterator iterator;
101     typedef collection::const_iterator const_iterator;
102
103     Row(bool default_is_stmt = false);
104     virtual ~Row() {}
105     void PostAppend();
106     void Reset(bool default_is_stmt);
107     void Dump(lldb_private::Log *log) const;
108     static void Insert(Row::collection &state_coll, const Row &state);
109     static void Dump(lldb_private::Log *log, const Row::collection &state_coll);
110
111     dw_addr_t address; // The program-counter value corresponding to a machine
112                        // instruction generated by the compiler.
113     uint32_t line; // An unsigned integer indicating a source line number. Lines
114                    // are numbered beginning at 1. The compiler may emit the
115                    // value 0 in cases where an instruction cannot be attributed
116                    // to any source line.
117     uint16_t column; // An unsigned integer indicating a column number within a
118                      // source line. Columns are numbered beginning at 1. The
119                      // value 0 is reserved to indicate that a statement begins
120                      // at the 'left edge' of the line.
121     uint16_t file; // An unsigned integer indicating the identity of the source
122                    // file corresponding to a machine instruction.
123     uint8_t is_stmt : 1, // A boolean indicating that the current instruction is
124                          // the beginning of a statement.
125         basic_block : 1, // A boolean indicating that the current instruction is
126                          // the beginning of a basic block.
127         end_sequence : 1, // A boolean indicating that the current address is
128                           // that of the first byte after the end of a sequence
129                           // of target machine instructions.
130         prologue_end : 1, // A boolean indicating that the current address is
131                           // one (of possibly many) where execution should be
132                           // suspended for an entry breakpoint of a function.
133         epilogue_begin : 1; // A boolean indicating that the current address is
134                             // one (of possibly many) where execution should be
135                             // suspended for an exit breakpoint of a function.
136     uint32_t isa; // An unsigned integer whose value encodes the applicable
137                   // instruction set architecture for the current instruction.
138   };
139
140   //------------------------------------------------------------------
141   // LineTable
142   //------------------------------------------------------------------
143   struct LineTable {
144     typedef std::shared_ptr<LineTable> shared_ptr;
145
146     LineTable() : prologue(), rows() {}
147
148     void AppendRow(const DWARFDebugLine::Row &state);
149     void Clear() {
150       prologue.reset();
151       rows.clear();
152     }
153
154     uint32_t LookupAddress(dw_addr_t address, dw_addr_t cu_high_pc) const;
155     void Dump(lldb_private::Log *log) const;
156
157     Prologue::shared_ptr prologue;
158     Row::collection rows;
159   };
160
161   //------------------------------------------------------------------
162   // State
163   //------------------------------------------------------------------
164   struct State : public Row {
165     typedef void (*Callback)(dw_offset_t offset, const State &state,
166                              void *userData);
167
168     // Special row codes used when calling the callback
169     enum { StartParsingLineTable = 0, DoneParsingLineTable = -1 };
170
171     State(Prologue::shared_ptr &prologue_sp, lldb_private::Log *log,
172           Callback callback, void *userData);
173
174     void AppendRowToMatrix(dw_offset_t offset);
175
176     void Finalize(dw_offset_t offset);
177
178     void Reset();
179
180     Prologue::shared_ptr prologue;
181     lldb_private::Log *log;
182     Callback callback; // Callback function that gets called each time an entry
183                        // is to be added to the matrix
184     void *callbackUserData;
185     int row; // The row number that starts at zero for the prologue, and
186              // increases for each row added to the matrix
187   private:
188     DISALLOW_COPY_AND_ASSIGN(State);
189   };
190
191   static bool DumpOpcodes(
192       lldb_private::Log *log, SymbolFileDWARF *dwarf2Data,
193       dw_offset_t line_offset = DW_INVALID_OFFSET,
194       uint32_t dump_flags = 0); // If line_offset is invalid, dump everything
195   static bool DumpLineTableRows(
196       lldb_private::Log *log, SymbolFileDWARF *dwarf2Data,
197       dw_offset_t line_offset =
198           DW_INVALID_OFFSET); // If line_offset is invalid, dump everything
199   static bool
200   ParseSupportFiles(const lldb::ModuleSP &module_sp,
201                     const lldb_private::DWARFDataExtractor &debug_line_data,
202                     const char *cu_comp_dir, dw_offset_t stmt_list,
203                     lldb_private::FileSpecList &support_files);
204   static bool
205   ParsePrologue(const lldb_private::DWARFDataExtractor &debug_line_data,
206                 lldb::offset_t *offset_ptr, Prologue *prologue);
207   static bool
208   ParseStatementTable(const lldb_private::DWARFDataExtractor &debug_line_data,
209                       lldb::offset_t *offset_ptr, State::Callback callback,
210                       void *userData);
211   static dw_offset_t
212   DumpStatementTable(lldb_private::Log *log,
213                      const lldb_private::DWARFDataExtractor &debug_line_data,
214                      const dw_offset_t line_offset);
215   static dw_offset_t
216   DumpStatementOpcodes(lldb_private::Log *log,
217                        const lldb_private::DWARFDataExtractor &debug_line_data,
218                        const dw_offset_t line_offset, uint32_t flags);
219   static bool
220   ParseStatementTable(const lldb_private::DWARFDataExtractor &debug_line_data,
221                       lldb::offset_t *offset_ptr, LineTable *line_table);
222   static void Parse(const lldb_private::DWARFDataExtractor &debug_line_data,
223                     DWARFDebugLine::State::Callback callback, void *userData);
224   //  static void AppendLineTableData(const DWARFDebugLine::Prologue* prologue,
225   //  const DWARFDebugLine::Row::collection& state_coll, const uint32_t
226   //  addr_size, BinaryStreamBuf &debug_line_data);
227
228   DWARFDebugLine() : m_lineTableMap() {}
229
230   void Parse(const lldb_private::DWARFDataExtractor &debug_line_data);
231   void ParseIfNeeded(const lldb_private::DWARFDataExtractor &debug_line_data);
232   LineTable::shared_ptr GetLineTable(const dw_offset_t offset) const;
233
234 protected:
235   typedef std::map<dw_offset_t, LineTable::shared_ptr> LineTableMap;
236   typedef LineTableMap::iterator LineTableIter;
237   typedef LineTableMap::const_iterator LineTableConstIter;
238
239   LineTableMap m_lineTableMap;
240 };
241
242 #endif // SymbolFileDWARF_DWARFDebugLine_h_