Commit 9e92552b authored by Rusty Russell's avatar Rusty Russell

htable: reduce size of htable by calculating max every time.

Signed-off-by: default avatarRusty Russell <rusty@rustcorp.com.au>
parent 2b3517d4
...@@ -78,11 +78,14 @@ void htable_init(struct htable *ht, ...@@ -78,11 +78,14 @@ void htable_init(struct htable *ht,
ht->table = &ht->perfect_bit; ht->table = &ht->perfect_bit;
} }
/* We've changed ht->bits, update ht->max and ht->max_with_deleted */ static inline size_t ht_max(const struct htable *ht)
static void htable_adjust_capacity(struct htable *ht)
{ {
ht->max = ((size_t)3 << ht->bits) / 4; return ((size_t)3 << ht->bits) / 4;
ht->max_with_deleted = ((size_t)9 << ht->bits) / 10; }
static inline size_t ht_max_with_deleted(const struct htable *ht)
{
return ((size_t)9 << ht->bits) / 10;
} }
bool htable_init_sized(struct htable *ht, bool htable_init_sized(struct htable *ht,
...@@ -102,7 +105,6 @@ bool htable_init_sized(struct htable *ht, ...@@ -102,7 +105,6 @@ bool htable_init_sized(struct htable *ht,
ht->table = &ht->perfect_bit; ht->table = &ht->perfect_bit;
return false; return false;
} }
htable_adjust_capacity(ht);
(void)htable_debug(ht, HTABLE_LOC); (void)htable_debug(ht, HTABLE_LOC);
return true; return true;
} }
...@@ -219,7 +221,6 @@ static COLD bool double_table(struct htable *ht) ...@@ -219,7 +221,6 @@ static COLD bool double_table(struct htable *ht)
return false; return false;
} }
ht->bits++; ht->bits++;
htable_adjust_capacity(ht);
/* If we lost our "perfect bit", get it back now. */ /* If we lost our "perfect bit", get it back now. */
if (!ht->perfect_bit && ht->common_mask) { if (!ht->perfect_bit && ht->common_mask) {
...@@ -318,9 +319,9 @@ static COLD void update_common(struct htable *ht, const void *p) ...@@ -318,9 +319,9 @@ static COLD void update_common(struct htable *ht, const void *p)
bool htable_add_(struct htable *ht, size_t hash, const void *p) bool htable_add_(struct htable *ht, size_t hash, const void *p)
{ {
if (ht->elems+1 > ht->max && !double_table(ht)) if (ht->elems+1 > ht_max(ht) && !double_table(ht))
return false; return false;
if (ht->elems+1 + ht->deleted > ht->max_with_deleted) if (ht->elems+1 + ht->deleted > ht_max_with_deleted(ht))
rehash_table(ht); rehash_table(ht);
assert(p); assert(p);
if (((uintptr_t)p & ht->common_mask) != ht->common_bits) if (((uintptr_t)p & ht->common_mask) != ht->common_bits)
......
...@@ -25,7 +25,7 @@ struct htable { ...@@ -25,7 +25,7 @@ struct htable {
size_t (*rehash)(const void *elem, void *priv); size_t (*rehash)(const void *elem, void *priv);
void *priv; void *priv;
unsigned int bits; unsigned int bits;
size_t elems, deleted, max, max_with_deleted; size_t elems, deleted;
/* These are the bits which are the same in all pointers. */ /* These are the bits which are the same in all pointers. */
uintptr_t common_mask, common_bits; uintptr_t common_mask, common_bits;
uintptr_t perfect_bit; uintptr_t perfect_bit;
...@@ -50,7 +50,7 @@ struct htable { ...@@ -50,7 +50,7 @@ struct htable {
* static struct htable ht = HTABLE_INITIALIZER(ht, rehash, NULL); * static struct htable ht = HTABLE_INITIALIZER(ht, rehash, NULL);
*/ */
#define HTABLE_INITIALIZER(name, rehash, priv) \ #define HTABLE_INITIALIZER(name, rehash, priv) \
{ rehash, priv, 0, 0, 0, 0, 0, -1, 0, 0, &name.perfect_bit } { rehash, priv, 0, 0, 0, -1, 0, 0, &name.perfect_bit }
/** /**
* htable_init - initialize an empty hash table. * htable_init - initialize an empty hash table.
......
...@@ -28,8 +28,8 @@ int main(void) ...@@ -28,8 +28,8 @@ int main(void)
htable_init(&ht, hash, NULL); htable_init(&ht, hash, NULL);
for (i = 0; i < NUM_VALS; i++) { for (i = 0; i < NUM_VALS; i++) {
ok1(ht.max >= i); ok1(ht_max(&ht) >= i);
ok1(ht.max <= i * 2); ok1(ht_max(&ht) <= i * 2);
htable_add(&ht, hash(&val[i], NULL), &val[i]); htable_add(&ht, hash(&val[i], NULL), &val[i]);
} }
......
...@@ -121,7 +121,7 @@ int main(void) ...@@ -121,7 +121,7 @@ int main(void)
dne = i; dne = i;
htable_init(&ht, hash, NULL); htable_init(&ht, hash, NULL);
ok1(ht.max == 0); ok1(ht_max(&ht) == 0);
ok1(ht.bits == 0); ok1(ht.bits == 0);
/* We cannot find an entry which doesn't exist. */ /* We cannot find an entry which doesn't exist. */
...@@ -130,7 +130,7 @@ int main(void) ...@@ -130,7 +130,7 @@ int main(void)
/* This should increase it once. */ /* This should increase it once. */
add_vals(&ht, val, 0, 1); add_vals(&ht, val, 0, 1);
ok1(ht.bits == 1); ok1(ht.bits == 1);
ok1(ht.max == 1); ok1(ht_max(&ht) == 1);
weight = 0; weight = 0;
for (i = 0; i < sizeof(ht.common_mask) * CHAR_BIT; i++) { for (i = 0; i < sizeof(ht.common_mask) * CHAR_BIT; i++) {
if (ht.common_mask & ((uintptr_t)1 << i)) { if (ht.common_mask & ((uintptr_t)1 << i)) {
...@@ -146,7 +146,7 @@ int main(void) ...@@ -146,7 +146,7 @@ int main(void)
/* This should increase it again. */ /* This should increase it again. */
add_vals(&ht, val, 1, 1); add_vals(&ht, val, 1, 1);
ok1(ht.bits == 2); ok1(ht.bits == 2);
ok1(ht.max == 3); ok1(ht_max(&ht) == 3);
/* Mask should be set. */ /* Mask should be set. */
ok1(ht.common_mask != 0); ok1(ht.common_mask != 0);
...@@ -208,15 +208,15 @@ int main(void) ...@@ -208,15 +208,15 @@ int main(void)
htable_clear(&ht); htable_clear(&ht);
ok1(htable_init_sized(&ht, hash, NULL, 1024)); ok1(htable_init_sized(&ht, hash, NULL, 1024));
ok1(ht.max >= 1024); ok1(ht_max(&ht) >= 1024);
htable_clear(&ht); htable_clear(&ht);
ok1(htable_init_sized(&ht, hash, NULL, 1023)); ok1(htable_init_sized(&ht, hash, NULL, 1023));
ok1(ht.max >= 1023); ok1(ht_max(&ht) >= 1023);
htable_clear(&ht); htable_clear(&ht);
ok1(htable_init_sized(&ht, hash, NULL, 1025)); ok1(htable_init_sized(&ht, hash, NULL, 1025));
ok1(ht.max >= 1025); ok1(ht_max(&ht) >= 1025);
htable_clear(&ht); htable_clear(&ht);
return exit_status(); return exit_status();
......
...@@ -26,8 +26,8 @@ int main(void) ...@@ -26,8 +26,8 @@ int main(void)
htable_init(&ht, hash, NULL); htable_init(&ht, hash, NULL);
for (i = 0; i < NUM_VALS; i++) { for (i = 0; i < NUM_VALS; i++) {
ok1(ht.max >= i); ok1(ht_max(&ht) >= i);
ok1(ht.max <= i * 2); ok1(ht_max(&ht) <= i * 2);
htable_add(&ht, hash(&val[i], NULL), &val[i]); htable_add(&ht, hash(&val[i], NULL), &val[i]);
} }
htable_clear(&ht); htable_clear(&ht);
......
...@@ -127,7 +127,7 @@ int main(void) ...@@ -127,7 +127,7 @@ int main(void)
dne = i; dne = i;
htable_obj_init(&ht); htable_obj_init(&ht);
ok1(ht.raw.max == 0); ok1(ht_max(&ht.raw) == 0);
ok1(ht.raw.bits == 0); ok1(ht.raw.bits == 0);
/* We cannot find an entry which doesn't exist. */ /* We cannot find an entry which doesn't exist. */
...@@ -136,7 +136,7 @@ int main(void) ...@@ -136,7 +136,7 @@ int main(void)
/* Fill it, it should increase in size. */ /* Fill it, it should increase in size. */
add_vals(&ht, val, NUM_VALS); add_vals(&ht, val, NUM_VALS);
ok1(ht.raw.bits == NUM_BITS + 1); ok1(ht.raw.bits == NUM_BITS + 1);
ok1(ht.raw.max < (1 << ht.raw.bits)); ok1(ht_max(&ht.raw) < (1 << ht.raw.bits));
/* Mask should be set. */ /* Mask should be set. */
ok1(ht.raw.common_mask != 0); ok1(ht.raw.common_mask != 0);
......
...@@ -122,7 +122,7 @@ int main(void) ...@@ -122,7 +122,7 @@ int main(void)
dne = i; dne = i;
htable_obj_init(&ht); htable_obj_init(&ht);
ok1(ht.raw.max == 0); ok1(ht_max(&ht.raw) == 0);
ok1(ht.raw.bits == 0); ok1(ht.raw.bits == 0);
/* We cannot find an entry which doesn't exist. */ /* We cannot find an entry which doesn't exist. */
...@@ -131,7 +131,7 @@ int main(void) ...@@ -131,7 +131,7 @@ int main(void)
/* Fill it, it should increase in size. */ /* Fill it, it should increase in size. */
add_vals(&ht, val, NUM_VALS); add_vals(&ht, val, NUM_VALS);
ok1(ht.raw.bits == NUM_BITS + 1); ok1(ht.raw.bits == NUM_BITS + 1);
ok1(ht.raw.max < (1 << ht.raw.bits)); ok1(ht_max(&ht.raw) < (1 << ht.raw.bits));
/* Mask should be set. */ /* Mask should be set. */
ok1(ht.raw.common_mask != 0); ok1(ht.raw.common_mask != 0);
......
...@@ -111,7 +111,7 @@ int main(void) ...@@ -111,7 +111,7 @@ int main(void)
dne = i; dne = i;
htable_init(&ht, hash, NULL); htable_init(&ht, hash, NULL);
ok1(ht.max == 0); ok1(ht_max(&ht) == 0);
ok1(ht.bits == 0); ok1(ht.bits == 0);
/* We cannot find an entry which doesn't exist. */ /* We cannot find an entry which doesn't exist. */
...@@ -120,7 +120,7 @@ int main(void) ...@@ -120,7 +120,7 @@ int main(void)
/* This should increase it once. */ /* This should increase it once. */
add_vals(&ht, val, 0, 1); add_vals(&ht, val, 0, 1);
ok1(ht.bits == 1); ok1(ht.bits == 1);
ok1(ht.max == 1); ok1(ht_max(&ht) == 1);
weight = 0; weight = 0;
for (i = 0; i < sizeof(ht.common_mask) * CHAR_BIT; i++) { for (i = 0; i < sizeof(ht.common_mask) * CHAR_BIT; i++) {
if (ht.common_mask & ((uintptr_t)1 << i)) { if (ht.common_mask & ((uintptr_t)1 << i)) {
...@@ -136,7 +136,7 @@ int main(void) ...@@ -136,7 +136,7 @@ int main(void)
/* This should increase it again. */ /* This should increase it again. */
add_vals(&ht, val, 1, 1); add_vals(&ht, val, 1, 1);
ok1(ht.bits == 2); ok1(ht.bits == 2);
ok1(ht.max == 3); ok1(ht_max(&ht) == 3);
/* Mask should be set. */ /* Mask should be set. */
ok1(ht.common_mask != 0); ok1(ht.common_mask != 0);
...@@ -197,15 +197,15 @@ int main(void) ...@@ -197,15 +197,15 @@ int main(void)
htable_clear(&ht); htable_clear(&ht);
ok1(htable_init_sized(&ht, hash, NULL, 1024)); ok1(htable_init_sized(&ht, hash, NULL, 1024));
ok1(ht.max >= 1024); ok1(ht_max(&ht) >= 1024);
htable_clear(&ht); htable_clear(&ht);
ok1(htable_init_sized(&ht, hash, NULL, 1023)); ok1(htable_init_sized(&ht, hash, NULL, 1023));
ok1(ht.max >= 1023); ok1(ht_max(&ht) >= 1023);
htable_clear(&ht); htable_clear(&ht);
ok1(htable_init_sized(&ht, hash, NULL, 1025)); ok1(htable_init_sized(&ht, hash, NULL, 1025));
ok1(ht.max >= 1025); ok1(ht_max(&ht) >= 1025);
htable_clear(&ht); htable_clear(&ht);
return exit_status(); return exit_status();
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment