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