[lld] 10e40a4 - [lld] Add support for other demanglers other than Itanium

Luís Ferreira via llvm-commits llvm-commits at lists.llvm.org
Tue Jan 4 19:27:52 PST 2022


Author: Luís Ferreira
Date: 2022-01-05T03:25:41Z
New Revision: 10e40a4ea3503d0ec352fd5699bc0875ee008efb

URL: https://github.com/llvm/llvm-project/commit/10e40a4ea3503d0ec352fd5699bc0875ee008efb
DIFF: https://github.com/llvm/llvm-project/commit/10e40a4ea3503d0ec352fd5699bc0875ee008efb.diff

LOG: [lld] Add support for other demanglers other than Itanium

LLVM core library supports demangling other mangled symbols other than itanium,
such as D and Rust. LLD should use those demanglers in order to output pretty
demangled symbols on error messages.

Reviewed By: MaskRay, #lld-macho

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

Added: 
    

Modified: 
    lld/COFF/Symbols.cpp
    lld/Common/Strings.cpp
    lld/ELF/SymbolTable.cpp
    lld/ELF/Symbols.cpp
    lld/MachO/CMakeLists.txt
    lld/MachO/Symbols.cpp
    lld/include/lld/Common/Strings.h
    lld/test/ELF/undef.s
    lld/wasm/Symbols.cpp

Removed: 
    


################################################################################
diff  --git a/lld/COFF/Symbols.cpp b/lld/COFF/Symbols.cpp
index 8a6a9b27d45fa..a03cb03f8d175 100644
--- a/lld/COFF/Symbols.cpp
+++ b/lld/COFF/Symbols.cpp
@@ -36,9 +36,9 @@ static std::string maybeDemangleSymbol(StringRef symName) {
     StringRef demangleInput = prefixless;
     if (config->machine == I386)
       demangleInput.consume_front("_");
-    std::string demangled = demangle(std::string(demangleInput));
+    std::string demangled = demangle(demangleInput, true);
     if (demangled != demangleInput)
-      return prefix + demangle(std::string(demangleInput));
+      return prefix + demangle(demangleInput, true);
     return (prefix + prefixless).str();
   }
   return std::string(symName);

diff  --git a/lld/Common/Strings.cpp b/lld/Common/Strings.cpp
index 7bf336490dae0..6e5478e335ca3 100644
--- a/lld/Common/Strings.cpp
+++ b/lld/Common/Strings.cpp
@@ -9,7 +9,6 @@
 #include "lld/Common/Strings.h"
 #include "lld/Common/ErrorHandler.h"
 #include "lld/Common/LLVM.h"
-#include "llvm/Demangle/Demangle.h"
 #include "llvm/Support/FileSystem.h"
 #include "llvm/Support/GlobPattern.h"
 #include <algorithm>
@@ -19,18 +18,6 @@
 using namespace llvm;
 using namespace lld;
 
-// Returns the demangled C++ symbol name for name.
-std::string lld::demangleItanium(StringRef name) {
-  // demangleItanium() can be called for all symbols. Only demangle C++ symbols,
-  // to avoid getting unexpected result for a C symbol that happens to match a
-  // mangled type name such as "Pi" (which would demangle to "int*").
-  if (!name.startswith("_Z") && !name.startswith("__Z") &&
-      !name.startswith("___Z") && !name.startswith("____Z"))
-    return std::string(name);
-
-  return demangle(std::string(name));
-}
-
 SingleStringMatcher::SingleStringMatcher(StringRef Pattern) {
   if (Pattern.size() > 2 && Pattern.startswith("\"") &&
       Pattern.endswith("\"")) {

diff  --git a/lld/ELF/SymbolTable.cpp b/lld/ELF/SymbolTable.cpp
index c93a166daa6e4..ec425cd7e1d12 100644
--- a/lld/ELF/SymbolTable.cpp
+++ b/lld/ELF/SymbolTable.cpp
@@ -143,12 +143,13 @@ StringMap<SmallVector<Symbol *, 0>> &SymbolTable::getDemangledSyms() {
         StringRef name = sym->getName();
         size_t pos = name.find('@');
         if (pos == std::string::npos)
-          demangled = demangleItanium(name);
+          demangled = demangle(name, config->demangle);
         else if (pos + 1 == name.size() || name[pos + 1] == '@')
-          demangled = demangleItanium(name.substr(0, pos));
+          demangled = demangle(name.substr(0, pos), config->demangle);
         else
-          demangled =
-              (demangleItanium(name.substr(0, pos)) + name.substr(pos)).str();
+          demangled = (demangle(name.substr(0, pos), config->demangle) +
+                       name.substr(pos))
+                          .str();
         (*demangledSyms)[demangled].push_back(sym);
       }
   }

diff  --git a/lld/ELF/Symbols.cpp b/lld/ELF/Symbols.cpp
index acb0dd27d0abf..ed83b75953dd9 100644
--- a/lld/ELF/Symbols.cpp
+++ b/lld/ELF/Symbols.cpp
@@ -26,16 +26,9 @@ using namespace llvm::ELF;
 using namespace lld;
 using namespace lld::elf;
 
-// Returns a symbol for an error message.
-static std::string demangle(StringRef symName) {
-  if (elf::config->demangle)
-    return demangleItanium(symName);
-  return std::string(symName);
-}
-
 std::string lld::toString(const elf::Symbol &sym) {
   StringRef name = sym.getName();
-  std::string ret = demangle(name);
+  std::string ret = demangle(name, config->demangle);
 
   const char *suffix = sym.getVersionSuffix();
   if (*suffix == '@')
@@ -44,7 +37,7 @@ std::string lld::toString(const elf::Symbol &sym) {
 }
 
 std::string lld::toELFString(const Archive::Symbol &b) {
-  return demangle(b.getName());
+  return demangle(b.getName(), config->demangle);
 }
 
 Defined *ElfSym::bss;

diff  --git a/lld/MachO/CMakeLists.txt b/lld/MachO/CMakeLists.txt
index a524544045c2d..abc9e473ef515 100644
--- a/lld/MachO/CMakeLists.txt
+++ b/lld/MachO/CMakeLists.txt
@@ -38,6 +38,7 @@ add_lld_library(lldMachO
   BitReader
   Core
   DebugInfoDWARF
+  Demangle
   LTO
   MC
   ObjCARCOpts

diff  --git a/lld/MachO/Symbols.cpp b/lld/MachO/Symbols.cpp
index bb6d073dcf308..b0ebd224affbd 100644
--- a/lld/MachO/Symbols.cpp
+++ b/lld/MachO/Symbols.cpp
@@ -9,6 +9,7 @@
 #include "Symbols.h"
 #include "InputFiles.h"
 #include "SyntheticSections.h"
+#include "lld/Common/Strings.h"
 
 using namespace llvm;
 using namespace lld;
@@ -27,17 +28,12 @@ static_assert(sizeof(void *) != 8 || sizeof(Defined) == 80,
 static_assert(sizeof(SymbolUnion) == sizeof(Defined),
               "Defined should be the largest Symbol kind");
 
-// Returns a symbol for an error message.
-static std::string demangle(StringRef symName) {
-  if (config->demangle)
-    return demangleItanium(symName);
-  return std::string(symName);
+std::string lld::toString(const Symbol &sym) {
+  return demangle(sym.getName(), config->demangle);
 }
 
-std::string lld::toString(const Symbol &sym) { return demangle(sym.getName()); }
-
 std::string lld::toMachOString(const object::Archive::Symbol &b) {
-  return demangle(b.getName());
+  return demangle(b.getName(), config->demangle);
 }
 
 uint64_t Symbol::getStubVA() const { return in.stubs->getVA(stubsIndex); }

diff  --git a/lld/include/lld/Common/Strings.h b/lld/include/lld/Common/Strings.h
index 71126f6150171..ece801892767a 100644
--- a/lld/include/lld/Common/Strings.h
+++ b/lld/include/lld/Common/Strings.h
@@ -12,14 +12,19 @@
 #include "llvm/ADT/ArrayRef.h"
 #include "llvm/ADT/Optional.h"
 #include "llvm/ADT/StringRef.h"
+#include "llvm/Demangle/Demangle.h"
 #include "llvm/Support/GlobPattern.h"
 #include <string>
 #include <vector>
 
 namespace lld {
-// Returns a demangled C++ symbol name. If Name is not a mangled
-// name, it returns name.
-std::string demangleItanium(llvm::StringRef name);
+// Returns a demangled symbol name. If Name is not a mangled name, it returns
+// name.
+inline std::string demangle(llvm::StringRef symName, bool shouldDemangle) {
+  if (shouldDemangle)
+    return llvm::demangle(symName.str().c_str());
+  return std::string(symName);
+}
 
 std::vector<uint8_t> parseHex(llvm::StringRef s);
 bool isValidCIdentifier(llvm::StringRef s);

diff  --git a/lld/test/ELF/undef.s b/lld/test/ELF/undef.s
index 931a482e1810b..6398b73d51e62 100644
--- a/lld/test/ELF/undef.s
+++ b/lld/test/ELF/undef.s
@@ -31,6 +31,18 @@
 # CHECK-NEXT: >>> referenced by undef.s
 # CHECK-NEXT: >>>               {{.*}}:(.text+0x1A)
 
+# CHECK:      error: undefined symbol: Pi
+# CHECK-NEXT: >>> referenced by undef.s
+# CHECK-NEXT: >>>               {{.*}}:(.text+0x1F)
+
+# CHECK:      error: undefined symbol: D main
+# CHECK-NEXT: >>> referenced by undef.s
+# CHECK-NEXT: >>>               {{.*}}:(.text+0x24)
+
+# CHECK:      error: undefined symbol: a::main
+# CHECK-NEXT: >>> referenced by undef.s
+# CHECK-NEXT: >>>               {{.*}}:(.text+0x29)
+
 # CHECK:      error: undefined symbol: zed2
 # CHECK-NEXT: >>> referenced by {{.*}}.o:(.text+0x0) in archive {{.*}}2.a
 
@@ -84,3 +96,6 @@ _start:
   call _Z3fooi
   call _ZTV3Foo
   call __Z3fooi
+  call Pi
+  call _Dmain
+  call _RNvC1a4main

diff  --git a/lld/wasm/Symbols.cpp b/lld/wasm/Symbols.cpp
index 08f532deea0be..5e6dcf8ca7919 100644
--- a/lld/wasm/Symbols.cpp
+++ b/lld/wasm/Symbols.cpp
@@ -22,6 +22,7 @@
 using namespace llvm;
 using namespace llvm::object;
 using namespace llvm::wasm;
+using namespace lld::wasm;
 
 namespace lld {
 std::string toString(const wasm::Symbol &sym) {
@@ -33,9 +34,8 @@ std::string maybeDemangleSymbol(StringRef name) {
   // `main` in the case where we need to pass it arguments.
   if (name == "__main_argc_argv")
     return "main";
-  if (wasm::config->demangle)
-    return demangleItanium(name);
-  return std::string(name);
+
+  return demangle(name, config->demangle);
 }
 
 std::string toString(wasm::Symbol::Kind kind) {


        


More information about the llvm-commits mailing list