23 #ifndef PS_POOLALLOCATOR_H 24 #define PS_POOLALLOCATOR_H 29 #include <csutil/threading/thread.h> 75 #define POOLALLOC_DEFAULT_ALLOCATION_OBJECTS 1024 79 template <
class TEMPLATE_CLASS>
82 CS::Threading::Mutex mutex;
87 struct st_pool_entry *next;
95 struct st_freelist_member
97 struct st_freelist_member *next;
102 struct st_freelist_member *freelist_head;
104 struct st_pool_entry *poollist_head;
110 uint32 allocation_step_itemcount;
116 allocation_step_itemcount = items_per_pool;
117 freelist_head = NULL;
118 poollist_head = NULL;
124 struct st_pool_entry *pool=poollist_head,*nextpool;
141 CS_ASSERT_MSG(
"Contention detected in PoolAllocator new", mutex.TryLock());
142 TEMPLATE_CLASS *objptr;
152 return (TEMPLATE_CLASS *)NULL;
156 objptr=(TEMPLATE_CLASS *)freelist_head;
157 freelist_head=freelist_head->next;
166 CS_ASSERT_MSG(
"Contention detected in PoolAllocator delete", mutex.TryLock());
174 #ifdef POOLALLOC_DEBUG_DELETE 176 CS_ASSERT(ObjectCameFromPool(obj));
179 memset(obj, 0xDD,
sizeof(TEMPLATE_CLASS));
182 ((
struct st_freelist_member *)obj)->next=freelist_head;
183 freelist_head=((
struct st_freelist_member *)obj);
189 return (ObjectCameFromPool((TEMPLATE_CLASS *)ptr)!=NULL);
195 struct st_pool_entry *ObjectCameFromPool(TEMPLATE_CLASS *obj)
198 struct st_pool_entry *testentry=poollist_head;
201 entrysize=
sizeof(TEMPLATE_CLASS);
202 if (entrysize<
sizeof(
struct st_freelist_member))
203 entrysize=
sizeof(
struct st_freelist_member);
216 if ((uint8 *)obj>(uint8 *)testentry &&
217 (uint8 *)obj<(uint8 *)testentry +
sizeof(st_pool_entry)+entrysize*allocation_step_itemcount)
219 if ((
unsigned long)((uint8 *)obj-((uint8 *)testentry +
sizeof(st_pool_entry))) % (
unsigned long)entrysize)
226 testentry=testentry->next;
236 if (
sizeof(TEMPLATE_CLASS)<
sizeof(
struct st_freelist_member))
240 struct st_freelist_member *workmember;
241 struct st_pool_entry *pool;
245 buffer=(uint8 *)calloc(1,
sizeof(st_pool_entry)+
sizeof(st_freelist_member)*allocation_step_itemcount);
251 pool=(st_pool_entry *)buffer;
254 workmember=(st_freelist_member *)(buffer+
sizeof(st_pool_entry));
255 for (i=0;i<allocation_step_itemcount-1;i++)
258 workmember->next=workmember+1;
263 workmember->next=freelist_head;
265 freelist_head=(st_freelist_member *)(buffer+
sizeof(st_pool_entry));
268 pool->next=poollist_head;
274 TEMPLATE_CLASS *workclass;
275 struct st_pool_entry *pool;
278 buffer=(uint8 *)malloc(
sizeof(st_pool_entry)+
sizeof(TEMPLATE_CLASS)*allocation_step_itemcount);
284 memset(buffer, 0,
sizeof(st_pool_entry));
285 memset(buffer+
sizeof(st_pool_entry), 0xDD,
sizeof(TEMPLATE_CLASS)*allocation_step_itemcount);
288 pool=(st_pool_entry *)buffer;
291 workclass=(TEMPLATE_CLASS *)(buffer+
sizeof(st_pool_entry));
292 for (i=0;i<allocation_step_itemcount-1;i++)
295 ((st_freelist_member *)workclass)->next=(st_freelist_member *)(workclass+1);
300 ((st_freelist_member *)workclass)->next=freelist_head;
303 freelist_head=(st_freelist_member *)(buffer+
sizeof(st_pool_entry));
306 pool->next=poollist_head;
void CallFromDelete(TEMPLATE_CLASS *obj)
Places a block back on the list of available blocks. Does NOT release memory back to the heap - ever...
#define POOLALLOC_DEFAULT_ALLOCATION_OBJECTS
PoolAllocator(int items_per_pool=POOLALLOC_DEFAULT_ALLOCATION_OBJECTS)
PoolAllocator constructor. Sets list heads to NULL and the per-pool object count to the passed value ...
bool PointerCameFromPool(void *ptr)
TEMPLATE_CLASS * CallFromNew()
Returns a new block from the list of available blocks. Allocates another pool if necessary.
#define CS_ASSERT_MSG(msg, x)
~PoolAllocator()
PoolAllocator destructor. Releases the memory assigned to the pools back to the heap and clears the p...