[llvm-branch-commits] [llvm] c9be4ef - [X86] Add TLS_(base_)addrX32 for X32 mode
Harald van Dijk via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Wed Dec 2 14:25:10 PST 2020
Author: Harald van Dijk
Date: 2020-12-02T22:20:36Z
New Revision: c9be4ef184c1a8cb042ae846f9f1818b3ffcddb0
URL: https://github.com/llvm/llvm-project/commit/c9be4ef184c1a8cb042ae846f9f1818b3ffcddb0
DIFF: https://github.com/llvm/llvm-project/commit/c9be4ef184c1a8cb042ae846f9f1818b3ffcddb0.diff
LOG: [X86] Add TLS_(base_)addrX32 for X32 mode
LLVM has TLS_(base_)addr32 for 32-bit TLS addresses in 32-bit mode, and
TLS_(base_)addr64 for 64-bit TLS addresses in 64-bit mode. x32 mode wants 32-bit
TLS addresses in 64-bit mode, which were not yet handled. This adds
TLS_(base_)addrX32 as copies of TLS_(base_)addr64, except that they use
tls32(base)addr rather than tls64(base)addr, and then restricts
TLS_(base_)addr64 to 64-bit LP64 mode, TLS_(base_)addrX32 to 64-bit ILP32 mode.
Reviewed By: RKSimon
Differential Revision: https://reviews.llvm.org/D92346
Added:
Modified:
llvm/lib/Target/X86/X86ISelLowering.cpp
llvm/lib/Target/X86/X86InstrCompiler.td
llvm/lib/Target/X86/X86MCInstLower.cpp
llvm/test/CodeGen/X86/pic.ll
Removed:
################################################################################
diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp
index 56e098a48dd5..caf9e690f5b8 100644
--- a/llvm/lib/Target/X86/X86ISelLowering.cpp
+++ b/llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -19123,7 +19123,7 @@ LowerToTLSGeneralDynamicModel32(GlobalAddressSDNode *GA, SelectionDAG &DAG,
return GetTLSADDR(DAG, Chain, GA, &InFlag, PtrVT, X86::EAX, X86II::MO_TLSGD);
}
-// Lower ISD::GlobalTLSAddress using the "general dynamic" model, 64 bit
+// Lower ISD::GlobalTLSAddress using the "general dynamic" model, 64 bit LP64
static SDValue
LowerToTLSGeneralDynamicModel64(GlobalAddressSDNode *GA, SelectionDAG &DAG,
const EVT PtrVT) {
@@ -19131,6 +19131,14 @@ LowerToTLSGeneralDynamicModel64(GlobalAddressSDNode *GA, SelectionDAG &DAG,
X86::RAX, X86II::MO_TLSGD);
}
+// Lower ISD::GlobalTLSAddress using the "general dynamic" model, 64 bit ILP32
+static SDValue
+LowerToTLSGeneralDynamicModelX32(GlobalAddressSDNode *GA, SelectionDAG &DAG,
+ const EVT PtrVT) {
+ return GetTLSADDR(DAG, DAG.getEntryNode(), GA, nullptr, PtrVT,
+ X86::EAX, X86II::MO_TLSGD);
+}
+
static SDValue LowerToTLSLocalDynamicModel(GlobalAddressSDNode *GA,
SelectionDAG &DAG,
const EVT PtrVT,
@@ -19241,8 +19249,11 @@ X86TargetLowering::LowerGlobalTLSAddress(SDValue Op, SelectionDAG &DAG) const {
TLSModel::Model model = DAG.getTarget().getTLSModel(GV);
switch (model) {
case TLSModel::GeneralDynamic:
- if (Subtarget.is64Bit())
- return LowerToTLSGeneralDynamicModel64(GA, DAG, PtrVT);
+ if (Subtarget.is64Bit()) {
+ if (Subtarget.isTarget64BitLP64())
+ return LowerToTLSGeneralDynamicModel64(GA, DAG, PtrVT);
+ return LowerToTLSGeneralDynamicModelX32(GA, DAG, PtrVT);
+ }
return LowerToTLSGeneralDynamicModel32(GA, DAG, PtrVT);
case TLSModel::LocalDynamic:
return LowerToTLSLocalDynamicModel(GA, DAG, PtrVT,
@@ -33511,8 +33522,10 @@ X86TargetLowering::EmitInstrWithCustomInserter(MachineInstr &MI,
default: llvm_unreachable("Unexpected instr type to insert");
case X86::TLS_addr32:
case X86::TLS_addr64:
+ case X86::TLS_addrX32:
case X86::TLS_base_addr32:
case X86::TLS_base_addr64:
+ case X86::TLS_base_addrX32:
return EmitLoweredTLSAddr(MI, BB);
case X86::INDIRECT_THUNK_CALL32:
case X86::INDIRECT_THUNK_CALL64:
diff --git a/llvm/lib/Target/X86/X86InstrCompiler.td b/llvm/lib/Target/X86/X86InstrCompiler.td
index 9f180c4c91aa..0c9f972cf225 100644
--- a/llvm/lib/Target/X86/X86InstrCompiler.td
+++ b/llvm/lib/Target/X86/X86InstrCompiler.td
@@ -467,11 +467,19 @@ let Defs = [RAX, RCX, RDX, RSI, RDI, R8, R9, R10, R11,
def TLS_addr64 : I<0, Pseudo, (outs), (ins i64mem:$sym),
"# TLS_addr64",
[(X86tlsaddr tls64addr:$sym)]>,
- Requires<[In64BitMode]>;
+ Requires<[In64BitMode, IsLP64]>;
def TLS_base_addr64 : I<0, Pseudo, (outs), (ins i64mem:$sym),
"# TLS_base_addr64",
[(X86tlsbaseaddr tls64baseaddr:$sym)]>,
- Requires<[In64BitMode]>;
+ Requires<[In64BitMode, IsLP64]>;
+def TLS_addrX32 : I<0, Pseudo, (outs), (ins i32mem:$sym),
+ "# TLS_addrX32",
+ [(X86tlsaddr tls32addr:$sym)]>,
+ Requires<[In64BitMode, NotLP64]>;
+def TLS_base_addrX32 : I<0, Pseudo, (outs), (ins i32mem:$sym),
+ "# TLS_base_addrX32",
+ [(X86tlsbaseaddr tls32baseaddr:$sym)]>,
+ Requires<[In64BitMode, NotLP64]>;
}
// Darwin TLS Support
diff --git a/llvm/lib/Target/X86/X86MCInstLower.cpp b/llvm/lib/Target/X86/X86MCInstLower.cpp
index af86c1fc7206..db015b1d9036 100644
--- a/llvm/lib/Target/X86/X86MCInstLower.cpp
+++ b/llvm/lib/Target/X86/X86MCInstLower.cpp
@@ -977,20 +977,22 @@ void X86MCInstLower::Lower(const MachineInstr *MI, MCInst &OutMI) const {
void X86AsmPrinter::LowerTlsAddr(X86MCInstLower &MCInstLowering,
const MachineInstr &MI) {
NoAutoPaddingScope NoPadScope(*OutStreamer);
- bool Is64Bits = MI.getOpcode() == X86::TLS_addr64 ||
- MI.getOpcode() == X86::TLS_base_addr64;
+ bool Is64Bits = MI.getOpcode() != X86::TLS_addr32 &&
+ MI.getOpcode() != X86::TLS_base_addr32;
MCContext &Ctx = OutStreamer->getContext();
MCSymbolRefExpr::VariantKind SRVK;
switch (MI.getOpcode()) {
case X86::TLS_addr32:
case X86::TLS_addr64:
+ case X86::TLS_addrX32:
SRVK = MCSymbolRefExpr::VK_TLSGD;
break;
case X86::TLS_base_addr32:
SRVK = MCSymbolRefExpr::VK_TLSLDM;
break;
case X86::TLS_base_addr64:
+ case X86::TLS_base_addrX32:
SRVK = MCSymbolRefExpr::VK_TLSLD;
break;
default:
@@ -2445,8 +2447,10 @@ void X86AsmPrinter::emitInstruction(const MachineInstr *MI) {
case X86::TLS_addr32:
case X86::TLS_addr64:
+ case X86::TLS_addrX32:
case X86::TLS_base_addr32:
case X86::TLS_base_addr64:
+ case X86::TLS_base_addrX32:
return LowerTlsAddr(MCInstLowering, *MI);
case X86::MOVPC32r: {
diff --git a/llvm/test/CodeGen/X86/pic.ll b/llvm/test/CodeGen/X86/pic.ll
index 34165d47bcb1..c936333a5726 100644
--- a/llvm/test/CodeGen/X86/pic.ll
+++ b/llvm/test/CodeGen/X86/pic.ll
@@ -252,3 +252,36 @@ declare void @foo6(...)
declare void @foo3(...)
declare void @foo4(...)
declare void @foo5(...)
+
+;; Check TLS references
+ at tlsptr = external thread_local global i32*
+ at tlsdst = external thread_local global i32
+ at tlssrc = external thread_local global i32
+
+define void @test8() nounwind {
+entry:
+ store i32* @tlsdst, i32** @tlsptr
+ %tmp.s = load i32, i32* @tlssrc
+ store i32 %tmp.s, i32* @tlsdst
+ ret void
+
+; CHECK-LABEL: test8:
+; CHECK-I686: calll .L8$pb
+; CHECK-I686-NEXT: .L8$pb:
+; CHECK-I686-NEXT: popl
+; CHECK-I686: addl $_GLOBAL_OFFSET_TABLE_+(.L{{.*}}-.L8$pb), %ebx
+; CHECK-I686-DAG: leal tlsdst at TLSGD(,%ebx), %eax
+; CHECK-I686-DAG: calll ___tls_get_addr at PLT
+; CHECK-I686-DAG: leal tlsptr at TLSGD(,%ebx), %eax
+; CHECK-I686-DAG: calll ___tls_get_addr at PLT
+; CHECK-I686-DAG: leal tlssrc at TLSGD(,%ebx), %eax
+; CHECK-I686-DAG: calll ___tls_get_addr at PLT
+; CHECK-X32-DAG: leaq tlsdst at TLSGD(%rip), %rdi
+; CHECK-X32-DAG: callq __tls_get_addr at PLT
+; CHECK-X32-DAG: leaq tlsptr at TLSGD(%rip), %rdi
+; CHECK-X32-DAG: callq __tls_get_addr at PLT
+; CHECK-X32-DAG: leaq tlssrc at TLSGD(%rip), %rdi
+; CHECK-X32-DAG: callq __tls_get_addr at PLT
+; CHECK-I686: ret
+; CHECK-X32: retq
+}
More information about the llvm-branch-commits
mailing list