[llvm] r373606 - Recommit r373598 "[yaml2obj/obj2yaml] - Add support for SHT_LLVM_ADDRSIG sections."

George Rimar via llvm-commits llvm-commits at lists.llvm.org
Thu Oct 3 07:52:33 PDT 2019


Author: grimar
Date: Thu Oct  3 07:52:33 2019
New Revision: 373606

URL: http://llvm.org/viewvc/llvm-project?rev=373606&view=rev
Log:
Recommit r373598 "[yaml2obj/obj2yaml] - Add support for SHT_LLVM_ADDRSIG sections."

Fix: call `consumeError()` for a case missed.

Original commit message:

SHT_LLVM_ADDRSIG is described here:
https://llvm.org/docs/Extensions.html#sht-llvm-addrsig-section-address-significance-table

This patch teaches tools to dump them and to parse the YAML declarations of such sections.

Differential revision: https://reviews.llvm.org/D68333

Added:
    llvm/trunk/test/tools/obj2yaml/elf-llvm-addrsig-section.yaml
    llvm/trunk/test/tools/yaml2obj/elf-llvm-addrsig-section.yaml
Modified:
    llvm/trunk/include/llvm/ObjectYAML/ELFYAML.h
    llvm/trunk/lib/ObjectYAML/ELFEmitter.cpp
    llvm/trunk/lib/ObjectYAML/ELFYAML.cpp
    llvm/trunk/test/tools/llvm-readobj/elf-section-types.test
    llvm/trunk/tools/obj2yaml/elf2yaml.cpp

Modified: llvm/trunk/include/llvm/ObjectYAML/ELFYAML.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ObjectYAML/ELFYAML.h?rev=373606&r1=373605&r2=373606&view=diff
==============================================================================
--- llvm/trunk/include/llvm/ObjectYAML/ELFYAML.h (original)
+++ llvm/trunk/include/llvm/ObjectYAML/ELFYAML.h Thu Oct  3 07:52:33 2019
@@ -137,7 +137,8 @@ struct Section {
     StackSizes,
     SymtabShndxSection,
     Symver,
-    MipsABIFlags
+    MipsABIFlags,
+    Addrsig
   };
   SectionKind Kind;
   StringRef Name;
@@ -256,6 +257,25 @@ struct VerneedSection : Section {
   }
 };
 
+struct AddrsigSymbol {
+  AddrsigSymbol(StringRef N) : Name(N), Index(None) {}
+  AddrsigSymbol(llvm::yaml::Hex32 Ndx) : Name(None), Index(Ndx) {}
+  AddrsigSymbol() : Name(None), Index(None) {}
+
+  Optional<StringRef> Name;
+  Optional<llvm::yaml::Hex32> Index;
+};
+
+struct AddrsigSection : Section {
+  Optional<yaml::BinaryRef> Content;
+  Optional<std::vector<AddrsigSymbol>> Symbols;
+
+  AddrsigSection() : Section(SectionKind::Addrsig) {}
+  static bool classof(const Section *S) {
+    return S->Kind == SectionKind::Addrsig;
+  }
+};
+
 struct SymverSection : Section {
   std::vector<uint16_t> Entries;
 
@@ -362,6 +382,7 @@ struct Object {
 } // end namespace ELFYAML
 } // end namespace llvm
 
+LLVM_YAML_IS_SEQUENCE_VECTOR(llvm::ELFYAML::AddrsigSymbol)
 LLVM_YAML_IS_SEQUENCE_VECTOR(llvm::ELFYAML::StackSizeEntry)
 LLVM_YAML_IS_SEQUENCE_VECTOR(llvm::ELFYAML::DynamicEntry)
 LLVM_YAML_IS_SEQUENCE_VECTOR(llvm::ELFYAML::ProgramHeader)
@@ -518,6 +539,10 @@ template <> struct MappingTraits<ELFYAML
   static void mapping(IO &IO, ELFYAML::VernauxEntry &E);
 };
 
+template <> struct MappingTraits<ELFYAML::AddrsigSymbol> {
+  static void mapping(IO &IO, ELFYAML::AddrsigSymbol &Sym);
+};
+
 template <> struct MappingTraits<ELFYAML::Relocation> {
   static void mapping(IO &IO, ELFYAML::Relocation &Rel);
 };

Modified: llvm/trunk/lib/ObjectYAML/ELFEmitter.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ObjectYAML/ELFEmitter.cpp?rev=373606&r1=373605&r2=373606&view=diff
==============================================================================
--- llvm/trunk/lib/ObjectYAML/ELFEmitter.cpp (original)
+++ llvm/trunk/lib/ObjectYAML/ELFEmitter.cpp Thu Oct  3 07:52:33 2019
@@ -174,6 +174,10 @@ template <class ELFT> class ELFState {
   void writeSectionContent(Elf_Shdr &SHeader,
                            const ELFYAML::HashSection &Section,
                            ContiguousBlobAccumulator &CBA);
+  void writeSectionContent(Elf_Shdr &SHeader,
+                           const ELFYAML::AddrsigSection &Section,
+                           ContiguousBlobAccumulator &CBA);
+
   ELFState(ELFYAML::Object &D, yaml::ErrorHandler EH);
 
 public:
@@ -423,6 +427,8 @@ void ELFState<ELFT>::initSectionHeaders(
       writeSectionContent(SHeader, *S, CBA);
     } else if (auto S = dyn_cast<ELFYAML::HashSection>(Sec)) {
       writeSectionContent(SHeader, *S, CBA);
+    } else if (auto S = dyn_cast<ELFYAML::AddrsigSection>(Sec)) {
+      writeSectionContent(SHeader, *S, CBA);
     } else {
       llvm_unreachable("Unknown section type");
     }
@@ -990,6 +996,30 @@ void ELFState<ELFT>::writeSectionContent
     Section.Content->writeAsBinary(OS);
 }
 
+template <class ELFT>
+void ELFState<ELFT>::writeSectionContent(Elf_Shdr &SHeader,
+                                         const ELFYAML::AddrsigSection &Section,
+                                         ContiguousBlobAccumulator &CBA) {
+  raw_ostream &OS =
+      CBA.getOSAndAlignedOffset(SHeader.sh_offset, SHeader.sh_addralign);
+
+  unsigned Link = 0;
+  if (Section.Link.empty() && SN2I.lookup(".symtab", Link))
+    SHeader.sh_link = Link;
+
+  if (Section.Content) {
+    SHeader.sh_size = writeContent(OS, Section.Content, None);
+    return;
+  }
+
+  for (const ELFYAML::AddrsigSymbol &Sym : *Section.Symbols) {
+    uint64_t Val =
+        Sym.Name ? toSymbolIndex(*Sym.Name, Section.Name, /*IsDynamic=*/false)
+                 : (uint32_t)*Sym.Index;
+    SHeader.sh_size += encodeULEB128(Val, OS);
+  }
+}
+
 template <class ELFT> void ELFState<ELFT>::buildSectionIndex() {
   for (unsigned I = 0, E = Doc.Sections.size(); I != E; ++I) {
     StringRef Name = Doc.Sections[I]->Name;

Modified: llvm/trunk/lib/ObjectYAML/ELFYAML.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ObjectYAML/ELFYAML.cpp?rev=373606&r1=373605&r2=373606&view=diff
==============================================================================
--- llvm/trunk/lib/ObjectYAML/ELFYAML.cpp (original)
+++ llvm/trunk/lib/ObjectYAML/ELFYAML.cpp Thu Oct  3 07:52:33 2019
@@ -1071,6 +1071,12 @@ static void sectionMapping(IO &IO, ELFYA
   IO.mapRequired("Entries", Section.Entries);
 }
 
+static void sectionMapping(IO &IO, ELFYAML::AddrsigSection &Section) {
+  commonSectionMapping(IO, Section);
+  IO.mapOptional("Content", Section.Content);
+  IO.mapOptional("Symbols", Section.Symbols);
+}
+
 void MappingTraits<ELFYAML::SectionOrType>::mapping(
     IO &IO, ELFYAML::SectionOrType &sectionOrType) {
   IO.mapRequired("SectionOrType", sectionOrType.sectionNameOrType);
@@ -1161,6 +1167,11 @@ void MappingTraits<std::unique_ptr<ELFYA
       Section.reset(new ELFYAML::SymtabShndxSection());
     sectionMapping(IO, *cast<ELFYAML::SymtabShndxSection>(Section.get()));
     break;
+  case ELF::SHT_LLVM_ADDRSIG:
+    if (!IO.outputting())
+      Section.reset(new ELFYAML::AddrsigSection());
+    sectionMapping(IO, *cast<ELFYAML::AddrsigSection>(Section.get()));
+    break;
   default:
     if (!IO.outputting()) {
       StringRef Name;
@@ -1233,6 +1244,26 @@ StringRef MappingTraits<std::unique_ptr<
     return {};
   }
 
+  if (const auto *Sec = dyn_cast<ELFYAML::AddrsigSection>(Section.get())) {
+    if (!Sec->Symbols && !Sec->Content)
+      return "one of \"Symbols\" or \"Content\" must be specified";
+
+    if (Sec->Content) {
+      if (Sec->Symbols)
+        return "\"Content\" and \"Symbols\" cannot be used together";
+      return {};
+    }
+
+    if (!Sec->Symbols)
+      return {};
+
+    for (const ELFYAML::AddrsigSymbol &AS : *Sec->Symbols)
+      if (AS.Index && AS.Name)
+        return "\"Index\" and \"Name\" cannot be used together when defining a "
+               "symbol";
+    return {};
+  }
+
   return {};
 }
 
@@ -1340,6 +1371,12 @@ void MappingTraits<ELFYAML::Object>::map
   IO.setContext(nullptr);
 }
 
+void MappingTraits<ELFYAML::AddrsigSymbol>::mapping(IO &IO, ELFYAML::AddrsigSymbol &Sym) {
+  assert(IO.getContext() && "The IO context is not initialized");
+  IO.mapOptional("Name", Sym.Name);
+  IO.mapOptional("Index", Sym.Index);
+}
+
 LLVM_YAML_STRONG_TYPEDEF(uint8_t, MIPS_AFL_REG)
 LLVM_YAML_STRONG_TYPEDEF(uint8_t, MIPS_ABI_FP)
 LLVM_YAML_STRONG_TYPEDEF(uint32_t, MIPS_AFL_EXT)

Modified: llvm/trunk/test/tools/llvm-readobj/elf-section-types.test
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-readobj/elf-section-types.test?rev=373606&r1=373605&r2=373606&view=diff
==============================================================================
--- llvm/trunk/test/tools/llvm-readobj/elf-section-types.test (original)
+++ llvm/trunk/test/tools/llvm-readobj/elf-section-types.test Thu Oct  3 07:52:33 2019
@@ -196,6 +196,7 @@ Sections:
     Type: SHT_LLVM_CALL_GRAPH_PROFILE
   - Name: llvm_addrsig
     Type: SHT_LLVM_ADDRSIG
+    Symbols:
   - Name: .deplibs
     Type: SHT_LLVM_DEPENDENT_LIBRARIES
   - Name: .llvm_sympart.f

Added: llvm/trunk/test/tools/obj2yaml/elf-llvm-addrsig-section.yaml
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/obj2yaml/elf-llvm-addrsig-section.yaml?rev=373606&view=auto
==============================================================================
--- llvm/trunk/test/tools/obj2yaml/elf-llvm-addrsig-section.yaml (added)
+++ llvm/trunk/test/tools/obj2yaml/elf-llvm-addrsig-section.yaml Thu Oct  3 07:52:33 2019
@@ -0,0 +1,98 @@
+## Check how obj2yaml dumps the SHT_LLVM_ADDRSIG section.
+
+## Check that when possible obj2yaml tries to produce the "Name" tag when
+## dumping entries of the SHT_LLVM_ADDRSIG section. It falls back to producing
+## the "Index" tag when it can't match a symbol index with a symbol table entry.
+
+# RUN: yaml2obj --docnum=1 %s -o %t1
+# RUN: obj2yaml %t1 | FileCheck %s --check-prefix=NAME
+
+# NAME:      - Name: .llvm_addrsig
+# NAME-NEXT:   Type: SHT_LLVM_ADDRSIG
+# NAME-NEXT:   Link: .symtab
+# NAME-NEXT:   Symbols:
+# NAME-NEXT:     - Name:  foo
+# NAME-NEXT:     - Name:  bar
+# NAME-NEXT:     - Index: 0x00000003
+# NAME-NEXT:     - Index: 0xFFFFFFFF
+# NAME:      - Name: .llvm_addrsig_unlinked
+# NAME-NEXT:   Type: SHT_LLVM_ADDRSIG
+# NAME-NEXT:   Symbols:
+# NAME-NEXT:     - Index: 0x00000001
+# NAME-NEXT:     - Index: 0x00000002
+# NAME-NEXT:     - Index: 0x00000003
+# NAME-NEXT:     - Index: 0xFFFFFFFF
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Symbols:
+      - Index: 1
+      - Index: 2
+      - Index: 3
+      - Index: 0xFFFFFFFF
+  - Name: .llvm_addrsig_unlinked
+    Type: SHT_LLVM_ADDRSIG
+    Link: 0
+    Symbols:
+      - Index: 1
+      - Index: 2
+      - Index: 3
+      - Index: 0xFFFFFFFF
+Symbols:
+  - Name:    foo
+    Type:    STT_FUNC
+    Binding: STB_GLOBAL
+  - Name:    bar
+    Type:    STT_FUNC
+    Binding: STB_GLOBAL
+
+## Check that obj2yaml dumps the SHT_LLVM_ADDRSIG section
+## data using the "Content" tag when at least one of the entries is broken,
+## e.g. because the entry contains a malformed uleb128 value.
+
+# RUN: yaml2obj --docnum=2 %s -o %t2
+# RUN: obj2yaml %t2 | FileCheck %s --check-prefix=INVALID-ENTRY
+
+# INVALID-ENTRY:      - Name:    .llvm_addrsig
+# INVALID-ENTRY-NEXT:   Type:    SHT_LLVM_ADDRSIG
+# INVALID-ENTRY-NEXT:   Link:    .symtab
+# INVALID-ENTRY-NEXT:   Content: FFFFFFFFFF
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Content: "FFFFFFFFFF"
+
+## obj2yaml produces a "Symbols" tag when describing an empty SHT_LLVM_ADDRSIG section.
+
+# RUN: yaml2obj --docnum=3 %s -o %t3
+# RUN: obj2yaml %t3 | FileCheck %s --check-prefix=EMPTY
+
+# EMPTY:      - Name:    .llvm_addrsig
+# EMPTY-NEXT:   Type:    SHT_LLVM_ADDRSIG
+# EMPTY-NEXT:   Link:    .symtab
+# EMPTY-NEXT:   Symbols: []
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Content: ""

Added: llvm/trunk/test/tools/yaml2obj/elf-llvm-addrsig-section.yaml
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/yaml2obj/elf-llvm-addrsig-section.yaml?rev=373606&view=auto
==============================================================================
--- llvm/trunk/test/tools/yaml2obj/elf-llvm-addrsig-section.yaml (added)
+++ llvm/trunk/test/tools/yaml2obj/elf-llvm-addrsig-section.yaml Thu Oct  3 07:52:33 2019
@@ -0,0 +1,213 @@
+## Check how yaml2obj produces SHT_LLVM_ADDRSIG sections.
+
+## Check we can describe SHT_LLVM_ADDRSIG using the "Symbols" tag. We can define
+## symbols either using names or indexes.
+
+# RUN: yaml2obj --docnum=1 %s -o %t1
+# RUN: llvm-readobj --sections --section-data %t1 | FileCheck %s --check-prefix=SYMBOLS
+
+# SYMBOLS:      Section {
+# SYMBOLS:        Index: 1
+# SYMBOLS-NEXT:   Name: .llvm_addrsig
+# SYMBOLS-NEXT:   Type: SHT_LLVM_ADDRSIG
+# SYMBOLS-NEXT:   Flags [
+# SYMBOLS-NEXT:   ]
+# SYMBOLS-NEXT:   Address: 0x0
+# SYMBOLS-NEXT:   Offset: 0x40
+# SYMBOLS-NEXT:   Size: 4
+# SYMBOLS-NEXT:   Link: 2
+# SYMBOLS-NEXT:   Info: 0
+# SYMBOLS-NEXT:   AddressAlignment: 0
+# SYMBOLS-NEXT:   EntrySize: 0
+# SYMBOLS-NEXT:   SectionData (
+# SYMBOLS-NEXT:     0000: 01020102
+# SYMBOLS-NEXT:   )
+# SYMBOLS-NEXT: }
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Symbols:
+      - Name: foo
+      - Name: bar
+      - Index: 1
+      - Index: 2
+Symbols:
+  - Name:    foo
+    Type:    STT_FUNC
+    Binding: STB_GLOBAL
+  - Name:    bar
+    Type:    STT_FUNC
+    Binding: STB_GLOBAL
+
+## We can't specify both "Index" and "Name" when defining a symbol.
+
+# RUN: not yaml2obj --docnum=2 %s 2>&1 | FileCheck %s --check-prefix=INDEX-NAME
+
+# INDEX-NAME: error: "Index" and "Name" cannot be used together when defining a symbol
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Symbols:
+      - Name: foo
+        Index: 1
+Symbols:
+  - Name:    foo
+    Type:    STT_FUNC
+    Binding: STB_GLOBAL
+
+## Check we report an error if an unknown symbol is referenced in the
+## SHT_LLVM_ADDRSIG section description.
+
+# RUN: not yaml2obj --docnum=3 %s 2>&1 | FileCheck %s --check-prefix=SYMBOL-UNKNOWN
+
+# SYMBOL-UNKNOWN: error: unknown symbol referenced: 'foo' by YAML section '.llvm_addrsig'
+# SYMBOL-UNKNOWN: error: unknown symbol referenced: 'bar' by YAML section '.llvm_addrsig'
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Symbols:
+      - Name: foo
+      - Name: bar
+
+## Check we can specify any arbitrary symbol indices.
+
+# RUN: yaml2obj --docnum=4 %s -o %t4
+# RUN: llvm-readobj --sections --section-data %t4 | FileCheck %s --check-prefix=SYMBOL-INDEX
+
+# SYMBOL-INDEX:      Type: SHT_LLVM_ADDRSIG
+# SYMBOL-INDEX:      SectionData (
+# SYMBOL-INDEX-NEXT:   0000: 00FF01C4 E6888901 FFFFFFFF 0F
+# SYMBOL-INDEX-NEXT: )
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Symbols:
+      - Index: 0
+      - Index: 255
+      - Index: 0x11223344
+## 0xFFFFFFFF is a maximum allowed index value.
+      - Index: 0xFFFFFFFF
+
+## Check that the maximum symbol index size is 32 bits.
+
+# RUN: not yaml2obj --docnum=5 %s 2>&1 | FileCheck %s --check-prefix=SYMBOL-INDEX-OVERFLOW
+
+# SYMBOL-INDEX-OVERFLOW: error: out of range hex32 number
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Symbols:
+      - Index: 0x1122334455
+
+## Check we can use the "Content" tag to specify any data for SHT_LLVM_ADDRSIG sections.
+
+# RUN: yaml2obj --docnum=6 %s -o %t6
+# RUN: llvm-readobj --sections --section-data %t6 | FileCheck %s --check-prefix=CONTENT
+
+# CONTENT:      Type: SHT_LLVM_ADDRSIG
+# CONTENT:      Size:
+# CONTENT-SAME: 5
+# CONTENT:      SectionData (
+# CONTENT-NEXT:   0000: 11223344 55
+# CONTENT-NEXT: )
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Content: "1122334455"
+
+## Either "Content" or "Symbols" must be specifed for SHT_LLVM_ADDRSIG sections.
+
+# RUN: not yaml2obj --docnum=7 %s 2>&1 | FileCheck %s --check-prefix=NO-TAGS
+
+# NO-TAGS: error: one of "Symbols" or "Content" must be specified
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+
+## "Content" and "Symbols" cannot be used together to describe the SHT_LLVM_ADDRSIG section.
+
+# RUN: not yaml2obj --docnum=8 %s 2>&1 | FileCheck %s --check-prefix=CONTENT-SYMBOLS
+
+# CONTENT-SYMBOLS: error: "Content" and "Symbols" cannot be used together
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Content: ""
+    Symbols:
+
+## Check we can set an arbitrary sh_link value for SHT_LLVM_ADDRSIG sections.
+
+# RUN: yaml2obj --docnum=9 %s -o %t9
+# RUN: llvm-readobj --sections %t9 | FileCheck %s --check-prefix=LINK
+
+# LINK:      Name: .llvm_addrsig
+# LINK:      Link:
+# LINK-SAME:       123{{$}}
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS64
+  Data:    ELFDATA2LSB
+  Type:    ET_DYN
+  Machine: EM_X86_64
+Sections:
+  - Name: .llvm_addrsig
+    Type: SHT_LLVM_ADDRSIG
+    Link: 123
+    Content: ""

Modified: llvm/trunk/tools/obj2yaml/elf2yaml.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/obj2yaml/elf2yaml.cpp?rev=373606&r1=373605&r2=373606&view=diff
==============================================================================
--- llvm/trunk/tools/obj2yaml/elf2yaml.cpp (original)
+++ llvm/trunk/tools/obj2yaml/elf2yaml.cpp Thu Oct  3 07:52:33 2019
@@ -41,6 +41,7 @@ class ELFDumper {
   Expected<StringRef> getUniquedSymbolName(const Elf_Sym *Sym,
                                            StringRef StrTable,
                                            const Elf_Shdr *SymTab);
+  Expected<StringRef> getSymbolName(uint32_t SymtabNdx, uint32_t SymbolNdx);
 
   const object::ELFFile<ELFT> &Obj;
   ArrayRef<Elf_Word> ShndxTable;
@@ -56,6 +57,7 @@ class ELFDumper {
   Error dumpRelocation(const RelT *Rel, const Elf_Shdr *SymTab,
                        ELFYAML::Relocation &R);
 
+  Expected<ELFYAML::AddrsigSection *> dumpAddrsigSection(const Elf_Shdr *Shdr);
   Expected<ELFYAML::DynamicSection *> dumpDynamicSection(const Elf_Shdr *Shdr);
   Expected<ELFYAML::RelocationSection *> dumpRelocSection(const Elf_Shdr *Shdr);
   Expected<ELFYAML::RawContentSection *>
@@ -284,6 +286,13 @@ template <class ELFT> Expected<ELFYAML::
       Y->Sections.emplace_back(*SecOrErr);
       break;
     }
+    case ELF::SHT_LLVM_ADDRSIG: {
+      Expected<ELFYAML::AddrsigSection *> SecOrErr = dumpAddrsigSection(&Sec);
+      if (!SecOrErr)
+        return SecOrErr.takeError();
+      Y->Sections.emplace_back(*SecOrErr);
+      break;
+    }
     case ELF::SHT_NULL: {
       // We only dump the SHT_NULL section at index 0 when it
       // has at least one non-null field, because yaml2obj
@@ -520,6 +529,46 @@ ELFDumper<ELFT>::dumpStackSizesSection(c
 }
 
 template <class ELFT>
+Expected<ELFYAML::AddrsigSection *>
+ELFDumper<ELFT>::dumpAddrsigSection(const Elf_Shdr *Shdr) {
+  auto S = std::make_unique<ELFYAML::AddrsigSection>();
+  if (Error E = dumpCommonSection(Shdr, *S))
+    return std::move(E);
+
+  auto ContentOrErr = Obj.getSectionContents(Shdr);
+  if (!ContentOrErr)
+    return ContentOrErr.takeError();
+
+  ArrayRef<uint8_t> Content = *ContentOrErr;
+  DataExtractor::Cursor Cur(0);
+  DataExtractor Data(Content, Obj.isLE(), /*AddressSize=*/0);
+  std::vector<ELFYAML::AddrsigSymbol> Symbols;
+  while (Cur && Cur.tell() < Content.size()) {
+    uint64_t SymNdx = Data.getULEB128(Cur);
+    if (!Cur)
+      break;
+
+    Expected<StringRef> SymbolName = getSymbolName(Shdr->sh_link, SymNdx);
+    if (!SymbolName || SymbolName->empty()) {
+      consumeError(SymbolName.takeError());
+      Symbols.emplace_back(SymNdx);
+      continue;
+    }
+
+    Symbols.emplace_back(*SymbolName);
+  }
+
+  if (Cur) {
+    S->Symbols = std::move(Symbols);
+    return S.release();
+  }
+
+  consumeError(Cur.takeError());
+  S->Content = yaml::BinaryRef(Content);
+  return S.release();
+}
+
+template <class ELFT>
 Expected<ELFYAML::DynamicSection *>
 ELFDumper<ELFT>::dumpDynamicSection(const Elf_Shdr *Shdr) {
   auto S = std::make_unique<ELFYAML::DynamicSection>();
@@ -791,25 +840,31 @@ ELFDumper<ELFT>::dumpVerneedSection(cons
 }
 
 template <class ELFT>
-Expected<ELFYAML::Group *> ELFDumper<ELFT>::dumpGroup(const Elf_Shdr *Shdr) {
-  auto S = std::make_unique<ELFYAML::Group>();
-  if (Error E = dumpCommonSection(Shdr, *S))
-    return std::move(E);
-
-  auto SymtabOrErr = Obj.getSection(Shdr->sh_link);
+Expected<StringRef> ELFDumper<ELFT>::getSymbolName(uint32_t SymtabNdx,
+                                                   uint32_t SymbolNdx) {
+  auto SymtabOrErr = Obj.getSection(SymtabNdx);
   if (!SymtabOrErr)
     return SymtabOrErr.takeError();
-  // Get symbol with index sh_info which name is the signature of the group.
+
   const Elf_Shdr *Symtab = *SymtabOrErr;
-  auto SymOrErr = Obj.getSymbol(Symtab, Shdr->sh_info);
+  auto SymOrErr = Obj.getSymbol(Symtab, SymbolNdx);
   if (!SymOrErr)
     return SymOrErr.takeError();
+
   auto StrTabOrErr = Obj.getStringTableForSymtab(*Symtab);
   if (!StrTabOrErr)
     return StrTabOrErr.takeError();
+  return getUniquedSymbolName(*SymOrErr, *StrTabOrErr, Symtab);
+}
+
+template <class ELFT>
+Expected<ELFYAML::Group *> ELFDumper<ELFT>::dumpGroup(const Elf_Shdr *Shdr) {
+  auto S = std::make_unique<ELFYAML::Group>();
+  if (Error E = dumpCommonSection(Shdr, *S))
+    return std::move(E);
 
-  Expected<StringRef> SymbolName =
-      getUniquedSymbolName(*SymOrErr, *StrTabOrErr, Symtab);
+  // Get symbol with index sh_info. This symbol's name is the signature of the group.
+  Expected<StringRef> SymbolName = getSymbolName(Shdr->sh_link, Shdr->sh_info);
   if (!SymbolName)
     return SymbolName.takeError();
   S->Signature = *SymbolName;




More information about the llvm-commits mailing list