[lld] [LLD] [COFF] Fix symbol names for import thunks (PR #160694)

via llvm-commits llvm-commits at lists.llvm.org
Thu Sep 25 05:21:17 PDT 2025


llvmbot wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-platform-windows

Author: Martin Storsjö (mstorsjo)

<details>
<summary>Changes</summary>

9cc9efc483339ece1d52923569bb755db42b69f3 changed LLD to use a StringTableBuilder for optimizing the string table, used for long section and symbol names.

That commit had a bug, where the symbol table entry for an import thunk with a long symbol name wouldn't get fetched from the StringTableBuilder, if the base symbol name (without the "__imp_" prefix) wasn't over 8 chars.

This should fix issues with Go, which errors out on reading the executables with a broken symbol table, as noted in https://github.com/mstorsjo/llvm-mingw/issues/518 and https://github.com/golang/go/issues/75219.

---
Full diff: https://github.com/llvm/llvm-project/pull/160694.diff


2 Files Affected:

- (modified) lld/COFF/Writer.cpp (+1-1) 
- (modified) lld/test/COFF/strtab.s (+19-3) 


``````````diff
diff --git a/lld/COFF/Writer.cpp b/lld/COFF/Writer.cpp
index b4f00996319b1..258a82e371f3a 100644
--- a/lld/COFF/Writer.cpp
+++ b/lld/COFF/Writer.cpp
@@ -1620,7 +1620,7 @@ void Writer::createSymbolAndStringTable() {
             dthunk->wrappedSym->writtenToSymtab = true;
             if (std::optional<coff_symbol16> sym =
                     createSymbol(dthunk->wrappedSym)) {
-              if (d->getName().size() > COFF::NameSize)
+              if (dthunk->wrappedSym->getName().size() > COFF::NameSize)
                 longNameSymbols.emplace_back(outputSymtab.size(),
                                              dthunk->wrappedSym->getName());
               outputSymtab.push_back(*sym);
diff --git a/lld/test/COFF/strtab.s b/lld/test/COFF/strtab.s
index fbdd8df52d540..9edc13e19e825 100644
--- a/lld/test/COFF/strtab.s
+++ b/lld/test/COFF/strtab.s
@@ -1,17 +1,32 @@
 # REQUIRES: x86
 # RUN: llvm-mc -triple=x86_64-windows-msvc %s -filetype=obj -o %t.obj
-# RUN: lld-link -out:%t.exe -entry:main %t.obj -debug:dwarf
+# RUN: lld-link -machine:x64 -def:%S/Inputs/library.def -implib:%t.lib
+# RUN: lld-link -out:%t.exe -entry:main %t.obj %t.lib -debug:dwarf
 # RUN: llvm-readobj --string-table %t.exe | FileCheck %s
+# RUN: llvm-nm %t.exe | FileCheck %s --check-prefix=SYMBOLS
+
+# Note, for this test to have the intended test coverage, the imported symbol
+# "function" needs to be such that the symbol name itself is <= 8 chars, while
+# "__imp_"+name is >8 chars.
 
 # CHECK:      StringTable {
-# CHECK-NEXT:   Length: 87
+# CHECK-NEXT:   Length: 102
 # CHECK-NEXT:   [     4] .debug_abbrev
 # CHECK-NEXT:   [    12] .debug_line
 # CHECK-NEXT:   [    1e] long_name_symbolz
 # CHECK-NEXT:   [    30] .debug_abbrez
-# CHECK-NEXT:   [    3e] __impl_long_name_symbolA
+# CHECK-NEXT:   [    3e] __imp_function
+# CHECK-NEXT:   [    4d] __impl_long_name_symbolA
 # CHECK-NEXT: }
 
+# SYMBOLS:      140001000 N .debug_abbrez
+# SYMBOLS-NEXT: 140002070 R __imp_function
+# SYMBOLS-NEXT: 140001000 t __impl_long_name_symbolA
+# SYMBOLS-NEXT: 140001010 T function
+# SYMBOLS-NEXT: 140001000 t long_name_symbolA
+# SYMBOLS-NEXT: 140001000 t long_name_symbolz
+# SYMBOLS-NEXT: 140001000 T main
+# SYMBOLS-NEXT: 140001000 t name_symbolA
 
 .global main
 .text
@@ -21,6 +36,7 @@ long_name_symbolA:
 __impl_long_name_symbolA:
 name_symbolA:
 .debug_abbrez:
+  call function
   ret
 
 .section        .debug_abbrev,"dr"

``````````

</details>


https://github.com/llvm/llvm-project/pull/160694


More information about the llvm-commits mailing list