]> git.saurik.com Git - bison.git/blame - src/nullable.c
2007-02-27 Paolo Bonzini <bonzini@gnu.org>
[bison.git] / src / nullable.c
CommitLineData
09939714
PE
1/* Calculate which nonterminals can expand into the null string for Bison.
2
68cae94e
PE
3 Copyright (C) 1984, 1989, 2000, 2001, 2002, 2003, 2004, 2005, 2006
4 Free Software Foundation, Inc.
122c0aac 5
3519ec76 6 This file is part of Bison, the GNU Compiler Compiler.
122c0aac 7
3519ec76
AD
8 Bison is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
11 any later version.
122c0aac 12
3519ec76
AD
13 Bison is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
122c0aac 17
3519ec76
AD
18 You should have received a copy of the GNU General Public License
19 along with Bison; see the file COPYING. If not, write to
0fb669f9
PE
20 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
21 Boston, MA 02110-1301, USA. */
122c0aac
RS
22
23
3519ec76
AD
24/* Set up NULLABLE, a vector saying which nonterminals can expand into
25 the null string. NULLABLE[I - NTOKENS] is nonzero if symbol I can
ceed8467 26 do so. */
122c0aac 27
2cec9080 28#include <config.h>
122c0aac 29#include "system.h"
a0b76449 30
9bfe901c 31#include "getargs.h"
122c0aac 32#include "gram.h"
3519ec76 33#include "nullable.h"
a0b76449
PE
34#include "reduce.h"
35#include "symtab.h"
122c0aac 36
bb0027a9 37/* Linked list of rules. */
a0b76449 38typedef struct rule_list
e68e0410 39{
a0b76449
PE
40 struct rule_list *next;
41 rule *value;
42} rule_list;
e68e0410 43
bb0027a9 44bool *nullable = NULL;
122c0aac 45
6bb1878b
AD
46static void
47nullable_print (FILE *out)
48{
49 int i;
50 fputs ("NULLABLE\n", out);
51 for (i = ntokens; i < nsyms; i++)
09939714
PE
52 fprintf (out, "\t%s: %s\n", symbols[i]->tag,
53 nullable[i - ntokens] ? "yes" : "no");
6bb1878b
AD
54 fputs ("\n\n", out);
55}
56
122c0aac 57void
bb0027a9 58nullable_compute (void)
122c0aac 59{
a0b76449
PE
60 rule_number ruleno;
61 symbol_number *s1;
62 symbol_number *s2;
63 rule_list *p;
122c0aac 64
da2a7671 65 symbol_number *squeue = xnmalloc (nvars, sizeof *squeue);
f6fbd3da 66 size_t *rcount = xcalloc (nrules, sizeof *rcount);
ed8e1f68
AD
67 /* RITEM contains all the rules, including useless productions.
68 Hence we must allocate room for useless nonterminals too. */
da2a7671 69 rule_list **rsets = xcalloc (nvars, sizeof *rsets);
ed8e1f68 70 /* This is said to be more elements than we actually use.
9e7f6bbd 71 Supposedly NRITEMS - NRULES is enough. But why take the risk? */
da2a7671 72 rule_list *relts = xnmalloc (nritems + nvars + 1, sizeof *relts);
122c0aac 73
da2a7671 74 nullable = xcalloc (nvars, sizeof *nullable);
122c0aac 75
122c0aac 76 s1 = s2 = squeue;
122c0aac
RS
77 p = relts;
78
4b3d3a8e 79 for (ruleno = 0; ruleno < nrules; ++ruleno)
1a2b5d37 80 if (rules[ruleno].useful)
ed8e1f68 81 {
a0b76449
PE
82 rule *rules_ruleno = &rules[ruleno];
83 if (rules_ruleno->rhs[0] >= 0)
9c2c67e6
AD
84 {
85 /* This rule has a non empty RHS. */
a737b216 86 item_number *rp = NULL;
d0829076 87 bool any_tokens = false;
a737b216
PE
88 for (rp = rules_ruleno->rhs; *rp >= 0; ++rp)
89 if (ISTOKEN (*rp))
d0829076 90 any_tokens = true;
9c2c67e6
AD
91
92 /* This rule has only nonterminals: schedule it for the second
93 pass. */
94 if (!any_tokens)
a737b216 95 for (rp = rules_ruleno->rhs; *rp >= 0; ++rp)
9c2c67e6
AD
96 {
97 rcount[ruleno]++;
a737b216 98 p->next = rsets[*rp - ntokens];
a0b76449 99 p->value = rules_ruleno;
a737b216 100 rsets[*rp - ntokens] = p;
9c2c67e6
AD
101 p++;
102 }
103 }
104 else
81b51460 105 {
9c2c67e6 106 /* This rule has an empty RHS. */
4f82b42a
PE
107 aver (item_number_as_rule_number (rules_ruleno->rhs[0])
108 == ruleno);
09939714
PE
109 if (rules_ruleno->useful
110 && ! nullable[rules_ruleno->lhs->number - ntokens])
9c2c67e6 111 {
d0829076 112 nullable[rules_ruleno->lhs->number - ntokens] = true;
a0b76449 113 *s2++ = rules_ruleno->lhs->number;
9c2c67e6 114 }
81b51460 115 }
ed8e1f68 116 }
122c0aac
RS
117
118 while (s1 < s2)
09939714 119 for (p = rsets[*s1++ - ntokens]; p; p = p->next)
e3e4e814 120 {
a0b76449
PE
121 rule *r = p->value;
122 if (--rcount[r->number] == 0)
09939714 123 if (r->useful && ! nullable[r->lhs->number - ntokens])
122c0aac 124 {
d0829076 125 nullable[r->lhs->number - ntokens] = true;
a0b76449 126 *s2++ = r->lhs->number;
122c0aac 127 }
e3e4e814 128 }
122c0aac 129
afbb696d
PE
130 free (squeue);
131 free (rcount);
132 free (rsets);
133 free (relts);
6bb1878b 134
273a74fa 135 if (trace_flag & trace_sets)
6bb1878b 136 nullable_print (stderr);
122c0aac
RS
137}
138
139
140void
bb0027a9 141nullable_free (void)
122c0aac 142{
afbb696d 143 free (nullable);
122c0aac 144}