Ark Server API (ASA) - Wiki
Loading...
Searching...
No Matches
MallocStomp.h
Go to the documentation of this file.
1// Copyright Epic Games, Inc. All Rights Reserved.
2
3#pragma once
4
5#include "CoreTypes.h"
6#include "HAL/MemoryBase.h"
7
8class FOutputDevice;
9class UWorld;
10
11/**
12 * Stomp memory allocator support should be enabled in Core.Build.cs.
13 * Run-time validation should be enabled using '-stompmalloc' command line argument.
14 */
15
16#if WITH_MALLOC_STOMP
17
18#if PLATFORM_WINDOWS
19 #include "Windows/WindowsHWrapper.h"
20#endif
21
22/**
23 * Stomp memory allocator. It helps find the following errors:
24 * - Read or writes off the end of an allocation.
25 * - Read or writes off the beginning of an allocation.
26 * - Read or writes after freeing an allocation.
27 */
28class FMallocStomp final : public FMalloc
29{
30private:
31#if PLATFORM_64BITS
32 /** Expected value to be found in the sentinel. */
33 static constexpr SIZE_T SentinelExpectedValue = 0xdeadbeefdeadbeef;
34#else
35 /** Expected value to be found in the sentinel. */
36 static constexpr SIZE_T SentinelExpectedValue = 0xdeadbeef;
37#endif
38
39 const SIZE_T PageSize;
40
41 struct FAllocationData
42 {
43 /** Pointer to the full allocation. Needed so the OS knows what to free. */
44 void *FullAllocationPointer;
45 /** Full size of the allocation including the extra page. */
46 SIZE_T FullSize;
47 /** Size of the allocation requested. */
48 SIZE_T Size;
49 /** Sentinel used to check for underrun. */
50 SIZE_T Sentinel;
51 };
52
53 /** If it is set to true, instead of focusing on overruns the allocator will focus on underruns. */
54 const bool bUseUnderrunMode;
55
56 UPTRINT VirtualAddressCursor = 0;
57 SIZE_T VirtualAddressMax = 0;
58 static constexpr SIZE_T VirtualAddressBlockSize = 1 * 1024 * 1024 * 1024; // 1 GB blocks
59
60public:
61 // FMalloc interface.
62 FMallocStomp(const bool InUseUnderrunMode = false);
63
64 /**
65 * Allocates a block of a given number of bytes of memory with the required alignment.
66 * In the process it allocates as many pages as necessary plus one that will be protected
67 * making it unaccessible and causing an exception. The actual allocation will be pushed
68 * to the end of the last valid unprotected page. To deal with underrun errors a sentinel
69 * is added right before the allocation in page which is checked on free.
70 *
71 * @param Size Size in bytes of the memory block to allocate.
72 * @param Alignment Alignment in bytes of the memory block to allocate.
73 * @return A pointer to the beginning of the memory block.
74 */
75 virtual void* Malloc(SIZE_T Size, uint32 Alignment) override;
76
77 virtual void* TryMalloc(SIZE_T Size, uint32 Alignment) override;
78
79 /**
80 * Changes the size of the memory block pointed to by OldPtr.
81 * The function may move the memory block to a new location.
82 *
83 * @param OldPtr Pointer to a memory block previously allocated with Malloc.
84 * @param NewSize New size in bytes for the memory block.
85 * @param Alignment Alignment in bytes for the reallocation.
86 * @return A pointer to the reallocated memory block, which may be either the same as ptr or a new location.
87 */
88 virtual void* Realloc(void* InPtr, SIZE_T NewSize, uint32 Alignment) override;
89
90 virtual void* TryRealloc(void* InPtr, SIZE_T NewSize, uint32 Alignment) override;
91
92 /**
93 * Frees a memory allocation and verifies the sentinel in the process.
94 *
95 * @param InPtr Pointer of the data to free.
96 */
97 virtual void Free(void* InPtr) override;
98
99 /**
100 * If possible determine the size of the memory allocated at the given address.
101 * This will included all the pages that were allocated so it will be far more
102 * than what's set on the FAllocationData.
103 *
104 * @param Original - Pointer to memory we are checking the size of
105 * @param SizeOut - If possible, this value is set to the size of the passed in pointer
106 * @return true if succeeded
107 */
108 virtual bool GetAllocationSize(void *Original, SIZE_T &SizeOut) override;
109
110 /**
111 * Dumps details about all allocations to an output device
112 *
113 * @param Ar [in] Output device
114 */
115 virtual void DumpAllocatorStats( FOutputDevice& Ar ) override
116 {
117 // No meaningful stats to dump.
118 }
119
120 /**
121 * Validates the allocator's heap
122 */
123 virtual bool ValidateHeap() override
124 {
125 // Nothing to do here since validation happens as data is accessed
126 // through page protection, and on each free checking the sentinel.
127 return true;
128 }
129
130 virtual bool Exec( UWorld* InWorld, const TCHAR* Cmd, FOutputDevice& Ar ) override
131 {
132 return false;
133 }
134
135 virtual const TCHAR* GetDescriptiveName() override
136 {
137 return TEXT( "Stomp" );
138 }
139
140 virtual bool IsInternallyThreadSafe() const override
141 {
142 // Stomp allocator is NOT thread-safe and must be externally-synchronized.
143 return false;
144 }
145};
146
147#endif // WITH_MALLOC_STOMP