2021-06-27 21:25:29 +00:00
/***
Copyright ( C ) 2021 J Reece Wilson ( a / k / a " Reece " ) . All rights reserved .
File : Heap . hpp
Date : 2021 - 6 - 9
Author : Reece
* * */
# pragma once
namespace Aurora : : Memory
{
2024-01-16 21:11:08 +00:00
struct ProxyHeap ;
2024-03-19 15:47:42 +00:00
static const AuUInt8 kHeapSize = 128 ;
static const AuUInt8 kHeap2Size = 255 ;
2024-01-16 21:11:08 +00:00
2024-07-13 02:07:02 +00:00
template < class T >
struct CppHeapWrapper ;
2024-07-14 23:14:58 +00:00
/**
2024-07-19 08:03:13 +00:00
* Note : The following public global aliases exists for heap and / or global process heap based allocations :
2024-07-14 23:14:58 +00:00
*
* AuHUPOf_t < T > AuNewClassArrayUnique ( [ pHeap , ] uElements , . . . )
* AuSPtr < T > AuNewClassArray ( [ pHeap , ] uElements , . . . )
* AuHUPOf_t < T > AuNewClassUnique ( [ pHeap , ] . . . )
* AuSPtr < T > AuNewClass ( [ pHeap , ] . . . )
* AuHUPOf_t < T > AuNullHeapPointer < T > ( )
*/
2022-07-21 09:59:02 +00:00
struct Heap
2021-06-27 21:25:29 +00:00
{
2022-07-21 09:59:02 +00:00
virtual AuSPtr < Heap > AllocateDivision ( AuUInt32 heap , AuUInt32 alignment = 32 ) = 0 ;
2024-01-16 21:11:08 +00:00
virtual Types : : size_t GetChunkSize ( const void * pHead ) = 0 ;
2022-12-08 19:34:15 +00:00
virtual HeapStats & GetStats ( ) = 0 ;
2024-03-04 04:44:49 +00:00
virtual void WalkHeap ( bool ( * fCallback ) ( void * , void * ) , void * pSecondArg ) = 0 ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// Potentially slower, zero allocate
2021-06-27 21:25:29 +00:00
template < typename T = void * >
2024-07-14 23:14:58 +00:00
T ZAlloc ( Types : : size_t uLength ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// POD zero allocation
2021-06-27 21:25:29 +00:00
template < typename T = void * >
2024-07-14 23:14:58 +00:00
T ZAlloc ( Types : : size_t uLength , Types : : size_t uAlignment ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// POD zero allocation
2021-06-27 21:25:29 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
T * ZAlloc ( ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// POD array, zero allocation
2021-06-27 21:25:29 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
T * NewArray ( Types : : size_t uLength ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// POD array, zero allocation
2021-06-27 21:25:29 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
T * NewArray ( Types : : size_t uLength , Types : : size_t uAlignment ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// Fast, POD, non-zeroing allocation
2021-06-27 21:25:29 +00:00
template < typename T = void * >
2024-07-14 23:14:58 +00:00
T FAlloc ( Types : : size_t uLength ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// Fast, POD, non-zeroing allocation
2021-06-27 21:25:29 +00:00
template < typename T = void * >
2024-07-14 23:14:58 +00:00
T FAlloc ( Types : : size_t uLength , Types : : size_t uAlignment ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// Fast, POD, non-zeroing allocation
2021-06-27 21:25:29 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
T * FAlloc ( ) ;
2021-06-27 21:25:29 +00:00
2024-03-19 15:47:42 +00:00
// Reallocs
2024-07-14 23:14:58 +00:00
/// POD, zero-based expansion or reallocation
2021-06-27 21:25:29 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
T ZRealloc ( T pHead , Types : : size_t uLength ) ;
2024-03-19 15:47:42 +00:00
2024-07-14 23:14:58 +00:00
/// POD, zero-based expansion or reallocation
2024-03-19 15:47:42 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
T ZRealloc ( T pHead , Types : : size_t uLength , Types : : size_t uAlignment ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// POD, expansion or reallocation
2021-06-27 21:25:29 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
T FRealloc ( T pHead , Types : : size_t uLength ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// POD, expansion or reallocation
2021-06-27 21:25:29 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
T FRealloc ( T pHead , Types : : size_t uLength , Types : : size_t uAlignment ) ;
2021-06-27 21:25:29 +00:00
2024-07-14 23:14:58 +00:00
/// Free
2021-06-27 21:25:29 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
void Free ( T pHead ) ;
2021-06-27 21:25:29 +00:00
2024-01-18 12:17:01 +00:00
protected :
template < typename T >
2024-07-14 23:14:58 +00:00
static void DeleteThat ( T * pThat ) ;
2024-01-18 12:17:01 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
static void DeleteThatArray ( T * pThat ) ;
2024-07-19 07:58:22 +00:00
template < typename T >
static void DeleteThatArray2 ( T * pThat ) ;
2024-02-15 01:10:23 +00:00
template < typename T , typename Z >
2024-07-14 23:14:58 +00:00
static void DeleteThatCastedOnce ( T * pThat ) ;
2024-01-18 12:17:01 +00:00
template < typename T >
2024-07-14 23:14:58 +00:00
static void RetardedSpecWrittenByRetards ( T * pThat ) ;
2024-01-18 12:17:01 +00:00
public :
2022-12-08 19:34:15 +00:00
template < class T , class . . . Args >
2024-07-14 23:14:58 +00:00
AuSPtr < T > NewClass ( Args & & . . . args ) ;
2022-12-08 19:34:15 +00:00
2024-03-19 15:47:42 +00:00
// note: callers can use AuHUPOf_t<Z> pUniquePointer = AuNullHeapPointer<Z>()
2024-01-18 12:17:01 +00:00
2024-03-17 13:16:43 +00:00
template < class T , class Z = T , class . . . Args >
2024-07-14 23:14:58 +00:00
AuUPtr < Z , decltype ( & Heap : : DeleteThat < Z > ) > NewClassUnique ( Args & & . . . args ) ;
2024-01-18 12:17:01 +00:00
2024-01-16 21:11:08 +00:00
template < class T , class . . . Args >
2024-07-14 23:14:58 +00:00
AuSPtr < T > NewClassArray ( AuUInt uElements , Args & & . . . fillCtr ) ;
template < class T , class . . . Args >
AuSPtr < T > NewClassArray2 ( AuUInt uElements , AuUInt uAlignment , Args & & . . . fillCtr ) ;
2021-06-27 21:25:29 +00:00
2024-01-19 19:40:38 +00:00
// note: callers can use AuHUPOf_t<T> pUniquePointer = AuNullHeapPointer<T>()
2024-01-18 12:17:01 +00:00
template < class T , class . . . Args >
2024-07-14 23:14:58 +00:00
AuUPtr < T , decltype ( & Heap : : DeleteThat < T > ) > NewClassArrayUnique ( AuUInt uElements , Args & & . . . fillCtr ) ;
template < class T , class . . . Args >
AuUPtr < T , decltype ( & Heap : : DeleteThat < T > ) > NewClassArray2Unique ( AuUInt uElements , AuUInt uAlignment , Args & & . . . fillCtr ) ;
2024-01-18 12:17:01 +00:00
2024-01-19 19:40:38 +00:00
template < class T >
2024-07-14 23:14:58 +00:00
cstatic AuUPtr < T , decltype ( & Heap : : DeleteThat < T > ) > NullUniquePointer ( ) ;
2024-01-19 19:40:38 +00:00
2024-02-14 06:35:43 +00:00
template < class Z , class T >
2024-07-14 23:14:58 +00:00
cstatic AuUPtr < Z , decltype ( & Heap : : DeleteThat < Z > ) > CastPointer ( AuUPtr < T , decltype ( & Heap : : DeleteThat < T > ) > & & pInPointer ) ;
2024-02-14 06:35:43 +00:00
2024-01-18 17:19:35 +00:00
template < typename T >
using HUPOf_t = AuUPtr < T , decltype ( & Heap : : DeleteThat < T > ) > ;
2024-01-16 21:11:08 +00:00
protected :
friend struct ProxyHeap ;
2024-01-27 08:04:29 +00:00
friend struct HeapAccessor ;
2022-01-18 19:31:15 +00:00
2022-12-08 19:34:15 +00:00
virtual AuSPtr < Heap > GetSelfReference ( ) = 0 ; // may return empty/default. not all heaps are sharable.
2024-01-16 21:11:08 +00:00
virtual Heap * GetSelfReferenceRaw ( ) = 0 ;
2022-12-08 19:34:15 +00:00
virtual AU_ALLOC void * _ZAlloc ( Types : : size_t uLength ) = 0 ;
2024-03-19 15:47:42 +00:00
virtual AU_ALLOC void * _ZAlloc ( Types : : size_t uLength , Types : : size_t uAlignment ) = 0 ;
2022-12-08 19:34:15 +00:00
virtual AU_ALLOC void * _FAlloc ( Types : : size_t uLength ) = 0 ;
2024-03-19 15:47:42 +00:00
virtual AU_ALLOC void * _FAlloc ( Types : : size_t uLength , Types : : size_t uAlignment ) = 0 ;
2022-12-08 19:34:15 +00:00
virtual AU_ALLOC void * _ZRealloc ( void * pBase , Types : : size_t uLength , Types : : size_t uAlign ) = 0 ;
virtual AU_ALLOC void * _ZRealloc ( void * pBase , Types : : size_t uLength ) = 0 ;
virtual AU_ALLOC void * _FRealloc ( void * pBase , Types : : size_t uLength , Types : : size_t uAlign ) = 0 ;
virtual AU_ALLOC void * _FRealloc ( void * pBase , Types : : size_t uLength ) = 0 ;
virtual void _Free ( void * pBase ) = 0 ;
2021-06-27 21:25:29 +00:00
} ;
2024-01-27 08:04:29 +00:00
struct HeapAccessor
{
cstatic AuSPtr < Heap > GetSelfReference ( Heap * pHeap )
{
return pHeap - > GetSelfReference ( ) ;
}
cstatic Heap * GetSelfReferenceRaw ( Heap * pHeap )
{
return pHeap - > GetSelfReferenceRaw ( ) ;
}
} ;
2024-07-19 08:03:13 +00:00
struct HeapAdapterHandle
{
void * pReserved [ 2 ] ;
} ;
struct HeapAdapterInterface
{
HeapAdapterHandle handle ;
// Required:
void * ( * fAllocate ) ( HeapAdapterHandle * pHandle ,
AuUInt uLength ,
AuUInt uAlignment ) = nullptr ;
// Required:
void ( * fFree ) ( HeapAdapterHandle * pHandle ,
void * pPointer ) = nullptr ;
// Optional:
AuUInt ( * fGetBlockSize ) ( HeapAdapterHandle * pHandle ,
void * pPointer ) = nullptr ;
// Optional:
void ( * fHeapDestroy ) ( HeapAdapterHandle * pHandle ) = nullptr ;
//
bool bHasAlignmentAwareness { } ;
} ;
2021-06-27 21:25:29 +00:00
/**
2024-03-19 15:47:42 +00:00
* Returns a heap interface backed by the default allocator
*/
2024-02-13 03:18:13 +00:00
AUKN_SHARED_API ( DefaultDiscontiguousHeap , Heap ) ;
inline Heap * GetDefaultDiscontiguousHeap ( )
{
return DefaultDiscontiguousHeapNew ( ) ;
}
inline AuSPtr < Heap > GetDefaultDiscontiguousHeapShared ( )
{
// Might not allocate the control block under some STLs, unlike DefaultDiscontiguousHeapSharedShared() which will generally always allocate a control block under most STLs
return AuUnsafeRaiiToShared ( GetDefaultDiscontiguousHeap ( ) ) ;
}
2021-06-27 21:25:29 +00:00
/**
2024-03-19 15:47:42 +00:00
* Allocates uLength amount of contiguous virtual memory
* @ return a heap backed by uLength bytes of virtual memory
* @ warning the SOO variant cannot guarantee release - on - last - free and will panic if uLength cannot be allocated . Use AllocHeap [ Shared / Unique / New ] ( uLength ) instead .
*/
2024-07-19 08:03:13 +00:00
AUKN_SHARED_SOO2_NCM ( AllocHeap , Heap , kHeapSize , ( ( AuUInt , uLength ) ) ,
AuUInt uLength ) ;
2024-01-15 12:04:40 +00:00
2024-03-19 15:47:42 +00:00
/**
2024-04-23 23:52:22 +00:00
* @ warning the SOO variant cannot guarantee release - on - last - free and will panic if an invalid memory handle is provided .
2024-03-19 15:47:42 +00:00
*/
2024-07-19 08:03:13 +00:00
AUKN_SHARED_SOO2_NCM ( RequestHeapOfRegion , Heap , kHeapSize , ( ( const MemoryViewWrite & , memory ) ) ,
const MemoryViewWrite & memory ) ;
2022-01-18 19:31:15 +00:00
2024-04-23 23:52:22 +00:00
/**
* @ warning the SOO variant cannot guarantee release - on - last - free and will panic if an invalid memory handle is provided .
*/
2024-07-19 08:03:13 +00:00
AUKN_SHARED_SOO2_NCM ( RequestHeapOfSharedRegion , Heap , kHeapSize , ( ( const AuSPtr < MemoryViewWrite > & , memory ) ) ,
const AuSPtr < MemoryViewWrite > & pMemory ) ;
2024-04-23 23:52:22 +00:00
2024-03-19 15:47:42 +00:00
/**
* Proxies an existing heap with encapsulated statistics .
* This is intended for debugging purposes when accurate heap stats of a heap - subset are desired .
* @ warning this heap cannot guarantee release - on - last - free
*/
2024-07-19 08:03:13 +00:00
AUKN_SHARED_SOO2_NCM ( HeapProxy , Heap , kHeap2Size , ( ( const AuSPtr < Heap > & , pHead ) ) ,
const AuSPtr < Heap > & pHead ) ;
2022-01-18 19:31:15 +00:00
2024-03-19 15:47:42 +00:00
/**
* Proxies an existing heap with encapsulated statistics and leak detector
* This is intended for debugging purposes when accurate heap stats of a heap - subset are desired .
* @ warning this heap cannot guarantee release - on - last - free
2021-06-27 21:25:29 +00:00
*/
2024-07-19 08:03:13 +00:00
AUKN_SHARED_SOO2_NCM ( HeapProxyEx , Heap , kHeap2Size , ( ( const AuSPtr < Heap > & , pHead ) , ( LeakFinderAlloc_f , pfAlloc ) , ( LeakFinderFree_f , pfFree ) ) ,
const AuSPtr < Heap > & pHead ,
LeakFinderAlloc_f pfAlloc ,
LeakFinderFree_f pfFree ) ;
/**
* Proxies an existing heap allocator library of a malloc and free ; bonus points for aligned malloc , get allocation size , and destroy
*/
AUKN_SHARED_SOO2_NCM ( HeapAdapter , Heap , kHeap2Size , ( ( const HeapAdapterInterface & , adapterInterface ) ) ,
const HeapAdapterInterface & adapterInterface ) ;
# if defined(AURORA_IS_MODERNNT_DERIVED)
AUKN_SHARED_SOO2_NCM ( HeapWin32Adapter , Heap , kHeap2Size , ( ( void * , hHeap ) ) , void * hHeap ) ;
# endif
2024-01-19 19:40:38 +00:00
}