diff options
Diffstat (limited to 'lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugLine.h')
-rw-r--r-- | lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugLine.h | 225 |
1 files changed, 225 insertions, 0 deletions
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugLine.h b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugLine.h new file mode 100644 index 00000000000..57b2f159661 --- /dev/null +++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugLine.h @@ -0,0 +1,225 @@ +//===-- DWARFDebugLine.h ----------------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#ifndef liblldb_DWARFDebugLine_h_ +#define liblldb_DWARFDebugLine_h_ + +#include <map> +#include <vector> +#include <string> + +#include "lldb/lldb-private.h" + +#include "DWARFDefines.h" + +class SymbolFileDWARF; +class DWARFDebugInfoEntry; + +//---------------------------------------------------------------------- +// DWARFDebugLine +//---------------------------------------------------------------------- +class DWARFDebugLine +{ +public: + //------------------------------------------------------------------ + // FileNameEntry + //------------------------------------------------------------------ + struct FileNameEntry + { + FileNameEntry() : + name(), + dir_idx(0), + mod_time(0), + length(0) + { + } + + std::string name; + dw_sleb128_t dir_idx; + dw_sleb128_t mod_time; + dw_sleb128_t length; + + }; + + //------------------------------------------------------------------ + // Prologue + //------------------------------------------------------------------ + struct Prologue + { + + Prologue() : + total_length(0), + version(0), + prologue_length(0), + min_inst_length(0), + default_is_stmt(0), + line_base(0), + line_range(0), + opcode_base(0), + standard_opcode_lengths(), + include_directories(), + file_names() + { + } + + typedef lldb::SharedPtr<Prologue>::Type shared_ptr; + + uint32_t total_length; // The size in bytes of the statement information for this compilation unit (not including the total_length field itself). + uint16_t version; // Version identifier for the statement information format. + uint32_t prologue_length;// The number of bytes following the prologue_length field to the beginning of the first byte of the statement program itself. + uint8_t min_inst_length;// The size in bytes of the smallest target machine instruction. Statement program opcodes that alter the address register first multiply their operands by this value. + uint8_t default_is_stmt;// The initial value of theis_stmtregister. + int8_t line_base; // This parameter affects the meaning of the special opcodes. See below. + uint8_t line_range; // This parameter affects the meaning of the special opcodes. See below. + uint8_t opcode_base; // The number assigned to the first special opcode. + std::vector<uint8_t> standard_opcode_lengths; + std::vector<std::string> include_directories; + std::vector<FileNameEntry> file_names; + + // Length of the prologue in bytes + uint32_t Length() const { return prologue_length + sizeof(total_length) + sizeof(version) + sizeof(prologue_length); } + // Length of the line table data in bytes (not including the prologue) + uint32_t StatementTableLength() const { return total_length + sizeof(total_length) - Length(); } + int32_t MaxLineIncrementForSpecialOpcode() const { return line_base + (int8_t)line_range - 1; }; + bool IsValid() const; +// void Append(BinaryStreamBuf& buff) const; + void Dump (lldb_private::Log *log); + void Clear() + { + total_length = version = prologue_length = min_inst_length = line_base = line_range = opcode_base = 0; + line_base = 0; + standard_opcode_lengths.clear(); + include_directories.clear(); + file_names.clear(); + } + bool GetFile(uint32_t file_idx, std::string& file, std::string& dir) const; + + }; + + // Standard .debug_line state machine structure + struct Row + { + typedef std::vector<Row> collection; + typedef collection::iterator iterator; + typedef collection::const_iterator const_iterator; + + Row(bool default_is_stmt = false); + virtual ~Row() {} + void PostAppend (); + void Reset(bool default_is_stmt); + void Dump(lldb_private::Log *log) const; + static void Insert(Row::collection& state_coll, const Row& state); + static void Dump(lldb_private::Log *log, const Row::collection& state_coll); + + dw_addr_t address; // The program-counter value corresponding to a machine instruction generated by the compiler. + uint32_t line; // An unsigned integer indicating a source line number. Lines are numbered beginning at 1. The compiler may emit the value 0 in cases where an instruction cannot be attributed to any source line. + uint16_t column; // An unsigned integer indicating a column number within a source line. Columns are numbered beginning at 1. The value 0 is reserved to indicate that a statement begins at the ‘‘left edge’’ of the line. + uint16_t file; // An unsigned integer indicating the identity of the source file corresponding to a machine instruction. + uint8_t is_stmt:1, // A boolean indicating that the current instruction is the beginning of a statement. + basic_block:1, // A boolean indicating that the current instruction is the beginning of a basic block. + end_sequence:1, // A boolean indicating that the current address is that of the first byte after the end of a sequence of target machine instructions. + prologue_end:1, // A boolean indicating that the current address is one (of possibly many) where execution should be suspended for an entry breakpoint of a function. + epilogue_begin:1;// A boolean indicating that the current address is one (of possibly many) where execution should be suspended for an exit breakpoint of a function. + uint32_t isa; // An unsigned integer whose value encodes the applicable instruction set architecture for the current instruction. + }; + + + //------------------------------------------------------------------ + // LineTable + //------------------------------------------------------------------ + struct LineTable + { + typedef lldb::SharedPtr<LineTable>::Type shared_ptr; + + LineTable() : + prologue(), + rows() + { + } + + void AppendRow(const DWARFDebugLine::Row& state); + void Clear() + { + prologue.reset(); + rows.clear(); + } + + uint32_t LookupAddress(dw_addr_t address, dw_addr_t cu_high_pc) const; + void Dump(lldb_private::Log *log) const; + + Prologue::shared_ptr prologue; + Row::collection rows; + }; + + //------------------------------------------------------------------ + // State + //------------------------------------------------------------------ + struct State : public Row + { + typedef void (*Callback)(dw_offset_t offset, const State& state, void* userData); + + // Special row codes used when calling the callback + enum + { + StartParsingLineTable = 0, + DoneParsingLineTable = -1 + }; + + State (Prologue::shared_ptr& prologue_sp, + lldb_private::Log *log, + Callback callback, + void* userData); + + void + AppendRowToMatrix (dw_offset_t offset); + + void + Finalize (dw_offset_t offset); + + void + Reset (); + + Prologue::shared_ptr prologue; + lldb_private::Log *log; + Callback callback; // Callback funcation that gets called each time an entry it to be added to the matrix + void* callbackUserData; + int row; // The row number that starts at zero for the prologue, and increases for each row added to the matrix + private: + DISALLOW_COPY_AND_ASSIGN (State); + }; + + static bool DumpOpcodes(lldb_private::Log *log, SymbolFileDWARF* dwarf2Data, dw_offset_t line_offset = DW_INVALID_OFFSET, uint32_t dump_flags = 0); // If line_offset is invalid, dump everything + static bool DumpLineTableRows(lldb_private::Log *log, SymbolFileDWARF* dwarf2Data, dw_offset_t line_offset = DW_INVALID_OFFSET); // If line_offset is invalid, dump everything + static bool ParseSupportFiles(const lldb_private::DataExtractor& debug_line_data, const char *cu_comp_dir, dw_offset_t stmt_list, lldb_private::FileSpecList &support_files); + static bool ParsePrologue(const lldb_private::DataExtractor& debug_line_data, dw_offset_t* offset_ptr, Prologue* prologue); + static bool ParseStatementTable(const lldb_private::DataExtractor& debug_line_data, dw_offset_t* offset_ptr, State::Callback callback, void* userData); + static dw_offset_t DumpStatementTable(lldb_private::Log *log, const lldb_private::DataExtractor& debug_line_data, const dw_offset_t line_offset); + static dw_offset_t DumpStatementOpcodes(lldb_private::Log *log, const lldb_private::DataExtractor& debug_line_data, const dw_offset_t line_offset, uint32_t flags); + static bool ParseStatementTable(const lldb_private::DataExtractor& debug_line_data, uint32_t* offset_ptr, LineTable* line_table); + static void Parse(const lldb_private::DataExtractor& debug_line_data, DWARFDebugLine::State::Callback callback, void* userData); +// static void AppendLineTableData(const DWARFDebugLine::Prologue* prologue, const DWARFDebugLine::Row::collection& state_coll, const uint32_t addr_size, BinaryStreamBuf &debug_line_data); + + DWARFDebugLine() : + m_lineTableMap() + { + } + + void Parse(const lldb_private::DataExtractor& debug_line_data); + void ParseIfNeeded(const lldb_private::DataExtractor& debug_line_data); + LineTable::shared_ptr GetLineTable(const dw_offset_t offset) const; + +protected: + typedef std::map<dw_offset_t, LineTable::shared_ptr> LineTableMap; + typedef LineTableMap::iterator LineTableIter; + typedef LineTableMap::const_iterator LineTableConstIter; + + LineTableMap m_lineTableMap; +}; + +#endif // liblldb_DWARFDebugLine_h_ |