// TODO: Test this error.
return SymbolsOrErr.takeError();
- if (EF.getHeader().e_machine == ELF::EM_ARM) {
+ if (EF.getHeader().e_machine == ELF::EM_AARCH64) {
+ if (Expected<StringRef> NameOrErr = getSymbolName(Sym)) {
+ StringRef Name = *NameOrErr;
+ if (Name.startswith("$d") || Name.startswith("$x"))
+ Result |= SymbolRef::SF_FormatSpecific;
+ } else {
+ // TODO: Actually report errors helpfully.
+ consumeError(NameOrErr.takeError());
+ }
+ } else if (EF.getHeader().e_machine == ELF::EM_ARM) {
if (Expected<StringRef> NameOrErr = getSymbolName(Sym)) {
StringRef Name = *NameOrErr;
if (Name.startswith("$d") || Name.startswith("$t") ||
--- /dev/null
+# REQUIRES: aarch64-registered-target
+## Ignore AArch64 mapping symbols (with a prefix of $d or $x).
+
+# RUN: llvm-mc -filetype=obj -triple=aarch64 %s -o %t
+
+## Verify that mapping symbols are actually present in the object at expected
+## addresses.
+# RUN: llvm-nm --special-syms %t | FileCheck %s -check-prefix MAPPING_SYM
+
+# MAPPING_SYM: 0000000000000000 t $d.0
+# MAPPING_SYM-NEXT: 000000000000000c t $d.2
+# MAPPING_SYM-NEXT: 0000000000000004 t $x.1
+# MAPPING_SYM-NEXT: 0000000000000000 T foo
+
+# RUN: llvm-symbolizer --obj=%t 0 4 0xc | FileCheck %s -check-prefix SYMBOL
+
+# SYMBOL: foo
+# SYMBOL-NEXT: ??:0:0
+# SYMBOL-EMPTY:
+# SYMBOL: foo
+# SYMBOL-NEXT: ??:0:0
+# SYMBOL-EMPTY:
+# SYMBOL: foo
+# SYMBOL-NEXT: ??:0:0
+
+ .global foo
+foo:
+ .word 32
+ nop
+ nop
+ .word 42
## Ignore ARM mapping symbols (with a prefix of $a, $d or $t).
# RUN: llvm-mc -filetype=obj -triple=armv7-none-linux %s -o %t
-# RUN: llvm-symbolizer --obj=%t 4 8 | FileCheck %s
+
+## Verify that mapping symbols are actually present in the object at expected
+## addresses.
+# RUN: llvm-nm --special-syms %t | FileCheck %s -check-prefix MAPPING_A
+
+# MAPPING_A: 00000004 t $a.1
+# MAPPING_A-NEXT: 00000000 t $d.0
+# MAPPING_A-NEXT: 00000008 t $d.2
+# MAPPING_A-NEXT: 00000000 T foo
+
# RUN: llvm-mc -filetype=obj -triple=thumbv7-none-linux %s -o %tthumb
-# RUN: llvm-symbolizer --obj=%tthumb 4 8 | FileCheck %s
+# RUN: llvm-nm --special-syms %tthumb | FileCheck %s -check-prefix MAPPING_T
+
+# MAPPING_T: 00000000 t $d.0
+# MAPPING_T-NEXT: 00000006 t $d.2
+# MAPPING_T-NEXT: 00000004 t $t.1
+# MAPPING_T-NEXT: 00000000 T foo
+
+# RUN: llvm-symbolizer --obj=%t 4 8 | FileCheck %s -check-prefix SYMBOL
+# RUN: llvm-symbolizer --obj=%tthumb 4 8 | FileCheck %s -check-prefix SYMBOL
-# CHECK: foo
-# CHECK-NEXT: ??:0:0
-# CHECK-EMPTY:
-# CHECK-NEXT: foo
-# CHECK-NEXT: ??:0:0
+# SYMBOL: foo
+# SYMBOL-NEXT: ??:0:0
+# SYMBOL-EMPTY:
+# SYMBOL-NEXT: foo
+# SYMBOL-NEXT: ??:0:0
.globl foo
foo:
--- /dev/null
+## Test --special-syms flag for ARM mapping symbols used to mark transitions
+## between ARM code, THUMB code and data ($a, $t, $t).
+#
+# RUN: yaml2obj %s -o %t
+# RUN: llvm-nm %t | count 0
+# RUN: llvm-nm --special-syms %t | FileCheck %s
+
+!ELF
+FileHeader:
+ Class: ELFCLASS32
+ Data: ELFDATA2LSB
+ Type: ET_REL
+ Machine: EM_ARM
+ Flags: [ EF_ARM_EABI_VER5 ]
+Sections:
+ - Name: .text
+ Type: SHT_PROGBITS
+ Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
+ AddressAlign: 0x4
+Symbols:
+ - Name: '$d.0'
+ Section: .text
+ - Name: '$a.1'
+ Section: .text
+ - Name: '$t.1'
+ Section: .text
+
+# CHECK: 00000000 t $a.1
+# CHECK: 00000000 t $d.0
+# CHECK: 00000000 t $t.1
# RUN: yaml2obj %s -o %t.o
-# RUN: llvm-nm --special-syms --debug-syms %t.o | FileCheck %s --implicit-check-not {{.}} --check-prefix SYMBOL
-# RUN: llvm-nm --special-syms -a %t.o | FileCheck %s --implicit-check-not {{.}} --check-prefix SYMBOL
+# RUN: llvm-nm --debug-syms %t.o | FileCheck %s --implicit-check-not {{.}} --check-prefix SYMBOL
+# RUN: llvm-nm -a %t.o | FileCheck %s --implicit-check-not {{.}} --check-prefix SYMBOL
# SYMBOL: 0000000000000000 n $a
# SYMBOL-NEXT: 0000000000000000 n $d
}
}
-static bool isSpecialSym(SymbolicFile &Obj, StringRef Name) {
- auto *ELFObj = dyn_cast<ELFObjectFileBase>(&Obj);
- if (!ELFObj)
- return false;
- uint16_t EMachine = ELFObj->getEMachine();
- if (EMachine != ELF::EM_ARM && EMachine != ELF::EM_AARCH64)
- return false;
- return !Name.empty() && Name[0] == '$';
-}
-
static void sortAndPrintSymbolList(SymbolicFile &Obj, bool printName,
StringRef ArchiveName,
StringRef ArchitectureName) {
bool Undefined = SymFlags & SymbolRef::SF_Undefined;
bool Global = SymFlags & SymbolRef::SF_Global;
bool Weak = SymFlags & SymbolRef::SF_Weak;
+ bool FormatSpecific = SymFlags & SymbolRef::SF_FormatSpecific;
if ((!Undefined && UndefinedOnly) || (Undefined && DefinedOnly) ||
(!Global && ExternalOnly) || (Weak && NoWeakSymbols) ||
- (!SpecialSyms && isSpecialSym(Obj, Name)))
+ (FormatSpecific && !(SpecialSyms || DebugSyms)))
continue;
if (PrintFileName)
writeFileName(outs(), ArchiveName, ArchitectureName);
error(SymFlagsOrErr.takeError(), Obj.getFileName());
return;
}
- if (!DebugSyms && (*SymFlagsOrErr & SymbolRef::SF_FormatSpecific))
+
+ // Don't drop format specifc symbols for ARM and AArch64 ELF targets, they
+ // are used to repesent mapping symbols and needed to honor the
+ // --special-syms option.
+ auto *ELFObj = dyn_cast<ELFObjectFileBase>(&Obj);
+ if ((!ELFObj || (ELFObj->getEMachine() != ELF::EM_ARM &&
+ ELFObj->getEMachine() != ELF::EM_AARCH64)) &&
+ !DebugSyms && (*SymFlagsOrErr & SymbolRef::SF_FormatSpecific))
continue;
if (WithoutAliases && (*SymFlagsOrErr & SymbolRef::SF_Indirect))
continue;