LLVM 19.0.0git
Memory.h
Go to the documentation of this file.
1//===- llvm/Support/Memory.h - Memory Support -------------------*- 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// This file declares the llvm::sys::Memory class.
10//
11//===----------------------------------------------------------------------===//
12
13#ifndef LLVM_SUPPORT_MEMORY_H
14#define LLVM_SUPPORT_MEMORY_H
15
17#include <system_error>
18
19namespace llvm {
20
21// Forward declare raw_ostream: it is used for debug dumping below.
22class raw_ostream;
23
24namespace sys {
25
26 /// This class encapsulates the notion of a memory block which has an address
27 /// and a size. It is used by the Memory class (a friend) as the result of
28 /// various memory allocation operations.
29 /// @see Memory
30 /// Memory block abstraction.
32 public:
33 MemoryBlock() : Address(nullptr), AllocatedSize(0) {}
34 MemoryBlock(void *addr, size_t allocatedSize)
35 : Address(addr), AllocatedSize(allocatedSize) {}
36 void *base() const { return Address; }
37 /// The size as it was allocated. This is always greater or equal to the
38 /// size that was originally requested.
39 size_t allocatedSize() const { return AllocatedSize; }
40
41 private:
42 void *Address; ///< Address of first byte of memory area
43 size_t AllocatedSize; ///< Size, in bytes of the memory area
44 unsigned Flags = 0;
45 friend class Memory;
46 };
47
48 /// This class provides various memory handling functions that manipulate
49 /// MemoryBlock instances.
50 /// @since 1.4
51 /// An abstraction for memory operations.
52 class Memory {
53 public:
55 MF_READ = 0x1000000,
56 MF_WRITE = 0x2000000,
57 MF_EXEC = 0x4000000,
58 MF_RWE_MASK = 0x7000000,
59
60 /// The \p MF_HUGE_HINT flag is used to indicate that the request for
61 /// a memory block should be satisfied with large pages if possible.
62 /// This is only a hint and small pages will be used as fallback.
63 ///
64 /// The presence or absence of this flag in the returned memory block
65 /// is (at least currently) *not* a reliable indicator that the memory
66 /// block will use or will not use large pages. On some systems a request
67 /// without this flag can be backed by large pages without this flag being
68 /// set, and on some other systems a request with this flag can fallback
69 /// to small pages without this flag being cleared.
70 MF_HUGE_HINT = 0x0000001
71 };
72
73 /// This method allocates a block of memory that is suitable for loading
74 /// dynamically generated code (e.g. JIT). An attempt to allocate
75 /// \p NumBytes bytes of virtual memory is made.
76 /// \p NearBlock may point to an existing allocation in which case
77 /// an attempt is made to allocate more memory near the existing block.
78 /// The actual allocated address is not guaranteed to be near the requested
79 /// address.
80 /// \p Flags is used to set the initial protection flags for the block
81 /// of the memory.
82 /// \p EC [out] returns an object describing any error that occurs.
83 ///
84 /// This method may allocate more than the number of bytes requested. The
85 /// actual number of bytes allocated is indicated in the returned
86 /// MemoryBlock.
87 ///
88 /// The start of the allocated block must be aligned with the
89 /// system allocation granularity (64K on Windows, page size on Linux).
90 /// If the address following \p NearBlock is not so aligned, it will be
91 /// rounded up to the next allocation granularity boundary.
92 ///
93 /// \r a non-null MemoryBlock if the function was successful,
94 /// otherwise a null MemoryBlock is with \p EC describing the error.
95 ///
96 /// Allocate mapped memory.
97 static MemoryBlock allocateMappedMemory(size_t NumBytes,
98 const MemoryBlock *const NearBlock,
99 unsigned Flags,
100 std::error_code &EC);
101
102 /// This method releases a block of memory that was allocated with the
103 /// allocateMappedMemory method. It should not be used to release any
104 /// memory block allocated any other way.
105 /// \p Block describes the memory to be released.
106 ///
107 /// \r error_success if the function was successful, or an error_code
108 /// describing the failure if an error occurred.
109 ///
110 /// Release mapped memory.
111 static std::error_code releaseMappedMemory(MemoryBlock &Block);
112
113 /// This method sets the protection flags for a block of memory to the
114 /// state specified by /p Flags. The behavior is not specified if the
115 /// memory was not allocated using the allocateMappedMemory method.
116 /// \p Block describes the memory block to be protected.
117 /// \p Flags specifies the new protection state to be assigned to the block.
118 ///
119 /// If \p Flags is MF_WRITE, the actual behavior varies
120 /// with the operating system (i.e. MF_READ | MF_WRITE on Windows) and the
121 /// target architecture (i.e. MF_WRITE -> MF_READ | MF_WRITE on i386).
122 ///
123 /// \r error_success if the function was successful, or an error_code
124 /// describing the failure if an error occurred.
125 ///
126 /// Set memory protection state.
127 static std::error_code protectMappedMemory(const MemoryBlock &Block,
128 unsigned Flags);
129
130 /// InvalidateInstructionCache - Before the JIT can run a block of code
131 /// that has been emitted it must invalidate the instruction cache on some
132 /// platforms.
133 static void InvalidateInstructionCache(const void *Addr, size_t Len);
134 };
135
136 /// Owning version of MemoryBlock.
138 public:
139 OwningMemoryBlock() = default;
140 explicit OwningMemoryBlock(MemoryBlock M) : M(M) {}
142 M = Other.M;
143 Other.M = MemoryBlock();
144 }
146 M = Other.M;
147 Other.M = MemoryBlock();
148 return *this;
149 }
151 if (M.base())
153 }
154 void *base() const { return M.base(); }
155 /// The size as it was allocated. This is always greater or equal to the
156 /// size that was originally requested.
157 size_t allocatedSize() const { return M.allocatedSize(); }
158 MemoryBlock getMemoryBlock() const { return M; }
159 std::error_code release() {
160 std::error_code EC;
161 if (M.base()) {
163 M = MemoryBlock();
164 }
165 return EC;
166 }
167 private:
168 MemoryBlock M;
169 };
170
171#ifndef NDEBUG
172 /// Debugging output for Memory::ProtectionFlags.
174
175 /// Debugging output for MemoryBlock.
177#endif // ifndef NDEBUG
178 } // end namespace sys
179 } // end namespace llvm
180
181#endif
uint64_t Addr
raw_pwrite_stream & OS
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition: raw_ostream.h:52
This class encapsulates the notion of a memory block which has an address and a size.
Definition: Memory.h:31
void * base() const
Definition: Memory.h:36
MemoryBlock(void *addr, size_t allocatedSize)
Definition: Memory.h:34
size_t allocatedSize() const
The size as it was allocated.
Definition: Memory.h:39
This class provides various memory handling functions that manipulate MemoryBlock instances.
Definition: Memory.h:52
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....
@ MF_HUGE_HINT
The MF_HUGE_HINT flag is used to indicate that the request for a memory block should be satisfied wit...
Definition: Memory.h:70
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...
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.
Owning version of MemoryBlock.
Definition: Memory.h:137
MemoryBlock getMemoryBlock() const
Definition: Memory.h:158
OwningMemoryBlock(OwningMemoryBlock &&Other)
Definition: Memory.h:141
void * base() const
Definition: Memory.h:154
size_t allocatedSize() const
The size as it was allocated.
Definition: Memory.h:157
OwningMemoryBlock(MemoryBlock M)
Definition: Memory.h:140
std::error_code release()
Definition: Memory.h:159
OwningMemoryBlock & operator=(OwningMemoryBlock &&Other)
Definition: Memory.h:145
raw_ostream & operator<<(raw_ostream &OS, const Memory::ProtectionFlags &PF)
Debugging output for Memory::ProtectionFlags.
Definition: Memory.cpp:34
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
@ Other
Any other memory.