[lld] r218259 - [ELF] Fix linking when a regular object defines a symbol that is used in a DSO
Rui Ueyama
ruiu at google.com
Mon Sep 22 10:52:51 PDT 2014
Author: ruiu
Date: Mon Sep 22 12:52:50 2014
New Revision: 218259
URL: http://llvm.org/viewvc/llvm-project?rev=218259&view=rev
Log:
[ELF] Fix linking when a regular object defines a symbol that is used in a DSO
Patch from Rafael Auler!
When a shared lib has an undefined symbol that is defined in a regular object
(the program), the final executable must export this symbol in the dynamic
symbol table. However, in the current logic, lld only puts the symbol in the
dynamic symbol table if the symbol is weak. This patch fixes lld to put the
symbol in the dynamic symbol table regardless if it is weak or not.
This caused a problem in FreeBSD10, whose programs link against a crt1.o
that defines the symbol __progname, which is, in turn, undefined in libc.so.7
and will only be resolved in runtime.
http://reviews.llvm.org/D5424
Added:
lld/trunk/test/elf/undef-from-dso-to-main.test
Modified:
lld/trunk/include/lld/ReaderWriter/ELFLinkingContext.h
lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp
lld/trunk/lib/ReaderWriter/ELF/OutputELFWriter.h
Modified: lld/trunk/include/lld/ReaderWriter/ELFLinkingContext.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/include/lld/ReaderWriter/ELFLinkingContext.h?rev=218259&r1=218258&r2=218259&view=diff
==============================================================================
--- lld/trunk/include/lld/ReaderWriter/ELFLinkingContext.h (original)
+++ lld/trunk/include/lld/ReaderWriter/ELFLinkingContext.h Mon Sep 22 12:52:50 2014
@@ -262,8 +262,8 @@ public:
void setCreateSeparateROSegment() { _mergeRODataToTextSegment = false; }
- bool hasCoalescedWeakPair(StringRef name) const {
- return _weakCoalescedSymbols.count(name) != 0;
+ bool hasCoalescedSharedLibPair(StringRef name) const {
+ return _sharedLibCoalescedSymbols.count(name) != 0;
}
private:
@@ -300,7 +300,7 @@ protected:
StringRefVector _rpathList;
StringRefVector _rpathLinkList;
std::map<std::string, uint64_t> _absoluteSymbols;
- llvm::StringSet<> _weakCoalescedSymbols;
+ llvm::StringSet<> _sharedLibCoalescedSymbols;
};
} // end namespace lld
Modified: lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp?rev=218259&r1=218258&r2=218259&view=diff
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp (original)
+++ lld/trunk/lib/ReaderWriter/ELF/ELFLinkingContext.cpp Mon Sep 22 12:52:50 2014
@@ -241,11 +241,6 @@ std::unique_ptr<File> ELFLinkingContext:
return std::move(undefinedSymFile);
}
-static bool isSharedWeakAtom(const UndefinedAtom *ua) {
- return ua->canBeNull() != UndefinedAtom::canBeNullNever &&
- isa<SharedLibraryFile>(ua->file());
-}
-
void ELFLinkingContext::notifySymbolTableCoalesce(const Atom *existingAtom,
const Atom *newAtom,
bool &useNew) {
@@ -259,11 +254,12 @@ void ELFLinkingContext::notifySymbolTabl
ua = dyn_cast<UndefinedAtom>(existingAtom);
}
- if (da && ua && da->scope() == Atom::scopeGlobal && isSharedWeakAtom(ua))
- // If strong defined atom coalesces away weak atom declared
- // in the shared object the strong atom needs to be dynamicaly exported.
+ if (da && ua && da->scope() == Atom::scopeGlobal &&
+ isa<SharedLibraryFile>(ua->file()))
+ // If strong defined atom coalesces away an atom declared
+ // in the shared object the strong atom needs to be dynamically exported.
// Save its name.
- _weakCoalescedSymbols.insert(ua->name());
+ _sharedLibCoalescedSymbols.insert(ua->name());
}
} // end namespace lld
Modified: lld/trunk/lib/ReaderWriter/ELF/OutputELFWriter.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/lib/ReaderWriter/ELF/OutputELFWriter.h?rev=218259&r1=218258&r2=218259&view=diff
==============================================================================
--- lld/trunk/lib/ReaderWriter/ELF/OutputELFWriter.h (original)
+++ lld/trunk/lib/ReaderWriter/ELF/OutputELFWriter.h Mon Sep 22 12:52:50 2014
@@ -183,7 +183,7 @@ void OutputELFWriter<ELFT>::buildDynamic
for (const auto &atom : section->atoms()) {
const DefinedAtom *da = dyn_cast<const DefinedAtom>(atom->_atom);
if (da && (da->dynamicExport() == DefinedAtom::dynamicExportAlways ||
- _context.hasCoalescedWeakPair(da->name())))
+ _context.hasCoalescedSharedLibPair(da->name())))
_dynamicSymbolTable->addSymbol(atom->_atom, section->ordinal(),
atom->_virtualAddr, atom);
}
Added: lld/trunk/test/elf/undef-from-dso-to-main.test
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/elf/undef-from-dso-to-main.test?rev=218259&view=auto
==============================================================================
--- lld/trunk/test/elf/undef-from-dso-to-main.test (added)
+++ lld/trunk/test/elf/undef-from-dso-to-main.test Mon Sep 22 12:52:50 2014
@@ -0,0 +1,7 @@
+# Tests that a reference from a DSO to a regular object
+# forces the final executable to export the symbol.
+
+RUN: lld -flavor gnu -target x86_64 %p/Inputs/defobj.o -L%p/Inputs -lundef2 -o %t1
+RUN: llvm-readobj -dyn-symbols %t1 | FileCheck -check-prefix CHECKSYMS %s
+
+CHECKSYMS: myexportedsymbol
More information about the llvm-commits
mailing list