00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027 #include <stdio.h>
00028 #include <stdlib.h>
00029 #include <string.h>
00030 #include "hashtable.h"
00031
00032 typedef struct _Hash_node {
00033 struct _Hash_node *next;
00034 void* key;
00035 unsigned int keysize;
00036 void* value;
00037 unsigned int valuesize;
00038 } Hash_node;
00039
00040 struct _Hash_table {
00041 unsigned int size;
00042 Hash_node** nodes;
00043 };
00044
00045
00046 Hash_table
00047 hash_init(unsigned int size)
00048 {
00049 Hash_table ht;
00050
00051 ht = (Hash_table) calloc(1,sizeof(struct _Hash_table));
00052 ht->size = size;
00053 ht->nodes = (Hash_node **) calloc (size, sizeof (Hash_node*));
00054 return ht;
00055 }
00056
00057 void
00058 hash_rec_free(Hash_node* node)
00059 {
00060 if (node)
00061 {
00062 if (node->next)
00063 hash_rec_free(node->next);
00064 if (node->key)
00065 free(node->key);
00066 if (node->value)
00067 free(node->value);
00068 free(node);
00069 }
00070 }
00071
00072 int
00073 hash_destroy(Hash_table hashtable)
00074 {
00075 unsigned int i;
00076 if (hashtable)
00077 {
00078 for(i=0; i<hashtable->size; i++)
00079 if (hashtable->nodes[i])
00080 hash_rec_free(hashtable->nodes[i]);
00081 if (hashtable->nodes)
00082 free(hashtable->nodes);
00083 free(hashtable);
00084 }
00085 return 0;
00086 }
00087
00088
00089 static unsigned int
00090 hash_key(Hash_table hashtable, void* ptr, unsigned int size)
00091 {
00092 unsigned int i;
00093 unsigned int key = 0;
00094
00095 if (size % 4 == 0)
00096 {
00097 unsigned int *v = (unsigned int*)ptr;
00098 for (i = 0; i < (size / 4); i++)
00099 key ^= (key << 3) ^ (key >> 1) ^ v[i];
00100 }
00101 else
00102 {
00103 unsigned char *v = (unsigned char*)ptr;
00104 for (i = 0; i < size; i++)
00105 key ^= (key << 3) ^ (key >> 1) ^ v[i];
00106 }
00107 key %= hashtable->size;
00108 return key;
00109 }
00110
00111
00112 void*
00113 hash_find(Hash_table hashtable, void* key, unsigned int keysize)
00114 {
00115 Hash_node *entry;
00116 unsigned int h_key;
00117
00118 h_key = hash_key(hashtable,key,keysize);
00119 for (entry = hashtable->nodes[h_key]; entry; entry = entry -> next)
00120 {
00121 if ((entry -> keysize == keysize) &&
00122 (memcmp(entry->key,key,keysize) == 0))
00123 {
00124 return entry->value;
00125 }
00126 }
00127 return NULL;
00128 }
00129
00130
00131 static Hash_node*
00132 new_entry(void* key, unsigned int keysize, void* value, unsigned int
00133 valuesize)
00134 {
00135 Hash_node *n;
00136 n = (Hash_node*)calloc(1,sizeof(Hash_node));
00137 n->key = (void*)malloc(keysize);
00138 n->value = (void*)malloc(valuesize);
00139 n->keysize = keysize;
00140 n->valuesize = valuesize;
00141 memcpy(n->key,key,keysize);
00142 memcpy(n->value,value,valuesize);
00143 return n;
00144 }
00145
00146
00147 int
00148 hash_add(Hash_table hashtable,
00149 void* key, unsigned int keysize,
00150 void* value, unsigned int valuesize)
00151 {
00152 Hash_node *entry;
00153 unsigned int h_key;
00154
00155 h_key = hash_key(hashtable,key,keysize);
00156 entry = new_entry(key,keysize,value,valuesize);
00157 entry->next = hashtable->nodes[h_key];
00158 hashtable->nodes[h_key] = entry;
00159
00160 return 0;
00161 }
00162
00163