1 //===------ utils/elf2yaml.cpp - obj2yaml conversion tool -------*- C++ -*-===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
10 #include "llvm/ADT/DenseSet.h"
11 #include "llvm/ADT/STLExtras.h"
12 #include "llvm/ADT/Twine.h"
13 #include "llvm/DebugInfo/DWARF/DWARFContext.h"
14 #include "llvm/Object/ELFObjectFile.h"
15 #include "llvm/ObjectYAML/DWARFYAML.h"
16 #include "llvm/ObjectYAML/ELFYAML.h"
17 #include "llvm/Support/DataExtractor.h"
18 #include "llvm/Support/ErrorHandling.h"
19 #include "llvm/Support/YAMLTraits.h"
27 LLVM_ELF_IMPORT_TYPES_ELFT(ELFT
)
29 ArrayRef
<Elf_Shdr
> Sections
;
30 ArrayRef
<Elf_Sym
> SymTable
;
32 DenseMap
<StringRef
, uint32_t> UsedSectionNames
;
33 std::vector
<std::string
> SectionNames
;
34 Optional
<uint32_t> ShStrTabIndex
;
36 DenseMap
<StringRef
, uint32_t> UsedSymbolNames
;
37 std::vector
<std::string
> SymbolNames
;
39 BumpPtrAllocator StringAllocator
;
41 Expected
<StringRef
> getUniquedSectionName(const Elf_Shdr
&Sec
);
42 Expected
<StringRef
> getUniquedSymbolName(const Elf_Sym
*Sym
,
44 const Elf_Shdr
*SymTab
);
45 Expected
<StringRef
> getSymbolName(uint32_t SymtabNdx
, uint32_t SymbolNdx
);
47 const object::ELFFile
<ELFT
> &Obj
;
48 std::unique_ptr
<DWARFContext
> DWARFCtx
;
50 DenseMap
<const Elf_Shdr
*, ArrayRef
<Elf_Word
>> ShndxTables
;
52 Expected
<std::vector
<ELFYAML::ProgramHeader
>>
53 dumpProgramHeaders(ArrayRef
<std::unique_ptr
<ELFYAML::Chunk
>> Sections
);
55 Optional
<DWARFYAML::Data
>
56 dumpDWARFSections(std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> &Sections
);
58 Error
dumpSymbols(const Elf_Shdr
*Symtab
,
59 Optional
<std::vector
<ELFYAML::Symbol
>> &Symbols
);
60 Error
dumpSymbol(const Elf_Sym
*Sym
, const Elf_Shdr
*SymTab
,
61 StringRef StrTable
, ELFYAML::Symbol
&S
);
62 Expected
<std::vector
<std::unique_ptr
<ELFYAML::Chunk
>>> dumpSections();
63 Error
dumpCommonSection(const Elf_Shdr
*Shdr
, ELFYAML::Section
&S
);
64 Error
dumpCommonRelocationSection(const Elf_Shdr
*Shdr
,
65 ELFYAML::RelocationSection
&S
);
67 Error
dumpRelocation(const RelT
*Rel
, const Elf_Shdr
*SymTab
,
68 ELFYAML::Relocation
&R
);
70 Expected
<ELFYAML::AddrsigSection
*> dumpAddrsigSection(const Elf_Shdr
*Shdr
);
71 Expected
<ELFYAML::LinkerOptionsSection
*>
72 dumpLinkerOptionsSection(const Elf_Shdr
*Shdr
);
73 Expected
<ELFYAML::DependentLibrariesSection
*>
74 dumpDependentLibrariesSection(const Elf_Shdr
*Shdr
);
75 Expected
<ELFYAML::CallGraphProfileSection
*>
76 dumpCallGraphProfileSection(const Elf_Shdr
*Shdr
);
77 Expected
<ELFYAML::DynamicSection
*> dumpDynamicSection(const Elf_Shdr
*Shdr
);
78 Expected
<ELFYAML::RelocationSection
*> dumpRelocSection(const Elf_Shdr
*Shdr
);
79 Expected
<ELFYAML::RelrSection
*> dumpRelrSection(const Elf_Shdr
*Shdr
);
80 Expected
<ELFYAML::RawContentSection
*>
81 dumpContentSection(const Elf_Shdr
*Shdr
);
82 Expected
<ELFYAML::SymtabShndxSection
*>
83 dumpSymtabShndxSection(const Elf_Shdr
*Shdr
);
84 Expected
<ELFYAML::NoBitsSection
*> dumpNoBitsSection(const Elf_Shdr
*Shdr
);
85 Expected
<ELFYAML::HashSection
*> dumpHashSection(const Elf_Shdr
*Shdr
);
86 Expected
<ELFYAML::NoteSection
*> dumpNoteSection(const Elf_Shdr
*Shdr
);
87 Expected
<ELFYAML::GnuHashSection
*> dumpGnuHashSection(const Elf_Shdr
*Shdr
);
88 Expected
<ELFYAML::VerdefSection
*> dumpVerdefSection(const Elf_Shdr
*Shdr
);
89 Expected
<ELFYAML::SymverSection
*> dumpSymverSection(const Elf_Shdr
*Shdr
);
90 Expected
<ELFYAML::VerneedSection
*> dumpVerneedSection(const Elf_Shdr
*Shdr
);
91 Expected
<ELFYAML::GroupSection
*> dumpGroupSection(const Elf_Shdr
*Shdr
);
92 Expected
<ELFYAML::ARMIndexTableSection
*>
93 dumpARMIndexTableSection(const Elf_Shdr
*Shdr
);
94 Expected
<ELFYAML::MipsABIFlags
*> dumpMipsABIFlags(const Elf_Shdr
*Shdr
);
95 Expected
<ELFYAML::StackSizesSection
*>
96 dumpStackSizesSection(const Elf_Shdr
*Shdr
);
97 Expected
<ELFYAML::BBAddrMapSection
*>
98 dumpBBAddrMapSection(const Elf_Shdr
*Shdr
);
99 Expected
<ELFYAML::RawContentSection
*>
100 dumpPlaceholderSection(const Elf_Shdr
*Shdr
);
102 bool shouldPrintSection(const ELFYAML::Section
&S
, const Elf_Shdr
&SHdr
,
103 Optional
<DWARFYAML::Data
> DWARF
);
106 ELFDumper(const object::ELFFile
<ELFT
> &O
, std::unique_ptr
<DWARFContext
> DCtx
);
107 Expected
<ELFYAML::Object
*> dump();
112 template <class ELFT
>
113 ELFDumper
<ELFT
>::ELFDumper(const object::ELFFile
<ELFT
> &O
,
114 std::unique_ptr
<DWARFContext
> DCtx
)
115 : Obj(O
), DWARFCtx(std::move(DCtx
)) {}
117 template <class ELFT
>
119 ELFDumper
<ELFT
>::getUniquedSectionName(const Elf_Shdr
&Sec
) {
120 unsigned SecIndex
= &Sec
- &Sections
[0];
121 if (!SectionNames
[SecIndex
].empty())
122 return SectionNames
[SecIndex
];
124 auto NameOrErr
= Obj
.getSectionName(Sec
);
127 StringRef Name
= *NameOrErr
;
128 // In some specific cases we might have more than one section without a
129 // name (sh_name == 0). It normally doesn't happen, but when we have this case
130 // it doesn't make sense to uniquify their names and add noise to the output.
134 std::string
&Ret
= SectionNames
[SecIndex
];
136 auto It
= UsedSectionNames
.insert({Name
, 0});
138 Ret
= ELFYAML::appendUniqueSuffix(Name
, Twine(++It
.first
->second
));
140 Ret
= std::string(Name
);
144 template <class ELFT
>
146 ELFDumper
<ELFT
>::getUniquedSymbolName(const Elf_Sym
*Sym
, StringRef StrTable
,
147 const Elf_Shdr
*SymTab
) {
148 Expected
<StringRef
> SymbolNameOrErr
= Sym
->getName(StrTable
);
149 if (!SymbolNameOrErr
)
150 return SymbolNameOrErr
;
151 StringRef Name
= *SymbolNameOrErr
;
152 if (Name
.empty() && Sym
->getType() == ELF::STT_SECTION
) {
153 Expected
<const Elf_Shdr
*> ShdrOrErr
=
154 Obj
.getSection(*Sym
, SymTab
, ShndxTables
.lookup(SymTab
));
156 return ShdrOrErr
.takeError();
157 // The null section has no name.
158 return (*ShdrOrErr
== nullptr) ? "" : getUniquedSectionName(**ShdrOrErr
);
161 // Symbols in .symtab can have duplicate names. For example, it is a common
162 // situation for local symbols in a relocatable object. Here we assign unique
163 // suffixes for such symbols so that we can differentiate them.
164 if (SymTab
->sh_type
== ELF::SHT_SYMTAB
) {
165 unsigned Index
= Sym
- SymTable
.data();
166 if (!SymbolNames
[Index
].empty())
167 return SymbolNames
[Index
];
169 auto It
= UsedSymbolNames
.insert({Name
, 0});
172 ELFYAML::appendUniqueSuffix(Name
, Twine(++It
.first
->second
));
174 SymbolNames
[Index
] = std::string(Name
);
175 return SymbolNames
[Index
];
181 template <class ELFT
>
182 bool ELFDumper
<ELFT
>::shouldPrintSection(const ELFYAML::Section
&S
,
183 const Elf_Shdr
&SHdr
,
184 Optional
<DWARFYAML::Data
> DWARF
) {
185 // We only print the SHT_NULL section at index 0 when it
186 // has at least one non-null field, because yaml2obj
187 // normally creates the zero section at index 0 implicitly.
188 if (S
.Type
== ELF::SHT_NULL
&& (&SHdr
== &Sections
[0])) {
189 const uint8_t *Begin
= reinterpret_cast<const uint8_t *>(&SHdr
);
190 const uint8_t *End
= Begin
+ sizeof(Elf_Shdr
);
191 return std::any_of(Begin
, End
, [](uint8_t V
) { return V
!= 0; });
194 // Normally we use "DWARF:" to describe contents of DWARF sections. Sometimes
195 // the content of DWARF sections can be successfully parsed into the "DWARF:"
196 // entry but their section headers may have special flags, entry size, address
197 // alignment, etc. We will preserve the header for them under such
199 StringRef SecName
= S
.Name
.substr(1);
200 if (DWARF
&& DWARF
->getNonEmptySectionNames().count(SecName
)) {
201 if (const ELFYAML::RawContentSection
*RawSec
=
202 dyn_cast
<const ELFYAML::RawContentSection
>(&S
)) {
203 if (RawSec
->Type
!= ELF::SHT_PROGBITS
|| RawSec
->Link
|| RawSec
->Info
||
204 RawSec
->AddressAlign
!= yaml::Hex64
{1} || RawSec
->Address
||
208 ELFYAML::ELF_SHF ShFlags
= RawSec
->Flags
.getValueOr(ELFYAML::ELF_SHF(0));
210 if (SecName
== "debug_str")
211 return ShFlags
!= ELFYAML::ELF_SHF(ELF::SHF_MERGE
| ELF::SHF_STRINGS
);
213 return ShFlags
!= ELFYAML::ELF_SHF
{0};
217 // Normally we use "Symbols:" and "DynamicSymbols:" to describe contents of
218 // symbol tables. We also build and emit corresponding string tables
219 // implicitly. But sometimes it is important to preserve positions and virtual
220 // addresses of allocatable sections, e.g. for creating program headers.
221 // Generally we are trying to reduce noise in the YAML output. Because
222 // of that we do not print non-allocatable versions of such sections and
223 // assume they are placed at the end.
224 // We also dump symbol tables when the Size field is set. It happens when they
225 // are empty, which should not normally happen.
226 if (S
.Type
== ELF::SHT_STRTAB
|| S
.Type
== ELF::SHT_SYMTAB
||
227 S
.Type
== ELF::SHT_DYNSYM
) {
228 return S
.Size
|| S
.Flags
.getValueOr(ELFYAML::ELF_SHF(0)) & ELF::SHF_ALLOC
;
234 template <class ELFT
>
235 static void dumpSectionOffsets(const typename
ELFT::Ehdr
&Header
,
236 ArrayRef
<ELFYAML::ProgramHeader
> Phdrs
,
237 std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> &V
,
238 ArrayRef
<typename
ELFT::Shdr
> S
) {
242 uint64_t ExpectedOffset
;
243 if (Header
.e_phoff
> 0)
244 ExpectedOffset
= Header
.e_phoff
+ Header
.e_phentsize
* Header
.e_phnum
;
246 ExpectedOffset
= sizeof(typename
ELFT::Ehdr
);
248 for (const std::unique_ptr
<ELFYAML::Chunk
> &C
:
249 makeArrayRef(V
).drop_front()) {
250 ELFYAML::Section
&Sec
= *cast
<ELFYAML::Section
>(C
.get());
251 const typename
ELFT::Shdr
&SecHdr
= S
[Sec
.OriginalSecNdx
];
253 ExpectedOffset
= alignTo(ExpectedOffset
,
254 SecHdr
.sh_addralign
? SecHdr
.sh_addralign
: 1uLL);
256 // We only set the "Offset" field when it can't be naturally derived
257 // from the offset and size of the previous section. This reduces
258 // the noise in the YAML output.
259 if (SecHdr
.sh_offset
!= ExpectedOffset
)
260 Sec
.Offset
= (yaml::Hex64
)SecHdr
.sh_offset
;
262 if (Sec
.Type
== ELF::SHT_NOBITS
&&
263 !ELFYAML::shouldAllocateFileSpace(Phdrs
,
264 *cast
<ELFYAML::NoBitsSection
>(&Sec
)))
265 ExpectedOffset
= SecHdr
.sh_offset
;
267 ExpectedOffset
= SecHdr
.sh_offset
+ SecHdr
.sh_size
;
271 template <class ELFT
> Expected
<ELFYAML::Object
*> ELFDumper
<ELFT
>::dump() {
272 auto Y
= std::make_unique
<ELFYAML::Object
>();
274 // Dump header. We do not dump EPh* and ESh* fields. When not explicitly set,
275 // the values are set by yaml2obj automatically and there is no need to dump
277 Y
->Header
.Class
= ELFYAML::ELF_ELFCLASS(Obj
.getHeader().getFileClass());
278 Y
->Header
.Data
= ELFYAML::ELF_ELFDATA(Obj
.getHeader().getDataEncoding());
279 Y
->Header
.OSABI
= Obj
.getHeader().e_ident
[ELF::EI_OSABI
];
280 Y
->Header
.ABIVersion
= Obj
.getHeader().e_ident
[ELF::EI_ABIVERSION
];
281 Y
->Header
.Type
= Obj
.getHeader().e_type
;
282 if (Obj
.getHeader().e_machine
!= 0)
283 Y
->Header
.Machine
= ELFYAML::ELF_EM(Obj
.getHeader().e_machine
);
284 Y
->Header
.Flags
= Obj
.getHeader().e_flags
;
285 Y
->Header
.Entry
= Obj
.getHeader().e_entry
;
288 auto SectionsOrErr
= Obj
.sections();
290 return SectionsOrErr
.takeError();
291 Sections
= *SectionsOrErr
;
292 SectionNames
.resize(Sections
.size());
294 if (Sections
.size() > 0) {
295 ShStrTabIndex
= Obj
.getHeader().e_shstrndx
;
296 if (*ShStrTabIndex
== ELF::SHN_XINDEX
)
297 ShStrTabIndex
= Sections
[0].sh_link
;
298 // TODO: Set EShStrndx if the value doesn't represent a real section.
301 // Normally an object that does not have sections has e_shnum == 0.
302 // Also, e_shnum might be 0, when the the number of entries in the section
303 // header table is larger than or equal to SHN_LORESERVE (0xff00). In this
304 // case the real number of entries is held in the sh_size member of the
305 // initial entry. We have a section header table when `e_shoff` is not 0.
306 if (Obj
.getHeader().e_shoff
!= 0 && Obj
.getHeader().e_shnum
== 0)
307 Y
->Header
.EShNum
= 0;
309 // Dump symbols. We need to do this early because other sections might want
310 // to access the deduplicated symbol names that we also create here.
311 const Elf_Shdr
*SymTab
= nullptr;
312 const Elf_Shdr
*DynSymTab
= nullptr;
314 for (const Elf_Shdr
&Sec
: Sections
) {
315 if (Sec
.sh_type
== ELF::SHT_SYMTAB
) {
317 } else if (Sec
.sh_type
== ELF::SHT_DYNSYM
) {
319 } else if (Sec
.sh_type
== ELF::SHT_SYMTAB_SHNDX
) {
320 // We need to locate SHT_SYMTAB_SHNDX sections early, because they
321 // might be needed for dumping symbols.
322 if (Expected
<ArrayRef
<Elf_Word
>> TableOrErr
= Obj
.getSHNDXTable(Sec
)) {
323 // The `getSHNDXTable` calls the `getSection` internally when validates
324 // the symbol table section linked to the SHT_SYMTAB_SHNDX section.
325 const Elf_Shdr
*LinkedSymTab
= cantFail(Obj
.getSection(Sec
.sh_link
));
326 if (!ShndxTables
.insert({LinkedSymTab
, *TableOrErr
}).second
)
327 return createStringError(
328 errc::invalid_argument
,
329 "multiple SHT_SYMTAB_SHNDX sections are "
330 "linked to the same symbol table with index " +
333 return createStringError(errc::invalid_argument
,
334 "unable to read extended section indexes: " +
335 toString(TableOrErr
.takeError()));
341 if (Error E
= dumpSymbols(SymTab
, Y
->Symbols
))
345 if (Error E
= dumpSymbols(DynSymTab
, Y
->DynamicSymbols
))
348 // We dump all sections first. It is simple and allows us to verify that all
349 // sections are valid and also to generalize the code. But we are not going to
350 // keep all of them in the final output (see comments for
351 // 'shouldPrintSection()'). Undesired chunks will be removed later.
352 Expected
<std::vector
<std::unique_ptr
<ELFYAML::Chunk
>>> ChunksOrErr
=
355 return ChunksOrErr
.takeError();
356 std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> Chunks
= std::move(*ChunksOrErr
);
358 std::vector
<ELFYAML::Section
*> OriginalOrder
;
360 for (const std::unique_ptr
<ELFYAML::Chunk
> &C
:
361 makeArrayRef(Chunks
).drop_front())
362 OriginalOrder
.push_back(cast
<ELFYAML::Section
>(C
.get()));
364 // Sometimes the order of sections in the section header table does not match
365 // their actual order. Here we sort sections by the file offset.
366 llvm::stable_sort(Chunks
, [&](const std::unique_ptr
<ELFYAML::Chunk
> &A
,
367 const std::unique_ptr
<ELFYAML::Chunk
> &B
) {
368 return Sections
[cast
<ELFYAML::Section
>(A
.get())->OriginalSecNdx
].sh_offset
<
369 Sections
[cast
<ELFYAML::Section
>(B
.get())->OriginalSecNdx
].sh_offset
;
372 // Dump program headers.
373 Expected
<std::vector
<ELFYAML::ProgramHeader
>> PhdrsOrErr
=
374 dumpProgramHeaders(Chunks
);
376 return PhdrsOrErr
.takeError();
377 Y
->ProgramHeaders
= std::move(*PhdrsOrErr
);
379 dumpSectionOffsets
<ELFT
>(Obj
.getHeader(), Y
->ProgramHeaders
, Chunks
,
382 // Dump DWARF sections.
383 Y
->DWARF
= dumpDWARFSections(Chunks
);
385 // We emit the "SectionHeaderTable" key when the order of sections in the
386 // sections header table doesn't match the file order.
387 const bool SectionsSorted
=
388 llvm::is_sorted(Chunks
, [&](const std::unique_ptr
<ELFYAML::Chunk
> &A
,
389 const std::unique_ptr
<ELFYAML::Chunk
> &B
) {
390 return cast
<ELFYAML::Section
>(A
.get())->OriginalSecNdx
<
391 cast
<ELFYAML::Section
>(B
.get())->OriginalSecNdx
;
393 if (!SectionsSorted
) {
394 std::unique_ptr
<ELFYAML::SectionHeaderTable
> SHT
=
395 std::make_unique
<ELFYAML::SectionHeaderTable
>(/*IsImplicit=*/false);
396 SHT
->Sections
.emplace();
397 for (ELFYAML::Section
*S
: OriginalOrder
)
398 SHT
->Sections
->push_back({S
->Name
});
399 Chunks
.push_back(std::move(SHT
));
402 llvm::erase_if(Chunks
, [this, &Y
](const std::unique_ptr
<ELFYAML::Chunk
> &C
) {
403 if (isa
<ELFYAML::SectionHeaderTable
>(*C
.get()))
406 const ELFYAML::Section
&S
= cast
<ELFYAML::Section
>(*C
.get());
407 return !shouldPrintSection(S
, Sections
[S
.OriginalSecNdx
], Y
->DWARF
);
410 // The section header string table by default is assumed to be called
411 // ".shstrtab" and be in its own unique section. However, it's possible for it
412 // to be called something else and shared with another section. If the name
413 // isn't the default, provide this in the YAML.
414 if (ShStrTabIndex
&& *ShStrTabIndex
!= ELF::SHN_UNDEF
&&
415 *ShStrTabIndex
< Sections
.size()) {
416 StringRef ShStrtabName
;
417 if (SymTab
&& SymTab
->sh_link
== *ShStrTabIndex
) {
418 // Section header string table is shared with the symbol table. Use that
419 // section's name (usually .strtab).
420 ShStrtabName
= cantFail(Obj
.getSectionName(Sections
[SymTab
->sh_link
]));
421 } else if (DynSymTab
&& DynSymTab
->sh_link
== *ShStrTabIndex
) {
422 // Section header string table is shared with the dynamic symbol table.
423 // Use that section's name (usually .dynstr).
424 ShStrtabName
= cantFail(Obj
.getSectionName(Sections
[DynSymTab
->sh_link
]));
426 // Otherwise, the section name potentially needs uniquifying.
427 ShStrtabName
= cantFail(getUniquedSectionName(Sections
[*ShStrTabIndex
]));
429 if (ShStrtabName
!= ".shstrtab")
430 Y
->Header
.SectionHeaderStringTable
= ShStrtabName
;
433 Y
->Chunks
= std::move(Chunks
);
437 template <class ELFT
>
438 static bool isInSegment(const ELFYAML::Section
&Sec
,
439 const typename
ELFT::Shdr
&SHdr
,
440 const typename
ELFT::Phdr
&Phdr
) {
441 if (Sec
.Type
== ELF::SHT_NULL
)
444 // A section is within a segment when its location in a file is within the
445 // [p_offset, p_offset + p_filesz] region.
446 bool FileOffsetsMatch
=
447 SHdr
.sh_offset
>= Phdr
.p_offset
&&
448 (SHdr
.sh_offset
+ SHdr
.sh_size
<= Phdr
.p_offset
+ Phdr
.p_filesz
);
450 bool VirtualAddressesMatch
= SHdr
.sh_addr
>= Phdr
.p_vaddr
&&
451 SHdr
.sh_addr
<= Phdr
.p_vaddr
+ Phdr
.p_memsz
;
453 if (FileOffsetsMatch
) {
454 // An empty section on the edges of a program header can be outside of the
455 // virtual address space of the segment. This means it is not included in
456 // the segment and we should ignore it.
457 if (SHdr
.sh_size
== 0 && (SHdr
.sh_offset
== Phdr
.p_offset
||
458 SHdr
.sh_offset
== Phdr
.p_offset
+ Phdr
.p_filesz
))
459 return VirtualAddressesMatch
;
463 // SHT_NOBITS sections usually occupy no physical space in a file. Such
464 // sections belong to a segment when they reside in the segment's virtual
466 if (Sec
.Type
!= ELF::SHT_NOBITS
)
468 return VirtualAddressesMatch
;
471 template <class ELFT
>
472 Expected
<std::vector
<ELFYAML::ProgramHeader
>>
473 ELFDumper
<ELFT
>::dumpProgramHeaders(
474 ArrayRef
<std::unique_ptr
<ELFYAML::Chunk
>> Chunks
) {
475 std::vector
<ELFYAML::ProgramHeader
> Ret
;
476 Expected
<typename
ELFT::PhdrRange
> PhdrsOrErr
= Obj
.program_headers();
478 return PhdrsOrErr
.takeError();
480 for (const typename
ELFT::Phdr
&Phdr
: *PhdrsOrErr
) {
481 ELFYAML::ProgramHeader PH
;
482 PH
.Type
= Phdr
.p_type
;
483 PH
.Flags
= Phdr
.p_flags
;
484 PH
.VAddr
= Phdr
.p_vaddr
;
485 PH
.PAddr
= Phdr
.p_paddr
;
487 // yaml2obj sets the alignment of a segment to 1 by default.
488 // We do not print the default alignment to reduce noise in the output.
489 if (Phdr
.p_align
!= 1)
490 PH
.Align
= static_cast<llvm::yaml::Hex64
>(Phdr
.p_align
);
492 // Here we match sections with segments.
493 // It is not possible to have a non-Section chunk, because
494 // obj2yaml does not create Fill chunks.
495 for (const std::unique_ptr
<ELFYAML::Chunk
> &C
: Chunks
) {
496 ELFYAML::Section
&S
= cast
<ELFYAML::Section
>(*C
.get());
497 if (isInSegment
<ELFT
>(S
, Sections
[S
.OriginalSecNdx
], Phdr
)) {
499 PH
.FirstSec
= S
.Name
;
501 PH
.Chunks
.push_back(C
.get());
511 template <class ELFT
>
512 Optional
<DWARFYAML::Data
> ELFDumper
<ELFT
>::dumpDWARFSections(
513 std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> &Sections
) {
514 DWARFYAML::Data DWARF
;
515 for (std::unique_ptr
<ELFYAML::Chunk
> &C
: Sections
) {
516 if (!C
->Name
.startswith(".debug_"))
519 if (ELFYAML::RawContentSection
*RawSec
=
520 dyn_cast
<ELFYAML::RawContentSection
>(C
.get())) {
521 // FIXME: The dumpDebug* functions should take the content as stored in
522 // RawSec. Currently, they just use the last section with the matching
523 // name, which defeats this attempt to skip reading a section header
524 // string table with the same name as a DWARF section.
525 if (ShStrTabIndex
&& RawSec
->OriginalSecNdx
== *ShStrTabIndex
)
527 Error Err
= Error::success();
528 cantFail(std::move(Err
));
530 if (RawSec
->Name
== ".debug_aranges")
531 Err
= dumpDebugARanges(*DWARFCtx
.get(), DWARF
);
532 else if (RawSec
->Name
== ".debug_str")
533 Err
= dumpDebugStrings(*DWARFCtx
.get(), DWARF
);
534 else if (RawSec
->Name
== ".debug_ranges")
535 Err
= dumpDebugRanges(*DWARFCtx
.get(), DWARF
);
536 else if (RawSec
->Name
== ".debug_addr")
537 Err
= dumpDebugAddr(*DWARFCtx
.get(), DWARF
);
541 // If the DWARF section cannot be successfully parsed, emit raw content
542 // instead of an entry in the DWARF section of the YAML.
544 consumeError(std::move(Err
));
546 RawSec
->Content
.reset();
550 if (DWARF
.getNonEmptySectionNames().empty())
555 template <class ELFT
>
556 Expected
<ELFYAML::RawContentSection
*>
557 ELFDumper
<ELFT
>::dumpPlaceholderSection(const Elf_Shdr
*Shdr
) {
558 auto S
= std::make_unique
<ELFYAML::RawContentSection
>();
559 if (Error E
= dumpCommonSection(Shdr
, *S
.get()))
562 // Normally symbol tables should not be empty. We dump the "Size"
563 // key when they are.
564 if ((Shdr
->sh_type
== ELF::SHT_SYMTAB
|| Shdr
->sh_type
== ELF::SHT_DYNSYM
) &&
571 template <class ELFT
>
572 Expected
<std::vector
<std::unique_ptr
<ELFYAML::Chunk
>>>
573 ELFDumper
<ELFT
>::dumpSections() {
574 std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> Ret
;
575 auto Add
= [&](Expected
<ELFYAML::Chunk
*> SecOrErr
) -> Error
{
577 return SecOrErr
.takeError();
578 Ret
.emplace_back(*SecOrErr
);
579 return Error::success();
582 auto GetDumper
= [this](unsigned Type
)
583 -> std::function
<Expected
<ELFYAML::Chunk
*>(const Elf_Shdr
*)> {
584 if (Obj
.getHeader().e_machine
== ELF::EM_ARM
&& Type
== ELF::SHT_ARM_EXIDX
)
585 return [this](const Elf_Shdr
*S
) { return dumpARMIndexTableSection(S
); };
587 if (Obj
.getHeader().e_machine
== ELF::EM_MIPS
&&
588 Type
== ELF::SHT_MIPS_ABIFLAGS
)
589 return [this](const Elf_Shdr
*S
) { return dumpMipsABIFlags(S
); };
592 case ELF::SHT_DYNAMIC
:
593 return [this](const Elf_Shdr
*S
) { return dumpDynamicSection(S
); };
594 case ELF::SHT_SYMTAB_SHNDX
:
595 return [this](const Elf_Shdr
*S
) { return dumpSymtabShndxSection(S
); };
598 return [this](const Elf_Shdr
*S
) { return dumpRelocSection(S
); };
600 return [this](const Elf_Shdr
*S
) { return dumpRelrSection(S
); };
602 return [this](const Elf_Shdr
*S
) { return dumpGroupSection(S
); };
603 case ELF::SHT_NOBITS
:
604 return [this](const Elf_Shdr
*S
) { return dumpNoBitsSection(S
); };
606 return [this](const Elf_Shdr
*S
) { return dumpNoteSection(S
); };
608 return [this](const Elf_Shdr
*S
) { return dumpHashSection(S
); };
609 case ELF::SHT_GNU_HASH
:
610 return [this](const Elf_Shdr
*S
) { return dumpGnuHashSection(S
); };
611 case ELF::SHT_GNU_verdef
:
612 return [this](const Elf_Shdr
*S
) { return dumpVerdefSection(S
); };
613 case ELF::SHT_GNU_versym
:
614 return [this](const Elf_Shdr
*S
) { return dumpSymverSection(S
); };
615 case ELF::SHT_GNU_verneed
:
616 return [this](const Elf_Shdr
*S
) { return dumpVerneedSection(S
); };
617 case ELF::SHT_LLVM_ADDRSIG
:
618 return [this](const Elf_Shdr
*S
) { return dumpAddrsigSection(S
); };
619 case ELF::SHT_LLVM_LINKER_OPTIONS
:
620 return [this](const Elf_Shdr
*S
) { return dumpLinkerOptionsSection(S
); };
621 case ELF::SHT_LLVM_DEPENDENT_LIBRARIES
:
622 return [this](const Elf_Shdr
*S
) {
623 return dumpDependentLibrariesSection(S
);
625 case ELF::SHT_LLVM_CALL_GRAPH_PROFILE
:
627 [this](const Elf_Shdr
*S
) { return dumpCallGraphProfileSection(S
); };
628 case ELF::SHT_LLVM_BB_ADDR_MAP
:
629 return [this](const Elf_Shdr
*S
) { return dumpBBAddrMapSection(S
); };
630 case ELF::SHT_STRTAB
:
631 case ELF::SHT_SYMTAB
:
632 case ELF::SHT_DYNSYM
:
633 // The contents of these sections are described by other parts of the YAML
634 // file. But we still want to dump them, because their properties can be
635 // important. See comments for 'shouldPrintSection()' for more details.
636 return [this](const Elf_Shdr
*S
) { return dumpPlaceholderSection(S
); };
642 for (const Elf_Shdr
&Sec
: Sections
) {
643 // We have dedicated dumping functions for most of the section types.
644 // Try to use one of them first.
645 if (std::function
<Expected
<ELFYAML::Chunk
*>(const Elf_Shdr
*)> DumpFn
=
646 GetDumper(Sec
.sh_type
)) {
647 if (Error E
= Add(DumpFn(&Sec
)))
652 // Recognize some special SHT_PROGBITS sections by name.
653 if (Sec
.sh_type
== ELF::SHT_PROGBITS
) {
654 auto NameOrErr
= Obj
.getSectionName(Sec
);
656 return NameOrErr
.takeError();
658 if (ELFYAML::StackSizesSection::nameMatches(*NameOrErr
)) {
659 if (Error E
= Add(dumpStackSizesSection(&Sec
)))
665 if (Error E
= Add(dumpContentSection(&Sec
)))
669 return std::move(Ret
);
672 template <class ELFT
>
673 Error ELFDumper
<ELFT
>::dumpSymbols(
674 const Elf_Shdr
*Symtab
, Optional
<std::vector
<ELFYAML::Symbol
>> &Symbols
) {
676 return Error::success();
678 auto SymtabOrErr
= Obj
.symbols(Symtab
);
680 return SymtabOrErr
.takeError();
682 if (SymtabOrErr
->empty())
683 return Error::success();
685 auto StrTableOrErr
= Obj
.getStringTableForSymtab(*Symtab
);
687 return StrTableOrErr
.takeError();
689 if (Symtab
->sh_type
== ELF::SHT_SYMTAB
) {
690 SymTable
= *SymtabOrErr
;
691 SymbolNames
.resize(SymTable
.size());
695 for (const auto &Sym
: (*SymtabOrErr
).drop_front()) {
697 if (auto EC
= dumpSymbol(&Sym
, Symtab
, *StrTableOrErr
, S
))
699 Symbols
->push_back(S
);
702 return Error::success();
705 template <class ELFT
>
706 Error ELFDumper
<ELFT
>::dumpSymbol(const Elf_Sym
*Sym
, const Elf_Shdr
*SymTab
,
707 StringRef StrTable
, ELFYAML::Symbol
&S
) {
708 S
.Type
= Sym
->getType();
710 S
.Value
= (yaml::Hex64
)Sym
->st_value
;
712 S
.Size
= (yaml::Hex64
)Sym
->st_size
;
713 S
.Other
= Sym
->st_other
;
714 S
.Binding
= Sym
->getBinding();
716 Expected
<StringRef
> SymbolNameOrErr
=
717 getUniquedSymbolName(Sym
, StrTable
, SymTab
);
718 if (!SymbolNameOrErr
)
719 return SymbolNameOrErr
.takeError();
720 S
.Name
= SymbolNameOrErr
.get();
722 if (Sym
->st_shndx
>= ELF::SHN_LORESERVE
) {
723 S
.Index
= (ELFYAML::ELF_SHN
)Sym
->st_shndx
;
724 return Error::success();
727 auto ShdrOrErr
= Obj
.getSection(*Sym
, SymTab
, ShndxTables
.lookup(SymTab
));
729 return ShdrOrErr
.takeError();
730 const Elf_Shdr
*Shdr
= *ShdrOrErr
;
732 return Error::success();
734 auto NameOrErr
= getUniquedSectionName(*Shdr
);
736 return NameOrErr
.takeError();
737 S
.Section
= NameOrErr
.get();
739 return Error::success();
742 template <class ELFT
>
743 template <class RelT
>
744 Error ELFDumper
<ELFT
>::dumpRelocation(const RelT
*Rel
, const Elf_Shdr
*SymTab
,
745 ELFYAML::Relocation
&R
) {
746 R
.Type
= Rel
->getType(Obj
.isMips64EL());
747 R
.Offset
= Rel
->r_offset
;
750 auto SymOrErr
= Obj
.getRelocationSymbol(*Rel
, SymTab
);
752 return SymOrErr
.takeError();
754 // We have might have a relocation with symbol index 0,
755 // e.g. R_X86_64_NONE or R_X86_64_GOTPC32.
756 const Elf_Sym
*Sym
= *SymOrErr
;
758 return Error::success();
760 auto StrTabSec
= Obj
.getSection(SymTab
->sh_link
);
762 return StrTabSec
.takeError();
763 auto StrTabOrErr
= Obj
.getStringTable(**StrTabSec
);
765 return StrTabOrErr
.takeError();
767 Expected
<StringRef
> NameOrErr
=
768 getUniquedSymbolName(Sym
, *StrTabOrErr
, SymTab
);
770 return NameOrErr
.takeError();
771 R
.Symbol
= NameOrErr
.get();
773 return Error::success();
776 template <class ELFT
>
777 Error ELFDumper
<ELFT
>::dumpCommonSection(const Elf_Shdr
*Shdr
,
778 ELFYAML::Section
&S
) {
779 // Dump fields. We do not dump the ShOffset field. When not explicitly
780 // set, the value is set by yaml2obj automatically.
781 S
.Type
= Shdr
->sh_type
;
783 S
.Flags
= static_cast<ELFYAML::ELF_SHF
>(Shdr
->sh_flags
);
785 S
.Address
= static_cast<uint64_t>(Shdr
->sh_addr
);
786 S
.AddressAlign
= Shdr
->sh_addralign
;
788 S
.OriginalSecNdx
= Shdr
- &Sections
[0];
790 Expected
<StringRef
> NameOrErr
= getUniquedSectionName(*Shdr
);
792 return NameOrErr
.takeError();
793 S
.Name
= NameOrErr
.get();
795 if (Shdr
->sh_entsize
!= ELFYAML::getDefaultShEntSize
<ELFT
>(
796 Obj
.getHeader().e_machine
, S
.Type
, S
.Name
))
797 S
.EntSize
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_entsize
);
799 if (Shdr
->sh_link
!= ELF::SHN_UNDEF
) {
800 Expected
<const Elf_Shdr
*> LinkSection
= Obj
.getSection(Shdr
->sh_link
);
802 return make_error
<StringError
>(
803 "unable to resolve sh_link reference in section '" + S
.Name
+
804 "': " + toString(LinkSection
.takeError()),
805 inconvertibleErrorCode());
807 NameOrErr
= getUniquedSectionName(**LinkSection
);
809 return NameOrErr
.takeError();
810 S
.Link
= NameOrErr
.get();
813 return Error::success();
816 template <class ELFT
>
817 Error ELFDumper
<ELFT
>::dumpCommonRelocationSection(
818 const Elf_Shdr
*Shdr
, ELFYAML::RelocationSection
&S
) {
819 if (Error E
= dumpCommonSection(Shdr
, S
))
822 // Having a zero sh_info field is normal: .rela.dyn is a dynamic
823 // relocation section that normally has no value in this field.
825 return Error::success();
827 auto InfoSection
= Obj
.getSection(Shdr
->sh_info
);
829 return InfoSection
.takeError();
831 Expected
<StringRef
> NameOrErr
= getUniquedSectionName(**InfoSection
);
833 return NameOrErr
.takeError();
834 S
.RelocatableSec
= NameOrErr
.get();
836 return Error::success();
839 template <class ELFT
>
840 Expected
<ELFYAML::StackSizesSection
*>
841 ELFDumper
<ELFT
>::dumpStackSizesSection(const Elf_Shdr
*Shdr
) {
842 auto S
= std::make_unique
<ELFYAML::StackSizesSection
>();
843 if (Error E
= dumpCommonSection(Shdr
, *S
))
846 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
848 return ContentOrErr
.takeError();
850 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
851 DataExtractor
Data(Content
, Obj
.isLE(), ELFT::Is64Bits
? 8 : 4);
853 std::vector
<ELFYAML::StackSizeEntry
> Entries
;
854 DataExtractor::Cursor
Cur(0);
855 while (Cur
&& Cur
.tell() < Content
.size()) {
856 uint64_t Address
= Data
.getAddress(Cur
);
857 uint64_t Size
= Data
.getULEB128(Cur
);
858 Entries
.push_back({Address
, Size
});
861 if (Content
.empty() || !Cur
) {
862 // If .stack_sizes cannot be decoded, we dump it as an array of bytes.
863 consumeError(Cur
.takeError());
864 S
->Content
= yaml::BinaryRef(Content
);
866 S
->Entries
= std::move(Entries
);
872 template <class ELFT
>
873 Expected
<ELFYAML::BBAddrMapSection
*>
874 ELFDumper
<ELFT
>::dumpBBAddrMapSection(const Elf_Shdr
*Shdr
) {
875 auto S
= std::make_unique
<ELFYAML::BBAddrMapSection
>();
876 if (Error E
= dumpCommonSection(Shdr
, *S
))
879 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
881 return ContentOrErr
.takeError();
883 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
887 DataExtractor
Data(Content
, Obj
.isLE(), ELFT::Is64Bits
? 8 : 4);
889 std::vector
<ELFYAML::BBAddrMapEntry
> Entries
;
890 DataExtractor::Cursor
Cur(0);
891 while (Cur
&& Cur
.tell() < Content
.size()) {
892 uint64_t Address
= Data
.getAddress(Cur
);
893 uint64_t NumBlocks
= Data
.getULEB128(Cur
);
894 std::vector
<ELFYAML::BBAddrMapEntry::BBEntry
> BBEntries
;
895 // Read the specified number of BB entries, or until decoding fails.
896 for (uint64_t BlockID
= 0; Cur
&& BlockID
< NumBlocks
; ++BlockID
) {
897 uint64_t Offset
= Data
.getULEB128(Cur
);
898 uint64_t Size
= Data
.getULEB128(Cur
);
899 uint64_t Metadata
= Data
.getULEB128(Cur
);
900 BBEntries
.push_back({Offset
, Size
, Metadata
});
902 Entries
.push_back({Address
, /*NumBlocks=*/{}, BBEntries
});
906 // If the section cannot be decoded, we dump it as an array of bytes.
907 consumeError(Cur
.takeError());
908 S
->Content
= yaml::BinaryRef(Content
);
910 S
->Entries
= std::move(Entries
);
916 template <class ELFT
>
917 Expected
<ELFYAML::AddrsigSection
*>
918 ELFDumper
<ELFT
>::dumpAddrsigSection(const Elf_Shdr
*Shdr
) {
919 auto S
= std::make_unique
<ELFYAML::AddrsigSection
>();
920 if (Error E
= dumpCommonSection(Shdr
, *S
))
923 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
925 return ContentOrErr
.takeError();
927 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
928 DataExtractor::Cursor
Cur(0);
929 DataExtractor
Data(Content
, Obj
.isLE(), /*AddressSize=*/0);
930 std::vector
<ELFYAML::YAMLFlowString
> Symbols
;
931 while (Cur
&& Cur
.tell() < Content
.size()) {
932 uint64_t SymNdx
= Data
.getULEB128(Cur
);
936 Expected
<StringRef
> SymbolName
= getSymbolName(Shdr
->sh_link
, SymNdx
);
937 if (!SymbolName
|| SymbolName
->empty()) {
938 consumeError(SymbolName
.takeError());
939 Symbols
.emplace_back(
940 StringRef(std::to_string(SymNdx
)).copy(StringAllocator
));
944 Symbols
.emplace_back(*SymbolName
);
948 S
->Symbols
= std::move(Symbols
);
952 consumeError(Cur
.takeError());
953 S
->Content
= yaml::BinaryRef(Content
);
957 template <class ELFT
>
958 Expected
<ELFYAML::LinkerOptionsSection
*>
959 ELFDumper
<ELFT
>::dumpLinkerOptionsSection(const Elf_Shdr
*Shdr
) {
960 auto S
= std::make_unique
<ELFYAML::LinkerOptionsSection
>();
961 if (Error E
= dumpCommonSection(Shdr
, *S
))
964 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
966 return ContentOrErr
.takeError();
968 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
969 if (Content
.empty() || Content
.back() != 0) {
970 S
->Content
= Content
;
974 SmallVector
<StringRef
, 16> Strings
;
975 toStringRef(Content
.drop_back()).split(Strings
, '\0');
976 if (Strings
.size() % 2 != 0) {
977 S
->Content
= Content
;
981 S
->Options
.emplace();
982 for (size_t I
= 0, E
= Strings
.size(); I
!= E
; I
+= 2)
983 S
->Options
->push_back({Strings
[I
], Strings
[I
+ 1]});
988 template <class ELFT
>
989 Expected
<ELFYAML::DependentLibrariesSection
*>
990 ELFDumper
<ELFT
>::dumpDependentLibrariesSection(const Elf_Shdr
*Shdr
) {
991 auto DL
= std::make_unique
<ELFYAML::DependentLibrariesSection
>();
992 if (Error E
= dumpCommonSection(Shdr
, *DL
))
995 Expected
<ArrayRef
<uint8_t>> ContentOrErr
= Obj
.getSectionContents(*Shdr
);
997 return ContentOrErr
.takeError();
999 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1000 if (!Content
.empty() && Content
.back() != 0) {
1001 DL
->Content
= Content
;
1002 return DL
.release();
1006 for (const uint8_t *I
= Content
.begin(), *E
= Content
.end(); I
< E
;) {
1007 StringRef
Lib((const char *)I
);
1008 DL
->Libs
->emplace_back(Lib
);
1009 I
+= Lib
.size() + 1;
1012 return DL
.release();
1015 template <class ELFT
>
1016 Expected
<ELFYAML::CallGraphProfileSection
*>
1017 ELFDumper
<ELFT
>::dumpCallGraphProfileSection(const Elf_Shdr
*Shdr
) {
1018 auto S
= std::make_unique
<ELFYAML::CallGraphProfileSection
>();
1019 if (Error E
= dumpCommonSection(Shdr
, *S
))
1020 return std::move(E
);
1022 Expected
<ArrayRef
<uint8_t>> ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1024 return ContentOrErr
.takeError();
1025 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1026 const uint32_t SizeOfEntry
= ELFYAML::getDefaultShEntSize
<ELFT
>(
1027 Obj
.getHeader().e_machine
, S
->Type
, S
->Name
);
1028 // Dump the section by using the Content key when it is truncated.
1029 // There is no need to create either "Content" or "Entries" fields when the
1030 // section is empty.
1031 if (Content
.empty() || Content
.size() % SizeOfEntry
!= 0) {
1032 if (!Content
.empty())
1033 S
->Content
= yaml::BinaryRef(Content
);
1037 std::vector
<ELFYAML::CallGraphEntryWeight
> Entries(Content
.size() /
1039 DataExtractor
Data(Content
, Obj
.isLE(), /*AddressSize=*/0);
1040 DataExtractor::Cursor
Cur(0);
1041 auto ReadEntry
= [&](ELFYAML::CallGraphEntryWeight
&E
) {
1042 E
.Weight
= Data
.getU64(Cur
);
1044 consumeError(Cur
.takeError());
1050 for (ELFYAML::CallGraphEntryWeight
&E
: Entries
) {
1053 S
->Content
= yaml::BinaryRef(Content
);
1057 S
->Entries
= std::move(Entries
);
1061 template <class ELFT
>
1062 Expected
<ELFYAML::DynamicSection
*>
1063 ELFDumper
<ELFT
>::dumpDynamicSection(const Elf_Shdr
*Shdr
) {
1064 auto S
= std::make_unique
<ELFYAML::DynamicSection
>();
1065 if (Error E
= dumpCommonSection(Shdr
, *S
))
1066 return std::move(E
);
1068 auto DynTagsOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Dyn
>(*Shdr
);
1070 return DynTagsOrErr
.takeError();
1072 S
->Entries
.emplace();
1073 for (const Elf_Dyn
&Dyn
: *DynTagsOrErr
)
1074 S
->Entries
->push_back({(ELFYAML::ELF_DYNTAG
)Dyn
.getTag(), Dyn
.getVal()});
1079 template <class ELFT
>
1080 Expected
<ELFYAML::RelocationSection
*>
1081 ELFDumper
<ELFT
>::dumpRelocSection(const Elf_Shdr
*Shdr
) {
1082 auto S
= std::make_unique
<ELFYAML::RelocationSection
>();
1083 if (auto E
= dumpCommonRelocationSection(Shdr
, *S
))
1084 return std::move(E
);
1086 auto SymTabOrErr
= Obj
.getSection(Shdr
->sh_link
);
1088 return SymTabOrErr
.takeError();
1090 if (Shdr
->sh_size
!= 0)
1091 S
->Relocations
.emplace();
1093 if (Shdr
->sh_type
== ELF::SHT_REL
) {
1094 auto Rels
= Obj
.rels(*Shdr
);
1096 return Rels
.takeError();
1097 for (const Elf_Rel
&Rel
: *Rels
) {
1098 ELFYAML::Relocation R
;
1099 if (Error E
= dumpRelocation(&Rel
, *SymTabOrErr
, R
))
1100 return std::move(E
);
1101 S
->Relocations
->push_back(R
);
1104 auto Rels
= Obj
.relas(*Shdr
);
1106 return Rels
.takeError();
1107 for (const Elf_Rela
&Rel
: *Rels
) {
1108 ELFYAML::Relocation R
;
1109 if (Error E
= dumpRelocation(&Rel
, *SymTabOrErr
, R
))
1110 return std::move(E
);
1111 R
.Addend
= Rel
.r_addend
;
1112 S
->Relocations
->push_back(R
);
1119 template <class ELFT
>
1120 Expected
<ELFYAML::RelrSection
*>
1121 ELFDumper
<ELFT
>::dumpRelrSection(const Elf_Shdr
*Shdr
) {
1122 auto S
= std::make_unique
<ELFYAML::RelrSection
>();
1123 if (auto E
= dumpCommonSection(Shdr
, *S
))
1124 return std::move(E
);
1126 if (Expected
<ArrayRef
<Elf_Relr
>> Relrs
= Obj
.relrs(*Shdr
)) {
1127 S
->Entries
.emplace();
1128 for (Elf_Relr Rel
: *Relrs
)
1129 S
->Entries
->emplace_back(Rel
);
1132 // Ignore. We are going to dump the data as raw content below.
1133 consumeError(Relrs
.takeError());
1136 Expected
<ArrayRef
<uint8_t>> ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1138 return ContentOrErr
.takeError();
1139 S
->Content
= *ContentOrErr
;
1143 template <class ELFT
>
1144 Expected
<ELFYAML::RawContentSection
*>
1145 ELFDumper
<ELFT
>::dumpContentSection(const Elf_Shdr
*Shdr
) {
1146 auto S
= std::make_unique
<ELFYAML::RawContentSection
>();
1147 if (Error E
= dumpCommonSection(Shdr
, *S
))
1148 return std::move(E
);
1150 unsigned SecIndex
= Shdr
- &Sections
[0];
1151 if (SecIndex
!= 0 || Shdr
->sh_type
!= ELF::SHT_NULL
) {
1152 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1154 return ContentOrErr
.takeError();
1155 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1156 if (!Content
.empty())
1157 S
->Content
= yaml::BinaryRef(Content
);
1159 S
->Size
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_size
);
1163 S
->Info
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_info
);
1167 template <class ELFT
>
1168 Expected
<ELFYAML::SymtabShndxSection
*>
1169 ELFDumper
<ELFT
>::dumpSymtabShndxSection(const Elf_Shdr
*Shdr
) {
1170 auto S
= std::make_unique
<ELFYAML::SymtabShndxSection
>();
1171 if (Error E
= dumpCommonSection(Shdr
, *S
))
1172 return std::move(E
);
1174 auto EntriesOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Word
>(*Shdr
);
1176 return EntriesOrErr
.takeError();
1178 S
->Entries
.emplace();
1179 for (const Elf_Word
&E
: *EntriesOrErr
)
1180 S
->Entries
->push_back(E
);
1184 template <class ELFT
>
1185 Expected
<ELFYAML::NoBitsSection
*>
1186 ELFDumper
<ELFT
>::dumpNoBitsSection(const Elf_Shdr
*Shdr
) {
1187 auto S
= std::make_unique
<ELFYAML::NoBitsSection
>();
1188 if (Error E
= dumpCommonSection(Shdr
, *S
))
1189 return std::move(E
);
1191 S
->Size
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_size
);
1195 template <class ELFT
>
1196 Expected
<ELFYAML::NoteSection
*>
1197 ELFDumper
<ELFT
>::dumpNoteSection(const Elf_Shdr
*Shdr
) {
1198 auto S
= std::make_unique
<ELFYAML::NoteSection
>();
1199 if (Error E
= dumpCommonSection(Shdr
, *S
))
1200 return std::move(E
);
1202 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1204 return ContentOrErr
.takeError();
1206 std::vector
<ELFYAML::NoteEntry
> Entries
;
1207 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1208 while (!Content
.empty()) {
1209 if (Content
.size() < sizeof(Elf_Nhdr
)) {
1210 S
->Content
= yaml::BinaryRef(*ContentOrErr
);
1214 const Elf_Nhdr
*Header
= reinterpret_cast<const Elf_Nhdr
*>(Content
.data());
1215 if (Content
.size() < Header
->getSize()) {
1216 S
->Content
= yaml::BinaryRef(*ContentOrErr
);
1220 Elf_Note
Note(*Header
);
1222 {Note
.getName(), Note
.getDesc(), (ELFYAML::ELF_NT
)Note
.getType()});
1224 Content
= Content
.drop_front(Header
->getSize());
1227 S
->Notes
= std::move(Entries
);
1231 template <class ELFT
>
1232 Expected
<ELFYAML::HashSection
*>
1233 ELFDumper
<ELFT
>::dumpHashSection(const Elf_Shdr
*Shdr
) {
1234 auto S
= std::make_unique
<ELFYAML::HashSection
>();
1235 if (Error E
= dumpCommonSection(Shdr
, *S
))
1236 return std::move(E
);
1238 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1240 return ContentOrErr
.takeError();
1242 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1243 if (Content
.size() % 4 != 0 || Content
.size() < 8) {
1244 S
->Content
= yaml::BinaryRef(Content
);
1248 DataExtractor::Cursor
Cur(0);
1249 DataExtractor
Data(Content
, Obj
.isLE(), /*AddressSize=*/0);
1250 uint64_t NBucket
= Data
.getU32(Cur
);
1251 uint64_t NChain
= Data
.getU32(Cur
);
1252 if (Content
.size() != (2 + NBucket
+ NChain
) * 4) {
1253 S
->Content
= yaml::BinaryRef(Content
);
1256 llvm_unreachable("entries were not read correctly");
1259 S
->Bucket
.emplace(NBucket
);
1260 for (uint32_t &V
: *S
->Bucket
)
1261 V
= Data
.getU32(Cur
);
1263 S
->Chain
.emplace(NChain
);
1264 for (uint32_t &V
: *S
->Chain
)
1265 V
= Data
.getU32(Cur
);
1269 llvm_unreachable("entries were not read correctly");
1272 template <class ELFT
>
1273 Expected
<ELFYAML::GnuHashSection
*>
1274 ELFDumper
<ELFT
>::dumpGnuHashSection(const Elf_Shdr
*Shdr
) {
1275 auto S
= std::make_unique
<ELFYAML::GnuHashSection
>();
1276 if (Error E
= dumpCommonSection(Shdr
, *S
))
1277 return std::move(E
);
1279 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1281 return ContentOrErr
.takeError();
1283 unsigned AddrSize
= ELFT::Is64Bits
? 8 : 4;
1284 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1285 DataExtractor
Data(Content
, Obj
.isLE(), AddrSize
);
1287 ELFYAML::GnuHashHeader Header
;
1288 DataExtractor::Cursor
Cur(0);
1289 uint64_t NBuckets
= Data
.getU32(Cur
);
1290 Header
.SymNdx
= Data
.getU32(Cur
);
1291 uint64_t MaskWords
= Data
.getU32(Cur
);
1292 Header
.Shift2
= Data
.getU32(Cur
);
1294 // Set just the raw binary content if we were unable to read the header
1295 // or when the section data is truncated or malformed.
1296 uint64_t Size
= Data
.getData().size() - Cur
.tell();
1297 if (!Cur
|| (Size
< MaskWords
* AddrSize
+ NBuckets
* 4) ||
1299 consumeError(Cur
.takeError());
1300 S
->Content
= yaml::BinaryRef(Content
);
1306 S
->BloomFilter
.emplace(MaskWords
);
1307 for (llvm::yaml::Hex64
&Val
: *S
->BloomFilter
)
1308 Val
= Data
.getAddress(Cur
);
1310 S
->HashBuckets
.emplace(NBuckets
);
1311 for (llvm::yaml::Hex32
&Val
: *S
->HashBuckets
)
1312 Val
= Data
.getU32(Cur
);
1314 S
->HashValues
.emplace((Data
.getData().size() - Cur
.tell()) / 4);
1315 for (llvm::yaml::Hex32
&Val
: *S
->HashValues
)
1316 Val
= Data
.getU32(Cur
);
1320 llvm_unreachable("GnuHashSection was not read correctly");
1323 template <class ELFT
>
1324 Expected
<ELFYAML::VerdefSection
*>
1325 ELFDumper
<ELFT
>::dumpVerdefSection(const Elf_Shdr
*Shdr
) {
1326 auto S
= std::make_unique
<ELFYAML::VerdefSection
>();
1327 if (Error E
= dumpCommonSection(Shdr
, *S
))
1328 return std::move(E
);
1330 auto StringTableShdrOrErr
= Obj
.getSection(Shdr
->sh_link
);
1331 if (!StringTableShdrOrErr
)
1332 return StringTableShdrOrErr
.takeError();
1334 auto StringTableOrErr
= Obj
.getStringTable(**StringTableShdrOrErr
);
1335 if (!StringTableOrErr
)
1336 return StringTableOrErr
.takeError();
1338 auto Contents
= Obj
.getSectionContents(*Shdr
);
1340 return Contents
.takeError();
1342 S
->Entries
.emplace();
1344 llvm::ArrayRef
<uint8_t> Data
= *Contents
;
1345 const uint8_t *Buf
= Data
.data();
1347 const Elf_Verdef
*Verdef
= reinterpret_cast<const Elf_Verdef
*>(Buf
);
1348 ELFYAML::VerdefEntry Entry
;
1349 if (Verdef
->vd_version
!= 1)
1350 return createStringError(errc::invalid_argument
,
1351 "invalid SHT_GNU_verdef section version: " +
1352 Twine(Verdef
->vd_version
));
1354 if (Verdef
->vd_flags
!= 0)
1355 Entry
.Flags
= Verdef
->vd_flags
;
1357 if (Verdef
->vd_ndx
!= 0)
1358 Entry
.VersionNdx
= Verdef
->vd_ndx
;
1360 if (Verdef
->vd_hash
!= 0)
1361 Entry
.Hash
= Verdef
->vd_hash
;
1363 const uint8_t *BufAux
= Buf
+ Verdef
->vd_aux
;
1365 const Elf_Verdaux
*Verdaux
=
1366 reinterpret_cast<const Elf_Verdaux
*>(BufAux
);
1367 Entry
.VerNames
.push_back(
1368 StringTableOrErr
->drop_front(Verdaux
->vda_name
).data());
1369 BufAux
= Verdaux
->vda_next
? BufAux
+ Verdaux
->vda_next
: nullptr;
1372 S
->Entries
->push_back(Entry
);
1373 Buf
= Verdef
->vd_next
? Buf
+ Verdef
->vd_next
: nullptr;
1376 if (Shdr
->sh_info
!= S
->Entries
->size())
1377 S
->Info
= (llvm::yaml::Hex64
)Shdr
->sh_info
;
1382 template <class ELFT
>
1383 Expected
<ELFYAML::SymverSection
*>
1384 ELFDumper
<ELFT
>::dumpSymverSection(const Elf_Shdr
*Shdr
) {
1385 auto S
= std::make_unique
<ELFYAML::SymverSection
>();
1386 if (Error E
= dumpCommonSection(Shdr
, *S
))
1387 return std::move(E
);
1389 auto VersionsOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Half
>(*Shdr
);
1391 return VersionsOrErr
.takeError();
1393 S
->Entries
.emplace();
1394 for (const Elf_Half
&E
: *VersionsOrErr
)
1395 S
->Entries
->push_back(E
);
1400 template <class ELFT
>
1401 Expected
<ELFYAML::VerneedSection
*>
1402 ELFDumper
<ELFT
>::dumpVerneedSection(const Elf_Shdr
*Shdr
) {
1403 auto S
= std::make_unique
<ELFYAML::VerneedSection
>();
1404 if (Error E
= dumpCommonSection(Shdr
, *S
))
1405 return std::move(E
);
1407 auto Contents
= Obj
.getSectionContents(*Shdr
);
1409 return Contents
.takeError();
1411 auto StringTableShdrOrErr
= Obj
.getSection(Shdr
->sh_link
);
1412 if (!StringTableShdrOrErr
)
1413 return StringTableShdrOrErr
.takeError();
1415 auto StringTableOrErr
= Obj
.getStringTable(**StringTableShdrOrErr
);
1416 if (!StringTableOrErr
)
1417 return StringTableOrErr
.takeError();
1419 S
->VerneedV
.emplace();
1421 llvm::ArrayRef
<uint8_t> Data
= *Contents
;
1422 const uint8_t *Buf
= Data
.data();
1424 const Elf_Verneed
*Verneed
= reinterpret_cast<const Elf_Verneed
*>(Buf
);
1426 ELFYAML::VerneedEntry Entry
;
1427 Entry
.Version
= Verneed
->vn_version
;
1429 StringRef(StringTableOrErr
->drop_front(Verneed
->vn_file
).data());
1431 const uint8_t *BufAux
= Buf
+ Verneed
->vn_aux
;
1433 const Elf_Vernaux
*Vernaux
=
1434 reinterpret_cast<const Elf_Vernaux
*>(BufAux
);
1436 ELFYAML::VernauxEntry Aux
;
1437 Aux
.Hash
= Vernaux
->vna_hash
;
1438 Aux
.Flags
= Vernaux
->vna_flags
;
1439 Aux
.Other
= Vernaux
->vna_other
;
1441 StringRef(StringTableOrErr
->drop_front(Vernaux
->vna_name
).data());
1443 Entry
.AuxV
.push_back(Aux
);
1444 BufAux
= Vernaux
->vna_next
? BufAux
+ Vernaux
->vna_next
: nullptr;
1447 S
->VerneedV
->push_back(Entry
);
1448 Buf
= Verneed
->vn_next
? Buf
+ Verneed
->vn_next
: nullptr;
1451 if (Shdr
->sh_info
!= S
->VerneedV
->size())
1452 S
->Info
= (llvm::yaml::Hex64
)Shdr
->sh_info
;
1457 template <class ELFT
>
1458 Expected
<StringRef
> ELFDumper
<ELFT
>::getSymbolName(uint32_t SymtabNdx
,
1459 uint32_t SymbolNdx
) {
1460 auto SymtabOrErr
= Obj
.getSection(SymtabNdx
);
1462 return SymtabOrErr
.takeError();
1464 const Elf_Shdr
*Symtab
= *SymtabOrErr
;
1465 auto SymOrErr
= Obj
.getSymbol(Symtab
, SymbolNdx
);
1467 return SymOrErr
.takeError();
1469 auto StrTabOrErr
= Obj
.getStringTableForSymtab(*Symtab
);
1471 return StrTabOrErr
.takeError();
1472 return getUniquedSymbolName(*SymOrErr
, *StrTabOrErr
, Symtab
);
1475 template <class ELFT
>
1476 Expected
<ELFYAML::GroupSection
*>
1477 ELFDumper
<ELFT
>::dumpGroupSection(const Elf_Shdr
*Shdr
) {
1478 auto S
= std::make_unique
<ELFYAML::GroupSection
>();
1479 if (Error E
= dumpCommonSection(Shdr
, *S
))
1480 return std::move(E
);
1482 // Get symbol with index sh_info. This symbol's name is the signature of the group.
1483 Expected
<StringRef
> SymbolName
= getSymbolName(Shdr
->sh_link
, Shdr
->sh_info
);
1485 return SymbolName
.takeError();
1486 S
->Signature
= *SymbolName
;
1488 auto MembersOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Word
>(*Shdr
);
1490 return MembersOrErr
.takeError();
1492 S
->Members
.emplace();
1493 for (Elf_Word Member
: *MembersOrErr
) {
1494 if (Member
== llvm::ELF::GRP_COMDAT
) {
1495 S
->Members
->push_back({"GRP_COMDAT"});
1499 Expected
<const Elf_Shdr
*> SHdrOrErr
= Obj
.getSection(Member
);
1501 return SHdrOrErr
.takeError();
1502 Expected
<StringRef
> NameOrErr
= getUniquedSectionName(**SHdrOrErr
);
1504 return NameOrErr
.takeError();
1505 S
->Members
->push_back({*NameOrErr
});
1510 template <class ELFT
>
1511 Expected
<ELFYAML::ARMIndexTableSection
*>
1512 ELFDumper
<ELFT
>::dumpARMIndexTableSection(const Elf_Shdr
*Shdr
) {
1513 auto S
= std::make_unique
<ELFYAML::ARMIndexTableSection
>();
1514 if (Error E
= dumpCommonSection(Shdr
, *S
))
1515 return std::move(E
);
1517 Expected
<ArrayRef
<uint8_t>> ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1519 return ContentOrErr
.takeError();
1521 if (ContentOrErr
->size() % (sizeof(Elf_Word
) * 2) != 0) {
1522 S
->Content
= yaml::BinaryRef(*ContentOrErr
);
1526 ArrayRef
<Elf_Word
> Words(
1527 reinterpret_cast<const Elf_Word
*>(ContentOrErr
->data()),
1528 ContentOrErr
->size() / sizeof(Elf_Word
));
1530 S
->Entries
.emplace();
1531 for (size_t I
= 0, E
= Words
.size(); I
!= E
; I
+= 2)
1532 S
->Entries
->push_back({(yaml::Hex32
)Words
[I
], (yaml::Hex32
)Words
[I
+ 1]});
1537 template <class ELFT
>
1538 Expected
<ELFYAML::MipsABIFlags
*>
1539 ELFDumper
<ELFT
>::dumpMipsABIFlags(const Elf_Shdr
*Shdr
) {
1540 assert(Shdr
->sh_type
== ELF::SHT_MIPS_ABIFLAGS
&&
1541 "Section type is not SHT_MIPS_ABIFLAGS");
1542 auto S
= std::make_unique
<ELFYAML::MipsABIFlags
>();
1543 if (Error E
= dumpCommonSection(Shdr
, *S
))
1544 return std::move(E
);
1546 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1548 return ContentOrErr
.takeError();
1550 auto *Flags
= reinterpret_cast<const object::Elf_Mips_ABIFlags
<ELFT
> *>(
1551 ContentOrErr
.get().data());
1552 S
->Version
= Flags
->version
;
1553 S
->ISALevel
= Flags
->isa_level
;
1554 S
->ISARevision
= Flags
->isa_rev
;
1555 S
->GPRSize
= Flags
->gpr_size
;
1556 S
->CPR1Size
= Flags
->cpr1_size
;
1557 S
->CPR2Size
= Flags
->cpr2_size
;
1558 S
->FpABI
= Flags
->fp_abi
;
1559 S
->ISAExtension
= Flags
->isa_ext
;
1560 S
->ASEs
= Flags
->ases
;
1561 S
->Flags1
= Flags
->flags1
;
1562 S
->Flags2
= Flags
->flags2
;
1566 template <class ELFT
>
1567 static Error
elf2yaml(raw_ostream
&Out
, const object::ELFFile
<ELFT
> &Obj
,
1568 std::unique_ptr
<DWARFContext
> DWARFCtx
) {
1569 ELFDumper
<ELFT
> Dumper(Obj
, std::move(DWARFCtx
));
1570 Expected
<ELFYAML::Object
*> YAMLOrErr
= Dumper
.dump();
1572 return YAMLOrErr
.takeError();
1574 std::unique_ptr
<ELFYAML::Object
> YAML(YAMLOrErr
.get());
1575 yaml::Output
Yout(Out
);
1578 return Error::success();
1581 Error
elf2yaml(raw_ostream
&Out
, const object::ObjectFile
&Obj
) {
1582 std::unique_ptr
<DWARFContext
> DWARFCtx
= DWARFContext::create(Obj
);
1583 if (const auto *ELFObj
= dyn_cast
<object::ELF32LEObjectFile
>(&Obj
))
1584 return elf2yaml(Out
, ELFObj
->getELFFile(), std::move(DWARFCtx
));
1586 if (const auto *ELFObj
= dyn_cast
<object::ELF32BEObjectFile
>(&Obj
))
1587 return elf2yaml(Out
, ELFObj
->getELFFile(), std::move(DWARFCtx
));
1589 if (const auto *ELFObj
= dyn_cast
<object::ELF64LEObjectFile
>(&Obj
))
1590 return elf2yaml(Out
, ELFObj
->getELFFile(), std::move(DWARFCtx
));
1592 if (const auto *ELFObj
= dyn_cast
<object::ELF64BEObjectFile
>(&Obj
))
1593 return elf2yaml(Out
, ELFObj
->getELFFile(), std::move(DWARFCtx
));
1595 llvm_unreachable("unknown ELF file format");