summaryrefslogtreecommitdiffstats
path: root/contrib/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h')
-rw-r--r--contrib/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h69
1 files changed, 60 insertions, 9 deletions
diff --git a/contrib/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h b/contrib/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h
index e085a92..dafd3c8 100644
--- a/contrib/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h
+++ b/contrib/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h
@@ -30,6 +30,7 @@
#include "llvm/Support/SwapByteOrder.h"
#include "llvm/Support/raw_ostream.h"
#include <map>
+#include <unordered_map>
#include <system_error>
using namespace llvm;
@@ -50,7 +51,6 @@ class Twine;
/// SectionEntry - represents a section emitted into memory by the dynamic
/// linker.
class SectionEntry {
-public:
/// Name - section name.
std::string Name;
@@ -70,15 +70,54 @@ public:
/// relocations (like ARM).
uintptr_t StubOffset;
+ /// The total amount of space allocated for this section. This includes the
+ /// section size and the maximum amount of space that the stubs can occupy.
+ size_t AllocationSize;
+
/// ObjAddress - address of the section in the in-memory object file. Used
/// for calculating relocations in some object formats (like MachO).
uintptr_t ObjAddress;
+public:
SectionEntry(StringRef name, uint8_t *address, size_t size,
- uintptr_t objAddress)
+ size_t allocationSize, uintptr_t objAddress)
: Name(name), Address(address), Size(size),
LoadAddress(reinterpret_cast<uintptr_t>(address)), StubOffset(size),
- ObjAddress(objAddress) {}
+ AllocationSize(allocationSize), ObjAddress(objAddress) {
+ // AllocationSize is used only in asserts, prevent an "unused private field"
+ // warning:
+ (void)AllocationSize;
+ }
+
+ StringRef getName() const { return Name; }
+
+ uint8_t *getAddress() const { return Address; }
+
+ /// \brief Return the address of this section with an offset.
+ uint8_t *getAddressWithOffset(unsigned OffsetBytes) const {
+ assert(OffsetBytes <= AllocationSize && "Offset out of bounds!");
+ return Address + OffsetBytes;
+ }
+
+ size_t getSize() const { return Size; }
+
+ uint64_t getLoadAddress() const { return LoadAddress; }
+ void setLoadAddress(uint64_t LA) { LoadAddress = LA; }
+
+ /// \brief Return the load address of this section with an offset.
+ uint64_t getLoadAddressWithOffset(unsigned OffsetBytes) const {
+ assert(OffsetBytes <= AllocationSize && "Offset out of bounds!");
+ return LoadAddress + OffsetBytes;
+ }
+
+ uintptr_t getStubOffset() const { return StubOffset; }
+
+ void advanceStubOffset(unsigned StubSize) {
+ StubOffset += StubSize;
+ assert(StubOffset <= AllocationSize && "Not enough space allocated!");
+ }
+
+ uintptr_t getObjAddress() const { return ObjAddress; }
};
/// RelocationEntry - used to represent relocations internally in the dynamic
@@ -188,6 +227,8 @@ class RuntimeDyldImpl {
friend class RuntimeDyld::LoadedObjectInfo;
friend class RuntimeDyldCheckerImpl;
protected:
+ static const unsigned AbsoluteSymbolSection = ~0U;
+
// The MemoryManager to load objects into.
RuntimeDyld::MemoryManager &MemMgr;
@@ -224,7 +265,7 @@ protected:
// Relocations to sections already loaded. Indexed by SectionID which is the
// source of the address. The target where the address will be written is
// SectionID/Offset in the relocation itself.
- DenseMap<unsigned, RelocationList> Relocations;
+ std::unordered_map<unsigned, RelocationList> Relocations;
// Relocations to external symbols that are not yet resolved. Symbols are
// external when they aren't found in the global symbol table of all loaded
@@ -269,11 +310,11 @@ protected:
}
uint64_t getSectionLoadAddress(unsigned SectionID) const {
- return Sections[SectionID].LoadAddress;
+ return Sections[SectionID].getLoadAddress();
}
uint8_t *getSectionAddress(unsigned SectionID) const {
- return (uint8_t *)Sections[SectionID].Address;
+ return Sections[SectionID].getAddress();
}
void writeInt16BE(uint8_t *Addr, uint16_t Value) {
@@ -378,7 +419,12 @@ protected:
const SectionRef &Section);
// \brief Implementation of the generic part of the loadObject algorithm.
- std::pair<unsigned, unsigned> loadObjectImpl(const object::ObjectFile &Obj);
+ ObjSectionToIDMap loadObjectImpl(const object::ObjectFile &Obj);
+
+ // \brief Return true if the relocation R may require allocating a stub.
+ virtual bool relocationNeedsStub(const RelocationRef &R) const {
+ return true; // Conservative answer
+ }
public:
RuntimeDyldImpl(RuntimeDyld::MemoryManager &MemMgr,
@@ -407,6 +453,9 @@ public:
if (pos == GlobalSymbolTable.end())
return nullptr;
const auto &SymInfo = pos->second;
+ // Absolute symbols do not have a local address.
+ if (SymInfo.getSectionID() == AbsoluteSymbolSection)
+ return nullptr;
return getSectionAddress(SymInfo.getSectionID()) + SymInfo.getOffset();
}
@@ -417,8 +466,10 @@ public:
if (pos == GlobalSymbolTable.end())
return nullptr;
const auto &SymEntry = pos->second;
- uint64_t TargetAddr =
- getSectionLoadAddress(SymEntry.getSectionID()) + SymEntry.getOffset();
+ uint64_t SectionAddr = 0;
+ if (SymEntry.getSectionID() != AbsoluteSymbolSection)
+ SectionAddr = getSectionLoadAddress(SymEntry.getSectionID());
+ uint64_t TargetAddr = SectionAddr + SymEntry.getOffset();
return RuntimeDyld::SymbolInfo(TargetAddr, SymEntry.getFlags());
}
OpenPOWER on IntegriCloud