[MCJIT] Fix some inconsistent handling of name mangling inside MCJIT.

This patch moves symbol mangling from findSymbol to getSymbolAddress. The
findSymbol, findExistingSymbol and findModuleForSymbol methods now always take
a mangled name, allowing the 'demangle-and-retry' cruft to be removed from
findSymbol. See http://llvm.org/PR28699 for details.

Patch by James Holderness. Thanks very much James!

llvm-svn: 281238
This commit is contained in:
Lang Hames 2016-09-12 17:19:24 +00:00
parent 74f490d331
commit 8d4be3aacf
2 changed files with 21 additions and 12 deletions

View File

@ -275,19 +275,20 @@ void MCJIT::finalizeModule(Module *M) {
}
JITSymbol MCJIT::findExistingSymbol(const std::string &Name) {
SmallString<128> FullName;
Mangler::getNameWithPrefix(FullName, Name, getDataLayout());
if (void *Addr = getPointerToGlobalIfAvailable(FullName))
if (void *Addr = getPointerToGlobalIfAvailable(Name))
return JITSymbol(static_cast<uint64_t>(
reinterpret_cast<uintptr_t>(Addr)),
JITSymbolFlags::Exported);
return Dyld.getSymbol(FullName);
return Dyld.getSymbol(Name);
}
Module *MCJIT::findModuleForSymbol(const std::string &Name,
bool CheckFunctionsOnly) {
StringRef DemangledName = Name;
if (DemangledName[0] == getDataLayout().getGlobalPrefix())
DemangledName = DemangledName.substr(1);
MutexGuard locked(lock);
// If it hasn't already been generated, see if it's in one of our modules.
@ -295,11 +296,11 @@ Module *MCJIT::findModuleForSymbol(const std::string &Name,
E = OwnedModules.end_added();
I != E; ++I) {
Module *M = *I;
Function *F = M->getFunction(Name);
Function *F = M->getFunction(DemangledName);
if (F && !F->isDeclaration())
return M;
if (!CheckFunctionsOnly) {
GlobalVariable *G = M->getGlobalVariable(Name);
GlobalVariable *G = M->getGlobalVariable(DemangledName);
if (G && !G->isDeclaration())
return M;
// FIXME: Do we need to worry about global aliases?
@ -311,7 +312,12 @@ Module *MCJIT::findModuleForSymbol(const std::string &Name,
uint64_t MCJIT::getSymbolAddress(const std::string &Name,
bool CheckFunctionsOnly) {
return findSymbol(Name, CheckFunctionsOnly).getAddress();
std::string MangledName;
{
raw_string_ostream MangledNameStream(MangledName);
Mangler::getNameWithPrefix(MangledNameStream, Name, getDataLayout());
}
return findSymbol(MangledName, CheckFunctionsOnly).getAddress();
}
JITSymbol MCJIT::findSymbol(const std::string &Name,
@ -648,10 +654,6 @@ void MCJIT::NotifyFreeingObject(const object::ObjectFile& Obj) {
JITSymbol
LinkingSymbolResolver::findSymbol(const std::string &Name) {
auto Result = ParentEngine.findSymbol(Name, false);
// If the symbols wasn't found and it begins with an underscore, try again
// without the underscore.
if (!Result && Name[0] == '_')
Result = ParentEngine.findSymbol(Name.substr(1), false);
if (Result)
return Result;
if (ParentEngine.isSymbolSearchingDisabled())

View File

@ -309,10 +309,17 @@ public:
// @}
// Takes a mangled name and returns the corresponding JITSymbol (if a
// definition of that mangled name has been added to the JIT).
JITSymbol findSymbol(const std::string &Name, bool CheckFunctionsOnly);
// DEPRECATED - Please use findSymbol instead.
//
// This is not directly exposed via the ExecutionEngine API, but it is
// used by the LinkingMemoryManager.
//
// getSymbolAddress takes an unmangled name and returns the corresponding
// JITSymbol if a definition of the name has been added to the JIT.
uint64_t getSymbolAddress(const std::string &Name,
bool CheckFunctionsOnly);