[lld] 8610cb0 - [ELF] -r: don't define _TLS_MODULE_BASE_
Fangrui Song via llvm-commits
llvm-commits at lists.llvm.org
Tue Nov 22 12:59:49 PST 2022
Author: Fangrui Song
Date: 2022-11-22T12:59:45-08:00
New Revision: 8610cb04605bbae3399972875aef69e5e457a879
URL: https://github.com/llvm/llvm-project/commit/8610cb04605bbae3399972875aef69e5e457a879
DIFF: https://github.com/llvm/llvm-project/commit/8610cb04605bbae3399972875aef69e5e457a879.diff
LOG: [ELF] -r: don't define _TLS_MODULE_BASE_
_TLS_MODULE_BASE_ is supposed to be defined by the final link. Defining it in a
relocatable link may render the final link value incorrect.
GNU ld i386/x86-64 have the same issue: https://sourceware.org/bugzilla/show_bug.cgi?id=29820
Added:
Modified:
lld/ELF/Writer.cpp
lld/test/ELF/x86-64-tlsdesc-ld.s
Removed:
################################################################################
diff --git a/lld/ELF/Writer.cpp b/lld/ELF/Writer.cpp
index 1098813a1114..eb5ebc8bdf8c 100644
--- a/lld/ELF/Writer.cpp
+++ b/lld/ELF/Writer.cpp
@@ -1862,26 +1862,26 @@ template <class ELFT> void Writer<ELFT>::finalizeSections() {
addOptionalRegular("__global_pointer$", sec ? sec : Out::elfHeader, 0x800,
STV_DEFAULT);
}
- }
- if (config->emachine == EM_386 || config->emachine == EM_X86_64) {
- // On targets that support TLSDESC, _TLS_MODULE_BASE_ is defined in such a
- // way that:
- //
- // 1) Without relaxation: it produces a dynamic TLSDESC relocation that
- // computes 0.
- // 2) With LD->LE relaxation: _TLS_MODULE_BASE_ at tpoff = 0 (lowest address in
- // the TLS block).
- //
- // 2) is special cased in @tpoff computation. To satisfy 1), we define it as
- // an absolute symbol of zero. This is
diff erent from GNU linkers which
- // define _TLS_MODULE_BASE_ relative to the first TLS section.
- Symbol *s = symtab.find("_TLS_MODULE_BASE_");
- if (s && s->isUndefined()) {
- s->resolve(Defined{/*file=*/nullptr, StringRef(), STB_GLOBAL, STV_HIDDEN,
- STT_TLS, /*value=*/0, 0,
- /*section=*/nullptr});
- ElfSym::tlsModuleBase = cast<Defined>(s);
+ if (config->emachine == EM_386 || config->emachine == EM_X86_64) {
+ // On targets that support TLSDESC, _TLS_MODULE_BASE_ is defined in such a
+ // way that:
+ //
+ // 1) Without relaxation: it produces a dynamic TLSDESC relocation that
+ // computes 0.
+ // 2) With LD->LE relaxation: _TLS_MODULE_BASE_ at tpoff = 0 (lowest address
+ // in the TLS block).
+ //
+ // 2) is special cased in @tpoff computation. To satisfy 1), we define it
+ // as an absolute symbol of zero. This is
diff erent from GNU linkers which
+ // define _TLS_MODULE_BASE_ relative to the first TLS section.
+ Symbol *s = symtab.find("_TLS_MODULE_BASE_");
+ if (s && s->isUndefined()) {
+ s->resolve(Defined{/*file=*/nullptr, StringRef(), STB_GLOBAL,
+ STV_HIDDEN, STT_TLS, /*value=*/0, 0,
+ /*section=*/nullptr});
+ ElfSym::tlsModuleBase = cast<Defined>(s);
+ }
}
}
diff --git a/lld/test/ELF/x86-64-tlsdesc-ld.s b/lld/test/ELF/x86-64-tlsdesc-ld.s
index 957decf54a4c..2f55aed4159b 100644
--- a/lld/test/ELF/x86-64-tlsdesc-ld.s
+++ b/lld/test/ELF/x86-64-tlsdesc-ld.s
@@ -32,6 +32,14 @@
# LE-NEXT: movl %fs:-8(%rax), %edx
# LE-NEXT: addl %fs:-4(%rax), %edx
+# RUN: ld.lld -r %t.o -o %t.ro
+# RUN: llvm-readelf -s %t.ro | FileCheck --check-prefix=RELOCATABLE %s
+# RUN: ld.lld %t.ro -o %t
+# RUN: llvm-readelf -r %t | FileCheck --check-prefix=NOREL %s
+# RUN: llvm-objdump --no-print-imm-hex -d --no-show-raw-insn %t | FileCheck --check-prefix=LE %s
+
+# RELOCATABLE: 0000000000000000 0 TLS GLOBAL DEFAULT UND _TLS_MODULE_BASE_
+
leaq _TLS_MODULE_BASE_ at tlsdesc(%rip), %rax
call *_TLS_MODULE_BASE_ at tlscall(%rax)
movl %fs:a at dtpoff(%rax), %edx
More information about the llvm-commits
mailing list