[llvm] 108ba4f - [llvm-readobj] Refactor ELFDumper::printAttributes()

Fangrui Song via llvm-commits llvm-commits at lists.llvm.org
Tue Aug 17 13:28:36 PDT 2021


Author: Jozef Lawrynowicz
Date: 2021-08-17T13:28:31-07:00
New Revision: 108ba4f4a48043067f0735f7f7c6f301045cf9b5

URL: https://github.com/llvm/llvm-project/commit/108ba4f4a48043067f0735f7f7c6f301045cf9b5
DIFF: https://github.com/llvm/llvm-project/commit/108ba4f4a48043067f0735f7f7c6f301045cf9b5.diff

LOG: [llvm-readobj] Refactor ELFDumper::printAttributes()

The current implementation of printAttributes makes it fiddly to extend
attribute support for new targets.

By refactoring the code so all target specific variables are
initialized in a switch/case statement, it becomes simpler to extend
attribute support for new targets.

Reviewed By: jhenderson, MaskRay

Differential Revision: https://reviews.llvm.org/D107968

Added: 
    llvm/test/tools/llvm-readobj/ELF/ARM/attribute-big-endian.test

Modified: 
    llvm/test/tools/llvm-readobj/ELF/RISCV/validate-attr-section.test
    llvm/tools/llvm-readobj/ELFDumper.cpp

Removed: 
    


################################################################################
diff  --git a/llvm/test/tools/llvm-readobj/ELF/ARM/attribute-big-endian.test b/llvm/test/tools/llvm-readobj/ELF/ARM/attribute-big-endian.test
new file mode 100644
index 000000000000..7d20b310f9d9
--- /dev/null
+++ b/llvm/test/tools/llvm-readobj/ELF/ARM/attribute-big-endian.test
@@ -0,0 +1,17 @@
+## We only implement attribute section printing for little-endian encoding.
+
+# RUN: yaml2obj %s -o %t.o
+# RUN: llvm-readobj -A %t.o 2>&1 | FileCheck %s -DFILE=%t.o
+
+# CHECK: warning: '[[FILE]]': attribute printing not implemented for big-endian ARM objects
+
+--- !ELF
+FileHeader:
+  Class:   ELFCLASS32
+## Test big-endian encoding.
+  Data:    ELFDATA2MSB
+  Type:    ET_REL
+  Machine: EM_ARM
+Sections:
+  - Name: .ARM.attributes
+    Type: SHT_ARM_ATTRIBUTES

diff  --git a/llvm/test/tools/llvm-readobj/ELF/RISCV/validate-attr-section.test b/llvm/test/tools/llvm-readobj/ELF/RISCV/validate-attr-section.test
index 66a5a7a8d31f..21bbb5ed93f1 100644
--- a/llvm/test/tools/llvm-readobj/ELF/RISCV/validate-attr-section.test
+++ b/llvm/test/tools/llvm-readobj/ELF/RISCV/validate-attr-section.test
@@ -1,9 +1,9 @@
 ## We only implement attribute section printing for little-endian encoding.
 
 # RUN: yaml2obj %s -o %t.o
-# RUN: llvm-readobj -A %t.o | FileCheck %s
+# RUN: llvm-readobj -A %t.o 2>&1 | FileCheck %s -DFILE=%t.o
 
-# CHECK: Attributes not implemented.
+# CHECK: warning: '[[FILE]]': attribute printing not implemented for big-endian RISC-V objects
 
 --- !ELF
 FileHeader:

diff  --git a/llvm/tools/llvm-readobj/ELFDumper.cpp b/llvm/tools/llvm-readobj/ELFDumper.cpp
index 000a10b1c2f8..1073f22ddd09 100644
--- a/llvm/tools/llvm-readobj/ELFDumper.cpp
+++ b/llvm/tools/llvm-readobj/ELFDumper.cpp
@@ -339,7 +339,8 @@ template <typename ELFT> class ELFDumper : public ObjDumper {
     return DynRegionInfo(ObjF, *this, Obj.base() + Offset, Size, EntSize);
   }
 
-  void printAttributes();
+  void printAttributes(unsigned, std::unique_ptr<ELFAttributeParser>,
+                       support::endianness);
   void printMipsReginfo();
   void printMipsOptions();
 
@@ -2557,8 +2558,22 @@ template <typename ELFT> void ELFDumper<ELFT>::printLoadName() {
 template <class ELFT> void ELFDumper<ELFT>::printArchSpecificInfo() {
   switch (Obj.getHeader().e_machine) {
   case EM_ARM:
+    if (Obj.isLE())
+      printAttributes(ELF::SHT_ARM_ATTRIBUTES,
+                      std::make_unique<ARMAttributeParser>(&W),
+                      support::little);
+    else
+      reportUniqueWarning("attribute printing not implemented for big-endian "
+                          "ARM objects");
+    break;
   case EM_RISCV:
-    printAttributes();
+    if (Obj.isLE())
+      printAttributes(ELF::SHT_RISCV_ATTRIBUTES,
+                      std::make_unique<RISCVAttributeParser>(&W),
+                      support::little);
+    else
+      reportUniqueWarning("attribute printing not implemented for big-endian "
+                          "RISC-V objects");
     break;
   case EM_MIPS: {
     printMipsABIFlags();
@@ -2581,20 +2596,15 @@ template <class ELFT> void ELFDumper<ELFT>::printArchSpecificInfo() {
   }
 }
 
-template <class ELFT> void ELFDumper<ELFT>::printAttributes() {
-  if (!Obj.isLE()) {
-    W.startLine() << "Attributes not implemented.\n";
-    return;
-  }
-
-  const unsigned Machine = Obj.getHeader().e_machine;
-  assert((Machine == EM_ARM || Machine == EM_RISCV) &&
-         "Attributes not implemented.");
-
+template <class ELFT>
+void ELFDumper<ELFT>::printAttributes(
+    unsigned AttrShType, std::unique_ptr<ELFAttributeParser> AttrParser,
+    support::endianness Endianness) {
+  assert((AttrShType != ELF::SHT_NULL) && AttrParser &&
+         "Incomplete ELF attribute implementation");
   DictScope BA(W, "BuildAttributes");
   for (const Elf_Shdr &Sec : cantFail(Obj.sections())) {
-    if (Sec.sh_type != ELF::SHT_ARM_ATTRIBUTES &&
-        Sec.sh_type != ELF::SHT_RISCV_ATTRIBUTES)
+    if (Sec.sh_type != AttrShType)
       continue;
 
     ArrayRef<uint8_t> Contents;
@@ -2613,13 +2623,7 @@ template <class ELFT> void ELFDumper<ELFT>::printAttributes() {
 
     W.printHex("FormatVersion", Contents[0]);
 
-    auto ParseAttrubutes = [&]() {
-      if (Machine == EM_ARM)
-        return ARMAttributeParser(&W).parse(Contents, support::little);
-      return RISCVAttributeParser(&W).parse(Contents, support::little);
-    };
-
-    if (Error E = ParseAttrubutes())
+    if (Error E = AttrParser->parse(Contents, Endianness))
       reportUniqueWarning("unable to dump attributes from the " +
                           describe(Sec) + ": " + toString(std::move(E)));
   }


        


More information about the llvm-commits mailing list