Add printing of Mach-O stabs in llvm-nm.
authorKevin Enderby <enderby@apple.com>
Thu, 17 Jul 2014 22:47:16 +0000 (22:47 +0000)
committerKevin Enderby <enderby@apple.com>
Thu, 17 Jul 2014 22:47:16 +0000 (22:47 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@213327 91177308-0d34-0410-b5e6-96231b3b80d8

include/llvm/Support/MachO.h
test/Object/Inputs/macho-hello-g.macho-x86_64 [new file with mode: 0755]
test/Object/nm-trivial-object.test
tools/llvm-nm/llvm-nm.cpp

index bd4dc2f6d1b44f61a47157bf703b1edf50a5b6e1..57d7dff89333d5becc1ec6ad88be053b7ea8b10e 100644 (file)
@@ -386,13 +386,15 @@ namespace llvm {
 
     enum StabType {
       // Constant values for the "n_type" field in llvm::MachO::nlist and
-      // llvm::MachO::nlist_64 when "(n_type & NlistMaskStab) != 0"
+      // llvm::MachO::nlist_64 when "(n_type & N_STAB) != 0"
       N_GSYM    = 0x20u,
       N_FNAME   = 0x22u,
       N_FUN     = 0x24u,
       N_STSYM   = 0x26u,
       N_LCSYM   = 0x28u,
       N_BNSYM   = 0x2Eu,
+      N_PC      = 0x30u,
+      N_AST     = 0x32u,
       N_OPT     = 0x3Cu,
       N_RSYM    = 0x40u,
       N_SLINE   = 0x44u,
diff --git a/test/Object/Inputs/macho-hello-g.macho-x86_64 b/test/Object/Inputs/macho-hello-g.macho-x86_64
new file mode 100755 (executable)
index 0000000..41be03a
Binary files /dev/null and b/test/Object/Inputs/macho-hello-g.macho-x86_64 differ
index 98bf9f92f2f6286fd0f03be0113a064da7299fff..49c7683c80d4178619dc6770a514f5261ac3d2b6 100644 (file)
@@ -26,6 +26,8 @@ RUN: llvm-nm %p/Inputs/macho-text-data-bss.macho-x86_64 -s __DATA __data \
 RUN:         | FileCheck %s -check-prefix macho-s
 RUN: llvm-nm -x %p/Inputs/macho-text-data-bss.macho-x86_64 \
 RUN:         | FileCheck %s -check-prefix macho-x
+RUN: llvm-nm -p -a %p/Inputs/macho-hello-g.macho-x86_64 \
+RUN:         | FileCheck %s -check-prefix macho-pa
 RUN: llvm-nm %p/Inputs/common.coff-i386 \
 RUN:         | FileCheck %s -check-prefix COFF-COMMON
 RUN: llvm-nm %p/Inputs/relocatable-with-section-address.elf-x86-64 \
@@ -115,6 +117,19 @@ macho-x: 000000000000000c 0f 02 0000 00000004 _d
 macho-x: 0000000000000000 0f 01 0000 00000001 _t
 macho-x: 0000000000000048 0f 05 0000 00000007 _t.eh
 
+macho-pa: 0000000000000000 - 00 0000    SO /Volumes/SandBox/
+macho-pa: 0000000000000000 - 00 0000    SO hello.c
+macho-pa: 0000000053c8408d - 03 0001   OSO /Volumes/SandBox/hello.o
+macho-pa: 0000000100000f30 - 01 0000 BNSYM 
+macho-pa: 0000000100000f30 - 01 0000   FUN _main
+macho-pa: 000000000000003b - 00 0000   FUN 
+macho-pa: 000000000000003b - 01 0000 ENSYM 
+macho-pa: 0000000000000000 - 01 0000    SO 
+macho-pa: 0000000100000000 T __mh_execute_header
+macho-pa: 0000000100000f30 T _main
+macho-pa:                  U _printf
+macho-pa:                  U dyld_stub_binder
+
 Test that nm uses addresses even with ELF .o files.
 ELF-SEC-ADDR64:      0000000000000058 D a
 ELF-SEC-ADDR64-NEXT: 000000000000005c D b
index d3d4f998e64fe39b638f26132f3c9c72fc373304..b0336d3c8ce59cf059d72274ad115c44ef75a9b5 100644 (file)
@@ -457,6 +457,84 @@ static void darwinPrintSymbol(MachOObjectFile *MachO, SymbolListT::iterator I,
   outs() << "\n";
 }
 
+// Table that maps Darwin's Mach-O stab constants to strings to allow printing.
+struct DarwinStabName {
+  uint8_t NType;
+  const char *Name;
+};
+static const struct DarwinStabName DarwinStabNames[] = {
+    {MachO::N_GSYM, "GSYM"},
+    {MachO::N_FNAME, "FNAME"},
+    {MachO::N_FUN, "FUN"},
+    {MachO::N_STSYM, "STSYM"},
+    {MachO::N_LCSYM, "LCSYM"},
+    {MachO::N_BNSYM, "BNSYM"},
+    {MachO::N_PC, "PC"},
+    {MachO::N_AST, "AST"},
+    {MachO::N_OPT, "OPT"},
+    {MachO::N_RSYM, "RSYM"},
+    {MachO::N_SLINE, "SLINE"},
+    {MachO::N_ENSYM, "ENSYM"},
+    {MachO::N_SSYM, "SSYM"},
+    {MachO::N_SO, "SO"},
+    {MachO::N_OSO, "OSO"},
+    {MachO::N_LSYM, "LSYM"},
+    {MachO::N_BINCL, "BINCL"},
+    {MachO::N_SOL, "SOL"},
+    {MachO::N_PARAMS, "PARAM"},
+    {MachO::N_VERSION, "VERS"},
+    {MachO::N_OLEVEL, "OLEV"},
+    {MachO::N_PSYM, "PSYM"},
+    {MachO::N_EINCL, "EINCL"},
+    {MachO::N_ENTRY, "ENTRY"},
+    {MachO::N_LBRAC, "LBRAC"},
+    {MachO::N_EXCL, "EXCL"},
+    {MachO::N_RBRAC, "RBRAC"},
+    {MachO::N_BCOMM, "BCOMM"},
+    {MachO::N_ECOMM, "ECOMM"},
+    {MachO::N_ECOML, "ECOML"},
+    {MachO::N_LENG, "LENG"},
+    {0, 0}};
+static const char *getDarwinStabString(uint8_t NType) {
+  for (unsigned i = 0; DarwinStabNames[i].Name; i++) {
+    if (DarwinStabNames[i].NType == NType)
+      return DarwinStabNames[i].Name;
+  }
+  return 0;
+}
+
+// darwinPrintStab() prints the n_sect, n_desc along with a symbolic name of
+// a stab n_type value in a Mach-O file.
+static void darwinPrintStab(MachOObjectFile *MachO, SymbolListT::iterator I) {
+  MachO::nlist_64 STE_64;
+  MachO::nlist STE;
+  uint8_t NType;
+  uint8_t NSect;
+  uint16_t NDesc;
+  if (MachO->is64Bit()) {
+    STE_64 = MachO->getSymbol64TableEntry(I->Symb);
+    NType = STE_64.n_type;
+    NSect = STE_64.n_sect;
+    NDesc = STE_64.n_desc;
+  } else {
+    STE = MachO->getSymbolTableEntry(I->Symb);
+    NType = STE.n_type;
+    NSect = STE.n_sect;
+    NDesc = STE.n_desc;
+  }
+
+  char Str[18] = "";
+  format("%02x", NSect).print(Str, sizeof(Str));
+  outs() << ' ' << Str << ' ';
+  format("%04x", NDesc).print(Str, sizeof(Str));
+  outs() << Str << ' ';
+  if (const char *stabString = getDarwinStabString(NType))
+    format("%5.5s", stabString).print(Str, sizeof(Str));
+  else
+    format("   %02x", NType).print(Str, sizeof(Str));
+  outs() << Str;
+}
+
 static void sortAndPrintSymbolList(SymbolicFile *Obj, bool printName) {
   if (!NoSort) {
     if (NumericSort)
@@ -532,7 +610,10 @@ static void sortAndPrintSymbolList(SymbolicFile *Obj, bool printName) {
         if (I->Size != UnknownAddressOrSize)
           outs() << ' ';
       }
-      outs() << I->TypeChar << " " << I->Name << "\n";
+      outs() << I->TypeChar;
+      if (I->TypeChar == '-' && MachO)
+        darwinPrintStab(MachO, I);
+      outs() << " " << I->Name << "\n";
     } else if (OutputFormat == sysv) {
       std::string PaddedName(I->Name);
       while (PaddedName.length() < 20)
@@ -657,6 +738,9 @@ static char getSymbolNMTypeChar(MachOObjectFile &Obj, basic_symbol_iterator I) {
   DataRefImpl Symb = I->getRawDataRefImpl();
   uint8_t NType = getNType(Obj, Symb);
 
+  if (NType & MachO::N_STAB)
+    return '-';
+
   switch (NType & MachO::N_TYPE) {
   case MachO::N_ABS:
     return 's';