diff options
author | Richard Mudgett <rmudgett@digium.com> | 2013-08-27 18:52:23 +0000 |
---|---|---|
committer | Richard Mudgett <rmudgett@digium.com> | 2013-08-27 18:52:23 +0000 |
commit | 3540c7ac6eca33609c294baa1fbcf56722536f6a (patch) | |
tree | 3419e765e4feef95c35dbc0f1e208fea7897bf80 /main | |
parent | c32f8a5ca972db19719c7512380c820ba972014a (diff) |
Made MALLOC_DEBUG less CPU intensive by default.
Storing a backtrace for each allocation in anticipation of a memory
management problem is very CPU intensive.
* Added the CLI "memory backtrace {on|off}" command to request that the
backtrace be gathered only on request. The backtrace is off by default.
(issue ASTERISK-22221)
Reported by: Matt Jordan
........
Merged revisions 397809 from http://svn.asterisk.org/svn/asterisk/branches/12
git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@397811 65c4cc65-6c06-0410-ace0-fbb531ad65f3
Diffstat (limited to 'main')
-rw-r--r-- | main/astmm.c | 42 |
1 files changed, 41 insertions, 1 deletions
diff --git a/main/astmm.c b/main/astmm.c index 2e1016ab5..3f6d702f4 100644 --- a/main/astmm.c +++ b/main/astmm.c @@ -142,6 +142,8 @@ enum summary_opts { static enum summary_opts atexit_summary; /*! Nonzero if the unfreed regions are listed at exit. */ static int atexit_list; +/*! Nonzero if the memory allocation backtrace is enabled. */ +static int backtrace_enabled; #define HASH(a) (((unsigned long)(a)) % ARRAY_LEN(regions)) @@ -235,7 +237,7 @@ static void *__ast_alloc_region(size_t size, const enum func_type which, const c reg->cache = cache; reg->lineno = lineno; reg->which = which; - reg->bt = ast_bt_create(); + reg->bt = backtrace_enabled ? ast_bt_create() : NULL; ast_copy_string(reg->file, file, sizeof(reg->file)); ast_copy_string(reg->func, func, sizeof(reg->func)); @@ -975,11 +977,49 @@ static char *handle_memory_show_summary(struct ast_cli_entry *e, int cmd, struct return CLI_SUCCESS; } +static char *handle_memory_backtrace(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a) +{ + switch (cmd) { + case CLI_INIT: + e->command = "memory backtrace"; + e->usage = + "Usage: memory backtrace {on|off}\n" + " Enable dumping an allocation backtrace with memory diagnostics.\n" + " Note that saving the backtrace data for each allocation\n" + " can be CPU intensive.\n"; + return NULL; + case CLI_GENERATE: + if (a->pos == 2) { + const char * const options[] = { "off", "on", NULL }; + + return ast_cli_complete(a->word, options, a->n); + } + return NULL; + } + + if (a->argc != 3) { + return CLI_SHOWUSAGE; + } + + if (ast_true(a->argv[2])) { + backtrace_enabled = 1; + } else if (ast_false(a->argv[2])) { + backtrace_enabled = 0; + } else { + return CLI_SHOWUSAGE; + } + + ast_cli(a->fd, "The memory backtrace is: %s\n", backtrace_enabled ? "On" : "Off"); + + return CLI_SUCCESS; +} + static struct ast_cli_entry cli_memory[] = { AST_CLI_DEFINE(handle_memory_atexit_list, "Enable memory allocations not freed at exit list."), AST_CLI_DEFINE(handle_memory_atexit_summary, "Enable memory allocations not freed at exit summary."), AST_CLI_DEFINE(handle_memory_show_allocations, "Display outstanding memory allocations"), AST_CLI_DEFINE(handle_memory_show_summary, "Summarize outstanding memory allocations"), + AST_CLI_DEFINE(handle_memory_backtrace, "Enable dumping an allocation backtrace with memory diagnostics."), }; AST_LIST_HEAD_NOLOCK(region_list, ast_region); |