mirror of
https://github.com/asterisk/asterisk.git
synced 2025-09-20 12:20:12 +00:00
Merged revisions 48987 via svnmerge from
https://origsvn.digium.com/svn/asterisk/branches/1.4 ........ r48987 | kpfleming | 2006-12-27 12:29:13 -0600 (Wed, 27 Dec 2006) | 2 lines allow 'show memory' and 'show memory summary' to distinguish memory allocations that were done for caching purposes, so they don't look like memory leaks ........ git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@48989 65c4cc65-6c06-0410-ace0-fbb531ad65f3
This commit is contained in:
@@ -957,7 +957,7 @@ struct iax_frame *iax_frame_new(int direction, int datalen)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!fr) {
|
if (!fr) {
|
||||||
if (!(fr = ast_calloc(1, sizeof(*fr) + datalen)))
|
if (!(fr = ast_calloc_cache(1, sizeof(*fr) + datalen)))
|
||||||
return NULL;
|
return NULL;
|
||||||
fr->mallocd_datalen = datalen;
|
fr->mallocd_datalen = datalen;
|
||||||
}
|
}
|
||||||
|
@@ -44,6 +44,7 @@
|
|||||||
#undef vasprintf
|
#undef vasprintf
|
||||||
|
|
||||||
void *__ast_calloc(size_t nmemb, size_t size, const char *file, int lineno, const char *func);
|
void *__ast_calloc(size_t nmemb, size_t size, const char *file, int lineno, const char *func);
|
||||||
|
void *__ast_calloc_cache(size_t nmemb, size_t size, const char *file, int lineno, const char *func);
|
||||||
void *__ast_malloc(size_t size, const char *file, int lineno, const char *func);
|
void *__ast_malloc(size_t size, const char *file, int lineno, const char *func);
|
||||||
void __ast_free(void *ptr, const char *file, int lineno, const char *func);
|
void __ast_free(void *ptr, const char *file, int lineno, const char *func);
|
||||||
void *__ast_realloc(void *ptr, size_t size, const char *file, int lineno, const char *func);
|
void *__ast_realloc(void *ptr, size_t size, const char *file, int lineno, const char *func);
|
||||||
@@ -59,6 +60,9 @@ void __ast_mm_init(void);
|
|||||||
#define calloc(a,b) \
|
#define calloc(a,b) \
|
||||||
__ast_calloc(a,b,__FILE__, __LINE__, __PRETTY_FUNCTION__)
|
__ast_calloc(a,b,__FILE__, __LINE__, __PRETTY_FUNCTION__)
|
||||||
|
|
||||||
|
#define ast_calloc_cache(a,b) \
|
||||||
|
__ast_calloc_cache(a,b,__FILE__, __LINE__, __PRETTY_FUNCTION__)
|
||||||
|
|
||||||
#define malloc(a) \
|
#define malloc(a) \
|
||||||
__ast_malloc(a,__FILE__, __LINE__, __PRETTY_FUNCTION__)
|
__ast_malloc(a,__FILE__, __LINE__, __PRETTY_FUNCTION__)
|
||||||
|
|
||||||
|
@@ -361,6 +361,19 @@ void * attribute_malloc _ast_calloc(size_t num, size_t len, const char *file, in
|
|||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
|
/*!
|
||||||
|
* \brief A wrapper for calloc() for use in cache pools
|
||||||
|
*
|
||||||
|
* ast_calloc_cache() is a wrapper for calloc() that will generate an Asterisk log
|
||||||
|
* message in the case that the allocation fails. When memory debugging is in use,
|
||||||
|
* the memory allocated by this function will be marked as 'cache' so it can be
|
||||||
|
* distinguished from normal memory allocations.
|
||||||
|
*
|
||||||
|
* The arguments and return value are the same as calloc()
|
||||||
|
*/
|
||||||
|
#define ast_calloc_cache(num, len) \
|
||||||
|
_ast_calloc((num), (len), __FILE__, __LINE__, __PRETTY_FUNCTION__)
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* \brief A wrapper for realloc()
|
* \brief A wrapper for realloc()
|
||||||
*
|
*
|
||||||
|
65
main/astmm.c
65
main/astmm.c
@@ -72,6 +72,7 @@ static struct ast_region {
|
|||||||
char func[40];
|
char func[40];
|
||||||
unsigned int lineno;
|
unsigned int lineno;
|
||||||
enum func_type which;
|
enum func_type which;
|
||||||
|
unsigned int cache; /* region was allocated as part of a cache pool */
|
||||||
size_t len;
|
size_t len;
|
||||||
unsigned int fence;
|
unsigned int fence;
|
||||||
unsigned char data[0];
|
unsigned char data[0];
|
||||||
@@ -92,7 +93,7 @@ AST_MUTEX_DEFINE_STATIC(showmemorylock);
|
|||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
static inline void *__ast_alloc_region(size_t size, const enum func_type which, const char *file, int lineno, const char *func)
|
static inline void *__ast_alloc_region(size_t size, const enum func_type which, const char *file, int lineno, const char *func, unsigned int cache)
|
||||||
{
|
{
|
||||||
struct ast_region *reg;
|
struct ast_region *reg;
|
||||||
void *ptr = NULL;
|
void *ptr = NULL;
|
||||||
@@ -109,6 +110,7 @@ static inline void *__ast_alloc_region(size_t size, const enum func_type which,
|
|||||||
reg->lineno = lineno;
|
reg->lineno = lineno;
|
||||||
reg->len = size;
|
reg->len = size;
|
||||||
reg->which = which;
|
reg->which = which;
|
||||||
|
reg->cache = cache;
|
||||||
ptr = reg->data;
|
ptr = reg->data;
|
||||||
hash = HASH(ptr);
|
hash = HASH(ptr);
|
||||||
reg->fence = FENCE_MAGIC;
|
reg->fence = FENCE_MAGIC;
|
||||||
@@ -181,7 +183,17 @@ void *__ast_calloc(size_t nmemb, size_t size, const char *file, int lineno, cons
|
|||||||
{
|
{
|
||||||
void *ptr;
|
void *ptr;
|
||||||
|
|
||||||
if ((ptr = __ast_alloc_region(size * nmemb, FUNC_CALLOC, file, lineno, func)))
|
if ((ptr = __ast_alloc_region(size * nmemb, FUNC_CALLOC, file, lineno, func, 0)))
|
||||||
|
memset(ptr, 0, size * nmemb);
|
||||||
|
|
||||||
|
return ptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
void *__ast_calloc_cache(size_t nmemb, size_t size, const char *file, int lineno, const char *func)
|
||||||
|
{
|
||||||
|
void *ptr;
|
||||||
|
|
||||||
|
if ((ptr = __ast_alloc_region(size * nmemb, FUNC_CALLOC, file, lineno, func, 1)))
|
||||||
memset(ptr, 0, size * nmemb);
|
memset(ptr, 0, size * nmemb);
|
||||||
|
|
||||||
return ptr;
|
return ptr;
|
||||||
@@ -189,7 +201,7 @@ void *__ast_calloc(size_t nmemb, size_t size, const char *file, int lineno, cons
|
|||||||
|
|
||||||
void *__ast_malloc(size_t size, const char *file, int lineno, const char *func)
|
void *__ast_malloc(size_t size, const char *file, int lineno, const char *func)
|
||||||
{
|
{
|
||||||
return __ast_alloc_region(size, FUNC_MALLOC, file, lineno, func);
|
return __ast_alloc_region(size, FUNC_MALLOC, file, lineno, func, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void __ast_free(void *ptr, const char *file, int lineno, const char *func)
|
void __ast_free(void *ptr, const char *file, int lineno, const char *func)
|
||||||
@@ -208,7 +220,7 @@ void *__ast_realloc(void *ptr, size_t size, const char *file, int lineno, const
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!(tmp = __ast_alloc_region(size, FUNC_REALLOC, file, lineno, func)))
|
if (!(tmp = __ast_alloc_region(size, FUNC_REALLOC, file, lineno, func, 0)))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
if (len > size)
|
if (len > size)
|
||||||
@@ -230,7 +242,7 @@ char *__ast_strdup(const char *s, const char *file, int lineno, const char *func
|
|||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
len = strlen(s) + 1;
|
len = strlen(s) + 1;
|
||||||
if ((ptr = __ast_alloc_region(len, FUNC_STRDUP, file, lineno, func)))
|
if ((ptr = __ast_alloc_region(len, FUNC_STRDUP, file, lineno, func, 0)))
|
||||||
strcpy(ptr, s);
|
strcpy(ptr, s);
|
||||||
|
|
||||||
return ptr;
|
return ptr;
|
||||||
@@ -247,7 +259,7 @@ char *__ast_strndup(const char *s, size_t n, const char *file, int lineno, const
|
|||||||
len = strlen(s) + 1;
|
len = strlen(s) + 1;
|
||||||
if (len > n)
|
if (len > n)
|
||||||
len = n;
|
len = n;
|
||||||
if ((ptr = __ast_alloc_region(len, FUNC_STRNDUP, file, lineno, func)))
|
if ((ptr = __ast_alloc_region(len, FUNC_STRNDUP, file, lineno, func, 0)))
|
||||||
strcpy(ptr, s);
|
strcpy(ptr, s);
|
||||||
|
|
||||||
return ptr;
|
return ptr;
|
||||||
@@ -264,7 +276,7 @@ int __ast_asprintf(const char *file, int lineno, const char *func, char **strp,
|
|||||||
va_copy(ap2, ap);
|
va_copy(ap2, ap);
|
||||||
size = vsnprintf(&s, 1, fmt, ap2);
|
size = vsnprintf(&s, 1, fmt, ap2);
|
||||||
va_end(ap2);
|
va_end(ap2);
|
||||||
if (!(*strp = __ast_alloc_region(size + 1, FUNC_ASPRINTF, file, lineno, func))) {
|
if (!(*strp = __ast_alloc_region(size + 1, FUNC_ASPRINTF, file, lineno, func, 0))) {
|
||||||
va_end(ap);
|
va_end(ap);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
@@ -284,7 +296,7 @@ int __ast_vasprintf(char **strp, const char *fmt, va_list ap, const char *file,
|
|||||||
va_copy(ap2, ap);
|
va_copy(ap2, ap);
|
||||||
size = vsnprintf(&s, 1, fmt, ap2);
|
size = vsnprintf(&s, 1, fmt, ap2);
|
||||||
va_end(ap2);
|
va_end(ap2);
|
||||||
if (!(*strp = __ast_alloc_region(size + 1, FUNC_VASPRINTF, file, lineno, func))) {
|
if (!(*strp = __ast_alloc_region(size + 1, FUNC_VASPRINTF, file, lineno, func, 0))) {
|
||||||
va_end(ap);
|
va_end(ap);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
@@ -299,6 +311,7 @@ static int handle_show_memory(int fd, int argc, char *argv[])
|
|||||||
struct ast_region *reg;
|
struct ast_region *reg;
|
||||||
unsigned int x;
|
unsigned int x;
|
||||||
unsigned int len = 0;
|
unsigned int len = 0;
|
||||||
|
unsigned int cache_len = 0;
|
||||||
unsigned int count = 0;
|
unsigned int count = 0;
|
||||||
unsigned int *fence;
|
unsigned int *fence;
|
||||||
|
|
||||||
@@ -321,16 +334,22 @@ static int handle_show_memory(int fd, int argc, char *argv[])
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (!fn || !strcasecmp(fn, reg->file)) {
|
if (!fn || !strcasecmp(fn, reg->file)) {
|
||||||
ast_cli(fd, "%10d bytes allocated in %20s at line %5d of %s\n",
|
ast_cli(fd, "%10d bytes allocated%s in %20s at line %5d of %s\n",
|
||||||
(int) reg->len, reg->func, reg->lineno, reg->file);
|
(int) reg->len, reg->cache ? " (cache)" : "",
|
||||||
|
reg->func, reg->lineno, reg->file);
|
||||||
len += reg->len;
|
len += reg->len;
|
||||||
|
if (reg->cache)
|
||||||
|
cache_len += reg->len;
|
||||||
count++;
|
count++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ast_mutex_unlock(&showmemorylock);
|
ast_mutex_unlock(&showmemorylock);
|
||||||
|
|
||||||
ast_cli(fd, "%d bytes allocated %d units total\n", len, count);
|
if (cache_len)
|
||||||
|
ast_cli(fd, "%d bytes allocated (%d in caches) in %d allocations", len, cache_len, count);
|
||||||
|
else
|
||||||
|
ast_cli(fd, "%d bytes allocated in %d allocations\n", len, count);
|
||||||
|
|
||||||
return RESULT_SUCCESS;
|
return RESULT_SUCCESS;
|
||||||
}
|
}
|
||||||
@@ -341,10 +360,12 @@ static int handle_show_memory_summary(int fd, int argc, char *argv[])
|
|||||||
int x;
|
int x;
|
||||||
struct ast_region *reg;
|
struct ast_region *reg;
|
||||||
unsigned int len = 0;
|
unsigned int len = 0;
|
||||||
|
unsigned int cache_len = 0;
|
||||||
int count = 0;
|
int count = 0;
|
||||||
struct file_summary {
|
struct file_summary {
|
||||||
char fn[80];
|
char fn[80];
|
||||||
int len;
|
int len;
|
||||||
|
int cache_len;
|
||||||
int count;
|
int count;
|
||||||
struct file_summary *next;
|
struct file_summary *next;
|
||||||
} *list = NULL, *cur;
|
} *list = NULL, *cur;
|
||||||
@@ -371,6 +392,8 @@ static int handle_show_memory_summary(int fd, int argc, char *argv[])
|
|||||||
}
|
}
|
||||||
|
|
||||||
cur->len += reg->len;
|
cur->len += reg->len;
|
||||||
|
if (reg->cache)
|
||||||
|
cur->cache_len += reg->len;
|
||||||
cur->count++;
|
cur->count++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -379,17 +402,31 @@ static int handle_show_memory_summary(int fd, int argc, char *argv[])
|
|||||||
/* Dump the whole list */
|
/* Dump the whole list */
|
||||||
for (cur = list; cur; cur = cur->next) {
|
for (cur = list; cur; cur = cur->next) {
|
||||||
len += cur->len;
|
len += cur->len;
|
||||||
|
cache_len += cur->cache_len;
|
||||||
count += cur->count;
|
count += cur->count;
|
||||||
|
if (cur->cache_len) {
|
||||||
if (fn) {
|
if (fn) {
|
||||||
ast_cli(fd, "%10d bytes in %5d allocations in function '%s' of '%s'\n",
|
ast_cli(fd, "%10d bytes (%10d cache) in %d allocations in function '%s' of '%s'\n",
|
||||||
|
cur->len, cur->cache_len, cur->count, cur->fn, fn);
|
||||||
|
} else {
|
||||||
|
ast_cli(fd, "%10d bytes (%10d cache) in %d allocations in file '%s'\n",
|
||||||
|
cur->len, cur->cache_len, cur->count, cur->fn);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (fn) {
|
||||||
|
ast_cli(fd, "%10d bytes in %d allocations in function '%s' of '%s'\n",
|
||||||
cur->len, cur->count, cur->fn, fn);
|
cur->len, cur->count, cur->fn, fn);
|
||||||
} else {
|
} else {
|
||||||
ast_cli(fd, "%10d bytes in %5d allocations in file '%s'\n",
|
ast_cli(fd, "%10d bytes in %d allocations in file '%s'\n",
|
||||||
cur->len, cur->count, cur->fn);
|
cur->len, cur->count, cur->fn);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ast_cli(fd, "%d bytes allocated %d units total\n", len, count);
|
if (cache_len)
|
||||||
|
ast_cli(fd, "%d bytes allocated (%d in caches) in %d allocations", len, cache_len, count);
|
||||||
|
else
|
||||||
|
ast_cli(fd, "%d bytes allocated in %d allocations\n", len, count);
|
||||||
|
|
||||||
return RESULT_SUCCESS;
|
return RESULT_SUCCESS;
|
||||||
}
|
}
|
||||||
|
@@ -301,7 +301,7 @@ static struct ast_frame *ast_frame_header_new(void)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!(f = ast_calloc(1, sizeof(*f))))
|
if (!(f = ast_calloc_cache(1, sizeof(*f))))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
f->mallocd_hdr_len = sizeof(*f);
|
f->mallocd_hdr_len = sizeof(*f);
|
||||||
@@ -458,7 +458,7 @@ struct ast_frame *ast_frdup(const struct ast_frame *f)
|
|||||||
AST_LIST_TRAVERSE_SAFE_END
|
AST_LIST_TRAVERSE_SAFE_END
|
||||||
}
|
}
|
||||||
if (!buf) {
|
if (!buf) {
|
||||||
if (!(buf = ast_calloc(1, len)))
|
if (!(buf = ast_calloc_cache(1, len)))
|
||||||
return NULL;
|
return NULL;
|
||||||
out = buf;
|
out = buf;
|
||||||
out->mallocd_hdr_len = len;
|
out->mallocd_hdr_len = len;
|
||||||
|
Reference in New Issue
Block a user