1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2025-01-31 12:41:49 +01:00

[RuntimeDyld] Call the SymbolResolver::findSymbolInLogicalDylib method when

searching for external symbols, and fall back to the SymbolResolver::findSymbol
method if the former returns null.

This makes RuntimeDyld behave more like a static linker: Symbol definitions
from within the current module's "logical dylib" will be preferred to
external definitions. We can build on this behavior in the future to properly
support weak symbol handling.

Custom symbol resolvers that override the findSymbolInLogicalDylib method may
notice changes due to this patch. Clients who have not overridden this method
should generally be unaffected, however users of the OrcMCJITReplacement class
may notice changes.

llvm-svn: 270716
This commit is contained in:
Lang Hames 2016-05-25 16:23:59 +00:00
parent 8544c01533
commit 0a4d39f9bf
8 changed files with 52 additions and 56 deletions

View File

@ -145,7 +145,7 @@ private:
return *this;
}
SymbolResolverFtor ExternalSymbolResolver;
std::unique_ptr<RuntimeDyld::SymbolResolver> ExternalSymbolResolver;
std::unique_ptr<ResourceOwner<RuntimeDyld::MemoryManager>> MemMgr;
ModuleAdderFtor ModuleAdder;
};
@ -188,10 +188,7 @@ public:
LogicalDylibs.push_back(CODLogicalDylib(BaseLayer));
auto &LDResources = LogicalDylibs.back().getDylibResources();
LDResources.ExternalSymbolResolver =
[Resolver](const std::string &Name) {
return Resolver->findSymbol(Name);
};
LDResources.ExternalSymbolResolver = std::move(Resolver);
auto &MemMgrRef = *MemMgr;
LDResources.MemMgr =
@ -357,10 +354,12 @@ private:
auto &LMResources = LD.getLogicalModuleResources(LMH);
if (auto Sym = LMResources.StubsMgr->findStub(Name, false))
return RuntimeDyld::SymbolInfo(Sym.getAddress(), Sym.getFlags());
return LD.getDylibResources().ExternalSymbolResolver(Name);
auto &LDResolver = LD.getDylibResources().ExternalSymbolResolver;
return LDResolver->findSymbolInLogicalDylib(Name);
},
[](const std::string &Name) {
return RuntimeDyld::SymbolInfo(nullptr);
[&LD](const std::string &Name) {
auto &LDResolver = LD.getDylibResources().ExternalSymbolResolver;
return LDResolver->findSymbol(Name);
});
auto GVsH =
@ -484,13 +483,12 @@ private:
if (auto Symbol = LD.findSymbolInternally(LMH, Name))
return RuntimeDyld::SymbolInfo(Symbol.getAddress(),
Symbol.getFlags());
return LD.getDylibResources().ExternalSymbolResolver(Name);
auto &LDResolver = LD.getDylibResources().ExternalSymbolResolver;
return LDResolver->findSymbolInLogicalDylib(Name);
},
[this, &LD, LMH](const std::string &Name) {
if (auto Symbol = LD.findSymbolInternally(LMH, Name))
return RuntimeDyld::SymbolInfo(Symbol.getAddress(),
Symbol.getFlags());
return RuntimeDyld::SymbolInfo(nullptr);
[this, &LD](const std::string &Name) {
auto &LDResolver = LD.getDylibResources().ExternalSymbolResolver;
return LDResolver->findSymbol(Name);
});
return LD.getDylibResources().ModuleAdder(BaseLayer, std::move(M),

View File

@ -22,37 +22,37 @@
namespace llvm {
namespace orc {
template <typename ExternalLookupFtorT, typename DylibLookupFtorT>
template <typename DylibLookupFtorT, typename ExternalLookupFtorT>
class LambdaResolver : public RuntimeDyld::SymbolResolver {
public:
LambdaResolver(ExternalLookupFtorT ExternalLookupFtor,
DylibLookupFtorT DylibLookupFtor)
: ExternalLookupFtor(ExternalLookupFtor),
DylibLookupFtor(DylibLookupFtor) {}
RuntimeDyld::SymbolInfo findSymbol(const std::string &Name) final {
return ExternalLookupFtor(Name);
}
LambdaResolver(DylibLookupFtorT DylibLookupFtor,
ExternalLookupFtorT ExternalLookupFtor)
: DylibLookupFtor(DylibLookupFtor),
ExternalLookupFtor(ExternalLookupFtor) {}
RuntimeDyld::SymbolInfo
findSymbolInLogicalDylib(const std::string &Name) final {
return DylibLookupFtor(Name);
}
RuntimeDyld::SymbolInfo findSymbol(const std::string &Name) final {
return ExternalLookupFtor(Name);
}
private:
ExternalLookupFtorT ExternalLookupFtor;
DylibLookupFtorT DylibLookupFtor;
ExternalLookupFtorT ExternalLookupFtor;
};
template <typename ExternalLookupFtorT,
typename DylibLookupFtorT>
std::unique_ptr<LambdaResolver<ExternalLookupFtorT, DylibLookupFtorT>>
createLambdaResolver(ExternalLookupFtorT ExternalLookupFtor,
DylibLookupFtorT DylibLookupFtor) {
typedef LambdaResolver<ExternalLookupFtorT, DylibLookupFtorT> LR;
return make_unique<LR>(std::move(ExternalLookupFtor),
std::move(DylibLookupFtor));
template <typename DylibLookupFtorT,
typename ExternalLookupFtorT>
std::unique_ptr<LambdaResolver<DylibLookupFtorT, ExternalLookupFtorT>>
createLambdaResolver(DylibLookupFtorT DylibLookupFtor,
ExternalLookupFtorT ExternalLookupFtor) {
typedef LambdaResolver<DylibLookupFtorT, ExternalLookupFtorT> LR;
return make_unique<LR>(std::move(DylibLookupFtor),
std::move(ExternalLookupFtor));
}
} // End namespace orc.

View File

@ -193,17 +193,9 @@ public:
public:
virtual ~SymbolResolver() {}
/// This method returns the address of the specified function or variable.
/// It is used to resolve symbols during module linking.
///
/// If the returned symbol's address is equal to ~0ULL then RuntimeDyld will
/// skip all relocations for that symbol, and the client will be responsible
/// for handling them manually.
virtual SymbolInfo findSymbol(const std::string &Name) = 0;
/// This method returns the address of the specified symbol if it exists
/// within the logical dynamic library represented by this
/// RTDyldMemoryManager. Unlike getSymbolAddress, queries through this
/// RTDyldMemoryManager. Unlike findSymbol, queries through this
/// interface should return addresses for hidden symbols.
///
/// This is of particular importance for the Orc JIT APIs, which support lazy
@ -212,13 +204,17 @@ public:
/// writing memory managers for MCJIT can usually ignore this method.
///
/// This method will be queried by RuntimeDyld when checking for previous
/// definitions of common symbols. It will *not* be queried by default when
/// resolving external symbols (this minimises the link-time overhead for
/// MCJIT clients who don't care about Orc features). If you are writing a
/// RTDyldMemoryManager for Orc and want "external" symbol resolution to
/// search the logical dylib, you should override your getSymbolAddress
/// method call this method directly.
/// definitions of common symbols.
virtual SymbolInfo findSymbolInLogicalDylib(const std::string &Name) = 0;
/// This method returns the address of the specified function or variable.
/// It is used to resolve symbols during module linking.
///
/// If the returned symbol's address is equal to ~0ULL then RuntimeDyld will
/// skip all relocations for that symbol, and the client will be responsible
/// for handling them manually.
virtual SymbolInfo findSymbol(const std::string &Name) = 0;
private:
virtual void anchor();
};

View File

@ -137,10 +137,10 @@ public:
return mapError(IndirectStubsMgr->updatePointer(Name, Addr));
}
std::shared_ptr<RuntimeDyld::SymbolResolver>
std::unique_ptr<RuntimeDyld::SymbolResolver>
createResolver(LLVMOrcSymbolResolverFn ExternalResolver,
void *ExternalResolverCtx) {
auto Resolver = orc::createLambdaResolver(
return orc::createLambdaResolver(
[this, ExternalResolver, ExternalResolverCtx](const std::string &Name) {
// Search order:
// 1. JIT'd symbols.
@ -162,8 +162,6 @@ public:
[](const std::string &Name) {
return RuntimeDyld::SymbolInfo(nullptr);
});
return std::shared_ptr<RuntimeDyld::SymbolResolver>(std::move(Resolver));
}
template <typename LayerT>

View File

@ -121,7 +121,7 @@ class OrcMCJITReplacement : public ExecutionEngine {
RuntimeDyld::SymbolInfo
findSymbolInLogicalDylib(const std::string &Name) override {
return M.ClientResolver->findSymbolInLogicalDylib(Name);
return M.ClientResolver->findSymbol(Name);
}
private:

View File

@ -916,7 +916,11 @@ void RuntimeDyldImpl::resolveExternalSymbols() {
if (Loc == GlobalSymbolTable.end()) {
// This is an external symbol, try to get its address from the symbol
// resolver.
Addr = Resolver.findSymbol(Name.data()).getAddress();
// First search for the symbol in this logical dylib.
Addr = Resolver.findSymbolInLogicalDylib(Name.data()).getAddress();
// If that fails, try searching for an external symbol.
if (!Addr)
Addr = Resolver.findSymbol(Name.data()).getAddress();
// The call to getSymbolAddress may have caused additional modules to
// be loaded, which may have added new entries to the
// ExternalSymbolRelocations map. Consquently, we need to update our

View File

@ -82,7 +82,7 @@ public:
// 1) Search the JIT symbols.
// 2) Check for C++ runtime overrides.
// 3) Search the host process (LLI)'s symbol table.
std::shared_ptr<RuntimeDyld::SymbolResolver> Resolver =
auto Resolver =
orc::createLambdaResolver(
[this](const std::string &Name) {
if (auto Sym = CODLayer.findSymbol(Name, true))

View File

@ -662,12 +662,12 @@ int main(int argc, char **argv, char * const *envp) {
// Forward MCJIT's symbol resolution calls to the remote.
static_cast<ForwardingMemoryManager*>(RTDyldMM)->setResolver(
orc::createLambdaResolver(
[](const std::string &Name) { return nullptr; },
[&](const std::string &Name) {
if (auto Addr = ExitOnErr(R.getSymbolAddress(Name)))
return RuntimeDyld::SymbolInfo(Addr, JITSymbolFlags::Exported);
return RuntimeDyld::SymbolInfo(nullptr);
},
[](const std::string &Name) { return nullptr; }
}
));
// Grab the target address of the JIT'd main function on the remote and call