diff options
-rw-r--r-- | src/gallium/auxiliary/cso_cache/cso_hash.c | 25 | ||||
-rw-r--r-- | src/gallium/auxiliary/cso_cache/cso_hash.h | 16 |
2 files changed, 36 insertions, 5 deletions
diff --git a/src/gallium/auxiliary/cso_cache/cso_hash.c b/src/gallium/auxiliary/cso_cache/cso_hash.c index 5cad5d3be71..ddce3822f7f 100644 --- a/src/gallium/auxiliary/cso_cache/cso_hash.c +++ b/src/gallium/auxiliary/cso_cache/cso_hash.c @@ -99,7 +99,7 @@ static void *cso_data_allocate_node(struct cso_hash_data *hash) return MALLOC(hash->nodeSize); } -static void cso_data_free_node(struct cso_node *node) +static void cso_free_node(struct cso_node *node) { FREE(node); } @@ -248,7 +248,7 @@ void cso_hash_delete(struct cso_hash *hash) struct cso_node *cur = *bucket++; while (cur != e_for_x) { struct cso_node *next = cur->next; - cso_data_free_node(cur); + cso_free_node(cur); cur = next; } } @@ -367,7 +367,7 @@ void * cso_hash_take(struct cso_hash *hash, if (*node != hash->data.e) { void *t = (*node)->value; struct cso_node *next = (*node)->next; - cso_data_free_node(*node); + cso_free_node(*node); *node = next; --hash->data.d->size; cso_data_has_shrunk(hash->data.d); @@ -393,3 +393,22 @@ int cso_hash_size(struct cso_hash *hash) { return hash->data.d->size; } + +struct cso_hash_iter cso_hash_erase(struct cso_hash *hash, struct cso_hash_iter iter) +{ + struct cso_hash_iter ret = iter; + struct cso_node *node = iter.node; + struct cso_node **node_ptr; + + if (node == hash->data.e) + return iter; + + ret = cso_hash_iter_next(ret); + node_ptr = (struct cso_node**)(&hash->data.d->buckets[node->key % hash->data.d->numBuckets]); + while (*node_ptr != node) + node_ptr = &(*node_ptr)->next; + *node_ptr = node->next; + cso_free_node(node); + --hash->data.d->size; + return ret; +} diff --git a/src/gallium/auxiliary/cso_cache/cso_hash.h b/src/gallium/auxiliary/cso_cache/cso_hash.h index a3a65b68c84..73c47420068 100644 --- a/src/gallium/auxiliary/cso_cache/cso_hash.h +++ b/src/gallium/auxiliary/cso_cache/cso_hash.h @@ -68,14 +68,26 @@ int cso_hash_size(struct cso_hash *hash); /** - * Create a list of objects and just add entry with the same key to the list. + * Adds a data with the given key to the hash. If entry with the given + * key is already in the hash, this current entry is instered before it + * in the collision list. + * Function returns iterator pointing to the inserted item in the hash. */ struct cso_hash_iter cso_hash_insert(struct cso_hash *hash, unsigned key, void *data); +/** + * Removes the item pointed to by the current iterator from the hash. + * Note that the data itself is not erased and if it was a malloc'ed pointer + * it will have to be freed after calling this function by the callee. + * Function returns iterator pointing to the item after the removed one in + * the hash. + */ +struct cso_hash_iter cso_hash_erase(struct cso_hash *hash, struct cso_hash_iter iter); void *cso_hash_take(struct cso_hash *hash, unsigned key); + struct cso_hash_iter cso_hash_first_node(struct cso_hash *hash); /** @@ -97,7 +109,7 @@ struct cso_hash_iter cso_hash_iter_prev(struct cso_hash_iter iter); * Convenience routine to iterate over the collision list while doing a memory * comparison to see which entry in the list is a direct copy of our template * and returns that entry. - */ + */ void *cso_hash_find_data_from_template( struct cso_hash *hash, unsigned hash_key, void *templ, |