struct
entry
... {
void *k, *v;
unsigned int h;
struct entry *next;
} ;
struct hashtable ... {
unsigned int tablelength;
struct entry **table;
unsigned int entrycount;
unsigned int loadlimit;
unsigned int primeindex;
unsigned int (*hashfn) (void *k);
int (*eqfn) (void *k1, void *k2);
} ;
static const unsigned int primes[] = ... {
53, 97, 193, 389, 769, 1543, 3079, 6151,
12289, 24593, 49157, 98317,
196613, 393241, 786433, 1572869,
3145739, 6291469, 12582917, 25165843,
50331653, 100663319, 201326611, 402653189,
805306457, 1610612741
} ;
const unsigned int prime_table_length = sizeof (primes) / sizeof (primes[ 0 ]);
const float max_load_factor = 0.65 ;
struct hashtable * create_hashtable(unsigned int minsize,
unsigned int ( * hashf) ( struct hashtable * , void * ),
int ( * eqf) ( void * , void * ))
... {
struct hashtable *h;
unsigned int pindex, size = primes[0];
/**//* Check requested hashtable isn't too large */
if (minsize > (1u << 30))
return NULL;
/**//* Enforce size as prime */
for (pindex=0; pindex < prime_table_length; pindex++)
...{
if (primes[pindex] > minsize)
...{
size = primes[pindex];
break;
}
}
h = (struct hashtable *)malloc(sizeof(struct hashtable));
if (NULL == h)
return NULL; /**//*oom*/
h->table = (struct entry **)malloc(sizeof(struct entry*) * size);
if (NULL == h->table)
...{
free(h);
return NULL;
} /**//*oom*/
memset(h->table, 0, size * sizeof(struct entry *));
h->tablelength = size;
h->primeindex = pindex;
h->entrycount = 0;
h->hashfn = hashf;
h->eqfn = eqf;
h->loadlimit = (unsigned int) ceil(size * max_load_factor);
return h;
}
unsigned int hash( struct hashtable * h, void * k)
... {
/**//* Aim to protect against poor hash functions by adding logic here
- logic taken from java 1.4 hashtable source */
unsigned int i = h->hashfn(k);
i += ~(i << 9);
i ^= ((i >> 14) | (i << 18)); /**//* >>> */
i += (i << 4);
i ^= ((i >> 10) | (i << 22)); /**//* >>> */
return i;
}
... {
void *k, *v;
unsigned int h;
struct entry *next;
} ;
struct hashtable ... {
unsigned int tablelength;
struct entry **table;
unsigned int entrycount;
unsigned int loadlimit;
unsigned int primeindex;
unsigned int (*hashfn) (void *k);
int (*eqfn) (void *k1, void *k2);
} ;
static const unsigned int primes[] = ... {
53, 97, 193, 389, 769, 1543, 3079, 6151,
12289, 24593, 49157, 98317,
196613, 393241, 786433, 1572869,
3145739, 6291469, 12582917, 25165843,
50331653, 100663319, 201326611, 402653189,
805306457, 1610612741
} ;
const unsigned int prime_table_length = sizeof (primes) / sizeof (primes[ 0 ]);
const float max_load_factor = 0.65 ;
struct hashtable * create_hashtable(unsigned int minsize,
unsigned int ( * hashf) ( struct hashtable * , void * ),
int ( * eqf) ( void * , void * ))
... {
struct hashtable *h;
unsigned int pindex, size = primes[0];
/**//* Check requested hashtable isn't too large */
if (minsize > (1u << 30))
return NULL;
/**//* Enforce size as prime */
for (pindex=0; pindex < prime_table_length; pindex++)
...{
if (primes[pindex] > minsize)
...{
size = primes[pindex];
break;
}
}
h = (struct hashtable *)malloc(sizeof(struct hashtable));
if (NULL == h)
return NULL; /**//*oom*/
h->table = (struct entry **)malloc(sizeof(struct entry*) * size);
if (NULL == h->table)
...{
free(h);
return NULL;
} /**//*oom*/
memset(h->table, 0, size * sizeof(struct entry *));
h->tablelength = size;
h->primeindex = pindex;
h->entrycount = 0;
h->hashfn = hashf;
h->eqfn = eqf;
h->loadlimit = (unsigned int) ceil(size * max_load_factor);
return h;
}
unsigned int hash( struct hashtable * h, void * k)
... {
/**//* Aim to protect against poor hash functions by adding logic here
- logic taken from java 1.4 hashtable source */
unsigned int i = h->hashfn(k);
i += ~(i << 9);
i ^= ((i >> 14) | (i << 18)); /**//* >>> */
i += (i << 4);
i ^= ((i >> 10) | (i << 22)); /**//* >>> */
return i;
}