14e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis//===-- DWARFDebugLine.cpp ------------------------------------------------===// 24e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis// 34e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis// The LLVM Compiler Infrastructure 44e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis// 54e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis// This file is distributed under the University of Illinois Open Source 64e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis// License. See LICENSE.TXT for details. 74e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis// 84e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis//===----------------------------------------------------------------------===// 94e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 104e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis#include "DWARFDebugLine.h" 11651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines#include "llvm/Support/Dwarf.h" 124e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis#include "llvm/Support/Format.h" 134e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis#include "llvm/Support/Path.h" 144e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis#include "llvm/Support/raw_ostream.h" 154e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis#include <algorithm> 164e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidisusing namespace llvm; 174e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidisusing namespace dwarf; 18651f13cea278ec967336033dd032faef0e9fc2ecStephen Hinestypedef DILineInfoSpecifier::FileLineInfoKind FileLineInfoKind; 194e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 204e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios KyrtzidisDWARFDebugLine::Prologue::Prologue() { 214e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis clear(); 224e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis} 234e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 244e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidisvoid DWARFDebugLine::Prologue::clear() { 254e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis TotalLength = Version = PrologueLength = 0; 264e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis MinInstLength = MaxOpsPerInst = DefaultIsStmt = LineBase = LineRange = 0; 274e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis OpcodeBase = 0; 284e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis StandardOpcodeLengths.clear(); 294e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis IncludeDirectories.clear(); 304e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis FileNames.clear(); 314e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis} 324e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 334e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidisvoid DWARFDebugLine::Prologue::dump(raw_ostream &OS) const { 344e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis OS << "Line table prologue:\n" 354e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis << format(" total_length: 0x%8.8x\n", TotalLength) 36e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis << format(" version: %u\n", Version) 37e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis << format(" prologue_length: 0x%8.8x\n", PrologueLength) 38e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis << format(" min_inst_length: %u\n", MinInstLength) 39e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis << format(Version >= 4 ? "max_ops_per_inst: %u\n" : "", MaxOpsPerInst) 40e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis << format(" default_is_stmt: %u\n", DefaultIsStmt) 414e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis << format(" line_base: %i\n", LineBase) 424e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis << format(" line_range: %u\n", LineRange) 43d6c8209fd1567db9c2721f441b50cb23cdf8d835Argyrios Kyrtzidis << format(" opcode_base: %u\n", OpcodeBase); 44d6c8209fd1567db9c2721f441b50cb23cdf8d835Argyrios Kyrtzidis 454e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis for (uint32_t i = 0; i < StandardOpcodeLengths.size(); ++i) 464e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis OS << format("standard_opcode_lengths[%s] = %u\n", LNStandardString(i+1), 474e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis StandardOpcodeLengths[i]); 484e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 494e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis if (!IncludeDirectories.empty()) 504e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis for (uint32_t i = 0; i < IncludeDirectories.size(); ++i) 514e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis OS << format("include_directories[%3u] = '", i+1) 524e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis << IncludeDirectories[i] << "'\n"; 534e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 544e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis if (!FileNames.empty()) { 554e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis OS << " Dir Mod Time File Len File Name\n" 564e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis << " ---- ---------- ---------- -----------" 574e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis "----------------\n"; 584e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis for (uint32_t i = 0; i < FileNames.size(); ++i) { 594e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis const FileNameEntry& fileEntry = FileNames[i]; 604e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis OS << format("file_names[%3u] %4" PRIu64 " ", i+1, fileEntry.DirIdx) 614e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis << format("0x%8.8" PRIx64 " 0x%8.8" PRIx64 " ", 624e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis fileEntry.ModTime, fileEntry.Length) 634e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis << fileEntry.Name << '\n'; 644e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis } 654e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis } 664e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis} 674e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 684e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidisbool DWARFDebugLine::Prologue::parse(DataExtractor debug_line_data, 694e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis uint32_t *offset_ptr) { 704e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis const uint32_t prologue_offset = *offset_ptr; 714e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 72145f7b2093a0050621141acd089e09edf6118a09Argyrios Kyrtzidis clear(); 73145f7b2093a0050621141acd089e09edf6118a09Argyrios Kyrtzidis TotalLength = debug_line_data.getU32(offset_ptr); 746d968363877388f0a0268711d59367907b465ae1Argyrios Kyrtzidis Version = debug_line_data.getU16(offset_ptr); 7558d2dbea680a75de266c5eff77cc15c323cfd48aArgyrios Kyrtzidis if (Version < 2) 7658d2dbea680a75de266c5eff77cc15c323cfd48aArgyrios Kyrtzidis return false; 7758d2dbea680a75de266c5eff77cc15c323cfd48aArgyrios Kyrtzidis 7858d2dbea680a75de266c5eff77cc15c323cfd48aArgyrios Kyrtzidis PrologueLength = debug_line_data.getU32(offset_ptr); 7958d2dbea680a75de266c5eff77cc15c323cfd48aArgyrios Kyrtzidis const uint32_t end_prologue_offset = PrologueLength + *offset_ptr; 8058d2dbea680a75de266c5eff77cc15c323cfd48aArgyrios Kyrtzidis MinInstLength = debug_line_data.getU8(offset_ptr); 8158d2dbea680a75de266c5eff77cc15c323cfd48aArgyrios Kyrtzidis if (Version >= 4) 8258d2dbea680a75de266c5eff77cc15c323cfd48aArgyrios Kyrtzidis MaxOpsPerInst = debug_line_data.getU8(offset_ptr); 8358d2dbea680a75de266c5eff77cc15c323cfd48aArgyrios Kyrtzidis DefaultIsStmt = debug_line_data.getU8(offset_ptr); 846d968363877388f0a0268711d59367907b465ae1Argyrios Kyrtzidis LineBase = debug_line_data.getU8(offset_ptr); 85145f7b2093a0050621141acd089e09edf6118a09Argyrios Kyrtzidis LineRange = debug_line_data.getU8(offset_ptr); 86145f7b2093a0050621141acd089e09edf6118a09Argyrios Kyrtzidis OpcodeBase = debug_line_data.getU8(offset_ptr); 87f8490eeb966103516da4e3ecb05e1a36b3e6e3ecArgyrios Kyrtzidis 88f8490eeb966103516da4e3ecb05e1a36b3e6e3ecArgyrios Kyrtzidis StandardOpcodeLengths.reserve(OpcodeBase - 1); 89f8490eeb966103516da4e3ecb05e1a36b3e6e3ecArgyrios Kyrtzidis for (uint32_t i = 1; i < OpcodeBase; ++i) { 90f8490eeb966103516da4e3ecb05e1a36b3e6e3ecArgyrios Kyrtzidis uint8_t op_len = debug_line_data.getU8(offset_ptr); 91f8490eeb966103516da4e3ecb05e1a36b3e6e3ecArgyrios Kyrtzidis StandardOpcodeLengths.push_back(op_len); 924e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis } 934e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 944e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis while (*offset_ptr < end_prologue_offset) { 954e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis const char *s = debug_line_data.getCStr(offset_ptr); 964e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis if (s && s[0]) 974e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis IncludeDirectories.push_back(s); 984e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis else 994e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis break; 1004e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis } 1014e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 1024e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis while (*offset_ptr < end_prologue_offset) { 1034e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis const char *name = debug_line_data.getCStr(offset_ptr); 1044e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis if (name && name[0]) { 1054e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis FileNameEntry fileEntry; 1064e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis fileEntry.Name = name; 1074e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis fileEntry.DirIdx = debug_line_data.getULEB128(offset_ptr); 108e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis fileEntry.ModTime = debug_line_data.getULEB128(offset_ptr); 109e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis fileEntry.Length = debug_line_data.getULEB128(offset_ptr); 110e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis FileNames.push_back(fileEntry); 111ef8225444452a1486bd721f3285301fe84643b00Stephen Hines } else { 112e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis break; 1134e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis } 1144e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis } 1154e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis 116e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis if (*offset_ptr != end_prologue_offset) { 117e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis fprintf(stderr, "warning: parsing line table prologue at 0x%8.8x should" 118e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis " have ended at 0x%8.8x but it ended at 0x%8.8x\n", 119e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis prologue_offset, end_prologue_offset, *offset_ptr); 120e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis return false; 121e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis } 122e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis return true; 123e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis} 124e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis 125ef8225444452a1486bd721f3285301fe84643b00Stephen HinesDWARFDebugLine::Row::Row(bool default_is_stmt) { 126e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis reset(default_is_stmt); 127e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis} 128e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis 129e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidisvoid DWARFDebugLine::Row::postAppend() { 130e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis BasicBlock = false; 131e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis PrologueEnd = false; 132e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis EpilogueBegin = false; 133e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis} 134e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis 135e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidisvoid DWARFDebugLine::Row::reset(bool default_is_stmt) { 136e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis Address = 0; 137e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis Line = 1; 138e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis Column = 0; 139e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis File = 1; 140e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis Isa = 0; 141e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis Discriminator = 0; 142e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis IsStmt = default_is_stmt; 143e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis BasicBlock = false; 144e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis EndSequence = false; 145e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis PrologueEnd = false; 146e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis EpilogueBegin = false; 147e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis} 148e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidis 149e422e45a6a89d450b8eca10f671b49874e87617aArgyrios Kyrtzidisvoid DWARFDebugLine::Row::dump(raw_ostream &OS) const { 1504e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis OS << format("0x%16.16" PRIx64 " %6u %6u", Address, Line, Column) 151b395c63b473bf1b3783bff371a993332e8c4c5e3Argyrios Kyrtzidis << format(" %6u %3u %13u ", File, Isa, Discriminator) 152b395c63b473bf1b3783bff371a993332e8c4c5e3Argyrios Kyrtzidis << (IsStmt ? " is_stmt" : "") 153b395c63b473bf1b3783bff371a993332e8c4c5e3Argyrios Kyrtzidis << (BasicBlock ? " basic_block" : "") 1544e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis << (PrologueEnd ? " prologue_end" : "") 1554e7064fa7e344e8f87a5b8457e96dfdd252c4a9eArgyrios Kyrtzidis << (EpilogueBegin ? " epilogue_begin" : "") 156 << (EndSequence ? " end_sequence" : "") 157 << '\n'; 158} 159 160DWARFDebugLine::Sequence::Sequence() { 161 reset(); 162} 163 164void DWARFDebugLine::Sequence::reset() { 165 LowPC = 0; 166 HighPC = 0; 167 FirstRowIndex = 0; 168 LastRowIndex = 0; 169 Empty = true; 170} 171 172DWARFDebugLine::LineTable::LineTable() { 173 clear(); 174} 175 176void DWARFDebugLine::LineTable::dump(raw_ostream &OS) const { 177 Prologue.dump(OS); 178 OS << '\n'; 179 180 if (!Rows.empty()) { 181 OS << "Address Line Column File ISA Discriminator Flags\n" 182 << "------------------ ------ ------ ------ --- ------------- " 183 "-------------\n"; 184 for (const Row &R : Rows) { 185 R.dump(OS); 186 } 187 } 188} 189 190void DWARFDebugLine::LineTable::clear() { 191 Prologue.clear(); 192 Rows.clear(); 193 Sequences.clear(); 194} 195 196DWARFDebugLine::ParsingState::ParsingState(struct LineTable *LT) 197 : LineTable(LT), RowNumber(0) { 198 resetRowAndSequence(); 199} 200 201void DWARFDebugLine::ParsingState::resetRowAndSequence() { 202 Row.reset(LineTable->Prologue.DefaultIsStmt); 203 Sequence.reset(); 204} 205 206void DWARFDebugLine::ParsingState::appendRowToMatrix(uint32_t offset) { 207 if (Sequence.Empty) { 208 // Record the beginning of instruction sequence. 209 Sequence.Empty = false; 210 Sequence.LowPC = Row.Address; 211 Sequence.FirstRowIndex = RowNumber; 212 } 213 ++RowNumber; 214 LineTable->appendRow(Row); 215 if (Row.EndSequence) { 216 // Record the end of instruction sequence. 217 Sequence.HighPC = Row.Address; 218 Sequence.LastRowIndex = RowNumber; 219 if (Sequence.isValid()) 220 LineTable->appendSequence(Sequence); 221 Sequence.reset(); 222 } 223 Row.postAppend(); 224} 225 226const DWARFDebugLine::LineTable * 227DWARFDebugLine::getLineTable(uint32_t offset) const { 228 LineTableConstIter pos = LineTableMap.find(offset); 229 if (pos != LineTableMap.end()) 230 return &pos->second; 231 return nullptr; 232} 233 234const DWARFDebugLine::LineTable * 235DWARFDebugLine::getOrParseLineTable(DataExtractor debug_line_data, 236 uint32_t offset) { 237 std::pair<LineTableIter, bool> pos = 238 LineTableMap.insert(LineTableMapTy::value_type(offset, LineTable())); 239 LineTable *LT = &pos.first->second; 240 if (pos.second) { 241 if (!LT->parse(debug_line_data, RelocMap, &offset)) 242 return nullptr; 243 } 244 return LT; 245} 246 247bool DWARFDebugLine::LineTable::parse(DataExtractor debug_line_data, 248 const RelocAddrMap *RMap, 249 uint32_t *offset_ptr) { 250 const uint32_t debug_line_offset = *offset_ptr; 251 252 clear(); 253 254 if (!Prologue.parse(debug_line_data, offset_ptr)) { 255 // Restore our offset and return false to indicate failure! 256 *offset_ptr = debug_line_offset; 257 return false; 258 } 259 260 const uint32_t end_offset = debug_line_offset + Prologue.TotalLength + 261 sizeof(Prologue.TotalLength); 262 263 ParsingState State(this); 264 265 while (*offset_ptr < end_offset) { 266 uint8_t opcode = debug_line_data.getU8(offset_ptr); 267 268 if (opcode == 0) { 269 // Extended Opcodes always start with a zero opcode followed by 270 // a uleb128 length so you can skip ones you don't know about 271 uint32_t ext_offset = *offset_ptr; 272 uint64_t len = debug_line_data.getULEB128(offset_ptr); 273 uint32_t arg_size = len - (*offset_ptr - ext_offset); 274 275 uint8_t sub_opcode = debug_line_data.getU8(offset_ptr); 276 switch (sub_opcode) { 277 case DW_LNE_end_sequence: 278 // Set the end_sequence register of the state machine to true and 279 // append a row to the matrix using the current values of the 280 // state-machine registers. Then reset the registers to the initial 281 // values specified above. Every statement program sequence must end 282 // with a DW_LNE_end_sequence instruction which creates a row whose 283 // address is that of the byte after the last target machine instruction 284 // of the sequence. 285 State.Row.EndSequence = true; 286 State.appendRowToMatrix(*offset_ptr); 287 State.resetRowAndSequence(); 288 break; 289 290 case DW_LNE_set_address: 291 // Takes a single relocatable address as an operand. The size of the 292 // operand is the size appropriate to hold an address on the target 293 // machine. Set the address register to the value given by the 294 // relocatable address. All of the other statement program opcodes 295 // that affect the address register add a delta to it. This instruction 296 // stores a relocatable value into it instead. 297 { 298 // If this address is in our relocation map, apply the relocation. 299 RelocAddrMap::const_iterator AI = RMap->find(*offset_ptr); 300 if (AI != RMap->end()) { 301 const std::pair<uint8_t, int64_t> &R = AI->second; 302 State.Row.Address = 303 debug_line_data.getAddress(offset_ptr) + R.second; 304 } else 305 State.Row.Address = debug_line_data.getAddress(offset_ptr); 306 } 307 break; 308 309 case DW_LNE_define_file: 310 // Takes 4 arguments. The first is a null terminated string containing 311 // a source file name. The second is an unsigned LEB128 number 312 // representing the directory index of the directory in which the file 313 // was found. The third is an unsigned LEB128 number representing the 314 // time of last modification of the file. The fourth is an unsigned 315 // LEB128 number representing the length in bytes of the file. The time 316 // and length fields may contain LEB128(0) if the information is not 317 // available. 318 // 319 // The directory index represents an entry in the include_directories 320 // section of the statement program prologue. The index is LEB128(0) 321 // if the file was found in the current directory of the compilation, 322 // LEB128(1) if it was found in the first directory in the 323 // include_directories section, and so on. The directory index is 324 // ignored for file names that represent full path names. 325 // 326 // The files are numbered, starting at 1, in the order in which they 327 // appear; the names in the prologue come before names defined by 328 // the DW_LNE_define_file instruction. These numbers are used in the 329 // the file register of the state machine. 330 { 331 FileNameEntry fileEntry; 332 fileEntry.Name = debug_line_data.getCStr(offset_ptr); 333 fileEntry.DirIdx = debug_line_data.getULEB128(offset_ptr); 334 fileEntry.ModTime = debug_line_data.getULEB128(offset_ptr); 335 fileEntry.Length = debug_line_data.getULEB128(offset_ptr); 336 Prologue.FileNames.push_back(fileEntry); 337 } 338 break; 339 340 case DW_LNE_set_discriminator: 341 State.Row.Discriminator = debug_line_data.getULEB128(offset_ptr); 342 break; 343 344 default: 345 // Length doesn't include the zero opcode byte or the length itself, but 346 // it does include the sub_opcode, so we have to adjust for that below 347 (*offset_ptr) += arg_size; 348 break; 349 } 350 } else if (opcode < Prologue.OpcodeBase) { 351 switch (opcode) { 352 // Standard Opcodes 353 case DW_LNS_copy: 354 // Takes no arguments. Append a row to the matrix using the 355 // current values of the state-machine registers. Then set 356 // the basic_block register to false. 357 State.appendRowToMatrix(*offset_ptr); 358 break; 359 360 case DW_LNS_advance_pc: 361 // Takes a single unsigned LEB128 operand, multiplies it by the 362 // min_inst_length field of the prologue, and adds the 363 // result to the address register of the state machine. 364 State.Row.Address += 365 debug_line_data.getULEB128(offset_ptr) * Prologue.MinInstLength; 366 break; 367 368 case DW_LNS_advance_line: 369 // Takes a single signed LEB128 operand and adds that value to 370 // the line register of the state machine. 371 State.Row.Line += debug_line_data.getSLEB128(offset_ptr); 372 break; 373 374 case DW_LNS_set_file: 375 // Takes a single unsigned LEB128 operand and stores it in the file 376 // register of the state machine. 377 State.Row.File = debug_line_data.getULEB128(offset_ptr); 378 break; 379 380 case DW_LNS_set_column: 381 // Takes a single unsigned LEB128 operand and stores it in the 382 // column register of the state machine. 383 State.Row.Column = debug_line_data.getULEB128(offset_ptr); 384 break; 385 386 case DW_LNS_negate_stmt: 387 // Takes no arguments. Set the is_stmt register of the state 388 // machine to the logical negation of its current value. 389 State.Row.IsStmt = !State.Row.IsStmt; 390 break; 391 392 case DW_LNS_set_basic_block: 393 // Takes no arguments. Set the basic_block register of the 394 // state machine to true 395 State.Row.BasicBlock = true; 396 break; 397 398 case DW_LNS_const_add_pc: 399 // Takes no arguments. Add to the address register of the state 400 // machine the address increment value corresponding to special 401 // opcode 255. The motivation for DW_LNS_const_add_pc is this: 402 // when the statement program needs to advance the address by a 403 // small amount, it can use a single special opcode, which occupies 404 // a single byte. When it needs to advance the address by up to 405 // twice the range of the last special opcode, it can use 406 // DW_LNS_const_add_pc followed by a special opcode, for a total 407 // of two bytes. Only if it needs to advance the address by more 408 // than twice that range will it need to use both DW_LNS_advance_pc 409 // and a special opcode, requiring three or more bytes. 410 { 411 uint8_t adjust_opcode = 255 - Prologue.OpcodeBase; 412 uint64_t addr_offset = 413 (adjust_opcode / Prologue.LineRange) * Prologue.MinInstLength; 414 State.Row.Address += addr_offset; 415 } 416 break; 417 418 case DW_LNS_fixed_advance_pc: 419 // Takes a single uhalf operand. Add to the address register of 420 // the state machine the value of the (unencoded) operand. This 421 // is the only extended opcode that takes an argument that is not 422 // a variable length number. The motivation for DW_LNS_fixed_advance_pc 423 // is this: existing assemblers cannot emit DW_LNS_advance_pc or 424 // special opcodes because they cannot encode LEB128 numbers or 425 // judge when the computation of a special opcode overflows and 426 // requires the use of DW_LNS_advance_pc. Such assemblers, however, 427 // can use DW_LNS_fixed_advance_pc instead, sacrificing compression. 428 State.Row.Address += debug_line_data.getU16(offset_ptr); 429 break; 430 431 case DW_LNS_set_prologue_end: 432 // Takes no arguments. Set the prologue_end register of the 433 // state machine to true 434 State.Row.PrologueEnd = true; 435 break; 436 437 case DW_LNS_set_epilogue_begin: 438 // Takes no arguments. Set the basic_block register of the 439 // state machine to true 440 State.Row.EpilogueBegin = true; 441 break; 442 443 case DW_LNS_set_isa: 444 // Takes a single unsigned LEB128 operand and stores it in the 445 // column register of the state machine. 446 State.Row.Isa = debug_line_data.getULEB128(offset_ptr); 447 break; 448 449 default: 450 // Handle any unknown standard opcodes here. We know the lengths 451 // of such opcodes because they are specified in the prologue 452 // as a multiple of LEB128 operands for each opcode. 453 { 454 assert(opcode - 1U < Prologue.StandardOpcodeLengths.size()); 455 uint8_t opcode_length = Prologue.StandardOpcodeLengths[opcode - 1]; 456 for (uint8_t i = 0; i < opcode_length; ++i) 457 debug_line_data.getULEB128(offset_ptr); 458 } 459 break; 460 } 461 } else { 462 // Special Opcodes 463 464 // A special opcode value is chosen based on the amount that needs 465 // to be added to the line and address registers. The maximum line 466 // increment for a special opcode is the value of the line_base 467 // field in the header, plus the value of the line_range field, 468 // minus 1 (line base + line range - 1). If the desired line 469 // increment is greater than the maximum line increment, a standard 470 // opcode must be used instead of a special opcode. The "address 471 // advance" is calculated by dividing the desired address increment 472 // by the minimum_instruction_length field from the header. The 473 // special opcode is then calculated using the following formula: 474 // 475 // opcode = (desired line increment - line_base) + 476 // (line_range * address advance) + opcode_base 477 // 478 // If the resulting opcode is greater than 255, a standard opcode 479 // must be used instead. 480 // 481 // To decode a special opcode, subtract the opcode_base from the 482 // opcode itself to give the adjusted opcode. The amount to 483 // increment the address register is the result of the adjusted 484 // opcode divided by the line_range multiplied by the 485 // minimum_instruction_length field from the header. That is: 486 // 487 // address increment = (adjusted opcode / line_range) * 488 // minimum_instruction_length 489 // 490 // The amount to increment the line register is the line_base plus 491 // the result of the adjusted opcode modulo the line_range. That is: 492 // 493 // line increment = line_base + (adjusted opcode % line_range) 494 495 uint8_t adjust_opcode = opcode - Prologue.OpcodeBase; 496 uint64_t addr_offset = 497 (adjust_opcode / Prologue.LineRange) * Prologue.MinInstLength; 498 int32_t line_offset = 499 Prologue.LineBase + (adjust_opcode % Prologue.LineRange); 500 State.Row.Line += line_offset; 501 State.Row.Address += addr_offset; 502 State.appendRowToMatrix(*offset_ptr); 503 } 504 } 505 506 if (!State.Sequence.Empty) { 507 fprintf(stderr, "warning: last sequence in debug line table is not" 508 "terminated!\n"); 509 } 510 511 // Sort all sequences so that address lookup will work faster. 512 if (!Sequences.empty()) { 513 std::sort(Sequences.begin(), Sequences.end(), Sequence::orderByLowPC); 514 // Note: actually, instruction address ranges of sequences should not 515 // overlap (in shared objects and executables). If they do, the address 516 // lookup would still work, though, but result would be ambiguous. 517 // We don't report warning in this case. For example, 518 // sometimes .so compiled from multiple object files contains a few 519 // rudimentary sequences for address ranges [0x0, 0xsomething). 520 } 521 522 return end_offset; 523} 524 525uint32_t DWARFDebugLine::LineTable::lookupAddress(uint64_t address) const { 526 uint32_t unknown_index = UINT32_MAX; 527 if (Sequences.empty()) 528 return unknown_index; 529 // First, find an instruction sequence containing the given address. 530 DWARFDebugLine::Sequence sequence; 531 sequence.LowPC = address; 532 SequenceIter first_seq = Sequences.begin(); 533 SequenceIter last_seq = Sequences.end(); 534 SequenceIter seq_pos = std::lower_bound(first_seq, last_seq, sequence, 535 DWARFDebugLine::Sequence::orderByLowPC); 536 DWARFDebugLine::Sequence found_seq; 537 if (seq_pos == last_seq) { 538 found_seq = Sequences.back(); 539 } else if (seq_pos->LowPC == address) { 540 found_seq = *seq_pos; 541 } else { 542 if (seq_pos == first_seq) 543 return unknown_index; 544 found_seq = *(seq_pos - 1); 545 } 546 if (!found_seq.containsPC(address)) 547 return unknown_index; 548 // Search for instruction address in the rows describing the sequence. 549 // Rows are stored in a vector, so we may use arithmetical operations with 550 // iterators. 551 DWARFDebugLine::Row row; 552 row.Address = address; 553 RowIter first_row = Rows.begin() + found_seq.FirstRowIndex; 554 RowIter last_row = Rows.begin() + found_seq.LastRowIndex; 555 RowIter row_pos = std::lower_bound(first_row, last_row, row, 556 DWARFDebugLine::Row::orderByAddress); 557 if (row_pos == last_row) { 558 return found_seq.LastRowIndex - 1; 559 } 560 uint32_t index = found_seq.FirstRowIndex + (row_pos - first_row); 561 if (row_pos->Address > address) { 562 if (row_pos == first_row) 563 return unknown_index; 564 else 565 index--; 566 } 567 return index; 568} 569 570bool DWARFDebugLine::LineTable::lookupAddressRange( 571 uint64_t address, uint64_t size, std::vector<uint32_t> &result) const { 572 if (Sequences.empty()) 573 return false; 574 uint64_t end_addr = address + size; 575 // First, find an instruction sequence containing the given address. 576 DWARFDebugLine::Sequence sequence; 577 sequence.LowPC = address; 578 SequenceIter first_seq = Sequences.begin(); 579 SequenceIter last_seq = Sequences.end(); 580 SequenceIter seq_pos = std::lower_bound(first_seq, last_seq, sequence, 581 DWARFDebugLine::Sequence::orderByLowPC); 582 if (seq_pos == last_seq || seq_pos->LowPC != address) { 583 if (seq_pos == first_seq) 584 return false; 585 seq_pos--; 586 } 587 if (!seq_pos->containsPC(address)) 588 return false; 589 590 SequenceIter start_pos = seq_pos; 591 592 // Add the rows from the first sequence to the vector, starting with the 593 // index we just calculated 594 595 while (seq_pos != last_seq && seq_pos->LowPC < end_addr) { 596 DWARFDebugLine::Sequence cur_seq = *seq_pos; 597 uint32_t first_row_index; 598 uint32_t last_row_index; 599 if (seq_pos == start_pos) { 600 // For the first sequence, we need to find which row in the sequence is the 601 // first in our range. Rows are stored in a vector, so we may use 602 // arithmetical operations with iterators. 603 DWARFDebugLine::Row row; 604 row.Address = address; 605 RowIter first_row = Rows.begin() + cur_seq.FirstRowIndex; 606 RowIter last_row = Rows.begin() + cur_seq.LastRowIndex; 607 RowIter row_pos = std::upper_bound(first_row, last_row, row, 608 DWARFDebugLine::Row::orderByAddress); 609 // The 'row_pos' iterator references the first row that is greater than 610 // our start address. Unless that's the first row, we want to start at 611 // the row before that. 612 first_row_index = cur_seq.FirstRowIndex + (row_pos - first_row); 613 if (row_pos != first_row) 614 --first_row_index; 615 } else 616 first_row_index = cur_seq.FirstRowIndex; 617 618 // For the last sequence in our range, we need to figure out the last row in 619 // range. For all other sequences we can go to the end of the sequence. 620 if (cur_seq.HighPC > end_addr) { 621 DWARFDebugLine::Row row; 622 row.Address = end_addr; 623 RowIter first_row = Rows.begin() + cur_seq.FirstRowIndex; 624 RowIter last_row = Rows.begin() + cur_seq.LastRowIndex; 625 RowIter row_pos = std::upper_bound(first_row, last_row, row, 626 DWARFDebugLine::Row::orderByAddress); 627 // The 'row_pos' iterator references the first row that is greater than 628 // our end address. The row before that is the last row we want. 629 last_row_index = cur_seq.FirstRowIndex + (row_pos - first_row) - 1; 630 } else 631 // Contrary to what you might expect, DWARFDebugLine::SequenceLastRowIndex 632 // isn't a valid index within the current sequence. It's that plus one. 633 last_row_index = cur_seq.LastRowIndex - 1; 634 635 for (uint32_t i = first_row_index; i <= last_row_index; ++i) { 636 result.push_back(i); 637 } 638 639 ++seq_pos; 640 } 641 642 return true; 643} 644 645bool 646DWARFDebugLine::LineTable::getFileNameByIndex(uint64_t FileIndex, 647 FileLineInfoKind Kind, 648 std::string &Result) const { 649 if (FileIndex == 0 || FileIndex > Prologue.FileNames.size() || 650 Kind == FileLineInfoKind::None) 651 return false; 652 const FileNameEntry &Entry = Prologue.FileNames[FileIndex - 1]; 653 const char *FileName = Entry.Name; 654 if (Kind != FileLineInfoKind::AbsoluteFilePath || 655 sys::path::is_absolute(FileName)) { 656 Result = FileName; 657 return true; 658 } 659 SmallString<16> FilePath; 660 uint64_t IncludeDirIndex = Entry.DirIdx; 661 // Be defensive about the contents of Entry. 662 if (IncludeDirIndex > 0 && 663 IncludeDirIndex <= Prologue.IncludeDirectories.size()) { 664 const char *IncludeDir = Prologue.IncludeDirectories[IncludeDirIndex - 1]; 665 sys::path::append(FilePath, IncludeDir); 666 } 667 sys::path::append(FilePath, FileName); 668 Result = FilePath.str(); 669 return true; 670} 671