mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-11-23 11:13:28 +01:00
[llvm-readobj/llvm-readelf] - Improve/cleanup the error reporting API.
urrently we have the following functions for error reporting: -- LLVM_ATTRIBUTE_NORETURN void reportError(Twine Msg); void reportError(Error Err, StringRef Input); void reportWarning(Twine Msg); void reportWarning(StringRef Input, Error Err); void warn(llvm::Error Err); void error(std::error_code EC); --- Problems are: naming is inconsistent, arguments order is inconsistent, some of the functions looks excessive. After applying this patch we have: --- LLVM_ATTRIBUTE_NORETURN void reportError(Error Err, StringRef Input); LLVM_ATTRIBUTE_NORETURN void reportError(std::error_code EC, StringRef Input); void reportWarning(Error Err, StringRef Input); --- I'd be happy to remove reportError(std::error_code EC, StringRef Input) too, but it is used by COFF heavily. Test cases were updated, they show an improvement introduced. Differential revision: https://reviews.llvm.org/D66286 llvm-svn: 369190
This commit is contained in:
parent
fd5f9a7c78
commit
bdd80e6afb
@ -135,9 +135,9 @@ Symbols:
|
||||
## Check that llvm-readobj reports a warning if .dynsym has an invalid sh_entsize.
|
||||
|
||||
# RUN: yaml2obj %s --docnum=7 -o %t7
|
||||
# RUN: llvm-readobj --dyn-symbols %t7 2>&1 | FileCheck --check-prefix=INVALID-DYNSYM-SIZE %s
|
||||
# RUN: llvm-readobj --dyn-symbols %t7 2>&1 | FileCheck -DFILE=%t7 --check-prefix=INVALID-DYNSYM-SIZE %s
|
||||
|
||||
# INVALID-DYNSYM-SIZE: warning: invalid section size (48) or entity size (32)
|
||||
# INVALID-DYNSYM-SIZE: warning: '[[FILE]]': invalid section size (48) or entity size (32)
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
@ -409,9 +409,9 @@ Symbols:
|
||||
## Check llvm-readobj reports it.
|
||||
|
||||
# RUN: yaml2obj %s --docnum=20 -o %t20
|
||||
# RUN: not llvm-readobj -dt %t20 2>&1 | FileCheck --check-prefix=INVALID-VERSION %s
|
||||
# RUN: not llvm-readobj -dt %t20 2>&1 | FileCheck -DFILE=%t20 --check-prefix=INVALID-VERSION %s
|
||||
|
||||
# INVALID-VERSION: error: Invalid version entry
|
||||
# INVALID-VERSION: error: '[[FILE]]': Invalid version entry
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
@ -438,9 +438,9 @@ DynamicSymbols:
|
||||
## Check llvm-readobj reports it.
|
||||
|
||||
# RUN: yaml2obj %s --docnum=21 -o %t21
|
||||
# RUN: llvm-readobj --dynamic-table %t21 2>&1 | FileCheck --check-prefix=INVALID-DTSTRTAB %s
|
||||
# RUN: llvm-readobj --dynamic-table %t21 2>&1 | FileCheck -DFILE=%t21 --check-prefix=INVALID-DTSTRTAB %s
|
||||
|
||||
# INVALID-DTSTRTAB: warning: Unable to parse DT_STRTAB: virtual address is not in any segment: 0xffff0000
|
||||
# INVALID-DTSTRTAB: warning: '[[FILE]]': Unable to parse DT_STRTAB: virtual address is not in any segment: 0xffff0000
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
@ -468,17 +468,17 @@ ProgramHeaders:
|
||||
|
||||
# RUN: llvm-readobj --dyn-relocations \
|
||||
# RUN: %p/Inputs/corrupt-invalid-relocation-size.elf.x86-64 2>&1 \
|
||||
# RUN: | FileCheck --check-prefix=RELOC-BROKEN-ENTSIZE %s
|
||||
# RUN: | FileCheck -DFILE=%p/Inputs/corrupt-invalid-relocation-size.elf.x86-64 --check-prefix=RELOC-BROKEN-ENTSIZE %s
|
||||
|
||||
# RELOC-BROKEN-ENTSIZE: warning: invalid section size (24) or entity size (25)
|
||||
# RELOC-BROKEN-ENTSIZE: warning: '[[FILE]]': invalid section size (24) or entity size (25)
|
||||
|
||||
## Check that llvm-readobj reports a warning when .dynamic section has an invalid
|
||||
## size, which isn't a multiple of the dynamic entry size.
|
||||
|
||||
# RUN: yaml2obj %s --docnum=22 -o %t22
|
||||
# RUN: llvm-readobj --dyn-relocations %t22 2>&1 | FileCheck --check-prefix=DYN-TABLE-SIZE %s
|
||||
# RUN: llvm-readobj --dyn-relocations %t22 2>&1 | FileCheck -DFILE=%t22 --check-prefix=DYN-TABLE-SIZE %s
|
||||
|
||||
# DYN-TABLE-SIZE: warning: invalid section size (1) or entity size (16)
|
||||
# DYN-TABLE-SIZE: warning: '[[FILE]]': invalid section size (1) or entity size (16)
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
@ -495,9 +495,9 @@ Sections:
|
||||
## than the object size. Check llvm-readobj reports it.
|
||||
|
||||
# RUN: yaml2obj %s --docnum=23 -o %t23
|
||||
# RUN: llvm-readobj --dyn-relocations %t23 2>&1 | FileCheck --check-prefix=DYN-TABLE-PHDR %s
|
||||
# RUN: llvm-readobj --dyn-relocations %t23 2>&1 | FileCheck -DFILE=%t23 --check-prefix=DYN-TABLE-PHDR %s
|
||||
|
||||
# DYN-TABLE-PHDR: warning: PT_DYNAMIC segment offset + size exceeds the size of the file
|
||||
# DYN-TABLE-PHDR: warning: '[[FILE]]': PT_DYNAMIC segment offset + size exceeds the size of the file
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
@ -522,7 +522,7 @@ ProgramHeaders:
|
||||
|
||||
# RUN: yaml2obj %s --docnum=24 -o %t24
|
||||
# RUN: llvm-readobj --dyn-relocations %t24 2>&1 \
|
||||
# RUN: | FileCheck --check-prefix=DYN-TABLE-PHDR %s
|
||||
# RUN: | FileCheck -DFILE=%t24 --check-prefix=DYN-TABLE-PHDR %s
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
|
@ -3,10 +3,10 @@
|
||||
|
||||
## Case 1: sh_link is set to 0.
|
||||
# RUN: yaml2obj --docnum=1 %s -o %t1
|
||||
# RUN: llvm-readobj -S %t1 2>&1 | FileCheck %s --check-prefixes=LLVM,ERR
|
||||
# RUN: llvm-readelf -S %t1 2>&1 | FileCheck %s --check-prefixes=GNU,ERR
|
||||
# RUN: llvm-readobj -S %t1 2>&1 | FileCheck %s -DFILE=%t1 --check-prefixes=LLVM,ERR
|
||||
# RUN: llvm-readelf -S %t1 2>&1 | FileCheck %s -DFILE=%t1 --check-prefixes=GNU,ERR
|
||||
|
||||
# ERR: warning: invalid sh_type for string table section [index 0]: expected SHT_STRTAB, but got SHT_NULL
|
||||
# ERR: warning: '[[FILE]]': invalid sh_type for string table section [index 0]: expected SHT_STRTAB, but got SHT_NULL
|
||||
|
||||
# LLVM: Name: .dynsym
|
||||
# LLVM-NEXT: Type: SHT_DYNSYM
|
||||
@ -36,10 +36,10 @@ Sections:
|
||||
## Case 2: sh_link is set to 255, which is larger than the number of the sections.
|
||||
# RUN: yaml2obj --docnum=2 %s -o %t2
|
||||
|
||||
# RUN: llvm-readobj -S %t2 2>&1 | FileCheck %s --check-prefixes=LLVM2,ERR2
|
||||
# RUN: llvm-readelf -S %t2 2>&1 | FileCheck %s --check-prefixes=GNU2,ERR2
|
||||
# RUN: llvm-readobj -S %t2 2>&1 | FileCheck -DFILE=%t2 %s --check-prefixes=LLVM2,ERR2
|
||||
# RUN: llvm-readelf -S %t2 2>&1 | FileCheck -DFILE=%t2 %s --check-prefixes=GNU2,ERR2
|
||||
|
||||
# ERR2: warning: invalid section index
|
||||
# ERR2: warning: '[[FILE]]': invalid section index
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
|
@ -3,29 +3,29 @@
|
||||
|
||||
# RUN: yaml2obj %s --docnum=1 -o %t.bad-size
|
||||
# RUN: llvm-readobj --all %t.bad-size 2>&1 \
|
||||
# RUN: | FileCheck %s --implicit-check-not=warning --check-prefix WARN
|
||||
# RUN: | FileCheck %s -DFILE=%t.bad-size --implicit-check-not=warning --check-prefix WARN
|
||||
# RUN: llvm-readelf --all %t.bad-size 2>&1 \
|
||||
# RUN: | FileCheck %s --implicit-check-not=warning --check-prefix WARN-GNU
|
||||
# RUN: | FileCheck %s -DFILE=%t.bad-size --implicit-check-not=warning --check-prefix WARN-GNU
|
||||
|
||||
# WARN-NOT: warning
|
||||
# WARN: warning: invalid section size (4) or entity size (16)
|
||||
# WARN: warning: '[[FILE]]': invalid section size (4) or entity size (16)
|
||||
# WARN-EMPTY:
|
||||
# WARN-NEXT: File:
|
||||
# WARN: Symbols [
|
||||
# WARN: ]
|
||||
# WARN-EMPTY:
|
||||
## A warning is printed at the place where a normal dynamic table should be.
|
||||
# WARN-NEXT: warning: invalid section size (4) or entity size (16)
|
||||
# WARN-NEXT: warning: '[[FILE]]': invalid section size (4) or entity size (16)
|
||||
# WARN-NEXT: ProgramHeaders [
|
||||
|
||||
# WARN-GNU-NOT: warning
|
||||
# WARN-GNU: warning: invalid section size (4) or entity size (16)
|
||||
# WARN-GNU: warning: '[[FILE]]': invalid section size (4) or entity size (16)
|
||||
# WARN-GNU-NEXT: ELF Header:
|
||||
# WARN-GNU: Symbol table '.symtab' contains 1 entries:
|
||||
# WARN-GNU: 0:
|
||||
# WARN-GNU-EMPTY:
|
||||
## A warning is printed at the place where a normal dynamic table should be.
|
||||
# WARN-GNU: warning: invalid section size (4) or entity size (16)
|
||||
# WARN-GNU: warning: '[[FILE]]': invalid section size (4) or entity size (16)
|
||||
# WARN-GNU-EMPTY:
|
||||
|
||||
--- !ELF
|
||||
@ -162,9 +162,9 @@ ProgramHeaders:
|
||||
## Test handling of DT_STRTAB pointing outside the file's address space.
|
||||
# RUN: yaml2obj %s --docnum=4 -o %t.bad-strtab
|
||||
|
||||
# RUN: llvm-readobj --dynamic-table %t.bad-strtab 2>&1 >/dev/null | FileCheck %s --check-prefix BAD-STRTAB-ERR
|
||||
# RUN: llvm-readelf --dynamic-table %t.bad-strtab 2>&1 >/dev/null | FileCheck %s --check-prefix BAD-STRTAB-ERR
|
||||
# BAD-STRTAB-ERR: warning: Unable to parse DT_STRTAB: virtual address is not in any segment: 0x2000000
|
||||
# RUN: llvm-readobj --dynamic-table %t.bad-strtab 2>&1 >/dev/null | FileCheck -DFILE=%t.bad-strtab %s --check-prefix BAD-STRTAB-ERR
|
||||
# RUN: llvm-readelf --dynamic-table %t.bad-strtab 2>&1 >/dev/null | FileCheck -DFILE=%t.bad-strtab %s --check-prefix BAD-STRTAB-ERR
|
||||
# BAD-STRTAB-ERR: warning: '[[FILE]]': Unable to parse DT_STRTAB: virtual address is not in any segment: 0x2000000
|
||||
|
||||
# RUN: llvm-readobj --dynamic-table --needed-libs %t.bad-strtab | FileCheck %s --check-prefixes=BAD-STRTAB,BAD-STRTAB-LLVM
|
||||
# RUN: llvm-readelf --dynamic-table --needed-libs %t.bad-strtab | FileCheck %s --check-prefixes=BAD-STRTAB,BAD-STRTAB-GNU
|
||||
@ -206,10 +206,10 @@ ProgramHeaders:
|
||||
|
||||
## Test handling of other d_ptr tags pointing outside the file's address space.
|
||||
# RUN: yaml2obj %s --docnum=5 -o %t.bad-rela
|
||||
# RUN: llvm-readobj --dynamic-table %t.bad-rela 2>&1 | FileCheck %s --check-prefixes=CHECK,BAD-RELA
|
||||
# RUN: llvm-readelf --dynamic-table %t.bad-rela 2>&1 | FileCheck %s --check-prefixes=CHECK,BAD-RELA-GNU
|
||||
# RUN: llvm-readobj --dynamic-table %t.bad-rela 2>&1 | FileCheck -DFILE=%t.bad-rela %s --check-prefixes=CHECK,BAD-RELA
|
||||
# RUN: llvm-readelf --dynamic-table %t.bad-rela 2>&1 | FileCheck -DFILE=%t.bad-rela %s --check-prefixes=CHECK,BAD-RELA-GNU
|
||||
|
||||
# CHECK: warning: Unable to parse DT_RELA: virtual address is not in any segment: 0x1000000
|
||||
# CHECK: warning: '[[FILE]]': Unable to parse DT_RELA: virtual address is not in any segment: 0x1000000
|
||||
|
||||
# BAD-RELA: DynamicSection [ (2 entries)
|
||||
# BAD-RELA-NEXT: Tag Type Name/Value
|
||||
|
@ -3,11 +3,11 @@
|
||||
|
||||
# RUN: yaml2obj %s -o %t.o
|
||||
# RUN: llvm-readobj --dynamic-table %t.o 2>&1 \
|
||||
# RUN: | FileCheck --check-prefixes=WARNING,LLVM %s
|
||||
# RUN: | FileCheck -DFILE=%t.o --check-prefixes=WARNING,LLVM %s
|
||||
# RUN: llvm-readelf --dynamic-table %t.o 2>&1 \
|
||||
# RUN: | FileCheck --check-prefixes=WARNING,GNU %s
|
||||
# RUN: | FileCheck -DFILE=%t.o --check-prefixes=WARNING,GNU %s
|
||||
|
||||
# WARNING: warning: The SHT_DYNAMIC section '.dynamic' is not contained within the PT_DYNAMIC segment
|
||||
# WARNING: warning: '[[FILE]]': The SHT_DYNAMIC section '.dynamic' is not contained within the PT_DYNAMIC segment
|
||||
|
||||
# LLVM: DynamicSection [ (2 entries)
|
||||
# LLVM-NEXT: Tag Type Name/Value
|
||||
|
@ -13,14 +13,14 @@
|
||||
# within the file.
|
||||
# RUN: cp %t.stripped %t.truncated1
|
||||
# RUN: %python -c "with open(r'%t.truncated1', 'r+') as f: f.truncate(0x1001)"
|
||||
# RUN: llvm-readobj %t.truncated1 --dynamic-table 2>&1 | FileCheck %s
|
||||
# RUN: llvm-readobj %t.truncated1 --dynamic-table 2>&1 | FileCheck -DFILE=%t.truncated1 %s
|
||||
|
||||
# Test case where the offset is too large to be in the file.
|
||||
# RUN: cp %t.stripped %t.truncated2
|
||||
# RUN: %python -c "with open(r'%t.truncated2', 'r+') as f: f.truncate(0xFFF)"
|
||||
# RUN: llvm-readobj %t.truncated2 --dynamic-table 2>&1 | FileCheck %s
|
||||
# RUN: llvm-readobj %t.truncated2 --dynamic-table 2>&1 | FileCheck -DFILE=%t.truncated2 %s
|
||||
|
||||
# CHECK: warning: PT_DYNAMIC segment offset + size exceeds the size of the file
|
||||
# CHECK: warning: '[[FILE]]': PT_DYNAMIC segment offset + size exceeds the size of the file
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
|
@ -6,11 +6,11 @@
|
||||
|
||||
# RUN: yaml2obj --docnum=1 %s -o %t.o
|
||||
# RUN: llvm-readobj --dynamic-table %t.o 2>&1 \
|
||||
# RUN: | FileCheck %s --check-prefixes=WARNING,LLVM
|
||||
# RUN: | FileCheck %s --DFILE=%t.o --check-prefixes=WARNING,LLVM
|
||||
# RUN: llvm-readelf --dynamic-table %t.o 2>&1 \
|
||||
# RUN: | FileCheck %s --check-prefixes=WARNING,GNU
|
||||
# RUN: | FileCheck %s --DFILE=%t.o --check-prefixes=WARNING,GNU
|
||||
|
||||
# WARNING: warning: The SHT_DYNAMIC section '.dynamic' is not at the start of PT_DYNAMIC segment
|
||||
# WARNING: warning: '[[FILE]]': The SHT_DYNAMIC section '.dynamic' is not at the start of PT_DYNAMIC segment
|
||||
|
||||
# LLVM: DynamicSection [ (2 entries)
|
||||
# LLVM-NEXT: Tag Type Name/Value
|
||||
|
@ -24,12 +24,12 @@
|
||||
# RUN: llvm-readobj -x 9 -x 9 -x .strtab -x .strtab %p/Inputs/trivial.obj.elf-x86-64 2>&1 | \
|
||||
# RUN: FileCheck %s --check-prefix=ELF
|
||||
# RUN: llvm-readobj -x 9 -x .strtab -x 10 -x not_exist \
|
||||
# RUN: %p/Inputs/trivial.obj.elf-x86-64 2>&1 | FileCheck %s --check-prefixes=ELF-WARN,ELF
|
||||
# RUN: %p/Inputs/trivial.obj.elf-x86-64 2>&1 | FileCheck %s -DFILE=%p/Inputs/trivial.obj.elf-x86-64 --check-prefixes=ELF-WARN,ELF
|
||||
|
||||
# ELF-SEC: [ 9] .strtab
|
||||
|
||||
# ELF-WARN: warning: could not find section 'not_exist'
|
||||
# ELF-WARN: warning: could not find section 10
|
||||
# ELF-WARN: warning: '[[FILE]]': could not find section 'not_exist'
|
||||
# ELF-WARN: warning: '[[FILE]]': could not find section 10
|
||||
# ELF: Hex dump of section '.strtab':
|
||||
# ELF-NEXT: 0x00000000 00747269 7669616c 2e6c6c00 6d61696e .trivial.ll.main
|
||||
# ELF-NEXT: 0x00000010 002e4c2e 73747200 70757473 00536f6d ..L.str.puts.Som
|
||||
|
@ -1,5 +1,5 @@
|
||||
RUN: not llvm-readobj --mips-plt-got %p/Inputs/relocs.obj.elf-mips 2>&1 | \
|
||||
RUN: FileCheck %s -check-prefix GOT-OBJ
|
||||
RUN: FileCheck %s -DFILE=%p/Inputs/relocs.obj.elf-mips -check-prefix GOT-OBJ
|
||||
RUN: llvm-readobj --mips-plt-got %p/Inputs/dynamic-table-exe.mips | \
|
||||
RUN: FileCheck %s -check-prefix GOT-EXE
|
||||
RUN: llvm-readobj --mips-plt-got %p/Inputs/dynamic-table-so.mips | \
|
||||
@ -12,7 +12,7 @@ RUN: llvm-readobj --mips-plt-got %p/Inputs/got-static.exe.mips | \
|
||||
RUN: FileCheck %s -check-prefix GOT-STATIC
|
||||
|
||||
RUN: not llvm-readelf --mips-plt-got %p/Inputs/relocs.obj.elf-mips 2>&1 | \
|
||||
RUN: FileCheck %s -check-prefix GNU-GOT-OBJ
|
||||
RUN: FileCheck %s -DFILE=%p/Inputs/relocs.obj.elf-mips -check-prefix GNU-GOT-OBJ
|
||||
RUN: llvm-readelf --mips-plt-got %p/Inputs/dynamic-table-exe.mips | \
|
||||
RUN: FileCheck %s --strict-whitespace -check-prefix GNU-GOT-EXE
|
||||
RUN: llvm-readelf --mips-plt-got %p/Inputs/dynamic-table-so.mips | \
|
||||
@ -24,7 +24,7 @@ RUN: FileCheck %s --strict-whitespace -check-prefix GNU-GOT-EMPTY
|
||||
RUN: llvm-readelf --mips-plt-got %p/Inputs/got-static.exe.mips | \
|
||||
RUN: FileCheck %s --strict-whitespace -check-prefix GNU-GOT-STATIC
|
||||
|
||||
GOT-OBJ: error: Cannot find .got section
|
||||
GOT-OBJ: error: '[[FILE]]': Cannot find .got section
|
||||
|
||||
GOT-EXE: Primary GOT {
|
||||
GOT-EXE-NEXT: Canonical gp value: 0x418880
|
||||
@ -380,7 +380,7 @@ GOT-STATIC-NEXT: }
|
||||
GOT-STATIC-NEXT: ]
|
||||
GOT-STATIC-NEXT: }
|
||||
|
||||
GNU-GOT-OBJ: error: Cannot find .got section
|
||||
GNU-GOT-OBJ: error: '[[FILE]]': Cannot find .got section
|
||||
|
||||
GNU-GOT-EXE: Primary GOT:
|
||||
GNU-GOT-EXE-NEXT: Canonical gp value: 00418880
|
||||
|
@ -8,8 +8,8 @@
|
||||
# using the assembly shown with each test case.
|
||||
|
||||
# RUN: yaml2obj --docnum=1 %s -o %t1.o
|
||||
# RUN: llvm-readelf -n %t1.o 2>&1 | FileCheck %s --check-prefix=ERR-HEADER-SHORT
|
||||
# ERR-HEADER-SHORT: warning: malformed note: header too short
|
||||
# RUN: llvm-readelf -n %t1.o 2>&1 | FileCheck -DFILE=%t1.o %s --check-prefix=ERR-HEADER-SHORT
|
||||
# ERR-HEADER-SHORT: warning: '[[FILE]]': malformed note: header too short
|
||||
|
||||
# .section ".note.foo", "a"
|
||||
# .align 4
|
||||
@ -38,8 +38,8 @@ ProgramHeaders:
|
||||
- Section: .note.foo
|
||||
|
||||
# RUN: yaml2obj --docnum=2 %s -o %t2.o
|
||||
# RUN: llvm-readelf -n %t2.o 2>&1 | FileCheck %s --check-prefix=ERR-NULL-TERM
|
||||
# ERR-NULL-TERM: warning: malformed note: not NUL terminated
|
||||
# RUN: llvm-readelf -n %t2.o 2>&1 | FileCheck -DFILE=%t2.o %s --check-prefix=ERR-NULL-TERM
|
||||
# ERR-NULL-TERM: warning: '[[FILE]]': malformed note: not NUL terminated
|
||||
|
||||
# .section ".note.foo", "a"
|
||||
# .align 4
|
||||
@ -73,8 +73,8 @@ ProgramHeaders:
|
||||
- Section: .note.foo
|
||||
|
||||
# RUN: yaml2obj --docnum=3 %s -o %t3.o
|
||||
# RUN: llvm-readelf -n %t3.o 2>&1 | FileCheck %s --check-prefix=ERR-FILE-COUNT
|
||||
# ERR-FILE-COUNT: warning: malformed note: too short for number of files
|
||||
# RUN: llvm-readelf -n %t3.o 2>&1 | FileCheck -DFILE=%t3.o %s --check-prefix=ERR-FILE-COUNT
|
||||
# ERR-FILE-COUNT: warning: '[[FILE]]': malformed note: too short for number of files
|
||||
|
||||
# .section ".note.foo", "a"
|
||||
# .align 4
|
||||
@ -108,8 +108,8 @@ ProgramHeaders:
|
||||
- Section: .note.foo
|
||||
|
||||
# RUN: yaml2obj --docnum=4 %s -o %t4.o
|
||||
# RUN: llvm-readelf -n %t4.o 2>&1 | FileCheck %s --check-prefix=ERR-FILE-END-EARLY
|
||||
# ERR-FILE-END-EARLY: warning: malformed note: too few filenames
|
||||
# RUN: llvm-readelf -n %t4.o 2>&1 | FileCheck -DFILE=%t4.o %s --check-prefix=ERR-FILE-END-EARLY
|
||||
# ERR-FILE-END-EARLY: warning: '[[FILE]]': malformed note: too few filenames
|
||||
|
||||
# .section ".note.foo", "a"
|
||||
# .align 4
|
||||
|
@ -51,14 +51,14 @@
|
||||
# CHECK-NEXT: [ 3] null{{$}}
|
||||
# CHECK-NOT: {{.}}
|
||||
|
||||
# RUN: llvm-readobj --string-dump=does_not_exist %t 2>&1 | FileCheck %s --check-prefix=WARN1
|
||||
# RUN: llvm-readobj --string-dump=42 %t 2>&1 | FileCheck %s --check-prefix=WARN2
|
||||
# RUN: llvm-readobj --string-dump=does_not_exist %t 2>&1 | FileCheck -DFILE=%t %s --check-prefix=WARN1
|
||||
# RUN: llvm-readobj --string-dump=42 %t 2>&1 | FileCheck %s -DFILE=%t --check-prefix=WARN2
|
||||
|
||||
# RUN: llvm-readelf --string-dump=does_not_exist %t 2>&1 | FileCheck %s --check-prefix=WARN1
|
||||
# RUN: llvm-readelf --string-dump=42 %t 2>&1 | FileCheck %s --check-prefix=WARN2
|
||||
# RUN: llvm-readelf --string-dump=does_not_exist %t 2>&1 | FileCheck -DFILE=%t %s --check-prefix=WARN1
|
||||
# RUN: llvm-readelf --string-dump=42 %t 2>&1 | FileCheck %s -DFILE=%t --check-prefix=WARN2
|
||||
|
||||
# WARN1: warning: could not find section 'does_not_exist'
|
||||
# WARN2: warning: could not find section 42
|
||||
# WARN1: warning: '[[FILE]]': could not find section 'does_not_exist'
|
||||
# WARN2: warning: '[[FILE]]': could not find section 42
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
|
@ -632,12 +632,14 @@ void COFFDumper::printFileHeaders() {
|
||||
// Print PE header. This header does not exist if this is an object file and
|
||||
// not an executable.
|
||||
const pe32_header *PEHeader = nullptr;
|
||||
error(Obj->getPE32Header(PEHeader));
|
||||
if (std::error_code EC = Obj->getPE32Header(PEHeader))
|
||||
reportError(EC, Obj->getFileName());
|
||||
if (PEHeader)
|
||||
printPEHeader<pe32_header>(PEHeader);
|
||||
|
||||
const pe32plus_header *PEPlusHeader = nullptr;
|
||||
error(Obj->getPE32PlusHeader(PEPlusHeader));
|
||||
if (std::error_code EC = Obj->getPE32PlusHeader(PEPlusHeader))
|
||||
reportError(EC, Obj->getFileName());
|
||||
if (PEPlusHeader)
|
||||
printPEHeader<pe32plus_header>(PEPlusHeader);
|
||||
|
||||
@ -732,7 +734,9 @@ void COFFDumper::printCOFFDebugDirectory() {
|
||||
if (D.Type == COFF::IMAGE_DEBUG_TYPE_CODEVIEW) {
|
||||
const codeview::DebugInfo *DebugInfo;
|
||||
StringRef PDBFileName;
|
||||
error(Obj->getDebugPDBInfo(&D, DebugInfo, PDBFileName));
|
||||
if (std::error_code EC = Obj->getDebugPDBInfo(&D, DebugInfo, PDBFileName))
|
||||
reportError(EC, Obj->getFileName());
|
||||
|
||||
DictScope PDBScope(W, "PDBInfo");
|
||||
W.printHex("PDBSignature", DebugInfo->Signature.CVSignature);
|
||||
if (DebugInfo->Signature.CVSignature == OMF::Signature::PDB70) {
|
||||
@ -744,8 +748,9 @@ void COFFDumper::printCOFFDebugDirectory() {
|
||||
// FIXME: Type values of 12 and 13 are commonly observed but are not in
|
||||
// the documented type enum. Figure out what they mean.
|
||||
ArrayRef<uint8_t> RawData;
|
||||
error(
|
||||
Obj->getRvaAndSizeAsBytes(D.AddressOfRawData, D.SizeOfData, RawData));
|
||||
if (std::error_code EC = Obj->getRvaAndSizeAsBytes(D.AddressOfRawData,
|
||||
D.SizeOfData, RawData))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printBinaryBlock("RawData", RawData);
|
||||
}
|
||||
}
|
||||
@ -754,8 +759,11 @@ void COFFDumper::printCOFFDebugDirectory() {
|
||||
void COFFDumper::printRVATable(uint64_t TableVA, uint64_t Count,
|
||||
uint64_t EntrySize, PrintExtraCB PrintExtra) {
|
||||
uintptr_t TableStart, TableEnd;
|
||||
error(Obj->getVaPtr(TableVA, TableStart));
|
||||
error(Obj->getVaPtr(TableVA + Count * EntrySize - 1, TableEnd));
|
||||
if (std::error_code EC = Obj->getVaPtr(TableVA, TableStart))
|
||||
reportError(EC, Obj->getFileName());
|
||||
if (std::error_code EC =
|
||||
Obj->getVaPtr(TableVA + Count * EntrySize - 1, TableEnd))
|
||||
reportError(EC, Obj->getFileName());
|
||||
TableEnd++;
|
||||
for (uintptr_t I = TableStart; I < TableEnd; I += EntrySize) {
|
||||
uint32_t RVA = *reinterpret_cast<const ulittle32_t *>(I);
|
||||
@ -959,7 +967,7 @@ void COFFDumper::printCodeViewSymbolSection(StringRef SectionName,
|
||||
|
||||
W.printHex("Magic", Magic);
|
||||
if (Magic != COFF::DEBUG_SECTION_MAGIC)
|
||||
return error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
|
||||
BinaryStreamReader FSReader(Data, support::little);
|
||||
initializeFileAndStringTables(FSReader);
|
||||
@ -985,7 +993,7 @@ void COFFDumper::printCodeViewSymbolSection(StringRef SectionName,
|
||||
|
||||
// Get the contents of the subsection.
|
||||
if (SubSectionSize > Data.size())
|
||||
return error(object_error::parse_failed);
|
||||
return reportError(object_error::parse_failed, Obj->getFileName());
|
||||
StringRef Contents = Data.substr(0, SubSectionSize);
|
||||
|
||||
// Add SubSectionSize to the current offset and align that offset to find
|
||||
@ -994,7 +1002,7 @@ void COFFDumper::printCodeViewSymbolSection(StringRef SectionName,
|
||||
size_t NextOffset = SectionOffset + SubSectionSize;
|
||||
NextOffset = alignTo(NextOffset, 4);
|
||||
if (NextOffset > SectionContents.size())
|
||||
return error(object_error::parse_failed);
|
||||
return reportError(object_error::parse_failed, Obj->getFileName());
|
||||
Data = SectionContents.drop_front(NextOffset);
|
||||
|
||||
// Optionally print the subsection bytes in case our parsing gets confused
|
||||
@ -1024,17 +1032,19 @@ void COFFDumper::printCodeViewSymbolSection(StringRef SectionName,
|
||||
if (SubSectionSize < 12) {
|
||||
// There should be at least three words to store two function
|
||||
// relocations and size of the code.
|
||||
error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
return;
|
||||
}
|
||||
|
||||
StringRef LinkageName;
|
||||
error(resolveSymbolName(Obj->getCOFFSection(Section), SectionOffset,
|
||||
LinkageName));
|
||||
if (std::error_code EC = resolveSymbolName(Obj->getCOFFSection(Section),
|
||||
SectionOffset, LinkageName))
|
||||
reportError(EC, Obj->getFileName());
|
||||
|
||||
W.printString("LinkageName", LinkageName);
|
||||
if (FunctionLineTables.count(LinkageName) != 0) {
|
||||
// Saw debug info for this function already?
|
||||
error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
return;
|
||||
}
|
||||
|
||||
@ -1051,8 +1061,10 @@ void COFFDumper::printCodeViewSymbolSection(StringRef SectionName,
|
||||
reportError(std::move(E), Obj->getFileName());
|
||||
|
||||
StringRef LinkageName;
|
||||
error(resolveSymbolName(Obj->getCOFFSection(Section), SectionContents,
|
||||
FrameData.getRelocPtr(), LinkageName));
|
||||
if (std::error_code EC =
|
||||
resolveSymbolName(Obj->getCOFFSection(Section), SectionContents,
|
||||
FrameData.getRelocPtr(), LinkageName))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printString("LinkageName", LinkageName);
|
||||
|
||||
// To find the active frame description, search this array for the
|
||||
@ -1122,7 +1134,7 @@ void COFFDumper::printCodeViewSymbolSection(StringRef SectionName,
|
||||
uint32_t ColumnIndex = 0;
|
||||
for (const auto &Line : Entry.LineNumbers) {
|
||||
if (Line.Offset >= LineInfo.header()->CodeSize) {
|
||||
error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
return;
|
||||
}
|
||||
|
||||
@ -1159,10 +1171,9 @@ void COFFDumper::printCodeViewSymbolsSubsection(StringRef Subsection,
|
||||
CompilationCPUType, opts::CodeViewSubsectionBytes);
|
||||
CVSymbolArray Symbols;
|
||||
BinaryStreamReader Reader(BinaryData, llvm::support::little);
|
||||
if (auto EC = Reader.readArray(Symbols, Reader.getLength())) {
|
||||
consumeError(std::move(EC));
|
||||
if (Error E = Reader.readArray(Symbols, Reader.getLength())) {
|
||||
W.flush();
|
||||
error(object_error::parse_failed);
|
||||
reportError(std::move(E), Obj->getFileName());
|
||||
}
|
||||
|
||||
if (Error E = CVSD.dump(Symbols)) {
|
||||
@ -1218,13 +1229,13 @@ void COFFDumper::printCodeViewInlineeLines(StringRef Subsection) {
|
||||
StringRef COFFDumper::getFileNameForFileOffset(uint32_t FileOffset) {
|
||||
// The file checksum subsection should precede all references to it.
|
||||
if (!CVFileChecksumTable.valid() || !CVStringTable.valid())
|
||||
error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
|
||||
auto Iter = CVFileChecksumTable.getArray().at(FileOffset);
|
||||
|
||||
// Check if the file checksum table offset is valid.
|
||||
if (Iter == CVFileChecksumTable.end())
|
||||
error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
|
||||
return unwrapOrError(Obj->getFileName(),
|
||||
CVStringTable.getString(Iter->FileNameOffset));
|
||||
@ -1248,14 +1259,14 @@ void COFFDumper::mergeCodeViewTypes(MergingTypeTableBuilder &CVIDs,
|
||||
reportError(std::move(E), Obj->getFileName());
|
||||
|
||||
if (Magic != 4)
|
||||
error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
|
||||
CVTypeArray Types;
|
||||
BinaryStreamReader Reader(Data, llvm::support::little);
|
||||
if (auto EC = Reader.readArray(Types, Reader.getLength())) {
|
||||
consumeError(std::move(EC));
|
||||
W.flush();
|
||||
error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
}
|
||||
SmallVector<TypeIndex, 128> SourceToDest;
|
||||
Optional<uint32_t> PCHSignature;
|
||||
@ -1290,7 +1301,7 @@ void COFFDumper::printCodeViewTypeSection(StringRef SectionName,
|
||||
|
||||
W.printHex("Magic", Magic);
|
||||
if (Magic != COFF::DEBUG_SECTION_MAGIC)
|
||||
return error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
|
||||
Types.reset(Data, 100);
|
||||
|
||||
@ -1386,7 +1397,9 @@ void COFFDumper::printRelocation(const SectionRef &Section,
|
||||
int64_t SymbolIndex = -1;
|
||||
if (Symbol != Obj->symbol_end()) {
|
||||
Expected<StringRef> SymbolNameOrErr = Symbol->getName();
|
||||
error(errorToErrorCode(SymbolNameOrErr.takeError()));
|
||||
if (!SymbolNameOrErr)
|
||||
reportError(SymbolNameOrErr.takeError(), Obj->getFileName());
|
||||
|
||||
SymbolName = *SymbolNameOrErr;
|
||||
SymbolIndex = Obj->getSymbolIndex(Obj->getCOFFSymbol(*Symbol));
|
||||
}
|
||||
@ -1463,7 +1476,8 @@ void COFFDumper::printSymbol(const SymbolRef &Sym) {
|
||||
for (uint8_t I = 0; I < Symbol.getNumberOfAuxSymbols(); ++I) {
|
||||
if (Symbol.isFunctionDefinition()) {
|
||||
const coff_aux_function_definition *Aux;
|
||||
error(getSymbolAuxData(Obj, Symbol, I, Aux));
|
||||
if (std::error_code EC = getSymbolAuxData(Obj, Symbol, I, Aux))
|
||||
reportError(EC, Obj->getFileName());
|
||||
|
||||
DictScope AS(W, "AuxFunctionDef");
|
||||
W.printNumber("TagIndex", Aux->TagIndex);
|
||||
@ -1473,14 +1487,15 @@ void COFFDumper::printSymbol(const SymbolRef &Sym) {
|
||||
|
||||
} else if (Symbol.isAnyUndefined()) {
|
||||
const coff_aux_weak_external *Aux;
|
||||
error(getSymbolAuxData(Obj, Symbol, I, Aux));
|
||||
if (std::error_code EC = getSymbolAuxData(Obj, Symbol, I, Aux))
|
||||
reportError(EC, Obj->getFileName());
|
||||
|
||||
Expected<COFFSymbolRef> Linked = Obj->getSymbol(Aux->TagIndex);
|
||||
StringRef LinkedName;
|
||||
std::error_code EC = errorToErrorCode(Linked.takeError());
|
||||
if (EC || (EC = Obj->getSymbolName(*Linked, LinkedName))) {
|
||||
LinkedName = "";
|
||||
error(EC);
|
||||
reportError(EC, Obj->getFileName());
|
||||
}
|
||||
|
||||
DictScope AS(W, "AuxWeakExternal");
|
||||
@ -1490,8 +1505,8 @@ void COFFDumper::printSymbol(const SymbolRef &Sym) {
|
||||
|
||||
} else if (Symbol.isFileRecord()) {
|
||||
const char *FileName;
|
||||
error(getSymbolAuxData(Obj, Symbol, I, FileName));
|
||||
|
||||
if (std::error_code EC = getSymbolAuxData(Obj, Symbol, I, FileName))
|
||||
reportError(EC, Obj->getFileName());
|
||||
DictScope AS(W, "AuxFileRecord");
|
||||
|
||||
StringRef Name(FileName, Symbol.getNumberOfAuxSymbols() *
|
||||
@ -1500,7 +1515,8 @@ void COFFDumper::printSymbol(const SymbolRef &Sym) {
|
||||
break;
|
||||
} else if (Symbol.isSectionDefinition()) {
|
||||
const coff_aux_section_definition *Aux;
|
||||
error(getSymbolAuxData(Obj, Symbol, I, Aux));
|
||||
if (std::error_code EC = getSymbolAuxData(Obj, Symbol, I, Aux))
|
||||
reportError(EC, Obj->getFileName());
|
||||
|
||||
int32_t AuxNumber = Aux->getNumber(Symbol.isBigObj());
|
||||
|
||||
@ -1517,7 +1533,7 @@ void COFFDumper::printSymbol(const SymbolRef &Sym) {
|
||||
const coff_section *Assoc;
|
||||
StringRef AssocName = "";
|
||||
if (std::error_code EC = Obj->getSection(AuxNumber, Assoc))
|
||||
error(EC);
|
||||
reportError(EC, Obj->getFileName());
|
||||
Expected<StringRef> Res = getSectionName(Obj, AuxNumber, Assoc);
|
||||
if (!Res)
|
||||
reportError(Res.takeError(), Obj->getFileName());
|
||||
@ -1527,7 +1543,8 @@ void COFFDumper::printSymbol(const SymbolRef &Sym) {
|
||||
}
|
||||
} else if (Symbol.isCLRToken()) {
|
||||
const coff_aux_clr_token *Aux;
|
||||
error(getSymbolAuxData(Obj, Symbol, I, Aux));
|
||||
if (std::error_code EC = getSymbolAuxData(Obj, Symbol, I, Aux))
|
||||
reportError(EC, Obj->getFileName());
|
||||
|
||||
Expected<COFFSymbolRef> ReferredSym =
|
||||
Obj->getSymbol(Aux->SymbolTableIndex);
|
||||
@ -1535,7 +1552,7 @@ void COFFDumper::printSymbol(const SymbolRef &Sym) {
|
||||
std::error_code EC = errorToErrorCode(ReferredSym.takeError());
|
||||
if (EC || (EC = Obj->getSymbolName(*ReferredSym, ReferredName))) {
|
||||
ReferredName = "";
|
||||
error(EC);
|
||||
reportError(EC, Obj->getFileName());
|
||||
}
|
||||
|
||||
DictScope AS(W, "AuxCLRToken");
|
||||
@ -1602,9 +1619,11 @@ void COFFDumper::printImportedSymbols(
|
||||
iterator_range<imported_symbol_iterator> Range) {
|
||||
for (const ImportedSymbolRef &I : Range) {
|
||||
StringRef Sym;
|
||||
error(I.getSymbolName(Sym));
|
||||
if (std::error_code EC = I.getSymbolName(Sym))
|
||||
reportError(EC, Obj->getFileName());
|
||||
uint16_t Ordinal;
|
||||
error(I.getOrdinal(Ordinal));
|
||||
if (std::error_code EC = I.getOrdinal(Ordinal))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printNumber("Symbol", Sym, Ordinal);
|
||||
}
|
||||
}
|
||||
@ -1616,12 +1635,17 @@ void COFFDumper::printDelayImportedSymbols(
|
||||
for (const ImportedSymbolRef &S : Range) {
|
||||
DictScope Import(W, "Import");
|
||||
StringRef Sym;
|
||||
error(S.getSymbolName(Sym));
|
||||
if (std::error_code EC = S.getSymbolName(Sym))
|
||||
reportError(EC, Obj->getFileName());
|
||||
|
||||
uint16_t Ordinal;
|
||||
error(S.getOrdinal(Ordinal));
|
||||
if (std::error_code EC = S.getOrdinal(Ordinal))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printNumber("Symbol", Sym, Ordinal);
|
||||
|
||||
uint64_t Addr;
|
||||
error(I.getImportAddress(Index++, Addr));
|
||||
if (std::error_code EC = I.getImportAddress(Index++, Addr))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printHex("Address", Addr);
|
||||
}
|
||||
}
|
||||
@ -1631,13 +1655,16 @@ void COFFDumper::printCOFFImports() {
|
||||
for (const ImportDirectoryEntryRef &I : Obj->import_directories()) {
|
||||
DictScope Import(W, "Import");
|
||||
StringRef Name;
|
||||
error(I.getName(Name));
|
||||
if (std::error_code EC = I.getName(Name))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printString("Name", Name);
|
||||
uint32_t ILTAddr;
|
||||
error(I.getImportLookupTableRVA(ILTAddr));
|
||||
if (std::error_code EC = I.getImportLookupTableRVA(ILTAddr))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printHex("ImportLookupTableRVA", ILTAddr);
|
||||
uint32_t IATAddr;
|
||||
error(I.getImportAddressTableRVA(IATAddr));
|
||||
if (std::error_code EC = I.getImportAddressTableRVA(IATAddr))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printHex("ImportAddressTableRVA", IATAddr);
|
||||
// The import lookup table can be missing with certain older linkers, so
|
||||
// fall back to the import address table in that case.
|
||||
@ -1651,10 +1678,12 @@ void COFFDumper::printCOFFImports() {
|
||||
for (const DelayImportDirectoryEntryRef &I : Obj->delay_import_directories()) {
|
||||
DictScope Import(W, "DelayImport");
|
||||
StringRef Name;
|
||||
error(I.getName(Name));
|
||||
if (std::error_code EC = I.getName(Name))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printString("Name", Name);
|
||||
const delay_import_directory_table_entry *Table;
|
||||
error(I.getDelayImportTable(Table));
|
||||
if (std::error_code EC = I.getDelayImportTable(Table))
|
||||
reportError(EC, Obj->getFileName());
|
||||
W.printHex("Attributes", Table->Attributes);
|
||||
W.printHex("ModuleHandle", Table->ModuleHandle);
|
||||
W.printHex("ImportAddressTable", Table->DelayImportAddressTable);
|
||||
@ -1672,9 +1701,12 @@ void COFFDumper::printCOFFExports() {
|
||||
StringRef Name;
|
||||
uint32_t Ordinal, RVA;
|
||||
|
||||
error(E.getSymbolName(Name));
|
||||
error(E.getOrdinal(Ordinal));
|
||||
error(E.getExportRVA(RVA));
|
||||
if (std::error_code EC = E.getSymbolName(Name))
|
||||
reportError(EC, Obj->getFileName());
|
||||
if (std::error_code EC = E.getOrdinal(Ordinal))
|
||||
reportError(EC, Obj->getFileName());
|
||||
if (std::error_code EC = E.getExportRVA(RVA))
|
||||
reportError(EC, Obj->getFileName());
|
||||
|
||||
W.printNumber("Ordinal", Ordinal);
|
||||
W.printString("Name", Name);
|
||||
@ -1712,8 +1744,10 @@ void COFFDumper::printCOFFBaseReloc() {
|
||||
for (const BaseRelocRef &I : Obj->base_relocs()) {
|
||||
uint8_t Type;
|
||||
uint32_t RVA;
|
||||
error(I.getRVA(RVA));
|
||||
error(I.getType(Type));
|
||||
if (std::error_code EC = I.getRVA(RVA))
|
||||
reportError(EC, Obj->getFileName());
|
||||
if (std::error_code EC = I.getType(Type))
|
||||
reportError(EC, Obj->getFileName());
|
||||
DictScope Import(W, "Entry");
|
||||
W.printString("Type", getBaseRelocTypeName(Type));
|
||||
W.printHex("Address", RVA);
|
||||
@ -1797,7 +1831,7 @@ void COFFDumper::printResourceDirectoryTable(
|
||||
}
|
||||
std::string EntryNameString;
|
||||
if (!llvm::convertUTF16ToUTF8String(RawEntryNameString, EntryNameString))
|
||||
error(object_error::parse_failed);
|
||||
reportError(object_error::parse_failed, Obj->getFileName());
|
||||
OS << ": ";
|
||||
OS << EntryNameString;
|
||||
} else {
|
||||
@ -1905,14 +1939,14 @@ void COFFDumper::printAddrsig() {
|
||||
const char *Err;
|
||||
uint64_t SymIndex = decodeULEB128(Cur, &Size, End, &Err);
|
||||
if (Err)
|
||||
reportError(Err);
|
||||
reportError(createError(Err), Obj->getFileName());
|
||||
|
||||
Expected<COFFSymbolRef> Sym = Obj->getSymbol(SymIndex);
|
||||
StringRef SymName;
|
||||
std::error_code EC = errorToErrorCode(Sym.takeError());
|
||||
if (EC || (EC = Obj->getSymbolName(*Sym, SymName))) {
|
||||
SymName = "";
|
||||
error(EC);
|
||||
reportError(EC, Obj->getFileName());
|
||||
}
|
||||
|
||||
W.printNumber("Sym", SymName, SymIndex);
|
||||
|
@ -44,12 +44,12 @@ public:
|
||||
void printUnwindInformation() const;
|
||||
};
|
||||
|
||||
template <class ELFO>
|
||||
static const typename ELFO::Elf_Shdr *findSectionByAddress(const ELFO *Obj,
|
||||
uint64_t Addr) {
|
||||
auto Sections = Obj->sections();
|
||||
template <class ELFT>
|
||||
static const typename object::ELFObjectFile<ELFT>::Elf_Shdr *
|
||||
findSectionByAddress(const object::ELFObjectFile<ELFT> *ObjF, uint64_t Addr) {
|
||||
auto Sections = ObjF->getELFFile()->sections();
|
||||
if (Error E = Sections.takeError())
|
||||
reportError(toString(std::move(E)));
|
||||
reportError(std::move(E), ObjF->getFileName());
|
||||
|
||||
for (const auto &Shdr : *Sections)
|
||||
if (Shdr.sh_addr == Addr)
|
||||
@ -64,13 +64,15 @@ void PrinterContext<ELFT>::printUnwindInformation() const {
|
||||
|
||||
auto PHs = Obj->program_headers();
|
||||
if (Error E = PHs.takeError())
|
||||
reportError(toString(std::move(E)));
|
||||
reportError(std::move(E), ObjF->getFileName());
|
||||
|
||||
for (const auto &Phdr : *PHs) {
|
||||
if (Phdr.p_type == ELF::PT_GNU_EH_FRAME) {
|
||||
EHFramePhdr = &Phdr;
|
||||
if (Phdr.p_memsz != Phdr.p_filesz)
|
||||
reportError("p_memsz does not match p_filesz for GNU_EH_FRAME");
|
||||
reportError(object::createError(
|
||||
"p_memsz does not match p_filesz for GNU_EH_FRAME"),
|
||||
ObjF->getFileName());
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -81,12 +83,12 @@ void PrinterContext<ELFT>::printUnwindInformation() const {
|
||||
|
||||
auto Sections = Obj->sections();
|
||||
if (Error E = Sections.takeError())
|
||||
reportError(toString(std::move(E)));
|
||||
reportError(std::move(E), ObjF->getFileName());
|
||||
|
||||
for (const auto &Shdr : *Sections) {
|
||||
auto SectionName = Obj->getSectionName(&Shdr);
|
||||
if (Error E = SectionName.takeError())
|
||||
reportError(toString(std::move(E)));
|
||||
reportError(std::move(E), ObjF->getFileName());
|
||||
|
||||
if (*SectionName == ".eh_frame")
|
||||
printEHFrame(&Shdr);
|
||||
@ -103,11 +105,11 @@ void PrinterContext<ELFT>::printEHFrameHdr(uint64_t EHFrameHdrOffset,
|
||||
W.startLine() << format("Size: 0x%" PRIx64 "\n", EHFrameHdrSize);
|
||||
|
||||
const object::ELFFile<ELFT> *Obj = ObjF->getELFFile();
|
||||
const auto *EHFrameHdrShdr = findSectionByAddress(Obj, EHFrameHdrAddress);
|
||||
const auto *EHFrameHdrShdr = findSectionByAddress(ObjF, EHFrameHdrAddress);
|
||||
if (EHFrameHdrShdr) {
|
||||
auto SectionName = Obj->getSectionName(EHFrameHdrShdr);
|
||||
if (Error E = SectionName.takeError())
|
||||
reportError(toString(std::move(E)));
|
||||
reportError(std::move(E), ObjF->getFileName());
|
||||
|
||||
W.printString("Corresponding Section", *SectionName);
|
||||
}
|
||||
@ -124,22 +126,27 @@ void PrinterContext<ELFT>::printEHFrameHdr(uint64_t EHFrameHdrOffset,
|
||||
auto Version = DE.getU8(&Offset);
|
||||
W.printNumber("version", Version);
|
||||
if (Version != 1)
|
||||
reportError("only version 1 of .eh_frame_hdr is supported");
|
||||
reportError(
|
||||
object::createError("only version 1 of .eh_frame_hdr is supported"),
|
||||
ObjF->getFileName());
|
||||
|
||||
uint64_t EHFramePtrEnc = DE.getU8(&Offset);
|
||||
W.startLine() << format("eh_frame_ptr_enc: 0x%" PRIx64 "\n", EHFramePtrEnc);
|
||||
if (EHFramePtrEnc != (dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4))
|
||||
reportError("unexpected encoding eh_frame_ptr_enc");
|
||||
reportError(object::createError("unexpected encoding eh_frame_ptr_enc"),
|
||||
ObjF->getFileName());
|
||||
|
||||
uint64_t FDECountEnc = DE.getU8(&Offset);
|
||||
W.startLine() << format("fde_count_enc: 0x%" PRIx64 "\n", FDECountEnc);
|
||||
if (FDECountEnc != dwarf::DW_EH_PE_udata4)
|
||||
reportError("unexpected encoding fde_count_enc");
|
||||
reportError(object::createError("unexpected encoding fde_count_enc"),
|
||||
ObjF->getFileName());
|
||||
|
||||
uint64_t TableEnc = DE.getU8(&Offset);
|
||||
W.startLine() << format("table_enc: 0x%" PRIx64 "\n", TableEnc);
|
||||
if (TableEnc != (dwarf::DW_EH_PE_datarel | dwarf::DW_EH_PE_sdata4))
|
||||
reportError("unexpected encoding table_enc");
|
||||
reportError(object::createError("unexpected encoding table_enc"),
|
||||
ObjF->getFileName());
|
||||
|
||||
auto EHFramePtr = DE.getSigned(&Offset, 4) + EHFrameHdrAddress + 4;
|
||||
W.startLine() << format("eh_frame_ptr: 0x%" PRIx64 "\n", EHFramePtr);
|
||||
@ -158,7 +165,8 @@ void PrinterContext<ELFT>::printEHFrameHdr(uint64_t EHFrameHdrOffset,
|
||||
W.startLine() << format("address: 0x%" PRIx64 "\n", Address);
|
||||
|
||||
if (InitialPC < PrevPC)
|
||||
reportError("initial_location is out of order");
|
||||
reportError(object::createError("initial_location is out of order"),
|
||||
ObjF->getFileName());
|
||||
|
||||
PrevPC = InitialPC;
|
||||
++NumEntries;
|
||||
@ -178,7 +186,7 @@ void PrinterContext<ELFT>::printEHFrame(
|
||||
const object::ELFFile<ELFT> *Obj = ObjF->getELFFile();
|
||||
auto Result = Obj->getSectionContents(EHFrameShdr);
|
||||
if (Error E = Result.takeError())
|
||||
reportError(toString(std::move(E)));
|
||||
reportError(std::move(E), ObjF->getFileName());
|
||||
|
||||
auto Contents = Result.get();
|
||||
DWARFDataExtractor DE(
|
||||
|
@ -122,9 +122,9 @@ template <class ELFT> class DumpStyle;
|
||||
/// the size, entity size and virtual address are different entries in arbitrary
|
||||
/// order (DT_REL, DT_RELSZ, DT_RELENT for example).
|
||||
struct DynRegionInfo {
|
||||
DynRegionInfo() = default;
|
||||
DynRegionInfo(const void *A, uint64_t S, uint64_t ES)
|
||||
: Addr(A), Size(S), EntSize(ES) {}
|
||||
DynRegionInfo(StringRef ObjName) : FileName(ObjName) {}
|
||||
DynRegionInfo(const void *A, uint64_t S, uint64_t ES, StringRef ObjName)
|
||||
: Addr(A), Size(S), EntSize(ES), FileName(ObjName) {}
|
||||
|
||||
/// Address in current address space.
|
||||
const void *Addr = nullptr;
|
||||
@ -133,14 +133,18 @@ struct DynRegionInfo {
|
||||
/// Size of each entity in the region.
|
||||
uint64_t EntSize = 0;
|
||||
|
||||
/// Name of the file. Used for error reporting.
|
||||
StringRef FileName;
|
||||
|
||||
template <typename Type> ArrayRef<Type> getAsArrayRef() const {
|
||||
const Type *Start = reinterpret_cast<const Type *>(Addr);
|
||||
if (!Start)
|
||||
return {Start, Start};
|
||||
if (EntSize != sizeof(Type) || Size % EntSize) {
|
||||
// TODO: Add a section index to this warning.
|
||||
reportWarning("invalid section size (" + Twine(Size) +
|
||||
") or entity size (" + Twine(EntSize) + ")");
|
||||
reportWarning(createError("invalid section size (" + Twine(Size) +
|
||||
") or entity size (" + Twine(EntSize) + ")"),
|
||||
FileName);
|
||||
return {Start, Start};
|
||||
}
|
||||
return {Start, Start + (Size / EntSize)};
|
||||
@ -199,18 +203,19 @@ private:
|
||||
if (DRI.Addr < Obj->base() ||
|
||||
reinterpret_cast<const uint8_t *>(DRI.Addr) + DRI.Size >
|
||||
Obj->base() + Obj->getBufSize())
|
||||
error(llvm::object::object_error::parse_failed);
|
||||
reportError(llvm::object::object_error::parse_failed,
|
||||
ObjF->getFileName());
|
||||
return DRI;
|
||||
}
|
||||
|
||||
DynRegionInfo createDRIFrom(const Elf_Phdr *P, uintX_t EntSize) {
|
||||
return checkDRI(
|
||||
{ObjF->getELFFile()->base() + P->p_offset, P->p_filesz, EntSize});
|
||||
return checkDRI({ObjF->getELFFile()->base() + P->p_offset, P->p_filesz,
|
||||
EntSize, ObjF->getFileName()});
|
||||
}
|
||||
|
||||
DynRegionInfo createDRIFrom(const Elf_Shdr *S) {
|
||||
return checkDRI(
|
||||
{ObjF->getELFFile()->base() + S->sh_offset, S->sh_size, S->sh_entsize});
|
||||
return checkDRI({ObjF->getELFFile()->base() + S->sh_offset, S->sh_size,
|
||||
S->sh_entsize, ObjF->getFileName()});
|
||||
}
|
||||
|
||||
void loadDynamicTable(const ELFFile<ELFT> *Obj);
|
||||
@ -362,7 +367,7 @@ public:
|
||||
// It does not print the same warning more than once.
|
||||
WarningHandler = [this](const Twine &Msg) {
|
||||
if (Warnings.insert(Msg.str()).second)
|
||||
reportWarning(FileName, createError(Msg));
|
||||
reportWarning(createError(Msg), FileName);
|
||||
return Error::success();
|
||||
};
|
||||
}
|
||||
@ -740,7 +745,7 @@ std::string ELFDumper<ELFT>::getStaticSymbolName(uint32_t Index) const {
|
||||
Elf_Sym_Range Syms =
|
||||
unwrapOrError(ObjF->getFileName(), Obj->symbols(DotSymtabSec));
|
||||
if (Index >= Syms.size())
|
||||
reportError("Invalid symbol index");
|
||||
reportError(createError("Invalid symbol index"), ObjF->getFileName());
|
||||
const Elf_Sym *Sym = &Syms[Index];
|
||||
return maybeDemangle(
|
||||
unwrapOrError(ObjF->getFileName(), Sym->getName(StrTable)));
|
||||
@ -761,7 +766,7 @@ StringRef ELFDumper<ELFT>::getSymbolVersionByIndex(StringRef StrTab,
|
||||
// Lookup this symbol in the version table.
|
||||
LoadVersionMap();
|
||||
if (VersionIndex >= VersionMap.size() || VersionMap[VersionIndex].isNull())
|
||||
reportError("Invalid version entry");
|
||||
reportError(createError("Invalid version entry"), ObjF->getFileName());
|
||||
const VersionMapEntry &Entry = VersionMap[VersionIndex];
|
||||
|
||||
// Get the version name string.
|
||||
@ -775,7 +780,7 @@ StringRef ELFDumper<ELFT>::getSymbolVersionByIndex(StringRef StrTab,
|
||||
IsDefault = false;
|
||||
}
|
||||
if (NameOffset >= StrTab.size())
|
||||
reportError("Invalid string offset");
|
||||
reportError(createError("Invalid string offset"), ObjF->getFileName());
|
||||
return StrTab.data() + NameOffset;
|
||||
}
|
||||
|
||||
@ -1428,8 +1433,9 @@ void ELFDumper<ELFT>::loadDynamicTable(const ELFFile<ELFT> *Obj) {
|
||||
// This allows us to dump the dynamic sections with a broken sh_entsize
|
||||
// field.
|
||||
if (DynamicSec) {
|
||||
DynamicTable = checkDRI({ObjF->getELFFile()->base() + DynamicSec->sh_offset,
|
||||
DynamicSec->sh_size, sizeof(Elf_Dyn)});
|
||||
DynamicTable =
|
||||
checkDRI({ObjF->getELFFile()->base() + DynamicSec->sh_offset,
|
||||
DynamicSec->sh_size, sizeof(Elf_Dyn), ObjF->getFileName()});
|
||||
parseDynamicTable();
|
||||
}
|
||||
|
||||
@ -1441,7 +1447,9 @@ void ELFDumper<ELFT>::loadDynamicTable(const ELFFile<ELFT> *Obj) {
|
||||
if (DynamicPhdr->p_offset + DynamicPhdr->p_filesz >
|
||||
ObjF->getMemoryBufferRef().getBufferSize()) {
|
||||
reportWarning(
|
||||
"PT_DYNAMIC segment offset + size exceeds the size of the file");
|
||||
createError(
|
||||
"PT_DYNAMIC segment offset + size exceeds the size of the file"),
|
||||
ObjF->getFileName());
|
||||
return;
|
||||
}
|
||||
|
||||
@ -1456,22 +1464,26 @@ void ELFDumper<ELFT>::loadDynamicTable(const ELFFile<ELFT> *Obj) {
|
||||
if (DynamicSec->sh_addr + DynamicSec->sh_size >
|
||||
DynamicPhdr->p_vaddr + DynamicPhdr->p_memsz ||
|
||||
DynamicSec->sh_addr < DynamicPhdr->p_vaddr)
|
||||
reportWarning("The SHT_DYNAMIC section '" + Name +
|
||||
"' is not contained within the "
|
||||
"PT_DYNAMIC segment");
|
||||
reportWarning(createError("The SHT_DYNAMIC section '" + Name +
|
||||
"' is not contained within the "
|
||||
"PT_DYNAMIC segment"),
|
||||
ObjF->getFileName());
|
||||
|
||||
if (DynamicSec->sh_addr != DynamicPhdr->p_vaddr)
|
||||
reportWarning("The SHT_DYNAMIC section '" + Name +
|
||||
"' is not at the start of "
|
||||
"PT_DYNAMIC segment");
|
||||
reportWarning(createError("The SHT_DYNAMIC section '" + Name +
|
||||
"' is not at the start of "
|
||||
"PT_DYNAMIC segment"),
|
||||
ObjF->getFileName());
|
||||
}
|
||||
|
||||
template <typename ELFT>
|
||||
ELFDumper<ELFT>::ELFDumper(const object::ELFObjectFile<ELFT> *ObjF,
|
||||
ScopedPrinter &Writer)
|
||||
: ObjDumper(Writer), ObjF(ObjF) {
|
||||
ScopedPrinter &Writer)
|
||||
: ObjDumper(Writer), ObjF(ObjF), DynRelRegion(ObjF->getFileName()),
|
||||
DynRelaRegion(ObjF->getFileName()), DynRelrRegion(ObjF->getFileName()),
|
||||
DynPLTRelRegion(ObjF->getFileName()), DynSymRegion(ObjF->getFileName()),
|
||||
DynamicTable(ObjF->getFileName()) {
|
||||
const ELFFile<ELFT> *Obj = ObjF->getELFFile();
|
||||
|
||||
for (const Elf_Shdr &Sec :
|
||||
unwrapOrError(ObjF->getFileName(), Obj->sections())) {
|
||||
switch (Sec.sh_type) {
|
||||
@ -1490,7 +1502,7 @@ ELFDumper<ELFT>::ELFDumper(const object::ELFObjectFile<ELFT> *ObjF,
|
||||
if (Expected<StringRef> E = Obj->getStringTableForSymtab(Sec))
|
||||
DynamicStringTable = *E;
|
||||
else
|
||||
warn(E.takeError());
|
||||
reportWarning(E.takeError(), ObjF->getFileName());
|
||||
}
|
||||
break;
|
||||
case ELF::SHT_SYMTAB_SHNDX:
|
||||
@ -1599,10 +1611,13 @@ template <typename ELFT> void ELFDumper<ELFT>::parseDynamicTable() {
|
||||
auto toMappedAddr = [&](uint64_t Tag, uint64_t VAddr) -> const uint8_t * {
|
||||
auto MappedAddrOrError = ObjF->getELFFile()->toMappedAddr(VAddr);
|
||||
if (!MappedAddrOrError) {
|
||||
reportWarning("Unable to parse DT_" +
|
||||
Twine(getTypeString(
|
||||
ObjF->getELFFile()->getHeader()->e_machine, Tag)) +
|
||||
": " + llvm::toString(MappedAddrOrError.takeError()));
|
||||
Error Err =
|
||||
createError("Unable to parse DT_" +
|
||||
Twine(getTypeString(
|
||||
ObjF->getELFFile()->getHeader()->e_machine, Tag)) +
|
||||
": " + llvm::toString(MappedAddrOrError.takeError()));
|
||||
|
||||
reportWarning(std::move(Err), ObjF->getFileName());
|
||||
return nullptr;
|
||||
}
|
||||
return MappedAddrOrError.get();
|
||||
@ -1671,8 +1686,9 @@ template <typename ELFT> void ELFDumper<ELFT>::parseDynamicTable() {
|
||||
else if (Dyn.getVal() == DT_RELA)
|
||||
DynPLTRelRegion.EntSize = sizeof(Elf_Rela);
|
||||
else
|
||||
reportError(Twine("unknown DT_PLTREL value of ") +
|
||||
Twine((uint64_t)Dyn.getVal()));
|
||||
reportError(createError(Twine("unknown DT_PLTREL value of ") +
|
||||
Twine((uint64_t)Dyn.getVal())),
|
||||
ObjF->getFileName());
|
||||
break;
|
||||
case ELF::DT_JMPREL:
|
||||
DynPLTRelRegion.Addr = toMappedAddr(Dyn.getTag(), Dyn.getPtr());
|
||||
@ -2094,7 +2110,7 @@ template <typename ELFT> void ELFDumper<ELFT>::printGnuHashTable() {
|
||||
Elf_Sym_Range Syms = dynamic_symbols();
|
||||
unsigned NumSyms = std::distance(Syms.begin(), Syms.end());
|
||||
if (!NumSyms)
|
||||
reportError("No dynamic symbol section");
|
||||
reportError(createError("No dynamic symbol section"), ObjF->getFileName());
|
||||
W.printHexList("Values", GnuHashTable->values(NumSyms));
|
||||
}
|
||||
|
||||
@ -2207,7 +2223,7 @@ MipsGOTParser<ELFT>::MipsGOTParser(const ELFO *Obj, StringRef FileName,
|
||||
if (IsStatic) {
|
||||
GotSec = findSectionByName(*Obj, FileName, ".got");
|
||||
if (!GotSec)
|
||||
reportError("Cannot find .got section");
|
||||
reportError(createError("Cannot find .got section"), FileName);
|
||||
|
||||
ArrayRef<uint8_t> Content =
|
||||
unwrapOrError(FileName, Obj->getSectionContents(GotSec));
|
||||
@ -2254,12 +2270,15 @@ MipsGOTParser<ELFT>::MipsGOTParser(const ELFO *Obj, StringRef FileName,
|
||||
|
||||
size_t DynSymTotal = DynSyms.size();
|
||||
if (*DtGotSym > DynSymTotal)
|
||||
reportError("MIPS_GOTSYM exceeds a number of dynamic symbols");
|
||||
reportError(
|
||||
createError("MIPS_GOTSYM exceeds a number of dynamic symbols"),
|
||||
FileName);
|
||||
|
||||
GotSec = findNotEmptySectionByAddress(Obj, FileName, *DtPltGot);
|
||||
if (!GotSec)
|
||||
reportError("There is no not empty GOT section at 0x" +
|
||||
Twine::utohexstr(*DtPltGot));
|
||||
reportError(createError("There is no not empty GOT section at 0x" +
|
||||
Twine::utohexstr(*DtPltGot)),
|
||||
FileName);
|
||||
|
||||
LocalNum = *DtLocalGotNum;
|
||||
GlobalNum = DynSymTotal - *DtGotSym;
|
||||
@ -2409,7 +2428,8 @@ MipsGOTParser<ELFT>::getPltSym(const Entry *E) const {
|
||||
template <class ELFT> void ELFDumper<ELFT>::printMipsPLTGOT() {
|
||||
const ELFFile<ELFT> *Obj = ObjF->getELFFile();
|
||||
if (Obj->getHeader()->e_machine != EM_MIPS)
|
||||
reportError("MIPS PLT GOT is available for MIPS targets only");
|
||||
reportError(createError("MIPS PLT GOT is available for MIPS targets only"),
|
||||
ObjF->getFileName());
|
||||
|
||||
MipsGOTParser<ELFT> Parser(Obj, ObjF->getFileName(), dynamic_table(),
|
||||
dynamic_symbols());
|
||||
@ -4492,7 +4512,7 @@ void GNUStyle<ELFT>::printNotes(const ELFFile<ELFT> *Obj) {
|
||||
if (Note)
|
||||
printCoreNote<ELFT>(OS, *Note);
|
||||
else
|
||||
warn(Note.takeError());
|
||||
reportWarning(Note.takeError(), this->FileName);
|
||||
}
|
||||
} else if (!Descriptor.empty()) {
|
||||
OS << " description data:";
|
||||
@ -4556,7 +4576,6 @@ void DumpStyle<ELFT>::printFunctionStackSize(
|
||||
}
|
||||
}
|
||||
|
||||
StringRef FileStr = Obj->getFileName();
|
||||
std::string FuncName = "?";
|
||||
// A valid SymbolRef has a non-null object file pointer.
|
||||
if (FuncSym.BasicSymbolRef::getObject()) {
|
||||
@ -4566,9 +4585,11 @@ void DumpStyle<ELFT>::printFunctionStackSize(
|
||||
FuncName = maybeDemangle(*FuncNameOrErr);
|
||||
else
|
||||
consumeError(FuncNameOrErr.takeError());
|
||||
} else
|
||||
reportWarning(" '" + FileStr +
|
||||
"': could not identify function symbol for stack size entry");
|
||||
} else {
|
||||
reportWarning(
|
||||
createError("could not identify function symbol for stack size entry"),
|
||||
Obj->getFileName());
|
||||
}
|
||||
|
||||
// Extract the size. The expectation is that Offset is pointing to the right
|
||||
// place, i.e. past the function address.
|
||||
@ -4581,7 +4602,7 @@ void DumpStyle<ELFT>::printFunctionStackSize(
|
||||
createStringError(object_error::parse_failed,
|
||||
"could not extract a valid stack size in section %s",
|
||||
SectionName.data()),
|
||||
FileStr);
|
||||
Obj->getFileName());
|
||||
|
||||
printStackSizeEntry(StackSize, FuncName);
|
||||
}
|
||||
@ -4619,13 +4640,14 @@ void DumpStyle<ELFT>::printStackSize(const ELFObjectFile<ELFT> *Obj,
|
||||
|
||||
auto SectionOrErr = RelocSym->getSection();
|
||||
if (!SectionOrErr) {
|
||||
reportWarning(" '" + FileStr +
|
||||
"': cannot identify the section for relocation symbol " +
|
||||
SymName);
|
||||
consumeError(SectionOrErr.takeError());
|
||||
reportWarning(
|
||||
createError("cannot identify the section for relocation symbol " +
|
||||
SymName),
|
||||
FileStr);
|
||||
} else if (*SectionOrErr != FunctionSec) {
|
||||
reportWarning(" '" + FileStr + "': relocation symbol " + SymName +
|
||||
" is not in the expected section");
|
||||
reportWarning(createError("relocation symbol " + SymName +
|
||||
" is not in the expected section"),
|
||||
FileStr);
|
||||
// Pretend that the symbol is in the correct section and report its
|
||||
// stack size anyway.
|
||||
FunctionSec = **SectionOrErr;
|
||||
@ -4713,7 +4735,7 @@ template <class ELFT>
|
||||
void DumpStyle<ELFT>::printRelocatableStackSizes(
|
||||
const ELFObjectFile<ELFT> *Obj, std::function<void()> PrintHeader) {
|
||||
const ELFFile<ELFT> *EF = Obj->getELFFile();
|
||||
StringRef FileStr = Obj->getFileName();
|
||||
|
||||
// Build a map between stack size sections and their corresponding relocation
|
||||
// sections.
|
||||
llvm::MapVector<SectionRef, SectionRef> StackSizeRelocMap;
|
||||
@ -4768,9 +4790,10 @@ void DumpStyle<ELFT>::printRelocatableStackSizes(
|
||||
consumeError(NameOrErr.takeError());
|
||||
|
||||
if (RelocSec == NullSection) {
|
||||
reportWarning(" '" + FileStr + "': section " + StackSizeSectionName +
|
||||
" does not have a corresponding "
|
||||
"relocation section");
|
||||
reportWarning(createError("section " + StackSizeSectionName +
|
||||
" does not have a corresponding "
|
||||
"relocation section"),
|
||||
Obj->getFileName());
|
||||
continue;
|
||||
}
|
||||
|
||||
@ -4805,7 +4828,7 @@ void DumpStyle<ELFT>::printRelocatableStackSizes(
|
||||
createStringError(object_error::parse_failed,
|
||||
"unsupported relocation type in section %s: %s",
|
||||
RelocSectionName.data(), RelocName.data()),
|
||||
FileStr);
|
||||
Obj->getFileName());
|
||||
}
|
||||
this->printStackSize(Obj, Reloc, FunctionSec, StackSizeSectionName,
|
||||
Resolver, Data);
|
||||
@ -5225,9 +5248,10 @@ void LLVMStyle<ELFT>::printSectionHeaders(const ELFO *Obj) {
|
||||
this->FileName,
|
||||
Obj->getSection(&Sym, Symtab, this->dumper()->getShndxTable()));
|
||||
if (SymSec == &Sec)
|
||||
printSymbol(Obj, &Sym,
|
||||
printSymbol(
|
||||
Obj, &Sym,
|
||||
unwrapOrError(this->FileName, Obj->symbols(Symtab)).begin(),
|
||||
StrTable, false);
|
||||
StrTable, false);
|
||||
}
|
||||
}
|
||||
|
||||
@ -5587,7 +5611,8 @@ void LLVMStyle<ELFT>::printAddrsig(const ELFFile<ELFT> *Obj) {
|
||||
const char *Err;
|
||||
uint64_t SymIndex = decodeULEB128(Cur, &Size, End, &Err);
|
||||
if (Err)
|
||||
reportError(Err);
|
||||
reportError(createError(Err), this->FileName);
|
||||
|
||||
W.printNumber("Sym", this->dumper()->getStaticSymbolName(SymIndex),
|
||||
SymIndex);
|
||||
Cur += Size;
|
||||
@ -5696,7 +5721,7 @@ void LLVMStyle<ELFT>::printNotes(const ELFFile<ELFT> *Obj) {
|
||||
if (Note)
|
||||
printCoreNoteLLVMStyle(*Note, W);
|
||||
else
|
||||
warn(Note.takeError());
|
||||
reportWarning(Note.takeError(), this->FileName);
|
||||
}
|
||||
} else if (!Descriptor.empty()) {
|
||||
W.printBinaryBlock("Description data", Descriptor);
|
||||
|
@ -556,7 +556,7 @@ void MachODumper::printRelocation(const MachOObjectFile *Obj,
|
||||
if (Symbol != Obj->symbol_end()) {
|
||||
Expected<StringRef> TargetNameOrErr = Symbol->getName();
|
||||
if (!TargetNameOrErr)
|
||||
error(errorToErrorCode(TargetNameOrErr.takeError()));
|
||||
reportError(TargetNameOrErr.takeError(), Obj->getFileName());
|
||||
TargetName = *TargetNameOrErr;
|
||||
}
|
||||
} else if (!IsScattered) {
|
||||
@ -630,7 +630,9 @@ void MachODumper::printSymbol(const SymbolRef &Symbol) {
|
||||
|
||||
StringRef SectionName = "";
|
||||
Expected<section_iterator> SecIOrErr = Symbol.getSection();
|
||||
error(errorToErrorCode(SecIOrErr.takeError()));
|
||||
if (!SecIOrErr)
|
||||
reportError(SecIOrErr.takeError(), Obj->getFileName());
|
||||
|
||||
section_iterator SecI = *SecIOrErr;
|
||||
if (SecI != Obj->section_end())
|
||||
SectionName = unwrapOrError(Obj->getFileName(), SecI->getName());
|
||||
|
@ -23,6 +23,10 @@
|
||||
|
||||
namespace llvm {
|
||||
|
||||
static inline Error createError(const Twine &Msg) {
|
||||
return createStringError(object::object_error::parse_failed, Msg);
|
||||
}
|
||||
|
||||
ObjDumper::ObjDumper(ScopedPrinter &Writer) : W(Writer) {}
|
||||
|
||||
ObjDumper::~ObjDumper() {
|
||||
@ -63,10 +67,15 @@ getSectionRefsByNameOrIndex(const object::ObjectFile *Obj,
|
||||
|
||||
for (const std::pair<std::string, bool> &S : SecNames)
|
||||
if (!S.second)
|
||||
reportWarning(formatv("could not find section '{0}'", S.first).str());
|
||||
reportWarning(
|
||||
createError(formatv("could not find section '{0}'", S.first).str()),
|
||||
Obj->getFileName());
|
||||
|
||||
for (std::pair<unsigned, bool> S : SecIndices)
|
||||
if (!S.second)
|
||||
reportWarning(formatv("could not find section {0}", S.first).str());
|
||||
reportWarning(
|
||||
createError(formatv("could not find section {0}", S.first).str()),
|
||||
Obj->getFileName());
|
||||
|
||||
return Ret;
|
||||
}
|
||||
|
@ -375,52 +375,46 @@ namespace opts {
|
||||
|
||||
namespace llvm {
|
||||
|
||||
LLVM_ATTRIBUTE_NORETURN void reportError(Twine Msg) {
|
||||
LLVM_ATTRIBUTE_NORETURN static void error(Twine Msg) {
|
||||
// Flush the standard output to print the error at a
|
||||
// proper place.
|
||||
fouts().flush();
|
||||
errs() << "\n";
|
||||
WithColor::error(errs()) << Msg << "\n";
|
||||
exit(1);
|
||||
}
|
||||
|
||||
void reportError(Error Err, StringRef Input) {
|
||||
LLVM_ATTRIBUTE_NORETURN void reportError(Error Err, StringRef Input) {
|
||||
assert(Err);
|
||||
if (Input == "-")
|
||||
Input = "<stdin>";
|
||||
handleAllErrors(createFileError(Input, std::move(Err)),
|
||||
[&](const ErrorInfoBase &EI) { reportError(EI.message()); });
|
||||
[&](const ErrorInfoBase &EI) { error(EI.message()); });
|
||||
llvm_unreachable("error() call should never return");
|
||||
}
|
||||
|
||||
void reportWarning(Twine Msg) {
|
||||
fouts().flush();
|
||||
errs() << "\n";
|
||||
WithColor::warning(errs()) << Msg << "\n";
|
||||
}
|
||||
|
||||
void reportWarning(StringRef Input, Error Err) {
|
||||
void reportWarning(Error Err, StringRef Input) {
|
||||
assert(Err);
|
||||
if (Input == "-")
|
||||
Input = "<stdin>";
|
||||
warn(createFileError(Input, std::move(Err)));
|
||||
|
||||
handleAllErrors(createFileError(Input, std::move(Err)),
|
||||
[&](const ErrorInfoBase &EI) {
|
||||
// Flush the standard output to print the warning at a
|
||||
// proper place.
|
||||
fouts().flush();
|
||||
errs() << "\n";
|
||||
WithColor::warning(errs()) << EI.message() << "\n";
|
||||
});
|
||||
}
|
||||
|
||||
void warn(Error Err) {
|
||||
handleAllErrors(std::move(Err), [&](const ErrorInfoBase &EI) {
|
||||
reportWarning(EI.message());
|
||||
});
|
||||
}
|
||||
|
||||
void error(std::error_code EC) {
|
||||
if (!EC)
|
||||
return;
|
||||
reportError(EC.message());
|
||||
}
|
||||
|
||||
} // namespace llvm
|
||||
|
||||
static void reportError(std::error_code EC, StringRef Input) {
|
||||
LLVM_ATTRIBUTE_NORETURN void reportError(std::error_code EC, StringRef Input) {
|
||||
assert(EC != readobj_error::success);
|
||||
reportError(errorCodeToError(EC), Input);
|
||||
}
|
||||
|
||||
} // namespace llvm
|
||||
|
||||
static bool isMipsArch(unsigned Arch) {
|
||||
switch (Arch) {
|
||||
case llvm::Triple::mips:
|
||||
|
@ -21,12 +21,9 @@ namespace llvm {
|
||||
}
|
||||
|
||||
// Various helper functions.
|
||||
LLVM_ATTRIBUTE_NORETURN void reportError(Twine Msg);
|
||||
void reportError(Error Err, StringRef Input);
|
||||
void reportWarning(Twine Msg);
|
||||
void reportWarning(StringRef Input, Error Err);
|
||||
void warn(llvm::Error Err);
|
||||
void error(std::error_code EC);
|
||||
LLVM_ATTRIBUTE_NORETURN void reportError(Error Err, StringRef Input);
|
||||
LLVM_ATTRIBUTE_NORETURN void reportError(std::error_code EC, StringRef Input);
|
||||
void reportWarning(Error Err, StringRef Input);
|
||||
|
||||
template <class T> T unwrapOrError(StringRef Input, Expected<T> EO) {
|
||||
if (EO)
|
||||
|
Loading…
Reference in New Issue
Block a user