Local dynamic TLS model for direct object output. Create the correct TLS MIPS
authorAkira Hatanaka <ahatanaka@mips.com>
Thu, 22 Dec 2011 01:05:17 +0000 (01:05 +0000)
committerAkira Hatanaka <ahatanaka@mips.com>
Thu, 22 Dec 2011 01:05:17 +0000 (01:05 +0000)
ELF relocations.

Patch by Jack Carter.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@147118 91177308-0d34-0410-b5e6-96231b3b80d8

include/llvm/MC/MCExpr.h
lib/MC/ELFObjectWriter.cpp
lib/MC/MCExpr.cpp
lib/Target/Mips/MCTargetDesc/MipsAsmBackend.cpp
lib/Target/Mips/MCTargetDesc/MipsFixupKinds.h
lib/Target/Mips/MCTargetDesc/MipsMCCodeEmitter.cpp
test/MC/Mips/elf-tls.ll [new file with mode: 0644]

index e7f5b6a7d5ff18a318a5fefb1074c2f69c05921c..195762e64b2f915e710ecabef34619dd1112548e 100644 (file)
@@ -176,7 +176,6 @@ public:
     VK_PPC_GAS_HA16,     // symbol@ha
     VK_PPC_GAS_LO16,      // symbol@l
 
-    VK_Mips_None,
     VK_Mips_GPREL,
     VK_Mips_GOT_CALL,
     VK_Mips_GOT16,
index ae29753582f108e69315531fa2866623d53f2c01..d0b3372b5de6a5122b123be5155f698b23915e87 100644 (file)
@@ -1474,6 +1474,15 @@ unsigned MipsELFObjectWriter::GetRelocType(const MCValue &Target,
   case Mips::fixup_Mips_TPREL_LO:
     Type = ELF::R_MIPS_TLS_TPREL_LO16;
     break;
+  case Mips::fixup_Mips_TLSLDM:
+    Type = ELF::R_MIPS_TLS_LDM;
+    break;
+  case Mips::fixup_Mips_DTPREL_HI:
+    Type = ELF::R_MIPS_TLS_DTPREL_HI16;
+    break;
+  case Mips::fixup_Mips_DTPREL_LO:
+    Type = ELF::R_MIPS_TLS_DTPREL_LO16;
+    break;
   case Mips::fixup_Mips_Branch_PCRel:
   case Mips::fixup_Mips_PC16:
     Type = ELF::R_MIPS_PC16;
index da297fb1d95a0cf1cd8d932655641a9ca9b4594b..4ebd71a5839e76dea05472a7734c643c6ebcd85a 100644 (file)
@@ -200,6 +200,24 @@ StringRef MCSymbolRefExpr::getVariantKindName(VariantKind Kind) {
   case VK_PPC_DARWIN_LO16: return "lo16";
   case VK_PPC_GAS_HA16: return "ha";
   case VK_PPC_GAS_LO16: return "l";
+  case VK_Mips_GPREL: return "GPREL";
+  case VK_Mips_GOT_CALL: return "GOT_CALL";
+  case VK_Mips_GOT16: return "GOT16";
+  case VK_Mips_GOT: return "GOT";
+  case VK_Mips_ABS_HI: return "ABS_HI";
+  case VK_Mips_ABS_LO: return "ABS_LO";
+  case VK_Mips_TLSGD: return "TLSGD";
+  case VK_Mips_TLSLDM: return "TLSLDM";
+  case VK_Mips_DTPREL_HI: return "DTPREL_HI";
+  case VK_Mips_DTPREL_LO: return "DTPREL_LO";
+  case VK_Mips_GOTTPREL: return "GOTTPREL";
+  case VK_Mips_TPREL_HI: return "TPREL_HI";
+  case VK_Mips_TPREL_LO: return "TPREL_LO";
+  case VK_Mips_GPOFF_HI: return "GPOFF_HI";
+  case VK_Mips_GPOFF_LO: return "GPOFF_LO";
+  case VK_Mips_GOT_DISP: return "GOT_DISP";
+  case VK_Mips_GOT_PAGE: return "GOT_PAGE";
+  case VK_Mips_GOT_OFST: return "GOT_OFST";
   }
 }
 
index 699148b22b11396a263bdd788ec76c7707c3a094..0f57d3cc06890dd5907b9c4cf925daa8ead8260b 100644 (file)
@@ -141,6 +141,9 @@ public:
       { "fixup_Mips_GOTTPREL",     0,     16,   0 },
       { "fixup_Mips_TPREL_HI",     0,     16,   0 },
       { "fixup_Mips_TPREL_LO",     0,     16,   0 },
+      { "fixup_Mips_TLSLDM",       0,     16,   0 },
+      { "fixup_Mips_DTPREL_HI",    0,     16,   0 },
+      { "fixup_Mips_DTPREL_LO",    0,     16,   0 },
       { "fixup_Mips_Branch_PCRel", 0,     16,  MCFixupKindInfo::FKF_IsPCRel }
     };
 
index a56c002315062c9e4a4f409b284c204c3ef7fcbd..80026829f98992397a682e9d6791b0fafd3f3eee 100644 (file)
@@ -83,6 +83,15 @@ namespace Mips {
     // resulting in - R_MIPS_TLS_TPREL_LO16.
     fixup_Mips_TPREL_LO,
 
+    // resulting in - R_MIPS_TLS_LDM.
+    fixup_Mips_TLSLDM,
+
+    // resulting in - R_MIPS_TLS_DTPREL_HI16.
+    fixup_Mips_DTPREL_HI,
+
+    // resulting in - R_MIPS_TLS_DTPREL_LO16.
+    fixup_Mips_DTPREL_LO,
+
     // PC relative branch fixup resulting in - R_MIPS_PC16
     fixup_Mips_Branch_PCRel,
 
index 463dcfe55dccd1119c1cf779a3d8801463274764..53cfd98d379cf944970de58fd1deac1e691cacff 100644 (file)
@@ -187,6 +187,7 @@ getMachineOpValue(const MCInst &MI, const MCOperand &MO,
 
     if (Kind == MCExpr::SymbolRef) {
       Mips::Fixups FixupKind;
+
       switch(cast<MCSymbolRefExpr>(Expr)->getKind()) {
       case MCSymbolRefExpr::VK_Mips_GPREL:
         FixupKind = Mips::fixup_Mips_GPREL16;
@@ -209,6 +210,15 @@ getMachineOpValue(const MCInst &MI, const MCOperand &MO,
       case MCSymbolRefExpr::VK_Mips_TLSGD:
         FixupKind = Mips::fixup_Mips_TLSGD;
         break;
+      case MCSymbolRefExpr::VK_Mips_TLSLDM:
+        FixupKind = Mips::fixup_Mips_TLSLDM;
+        break;
+      case MCSymbolRefExpr::VK_Mips_DTPREL_HI:
+        FixupKind = Mips::fixup_Mips_DTPREL_HI;
+        break;
+      case MCSymbolRefExpr::VK_Mips_DTPREL_LO:
+        FixupKind = Mips::fixup_Mips_DTPREL_LO;
+        break;
       case MCSymbolRefExpr::VK_Mips_GOTTPREL:
         FixupKind = Mips::fixup_Mips_GOTTPREL;
         break;
diff --git a/test/MC/Mips/elf-tls.ll b/test/MC/Mips/elf-tls.ll
new file mode 100644 (file)
index 0000000..b4183b8
--- /dev/null
@@ -0,0 +1,36 @@
+; RUN: llc -filetype=obj -mtriple mipsel-unknown-linux %s -o - | elf-dump --dump-section-data  | FileCheck %s
+
+; Check that the appropriate relocations were created.
+
+; CHECK:     ('r_type', 0x2b)
+; CHECK:     ('r_type', 0x2c)
+; CHECK:     ('r_type', 0x2d)
+
+@t1 = thread_local global i32 0, align 4
+
+define i32 @f1() nounwind {
+entry:
+  %tmp = load i32* @t1, align 4
+  ret i32 %tmp
+
+}
+
+
+@t2 = external thread_local global i32
+
+define i32 @f2() nounwind {
+entry:
+  %tmp = load i32* @t2, align 4
+  ret i32 %tmp
+
+}
+
+@f3.i = internal thread_local unnamed_addr global i32 1, align 4
+
+define i32 @f3() nounwind {
+entry:
+  %0 = load i32* @f3.i, align 4
+  %inc = add nsw i32 %0, 1
+  store i32 %inc, i32* @f3.i, align 4
+  ret i32 %inc
+}