[PATCH] D85994: [LLD][PowerPC] Add check in LLD to produce an error for missing TLSGD/TLSLD

Stefan Pintilie via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Fri Aug 14 13:34:13 PDT 2020


stefanp created this revision.
stefanp added reviewers: nemanjai, NeHuang, sfertile, MaskRay, hfinkel.
Herald added subscribers: shchenz, kbarton, arichardson, emaste.
Herald added a reviewer: espindola.
Herald added a project: LLVM.
stefanp requested review of this revision.
Herald added a subscriber: wuzish.

The function `__tls_get_addr` is used to get the address of an object that is Thread Local Storage.
It needs to have two relocations on it. 
One relocation is for the function call itself and it is either R_PPC64_REL24 or R_PPC64_REL24_NOTOC.
The other is R_PPC64_TLSGD or R_PPC64_TLSLD for the symbol that is having its address computed.

This patch adds a new error check in LLD that makes sure calls to `__tls_get_addr` are not missing the TLSGD/TLSLD.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D85994

Files:
  lld/ELF/Relocations.cpp
  lld/test/ELF/Inputs/GeneralDynamicMissingTLSGD.o
  lld/test/ELF/Inputs/GeneralDynamicMissingTLSGD_NOTOC.o
  lld/test/ELF/Inputs/LocalDynamicMissingTLSLD.o
  lld/test/ELF/Inputs/LocalDynamicMissingTLSLD_NOTOC.o
  lld/test/ELF/ppc64-error-missing-tlsgdld.s


Index: lld/test/ELF/ppc64-error-missing-tlsgdld.s
===================================================================
--- /dev/null
+++ lld/test/ELF/ppc64-error-missing-tlsgdld.s
@@ -0,0 +1,23 @@
+# REQUIRES ppc
+
+# RUN: not ld.lld --shared %p/Inputs/GeneralDynamicMissingTLSGD.o -o %t
+# RUN: not ld.lld --shared %p/Inputs/LocalDynamicMissingTLSLD.o -o %t
+# RUN: not ld.lld --shared %p/Inputs/GeneralDynamicMissingTLSGD_NOTOC.o -o %t
+# RUN: not ld.lld --shared %p/Inputs/LocalDynamicMissingTLSLD_NOTOC.o -o %t
+
+## Make sure that lld produces the correct error when a call to __tls_get_addr
+## does not have a corresponding R_PPC64_TLSGD/R_PPC64_TLSLD relocation.
+## This file uses pre-built object files because clang cannot produce object
+## files with this error at this time.
+
+CHECK:       error: Call to __tls_get_addr is missing a R_PPC64_TLSGD/R_PPC64_TLSLD relocation.
+CHECK-NEXT:    defined in ./Inputs/GeneralDynamicMissingTLSGD.o
+
+CHECK:       error: Call to __tls_get_addr is missing a R_PPC64_TLSGD/R_PPC64_TLSLD relocation.
+CHECK-NEXT:    defined in ./Inputs/LocalDynamicMissingTLSLD.o
+
+CHECK:       error: Call to __tls_get_addr is missing a R_PPC64_TLSGD/R_PPC64_TLSLD relocation.
+CHECK-NEXT:    defined in ./Inputs/GeneralDynamicMissingTLSGD_NOTOC.o
+
+CHECK:       error: Call to __tls_get_addr is missing a R_PPC64_TLSGD/R_PPC64_TLSLD relocation.
+CHECK-NEXT:    defined in ./Inputs/LocalDynamicMissingTLSLD_NOTOC.o
Index: lld/ELF/Relocations.cpp
===================================================================
--- lld/ELF/Relocations.cpp
+++ lld/ELF/Relocations.cpp
@@ -1306,8 +1306,25 @@
 
   // Read an addend.
   int64_t addend = computeAddend<ELFT>(rel, end, sec, expr, sym.isLocal());
-
   if (config->emachine == EM_PPC64) {
+    // Subtract 2 to get the previous iterator because we have already done ++i
+    // above.
+    const RelTy &prevRel = *(i - 2);
+    RelType prevType = prevRel.getType(config->isMips64EL);
+    // When computing the address of a TLS symbol for the General Dynamic
+    // and Local Dynamic models a call is made to __tls_get_addr. This function
+    // requires two relocations on it. The first is for the symbol marked with
+    // R_PPC64_TLSGD or R_PPC64_TLSLD. The second is for the function call
+    // itself and is marked with R_PPC64_REL24 or R_PPC64_REL24_NOTOC.
+    // The following code checks that the TLSGD/LD relocations are not missing.
+    if (((type == R_PPC64_REL24 || type == R_PPC64_REL24_NOTOC) &&
+         sym.getName() == "__tls_get_addr") &&
+        (prevRel.r_offset != rel.r_offset ||
+         (prevType != R_PPC64_TLSGD && prevType != R_PPC64_TLSLD)))
+      error("Call to __tls_get_addr is missing a R_PPC64_TLSGD/R_PPC64_TLSLD "
+            "relocation." +
+            getLocation(sec, sym, offset));
+
     // We can separate the small code model relocations into 2 categories:
     // 1) Those that access the compiler generated .toc sections.
     // 2) Those that access the linker allocated got entries.


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D85994.285744.patch
Type: text/x-patch
Size: 3025 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20200814/f2ef4328/attachment.bin>


More information about the llvm-commits mailing list