MemoryMapper.h 5.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186
  1. #pragma once
  2. #ifdef __GNUC__
  3. #pragma GCC diagnostic push
  4. #pragma GCC diagnostic ignored "-Wunused-parameter"
  5. #endif
  6. //===- MemoryMapper.h - Cross-process memory mapper -------------*- C++ -*-===//
  7. //
  8. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  9. // See https://llvm.org/LICENSE.txt for license information.
  10. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  11. //
  12. //===----------------------------------------------------------------------===//
  13. //
  14. // Cross-process (and in-process) memory mapping and transfer
  15. //
  16. //===----------------------------------------------------------------------===//
  17. #ifndef LLVM_EXECUTIONENGINE_ORC_MEMORYMAPPER_H
  18. #define LLVM_EXECUTIONENGINE_ORC_MEMORYMAPPER_H
  19. #include "llvm/ExecutionEngine/Orc/Core.h"
  20. #include "llvm/ExecutionEngine/Orc/Shared/MemoryFlags.h"
  21. #include "llvm/Support/Process.h"
  22. #include <mutex>
  23. namespace llvm {
  24. namespace orc {
  25. /// Manages mapping, content transfer and protections for JIT memory
  26. class MemoryMapper {
  27. public:
  28. /// Represents a single allocation containing multiple segments and
  29. /// initialization and deinitialization actions
  30. struct AllocInfo {
  31. struct SegInfo {
  32. ExecutorAddrDiff Offset;
  33. const char *WorkingMem;
  34. size_t ContentSize;
  35. size_t ZeroFillSize;
  36. AllocGroup AG;
  37. };
  38. ExecutorAddr MappingBase;
  39. std::vector<SegInfo> Segments;
  40. shared::AllocActions Actions;
  41. };
  42. using OnReservedFunction = unique_function<void(Expected<ExecutorAddrRange>)>;
  43. // Page size of the target process
  44. virtual unsigned int getPageSize() = 0;
  45. /// Reserves address space in executor process
  46. virtual void reserve(size_t NumBytes, OnReservedFunction OnReserved) = 0;
  47. /// Provides working memory
  48. virtual char *prepare(ExecutorAddr Addr, size_t ContentSize) = 0;
  49. using OnInitializedFunction = unique_function<void(Expected<ExecutorAddr>)>;
  50. /// Ensures executor memory is synchronized with working copy memory, sends
  51. /// functions to be called after initilization and before deinitialization and
  52. /// applies memory protections
  53. /// Returns a unique address identifying the allocation. This address should
  54. /// be passed to deinitialize to run deallocation actions (and reset
  55. /// permissions where possible).
  56. virtual void initialize(AllocInfo &AI,
  57. OnInitializedFunction OnInitialized) = 0;
  58. using OnDeinitializedFunction = unique_function<void(Error)>;
  59. /// Runs previously specified deinitialization actions
  60. /// Executor addresses returned by initialize should be passed
  61. virtual void deinitialize(ArrayRef<ExecutorAddr> Allocations,
  62. OnDeinitializedFunction OnDeInitialized) = 0;
  63. using OnReleasedFunction = unique_function<void(Error)>;
  64. /// Release address space acquired through reserve()
  65. virtual void release(ArrayRef<ExecutorAddr> Reservations,
  66. OnReleasedFunction OnRelease) = 0;
  67. virtual ~MemoryMapper();
  68. };
  69. class InProcessMemoryMapper : public MemoryMapper {
  70. public:
  71. InProcessMemoryMapper(size_t PageSize);
  72. static Expected<std::unique_ptr<InProcessMemoryMapper>> Create();
  73. unsigned int getPageSize() override { return PageSize; }
  74. void reserve(size_t NumBytes, OnReservedFunction OnReserved) override;
  75. void initialize(AllocInfo &AI, OnInitializedFunction OnInitialized) override;
  76. char *prepare(ExecutorAddr Addr, size_t ContentSize) override;
  77. void deinitialize(ArrayRef<ExecutorAddr> Allocations,
  78. OnDeinitializedFunction OnDeInitialized) override;
  79. void release(ArrayRef<ExecutorAddr> Reservations,
  80. OnReleasedFunction OnRelease) override;
  81. ~InProcessMemoryMapper() override;
  82. private:
  83. struct Allocation {
  84. size_t Size;
  85. std::vector<shared::WrapperFunctionCall> DeinitializationActions;
  86. };
  87. using AllocationMap = DenseMap<ExecutorAddr, Allocation>;
  88. struct Reservation {
  89. size_t Size;
  90. std::vector<ExecutorAddr> Allocations;
  91. };
  92. using ReservationMap = DenseMap<void *, Reservation>;
  93. std::mutex Mutex;
  94. ReservationMap Reservations;
  95. AllocationMap Allocations;
  96. size_t PageSize;
  97. };
  98. class SharedMemoryMapper final : public MemoryMapper {
  99. public:
  100. struct SymbolAddrs {
  101. ExecutorAddr Instance;
  102. ExecutorAddr Reserve;
  103. ExecutorAddr Initialize;
  104. ExecutorAddr Deinitialize;
  105. ExecutorAddr Release;
  106. };
  107. SharedMemoryMapper(ExecutorProcessControl &EPC, SymbolAddrs SAs,
  108. size_t PageSize);
  109. static Expected<std::unique_ptr<SharedMemoryMapper>>
  110. Create(ExecutorProcessControl &EPC, SymbolAddrs SAs);
  111. unsigned int getPageSize() override { return PageSize; }
  112. void reserve(size_t NumBytes, OnReservedFunction OnReserved) override;
  113. char *prepare(ExecutorAddr Addr, size_t ContentSize) override;
  114. void initialize(AllocInfo &AI, OnInitializedFunction OnInitialized) override;
  115. void deinitialize(ArrayRef<ExecutorAddr> Allocations,
  116. OnDeinitializedFunction OnDeInitialized) override;
  117. void release(ArrayRef<ExecutorAddr> Reservations,
  118. OnReleasedFunction OnRelease) override;
  119. ~SharedMemoryMapper() override;
  120. private:
  121. struct Reservation {
  122. void *LocalAddr;
  123. size_t Size;
  124. };
  125. ExecutorProcessControl &EPC;
  126. SymbolAddrs SAs;
  127. std::mutex Mutex;
  128. std::map<ExecutorAddr, Reservation> Reservations;
  129. size_t PageSize;
  130. };
  131. } // namespace orc
  132. } // end namespace llvm
  133. #endif // LLVM_EXECUTIONENGINE_ORC_MEMORYMAPPER_H
  134. #ifdef __GNUC__
  135. #pragma GCC diagnostic pop
  136. #endif