summaryrefslogtreecommitdiff
path: root/util/malloc-stats.c
diff options
context:
space:
mode:
authorBehdad Esfahbod <behdad@behdad.org>2009-01-31 22:10:57 -0500
committerBehdad Esfahbod <behdad@behdad.org>2009-01-31 22:10:57 -0500
commitd63c1ab3ffcb64220a05c80e674324f524f29dc2 (patch)
tree0551782de2f8f6f5f8082c675daceac8d6439eb1 /util/malloc-stats.c
parent64d1c7587041f765b393e1802a10cce02b807ad1 (diff)
downloadcairo-d63c1ab3ffcb64220a05c80e674324f524f29dc2.tar.gz
[util/malloc-stats] Do a single backtrace_symbols() call
I was hoping that this may speed things up, but it didn't. :(
Diffstat (limited to 'util/malloc-stats.c')
-rw-r--r--util/malloc-stats.c58
1 files changed, 50 insertions, 8 deletions
diff --git a/util/malloc-stats.c b/util/malloc-stats.c
index 74381fba0..ddf884929 100644
--- a/util/malloc-stats.c
+++ b/util/malloc-stats.c
@@ -136,6 +136,40 @@ resolve_addr (const void *addr) {
}
static void
+resolve_addrs (struct func_stat_t *func_stats, int num)
+{
+ int i;
+ void **addrs;
+ char **strings;
+
+ addrs = malloc (num * sizeof (void *));
+ for (i = 0; i < num; i++)
+ addrs[i] = (void *) func_stats[i].addr;
+
+ strings = backtrace_symbols (addrs, num);
+
+ for (i = 0; i < num; i++) {
+ char *p;
+ char *name;
+ int len;
+
+ p = strchr (strings[i], '\t');
+ if (p)
+ p++;
+ else
+ p = strings[i];
+
+ len = strlen (p) + 1;
+ name = _perm_alloc (len);
+ memcpy (name, p, len);
+ func_stats[i].name = name;
+ }
+
+ free (strings);
+ free (addrs);
+}
+
+static void
func_stats_add (const void *caller, int is_realloc, size_t size)
{
int i;
@@ -156,7 +190,7 @@ func_stats_add (const void *caller, int is_realloc, size_t size)
elt->next = func_stats[i];
func_stats[i] = elt;
elt->addr = caller;
- elt->name = resolve_addr (caller);
+ elt->name = NULL;
memset (&elt->stat, 0, sizeof (struct alloc_stats_t));
}
@@ -323,24 +357,30 @@ malloc_stats (void)
if (sorted_func_stats == NULL)
return;
- sorted_func_stats[0].next = NULL;
- sorted_func_stats[0].addr = (void *) -1;
- sorted_func_stats[0].name = "(total)";
- sorted_func_stats[0].stat = total_allocations;
-
- for (i = j = 0; i < ARRAY_SIZE (func_stats); i++) {
+ j = 0;
+ for (i = 0; i < ARRAY_SIZE (func_stats); i++) {
struct func_stat_t *elt;
for (elt = func_stats[i]; elt != NULL; elt = elt->next)
- sorted_func_stats[++j] = *elt;
+ sorted_func_stats[j++] = *elt;
}
+ resolve_addrs (sorted_func_stats, j);
+
/* merge entries with same name */
qsort (sorted_func_stats, j,
sizeof (struct func_stat_t), compare_func_stats_name);
j = merge_similar_entries (sorted_func_stats, j);
+
qsort (sorted_func_stats, j,
sizeof (struct func_stat_t), compare_func_stats);
+ /* add total */
+ sorted_func_stats[j].next = NULL;
+ sorted_func_stats[j].addr = (void *) -1;
+ sorted_func_stats[j].name = "(total)";
+ sorted_func_stats[j].stat = total_allocations;
+ j++;
+
setlocale (LC_ALL, "");
printf (" TOTAL MALLOC REALLOC\n");
@@ -351,5 +391,7 @@ malloc_stats (void)
sorted_func_stats[i].name);
}
+ /* XXX free other stuff? */
+
free (sorted_func_stats);
}