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/Object/ELFObjectFile.h"
13 #include "llvm/ObjectYAML/ELFYAML.h"
14 #include "llvm/Support/ErrorHandling.h"
15 #include "llvm/Support/YAMLTraits.h"
23 typedef object::Elf_Sym_Impl
<ELFT
> Elf_Sym
;
24 typedef typename
ELFT::Dyn Elf_Dyn
;
25 typedef typename
ELFT::Shdr Elf_Shdr
;
26 typedef typename
ELFT::Word Elf_Word
;
27 typedef typename
ELFT::Rel Elf_Rel
;
28 typedef typename
ELFT::Rela Elf_Rela
;
30 ArrayRef
<Elf_Shdr
> Sections
;
31 ArrayRef
<Elf_Sym
> SymTable
;
33 DenseMap
<StringRef
, uint32_t> UsedSectionNames
;
34 std::vector
<std::string
> SectionNames
;
36 DenseMap
<StringRef
, uint32_t> UsedSymbolNames
;
37 std::vector
<std::string
> SymbolNames
;
39 Expected
<StringRef
> getUniquedSectionName(const Elf_Shdr
*Sec
);
40 Expected
<StringRef
> getUniquedSymbolName(const Elf_Sym
*Sym
,
42 const Elf_Shdr
*SymTab
);
44 const object::ELFFile
<ELFT
> &Obj
;
45 ArrayRef
<Elf_Word
> ShndxTable
;
47 Error
dumpSymbols(const Elf_Shdr
*Symtab
,
48 std::vector
<ELFYAML::Symbol
> &Symbols
);
49 Error
dumpSymbol(const Elf_Sym
*Sym
, const Elf_Shdr
*SymTab
,
50 StringRef StrTable
, ELFYAML::Symbol
&S
);
51 Error
dumpCommonSection(const Elf_Shdr
*Shdr
, ELFYAML::Section
&S
);
52 Error
dumpCommonRelocationSection(const Elf_Shdr
*Shdr
,
53 ELFYAML::RelocationSection
&S
);
55 Error
dumpRelocation(const RelT
*Rel
, const Elf_Shdr
*SymTab
,
56 ELFYAML::Relocation
&R
);
58 Expected
<ELFYAML::DynamicSection
*> dumpDynamicSection(const Elf_Shdr
*Shdr
);
59 Expected
<ELFYAML::RelocationSection
*> dumpRelocSection(const Elf_Shdr
*Shdr
);
60 Expected
<ELFYAML::RawContentSection
*>
61 dumpContentSection(const Elf_Shdr
*Shdr
);
62 Expected
<ELFYAML::SymtabShndxSection
*>
63 dumpSymtabShndxSection(const Elf_Shdr
*Shdr
);
64 Expected
<ELFYAML::NoBitsSection
*> dumpNoBitsSection(const Elf_Shdr
*Shdr
);
65 Expected
<ELFYAML::VerdefSection
*> dumpVerdefSection(const Elf_Shdr
*Shdr
);
66 Expected
<ELFYAML::SymverSection
*> dumpSymverSection(const Elf_Shdr
*Shdr
);
67 Expected
<ELFYAML::VerneedSection
*> dumpVerneedSection(const Elf_Shdr
*Shdr
);
68 Expected
<ELFYAML::Group
*> dumpGroup(const Elf_Shdr
*Shdr
);
69 Expected
<ELFYAML::MipsABIFlags
*> dumpMipsABIFlags(const Elf_Shdr
*Shdr
);
72 ELFDumper(const object::ELFFile
<ELFT
> &O
);
73 Expected
<ELFYAML::Object
*> dump();
79 ELFDumper
<ELFT
>::ELFDumper(const object::ELFFile
<ELFT
> &O
)
84 ELFDumper
<ELFT
>::getUniquedSectionName(const Elf_Shdr
*Sec
) {
85 unsigned SecIndex
= Sec
- &Sections
[0];
86 assert(&Sections
[SecIndex
] == Sec
);
87 if (!SectionNames
[SecIndex
].empty())
88 return SectionNames
[SecIndex
];
90 auto NameOrErr
= Obj
.getSectionName(Sec
);
93 StringRef Name
= *NameOrErr
;
94 std::string
&Ret
= SectionNames
[SecIndex
];
96 auto It
= UsedSectionNames
.insert({Name
, 0});
98 Ret
= (Name
+ " [" + Twine(++It
.first
->second
) + "]").str();
104 template <class ELFT
>
106 ELFDumper
<ELFT
>::getUniquedSymbolName(const Elf_Sym
*Sym
, StringRef StrTable
,
107 const Elf_Shdr
*SymTab
) {
108 Expected
<StringRef
> SymbolNameOrErr
= Sym
->getName(StrTable
);
109 if (!SymbolNameOrErr
)
110 return SymbolNameOrErr
;
111 StringRef Name
= *SymbolNameOrErr
;
112 if (Name
.empty() && Sym
->getType() == ELF::STT_SECTION
) {
113 auto ShdrOrErr
= Obj
.getSection(Sym
, SymTab
, ShndxTable
);
115 return ShdrOrErr
.takeError();
116 return getUniquedSectionName(*ShdrOrErr
);
119 // Symbols in .symtab can have duplicate names. For example, it is a common
120 // situation for local symbols in a relocatable object. Here we assign unique
121 // suffixes for such symbols so that we can differentiate them.
122 if (SymTab
->sh_type
== ELF::SHT_SYMTAB
) {
123 unsigned Index
= Sym
- SymTable
.data();
124 if (!SymbolNames
[Index
].empty())
125 return SymbolNames
[Index
];
127 auto It
= UsedSymbolNames
.insert({Name
, 0});
130 (Name
+ " [" + Twine(++It
.first
->second
) + "]").str();
132 SymbolNames
[Index
] = Name
;
133 return SymbolNames
[Index
];
139 template <class ELFT
> Expected
<ELFYAML::Object
*> ELFDumper
<ELFT
>::dump() {
140 auto Y
= std::make_unique
<ELFYAML::Object
>();
142 // Dump header. We do not dump SHEntSize, SHOffset, SHNum and SHStrNdx field.
143 // When not explicitly set, the values are set by yaml2obj automatically
144 // and there is no need to dump them here.
145 Y
->Header
.Class
= ELFYAML::ELF_ELFCLASS(Obj
.getHeader()->getFileClass());
146 Y
->Header
.Data
= ELFYAML::ELF_ELFDATA(Obj
.getHeader()->getDataEncoding());
147 Y
->Header
.OSABI
= Obj
.getHeader()->e_ident
[ELF::EI_OSABI
];
148 Y
->Header
.ABIVersion
= Obj
.getHeader()->e_ident
[ELF::EI_ABIVERSION
];
149 Y
->Header
.Type
= Obj
.getHeader()->e_type
;
150 Y
->Header
.Machine
= Obj
.getHeader()->e_machine
;
151 Y
->Header
.Flags
= Obj
.getHeader()->e_flags
;
152 Y
->Header
.Entry
= Obj
.getHeader()->e_entry
;
155 auto SectionsOrErr
= Obj
.sections();
157 return SectionsOrErr
.takeError();
158 Sections
= *SectionsOrErr
;
159 SectionNames
.resize(Sections
.size());
161 // Dump symbols. We need to do this early because other sections might want
162 // to access the deduplicated symbol names that we also create here.
163 const Elf_Shdr
*SymTab
= nullptr;
164 const Elf_Shdr
*SymTabShndx
= nullptr;
165 const Elf_Shdr
*DynSymTab
= nullptr;
167 for (const Elf_Shdr
&Sec
: Sections
) {
168 if (Sec
.sh_type
== ELF::SHT_SYMTAB
) {
170 } else if (Sec
.sh_type
== ELF::SHT_DYNSYM
) {
172 } else if (Sec
.sh_type
== ELF::SHT_SYMTAB_SHNDX
) {
173 // ABI allows us to have one SHT_SYMTAB_SHNDX for each symbol table.
174 // We only support having the SHT_SYMTAB_SHNDX for SHT_SYMTAB now.
176 return createStringError(obj2yaml_error::not_implemented
,
177 "multiple SHT_SYMTAB_SHNDX sections are not supported");
182 // We need to locate the SHT_SYMTAB_SHNDX section early, because it might be
183 // needed for dumping symbols.
185 if (!SymTab
|| SymTabShndx
->sh_link
!= SymTab
- Sections
.begin())
186 return createStringError(
187 obj2yaml_error::not_implemented
,
188 "only SHT_SYMTAB_SHNDX associated with SHT_SYMTAB are supported");
190 auto TableOrErr
= Obj
.getSHNDXTable(*SymTabShndx
);
192 return TableOrErr
.takeError();
193 ShndxTable
= *TableOrErr
;
196 if (Error E
= dumpSymbols(SymTab
, Y
->Symbols
))
199 if (Error E
= dumpSymbols(DynSymTab
, Y
->DynamicSymbols
))
202 for (const Elf_Shdr
&Sec
: Sections
) {
203 switch (Sec
.sh_type
) {
204 case ELF::SHT_DYNAMIC
: {
205 Expected
<ELFYAML::DynamicSection
*> SecOrErr
= dumpDynamicSection(&Sec
);
207 return SecOrErr
.takeError();
208 Y
->Sections
.emplace_back(*SecOrErr
);
211 case ELF::SHT_STRTAB
:
212 case ELF::SHT_SYMTAB
:
213 case ELF::SHT_DYNSYM
:
214 // Do not dump these sections.
216 case ELF::SHT_SYMTAB_SHNDX
: {
217 Expected
<ELFYAML::SymtabShndxSection
*> SecOrErr
=
218 dumpSymtabShndxSection(&Sec
);
220 return SecOrErr
.takeError();
221 Y
->Sections
.emplace_back(*SecOrErr
);
225 case ELF::SHT_RELA
: {
226 Expected
<ELFYAML::RelocationSection
*> SecOrErr
= dumpRelocSection(&Sec
);
228 return SecOrErr
.takeError();
229 Y
->Sections
.emplace_back(*SecOrErr
);
232 case ELF::SHT_GROUP
: {
233 Expected
<ELFYAML::Group
*> GroupOrErr
= dumpGroup(&Sec
);
235 return GroupOrErr
.takeError();
236 Y
->Sections
.emplace_back(*GroupOrErr
);
239 case ELF::SHT_MIPS_ABIFLAGS
: {
240 Expected
<ELFYAML::MipsABIFlags
*> SecOrErr
= dumpMipsABIFlags(&Sec
);
242 return SecOrErr
.takeError();
243 Y
->Sections
.emplace_back(*SecOrErr
);
246 case ELF::SHT_NOBITS
: {
247 Expected
<ELFYAML::NoBitsSection
*> SecOrErr
= dumpNoBitsSection(&Sec
);
249 return SecOrErr
.takeError();
250 Y
->Sections
.emplace_back(*SecOrErr
);
253 case ELF::SHT_GNU_verdef
: {
254 Expected
<ELFYAML::VerdefSection
*> SecOrErr
= dumpVerdefSection(&Sec
);
256 return SecOrErr
.takeError();
257 Y
->Sections
.emplace_back(*SecOrErr
);
260 case ELF::SHT_GNU_versym
: {
261 Expected
<ELFYAML::SymverSection
*> SecOrErr
= dumpSymverSection(&Sec
);
263 return SecOrErr
.takeError();
264 Y
->Sections
.emplace_back(*SecOrErr
);
267 case ELF::SHT_GNU_verneed
: {
268 Expected
<ELFYAML::VerneedSection
*> SecOrErr
= dumpVerneedSection(&Sec
);
270 return SecOrErr
.takeError();
271 Y
->Sections
.emplace_back(*SecOrErr
);
274 case ELF::SHT_NULL
: {
275 // We only dump the SHT_NULL section at index 0 when it
276 // has at least one non-null field, because yaml2obj
277 // normally creates the zero section at index 0 implicitly.
278 if (&Sec
== &Sections
[0]) {
279 const uint8_t *Begin
= reinterpret_cast<const uint8_t *>(&Sec
);
280 const uint8_t *End
= Begin
+ sizeof(Elf_Shdr
);
281 if (std::find_if(Begin
, End
, [](uint8_t V
) { return V
!= 0; }) == End
)
287 Expected
<ELFYAML::RawContentSection
*> SecOrErr
=
288 dumpContentSection(&Sec
);
290 return SecOrErr
.takeError();
291 Y
->Sections
.emplace_back(*SecOrErr
);
299 template <class ELFT
>
300 Error ELFDumper
<ELFT
>::dumpSymbols(const Elf_Shdr
*Symtab
,
301 std::vector
<ELFYAML::Symbol
> &Symbols
) {
303 return Error::success();
305 auto StrTableOrErr
= Obj
.getStringTableForSymtab(*Symtab
);
307 return StrTableOrErr
.takeError();
308 StringRef StrTable
= *StrTableOrErr
;
310 auto SymtabOrErr
= Obj
.symbols(Symtab
);
312 return SymtabOrErr
.takeError();
314 if (Symtab
->sh_type
== ELF::SHT_SYMTAB
) {
315 SymTable
= *SymtabOrErr
;
316 SymbolNames
.resize(SymTable
.size());
319 for (const auto &Sym
: (*SymtabOrErr
).drop_front()) {
321 if (auto EC
= dumpSymbol(&Sym
, Symtab
, StrTable
, S
))
323 Symbols
.push_back(S
);
326 return Error::success();
329 template <class ELFT
>
330 Error ELFDumper
<ELFT
>::dumpSymbol(const Elf_Sym
*Sym
, const Elf_Shdr
*SymTab
,
331 StringRef StrTable
, ELFYAML::Symbol
&S
) {
332 S
.Type
= Sym
->getType();
333 S
.Value
= Sym
->st_value
;
334 S
.Size
= Sym
->st_size
;
335 S
.Other
= Sym
->st_other
;
336 S
.Binding
= Sym
->getBinding();
338 Expected
<StringRef
> SymbolNameOrErr
=
339 getUniquedSymbolName(Sym
, StrTable
, SymTab
);
340 if (!SymbolNameOrErr
)
341 return SymbolNameOrErr
.takeError();
342 S
.Name
= SymbolNameOrErr
.get();
344 if (Sym
->st_shndx
>= ELF::SHN_LORESERVE
) {
345 S
.Index
= (ELFYAML::ELF_SHN
)Sym
->st_shndx
;
346 return Error::success();
349 auto ShdrOrErr
= Obj
.getSection(Sym
, SymTab
, ShndxTable
);
351 return ShdrOrErr
.takeError();
352 const Elf_Shdr
*Shdr
= *ShdrOrErr
;
354 return Error::success();
356 auto NameOrErr
= getUniquedSectionName(Shdr
);
358 return NameOrErr
.takeError();
359 S
.Section
= NameOrErr
.get();
361 return Error::success();
364 template <class ELFT
>
365 template <class RelT
>
366 Error ELFDumper
<ELFT
>::dumpRelocation(const RelT
*Rel
, const Elf_Shdr
*SymTab
,
367 ELFYAML::Relocation
&R
) {
368 R
.Type
= Rel
->getType(Obj
.isMips64EL());
369 R
.Offset
= Rel
->r_offset
;
372 auto SymOrErr
= Obj
.getRelocationSymbol(Rel
, SymTab
);
374 return SymOrErr
.takeError();
375 const Elf_Sym
*Sym
= *SymOrErr
;
376 auto StrTabSec
= Obj
.getSection(SymTab
->sh_link
);
378 return StrTabSec
.takeError();
379 auto StrTabOrErr
= Obj
.getStringTable(*StrTabSec
);
381 return StrTabOrErr
.takeError();
382 StringRef StrTab
= *StrTabOrErr
;
385 Expected
<StringRef
> NameOrErr
= getUniquedSymbolName(Sym
, StrTab
, SymTab
);
387 return NameOrErr
.takeError();
388 R
.Symbol
= NameOrErr
.get();
390 // We have some edge cases of relocations without a symbol associated,
391 // e.g. an object containing the invalid (according to the System V
392 // ABI) R_X86_64_NONE reloc. Create a symbol with an empty name instead
397 return Error::success();
400 template <class ELFT
>
401 Error ELFDumper
<ELFT
>::dumpCommonSection(const Elf_Shdr
*Shdr
,
402 ELFYAML::Section
&S
) {
403 // Dump fields. We do not dump the ShOffset field. When not explicitly
404 // set, the value is set by yaml2obj automatically.
405 S
.Type
= Shdr
->sh_type
;
407 S
.Flags
= static_cast<ELFYAML::ELF_SHF
>(Shdr
->sh_flags
);
408 S
.Address
= Shdr
->sh_addr
;
409 S
.AddressAlign
= Shdr
->sh_addralign
;
410 if (Shdr
->sh_entsize
)
411 S
.EntSize
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_entsize
);
413 auto NameOrErr
= getUniquedSectionName(Shdr
);
415 return NameOrErr
.takeError();
416 S
.Name
= NameOrErr
.get();
418 if (Shdr
->sh_link
!= ELF::SHN_UNDEF
) {
419 auto LinkSection
= Obj
.getSection(Shdr
->sh_link
);
421 return make_error
<StringError
>(
422 "unable to resolve sh_link reference in section '" + S
.Name
+
423 "': " + toString(LinkSection
.takeError()),
424 inconvertibleErrorCode());
426 NameOrErr
= getUniquedSectionName(*LinkSection
);
428 return NameOrErr
.takeError();
429 S
.Link
= NameOrErr
.get();
432 return Error::success();
435 template <class ELFT
>
436 Error ELFDumper
<ELFT
>::dumpCommonRelocationSection(
437 const Elf_Shdr
*Shdr
, ELFYAML::RelocationSection
&S
) {
438 if (Error E
= dumpCommonSection(Shdr
, S
))
441 auto InfoSection
= Obj
.getSection(Shdr
->sh_info
);
443 return InfoSection
.takeError();
445 auto NameOrErr
= getUniquedSectionName(*InfoSection
);
447 return NameOrErr
.takeError();
448 S
.RelocatableSec
= NameOrErr
.get();
450 return Error::success();
453 template <class ELFT
>
454 Expected
<ELFYAML::DynamicSection
*>
455 ELFDumper
<ELFT
>::dumpDynamicSection(const Elf_Shdr
*Shdr
) {
456 auto S
= std::make_unique
<ELFYAML::DynamicSection
>();
457 if (Error E
= dumpCommonSection(Shdr
, *S
))
460 auto DynTagsOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Dyn
>(Shdr
);
462 return DynTagsOrErr
.takeError();
464 for (const Elf_Dyn
&Dyn
: *DynTagsOrErr
)
465 S
->Entries
.push_back({(ELFYAML::ELF_DYNTAG
)Dyn
.getTag(), Dyn
.getVal()});
470 template <class ELFT
>
471 Expected
<ELFYAML::RelocationSection
*>
472 ELFDumper
<ELFT
>::dumpRelocSection(const Elf_Shdr
*Shdr
) {
473 auto S
= std::make_unique
<ELFYAML::RelocationSection
>();
474 if (auto E
= dumpCommonRelocationSection(Shdr
, *S
))
477 auto SymTabOrErr
= Obj
.getSection(Shdr
->sh_link
);
479 return SymTabOrErr
.takeError();
480 const Elf_Shdr
*SymTab
= *SymTabOrErr
;
482 if (Shdr
->sh_type
== ELF::SHT_REL
) {
483 auto Rels
= Obj
.rels(Shdr
);
485 return Rels
.takeError();
486 for (const Elf_Rel
&Rel
: *Rels
) {
487 ELFYAML::Relocation R
;
488 if (Error E
= dumpRelocation(&Rel
, SymTab
, R
))
490 S
->Relocations
.push_back(R
);
493 auto Rels
= Obj
.relas(Shdr
);
495 return Rels
.takeError();
496 for (const Elf_Rela
&Rel
: *Rels
) {
497 ELFYAML::Relocation R
;
498 if (Error E
= dumpRelocation(&Rel
, SymTab
, R
))
500 R
.Addend
= Rel
.r_addend
;
501 S
->Relocations
.push_back(R
);
508 template <class ELFT
>
509 Expected
<ELFYAML::RawContentSection
*>
510 ELFDumper
<ELFT
>::dumpContentSection(const Elf_Shdr
*Shdr
) {
511 auto S
= std::make_unique
<ELFYAML::RawContentSection
>();
512 if (Error E
= dumpCommonSection(Shdr
, *S
))
515 unsigned SecIndex
= Shdr
- &Sections
[0];
516 if (SecIndex
!= 0 || Shdr
->sh_type
!= ELF::SHT_NULL
) {
517 auto ContentOrErr
= Obj
.getSectionContents(Shdr
);
519 return ContentOrErr
.takeError();
520 ArrayRef
<uint8_t> Content
= *ContentOrErr
;
521 if (!Content
.empty())
522 S
->Content
= yaml::BinaryRef(Content
);
524 S
->Size
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_size
);
528 S
->Info
= static_cast<llvm::yaml::Hex64
>(Shdr
->sh_info
);
532 template <class ELFT
>
533 Expected
<ELFYAML::SymtabShndxSection
*>
534 ELFDumper
<ELFT
>::dumpSymtabShndxSection(const Elf_Shdr
*Shdr
) {
535 auto S
= std::make_unique
<ELFYAML::SymtabShndxSection
>();
536 if (Error E
= dumpCommonSection(Shdr
, *S
))
539 auto EntriesOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Word
>(Shdr
);
541 return EntriesOrErr
.takeError();
542 for (const Elf_Word
&E
: *EntriesOrErr
)
543 S
->Entries
.push_back(E
);
547 template <class ELFT
>
548 Expected
<ELFYAML::NoBitsSection
*>
549 ELFDumper
<ELFT
>::dumpNoBitsSection(const Elf_Shdr
*Shdr
) {
550 auto S
= std::make_unique
<ELFYAML::NoBitsSection
>();
551 if (Error E
= dumpCommonSection(Shdr
, *S
))
553 S
->Size
= Shdr
->sh_size
;
558 template <class ELFT
>
559 Expected
<ELFYAML::VerdefSection
*>
560 ELFDumper
<ELFT
>::dumpVerdefSection(const Elf_Shdr
*Shdr
) {
561 typedef typename
ELFT::Verdef Elf_Verdef
;
562 typedef typename
ELFT::Verdaux Elf_Verdaux
;
564 auto S
= std::make_unique
<ELFYAML::VerdefSection
>();
565 if (Error E
= dumpCommonSection(Shdr
, *S
))
568 S
->Info
= Shdr
->sh_info
;
570 auto StringTableShdrOrErr
= Obj
.getSection(Shdr
->sh_link
);
571 if (!StringTableShdrOrErr
)
572 return StringTableShdrOrErr
.takeError();
574 auto StringTableOrErr
= Obj
.getStringTable(*StringTableShdrOrErr
);
575 if (!StringTableOrErr
)
576 return StringTableOrErr
.takeError();
578 auto Contents
= Obj
.getSectionContents(Shdr
);
580 return Contents
.takeError();
582 llvm::ArrayRef
<uint8_t> Data
= *Contents
;
583 const uint8_t *Buf
= Data
.data();
585 const Elf_Verdef
*Verdef
= reinterpret_cast<const Elf_Verdef
*>(Buf
);
586 ELFYAML::VerdefEntry Entry
;
587 Entry
.Version
= Verdef
->vd_version
;
588 Entry
.Flags
= Verdef
->vd_flags
;
589 Entry
.VersionNdx
= Verdef
->vd_ndx
;
590 Entry
.Hash
= Verdef
->vd_hash
;
592 const uint8_t *BufAux
= Buf
+ Verdef
->vd_aux
;
594 const Elf_Verdaux
*Verdaux
=
595 reinterpret_cast<const Elf_Verdaux
*>(BufAux
);
596 Entry
.VerNames
.push_back(
597 StringTableOrErr
->drop_front(Verdaux
->vda_name
).data());
598 BufAux
= Verdaux
->vda_next
? BufAux
+ Verdaux
->vda_next
: nullptr;
601 S
->Entries
.push_back(Entry
);
602 Buf
= Verdef
->vd_next
? Buf
+ Verdef
->vd_next
: nullptr;
608 template <class ELFT
>
609 Expected
<ELFYAML::SymverSection
*>
610 ELFDumper
<ELFT
>::dumpSymverSection(const Elf_Shdr
*Shdr
) {
611 typedef typename
ELFT::Half Elf_Half
;
613 auto S
= std::make_unique
<ELFYAML::SymverSection
>();
614 if (Error E
= dumpCommonSection(Shdr
, *S
))
617 auto VersionsOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Half
>(Shdr
);
619 return VersionsOrErr
.takeError();
620 for (const Elf_Half
&E
: *VersionsOrErr
)
621 S
->Entries
.push_back(E
);
626 template <class ELFT
>
627 Expected
<ELFYAML::VerneedSection
*>
628 ELFDumper
<ELFT
>::dumpVerneedSection(const Elf_Shdr
*Shdr
) {
629 typedef typename
ELFT::Verneed Elf_Verneed
;
630 typedef typename
ELFT::Vernaux Elf_Vernaux
;
632 auto S
= std::make_unique
<ELFYAML::VerneedSection
>();
633 if (Error E
= dumpCommonSection(Shdr
, *S
))
636 S
->Info
= Shdr
->sh_info
;
638 auto Contents
= Obj
.getSectionContents(Shdr
);
640 return Contents
.takeError();
642 auto StringTableShdrOrErr
= Obj
.getSection(Shdr
->sh_link
);
643 if (!StringTableShdrOrErr
)
644 return StringTableShdrOrErr
.takeError();
646 auto StringTableOrErr
= Obj
.getStringTable(*StringTableShdrOrErr
);
647 if (!StringTableOrErr
)
648 return StringTableOrErr
.takeError();
650 llvm::ArrayRef
<uint8_t> Data
= *Contents
;
651 const uint8_t *Buf
= Data
.data();
653 const Elf_Verneed
*Verneed
= reinterpret_cast<const Elf_Verneed
*>(Buf
);
655 ELFYAML::VerneedEntry Entry
;
656 Entry
.Version
= Verneed
->vn_version
;
658 StringRef(StringTableOrErr
->drop_front(Verneed
->vn_file
).data());
660 const uint8_t *BufAux
= Buf
+ Verneed
->vn_aux
;
662 const Elf_Vernaux
*Vernaux
=
663 reinterpret_cast<const Elf_Vernaux
*>(BufAux
);
665 ELFYAML::VernauxEntry Aux
;
666 Aux
.Hash
= Vernaux
->vna_hash
;
667 Aux
.Flags
= Vernaux
->vna_flags
;
668 Aux
.Other
= Vernaux
->vna_other
;
670 StringRef(StringTableOrErr
->drop_front(Vernaux
->vna_name
).data());
672 Entry
.AuxV
.push_back(Aux
);
673 BufAux
= Vernaux
->vna_next
? BufAux
+ Vernaux
->vna_next
: nullptr;
676 S
->VerneedV
.push_back(Entry
);
677 Buf
= Verneed
->vn_next
? Buf
+ Verneed
->vn_next
: nullptr;
683 template <class ELFT
>
684 Expected
<ELFYAML::Group
*> ELFDumper
<ELFT
>::dumpGroup(const Elf_Shdr
*Shdr
) {
685 auto S
= std::make_unique
<ELFYAML::Group
>();
686 if (Error E
= dumpCommonSection(Shdr
, *S
))
689 auto SymtabOrErr
= Obj
.getSection(Shdr
->sh_link
);
691 return SymtabOrErr
.takeError();
692 // Get symbol with index sh_info which name is the signature of the group.
693 const Elf_Shdr
*Symtab
= *SymtabOrErr
;
694 auto SymOrErr
= Obj
.getSymbol(Symtab
, Shdr
->sh_info
);
696 return SymOrErr
.takeError();
697 auto StrTabOrErr
= Obj
.getStringTableForSymtab(*Symtab
);
699 return StrTabOrErr
.takeError();
701 Expected
<StringRef
> SymbolName
=
702 getUniquedSymbolName(*SymOrErr
, *StrTabOrErr
, Symtab
);
704 return SymbolName
.takeError();
705 S
->Signature
= *SymbolName
;
707 auto MembersOrErr
= Obj
.template getSectionContentsAsArray
<Elf_Word
>(Shdr
);
709 return MembersOrErr
.takeError();
711 for (Elf_Word Member
: *MembersOrErr
) {
712 if (Member
== llvm::ELF::GRP_COMDAT
) {
713 S
->Members
.push_back({"GRP_COMDAT"});
717 auto SHdrOrErr
= Obj
.getSection(Member
);
719 return SHdrOrErr
.takeError();
720 auto NameOrErr
= getUniquedSectionName(*SHdrOrErr
);
722 return NameOrErr
.takeError();
723 S
->Members
.push_back({*NameOrErr
});
728 template <class ELFT
>
729 Expected
<ELFYAML::MipsABIFlags
*>
730 ELFDumper
<ELFT
>::dumpMipsABIFlags(const Elf_Shdr
*Shdr
) {
731 assert(Shdr
->sh_type
== ELF::SHT_MIPS_ABIFLAGS
&&
732 "Section type is not SHT_MIPS_ABIFLAGS");
733 auto S
= std::make_unique
<ELFYAML::MipsABIFlags
>();
734 if (Error E
= dumpCommonSection(Shdr
, *S
))
737 auto ContentOrErr
= Obj
.getSectionContents(Shdr
);
739 return ContentOrErr
.takeError();
741 auto *Flags
= reinterpret_cast<const object::Elf_Mips_ABIFlags
<ELFT
> *>(
742 ContentOrErr
.get().data());
743 S
->Version
= Flags
->version
;
744 S
->ISALevel
= Flags
->isa_level
;
745 S
->ISARevision
= Flags
->isa_rev
;
746 S
->GPRSize
= Flags
->gpr_size
;
747 S
->CPR1Size
= Flags
->cpr1_size
;
748 S
->CPR2Size
= Flags
->cpr2_size
;
749 S
->FpABI
= Flags
->fp_abi
;
750 S
->ISAExtension
= Flags
->isa_ext
;
751 S
->ASEs
= Flags
->ases
;
752 S
->Flags1
= Flags
->flags1
;
753 S
->Flags2
= Flags
->flags2
;
757 template <class ELFT
>
758 static Error
elf2yaml(raw_ostream
&Out
, const object::ELFFile
<ELFT
> &Obj
) {
759 ELFDumper
<ELFT
> Dumper(Obj
);
760 Expected
<ELFYAML::Object
*> YAMLOrErr
= Dumper
.dump();
762 return YAMLOrErr
.takeError();
764 std::unique_ptr
<ELFYAML::Object
> YAML(YAMLOrErr
.get());
765 yaml::Output
Yout(Out
);
768 return Error::success();
771 Error
elf2yaml(raw_ostream
&Out
, const object::ObjectFile
&Obj
) {
772 if (const auto *ELFObj
= dyn_cast
<object::ELF32LEObjectFile
>(&Obj
))
773 return elf2yaml(Out
, *ELFObj
->getELFFile());
775 if (const auto *ELFObj
= dyn_cast
<object::ELF32BEObjectFile
>(&Obj
))
776 return elf2yaml(Out
, *ELFObj
->getELFFile());
778 if (const auto *ELFObj
= dyn_cast
<object::ELF64LEObjectFile
>(&Obj
))
779 return elf2yaml(Out
, *ELFObj
->getELFFile());
781 if (const auto *ELFObj
= dyn_cast
<object::ELF64BEObjectFile
>(&Obj
))
782 return elf2yaml(Out
, *ELFObj
->getELFFile());
784 llvm_unreachable("unknown ELF file format");