本文整理汇总了C++中ObjectImage类的典型用法代码示例。如果您正苦于以下问题:C++ ObjectImage类的具体用法?C++ ObjectImage怎么用?C++ ObjectImage使用的例子?那么, 这里精选的类代码示例或许可以为您提供帮助。
在下文中一共展示了ObjectImage类的15个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。
示例1: computeSectionStubBufSize
// compute stub buffer size for the given section
unsigned RuntimeDyldImpl::computeSectionStubBufSize(ObjectImage &Obj,
const SectionRef &Section) {
unsigned StubSize = getMaxStubSize();
if (StubSize == 0) {
return 0;
}
// FIXME: this is an inefficient way to handle this. We should computed the
// necessary section allocation size in loadObject by walking all the sections
// once.
unsigned StubBufSize = 0;
for (section_iterator SI = Obj.begin_sections(), SE = Obj.end_sections();
SI != SE; ++SI) {
section_iterator RelSecI = SI->getRelocatedSection();
if (!(RelSecI == Section))
continue;
for (const RelocationRef &Reloc : SI->relocations()) {
(void)Reloc;
StubBufSize += StubSize;
}
}
// Get section data size and alignment
uint64_t DataSize = Section.getSize();
uint64_t Alignment64 = Section.getAlignment();
// Add stubbuf size alignment
unsigned Alignment = (unsigned)Alignment64 & 0xffffffffL;
unsigned StubAlignment = getStubAlignment();
unsigned EndAlignment = (DataSize | Alignment) & -(DataSize | Alignment);
if (StubAlignment > EndAlignment)
StubBufSize += StubAlignment - EndAlignment;
return StubBufSize;
}
示例2: finalizeLoad
void RuntimeDyldMachO::finalizeLoad(ObjectImage &ObjImg,
ObjSectionToIDMap &SectionMap) {
unsigned EHFrameSID = RTDYLD_INVALID_SECTION_ID;
unsigned TextSID = RTDYLD_INVALID_SECTION_ID;
unsigned ExceptTabSID = RTDYLD_INVALID_SECTION_ID;
ObjSectionToIDMap::iterator i, e;
for (i = SectionMap.begin(), e = SectionMap.end(); i != e; ++i) {
const SectionRef &Section = i->first;
StringRef Name;
Section.getName(Name);
if (Name == "__eh_frame")
EHFrameSID = i->second;
else if (Name == "__text")
TextSID = i->second;
else if (Name == "__gcc_except_tab")
ExceptTabSID = i->second;
else if (Name == "__jump_table")
populateJumpTable(cast<MachOObjectFile>(*ObjImg.getObjectFile()),
Section, i->second);
else if (Name == "__pointers")
populatePointersSection(cast<MachOObjectFile>(*ObjImg.getObjectFile()),
Section, i->second);
}
UnregisteredEHFrameSections.push_back(
EHFrameRelatedSections(EHFrameSID, TextSID, ExceptTabSID));
}
示例3: emitCommonSymbols
void RuntimeDyldImpl::emitCommonSymbols(ObjectImage &Obj,
const CommonSymbolMap &CommonSymbols,
uint64_t TotalSize,
SymbolTableMap &SymbolTable) {
// Allocate memory for the section
unsigned SectionID = Sections.size();
uint8_t *Addr = MemMgr->allocateDataSection(TotalSize, sizeof(void*),
SectionID);
if (!Addr)
report_fatal_error("Unable to allocate memory for common symbols!");
uint64_t Offset = 0;
Sections.push_back(SectionEntry(Addr, TotalSize, TotalSize, 0));
memset(Addr, 0, TotalSize);
DEBUG(dbgs() << "emitCommonSection SectionID: " << SectionID
<< " new addr: " << format("%p", Addr)
<< " DataSize: " << TotalSize
<< "\n");
// Assign the address of each symbol
for (CommonSymbolMap::const_iterator it = CommonSymbols.begin(),
itEnd = CommonSymbols.end(); it != itEnd; it++) {
StringRef Name;
it->first.getName(Name);
Obj.updateSymbolAddress(it->first, (uint64_t)Addr);
SymbolTable[Name.data()] = SymbolLoc(SectionID, Offset);
uint64_t Size = it->second;
Offset += Size;
Addr += Size;
}
}
示例4: locked
void MCJIT::generateCodeForModule(Module *M) {
// Get a thread lock to make sure we aren't trying to load multiple times
MutexGuard locked(lock);
// This must be a module which has already been added to this MCJIT instance.
assert(OwnedModules.ownsModule(M) &&
"MCJIT::generateCodeForModule: Unknown module.");
// Re-compilation is not supported
if (OwnedModules.hasModuleBeenLoaded(M))
return;
std::unique_ptr<ObjectBuffer> ObjectToLoad;
// Try to load the pre-compiled object from cache if possible
if (ObjCache) {
std::unique_ptr<MemoryBuffer> PreCompiledObject(ObjCache->getObject(M));
if (PreCompiledObject.get())
ObjectToLoad.reset(new ObjectBuffer(PreCompiledObject.release()));
}
// If the cache did not contain a suitable object, compile the object
if (!ObjectToLoad) {
ObjectToLoad.reset(emitObject(M));
assert(ObjectToLoad.get() && "Compilation did not produce an object.");
}
// Load the object into the dynamic linker.
// MCJIT now owns the ObjectImage pointer (via its LoadedObjects list).
ObjectImage *LoadedObject = Dyld.loadObject(ObjectToLoad.release());
LoadedObjects.push_back(LoadedObject);
if (!LoadedObject)
report_fatal_error(Dyld.getErrorString());
// FIXME: Make this optional, maybe even move it to a JIT event listener
LoadedObject->registerWithDebugger();
NotifyObjectEmitted(*LoadedObject);
OwnedModules.markModuleAsLoaded(M);
}
示例5: NotifyObjectEmitted
virtual void NotifyObjectEmitted(const ObjectImage &obj)
{
uint64_t Addr;
object::SymbolRef::Type SymbolType;
#ifdef LLVM35
for (const object::SymbolRef &sym_iter : obj.symbols()) {
sym_iter.getType(SymbolType);
if (SymbolType != object::SymbolRef::ST_Function) continue;
sym_iter.getAddress(Addr);
ObjectInfo tmp = {obj.getObjectFile(), sym_iter, obj.getData().size()};
objectmap[Addr] = tmp;
}
#else
error_code itererr;
object::symbol_iterator sym_iter = obj.begin_symbols();
object::symbol_iterator sym_end = obj.end_symbols();
for (; sym_iter != sym_end; sym_iter.increment(itererr)) {
sym_iter->getType(SymbolType);
if (SymbolType != object::SymbolRef::ST_Function) continue;
sym_iter->getAddress(Addr);
ObjectInfo tmp = {obj.getObjectFile(), *sym_iter};
objectmap[Addr] = tmp;
}
#endif
}
示例6: makeValueAddendPCRel
void RuntimeDyldMachO::makeValueAddendPCRel(RelocationValueRef &Value,
ObjectImage &ObjImg,
const relocation_iterator &RI,
unsigned OffsetToNextPC) {
const MachOObjectFile &Obj =
static_cast<const MachOObjectFile &>(*ObjImg.getObjectFile());
MachO::any_relocation_info RelInfo =
Obj.getRelocation(RI->getRawDataRefImpl());
bool IsPCRel = Obj.getAnyRelocationPCRel(RelInfo);
if (IsPCRel) {
uint64_t RelocAddr = 0;
RI->getAddress(RelocAddr);
Value.Addend += RelocAddr + OffsetToNextPC;
}
}
示例7: getRelocationValueRef
RelocationValueRef RuntimeDyldMachO::getRelocationValueRef(
ObjectImage &ObjImg, const relocation_iterator &RI,
const RelocationEntry &RE, ObjSectionToIDMap &ObjSectionToID,
const SymbolTableMap &Symbols) {
const MachOObjectFile &Obj =
static_cast<const MachOObjectFile &>(*ObjImg.getObjectFile());
MachO::any_relocation_info RelInfo =
Obj.getRelocation(RI->getRawDataRefImpl());
RelocationValueRef Value;
bool IsExternal = Obj.getPlainRelocationExternal(RelInfo);
if (IsExternal) {
symbol_iterator Symbol = RI->getSymbol();
StringRef TargetName;
Symbol->getName(TargetName);
SymbolTableMap::const_iterator SI = Symbols.find(TargetName.data());
if (SI != Symbols.end()) {
Value.SectionID = SI->second.first;
Value.Addend = SI->second.second + RE.Addend;
} else {
SI = GlobalSymbolTable.find(TargetName.data());
if (SI != GlobalSymbolTable.end()) {
Value.SectionID = SI->second.first;
Value.Addend = SI->second.second + RE.Addend;
} else {
Value.SymbolName = TargetName.data();
Value.Addend = RE.Addend;
}
}
} else {
SectionRef Sec = Obj.getRelocationSection(RelInfo);
bool IsCode = false;
Sec.isText(IsCode);
Value.SectionID = findOrEmitSection(ObjImg, Sec, IsCode, ObjSectionToID);
uint64_t Addr;
Sec.getAddress(Addr);
Value.Addend = RE.Addend - Addr;
}
return Value;
}
示例8: processRelocationRef
void RuntimeDyldMachO::processRelocationRef(unsigned SectionID,
RelocationRef RelI,
ObjectImage &Obj,
ObjSectionToIDMap &ObjSectionToID,
const SymbolTableMap &Symbols,
StubMap &Stubs) {
const ObjectFile *OF = Obj.getObjectFile();
const MachOObjectFile *MachO = static_cast<const MachOObjectFile*>(OF);
MachO::any_relocation_info RE= MachO->getRelocation(RelI.getRawDataRefImpl());
uint32_t RelType = MachO->getAnyRelocationType(RE);
// FIXME: Properly handle scattered relocations.
// For now, optimistically skip these: they can often be ignored, as
// the static linker will already have applied the relocation, and it
// only needs to be reapplied if symbols move relative to one another.
// Note: This will fail horribly where the relocations *do* need to be
// applied, but that was already the case.
if (MachO->isRelocationScattered(RE))
return;
RelocationValueRef Value;
SectionEntry &Section = Sections[SectionID];
bool isExtern = MachO->getPlainRelocationExternal(RE);
bool IsPCRel = MachO->getAnyRelocationPCRel(RE);
unsigned Size = MachO->getAnyRelocationLength(RE);
uint64_t Offset;
RelI.getOffset(Offset);
uint8_t *LocalAddress = Section.Address + Offset;
unsigned NumBytes = 1 << Size;
uint64_t Addend = 0;
memcpy(&Addend, LocalAddress, NumBytes);
if (isExtern) {
// Obtain the symbol name which is referenced in the relocation
symbol_iterator Symbol = RelI.getSymbol();
StringRef TargetName;
Symbol->getName(TargetName);
// First search for the symbol in the local symbol table
SymbolTableMap::const_iterator lsi = Symbols.find(TargetName.data());
if (lsi != Symbols.end()) {
Value.SectionID = lsi->second.first;
Value.Addend = lsi->second.second + Addend;
} else {
// Search for the symbol in the global symbol table
SymbolTableMap::const_iterator gsi = GlobalSymbolTable.find(TargetName.data());
if (gsi != GlobalSymbolTable.end()) {
Value.SectionID = gsi->second.first;
Value.Addend = gsi->second.second + Addend;
} else {
Value.SymbolName = TargetName.data();
Value.Addend = Addend;
}
}
} else {
SectionRef Sec = MachO->getRelocationSection(RE);
bool IsCode = false;
Sec.isText(IsCode);
Value.SectionID = findOrEmitSection(Obj, Sec, IsCode, ObjSectionToID);
uint64_t Addr;
Sec.getAddress(Addr);
Value.Addend = Addend - Addr;
if (IsPCRel)
Value.Addend += Offset + NumBytes;
}
if (Arch == Triple::x86_64 && (RelType == MachO::X86_64_RELOC_GOT ||
RelType == MachO::X86_64_RELOC_GOT_LOAD)) {
assert(IsPCRel);
assert(Size == 2);
StubMap::const_iterator i = Stubs.find(Value);
uint8_t *Addr;
if (i != Stubs.end()) {
Addr = Section.Address + i->second;
} else {
Stubs[Value] = Section.StubOffset;
uint8_t *GOTEntry = Section.Address + Section.StubOffset;
RelocationEntry RE(SectionID, Section.StubOffset,
MachO::X86_64_RELOC_UNSIGNED, 0, false, 3);
if (Value.SymbolName)
addRelocationForSymbol(RE, Value.SymbolName);
else
addRelocationForSection(RE, Value.SectionID);
Section.StubOffset += 8;
Addr = GOTEntry;
}
resolveRelocation(Section, Offset, (uint64_t)Addr,
MachO::X86_64_RELOC_UNSIGNED, Value.Addend, true, 2);
} else if (Arch == Triple::arm &&
(RelType & 0xf) == MachO::ARM_RELOC_BR24) {
// This is an ARM branch relocation, need to use a stub function.
// Look up for existing stub.
StubMap::const_iterator i = Stubs.find(Value);
if (i != Stubs.end())
resolveRelocation(Section, Offset,
(uint64_t)Section.Address + i->second,
RelType, 0, IsPCRel, Size);
else {
//.........这里部分代码省略.........
示例9: processRelocationRef
void RuntimeDyldMachO::processRelocationRef(const ObjRelocationInfo &Rel,
ObjectImage &Obj,
ObjSectionToIDMap &ObjSectionToID,
const SymbolTableMap &Symbols,
StubMap &Stubs) {
uint32_t RelType = (uint32_t) (Rel.Type & 0xffffffffL);
RelocationValueRef Value;
SectionEntry &Section = Sections[Rel.SectionID];
bool isExtern = (RelType >> 27) & 1;
if (isExtern) {
// Obtain the symbol name which is referenced in the relocation
StringRef TargetName;
const SymbolRef &Symbol = Rel.Symbol;
Symbol.getName(TargetName);
// First search for the symbol in the local symbol table
SymbolTableMap::const_iterator lsi = Symbols.find(TargetName.data());
if (lsi != Symbols.end()) {
Value.SectionID = lsi->second.first;
Value.Addend = lsi->second.second;
} else {
// Search for the symbol in the global symbol table
SymbolTableMap::const_iterator gsi = GlobalSymbolTable.find(TargetName.data());
if (gsi != GlobalSymbolTable.end()) {
Value.SectionID = gsi->second.first;
Value.Addend = gsi->second.second;
} else
Value.SymbolName = TargetName.data();
}
} else {
error_code err;
uint8_t sectionIndex = static_cast<uint8_t>(RelType & 0xFF);
section_iterator si = Obj.begin_sections(),
se = Obj.end_sections();
for (uint8_t i = 1; i < sectionIndex; i++) {
error_code err;
si.increment(err);
if (si == se)
break;
}
assert(si != se && "No section containing relocation!");
Value.SectionID = findOrEmitSection(Obj, *si, true, ObjSectionToID);
Value.Addend = 0;
// FIXME: The size and type of the relocation determines if we can
// encode an Addend in the target location itself, and if so, how many
// bytes we should read in order to get it. We don't yet support doing
// that, and just assuming it's sizeof(intptr_t) is blatantly wrong.
//Value.Addend = *(const intptr_t *)Target;
if (Value.Addend) {
// The MachO addend is an offset from the current section. We need it
// to be an offset from the destination section
Value.Addend += Section.ObjAddress - Sections[Value.SectionID].ObjAddress;
}
}
if (Arch == Triple::arm && (RelType & 0xf) == macho::RIT_ARM_Branch24Bit) {
// This is an ARM branch relocation, need to use a stub function.
// Look up for existing stub.
StubMap::const_iterator i = Stubs.find(Value);
if (i != Stubs.end())
resolveRelocation(Section, Rel.Offset,
(uint64_t)Section.Address + i->second,
RelType, 0);
else {
// Create a new stub function.
Stubs[Value] = Section.StubOffset;
uint8_t *StubTargetAddr = createStubFunction(Section.Address +
Section.StubOffset);
RelocationEntry RE(Rel.SectionID, StubTargetAddr - Section.Address,
macho::RIT_Vanilla, Value.Addend);
if (Value.SymbolName)
addRelocationForSymbol(RE, Value.SymbolName);
else
addRelocationForSection(RE, Value.SectionID);
resolveRelocation(Section, Rel.Offset,
(uint64_t)Section.Address + Section.StubOffset,
RelType, 0);
Section.StubOffset += getMaxStubSize();
}
} else {
RelocationEntry RE(Rel.SectionID, Rel.Offset, RelType, Value.Addend);
if (Value.SymbolName)
addRelocationForSymbol(RE, Value.SymbolName);
else
addRelocationForSection(RE, Value.SectionID);
}
}
示例10: NotifyObjectEmitted
virtual void NotifyObjectEmitted(const ObjectImage &obj)
#endif
{
int8_t gc_state = jl_gc_safe_enter();
uv_rwlock_wrlock(&threadsafe);
jl_gc_safe_leave(gc_state);
#ifdef LLVM36
object::section_iterator Section = obj.section_begin();
object::section_iterator EndSection = obj.section_end();
#else
object::section_iterator Section = obj.begin_sections();
object::section_iterator EndSection = obj.end_sections();
#endif
#if defined(_OS_WINDOWS_)
uint64_t SectionAddrCheck = 0; // assert that all of the Sections are at the same location
uint8_t *UnwindData = NULL;
#if defined(_CPU_X86_64_)
uint8_t *catchjmp = NULL;
for (const object::SymbolRef &sym_iter : obj.symbols()) {
StringRef sName;
#ifdef LLVM37
sName = sym_iter.getName().get();
#else
sym_iter.getName(sName);
#endif
uint8_t **pAddr = NULL;
if (sName.equals("__UnwindData")) {
pAddr = &UnwindData;
}
else if (sName.equals("__catchjmp")) {
pAddr = &catchjmp;
}
if (pAddr) {
uint64_t Addr, SectionAddr;
#if defined(LLVM38)
Addr = sym_iter.getAddress().get();
Section = sym_iter.getSection().get();
assert(Section != EndSection && Section->isText());
SectionAddr = L.getSectionLoadAddress(*Section);
#elif defined(LLVM37)
Addr = sym_iter.getAddress().get();
sym_iter.getSection(Section);
assert(Section != EndSection && Section->isText());
Section->getName(sName);
SectionAddr = L.getSectionLoadAddress(sName);
#elif defined(LLVM36)
sym_iter.getAddress(Addr);
sym_iter.getSection(Section);
assert(Section != EndSection && Section->isText());
Section->getName(sName);
SectionAddr = L.getSectionLoadAddress(sName);
#else // LLVM35
sym_iter.getAddress(Addr);
sym_iter.getSection(Section);
assert(Section != EndSection);
assert(!Section->isText(isText) && isText);
Section->getAddress(SectionAddr);
#endif
#ifdef LLVM36
Addr += SectionAddr;
#endif
*pAddr = (uint8_t*)Addr;
if (SectionAddrCheck)
assert(SectionAddrCheck == SectionAddr);
else
SectionAddrCheck = SectionAddr;
}
}
assert(catchjmp);
assert(UnwindData);
assert(SectionAddrCheck);
catchjmp[0] = 0x48;
catchjmp[1] = 0xb8; // mov RAX, QWORD PTR [&_seh_exception_handle]
*(uint64_t*)(&catchjmp[2]) = (uint64_t)&_seh_exception_handler;
catchjmp[10] = 0xff;
catchjmp[11] = 0xe0; // jmp RAX
UnwindData[0] = 0x09; // version info, UNW_FLAG_EHANDLER
UnwindData[1] = 4; // size of prolog (bytes)
UnwindData[2] = 2; // count of unwind codes (slots)
UnwindData[3] = 0x05; // frame register (rbp) = rsp
UnwindData[4] = 4; // second instruction
UnwindData[5] = 0x03; // mov RBP, RSP
UnwindData[6] = 1; // first instruction
UnwindData[7] = 0x50; // push RBP
*(DWORD*)&UnwindData[8] = (DWORD)(catchjmp - (uint8_t*)SectionAddrCheck); // relative location of catchjmp
#endif // defined(_OS_X86_64_)
#endif // defined(_OS_WINDOWS_)
#ifdef LLVM37
auto symbols = object::computeSymbolSizes(obj);
for(const auto &sym_size : symbols) {
const object::SymbolRef &sym_iter = sym_size.first;
object::SymbolRef::Type SymbolType = sym_iter.getType();
if (SymbolType != object::SymbolRef::ST_Function) continue;
uint64_t Size = sym_size.second;
uint64_t Addr = sym_iter.getAddress().get();
#ifdef LLVM38
Section = sym_iter.getSection().get();
#else
//.........这里部分代码省略.........
示例11: computeTotalAllocSize
// Compute an upper bound of the memory size that is required to load all
// sections
void RuntimeDyldImpl::computeTotalAllocSize(ObjectImage &Obj,
uint64_t &CodeSize,
uint64_t &DataSizeRO,
uint64_t &DataSizeRW) {
// Compute the size of all sections required for execution
std::vector<uint64_t> CodeSectionSizes;
std::vector<uint64_t> ROSectionSizes;
std::vector<uint64_t> RWSectionSizes;
uint64_t MaxAlignment = sizeof(void *);
// Collect sizes of all sections to be loaded;
// also determine the max alignment of all sections
for (section_iterator SI = Obj.begin_sections(), SE = Obj.end_sections();
SI != SE; ++SI) {
const SectionRef &Section = *SI;
bool IsRequired = Section.isRequiredForExecution();
// Consider only the sections that are required to be loaded for execution
if (IsRequired) {
StringRef Name;
uint64_t DataSize = Section.getSize();
uint64_t Alignment64 = Section.getAlignment();
bool IsCode = Section.isText();
bool IsReadOnly = Section.isReadOnlyData();
Check(Section.getName(Name));
unsigned Alignment = (unsigned)Alignment64 & 0xffffffffL;
uint64_t StubBufSize = computeSectionStubBufSize(Obj, Section);
uint64_t SectionSize = DataSize + StubBufSize;
// The .eh_frame section (at least on Linux) needs an extra four bytes
// padded
// with zeroes added at the end. For MachO objects, this section has a
// slightly different name, so this won't have any effect for MachO
// objects.
if (Name == ".eh_frame")
SectionSize += 4;
if (SectionSize > 0) {
// save the total size of the section
if (IsCode) {
CodeSectionSizes.push_back(SectionSize);
} else if (IsReadOnly) {
ROSectionSizes.push_back(SectionSize);
} else {
RWSectionSizes.push_back(SectionSize);
}
// update the max alignment
if (Alignment > MaxAlignment) {
MaxAlignment = Alignment;
}
}
}
}
// Compute the size of all common symbols
uint64_t CommonSize = 0;
for (symbol_iterator I = Obj.begin_symbols(), E = Obj.end_symbols(); I != E;
++I) {
uint32_t Flags = I->getFlags();
if (Flags & SymbolRef::SF_Common) {
// Add the common symbols to a list. We'll allocate them all below.
uint64_t Size = 0;
Check(I->getSize(Size));
CommonSize += Size;
}
}
if (CommonSize != 0) {
RWSectionSizes.push_back(CommonSize);
}
// Compute the required allocation space for each different type of sections
// (code, read-only data, read-write data) assuming that all sections are
// allocated with the max alignment. Note that we cannot compute with the
// individual alignments of the sections, because then the required size
// depends on the order, in which the sections are allocated.
CodeSize = computeAllocationSizeForSections(CodeSectionSizes, MaxAlignment);
DataSizeRO = computeAllocationSizeForSections(ROSectionSizes, MaxAlignment);
DataSizeRW = computeAllocationSizeForSections(RWSectionSizes, MaxAlignment);
}
示例12: emitSection
unsigned RuntimeDyldImpl::emitSection(ObjectImage &Obj,
const SectionRef &Section,
bool IsCode) {
unsigned StubBufSize = 0,
StubSize = getMaxStubSize();
error_code err;
if (StubSize > 0) {
for (relocation_iterator i = Section.begin_relocations(),
e = Section.end_relocations(); i != e; i.increment(err), Check(err))
StubBufSize += StubSize;
}
StringRef data;
uint64_t Alignment64;
Check(Section.getContents(data));
Check(Section.getAlignment(Alignment64));
unsigned Alignment = (unsigned)Alignment64 & 0xffffffffL;
bool IsRequired;
bool IsVirtual;
bool IsZeroInit;
uint64_t DataSize;
Check(Section.isRequiredForExecution(IsRequired));
Check(Section.isVirtual(IsVirtual));
Check(Section.isZeroInit(IsZeroInit));
Check(Section.getSize(DataSize));
unsigned Allocate;
unsigned SectionID = Sections.size();
uint8_t *Addr;
const char *pData = 0;
// Some sections, such as debug info, don't need to be loaded for execution.
// Leave those where they are.
if (IsRequired) {
Allocate = DataSize + StubBufSize;
Addr = IsCode
? MemMgr->allocateCodeSection(Allocate, Alignment, SectionID)
: MemMgr->allocateDataSection(Allocate, Alignment, SectionID);
if (!Addr)
report_fatal_error("Unable to allocate section memory!");
// Virtual sections have no data in the object image, so leave pData = 0
if (!IsVirtual)
pData = data.data();
// Zero-initialize or copy the data from the image
if (IsZeroInit || IsVirtual)
memset(Addr, 0, DataSize);
else
memcpy(Addr, pData, DataSize);
DEBUG(dbgs() << "emitSection SectionID: " << SectionID
<< " obj addr: " << format("%p", pData)
<< " new addr: " << format("%p", Addr)
<< " DataSize: " << DataSize
<< " StubBufSize: " << StubBufSize
<< " Allocate: " << Allocate
<< "\n");
Obj.updateSectionAddress(Section, (uint64_t)Addr);
}
else {
// Even if we didn't load the section, we need to record an entry for it
// to handle later processing (and by 'handle' I mean don't do anything
// with these sections).
Allocate = 0;
Addr = 0;
DEBUG(dbgs() << "emitSection SectionID: " << SectionID
<< " obj addr: " << format("%p", data.data())
<< " new addr: 0"
<< " DataSize: " << DataSize
<< " StubBufSize: " << StubBufSize
<< " Allocate: " << Allocate
<< "\n");
}
Sections.push_back(SectionEntry(Addr, Allocate, DataSize,(uintptr_t)pData));
return SectionID;
}
示例13: NotifyObjectEmitted
virtual void NotifyObjectEmitted(const ObjectImage &obj)
#endif
{
uint64_t Addr;
uint64_t Size;
object::SymbolRef::Type SymbolType;
#ifdef LLVM36
object::section_iterator Section = obj.section_begin();
object::section_iterator EndSection = obj.section_end();
uint64_t SectionAddr = 0;
StringRef sName;
#else
object::section_iterator Section = obj.begin_sections();
object::section_iterator EndSection = obj.end_sections();
bool isText;
#ifndef _OS_LINUX_
StringRef sName;
#endif
#endif
#ifndef LLVM36
uint64_t SectionAddr = 0;
#endif
uint64_t SectionSize = 0;
uint64_t SectionAddrCheck = 0; // assert that all of the Sections are at the same location
#if defined(_OS_WINDOWS_)
#if defined(_CPU_X86_64_)
uint8_t *UnwindData = NULL;
uint8_t *catchjmp = NULL;
for (const object::SymbolRef &sym_iter : obj.symbols()) {
# ifdef LLVM37
sName = sym_iter.getName().get();
# else
sym_iter.getName(sName);
# endif
if (sName.equals("__UnwindData")) {
# ifdef LLVM37
Addr = sym_iter.getAddress().get();
# else
sym_iter.getAddress(Addr);
# endif
sym_iter.getSection(Section);
# ifdef LLVM36
assert(Section->isText());
Section->getName(sName);
SectionAddr = L.getSectionLoadAddress(sName);
Addr += SectionAddr;
# else
if (Section->isText(isText) || !isText) assert(0 && "!isText");
Section->getAddress(SectionAddr);
# endif
UnwindData = (uint8_t*)Addr;
if (SectionAddrCheck)
assert(SectionAddrCheck == SectionAddr);
else
SectionAddrCheck = SectionAddr;
}
if (sName.equals("__catchjmp")) {
# ifdef LLVM37
Addr = sym_iter.getAddress().get();
# else
sym_iter.getAddress(Addr);
# endif
sym_iter.getSection(Section);
# ifdef LLVM36
assert(Section->isText());
Section->getName(sName);
SectionAddr = L.getSectionLoadAddress(sName);
Addr += SectionAddr;
# else
if (Section->isText(isText) || !isText) assert(0 && "!isText");
Section->getAddress(SectionAddr);
# endif
catchjmp = (uint8_t*)Addr;
if (SectionAddrCheck)
assert(SectionAddrCheck == SectionAddr);
else
SectionAddrCheck = SectionAddr;
}
}
assert(catchjmp);
assert(UnwindData);
catchjmp[0] = 0x48;
catchjmp[1] = 0xb8; // mov RAX, QWORD PTR [&_seh_exception_handle]
*(uint64_t*)(&catchjmp[2]) = (uint64_t)&_seh_exception_handler;
catchjmp[10] = 0xff;
catchjmp[11] = 0xe0; // jmp RAX
UnwindData[0] = 0x09; // version info, UNW_FLAG_EHANDLER
UnwindData[1] = 4; // size of prolog (bytes)
UnwindData[2] = 2; // count of unwind codes (slots)
UnwindData[3] = 0x05; // frame register (rbp) = rsp
UnwindData[4] = 4; // second instruction
UnwindData[5] = 0x03; // mov RBP, RSP
UnwindData[6] = 1; // first instruction
UnwindData[7] = 0x50; // push RBP
*(DWORD*)&UnwindData[8] = (DWORD)(catchjmp - (uint8_t*)SectionAddr); // relative location of catchjmp
#else // defined(_OS_X86_64_)
uint8_t *UnwindData = NULL;
#endif // defined(_OS_X86_64_)
//.........这里部分代码省略.........
示例14: emitSection
unsigned RuntimeDyldImpl::emitSection(ObjectImage &Obj,
const SectionRef &Section,
bool IsCode) {
unsigned StubBufSize = 0,
StubSize = getMaxStubSize();
error_code err;
const ObjectFile *ObjFile = Obj.getObjectFile();
// FIXME: this is an inefficient way to handle this. We should computed the
// necessary section allocation size in loadObject by walking all the sections
// once.
if (StubSize > 0) {
for (section_iterator SI = ObjFile->begin_sections(),
SE = ObjFile->end_sections();
SI != SE; SI.increment(err), Check(err)) {
section_iterator RelSecI = SI->getRelocatedSection();
if (!(RelSecI == Section))
continue;
for (relocation_iterator I = SI->begin_relocations(),
E = SI->end_relocations(); I != E; I.increment(err), Check(err)) {
StubBufSize += StubSize;
}
}
}
StringRef data;
uint64_t Alignment64;
Check(Section.getContents(data));
Check(Section.getAlignment(Alignment64));
unsigned Alignment = (unsigned)Alignment64 & 0xffffffffL;
bool IsRequired;
bool IsVirtual;
bool IsZeroInit;
bool IsReadOnly;
uint64_t DataSize;
StringRef Name;
Check(Section.isRequiredForExecution(IsRequired));
Check(Section.isVirtual(IsVirtual));
Check(Section.isZeroInit(IsZeroInit));
Check(Section.isReadOnlyData(IsReadOnly));
Check(Section.getSize(DataSize));
Check(Section.getName(Name));
if (StubSize > 0) {
unsigned StubAlignment = getStubAlignment();
unsigned EndAlignment = (DataSize | Alignment) & -(DataSize | Alignment);
if (StubAlignment > EndAlignment)
StubBufSize += StubAlignment - EndAlignment;
}
unsigned Allocate;
unsigned SectionID = Sections.size();
uint8_t *Addr;
const char *pData = 0;
// Some sections, such as debug info, don't need to be loaded for execution.
// Leave those where they are.
if (IsRequired) {
Allocate = DataSize + StubBufSize;
Addr = IsCode
? MemMgr->allocateCodeSection(Allocate, Alignment, SectionID)
: MemMgr->allocateDataSection(Allocate, Alignment, SectionID, IsReadOnly);
if (!Addr)
report_fatal_error("Unable to allocate section memory!");
// Virtual sections have no data in the object image, so leave pData = 0
if (!IsVirtual)
pData = data.data();
// Zero-initialize or copy the data from the image
if (IsZeroInit || IsVirtual)
memset(Addr, 0, DataSize);
else
memcpy(Addr, pData, DataSize);
DEBUG(dbgs() << "emitSection SectionID: " << SectionID
<< " Name: " << Name
<< " obj addr: " << format("%p", pData)
<< " new addr: " << format("%p", Addr)
<< " DataSize: " << DataSize
<< " StubBufSize: " << StubBufSize
<< " Allocate: " << Allocate
<< "\n");
Obj.updateSectionAddress(Section, (uint64_t)Addr);
}
else {
// Even if we didn't load the section, we need to record an entry for it
// to handle later processing (and by 'handle' I mean don't do anything
// with these sections).
Allocate = 0;
Addr = 0;
DEBUG(dbgs() << "emitSection SectionID: " << SectionID
<< " Name: " << Name
<< " obj addr: " << format("%p", data.data())
<< " new addr: 0"
<< " DataSize: " << DataSize
<< " StubBufSize: " << StubBufSize
<< " Allocate: " << Allocate
<< "\n");
//.........这里部分代码省略.........
示例15: emitSection
unsigned RuntimeDyldImpl::emitSection(ObjectImage &Obj,
const SectionRef &Section, bool IsCode) {
StringRef data;
uint64_t Alignment64;
Check(Section.getContents(data));
Check(Section.getAlignment(Alignment64));
unsigned Alignment = (unsigned)Alignment64 & 0xffffffffL;
bool IsRequired;
bool IsVirtual;
bool IsZeroInit;
bool IsReadOnly;
uint64_t DataSize;
unsigned PaddingSize = 0;
unsigned StubBufSize = 0;
StringRef Name;
Check(Section.isRequiredForExecution(IsRequired));
Check(Section.isVirtual(IsVirtual));
Check(Section.isZeroInit(IsZeroInit));
Check(Section.isReadOnlyData(IsReadOnly));
Check(Section.getSize(DataSize));
Check(Section.getName(Name));
StubBufSize = computeSectionStubBufSize(Obj, Section);
// The .eh_frame section (at least on Linux) needs an extra four bytes padded
// with zeroes added at the end. For MachO objects, this section has a
// slightly different name, so this won't have any effect for MachO objects.
if (Name == ".eh_frame")
PaddingSize = 4;
uintptr_t Allocate;
unsigned SectionID = Sections.size();
uint8_t *Addr;
const char *pData = 0;
// Some sections, such as debug info, don't need to be loaded for execution.
// Leave those where they are.
if (IsRequired) {
Allocate = DataSize + PaddingSize + StubBufSize;
Addr = IsCode ? MemMgr->allocateCodeSection(Allocate, Alignment, SectionID,
Name)
: MemMgr->allocateDataSection(Allocate, Alignment, SectionID,
Name, IsReadOnly);
if (!Addr)
report_fatal_error("Unable to allocate section memory!");
// Virtual sections have no data in the object image, so leave pData = 0
if (!IsVirtual)
pData = data.data();
// Zero-initialize or copy the data from the image
if (IsZeroInit || IsVirtual)
memset(Addr, 0, DataSize);
else
memcpy(Addr, pData, DataSize);
// Fill in any extra bytes we allocated for padding
if (PaddingSize != 0) {
memset(Addr + DataSize, 0, PaddingSize);
// Update the DataSize variable so that the stub offset is set correctly.
DataSize += PaddingSize;
}
DEBUG(dbgs() << "emitSection SectionID: " << SectionID << " Name: " << Name
<< " obj addr: " << format("%p", pData)
<< " new addr: " << format("%p", Addr)
<< " DataSize: " << DataSize << " StubBufSize: " << StubBufSize
<< " Allocate: " << Allocate << "\n");
Obj.updateSectionAddress(Section, (uint64_t)Addr);
} else {
// Even if we didn't load the section, we need to record an entry for it
// to handle later processing (and by 'handle' I mean don't do anything
// with these sections).
Allocate = 0;
Addr = 0;
DEBUG(dbgs() << "emitSection SectionID: " << SectionID << " Name: " << Name
<< " obj addr: " << format("%p", data.data()) << " new addr: 0"
<< " DataSize: " << DataSize << " StubBufSize: " << StubBufSize
<< " Allocate: " << Allocate << "\n");
}
Sections.push_back(SectionEntry(Name, Addr, DataSize, (uintptr_t)pData));
return SectionID;
}