[lld] r272282 - ELF: Compute used bit for --as-needed during symbol resolution.

Peter Collingbourne via llvm-commits llvm-commits at lists.llvm.org
Thu Jun 9 11:01:35 PDT 2016


Author: pcc
Date: Thu Jun  9 13:01:35 2016
New Revision: 272282

URL: http://llvm.org/viewvc/llvm-project?rev=272282&view=rev
Log:
ELF: Compute used bit for --as-needed during symbol resolution.

We can now use this to decide whether to emit a verneed during the final
pass over the symbols. We were previously wrongly creating a verneed entry
in the case where all references to a DSO's symbols were weak.

In a future change we may also want to use the used bit to control whether
shared symbols are preemptible and appear in the dynsym. This seems a little
tricky to do at the moment because isNeeded() is templated.

The only other functional change here is that we emit a DT_NEEDED for DSOs
whose symbols are all preempted by objects that appear later in the link. But
that doesn't seem too important to me.

Differential Revision: http://reviews.llvm.org/D21171

Added:
    lld/trunk/test/ELF/verneed-as-needed-weak.s
Modified:
    lld/trunk/ELF/SymbolTable.cpp
    lld/trunk/ELF/Writer.cpp

Modified: lld/trunk/ELF/SymbolTable.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/SymbolTable.cpp?rev=272282&r1=272281&r2=272282&view=diff
==============================================================================
--- lld/trunk/ELF/SymbolTable.cpp (original)
+++ lld/trunk/ELF/SymbolTable.cpp Thu Jun  9 13:01:35 2016
@@ -238,9 +238,12 @@ Symbol *SymbolTable<ELFT>::addUndefined(
     cast<Undefined>(S->body())->File = File;
     return S;
   }
-  if (Binding != STB_WEAK &&
-      (S->body()->isShared() || S->body()->isLazy()))
-    S->Binding = Binding;
+  if (Binding != STB_WEAK) {
+    if (S->body()->isShared() || S->body()->isLazy())
+      S->Binding = Binding;
+    if (auto *SS = dyn_cast<SharedSymbol<ELFT>>(S->body()))
+      SS->File->IsUsed = true;
+  }
   if (auto *L = dyn_cast<Lazy>(S->body())) {
     // An undefined weak will not fetch archive members, but we have to remember
     // its type. See also comment in addLazyArchive.
@@ -393,8 +396,11 @@ void SymbolTable<ELFT>::addShared(Shared
   // Make sure we preempt DSO symbols with default visibility.
   if (Sym.getVisibility() == STV_DEFAULT)
     S->ExportDynamic = true;
-  if (WasInserted || isa<Undefined>(S->body()))
+  if (WasInserted || isa<Undefined>(S->body())) {
     replaceBody<SharedSymbol<ELFT>>(S, F, Name, Sym, Verdef);
+    if (!S->isWeak())
+      F->IsUsed = true;
+  }
 }
 
 template <class ELFT>

Modified: lld/trunk/ELF/Writer.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Writer.cpp?rev=272282&r1=272281&r2=272282&view=diff
==============================================================================
--- lld/trunk/ELF/Writer.cpp (original)
+++ lld/trunk/ELF/Writer.cpp Thu Jun  9 13:01:35 2016
@@ -813,11 +813,6 @@ template <class ELFT> void Writer<ELFT>:
   for (Symbol *S : Symtab.getSymbols()) {
     SymbolBody *Body = S->body();
 
-    // Set "used" bit for --as-needed.
-    if (S->IsUsedInRegularObj && !S->isWeak())
-      if (auto *SS = dyn_cast<SharedSymbol<ELFT>>(Body))
-        SS->File->IsUsed = true;
-
     // We only report undefined symbols in regular objects. This means that we
     // will accept an undefined reference in bitcode if it can be optimized out.
     if (S->IsUsedInRegularObj && Body->isUndefined() && !S->isWeak())
@@ -834,7 +829,8 @@ template <class ELFT> void Writer<ELFT>:
     if (isOutputDynamic() && S->includeInDynsym()) {
       Out<ELFT>::DynSymTab->addSymbol(Body);
       if (auto *SS = dyn_cast<SharedSymbol<ELFT>>(Body))
-        Out<ELFT>::VerNeed->addSymbol(SS);
+        if (SS->File->isNeeded())
+          Out<ELFT>::VerNeed->addSymbol(SS);
     }
   }
 

Added: lld/trunk/test/ELF/verneed-as-needed-weak.s
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/ELF/verneed-as-needed-weak.s?rev=272282&view=auto
==============================================================================
--- lld/trunk/test/ELF/verneed-as-needed-weak.s (added)
+++ lld/trunk/test/ELF/verneed-as-needed-weak.s Thu Jun  9 13:01:35 2016
@@ -0,0 +1,14 @@
+# REQUIRES: x86
+# RUN: llvm-mc -filetype=obj -triple=x86_64-pc-linux %s -o %t.o
+# RUN: ld.lld %t.o --as-needed %S/Inputs/verneed1.so -o %t
+# RUN: llvm-readobj -V %t | FileCheck %s
+
+# CHECK:       SHT_GNU_verneed {
+# CHECK-NEXT:  }
+
+.weak f1
+
+.globl _start
+_start:
+.data
+.long f1




More information about the llvm-commits mailing list