"L. Spiro Engine"
|
00001 00029 #ifndef __LSA_SMALLALLOCATOR_H__ 00030 #define __LSA_SMALLALLOCATOR_H__ 00031 00032 #include "../OSHeap/LSAOsHeap.h" 00033 00034 00035 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00036 // MACROS 00037 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00038 // The number of 256-byte blocks to use as a guideline for the sizes of the small allocators. 00039 #define LSA_SMALL_ALLOCATOR_BLOCKS 64 00040 00041 // The smallest allocation size. 00042 #define LSA_SMALLEST_ALLOCATION_BITS LSA_MIN_ALIGN_BITS 00043 #define LSA_SMALLEST_ALLOCATION_SIZE (1 << LSA_SMALLEST_ALLOCATION_BITS) 00044 00045 // The largest allocation size. 00046 #define LSA_LARGEST_ALLOCATION_SIZE 256 00047 00048 // Number of blocks in a full working set. 00049 #define LSA_WS (LSA_LARGEST_ALLOCATION_SIZE / LSA_SMALLEST_ALLOCATION_SIZE) 00050 00051 namespace lsa { 00052 00072 class CSmallAllocator { 00073 // Only the CStdAllocator class can create this object. 00074 friend class CStdAllocator; 00075 00076 protected : 00077 // == Various constructors. 00078 LSE_CALL CSmallAllocator( LSVOID * _pvAddress, LSUINT32 _ui32Total256Blocks ); 00079 00080 00081 // == Types. 00086 typedef struct LSA_SMALL_ALLOC_BLOCKSET { 00092 LSA_SIZE * psBits; 00093 00097 LSUINT8 * pui8Blocks; 00098 00102 LSUINT32 ui32Blocks; 00103 } * LPLSA_SMALL_ALLOC_BLOCKSET, * const LPCLSA_SMALL_ALLOC_BLOCKSET; 00104 00105 00106 // == Members. 00107 // The pointer to the next CSmallAllocator object in the linked list managed by our 00108 // superiors. 00109 CSmallAllocator * m_psaNext; 00110 00111 // The arrays of pointers to the starts of each row of blocks for each given size. 00112 // We handle 16 sizes (from 16 bytes to 256 bytes). These point to the first blocks 00113 // in each size class. 00114 LSA_SMALL_ALLOC_BLOCKSET m_pui8BlockStarts[LSA_WS]; 00115 00116 // The beginning address of our heap. 00117 LSA_SIZE m_sLow; 00118 00119 // The ending address of our heap. 00120 LSA_SIZE m_sHi; 00121 00122 00123 // == Functions. 00130 LSVOID LSE_CALL Init( LSVOID * _pvAddress, LSUINT32 _ui32Total256Blocks ); 00131 00140 LSVOID * LSE_CALL Alloc( LSA_SIZE _sSize, LSUINT32 _ui32Align = LSA_MIN_ALIGN ); 00141 00149 LSBOOL LSE_CALL Free( LSVOID * _pvAddr ); 00150 00164 LSVOID * LSE_CALL ReAlloc( LSVOID * _pvAddr, LSA_SIZE _sSize, 00165 LSA_SIZE &_sOldSize ); 00166 00172 LSBOOL LSE_CALL IsEmpty() const; 00173 00177 LSVOID LSE_CALL Trash(); 00178 00185 LSBOOL LSE_CALL HaveAddress( const LSVOID * _pvAddr ) const; 00186 00205 static LSA_SIZE LSE_CALL GetWorkingSetSizeByNumberOf256Blocks( LSUINT32 _ui32Total256Blocks, 00206 const LSVOID * _pvAddress = NULL, 00207 LSA_SMALL_ALLOC_BLOCKSET * _psabBlocks = NULL ); 00208 00217 static LSA_SIZE LSE_CALL GetFullAllocatorSizeWithNumberOf256Blocks( LSVOID * _pvAddress, 00218 LSUINT32 _ui32Total256Blocks ); 00219 00226 static LSUINT32 LSE_CALL GetElementsFromBits( LSUINT32 _ui32Bits ); 00227 00235 static LSUINT32 LSE_CALL GetByteAndBitFromBit( const LSUINT32 &_ui32Bit, 00236 LSUINT32 &_ui32ReturnBit ); 00237 00244 static LSUINT32 LSE_CALL Find0Bit( LSA_SIZE _sValue ); 00245 00253 LSE_INLINE static LSUINTPTR LSE_CALL GetBlockOffset( LSUINT32 _ui32SetIndex, LSUINT32 _ui32BlockIndex ); 00254 }; 00255 00256 00257 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00258 // DEFINITIONS 00259 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * 00266 LSE_INLINE LSBOOL LSE_CALL CSmallAllocator::HaveAddress( const LSVOID * _pvAddr ) const { 00267 LSUINTPTR uiptrThis = reinterpret_cast<LSUINTPTR>(_pvAddr); 00268 return uiptrThis >= m_sLow && uiptrThis < m_sHi; 00269 } 00270 00278 LSE_INLINE LSUINTPTR LSE_CALL CSmallAllocator::GetBlockOffset( LSUINT32 _ui32SetIndex, LSUINT32 _ui32BlockIndex ) { 00279 LSUINTPTR uiptrSize = (_ui32SetIndex + 1) * LSA_SMALLEST_ALLOCATION_SIZE; 00280 return uiptrSize * _ui32BlockIndex; 00281 } 00282 00283 00284 } // namespace lsa 00285 00286 #endif // __LSA_SMALLALLOCATOR_H__