function pointer whitelists on data types.

git-svn-id: file:///svn/unbound/trunk@660 be551aaa-1e26-0410-a405-d3ace91eadb9
This commit is contained in:
Wouter Wijngaards 2007-10-05 11:41:12 +00:00
parent 9a60182c86
commit 2a547a35a7
32 changed files with 461 additions and 246 deletions

View file

@ -48,8 +48,7 @@
#include "util/config_file.h"
#include "util/net_help.h"
/** compare two donotq entries */
static int
int
donotq_cmp(const void* k1, const void* k2)
{
struct iter_donotq_addr* n1 = (struct iter_donotq_addr*)k1;

View file

@ -110,5 +110,7 @@ int donotq_lookup(struct iter_donotq* donotq, struct sockaddr_storage* addr,
*/
size_t donotq_get_mem(struct iter_donotq* donotq);
/** compare two donotq entries */
int donotq_cmp(const void* k1, const void* k2);
#endif /* ITERATOR_ITER_DONOTQ_H */

View file

@ -48,8 +48,7 @@
#include "util/net_help.h"
#include "util/data/dname.h"
/** compare two fwd entries */
static int
int
fwd_cmp(const void* k1, const void* k2)
{
int m;

View file

@ -125,4 +125,7 @@ struct delegpt* forwards_lookup(struct iter_forwards* fwd,
*/
size_t forwards_get_mem(struct iter_forwards* fwd);
/** compare two fwd entries */
int fwd_cmp(const void* k1, const void* k2);
#endif /* ITERATOR_ITER_FWD_H */

View file

@ -48,8 +48,7 @@
#include "util/net_help.h"
#include "util/data/dname.h"
/** compare two hint entries */
static int
int
stub_cmp(const void* k1, const void* k2)
{
int m;

View file

@ -134,4 +134,7 @@ struct delegpt* hints_lookup_stub(struct iter_hints* hints,
*/
size_t hints_get_mem(struct iter_hints* hints);
/** compare two hint entries */
int stub_cmp(const void* k1, const void* k2);
#endif /* ITERATOR_ITER_HINTS_H */

View file

@ -47,9 +47,7 @@
#include "util/net_help.h"
#include "util/config_file.h"
/** calculate size for the hashtable, does not count size of lameness,
* so the hashtable is a fixed number of items */
static size_t
size_t
infra_host_sizefunc(void* k, void* ATTR_UNUSED(d))
{
struct infra_host_key* key = (struct infra_host_key*)k;
@ -57,8 +55,7 @@ infra_host_sizefunc(void* k, void* ATTR_UNUSED(d))
+ lock_get_mem(&key->entry.lock);
}
/** compare two addresses, returns -1, 0, or +1 */
static int
int
infra_host_compfunc(void* key1, void* key2)
{
struct infra_host_key* k1 = (struct infra_host_key*)key1;
@ -66,8 +63,7 @@ infra_host_compfunc(void* key1, void* key2)
return sockaddr_cmp(&k1->addr, k1->addrlen, &k2->addr, k2->addrlen);
}
/** delete key, and destroy the lock */
static void
void
infra_host_delkeyfunc(void* k, void* ATTR_UNUSED(arg), int il)
{
struct infra_host_key* key = (struct infra_host_key*)k;
@ -78,8 +74,7 @@ infra_host_delkeyfunc(void* k, void* ATTR_UNUSED(arg), int il)
free(key);
}
/** delete data and destroy the lameness hashtable */
static void
void
infra_host_deldatafunc(void* d, void* ATTR_UNUSED(arg))
{
struct infra_host_data* data = (struct infra_host_data*)d;
@ -290,9 +285,7 @@ infra_lookup_lame(struct infra_host_data* host,
return 1;
}
/** calculate size, which is fixed, zonename does not count so that
* a fixed number of items is stored */
static size_t
size_t
infra_lame_sizefunc(void* k, void* ATTR_UNUSED(d))
{
struct infra_lame_key* key = (struct infra_lame_key*)k;
@ -300,8 +293,7 @@ infra_lame_sizefunc(void* k, void* ATTR_UNUSED(d))
+ key->namelen + lock_get_mem(&key->entry.lock);
}
/** compare zone names, returns -1, 0, +1 */
static int
int
infra_lame_compfunc(void* key1, void* key2)
{
struct infra_lame_key* k1 = (struct infra_lame_key*)key1;
@ -314,8 +306,7 @@ infra_lame_compfunc(void* key1, void* key2)
return query_dname_compare(k1->zonename, k2->zonename);
}
/** free key, lock and zonename */
static void
void
infra_lame_delkeyfunc(void* k, void* ATTR_UNUSED(arg), int il)
{
struct infra_lame_key* key = (struct infra_lame_key*)k;
@ -327,8 +318,7 @@ infra_lame_delkeyfunc(void* k, void* ATTR_UNUSED(arg), int il)
free(key);
}
/** free the lameness data */
static void
void
infra_lame_deldatafunc(void* d, void* ATTR_UNUSED(arg))
{
if(!d)

View file

@ -242,4 +242,30 @@ int infra_get_lame_rtt(struct infra_cache* infra,
*/
size_t infra_get_mem(struct infra_cache* infra);
/** calculate size for the hashtable, does not count size of lameness,
* so the hashtable is a fixed number of items */
size_t infra_host_sizefunc(void* k, void* d);
/** compare two addresses, returns -1, 0, or +1 */
int infra_host_compfunc(void* key1, void* key2);
/** delete key, and destroy the lock */
void infra_host_delkeyfunc(void* k, void* arg, int il);
/** delete data and destroy the lameness hashtable */
void infra_host_deldatafunc(void* d, void* arg);
/** calculate size, which is fixed, zonename does not count so that
* a fixed number of items is stored */
size_t infra_lame_sizefunc(void* k, void* d);
/** compare zone names, returns -1, 0, +1 */
int infra_lame_compfunc(void* key1, void* key2);
/** free key, lock and zonename */
void infra_lame_delkeyfunc(void* k, void* arg, int il);
/** free the lameness data */
void infra_lame_deldatafunc(void* d, void* arg);
#endif /* SERVICES_CACHE_INFRA_H */

View file

@ -53,8 +53,7 @@
#include "util/data/msgencode.h"
#include "util/timehist.h"
/** compare two mesh_states */
static int
int
mesh_state_compare(const void* ap, const void* bp)
{
struct mesh_state* a = (struct mesh_state*)ap;
@ -78,8 +77,7 @@ mesh_state_compare(const void* ap, const void* bp)
return query_info_compare(&a->s.qinfo, &b->s.qinfo);
}
/** compare two mesh references */
static int
int
mesh_state_ref_compare(const void* ap, const void* bp)
{
struct mesh_state_ref* a = (struct mesh_state_ref*)ap;

View file

@ -378,4 +378,10 @@ size_t mesh_get_mem(struct mesh_area* mesh);
int mesh_detect_cycle(struct module_qstate* qstate, struct query_info* qinfo,
uint16_t flags, int prime);
/** compare two mesh_states */
int mesh_state_compare(const void* ap, const void* bp);
/** compare two mesh references */
int mesh_state_ref_compare(const void* ap, const void* bp);
#endif /* SERVICES_MESH_H */

View file

@ -67,8 +67,7 @@
static void serviced_tcp_initiate(struct outside_network* outnet,
struct serviced_query* sq, ldns_buffer* buff);
/** compare function of pending rbtree */
static int
int
pending_cmp(const void* key1, const void* key2)
{
struct pending *p1 = (struct pending*)key1;
@ -81,8 +80,7 @@ pending_cmp(const void* key1, const void* key2)
return sockaddr_cmp(&p1->addr, p1->addrlen, &p2->addr, p2->addrlen);
}
/** compare function of serviced query rbtree */
static int
int
serviced_cmp(const void* key1, const void* key2)
{
struct serviced_query* q1 = (struct serviced_query*)key1;

View file

@ -391,4 +391,10 @@ int serviced_udp_callback(struct comm_point* c, void* arg, int error,
int serviced_tcp_callback(struct comm_point* c, void* arg, int error,
struct comm_reply* rep);
/** compare function of pending rbtree */
int pending_cmp(const void* key1, const void* key2);
/** compare function of serviced query rbtree */
int serviced_cmp(const void* key1, const void* key2);
#endif /* OUTSIDE_NETWORK_H */

View file

@ -830,3 +830,20 @@ checklock_thrjoin(pthread_t thread)
}
#endif /* USE_THREAD_DEBUG */
int order_lock_cmp(const void* e1, const void* e2)
{
struct order_id* o1 = (struct order_id*)e1;
struct order_id* o2 = (struct order_id*)e2;
if(o1->thr < o2->thr) return -1;
if(o1->thr > o2->thr) return 1;
if(o1->instance < o2->instance) return -1;
if(o1->instance > o2->instance) return 1;
return 0;
}
int
codeline_cmp(const void* a, const void* b)
{
return strcmp((const char*)a, (const char*)b);
}

View file

@ -341,4 +341,16 @@ typedef pthread_key_t ub_thread_key_t;
#endif /* USE_THREAD_DEBUG */
/** keep track of lock id in lock-verify application */
struct order_id {
/** the thread id that created it */
int thr;
/** the instance number of creation */
int instance;
};
/** compare two order_ids */
int order_lock_cmp(const void* e1, const void* e2);
/** compare two codeline structs for rbtree */
int codeline_cmp(const void* a, const void* b);
#endif /* TESTCODE_CHECK_LOCKS_H */

View file

@ -1038,4 +1038,16 @@ int serviced_tcp_callback(struct comm_point* ATTR_UNUSED(c),
return 0;
}
int pending_cmp(const void* ATTR_UNUSED(a), const void* ATTR_UNUSED(b))
{
log_assert(0);
return 0;
}
int serviced_cmp(const void* ATTR_UNUSED(a), const void* ATTR_UNUSED(b))
{
log_assert(0);
return 0;
}
/*********** End of Dummy routines ***********/

View file

@ -46,18 +46,12 @@
#include "config.h"
#include "util/log.h"
#include "util/rbtree.h"
#include "util/locks.h"
#include "testcode/checklocks.h"
/* --- data structures --- */
struct lock_ref;
/** key for lock lookup */
struct order_id {
/** the thread id that created it */
int thr;
/** the instance number of creation */
int instance;
};
/** a lock */
struct order_lock {
/** rbnode in all tree */
@ -103,18 +97,6 @@ usage()
printf("lock_verify <trace files>\n");
}
/** compare two order_ids */
int order_lock_cmp(const void* e1, const void* e2)
{
struct order_id* o1 = (struct order_id*)e1;
struct order_id* o2 = (struct order_id*)e2;
if(o1->thr < o2->thr) return -1;
if(o1->thr > o2->thr) return 1;
if(o1->instance < o2->instance) return -1;
if(o1->instance > o2->instance) return 1;
return 0;
}
/** read header entry.
* @param in: file to read header of.
* @return: False if it does not belong to the rest. */

View file

@ -42,6 +42,8 @@
#include "config.h"
#include "util/log.h"
#include "util/rbtree.h"
#include "util/locks.h"
#include "testcode/checklocks.h"
#include <sys/stat.h>
/**
@ -77,13 +79,6 @@ usage()
exit(1);
}
/** compare two codeline structs for rbtree */
static int
codeline_cmp(const void* a, const void* b)
{
return strcmp((const char*)a, (const char*)b);
}
/** match logfile line to see if it needs accounting processing */
static int
match(char* line)

View file

@ -42,36 +42,24 @@
#include "testcode/unitmain.h"
#include "util/log.h"
#include "util/storage/lruhash.h"
#include "util/storage/slabhash.h" /* for the test structures */
/* --- test representation --- */
/** structure contains test key */
struct testkey {
/** the key id */
int id;
/** the entry */
struct lruhash_entry entry;
};
/** structure contains test data */
struct testdata {
/** data value */
int data;
};
/** use this type for the lruhash test key */
typedef struct slabhash_testkey testkey_t;
/** use this type for the lruhash test data */
typedef struct slabhash_testdata testdata_t;
/** sizefunc for lruhash */
static size_t test_sizefunc(void*, void*);
/** comparefunc for lruhash */
static int test_compfunc(void*, void*);
/** delkey for lruhash */
static void test_delkey(void*, void*, int);
/** deldata for lruhash */
static void test_deldata(void*, void*);
/* --- end test representation --- */
/** delete key */
static void delkey(struct slabhash_testkey* k) {
lock_rw_destroy(&k->entry.lock); free(k);}
/** delete data */
static void deldata(struct slabhash_testdata* d) {free(d);}
/** hash func, very bad to improve collisions */
static hashvalue_t myhash(int id) {return (hashvalue_t)id & 0x0f;}
/** allocate new key, fill in hash */
static struct testkey* newkey(int id) {
struct testkey* k = (struct testkey*)calloc(1, sizeof(struct testkey));
static testkey_t* newkey(int id) {
testkey_t* k = (testkey_t*)calloc(1, sizeof(testkey_t));
if(!k) fatal_exit("out of memory");
k->id = id;
k->entry.hash = myhash(id);
@ -80,28 +68,23 @@ static struct testkey* newkey(int id) {
return k;
}
/** new data el */
static struct testdata* newdata(int val) {
struct testdata* d = (struct testdata*)calloc(1,
sizeof(struct testdata));
static testdata_t* newdata(int val) {
testdata_t* d = (testdata_t*)calloc(1,
sizeof(testdata_t));
if(!d) fatal_exit("out of memory");
d->data = val;
return d;
}
/** delete key */
static void delkey(struct testkey* k) {
lock_rw_destroy(&k->entry.lock); free(k);}
/** delete data */
static void deldata(struct testdata* d) {free(d);}
/** test bin_find_entry function and bin_overflow_remove */
static void
test_bin_find_entry(struct lruhash* table)
{
struct testkey* k = newkey(12);
struct testdata* d = newdata(128);
struct testkey* k2 = newkey(12 + 1024);
struct testkey* k3 = newkey(14);
struct testkey* k4 = newkey(12 + 1024*2);
testkey_t* k = newkey(12);
testdata_t* d = newdata(128);
testkey_t* k2 = newkey(12 + 1024);
testkey_t* k3 = newkey(14);
testkey_t* k4 = newkey(12 + 1024*2);
hashvalue_t h = myhash(12);
struct lruhash_bin bin;
memset(&bin, 0, sizeof(bin));
@ -178,8 +161,8 @@ test_bin_find_entry(struct lruhash* table)
/** test lru_front lru_remove */
static void test_lru(struct lruhash* table)
{
struct testkey* k = newkey(12);
struct testkey* k2 = newkey(14);
testkey_t* k = newkey(12);
testkey_t* k2 = newkey(14);
lock_quick_lock(&table->lock);
unit_assert( table->lru_start == NULL && table->lru_end == NULL);
@ -225,10 +208,10 @@ static void test_lru(struct lruhash* table)
static void
test_short_table(struct lruhash* table)
{
struct testkey* k = newkey(12);
struct testkey* k2 = newkey(14);
struct testdata* d = newdata(128);
struct testdata* d2 = newdata(129);
testkey_t* k = newkey(12);
testkey_t* k2 = newkey(14);
testdata_t* d = newdata(128);
testdata_t* d2 = newdata(129);
k->entry.data = d;
k2->entry.data = d2;
@ -249,11 +232,11 @@ test_short_table(struct lruhash* table)
/** test adding a random element */
static void
testadd(struct lruhash* table, struct testdata* ref[])
testadd(struct lruhash* table, testdata_t* ref[])
{
int numtoadd = random() % HASHTESTMAX;
struct testdata* data = newdata(numtoadd);
struct testkey* key = newkey(numtoadd);
testdata_t* data = newdata(numtoadd);
testkey_t* key = newkey(numtoadd);
key->entry.data = data;
lruhash_insert(table, myhash(numtoadd), &key->entry, data, NULL);
ref[numtoadd] = data;
@ -261,10 +244,10 @@ testadd(struct lruhash* table, struct testdata* ref[])
/** test adding a random element */
static void
testremove(struct lruhash* table, struct testdata* ref[])
testremove(struct lruhash* table, testdata_t* ref[])
{
int num = random() % HASHTESTMAX;
struct testkey* key = newkey(num);
testkey_t* key = newkey(num);
lruhash_remove(table, myhash(num), key);
ref[num] = NULL;
delkey(key);
@ -272,12 +255,12 @@ testremove(struct lruhash* table, struct testdata* ref[])
/** test adding a random element */
static void
testlookup(struct lruhash* table, struct testdata* ref[])
testlookup(struct lruhash* table, testdata_t* ref[])
{
int num = random() % HASHTESTMAX;
struct testkey* key = newkey(num);
testkey_t* key = newkey(num);
struct lruhash_entry* en = lruhash_lookup(table, myhash(num), key, 0);
struct testdata* data = en? (struct testdata*)en->data : NULL;
testdata_t* data = en? (testdata_t*)en->data : NULL;
if(en) {
unit_assert(en->key);
unit_assert(en->data);
@ -321,17 +304,17 @@ check_table(struct lruhash* table)
/* this assertion is specific to the unit test */
unit_assert( table->space_used ==
table->num * test_sizefunc(NULL, NULL) );
table->num * test_slabhash_sizefunc(NULL, NULL) );
lock_quick_unlock(&table->lock);
}
/** test adding a random element (unlimited range) */
static void
testadd_unlim(struct lruhash* table, struct testdata** ref)
testadd_unlim(struct lruhash* table, testdata_t** ref)
{
int numtoadd = random() % (HASHTESTMAX * 10);
struct testdata* data = newdata(numtoadd);
struct testkey* key = newkey(numtoadd);
testdata_t* data = newdata(numtoadd);
testkey_t* key = newkey(numtoadd);
key->entry.data = data;
lruhash_insert(table, myhash(numtoadd), &key->entry, data, NULL);
if(ref)
@ -340,10 +323,10 @@ testadd_unlim(struct lruhash* table, struct testdata** ref)
/** test adding a random element (unlimited range) */
static void
testremove_unlim(struct lruhash* table, struct testdata** ref)
testremove_unlim(struct lruhash* table, testdata_t** ref)
{
int num = random() % (HASHTESTMAX*10);
struct testkey* key = newkey(num);
testkey_t* key = newkey(num);
lruhash_remove(table, myhash(num), key);
if(ref)
ref[num] = NULL;
@ -352,12 +335,12 @@ testremove_unlim(struct lruhash* table, struct testdata** ref)
/** test adding a random element (unlimited range) */
static void
testlookup_unlim(struct lruhash* table, struct testdata** ref)
testlookup_unlim(struct lruhash* table, testdata_t** ref)
{
int num = random() % (HASHTESTMAX*10);
struct testkey* key = newkey(num);
testkey_t* key = newkey(num);
struct lruhash_entry* en = lruhash_lookup(table, myhash(num), key, 0);
struct testdata* data = en? (struct testdata*)en->data : NULL;
testdata_t* data = en? (testdata_t*)en->data : NULL;
if(en) {
unit_assert(en->key);
unit_assert(en->data);
@ -377,13 +360,13 @@ static void
test_long_table(struct lruhash* table)
{
/* assuming it all fits in the hastable, this check will work */
struct testdata* ref[HASHTESTMAX * 100];
testdata_t* ref[HASHTESTMAX * 100];
size_t i;
memset(ref, 0, sizeof(ref));
/* test assumption */
if(0) log_info(" size %d x %d < %d", (int)test_sizefunc(NULL, NULL),
if(0) log_info(" size %d x %d < %d", (int)test_slabhash_sizefunc(NULL, NULL),
(int)HASHTESTMAX, (int)table->space_max);
unit_assert( test_sizefunc(NULL, NULL)*HASHTESTMAX < table->space_max);
unit_assert( test_slabhash_sizefunc(NULL, NULL)*HASHTESTMAX < table->space_max);
if(0) lruhash_status(table, "unit test", 1);
srandom(48);
for(i=0; i<1000; i++) {
@ -496,41 +479,16 @@ void lruhash_test()
struct lruhash* table ;
printf("lruhash test\n");
table = lruhash_create(2, 4096,
test_sizefunc, test_compfunc, test_delkey, test_deldata, NULL);
test_slabhash_sizefunc, test_slabhash_compfunc,
test_slabhash_delkey, test_slabhash_deldata, NULL);
test_bin_find_entry(table);
test_lru(table);
test_short_table(table);
test_long_table(table);
lruhash_delete(table);
table = lruhash_create(2, 4096,
test_sizefunc, test_compfunc, test_delkey, test_deldata, NULL);
test_slabhash_sizefunc, test_slabhash_compfunc,
test_slabhash_delkey, test_slabhash_deldata, NULL);
test_threaded_table(table);
lruhash_delete(table);
}
static size_t test_sizefunc(void* ATTR_UNUSED(key), void* ATTR_UNUSED(data))
{
return sizeof(struct testkey) + sizeof(struct testdata);
}
static int test_compfunc(void* key1, void* key2)
{
struct testkey* k1 = (struct testkey*)key1;
struct testkey* k2 = (struct testkey*)key2;
if(k1->id == k2->id)
return 0;
if(k1->id > k2->id)
return 1;
return -1;
}
static void test_delkey(void* key, void* ATTR_UNUSED(arg), int l)
{
if(l) { lock_rw_unlock(&((struct testkey*)key)->entry.lock); }
delkey((struct testkey*)key);
}
static void test_deldata(void* data, void* ATTR_UNUSED(arg))
{
deldata((struct testdata*)data);
}

View file

@ -43,29 +43,14 @@
#include "util/log.h"
#include "util/storage/slabhash.h"
/* --- test representation --- */
/** structure contains test key */
struct slabtestkey {
/** the key id */
int id;
/** the entry */
struct lruhash_entry entry;
};
/** structure contains test data */
struct slabtestdata {
/** data value */
int data;
};
/** use this type for the slabhash test key */
typedef struct slabhash_testkey testkey_t;
/** use this type for the slabhash test data */
typedef struct slabhash_testdata testdata_t;
/** sizefunc for lruhash */
static size_t test_sizefunc(void*, void*);
/** comparefunc for lruhash */
static int test_compfunc(void*, void*);
/** delkey for lruhash */
static void test_delkey(void*, void*, int);
/** deldata for lruhash */
static void test_deldata(void*, void*);
/* --- end test representation --- */
/** delete key */
static void delkey(struct slabhash_testkey* k) {
lock_rw_destroy(&k->entry.lock); free(k);}
/** hash func, very bad to improve collisions, both high and low bits */
static hashvalue_t myhash(int id) {
@ -75,8 +60,8 @@ static hashvalue_t myhash(int id) {
}
/** allocate new key, fill in hash */
static struct slabtestkey* newkey(int id) {
struct slabtestkey* k = (struct slabtestkey*)calloc(1, sizeof(struct slabtestkey));
static testkey_t* newkey(int id) {
testkey_t* k = (testkey_t*)calloc(1, sizeof(testkey_t));
if(!k) fatal_exit("out of memory");
k->id = id;
k->entry.hash = myhash(id);
@ -85,27 +70,22 @@ static struct slabtestkey* newkey(int id) {
return k;
}
/** new data el */
static struct slabtestdata* newdata(int val) {
struct slabtestdata* d = (struct slabtestdata*)calloc(1,
sizeof(struct slabtestdata));
static testdata_t* newdata(int val) {
testdata_t* d = (testdata_t*)calloc(1,
sizeof(testdata_t));
if(!d) fatal_exit("out of memory");
d->data = val;
return d;
}
/** delete key */
static void delkey(struct slabtestkey* k) {
lock_rw_destroy(&k->entry.lock); free(k);}
/** delete data */
static void deldata(struct slabtestdata* d) {free(d);}
/** test hashtable using short sequence */
static void
test_short_table(struct slabhash* table)
{
struct slabtestkey* k = newkey(12);
struct slabtestkey* k2 = newkey(14);
struct slabtestdata* d = newdata(128);
struct slabtestdata* d2 = newdata(129);
testkey_t* k = newkey(12);
testkey_t* k2 = newkey(14);
testdata_t* d = newdata(128);
testdata_t* d2 = newdata(129);
k->entry.data = d;
k2->entry.data = d2;
@ -126,11 +106,11 @@ test_short_table(struct slabhash* table)
/** test adding a random element */
static void
testadd(struct slabhash* table, struct slabtestdata* ref[])
testadd(struct slabhash* table, testdata_t* ref[])
{
int numtoadd = random() % HASHTESTMAX;
struct slabtestdata* data = newdata(numtoadd);
struct slabtestkey* key = newkey(numtoadd);
testdata_t* data = newdata(numtoadd);
testkey_t* key = newkey(numtoadd);
key->entry.data = data;
slabhash_insert(table, myhash(numtoadd), &key->entry, data, NULL);
ref[numtoadd] = data;
@ -138,10 +118,10 @@ testadd(struct slabhash* table, struct slabtestdata* ref[])
/** test adding a random element */
static void
testremove(struct slabhash* table, struct slabtestdata* ref[])
testremove(struct slabhash* table, testdata_t* ref[])
{
int num = random() % HASHTESTMAX;
struct slabtestkey* key = newkey(num);
testkey_t* key = newkey(num);
slabhash_remove(table, myhash(num), key);
ref[num] = NULL;
delkey(key);
@ -149,12 +129,12 @@ testremove(struct slabhash* table, struct slabtestdata* ref[])
/** test adding a random element */
static void
testlookup(struct slabhash* table, struct slabtestdata* ref[])
testlookup(struct slabhash* table, testdata_t* ref[])
{
int num = random() % HASHTESTMAX;
struct slabtestkey* key = newkey(num);
testkey_t* key = newkey(num);
struct lruhash_entry* en = slabhash_lookup(table, myhash(num), key, 0);
struct slabtestdata* data = en? (struct slabtestdata*)en->data : NULL;
testdata_t* data = en? (testdata_t*)en->data : NULL;
if(en) {
unit_assert(en->key);
unit_assert(en->data);
@ -198,7 +178,7 @@ check_lru_table(struct lruhash* table)
/* this assertion is specific to the unit test */
unit_assert( table->space_used ==
table->num * test_sizefunc(NULL, NULL) );
table->num * test_slabhash_sizefunc(NULL, NULL) );
lock_quick_unlock(&table->lock);
}
@ -213,11 +193,11 @@ check_table(struct slabhash* table)
/** test adding a random element (unlimited range) */
static void
testadd_unlim(struct slabhash* table, struct slabtestdata** ref)
testadd_unlim(struct slabhash* table, testdata_t** ref)
{
int numtoadd = random() % (HASHTESTMAX * 10);
struct slabtestdata* data = newdata(numtoadd);
struct slabtestkey* key = newkey(numtoadd);
testdata_t* data = newdata(numtoadd);
testkey_t* key = newkey(numtoadd);
key->entry.data = data;
slabhash_insert(table, myhash(numtoadd), &key->entry, data, NULL);
if(ref)
@ -226,10 +206,10 @@ testadd_unlim(struct slabhash* table, struct slabtestdata** ref)
/** test adding a random element (unlimited range) */
static void
testremove_unlim(struct slabhash* table, struct slabtestdata** ref)
testremove_unlim(struct slabhash* table, testdata_t** ref)
{
int num = random() % (HASHTESTMAX*10);
struct slabtestkey* key = newkey(num);
testkey_t* key = newkey(num);
slabhash_remove(table, myhash(num), key);
if(ref)
ref[num] = NULL;
@ -238,12 +218,12 @@ testremove_unlim(struct slabhash* table, struct slabtestdata** ref)
/** test adding a random element (unlimited range) */
static void
testlookup_unlim(struct slabhash* table, struct slabtestdata** ref)
testlookup_unlim(struct slabhash* table, testdata_t** ref)
{
int num = random() % (HASHTESTMAX*10);
struct slabtestkey* key = newkey(num);
testkey_t* key = newkey(num);
struct lruhash_entry* en = slabhash_lookup(table, myhash(num), key, 0);
struct slabtestdata* data = en? (struct slabtestdata*)en->data : NULL;
testdata_t* data = en? (testdata_t*)en->data : NULL;
if(en) {
unit_assert(en->key);
unit_assert(en->data);
@ -263,7 +243,7 @@ static void
test_long_table(struct slabhash* table)
{
/* assuming it all fits in the hastable, this check will work */
struct slabtestdata* ref[HASHTESTMAX * 100];
testdata_t* ref[HASHTESTMAX * 100];
size_t i;
memset(ref, 0, sizeof(ref));
/* test assumption */
@ -378,39 +358,14 @@ void slabhash_test()
struct slabhash* table;
printf("slabhash test\n");
table = slabhash_create(4, 2, 5200,
test_sizefunc, test_compfunc, test_delkey, test_deldata, NULL);
test_slabhash_sizefunc, test_slabhash_compfunc,
test_slabhash_delkey, test_slabhash_deldata, NULL);
test_short_table(table);
test_long_table(table);
slabhash_delete(table);
table = slabhash_create(4, 2, 5200,
test_sizefunc, test_compfunc, test_delkey, test_deldata, NULL);
test_slabhash_sizefunc, test_slabhash_compfunc,
test_slabhash_delkey, test_slabhash_deldata, NULL);
test_threaded_table(table);
slabhash_delete(table);
}
static size_t test_sizefunc(void* ATTR_UNUSED(key), void* ATTR_UNUSED(data))
{
return sizeof(struct slabtestkey) + sizeof(struct slabtestdata);
}
static int test_compfunc(void* key1, void* key2)
{
struct slabtestkey* k1 = (struct slabtestkey*)key1;
struct slabtestkey* k2 = (struct slabtestkey*)key2;
if(k1->id == k2->id)
return 0;
if(k1->id > k2->id)
return 1;
return -1;
}
static void test_delkey(void* key, void* ATTR_UNUSED(arg), int l)
{
if(l) { lock_rw_unlock(&((struct slabtestkey*)key)->entry.lock); }
delkey((struct slabtestkey*)key);
}
static void test_deldata(void* data, void* ATTR_UNUSED(arg))
{
deldata((struct slabtestdata*)data);
}

View file

@ -45,8 +45,23 @@
*/
#include "config.h"
#include "util/fptr_wlist.h"
#include "util/mini_event.h"
#include "daemon/worker.h"
#include "services/outside_network.h"
#include "services/mesh.h"
#include "services/cache/infra.h"
#include "iterator/iter_donotq.h"
#include "iterator/iter_fwd.h"
#include "iterator/iter_hints.h"
#include "validator/val_anchor.h"
#include "validator/val_nsec3.h"
#include "validator/val_sigcrypt.h"
#include "validator/val_kentry.h"
#include "util/data/msgreply.h"
#include "util/data/packed_rrset.h"
#include "util/storage/slabhash.h"
#include "util/locks.h"
#include "testcode/checklocks.h"
int
fptr_whitelist_comm_point(comm_point_callback_t *fptr)
@ -107,3 +122,85 @@ fptr_whitelist_serviced_query(comm_point_callback_t *fptr)
if(fptr == &worker_handle_service_reply) return 1;
return 0;
}
int
fptr_whitelist_region_allocator(void *(*fptr)(size_t))
{
/* TODO: remove callbacks from new region type */
if(fptr == &malloc) return 1;
return 0;
}
int
fptr_whitelist_region_deallocator(void (*fptr)(void*))
{
if(fptr == &free) return 1;
return 0;
}
int
fptr_whitelist_rbtree_cmp(int (*fptr) (const void *, const void *))
{
if(fptr == &mesh_state_compare) return 1;
else if(fptr == &mesh_state_ref_compare) return 1;
else if(fptr == &donotq_cmp) return 1;
else if(fptr == &fwd_cmp) return 1;
else if(fptr == &stub_cmp) return 1;
else if(fptr == &pending_cmp) return 1;
else if(fptr == &serviced_cmp) return 1;
else if(fptr == &order_lock_cmp) return 1;
else if(fptr == &codeline_cmp) return 1;
else if(fptr == &nsec3_hash_cmp) return 1;
else if(fptr == &mini_ev_cmp) return 1;
else if(fptr == &anchor_cmp) return 1;
else if(fptr == &canonical_tree_compare) return 1;
return 0;
}
int
fptr_whitelist_hash_sizefunc(lruhash_sizefunc_t fptr)
{
if(fptr == &msgreply_sizefunc) return 1;
else if(fptr == &ub_rrset_sizefunc) return 1;
else if(fptr == &infra_host_sizefunc) return 1;
else if(fptr == &key_entry_sizefunc) return 1;
else if(fptr == &infra_lame_sizefunc) return 1;
else if(fptr == &test_slabhash_sizefunc) return 1;
return 0;
}
int
fptr_whitelist_hash_compfunc(lruhash_compfunc_t fptr)
{
if(fptr == &query_info_compare) return 1;
else if(fptr == &ub_rrset_compare) return 1;
else if(fptr == &infra_host_compfunc) return 1;
else if(fptr == &key_entry_compfunc) return 1;
else if(fptr == &infra_lame_compfunc) return 1;
else if(fptr == &test_slabhash_compfunc) return 1;
return 0;
}
int
fptr_whitelist_hash_delkeyfunc(lruhash_delkeyfunc_t fptr)
{
if(fptr == &query_entry_delete) return 1;
else if(fptr == &ub_rrset_key_delete) return 1;
else if(fptr == &infra_host_delkeyfunc) return 1;
else if(fptr == &key_entry_delkeyfunc) return 1;
else if(fptr == &infra_lame_delkeyfunc) return 1;
else if(fptr == &test_slabhash_delkey) return 1;
return 0;
}
int
fptr_whitelist_hash_deldatafunc(lruhash_deldatafunc_t fptr)
{
if(fptr == &reply_info_delete) return 1;
else if(fptr == &rrset_data_delete) return 1;
else if(fptr == &infra_host_deldatafunc) return 1;
else if(fptr == &key_entry_deldatafunc) return 1;
else if(fptr == &infra_lame_deldatafunc) return 1;
else if(fptr == &test_slabhash_deldata) return 1;
return 0;
}

View file

@ -47,12 +47,15 @@
* Function pointers are used in
* o network code callbacks.
* o rbtree, lruhash, region data manipulation
* in lruhash, the assertions are before the critical regions.
* in other places, assertions are before the callback.
* o module operations.
*/
#ifndef UTIL_FPTR_WLIST_H
#define UTIL_FPTR_WLIST_H
#include "util/netevent.h"
#include "util/storage/lruhash.h"
/**
* Check function pointer whitelist for comm_point callback values.
@ -89,7 +92,6 @@ int fptr_whitelist_event(void (*fptr)(int, short, void *));
/**
* Check function pointer whitelist for pending udp callback values.
* This is not called by libevent itself, but checked by netevent.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
@ -98,7 +100,6 @@ int fptr_whitelist_pending_udp(comm_point_callback_t *fptr);
/**
* Check function pointer whitelist for pending tcp callback values.
* This is not called by libevent itself, but checked by netevent.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
@ -107,12 +108,66 @@ int fptr_whitelist_pending_tcp(comm_point_callback_t *fptr);
/**
* Check function pointer whitelist for serviced query callback values.
* This is not called by libevent itself, but checked by netevent.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
*/
int fptr_whitelist_serviced_query(comm_point_callback_t *fptr);
/**
* Check function pointer whitelist for region allocator callback values.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
*/
int fptr_whitelist_region_allocator(void *(*fptr)(size_t));
/**
* Check function pointer whitelist for region deallocator callback values.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
*/
int fptr_whitelist_region_deallocator(void (*fptr)(void*));
/**
* Check function pointer whitelist for rbtree cmp callback values.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
*/
int fptr_whitelist_rbtree_cmp(int (*fptr) (const void *, const void *));
/**
* Check function pointer whitelist for lruhash sizefunc callback values.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
*/
int fptr_whitelist_hash_sizefunc(lruhash_sizefunc_t fptr);
/**
* Check function pointer whitelist for lruhash compfunc callback values.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
*/
int fptr_whitelist_hash_compfunc(lruhash_compfunc_t fptr);
/**
* Check function pointer whitelist for lruhash delkeyfunc callback values.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
*/
int fptr_whitelist_hash_delkeyfunc(lruhash_delkeyfunc_t fptr);
/**
* Check function pointer whitelist for lruhash deldata callback values.
*
* @param fptr: function pointer to check.
* @return false if not in whitelist.
*/
int fptr_whitelist_hash_deldatafunc(lruhash_deldatafunc_t fptr);
#endif /* UTIL_FPTR_WLIST_H */

View file

@ -47,7 +47,7 @@
#include "util/mini_event.h"
/** compare events in tree, based on timevalue, ptr for uniqueness */
static int ev_cmp(const void* a, const void* b)
int mini_ev_cmp(const void* a, const void* b)
{
const struct event *e = (const struct event*)a;
const struct event *f = (const struct event*)b;
@ -74,7 +74,7 @@ void *event_init(void)
if(!base)
return NULL;
memset(base, 0, sizeof(*base));
base->times = rbtree_create(ev_cmp);
base->times = rbtree_create(mini_ev_cmp);
if(!base->times) {
event_base_free(base);
return NULL;
@ -338,4 +338,9 @@ int signal_del(struct event* ev)
return 0;
}
#else /* USE_MINI_EVENT */
int mini_ev_cmp(const void* ATTR_UNUSED(a), const void* ATTR_UNUSED(b))
{
return 0;
}
#endif /* USE_MINI_EVENT */

View file

@ -156,4 +156,8 @@ int signal_add(struct event *, struct timeval *);
int signal_del(struct event *);
#endif /* USE_MINI_EVENT */
/** compare events in tree, based on timevalue, ptr for uniqueness */
int mini_ev_cmp(const void* a, const void* b);
#endif /* MINI_EVENT_H */

View file

@ -41,6 +41,7 @@
#include "config.h"
#include "log.h"
#include "fptr_wlist.h"
#include "util/rbtree.h"
/** Node colour black */
@ -232,6 +233,7 @@ rbtree_insert (rbtree_t *rbtree, rbnode_t *data)
rbnode_t *node = rbtree->root;
rbnode_t *parent = RBTREE_NULL;
log_assert(fptr_whitelist_rbtree_cmp(rbtree->cmp));
/* Lets find the new parent... */
while (node != RBTREE_NULL) {
/* Compare two keys, do we have a duplicate? */
@ -513,7 +515,8 @@ rbtree_find_less_equal(rbtree_t *rbtree, const void *key, rbnode_t **result)
node = rbtree->root;
*result = NULL;
log_assert(fptr_whitelist_rbtree_cmp(rbtree->cmp));
/* While there are children... */
while (node != RBTREE_NULL) {
r = rbtree->cmp(key, node->key);

View file

@ -43,6 +43,7 @@
#include "config.h"
#include "util/log.h"
#include "util/region-allocator.h"
#include "util/fptr_wlist.h"
#ifdef ALIGNMENT
# undef ALIGNMENT
@ -146,9 +147,11 @@ alloc_region_base(void *(*allocator)(size_t size),
log_assert(initial_cleanup_count > 0);
result->maximum_cleanup_count = initial_cleanup_count;
result->cleanup_count = 0;
log_assert(fptr_whitelist_region_allocator(allocator));
result->cleanups = (cleanup_type *) allocator(
result->maximum_cleanup_count * sizeof(cleanup_type));
if (!result->cleanups) {
log_assert(fptr_whitelist_region_deallocator(deallocator));
deallocator(result);
return NULL;
}
@ -168,12 +171,14 @@ region_create(void *(*allocator)(size_t), void (*deallocator)(void *))
allocator = &unbound_stat_malloc_region;
deallocator = &unbound_stat_free_region;
#endif
log_assert(fptr_whitelist_region_allocator(allocator));
result = alloc_region_base(allocator, deallocator,
DEFAULT_INITIAL_CLEANUP_SIZE);
if(!result)
return NULL;
result->data = (char *) allocator(result->chunk_size);
if (!result->data) {
log_assert(fptr_whitelist_region_deallocator(deallocator));
deallocator(result->cleanups);
deallocator(result);
return NULL;
@ -198,6 +203,7 @@ region_type *region_create_custom(void *(*allocator)(size_t),
allocator = &unbound_stat_malloc_region;
deallocator = &unbound_stat_free_region;
#endif
log_assert(fptr_whitelist_region_allocator(allocator));
result = alloc_region_base(allocator, deallocator,
initial_cleanup_size);
if(!result)
@ -208,6 +214,8 @@ region_type *region_create_custom(void *(*allocator)(size_t),
if(result->chunk_size > 0) {
result->data = (char *) allocator(result->chunk_size);
if (!result->data) {
log_assert(fptr_whitelist_region_deallocator(
deallocator));
deallocator(result->cleanups);
deallocator(result);
return NULL;
@ -236,6 +244,7 @@ region_destroy(region_type *region)
return;
deallocator = region->deallocator;
log_assert(fptr_whitelist_region_deallocator(deallocator));
region_free_all(region);
deallocator(region->cleanups);
@ -251,6 +260,7 @@ region_add_cleanup(region_type *region, void (*action)(void *), void *data)
{
log_assert(action);
log_assert(fptr_whitelist_region_allocator(region->allocator));
if (region->cleanup_count >= region->maximum_cleanup_count) {
cleanup_type *cleanups = (cleanup_type *) region->allocator(
2 * region->maximum_cleanup_count * sizeof(cleanup_type));
@ -258,6 +268,8 @@ region_add_cleanup(region_type *region, void (*action)(void *), void *data)
memcpy(cleanups, region->cleanups,
region->cleanup_count * sizeof(cleanup_type));
log_assert(fptr_whitelist_region_deallocator(
region->deallocator));
region->deallocator(region->cleanups);
region->cleanups = cleanups;
@ -283,9 +295,12 @@ region_alloc(region_type *region, size_t size)
aligned_size = ALIGN_UP(size, ALIGNMENT);
if (aligned_size >= region->large_object_size) {
log_assert(fptr_whitelist_region_allocator(region->allocator));
result = region->allocator(size);
if (!result) return NULL;
log_assert(fptr_whitelist_region_deallocator(
region->deallocator));
if (!region_add_cleanup(region, region->deallocator, result)) {
region->deallocator(result);
return NULL;
@ -305,6 +320,7 @@ region_alloc(region_type *region, size_t size)
return result;
}
log_assert(fptr_whitelist_region_allocator(region->allocator));
if (region->allocated + aligned_size > region->chunk_size) {
void *chunk = region->allocator(region->chunk_size);
size_t wasted;
@ -321,6 +337,8 @@ region_alloc(region_type *region, size_t size)
++region->chunk_count;
region->unused_space += region->chunk_size - region->allocated;
log_assert(fptr_whitelist_region_deallocator(
region->deallocator));
if(!region_add_cleanup(region, region->deallocator, chunk)) {
region->deallocator(chunk);
region->chunk_count--;

View file

@ -42,6 +42,7 @@
#include "config.h"
#include "util/storage/lruhash.h"
#include "util/fptr_wlist.h"
void
bin_init(struct lruhash_bin* array, size_t size)
@ -298,6 +299,10 @@ lruhash_insert(struct lruhash* table, hashvalue_t hash,
struct lruhash_bin* bin;
struct lruhash_entry* found, *reclaimlist=NULL;
size_t need_size;
log_assert(fptr_whitelist_hash_sizefunc(table->sizefunc));
log_assert(fptr_whitelist_hash_delkeyfunc(table->delkeyfunc));
log_assert(fptr_whitelist_hash_deldatafunc(table->deldatafunc));
log_assert(fptr_whitelist_hash_compfunc(table->compfunc));
need_size = table->sizefunc(entry->key, data);
if(cb_arg == NULL) cb_arg = table->cb_arg;
@ -347,6 +352,7 @@ lruhash_lookup(struct lruhash* table, hashvalue_t hash, void* key, int wr)
{
struct lruhash_entry* entry;
struct lruhash_bin* bin;
log_assert(fptr_whitelist_hash_compfunc(table->compfunc));
lock_quick_lock(&table->lock);
bin = &table->array[hash & table->size_mask];
@ -369,6 +375,10 @@ lruhash_remove(struct lruhash* table, hashvalue_t hash, void* key)
struct lruhash_entry* entry;
struct lruhash_bin* bin;
void *d;
log_assert(fptr_whitelist_hash_sizefunc(table->sizefunc));
log_assert(fptr_whitelist_hash_delkeyfunc(table->delkeyfunc));
log_assert(fptr_whitelist_hash_deldatafunc(table->deldatafunc));
log_assert(fptr_whitelist_hash_compfunc(table->compfunc));
lock_quick_lock(&table->lock);
bin = &table->array[hash & table->size_mask];

View file

@ -158,3 +158,38 @@ struct lruhash* slabhash_gettable(struct slabhash* sl, hashvalue_t hash)
{
return sl->array[slab_idx(sl, hash)];
}
/* test code, here to avoid linking problems with fptr_wlist */
/** delete key */
static void delkey(struct slabhash_testkey* k) {
lock_rw_destroy(&k->entry.lock); free(k);}
/** delete data */
static void deldata(struct slabhash_testdata* d) {free(d);}
size_t test_slabhash_sizefunc(void* ATTR_UNUSED(key), void* ATTR_UNUSED(data))
{
return sizeof(struct slabhash_testkey) +
sizeof(struct slabhash_testdata);
}
int test_slabhash_compfunc(void* key1, void* key2)
{
struct slabhash_testkey* k1 = (struct slabhash_testkey*)key1;
struct slabhash_testkey* k2 = (struct slabhash_testkey*)key2;
if(k1->id == k2->id)
return 0;
if(k1->id > k2->id)
return 1;
return -1;
}
void test_slabhash_delkey(void* key, void* ATTR_UNUSED(arg), int l)
{
if(l) { lock_rw_unlock(&((struct slabhash_testkey*)key)->entry.lock); }
delkey((struct slabhash_testkey*)key);
}
void test_slabhash_deldata(void* data, void* ATTR_UNUSED(arg))
{
deldata((struct slabhash_testdata*)data);
}

View file

@ -161,4 +161,28 @@ size_t slabhash_get_mem(struct slabhash* table);
*/
struct lruhash* slabhash_gettable(struct slabhash* table, hashvalue_t hash);
/* --- test representation --- */
/** test structure contains test key */
struct slabhash_testkey {
/** the key id */
int id;
/** the entry */
struct lruhash_entry entry;
};
/** test structure contains test data */
struct slabhash_testdata {
/** data value */
int data;
};
/** test sizefunc for lruhash */
size_t test_slabhash_sizefunc(void*, void*);
/** test comparefunc for lruhash */
int test_slabhash_compfunc(void*, void*);
/** test delkey for lruhash */
void test_slabhash_delkey(void*, void*, int);
/** test deldata for lruhash */
void test_slabhash_deldata(void*, void*);
/* --- end test representation --- */
#endif /* UTIL_STORAGE_SLABHASH_H */

View file

@ -47,8 +47,7 @@
#include "util/region-allocator.h"
#include "util/config_file.h"
/** compare two trust anchors */
static int
int
anchor_cmp(const void* k1, const void* k2)
{
int m;

View file

@ -158,4 +158,7 @@ int anchor_store_str(struct val_anchors* anchors, ldns_buffer* buffer,
*/
size_t anchors_get_mem(struct val_anchors* anchors);
/** compare two trust anchors */
int anchor_cmp(const void* k1, const void* k2);
#endif /* VALIDATOR_VAL_ANCHOR_H */

View file

@ -794,10 +794,7 @@ canonical_compare(struct ub_packed_rrset_key* rrset, size_t i, size_t j)
return 0;
}
/**
* canonical compare for two tree entries
*/
static int
int
canonical_tree_compare(const void* k1, const void* k2)
{
struct canon_rr* r1 = (struct canon_rr*)k1;

View file

@ -200,4 +200,9 @@ enum sec_status dnskey_verify_rrset_sig(struct region* region,
size_t dnskey_idx, size_t sig_idx,
struct rbtree_t** sortree, int* buf_canon);
/**
* canonical compare for two tree entries
*/
int canonical_tree_compare(const void* k1, const void* k2);
#endif /* VALIDATOR_VAL_SIGCRYPT_H */