00001 #include <stdlib.h>
00002 #include <string.h>
00003 #include "hash.h"
00004 #include "util.h"
00005
00006 #define HASHSIZE 4093
00007
00008 static int hash_value(char *name);
00009
00010
00011
00012 struct s_hash **
00013 alloc_hash_table(void)
00014 {
00015
00016
00017
00018 struct s_hash **hash_table;
00019
00020 hash_table = (struct s_hash **)my_calloc(sizeof(struct s_hash *),
00021 HASHSIZE);
00022 return (hash_table);
00023 }
00024
00025
00026 void
00027 free_hash_table(struct s_hash **hash_table)
00028 {
00029
00030
00031
00032 int i;
00033 struct s_hash *h_ptr, *temp_ptr;
00034
00035 for(i = 0; i < HASHSIZE; i++)
00036 {
00037 h_ptr = hash_table[i];
00038 while(h_ptr != NULL)
00039 {
00040 free(h_ptr->name);
00041 temp_ptr = h_ptr->next;
00042 free(h_ptr);
00043 h_ptr = temp_ptr;
00044 }
00045 }
00046
00047 free(hash_table);
00048 }
00049
00050
00051 struct s_hash_iterator
00052 start_hash_table_iterator(void)
00053 {
00054
00055
00056
00057
00058 struct s_hash_iterator hash_iterator;
00059
00060 hash_iterator.i = -1;
00061 hash_iterator.h_ptr = NULL;
00062 return (hash_iterator);
00063 }
00064
00065
00066 struct s_hash *
00067 get_next_hash(struct s_hash **hash_table,
00068 struct s_hash_iterator *hash_iterator)
00069 {
00070
00071
00072
00073
00074 int i;
00075 struct s_hash *h_ptr;
00076
00077 i = hash_iterator->i;
00078 h_ptr = hash_iterator->h_ptr;
00079
00080 while(h_ptr == NULL)
00081 {
00082 i++;
00083 if(i >= HASHSIZE)
00084 return (NULL);
00085
00086 h_ptr = hash_table[i];
00087 }
00088
00089 hash_iterator->h_ptr = h_ptr->next;
00090 hash_iterator->i = i;
00091 return (h_ptr);
00092 }
00093
00094
00095 struct s_hash *
00096 insert_in_hash_table(struct s_hash **hash_table,
00097 char *name,
00098 int next_free_index)
00099 {
00100
00101
00102
00103
00104
00105
00106
00107 int i;
00108 struct s_hash *h_ptr, *prev_ptr;
00109
00110 i = hash_value(name);
00111 prev_ptr = NULL;
00112 h_ptr = hash_table[i];
00113
00114 while(h_ptr != NULL)
00115 {
00116 if(strcmp(h_ptr->name, name) == 0)
00117 {
00118 h_ptr->count++;
00119 return (h_ptr);
00120 }
00121
00122 prev_ptr = h_ptr;
00123 h_ptr = h_ptr->next;
00124 }
00125
00126
00127
00128 h_ptr = (struct s_hash *)my_malloc(sizeof(struct s_hash));
00129 if(prev_ptr == NULL)
00130 {
00131 hash_table[i] = h_ptr;
00132 }
00133 else
00134 {
00135 prev_ptr->next = h_ptr;
00136 }
00137 h_ptr->next = NULL;
00138 h_ptr->index = next_free_index;
00139 h_ptr->count = 1;
00140 h_ptr->name = (char *)my_malloc((strlen(name) + 1) * sizeof(char));
00141 strcpy(h_ptr->name, name);
00142 return (h_ptr);
00143 }
00144
00145
00146 struct s_hash *
00147 get_hash_entry(struct s_hash **hash_table,
00148 char *name)
00149 {
00150
00151
00152
00153
00154 int i;
00155 struct s_hash *h_ptr;
00156
00157 i = hash_value(name);
00158 h_ptr = hash_table[i];
00159
00160 while(h_ptr != NULL)
00161 {
00162 if(strcmp(h_ptr->name, name) == 0)
00163 return (h_ptr);
00164
00165 h_ptr = h_ptr->next;
00166 }
00167
00168 return (NULL);
00169 }
00170
00171
00172 static int
00173 hash_value(char *name)
00174 {
00175
00176
00177
00178
00179 int i, k;
00180 int val = 0, mult = 1;
00181
00182 i = strlen(name);
00183 k = max(i - 8, 0);
00184 for(i = strlen(name) - 1; i >= k; i--)
00185 {
00186 val += mult * ((int)name[i]);
00187 mult *= 7;
00188 }
00189 val += (int)name[0];
00190 val %= HASHSIZE;
00191 return (val);
00192 }