RuntimeDyld symbol info previously consisted of just a Section/Offset pair. This
patch replaces that pair type with a SymbolInfo class that also tracks symbol
visibility. A new method, RuntimeDyld::getExportedSymbolLoadAddress, is
introduced which only returns a non-zero result for exported symbols. For
non-exported or non-existant symbols this method will return zero. The
RuntimeDyld::getSymbolAddress method retains its current behavior, returning
non-zero results for all symbols regardless of visibility.
No in-tree clients of RuntimeDyld are changed. The newly introduced
functionality will be used by the Orc APIs.
No test case: Since this patch doesn't modify the behavior for any in-tree
clients we don't have a good tool to test this with yet. Once Orc is in we can
use it to write regression tests that test these changes.
llvm-svn: 226341
/// and resolve relocatons based on where they put it).
void *getSymbolAddress(StringRef Name) const;
- /// Get the address of the target copy of the symbol. This is the address
- /// used for relocation.
+ /// Get the address of the target copy of the symbol (works for both exported
+ /// and non-exported symbols). This is the address used for relocation.
uint64_t getSymbolLoadAddress(StringRef Name) const;
+ /// Get the address of the target copy of the symbol (works for exported
+ /// symbols only). This is the address used for relocation.
+ uint64_t getExportedSymbolLoadAddress(StringRef Name) const;
+
/// Resolve the relocations for all symbols we currently know about.
void resolveRelocations();
bool IsCode = SI->isText();
unsigned SectionID =
findOrEmitSection(Obj, *SI, IsCode, LocalSections);
- DEBUG(dbgs() << "\tOffset: " << format("%p", (uintptr_t)SectOffset)
- << " flags: " << Flags << " SID: " << SectionID);
- GlobalSymbolTable[Name] = SymbolLoc(SectionID, SectOffset);
+ DEBUG(dbgs() << "\tType: " << SymType << " Name: " << Name
+ << " SID: " << SectionID << " Offset: "
+ << format("%p", (uintptr_t)SectOffset)
+ << " flags: " << Flags << "\n");
+ SymbolInfo::Visibility Vis =
+ (Flags & SymbolRef::SF_Exported) ?
+ SymbolInfo::Default : SymbolInfo::Hidden;
+ GlobalSymbolTable[Name] = {SectionID, SectOffset, Vis};
}
}
DEBUG(dbgs() << "\tType: " << SymType << " Name: " << Name << "\n");
void RuntimeDyldImpl::emitCommonSymbols(const ObjectFile &Obj,
const CommonSymbolMap &CommonSymbols,
uint64_t TotalSize,
- SymbolTableMap &SymbolTable) {
+ RTDyldSymbolTable &SymbolTable) {
// Allocate memory for the section
unsigned SectionID = Sections.size();
uint8_t *Addr = MemMgr->allocateDataSection(TotalSize, sizeof(void *),
DEBUG(dbgs() << "Allocating common symbol " << Name << " address "
<< format("%p\n", Addr));
}
- SymbolTable[Name.data()] = SymbolLoc(SectionID, Offset);
+ uint32_t Flags = it->first.getFlags();
+ SymbolInfo::Visibility Vis =
+ (Flags & SymbolRef::SF_Exported) ?
+ SymbolInfo::Default : SymbolInfo::Hidden;
+ SymbolTable[Name.data()] = {SectionID, Offset, Vis};
Offset += Size;
Addr += Size;
}
// Relocation by symbol. If the symbol is found in the global symbol table,
// create an appropriate section relocation. Otherwise, add it to
// ExternalSymbolRelocations.
- SymbolTableMap::const_iterator Loc = GlobalSymbolTable.find(SymbolName);
+ RTDyldSymbolTable::const_iterator Loc = GlobalSymbolTable.find(SymbolName);
if (Loc == GlobalSymbolTable.end()) {
ExternalSymbolRelocations[SymbolName].push_back(RE);
} else {
// Copy the RE since we want to modify its addend.
RelocationEntry RECopy = RE;
- RECopy.Addend += Loc->second.second;
- Relocations[Loc->second.first].push_back(RECopy);
+ const auto &SymInfo = Loc->second;
+ RECopy.Addend += SymInfo.getOffset();
+ Relocations[SymInfo.getSectionID()].push_back(RECopy);
}
}
resolveRelocationList(Relocs, 0);
} else {
uint64_t Addr = 0;
- SymbolTableMap::const_iterator Loc = GlobalSymbolTable.find(Name);
+ RTDyldSymbolTable::const_iterator Loc = GlobalSymbolTable.find(Name);
if (Loc == GlobalSymbolTable.end()) {
// This is an external symbol, try to get its address from
// MemoryManager.
} else {
// We found the symbol in our global table. It was probably in a
// Module that we loaded previously.
- SymbolLoc SymLoc = Loc->second;
- Addr = getSectionLoadAddress(SymLoc.first) + SymLoc.second;
+ const auto &SymInfo = Loc->second;
+ Addr = getSectionLoadAddress(SymInfo.getSectionID()) +
+ SymInfo.getOffset();
}
// FIXME: Implement error handling that doesn't kill the host program!
return Dyld->getSymbolLoadAddress(Name);
}
+uint64_t RuntimeDyld::getExportedSymbolLoadAddress(StringRef Name) const {
+ if (!Dyld)
+ return 0;
+ return Dyld->getExportedSymbolLoadAddress(Name);
+}
+
void RuntimeDyld::resolveRelocations() { Dyld->resolveRelocations(); }
void RuntimeDyld::reassignSectionAddress(unsigned SectionID, uint64_t Addr) {
StringRef
RuntimeDyldCheckerImpl::getSubsectionStartingAt(StringRef Name) const {
- RuntimeDyldImpl::SymbolTableMap::const_iterator pos =
+ RTDyldSymbolTable::const_iterator pos =
getRTDyld().GlobalSymbolTable.find(Name);
if (pos == getRTDyld().GlobalSymbolTable.end())
return StringRef();
- RuntimeDyldImpl::SymbolLoc Loc = pos->second;
- uint8_t *SectionAddr = getRTDyld().getSectionAddress(Loc.first);
- return StringRef(reinterpret_cast<const char *>(SectionAddr) + Loc.second,
- getRTDyld().Sections[Loc.first].Size - Loc.second);
+ const auto &SymInfo = pos->second;
+ uint8_t *SectionAddr = getRTDyld().getSectionAddress(SymInfo.getSectionID());
+ return StringRef(reinterpret_cast<const char *>(SectionAddr) +
+ SymInfo.getOffset(),
+ getRTDyld().Sections[SymInfo.getSectionID()].Size -
+ SymInfo.getOffset());
}
void RuntimeDyldCheckerImpl::registerSection(
// If this is a (Section, Offset) pair, do a reverse lookup in the
// global symbol table to find the name.
for (auto &GSTEntry : getRTDyld().GlobalSymbolTable) {
- if (GSTEntry.second.first == StubMapEntry.first.SectionID &&
- GSTEntry.second.second ==
- static_cast<uint64_t>(StubMapEntry.first.Offset)) {
+ const auto &SymInfo = GSTEntry.second;
+ if (SymInfo.getSectionID() == StubMapEntry.first.SectionID &&
+ SymInfo.getOffset() ==
+ static_cast<uint64_t>(StubMapEntry.first.Offset)) {
SymbolName = GSTEntry.first();
break;
}
SymbolRef::Type SymType = SymbolRef::ST_Unknown;
// Search for the symbol in the global symbol table
- SymbolTableMap::const_iterator gsi = GlobalSymbolTable.end();
+ RTDyldSymbolTable::const_iterator gsi = GlobalSymbolTable.end();
if (Symbol != Obj.symbol_end()) {
gsi = GlobalSymbolTable.find(TargetName.data());
Symbol->getType(SymType);
}
if (gsi != GlobalSymbolTable.end()) {
- Value.SectionID = gsi->second.first;
- Value.Offset = gsi->second.second;
- Value.Addend = gsi->second.second + Addend;
+ const auto &SymInfo = gsi->second;
+ Value.SectionID = SymInfo.getSectionID();
+ Value.Offset = SymInfo.getOffset();
+ Value.Addend = SymInfo.getOffset() + Addend;
} else {
switch (SymType) {
case SymbolRef::ST_Debug: {
}
};
+/// @brief Symbol info for RuntimeDyld.
+class SymbolInfo {
+public:
+ typedef enum { Hidden = 0, Default = 1 } Visibility;
+
+ SymbolInfo() : Offset(0), SectionID(0), Vis(Hidden) {}
+
+ SymbolInfo(unsigned SectionID, uint64_t Offset, Visibility Vis)
+ : Offset(Offset), SectionID(SectionID), Vis(Vis) {}
+
+ unsigned getSectionID() const { return SectionID; }
+ uint64_t getOffset() const { return Offset; }
+ Visibility getVisibility() const { return Vis; }
+
+private:
+ uint64_t Offset;
+ unsigned SectionID : 31;
+ Visibility Vis : 1;
+};
+
+typedef StringMap<SymbolInfo> RTDyldSymbolTable;
+
class RuntimeDyldImpl {
friend class RuntimeDyld::LoadedObjectInfo;
friend class RuntimeDyldCheckerImpl;
// references it.
typedef std::map<SectionRef, unsigned> ObjSectionToIDMap;
- // A global symbol table for symbols from all loaded modules. Maps the
- // symbol name to a (SectionID, offset in section) pair.
- typedef std::pair<unsigned, uintptr_t> SymbolLoc;
- typedef StringMap<SymbolLoc> SymbolTableMap;
- SymbolTableMap GlobalSymbolTable;
+ // A global symbol table for symbols from all loaded modules.
+ RTDyldSymbolTable GlobalSymbolTable;
// Pair representing the size and alignment requirement for a common symbol.
typedef std::pair<unsigned, unsigned> CommonSymbolInfo;
/// symbol table.
void emitCommonSymbols(const ObjectFile &Obj,
const CommonSymbolMap &CommonSymbols,
- uint64_t TotalSize, SymbolTableMap &SymbolTable);
+ uint64_t TotalSize, RTDyldSymbolTable &SymbolTable);
/// \brief Emits section data from the object file to the MemoryManager.
/// \param IsCode if it's true then allocateCodeSection() will be
uint8_t* getSymbolAddress(StringRef Name) const {
// FIXME: Just look up as a function for now. Overly simple of course.
// Work in progress.
- SymbolTableMap::const_iterator pos = GlobalSymbolTable.find(Name);
+ RTDyldSymbolTable::const_iterator pos = GlobalSymbolTable.find(Name);
if (pos == GlobalSymbolTable.end())
return nullptr;
- SymbolLoc Loc = pos->second;
- return getSectionAddress(Loc.first) + Loc.second;
+ const auto &SymInfo = pos->second;
+ return getSectionAddress(SymInfo.getSectionID()) + SymInfo.getOffset();
}
uint64_t getSymbolLoadAddress(StringRef Name) const {
// FIXME: Just look up as a function for now. Overly simple of course.
// Work in progress.
- SymbolTableMap::const_iterator pos = GlobalSymbolTable.find(Name);
+ RTDyldSymbolTable::const_iterator pos = GlobalSymbolTable.find(Name);
if (pos == GlobalSymbolTable.end())
return 0;
- SymbolLoc Loc = pos->second;
- return getSectionLoadAddress(Loc.first) + Loc.second;
+ const auto &SymInfo = pos->second;
+ return getSectionLoadAddress(SymInfo.getSectionID()) + SymInfo.getOffset();
+ }
+
+ uint64_t getExportedSymbolLoadAddress(StringRef Name) const {
+ RTDyldSymbolTable::const_iterator pos = GlobalSymbolTable.find(Name);
+ if (pos == GlobalSymbolTable.end())
+ return 0;
+ const auto &SymInfo = pos->second;
+ if (SymInfo.getVisibility() == SymbolInfo::Hidden)
+ return 0;
+ return getSectionLoadAddress(SymInfo.getSectionID()) + SymInfo.getOffset();
}
void resolveRelocations();
symbol_iterator Symbol = RI->getSymbol();
StringRef TargetName;
Symbol->getName(TargetName);
- SymbolTableMap::const_iterator SI =
+ RTDyldSymbolTable::const_iterator SI =
GlobalSymbolTable.find(TargetName.data());
if (SI != GlobalSymbolTable.end()) {
- Value.SectionID = SI->second.first;
- Value.Offset = SI->second.second + RE.Addend;
+ const auto &SymInfo = SI->second;
+ Value.SectionID = SymInfo.getSectionID();
+ Value.Offset = SymInfo.getOffset() + RE.Addend;
} else {
Value.SymbolName = TargetName.data();
Value.Offset = RE.Addend;