diff options
author | Panu Matilainen <pmatilai@redhat.com> | 2012-09-12 16:47:43 +0300 |
---|---|---|
committer | Panu Matilainen <pmatilai@redhat.com> | 2012-09-12 19:17:20 +0300 |
commit | 06546854933d0d7682bffbdf11c50c1efde17045 (patch) | |
tree | b20ade2fd5d4e73ac875aee9a2c45aed250381ed /rpmio | |
parent | 86dbb8844807b077f27255cccc9c0714a0005d02 (diff) | |
download | librpm-tizen-06546854933d0d7682bffbdf11c50c1efde17045.tar.gz librpm-tizen-06546854933d0d7682bffbdf11c50c1efde17045.tar.bz2 librpm-tizen-06546854933d0d7682bffbdf11c50c1efde17045.zip |
Allow keeping hash table around on pool freeze, adjust callers
- Pool id -> string always works with a frozen pool, but in some cases
we'll need to go the other way, allow caller to specify whether
string -> id lookups should be possible on frozen pool.
- On glibc, realloc() to smaller size doesn't move the data but on
other platforms (including valgrind) it can and does move, which
would require a full rehash. For now, just leave all the data
alone unless we're also freeing the hash, the memory savings
isn't much for a global pool (which is where this matters)
Diffstat (limited to 'rpmio')
-rw-r--r-- | rpmio/rpmstrpool.c | 43 | ||||
-rw-r--r-- | rpmio/rpmstrpool.h | 4 |
2 files changed, 29 insertions, 18 deletions
diff --git a/rpmio/rpmstrpool.c b/rpmio/rpmstrpool.c index 38b676c03..5792471d8 100644 --- a/rpmio/rpmstrpool.c +++ b/rpmio/rpmstrpool.c @@ -25,6 +25,7 @@ struct rpmstrPool_s { size_t data_size; /* string data area size */ size_t data_alloced; /* string data area allocation size */ strHash hash; /* string -> sid hash table */ + int frozen; /* are new id additions allowed? */ int nrefs; /* refcount */ }; @@ -58,28 +59,38 @@ rpmstrPool rpmstrPoolLink(rpmstrPool pool) return pool; } -void rpmstrPoolFreeze(rpmstrPool pool) +void rpmstrPoolFreeze(rpmstrPool pool, int keephash) { - if (pool && pool->hash) { - pool->hash = strHashFree(pool->hash); - pool->data_alloced = pool->data_size; - pool->data = xrealloc(pool->data, pool->data_alloced); - pool->offs_alloced = pool->offs_size + 1; - pool->offs = xrealloc(pool->offs, - pool->offs_alloced * sizeof(*pool->offs)); + if (pool && !pool->frozen) { + /* + * realloc() might require rehashing even when downsizing, + * dont bother unless we're also discarding the hash. + */ + if (!keephash) { + pool->hash = strHashFree(pool->hash); + pool->data_alloced = pool->data_size; + pool->data = xrealloc(pool->data, pool->data_alloced); + pool->offs_alloced = pool->offs_size + 1; + pool->offs = xrealloc(pool->offs, + pool->offs_alloced * sizeof(*pool->offs)); + } + pool->frozen = 1; } } void rpmstrPoolUnfreeze(rpmstrPool pool) { - if (pool && pool->hash == NULL) { - int sizehint = (pool->offs_size / 2) - 1; - if (sizehint < STRHASH_INITSIZE) - sizehint = STRHASH_INITSIZE; - pool->hash = strHashCreate(sizehint, rstrhash, strcmp, NULL, NULL); - for (int i = 1; i < pool->offs_size; i++) { - strHashAddEntry(pool->hash, rpmstrPoolStr(pool, i), i); + if (pool) { + if (pool->hash == NULL) { + int sizehint = (pool->offs_size / 2) - 1; + if (sizehint < STRHASH_INITSIZE) + sizehint = STRHASH_INITSIZE; + pool->hash = strHashCreate(sizehint, rstrhash, strcmp, NULL, NULL); + for (int i = 1; i < pool->offs_size; i++) { + strHashAddEntry(pool->hash, rpmstrPoolStr(pool, i), i); + } } + pool->frozen = 0; } } @@ -130,7 +141,7 @@ rpmsid rpmstrPoolIdn(rpmstrPool pool, const char *s, size_t slen, int create) rpmsid *sids; if (strHashGetHEntry(pool->hash, s, hash, &sids, NULL, NULL)) { sid = sids[0]; - } else if (create) { + } else if (create && !pool->frozen) { sid = rpmstrPoolPut(pool, s, slen, hash); } } diff --git a/rpmio/rpmstrpool.h b/rpmio/rpmstrpool.h index 958a47033..67e162056 100644 --- a/rpmio/rpmstrpool.h +++ b/rpmio/rpmstrpool.h @@ -18,8 +18,8 @@ rpmstrPool rpmstrPoolFree(rpmstrPool sidpool); /* reference a string pool */ rpmstrPool rpmstrPoolLink(rpmstrPool sidpool); -/* freeze pool to free memory */ -void rpmstrPoolFreeze(rpmstrPool sidpool); +/* freeze pool to free memory (keephash required for string -> id lookups) */ +void rpmstrPoolFreeze(rpmstrPool sidpool, int keephash); /* unfreeze pool (ie recreate hash table) */ void rpmstrPoolUnfreeze(rpmstrPool sidpool); |