|
version 1.4, 2014/01/29 16:42:57
|
version 1.5.2.1, 2015/07/01 21:31:26
|
|
Line 12 terms:
|
Line 12 terms:
|
| All of the documentation and software included in the ELWIX and AITNET |
All of the documentation and software included in the ELWIX and AITNET |
| Releases is copyrighted by ELWIX - Sofia/Bulgaria <info@elwix.org> |
Releases is copyrighted by ELWIX - Sofia/Bulgaria <info@elwix.org> |
| |
|
| Copyright 2004 - 2014 | Copyright 2004 - 2015 |
| by Michael Pounov <misho@elwix.org>. All rights reserved. |
by Michael Pounov <misho@elwix.org>. All rights reserved. |
| |
|
| Redistribution and use in source and binary forms, with or without |
Redistribution and use in source and binary forms, with or without |
|
Line 218 mpool_malloc(mpool_t * __restrict mp, u_int size, cons
|
Line 218 mpool_malloc(mpool_t * __restrict mp, u_int size, cons
|
| return NULL; |
return NULL; |
| } else { /* quota */ |
} else { /* quota */ |
| mp->pool_quota.curr += size; |
mp->pool_quota.curr += size; |
| |
mp->pool_quota.real += 1 << (idx + MEM_MIN_BUCKET); |
| memset(m->alloc_mem, 0, align + 12); |
memset(m->alloc_mem, 0, align + 12); |
| } |
} |
| } |
} |
|
Line 246 mpool_malloc(mpool_t * __restrict mp, u_int size, cons
|
Line 247 mpool_malloc(mpool_t * __restrict mp, u_int size, cons
|
| void * |
void * |
| mpool_realloc(mpool_t * __restrict mp, void * __restrict data, u_int newsize, const char *memname) |
mpool_realloc(mpool_t * __restrict mp, void * __restrict data, u_int newsize, const char *memname) |
| { |
{ |
| struct tagAlloc *m, *tmp; |
|
| int idx, oidx; |
int idx, oidx; |
| void *p; |
void *p; |
| u_int align, osize; | u_int osize; |
| | #ifdef MPOOL_USE_REALLOC |
| | struct tagAlloc *m, *tmp; |
| | u_int align; |
| | #endif |
| |
|
| /* if !data execute mpool_malloc() */ |
/* if !data execute mpool_malloc() */ |
| if (!data) |
if (!data) |
|
Line 263 mpool_realloc(mpool_t * __restrict mp, void * __restri
|
Line 267 mpool_realloc(mpool_t * __restrict mp, void * __restri
|
| if (MEM_BADADDR(data) || MEM_CORRUPT(data)) { |
if (MEM_BADADDR(data) || MEM_CORRUPT(data)) { |
| elwix_SetErr(EFAULT, "Corrupted memory address"); |
elwix_SetErr(EFAULT, "Corrupted memory address"); |
| return NULL; |
return NULL; |
| } else { |
|
| osize = ((u_int*)data)[-2] * sizeof(u_int); |
|
| oidx = BucketIndex(osize); |
|
| } |
} |
| /* prepare new size */ |
/* prepare new size */ |
| if (newsize > MEM_ALLOC_MAX) { |
if (newsize > MEM_ALLOC_MAX) { |
| elwix_SetErr(ENOMEM, "Memory size is too large"); |
elwix_SetErr(ENOMEM, "Memory size is too large"); |
| return NULL; |
return NULL; |
| } else { |
|
| newsize = (newsize + 3) & ~3; /* must align to 4 because needed room for sentinels */ |
|
| idx = BucketIndex(newsize); |
|
| } |
} |
| |
|
| mpool_lock(mp); |
mpool_lock(mp); |
| |
|
| |
osize = ((u_int*)data)[-2] * sizeof(u_int); |
| |
oidx = BucketIndex(osize); |
| |
newsize = (newsize + 3) & ~3; /* must align to 4 because needed room for sentinels */ |
| |
idx = BucketIndex(newsize); |
| |
|
| /* quota */ |
/* quota */ |
| if (mp->pool_quota.max && |
if (mp->pool_quota.max && |
| (mp->pool_quota.curr + ((u_long) newsize - osize)) > mp->pool_quota.max) { |
(mp->pool_quota.curr + ((u_long) newsize - osize)) > mp->pool_quota.max) { |
|
Line 286 mpool_realloc(mpool_t * __restrict mp, void * __restri
|
Line 289 mpool_realloc(mpool_t * __restrict mp, void * __restri
|
| return NULL; |
return NULL; |
| } |
} |
| |
|
| |
#ifndef MPOOL_USE_REALLOC |
| |
if (oidx != idx) { |
| |
mpool_unlock(mp); |
| |
p = mpool_malloc(mp, newsize, memname); |
| |
if (!p) |
| |
return NULL; |
| |
|
| |
memcpy(p, data, osize); |
| |
mpool_free(mp, data, 0); |
| |
} else { |
| |
p = data; |
| |
|
| |
((u_int*) p)[-2] = newsize / sizeof(u_int); |
| |
((u_int*) p)[newsize / sizeof(u_int)] = MEM_MAGIC_STOP; |
| |
|
| |
mp->pool_bytes.alloc += (u_long) newsize - osize; |
| |
mp->pool_quota.curr += (u_long) newsize - osize; |
| |
|
| |
mpool_unlock(mp); |
| |
} |
| |
|
| |
return p; |
| |
#else |
| /* find old memory block */ |
/* find old memory block */ |
| TAILQ_FOREACH_SAFE(m, &mp->pool_active[oidx], alloc_node, tmp) { |
TAILQ_FOREACH_SAFE(m, &mp->pool_active[oidx], alloc_node, tmp) { |
| if (mem_data(m, void*) == data && mem_size(m) == osize) { |
if (mem_data(m, void*) == data && mem_size(m) == osize) { |
|
Line 326 mpool_realloc(mpool_t * __restrict mp, void * __restri
|
Line 352 mpool_realloc(mpool_t * __restrict mp, void * __restri
|
| } |
} |
| /* quota */ |
/* quota */ |
| mp->pool_quota.curr += (u_long) newsize - osize; |
mp->pool_quota.curr += (u_long) newsize - osize; |
| |
mp->pool_quota.real += (1 << (idx + MEM_MIN_BUCKET)) - (1 << (oidx + MEM_MIN_BUCKET)); |
| |
|
| m->alloc_mem[0] = newsize / sizeof(u_int); |
m->alloc_mem[0] = newsize / sizeof(u_int); |
| m->alloc_mem[1] = MEM_MAGIC_START; |
m->alloc_mem[1] = MEM_MAGIC_START; |
|
Line 343 mpool_realloc(mpool_t * __restrict mp, void * __restri
|
Line 370 mpool_realloc(mpool_t * __restrict mp, void * __restri
|
| |
|
| mpool_unlock(mp); |
mpool_unlock(mp); |
| return mem_data(m, void*); |
return mem_data(m, void*); |
| |
#endif |
| } |
} |
| |
|
| /* |
/* |
|
Line 382 mpool_purge(mpool_t * __restrict mp, u_int atmost)
|
Line 410 mpool_purge(mpool_t * __restrict mp, u_int atmost)
|
| mp->pool_bytes.free += mem_size(m); |
mp->pool_bytes.free += mem_size(m); |
| /* quota */ |
/* quota */ |
| mp->pool_quota.curr -= mem_size(m); |
mp->pool_quota.curr -= mem_size(m); |
| |
mp->pool_quota.real -= 1 << (i + MEM_MIN_BUCKET); |
| |
|
| if (m->alloc_mem) |
if (m->alloc_mem) |
| free(m->alloc_mem); |
free(m->alloc_mem); |
|
Line 440 mpool_free(mpool_t * __restrict mp, void * __restrict
|
Line 469 mpool_free(mpool_t * __restrict mp, void * __restrict
|
| mp->pool_bytes.free += mem_size(m); |
mp->pool_bytes.free += mem_size(m); |
| /* quota */ |
/* quota */ |
| mp->pool_quota.curr -= mem_size(m); |
mp->pool_quota.curr -= mem_size(m); |
| |
mp->pool_quota.real -= 1 << (idx + MEM_MIN_BUCKET); |
| |
|
| if (m->alloc_mem) |
if (m->alloc_mem) |
| free(m->alloc_mem); |
free(m->alloc_mem); |
|
Line 492 mpool_free2(mpool_t * __restrict mp, u_int size, const
|
Line 522 mpool_free2(mpool_t * __restrict mp, u_int size, const
|
| mp->pool_bytes.free += mem_size(m); |
mp->pool_bytes.free += mem_size(m); |
| /* quota */ |
/* quota */ |
| mp->pool_quota.curr -= mem_size(m); |
mp->pool_quota.curr -= mem_size(m); |
| |
mp->pool_quota.real -= 1 << (idx + MEM_MIN_BUCKET); |
| |
|
| if (m->alloc_mem) |
if (m->alloc_mem) |
| free(m->alloc_mem); |
free(m->alloc_mem); |
|
Line 627 mpool_setquota(mpool_t * __restrict mp, u_long maxmem)
|
Line 658 mpool_setquota(mpool_t * __restrict mp, u_long maxmem)
|
| * mpool_getquota() - Get memory quota |
* mpool_getquota() - Get memory quota |
| * |
* |
| * @mp = Memory pool |
* @mp = Memory pool |
| * @currmem = Return current memory | * @currmem = Return current memory usage |
| | * @realmem = Return current real memory usage |
| * @maxmem = Return max quota size |
* @maxmem = Return max quota size |
| * return: none |
* return: none |
| */ |
*/ |
| void |
void |
| mpool_getquota(mpool_t * __restrict mp, u_long *currmem, u_long *maxmem) | mpool_getquota(mpool_t * __restrict mp, u_long *currmem, u_long *realmem, u_long *maxmem) |
| { |
{ |
| if (!mp) |
if (!mp) |
| return; |
return; |
| |
|
| if (maxmem) |
if (maxmem) |
| *maxmem = mp->pool_quota.max; |
*maxmem = mp->pool_quota.max; |
| |
if (realmem) |
| |
*realmem = mp->pool_quota.real; |
| if (currmem) |
if (currmem) |
| *currmem = mp->pool_quota.curr; |
*currmem = mp->pool_quota.curr; |
| } |
} |
|
Line 734 mpool_xstrdup(const char *str)
|
Line 768 mpool_xstrdup(const char *str)
|
| { |
{ |
| return mpool_strdup(elwix_mpool, str, elwix_Prog); |
return mpool_strdup(elwix_mpool, str, elwix_Prog); |
| } |
} |
| |
|
| |
/* |
| |
* mpool_xstatistics() - elwix memory pool statistics wrapper |
| |
* |
| |
* @cb = Export statistics to callback |
| |
* return: none |
| |
*/ |
| |
void |
| |
mpool_xstatistics(mpool_stat_cb cb) |
| |
{ |
| |
mpool_statistics(elwix_mpool, cb); |
| |
} |
| |
|
| |
static void |
| |
xdump_show(u_int size, u_int act, u_int inact) |
| |
{ |
| |
if (!act && !inact) |
| |
return; /* skip empty bucket */ |
| |
|
| |
if (size < 1024) |
| |
printf("\t\t* BUCKET %uB size, %u active, %u inactive\n", |
| |
size, act, inact); |
| |
else if (size < 1048576) |
| |
printf("\t\t* BUCKET %uKB size, %u active, %u inactive\n", |
| |
size / 1024, act, inact); |
| |
else |
| |
printf("\t\t* BUCKET %uMB size, %u active, %u inactive\n", |
| |
size / 1048576, act, inact); |
| |
} |
| |
|
| |
/* |
| |
* mpool_dump() - Dump elwix memory pool statistics |
| |
* |
| |
* @mp = memory pool, if =NULL dump elwix default memory pool |
| |
* @fmt = prefix info format string |
| |
* @... = argument(s) |
| |
* return: none |
| |
*/ |
| |
void |
| |
mpool_dump(mpool_t * __restrict mp, const char *fmt, ...) |
| |
{ |
| |
va_list lst; |
| |
mpool_t *p = mp ? mp : elwix_mpool; |
| |
|
| |
if (fmt) { |
| |
va_start(lst, fmt); |
| |
vprintf(fmt, lst); |
| |
va_end(lst); |
| |
} else |
| |
printf("\n%s(%d)\n", __func__, __LINE__); |
| |
|
| |
printf("------------------------------------------------------------\n"); |
| |
printf( " ELWIX memory pool ::\n" |
| |
"\t- quotas Current/Real/Max = %lu/%lu/%lu\n" |
| |
"\t- calls Alloc/Free/Cache = %lu/%lu/%lu\n" |
| |
"\t- bytes Alloc/Free/Cache = %lu/%lu/%lu\n" |
| |
"\t- buckets :\n", |
| |
p->pool_quota.curr, p->pool_quota.real, p->pool_quota.max, |
| |
p->pool_calls.alloc, p->pool_calls.free, p->pool_calls.cache, |
| |
p->pool_bytes.alloc, p->pool_bytes.free, p->pool_bytes.cache); |
| |
|
| |
mpool_statistics(p, xdump_show); |
| |
printf("------------------------------------------------------------\n"); |
| |
} |
| |
|