diff options
Diffstat (limited to 'llvm/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp')
-rw-r--r-- | llvm/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp | 37 |
1 files changed, 35 insertions, 2 deletions
diff --git a/llvm/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp b/llvm/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp index 53e676bc7031..886fe1dff976 100644 --- a/llvm/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp +++ b/llvm/lib/DebugInfo/DWARF/DWARFDataExtractor.cpp @@ -7,11 +7,42 @@ //===----------------------------------------------------------------------===// #include "llvm/DebugInfo/DWARF/DWARFDataExtractor.h" -#include "llvm/BinaryFormat/Dwarf.h" #include "llvm/DebugInfo/DWARF/DWARFContext.h" using namespace llvm; +std::pair<uint64_t, dwarf::DwarfFormat> +DWARFDataExtractor::getInitialLength(uint64_t *Off, Error *Err) const { + ErrorAsOutParameter ErrAsOut(Err); + if (Err && *Err) + return {0, dwarf::DWARF32}; + + Cursor C(*Off); + uint64_t Length = getRelocatedValue(C, 4); + dwarf::DwarfFormat Format = dwarf::DWARF32; + if (Length == dwarf::DW_LENGTH_DWARF64) { + Length = getRelocatedValue(C, 8); + Format = dwarf::DWARF64; + } else if (Length >= dwarf::DW_LENGTH_lo_reserved) { + cantFail(C.takeError()); + if (Err) + *Err = createStringError( + errc::invalid_argument, + "unsupported reserved unit length of value 0x%8.8" PRIx64, Length); + return {0, dwarf::DWARF32}; + } + + if (C) { + *Off = C.tell(); + return {Length, Format}; + } + if (Err) + *Err = C.takeError(); + else + consumeError(C.takeError()); + return {0, dwarf::DWARF32}; +} + uint64_t DWARFDataExtractor::getRelocatedValue(uint32_t Size, uint64_t *Off, uint64_t *SecNdx, Error *Err) const { @@ -19,9 +50,11 @@ uint64_t DWARFDataExtractor::getRelocatedValue(uint32_t Size, uint64_t *Off, *SecNdx = object::SectionedAddress::UndefSection; if (!Section) return getUnsigned(Off, Size, Err); + + ErrorAsOutParameter ErrAsOut(Err); Optional<RelocAddrEntry> E = Obj->find(*Section, *Off); uint64_t A = getUnsigned(Off, Size, Err); - if (!E) + if (!E || (Err && *Err)) return A; if (SecNdx) *SecNdx = E->SectionIndex; |