diff options
author | Igor Kudrin <ikudrin@accesssoftek.com> | 2019-08-06 10:47:20 +0000 |
---|---|---|
committer | Igor Kudrin <ikudrin@accesssoftek.com> | 2019-08-06 10:47:20 +0000 |
commit | f5f35c5cd110e22c4b216ec1dc53255e32adc011 (patch) | |
tree | ff284ebcb776857fe4043391261ae627d08321f3 /llvm/lib/Support/DataExtractor.cpp | |
parent | 7b24dd741c6c4734f8cf5b9fafc12bf9e38411d6 (diff) | |
download | bcm5719-llvm-f5f35c5cd110e22c4b216ec1dc53255e32adc011.tar.gz bcm5719-llvm-f5f35c5cd110e22c4b216ec1dc53255e32adc011.zip |
Support 64-bit offsets in utility classes (1/5)
Using 64-bit offsets is required to fully implement 64-bit DWARF.
As these classes are used in many different libraries they should
temporarily support both 32- and 64-bit offsets.
Differential Revision: https://reviews.llvm.org/D64006
llvm-svn: 368013
Diffstat (limited to 'llvm/lib/Support/DataExtractor.cpp')
-rw-r--r-- | llvm/lib/Support/DataExtractor.cpp | 130 |
1 files changed, 107 insertions, 23 deletions
diff --git a/llvm/lib/Support/DataExtractor.cpp b/llvm/lib/Support/DataExtractor.cpp index 673bbb4d06f..73c215ea05a 100644 --- a/llvm/lib/Support/DataExtractor.cpp +++ b/llvm/lib/Support/DataExtractor.cpp @@ -14,10 +14,10 @@ using namespace llvm; template <typename T> -static T getU(uint32_t *offset_ptr, const DataExtractor *de, +static T getU(uint64_t *offset_ptr, const DataExtractor *de, bool isLittleEndian, const char *Data) { T val = 0; - uint32_t offset = *offset_ptr; + uint64_t offset = *offset_ptr; if (de->isValidOffsetForDataOfSize(offset, sizeof(val))) { std::memcpy(&val, &Data[offset], sizeof(val)); if (sys::IsLittleEndianHost != isLittleEndian) @@ -30,9 +30,9 @@ static T getU(uint32_t *offset_ptr, const DataExtractor *de, } template <typename T> -static T *getUs(uint32_t *offset_ptr, T *dst, uint32_t count, +static T *getUs(uint64_t *offset_ptr, T *dst, uint32_t count, const DataExtractor *de, bool isLittleEndian, const char *Data){ - uint32_t offset = *offset_ptr; + uint64_t offset = *offset_ptr; if (count > 0 && de->isValidOffsetForDataOfSize(offset, sizeof(*dst)*count)) { for (T *value_ptr = dst, *end = dst + count; value_ptr != end; @@ -47,56 +47,55 @@ static T *getUs(uint32_t *offset_ptr, T *dst, uint32_t count, return nullptr; } -uint8_t DataExtractor::getU8(uint32_t *offset_ptr) const { +uint8_t DataExtractor::getU8(uint64_t *offset_ptr) const { return getU<uint8_t>(offset_ptr, this, IsLittleEndian, Data.data()); } uint8_t * -DataExtractor::getU8(uint32_t *offset_ptr, uint8_t *dst, uint32_t count) const { +DataExtractor::getU8(uint64_t *offset_ptr, uint8_t *dst, uint32_t count) const { return getUs<uint8_t>(offset_ptr, dst, count, this, IsLittleEndian, Data.data()); } - -uint16_t DataExtractor::getU16(uint32_t *offset_ptr) const { +uint16_t DataExtractor::getU16(uint64_t *offset_ptr) const { return getU<uint16_t>(offset_ptr, this, IsLittleEndian, Data.data()); } -uint16_t *DataExtractor::getU16(uint32_t *offset_ptr, uint16_t *dst, +uint16_t *DataExtractor::getU16(uint64_t *offset_ptr, uint16_t *dst, uint32_t count) const { return getUs<uint16_t>(offset_ptr, dst, count, this, IsLittleEndian, Data.data()); } -uint32_t DataExtractor::getU24(uint32_t *offset_ptr) const { +uint32_t DataExtractor::getU24(uint64_t *offset_ptr) const { uint24_t ExtractedVal = getU<uint24_t>(offset_ptr, this, IsLittleEndian, Data.data()); // The 3 bytes are in the correct byte order for the host. return ExtractedVal.getAsUint32(sys::IsLittleEndianHost); } -uint32_t DataExtractor::getU32(uint32_t *offset_ptr) const { +uint32_t DataExtractor::getU32(uint64_t *offset_ptr) const { return getU<uint32_t>(offset_ptr, this, IsLittleEndian, Data.data()); } -uint32_t *DataExtractor::getU32(uint32_t *offset_ptr, uint32_t *dst, +uint32_t *DataExtractor::getU32(uint64_t *offset_ptr, uint32_t *dst, uint32_t count) const { return getUs<uint32_t>(offset_ptr, dst, count, this, IsLittleEndian, Data.data()); } -uint64_t DataExtractor::getU64(uint32_t *offset_ptr) const { +uint64_t DataExtractor::getU64(uint64_t *offset_ptr) const { return getU<uint64_t>(offset_ptr, this, IsLittleEndian, Data.data()); } -uint64_t *DataExtractor::getU64(uint32_t *offset_ptr, uint64_t *dst, +uint64_t *DataExtractor::getU64(uint64_t *offset_ptr, uint64_t *dst, uint32_t count) const { return getUs<uint64_t>(offset_ptr, dst, count, this, IsLittleEndian, Data.data()); } uint64_t -DataExtractor::getUnsigned(uint32_t *offset_ptr, uint32_t byte_size) const { +DataExtractor::getUnsigned(uint64_t *offset_ptr, uint32_t byte_size) const { switch (byte_size) { case 1: return getU8(offset_ptr); @@ -111,7 +110,7 @@ DataExtractor::getUnsigned(uint32_t *offset_ptr, uint32_t byte_size) const { } int64_t -DataExtractor::getSigned(uint32_t *offset_ptr, uint32_t byte_size) const { +DataExtractor::getSigned(uint64_t *offset_ptr, uint32_t byte_size) const { switch (byte_size) { case 1: return (int8_t)getU8(offset_ptr); @@ -125,8 +124,8 @@ DataExtractor::getSigned(uint32_t *offset_ptr, uint32_t byte_size) const { llvm_unreachable("getSigned unhandled case!"); } -const char *DataExtractor::getCStr(uint32_t *offset_ptr) const { - uint32_t offset = *offset_ptr; +const char *DataExtractor::getCStr(uint64_t *offset_ptr) const { + uint64_t offset = *offset_ptr; StringRef::size_type pos = Data.find('\0', offset); if (pos != StringRef::npos) { *offset_ptr = pos + 1; @@ -135,17 +134,17 @@ const char *DataExtractor::getCStr(uint32_t *offset_ptr) const { return nullptr; } -StringRef DataExtractor::getCStrRef(uint32_t *OffsetPtr) const { - uint32_t Start = *OffsetPtr; +StringRef DataExtractor::getCStrRef(uint64_t *offset_ptr) const { + uint64_t Start = *offset_ptr; StringRef::size_type Pos = Data.find('\0', Start); if (Pos != StringRef::npos) { - *OffsetPtr = Pos + 1; + *offset_ptr = Pos + 1; return StringRef(Data.data() + Start, Pos - Start); } return StringRef(); } -uint64_t DataExtractor::getULEB128(uint32_t *offset_ptr) const { +uint64_t DataExtractor::getULEB128(uint64_t *offset_ptr) const { assert(*offset_ptr <= Data.size()); const char *error; @@ -159,7 +158,7 @@ uint64_t DataExtractor::getULEB128(uint32_t *offset_ptr) const { return result; } -int64_t DataExtractor::getSLEB128(uint32_t *offset_ptr) const { +int64_t DataExtractor::getSLEB128(uint64_t *offset_ptr) const { assert(*offset_ptr <= Data.size()); const char *error; @@ -172,3 +171,88 @@ int64_t DataExtractor::getSLEB128(uint32_t *offset_ptr) const { *offset_ptr += bytes_read; return result; } + +// The following is temporary code aimed to preserve compatibility with +// existing code which uses 32-bit offsets. +// It will be removed when migration to 64-bit offsets is finished. + +namespace { + +class WrapOffset { + uint64_t offset64; + uint32_t *offset32_ptr; + +public: + WrapOffset(uint32_t *offset_ptr) + : offset64(*offset_ptr), offset32_ptr(offset_ptr) {} + ~WrapOffset() { *offset32_ptr = offset64; } + operator uint64_t *() { return &offset64; } +}; + +} + +uint8_t DataExtractor::getU8(uint32_t *offset_ptr) const { + return getU8(WrapOffset(offset_ptr)); +} + +uint8_t * +DataExtractor::getU8(uint32_t *offset_ptr, uint8_t *dst, uint32_t count) const { + return getU8(WrapOffset(offset_ptr), dst, count); +} + +uint16_t DataExtractor::getU16(uint32_t *offset_ptr) const { + return getU16(WrapOffset(offset_ptr)); +} + +uint16_t *DataExtractor::getU16(uint32_t *offset_ptr, uint16_t *dst, + uint32_t count) const { + return getU16(WrapOffset(offset_ptr), dst, count); +} + +uint32_t DataExtractor::getU24(uint32_t *offset_ptr) const { + return getU24(WrapOffset(offset_ptr)); +} + +uint32_t DataExtractor::getU32(uint32_t *offset_ptr) const { + return getU32(WrapOffset(offset_ptr)); +} + +uint32_t *DataExtractor::getU32(uint32_t *offset_ptr, uint32_t *dst, + uint32_t count) const { + return getU32(WrapOffset(offset_ptr), dst, count); +} + +uint64_t DataExtractor::getU64(uint32_t *offset_ptr) const { + return getU64(WrapOffset(offset_ptr)); +} + +uint64_t *DataExtractor::getU64(uint32_t *offset_ptr, uint64_t *dst, + uint32_t count) const { + return getU64(WrapOffset(offset_ptr), dst, count); +} + +uint64_t +DataExtractor::getUnsigned(uint32_t *offset_ptr, uint32_t byte_size) const { + return getUnsigned(WrapOffset(offset_ptr), byte_size); +} + +int64_t +DataExtractor::getSigned(uint32_t *offset_ptr, uint32_t byte_size) const { + return getSigned(WrapOffset(offset_ptr), byte_size); +} + +const char *DataExtractor::getCStr(uint32_t *offset_ptr) const { + return getCStr(WrapOffset(offset_ptr)); +} + +StringRef DataExtractor::getCStrRef(uint32_t *offset_ptr) const { + return getCStrRef(WrapOffset(offset_ptr)); +} + +uint64_t DataExtractor::getULEB128(uint32_t *offset_ptr) const { + return getULEB128(WrapOffset(offset_ptr)); +} + +int64_t DataExtractor::getSLEB128(uint32_t *offset_ptr) const { + return getSLEB128(WrapOffset(offset_ptr)); +} |