diff options
author | Kaz Kylheku <kaz@kylheku.com> | 2012-02-22 03:36:37 -0800 |
---|---|---|
committer | Kaz Kylheku <kaz@kylheku.com> | 2012-02-22 03:36:37 -0800 |
commit | 26f0db2ae285c260b18adf469511baad1bfee37b (patch) | |
tree | 9c9b0d3265f94dac399d2757da5d26cf5e3d6a35 | |
parent | 2868a7009f04a40d52c27503a0a4feb50da5c877 (diff) | |
download | txr-26f0db2ae285c260b18adf469511baad1bfee37b.tar.gz txr-26f0db2ae285c260b18adf469511baad1bfee37b.tar.bz2 txr-26f0db2ae285c260b18adf469511baad1bfee37b.zip |
* hash.c (remhash): Rewrote buggy function.
It was decrementing the hash count without checking that
something was deleted from the chain. The deletion was done
incorrectly, without regard for the kind of comparison fucntion
used by the hash table.
-rw-r--r-- | ChangeLog | 8 | ||||
-rw-r--r-- | hash.c | 12 |
2 files changed, 17 insertions, 3 deletions
@@ -1,5 +1,13 @@ 2012-02-22 Kaz Kylheku <kaz@kylheku.com> + * hash.c (remhash): Rewrote buggy function. + It was decrementing the hash count without checking that + something was deleted from the chain. The deletion was done + incorrectly, without regard for the kind of comparison fucntion + used by the hash table. + +2012-02-22 Kaz Kylheku <kaz@kylheku.com> + * eval.c (eval_init): Intrinsic bindings for sub, ref, refset and replace. @@ -342,9 +342,15 @@ val remhash(val hash, val key) { struct hash *h = (struct hash *) cobj_handle(hash, hash_s); val *pchain = vecref_l(h->table, num(h->hash_fun(key) % h->modulus)); - *pchain = alist_remove1(*pchain, key); - h->count--; - bug_unless (h->count >= 0); + val existing = h->assoc_fun(key, *pchain); + + if (existing) { + val loc = memq(existing, *pchain); + *pchain = nappend2(ldiff(*pchain, loc), cdr(loc)); + h->count--; + bug_unless (h->count >= 0); + } + return nil; } |