diff options
author | Soren Sandmann <sandmann@daimi.au.dk> | 2006-11-20 07:25:02 +0000 |
---|---|---|
committer | Søren Sandmann Pedersen <ssp@src.gnome.org> | 2006-11-20 07:25:02 +0000 |
commit | d1a082ffec6f2e4f40ae9afbed10689d122f6c64 (patch) | |
tree | 8e0e5a222b8f7e71ddf3d49ba474caea2979a76a /stackstash.c | |
parent | cce917856b7c7c1ab47deeae4639c0289efb9a48 (diff) |
reset the collector after generating the profile.
2006-11-20 Soren Sandmann <sandmann@daimi.au.dk>
* sysprof.c (ensure_profile): reset the collector after generating
the profile.
* stackstash.c (struct StackStash): Add cached_nodes and blocks.
(stack_node_new): Allocate stack nodes in blocks.
Diffstat (limited to 'stackstash.c')
-rw-r--r-- | stackstash.c | 104 |
1 files changed, 63 insertions, 41 deletions
diff --git a/stackstash.c b/stackstash.c index dd09069..1844946 100644 --- a/stackstash.c +++ b/stackstash.c @@ -25,12 +25,36 @@ struct StackStash StackNode * root; GHashTable * nodes_by_data; GDestroyNotify destroy; + + StackNode * cached_nodes; + GPtrArray * blocks; }; StackNode * -stack_node_new (void) +stack_node_new (StackStash *stash) { - StackNode *node = g_new (StackNode, 1); + StackNode *node; + + if (!stash->cached_nodes) + { +#define BLOCK_SIZE 32768 +#define N_NODES (BLOCK_SIZE / sizeof (StackNode)) + + StackNode *block = g_malloc (BLOCK_SIZE); + int i; + + for (i = 0; i < N_NODES; ++i) + { + block[i].next = stash->cached_nodes; + stash->cached_nodes = &(block[i]); + } + + g_ptr_array_add (stash->blocks, block); + } + + node = stash->cached_nodes; + stash->cached_nodes = node->next; + node->siblings = NULL; node->children = NULL; node->address = NULL; @@ -38,6 +62,7 @@ stack_node_new (void) node->size = 0; node->next = NULL; node->total = 0; + return node; } @@ -51,6 +76,9 @@ create_stack_stash (GDestroyNotify destroy) stash->nodes_by_data = g_hash_table_new (g_direct_hash, g_direct_equal); stash->ref_count = 1; stash->destroy = destroy; + + stash->cached_nodes = NULL; + stash->blocks = g_ptr_array_new (); return stash; } @@ -62,6 +90,38 @@ stack_stash_new (GDestroyNotify destroy) return create_stack_stash (destroy); } + +static void +free_key (gpointer key, + gpointer value, + gpointer data) +{ + GDestroyNotify destroy = data; + + destroy (key); +} + +static void +stack_stash_free (StackStash *stash) +{ + int i; + + if (stash->destroy) + { + g_hash_table_foreach (stash->nodes_by_data, free_key, + stash->destroy); + } + + g_hash_table_destroy (stash->nodes_by_data); + + for (i = 0; i < stash->blocks->len; ++i) + g_free (stash->blocks->pdata[i]); + + g_ptr_array_free (stash->blocks, TRUE); + + g_free (stash); +} + static void decorate_node (StackStash *stash, StackNode *node) @@ -118,7 +178,7 @@ stack_stash_add_trace (StackStash *stash, if (!match) { - match = stack_node_new (); + match = stack_node_new (stash); match->address = (gpointer)addrs[i]; match->siblings = *location; match->parent = parent; @@ -186,44 +246,6 @@ stack_node_foreach_trace (StackNode *node, do_callback (node->children, &link, func, data); } -static void -stack_node_free (StackNode *node) -{ - if (!node) - return; - - stack_node_free (node->siblings); - stack_node_free (node->children); - - g_free (node); -} - -static void -free_key (gpointer key, - gpointer value, - gpointer data) -{ - GDestroyNotify destroy = data; - - destroy (key); -} - -static void -stack_stash_free (StackStash *stash) -{ - stack_node_free (stash->root); - - if (stash->destroy) - { - g_hash_table_foreach (stash->nodes_by_data, free_key, - stash->destroy); - } - - g_hash_table_destroy (stash->nodes_by_data); - - g_free (stash); -} - void stack_stash_unref (StackStash *stash) { |