xref: /original-bsd/usr.bin/yacc/symtab.c (revision 0999a820)
1 /*
2  * Copyright (c) 1989 The Regents of the University of California.
3  * All rights reserved.
4  *
5  * This code is derived from software contributed to Berkeley by
6  * Robert Paul Corbett.
7  *
8  * %sccs.include.redist.c%
9  */
10 
11 #ifndef lint
12 static char sccsid[] = "@(#)symtab.c	5.3 (Berkeley) 06/01/90";
13 #endif /* not lint */
14 
15 #include "defs.h"
16 
17 /* TABLE_SIZE is the number of entries in the symbol table. */
18 /* TABLE_SIZE must be a power of two.			    */
19 
20 #define	TABLE_SIZE 1024
21 
22 
23 bucket **symbol_table;
24 bucket *first_symbol;
25 bucket *last_symbol;
26 
27 
28 int
29 hash(name)
30 char *name;
31 {
32     register char *s;
33     register int c, k;
34 
35     assert(name && *name);
36     s = name;
37     k = *s;
38     while (c = *++s)
39 	k = (31*k + c) & (TABLE_SIZE - 1);
40 
41     return (k);
42 }
43 
44 
45 bucket *
46 make_bucket(name)
47 char *name;
48 {
49     register bucket *bp;
50 
51     assert(name);
52     bp = (bucket *) MALLOC(sizeof(bucket));
53     if (bp == 0) no_space();
54     bp->link = 0;
55     bp->next = 0;
56     bp->name = MALLOC(strlen(name) + 1);
57     if (bp->name == 0) no_space();
58     bp->tag = 0;
59     bp->value = UNDEFINED;
60     bp->index = 0;
61     bp->prec = 0;
62     bp-> class = UNKNOWN;
63     bp->assoc = TOKEN;
64 
65     if (bp->name == 0) no_space();
66     strcpy(bp->name, name);
67 
68     return (bp);
69 }
70 
71 
72 bucket *
73 lookup(name)
74 char *name;
75 {
76     register bucket *bp, **bpp;
77 
78     bpp = symbol_table + hash(name);
79     bp = *bpp;
80 
81     while (bp)
82     {
83 	if (strcmp(name, bp->name) == 0) return (bp);
84 	bpp = &bp->link;
85 	bp = *bpp;
86     }
87 
88     *bpp = bp = make_bucket(name);
89     last_symbol->next = bp;
90     last_symbol = bp;
91 
92     return (bp);
93 }
94 
95 
96 create_symbol_table()
97 {
98     register int i;
99     register bucket *bp;
100 
101     symbol_table = (bucket **) MALLOC(TABLE_SIZE*sizeof(bucket *));
102     if (symbol_table == 0) no_space();
103     for (i = 0; i < TABLE_SIZE; i++)
104 	symbol_table[i] = 0;
105 
106     bp = make_bucket("error");
107     bp->index = 1;
108     bp->class = TERM;
109 
110     first_symbol = bp;
111     last_symbol = bp;
112     symbol_table[hash("error")] = bp;
113 }
114 
115 
116 free_symbol_table()
117 {
118     FREE(symbol_table);
119     symbol_table = 0;
120 }
121 
122 
123 free_symbols()
124 {
125     register bucket *p, *q;
126 
127     for (p = first_symbol; p; p = q)
128     {
129 	q = p->next;
130 	FREE(p);
131     }
132 }
133