[lld] r269375 - Slit the relocation scan in two parts.

Rafael Espindola via llvm-commits llvm-commits at lists.llvm.org
Thu May 12 15:51:23 PDT 2016


Author: rafael
Date: Thu May 12 17:51:22 2016
New Revision: 269375

URL: http://llvm.org/viewvc/llvm-project?rev=269375&view=rev
Log:
Slit the relocation scan in two parts.

The first part handles whatever has to be written to the r_offset
position.

The second part handles creating got and plt entries.

Modified:
    lld/trunk/ELF/Writer.cpp

Modified: lld/trunk/ELF/Writer.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Writer.cpp?rev=269375&r1=269374&r2=269375&view=diff
==============================================================================
--- lld/trunk/ELF/Writer.cpp (original)
+++ lld/trunk/ELF/Writer.cpp Thu May 12 17:51:22 2016
@@ -672,15 +672,51 @@ void Writer<ELFT>::scanRelocs(InputSecti
       continue;
     }
 
-    if (Expr == R_GOT && !isStaticLinkTimeConstant<ELFT>(Expr, Type, Body) &&
-        Config->Shared)
-      AddDyn({Target->RelativeRel, C.OutSec, Offset, true, &Body, Addend});
-
-    // If a relocation needs PLT, we create a PLT and a GOT slot
-    // for the symbol.
-    if (needsPlt(Expr)) {
+    if (needsPlt(Expr) || Expr == R_THUNK || refersToGotEntry(Expr) ||
+        !Body.isPreemptible()) {
+      // If the relocation points to something in the file, remember it so that
+      // we can apply it when writting the section.
       C.Relocations.push_back({Expr, Type, Offset, Addend, &Body});
 
+      // If the output being produced is position independent, the final value
+      // is still not known. In that case we still need some help from the
+      // dynamic linker. We can however do better than just copying the incoming
+      // relocation. We can process some of it and and just ask the dynamic
+      // linker to add the load address.
+      if (!isStaticLinkTimeConstant<ELFT>(Expr, Type, Body))
+        AddDyn({Target->RelativeRel, C.OutSec, Offset, true, &Body, Addend});
+    } else {
+      // We don't know anything about the finaly symbol. Just ask the dynamic
+      // linker to handle the relocation for us.
+      AddDyn({Target->getDynRel(Type), C.OutSec, Offset, false, &Body, Addend});
+      // MIPS ABI turns using of GOT and dynamic relocations inside out.
+      // While regular ABI uses dynamic relocations to fill up GOT entries
+      // MIPS ABI requires dynamic linker to fills up GOT entries using
+      // specially sorted dynamic symbol table. This affects even dynamic
+      // relocations against symbols which do not require GOT entries
+      // creation explicitly, i.e. do not have any GOT-relocations. So if
+      // a preemptible symbol has a dynamic relocation we anyway have
+      // to create a GOT entry for it.
+      // If a non-preemptible symbol has a dynamic relocation against it,
+      // dynamic linker takes it st_value, adds offset and writes down
+      // result of the dynamic relocation. In case of preemptible symbol
+      // dynamic linker performs symbol resolution, writes the symbol value
+      // to the GOT entry and reads the GOT entry when it needs to perform
+      // a dynamic relocation.
+      // ftp://www.linux-mips.org/pub/linux/mips/doc/ABI/mipsabi.pdf p.4-19
+      if (Config->EMachine == EM_MIPS && !Body.isInGot())
+        Out<ELFT>::Got->addEntry(Body);
+      continue;
+    }
+
+    if (Expr == R_THUNK)
+      continue;
+
+    // At this point we are done with the relocated position. Some relocations
+    // also require us to create a got or plt entry.
+
+    // If a relocation needs PLT, we create a PLT and a GOT slot for the symbol.
+    if (needsPlt(Expr)) {
       if (Body.isInPlt())
         continue;
       Out<ELFT>::Plt->addEntry(Body);
@@ -706,14 +742,7 @@ void Writer<ELFT>::scanRelocs(InputSecti
       continue;
     }
 
-    if (Expr == R_THUNK) {
-      C.Relocations.push_back({Expr, Type, Offset, Addend, &Body});
-      continue;
-    }
-
-    // If a relocation needs GOT, we create a GOT slot for the symbol.
     if (refersToGotEntry(Expr)) {
-      C.Relocations.push_back({Expr, Type, Offset, Addend, &Body});
       if (Body.isInGot())
         continue;
       Out<ELFT>::Got->addEntry(Body);
@@ -739,45 +768,6 @@ void Writer<ELFT>::scanRelocs(InputSecti
       }
       continue;
     }
-
-    if (Body.isPreemptible()) {
-      // We don't know anything about the finaly symbol. Just ask the dynamic
-      // linker to handle the relocation for us.
-      AddDyn({Target->getDynRel(Type), C.OutSec, Offset, false, &Body, Addend});
-      // MIPS ABI turns using of GOT and dynamic relocations inside out.
-      // While regular ABI uses dynamic relocations to fill up GOT entries
-      // MIPS ABI requires dynamic linker to fills up GOT entries using
-      // specially sorted dynamic symbol table. This affects even dynamic
-      // relocations against symbols which do not require GOT entries
-      // creation explicitly, i.e. do not have any GOT-relocations. So if
-      // a preemptible symbol has a dynamic relocation we anyway have
-      // to create a GOT entry for it.
-      // If a non-preemptible symbol has a dynamic relocation against it,
-      // dynamic linker takes it st_value, adds offset and writes down
-      // result of the dynamic relocation. In case of preemptible symbol
-      // dynamic linker performs symbol resolution, writes the symbol value
-      // to the GOT entry and reads the GOT entry when it needs to perform
-      // a dynamic relocation.
-      // ftp://www.linux-mips.org/pub/linux/mips/doc/ABI/mipsabi.pdf p.4-19
-      if (Config->EMachine == EM_MIPS && !Body.isInGot())
-        Out<ELFT>::Got->addEntry(Body);
-      continue;
-    }
-
-    // We know that this is the final symbol. If the program being produced
-    // is position independent, the final value is still not known.
-    // If the relocation depends on the symbol value (not the size or distances
-    // in the output), we still need some help from the dynamic linker.
-    // We can however do better than just copying the incoming relocation. We
-    // can process some of it and and just ask the dynamic linker to add the
-    // load address.
-    if (!Config->Pic || isStaticLinkTimeConstant<ELFT>(Expr, Type, Body)) {
-      C.Relocations.push_back({Expr, Type, Offset, Addend, &Body});
-      continue;
-    }
-
-    AddDyn({Target->RelativeRel, C.OutSec, Offset, true, &Body, Addend});
-    C.Relocations.push_back({Expr, Type, Offset, Addend, &Body});
   }
 
   // Scan relocations for necessary thunks.




More information about the llvm-commits mailing list