665 lines
21 KiB
YAML
665 lines
21 KiB
YAML
## Show that obj2yaml is able to dump program headers.
|
|
|
|
## Part I. Base check. All simple cases that look OK as a part of a single large test live here.
|
|
|
|
# RUN: yaml2obj %s -o %t1
|
|
|
|
## Show the layout of the object before we dump it using obj2yaml.
|
|
## The check is here to make it clear what the layout should look like.
|
|
# RUN: llvm-readelf --segments %t1 | FileCheck %s --check-prefix=SEGMENT-MAPPING
|
|
|
|
# SEGMENT-MAPPING: Program Headers:
|
|
# SEGMENT-MAPPING-NEXT: Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align
|
|
# SEGMENT-MAPPING-NEXT: LOAD 0x000000 0x0000000000000000 0x0000000000000000 0x000281 0x000281 R 0x1000
|
|
# SEGMENT-MAPPING-NEXT: LOAD 0x000281 0x0000000000001000 0x0000000000001000 0x000010 0x000010 R E 0x1000
|
|
# SEGMENT-MAPPING-NEXT: LOAD 0x000291 0x0000000000002000 0x0000000000002000 0x000009 0x000009 R 0x1000
|
|
# SEGMENT-MAPPING-NEXT: LOAD 0x00029a 0x0000000000003ef0 0x0000000000003ef0 0x000011 0x000011 RW 0x1000
|
|
# SEGMENT-MAPPING-NEXT: DYNAMIC 0x00029a 0x0000000000003ef0 0x0000000000003ef0 0x000010 0x000010 RW 0x8
|
|
# SEGMENT-MAPPING-NEXT: GNU_RELRO 0x00029a 0x0000000000003ef0 0x0000000000003ef0 0x000010 0x000010 R 0x1
|
|
# SEGMENT-MAPPING-NEXT: LOAD 0x000000 0x0000000000004000 0x0000000000004000 0x000000 0x000000 R 0x1
|
|
# SEGMENT-MAPPING-NEXT: LOAD 0x000248 0x00000000000001a0 0x00000000000001a0 0x000020 0x000020 R 0x1
|
|
# SEGMENT-MAPPING-NEXT: LOAD 0x000248 0x00000000000001a0 0x00000000000001a0 0x000020 0x000020 R 0x1
|
|
# SEGMENT-MAPPING: Section to Segment mapping:
|
|
# SEGMENT-MAPPING-NEXT: Segment Sections...
|
|
# SEGMENT-MAPPING-NEXT: 00 .hash .gnu.hash .dynsym .dynstr {{$}}
|
|
# SEGMENT-MAPPING-NEXT: 01 .foo .zed {{$}}
|
|
# SEGMENT-MAPPING-NEXT: 02 .foo .baz {{$}}
|
|
# SEGMENT-MAPPING-NEXT: 03 .dynamic .dynamic.tail {{$}}
|
|
# SEGMENT-MAPPING-NEXT: 04 .dynamic {{$}}
|
|
# SEGMENT-MAPPING-NEXT: 05 .dynamic {{$}}
|
|
# SEGMENT-MAPPING-NEXT: 06{{ *$}}
|
|
# SEGMENT-MAPPING-NEXT: 07 .gnu.hash {{$}}
|
|
# SEGMENT-MAPPING-NEXT: 08 .gnu.hash {{$}}
|
|
# SEGMENT-MAPPING-NEXT: None .symtab .strtab .shstrtab {{$}}
|
|
|
|
## Check that obj2yaml produced a correct program headers description.
|
|
|
|
# RUN: obj2yaml %t1 | FileCheck %s --check-prefix=YAML
|
|
|
|
# YAML: ProgramHeaders:
|
|
# YAML-NEXT: - Type: PT_LOAD
|
|
# YAML-NEXT: Flags: [ PF_R ]
|
|
# YAML-NEXT: FirstSec: .hash
|
|
# YAML-NEXT: LastSec: .dynstr
|
|
# YAML-NEXT: Align: 0x1000
|
|
# YAML-NEXT: - Type: PT_LOAD
|
|
# YAML-NEXT: Flags: [ PF_X, PF_R ]
|
|
# YAML-NEXT: FirstSec: .foo
|
|
# YAML-NEXT: LastSec: .zed
|
|
# YAML-NEXT: VAddr: 0x1000
|
|
# YAML-NEXT: Align: 0x1000
|
|
# YAML-NEXT: - Type: PT_LOAD
|
|
# YAML-NEXT: Flags: [ PF_R ]
|
|
# YAML-NEXT: FirstSec: '.foo (1)'
|
|
# YAML-NEXT: LastSec: .baz
|
|
# YAML-NEXT: VAddr: 0x2000
|
|
# YAML-NEXT: Align: 0x1000
|
|
# YAML-NEXT: - Type: PT_LOAD
|
|
# YAML-NEXT: Flags: [ PF_W, PF_R ]
|
|
# YAML-NEXT: FirstSec: .dynamic
|
|
# YAML-NEXT: LastSec: .dynamic.tail
|
|
# YAML-NEXT: VAddr: 0x3EF0
|
|
# YAML-NEXT: Align: 0x1000
|
|
# YAML-NEXT: - Type: PT_DYNAMIC
|
|
# YAML-NEXT: Flags: [ PF_W, PF_R ]
|
|
# YAML-NEXT: FirstSec: .dynamic
|
|
# YAML-NEXT: LastSec: .dynamic
|
|
# YAML-NEXT: VAddr: 0x3EF0
|
|
# YAML-NEXT: Align: 0x8
|
|
# YAML-NEXT: - Type: PT_GNU_RELRO
|
|
# YAML-NEXT: Flags: [ PF_R ]
|
|
# YAML-NEXT: FirstSec: .dynamic
|
|
# YAML-NEXT: LastSec: .dynamic
|
|
# YAML-NEXT: VAddr: 0x3EF0
|
|
# YAML-NEXT: - Type: PT_LOAD
|
|
# YAML-NEXT: Flags: [ PF_R ]
|
|
# YAML-NEXT: VAddr: 0x4000
|
|
# YAML-NEXT: - Type: PT_LOAD
|
|
# YAML-NEXT: Flags: [ PF_R ]
|
|
# YAML-NEXT: FirstSec: .gnu.hash
|
|
# YAML-NEXT: LastSec: .gnu.hash
|
|
# YAML-NEXT: VAddr: 0x1A0
|
|
# YAML-NEXT: - Type: PT_LOAD
|
|
# YAML-NEXT: Flags: [ PF_R ]
|
|
# YAML-NEXT: FirstSec: .gnu.hash
|
|
# YAML-NEXT: LastSec: .gnu.hash
|
|
# YAML-NEXT: VAddr: 0x1A0
|
|
# YAML-NEXT: Sections:
|
|
|
|
--- !ELF
|
|
FileHeader:
|
|
Class: ELFCLASS64
|
|
Data: ELFDATA2LSB
|
|
Type: ET_DYN
|
|
ProgramHeaders:
|
|
## Check we can create a PT_LOAD with arbitrary (we used .hash, .gnu.hash)
|
|
## and implicit sections (we use .dynsym, .dynstr). It also checks that the
|
|
## SHT_NULL section at index 0 is not included in the segment.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .hash
|
|
LastSec: .dynstr
|
|
Align: 0x1000
|
|
Offset: 0x0
|
|
## Check we can create a PT_LOAD with a different set of properties and sections.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_X, PF_R ]
|
|
FirstSec: .foo
|
|
LastSec: .zed
|
|
VAddr: 0x1000
|
|
Align: 0x1000
|
|
## Create a PT_LOAD to demonstate we are able to refer to output sections with the same name.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: '.foo (1)'
|
|
LastSec: .baz
|
|
VAddr: 0x2000
|
|
Align: 0x1000
|
|
## Show we can create a writeable PT_LOAD segment and put an arbitrary section into it.
|
|
## Here we test both regular (SHT_PROGBITS) and a special section (SHT_DYNAMIC).
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .dynamic
|
|
LastSec: .dynamic.tail
|
|
VAddr: 0x3EF0
|
|
Align: 0x1000
|
|
## Show we can create a nested dynamic segment and put a section into it.
|
|
- Type: PT_DYNAMIC
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .dynamic
|
|
LastSec: .dynamic
|
|
VAddr: 0x3EF0
|
|
Align: 0x8
|
|
## Show we can create a relro segment and put a section into it.
|
|
## We used .dynamic here and in tests above to demonstrate that
|
|
## we can place a section in any number of segments.
|
|
## Also, we explicitly set the "Align" property to 1 to demonstate
|
|
## that we do not dump it, because it is the default alignment
|
|
## value set by yaml2obj.
|
|
- Type: PT_GNU_RELRO
|
|
Flags: [ PF_R ]
|
|
FirstSec: .dynamic
|
|
LastSec: .dynamic
|
|
VAddr: 0x3EF0
|
|
Align: 0x1
|
|
## Show we can dump a standalone empty segment.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
VAddr: 0x4000
|
|
Align: 0x1
|
|
## ELF specification says that loadable segment entries in the
|
|
## program header are sorted by virtual address.
|
|
## Show we can dump an out of order segment.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .gnu.hash
|
|
LastSec: .gnu.hash
|
|
VAddr: 0x1A0
|
|
Align: 0x1
|
|
## Test we are able to dump duplicated segments.
|
|
## We use a segment that is the same as the previous one for this.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .gnu.hash
|
|
LastSec: .gnu.hash
|
|
VAddr: 0x1A0
|
|
Align: 0x1
|
|
Sections:
|
|
- Name: .hash
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Address: 0x190
|
|
Size: 0x10
|
|
- Name: .gnu.hash
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Address: 0x1A0
|
|
Size: 0x20
|
|
- Name: .dynsym
|
|
Type: SHT_DYNSYM
|
|
Flags: [ SHF_ALLOC ]
|
|
Address: 0x1C0
|
|
Link: .dynstr
|
|
EntSize: 0x18
|
|
- Name: .dynstr
|
|
Type: SHT_STRTAB
|
|
Flags: [ SHF_ALLOC ]
|
|
Address: 0x1D8
|
|
- Name: .foo
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
|
|
Address: 0x1000
|
|
Size: 0x8
|
|
- Name: .zed
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
|
|
Address: 0x1008
|
|
Size: 0x8
|
|
- Name: '.foo (1)'
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Address: 0x2000
|
|
Size: 0x8
|
|
- Name: .baz
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Address: 0x2008
|
|
Size: 0x1
|
|
- Name: .dynamic
|
|
Type: SHT_DYNAMIC
|
|
Flags: [ SHF_WRITE, SHF_ALLOC ]
|
|
Address: 0x0000000000003EF0
|
|
Link: .dynstr
|
|
Entries:
|
|
- Tag: DT_NULL
|
|
Value: 0x0
|
|
- Name: .dynamic.tail
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_WRITE, SHF_ALLOC ]
|
|
Content: "FE"
|
|
Symbols: []
|
|
DynamicSymbols: []
|
|
|
|
## Part II. More specific tests.
|
|
|
|
## Check we are able to dump segments that are empty or
|
|
## contain empty sections.
|
|
# RUN: yaml2obj --docnum=2 %s -o %t2
|
|
# RUN: obj2yaml %t2 | FileCheck %s --check-prefix=EMPTY
|
|
|
|
# EMPTY: - Type: PT_LOAD
|
|
# EMPTY-NEXT: Flags: [ PF_W, PF_R ]
|
|
# EMPTY-NEXT: FirstSec: .empty.tls.start
|
|
# EMPTY-NEXT: LastSec: .empty.tls.end
|
|
# EMPTY-NEXT: VAddr: 0x1000
|
|
# EMPTY-NEXT: Align: 0x1000
|
|
# EMPTY-NEXT: - Type: PT_TLS
|
|
# EMPTY-NEXT: Flags: [ PF_W, PF_R ]
|
|
# EMPTY-NEXT: FirstSec: .empty.tls.start
|
|
# EMPTY-NEXT: LastSec: .empty.tls.start
|
|
# EMPTY-NEXT: VAddr: 0x1000
|
|
# EMPTY-NEXT: - Type: PT_TLS
|
|
# EMPTY-NEXT: Flags: [ PF_W, PF_R ]
|
|
# EMPTY-NEXT: FirstSec: .empty.tls.middle
|
|
# EMPTY-NEXT: LastSec: .empty.tls.middle
|
|
# EMPTY-NEXT: VAddr: 0x1100
|
|
# EMPTY-NEXT: - Type: PT_TLS
|
|
# EMPTY-NEXT: Flags: [ PF_W, PF_R ]
|
|
# EMPTY-NEXT: FirstSec: .empty.tls.end
|
|
# EMPTY-NEXT: LastSec: .empty.tls.end
|
|
# EMPTY-NEXT: VAddr: 0x1200
|
|
# EMPTY-NEXT: Sections:
|
|
|
|
--- !ELF
|
|
FileHeader:
|
|
Class: ELFCLASS64
|
|
Data: ELFDATA2LSB
|
|
Type: ET_DYN
|
|
ProgramHeaders:
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .empty.tls.start
|
|
LastSec: .empty.tls.end
|
|
VAddr: 0x1000
|
|
Align: 0x1000
|
|
- Type: PT_TLS
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .empty.tls.start
|
|
LastSec: .empty.tls.start
|
|
VAddr: 0x1000
|
|
Align: 0x1
|
|
- Type: PT_TLS
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .empty.tls.middle
|
|
LastSec: .empty.tls.middle
|
|
VAddr: 0x1100
|
|
Align: 0x1
|
|
- Type: PT_TLS
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .empty.tls.end
|
|
LastSec: .empty.tls.end
|
|
VAddr: 0x1200
|
|
Align: 0x1
|
|
Sections:
|
|
- Name: .empty.tls.start
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_TLS ]
|
|
Size: 0x0
|
|
Address: 0x1000
|
|
- Name: .section.1
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Size: 0x100
|
|
- Name: .empty.tls.middle
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_TLS ]
|
|
Size: 0x0
|
|
- Name: .section.2
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Size: 0x100
|
|
- Name: .empty.tls.end
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_TLS ]
|
|
Size: 0x0
|
|
|
|
## Document we are able to dump misaligned segments.
|
|
## I.e. segments where (p_offset % p_align) != (p_vaddr % p_align).
|
|
# RUN: yaml2obj --docnum=3 %s -o %t3
|
|
# RUN: llvm-readelf --segments --sections %t3 | FileCheck %s --check-prefix=MISALIGNED-READELF
|
|
# RUN: obj2yaml %t3 | FileCheck %s --check-prefix=MISALIGNED-YAML
|
|
|
|
## As a misaligned p_offset value we use (`.foo` section offset - 1).
|
|
# MISALIGNED-READELF: [Nr] Name Type Address Off
|
|
# MISALIGNED-READELF: [ 1] .foo PROGBITS 0000000000001000 000078
|
|
# MISALIGNED-READELF: Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align
|
|
# MISALIGNED-READELF-NEXT: LOAD 0x000077 0x0000000000001000 0x0000000000001000 0x000078 0x000078 R 0x1000
|
|
|
|
# MISALIGNED-YAML: ProgramHeaders:
|
|
# MISALIGNED-YAML-NEXT: - Type: PT_LOAD
|
|
# MISALIGNED-YAML-NEXT: Flags: [ PF_R ]
|
|
# MISALIGNED-YAML-NEXT: FirstSec: .foo
|
|
# MISALIGNED-YAML-NEXT: LastSec: .foo
|
|
# MISALIGNED-YAML-NEXT: VAddr: 0x1000
|
|
# MISALIGNED-YAML-NEXT: Align: 0x1000
|
|
# MISALIGNED-YAML-NEXT: Sections:
|
|
|
|
--- !ELF
|
|
FileHeader:
|
|
Class: ELFCLASS64
|
|
Data: ELFDATA2LSB
|
|
Type: ET_DYN
|
|
ProgramHeaders:
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .foo
|
|
LastSec: .foo
|
|
VAddr: 0x1000
|
|
Align: 0x1000
|
|
Offset: 0x000077
|
|
Sections:
|
|
- Name: .foo
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Size: 0x77
|
|
Address: 0x1000
|
|
|
|
## Test we include non-allocatable sections in segments.
|
|
## We also document that SHT_NULL sections are not considered to be inside a segment.
|
|
# RUN: yaml2obj --docnum=4 %s -o %t4
|
|
# RUN: obj2yaml %t4 | FileCheck %s --check-prefix=NON-ALLOC
|
|
|
|
# NON-ALLOC: ProgramHeaders:
|
|
# NON-ALLOC-NEXT: - Type: PT_LOAD
|
|
# NON-ALLOC-NEXT: Flags: [ PF_R ]
|
|
# NON-ALLOC-NEXT: FirstSec: .alloc.1
|
|
# NON-ALLOC-NEXT: LastSec: .non-alloc.1
|
|
# NON-ALLOC-NEXT: - Type: PT_LOAD
|
|
# NON-ALLOC-NEXT: Flags: [ PF_R ]
|
|
# NON-ALLOC-NEXT: FirstSec: .alloc.1
|
|
# NON-ALLOC-NEXT: LastSec: .non-alloc.1
|
|
# NON-ALLOC-NEXT: - Type: PT_LOAD
|
|
# NON-ALLOC-NEXT: Flags: [ PF_R ]
|
|
# NON-ALLOC-NEXT: FirstSec: .alloc.2
|
|
# NON-ALLOC-NEXT: LastSec: .alloc.2
|
|
# NON-ALLOC-NEXT: - Type: PT_LOAD
|
|
# NON-ALLOC-NEXT: Flags: [ PF_R ]
|
|
# NON-ALLOC-NEXT: FirstSec: .alloc.1
|
|
# NON-ALLOC-NEXT: LastSec: .alloc.2
|
|
# NON-ALLOC-NEXT: Sections:
|
|
|
|
--- !ELF
|
|
FileHeader:
|
|
Class: ELFCLASS64
|
|
Data: ELFDATA2LSB
|
|
Type: ET_DYN
|
|
ProgramHeaders:
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .alloc.1
|
|
LastSec: .non-alloc.1
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .alloc.1
|
|
LastSec: .non-alloc.2
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .non-alloc.2
|
|
LastSec: .alloc.2
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .alloc.1
|
|
LastSec: .alloc.2
|
|
Sections:
|
|
- Name: .alloc.1
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Size: 0x100
|
|
Address: 0x1000
|
|
- Name: .non-alloc.1
|
|
Type: SHT_PROGBITS
|
|
Flags: [ ]
|
|
Size: 0x10
|
|
- Name: .non-alloc.2
|
|
Type: SHT_NULL
|
|
Flags: [ ]
|
|
Size: 0x10
|
|
- Name: .alloc.2
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Size: 0x1
|
|
|
|
## Check how we dump segments which contain SHT_NOBITS sections.
|
|
# RUN: yaml2obj --docnum=5 %s -o %t5
|
|
# RUN: obj2yaml %t5 | FileCheck %s --check-prefix=NOBITS
|
|
|
|
# NOBITS: ProgramHeaders:
|
|
# NOBITS-NEXT: - Type: PT_LOAD
|
|
# NOBITS-NEXT: Flags: [ PF_W, PF_R ]
|
|
# NOBITS-NEXT: FirstSec: .bss
|
|
# NOBITS-NEXT: LastSec: .bss
|
|
# NOBITS-NEXT: - Type: PT_LOAD
|
|
# NOBITS-NEXT: Flags: [ PF_W, PF_R ]
|
|
# NOBITS-NEXT: FirstSec: .data.1
|
|
# NOBITS-NEXT: LastSec: .bss
|
|
# NOBITS-NEXT: - Type: PT_LOAD
|
|
# NOBITS-NEXT: Flags: [ PF_W, PF_R ]
|
|
# NOBITS-NEXT: FirstSec: .data.1
|
|
# NOBITS-NEXT: LastSec: .data.2
|
|
# NOBITS-NEXT: - Type: PT_LOAD
|
|
# NOBITS-NEXT: Flags: [ PF_W, PF_R ]
|
|
# NOBITS-NEXT: FirstSec: .bss
|
|
# NOBITS-NEXT: LastSec: .data.2
|
|
# NOBITS-NEXT: - Type: PT_LOAD
|
|
# NOBITS-NEXT: Flags: [ PF_W, PF_R ]
|
|
# NOBITS-NEXT: FirstSec: .foo.bss
|
|
# NOBITS-NEXT: LastSec: .bar.bss
|
|
# NOBITS-NEXT: VAddr: 0x200000000
|
|
# NOBITS-NEXT: Sections:
|
|
|
|
--- !ELF
|
|
FileHeader:
|
|
Class: ELFCLASS64
|
|
Data: ELFDATA2LSB
|
|
Type: ET_EXEC
|
|
ProgramHeaders:
|
|
## Case 1: the segment contains a single SHT_NOBITS section.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .bss
|
|
LastSec: .bss
|
|
## Case 2: the SHT_NOBITS section is the last section in the segment.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .data.1
|
|
LastSec: .bss
|
|
## Case 3: the SHT_NOBITS section is in the middle of the segment.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .data.1
|
|
LastSec: .data.2
|
|
## Case 4: the SHT_NOBITS section is the first section in the segment.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .bss
|
|
LastSec: .data.2
|
|
## Case 5: another two SHT_NOBITS sections in a different segment.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .foo.bss
|
|
LastSec: .bar.bss
|
|
VAddr: 0x200000000
|
|
Sections:
|
|
- Name: .data.1
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_WRITE, SHF_ALLOC ]
|
|
## Use an arbitrary address and size.
|
|
Address: 0x1000
|
|
Size: 0x1
|
|
- Name: .bss
|
|
Type: SHT_NOBITS
|
|
Flags: [ SHF_WRITE, SHF_ALLOC ]
|
|
## Use a size that is larger than the file size.
|
|
ShSize: 0x00000000FFFFFFFF
|
|
- Name: .data.2
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_WRITE, SHF_ALLOC ]
|
|
## Use an arbitrary size.
|
|
Size: 0x1
|
|
- Name: .foo.bss
|
|
Type: SHT_NOBITS
|
|
Flags: [ SHF_WRITE, SHF_ALLOC ]
|
|
## Set an arbitrary address and size so that this section can be used
|
|
## to start a different non-overlapping segment.
|
|
## I.e. its address is larger than addresses of previous sections.
|
|
Size: 0x10
|
|
Address: 0x200000000
|
|
- Name: .bar.bss
|
|
Type: SHT_NOBITS
|
|
Flags: [ SHF_WRITE, SHF_ALLOC ]
|
|
## Use an arbitrary size that is different to the size of
|
|
## the previous section.
|
|
Size: 0x20
|
|
|
|
## Check that we require sections in a program header
|
|
## declaration to be sorted by their offsets.
|
|
# RUN: not yaml2obj --docnum=6 %s -o %t6 2>&1 | \
|
|
# RUN: FileCheck %s --check-prefix=UNSORTED --implicit-check-not="error:"
|
|
|
|
# UNSORTED: error: program header with index 0: the section index of .bar is greater than the index of .foo
|
|
# UNSORTED-NEXT: error: sections in the program header with index 3 are not sorted by their file offset
|
|
|
|
--- !ELF
|
|
FileHeader:
|
|
Class: ELFCLASS64
|
|
Data: ELFDATA2LSB
|
|
Type: ET_DYN
|
|
ProgramHeaders:
|
|
## Case 1: the .bar section is placed after the .foo section in the file.
|
|
## Check we report an error about the violation of the order.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .bar
|
|
LastSec: .foo
|
|
VAddr: 0x1000
|
|
## There is nothing wrong with this segment. We have it to show that
|
|
## we report correct program header indices in error messages.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .foo
|
|
LastSec: .bar
|
|
VAddr: 0x1000
|
|
## Case 2: the .bar section is placed before the .zed section in the file,
|
|
## but the sh_offset of .zed is less than the sh_offset of
|
|
## the .bar section because of the "ShOffset" property.
|
|
## Document we report an error for such a case.
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_R ]
|
|
FirstSec: .bar
|
|
LastSec: .zed
|
|
VAddr: 0x1001
|
|
Sections:
|
|
- Name: .foo
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Size: 0x1
|
|
Address: 0x1000
|
|
- Name: .bar
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Size: 0x1
|
|
- Name: .zed
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC ]
|
|
Size: 0x1
|
|
ShOffset: 0x0
|
|
|
|
## Check how we dump segments which contain empty sections.
|
|
# RUN: yaml2obj --docnum=7 %s -o %t7
|
|
|
|
## Show the layout of the object before we dump it using obj2yaml.
|
|
## Notes: 1) '.empty.foo', '.empty.bar1' and '.bar' have the same file offset, but '.empty.foo'
|
|
## has a VA that is outside of the segment, hence we should not include it in it.
|
|
## 2) '.bar1' ends at 0x79, which is the starting file offset of both '.empty.bar2'
|
|
## and '.empty.zed'. We should only include '.empty.bar2', because the VA of the
|
|
## '.empty.zed' section is outside the segment's virtual space.
|
|
# RUN: llvm-readelf -sections %t7 | FileCheck %s --check-prefix=ZERO-SIZE-MAPPING
|
|
|
|
# ZERO-SIZE-MAPPING: Section Headers:
|
|
# ZERO-SIZE-MAPPING-NEXT: [Nr] Name Type Address Off Size
|
|
# ZERO-SIZE-MAPPING: [ 1] .empty.foo PROGBITS 0000000000001000 000078 000000
|
|
# ZERO-SIZE-MAPPING-NEXT: [ 2] .empty.bar1 PROGBITS 0000000000002000 000078 000000
|
|
# ZERO-SIZE-MAPPING-NEXT: [ 3] .bar PROGBITS 0000000000002000 000078 000001
|
|
# ZERO-SIZE-MAPPING-NEXT: [ 4] .empty.bar2 PROGBITS 0000000000002001 000079 000000
|
|
# ZERO-SIZE-MAPPING-NEXT: [ 5] .empty.zed PROGBITS 0000000000003000 000079 000000
|
|
|
|
# RUN: obj2yaml %t7 | FileCheck %s --check-prefix=ZERO-SIZE
|
|
|
|
# ZERO-SIZE: ProgramHeaders:
|
|
# ZERO-SIZE-NEXT: - Type: PT_LOAD
|
|
# ZERO-SIZE-NEXT: Flags: [ PF_W, PF_R ]
|
|
# ZERO-SIZE-NEXT: FirstSec: .empty.bar1
|
|
# ZERO-SIZE-NEXT: LastSec: .empty.bar2
|
|
# ZERO-SIZE-NEXT: VAddr: 0x2000
|
|
# ZERO-SIZE-NEXT: Sections:
|
|
|
|
--- !ELF
|
|
FileHeader:
|
|
Class: ELFCLASS64
|
|
Data: ELFDATA2LSB
|
|
Type: ET_EXEC
|
|
ProgramHeaders:
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_W, PF_R ]
|
|
FirstSec: .bar
|
|
LastSec: .bar
|
|
VAddr: 0x2000
|
|
Sections:
|
|
- Name: .empty.foo
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
|
|
Address: 0x1000
|
|
- Name: .empty.bar1
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
|
|
Address: 0x2000
|
|
- Name: .bar
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_WRITE, SHF_ALLOC ]
|
|
Address: 0x2000
|
|
Size: 0x1
|
|
- Name: .empty.bar2
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
|
|
Address: 0x2001
|
|
- Name: .empty.zed
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
|
|
Address: 0x3000
|
|
|
|
## Check how we dump a segment when we have sections that are outside of the virtual
|
|
## address space of a segment, but inside its file space. We do not include such sections
|
|
## in a segment when they are at the edges of a segment, because this is a normal case and
|
|
## it may mean they belong to a different segment.
|
|
# RUN: yaml2obj --docnum=8 %s -o %t8
|
|
# RUN: obj2yaml %t8 | FileCheck %s --check-prefix=BROKEN-VA
|
|
|
|
# BROKEN-VA: ProgramHeaders:
|
|
# BROKEN-VA-NEXT: - Type: PT_LOAD
|
|
# BROKEN-VA-NEXT: Flags: [ PF_W, PF_R ]
|
|
# BROKEN-VA-NEXT: FirstSec: .empty_middle
|
|
# BROKEN-VA-NEXT: LastSec: .empty_middle
|
|
# BROKEN-VA-NEXT: VAddr: 0x1000
|
|
|
|
--- !ELF
|
|
FileHeader:
|
|
Class: ELFCLASS64
|
|
Data: ELFDATA2LSB
|
|
Type: ET_EXEC
|
|
ProgramHeaders:
|
|
- Type: PT_LOAD
|
|
Flags: [ PF_W, PF_R ]
|
|
VAddr: 0x1000
|
|
FirstSec: .empty_begin
|
|
LastSec: .empty_end
|
|
Sections:
|
|
- Name: .empty_begin
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
|
|
Address: 0xFEFEFEFE
|
|
- Type: Fill
|
|
Pattern: "00"
|
|
Size: 1
|
|
Name: begin
|
|
- Name: .empty_middle
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
|
|
Address: 0xFEFEFEFE
|
|
- Type: Fill
|
|
Pattern: "00"
|
|
Size: 1
|
|
- Name: .empty_end
|
|
Type: SHT_PROGBITS
|
|
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
|
|
Address: 0xFEFEFEFE
|