Simple data structures / objects in plain C Snapshot
|
00001 /* Copyright (c) Michael Moser (2011) . 3-clause BSD License applies */ 00002 00003 #include "hashfunction.h" 00004 00005 00006 00007 HASH_VALUE HASHFUNCTION_sample_hash_func(void * keydata, ssize_t key_length) 00008 { 00009 unsigned char * key = (unsigned char *) keydata; 00010 HASH_VALUE hash_val = 0; 00011 00012 if (key_length != -1 ) { 00013 do { 00014 hash_val = (hash_val<<5) + hash_val + *key++; 00015 key_length --; 00016 } while (key_length != 0); 00017 return hash_val; 00018 } else { 00019 00020 00021 while (*key ) { 00022 hash_val = (hash_val<<5) + hash_val + *key++; 00023 00024 } 00025 return hash_val; 00026 } 00027 00028 } 00029 00030 HASH_VALUE HASHFUNCTION_PJW(void * keydata, ssize_t key_length) 00031 { 00032 unsigned char * key = (unsigned char *) keydata; 00033 HASH_VALUE g = 0, hash_val = 0; 00034 00035 if (key_length != -1) { 00036 do { 00037 hash_val = (hash_val<<4) + hash_val + *key++; 00038 g = hash_val & 0xF0000000; 00039 if (g) { 00040 hash_val = hash_val ^ ( g >> 24); 00041 hash_val = hash_val ^ g; 00042 } 00043 key_length --; 00044 } while (key_length != 0); 00045 00046 return hash_val; 00047 } else { 00048 00049 00050 while (*key ) { 00051 hash_val = (hash_val<<4) + hash_val + *key++; 00052 g = hash_val & 0xF0000000; 00053 if (g) { 00054 hash_val = hash_val ^ ( g >> 24); 00055 hash_val = hash_val ^ g; 00056 } 00057 } 00058 return hash_val; 00059 } 00060 } 00061 00062 HASH_VALUE HASHFUNCTION_rotating(void * keydata, ssize_t key_length) 00063 { 00064 HASH_VALUE hash; 00065 unsigned char * key = (unsigned char *) keydata; 00066 ssize_t i; 00067 00068 if (key_length != -1) { 00069 for (hash = key_length, i=0; i<key_length; ++i) { 00070 hash = (hash<<4)^(hash>>28) ^ key[i]; 00071 } 00072 return hash; 00073 } else { 00074 00075 00076 for (hash = ((size_t)*key) << 16; *key ; ++key) { 00077 hash = (hash<<4)^(hash>>28) ^ (*key); 00078 } 00079 return hash; 00080 } 00081 } 00082 00083 HASH_VALUE HASHFUNCTION_shift_and_xor(void * keydata, ssize_t key_length) 00084 { 00085 HASH_VALUE hash; 00086 unsigned char * key = (unsigned char *) keydata; 00087 ssize_t i; 00088 00089 if (key_length != -1) { 00090 for (hash = key_length, i=0; i<key_length; ++i) { 00091 hash ^= (hash<<5) + (hash>>2) + key[i]; 00092 } 00093 return hash; 00094 } else { 00095 00096 00097 for (hash = ((size_t)*key) << 16; *key ; ++key) { 00098 hash ^= (hash<<5) + (hash>>2) + (*key); 00099 } 00100 return hash; 00101 } 00102 } 00103 00104 00105 HASH_VALUE HASHFUNCTION_Fowler_Noll_Vo(void * keydata, ssize_t key_length) 00106 { 00107 HASH_VALUE hash = 2166136261U; 00108 unsigned char * key = (unsigned char *) keydata; 00109 ssize_t i; 00110 00111 if (key_length != -1) { 00112 for (hash = 0, i=0; i<key_length; ++i) { 00113 hash = ( hash * 16777619U ) ^ key[i]; 00114 } 00115 return hash; 00116 } else { 00117 00118 00119 for (hash = 0; *key ; ++key) { 00120 hash = ( hash * 16777619U ) ^ (*key); 00121 } 00122 return hash; 00123 } 00124 } 00125 00126 HASH_VALUE HASHFUNCTION_Bob_Jenkins_one_at_a_time(void * keydata, ssize_t key_length) 00127 { 00128 HASH_VALUE h = 2166136261U; 00129 unsigned char * key = (unsigned char *) keydata; 00130 ssize_t i; 00131 00132 00133 if (key_length != -1) { 00134 00135 for ( i = 0; i < key_length; i++ ) { 00136 h += key[i]; 00137 h += ( h << 10 ); 00138 h ^= ( h >> 6 ); 00139 } 00140 00141 h += ( h << 3 ); 00142 h ^= ( h >> 11 ); 00143 h += ( h << 15 ); 00144 00145 return h; 00146 00147 } else { 00148 00149 00150 for ( ; *key ; ++key ) { 00151 h += *key; 00152 h += ( h << 10 ); 00153 h ^= ( h >> 6 ); 00154 } 00155 00156 h += ( h << 3 ); 00157 h ^= ( h >> 11 ); 00158 h += ( h << 15 ); 00159 00160 return h; 00161 } 00162 } 00163 00164 HASH_VALUE HASHFUNCTION_ELF(void * keydata, ssize_t key_length) 00165 { 00166 HASH_VALUE h = 2166136261U,g; 00167 unsigned char * key = (unsigned char *) keydata; 00168 ssize_t i; 00169 00170 if (key_length != -1) { 00171 00172 for ( i = 0; i < key_length; i++ ) { 00173 h = ( h << 4 ) + key[i]; 00174 g = h & 0xf0000000L; 00175 00176 if ( g != 0 ) 00177 h ^= g >> 24; 00178 00179 h &= ~g; 00180 } 00181 return h; 00182 00183 } else { 00184 00185 00186 for ( ; *key ;key++ ) { 00187 h = ( h << 4 ) + *key; 00188 g = h & 0xf0000000L; 00189 00190 if ( g != 0 ) 00191 h ^= g >> 24; 00192 00193 h &= ~g; 00194 00195 return h; 00196 } 00197 00198 return h; 00199 } 00200 } 00201 00202 #define hashsize(n) ( 1U << (n) ) 00203 #define hashmask(n) ( hashsize ( n ) - 1 ) 00204 00205 #define mix(a,b,c) \ 00206 { \ 00207 a -= b; a -= c; a ^= ( c >> 13 ); \ 00208 b -= c; b -= a; b ^= ( a << 8 ); \ 00209 c -= a; c -= b; c ^= ( b >> 13 ); \ 00210 a -= b; a -= c; a ^= ( c >> 12 ); \ 00211 b -= c; b -= a; b ^= ( a << 16 ); \ 00212 c -= a; c -= b; c ^= ( b >> 5 ); \ 00213 a -= b; a -= c; a ^= ( c >> 3 ); \ 00214 b -= c; b -= a; b ^= ( a << 10 ); \ 00215 c -= a; c -= b; c ^= ( b >> 15 ); \ 00216 } 00217 00218 #define BJ_INIT_VAL 2166136261U 00219 00220 HASH_VALUE HASHFUNCTION_Bob_Jenkins(void * keydata, ssize_t length) 00221 { 00222 unsigned char *k = keydata; 00223 unsigned a, b; 00224 unsigned c = BJ_INIT_VAL; 00225 unsigned len = length; 00226 00227 a = b = 0x9e3779b9; 00228 00229 if (length != -1) { 00230 00231 while ( len >= 12 ) { 00232 a += ( k[0] + ( (unsigned)k[1] << 8 ) 00233 + ( (unsigned)k[2] << 16 ) 00234 + ( (unsigned)k[3] << 24 ) ); 00235 b += ( k[4] + ( (unsigned)k[5] << 8 ) 00236 + ( (unsigned)k[6] << 16 ) 00237 + ( (unsigned)k[7] << 24 ) ); 00238 c += ( k[8] + ( (unsigned)k[9] << 8 ) 00239 + ( (unsigned)k[10] << 16 ) 00240 + ( (unsigned)k[11] << 24 ) ); 00241 00242 mix ( a, b, c ); 00243 00244 k += 12; 00245 len -= 12; 00246 } 00247 } else { 00248 size_t pos_k = 0; 00249 unsigned char *next_k; 00250 00251 00252 length = 0; 00253 00254 while(1) { 00255 00256 for(pos_k = 0, next_k = (unsigned char *) k; 00257 *next_k && pos_k<12 ; 00258 pos_k++, next_k++); 00259 00260 length += pos_k; 00261 00262 if (pos_k < 12) { 00263 len = pos_k; 00264 break; 00265 } 00266 00267 a += ( k[0] + ( (unsigned)k[1] << 8 ) 00268 + ( (unsigned)k[2] << 16 ) 00269 + ( (unsigned)k[3] << 24 ) ); 00270 b += ( k[4] + ( (unsigned)k[5] << 8 ) 00271 + ( (unsigned)k[6] << 16 ) 00272 + ( (unsigned)k[7] << 24 ) ); 00273 c += ( k[8] + ( (unsigned)k[9] << 8 ) 00274 + ( (unsigned)k[10] << 16 ) 00275 + ( (unsigned)k[11] << 24 ) ); 00276 00277 mix ( a, b, c ); 00278 00279 k += 12; 00280 00281 } 00282 } 00283 00284 c += length; 00285 00286 switch ( len ) { 00287 case 11: c += ( (unsigned)k[10] << 24 ); 00288 case 10: c += ( (unsigned)k[9] << 16 ); 00289 case 9 : c += ( (unsigned)k[8] << 8 ); 00290 /* First byte of c reserved for length */ 00291 case 8 : b += ( (unsigned)k[7] << 24 ); 00292 case 7 : b += ( (unsigned)k[6] << 16 ); 00293 case 6 : b += ( (unsigned)k[5] << 8 ); 00294 case 5 : b += k[4]; 00295 case 4 : a += ( (unsigned)k[3] << 24 ); 00296 case 3 : a += ( (unsigned)k[2] << 16 ); 00297 case 2 : a += ( (unsigned)k[1] << 8 ); 00298 case 1 : a += k[0]; 00299 } 00300 00301 mix ( a, b, c ); 00302 00303 return c; 00304 }