LLVM API Documentation
00001 //===-- DWARFDebugLoc.cpp -------------------------------------------------===// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file is distributed under the University of Illinois Open Source 00006 // License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 00010 #include "DWARFDebugLoc.h" 00011 #include "llvm/Support/Compiler.h" 00012 #include "llvm/Support/Format.h" 00013 #include "llvm/Support/raw_ostream.h" 00014 #include "llvm/Support/Dwarf.h" 00015 00016 using namespace llvm; 00017 00018 void DWARFDebugLoc::dump(raw_ostream &OS) const { 00019 for (const LocationList &L : Locations) { 00020 OS << format("0x%8.8x: ", L.Offset); 00021 const unsigned Indent = 12; 00022 for (const Entry &E : L.Entries) { 00023 if (&E != L.Entries.begin()) 00024 OS.indent(Indent); 00025 OS << "Beginning address offset: " << format("0x%016" PRIx64, E.Begin) 00026 << '\n'; 00027 OS.indent(Indent) << " Ending address offset: " 00028 << format("0x%016" PRIx64, E.End) << '\n'; 00029 OS.indent(Indent) << " Location description: "; 00030 for (unsigned char Loc : E.Loc) { 00031 OS << format("%2.2x ", Loc); 00032 } 00033 OS << "\n\n"; 00034 } 00035 } 00036 } 00037 00038 void DWARFDebugLoc::parse(DataExtractor data, unsigned AddressSize) { 00039 uint32_t Offset = 0; 00040 while (data.isValidOffset(Offset+AddressSize-1)) { 00041 Locations.resize(Locations.size() + 1); 00042 LocationList &Loc = Locations.back(); 00043 Loc.Offset = Offset; 00044 // 2.6.2 Location Lists 00045 // A location list entry consists of: 00046 while (true) { 00047 Entry E; 00048 RelocAddrMap::const_iterator AI = RelocMap.find(Offset); 00049 // 1. A beginning address offset. ... 00050 E.Begin = data.getUnsigned(&Offset, AddressSize); 00051 if (AI != RelocMap.end()) 00052 E.Begin += AI->second.second; 00053 00054 AI = RelocMap.find(Offset); 00055 // 2. An ending address offset. ... 00056 E.End = data.getUnsigned(&Offset, AddressSize); 00057 if (AI != RelocMap.end()) 00058 E.End += AI->second.second; 00059 00060 // The end of any given location list is marked by an end of list entry, 00061 // which consists of a 0 for the beginning address offset and a 0 for the 00062 // ending address offset. 00063 if (E.Begin == 0 && E.End == 0) 00064 break; 00065 00066 unsigned Bytes = data.getU16(&Offset); 00067 // A single location description describing the location of the object... 00068 StringRef str = data.getData().substr(Offset, Bytes); 00069 Offset += Bytes; 00070 E.Loc.reserve(str.size()); 00071 std::copy(str.begin(), str.end(), std::back_inserter(E.Loc)); 00072 Loc.Entries.push_back(std::move(E)); 00073 } 00074 } 00075 if (data.isValidOffset(Offset)) 00076 llvm::errs() << "error: failed to consume entire .debug_loc section\n"; 00077 } 00078 00079 void DWARFDebugLocDWO::parse(DataExtractor data) { 00080 uint32_t Offset = 0; 00081 while (data.isValidOffset(Offset)) { 00082 Locations.resize(Locations.size() + 1); 00083 LocationList &Loc = Locations.back(); 00084 Loc.Offset = Offset; 00085 dwarf::LocationListEntry Kind; 00086 while ((Kind = static_cast<dwarf::LocationListEntry>( 00087 data.getU8(&Offset))) != dwarf::DW_LLE_end_of_list_entry) { 00088 00089 if (Kind != dwarf::DW_LLE_start_length_entry) { 00090 llvm::errs() << "error: dumping support for LLE of kind " << (int)Kind 00091 << " not implemented\n"; 00092 return; 00093 } 00094 00095 Entry E; 00096 00097 E.Start = data.getULEB128(&Offset); 00098 E.Length = data.getU32(&Offset); 00099 00100 unsigned Bytes = data.getU16(&Offset); 00101 // A single location description describing the location of the object... 00102 StringRef str = data.getData().substr(Offset, Bytes); 00103 Offset += Bytes; 00104 E.Loc.resize(str.size()); 00105 std::copy(str.begin(), str.end(), E.Loc.begin()); 00106 00107 Loc.Entries.push_back(std::move(E)); 00108 } 00109 } 00110 } 00111 00112 void DWARFDebugLocDWO::dump(raw_ostream &OS) const { 00113 for (const LocationList &L : Locations) { 00114 OS << format("0x%8.8x: ", L.Offset); 00115 const unsigned Indent = 12; 00116 for (const Entry &E : L.Entries) { 00117 if (&E != L.Entries.begin()) 00118 OS.indent(Indent); 00119 OS << "Beginning address index: " << E.Start << '\n'; 00120 OS.indent(Indent) << " Length: " << E.Length << '\n'; 00121 OS.indent(Indent) << " Location description: "; 00122 for (unsigned char Loc : E.Loc) 00123 OS << format("%2.2x ", Loc); 00124 OS << "\n\n"; 00125 } 00126 } 00127 } 00128