15 #include "llvm/Config/config.h"
27 return allocateSection(RODataMem, Size, Alignment);
28 return allocateSection(RWDataMem, Size, Alignment);
35 return allocateSection(CodeMem, Size, Alignment);
38 uint8_t *SectionMemoryManager::allocateSection(MemoryGroup &MemGroup,
44 assert(!(Alignment & (Alignment - 1)) &&
"Alignment must be a power of two.");
46 uintptr_t RequiredSize = Alignment * ((Size + Alignment - 1)/Alignment + 1);
51 for (
int i = 0, e = MemGroup.FreeMem.size(); i != e; ++i) {
53 if (MB.
size() >= RequiredSize) {
54 Addr = (uintptr_t)MB.
base();
55 uintptr_t EndOfBlock = Addr + MB.
size();
57 Addr = (Addr + Alignment - 1) & ~(uintptr_t)(Alignment - 1);
60 EndOfBlock - Addr - Size);
61 return (uint8_t*)Addr;
88 MemGroup.AllocatedMem.push_back(MB);
89 Addr = (uintptr_t)MB.base();
90 uintptr_t EndOfBlock = Addr + MB.size();
93 Addr = (Addr + Alignment - 1) & ~(uintptr_t)(Alignment - 1);
97 unsigned FreeSize = EndOfBlock-Addr-Size;
99 MemGroup.FreeMem.push_back(sys::MemoryBlock((
void*)(Addr + Size), FreeSize));
102 return (uint8_t*)Addr;
111 CodeMem.FreeMem.clear();
114 ec = applyMemoryGroupPermissions(CodeMem,
118 *ErrMsg = ec.message();
124 RODataMem.FreeMem.clear();
127 ec = applyMemoryGroupPermissions(RODataMem,
131 *ErrMsg = ec.message();
147 SectionMemoryManager::applyMemoryGroupPermissions(MemoryGroup &MemGroup,
148 unsigned Permissions) {
150 for (
int i = 0, e = MemGroup.AllocatedMem.size(); i != e; ++i) {
159 return std::error_code();
163 for (
int i = 0, e = CodeMem.AllocatedMem.size(); i != e; ++i)
165 CodeMem.AllocatedMem[i].size());
169 for (
unsigned i = 0, e = CodeMem.AllocatedMem.size(); i != e; ++i)
171 for (
unsigned i = 0, e = RWDataMem.AllocatedMem.size(); i != e; ++i)
173 for (
unsigned i = 0, e = RODataMem.AllocatedMem.size(); i != e; ++i)
static std::error_code releaseMappedMemory(MemoryBlock &Block)
This method releases a block of memory that was allocated with the allocateMappedMemory method...
static MemoryBlock allocateMappedMemory(size_t NumBytes, const MemoryBlock *const NearBlock, unsigned Flags, std::error_code &EC)
This method allocates a block of memory that is suitable for loading dynamically generated code (e...
static void InvalidateInstructionCache(const void *Addr, size_t Len)
InvalidateInstructionCache - Before the JIT can run a block of code that has been emitted it must inv...
~SectionMemoryManager() override
virtual void invalidateInstructionCache()
Invalidate instruction cache for code sections.
uint8_t * allocateCodeSection(uintptr_t Size, unsigned Alignment, unsigned SectionID, StringRef SectionName) override
Allocates a memory block of (at least) the given size suitable for executable code.
uint8_t * allocateDataSection(uintptr_t Size, unsigned Alignment, unsigned SectionID, StringRef SectionName, bool isReadOnly) override
Allocates a memory block of (at least) the given size suitable for executable code.
This class encapsulates the notion of a memory block which has an address and a size.
bool finalizeMemory(std::string *ErrMsg=nullptr) override
Update section-specific memory permissions and other attributes.
StringRef - Represent a constant reference to a string, i.e.
static std::error_code protectMappedMemory(const MemoryBlock &Block, unsigned Flags)
This method sets the protection flags for a block of memory to the state specified by /p Flags...