]> git.saurik.com Git - bison.git/blame - src/print_graph.c
Merge remote-tracking branch 'origin/maint'
[bison.git] / src / print_graph.c
CommitLineData
35fe0834 1/* Output a graph of the generated parser, for Bison.
16bb742f 2
34136e65 3 Copyright (C) 2001-2007, 2009-2012 Free Software Foundation, Inc.
ce4d5ce0
AD
4
5 This file is part of Bison, the GNU Compiler Compiler.
6
f16b0819 7 This program is free software: you can redistribute it and/or modify
ce4d5ce0 8 it under the terms of the GNU General Public License as published by
f16b0819
PE
9 the Free Software Foundation, either version 3 of the License, or
10 (at your option) any later version.
ce4d5ce0 11
f16b0819 12 This program is distributed in the hope that it will be useful,
ce4d5ce0
AD
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
f16b0819 18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
ce4d5ce0 19
2cec9080 20#include <config.h>
ce4d5ce0 21#include "system.h"
16bb742f 22
ce4d5ce0 23#include "LR0.h"
16bb742f 24#include "closure.h"
ce4d5ce0 25#include "complain.h"
16bb742f
PE
26#include "conflicts.h"
27#include "files.h"
ce4d5ce0 28#include "getargs.h"
16bb742f 29#include "gram.h"
35fe0834 30#include "graphviz.h"
16bb742f 31#include "lalr.h"
ce4d5ce0 32#include "print_graph.h"
16bb742f
PE
33#include "reader.h"
34#include "state.h"
35#include "symtab.h"
ce4d5ce0 36
8adfa272 37
6b98e4b5
AD
38/*----------------------------.
39| Construct the node labels. |
40`----------------------------*/
8adfa272 41
ce4d5ce0 42static void
16bb742f 43print_core (struct obstack *oout, state *s)
ce4d5ce0 44{
f6fbd3da 45 size_t i;
16bb742f 46 item_number *sitems = s->items;
f6fbd3da 47 size_t snritems = s->nitems;
22c2cbc0 48
2e729273 49 /* Output all the items of a state, not only its kernel. */
05811fd7 50 if (report_flag & report_itemsets)
30171f79 51 {
5123689b 52 closure (sitems, snritems);
30171f79 53 sitems = itemset;
b09f4f48 54 snritems = nitemset;
30171f79 55 }
22c2cbc0 56
35fe0834 57 obstack_fgrow1 (oout, "%d", s->number);
5123689b 58 for (i = 0; i < snritems; i++)
ce4d5ce0 59 {
16bb742f
PE
60 item_number *sp;
61 item_number *sp1;
62 rule_number r;
c4b66126 63
2e729273 64 sp1 = sp = ritem + sitems[i];
ce4d5ce0 65
75142d45 66 while (*sp >= 0)
e9690142 67 sp++;
ce4d5ce0 68
16bb742f 69 r = item_number_as_rule_number (*sp);
ce4d5ce0 70
35fe0834 71 obstack_fgrow1 (oout, "\n%s -> ", rules[r].lhs->tag);
ce4d5ce0 72
16bb742f 73 for (sp = rules[r].rhs; sp < sp1; sp++)
e9690142 74 obstack_fgrow1 (oout, "%s ", symbols[*sp]->tag);
ce4d5ce0 75
d4e7d3a1 76 obstack_1grow (oout, '.');
22c2cbc0 77
75142d45 78 for (/* Nothing */; *sp >= 0; ++sp)
e9690142 79 obstack_fgrow1 (oout, " %s", symbols[*sp]->tag);
d4e7d3a1 80
742e4900 81 /* Experimental feature: display the lookahead tokens. */
255a6b90
JD
82 if (report_flag & report_lookahead_tokens
83 && item_number_is_rule_number (*sp1))
e9690142
JD
84 {
85 /* Find the reduction we are handling. */
86 reductions *reds = s->reductions;
87 int redno = state_reduction_find (s, &rules[r]);
88
89 /* Print them if there are. */
90 if (reds->lookahead_tokens && redno != -1)
91 {
92 bitset_iterator biter;
93 int k;
94 char const *sep = "";
95 obstack_sgrow (oout, "[");
96 BITSET_FOR_EACH (biter, reds->lookahead_tokens[redno], k, 0)
97 {
98 obstack_fgrow2 (oout, "%s%s", sep, symbols[k]->tag);
99 sep = ", ";
100 }
101 obstack_sgrow (oout, "]");
102 }
103 }
ce4d5ce0 104 }
ce4d5ce0
AD
105}
106
08a946e0
AD
107
108/*---------------------------------------------------------------.
109| Output in graph_obstack edges specifications in incidence with |
110| current node. |
111`---------------------------------------------------------------*/
112
ce4d5ce0 113static void
35fe0834 114print_actions (state const *s, FILE *fgraph)
ce4d5ce0
AD
115{
116 int i;
d954473d 117
35fe0834 118 transitions const *trans = s->transitions;
22c2cbc0 119
35fe0834 120 if (!trans->num && !s->reductions)
5092aba5 121 return;
ce4d5ce0 122
16bb742f
PE
123 for (i = 0; i < trans->num; i++)
124 if (!TRANSITION_IS_DISABLED (trans, i))
d954473d 125 {
e9690142
JD
126 state *s1 = trans->states[i];
127 symbol_number sym = s1->accessing_symbol;
128
129 /* Shifts are solid, gotos are dashed, and error is dotted. */
130 char const *style =
131 (TRANSITION_IS_ERROR (trans, i) ? "dotted"
132 : TRANSITION_IS_SHIFT (trans, i) ? "solid"
133 : "dashed");
134
135 if (TRANSITION_IS_ERROR (trans, i)
f518dbaf 136 && STRNEQ (symbols[sym]->tag, "error"))
e9690142
JD
137 abort ();
138 output_edge (s->number, s1->number,
139 TRANSITION_IS_ERROR (trans, i) ? NULL : symbols[sym]->tag,
140 style, fgraph);
d954473d 141 }
ce4d5ce0
AD
142}
143
08a946e0
AD
144
145/*-------------------------------------------------------------.
146| Output in FGRAPH the current node specifications and exiting |
147| edges. |
148`-------------------------------------------------------------*/
149
ce4d5ce0 150static void
35fe0834 151print_state (state *s, FILE *fgraph)
ce4d5ce0 152{
600cad3b 153 struct obstack node_obstack;
ce4d5ce0 154
35fe0834 155 /* A node's label contains its items. */
600cad3b 156 obstack_init (&node_obstack);
16bb742f 157 print_core (&node_obstack, s);
08a946e0 158 obstack_1grow (&node_obstack, '\0');
35fe0834
PE
159 output_node (s->number, obstack_finish (&node_obstack), fgraph);
160 obstack_free (&node_obstack, 0);
342b8b6e 161
08a946e0 162 /* Output the edges. */
35fe0834 163 print_actions (s, fgraph);
ce4d5ce0
AD
164}
165\f
166
167void
168print_graph (void)
169{
16bb742f 170 state_number i;
35fe0834
PE
171 FILE *fgraph = xfopen (spec_graph_file, "w");
172 start_graph (fgraph);
ce4d5ce0 173
08a946e0 174 /* Output nodes and edges. */
9e7f6bbd 175 new_closure (nritems);
ce4d5ce0 176 for (i = 0; i < nstates; i++)
35fe0834 177 print_state (states[i], fgraph);
2e729273 178 free_closure ();
ce4d5ce0 179
35fe0834 180 finish_graph (fgraph);
342b8b6e 181 xfclose (fgraph);
ce4d5ce0 182}