[llvm] r237772 - [X86] Implement the local-exec TLS model for Windows targets

David Majnemer david.majnemer at gmail.com
Tue May 19 21:45:26 PDT 2015


Author: majnemer
Date: Tue May 19 23:45:26 2015
New Revision: 237772

URL: http://llvm.org/viewvc/llvm-project?rev=237772&view=rev
Log:
[X86] Implement the local-exec TLS model for Windows targets

We know that _tls_index is zero for local-exec TLS variables because
they are always defined in the executable.

Modified:
    llvm/trunk/lib/Target/X86/X86ISelLowering.cpp
    llvm/trunk/test/CodeGen/X86/tls.ll

Modified: llvm/trunk/lib/Target/X86/X86ISelLowering.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/X86/X86ISelLowering.cpp?rev=237772&r1=237771&r2=237772&view=diff
==============================================================================
--- llvm/trunk/lib/Target/X86/X86ISelLowering.cpp (original)
+++ llvm/trunk/lib/Target/X86/X86ISelLowering.cpp Tue May 19 23:45:26 2015
@@ -11289,7 +11289,6 @@ X86TargetLowering::LowerGlobalTLSAddress
 
   if (Subtarget->isTargetELF()) {
     TLSModel::Model model = DAG.getTarget().getTLSModel(GV);
-
     switch (model) {
       case TLSModel::GeneralDynamic:
         if (Subtarget->is64Bit())
@@ -11388,21 +11387,27 @@ X86TargetLowering::LowerGlobalTLSAddress
         DAG.getLoad(getPointerTy(), dl, Chain, TlsArray,
                     MachinePointerInfo(Ptr), false, false, false, 0);
 
-    // Load the _tls_index variable
-    SDValue IDX = DAG.getExternalSymbol("_tls_index", getPointerTy());
-    if (Subtarget->is64Bit())
-      IDX = DAG.getExtLoad(ISD::ZEXTLOAD, dl, getPointerTy(), Chain,
-                           IDX, MachinePointerInfo(), MVT::i32,
-                           false, false, false, 0);
-    else
-      IDX = DAG.getLoad(getPointerTy(), dl, Chain, IDX, MachinePointerInfo(),
-                        false, false, false, 0);
+    SDValue res;
+    if (GV->getThreadLocalMode() == GlobalVariable::LocalExecTLSModel) {
+      res = ThreadPointer;
+    } else {
+      // Load the _tls_index variable
+      SDValue IDX = DAG.getExternalSymbol("_tls_index", getPointerTy());
+      if (Subtarget->is64Bit())
+        IDX = DAG.getExtLoad(ISD::ZEXTLOAD, dl, getPointerTy(), Chain, IDX,
+                             MachinePointerInfo(), MVT::i32, false, false,
+                             false, 0);
+      else
+        IDX = DAG.getLoad(getPointerTy(), dl, Chain, IDX, MachinePointerInfo(),
+                          false, false, false, 0);
+
+      SDValue Scale = DAG.getConstant(Log2_64_Ceil(TD->getPointerSize()), dl,
+                                      getPointerTy());
+      IDX = DAG.getNode(ISD::SHL, dl, getPointerTy(), IDX, Scale);
 
-    SDValue Scale = DAG.getConstant(Log2_64_Ceil(TD->getPointerSize()), dl,
-                                    getPointerTy());
-    IDX = DAG.getNode(ISD::SHL, dl, getPointerTy(), IDX, Scale);
+      res = DAG.getNode(ISD::ADD, dl, getPointerTy(), ThreadPointer, IDX);
+    }
 
-    SDValue res = DAG.getNode(ISD::ADD, dl, getPointerTy(), ThreadPointer, IDX);
     res = DAG.getLoad(getPointerTy(), dl, Chain, res, MachinePointerInfo(),
                       false, false, false, 0);
 

Modified: llvm/trunk/test/CodeGen/X86/tls.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/X86/tls.ll?rev=237772&r1=237771&r2=237772&view=diff
==============================================================================
--- llvm/trunk/test/CodeGen/X86/tls.ll (original)
+++ llvm/trunk/test/CodeGen/X86/tls.ll Tue May 19 23:45:26 2015
@@ -12,6 +12,7 @@
 @i5 = external hidden thread_local global i32
 @s1 = thread_local global i16 15
 @b1 = thread_local global i8 0
+ at b2 = thread_local(localexec) global i8 0
 
 define i32 @f1() {
 ; X32_LINUX-LABEL: f1:
@@ -409,3 +410,31 @@ entry:
 	ret i32 %tmp2
 }
 
+define i8* @f15() {
+; X32_LINUX-LABEL: f15:
+; X32_LINUX:      movl %gs:0, %eax
+; X32_LINUX-NEXT: leal b2 at NTPOFF(%eax), %eax
+; X32_LINUX-NEXT: ret
+; X64_LINUX-LABEL: f15:
+; X64_LINUX:      movq %fs:0, %rax
+; X64_LINUX-NEXT: leaq b2 at TPOFF(%rax), %rax
+; X64_LINUX-NEXT: ret
+; X32_WIN-LABEL: f15:
+; X32_WIN:      movl %fs:__tls_array, %eax
+; X32_WIN-NEXT: movl (%eax), %eax
+; X32_WIN-NEXT: leal _b2 at SECREL32(%eax), %eax
+; X32_WIN-NEXT: ret
+; X64_WIN-LABEL: f15:
+; X64_WIN:      movq %gs:88, %rax
+; X64_WIN-NEXT: movq (%rax), %rax
+; X64_WIN-NEXT: leaq b2 at SECREL32(%rax), %rax
+; X64_WIN-NEXT: ret
+; MINGW32-LABEL: f15:
+; MINGW32:      movl %fs:44, %eax
+; MINGW32-NEXT: movl (%eax), %eax
+; MINGW32-NEXT: leal _b2 at SECREL32(%eax), %eax
+; MINGW32-NEXT: ret
+entry:
+	ret i8* @b2
+}
+





More information about the llvm-commits mailing list