diff options
author | Branko Čibej <brane@apache.org> | 2004-11-14 12:00:24 +0000 |
---|---|---|
committer | Branko Čibej <brane@apache.org> | 2004-11-14 12:00:24 +0000 |
commit | 0d96d5f5511d1706cee142da29b84fe89e8719d4 (patch) | |
tree | 53108ad89881c9752fcb77dba2dfb3779fa1d025 | |
parent | 747393534563411cdd649633bf2a4651468cd292 (diff) | |
download | apr-0d96d5f5511d1706cee142da29b84fe89e8719d4.tar.gz |
Merged trunk r65572 to APU_0_9_BRANCH.
git-svn-id: https://svn.apache.org/repos/asf/apr/apr/branches/APR_0_9_BRANCH@65594 13f79535-47bb-0310-9956-ffa450edef68
-rw-r--r-- | CHANGES | 3 | ||||
-rw-r--r-- | tables/apr_hash.c | 12 |
2 files changed, 14 insertions, 1 deletions
@@ -1,5 +1,8 @@ Changes with APR 0.9.5 + *) Prevent unbounded memory use during repeated operations on a hash table. + [Julian Foad <julianfoad btopenworld.com> + *) fix apr_file_dup and apr_file_dup2 win32 implementations to create a mutex [Steve Hay <steve.hay uk.radan.com>] diff --git a/tables/apr_hash.c b/tables/apr_hash.c index 42a860d35..b06ecb942 100644 --- a/tables/apr_hash.c +++ b/tables/apr_hash.c @@ -72,6 +72,7 @@ struct apr_hash_t { apr_hash_entry_t **array; apr_hash_index_t iterator; /* For apr_hash_first(NULL, ...) */ unsigned int count, max; + apr_hash_entry_t *free; /* List of recycled entries */ }; #define INITIAL_MAX 15 /* tunable == 2^n - 1 */ @@ -91,6 +92,7 @@ APR_DECLARE(apr_hash_t *) apr_hash_make(apr_pool_t *pool) apr_hash_t *ht; ht = apr_palloc(pool, sizeof(apr_hash_t)); ht->pool = pool; + ht->free = NULL; ht->count = 0; ht->max = INITIAL_MAX; ht->array = alloc_array(ht, ht->max); @@ -243,7 +245,10 @@ static apr_hash_entry_t **find_entry(apr_hash_t *ht, return hep; /* add a new entry for non-NULL values */ - he = apr_palloc(ht->pool, sizeof(*he)); + if (he = ht->free) + ht->free = he->next; + else + he = apr_palloc(ht->pool, sizeof(*he)); he->next = NULL; he->hash = hash; he->key = key; @@ -265,6 +270,7 @@ APR_DECLARE(apr_hash_t *) apr_hash_copy(apr_pool_t *pool, sizeof(*ht->array) * (orig->max + 1) + sizeof(apr_hash_entry_t) * orig->count); ht->pool = pool; + ht->free = NULL; ht->count = orig->count; ht->max = orig->max; ht->array = (apr_hash_entry_t **)((char *)ht + sizeof(apr_hash_t)); @@ -311,7 +317,10 @@ APR_DECLARE(void) apr_hash_set(apr_hash_t *ht, if (*hep) { if (!val) { /* delete entry */ + apr_hash_entry_t *old = *hep; *hep = (*hep)->next; + old->next = ht->free; + ht->free = old; --ht->count; } else { @@ -374,6 +383,7 @@ APR_DECLARE(apr_hash_t *) apr_hash_merge(apr_pool_t *p, res = apr_palloc(p, sizeof(apr_hash_t)); res->pool = p; + res->free = NULL; res->count = base->count; res->max = (overlay->max > base->max) ? overlay->max : base->max; if (base->count + overlay->count > res->max) { |