From 27c669242aedf4ff3e3b38cb204554b459633e77 Mon Sep 17 00:00:00 2001 From: Jeffrey Yasskin Date: Tue, 20 Oct 2009 18:13:21 +0000 Subject: Move the Function*->allocated blocks map from the JITMemoryManager to the JITEmitter. I'm gradually making Functions auto-remove themselves from the JIT when they're destroyed. In this case, the Function needs to be removed from the JITEmitter, but the map recording which Functions need to be removed lived behind the JITMemoryManager interface, which made things difficult. This patch replaces the deallocateMemForFunction(Function*) method with a pair of methods deallocateFunctionBody(void *) and deallocateExceptionTable(void *) corresponding to the two startFoo/endFoo pairs. llvm-svn: 84651 --- llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp | 20 +++++++++-- llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp | 44 +++++++---------------- 2 files changed, 30 insertions(+), 34 deletions(-) (limited to 'llvm/lib/ExecutionEngine/JIT') diff --git a/llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp b/llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp index 5066447cd98..073d6fbbde6 100644 --- a/llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp +++ b/llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp @@ -42,6 +42,7 @@ #include "llvm/System/Disassembler.h" #include "llvm/System/Memory.h" #include "llvm/Target/TargetInstrInfo.h" +#include "llvm/ADT/DenseMap.h" #include "llvm/ADT/SmallPtrSet.h" #include "llvm/ADT/SmallVector.h" #include "llvm/ADT/Statistic.h" @@ -548,6 +549,13 @@ namespace { /// finishFunction. JITEvent_EmittedFunctionDetails EmissionDetails; + struct EmittedCode { + void *FunctionBody; + void *ExceptionTable; + EmittedCode() : FunctionBody(0), ExceptionTable(0) {} + }; + DenseMap EmittedFunctions; + // CurFnStubUses - For a given Function, a vector of stubs that it // references. This facilitates the JIT detecting that a stub is no // longer used, so that it may be deallocated. @@ -1011,7 +1019,8 @@ void JITEmitter::startFunction(MachineFunction &F) { BufferBegin = CurBufferPtr = MemMgr->startFunctionBody(F.getFunction(), ActualSize); BufferEnd = BufferBegin+ActualSize; - + EmittedFunctions[F.getFunction()].FunctionBody = BufferBegin; + // Ensure the constant pool/jump table info is at least 4-byte aligned. emitAlignment(16); @@ -1201,6 +1210,7 @@ bool JITEmitter::finishFunction(MachineFunction &F) { BufferBegin = CurBufferPtr = MemMgr->startExceptionTable(F.getFunction(), ActualSize); BufferEnd = BufferBegin+ActualSize; + EmittedFunctions[F.getFunction()].ExceptionTable = BufferBegin; uint8_t *EhStart; uint8_t *FrameRegister = DE->EmitDwarfTable(F, *this, FnStart, FnEnd, EhStart); @@ -1244,7 +1254,13 @@ void JITEmitter::retryWithMoreMemory(MachineFunction &F) { /// deallocateMemForFunction - Deallocate all memory for the specified /// function body. Also drop any references the function has to stubs. void JITEmitter::deallocateMemForFunction(const Function *F) { - MemMgr->deallocateMemForFunction(F); + DenseMap::iterator Emitted = + EmittedFunctions.find(F); + if (Emitted != EmittedFunctions.end()) { + MemMgr->deallocateFunctionBody(Emitted->second.FunctionBody); + MemMgr->deallocateExceptionTable(Emitted->second.ExceptionTable); + EmittedFunctions.erase(Emitted); + } // TODO: Do we need to unregister exception handling information from libgcc // here? diff --git a/llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp b/llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp index 474843f0662..ea9d09fffc7 100644 --- a/llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp +++ b/llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp @@ -297,9 +297,6 @@ namespace { uint8_t *GOTBase; // Target Specific reserved memory void *DlsymTable; // Stub external symbol information - - std::map FunctionBlocks; - std::map TableBlocks; public: DefaultJITMemoryManager(); ~DefaultJITMemoryManager(); @@ -414,7 +411,6 @@ namespace { "Mismatched function start/end!"); uintptr_t BlockSize = FunctionEnd - (uint8_t *)CurBlock; - FunctionBlocks[F] = CurBlock; // Release the memory at the end of this block that isn't needed. FreeMemoryList =CurBlock->TrimAllocationToSize(FreeMemoryList, BlockSize); @@ -464,7 +460,6 @@ namespace { "Mismatched table start/end!"); uintptr_t BlockSize = TableEnd - (uint8_t *)CurBlock; - TableBlocks[F] = CurBlock; // Release the memory at the end of this block that isn't needed. FreeMemoryList =CurBlock->TrimAllocationToSize(FreeMemoryList, BlockSize); @@ -478,15 +473,9 @@ namespace { return DlsymTable; } - /// deallocateMemForFunction - Deallocate all memory for the specified - /// function body. - void deallocateMemForFunction(const Function *F) { - std::map::iterator - I = FunctionBlocks.find(F); - if (I == FunctionBlocks.end()) return; - + void deallocateBlock(void *Block) { // Find the block that is allocated for this function. - MemoryRangeHeader *MemRange = I->second; + MemoryRangeHeader *MemRange = static_cast(Block) - 1; assert(MemRange->ThisAllocated && "Block isn't allocated!"); // Fill the buffer with garbage! @@ -496,27 +485,18 @@ namespace { // Free the memory. FreeMemoryList = MemRange->FreeBlock(FreeMemoryList); - - // Finally, remove this entry from FunctionBlocks. - FunctionBlocks.erase(I); - - I = TableBlocks.find(F); - if (I == TableBlocks.end()) return; - - // Find the block that is allocated for this function. - MemRange = I->second; - assert(MemRange->ThisAllocated && "Block isn't allocated!"); + } - // Fill the buffer with garbage! - if (PoisonMemory) { - memset(MemRange+1, 0xCD, MemRange->BlockSize-sizeof(*MemRange)); - } + /// deallocateFunctionBody - Deallocate all memory for the specified + /// function body. + void deallocateFunctionBody(void *Body) { + deallocateBlock(Body); + } - // Free the memory. - FreeMemoryList = MemRange->FreeBlock(FreeMemoryList); - - // Finally, remove this entry from TableBlocks. - TableBlocks.erase(I); + /// deallocateExceptionTable - Deallocate memory for the specified + /// exception table. + void deallocateExceptionTable(void *ET) { + deallocateBlock(ET); } /// setMemoryWritable - When code generation is in progress, -- cgit v1.2.3