1*38fd1498Szrj /* Hash tables for the CPP library.
2*38fd1498Szrj Copyright (C) 1986-2018 Free Software Foundation, Inc.
3*38fd1498Szrj Written by Per Bothner, 1994.
4*38fd1498Szrj Based on CCCP program by Paul Rubin, June 1986
5*38fd1498Szrj Adapted to ANSI C, Richard Stallman, Jan 1987
6*38fd1498Szrj
7*38fd1498Szrj This program is free software; you can redistribute it and/or modify it
8*38fd1498Szrj under the terms of the GNU General Public License as published by the
9*38fd1498Szrj Free Software Foundation; either version 3, or (at your option) any
10*38fd1498Szrj later version.
11*38fd1498Szrj
12*38fd1498Szrj This program is distributed in the hope that it will be useful,
13*38fd1498Szrj but WITHOUT ANY WARRANTY; without even the implied warranty of
14*38fd1498Szrj MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15*38fd1498Szrj GNU General Public License for more details.
16*38fd1498Szrj
17*38fd1498Szrj You should have received a copy of the GNU General Public License
18*38fd1498Szrj along with this program; see the file COPYING3. If not see
19*38fd1498Szrj <http://www.gnu.org/licenses/>.
20*38fd1498Szrj
21*38fd1498Szrj In other words, you are welcome to use, share and improve this program.
22*38fd1498Szrj You are forbidden to forbid anyone else to use, share and improve
23*38fd1498Szrj what you give them. Help stamp out software-hoarding! */
24*38fd1498Szrj
25*38fd1498Szrj #include "config.h"
26*38fd1498Szrj #include "system.h"
27*38fd1498Szrj #include "cpplib.h"
28*38fd1498Szrj #include "internal.h"
29*38fd1498Szrj
30*38fd1498Szrj static hashnode alloc_node (cpp_hash_table *);
31*38fd1498Szrj
32*38fd1498Szrj /* Return an identifier node for hashtable.c. Used by cpplib except
33*38fd1498Szrj when integrated with the C front ends. */
34*38fd1498Szrj static hashnode
alloc_node(cpp_hash_table * table)35*38fd1498Szrj alloc_node (cpp_hash_table *table)
36*38fd1498Szrj {
37*38fd1498Szrj cpp_hashnode *node;
38*38fd1498Szrj
39*38fd1498Szrj node = XOBNEW (&table->pfile->hash_ob, cpp_hashnode);
40*38fd1498Szrj memset (node, 0, sizeof (cpp_hashnode));
41*38fd1498Szrj return HT_NODE (node);
42*38fd1498Szrj }
43*38fd1498Szrj
44*38fd1498Szrj /* Set up the identifier hash table. Use TABLE if non-null, otherwise
45*38fd1498Szrj create our own. */
46*38fd1498Szrj void
_cpp_init_hashtable(cpp_reader * pfile,cpp_hash_table * table)47*38fd1498Szrj _cpp_init_hashtable (cpp_reader *pfile, cpp_hash_table *table)
48*38fd1498Szrj {
49*38fd1498Szrj struct spec_nodes *s;
50*38fd1498Szrj
51*38fd1498Szrj if (table == NULL)
52*38fd1498Szrj {
53*38fd1498Szrj pfile->our_hashtable = 1;
54*38fd1498Szrj table = ht_create (13); /* 8K (=2^13) entries. */
55*38fd1498Szrj table->alloc_node = alloc_node;
56*38fd1498Szrj
57*38fd1498Szrj obstack_specify_allocation (&pfile->hash_ob, 0, 0, xmalloc, free);
58*38fd1498Szrj }
59*38fd1498Szrj
60*38fd1498Szrj table->pfile = pfile;
61*38fd1498Szrj pfile->hash_table = table;
62*38fd1498Szrj
63*38fd1498Szrj /* Now we can initialize things that use the hash table. */
64*38fd1498Szrj _cpp_init_directives (pfile);
65*38fd1498Szrj _cpp_init_internal_pragmas (pfile);
66*38fd1498Szrj
67*38fd1498Szrj s = &pfile->spec_nodes;
68*38fd1498Szrj s->n_defined = cpp_lookup (pfile, DSC("defined"));
69*38fd1498Szrj s->n_true = cpp_lookup (pfile, DSC("true"));
70*38fd1498Szrj s->n_false = cpp_lookup (pfile, DSC("false"));
71*38fd1498Szrj s->n__VA_ARGS__ = cpp_lookup (pfile, DSC("__VA_ARGS__"));
72*38fd1498Szrj s->n__VA_ARGS__->flags |= NODE_DIAGNOSTIC;
73*38fd1498Szrj s->n__VA_OPT__ = cpp_lookup (pfile, DSC("__VA_OPT__"));
74*38fd1498Szrj s->n__VA_OPT__->flags |= NODE_DIAGNOSTIC;
75*38fd1498Szrj s->n__has_include__ = cpp_lookup (pfile, DSC("__has_include__"));
76*38fd1498Szrj s->n__has_include_next__ = cpp_lookup (pfile, DSC("__has_include_next__"));
77*38fd1498Szrj }
78*38fd1498Szrj
79*38fd1498Szrj /* Tear down the identifier hash table. */
80*38fd1498Szrj void
_cpp_destroy_hashtable(cpp_reader * pfile)81*38fd1498Szrj _cpp_destroy_hashtable (cpp_reader *pfile)
82*38fd1498Szrj {
83*38fd1498Szrj if (pfile->our_hashtable)
84*38fd1498Szrj {
85*38fd1498Szrj ht_destroy (pfile->hash_table);
86*38fd1498Szrj obstack_free (&pfile->hash_ob, 0);
87*38fd1498Szrj }
88*38fd1498Szrj }
89*38fd1498Szrj
90*38fd1498Szrj /* Returns the hash entry for the STR of length LEN, creating one
91*38fd1498Szrj if necessary. */
92*38fd1498Szrj cpp_hashnode *
cpp_lookup(cpp_reader * pfile,const unsigned char * str,unsigned int len)93*38fd1498Szrj cpp_lookup (cpp_reader *pfile, const unsigned char *str, unsigned int len)
94*38fd1498Szrj {
95*38fd1498Szrj /* ht_lookup cannot return NULL. */
96*38fd1498Szrj return CPP_HASHNODE (ht_lookup (pfile->hash_table, str, len, HT_ALLOC));
97*38fd1498Szrj }
98*38fd1498Szrj
99*38fd1498Szrj /* Determine whether the str STR, of length LEN, is a defined macro. */
100*38fd1498Szrj int
cpp_defined(cpp_reader * pfile,const unsigned char * str,int len)101*38fd1498Szrj cpp_defined (cpp_reader *pfile, const unsigned char *str, int len)
102*38fd1498Szrj {
103*38fd1498Szrj cpp_hashnode *node;
104*38fd1498Szrj
105*38fd1498Szrj node = CPP_HASHNODE (ht_lookup (pfile->hash_table, str, len, HT_NO_INSERT));
106*38fd1498Szrj
107*38fd1498Szrj /* If it's of type NT_MACRO, it cannot be poisoned. */
108*38fd1498Szrj return node && node->type == NT_MACRO;
109*38fd1498Szrj }
110*38fd1498Szrj
111*38fd1498Szrj /* We don't need a proxy since the hash table's identifier comes first
112*38fd1498Szrj in cpp_hashnode. However, in case this is ever changed, we have a
113*38fd1498Szrj static assertion for it. */
114*38fd1498Szrj extern char proxy_assertion_broken[offsetof (struct cpp_hashnode, ident) == 0 ? 1 : -1];
115*38fd1498Szrj
116*38fd1498Szrj /* For all nodes in the hashtable, callback CB with parameters PFILE,
117*38fd1498Szrj the node, and V. */
118*38fd1498Szrj void
cpp_forall_identifiers(cpp_reader * pfile,cpp_cb cb,void * v)119*38fd1498Szrj cpp_forall_identifiers (cpp_reader *pfile, cpp_cb cb, void *v)
120*38fd1498Szrj {
121*38fd1498Szrj ht_forall (pfile->hash_table, (ht_cb) cb, v);
122*38fd1498Szrj }
123