UDocumentation UE5.7 10.02.2026 (Source)
API documentation for Unreal Engine 5.7
D3D12Allocation.h
Go to the documentation of this file.
1// Copyright Epic Games, Inc. All Rights Reserved.
2
3/*=============================================================================
4D3D12Allocation.h: A Collection of allocators
5=============================================================================*/
6
7#pragma once
8
9#include "D3D12Resources.h"
10#include "D3D12PoolAllocator.h"
11#include "Misc/ScopeRWLock.h"
12
14
15#define SUB_ALLOCATED_DEFAULT_ALLOCATIONS 1
16
17// Enable pool allocator by default only on Windows until all initial issues have been resolved.
18// Xbox is currently using the buddy allocator with a lot smaller pool sizes so the alignment waste is a lot less
19// It also has less of a problem with committed resource allocations
20#if !defined(USE_BUFFER_POOL_ALLOCATOR)
21#define USE_BUFFER_POOL_ALLOCATOR (PLATFORM_WINDOWS)
22#endif
23
24#if !defined(USE_TEXTURE_POOL_ALLOCATOR)
25#define USE_TEXTURE_POOL_ALLOCATOR (PLATFORM_WINDOWS)
26#endif
27
28// Segregated free list texture allocator
29// Description:
30// - Binned read-only texture allocation based on sizes
31// Suggestions:
32// - You can check memory wastage using "stat d3d12rhi" in a dev build
33// - Tune d3d12.ReadOnlyTextureAllocator.MinPoolSize/MinNumToPool/MaxPoolSize
34// according to video memory budget
35// - Memory overhead is slightly over 200 MB in internal tests but consider
36// adjusting above cvars or disabling if it fails your use case
37// - The purpose of this allocator is pooling texture allocations because
38// creating committed resources is slow on PC. But if committed resource
39// creation ever becomes fast, there is no need for this allocator
40// Internal test statistics (11/6/2018):
41// - Average read-only texture alloc time reduced from ~420 us to ~72 us
42// - Number of allocations over 1 ms reduced from 8145 to 504 (from 14.76% to
43// 0.92%) over a 17 minutes 11 seconds game replay
44// - Peak memory overhead was ~207 MB (from 2666.58 MB to 2874.08 MB)
45// TODO:
46// - Defragmentation support
47#define D3D12RHI_SEGREGATED_TEXTURE_ALLOC (PLATFORM_WINDOWS)
48#define D3D12RHI_SEGLIST_ALLOC_TRACK_WASTAGE (!(UE_BUILD_TEST || UE_BUILD_SHIPPING))
49
50#define D3D12RHI_SEGLIST_ALLOC_TRACK_LEAK_STACK_DEPTH 12
51
52#define D3D12RHI_TRACK_DETAILED_STATS (PLATFORM_WINDOWS && !(UE_BUILD_TEST || UE_BUILD_SHIPPING))
53
66
68{
69 uint32 Prime0 = 0xa6c70167;
70 uint32 Prime1 = 0x5d18b207;
71 uint32 Prime2 = 0xd0a489f9;
72 uint32 Value0 = (uint32)(((uint64)S.Heap) >> 32);
73 uint32 Value1 = (uint32)(uint64)S.Heap;
74 uint32 Value2 = S.Offset;
75 return Value0 * Prime0 + Value1 * Prime1 + Value2 * Prime2;
76}
77
78
80
81class FD3D12SegList;
82
84{
85public:
86
90 const FString& Name,
93
96
97protected:
98
100 const FString DebugName;
102
103 // Any allocation larger than this just gets straight up allocated (i.e. not pooled).
104 // These large allocations should be infrequent so the CPU overhead should be minimal
106
108
109#if defined(D3D12RHI_TRACK_DETAILED_STATS)
115#endif
116};
117
118//-----------------------------------------------------------------------------
119// Buddy Allocator
120//-----------------------------------------------------------------------------
121// Allocates blocks from a fixed range using buddy allocation method.
122// Buddy allocation allows reasonably fast allocation of arbitrary size blocks
123// with minimal fragmentation and provides efficient reuse of freed ranges.
124// When a block is de-allocated an attempt is made to merge it with it's
125// neighbour (buddy) if it is contiguous and free.
126// Based on reference implementation by MSFT: billkris
127
128// Unfortunately the api restricts the minimum size of a placed buffer resource to 64k
129#define MIN_PLACED_RESOURCE_SIZE (64 * 1024)
130#define D3D_BUFFER_ALIGNMENT (64 * 1024)
131
132#if defined(D3D12RHI_TRACK_DETAILED_STATS)
133#define INCREASE_ALLOC_COUNTER(A, B) (A = A + B);
134#define DECREASE_ALLOC_COUNTER(A, B) (A = A - B);
135#else
136#define INCREASE_ALLOC_COUNTER(A, B)
137#define DECREASE_ALLOC_COUNTER(A, B)
138#endif
139
140
142{
143public:
144
148 const FString& Name,
154
155 bool TryAllocate(uint32 SizeInBytes, uint32 Alignment, FD3D12ResourceLocation& ResourceLocation);
156
157 void Deallocate(FD3D12ResourceLocation& ResourceLocation);
158
159 void Initialize();
160
161 void Destroy();
162
163 void CleanUpAllocations();
164
165 void DumpAllocatorStats(class FOutputDevice& Ar);
167
168 void ReleaseAllResources();
169
170 void Reset();
171
172 inline bool IsEmpty()
173 {
174 return FreeBlocks[MaxOrder].Num() == 1;
175 }
176 inline uint64 GetLastUsedFrameFence() const { return LastUsedFrameFence; }
177
178 inline uint32 GetTotalSizeUsed() const { return TotalSizeUsed; }
180
182
183 inline bool IsOwner(FD3D12ResourceLocation& ResourceLocation)
184 {
185 return ResourceLocation.GetAllocator() == (FD3D12BaseAllocatorType*)this;
186 }
187
188protected:
189
193
196
197private:
198 struct RetiredBlock
199 {
200 FD3D12Resource* PlacedResource;
201 uint64 FrameFence;
203#if defined(D3D12RHI_TRACK_DETAILED_STATS)
204 // Actual size only used for tracking memory stats
205 uint32 AllocationSize;
206#endif
207 };
208
209 TArray<RetiredBlock> DeferredDeletionQueue;
210 TArray<TSet<uint32>> FreeBlocks;
211 uint64 LastUsedFrameFence;
212 uint32 MaxOrder;
213 uint32 TotalSizeUsed;
214 HeapId TraceHeapId;
215
216 bool HeapFullMessageDisplayed;
217
218 inline uint32 SizeToUnitSize(uint32 size) const
219 {
220 return (size + (MinBlockSize - 1)) / MinBlockSize;
221 }
222
223 inline uint32 UnitSizeToOrder(uint32 size) const
224 {
225 unsigned long Result;
226 _BitScanReverse(&Result, size + size - 1); // ceil(log2(size))
227 return Result;
228 }
229
230 inline uint32 GetBuddyOffset(const uint32 &offset, const uint32 &size)
231 {
232 return offset ^ size;
233 }
234
235 uint32 OrderToUnitSize(uint32 order) const { return ((uint32)1) << order; }
236 uint32 AllocateBlock(uint32 order);
237 void DeallocateBlock(uint32 offset, uint32 order);
238
239 bool CanAllocate(uint32 size, uint32 alignment);
240
241 void DeallocateInternal(RetiredBlock& Block);
242
243 void Allocate(uint32 SizeInBytes, uint32 Alignment, FD3D12ResourceLocation& ResourceLocation);
244};
245
246//-----------------------------------------------------------------------------
247// Multi-Buddy Allocator
248//-----------------------------------------------------------------------------
249// Builds on top of the Buddy Allocator but covers some of it's deficiencies by
250// managing multiple buddy allocator instances to better match memory usage over
251// time.
252
300
301//-----------------------------------------------------------------------------
302// Bucket Allocator
303//-----------------------------------------------------------------------------
304// Resources are allocated from buckets, which are just a collection of resources of a particular size.
305// Blocks can be an entire resource or a sub allocation from a resource.
307{
308public:
309
313 const FString& Name,
315
316 bool TryAllocate(uint32 SizeInBytes, uint32 Alignment, FD3D12ResourceLocation& ResourceLocation);
317
318 void Deallocate(FD3D12ResourceLocation& ResourceLocation);
319
320 void Initialize();
321
322 void Destroy();
323
325
326 void DumpAllocatorStats(class FOutputDevice& Ar);
328
329 void ReleaseAllResources();
330
331 void Reset();
332
333private:
334
335 static uint32 FORCEINLINE BucketFromSize(uint32 size, uint32 bucketShift)
336 {
337 uint32 bucket = FMath::CeilLogTwo(size);
339 return bucket;
340 }
341
342 static uint32 FORCEINLINE BlockSizeFromBufferSize(uint32 bufferSize, uint32 bucketShift)
343 {
344 const uint32 minSize = 1 << bucketShift;
345 return bufferSize > minSize ? FMath::RoundUpToPowerOfTwo(bufferSize) : minSize;
346 }
347
348#if SUB_ALLOCATED_DEFAULT_ALLOCATIONS
349 static const uint32 MIN_HEAP_SIZE = 256 * 1024;
350#else
351 static const uint32 MIN_HEAP_SIZE = 64 * 1024;
352#endif
353
354 static const uint32 BucketShift = 6;
355 static const uint32 NumBuckets = 22; // bucket resource sizes range from 64 to 2^28
356
357 FThreadsafeQueue<FD3D12BlockAllocatorPrivateData> AvailableBlocks[NumBuckets];
359 TArray<FD3D12Resource*> SubAllocatedResources;// keep a list of the sub-allocated resources so that they may be cleaned up
360
361 // This frame count value helps makes sure that we don't delete resources too soon. If resources are deleted too soon,
362 // we can get in a loop the heap allocator will be constantly deleting and creating resources every frame which
363 // results in CPU stutters. DynamicRetentionFrameCount was tested and set to a value that appears to be adequate for
364 // creating a stable state on the Infiltrator demo.
365 const uint64 BlockRetentionFrameCount;
366};
367
368
369//-----------------------------------------------------------------------------
370// FD3D12UploadHeapAllocator
371//-----------------------------------------------------------------------------
372// This is designed for allocation of scratch memory such as temporary staging buffers
373// or shadow buffers for dynamic resources.
375{
376public:
377
379
380 void Init() {}
381 void Destroy();
382
383 // Allocates <size> bytes from the end of an available resource heap.
386
388 void UpdateMemoryStats();
389
390private:
391 HeapId TraceHeapId;
392 // Buddy allocator used for all 'small' allocation - fast but aligns to power of 2
393 FD3D12MultiBuddyAllocator SmallBlockAllocator;
394 // Pool allocator for all bigger allocations - less fast but less alignment waste
395 FCriticalSection BigBlockCS;
396 FD3D12PoolAllocator BigBlockAllocator;
397 // Seperate buddy allocator used for the fast constant allocator pages which get always freed within the same frame by default
398 // (different allocator to avoid fragmentation with the other pools - always the same size allocations)
399 FD3D12MultiBuddyAllocator FastConstantPageAllocator;
400};
401
402//-----------------------------------------------------------------------------
403// FD3D12DefaultBufferPool
404//-----------------------------------------------------------------------------
430
431#if USE_BUFFER_POOL_ALLOCATOR
433#else
435#endif
436
437// FD3D12DefaultBufferAllocator
438//
471
472//-----------------------------------------------------------------------------
473// Fast Allocation
474//-----------------------------------------------------------------------------
475
506
532
551
553{
554public:
556
558 void ClearResource() { UnderlyingResource.Clear(); }
559
560private:
561 FD3D12ResourceLocation UnderlyingResource;
562
563 uint32 Offset;
564 uint32 PageSize;
565};
566
567//-----------------------------------------------------------------------------
568// FD3D12SegListAllocator
569//-----------------------------------------------------------------------------
570
572{
573private:
578 uint64 HeapSize,
580 uint32 Idx) :
582 OwnerList(Owner),
583 ArrayIdx(Idx),
584 FirstFreeOffset(0)
585 {
586 this->SetHeap(NewHeap, TEXT("SegListHeap"));
587 BeginTrackingResidency(HeapSize);
588 }
589
590 virtual ~FD3D12SegHeap() = default;
591
592 FD3D12SegHeap(const FD3D12SegHeap&) = delete;
593 FD3D12SegHeap(FD3D12SegHeap&&) = delete;
594
595 FD3D12SegHeap& operator=(const FD3D12SegHeap&) = delete;
596 FD3D12SegHeap& operator=(FD3D12SegHeap&&) = delete;
597
598 bool IsArrayIdxValid() const { return ArrayIdx >= 0; }
599
600 bool IsFull(uint32 HeapSize) const
601 {
602 check(FirstFreeOffset <= HeapSize);
603 return !FreeBlockOffsets.Num() && FirstFreeOffset == HeapSize;
604 }
605
606 bool IsEmpty(uint32 BlockSize) const
607 {
608 return FreeBlockOffsets.Num() * BlockSize == FirstFreeOffset;
609 }
610
611 // @return - In-heap offset of the allocated block
612 uint32 AllocateBlock(uint32 BlockSize)
613 {
614 if (!FreeBlockOffsets.Num())
615 {
616 uint32 Ret = FirstFreeOffset;
617 FirstFreeOffset += BlockSize;
618 return Ret;
619 }
620 else
621 {
622 return FreeBlockOffsets.Pop();
623 }
624 }
625
626 TArray<uint32> FreeBlockOffsets;
627 FD3D12SegList* OwnerList;
628 int32 ArrayIdx;
629 uint32 FirstFreeOffset;
630
631 friend class FD3D12SegList;
633};
634
636{
637private:
639 : BlockSize(InBlockSize)
640 , HeapSize(InHeapSize)
641#if D3D12RHI_SEGLIST_ALLOC_TRACK_WASTAGE
642 , TotalBytesAllocated(0)
643#endif
644 {
645 check(!(HeapSize % BlockSize));
646 check(HeapSize / BlockSize > 1);
647 }
648
650 {
651 FScopeLock Lock(&CS);
652 check(!!BlockSize);
653 check(!!HeapSize);
654 for (const auto& Heap : FreeHeaps)
655 {
656 ensure(Heap->GetRefCount() == 1);
657 }
658 }
659
660 FD3D12SegList(const FD3D12SegList&) = delete;
661 FD3D12SegList(FD3D12SegList&&) = delete;
662
663 FD3D12SegList& operator=(const FD3D12SegList&) = delete;
664 FD3D12SegList& operator=(FD3D12SegList&&) = delete;
665
666 // @return - In-heap offset of the allocated block
667 uint32 AllocateBlock(
668 FD3D12Device* Device,
670 D3D12_HEAP_TYPE HeapType,
671 D3D12_HEAP_FLAGS HeapFlags,
673 {
674 FScopeLock Lock(&CS);
676
677 if (!!FreeHeaps.Num())
678 {
679 const int32 LastHeapIdx = FreeHeaps.Num() - 1;
680 OutHeap = FreeHeaps[LastHeapIdx];
681 Offset = OutHeap->AllocateBlock(BlockSize);
682 check(Offset <= HeapSize - BlockSize);
683 if (OutHeap->IsFull(HeapSize))
684 {
685 // Heap is full
686 OutHeap->ArrayIdx = INDEX_NONE;
687 FreeHeaps.RemoveAt(LastHeapIdx);
688 }
689 }
690 else
691 {
692 OutHeap = CreateBackingHeap(Device, VisibleNodeMask, HeapType, HeapFlags);
693 Offset = OutHeap->AllocateBlock(BlockSize);
694#if D3D12RHI_SEGLIST_ALLOC_TRACK_WASTAGE
695 TotalBytesAllocated += HeapSize;
696#endif
697 }
698 return Offset;
699 }
700
701 // Deferred deletion is handled by FD3D12SegListAllocator
702 void FreeBlock(FD3D12SegHeap* RESTRICT Heap, uint32 Offset)
703 {
704 FScopeLock Lock(&CS);
705
706 check(!(Offset % BlockSize));
707 check(Offset <= HeapSize - BlockSize);
708 check(this == Heap->OwnerList);
709
710 const bool bFull = Heap->IsFull(HeapSize);
711 Heap->FreeBlockOffsets.Add(Offset);
712
713 if (bFull)
714 {
715 // Heap was full
716 check(!Heap->IsArrayIdxValid());
717 Heap->ArrayIdx = FreeHeaps.Add(Heap);
718 }
719 else if (Heap->IsEmpty(BlockSize))
720 {
721 // Heap is empty
722 check(Heap->GetRefCount() == 1);
723 check(Heap->IsArrayIdxValid());
724 check(FreeHeaps.Num() > Heap->ArrayIdx);
725 const int32 Idx = Heap->ArrayIdx;
726 const int32 LastIdx = FreeHeaps.Num() - 1;
727 FreeHeaps.RemoveAtSwap(Idx);
728 if (Idx != LastIdx)
729 {
730 FreeHeaps[Idx]->ArrayIdx = Idx;
731 }
732#if D3D12RHI_SEGLIST_ALLOC_TRACK_WASTAGE
733 TotalBytesAllocated -= HeapSize;
734#endif
735 }
736 }
737
738 FD3D12SegHeap* CreateBackingHeap(
741 D3D12_HEAP_TYPE HeapType,
742 D3D12_HEAP_FLAGS HeapFlags);
743
746 uint32 BlockSize;
747 uint32 HeapSize;
748
749#if D3D12RHI_SEGLIST_ALLOC_TRACK_WASTAGE
750 uint64 TotalBytesAllocated;
751#endif
752
754};
755
756#if !D3D12RHI_SEGLIST_ALLOC_TRACK_WASTAGE
757static_assert(sizeof(FD3D12SegList) <= 64, "Try to make it fit in a single cacheline");
758#endif
759
761{
762public:
763 static constexpr uint32 InvalidOffset = 0xffffffff;
764
773
775 {
776 check(!SegLists.Num());
777 check(!FenceValues.Num());
778 check(!DeferredDeletionQueue.Num());
779 VerifyEmpty();
780 }
781
784
787
789 {
790 check(!(Alignment & Alignment - 1));
791
792 const uint64 BlockSize = CalculateBlockSize(SizeInBytes, Alignment);
793 if (ShouldPool(BlockSize))
794 {
796 {
797 FRWScopeLock Lock(SegListsRWLock, SLT_ReadOnly);
798 FD3D12SegList** SegListPtr = SegLists.Find(BlockSize);
799 SegList = !!SegListPtr ? *SegListPtr : nullptr;
800 }
801 if (!SegList)
802 {
803 const uint32 HeapSize = CalculateHeapSize(BlockSize);
804 {
805 FRWScopeLock Lock(SegListsRWLock, SLT_Write);
806 FD3D12SegList** SegListPtr = SegLists.Find(BlockSize);
807 SegList = !!SegListPtr ?
808 *SegListPtr :
809 SegLists.Add(BlockSize, new FD3D12SegList(BlockSize, HeapSize));
810 }
811 }
812 check(!!SegList);
813 uint32 Ret = SegList->AllocateBlock(
814 this->GetParentDevice(),
815 this->GetVisibilityMask(),
816 HeapType,
817 HeapFlags,
818 OutHeap);
819 check(Ret != InvalidOffset);
820 OnAlloc(Ret, OutHeap.GetReference(), SizeInBytes);
821 return Ret;
822 }
823 OutHeap = nullptr;
824 return InvalidOffset;
825 }
826
827 void Deallocate(FD3D12Resource* PlacedResource, uint32 Offset, uint32 SizeInBytes);
828
829 void CleanUpAllocations();
830
831 void Destroy();
832
834 {
835#if D3D12RHI_SEGLIST_ALLOC_TRACK_WASTAGE
836 FScopeLock LockCS(&DeferredDeletionCS);
837 FRWScopeLock LockRW(SegListsRWLock, SLT_Write);
838
840 for (const auto& Pair : SegLists)
841 {
842 const FD3D12SegList* SegList = Pair.Value;
843 OutTotalAllocated += SegList->TotalBytesAllocated;
844 }
845 OutTotalUnused = OutTotalAllocated - TotalBytesRequested.Load(EMemoryOrder::Relaxed);
846 return true;
847#else
848 return false;
849#endif
850 }
851
852private:
853 struct FRetiredBlock
854 {
855 // FD3D12Resource knows which heap it is from
856 FD3D12Resource* PlacedResource;
857 uint32 Offset;
858 uint32 ResourceSize;
859
860 FRetiredBlock(
862 uint32 InOffset,
864 PlacedResource(InResource),
865 Offset(InOffset),
866 ResourceSize(InResourceSize)
867 {}
868 };
869
870 static constexpr uint64 CalculateBlockSize(uint64 SizeInBytes, uint64 Alignment)
871 {
872 return (SizeInBytes + Alignment - 1) & ~(Alignment - 1);
873 }
874
875 bool ShouldPool(uint64 BlockSize) const
876 {
877 return BlockSize * 2 <= MaxPoolSize;
878 }
879
880 uint32 CalculateHeapSize(uint32 BlockSize) const
881 {
882 check(MinPoolSize + BlockSize - 1 > MinPoolSize);
883 uint32 NumPooled = (MinPoolSize + BlockSize - 1) / BlockSize;
884 if (NumPooled < MinNumToPool)
885 {
886 NumPooled = MinNumToPool;
887 }
888 const uint32 MaxNumPooled = MaxPoolSize / BlockSize;
890 {
892 }
893 check(NumPooled > 1);
894 check(NumPooled * BlockSize >= MinPoolSize);
895 check(NumPooled * BlockSize <= MaxPoolSize);
896 return NumPooled * BlockSize;
897 }
898
899 template <typename AllocX, typename AllocY>
901
903 TArray<uint64> FenceValues;
904 TArray<TArray<FRetiredBlock>> DeferredDeletionQueue;
905 mutable FRWLock SegListsRWLock;
906 mutable FCriticalSection DeferredDeletionCS;
907 const D3D12_HEAP_TYPE HeapType;
908 const D3D12_HEAP_FLAGS HeapFlags;
909 const uint32 MinPoolSize;
910 const uint32 MinNumToPool;
911 const uint32 MaxPoolSize;
912
913#if D3D12RHI_SEGLIST_ALLOC_TRACK_WASTAGE
914 TAtomic<uint64> TotalBytesRequested;
915 FCriticalSection SegListTrackedAllocationCS;
916 TSet<FD3D12SegListAllocatorLeakTrack> SegListTrackedAllocations;
917
918
919 void DumpStack(const FD3D12SegListAllocatorLeakTrack& LeakTrack);
920 void OnAlloc(uint32 Offset, void* Heap, uint32 Size);
921 void OnFree(uint32 Offset, void* Heap, uint32 Size);
922 void VerifyEmpty();
923#else
924 void OnAlloc(uint32 Offset, void* Heap, uint32 Size) {}
925 void OnFree(uint32 Offset, void* Heap, uint32 Size) {}
926 void VerifyEmpty(){}
927#endif
928};
929
930//-----------------------------------------------------------------------------
931// FD3D12TextureAllocator
932//-----------------------------------------------------------------------------
933
934#if USE_TEXTURE_POOL_ALLOCATOR
936{
937public:
939
942 const D3D12_CLEAR_VALUE* ClearValue,
943 EPixelFormat UEFormat,
947 const TCHAR* Name);
948
949 void BeginFrame(FD3D12ContextArray const& Contexts);
950 void CleanUpAllocations();
951 void Destroy();
953
954private:
955
956 enum class EPoolType
957 {
959 ReadOnly,
961 UAV,
962 Count,
963 };
964
965 FD3D12PoolAllocator* PoolAllocators[(int)EPoolType::Count];
966 HeapId TraceHeapId;
967};
968#elif D3D12RHI_SEGREGATED_TEXTURE_ALLOC
970{
971public:
973
975
976 void BeginFrame(FRHICommandListBase& RHICmdList) {}
977 void CleanUpAllocations()
978 {
979 ReadOnlyTexturePool.CleanUpAllocations();
980 }
981
982 void Destroy()
983 {
984 ReadOnlyTexturePool.Destroy();
985 }
986
988 {
989 return ReadOnlyTexturePool.GetMemoryStats(OutTotalAllocated, OutTotalUnused);
990 }
991
992private:
993 FD3D12SegListAllocator ReadOnlyTexturePool;
994};
995#else
1011
1013{
1014public:
1016
1018 FD3D12ResourceDesc Desc,
1019 const D3D12_CLEAR_VALUE* ClearValue,
1020 EPixelFormat UEFormat,
1024 const TCHAR* Name);
1025
1026 void BeginFrame(FD3D12ContextArray const& Contexts) {}
1027 void CleanUpAllocations() { ReadOnlyTexturePool.CleanUpAllocations(0); }
1028
1029 void Destroy() { ReadOnlyTexturePool.Destroy(); }
1031
1032private:
1033 HeapId TraceHeapId;
1034 FD3D12TextureAllocator ReadOnlyTexturePool;
1035};
1036#endif
#define FORCEINLINE
Definition AndroidPlatform.h:140
#define check(expr)
Definition AssertionMacros.h:314
#define ensure( InExpression)
Definition AssertionMacros.h:464
@ INDEX_NONE
Definition CoreMiscDefines.h:150
#define TEXT(x)
Definition Platform.h:1272
FPlatformTypes::TCHAR TCHAR
Either ANSICHAR or WIDECHAR, depending on whether the platform supports wide characters or the requir...
Definition Platform.h:1135
FPlatformTypes::int32 int32
A 32-bit signed integer.
Definition Platform.h:1125
#define RESTRICT
Definition Platform.h:706
FPlatformTypes::uint64 uint64
A 64-bit unsigned integer.
Definition Platform.h:1117
UE_FORCEINLINE_HINT TSharedRef< CastToType, Mode > StaticCastSharedRef(TSharedRef< CastFromType, Mode > const &InSharedRef)
Definition SharedPointer.h:127
UE::FPlatformRecursiveMutex FCriticalSection
Definition CriticalSection.h:53
ED3D12Access
Definition D3D12Access.h:15
const uint32 kD3D12ManualSubAllocationAlignment
Definition D3D12Allocation.h:79
FORCEINLINE uint32 GetTypeHash(const FD3D12SegListAllocatorLeakTrack &S)
Definition D3D12Allocation.h:67
#define D3D12RHI_SEGLIST_ALLOC_TRACK_LEAK_STACK_DEPTH
Definition D3D12Allocation.h:50
FD3D12DefaultBufferPool FD3D12BufferPool
Definition D3D12Allocation.h:434
EResourceAllocationStrategy
Definition D3D12PoolAllocator.h:8
class FD3D12BuddyAllocator FD3D12BaseAllocatorType
Definition D3D12Resources.h:586
ED3D12ResourceStateMode
Definition D3D12Resources.h:52
uint32 HeapId
Definition MemoryTrace.h:30
EPixelFormat
Definition PixelFormat.h:16
EBufferUsageFlags
Definition RHIDefinitions.h:892
UE::TConsumeAllMpmcQueue< FRHIResource * > PendingDeletes
Definition RHIResources.cpp:12
@ SLT_ReadOnly
Definition ScopeRWLock.h:138
@ SLT_Write
Definition ScopeRWLock.h:139
FRWLock Lock
Definition UnversionedPropertySerialization.cpp:921
uint32 Offset
Definition VulkanMemory.cpp:4033
uint32 Size
Definition VulkanMemory.cpp:4034
uint32_t uint32
Definition binka_ue_file_header.h:6
Definition D3D12RHICommon.h:54
Definition D3D12Adapter.h:136
Definition D3D12Allocation.h:307
void UpdateMemoryStats(uint32 &IOMemoryAllocated, uint32 &IOMemoryUsed, uint32 &IOMemoryFree, uint32 &IOAlignmentWaste, uint32 &IOAllocatedPageCount, uint32 &IOFullPageCount)
Definition D3D12Allocation.h:327
void Destroy()
Definition D3D12Allocation.cpp:1019
void Reset()
Definition D3D12Allocation.cpp:1096
bool TryAllocate(uint32 SizeInBytes, uint32 Alignment, FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.cpp:897
void ReleaseAllResources()
Definition D3D12Allocation.cpp:1064
void CleanUpAllocations(uint64 InFrameLag)
Definition D3D12Allocation.cpp:1023
void Initialize()
Definition D3D12Allocation.cpp:1014
void Deallocate(FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.cpp:1001
void DumpAllocatorStats(class FOutputDevice &Ar)
Definition D3D12Allocation.cpp:1060
Definition D3D12Allocation.h:142
uint64 GetAllocationOffsetInBytes(const FD3D12BuddyAllocatorPrivateData &AllocatorPrivateData) const
Definition D3D12Allocation.h:179
uint64 GetLastUsedFrameFence() const
Definition D3D12Allocation.h:176
void Destroy()
Definition D3D12Allocation.cpp:350
TRefCountPtr< FD3D12Heap > BackingHeap
Definition D3D12Allocation.h:195
void CleanUpAllocations()
Definition D3D12Allocation.cpp:596
uint32 GetTotalSizeUsed() const
Definition D3D12Allocation.h:178
bool IsEmpty()
Definition D3D12Allocation.h:172
const uint32 MaxBlockSize
Definition D3D12Allocation.h:190
TRefCountPtr< FD3D12Resource > BackingResource
Definition D3D12Allocation.h:194
void Reset()
Definition D3D12Allocation.cpp:737
bool IsOwner(FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.h:183
void Deallocate(FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.cpp:530
void Initialize()
Definition D3D12Allocation.cpp:261
const EResourceAllocationStrategy AllocationStrategy
Definition D3D12Allocation.h:192
void DumpAllocatorStats(class FOutputDevice &Ar)
Definition D3D12Allocation.cpp:663
const uint32 MinBlockSize
Definition D3D12Allocation.h:191
FD3D12Heap * GetBackingHeap()
Definition D3D12Allocation.h:181
void UpdateMemoryStats(uint32 &IOMemoryAllocated, uint32 &IOMemoryUsed, uint32 &IOMemoryFree, uint32 &IOAlignmentWaste, uint32 &IOAllocatedPageCount, uint32 &IOFullPageCount)
Definition D3D12Allocation.cpp:692
void ReleaseAllResources()
Definition D3D12Allocation.cpp:627
bool TryAllocate(uint32 SizeInBytes, uint32 Alignment, FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.cpp:514
Definition D3D12View.h:336
Definition D3D12CommandContext.h:1193
Definition D3D12Allocation.h:440
void UpdateMemoryStats()
Definition D3D12Allocation.cpp:1755
void FreeDefaultBufferPools()
Definition D3D12Allocation.cpp:1679
void AllocDefaultResource(D3D12_HEAP_TYPE InHeapType, const D3D12_RESOURCE_DESC &pDesc, EBufferUsageFlags InBufferUsage, ED3D12ResourceStateMode InResourceStateMode, ED3D12Access InCreateD3D12Access, FD3D12ResourceLocation &ResourceLocation, uint32 Alignment, const TCHAR *Name)
Definition D3D12Allocation.cpp:1577
void CleanupFreeBlocks(uint64 InFrameLag)
Definition D3D12Allocation.cpp:1742
static ED3D12Access GetDefaultInitialD3D12Access(D3D12_HEAP_TYPE InHeapType, EBufferUsageFlags InBufferFlags, ED3D12ResourceStateMode InResourceStateMode)
Definition D3D12Allocation.cpp:1543
static bool IsPlacedResource(D3D12_RESOURCE_FLAGS InResourceFlags, ED3D12ResourceStateMode InResourceStateMode, uint32 Alignment)
Definition D3D12Allocation.cpp:1536
Definition D3D12Allocation.h:406
static FD3D12ResourceInitConfig GetResourceAllocatorInitConfig(D3D12_HEAP_TYPE InHeapType, D3D12_RESOURCE_FLAGS InResourceFlags, EBufferUsageFlags InBufferUsage)
Definition D3D12Allocation.cpp:1247
void UpdateMemoryStats(uint32 &IOMemoryAllocated, uint32 &IOMemoryUsed, uint32 &IOMemoryFree, uint32 &IOMemoryEndFree, uint32 &IOAlignmentWaste, uint32 &IOAllocatedPageCount, uint32 &IOFullPageCount)
Definition D3D12Allocation.cpp:1452
~FD3D12DefaultBufferPool()
Definition D3D12Allocation.h:409
static EResourceAllocationStrategy GetResourceAllocationStrategy(D3D12_RESOURCE_FLAGS InResourceFlags, ED3D12ResourceStateMode InResourceStateMode, uint32 Alignment)
Definition D3D12Allocation.cpp:1290
void CleanUpAllocations(uint64 InFrameLag)
Definition D3D12Allocation.cpp:1330
bool SupportsAllocation(D3D12_HEAP_TYPE InHeapType, D3D12_RESOURCE_FLAGS InResourceFlags, EBufferUsageFlags InBufferUsage, ED3D12ResourceStateMode InResourceStateMode, uint32 Alignment) const
Definition D3D12Allocation.cpp:1322
void AllocDefaultResource(D3D12_HEAP_TYPE InHeapType, const D3D12_RESOURCE_DESC &InDesc, EBufferUsageFlags InBufferUsage, ED3D12ResourceStateMode InResourceStateMode, ED3D12Access InCreateD3D12Access, uint32 InAlignment, const TCHAR *InName, FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.cpp:1336
Definition D3D12RHICommon.h:78
FORCEINLINE FD3D12Device * GetParentDevice() const
Definition D3D12RHICommon.h:85
FD3D12Device * Parent
Definition D3D12RHICommon.h:80
Definition D3D12Device.h:176
Definition D3D12Allocation.h:508
FD3D12FastAllocatorPage * RequestFastAllocatorPage()
Definition D3D12Allocation.cpp:2310
void CleanupPages(uint64 FrameLag)
Definition D3D12Allocation.cpp:2376
uint32 GetPageSize() const
Definition D3D12Allocation.h:518
void ReturnFastAllocatorPage(FD3D12FastAllocatorPage *Page)
Definition D3D12Allocation.cpp:2368
void Destroy()
Definition D3D12Allocation.cpp:2406
const D3D12_HEAP_PROPERTIES HeapProperties
Definition D3D12Allocation.h:528
D3D12_HEAP_TYPE GetHeapType() const
Definition D3D12Allocation.h:520
TArray< FD3D12FastAllocatorPage * > Pool
Definition D3D12Allocation.h:530
const uint32 PageSize
Definition D3D12Allocation.h:527
bool IsCPUWritable() const
Definition D3D12Allocation.h:521
Definition D3D12Allocation.h:534
FD3D12FastAllocatorPagePool PagePool
Definition D3D12Allocation.h:545
FCriticalSection CS
Definition D3D12Allocation.h:549
FD3D12FastAllocatorPage * CurrentAllocatorPage
Definition D3D12Allocation.h:547
void Destroy()
Definition D3D12Allocation.cpp:2284
void CleanupPages(uint64 FrameLag)
Definition D3D12Allocation.cpp:2278
void * Allocate(uint32 Size, uint32 Alignment, class FD3D12ResourceLocation *ResourceLocation)
Definition D3D12Allocation.cpp:2208
Definition D3D12Allocation.h:553
void ClearResource()
Definition D3D12Allocation.h:558
void * Allocate(uint32 Bytes, class FD3D12ResourceLocation &OutLocation, FD3D12ConstantBufferView *OutCBView)
Definition D3D12Allocation.cpp:2431
SGPU_CONSTEXPR FRHIGPUMask GetVisibilityMask() const
Definition D3D12RHICommon.h:116
Definition D3D12Resources.h:73
void SetHeap(ID3D12Heap *HeapIn, const TCHAR *const InName, bool bTrack=true, bool bForceGetGPUAddress=false)
Definition D3D12Resources.cpp:704
void BeginTrackingResidency(uint64 Size)
Definition D3D12Resources.cpp:757
Definition D3D12Allocation.h:254
const EResourceAllocationStrategy GetAllocationStrategy() const
Definition D3D12Allocation.h:268
TArray< FD3D12BuddyAllocator * > Allocators
Definition D3D12Allocation.h:295
void DumpAllocatorStats(class FOutputDevice &Ar)
Definition D3D12Allocation.cpp:849
void ReleaseAllResources()
Definition D3D12Allocation.cpp:866
~FD3D12MultiBuddyAllocator()
Definition D3D12Allocation.cpp:770
FD3D12BuddyAllocator * CreateNewAllocator(uint32 InMinSizeInBytes)
Definition D3D12Allocation.cpp:797
const EResourceAllocationStrategy AllocationStrategy
Definition D3D12Allocation.h:291
const uint32 DefaultPoolSize
Definition D3D12Allocation.h:293
void Deallocate(FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.cpp:791
bool TryAllocate(uint32 SizeInBytes, uint32 Alignment, FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.cpp:775
void CleanUpAllocations(uint64 InFrameLag)
Definition D3D12Allocation.cpp:823
void Destroy()
Definition D3D12Allocation.cpp:818
const uint32 MinBlockSize
Definition D3D12Allocation.h:292
void Initialize()
Definition D3D12Allocation.cpp:813
void UpdateMemoryStats(uint32 &IOMemoryAllocated, uint32 &IOMemoryUsed, uint32 &IOMemoryFree, uint32 &IOAlignmentWaste, uint32 &IOAllocatedPageCount, uint32 &IOFullPageCount)
Definition D3D12Allocation.cpp:854
void Reset()
Definition D3D12Allocation.cpp:880
Definition D3D12RHICommon.h:153
D3D12 specific implementation of the FRHIPoolAllocator.
Definition D3D12PoolAllocator.h:130
Definition D3D12Allocation.h:84
bool Initialized
Definition D3D12Allocation.h:101
const uint32 GetMaximumAllocationSizeForPooling() const
Definition D3D12Allocation.h:95
~FD3D12ResourceAllocator()
Definition D3D12Allocation.cpp:222
uint32 PeakUsage
Definition D3D12Allocation.h:113
uint32 SpaceActualUsed
Definition D3D12Allocation.h:111
const FD3D12ResourceInitConfig & GetInitConfig() const
Definition D3D12Allocation.h:94
uint32 NumBlocksInDeferredDeletionQueue
Definition D3D12Allocation.h:112
uint32 SpaceAlignedUsed
Definition D3D12Allocation.h:110
FCriticalSection CS
Definition D3D12Allocation.h:107
const FD3D12ResourceInitConfig InitConfig
Definition D3D12Allocation.h:99
const FString DebugName
Definition D3D12Allocation.h:100
uint32 FailedAllocationSpace
Definition D3D12Allocation.h:114
const uint32 MaximumAllocationSizeForPooling
Definition D3D12Allocation.h:105
Definition D3D12Resources.h:641
FD3D12BaseAllocatorType * GetAllocator()
Definition D3D12Resources.h:697
void Clear()
Definition D3D12Resources.cpp:1179
Definition D3D12Resources.h:181
Definition D3D12Allocation.h:572
Definition D3D12Allocation.h:761
FD3D12SegListAllocator & operator=(FD3D12SegListAllocator &&)=delete
uint32 Allocate(uint64 SizeInBytes, uint64 Alignment, TRefCountPtr< FD3D12SegHeap > &OutHeap)
Definition D3D12Allocation.h:788
void Destroy()
Definition D3D12Allocation.cpp:2591
FD3D12SegListAllocator(FD3D12SegListAllocator &&)=delete
void CleanUpAllocations()
Definition D3D12Allocation.cpp:2559
FD3D12SegListAllocator & operator=(const FD3D12SegListAllocator &)=delete
FD3D12SegListAllocator(const FD3D12SegListAllocator &)=delete
static constexpr uint32 InvalidOffset
Definition D3D12Allocation.h:763
void Deallocate(FD3D12Resource *PlacedResource, uint32 Offset, uint32 SizeInBytes)
Definition D3D12Allocation.cpp:2510
~FD3D12SegListAllocator()
Definition D3D12Allocation.h:774
bool GetMemoryStats(uint64 &OutTotalAllocated, uint64 &OutTotalUnused) const
Definition D3D12Allocation.h:833
Definition D3D12Allocation.h:636
Definition D3D12Allocation.h:1013
bool GetMemoryStats(uint64 &OutTotalAllocated, uint64 &OutTotalUnused) const
Definition D3D12Allocation.h:1030
HRESULT AllocateTexture(FD3D12ResourceDesc Desc, const D3D12_CLEAR_VALUE *ClearValue, EPixelFormat UEFormat, FD3D12ResourceLocation &TextureLocation, ED3D12Access InInitialD3D12Access, ED3D12Access InDefaultD3D12Access, const TCHAR *Name)
Definition D3D12Allocation.cpp:2152
void BeginFrame(FD3D12ContextArray const &Contexts)
Definition D3D12Allocation.h:1026
void Destroy()
Definition D3D12Allocation.h:1029
void CleanUpAllocations()
Definition D3D12Allocation.h:1027
Definition D3D12Allocation.h:997
HRESULT AllocateTexture(FD3D12ResourceDesc Desc, const D3D12_CLEAR_VALUE *ClearValue, FD3D12ResourceLocation &TextureLocation, ED3D12Access InInitialD3D12Access, ED3D12Access InDefaultD3D12Access, const TCHAR *Name)
Definition D3D12Allocation.cpp:2082
~FD3D12TextureAllocator()
Definition D3D12Allocation.cpp:2078
Definition D3D12Allocation.h:375
void Destroy()
Definition D3D12Allocation.cpp:1148
void CleanUpAllocations(uint64 InFrameLag)
Definition D3D12Allocation.cpp:1204
void * AllocUploadResource(uint32 InSize, uint32 InAlignment, FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.cpp:1156
void Init()
Definition D3D12Allocation.h:380
void * AllocFastConstantAllocationPage(uint32 InSize, uint32 InAlignment, FD3D12ResourceLocation &ResourceLocation)
Definition D3D12Allocation.cpp:1193
void UpdateMemoryStats()
Definition D3D12Allocation.cpp:1215
Definition OutputDevice.h:133
Definition RHICommandList.h:455
Definition ScopeRWLock.h:199
Definition ScopeLock.h:141
Definition Array.h:670
UE_REWRITE SizeType Num() const
Definition Array.h:1144
void RemoveAt(SizeType Index, EAllowShrinking AllowShrinking=UE::Core::Private::AllowShrinkingByDefault< AllocatorType >())
Definition Array.h:2083
UE_FORCEINLINE_HINT void RemoveAtSwap(SizeType Index, EAllowShrinking AllowShrinking=UE::Core::Private::AllowShrinkingByDefault< AllocatorType >())
Definition Array.h:2185
UE_NODEBUG UE_FORCEINLINE_HINT SizeType Add(ElementType &&Item)
Definition Array.h:2696
ElementType Pop(EAllowShrinking AllowShrinking=UE::Core::Private::AllowShrinkingByDefault< AllocatorType >())
Definition Array.h:1196
Definition Atomic.h:538
Definition UnrealString.h.inl:34
Definition RefCounting.h:454
UE_FORCEINLINE_HINT ReferencedType * GetReference() const
Definition RefCounting.h:584
Definition CriticalSection.h:14
int
Definition TestServer.py:515
UE_STRING_CLASS Result(Forward< LhsType >(Lhs), RhsLen)
Definition String.cpp.inl:732
Definition D3D12Resources.h:589
Definition D3D12Allocation.h:477
FD3D12FastAllocatorPage(uint32 Size)
Definition D3D12Allocation.h:484
void Reset()
Definition D3D12Allocation.h:492
const uint32 PageSize
Definition D3D12Allocation.h:500
void UpdateFence()
Definition D3D12Allocation.cpp:2359
TRefCountPtr< FD3D12Resource > FastAllocBuffer
Definition D3D12Allocation.h:501
uint32 NextFastAllocOffset
Definition D3D12Allocation.h:502
uint64 FrameFence
Definition D3D12Allocation.h:504
void * FastAllocData
Definition D3D12Allocation.h:503
FD3D12FastAllocatorPage()
Definition D3D12Allocation.h:478
~FD3D12FastAllocatorPage()
Definition D3D12Allocation.cpp:2351
Definition D3D12Resources.h:134
Definition D3D12PoolAllocator.h:24
Definition D3D12Allocation.h:55
uint32 Size
Definition D3D12Allocation.h:58
void * Heap
Definition D3D12Allocation.h:57
bool operator==(const FD3D12SegListAllocatorLeakTrack &Other) const
Definition D3D12Allocation.h:61
uint32 Offset
Definition D3D12Allocation.h:56
uint64 Stack[D3D12RHI_SEGLIST_ALLOC_TRACK_LEAK_STACK_DEPTH]
Definition D3D12Allocation.h:60
uint32 StackDepth
Definition D3D12Allocation.h:59
Definition MultiGPU.h:33
Definition D3D12Util.h:275