diff options
author | Eric Christopher <echristo@gmail.com> | 2012-11-07 23:22:07 +0000 |
---|---|---|
committer | Eric Christopher <echristo@gmail.com> | 2012-11-07 23:22:07 +0000 |
commit | 806e03d2381709ddfb5a8012729bbe6eae12caf5 (patch) | |
tree | d01da4fb8a09017a564b27968af88dc1fb82084d /lib/DebugInfo | |
parent | b0319962cfdb18da38ef47da621f148fe144b092 (diff) | |
download | external_llvm-806e03d2381709ddfb5a8012729bbe6eae12caf5.zip external_llvm-806e03d2381709ddfb5a8012729bbe6eae12caf5.tar.gz external_llvm-806e03d2381709ddfb5a8012729bbe6eae12caf5.tar.bz2 |
Add a relocation visitor to lib object. This works via caching relocated
values in a map that can be passed to consumers. Add a testcase that
ensures this works for llvm-dwarfdump.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@167558 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/DebugInfo')
-rw-r--r-- | lib/DebugInfo/DIContext.cpp | 5 | ||||
-rw-r--r-- | lib/DebugInfo/DWARFContext.h | 11 | ||||
-rw-r--r-- | lib/DebugInfo/DWARFFormValue.cpp | 25 |
3 files changed, 32 insertions, 9 deletions
diff --git a/lib/DebugInfo/DIContext.cpp b/lib/DebugInfo/DIContext.cpp index ead57f9..691a92c 100644 --- a/lib/DebugInfo/DIContext.cpp +++ b/lib/DebugInfo/DIContext.cpp @@ -19,8 +19,9 @@ DIContext *DIContext::getDWARFContext(bool isLittleEndian, StringRef aRangeSection, StringRef lineSection, StringRef stringSection, - StringRef rangeSection) { + StringRef rangeSection, + const RelocAddrMap &Map) { return new DWARFContextInMemory(isLittleEndian, infoSection, abbrevSection, aRangeSection, lineSection, stringSection, - rangeSection); + rangeSection, Map); } diff --git a/lib/DebugInfo/DWARFContext.h b/lib/DebugInfo/DWARFContext.h index d10e850..4001792 100644 --- a/lib/DebugInfo/DWARFContext.h +++ b/lib/DebugInfo/DWARFContext.h @@ -26,6 +26,7 @@ namespace llvm { /// methods that a concrete implementation provides. class DWARFContext : public DIContext { bool IsLittleEndian; + const RelocAddrMap &RelocMap; SmallVector<DWARFCompileUnit, 1> CUs; OwningPtr<DWARFDebugAbbrev> Abbrev; @@ -38,9 +39,11 @@ class DWARFContext : public DIContext { /// Read compile units from the debug_info section and store them in CUs. void parseCompileUnits(); protected: - DWARFContext(bool isLittleEndian) : IsLittleEndian(isLittleEndian) {} + DWARFContext(bool isLittleEndian, const RelocAddrMap &Map) : + IsLittleEndian(isLittleEndian), RelocMap(Map) {} public: virtual void dump(raw_ostream &OS); + /// Get the number of compile units in this context. unsigned getNumCompileUnits() { if (CUs.empty()) @@ -70,6 +73,7 @@ public: DILineInfoSpecifier Specifier = DILineInfoSpecifier()); bool isLittleEndian() const { return IsLittleEndian; } + const RelocAddrMap &relocMap() const { return RelocMap; } virtual StringRef getInfoSection() = 0; virtual StringRef getAbbrevSection() = 0; @@ -108,8 +112,9 @@ public: StringRef aRangeSection, StringRef lineSection, StringRef stringSection, - StringRef rangeSection) - : DWARFContext(isLittleEndian), + StringRef rangeSection, + const RelocAddrMap &Map = RelocAddrMap()) + : DWARFContext(isLittleEndian, Map), InfoSection(infoSection), AbbrevSection(abbrevSection), ARangeSection(aRangeSection), diff --git a/lib/DebugInfo/DWARFFormValue.cpp b/lib/DebugInfo/DWARFFormValue.cpp index c9ecbbb..fea9fd7 100644 --- a/lib/DebugInfo/DWARFFormValue.cpp +++ b/lib/DebugInfo/DWARFFormValue.cpp @@ -10,6 +10,7 @@ #include "DWARFFormValue.h" #include "DWARFCompileUnit.h" #include "DWARFContext.h" +#include "llvm/Support/Debug.h" #include "llvm/Support/Dwarf.h" #include "llvm/Support/Format.h" #include "llvm/Support/raw_ostream.h" @@ -98,8 +99,16 @@ DWARFFormValue::extractValue(DataExtractor data, uint32_t *offset_ptr, indirect = false; switch (Form) { case DW_FORM_addr: - case DW_FORM_ref_addr: - Value.uval = data.getUnsigned(offset_ptr, cu->getAddressByteSize()); + case DW_FORM_ref_addr: { + RelocAddrMap::const_iterator AI + = cu->getContext().relocMap().find(*offset_ptr); + if (AI != cu->getContext().relocMap().end()) { + const std::pair<uint8_t, int64_t> &R = AI->second; + Value.uval = R.second; + *offset_ptr += R.first; + } else + Value.uval = data.getUnsigned(offset_ptr, cu->getAddressByteSize()); + } break; case DW_FORM_exprloc: case DW_FORM_block: @@ -138,9 +147,17 @@ DWARFFormValue::extractValue(DataExtractor data, uint32_t *offset_ptr, case DW_FORM_sdata: Value.sval = data.getSLEB128(offset_ptr); break; - case DW_FORM_strp: - Value.uval = data.getU32(offset_ptr); + case DW_FORM_strp: { + RelocAddrMap::const_iterator AI + = cu->getContext().relocMap().find(*offset_ptr); + if (AI != cu->getContext().relocMap().end()) { + const std::pair<uint8_t, int64_t> &R = AI->second; + Value.uval = R.second; + *offset_ptr += R.first; + } else + Value.uval = data.getU32(offset_ptr); break; + } case DW_FORM_udata: case DW_FORM_ref_udata: Value.uval = data.getULEB128(offset_ptr); |