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/Errc.h"
19 #include "llvm/Support/ErrorHandling.h"
20 #include "llvm/Support/YAMLTraits.h"
29 LLVM_ELF_IMPORT_TYPES_ELFT(ELFT
)
31 ArrayRef
<Elf_Shdr
> Sections
;
32 ArrayRef
<Elf_Sym
> SymTable
;
34 DenseMap
<StringRef
, uint32_t> UsedSectionNames
;
35 std::vector
<std::string
> SectionNames
;
36 std::optional
<uint32_t> ShStrTabIndex
;
38 DenseMap
<StringRef
, uint32_t> UsedSymbolNames
;
39 std::vector
<std::string
> SymbolNames
;
41 BumpPtrAllocator StringAllocator
;
43 Expected
<StringRef
> getUniquedSectionName(const Elf_Shdr
&Sec
);
44 Expected
<StringRef
> getUniquedSymbolName(const Elf_Sym
*Sym
,
46 const Elf_Shdr
*SymTab
);
47 Expected
<StringRef
> getSymbolName(uint32_t SymtabNdx
, uint32_t SymbolNdx
);
49 const object::ELFFile
<ELFT
> &Obj
;
50 std::unique_ptr
<DWARFContext
> DWARFCtx
;
52 DenseMap
<const Elf_Shdr
*, ArrayRef
<Elf_Word
>> ShndxTables
;
54 Expected
<std::vector
<ELFYAML::ProgramHeader
>>
55 dumpProgramHeaders(ArrayRef
<std::unique_ptr
<ELFYAML::Chunk
>> Sections
);
57 std::optional
<DWARFYAML::Data
>
58 dumpDWARFSections(std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> &Sections
);
60 Error
dumpSymbols(const Elf_Shdr
*Symtab
,
61 std::optional
<std::vector
<ELFYAML::Symbol
>> &Symbols
);
62 Error
dumpSymbol(const Elf_Sym
*Sym
, const Elf_Shdr
*SymTab
,
63 StringRef StrTable
, ELFYAML::Symbol
&S
);
64 Expected
<std::vector
<std::unique_ptr
<ELFYAML::Chunk
>>> dumpSections();
65 Error
dumpCommonSection(const Elf_Shdr
*Shdr
, ELFYAML::Section
&S
);
66 Error
dumpCommonRelocationSection(const Elf_Shdr
*Shdr
,
67 ELFYAML::RelocationSection
&S
);
69 Error
dumpRelocation(const RelT
*Rel
, const Elf_Shdr
*SymTab
,
70 ELFYAML::Relocation
&R
);
72 Expected
<ELFYAML::AddrsigSection
*> dumpAddrsigSection(const Elf_Shdr
*Shdr
);
73 Expected
<ELFYAML::LinkerOptionsSection
*>
74 dumpLinkerOptionsSection(const Elf_Shdr
*Shdr
);
75 Expected
<ELFYAML::DependentLibrariesSection
*>
76 dumpDependentLibrariesSection(const Elf_Shdr
*Shdr
);
77 Expected
<ELFYAML::CallGraphProfileSection
*>
78 dumpCallGraphProfileSection(const Elf_Shdr
*Shdr
);
79 Expected
<ELFYAML::DynamicSection
*> dumpDynamicSection(const Elf_Shdr
*Shdr
);
80 Expected
<ELFYAML::RelocationSection
*> dumpRelocSection(const Elf_Shdr
*Shdr
);
81 Expected
<ELFYAML::RelrSection
*> dumpRelrSection(const Elf_Shdr
*Shdr
);
82 Expected
<ELFYAML::RawContentSection
*>
83 dumpContentSection(const Elf_Shdr
*Shdr
);
84 Expected
<ELFYAML::SymtabShndxSection
*>
85 dumpSymtabShndxSection(const Elf_Shdr
*Shdr
);
86 Expected
<ELFYAML::NoBitsSection
*> dumpNoBitsSection(const Elf_Shdr
*Shdr
);
87 Expected
<ELFYAML::HashSection
*> dumpHashSection(const Elf_Shdr
*Shdr
);
88 Expected
<ELFYAML::NoteSection
*> dumpNoteSection(const Elf_Shdr
*Shdr
);
89 Expected
<ELFYAML::GnuHashSection
*> dumpGnuHashSection(const Elf_Shdr
*Shdr
);
90 Expected
<ELFYAML::VerdefSection
*> dumpVerdefSection(const Elf_Shdr
*Shdr
);
91 Expected
<ELFYAML::SymverSection
*> dumpSymverSection(const Elf_Shdr
*Shdr
);
92 Expected
<ELFYAML::VerneedSection
*> dumpVerneedSection(const Elf_Shdr
*Shdr
);
93 Expected
<ELFYAML::GroupSection
*> dumpGroupSection(const Elf_Shdr
*Shdr
);
94 Expected
<ELFYAML::ARMIndexTableSection
*>
95 dumpARMIndexTableSection(const Elf_Shdr
*Shdr
);
96 Expected
<ELFYAML::MipsABIFlags
*> dumpMipsABIFlags(const Elf_Shdr
*Shdr
);
97 Expected
<ELFYAML::StackSizesSection
*>
98 dumpStackSizesSection(const Elf_Shdr
*Shdr
);
99 Expected
<ELFYAML::BBAddrMapSection
*>
100 dumpBBAddrMapSection(const Elf_Shdr
*Shdr
);
101 Expected
<ELFYAML::RawContentSection
*>
102 dumpPlaceholderSection(const Elf_Shdr
*Shdr
);
104 bool shouldPrintSection(const ELFYAML::Section
&S
, const Elf_Shdr
&SHdr
,
105 std::optional
<DWARFYAML::Data
> DWARF
);
108 ELFDumper(const object::ELFFile
<ELFT
> &O
, std::unique_ptr
<DWARFContext
> DCtx
);
109 Expected
<ELFYAML::Object
*> dump();
114 template <class ELFT
>
115 ELFDumper
<ELFT
>::ELFDumper(const object::ELFFile
<ELFT
> &O
,
116 std::unique_ptr
<DWARFContext
> DCtx
)
117 : Obj(O
), DWARFCtx(std::move(DCtx
)) {}
119 template <class ELFT
>
121 ELFDumper
<ELFT
>::getUniquedSectionName(const Elf_Shdr
&Sec
) {
122 unsigned SecIndex
= &Sec
- &Sections
[0];
123 if (!SectionNames
[SecIndex
].empty())
124 return SectionNames
[SecIndex
];
126 auto NameOrErr
= Obj
.getSectionName(Sec
);
129 StringRef Name
= *NameOrErr
;
130 // In some specific cases we might have more than one section without a
131 // name (sh_name == 0). It normally doesn't happen, but when we have this case
132 // it doesn't make sense to uniquify their names and add noise to the output.
136 std::string
&Ret
= SectionNames
[SecIndex
];
138 auto It
= UsedSectionNames
.insert({Name
, 0});
140 Ret
= ELFYAML::appendUniqueSuffix(Name
, Twine(++It
.first
->second
));
142 Ret
= std::string(Name
);
146 template <class ELFT
>
148 ELFDumper
<ELFT
>::getUniquedSymbolName(const Elf_Sym
*Sym
, StringRef StrTable
,
149 const Elf_Shdr
*SymTab
) {
150 Expected
<StringRef
> SymbolNameOrErr
= Sym
->getName(StrTable
);
151 if (!SymbolNameOrErr
)
152 return SymbolNameOrErr
;
153 StringRef Name
= *SymbolNameOrErr
;
154 if (Name
.empty() && Sym
->getType() == ELF::STT_SECTION
) {
155 Expected
<const Elf_Shdr
*> ShdrOrErr
=
156 Obj
.getSection(*Sym
, SymTab
, ShndxTables
.lookup(SymTab
));
158 return ShdrOrErr
.takeError();
159 // The null section has no name.
160 return (*ShdrOrErr
== nullptr) ? "" : getUniquedSectionName(**ShdrOrErr
);
163 // Symbols in .symtab can have duplicate names. For example, it is a common
164 // situation for local symbols in a relocatable object. Here we assign unique
165 // suffixes for such symbols so that we can differentiate them.
166 if (SymTab
->sh_type
== ELF::SHT_SYMTAB
) {
167 unsigned Index
= Sym
- SymTable
.data();
168 if (!SymbolNames
[Index
].empty())
169 return SymbolNames
[Index
];
171 auto It
= UsedSymbolNames
.insert({Name
, 0});
174 ELFYAML::appendUniqueSuffix(Name
, Twine(++It
.first
->second
));
176 SymbolNames
[Index
] = std::string(Name
);
177 return SymbolNames
[Index
];
183 template <class ELFT
>
184 bool ELFDumper
<ELFT
>::shouldPrintSection(const ELFYAML::Section
&S
,
185 const Elf_Shdr
&SHdr
,
186 std::optional
<DWARFYAML::Data
> DWARF
) {
187 // We only print the SHT_NULL section at index 0 when it
188 // has at least one non-null field, because yaml2obj
189 // normally creates the zero section at index 0 implicitly.
190 if (S
.Type
== ELF::SHT_NULL
&& (&SHdr
== &Sections
[0])) {
191 const uint8_t *Begin
= reinterpret_cast<const uint8_t *>(&SHdr
);
192 const uint8_t *End
= Begin
+ sizeof(Elf_Shdr
);
193 return std::any_of(Begin
, End
, [](uint8_t V
) { return V
!= 0; });
196 // Normally we use "DWARF:" to describe contents of DWARF sections. Sometimes
197 // the content of DWARF sections can be successfully parsed into the "DWARF:"
198 // entry but their section headers may have special flags, entry size, address
199 // alignment, etc. We will preserve the header for them under such
201 StringRef SecName
= S
.Name
.substr(1);
202 if (DWARF
&& DWARF
->getNonEmptySectionNames().count(SecName
)) {
203 if (const ELFYAML::RawContentSection
*RawSec
=
204 dyn_cast
<const ELFYAML::RawContentSection
>(&S
)) {
205 if (RawSec
->Type
!= ELF::SHT_PROGBITS
|| RawSec
->Link
|| RawSec
->Info
||
206 RawSec
->AddressAlign
!= yaml::Hex64
{1} || RawSec
->Address
||
210 ELFYAML::ELF_SHF ShFlags
= RawSec
->Flags
.value_or(ELFYAML::ELF_SHF(0));
212 if (SecName
== "debug_str")
213 return ShFlags
!= ELFYAML::ELF_SHF(ELF::SHF_MERGE
| ELF::SHF_STRINGS
);
215 return ShFlags
!= ELFYAML::ELF_SHF
{0};
219 // Normally we use "Symbols:" and "DynamicSymbols:" to describe contents of
220 // symbol tables. We also build and emit corresponding string tables
221 // implicitly. But sometimes it is important to preserve positions and virtual
222 // addresses of allocatable sections, e.g. for creating program headers.
223 // Generally we are trying to reduce noise in the YAML output. Because
224 // of that we do not print non-allocatable versions of such sections and
225 // assume they are placed at the end.
226 // We also dump symbol tables when the Size field is set. It happens when they
227 // are empty, which should not normally happen.
228 if (S
.Type
== ELF::SHT_STRTAB
|| S
.Type
== ELF::SHT_SYMTAB
||
229 S
.Type
== ELF::SHT_DYNSYM
) {
230 return S
.Size
|| S
.Flags
.value_or(ELFYAML::ELF_SHF(0)) & ELF::SHF_ALLOC
;
236 template <class ELFT
>
237 static void dumpSectionOffsets(const typename
ELFT::Ehdr
&Header
,
238 ArrayRef
<ELFYAML::ProgramHeader
> Phdrs
,
239 std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> &V
,
240 ArrayRef
<typename
ELFT::Shdr
> S
) {
244 uint64_t ExpectedOffset
;
245 if (Header
.e_phoff
> 0)
246 ExpectedOffset
= Header
.e_phoff
+ Header
.e_phentsize
* Header
.e_phnum
;
248 ExpectedOffset
= sizeof(typename
ELFT::Ehdr
);
250 for (const std::unique_ptr
<ELFYAML::Chunk
> &C
: ArrayRef(V
).drop_front()) {
251 ELFYAML::Section
&Sec
= *cast
<ELFYAML::Section
>(C
.get());
252 const typename
ELFT::Shdr
&SecHdr
= S
[Sec
.OriginalSecNdx
];
254 ExpectedOffset
= alignTo(ExpectedOffset
,
255 SecHdr
.sh_addralign
? SecHdr
.sh_addralign
: 1uLL);
257 // We only set the "Offset" field when it can't be naturally derived
258 // from the offset and size of the previous section. This reduces
259 // the noise in the YAML output.
260 if (SecHdr
.sh_offset
!= ExpectedOffset
)
261 Sec
.Offset
= (yaml::Hex64
)SecHdr
.sh_offset
;
263 if (Sec
.Type
== ELF::SHT_NOBITS
&&
264 !ELFYAML::shouldAllocateFileSpace(Phdrs
,
265 *cast
<ELFYAML::NoBitsSection
>(&Sec
)))
266 ExpectedOffset
= SecHdr
.sh_offset
;
268 ExpectedOffset
= SecHdr
.sh_offset
+ SecHdr
.sh_size
;
272 template <class ELFT
> Expected
<ELFYAML::Object
*> ELFDumper
<ELFT
>::dump() {
273 auto Y
= std::make_unique
<ELFYAML::Object
>();
275 // Dump header. We do not dump EPh* and ESh* fields. When not explicitly set,
276 // the values are set by yaml2obj automatically and there is no need to dump
278 Y
->Header
.Class
= ELFYAML::ELF_ELFCLASS(Obj
.getHeader().getFileClass());
279 Y
->Header
.Data
= ELFYAML::ELF_ELFDATA(Obj
.getHeader().getDataEncoding());
280 Y
->Header
.OSABI
= Obj
.getHeader().e_ident
[ELF::EI_OSABI
];
281 Y
->Header
.ABIVersion
= Obj
.getHeader().e_ident
[ELF::EI_ABIVERSION
];
282 Y
->Header
.Type
= Obj
.getHeader().e_type
;
283 if (Obj
.getHeader().e_machine
!= 0)
284 Y
->Header
.Machine
= ELFYAML::ELF_EM(Obj
.getHeader().e_machine
);
285 Y
->Header
.Flags
= Obj
.getHeader().e_flags
;
286 Y
->Header
.Entry
= Obj
.getHeader().e_entry
;
289 auto SectionsOrErr
= Obj
.sections();
291 return SectionsOrErr
.takeError();
292 Sections
= *SectionsOrErr
;
293 SectionNames
.resize(Sections
.size());
295 if (Sections
.size() > 0) {
296 ShStrTabIndex
= Obj
.getHeader().e_shstrndx
;
297 if (*ShStrTabIndex
== ELF::SHN_XINDEX
)
298 ShStrTabIndex
= Sections
[0].sh_link
;
299 // TODO: Set EShStrndx if the value doesn't represent a real section.
302 // Normally an object that does not have sections has e_shnum == 0.
303 // Also, e_shnum might be 0, when the the number of entries in the section
304 // header table is larger than or equal to SHN_LORESERVE (0xff00). In this
305 // case the real number of entries is held in the sh_size member of the
306 // initial entry. We have a section header table when `e_shoff` is not 0.
307 if (Obj
.getHeader().e_shoff
!= 0 && Obj
.getHeader().e_shnum
== 0)
308 Y
->Header
.EShNum
= 0;
310 // Dump symbols. We need to do this early because other sections might want
311 // to access the deduplicated symbol names that we also create here.
312 const Elf_Shdr
*SymTab
= nullptr;
313 const Elf_Shdr
*DynSymTab
= nullptr;
315 for (const Elf_Shdr
&Sec
: Sections
) {
316 if (Sec
.sh_type
== ELF::SHT_SYMTAB
) {
318 } else if (Sec
.sh_type
== ELF::SHT_DYNSYM
) {
320 } else if (Sec
.sh_type
== ELF::SHT_SYMTAB_SHNDX
) {
321 // We need to locate SHT_SYMTAB_SHNDX sections early, because they
322 // might be needed for dumping symbols.
323 if (Expected
<ArrayRef
<Elf_Word
>> TableOrErr
= Obj
.getSHNDXTable(Sec
)) {
324 // The `getSHNDXTable` calls the `getSection` internally when validates
325 // the symbol table section linked to the SHT_SYMTAB_SHNDX section.
326 const Elf_Shdr
*LinkedSymTab
= cantFail(Obj
.getSection(Sec
.sh_link
));
327 if (!ShndxTables
.insert({LinkedSymTab
, *TableOrErr
}).second
)
328 return createStringError(
329 errc::invalid_argument
,
330 "multiple SHT_SYMTAB_SHNDX sections are "
331 "linked to the same symbol table with index " +
334 return createStringError(errc::invalid_argument
,
335 "unable to read extended section indexes: " +
336 toString(TableOrErr
.takeError()));
342 if (Error E
= dumpSymbols(SymTab
, Y
->Symbols
))
346 if (Error E
= dumpSymbols(DynSymTab
, Y
->DynamicSymbols
))
349 // We dump all sections first. It is simple and allows us to verify that all
350 // sections are valid and also to generalize the code. But we are not going to
351 // keep all of them in the final output (see comments for
352 // 'shouldPrintSection()'). Undesired chunks will be removed later.
353 Expected
<std::vector
<std::unique_ptr
<ELFYAML::Chunk
>>> ChunksOrErr
=
356 return ChunksOrErr
.takeError();
357 std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> Chunks
= std::move(*ChunksOrErr
);
359 std::vector
<ELFYAML::Section
*> OriginalOrder
;
361 for (const std::unique_ptr
<ELFYAML::Chunk
> &C
:
362 ArrayRef(Chunks
).drop_front())
363 OriginalOrder
.push_back(cast
<ELFYAML::Section
>(C
.get()));
365 // Sometimes the order of sections in the section header table does not match
366 // their actual order. Here we sort sections by the file offset.
367 llvm::stable_sort(Chunks
, [&](const std::unique_ptr
<ELFYAML::Chunk
> &A
,
368 const std::unique_ptr
<ELFYAML::Chunk
> &B
) {
369 return Sections
[cast
<ELFYAML::Section
>(A
.get())->OriginalSecNdx
].sh_offset
<
370 Sections
[cast
<ELFYAML::Section
>(B
.get())->OriginalSecNdx
].sh_offset
;
373 // Dump program headers.
374 Expected
<std::vector
<ELFYAML::ProgramHeader
>> PhdrsOrErr
=
375 dumpProgramHeaders(Chunks
);
377 return PhdrsOrErr
.takeError();
378 Y
->ProgramHeaders
= std::move(*PhdrsOrErr
);
380 dumpSectionOffsets
<ELFT
>(Obj
.getHeader(), Y
->ProgramHeaders
, Chunks
,
383 // Dump DWARF sections.
384 Y
->DWARF
= dumpDWARFSections(Chunks
);
386 // We emit the "SectionHeaderTable" key when the order of sections in the
387 // sections header table doesn't match the file order.
388 const bool SectionsSorted
=
389 llvm::is_sorted(Chunks
, [&](const std::unique_ptr
<ELFYAML::Chunk
> &A
,
390 const std::unique_ptr
<ELFYAML::Chunk
> &B
) {
391 return cast
<ELFYAML::Section
>(A
.get())->OriginalSecNdx
<
392 cast
<ELFYAML::Section
>(B
.get())->OriginalSecNdx
;
394 if (!SectionsSorted
) {
395 std::unique_ptr
<ELFYAML::SectionHeaderTable
> SHT
=
396 std::make_unique
<ELFYAML::SectionHeaderTable
>(/*IsImplicit=*/false);
397 SHT
->Sections
.emplace();
398 for (ELFYAML::Section
*S
: OriginalOrder
)
399 SHT
->Sections
->push_back({S
->Name
});
400 Chunks
.push_back(std::move(SHT
));
403 llvm::erase_if(Chunks
, [this, &Y
](const std::unique_ptr
<ELFYAML::Chunk
> &C
) {
404 if (isa
<ELFYAML::SectionHeaderTable
>(*C
))
407 const ELFYAML::Section
&S
= cast
<ELFYAML::Section
>(*C
);
408 return !shouldPrintSection(S
, Sections
[S
.OriginalSecNdx
], Y
->DWARF
);
411 // The section header string table by default is assumed to be called
412 // ".shstrtab" and be in its own unique section. However, it's possible for it
413 // to be called something else and shared with another section. If the name
414 // isn't the default, provide this in the YAML.
415 if (ShStrTabIndex
&& *ShStrTabIndex
!= ELF::SHN_UNDEF
&&
416 *ShStrTabIndex
< Sections
.size()) {
417 StringRef ShStrtabName
;
418 if (SymTab
&& SymTab
->sh_link
== *ShStrTabIndex
) {
419 // Section header string table is shared with the symbol table. Use that
420 // section's name (usually .strtab).
421 ShStrtabName
= cantFail(Obj
.getSectionName(Sections
[SymTab
->sh_link
]));
422 } else if (DynSymTab
&& DynSymTab
->sh_link
== *ShStrTabIndex
) {
423 // Section header string table is shared with the dynamic symbol table.
424 // Use that section's name (usually .dynstr).
425 ShStrtabName
= cantFail(Obj
.getSectionName(Sections
[DynSymTab
->sh_link
]));
427 // Otherwise, the section name potentially needs uniquifying.
428 ShStrtabName
= cantFail(getUniquedSectionName(Sections
[*ShStrTabIndex
]));
430 if (ShStrtabName
!= ".shstrtab")
431 Y
->Header
.SectionHeaderStringTable
= ShStrtabName
;
434 Y
->Chunks
= std::move(Chunks
);
438 template <class ELFT
>
439 static bool isInSegment(const ELFYAML::Section
&Sec
,
440 const typename
ELFT::Shdr
&SHdr
,
441 const typename
ELFT::Phdr
&Phdr
) {
442 if (Sec
.Type
== ELF::SHT_NULL
)
445 // A section is within a segment when its location in a file is within the
446 // [p_offset, p_offset + p_filesz] region.
447 bool FileOffsetsMatch
=
448 SHdr
.sh_offset
>= Phdr
.p_offset
&&
449 (SHdr
.sh_offset
+ SHdr
.sh_size
<= Phdr
.p_offset
+ Phdr
.p_filesz
);
451 bool VirtualAddressesMatch
= SHdr
.sh_addr
>= Phdr
.p_vaddr
&&
452 SHdr
.sh_addr
<= Phdr
.p_vaddr
+ Phdr
.p_memsz
;
454 if (FileOffsetsMatch
) {
455 // An empty section on the edges of a program header can be outside of the
456 // virtual address space of the segment. This means it is not included in
457 // the segment and we should ignore it.
458 if (SHdr
.sh_size
== 0 && (SHdr
.sh_offset
== Phdr
.p_offset
||
459 SHdr
.sh_offset
== Phdr
.p_offset
+ Phdr
.p_filesz
))
460 return VirtualAddressesMatch
;
464 // SHT_NOBITS sections usually occupy no physical space in a file. Such
465 // sections belong to a segment when they reside in the segment's virtual
467 if (Sec
.Type
!= ELF::SHT_NOBITS
)
469 return VirtualAddressesMatch
;
472 template <class ELFT
>
473 Expected
<std::vector
<ELFYAML::ProgramHeader
>>
474 ELFDumper
<ELFT
>::dumpProgramHeaders(
475 ArrayRef
<std::unique_ptr
<ELFYAML::Chunk
>> Chunks
) {
476 std::vector
<ELFYAML::ProgramHeader
> Ret
;
477 Expected
<typename
ELFT::PhdrRange
> PhdrsOrErr
= Obj
.program_headers();
479 return PhdrsOrErr
.takeError();
481 for (const typename
ELFT::Phdr
&Phdr
: *PhdrsOrErr
) {
482 ELFYAML::ProgramHeader PH
;
483 PH
.Type
= Phdr
.p_type
;
484 PH
.Flags
= Phdr
.p_flags
;
485 PH
.VAddr
= Phdr
.p_vaddr
;
486 PH
.PAddr
= Phdr
.p_paddr
;
488 // yaml2obj sets the alignment of a segment to 1 by default.
489 // We do not print the default alignment to reduce noise in the output.
490 if (Phdr
.p_align
!= 1)
491 PH
.Align
= static_cast<llvm::yaml::Hex64
>(Phdr
.p_align
);
493 // Here we match sections with segments.
494 // It is not possible to have a non-Section chunk, because
495 // obj2yaml does not create Fill chunks.
496 for (const std::unique_ptr
<ELFYAML::Chunk
> &C
: Chunks
) {
497 ELFYAML::Section
&S
= cast
<ELFYAML::Section
>(*C
);
498 if (isInSegment
<ELFT
>(S
, Sections
[S
.OriginalSecNdx
], Phdr
)) {
500 PH
.FirstSec
= S
.Name
;
502 PH
.Chunks
.push_back(C
.get());
512 template <class ELFT
>
513 std::optional
<DWARFYAML::Data
> ELFDumper
<ELFT
>::dumpDWARFSections(
514 std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> &Sections
) {
515 DWARFYAML::Data DWARF
;
516 for (std::unique_ptr
<ELFYAML::Chunk
> &C
: Sections
) {
517 if (!C
->Name
.startswith(".debug_"))
520 if (ELFYAML::RawContentSection
*RawSec
=
521 dyn_cast
<ELFYAML::RawContentSection
>(C
.get())) {
522 // FIXME: The dumpDebug* functions should take the content as stored in
523 // RawSec. Currently, they just use the last section with the matching
524 // name, which defeats this attempt to skip reading a section header
525 // string table with the same name as a DWARF section.
526 if (ShStrTabIndex
&& RawSec
->OriginalSecNdx
== *ShStrTabIndex
)
528 Error Err
= Error::success();
529 cantFail(std::move(Err
));
531 if (RawSec
->Name
== ".debug_aranges")
532 Err
= dumpDebugARanges(*DWARFCtx
, DWARF
);
533 else if (RawSec
->Name
== ".debug_str")
534 Err
= dumpDebugStrings(*DWARFCtx
, DWARF
);
535 else if (RawSec
->Name
== ".debug_ranges")
536 Err
= dumpDebugRanges(*DWARFCtx
, DWARF
);
537 else if (RawSec
->Name
== ".debug_addr")
538 Err
= dumpDebugAddr(*DWARFCtx
, DWARF
);
542 // If the DWARF section cannot be successfully parsed, emit raw content
543 // instead of an entry in the DWARF section of the YAML.
545 consumeError(std::move(Err
));
547 RawSec
->Content
.reset();
551 if (DWARF
.getNonEmptySectionNames().empty())
556 template <class ELFT
>
557 Expected
<ELFYAML::RawContentSection
*>
558 ELFDumper
<ELFT
>::dumpPlaceholderSection(const Elf_Shdr
*Shdr
) {
559 auto S
= std::make_unique
<ELFYAML::RawContentSection
>();
560 if (Error E
= dumpCommonSection(Shdr
, *S
.get()))
563 // Normally symbol tables should not be empty. We dump the "Size"
564 // key when they are.
565 if ((Shdr
->sh_type
== ELF::SHT_SYMTAB
|| Shdr
->sh_type
== ELF::SHT_DYNSYM
) &&
572 template <class ELFT
>
573 Expected
<std::vector
<std::unique_ptr
<ELFYAML::Chunk
>>>
574 ELFDumper
<ELFT
>::dumpSections() {
575 std::vector
<std::unique_ptr
<ELFYAML::Chunk
>> Ret
;
576 auto Add
= [&](Expected
<ELFYAML::Chunk
*> SecOrErr
) -> Error
{
578 return SecOrErr
.takeError();
579 Ret
.emplace_back(*SecOrErr
);
580 return Error::success();
583 auto GetDumper
= [this](unsigned Type
)
584 -> std::function
<Expected
<ELFYAML::Chunk
*>(const Elf_Shdr
*)> {
585 if (Obj
.getHeader().e_machine
== ELF::EM_ARM
&& Type
== ELF::SHT_ARM_EXIDX
)
586 return [this](const Elf_Shdr
*S
) { return dumpARMIndexTableSection(S
); };
588 if (Obj
.getHeader().e_machine
== ELF::EM_MIPS
&&
589 Type
== ELF::SHT_MIPS_ABIFLAGS
)
590 return [this](const Elf_Shdr
*S
) { return dumpMipsABIFlags(S
); };
593 case ELF::SHT_DYNAMIC
:
594 return [this](const Elf_Shdr
*S
) { return dumpDynamicSection(S
); };
595 case ELF::SHT_SYMTAB_SHNDX
:
596 return [this](const Elf_Shdr
*S
) { return dumpSymtabShndxSection(S
); };
599 return [this](const Elf_Shdr
*S
) { return dumpRelocSection(S
); };
601 return [this](const Elf_Shdr
*S
) { return dumpRelrSection(S
); };
603 return [this](const Elf_Shdr
*S
) { return dumpGroupSection(S
); };
604 case ELF::SHT_NOBITS
:
605 return [this](const Elf_Shdr
*S
) { return dumpNoBitsSection(S
); };
607 return [this](const Elf_Shdr
*S
) { return dumpNoteSection(S
); };
609 return [this](const Elf_Shdr
*S
) { return dumpHashSection(S
); };
610 case ELF::SHT_GNU_HASH
:
611 return [this](const Elf_Shdr
*S
) { return dumpGnuHashSection(S
); };
612 case ELF::SHT_GNU_verdef
:
613 return [this](const Elf_Shdr
*S
) { return dumpVerdefSection(S
); };
614 case ELF::SHT_GNU_versym
:
615 return [this](const Elf_Shdr
*S
) { return dumpSymverSection(S
); };
616 case ELF::SHT_GNU_verneed
:
617 return [this](const Elf_Shdr
*S
) { return dumpVerneedSection(S
); };
618 case ELF::SHT_LLVM_ADDRSIG
:
619 return [this](const Elf_Shdr
*S
) { return dumpAddrsigSection(S
); };
620 case ELF::SHT_LLVM_LINKER_OPTIONS
:
621 return [this](const Elf_Shdr
*S
) { return dumpLinkerOptionsSection(S
); };
622 case ELF::SHT_LLVM_DEPENDENT_LIBRARIES
:
623 return [this](const Elf_Shdr
*S
) {
624 return dumpDependentLibrariesSection(S
);
626 case ELF::SHT_LLVM_CALL_GRAPH_PROFILE
:
628 [this](const Elf_Shdr
*S
) { return dumpCallGraphProfileSection(S
); };
629 case ELF::SHT_LLVM_BB_ADDR_MAP_V0
:
630 case ELF::SHT_LLVM_BB_ADDR_MAP
:
631 return [this](const Elf_Shdr
*S
) { return dumpBBAddrMapSection(S
); };
632 case ELF::SHT_STRTAB
:
633 case ELF::SHT_SYMTAB
:
634 case ELF::SHT_DYNSYM
:
635 // The contents of these sections are described by other parts of the YAML
636 // file. But we still want to dump them, because their properties can be
637 // important. See comments for 'shouldPrintSection()' for more details.
638 return [this](const Elf_Shdr
*S
) { return dumpPlaceholderSection(S
); };
644 for (const Elf_Shdr
&Sec
: Sections
) {
645 // We have dedicated dumping functions for most of the section types.
646 // Try to use one of them first.
647 if (std::function
<Expected
<ELFYAML::Chunk
*>(const Elf_Shdr
*)> DumpFn
=
648 GetDumper(Sec
.sh_type
)) {
649 if (Error E
= Add(DumpFn(&Sec
)))
654 // Recognize some special SHT_PROGBITS sections by name.
655 if (Sec
.sh_type
== ELF::SHT_PROGBITS
) {
656 auto NameOrErr
= Obj
.getSectionName(Sec
);
658 return NameOrErr
.takeError();
660 if (ELFYAML::StackSizesSection::nameMatches(*NameOrErr
)) {
661 if (Error E
= Add(dumpStackSizesSection(&Sec
)))
667 if (Error E
= Add(dumpContentSection(&Sec
)))
671 return std::move(Ret
);
674 template <class ELFT
>
675 Error ELFDumper
<ELFT
>::dumpSymbols(
676 const Elf_Shdr
*Symtab
,
677 std::optional
<std::vector
<ELFYAML::Symbol
>> &Symbols
) {
679 return Error::success();
681 auto SymtabOrErr
= Obj
.symbols(Symtab
);
683 return SymtabOrErr
.takeError();
685 if (SymtabOrErr
->empty())
686 return Error::success();
688 auto StrTableOrErr
= Obj
.getStringTableForSymtab(*Symtab
);
690 return StrTableOrErr
.takeError();
692 if (Symtab
->sh_type
== ELF::SHT_SYMTAB
) {
693 SymTable
= *SymtabOrErr
;
694 SymbolNames
.resize(SymTable
.size());
698 for (const auto &Sym
: (*SymtabOrErr
).drop_front()) {
700 if (auto EC
= dumpSymbol(&Sym
, Symtab
, *StrTableOrErr
, S
))
702 Symbols
->push_back(S
);
705 return Error::success();
708 template <class ELFT
>
709 Error ELFDumper
<ELFT
>::dumpSymbol(const Elf_Sym
*Sym
, const Elf_Shdr
*SymTab
,
710 StringRef StrTable
, ELFYAML::Symbol
&S
) {
711 S
.Type
= Sym
->getType();
713 S
.Value
= (yaml::Hex64
)Sym
->st_value
;
715 S
.Size
= (yaml::Hex64
)Sym
->st_size
;
716 S
.Other
= Sym
->st_other
;
717 S
.Binding
= Sym
->getBinding();
719 Expected
<StringRef
> SymbolNameOrErr
=
720 getUniquedSymbolName(Sym
, StrTable
, SymTab
);
721 if (!SymbolNameOrErr
)
722 return SymbolNameOrErr
.takeError();
723 S
.Name
= SymbolNameOrErr
.get();
725 if (Sym
->st_shndx
>= ELF::SHN_LORESERVE
) {
726 S
.Index
= (ELFYAML::ELF_SHN
)Sym
->st_shndx
;
727 return Error::success();
730 auto ShdrOrErr
= Obj
.getSection(*Sym
, SymTab
, ShndxTables
.lookup(SymTab
));
732 return ShdrOrErr
.takeError();
733 const Elf_Shdr
*Shdr
= *ShdrOrErr
;
735 return Error::success();
737 auto NameOrErr
= getUniquedSectionName(*Shdr
);
739 return NameOrErr
.takeError();
740 S
.Section
= NameOrErr
.get();
742 return Error::success();
745 template <class ELFT
>
746 template <class RelT
>
747 Error ELFDumper
<ELFT
>::dumpRelocation(const RelT
*Rel
, const Elf_Shdr
*SymTab
,
748 ELFYAML::Relocation
&R
) {
749 R
.Type
= Rel
->getType(Obj
.isMips64EL());
750 R
.Offset
= Rel
->r_offset
;
753 auto SymOrErr
= Obj
.getRelocationSymbol(*Rel
, SymTab
);
755 return SymOrErr
.takeError();
757 // We have might have a relocation with symbol index 0,
758 // e.g. R_X86_64_NONE or R_X86_64_GOTPC32.
759 const Elf_Sym
*Sym
= *SymOrErr
;
761 return Error::success();
763 auto StrTabSec
= Obj
.getSection(SymTab
->sh_link
);
765 return StrTabSec
.takeError();
766 auto StrTabOrErr
= Obj
.getStringTable(**StrTabSec
);
768 return StrTabOrErr
.takeError();
770 Expected
<StringRef
> NameOrErr
=
771 getUniquedSymbolName(Sym
, *StrTabOrErr
, SymTab
);
773 return NameOrErr
.takeError();
774 R
.Symbol
= NameOrErr
.get();
776 return Error::success();
779 template <class ELFT
>
780 Error ELFDumper
<ELFT
>::dumpCommonSection(const Elf_Shdr
*Shdr
,
781 ELFYAML::Section
&S
) {
782 // Dump fields. We do not dump the ShOffset field. When not explicitly
783 // set, the value is set by yaml2obj automatically.
784 S
.Type
= Shdr
->sh_type
;
786 S
.Flags
= static_cast<ELFYAML::ELF_SHF
>(Shdr
->sh_flags
);
788 S
.Address
= static_cast<uint64_t>(Shdr
->sh_addr
);
789 S
.AddressAlign
= Shdr
->sh_addralign
;
791 S
.OriginalSecNdx
= Shdr
- &Sections
[0];
793 Expected
<StringRef
> NameOrErr
= getUniquedSectionName(*Shdr
);
795 return NameOrErr
.takeError();
796 S
.Name
= NameOrErr
.get();
798 if (Shdr
->sh_entsize
!= ELFYAML::getDefaultShEntSize
<ELFT
>(
799 Obj
.getHeader().e_machine
, S
.Type
, S
.Name
))
800 S
.EntSize
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_entsize
);
802 if (Shdr
->sh_link
!= ELF::SHN_UNDEF
) {
803 Expected
<const Elf_Shdr
*> LinkSection
= Obj
.getSection(Shdr
->sh_link
);
805 return make_error
<StringError
>(
806 "unable to resolve sh_link reference in section '" + S
.Name
+
807 "': " + toString(LinkSection
.takeError()),
808 inconvertibleErrorCode());
810 NameOrErr
= getUniquedSectionName(**LinkSection
);
812 return NameOrErr
.takeError();
813 S
.Link
= NameOrErr
.get();
816 return Error::success();
819 template <class ELFT
>
820 Error ELFDumper
<ELFT
>::dumpCommonRelocationSection(
821 const Elf_Shdr
*Shdr
, ELFYAML::RelocationSection
&S
) {
822 if (Error E
= dumpCommonSection(Shdr
, S
))
825 // Having a zero sh_info field is normal: .rela.dyn is a dynamic
826 // relocation section that normally has no value in this field.
828 return Error::success();
830 auto InfoSection
= Obj
.getSection(Shdr
->sh_info
);
832 return InfoSection
.takeError();
834 Expected
<StringRef
> NameOrErr
= getUniquedSectionName(**InfoSection
);
836 return NameOrErr
.takeError();
837 S
.RelocatableSec
= NameOrErr
.get();
839 return Error::success();
842 template <class ELFT
>
843 Expected
<ELFYAML::StackSizesSection
*>
844 ELFDumper
<ELFT
>::dumpStackSizesSection(const Elf_Shdr
*Shdr
) {
845 auto S
= std::make_unique
<ELFYAML::StackSizesSection
>();
846 if (Error E
= dumpCommonSection(Shdr
, *S
))
849 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
851 return ContentOrErr
.takeError();
853 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
854 DataExtractor
Data(Content
, Obj
.isLE(), ELFT::Is64Bits
? 8 : 4);
856 std::vector
<ELFYAML::StackSizeEntry
> Entries
;
857 DataExtractor::Cursor
Cur(0);
858 while (Cur
&& Cur
.tell() < Content
.size()) {
859 uint64_t Address
= Data
.getAddress(Cur
);
860 uint64_t Size
= Data
.getULEB128(Cur
);
861 Entries
.push_back({Address
, Size
});
864 if (Content
.empty() || !Cur
) {
865 // If .stack_sizes cannot be decoded, we dump it as an array of bytes.
866 consumeError(Cur
.takeError());
867 S
->Content
= yaml::BinaryRef(Content
);
869 S
->Entries
= std::move(Entries
);
875 template <class ELFT
>
876 Expected
<ELFYAML::BBAddrMapSection
*>
877 ELFDumper
<ELFT
>::dumpBBAddrMapSection(const Elf_Shdr
*Shdr
) {
878 auto S
= std::make_unique
<ELFYAML::BBAddrMapSection
>();
879 if (Error E
= dumpCommonSection(Shdr
, *S
))
882 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
884 return ContentOrErr
.takeError();
886 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
890 DataExtractor
Data(Content
, Obj
.isLE(), ELFT::Is64Bits
? 8 : 4);
892 std::vector
<ELFYAML::BBAddrMapEntry
> Entries
;
893 DataExtractor::Cursor
Cur(0);
896 while (Cur
&& Cur
.tell() < Content
.size()) {
897 if (Shdr
->sh_type
== ELF::SHT_LLVM_BB_ADDR_MAP
) {
898 Version
= Data
.getU8(Cur
);
899 if (Cur
&& Version
> 2)
900 return createStringError(
901 errc::invalid_argument
,
902 "invalid SHT_LLVM_BB_ADDR_MAP section version: " +
903 Twine(static_cast<int>(Version
)));
904 Feature
= Data
.getU8(Cur
);
906 uint64_t Address
= Data
.getAddress(Cur
);
907 uint64_t NumBlocks
= Data
.getULEB128(Cur
);
908 std::vector
<ELFYAML::BBAddrMapEntry::BBEntry
> BBEntries
;
909 // Read the specified number of BB entries, or until decoding fails.
910 for (uint64_t BlockIndex
= 0; Cur
&& BlockIndex
< NumBlocks
; ++BlockIndex
) {
911 uint32_t ID
= Version
>= 2 ? Data
.getULEB128(Cur
) : BlockIndex
;
912 uint64_t Offset
= Data
.getULEB128(Cur
);
913 uint64_t Size
= Data
.getULEB128(Cur
);
914 uint64_t Metadata
= Data
.getULEB128(Cur
);
915 BBEntries
.push_back({ID
, Offset
, Size
, Metadata
});
918 {Version
, Feature
, Address
, /*NumBlocks=*/{}, std::move(BBEntries
)});
922 // If the section cannot be decoded, we dump it as an array of bytes.
923 consumeError(Cur
.takeError());
924 S
->Content
= yaml::BinaryRef(Content
);
926 S
->Entries
= std::move(Entries
);
932 template <class ELFT
>
933 Expected
<ELFYAML::AddrsigSection
*>
934 ELFDumper
<ELFT
>::dumpAddrsigSection(const Elf_Shdr
*Shdr
) {
935 auto S
= std::make_unique
<ELFYAML::AddrsigSection
>();
936 if (Error E
= dumpCommonSection(Shdr
, *S
))
939 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
941 return ContentOrErr
.takeError();
943 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
944 DataExtractor::Cursor
Cur(0);
945 DataExtractor
Data(Content
, Obj
.isLE(), /*AddressSize=*/0);
946 std::vector
<ELFYAML::YAMLFlowString
> Symbols
;
947 while (Cur
&& Cur
.tell() < Content
.size()) {
948 uint64_t SymNdx
= Data
.getULEB128(Cur
);
952 Expected
<StringRef
> SymbolName
= getSymbolName(Shdr
->sh_link
, SymNdx
);
953 if (!SymbolName
|| SymbolName
->empty()) {
954 consumeError(SymbolName
.takeError());
955 Symbols
.emplace_back(
956 StringRef(std::to_string(SymNdx
)).copy(StringAllocator
));
960 Symbols
.emplace_back(*SymbolName
);
964 S
->Symbols
= std::move(Symbols
);
968 consumeError(Cur
.takeError());
969 S
->Content
= yaml::BinaryRef(Content
);
973 template <class ELFT
>
974 Expected
<ELFYAML::LinkerOptionsSection
*>
975 ELFDumper
<ELFT
>::dumpLinkerOptionsSection(const Elf_Shdr
*Shdr
) {
976 auto S
= std::make_unique
<ELFYAML::LinkerOptionsSection
>();
977 if (Error E
= dumpCommonSection(Shdr
, *S
))
980 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
982 return ContentOrErr
.takeError();
984 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
985 if (Content
.empty() || Content
.back() != 0) {
986 S
->Content
= Content
;
990 SmallVector
<StringRef
, 16> Strings
;
991 toStringRef(Content
.drop_back()).split(Strings
, '\0');
992 if (Strings
.size() % 2 != 0) {
993 S
->Content
= Content
;
997 S
->Options
.emplace();
998 for (size_t I
= 0, E
= Strings
.size(); I
!= E
; I
+= 2)
999 S
->Options
->push_back({Strings
[I
], Strings
[I
+ 1]});
1004 template <class ELFT
>
1005 Expected
<ELFYAML::DependentLibrariesSection
*>
1006 ELFDumper
<ELFT
>::dumpDependentLibrariesSection(const Elf_Shdr
*Shdr
) {
1007 auto DL
= std::make_unique
<ELFYAML::DependentLibrariesSection
>();
1008 if (Error E
= dumpCommonSection(Shdr
, *DL
))
1009 return std::move(E
);
1011 Expected
<ArrayRef
<uint8_t>> ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1013 return ContentOrErr
.takeError();
1015 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1016 if (!Content
.empty() && Content
.back() != 0) {
1017 DL
->Content
= Content
;
1018 return DL
.release();
1022 for (const uint8_t *I
= Content
.begin(), *E
= Content
.end(); I
< E
;) {
1023 StringRef
Lib((const char *)I
);
1024 DL
->Libs
->emplace_back(Lib
);
1025 I
+= Lib
.size() + 1;
1028 return DL
.release();
1031 template <class ELFT
>
1032 Expected
<ELFYAML::CallGraphProfileSection
*>
1033 ELFDumper
<ELFT
>::dumpCallGraphProfileSection(const Elf_Shdr
*Shdr
) {
1034 auto S
= std::make_unique
<ELFYAML::CallGraphProfileSection
>();
1035 if (Error E
= dumpCommonSection(Shdr
, *S
))
1036 return std::move(E
);
1038 Expected
<ArrayRef
<uint8_t>> ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1040 return ContentOrErr
.takeError();
1041 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1042 const uint32_t SizeOfEntry
= ELFYAML::getDefaultShEntSize
<ELFT
>(
1043 Obj
.getHeader().e_machine
, S
->Type
, S
->Name
);
1044 // Dump the section by using the Content key when it is truncated.
1045 // There is no need to create either "Content" or "Entries" fields when the
1046 // section is empty.
1047 if (Content
.empty() || Content
.size() % SizeOfEntry
!= 0) {
1048 if (!Content
.empty())
1049 S
->Content
= yaml::BinaryRef(Content
);
1053 std::vector
<ELFYAML::CallGraphEntryWeight
> Entries(Content
.size() /
1055 DataExtractor
Data(Content
, Obj
.isLE(), /*AddressSize=*/0);
1056 DataExtractor::Cursor
Cur(0);
1057 auto ReadEntry
= [&](ELFYAML::CallGraphEntryWeight
&E
) {
1058 E
.Weight
= Data
.getU64(Cur
);
1060 consumeError(Cur
.takeError());
1066 for (ELFYAML::CallGraphEntryWeight
&E
: Entries
) {
1069 S
->Content
= yaml::BinaryRef(Content
);
1073 S
->Entries
= std::move(Entries
);
1077 template <class ELFT
>
1078 Expected
<ELFYAML::DynamicSection
*>
1079 ELFDumper
<ELFT
>::dumpDynamicSection(const Elf_Shdr
*Shdr
) {
1080 auto S
= std::make_unique
<ELFYAML::DynamicSection
>();
1081 if (Error E
= dumpCommonSection(Shdr
, *S
))
1082 return std::move(E
);
1084 auto DynTagsOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Dyn
>(*Shdr
);
1086 return DynTagsOrErr
.takeError();
1088 S
->Entries
.emplace();
1089 for (const Elf_Dyn
&Dyn
: *DynTagsOrErr
)
1090 S
->Entries
->push_back({(ELFYAML::ELF_DYNTAG
)Dyn
.getTag(), Dyn
.getVal()});
1095 template <class ELFT
>
1096 Expected
<ELFYAML::RelocationSection
*>
1097 ELFDumper
<ELFT
>::dumpRelocSection(const Elf_Shdr
*Shdr
) {
1098 auto S
= std::make_unique
<ELFYAML::RelocationSection
>();
1099 if (auto E
= dumpCommonRelocationSection(Shdr
, *S
))
1100 return std::move(E
);
1102 auto SymTabOrErr
= Obj
.getSection(Shdr
->sh_link
);
1104 return SymTabOrErr
.takeError();
1106 if (Shdr
->sh_size
!= 0)
1107 S
->Relocations
.emplace();
1109 if (Shdr
->sh_type
== ELF::SHT_REL
) {
1110 auto Rels
= Obj
.rels(*Shdr
);
1112 return Rels
.takeError();
1113 for (const Elf_Rel
&Rel
: *Rels
) {
1114 ELFYAML::Relocation R
;
1115 if (Error E
= dumpRelocation(&Rel
, *SymTabOrErr
, R
))
1116 return std::move(E
);
1117 S
->Relocations
->push_back(R
);
1120 auto Rels
= Obj
.relas(*Shdr
);
1122 return Rels
.takeError();
1123 for (const Elf_Rela
&Rel
: *Rels
) {
1124 ELFYAML::Relocation R
;
1125 if (Error E
= dumpRelocation(&Rel
, *SymTabOrErr
, R
))
1126 return std::move(E
);
1127 R
.Addend
= Rel
.r_addend
;
1128 S
->Relocations
->push_back(R
);
1135 template <class ELFT
>
1136 Expected
<ELFYAML::RelrSection
*>
1137 ELFDumper
<ELFT
>::dumpRelrSection(const Elf_Shdr
*Shdr
) {
1138 auto S
= std::make_unique
<ELFYAML::RelrSection
>();
1139 if (auto E
= dumpCommonSection(Shdr
, *S
))
1140 return std::move(E
);
1142 if (Expected
<ArrayRef
<Elf_Relr
>> Relrs
= Obj
.relrs(*Shdr
)) {
1143 S
->Entries
.emplace();
1144 for (Elf_Relr Rel
: *Relrs
)
1145 S
->Entries
->emplace_back(Rel
);
1148 // Ignore. We are going to dump the data as raw content below.
1149 consumeError(Relrs
.takeError());
1152 Expected
<ArrayRef
<uint8_t>> ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1154 return ContentOrErr
.takeError();
1155 S
->Content
= *ContentOrErr
;
1159 template <class ELFT
>
1160 Expected
<ELFYAML::RawContentSection
*>
1161 ELFDumper
<ELFT
>::dumpContentSection(const Elf_Shdr
*Shdr
) {
1162 auto S
= std::make_unique
<ELFYAML::RawContentSection
>();
1163 if (Error E
= dumpCommonSection(Shdr
, *S
))
1164 return std::move(E
);
1166 unsigned SecIndex
= Shdr
- &Sections
[0];
1167 if (SecIndex
!= 0 || Shdr
->sh_type
!= ELF::SHT_NULL
) {
1168 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1170 return ContentOrErr
.takeError();
1171 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1172 if (!Content
.empty())
1173 S
->Content
= yaml::BinaryRef(Content
);
1175 S
->Size
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_size
);
1179 S
->Info
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_info
);
1183 template <class ELFT
>
1184 Expected
<ELFYAML::SymtabShndxSection
*>
1185 ELFDumper
<ELFT
>::dumpSymtabShndxSection(const Elf_Shdr
*Shdr
) {
1186 auto S
= std::make_unique
<ELFYAML::SymtabShndxSection
>();
1187 if (Error E
= dumpCommonSection(Shdr
, *S
))
1188 return std::move(E
);
1190 auto EntriesOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Word
>(*Shdr
);
1192 return EntriesOrErr
.takeError();
1194 S
->Entries
.emplace();
1195 for (const Elf_Word
&E
: *EntriesOrErr
)
1196 S
->Entries
->push_back(E
);
1200 template <class ELFT
>
1201 Expected
<ELFYAML::NoBitsSection
*>
1202 ELFDumper
<ELFT
>::dumpNoBitsSection(const Elf_Shdr
*Shdr
) {
1203 auto S
= std::make_unique
<ELFYAML::NoBitsSection
>();
1204 if (Error E
= dumpCommonSection(Shdr
, *S
))
1205 return std::move(E
);
1207 S
->Size
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_size
);
1211 template <class ELFT
>
1212 Expected
<ELFYAML::NoteSection
*>
1213 ELFDumper
<ELFT
>::dumpNoteSection(const Elf_Shdr
*Shdr
) {
1214 auto S
= std::make_unique
<ELFYAML::NoteSection
>();
1215 if (Error E
= dumpCommonSection(Shdr
, *S
))
1216 return std::move(E
);
1218 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1220 return ContentOrErr
.takeError();
1222 std::vector
<ELFYAML::NoteEntry
> Entries
;
1223 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1224 size_t Align
= std::max
<size_t>(Shdr
->sh_addralign
, 4);
1225 while (!Content
.empty()) {
1226 if (Content
.size() < sizeof(Elf_Nhdr
)) {
1227 S
->Content
= yaml::BinaryRef(*ContentOrErr
);
1231 const Elf_Nhdr
*Header
= reinterpret_cast<const Elf_Nhdr
*>(Content
.data());
1232 if (Content
.size() < Header
->getSize(Align
)) {
1233 S
->Content
= yaml::BinaryRef(*ContentOrErr
);
1237 Elf_Note
Note(*Header
);
1239 {Note
.getName(), Note
.getDesc(Align
), (ELFYAML::ELF_NT
)Note
.getType()});
1241 Content
= Content
.drop_front(Header
->getSize(Align
));
1244 S
->Notes
= std::move(Entries
);
1248 template <class ELFT
>
1249 Expected
<ELFYAML::HashSection
*>
1250 ELFDumper
<ELFT
>::dumpHashSection(const Elf_Shdr
*Shdr
) {
1251 auto S
= std::make_unique
<ELFYAML::HashSection
>();
1252 if (Error E
= dumpCommonSection(Shdr
, *S
))
1253 return std::move(E
);
1255 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1257 return ContentOrErr
.takeError();
1259 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1260 if (Content
.size() % 4 != 0 || Content
.size() < 8) {
1261 S
->Content
= yaml::BinaryRef(Content
);
1265 DataExtractor::Cursor
Cur(0);
1266 DataExtractor
Data(Content
, Obj
.isLE(), /*AddressSize=*/0);
1267 uint64_t NBucket
= Data
.getU32(Cur
);
1268 uint64_t NChain
= Data
.getU32(Cur
);
1269 if (Content
.size() != (2 + NBucket
+ NChain
) * 4) {
1270 S
->Content
= yaml::BinaryRef(Content
);
1273 llvm_unreachable("entries were not read correctly");
1276 S
->Bucket
.emplace(NBucket
);
1277 for (uint32_t &V
: *S
->Bucket
)
1278 V
= Data
.getU32(Cur
);
1280 S
->Chain
.emplace(NChain
);
1281 for (uint32_t &V
: *S
->Chain
)
1282 V
= Data
.getU32(Cur
);
1286 llvm_unreachable("entries were not read correctly");
1289 template <class ELFT
>
1290 Expected
<ELFYAML::GnuHashSection
*>
1291 ELFDumper
<ELFT
>::dumpGnuHashSection(const Elf_Shdr
*Shdr
) {
1292 auto S
= std::make_unique
<ELFYAML::GnuHashSection
>();
1293 if (Error E
= dumpCommonSection(Shdr
, *S
))
1294 return std::move(E
);
1296 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1298 return ContentOrErr
.takeError();
1300 unsigned AddrSize
= ELFT::Is64Bits
? 8 : 4;
1301 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
1302 DataExtractor
Data(Content
, Obj
.isLE(), AddrSize
);
1304 ELFYAML::GnuHashHeader Header
;
1305 DataExtractor::Cursor
Cur(0);
1306 uint64_t NBuckets
= Data
.getU32(Cur
);
1307 Header
.SymNdx
= Data
.getU32(Cur
);
1308 uint64_t MaskWords
= Data
.getU32(Cur
);
1309 Header
.Shift2
= Data
.getU32(Cur
);
1311 // Set just the raw binary content if we were unable to read the header
1312 // or when the section data is truncated or malformed.
1313 uint64_t Size
= Data
.getData().size() - Cur
.tell();
1314 if (!Cur
|| (Size
< MaskWords
* AddrSize
+ NBuckets
* 4) ||
1316 consumeError(Cur
.takeError());
1317 S
->Content
= yaml::BinaryRef(Content
);
1323 S
->BloomFilter
.emplace(MaskWords
);
1324 for (llvm::yaml::Hex64
&Val
: *S
->BloomFilter
)
1325 Val
= Data
.getAddress(Cur
);
1327 S
->HashBuckets
.emplace(NBuckets
);
1328 for (llvm::yaml::Hex32
&Val
: *S
->HashBuckets
)
1329 Val
= Data
.getU32(Cur
);
1331 S
->HashValues
.emplace((Data
.getData().size() - Cur
.tell()) / 4);
1332 for (llvm::yaml::Hex32
&Val
: *S
->HashValues
)
1333 Val
= Data
.getU32(Cur
);
1337 llvm_unreachable("GnuHashSection was not read correctly");
1340 template <class ELFT
>
1341 Expected
<ELFYAML::VerdefSection
*>
1342 ELFDumper
<ELFT
>::dumpVerdefSection(const Elf_Shdr
*Shdr
) {
1343 auto S
= std::make_unique
<ELFYAML::VerdefSection
>();
1344 if (Error E
= dumpCommonSection(Shdr
, *S
))
1345 return std::move(E
);
1347 auto StringTableShdrOrErr
= Obj
.getSection(Shdr
->sh_link
);
1348 if (!StringTableShdrOrErr
)
1349 return StringTableShdrOrErr
.takeError();
1351 auto StringTableOrErr
= Obj
.getStringTable(**StringTableShdrOrErr
);
1352 if (!StringTableOrErr
)
1353 return StringTableOrErr
.takeError();
1355 auto Contents
= Obj
.getSectionContents(*Shdr
);
1357 return Contents
.takeError();
1359 S
->Entries
.emplace();
1361 llvm::ArrayRef
<uint8_t> Data
= *Contents
;
1362 const uint8_t *Buf
= Data
.data();
1364 const Elf_Verdef
*Verdef
= reinterpret_cast<const Elf_Verdef
*>(Buf
);
1365 ELFYAML::VerdefEntry Entry
;
1366 if (Verdef
->vd_version
!= 1)
1367 return createStringError(errc::invalid_argument
,
1368 "invalid SHT_GNU_verdef section version: " +
1369 Twine(Verdef
->vd_version
));
1371 if (Verdef
->vd_flags
!= 0)
1372 Entry
.Flags
= Verdef
->vd_flags
;
1374 if (Verdef
->vd_ndx
!= 0)
1375 Entry
.VersionNdx
= Verdef
->vd_ndx
;
1377 if (Verdef
->vd_hash
!= 0)
1378 Entry
.Hash
= Verdef
->vd_hash
;
1380 const uint8_t *BufAux
= Buf
+ Verdef
->vd_aux
;
1382 const Elf_Verdaux
*Verdaux
=
1383 reinterpret_cast<const Elf_Verdaux
*>(BufAux
);
1384 Entry
.VerNames
.push_back(
1385 StringTableOrErr
->drop_front(Verdaux
->vda_name
).data());
1386 BufAux
= Verdaux
->vda_next
? BufAux
+ Verdaux
->vda_next
: nullptr;
1389 S
->Entries
->push_back(Entry
);
1390 Buf
= Verdef
->vd_next
? Buf
+ Verdef
->vd_next
: nullptr;
1393 if (Shdr
->sh_info
!= S
->Entries
->size())
1394 S
->Info
= (llvm::yaml::Hex64
)Shdr
->sh_info
;
1399 template <class ELFT
>
1400 Expected
<ELFYAML::SymverSection
*>
1401 ELFDumper
<ELFT
>::dumpSymverSection(const Elf_Shdr
*Shdr
) {
1402 auto S
= std::make_unique
<ELFYAML::SymverSection
>();
1403 if (Error E
= dumpCommonSection(Shdr
, *S
))
1404 return std::move(E
);
1406 auto VersionsOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Half
>(*Shdr
);
1408 return VersionsOrErr
.takeError();
1410 S
->Entries
.emplace();
1411 for (const Elf_Half
&E
: *VersionsOrErr
)
1412 S
->Entries
->push_back(E
);
1417 template <class ELFT
>
1418 Expected
<ELFYAML::VerneedSection
*>
1419 ELFDumper
<ELFT
>::dumpVerneedSection(const Elf_Shdr
*Shdr
) {
1420 auto S
= std::make_unique
<ELFYAML::VerneedSection
>();
1421 if (Error E
= dumpCommonSection(Shdr
, *S
))
1422 return std::move(E
);
1424 auto Contents
= Obj
.getSectionContents(*Shdr
);
1426 return Contents
.takeError();
1428 auto StringTableShdrOrErr
= Obj
.getSection(Shdr
->sh_link
);
1429 if (!StringTableShdrOrErr
)
1430 return StringTableShdrOrErr
.takeError();
1432 auto StringTableOrErr
= Obj
.getStringTable(**StringTableShdrOrErr
);
1433 if (!StringTableOrErr
)
1434 return StringTableOrErr
.takeError();
1436 S
->VerneedV
.emplace();
1438 llvm::ArrayRef
<uint8_t> Data
= *Contents
;
1439 const uint8_t *Buf
= Data
.data();
1441 const Elf_Verneed
*Verneed
= reinterpret_cast<const Elf_Verneed
*>(Buf
);
1443 ELFYAML::VerneedEntry Entry
;
1444 Entry
.Version
= Verneed
->vn_version
;
1446 StringRef(StringTableOrErr
->drop_front(Verneed
->vn_file
).data());
1448 const uint8_t *BufAux
= Buf
+ Verneed
->vn_aux
;
1450 const Elf_Vernaux
*Vernaux
=
1451 reinterpret_cast<const Elf_Vernaux
*>(BufAux
);
1453 ELFYAML::VernauxEntry Aux
;
1454 Aux
.Hash
= Vernaux
->vna_hash
;
1455 Aux
.Flags
= Vernaux
->vna_flags
;
1456 Aux
.Other
= Vernaux
->vna_other
;
1458 StringRef(StringTableOrErr
->drop_front(Vernaux
->vna_name
).data());
1460 Entry
.AuxV
.push_back(Aux
);
1461 BufAux
= Vernaux
->vna_next
? BufAux
+ Vernaux
->vna_next
: nullptr;
1464 S
->VerneedV
->push_back(Entry
);
1465 Buf
= Verneed
->vn_next
? Buf
+ Verneed
->vn_next
: nullptr;
1468 if (Shdr
->sh_info
!= S
->VerneedV
->size())
1469 S
->Info
= (llvm::yaml::Hex64
)Shdr
->sh_info
;
1474 template <class ELFT
>
1475 Expected
<StringRef
> ELFDumper
<ELFT
>::getSymbolName(uint32_t SymtabNdx
,
1476 uint32_t SymbolNdx
) {
1477 auto SymtabOrErr
= Obj
.getSection(SymtabNdx
);
1479 return SymtabOrErr
.takeError();
1481 const Elf_Shdr
*Symtab
= *SymtabOrErr
;
1482 auto SymOrErr
= Obj
.getSymbol(Symtab
, SymbolNdx
);
1484 return SymOrErr
.takeError();
1486 auto StrTabOrErr
= Obj
.getStringTableForSymtab(*Symtab
);
1488 return StrTabOrErr
.takeError();
1489 return getUniquedSymbolName(*SymOrErr
, *StrTabOrErr
, Symtab
);
1492 template <class ELFT
>
1493 Expected
<ELFYAML::GroupSection
*>
1494 ELFDumper
<ELFT
>::dumpGroupSection(const Elf_Shdr
*Shdr
) {
1495 auto S
= std::make_unique
<ELFYAML::GroupSection
>();
1496 if (Error E
= dumpCommonSection(Shdr
, *S
))
1497 return std::move(E
);
1499 // Get symbol with index sh_info. This symbol's name is the signature of the group.
1500 Expected
<StringRef
> SymbolName
= getSymbolName(Shdr
->sh_link
, Shdr
->sh_info
);
1502 return SymbolName
.takeError();
1503 S
->Signature
= *SymbolName
;
1505 auto MembersOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Word
>(*Shdr
);
1507 return MembersOrErr
.takeError();
1509 S
->Members
.emplace();
1510 for (Elf_Word Member
: *MembersOrErr
) {
1511 if (Member
== llvm::ELF::GRP_COMDAT
) {
1512 S
->Members
->push_back({"GRP_COMDAT"});
1516 Expected
<const Elf_Shdr
*> SHdrOrErr
= Obj
.getSection(Member
);
1518 return SHdrOrErr
.takeError();
1519 Expected
<StringRef
> NameOrErr
= getUniquedSectionName(**SHdrOrErr
);
1521 return NameOrErr
.takeError();
1522 S
->Members
->push_back({*NameOrErr
});
1527 template <class ELFT
>
1528 Expected
<ELFYAML::ARMIndexTableSection
*>
1529 ELFDumper
<ELFT
>::dumpARMIndexTableSection(const Elf_Shdr
*Shdr
) {
1530 auto S
= std::make_unique
<ELFYAML::ARMIndexTableSection
>();
1531 if (Error E
= dumpCommonSection(Shdr
, *S
))
1532 return std::move(E
);
1534 Expected
<ArrayRef
<uint8_t>> ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1536 return ContentOrErr
.takeError();
1538 if (ContentOrErr
->size() % (sizeof(Elf_Word
) * 2) != 0) {
1539 S
->Content
= yaml::BinaryRef(*ContentOrErr
);
1543 ArrayRef
<Elf_Word
> Words(
1544 reinterpret_cast<const Elf_Word
*>(ContentOrErr
->data()),
1545 ContentOrErr
->size() / sizeof(Elf_Word
));
1547 S
->Entries
.emplace();
1548 for (size_t I
= 0, E
= Words
.size(); I
!= E
; I
+= 2)
1549 S
->Entries
->push_back({(yaml::Hex32
)Words
[I
], (yaml::Hex32
)Words
[I
+ 1]});
1554 template <class ELFT
>
1555 Expected
<ELFYAML::MipsABIFlags
*>
1556 ELFDumper
<ELFT
>::dumpMipsABIFlags(const Elf_Shdr
*Shdr
) {
1557 assert(Shdr
->sh_type
== ELF::SHT_MIPS_ABIFLAGS
&&
1558 "Section type is not SHT_MIPS_ABIFLAGS");
1559 auto S
= std::make_unique
<ELFYAML::MipsABIFlags
>();
1560 if (Error E
= dumpCommonSection(Shdr
, *S
))
1561 return std::move(E
);
1563 auto ContentOrErr
= Obj
.getSectionContents(*Shdr
);
1565 return ContentOrErr
.takeError();
1567 auto *Flags
= reinterpret_cast<const object::Elf_Mips_ABIFlags
<ELFT
> *>(
1568 ContentOrErr
.get().data());
1569 S
->Version
= Flags
->version
;
1570 S
->ISALevel
= Flags
->isa_level
;
1571 S
->ISARevision
= Flags
->isa_rev
;
1572 S
->GPRSize
= Flags
->gpr_size
;
1573 S
->CPR1Size
= Flags
->cpr1_size
;
1574 S
->CPR2Size
= Flags
->cpr2_size
;
1575 S
->FpABI
= Flags
->fp_abi
;
1576 S
->ISAExtension
= Flags
->isa_ext
;
1577 S
->ASEs
= Flags
->ases
;
1578 S
->Flags1
= Flags
->flags1
;
1579 S
->Flags2
= Flags
->flags2
;
1583 template <class ELFT
>
1584 static Error
elf2yaml(raw_ostream
&Out
, const object::ELFFile
<ELFT
> &Obj
,
1585 std::unique_ptr
<DWARFContext
> DWARFCtx
) {
1586 ELFDumper
<ELFT
> Dumper(Obj
, std::move(DWARFCtx
));
1587 Expected
<ELFYAML::Object
*> YAMLOrErr
= Dumper
.dump();
1589 return YAMLOrErr
.takeError();
1591 std::unique_ptr
<ELFYAML::Object
> YAML(YAMLOrErr
.get());
1592 yaml::Output
Yout(Out
);
1595 return Error::success();
1598 Error
elf2yaml(raw_ostream
&Out
, const object::ObjectFile
&Obj
) {
1599 std::unique_ptr
<DWARFContext
> DWARFCtx
= DWARFContext::create(Obj
);
1600 if (const auto *ELFObj
= dyn_cast
<object::ELF32LEObjectFile
>(&Obj
))
1601 return elf2yaml(Out
, ELFObj
->getELFFile(), std::move(DWARFCtx
));
1603 if (const auto *ELFObj
= dyn_cast
<object::ELF32BEObjectFile
>(&Obj
))
1604 return elf2yaml(Out
, ELFObj
->getELFFile(), std::move(DWARFCtx
));
1606 if (const auto *ELFObj
= dyn_cast
<object::ELF64LEObjectFile
>(&Obj
))
1607 return elf2yaml(Out
, ELFObj
->getELFFile(), std::move(DWARFCtx
));
1609 if (const auto *ELFObj
= dyn_cast
<object::ELF64BEObjectFile
>(&Obj
))
1610 return elf2yaml(Out
, ELFObj
->getELFFile(), std::move(DWARFCtx
));
1612 llvm_unreachable("unknown ELF file format");