[yaml2obj/obj2yaml] - Add support for SHT_HASH sections.
[llvm-complete.git] / tools / obj2yaml / elf2yaml.cpp
blobb70a5dd078424275a301ee87bd09335f08530e51
1 //===------ utils/elf2yaml.cpp - obj2yaml conversion tool -------*- C++ -*-===//
2 //
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
6 //
7 //===----------------------------------------------------------------------===//
9 #include "Error.h"
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/DataExtractor.h"
15 #include "llvm/Support/ErrorHandling.h"
16 #include "llvm/Support/YAMLTraits.h"
18 using namespace llvm;
20 namespace {
22 template <class ELFT>
23 class ELFDumper {
24 typedef object::Elf_Sym_Impl<ELFT> Elf_Sym;
25 typedef typename ELFT::Dyn Elf_Dyn;
26 typedef typename ELFT::Shdr Elf_Shdr;
27 typedef typename ELFT::Word Elf_Word;
28 typedef typename ELFT::Rel Elf_Rel;
29 typedef typename ELFT::Rela Elf_Rela;
31 ArrayRef<Elf_Shdr> Sections;
32 ArrayRef<Elf_Sym> SymTable;
34 DenseMap<StringRef, uint32_t> UsedSectionNames;
35 std::vector<std::string> SectionNames;
37 DenseMap<StringRef, uint32_t> UsedSymbolNames;
38 std::vector<std::string> SymbolNames;
40 Expected<StringRef> getUniquedSectionName(const Elf_Shdr *Sec);
41 Expected<StringRef> getUniquedSymbolName(const Elf_Sym *Sym,
42 StringRef StrTable,
43 const Elf_Shdr *SymTab);
45 const object::ELFFile<ELFT> &Obj;
46 ArrayRef<Elf_Word> ShndxTable;
48 Error dumpSymbols(const Elf_Shdr *Symtab,
49 std::vector<ELFYAML::Symbol> &Symbols);
50 Error dumpSymbol(const Elf_Sym *Sym, const Elf_Shdr *SymTab,
51 StringRef StrTable, ELFYAML::Symbol &S);
52 Error dumpCommonSection(const Elf_Shdr *Shdr, ELFYAML::Section &S);
53 Error dumpCommonRelocationSection(const Elf_Shdr *Shdr,
54 ELFYAML::RelocationSection &S);
55 template <class RelT>
56 Error dumpRelocation(const RelT *Rel, const Elf_Shdr *SymTab,
57 ELFYAML::Relocation &R);
59 Expected<ELFYAML::DynamicSection *> dumpDynamicSection(const Elf_Shdr *Shdr);
60 Expected<ELFYAML::RelocationSection *> dumpRelocSection(const Elf_Shdr *Shdr);
61 Expected<ELFYAML::RawContentSection *>
62 dumpContentSection(const Elf_Shdr *Shdr);
63 Expected<ELFYAML::SymtabShndxSection *>
64 dumpSymtabShndxSection(const Elf_Shdr *Shdr);
65 Expected<ELFYAML::NoBitsSection *> dumpNoBitsSection(const Elf_Shdr *Shdr);
66 Expected<ELFYAML::HashSection *> dumpHashSection(const Elf_Shdr *Shdr);
67 Expected<ELFYAML::VerdefSection *> dumpVerdefSection(const Elf_Shdr *Shdr);
68 Expected<ELFYAML::SymverSection *> dumpSymverSection(const Elf_Shdr *Shdr);
69 Expected<ELFYAML::VerneedSection *> dumpVerneedSection(const Elf_Shdr *Shdr);
70 Expected<ELFYAML::Group *> dumpGroup(const Elf_Shdr *Shdr);
71 Expected<ELFYAML::MipsABIFlags *> dumpMipsABIFlags(const Elf_Shdr *Shdr);
72 Expected<ELFYAML::StackSizesSection *>
73 dumpStackSizesSection(const Elf_Shdr *Shdr);
75 Expected<ELFYAML::Section *> dumpSpecialSection(const Elf_Shdr *Shdr);
77 public:
78 ELFDumper(const object::ELFFile<ELFT> &O);
79 Expected<ELFYAML::Object *> dump();
84 template <class ELFT>
85 ELFDumper<ELFT>::ELFDumper(const object::ELFFile<ELFT> &O)
86 : Obj(O) {}
88 template <class ELFT>
89 Expected<StringRef>
90 ELFDumper<ELFT>::getUniquedSectionName(const Elf_Shdr *Sec) {
91 unsigned SecIndex = Sec - &Sections[0];
92 assert(&Sections[SecIndex] == Sec);
93 if (!SectionNames[SecIndex].empty())
94 return SectionNames[SecIndex];
96 auto NameOrErr = Obj.getSectionName(Sec);
97 if (!NameOrErr)
98 return NameOrErr;
99 StringRef Name = *NameOrErr;
100 std::string &Ret = SectionNames[SecIndex];
102 auto It = UsedSectionNames.insert({Name, 0});
103 if (!It.second)
104 Ret = (Name + " [" + Twine(++It.first->second) + "]").str();
105 else
106 Ret = Name;
107 return Ret;
110 template <class ELFT>
111 Expected<StringRef>
112 ELFDumper<ELFT>::getUniquedSymbolName(const Elf_Sym *Sym, StringRef StrTable,
113 const Elf_Shdr *SymTab) {
114 Expected<StringRef> SymbolNameOrErr = Sym->getName(StrTable);
115 if (!SymbolNameOrErr)
116 return SymbolNameOrErr;
117 StringRef Name = *SymbolNameOrErr;
118 if (Name.empty() && Sym->getType() == ELF::STT_SECTION) {
119 auto ShdrOrErr = Obj.getSection(Sym, SymTab, ShndxTable);
120 if (!ShdrOrErr)
121 return ShdrOrErr.takeError();
122 return getUniquedSectionName(*ShdrOrErr);
125 // Symbols in .symtab can have duplicate names. For example, it is a common
126 // situation for local symbols in a relocatable object. Here we assign unique
127 // suffixes for such symbols so that we can differentiate them.
128 if (SymTab->sh_type == ELF::SHT_SYMTAB) {
129 unsigned Index = Sym - SymTable.data();
130 if (!SymbolNames[Index].empty())
131 return SymbolNames[Index];
133 auto It = UsedSymbolNames.insert({Name, 0});
134 if (!It.second)
135 SymbolNames[Index] =
136 (Name + " [" + Twine(++It.first->second) + "]").str();
137 else
138 SymbolNames[Index] = Name;
139 return SymbolNames[Index];
142 return Name;
145 template <class ELFT> Expected<ELFYAML::Object *> ELFDumper<ELFT>::dump() {
146 auto Y = std::make_unique<ELFYAML::Object>();
148 // Dump header. We do not dump SHEntSize, SHOff, SHNum and SHStrNdx fields.
149 // When not explicitly set, the values are set by yaml2obj automatically
150 // and there is no need to dump them here.
151 Y->Header.Class = ELFYAML::ELF_ELFCLASS(Obj.getHeader()->getFileClass());
152 Y->Header.Data = ELFYAML::ELF_ELFDATA(Obj.getHeader()->getDataEncoding());
153 Y->Header.OSABI = Obj.getHeader()->e_ident[ELF::EI_OSABI];
154 Y->Header.ABIVersion = Obj.getHeader()->e_ident[ELF::EI_ABIVERSION];
155 Y->Header.Type = Obj.getHeader()->e_type;
156 Y->Header.Machine = Obj.getHeader()->e_machine;
157 Y->Header.Flags = Obj.getHeader()->e_flags;
158 Y->Header.Entry = Obj.getHeader()->e_entry;
160 // Dump sections
161 auto SectionsOrErr = Obj.sections();
162 if (!SectionsOrErr)
163 return SectionsOrErr.takeError();
164 Sections = *SectionsOrErr;
165 SectionNames.resize(Sections.size());
167 // Dump symbols. We need to do this early because other sections might want
168 // to access the deduplicated symbol names that we also create here.
169 const Elf_Shdr *SymTab = nullptr;
170 const Elf_Shdr *SymTabShndx = nullptr;
171 const Elf_Shdr *DynSymTab = nullptr;
173 for (const Elf_Shdr &Sec : Sections) {
174 if (Sec.sh_type == ELF::SHT_SYMTAB) {
175 SymTab = &Sec;
176 } else if (Sec.sh_type == ELF::SHT_DYNSYM) {
177 DynSymTab = &Sec;
178 } else if (Sec.sh_type == ELF::SHT_SYMTAB_SHNDX) {
179 // ABI allows us to have one SHT_SYMTAB_SHNDX for each symbol table.
180 // We only support having the SHT_SYMTAB_SHNDX for SHT_SYMTAB now.
181 if (SymTabShndx)
182 return createStringError(obj2yaml_error::not_implemented,
183 "multiple SHT_SYMTAB_SHNDX sections are not supported");
184 SymTabShndx = &Sec;
188 // We need to locate the SHT_SYMTAB_SHNDX section early, because it might be
189 // needed for dumping symbols.
190 if (SymTabShndx) {
191 if (!SymTab || SymTabShndx->sh_link != SymTab - Sections.begin())
192 return createStringError(
193 obj2yaml_error::not_implemented,
194 "only SHT_SYMTAB_SHNDX associated with SHT_SYMTAB are supported");
196 auto TableOrErr = Obj.getSHNDXTable(*SymTabShndx);
197 if (!TableOrErr)
198 return TableOrErr.takeError();
199 ShndxTable = *TableOrErr;
201 if (SymTab)
202 if (Error E = dumpSymbols(SymTab, Y->Symbols))
203 return std::move(E);
204 if (DynSymTab)
205 if (Error E = dumpSymbols(DynSymTab, Y->DynamicSymbols))
206 return std::move(E);
208 for (const Elf_Shdr &Sec : Sections) {
209 switch (Sec.sh_type) {
210 case ELF::SHT_DYNAMIC: {
211 Expected<ELFYAML::DynamicSection *> SecOrErr = dumpDynamicSection(&Sec);
212 if (!SecOrErr)
213 return SecOrErr.takeError();
214 Y->Sections.emplace_back(*SecOrErr);
215 break;
217 case ELF::SHT_STRTAB:
218 case ELF::SHT_SYMTAB:
219 case ELF::SHT_DYNSYM:
220 // Do not dump these sections.
221 break;
222 case ELF::SHT_SYMTAB_SHNDX: {
223 Expected<ELFYAML::SymtabShndxSection *> SecOrErr =
224 dumpSymtabShndxSection(&Sec);
225 if (!SecOrErr)
226 return SecOrErr.takeError();
227 Y->Sections.emplace_back(*SecOrErr);
228 break;
230 case ELF::SHT_REL:
231 case ELF::SHT_RELA: {
232 Expected<ELFYAML::RelocationSection *> SecOrErr = dumpRelocSection(&Sec);
233 if (!SecOrErr)
234 return SecOrErr.takeError();
235 Y->Sections.emplace_back(*SecOrErr);
236 break;
238 case ELF::SHT_GROUP: {
239 Expected<ELFYAML::Group *> GroupOrErr = dumpGroup(&Sec);
240 if (!GroupOrErr)
241 return GroupOrErr.takeError();
242 Y->Sections.emplace_back(*GroupOrErr);
243 break;
245 case ELF::SHT_MIPS_ABIFLAGS: {
246 Expected<ELFYAML::MipsABIFlags *> SecOrErr = dumpMipsABIFlags(&Sec);
247 if (!SecOrErr)
248 return SecOrErr.takeError();
249 Y->Sections.emplace_back(*SecOrErr);
250 break;
252 case ELF::SHT_NOBITS: {
253 Expected<ELFYAML::NoBitsSection *> SecOrErr = dumpNoBitsSection(&Sec);
254 if (!SecOrErr)
255 return SecOrErr.takeError();
256 Y->Sections.emplace_back(*SecOrErr);
257 break;
259 case ELF::SHT_HASH: {
260 Expected<ELFYAML::HashSection *> SecOrErr = dumpHashSection(&Sec);
261 if (!SecOrErr)
262 return SecOrErr.takeError();
263 Y->Sections.emplace_back(*SecOrErr);
264 break;
266 case ELF::SHT_GNU_verdef: {
267 Expected<ELFYAML::VerdefSection *> SecOrErr = dumpVerdefSection(&Sec);
268 if (!SecOrErr)
269 return SecOrErr.takeError();
270 Y->Sections.emplace_back(*SecOrErr);
271 break;
273 case ELF::SHT_GNU_versym: {
274 Expected<ELFYAML::SymverSection *> SecOrErr = dumpSymverSection(&Sec);
275 if (!SecOrErr)
276 return SecOrErr.takeError();
277 Y->Sections.emplace_back(*SecOrErr);
278 break;
280 case ELF::SHT_GNU_verneed: {
281 Expected<ELFYAML::VerneedSection *> SecOrErr = dumpVerneedSection(&Sec);
282 if (!SecOrErr)
283 return SecOrErr.takeError();
284 Y->Sections.emplace_back(*SecOrErr);
285 break;
287 case ELF::SHT_NULL: {
288 // We only dump the SHT_NULL section at index 0 when it
289 // has at least one non-null field, because yaml2obj
290 // normally creates the zero section at index 0 implicitly.
291 if (&Sec == &Sections[0]) {
292 const uint8_t *Begin = reinterpret_cast<const uint8_t *>(&Sec);
293 const uint8_t *End = Begin + sizeof(Elf_Shdr);
294 if (std::find_if(Begin, End, [](uint8_t V) { return V != 0; }) == End)
295 break;
297 LLVM_FALLTHROUGH;
299 default: {
300 // Recognize some special SHT_PROGBITS sections by name.
301 if (Sec.sh_type == ELF::SHT_PROGBITS) {
302 Expected<ELFYAML::Section *> SpecialSecOrErr = dumpSpecialSection(&Sec);
303 if (!SpecialSecOrErr)
304 return SpecialSecOrErr.takeError();
305 if (*SpecialSecOrErr) {
306 Y->Sections.emplace_back(*SpecialSecOrErr);
307 break;
311 Expected<ELFYAML::RawContentSection *> SecOrErr =
312 dumpContentSection(&Sec);
313 if (!SecOrErr)
314 return SecOrErr.takeError();
315 Y->Sections.emplace_back(*SecOrErr);
320 return Y.release();
323 template <class ELFT>
324 Error ELFDumper<ELFT>::dumpSymbols(const Elf_Shdr *Symtab,
325 std::vector<ELFYAML::Symbol> &Symbols) {
326 if (!Symtab)
327 return Error::success();
329 auto StrTableOrErr = Obj.getStringTableForSymtab(*Symtab);
330 if (!StrTableOrErr)
331 return StrTableOrErr.takeError();
332 StringRef StrTable = *StrTableOrErr;
334 auto SymtabOrErr = Obj.symbols(Symtab);
335 if (!SymtabOrErr)
336 return SymtabOrErr.takeError();
338 if (Symtab->sh_type == ELF::SHT_SYMTAB) {
339 SymTable = *SymtabOrErr;
340 SymbolNames.resize(SymTable.size());
343 for (const auto &Sym : (*SymtabOrErr).drop_front()) {
344 ELFYAML::Symbol S;
345 if (auto EC = dumpSymbol(&Sym, Symtab, StrTable, S))
346 return EC;
347 Symbols.push_back(S);
350 return Error::success();
353 template <class ELFT>
354 Error ELFDumper<ELFT>::dumpSymbol(const Elf_Sym *Sym, const Elf_Shdr *SymTab,
355 StringRef StrTable, ELFYAML::Symbol &S) {
356 S.Type = Sym->getType();
357 S.Value = Sym->st_value;
358 S.Size = Sym->st_size;
359 S.Other = Sym->st_other;
360 S.Binding = Sym->getBinding();
362 Expected<StringRef> SymbolNameOrErr =
363 getUniquedSymbolName(Sym, StrTable, SymTab);
364 if (!SymbolNameOrErr)
365 return SymbolNameOrErr.takeError();
366 S.Name = SymbolNameOrErr.get();
368 if (Sym->st_shndx >= ELF::SHN_LORESERVE) {
369 S.Index = (ELFYAML::ELF_SHN)Sym->st_shndx;
370 return Error::success();
373 auto ShdrOrErr = Obj.getSection(Sym, SymTab, ShndxTable);
374 if (!ShdrOrErr)
375 return ShdrOrErr.takeError();
376 const Elf_Shdr *Shdr = *ShdrOrErr;
377 if (!Shdr)
378 return Error::success();
380 auto NameOrErr = getUniquedSectionName(Shdr);
381 if (!NameOrErr)
382 return NameOrErr.takeError();
383 S.Section = NameOrErr.get();
385 return Error::success();
388 template <class ELFT>
389 template <class RelT>
390 Error ELFDumper<ELFT>::dumpRelocation(const RelT *Rel, const Elf_Shdr *SymTab,
391 ELFYAML::Relocation &R) {
392 R.Type = Rel->getType(Obj.isMips64EL());
393 R.Offset = Rel->r_offset;
394 R.Addend = 0;
396 auto SymOrErr = Obj.getRelocationSymbol(Rel, SymTab);
397 if (!SymOrErr)
398 return SymOrErr.takeError();
399 const Elf_Sym *Sym = *SymOrErr;
400 auto StrTabSec = Obj.getSection(SymTab->sh_link);
401 if (!StrTabSec)
402 return StrTabSec.takeError();
403 auto StrTabOrErr = Obj.getStringTable(*StrTabSec);
404 if (!StrTabOrErr)
405 return StrTabOrErr.takeError();
406 StringRef StrTab = *StrTabOrErr;
408 if (Sym) {
409 Expected<StringRef> NameOrErr = getUniquedSymbolName(Sym, StrTab, SymTab);
410 if (!NameOrErr)
411 return NameOrErr.takeError();
412 R.Symbol = NameOrErr.get();
413 } else {
414 // We have some edge cases of relocations without a symbol associated,
415 // e.g. an object containing the invalid (according to the System V
416 // ABI) R_X86_64_NONE reloc. Create a symbol with an empty name instead
417 // of crashing.
418 R.Symbol = "";
421 return Error::success();
424 template <class ELFT>
425 Error ELFDumper<ELFT>::dumpCommonSection(const Elf_Shdr *Shdr,
426 ELFYAML::Section &S) {
427 // Dump fields. We do not dump the ShOffset field. When not explicitly
428 // set, the value is set by yaml2obj automatically.
429 S.Type = Shdr->sh_type;
430 if (Shdr->sh_flags)
431 S.Flags = static_cast<ELFYAML::ELF_SHF>(Shdr->sh_flags);
432 S.Address = Shdr->sh_addr;
433 S.AddressAlign = Shdr->sh_addralign;
434 if (Shdr->sh_entsize)
435 S.EntSize = static_cast<llvm::yaml::Hex64>(Shdr->sh_entsize);
437 auto NameOrErr = getUniquedSectionName(Shdr);
438 if (!NameOrErr)
439 return NameOrErr.takeError();
440 S.Name = NameOrErr.get();
442 if (Shdr->sh_link != ELF::SHN_UNDEF) {
443 auto LinkSection = Obj.getSection(Shdr->sh_link);
444 if (!LinkSection)
445 return make_error<StringError>(
446 "unable to resolve sh_link reference in section '" + S.Name +
447 "': " + toString(LinkSection.takeError()),
448 inconvertibleErrorCode());
450 NameOrErr = getUniquedSectionName(*LinkSection);
451 if (!NameOrErr)
452 return NameOrErr.takeError();
453 S.Link = NameOrErr.get();
456 return Error::success();
459 template <class ELFT>
460 Expected<ELFYAML::Section *>
461 ELFDumper<ELFT>::dumpSpecialSection(const Elf_Shdr *Shdr) {
462 auto NameOrErr = getUniquedSectionName(Shdr);
463 if (!NameOrErr)
464 return NameOrErr.takeError();
466 if (ELFYAML::StackSizesSection::nameMatches(*NameOrErr))
467 return dumpStackSizesSection(Shdr);
468 return nullptr;
471 template <class ELFT>
472 Error ELFDumper<ELFT>::dumpCommonRelocationSection(
473 const Elf_Shdr *Shdr, ELFYAML::RelocationSection &S) {
474 if (Error E = dumpCommonSection(Shdr, S))
475 return E;
477 auto InfoSection = Obj.getSection(Shdr->sh_info);
478 if (!InfoSection)
479 return InfoSection.takeError();
481 auto NameOrErr = getUniquedSectionName(*InfoSection);
482 if (!NameOrErr)
483 return NameOrErr.takeError();
484 S.RelocatableSec = NameOrErr.get();
486 return Error::success();
489 template <class ELFT>
490 Expected<ELFYAML::StackSizesSection *>
491 ELFDumper<ELFT>::dumpStackSizesSection(const Elf_Shdr *Shdr) {
492 auto S = std::make_unique<ELFYAML::StackSizesSection>();
493 if (Error E = dumpCommonSection(Shdr, *S))
494 return std::move(E);
496 auto ContentOrErr = Obj.getSectionContents(Shdr);
497 if (!ContentOrErr)
498 return ContentOrErr.takeError();
500 ArrayRef<uint8_t> Content = *ContentOrErr;
501 DataExtractor Data(Content, Obj.isLE(), ELFT::Is64Bits ? 8 : 4);
503 std::vector<ELFYAML::StackSizeEntry> Entries;
504 DataExtractor::Cursor Cur(0);
505 while (Cur && Cur.tell() < Content.size()) {
506 uint64_t Address = Data.getAddress(Cur);
507 uint64_t Size = Data.getULEB128(Cur);
508 Entries.push_back({Address, Size});
511 if (Content.empty() || !Cur) {
512 // If .stack_sizes cannot be decoded, we dump it as an array of bytes.
513 consumeError(Cur.takeError());
514 S->Content = yaml::BinaryRef(Content);
515 } else {
516 S->Entries = std::move(Entries);
519 return S.release();
522 template <class ELFT>
523 Expected<ELFYAML::DynamicSection *>
524 ELFDumper<ELFT>::dumpDynamicSection(const Elf_Shdr *Shdr) {
525 auto S = std::make_unique<ELFYAML::DynamicSection>();
526 if (Error E = dumpCommonSection(Shdr, *S))
527 return std::move(E);
529 auto DynTagsOrErr = Obj.template getSectionContentsAsArray<Elf_Dyn>(Shdr);
530 if (!DynTagsOrErr)
531 return DynTagsOrErr.takeError();
533 for (const Elf_Dyn &Dyn : *DynTagsOrErr)
534 S->Entries.push_back({(ELFYAML::ELF_DYNTAG)Dyn.getTag(), Dyn.getVal()});
536 return S.release();
539 template <class ELFT>
540 Expected<ELFYAML::RelocationSection *>
541 ELFDumper<ELFT>::dumpRelocSection(const Elf_Shdr *Shdr) {
542 auto S = std::make_unique<ELFYAML::RelocationSection>();
543 if (auto E = dumpCommonRelocationSection(Shdr, *S))
544 return std::move(E);
546 auto SymTabOrErr = Obj.getSection(Shdr->sh_link);
547 if (!SymTabOrErr)
548 return SymTabOrErr.takeError();
549 const Elf_Shdr *SymTab = *SymTabOrErr;
551 if (Shdr->sh_type == ELF::SHT_REL) {
552 auto Rels = Obj.rels(Shdr);
553 if (!Rels)
554 return Rels.takeError();
555 for (const Elf_Rel &Rel : *Rels) {
556 ELFYAML::Relocation R;
557 if (Error E = dumpRelocation(&Rel, SymTab, R))
558 return std::move(E);
559 S->Relocations.push_back(R);
561 } else {
562 auto Rels = Obj.relas(Shdr);
563 if (!Rels)
564 return Rels.takeError();
565 for (const Elf_Rela &Rel : *Rels) {
566 ELFYAML::Relocation R;
567 if (Error E = dumpRelocation(&Rel, SymTab, R))
568 return std::move(E);
569 R.Addend = Rel.r_addend;
570 S->Relocations.push_back(R);
574 return S.release();
577 template <class ELFT>
578 Expected<ELFYAML::RawContentSection *>
579 ELFDumper<ELFT>::dumpContentSection(const Elf_Shdr *Shdr) {
580 auto S = std::make_unique<ELFYAML::RawContentSection>();
581 if (Error E = dumpCommonSection(Shdr, *S))
582 return std::move(E);
584 unsigned SecIndex = Shdr - &Sections[0];
585 if (SecIndex != 0 || Shdr->sh_type != ELF::SHT_NULL) {
586 auto ContentOrErr = Obj.getSectionContents(Shdr);
587 if (!ContentOrErr)
588 return ContentOrErr.takeError();
589 ArrayRef<uint8_t> Content = *ContentOrErr;
590 if (!Content.empty())
591 S->Content = yaml::BinaryRef(Content);
592 } else {
593 S->Size = static_cast<llvm::yaml::Hex64>(Shdr->sh_size);
596 if (Shdr->sh_info)
597 S->Info = static_cast<llvm::yaml::Hex64>(Shdr->sh_info);
598 return S.release();
601 template <class ELFT>
602 Expected<ELFYAML::SymtabShndxSection *>
603 ELFDumper<ELFT>::dumpSymtabShndxSection(const Elf_Shdr *Shdr) {
604 auto S = std::make_unique<ELFYAML::SymtabShndxSection>();
605 if (Error E = dumpCommonSection(Shdr, *S))
606 return std::move(E);
608 auto EntriesOrErr = Obj.template getSectionContentsAsArray<Elf_Word>(Shdr);
609 if (!EntriesOrErr)
610 return EntriesOrErr.takeError();
611 for (const Elf_Word &E : *EntriesOrErr)
612 S->Entries.push_back(E);
613 return S.release();
616 template <class ELFT>
617 Expected<ELFYAML::NoBitsSection *>
618 ELFDumper<ELFT>::dumpNoBitsSection(const Elf_Shdr *Shdr) {
619 auto S = std::make_unique<ELFYAML::NoBitsSection>();
620 if (Error E = dumpCommonSection(Shdr, *S))
621 return std::move(E);
622 S->Size = Shdr->sh_size;
624 return S.release();
627 template <class ELFT>
628 Expected<ELFYAML::HashSection *>
629 ELFDumper<ELFT>::dumpHashSection(const Elf_Shdr *Shdr) {
630 auto S = std::make_unique<ELFYAML::HashSection>();
631 if (Error E = dumpCommonSection(Shdr, *S))
632 return std::move(E);
634 auto ContentOrErr = Obj.getSectionContents(Shdr);
635 if (!ContentOrErr)
636 return ContentOrErr.takeError();
638 ArrayRef<uint8_t> Content = *ContentOrErr;
639 if (Content.size() % 4 != 0 || Content.size() < 8) {
640 S->Content = yaml::BinaryRef(Content);
641 return S.release();
644 DataExtractor::Cursor Cur(0);
645 DataExtractor Data(Content, Obj.isLE(), /*AddressSize=*/0);
646 uint32_t NBucket = Data.getU32(Cur);
647 uint32_t NChain = Data.getU32(Cur);
648 if (Content.size() != (2 + NBucket + NChain) * 4) {
649 S->Content = yaml::BinaryRef(Content);
650 return S.release();
653 S->Bucket.emplace(NBucket);
654 for (uint32_t &V : *S->Bucket)
655 V = Data.getU32(Cur);
657 S->Chain.emplace(NChain);
658 for (uint32_t &V : *S->Chain)
659 V = Data.getU32(Cur);
661 if (!Cur)
662 llvm_unreachable("entries were not read correctly");
663 return S.release();
666 template <class ELFT>
667 Expected<ELFYAML::VerdefSection *>
668 ELFDumper<ELFT>::dumpVerdefSection(const Elf_Shdr *Shdr) {
669 typedef typename ELFT::Verdef Elf_Verdef;
670 typedef typename ELFT::Verdaux Elf_Verdaux;
672 auto S = std::make_unique<ELFYAML::VerdefSection>();
673 if (Error E = dumpCommonSection(Shdr, *S))
674 return std::move(E);
676 S->Info = Shdr->sh_info;
678 auto StringTableShdrOrErr = Obj.getSection(Shdr->sh_link);
679 if (!StringTableShdrOrErr)
680 return StringTableShdrOrErr.takeError();
682 auto StringTableOrErr = Obj.getStringTable(*StringTableShdrOrErr);
683 if (!StringTableOrErr)
684 return StringTableOrErr.takeError();
686 auto Contents = Obj.getSectionContents(Shdr);
687 if (!Contents)
688 return Contents.takeError();
690 llvm::ArrayRef<uint8_t> Data = *Contents;
691 const uint8_t *Buf = Data.data();
692 while (Buf) {
693 const Elf_Verdef *Verdef = reinterpret_cast<const Elf_Verdef *>(Buf);
694 ELFYAML::VerdefEntry Entry;
695 Entry.Version = Verdef->vd_version;
696 Entry.Flags = Verdef->vd_flags;
697 Entry.VersionNdx = Verdef->vd_ndx;
698 Entry.Hash = Verdef->vd_hash;
700 const uint8_t *BufAux = Buf + Verdef->vd_aux;
701 while (BufAux) {
702 const Elf_Verdaux *Verdaux =
703 reinterpret_cast<const Elf_Verdaux *>(BufAux);
704 Entry.VerNames.push_back(
705 StringTableOrErr->drop_front(Verdaux->vda_name).data());
706 BufAux = Verdaux->vda_next ? BufAux + Verdaux->vda_next : nullptr;
709 S->Entries.push_back(Entry);
710 Buf = Verdef->vd_next ? Buf + Verdef->vd_next : nullptr;
713 return S.release();
716 template <class ELFT>
717 Expected<ELFYAML::SymverSection *>
718 ELFDumper<ELFT>::dumpSymverSection(const Elf_Shdr *Shdr) {
719 typedef typename ELFT::Half Elf_Half;
721 auto S = std::make_unique<ELFYAML::SymverSection>();
722 if (Error E = dumpCommonSection(Shdr, *S))
723 return std::move(E);
725 auto VersionsOrErr = Obj.template getSectionContentsAsArray<Elf_Half>(Shdr);
726 if (!VersionsOrErr)
727 return VersionsOrErr.takeError();
728 for (const Elf_Half &E : *VersionsOrErr)
729 S->Entries.push_back(E);
731 return S.release();
734 template <class ELFT>
735 Expected<ELFYAML::VerneedSection *>
736 ELFDumper<ELFT>::dumpVerneedSection(const Elf_Shdr *Shdr) {
737 typedef typename ELFT::Verneed Elf_Verneed;
738 typedef typename ELFT::Vernaux Elf_Vernaux;
740 auto S = std::make_unique<ELFYAML::VerneedSection>();
741 if (Error E = dumpCommonSection(Shdr, *S))
742 return std::move(E);
744 S->Info = Shdr->sh_info;
746 auto Contents = Obj.getSectionContents(Shdr);
747 if (!Contents)
748 return Contents.takeError();
750 auto StringTableShdrOrErr = Obj.getSection(Shdr->sh_link);
751 if (!StringTableShdrOrErr)
752 return StringTableShdrOrErr.takeError();
754 auto StringTableOrErr = Obj.getStringTable(*StringTableShdrOrErr);
755 if (!StringTableOrErr)
756 return StringTableOrErr.takeError();
758 llvm::ArrayRef<uint8_t> Data = *Contents;
759 const uint8_t *Buf = Data.data();
760 while (Buf) {
761 const Elf_Verneed *Verneed = reinterpret_cast<const Elf_Verneed *>(Buf);
763 ELFYAML::VerneedEntry Entry;
764 Entry.Version = Verneed->vn_version;
765 Entry.File =
766 StringRef(StringTableOrErr->drop_front(Verneed->vn_file).data());
768 const uint8_t *BufAux = Buf + Verneed->vn_aux;
769 while (BufAux) {
770 const Elf_Vernaux *Vernaux =
771 reinterpret_cast<const Elf_Vernaux *>(BufAux);
773 ELFYAML::VernauxEntry Aux;
774 Aux.Hash = Vernaux->vna_hash;
775 Aux.Flags = Vernaux->vna_flags;
776 Aux.Other = Vernaux->vna_other;
777 Aux.Name =
778 StringRef(StringTableOrErr->drop_front(Vernaux->vna_name).data());
780 Entry.AuxV.push_back(Aux);
781 BufAux = Vernaux->vna_next ? BufAux + Vernaux->vna_next : nullptr;
784 S->VerneedV.push_back(Entry);
785 Buf = Verneed->vn_next ? Buf + Verneed->vn_next : nullptr;
788 return S.release();
791 template <class ELFT>
792 Expected<ELFYAML::Group *> ELFDumper<ELFT>::dumpGroup(const Elf_Shdr *Shdr) {
793 auto S = std::make_unique<ELFYAML::Group>();
794 if (Error E = dumpCommonSection(Shdr, *S))
795 return std::move(E);
797 auto SymtabOrErr = Obj.getSection(Shdr->sh_link);
798 if (!SymtabOrErr)
799 return SymtabOrErr.takeError();
800 // Get symbol with index sh_info which name is the signature of the group.
801 const Elf_Shdr *Symtab = *SymtabOrErr;
802 auto SymOrErr = Obj.getSymbol(Symtab, Shdr->sh_info);
803 if (!SymOrErr)
804 return SymOrErr.takeError();
805 auto StrTabOrErr = Obj.getStringTableForSymtab(*Symtab);
806 if (!StrTabOrErr)
807 return StrTabOrErr.takeError();
809 Expected<StringRef> SymbolName =
810 getUniquedSymbolName(*SymOrErr, *StrTabOrErr, Symtab);
811 if (!SymbolName)
812 return SymbolName.takeError();
813 S->Signature = *SymbolName;
815 auto MembersOrErr = Obj.template getSectionContentsAsArray<Elf_Word>(Shdr);
816 if (!MembersOrErr)
817 return MembersOrErr.takeError();
819 for (Elf_Word Member : *MembersOrErr) {
820 if (Member == llvm::ELF::GRP_COMDAT) {
821 S->Members.push_back({"GRP_COMDAT"});
822 continue;
825 auto SHdrOrErr = Obj.getSection(Member);
826 if (!SHdrOrErr)
827 return SHdrOrErr.takeError();
828 auto NameOrErr = getUniquedSectionName(*SHdrOrErr);
829 if (!NameOrErr)
830 return NameOrErr.takeError();
831 S->Members.push_back({*NameOrErr});
833 return S.release();
836 template <class ELFT>
837 Expected<ELFYAML::MipsABIFlags *>
838 ELFDumper<ELFT>::dumpMipsABIFlags(const Elf_Shdr *Shdr) {
839 assert(Shdr->sh_type == ELF::SHT_MIPS_ABIFLAGS &&
840 "Section type is not SHT_MIPS_ABIFLAGS");
841 auto S = std::make_unique<ELFYAML::MipsABIFlags>();
842 if (Error E = dumpCommonSection(Shdr, *S))
843 return std::move(E);
845 auto ContentOrErr = Obj.getSectionContents(Shdr);
846 if (!ContentOrErr)
847 return ContentOrErr.takeError();
849 auto *Flags = reinterpret_cast<const object::Elf_Mips_ABIFlags<ELFT> *>(
850 ContentOrErr.get().data());
851 S->Version = Flags->version;
852 S->ISALevel = Flags->isa_level;
853 S->ISARevision = Flags->isa_rev;
854 S->GPRSize = Flags->gpr_size;
855 S->CPR1Size = Flags->cpr1_size;
856 S->CPR2Size = Flags->cpr2_size;
857 S->FpABI = Flags->fp_abi;
858 S->ISAExtension = Flags->isa_ext;
859 S->ASEs = Flags->ases;
860 S->Flags1 = Flags->flags1;
861 S->Flags2 = Flags->flags2;
862 return S.release();
865 template <class ELFT>
866 static Error elf2yaml(raw_ostream &Out, const object::ELFFile<ELFT> &Obj) {
867 ELFDumper<ELFT> Dumper(Obj);
868 Expected<ELFYAML::Object *> YAMLOrErr = Dumper.dump();
869 if (!YAMLOrErr)
870 return YAMLOrErr.takeError();
872 std::unique_ptr<ELFYAML::Object> YAML(YAMLOrErr.get());
873 yaml::Output Yout(Out);
874 Yout << *YAML;
876 return Error::success();
879 Error elf2yaml(raw_ostream &Out, const object::ObjectFile &Obj) {
880 if (const auto *ELFObj = dyn_cast<object::ELF32LEObjectFile>(&Obj))
881 return elf2yaml(Out, *ELFObj->getELFFile());
883 if (const auto *ELFObj = dyn_cast<object::ELF32BEObjectFile>(&Obj))
884 return elf2yaml(Out, *ELFObj->getELFFile());
886 if (const auto *ELFObj = dyn_cast<object::ELF64LEObjectFile>(&Obj))
887 return elf2yaml(Out, *ELFObj->getELFFile());
889 if (const auto *ELFObj = dyn_cast<object::ELF64BEObjectFile>(&Obj))
890 return elf2yaml(Out, *ELFObj->getELFFile());
892 llvm_unreachable("unknown ELF file format");