6 #include <memcached/genhash.h>
7 #include "genhash_int.h"
10 static int prime_size_table[]={
11 3, 7, 13, 23, 47, 97, 193, 383, 769, 1531, 3067, 6143, 12289, 24571, 49157,
12 98299, 196613, 393209, 786433, 1572869, 3145721, 6291449, 12582917,
13 25165813, 50331653, 100663291, 201326611, 402653189, 805306357,
18 dup_key(
genhash_t *h,
const void *key,
size_t klen)
20 if (h->ops.
dupKey != NULL) {
21 return h->ops.
dupKey(key, klen);
28 dup_value(
genhash_t *h,
const void *value,
size_t vlen)
54 estimate_table_size(
int est)
59 magn=(int)log((
double)est)/log(2);
61 magn = (magn < 0) ? 0 : magn;
62 assert(magn < (
sizeof(prime_size_table) /
sizeof(
int)));
63 rv=prime_size_table[magn];
76 assert(ops.
hasheq != NULL);
80 size=estimate_table_size(est);
82 + (size *
sizeof(
struct genhash_entry_t *)));
101 const void* v,
size_t vlen)
104 struct genhash_entry_t *p;
108 n=h->ops.
hashfunc(k, klen) % h->size;
112 p=calloc(1,
sizeof(
struct genhash_entry_t));
115 p->key=dup_key(h, k, klen);
117 p->value=dup_value(h, v, vlen);
120 p->next=h->buckets[
n];
124 static struct genhash_entry_t *
125 genhash_find_entry(
genhash_t *h,
const void* k,
size_t klen)
128 struct genhash_entry_t *p;
131 n=h->ops.
hashfunc(k, klen) % h->size;
136 for(p=h->buckets[n]; p && !h->ops.
hasheq(k, klen, p->key, p->nkey); p=p->next);
143 struct genhash_entry_t *p;
146 p=genhash_find_entry(h, k, klen);
156 const void* v,
size_t vlen)
158 struct genhash_entry_t *p;
161 p=genhash_find_entry(h, k, klen);
164 free_value(h, p->value);
165 p->value=dup_value(h, v, vlen);
177 void *(*upd)(
const void *,
const void *,
size_t *,
void *),
180 const void *def,
size_t deflen)
182 struct genhash_entry_t *p;
186 p=genhash_find_entry(h, k, klen);
189 void *newValue=upd(k, p->value, &newSize, arg);
190 free_value(h, p->value);
191 p->value=dup_value(h, newValue, newSize);
195 void *newValue=upd(k, def, &newSize, arg);
205 free_item(
genhash_t *h,
struct genhash_entry_t *
i)
209 free_value(h, i->value);
216 struct genhash_entry_t *deleteme=NULL;
221 n=h->ops.
hashfunc(k, klen) % h->size;
225 if(h->buckets[n] != NULL) {
227 if(h->ops.
hasheq(h->buckets[n]->key, h->buckets[n]->nkey, k, klen)) {
228 deleteme=h->buckets[
n];
229 h->buckets[
n]=deleteme->next;
231 struct genhash_entry_t *p=NULL;
232 for(p=h->buckets[n]; deleteme==NULL && p->next != NULL; p=p->next) {
233 if(h->ops.
hasheq(p->next->key, p->next->nkey, k, klen)) {
235 p->next=deleteme->next;
240 if(deleteme != NULL) {
241 free_item(h, deleteme);
260 void (*iterfunc)(
const void* key,
size_t nkey,
261 const void* val,
size_t nval,
262 void *arg),
void *arg)
265 struct genhash_entry_t *p=NULL;
268 for(i=0; i<h->size; i++) {
269 for(p=h->buckets[i]; p!=NULL; p=p->next) {
270 iterfunc(p->key, p->nkey, p->value, p->nvalue, arg);
281 for(i = 0; i < h->size; i++) {
282 while(h->buckets[i]) {
283 struct genhash_entry_t *p = NULL;
285 h->buckets[
i] = p->next;
294 count_entries(
const void *key,
size_t klen,
295 const void *val,
size_t vlen,
void *arg)
297 int *count=(
int *)arg;
320 void (*iterfunc)(
const void* key,
size_t klen,
321 const void* val,
size_t vlen,
322 void *arg),
void *arg)
325 struct genhash_entry_t *p=NULL;
328 n=h->ops.
hashfunc(key, klen) % h->size;
332 for(p=h->buckets[n]; p!=NULL; p=p->next) {
333 if(h->ops.
hasheq(key, klen, p->key, p->nkey)) {
334 iterfunc(p->key, p->nkey, p->value, p->nvalue, arg);
346 for(i=0; i < nkey; i++) {
347 rv = ((rv << 5) + rv) ^ str[
i];