[llvm] r236737 - [llvm-readobj] Print .MIPS.abiflags section content

Simon Atanasyan simon at atanasyan.com
Thu May 7 08:40:36 PDT 2015


Author: atanasyan
Date: Thu May  7 10:40:35 2015
New Revision: 236737

URL: http://llvm.org/viewvc/llvm-project?rev=236737&view=rev
Log:
[llvm-readobj] Print .MIPS.abiflags section content

This change adds new flag -mips-abi-flags to the llvm-readobj. This flag
forces printing of .MIPS.abiflags section content.

https://dmz-portal.mips.com/wiki/MIPS_O32_ABI_-_FR0_and_FR1_Interlinking#10.2.1._.MIPS.abiflags

Added:
    llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mips
    llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mipsel
    llvm/trunk/test/tools/llvm-readobj/mips-abiflags.test
Modified:
    llvm/trunk/include/llvm/Object/ELFTypes.h
    llvm/trunk/tools/llvm-readobj/ELFDumper.cpp
    llvm/trunk/tools/llvm-readobj/ObjDumper.h
    llvm/trunk/tools/llvm-readobj/llvm-readobj.cpp

Modified: llvm/trunk/include/llvm/Object/ELFTypes.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Object/ELFTypes.h?rev=236737&r1=236736&r2=236737&view=diff
==============================================================================
--- llvm/trunk/include/llvm/Object/ELFTypes.h (original)
+++ llvm/trunk/include/llvm/Object/ELFTypes.h Thu May  7 10:40:35 2015
@@ -489,6 +489,22 @@ struct Elf_Phdr_Impl<ELFType<TargetEndia
   Elf_Xword p_align;  // Segment alignment constraint
 };
 
+// .MIPS.abiflags section content
+template <class ELFT> struct Elf_Mips_ABIFlags {
+  LLVM_ELF_IMPORT_TYPES_ELFT(ELFT)
+  Elf_Half version;  // Version of the structure
+  uint8_t isa_level; // ISA level: 1-5, 32, and 64
+  uint8_t isa_rev;   // ISA revision (0 for MIPS I - MIPS V)
+  uint8_t gpr_size;  // General purpose registers size
+  uint8_t cpr1_size; // Co-processor 1 registers size
+  uint8_t cpr2_size; // Co-processor 2 registers size
+  uint8_t fp_abi;    // Floating-point ABI flag
+  Elf_Word isa_ext;  // Processor-specific extension
+  Elf_Word ases;     // ASEs flags
+  Elf_Word flags1;   // General flags
+  Elf_Word flags2;   // General flags
+};
+
 } // end namespace object.
 } // end namespace llvm.
 

Added: llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mips
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mips?rev=236737&view=auto
==============================================================================
Binary files llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mips (added) and llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mips Thu May  7 10:40:35 2015 differ

Added: llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mipsel
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mipsel?rev=236737&view=auto
==============================================================================
Binary files llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mipsel (added) and llvm/trunk/test/tools/llvm-readobj/Inputs/abiflags.obj.elf-mipsel Thu May  7 10:40:35 2015 differ

Added: llvm/trunk/test/tools/llvm-readobj/mips-abiflags.test
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-readobj/mips-abiflags.test?rev=236737&view=auto
==============================================================================
--- llvm/trunk/test/tools/llvm-readobj/mips-abiflags.test (added)
+++ llvm/trunk/test/tools/llvm-readobj/mips-abiflags.test Thu May  7 10:40:35 2015
@@ -0,0 +1,42 @@
+RUN: llvm-readobj -mips-abi-flags %p/Inputs/abiflags.obj.elf-mipsel | \
+RUN:   FileCheck -check-prefix=EL64 %s
+RUN: llvm-readobj -mips-abi-flags %p/Inputs/abiflags.obj.elf-mips | \
+RUN:   FileCheck -check-prefix=BE32 %s
+
+EL64:      MIPS ABI Flags {
+EL64-NEXT:   Version: 0
+EL64-NEXT:   ISA: MIPS64r5
+EL64-NEXT:   ISA Extension: Cavium Networks Octeon3 (0x13)
+EL64-NEXT:   ASEs [ (0x103)
+EL64-NEXT:     DSP (0x1)
+EL64-NEXT:     DSPR2 (0x2)
+EL64-NEXT:     VZ (0x100)
+EL64-NEXT:   ]
+EL64-NEXT:   FP ABI: Hard float (double precision) (0x1)
+EL64-NEXT:   GPR size: 64
+EL64-NEXT:   CPR1 size: 64
+EL64-NEXT:   CPR2 size: 0
+EL64-NEXT:   Flags 1 [ (0x1)
+EL64-NEXT:     ODDSPREG (0x1)
+EL64-NEXT:   ]
+EL64-NEXT:   Flags 2: 0x0
+EL64-NEXT: }
+
+BE32:      MIPS ABI Flags {
+BE32-NEXT:   Version: 0
+BE32-NEXT:   ISA: MIPS32r2
+BE32-NEXT:   ISA Extension: None (0x0)
+BE32-NEXT:   ASEs [ (0x803)
+BE32-NEXT:     DSP (0x1)
+BE32-NEXT:     DSPR2 (0x2)
+BE32-NEXT:     microMIPS (0x800)
+BE32-NEXT:   ]
+BE32-NEXT:   FP ABI: Soft float (0x3)
+BE32-NEXT:   GPR size: 32
+BE32-NEXT:   CPR1 size: 0
+BE32-NEXT:   CPR2 size: 0
+BE32-NEXT:   Flags 1 [ (0x1)
+BE32-NEXT:     ODDSPREG (0x1)
+BE32-NEXT:   ]
+BE32-NEXT:   Flags 2: 0x0
+BE32-NEXT: }

Modified: llvm/trunk/tools/llvm-readobj/ELFDumper.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-readobj/ELFDumper.cpp?rev=236737&r1=236736&r2=236737&view=diff
==============================================================================
--- llvm/trunk/tools/llvm-readobj/ELFDumper.cpp (original)
+++ llvm/trunk/tools/llvm-readobj/ELFDumper.cpp Thu May  7 10:40:35 2015
@@ -26,6 +26,7 @@
 #include "llvm/Support/Compiler.h"
 #include "llvm/Support/Format.h"
 #include "llvm/Support/MathExtras.h"
+#include "llvm/Support/MipsABIFlags.h"
 #include "llvm/Support/raw_ostream.h"
 
 using namespace llvm;
@@ -56,6 +57,7 @@ public:
 
   void printAttributes() override;
   void printMipsPLTGOT() override;
+  void printMipsABIFlags() override;
 
 private:
   typedef ELFFile<ELFT> ELFO;
@@ -170,6 +172,16 @@ findSectionByAddress(const ELFFile<ELFT>
   return nullptr;
 }
 
+template <class ELFT>
+static const typename ELFFile<ELFT>::Elf_Shdr *
+findSectionByName(const ELFFile<ELFT> &Obj, StringRef Name) {
+  for (const auto &Shdr : Obj.sections()) {
+    if (Name == errorOrDefault(Obj.getSectionName(&Shdr)))
+      return &Shdr;
+  }
+  return nullptr;
+}
+
 static const EnumEntry<unsigned> ElfClass[] = {
   { "None",   ELF::ELFCLASSNONE },
   { "32-bit", ELF::ELFCLASS32   },
@@ -1249,3 +1261,112 @@ template <class ELFT> void ELFDumper<ELF
 
   MipsGOTParser<ELFT>(Obj, W).parseGOT(*GotShdr);
 }
+
+static const EnumEntry<unsigned> ElfMipsISAExtType[] = {
+  {"None",                    Mips::AFL_EXT_NONE},
+  {"Broadcom SB-1",           Mips::AFL_EXT_SB1},
+  {"Cavium Networks Octeon",  Mips::AFL_EXT_OCTEON},
+  {"Cavium Networks Octeon2", Mips::AFL_EXT_OCTEON2},
+  {"Cavium Networks OcteonP", Mips::AFL_EXT_OCTEONP},
+  {"Cavium Networks Octeon3", Mips::AFL_EXT_OCTEON3},
+  {"LSI R4010",               Mips::AFL_EXT_4010},
+  {"Loongson 2E",             Mips::AFL_EXT_LOONGSON_2E},
+  {"Loongson 2F",             Mips::AFL_EXT_LOONGSON_2F},
+  {"Loongson 3A",             Mips::AFL_EXT_LOONGSON_3A},
+  {"MIPS R4650",              Mips::AFL_EXT_4650},
+  {"MIPS R5900",              Mips::AFL_EXT_5900},
+  {"MIPS R10000",             Mips::AFL_EXT_10000},
+  {"NEC VR4100",              Mips::AFL_EXT_4100},
+  {"NEC VR4111/VR4181",       Mips::AFL_EXT_4111},
+  {"NEC VR4120",              Mips::AFL_EXT_4120},
+  {"NEC VR5400",              Mips::AFL_EXT_5400},
+  {"NEC VR5500",              Mips::AFL_EXT_5500},
+  {"RMI Xlr",                 Mips::AFL_EXT_XLR},
+  {"Toshiba R3900",           Mips::AFL_EXT_3900}
+};
+
+static const EnumEntry<unsigned> ElfMipsASEFlags[] = {
+  {"DSP",                Mips::AFL_ASE_DSP},
+  {"DSPR2",              Mips::AFL_ASE_DSPR2},
+  {"Enhanced VA Scheme", Mips::AFL_ASE_EVA},
+  {"MCU",                Mips::AFL_ASE_MCU},
+  {"MDMX",               Mips::AFL_ASE_MDMX},
+  {"MIPS-3D",            Mips::AFL_ASE_MIPS3D},
+  {"MT",                 Mips::AFL_ASE_MT},
+  {"SmartMIPS",          Mips::AFL_ASE_SMARTMIPS},
+  {"VZ",                 Mips::AFL_ASE_VIRT},
+  {"MSA",                Mips::AFL_ASE_MSA},
+  {"MIPS16",             Mips::AFL_ASE_MIPS16},
+  {"microMIPS",          Mips::AFL_ASE_MICROMIPS},
+  {"XPA",                Mips::AFL_ASE_XPA}
+};
+
+static const EnumEntry<unsigned> ElfMipsFpABIType[] = {
+  {"Hard or soft float",                  Mips::Val_GNU_MIPS_ABI_FP_ANY},
+  {"Hard float (double precision)",       Mips::Val_GNU_MIPS_ABI_FP_DOUBLE},
+  {"Hard float (single precision)",       Mips::Val_GNU_MIPS_ABI_FP_SINGLE},
+  {"Soft float",                          Mips::Val_GNU_MIPS_ABI_FP_SOFT},
+  {"Hard float (MIPS32r2 64-bit FPU 12 callee-saved)",
+   Mips::Val_GNU_MIPS_ABI_FP_OLD_64},
+  {"Hard float (32-bit CPU, Any FPU)",    Mips::Val_GNU_MIPS_ABI_FP_XX},
+  {"Hard float (32-bit CPU, 64-bit FPU)", Mips::Val_GNU_MIPS_ABI_FP_64},
+  {"Hard float compat (32-bit CPU, 64-bit FPU)",
+   Mips::Val_GNU_MIPS_ABI_FP_64A}
+};
+
+static const EnumEntry<unsigned> ElfMipsFlags1[] {
+  {"ODDSPREG", Mips::AFL_FLAGS1_ODDSPREG},
+};
+
+static int getMipsRegisterSize(uint8_t Flag) {
+  switch (Flag) {
+  case Mips::AFL_REG_NONE:
+    return 0;
+  case Mips::AFL_REG_32:
+    return 32;
+  case Mips::AFL_REG_64:
+    return 64;
+  case Mips::AFL_REG_128:
+    return 128;
+  default:
+    return -1;
+  }
+}
+
+template <class ELFT> void ELFDumper<ELFT>::printMipsABIFlags() {
+  const Elf_Shdr *Shdr = findSectionByName(*Obj, ".MIPS.abiflags");
+  if (!Shdr) {
+    W.startLine() << "There is no .MIPS.abiflags section in the file.\n";
+    return;
+  }
+  ErrorOr<ArrayRef<uint8_t>> Sec = Obj->getSectionContents(Shdr);
+  if (!Sec) {
+    W.startLine() << "The .MIPS.abiflags section is empty.\n";
+    return;
+  }
+  if (Sec->size() != sizeof(Elf_Mips_ABIFlags<ELFT>)) {
+    W.startLine() << "The .MIPS.abiflags section has a wrong size.\n";
+    return;
+  }
+
+  auto *Flags = reinterpret_cast<const Elf_Mips_ABIFlags<ELFT> *>(Sec->data());
+
+  raw_ostream &OS = W.getOStream();
+  DictScope GS(W, "MIPS ABI Flags");
+
+  W.printNumber("Version", Flags->version);
+  W.startLine() << "ISA: ";
+  if (Flags->isa_rev <= 1)
+    OS << format("MIPS%u", Flags->isa_level);
+  else
+    OS << format("MIPS%ur%u", Flags->isa_level, Flags->isa_rev);
+  OS << "\n";
+  W.printEnum("ISA Extension", Flags->isa_ext, makeArrayRef(ElfMipsISAExtType));
+  W.printFlags("ASEs", Flags->ases, makeArrayRef(ElfMipsASEFlags));
+  W.printEnum("FP ABI", Flags->fp_abi, makeArrayRef(ElfMipsFpABIType));
+  W.printNumber("GPR size", getMipsRegisterSize(Flags->gpr_size));
+  W.printNumber("CPR1 size", getMipsRegisterSize(Flags->cpr1_size));
+  W.printNumber("CPR2 size", getMipsRegisterSize(Flags->cpr2_size));
+  W.printFlags("Flags 1", Flags->flags1, makeArrayRef(ElfMipsFlags1));
+  W.printHex("Flags 2", Flags->flags2);
+}

Modified: llvm/trunk/tools/llvm-readobj/ObjDumper.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-readobj/ObjDumper.h?rev=236737&r1=236736&r2=236737&view=diff
==============================================================================
--- llvm/trunk/tools/llvm-readobj/ObjDumper.h (original)
+++ llvm/trunk/tools/llvm-readobj/ObjDumper.h Thu May  7 10:40:35 2015
@@ -42,6 +42,7 @@ public:
 
   // Only implemented for MIPS ELF at this time.
   virtual void printMipsPLTGOT() { }
+  virtual void printMipsABIFlags() { }
 
   // Only implemented for PE/COFF.
   virtual void printCOFFImports() { }

Modified: llvm/trunk/tools/llvm-readobj/llvm-readobj.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-readobj/llvm-readobj.cpp?rev=236737&r1=236736&r2=236737&view=diff
==============================================================================
--- llvm/trunk/tools/llvm-readobj/llvm-readobj.cpp (original)
+++ llvm/trunk/tools/llvm-readobj/llvm-readobj.cpp Thu May  7 10:40:35 2015
@@ -148,6 +148,10 @@ namespace opts {
   MipsPLTGOT("mips-plt-got",
              cl::desc("Display the MIPS GOT and PLT GOT sections"));
 
+  // -mips-abi-flags
+  cl::opt<bool> MipsABIFlags("mips-abi-flags",
+                             cl::desc("Display the MIPS.abiflags section"));
+
   // -coff-imports
   cl::opt<bool>
   COFFImports("coff-imports", cl::desc("Display the PE/COFF import table"));
@@ -287,9 +291,12 @@ static void dumpObject(const ObjectFile
   if (Obj->getArch() == llvm::Triple::arm && Obj->isELF())
     if (opts::ARMAttributes)
       Dumper->printAttributes();
-  if (isMipsArch(Obj->getArch()) && Obj->isELF())
+  if (isMipsArch(Obj->getArch()) && Obj->isELF()) {
     if (opts::MipsPLTGOT)
       Dumper->printMipsPLTGOT();
+    if (opts::MipsABIFlags)
+      Dumper->printMipsABIFlags();
+  }
   if (opts::COFFImports)
     Dumper->printCOFFImports();
   if (opts::COFFExports)





More information about the llvm-commits mailing list