1 //===-- JITLinkMemoryManager.h - JITLink mem manager interface --*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // Contains the JITLinkMemoryManager interface. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #ifndef LLVM_EXECUTIONENGINE_JITLINK_JITLINKMEMORYMANAGER_H 14 #define LLVM_EXECUTIONENGINE_JITLINK_JITLINKMEMORYMANAGER_H 15 16 #include "llvm/ADT/DenseMap.h" 17 #include "llvm/ExecutionEngine/JITSymbol.h" 18 #include "llvm/Support/Error.h" 19 #include "llvm/Support/Memory.h" 20 #include <cstdint> 21 22 namespace llvm { 23 namespace jitlink { 24 25 /// Manages allocations of JIT memory. 26 /// 27 /// Instances of this class may be accessed concurrently from multiple threads 28 /// and their implemetations should include any necessary synchronization. 29 class JITLinkMemoryManager { 30 public: 31 using ProtectionFlags = sys::Memory::ProtectionFlags; 32 33 class SegmentRequest { 34 public: 35 SegmentRequest() = default; SegmentRequest(uint64_t Alignment,size_t ContentSize,uint64_t ZeroFillSize)36 SegmentRequest(uint64_t Alignment, size_t ContentSize, 37 uint64_t ZeroFillSize) 38 : Alignment(Alignment), ContentSize(ContentSize), 39 ZeroFillSize(ZeroFillSize) { 40 assert(isPowerOf2_32(Alignment) && "Alignment must be power of 2"); 41 } getAlignment()42 uint64_t getAlignment() const { return Alignment; } getContentSize()43 size_t getContentSize() const { return ContentSize; } getZeroFillSize()44 uint64_t getZeroFillSize() const { return ZeroFillSize; } 45 private: 46 uint64_t Alignment = 0; 47 size_t ContentSize = 0; 48 uint64_t ZeroFillSize = 0; 49 }; 50 51 using SegmentsRequestMap = DenseMap<unsigned, SegmentRequest>; 52 53 /// Represents an allocation created by the memory manager. 54 /// 55 /// An allocation object is responsible for allocating and owning jit-linker 56 /// working and target memory, and for transfering from working to target 57 /// memory. 58 /// 59 class Allocation { 60 public: 61 using FinalizeContinuation = std::function<void(Error)>; 62 63 virtual ~Allocation(); 64 65 /// Should return the address of linker working memory for the segment with 66 /// the given protection flags. 67 virtual MutableArrayRef<char> getWorkingMemory(ProtectionFlags Seg) = 0; 68 69 /// Should return the final address in the target process where the segment 70 /// will reside. 71 virtual JITTargetAddress getTargetMemory(ProtectionFlags Seg) = 0; 72 73 /// Should transfer from working memory to target memory, and release 74 /// working memory. 75 virtual void finalizeAsync(FinalizeContinuation OnFinalize) = 0; 76 77 /// Should deallocate target memory. 78 virtual Error deallocate() = 0; 79 }; 80 81 virtual ~JITLinkMemoryManager(); 82 83 /// Create an Allocation object. 84 virtual Expected<std::unique_ptr<Allocation>> 85 allocate(const SegmentsRequestMap &Request) = 0; 86 }; 87 88 /// A JITLinkMemoryManager that allocates in-process memory. 89 class InProcessMemoryManager : public JITLinkMemoryManager { 90 public: 91 Expected<std::unique_ptr<Allocation>> 92 allocate(const SegmentsRequestMap &Request) override; 93 }; 94 95 } // end namespace jitlink 96 } // end namespace llvm 97 98 #endif // LLVM_EXECUTIONENGINE_JITLINK_JITLINK_H 99