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 #include "xsb_config.h"
00027 #include "xsb_debug.h"
00028
00029 #include <string.h>
00030 #include <stdio.h>
00031 #include <stdlib.h>
00032
00033 #include "auxlry.h"
00034 #include "cell_xsb.h"
00035 #include "hash_xsb.h"
00036 #include "psc_xsb.h"
00037 #include "flags_xsb.h"
00038 #include "memory_xsb.h"
00039 #include "thread_xsb.h"
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049 Hash_Table symbol_table = {2053, 0, NULL};
00050 Hash_Table string_table = {16381, 0, NULL};
00051
00052
00053
00054
00055
00056
00057
00058 #define NUM_OF_PRIMES 16
00059 static unsigned int primes[NUM_OF_PRIMES] =
00060 {127, 257, 509, 1021, 2053, 4099, 8191, 16381, 32771, 65537, 131071,
00061 262147, 524287, 1048573, 2097143, 4194301};
00062
00063
00064
00065
00066
00067
00068
00069 unsigned long next_prime(unsigned long some_int) {
00070
00071 byte i;
00072
00073 i = 0;
00074 while ( (some_int >= primes[i]) && (i < NUM_OF_PRIMES) )
00075 i++;
00076
00077 if (i < NUM_OF_PRIMES)
00078 return (primes[i]);
00079 else
00080 return (2 * some_int - 1);
00081 }
00082
00083
00084
00085
00086
00087
00088
00089 unsigned long hash(char *obj_name, byte arity, unsigned long hash_table_size) {
00090
00091 unsigned long hashval, temp;
00092 int i, j, k;
00093
00094 hashval = 0;
00095 if (*obj_name != '\0')
00096 for (k=0; k<10; k++) {
00097 for (i = 4; i >= 0; i--) {
00098 temp = 0;
00099 for (j = 0; j < 5; j++) {
00100 temp = (temp << i) + *obj_name;
00101 obj_name++;
00102 if (*obj_name == '\0') {
00103 hashval = hashval + temp;
00104 goto Done;
00105 }
00106 }
00107 hashval = hashval + temp;
00108 }
00109 }
00110 Done:
00111 return ((hashval + arity) MOD hash_table_size);
00112 }
00113
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142 void expand_symbol_table() {
00143
00144 Pair *new_table, *bucket_ptr, cur_pair, next_pair;
00145 Psc cur_psc;
00146 unsigned long index, new_size, new_index;
00147
00148 new_size = next_prime(symbol_table.size);
00149 new_table = (Pair *)mem_calloc(new_size, sizeof(void *),ATOM_SPACE);
00150
00151 for (bucket_ptr = (Pair *)symbol_table.table, index = 0;
00152 index < symbol_table.size; bucket_ptr++, index++)
00153
00154 for (cur_pair = *bucket_ptr; cur_pair != NULL; cur_pair = next_pair) {
00155 next_pair = pair_next(cur_pair);
00156 cur_psc = pair_psc(cur_pair);
00157 new_index = hash(get_name(cur_psc), get_arity(cur_psc), new_size);
00158 pair_next(cur_pair) = new_table[new_index];
00159 new_table[new_index] = cur_pair;
00160 }
00161
00162 mem_dealloc((void *)symbol_table.table,symbol_table.size,ATOM_SPACE);
00163 symbol_table.size = new_size;
00164 symbol_table.table = (void **)new_table;
00165
00166 }
00167
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177
00178 void expand_string_table() {
00179
00180 void **new_table, **bucket_ptr, **cur_entry, **next_entry;
00181 char *string;
00182 unsigned long index, new_size, new_index;
00183
00184 new_size = next_prime(string_table.size);
00185 new_table = (void **)mem_calloc(new_size, sizeof(void *),STRING_SPACE);
00186
00187 for (bucket_ptr = string_table.table, index = 0;
00188 index < string_table.size;
00189 bucket_ptr++, index++)
00190 for (cur_entry = (void **)*bucket_ptr;
00191 cur_entry != NULL;
00192 cur_entry = next_entry) {
00193 next_entry = (void **)*cur_entry;
00194 string = (char *)(cur_entry + 1);
00195 new_index = hash(string, 0, new_size);
00196 *cur_entry = new_table[new_index];
00197 new_table[new_index] = (void *)cur_entry;
00198 }
00199
00200 mem_dealloc((void *)string_table.table,string_table.size,STRING_SPACE);
00201 string_table.size = new_size;
00202 string_table.table = new_table;
00203
00204 }
00205
00206
00207
00208
00209
00210
00211
00212
00213
00214 void symbol_table_stats(CTXTdecl) {
00215
00216 unsigned long i, symbols, bucket_contains, used_buckets, unused_buckets,
00217 fullest_bucket_size, fullest_bucket_num, last_index;
00218 int first_index;
00219 Pair pair_ptr;
00220
00221 SYS_MUTEX_LOCK( MUTEX_SYMBOL ) ;
00222
00223 symbols = used_buckets = unused_buckets = last_index = 0;
00224 fullest_bucket_size = fullest_bucket_num = 0;
00225 first_index = -1;
00226
00227 for (i = 0; i < symbol_table.size; i++) {
00228 if (symbol_table.table[i] != NULL) {
00229 if (first_index == -1)
00230 first_index = i;
00231 last_index = i;
00232 used_buckets++;
00233 bucket_contains = 0;
00234 for (pair_ptr = (Pair)symbol_table.table[i]; pair_ptr != NULL;
00235 pair_ptr = pair_next(pair_ptr)) {
00236 symbols++;
00237 bucket_contains++;
00238 }
00239 if (bucket_contains > fullest_bucket_size) {
00240 fullest_bucket_size = bucket_contains;
00241 fullest_bucket_num = i;
00242 }
00243 }
00244 else
00245 unused_buckets++;
00246 }
00247 printf("\nSymbol table statistics:");
00248 printf("\n------------------------\n");
00249 printf("Table Size:\t%lu\n", symbol_table.size);
00250 printf("Total Symbols:\t%lu\n", symbols);
00251 if (symbols != symbol_table.contains)
00252 printf("Symbol count incorrect in 'symbol_table': %lu\n",
00253 symbol_table.contains);
00254 printf("\tused buckets:\t%lu (range: [%d, %lu])\n", used_buckets,
00255 first_index, last_index);
00256 printf("\tunused buckets:\t%lu\n", unused_buckets);
00257 printf("\tmaximum bucket size:\t%lu (#: %lu)\n", fullest_bucket_size,
00258 fullest_bucket_num);
00259
00260 SYS_MUTEX_UNLOCK( MUTEX_SYMBOL ) ;
00261
00262 }
00263
00264
00265 void string_table_stats(CTXTdecl) {
00266
00267 unsigned long i, strings, bucket_contains, used_buckets, unused_buckets,
00268 fullest_bucket_size, fullest_bucket_num, last_index;
00269 int first_index;
00270 void *ptr;
00271
00272 SYS_MUTEX_LOCK( MUTEX_STRING ) ;
00273
00274 strings = used_buckets = unused_buckets = last_index = 0;
00275 fullest_bucket_size = fullest_bucket_num = 0;
00276 first_index = -1;
00277
00278 for (i = 0; i < string_table.size; i++) {
00279 if (string_table.table[i] != NULL) {
00280 if (first_index == -1)
00281 first_index = i;
00282 last_index = i;
00283 used_buckets++;
00284 bucket_contains = 0;
00285 for (ptr = string_table.table[i]; ptr != NULL; ptr = *(void **)ptr) {
00286 strings++;
00287 bucket_contains++;
00288 }
00289 if (bucket_contains > fullest_bucket_size) {
00290 fullest_bucket_size = bucket_contains;
00291 fullest_bucket_num = i;
00292 }
00293 }
00294 else
00295 unused_buckets++;
00296 }
00297 printf("\nString table statistics:");
00298 printf("\n------------------------\n");
00299 printf("Table Size:\t%lu\n", string_table.size);
00300 printf("Total Strings:\t%lu\n", strings);
00301 if (strings != string_table.contains)
00302 printf("String count incorrect in 'string_table': %lu\n",
00303 string_table.contains);
00304 printf("\tused buckets:\t%lu (range: [%d, %lu])\n", used_buckets,
00305 first_index, last_index);
00306 printf("\tunused buckets:\t%lu\n", unused_buckets);
00307 printf("\tmaximum bucket size:\t%lu (#: %lu)\n", fullest_bucket_size,
00308 fullest_bucket_num);
00309
00310 SYS_MUTEX_UNLOCK( MUTEX_STRING ) ;
00311
00312 }
00313
00314 void free_unused_strings() {
00315 unsigned long i;
00316 void *ptr, *prevptr;
00317 int used = 0, unused = 0;
00318
00319 for (i = 0; i < string_table.size; i++) {
00320 if (string_table.table[i] != NULL) {
00321 prevptr = &string_table.table[i];
00322 ptr = *(void **)prevptr;
00323 while (ptr != NULL) {
00324 if ((*(Integer *)ptr) & 1) {
00325 used++;
00326 (*(Integer *)ptr) &= ~1;
00327 prevptr = ptr;
00328 ptr = *(void **)ptr;
00329 } else {
00330 unused++;
00331
00332 *(void **)prevptr = *(void **)ptr;
00333 mem_dealloc(ptr,strlen(((char *)ptr)+4)+sizeof(void *)+1,STRING_SPACE);
00334
00335 ptr = *(void **)prevptr;
00336 string_table.contains--;
00337
00338 }
00339 }
00340 }
00341 }
00342
00343
00344 }
00345
00346
00347