symtab.c revision 235723
1/* $Id: symtab.c,v 1.9 2010/11/24 15:12:29 tom Exp $ */ 2 3#include "defs.h" 4 5/* TABLE_SIZE is the number of entries in the symbol table. */ 6/* TABLE_SIZE must be a power of two. */ 7 8#define TABLE_SIZE 1024 9 10static bucket **symbol_table = 0; 11bucket *first_symbol; 12bucket *last_symbol; 13 14static int 15hash(const char *name) 16{ 17 const char *s; 18 int c, k; 19 20 assert(name && *name); 21 s = name; 22 k = *s; 23 while ((c = *++s) != 0) 24 k = (31 * k + c) & (TABLE_SIZE - 1); 25 26 return (k); 27} 28 29bucket * 30make_bucket(const char *name) 31{ 32 bucket *bp; 33 34 assert(name != 0); 35 36 bp = (bucket *)MALLOC(sizeof(bucket)); 37 NO_SPACE(bp); 38 39 bp->link = 0; 40 bp->next = 0; 41 42 bp->name = MALLOC(strlen(name) + 1); 43 NO_SPACE(bp->name); 44 45 bp->tag = 0; 46 bp->value = UNDEFINED; 47 bp->index = 0; 48 bp->prec = 0; 49 bp->class = UNKNOWN; 50 bp->assoc = TOKEN; 51 strcpy(bp->name, name); 52 53 return (bp); 54} 55 56bucket * 57lookup(const char *name) 58{ 59 bucket *bp, **bpp; 60 61 bpp = symbol_table + hash(name); 62 bp = *bpp; 63 64 while (bp) 65 { 66 if (strcmp(name, bp->name) == 0) 67 return (bp); 68 bpp = &bp->link; 69 bp = *bpp; 70 } 71 72 *bpp = bp = make_bucket(name); 73 last_symbol->next = bp; 74 last_symbol = bp; 75 76 return (bp); 77} 78 79void 80create_symbol_table(void) 81{ 82 int i; 83 bucket *bp; 84 85 symbol_table = (bucket **)MALLOC(TABLE_SIZE * sizeof(bucket *)); 86 NO_SPACE(symbol_table); 87 88 for (i = 0; i < TABLE_SIZE; i++) 89 symbol_table[i] = 0; 90 91 bp = make_bucket("error"); 92 bp->index = 1; 93 bp->class = TERM; 94 95 first_symbol = bp; 96 last_symbol = bp; 97 symbol_table[hash("error")] = bp; 98} 99 100void 101free_symbol_table(void) 102{ 103 FREE(symbol_table); 104 symbol_table = 0; 105} 106 107void 108free_symbols(void) 109{ 110 bucket *p, *q; 111 112 for (p = first_symbol; p; p = q) 113 { 114 q = p->next; 115 FREE(p); 116 } 117} 118