From e041252f788d80c53d91696b5bfc37cb47ccda54 Mon Sep 17 00:00:00 2001 From: Simo Sorce Date: Tue, 8 Dec 2009 14:05:22 -0500 Subject: dhash: Add private pointer for delete callback Also pass a flag to the delete callback to tell it if this is a normal entry removal or we are cleaning up the tbale definitively. --- common/dhash/dhash.c | 23 +++++++++++++++++------ common/dhash/dhash.h | 15 ++++++++++++--- common/dhash/dhash_example.c | 5 +++-- common/dhash/dhash_test.c | 5 +++-- server/responder/common/responder_dp.c | 2 +- server/util/find_uid.c | 3 ++- 6 files changed, 38 insertions(+), 15 deletions(-) diff --git a/common/dhash/dhash.c b/common/dhash/dhash.c index 07815ec80..fb024c85e 100644 --- a/common/dhash/dhash.c +++ b/common/dhash/dhash.c @@ -36,6 +36,11 @@ #define halloc(table, size) table->halloc(size, table->halloc_pvt) #define hfree(table, ptr) table->hfree(ptr, table->halloc_pvt) +#define hdelete_callback(table, type, entry) do { \ + if (table->delete_callback) { \ + table->delete_callback(entry, type, table->delete_pvt); \ + } \ +} while(0) /*****************************************************************************/ /************************** Internal Type Definitions ************************/ @@ -59,7 +64,8 @@ struct hash_table_str { unsigned int directory_size_shift; unsigned long segment_size; unsigned int segment_size_shift; - hash_delete_callback delete_callback; + hash_delete_callback *delete_callback; + void *delete_pvt; hash_alloc_func *halloc; hash_free_func *hfree; void *halloc_pvt; @@ -457,10 +463,13 @@ const char* hash_error_string(int error) int hash_create(unsigned long count, hash_table_t **tbl, - hash_delete_callback delete_callback) + hash_delete_callback *delete_callback, + void *delete_private_data) { return hash_create_ex(count, tbl, 0, 0, 0, 0, - NULL, NULL, NULL, delete_callback); + NULL, NULL, NULL, + delete_callback, + delete_private_data); } int hash_create_ex(unsigned long count, hash_table_t **tbl, @@ -471,7 +480,8 @@ int hash_create_ex(unsigned long count, hash_table_t **tbl, hash_alloc_func *alloc_func, hash_free_func *free_func, void *alloc_private_data, - hash_delete_callback delete_callback) + hash_delete_callback *delete_callback, + void *delete_private_data) { unsigned long i; unsigned int n_addr_bits; @@ -526,6 +536,7 @@ int hash_create_ex(unsigned long count, hash_table_t **tbl, table->p = 0; table->entry_count = 0; table->delete_callback = delete_callback; + table->delete_pvt = delete_private_data; /* * Allocate initial 'i' segments of buckets @@ -585,7 +596,7 @@ int hash_destroy(hash_table_t *table) p = s[j]; while (p != NULL) { q = p->next; - if (table->delete_callback) table->delete_callback(&p->entry); + hdelete_callback(table, HASH_TABLE_DESTROY, &p->entry); if (p->entry.key.type == HASH_KEY_STRING) { hfree(table, (char *)p->entry.key.str); } @@ -935,7 +946,7 @@ int hash_delete(hash_table_t *table, hash_key_t *key) lookup(table, key, &element, &chain); if (element) { - if (table->delete_callback) table->delete_callback(&element->entry); + hdelete_callback(table, HASH_ENTRY_DESTROY, &element->entry); *chain = element->next; /* remove from chain */ /* * Table too sparse? diff --git a/common/dhash/dhash.h b/common/dhash/dhash.h index a8b0d83f6..72b054e8e 100644 --- a/common/dhash/dhash.h +++ b/common/dhash/dhash.h @@ -97,6 +97,12 @@ typedef enum HASH_VALUE_DOUBLE } hash_value_enum; +typedef enum +{ + HASH_TABLE_DESTROY, + HASH_ENTRY_DESTROY +} hash_destroy_enum; + typedef struct hash_key_t { hash_key_enum type; union { @@ -135,7 +141,8 @@ typedef struct hash_statistics_t { /* typedef's for callback based iteration */ typedef bool(*hash_iterate_callback)(hash_entry_t *item, void *user_data); -typedef void (*hash_delete_callback)(hash_entry_t *item); +typedef void (hash_delete_callback)(hash_entry_t *item, + hash_destroy_enum type, void *pvt); /* typedef's for iteration object based iteration */ struct hash_iter_context_t; @@ -172,7 +179,8 @@ const char* hash_error_string(int error); * may need to be disposed of. The delete_callback may be NULL. */ int hash_create(unsigned long count, hash_table_t **tbl, - hash_delete_callback delete_callback); + hash_delete_callback *delete_callback, + void *delete_private_data); /* * Create a new hash table and fine tune it's configurable parameters. @@ -197,7 +205,8 @@ int hash_create_ex(unsigned long count, hash_table_t **tbl, hash_alloc_func *alloc_func, hash_free_func *free_func, void *alloc_private_data, - hash_delete_callback delete_callback); + hash_delete_callback *delete_callback, + void *delete_private_data); #ifdef HASH_STATISTICS /* diff --git a/common/dhash/dhash_example.c b/common/dhash/dhash_example.c index b7de62356..7ed01d71a 100644 --- a/common/dhash/dhash_example.c +++ b/common/dhash/dhash_example.c @@ -9,7 +9,7 @@ struct my_data_t { char bar[128]; }; -void delete_callback(hash_entry_t *entry) +void delete_callback(hash_entry_t *entry, hash_destroy_enum type, void *pvt) { if (entry->value.type == HASH_VALUE_PTR) free(entry->value.ptr); } @@ -45,7 +45,8 @@ int main(int argc, char **argv) unsigned long count; /* Create a hash table */ - if ((error = hash_create(10, &table, delete_callback)) != HASH_SUCCESS) { + error = hash_create(10, &table, delete_callback, NULL); + if (error != HASH_SUCCESS) { fprintf(stderr, "cannot create hash table (%s)\n", hash_error_string(error)); return error; } diff --git a/common/dhash/dhash_test.c b/common/dhash/dhash_test.c index fedfa66a2..27eb88d52 100644 --- a/common/dhash/dhash_test.c +++ b/common/dhash/dhash_test.c @@ -98,7 +98,7 @@ bool callback(hash_entry_t *item, void *user_data) return true; } -void delete_callback(hash_entry_t *item) +void delete_callback(hash_entry_t *item, hash_destroy_enum type, void *pvt) { if (item->value.type == HASH_VALUE_PTR) free(item->value.ptr); } @@ -188,7 +188,8 @@ int main(int argc, char **argv) if ((status = hash_create_ex(1, &table, directory_bits, segment_bits, min_load_factor, max_load_factor, - NULL, NULL, NULL, delete_callback)) != HASH_SUCCESS) { + NULL, NULL, NULL, + delete_callback, NULL)) != HASH_SUCCESS) { fprintf(stderr, "table creation failed at line %d (%s)\n", __LINE__, error_string(status)); exit(1); } diff --git a/server/responder/common/responder_dp.c b/server/responder/common/responder_dp.c index 1fe1d95ec..305f6d8fa 100644 --- a/server/responder/common/responder_dp.c +++ b/server/responder/common/responder_dp.c @@ -286,7 +286,7 @@ int sss_dp_send_acct_req(struct resp_ctx *rctx, TALLOC_CTX *callback_memctx, if (dp_requests == NULL) { /* Create a hash table to handle queued update requests */ - ret = hash_create(10, &dp_requests, NULL); + ret = hash_create(10, &dp_requests, NULL, NULL); if (ret != HASH_SUCCESS) { fprintf(stderr, "cannot create hash table (%s)\n", hash_error_string(ret)); return EIO; diff --git a/server/util/find_uid.c b/server/util/find_uid.c index 09c47b3d8..63907f17a 100644 --- a/server/util/find_uid.c +++ b/server/util/find_uid.c @@ -263,7 +263,8 @@ errno_t get_uid_table(TALLOC_CTX *mem_ctx, hash_table_t **table) int ret; ret = hash_create_ex(INITIAL_TABLE_SIZE, table, 0, 0, 0, 0, - hash_talloc, hash_talloc_free, mem_ctx, NULL); + hash_talloc, hash_talloc_free, mem_ctx, + NULL, NULL); if (ret != HASH_SUCCESS) { DEBUG(1, ("hash_create_ex failed [%s]\n", hash_error_string(ret))); return ENOMEM; -- cgit