[llvm] e12a028 - [llvm-jitlink] Support promotion of ODR weak symbols in -harness mode.
Lang Hames via llvm-commits
llvm-commits at lists.llvm.org
Sat Aug 1 18:33:55 PDT 2020
Author: Lang Hames
Date: 2020-08-01T18:33:44-07:00
New Revision: e12a028ed3ed79fba1e1aa5212c7e22d83949192
URL: https://github.com/llvm/llvm-project/commit/e12a028ed3ed79fba1e1aa5212c7e22d83949192
DIFF: https://github.com/llvm/llvm-project/commit/e12a028ed3ed79fba1e1aa5212c7e22d83949192.diff
LOG: [llvm-jitlink] Support promotion of ODR weak symbols in -harness mode.
This prevents weak symbols from being immediately dead-stripped when not
directly referenced from the test harneess, enabling use of weak symbols
from the code under test.
Added:
Modified:
llvm/test/ExecutionEngine/JITLink/X86/Inputs/MachO_test_harness_test.s
llvm/tools/llvm-jitlink/llvm-jitlink.cpp
llvm/tools/llvm-jitlink/llvm-jitlink.h
Removed:
################################################################################
diff --git a/llvm/test/ExecutionEngine/JITLink/X86/Inputs/MachO_test_harness_test.s b/llvm/test/ExecutionEngine/JITLink/X86/Inputs/MachO_test_harness_test.s
index e0764a93fa43..3ca616a4a729 100644
--- a/llvm/test/ExecutionEngine/JITLink/X86/Inputs/MachO_test_harness_test.s
+++ b/llvm/test/ExecutionEngine/JITLink/X86/Inputs/MachO_test_harness_test.s
@@ -17,9 +17,16 @@ _public_func_to_interpose:
_private_func_to_interpose:
retq
+ .globl _used_weak
+ .weak_definition _used_weak
+ .p2align 4, 0x90
+_used_weak:
+ retq
+
.globl _public_func_to_test
.p2align 4, 0x90
_public_func_to_test:
+ callq _used_weak
jmp _public_func_to_interpose
.p2align 4, 0x90
diff --git a/llvm/tools/llvm-jitlink/llvm-jitlink.cpp b/llvm/tools/llvm-jitlink/llvm-jitlink.cpp
index 6828944ced23..22d29c12e192 100644
--- a/llvm/tools/llvm-jitlink/llvm-jitlink.cpp
+++ b/llvm/tools/llvm-jitlink/llvm-jitlink.cpp
@@ -188,10 +188,28 @@ static Error applyHarnessPromotions(Session &S, LinkGraph &G) {
if (!Sym->hasName())
continue;
- if (S.HarnessExternals.count(Sym->getName())) {
+ if (Sym->getLinkage() == Linkage::Weak) {
+ if (!S.CanonicalWeakDefs.count(Sym->getName()) ||
+ S.CanonicalWeakDefs[Sym->getName()] != G.getName()) {
+ LLVM_DEBUG({
+ dbgs() << " Externalizing weak symbol " << Sym->getName() << "\n";
+ });
+ DefinitionsToRemove.push_back(Sym);
+ } else {
+ LLVM_DEBUG({
+ dbgs() << " Making weak symbol " << Sym->getName() << " strong\n";
+ });
+ if (S.HarnessExternals.count(Sym->getName()))
+ Sym->setScope(Scope::Default);
+ else
+ Sym->setScope(Scope::Hidden);
+ Sym->setLinkage(Linkage::Strong);
+ }
+ } else if (S.HarnessExternals.count(Sym->getName())) {
LLVM_DEBUG(dbgs() << " Promoting " << Sym->getName() << "\n");
Sym->setScope(Scope::Default);
Sym->setLive(true);
+ continue;
} else if (S.HarnessDefinitions.count(Sym->getName())) {
LLVM_DEBUG(dbgs() << " Externalizing " << Sym->getName() << "\n");
DefinitionsToRemove.push_back(Sym);
@@ -504,10 +522,6 @@ Error LLVMJITLinkObjectLinkingLayer::add(JITDylib &JD,
if (!Name)
return Name.takeError();
- // Skip symbols that aren't in the HarnessExternals set.
- if (!S.HarnessExternals.count(*Name))
- continue;
-
// Skip symbols that have type SF_File.
if (auto SymType = Sym.getType()) {
if (*SymType == object::SymbolRef::ST_File)
@@ -515,13 +529,28 @@ Error LLVMJITLinkObjectLinkingLayer::add(JITDylib &JD,
} else
return SymType.takeError();
- auto InternedName = S.ES.intern(*Name);
auto SymFlags = JITSymbolFlags::fromObjectSymbol(Sym);
if (!SymFlags)
return SymFlags.takeError();
- *SymFlags |= JITSymbolFlags::Exported;
+ if (SymFlags->isWeak()) {
+ // If this is a weak symbol that's not defined in the harness then we
+ // need to either mark it as strong (if this is the first definition
+ // that we've seen) or discard it.
+ if (S.HarnessDefinitions.count(*Name) || S.CanonicalWeakDefs.count(*Name))
+ continue;
+ S.CanonicalWeakDefs[*Name] = O->getBufferIdentifier();
+ *SymFlags &= ~JITSymbolFlags::Weak;
+ if (!S.HarnessExternals.count(*Name))
+ *SymFlags &= ~JITSymbolFlags::Exported;
+ } else if (S.HarnessExternals.count(*Name)) {
+ *SymFlags |= JITSymbolFlags::Exported;
+ } else {
+ // Skip symbols that aren't in the HarnessExternals set.
+ continue;
+ }
+ auto InternedName = S.ES.intern(*Name);
SymbolFlags[InternedName] = std::move(*SymFlags);
}
diff --git a/llvm/tools/llvm-jitlink/llvm-jitlink.h b/llvm/tools/llvm-jitlink/llvm-jitlink.h
index c16aed9f2b50..227d3a9225c8 100644
--- a/llvm/tools/llvm-jitlink/llvm-jitlink.h
+++ b/llvm/tools/llvm-jitlink/llvm-jitlink.h
@@ -86,6 +86,7 @@ struct Session {
StringSet<> HarnessFiles;
StringSet<> HarnessExternals;
StringSet<> HarnessDefinitions;
+ DenseMap<StringRef, StringRef> CanonicalWeakDefs;
private:
Session(Triple TT, Error &Err);
More information about the llvm-commits
mailing list