forked from OSchip/llvm-project
Revert "[llvm-readobj] [ARMWinEH] Fix handling of relocations and symbol offsets"
This reverts commit 3778924088
.
The added test fails on at least one buildbot, by printing a reversed
combination, printing "func3_xdata +0x18 (0x8)" while it's supposed to
be "func3_xdata +0x8 (0x18)", see e.g.
https://lab.llvm.org/buildbot/#/builders/107/builds/7269. Currently
no idea how that could happen, but reverting until it can be figured
out.
This commit is contained in:
parent
96ec6d91e4
commit
5bf2ef9d86
|
@ -1,59 +0,0 @@
|
||||||
# Check that we resolve the function name properly
|
|
||||||
|
|
||||||
# RUN: yaml2obj %s -o %t.obj
|
|
||||||
# RUN: llvm-readobj --unwind %t.obj | FileCheck %s
|
|
||||||
|
|
||||||
# CHECK: Function: entry (0x140001000)
|
|
||||||
|
|
||||||
--- !COFF
|
|
||||||
OptionalHeader:
|
|
||||||
AddressOfEntryPoint: 4096
|
|
||||||
ImageBase: 5368709120
|
|
||||||
SectionAlignment: 4096
|
|
||||||
FileAlignment: 512
|
|
||||||
MajorOperatingSystemVersion: 6
|
|
||||||
MinorOperatingSystemVersion: 0
|
|
||||||
MajorImageVersion: 0
|
|
||||||
MinorImageVersion: 0
|
|
||||||
MajorSubsystemVersion: 6
|
|
||||||
MinorSubsystemVersion: 0
|
|
||||||
Subsystem: IMAGE_SUBSYSTEM_WINDOWS_CUI
|
|
||||||
DLLCharacteristics: [ IMAGE_DLL_CHARACTERISTICS_HIGH_ENTROPY_VA, IMAGE_DLL_CHARACTERISTICS_DYNAMIC_BASE, IMAGE_DLL_CHARACTERISTICS_NX_COMPAT, IMAGE_DLL_CHARACTERISTICS_TERMINAL_SERVER_AWARE ]
|
|
||||||
SizeOfStackReserve: 1048576
|
|
||||||
SizeOfStackCommit: 4096
|
|
||||||
SizeOfHeapReserve: 1048576
|
|
||||||
SizeOfHeapCommit: 4096
|
|
||||||
header:
|
|
||||||
Machine: IMAGE_FILE_MACHINE_ARM64
|
|
||||||
Characteristics: [ IMAGE_FILE_EXECUTABLE_IMAGE, IMAGE_FILE_LARGE_ADDRESS_AWARE ]
|
|
||||||
sections:
|
|
||||||
- Name: .text
|
|
||||||
Characteristics: [ IMAGE_SCN_CNT_CODE, IMAGE_SCN_MEM_EXECUTE, IMAGE_SCN_MEM_READ ]
|
|
||||||
VirtualAddress: 4096
|
|
||||||
VirtualSize: 20
|
|
||||||
SectionData: FD7BBFA9FD0300911F2003D5FD7BC1A8C0035FD6
|
|
||||||
- Name: .pdata
|
|
||||||
Characteristics: [ IMAGE_SCN_CNT_INITIALIZED_DATA, IMAGE_SCN_MEM_READ ]
|
|
||||||
VirtualAddress: 8192
|
|
||||||
VirtualSize: 8
|
|
||||||
SectionData: '001000001500E000'
|
|
||||||
symbols:
|
|
||||||
- Name: .text
|
|
||||||
Value: 0
|
|
||||||
SectionNumber: 1
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
- Name: .pdata
|
|
||||||
Value: 0
|
|
||||||
SectionNumber: 2
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
- Name: entry
|
|
||||||
Value: 0
|
|
||||||
SectionNumber: 1
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_FUNCTION
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_EXTERNAL
|
|
||||||
...
|
|
|
@ -1,196 +0,0 @@
|
||||||
# Test reading an ExceptionRecord which is referenced in different ways:
|
|
||||||
# - Relocation against base of .xdata record, immediate offset in .pdata
|
|
||||||
# (what LLVM produces)
|
|
||||||
# - Relocation against symbol in .xdata, no immediate offset in .pdata
|
|
||||||
# (what MSVC produces)
|
|
||||||
# - Combination of the two above (unlikely to occur in the wild, but for
|
|
||||||
# testing the consistency of the code)
|
|
||||||
|
|
||||||
# RUN: yaml2obj %s -o %t.obj
|
|
||||||
# RUN: llvm-readobj --unwind %t.obj | FileCheck %s
|
|
||||||
|
|
||||||
# CHECK: UnwindInformation [
|
|
||||||
# CHECK-NEXT: RuntimeFunction {
|
|
||||||
# CHECK-NEXT: Function: func (0x0)
|
|
||||||
# CHECK-NEXT: ExceptionRecord: .xdata (0x0)
|
|
||||||
# CHECK-NEXT: ExceptionData {
|
|
||||||
# CHECK-NEXT: FunctionLength: 4
|
|
||||||
# CHECK-NEXT: Version: 0
|
|
||||||
# CHECK-NEXT: ExceptionData: No
|
|
||||||
# CHECK-NEXT: EpiloguePacked: No
|
|
||||||
# CHECK-NEXT: EpilogueScopes: 0
|
|
||||||
# CHECK-NEXT: ByteCodeLength: 4
|
|
||||||
# CHECK-NEXT: Prologue [
|
|
||||||
# CHECK-NEXT: 0xd400 ; str x19, [sp, #-8]!
|
|
||||||
# CHECK-NEXT: 0xe4 ; end
|
|
||||||
# CHECK-NEXT: ]
|
|
||||||
# CHECK-NEXT: EpilogueScopes [
|
|
||||||
# CHECK-NEXT: ]
|
|
||||||
# CHECK-NEXT: }
|
|
||||||
# CHECK-NEXT: }
|
|
||||||
# CHECK-NEXT: RuntimeFunction {
|
|
||||||
# CHECK-NEXT: Function: func2 (0x4)
|
|
||||||
# CHECK-NEXT: ExceptionRecord: .xdata +0x8 (0x8)
|
|
||||||
# CHECK-NEXT: ExceptionData {
|
|
||||||
# CHECK-NEXT: FunctionLength: 4
|
|
||||||
# CHECK-NEXT: Version: 0
|
|
||||||
# CHECK-NEXT: ExceptionData: No
|
|
||||||
# CHECK-NEXT: EpiloguePacked: No
|
|
||||||
# CHECK-NEXT: EpilogueScopes: 0
|
|
||||||
# CHECK-NEXT: ByteCodeLength: 4
|
|
||||||
# CHECK-NEXT: Prologue [
|
|
||||||
# CHECK-NEXT: 0xdc01 ; str d8, [sp, #8]
|
|
||||||
# CHECK-NEXT: 0xe4 ; end
|
|
||||||
# CHECK-NEXT: ]
|
|
||||||
# CHECK-NEXT: EpilogueScopes [
|
|
||||||
# CHECK-NEXT: ]
|
|
||||||
# CHECK-NEXT: }
|
|
||||||
# CHECK-NEXT: }
|
|
||||||
# CHECK-NEXT: RuntimeFunction {
|
|
||||||
# CHECK-NEXT: Function: func3 (0x8)
|
|
||||||
# CHECK-NEXT: ExceptionRecord: func3_xdata (0x10)
|
|
||||||
# CHECK-NEXT: ExceptionData {
|
|
||||||
# CHECK-NEXT: FunctionLength: 4
|
|
||||||
# CHECK-NEXT: Version: 0
|
|
||||||
# CHECK-NEXT: ExceptionData: No
|
|
||||||
# CHECK-NEXT: EpiloguePacked: No
|
|
||||||
# CHECK-NEXT: EpilogueScopes: 0
|
|
||||||
# CHECK-NEXT: ByteCodeLength: 4
|
|
||||||
# CHECK-NEXT: Prologue [
|
|
||||||
# CHECK-NEXT: 0xe1 ; mov fp, sp
|
|
||||||
# CHECK-NEXT: 0xe4 ; end
|
|
||||||
# CHECK-NEXT: ]
|
|
||||||
# CHECK-NEXT: EpilogueScopes [
|
|
||||||
# CHECK-NEXT: ]
|
|
||||||
# CHECK-NEXT: }
|
|
||||||
# CHECK-NEXT: }
|
|
||||||
# CHECK-NEXT: RuntimeFunction {
|
|
||||||
# CHECK-NEXT: Function: func4 (0xC)
|
|
||||||
# CHECK-NEXT: ExceptionRecord: func3_xdata +0x8 (0x18)
|
|
||||||
# CHECK-NEXT: ExceptionData {
|
|
||||||
# CHECK-NEXT: FunctionLength: 4
|
|
||||||
# CHECK-NEXT: Version: 0
|
|
||||||
# CHECK-NEXT: ExceptionData: No
|
|
||||||
# CHECK-NEXT: EpiloguePacked: No
|
|
||||||
# CHECK-NEXT: EpilogueScopes: 0
|
|
||||||
# CHECK-NEXT: ByteCodeLength: 4
|
|
||||||
# CHECK-NEXT: Prologue [
|
|
||||||
# CHECK-NEXT: 0x81 ; stp x29, x30, [sp, #-16]!
|
|
||||||
# CHECK-NEXT: 0xe4 ; end
|
|
||||||
# CHECK-NEXT: ]
|
|
||||||
# CHECK-NEXT: EpilogueScopes [
|
|
||||||
# CHECK-NEXT: ]
|
|
||||||
# CHECK-NEXT: }
|
|
||||||
# CHECK-NEXT: }
|
|
||||||
# CHECK-NEXT: ]
|
|
||||||
|
|
||||||
--- !COFF
|
|
||||||
header:
|
|
||||||
Machine: IMAGE_FILE_MACHINE_ARM64
|
|
||||||
Characteristics: [ ]
|
|
||||||
sections:
|
|
||||||
- Name: .text
|
|
||||||
Characteristics: [ IMAGE_SCN_CNT_CODE, IMAGE_SCN_MEM_EXECUTE, IMAGE_SCN_MEM_READ ]
|
|
||||||
Alignment: 4
|
|
||||||
SectionData: F38F1FF8E80700FDFD030091FD7BBFA9
|
|
||||||
- Name: .xdata
|
|
||||||
Characteristics: [ IMAGE_SCN_CNT_INITIALIZED_DATA, IMAGE_SCN_MEM_READ ]
|
|
||||||
Alignment: 4
|
|
||||||
SectionData: 01000008D400E4E301000008DC01E4E301000008E1E4E3E30100000881E4E3E3
|
|
||||||
- Name: .pdata
|
|
||||||
Characteristics: [ IMAGE_SCN_CNT_INITIALIZED_DATA, IMAGE_SCN_MEM_READ ]
|
|
||||||
Alignment: 4
|
|
||||||
SectionData: '0000000000000000000000000800000000000000000000000000000008000000'
|
|
||||||
Relocations:
|
|
||||||
- VirtualAddress: 0
|
|
||||||
SymbolName: func
|
|
||||||
Type: IMAGE_REL_ARM64_ADDR32NB
|
|
||||||
- VirtualAddress: 4
|
|
||||||
SymbolName: .xdata
|
|
||||||
Type: IMAGE_REL_ARM64_ADDR32NB
|
|
||||||
- VirtualAddress: 8
|
|
||||||
SymbolName: func2
|
|
||||||
Type: IMAGE_REL_ARM64_ADDR32NB
|
|
||||||
- VirtualAddress: 12
|
|
||||||
SymbolName: .xdata
|
|
||||||
Type: IMAGE_REL_ARM64_ADDR32NB
|
|
||||||
- VirtualAddress: 16
|
|
||||||
SymbolName: func3
|
|
||||||
Type: IMAGE_REL_ARM64_ADDR32NB
|
|
||||||
- VirtualAddress: 20
|
|
||||||
SymbolName: func3_xdata
|
|
||||||
Type: IMAGE_REL_ARM64_ADDR32NB
|
|
||||||
- VirtualAddress: 24
|
|
||||||
SymbolName: func4
|
|
||||||
Type: IMAGE_REL_ARM64_ADDR32NB
|
|
||||||
- VirtualAddress: 28
|
|
||||||
SymbolName: func3_xdata
|
|
||||||
Type: IMAGE_REL_ARM64_ADDR32NB
|
|
||||||
symbols:
|
|
||||||
- Name: .text
|
|
||||||
Value: 0
|
|
||||||
SectionNumber: 1
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
SectionDefinition:
|
|
||||||
Length: 16
|
|
||||||
NumberOfRelocations: 0
|
|
||||||
NumberOfLinenumbers: 0
|
|
||||||
CheckSum: 2581817939
|
|
||||||
Number: 1
|
|
||||||
- Name: .xdata
|
|
||||||
Value: 0
|
|
||||||
SectionNumber: 2
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
SectionDefinition:
|
|
||||||
Length: 32
|
|
||||||
NumberOfRelocations: 0
|
|
||||||
NumberOfLinenumbers: 0
|
|
||||||
CheckSum: 3086971960
|
|
||||||
Number: 2
|
|
||||||
- Name: .pdata
|
|
||||||
Value: 0
|
|
||||||
SectionNumber: 3
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
SectionDefinition:
|
|
||||||
Length: 32
|
|
||||||
NumberOfRelocations: 8
|
|
||||||
NumberOfLinenumbers: 0
|
|
||||||
CheckSum: 0
|
|
||||||
Number: 3
|
|
||||||
- Name: func
|
|
||||||
Value: 0
|
|
||||||
SectionNumber: 1
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
- Name: func2
|
|
||||||
Value: 4
|
|
||||||
SectionNumber: 1
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
- Name: func3
|
|
||||||
Value: 8
|
|
||||||
SectionNumber: 1
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
- Name: func4
|
|
||||||
Value: 12
|
|
||||||
SectionNumber: 1
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
- Name: func3_xdata
|
|
||||||
Value: 16
|
|
||||||
SectionNumber: 2
|
|
||||||
SimpleType: IMAGE_SYM_TYPE_NULL
|
|
||||||
ComplexType: IMAGE_SYM_DTYPE_NULL
|
|
||||||
StorageClass: IMAGE_SYM_CLASS_STATIC
|
|
||||||
...
|
|
|
@ -238,41 +238,6 @@ ErrorOr<SymbolRef> Decoder::getRelocatedSymbol(const COFFObjectFile &,
|
||||||
return inconvertibleErrorCode();
|
return inconvertibleErrorCode();
|
||||||
}
|
}
|
||||||
|
|
||||||
ErrorOr<SymbolRef> Decoder::getSymbolForLocation(
|
|
||||||
const COFFObjectFile &COFF, const SectionRef &Section,
|
|
||||||
uint64_t OffsetInSection, uint64_t ImmediateOffset, uint64_t &SymbolAddress,
|
|
||||||
uint64_t &SymbolOffset, bool FunctionOnly) {
|
|
||||||
// Try to locate a relocation that points at the offset in the section
|
|
||||||
ErrorOr<SymbolRef> SymOrErr =
|
|
||||||
getRelocatedSymbol(COFF, Section, OffsetInSection);
|
|
||||||
if (SymOrErr) {
|
|
||||||
// We found a relocation symbol; the immediate offset needs to be added
|
|
||||||
// to the symbol address.
|
|
||||||
SymbolOffset = ImmediateOffset;
|
|
||||||
|
|
||||||
Expected<uint64_t> AddressOrErr = SymOrErr->getAddress();
|
|
||||||
if (!AddressOrErr) {
|
|
||||||
std::string Buf;
|
|
||||||
llvm::raw_string_ostream OS(Buf);
|
|
||||||
logAllUnhandledErrors(AddressOrErr.takeError(), OS);
|
|
||||||
OS.flush();
|
|
||||||
report_fatal_error(Buf);
|
|
||||||
}
|
|
||||||
// We apply SymbolOffset here directly. We return it separately to allow
|
|
||||||
// the caller to print it as an offset on the symbol name.
|
|
||||||
SymbolAddress = *AddressOrErr + SymbolOffset;
|
|
||||||
} else {
|
|
||||||
// No matching relocation found; operating on a linked image. Try to
|
|
||||||
// find a descriptive symbol if possible. The immediate offset contains
|
|
||||||
// the image relative address, and we shouldn't add any offset to the
|
|
||||||
// symbol.
|
|
||||||
SymbolAddress = COFF.getImageBase() + ImmediateOffset;
|
|
||||||
SymbolOffset = 0;
|
|
||||||
SymOrErr = getSymbol(COFF, SymbolAddress, FunctionOnly);
|
|
||||||
}
|
|
||||||
return SymOrErr;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool Decoder::opcode_0xxxxxxx(const uint8_t *OC, unsigned &Offset,
|
bool Decoder::opcode_0xxxxxxx(const uint8_t *OC, unsigned &Offset,
|
||||||
unsigned Length, bool Prologue) {
|
unsigned Length, bool Prologue) {
|
||||||
uint8_t Imm = OC[Offset] & 0x7f;
|
uint8_t Imm = OC[Offset] & 0x7f;
|
||||||
|
@ -954,16 +919,16 @@ bool Decoder::dumpXDataRecord(const COFFObjectFile &COFF,
|
||||||
}
|
}
|
||||||
|
|
||||||
if (XData.X()) {
|
if (XData.X()) {
|
||||||
|
const uint64_t Address = COFF.getImageBase() + XData.ExceptionHandlerRVA();
|
||||||
const uint32_t Parameter = XData.ExceptionHandlerParameter();
|
const uint32_t Parameter = XData.ExceptionHandlerParameter();
|
||||||
const size_t HandlerOffset = HeaderWords(XData) +
|
const size_t HandlerOffset = HeaderWords(XData)
|
||||||
(XData.E() ? 0 : XData.EpilogueCount()) +
|
+ (XData.E() ? 0 : XData.EpilogueCount())
|
||||||
XData.CodeWords();
|
+ XData.CodeWords();
|
||||||
|
|
||||||
uint64_t Address, SymbolOffset;
|
ErrorOr<SymbolRef> Symbol = getRelocatedSymbol(
|
||||||
ErrorOr<SymbolRef> Symbol = getSymbolForLocation(
|
COFF, Section, Offset + HandlerOffset * sizeof(uint32_t));
|
||||||
COFF, Section, Offset + HandlerOffset * sizeof(uint32_t),
|
if (!Symbol)
|
||||||
XData.ExceptionHandlerRVA(), Address, SymbolOffset,
|
Symbol = getSymbol(COFF, Address, /*FunctionOnly=*/true);
|
||||||
/*FunctionOnly=*/true);
|
|
||||||
if (!Symbol) {
|
if (!Symbol) {
|
||||||
ListScope EHS(SW, "ExceptionHandler");
|
ListScope EHS(SW, "ExceptionHandler");
|
||||||
SW.printHex("Routine", Address);
|
SW.printHex("Routine", Address);
|
||||||
|
@ -981,7 +946,7 @@ bool Decoder::dumpXDataRecord(const COFFObjectFile &COFF,
|
||||||
}
|
}
|
||||||
|
|
||||||
ListScope EHS(SW, "ExceptionHandler");
|
ListScope EHS(SW, "ExceptionHandler");
|
||||||
SW.printString("Routine", formatSymbol(*Name, Address, SymbolOffset));
|
SW.printString("Routine", formatSymbol(*Name, Address));
|
||||||
SW.printHex("Parameter", Parameter);
|
SW.printHex("Parameter", Parameter);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -994,15 +959,14 @@ bool Decoder::dumpUnpackedEntry(const COFFObjectFile &COFF,
|
||||||
assert(RF.Flag() == RuntimeFunctionFlag::RFF_Unpacked &&
|
assert(RF.Flag() == RuntimeFunctionFlag::RFF_Unpacked &&
|
||||||
"packed entry cannot be treated as an unpacked entry");
|
"packed entry cannot be treated as an unpacked entry");
|
||||||
|
|
||||||
uint64_t FunctionAddress, FunctionOffset;
|
ErrorOr<SymbolRef> Function = getRelocatedSymbol(COFF, Section, Offset);
|
||||||
ErrorOr<SymbolRef> Function = getSymbolForLocation(
|
if (!Function)
|
||||||
COFF, Section, Offset, RF.BeginAddress, FunctionAddress, FunctionOffset,
|
Function = getSymbol(COFF, COFF.getImageBase() + RF.BeginAddress,
|
||||||
/*FunctionOnly=*/true);
|
/*FunctionOnly=*/true);
|
||||||
|
|
||||||
uint64_t XDataAddress, XDataOffset;
|
ErrorOr<SymbolRef> XDataRecord = getRelocatedSymbol(COFF, Section, Offset + 4);
|
||||||
ErrorOr<SymbolRef> XDataRecord = getSymbolForLocation(
|
if (!XDataRecord)
|
||||||
COFF, Section, Offset + 4, RF.ExceptionInformationRVA(), XDataAddress,
|
XDataRecord = getSymbol(COFF, RF.ExceptionInformationRVA());
|
||||||
XDataOffset);
|
|
||||||
|
|
||||||
if (!RF.BeginAddress && !Function)
|
if (!RF.BeginAddress && !Function)
|
||||||
return false;
|
return false;
|
||||||
|
@ -1010,6 +974,7 @@ bool Decoder::dumpUnpackedEntry(const COFFObjectFile &COFF,
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
StringRef FunctionName;
|
StringRef FunctionName;
|
||||||
|
uint64_t FunctionAddress;
|
||||||
if (Function) {
|
if (Function) {
|
||||||
Expected<StringRef> FunctionNameOrErr = Function->getName();
|
Expected<StringRef> FunctionNameOrErr = Function->getName();
|
||||||
if (!FunctionNameOrErr) {
|
if (!FunctionNameOrErr) {
|
||||||
|
@ -1020,10 +985,20 @@ bool Decoder::dumpUnpackedEntry(const COFFObjectFile &COFF,
|
||||||
report_fatal_error(Buf);
|
report_fatal_error(Buf);
|
||||||
}
|
}
|
||||||
FunctionName = *FunctionNameOrErr;
|
FunctionName = *FunctionNameOrErr;
|
||||||
|
Expected<uint64_t> FunctionAddressOrErr = Function->getAddress();
|
||||||
|
if (!FunctionAddressOrErr) {
|
||||||
|
std::string Buf;
|
||||||
|
llvm::raw_string_ostream OS(Buf);
|
||||||
|
logAllUnhandledErrors(FunctionAddressOrErr.takeError(), OS);
|
||||||
|
OS.flush();
|
||||||
|
report_fatal_error(Buf);
|
||||||
|
}
|
||||||
|
FunctionAddress = *FunctionAddressOrErr;
|
||||||
|
} else {
|
||||||
|
FunctionAddress = COFF.getImageBase() + RF.BeginAddress;
|
||||||
}
|
}
|
||||||
|
|
||||||
SW.printString("Function",
|
SW.printString("Function", formatSymbol(FunctionName, FunctionAddress));
|
||||||
formatSymbol(FunctionName, FunctionAddress, FunctionOffset));
|
|
||||||
|
|
||||||
if (XDataRecord) {
|
if (XDataRecord) {
|
||||||
Expected<StringRef> Name = XDataRecord->getName();
|
Expected<StringRef> Name = XDataRecord->getName();
|
||||||
|
@ -1035,8 +1010,17 @@ bool Decoder::dumpUnpackedEntry(const COFFObjectFile &COFF,
|
||||||
report_fatal_error(Buf);
|
report_fatal_error(Buf);
|
||||||
}
|
}
|
||||||
|
|
||||||
SW.printString("ExceptionRecord",
|
Expected<uint64_t> AddressOrErr = XDataRecord->getAddress();
|
||||||
formatSymbol(*Name, XDataAddress, XDataOffset));
|
if (!AddressOrErr) {
|
||||||
|
std::string Buf;
|
||||||
|
llvm::raw_string_ostream OS(Buf);
|
||||||
|
logAllUnhandledErrors(AddressOrErr.takeError(), OS);
|
||||||
|
OS.flush();
|
||||||
|
report_fatal_error(Buf);
|
||||||
|
}
|
||||||
|
uint64_t Address = *AddressOrErr;
|
||||||
|
|
||||||
|
SW.printString("ExceptionRecord", formatSymbol(*Name, Address));
|
||||||
|
|
||||||
Expected<section_iterator> SIOrErr = XDataRecord->getSection();
|
Expected<section_iterator> SIOrErr = XDataRecord->getSection();
|
||||||
if (!SIOrErr) {
|
if (!SIOrErr) {
|
||||||
|
@ -1046,15 +1030,18 @@ bool Decoder::dumpUnpackedEntry(const COFFObjectFile &COFF,
|
||||||
}
|
}
|
||||||
section_iterator SI = *SIOrErr;
|
section_iterator SI = *SIOrErr;
|
||||||
|
|
||||||
return dumpXDataRecord(COFF, *SI, FunctionAddress, XDataAddress);
|
// FIXME: Do we need to add an offset from the relocation?
|
||||||
|
return dumpXDataRecord(COFF, *SI, FunctionAddress,
|
||||||
|
RF.ExceptionInformationRVA());
|
||||||
} else {
|
} else {
|
||||||
SW.printString("ExceptionRecord", formatSymbol("", XDataAddress));
|
uint64_t Address = COFF.getImageBase() + RF.ExceptionInformationRVA();
|
||||||
|
SW.printString("ExceptionRecord", formatSymbol("", Address));
|
||||||
|
|
||||||
ErrorOr<SectionRef> Section = getSectionContaining(COFF, XDataAddress);
|
ErrorOr<SectionRef> Section = getSectionContaining(COFF, Address);
|
||||||
if (!Section)
|
if (!Section)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
return dumpXDataRecord(COFF, *Section, FunctionAddress, XDataAddress);
|
return dumpXDataRecord(COFF, *Section, FunctionAddress, Address);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1065,12 +1052,12 @@ bool Decoder::dumpPackedEntry(const object::COFFObjectFile &COFF,
|
||||||
RF.Flag() == RuntimeFunctionFlag::RFF_PackedFragment) &&
|
RF.Flag() == RuntimeFunctionFlag::RFF_PackedFragment) &&
|
||||||
"unpacked entry cannot be treated as a packed entry");
|
"unpacked entry cannot be treated as a packed entry");
|
||||||
|
|
||||||
uint64_t FunctionAddress, FunctionOffset;
|
ErrorOr<SymbolRef> Function = getRelocatedSymbol(COFF, Section, Offset);
|
||||||
ErrorOr<SymbolRef> Function = getSymbolForLocation(
|
if (!Function)
|
||||||
COFF, Section, Offset, RF.BeginAddress, FunctionAddress, FunctionOffset,
|
Function = getSymbol(COFF, RF.BeginAddress, /*FunctionOnly=*/true);
|
||||||
/*FunctionOnly=*/true);
|
|
||||||
|
|
||||||
StringRef FunctionName;
|
StringRef FunctionName;
|
||||||
|
uint64_t FunctionAddress;
|
||||||
if (Function) {
|
if (Function) {
|
||||||
Expected<StringRef> FunctionNameOrErr = Function->getName();
|
Expected<StringRef> FunctionNameOrErr = Function->getName();
|
||||||
if (!FunctionNameOrErr) {
|
if (!FunctionNameOrErr) {
|
||||||
|
@ -1081,10 +1068,20 @@ bool Decoder::dumpPackedEntry(const object::COFFObjectFile &COFF,
|
||||||
report_fatal_error(Buf);
|
report_fatal_error(Buf);
|
||||||
}
|
}
|
||||||
FunctionName = *FunctionNameOrErr;
|
FunctionName = *FunctionNameOrErr;
|
||||||
|
Expected<uint64_t> FunctionAddressOrErr = Function->getAddress();
|
||||||
|
if (!FunctionAddressOrErr) {
|
||||||
|
std::string Buf;
|
||||||
|
llvm::raw_string_ostream OS(Buf);
|
||||||
|
logAllUnhandledErrors(FunctionAddressOrErr.takeError(), OS);
|
||||||
|
OS.flush();
|
||||||
|
report_fatal_error(Buf);
|
||||||
|
}
|
||||||
|
FunctionAddress = *FunctionAddressOrErr;
|
||||||
|
} else {
|
||||||
|
FunctionAddress = COFF.getPE32Header()->ImageBase + RF.BeginAddress;
|
||||||
}
|
}
|
||||||
|
|
||||||
SW.printString("Function",
|
SW.printString("Function", formatSymbol(FunctionName, FunctionAddress));
|
||||||
formatSymbol(FunctionName, FunctionAddress, FunctionOffset));
|
|
||||||
if (!isAArch64)
|
if (!isAArch64)
|
||||||
SW.printBoolean("Fragment",
|
SW.printBoolean("Fragment",
|
||||||
RF.Flag() == RuntimeFunctionFlag::RFF_PackedFragment);
|
RF.Flag() == RuntimeFunctionFlag::RFF_PackedFragment);
|
||||||
|
@ -1107,12 +1104,12 @@ bool Decoder::dumpPackedARM64Entry(const object::COFFObjectFile &COFF,
|
||||||
RF.Flag() == RuntimeFunctionFlag::RFF_PackedFragment) &&
|
RF.Flag() == RuntimeFunctionFlag::RFF_PackedFragment) &&
|
||||||
"unpacked entry cannot be treated as a packed entry");
|
"unpacked entry cannot be treated as a packed entry");
|
||||||
|
|
||||||
uint64_t FunctionAddress, FunctionOffset;
|
ErrorOr<SymbolRef> Function = getRelocatedSymbol(COFF, Section, Offset);
|
||||||
ErrorOr<SymbolRef> Function = getSymbolForLocation(
|
if (!Function)
|
||||||
COFF, Section, Offset, RF.BeginAddress, FunctionAddress, FunctionOffset,
|
Function = getSymbol(COFF, RF.BeginAddress, /*FunctionOnly=*/true);
|
||||||
/*FunctionOnly=*/true);
|
|
||||||
|
|
||||||
StringRef FunctionName;
|
StringRef FunctionName;
|
||||||
|
uint64_t FunctionAddress;
|
||||||
if (Function) {
|
if (Function) {
|
||||||
Expected<StringRef> FunctionNameOrErr = Function->getName();
|
Expected<StringRef> FunctionNameOrErr = Function->getName();
|
||||||
if (!FunctionNameOrErr) {
|
if (!FunctionNameOrErr) {
|
||||||
|
@ -1123,10 +1120,20 @@ bool Decoder::dumpPackedARM64Entry(const object::COFFObjectFile &COFF,
|
||||||
report_fatal_error(Buf);
|
report_fatal_error(Buf);
|
||||||
}
|
}
|
||||||
FunctionName = *FunctionNameOrErr;
|
FunctionName = *FunctionNameOrErr;
|
||||||
|
Expected<uint64_t> FunctionAddressOrErr = Function->getAddress();
|
||||||
|
if (!FunctionAddressOrErr) {
|
||||||
|
std::string Buf;
|
||||||
|
llvm::raw_string_ostream OS(Buf);
|
||||||
|
logAllUnhandledErrors(FunctionAddressOrErr.takeError(), OS);
|
||||||
|
OS.flush();
|
||||||
|
report_fatal_error(Buf);
|
||||||
|
}
|
||||||
|
FunctionAddress = *FunctionAddressOrErr;
|
||||||
|
} else {
|
||||||
|
FunctionAddress = COFF.getPE32PlusHeader()->ImageBase + RF.BeginAddress;
|
||||||
}
|
}
|
||||||
|
|
||||||
SW.printString("Function",
|
SW.printString("Function", formatSymbol(FunctionName, FunctionAddress));
|
||||||
formatSymbol(FunctionName, FunctionAddress, FunctionOffset));
|
|
||||||
SW.printBoolean("Fragment",
|
SW.printBoolean("Fragment",
|
||||||
RF.Flag() == RuntimeFunctionFlag::RFF_PackedFragment);
|
RF.Flag() == RuntimeFunctionFlag::RFF_PackedFragment);
|
||||||
SW.printNumber("FunctionLength", RF.FunctionLength());
|
SW.printNumber("FunctionLength", RF.FunctionLength());
|
||||||
|
|
|
@ -146,13 +146,6 @@ class Decoder {
|
||||||
getRelocatedSymbol(const object::COFFObjectFile &COFF,
|
getRelocatedSymbol(const object::COFFObjectFile &COFF,
|
||||||
const object::SectionRef &Section, uint64_t Offset);
|
const object::SectionRef &Section, uint64_t Offset);
|
||||||
|
|
||||||
ErrorOr<object::SymbolRef>
|
|
||||||
getSymbolForLocation(const object::COFFObjectFile &COFF,
|
|
||||||
const object::SectionRef &Section,
|
|
||||||
uint64_t OffsetInSection, uint64_t ImmediateOffset,
|
|
||||||
uint64_t &SymbolAddress, uint64_t &SymbolOffset,
|
|
||||||
bool FunctionOnly = false);
|
|
||||||
|
|
||||||
bool dumpXDataRecord(const object::COFFObjectFile &COFF,
|
bool dumpXDataRecord(const object::COFFObjectFile &COFF,
|
||||||
const object::SectionRef &Section,
|
const object::SectionRef &Section,
|
||||||
uint64_t FunctionAddress, uint64_t VA);
|
uint64_t FunctionAddress, uint64_t VA);
|
||||||
|
|
Loading…
Reference in New Issue