unsigned int flags; /* MEM_F_* */
unsigned int users; /* number of pools sharing this zone */
unsigned int failed; /* failed allocations */
- /* 32-bit hole here */
+ unsigned int alloc_sz; /* allocated size (includes hidden fields) */
struct list list; /* list of all known pools */
char name[12]; /* name of the pool */
struct pool_cache_head cache[MAX_THREADS]; /* pool caches */
#endif // DEBUG_MEMORY_POOLS
/* It's possible to trace callers of pool_free() by placing their pointer
- * after the end of the area and the optional mark above.
+ * after the end of the area and the optional mark above, which means the
+ * end of the allocated array.
*/
#if defined(DEBUG_POOL_TRACING)
# define POOL_EXTRA_CALLER (sizeof(void *))
typeof(pool) __p = (pool); \
typeof(item) __i = (item); \
typeof(caller) __c = (caller); \
- *(typeof(caller)*)(((char *)__i) + __p->size + POOL_EXTRA_MARK) = __c; \
+ *(typeof(caller)*)(((char *)__i) + __p->alloc_sz - sizeof(void*)) = __c; \
} while (0)
#else // DEBUG_POOL_TRACING
return NULL;
if (name)
strlcpy2(pool->name, name, sizeof(pool->name));
+ pool->alloc_sz = size + POOL_EXTRA;
pool->size = size;
pool->flags = flags;
LIST_APPEND(start, &pool->list);
void *pool_get_from_os(struct pool_head *pool)
{
if (!pool->limit || pool->allocated < pool->limit) {
- void *ptr = pool_alloc_area(pool->size + POOL_EXTRA);
+ void *ptr = pool_alloc_area(pool->alloc_sz);
if (ptr) {
_HA_ATOMIC_INC(&pool->allocated);
return ptr;
*(uint32_t *)ptr = 0xDEADADD4;
#endif /* DEBUG_UAF */
- pool_free_area(ptr, pool->size + POOL_EXTRA);
+ pool_free_area(ptr, pool->alloc_sz);
_HA_ATOMIC_DEC(&pool->allocated);
}