]> git.saurik.com Git - bison.git/blame - src/output.c
* tests/regression.at (Web2c Actions): Blindly move the actual
[bison.git] / src / output.c
CommitLineData
c3e23647 1/* Output the generated parsing program for bison,
255ef638
AD
2 Copyright 1984, 1986, 1989, 1992, 2000, 2001
3 Free Software Foundation, Inc.
c3e23647 4
9ee3c97b 5 This file is part of Bison, the GNU Compiler Compiler.
c3e23647 6
9ee3c97b
AD
7 Bison is free software; you can redistribute it and/or modify it
8 under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
10 any later version.
c3e23647 11
9ee3c97b
AD
12 Bison is distributed in the hope that it will be useful, but
13 WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 General Public License for more details.
c3e23647 16
9ee3c97b
AD
17 You should have received a copy of the GNU General Public License
18 along with Bison; see the file COPYING. If not, write to the Free
19 Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
20 02111-1307, USA. */
c3e23647
RS
21
22
255ef638
AD
23/* The parser tables consist of these tables. Marked ones needed only
24 for the semantic parser. Double marked are output only if switches
25 are set.
c3e23647 26
255ef638
AD
27 YYTRANSLATE = vector mapping yylex's token numbers into bison's
28 token numbers.
c3e23647 29
255ef638 30 ++ YYTNAME = vector of string-names indexed by bison token number.
c3e23647 31
255ef638
AD
32 ++ YYTOKNUM = vector of yylex token numbers corresponding to
33 entries in YYTNAME.
c3e23647 34
255ef638
AD
35 YYRLINE = vector of line-numbers of all rules. For yydebug
36 printouts.
c3e23647 37
255ef638
AD
38 YYRHS = vector of items of all rules. This is exactly what RITEMS
39 contains. For yydebug and for semantic parser.
c3e23647 40
255ef638 41 YYPRHS[R] = index in YYRHS of first item for rule R.
c3e23647 42
255ef638 43 YYR1[R] = symbol number of symbol that rule R derives.
c3e23647 44
255ef638 45 YYR2[R] = number of symbols composing right hand side of rule R.
c3e23647 46
255ef638
AD
47 + YYSTOS[S] = the symbol number of the symbol that leads to state
48 S.
e372befa 49
255ef638
AD
50 YYDEFACT[S] = default rule to reduce with in state s, when YYTABLE
51 doesn't specify something else to do. Zero means the default is an
52 error.
c3e23647 53
255ef638
AD
54 YYDEFGOTO[I] = default state to go to after a reduction of a rule
55 that generates variable NTOKENS + I, except when YYTABLE specifies
56 something else to do.
c3e23647 57
255ef638
AD
58 YYPACT[S] = index in YYTABLE of the portion describing state S.
59 The lookahead token's type is used to index that portion to find
60 out what to do.
c3e23647 61
255ef638
AD
62 If the value in YYTABLE is positive, we shift the token and go to
63 that state.
c3e23647 64
6c89f1c1 65 If the value is negative, it is minus a rule number to reduce by.
c3e23647 66
255ef638
AD
67 If the value is zero, the default action from YYDEFACT[S] is used.
68
69 YYPGOTO[I] = the index in YYTABLE of the portion describing what to
70 do after reducing a rule that derives variable I + NTOKENS. This
71 portion is indexed by the parser state number, S, as of before the
72 text for this nonterminal was read. The value from YYTABLE is the
73 state to go to if the corresponding value in YYCHECK is S.
74
75 YYTABLE = a vector filled with portions for different uses, found
76 via YYPACT and YYPGOTO.
77
78 YYCHECK = a vector indexed in parallel with YYTABLE. It indicates,
79 in a roundabout way, the bounds of the portion you are trying to
80 examine.
81
82 Suppose that the portion of yytable starts at index P and the index
83 to be examined within the portion is I. Then if YYCHECK[P+I] != I,
84 I is outside the bounds of what is actually allocated, and the
85 default (from YYDEFACT or YYDEFGOTO) should be used. Otherwise,
86 YYTABLE[P+I] should be used.
87
88 YYFINAL = the state number of the termination state. YYFLAG = most
89 negative short int. Used to flag ?? */
c3e23647 90
c3e23647 91#include "system.h"
14d3eb9b 92#include "quotearg.h"
ceed8467 93#include "getargs.h"
c3e23647
RS
94#include "files.h"
95#include "gram.h"
b2ca4022 96#include "LR0.h"
a0f6b076 97#include "complain.h"
6c89f1c1 98#include "output.h"
720d742f 99#include "lalr.h"
a70083a3 100#include "reader.h"
0619caf0 101#include "conflicts.h"
11d82f03 102#include "muscle_tab.h"
c3e23647 103
d019d655 104
c3e23647
RS
105static int nvectors;
106static int nentries;
342b8b6e
AD
107static short **froms = NULL;
108static short **tos = NULL;
109static short *tally = NULL;
110static short *width = NULL;
111static short *actrow = NULL;
112static short *state_count = NULL;
113static short *order = NULL;
114static short *base = NULL;
115static short *pos = NULL;
116static short *table = NULL;
117static short *check = NULL;
c3e23647
RS
118static int lowzero;
119static int high;
120
11d82f03 121struct obstack muscle_obstack;
f87685c3 122static struct obstack format_obstack;
c3e23647 123
c7925b99
MA
124int error_verbose = 0;
125
f0440388
MA
126/* Returns the number of lines of S. */
127static size_t
128get_lines_number (const char *s)
129{
130 size_t lines = 0;
1fa14068 131
f0440388
MA
132 size_t i;
133 for (i = 0; s[i]; ++i)
d0b0fefa
AD
134 if (s[i] == '\n')
135 ++lines;
1fa14068 136
f0440388
MA
137 return lines;
138}
139
140
26f609ff 141/* FIXME. */
c3e23647 142
d019d655 143static inline void
342b8b6e
AD
144output_table_data (struct obstack *oout,
145 short *table_data,
146 short first,
1fa14068
AD
147 int begin,
148 int end)
d019d655 149{
26f609ff
RA
150 int i;
151 int j = 1;
342b8b6e 152
26f609ff
RA
153 obstack_fgrow1 (oout, "%6d", first);
154 for (i = begin; i < end; ++i)
d019d655 155 {
896fe5c1 156 obstack_1grow (oout, ',');
d019d655
AD
157 if (j >= 10)
158 {
ff4423cc 159 obstack_sgrow (oout, "\n ");
d019d655
AD
160 j = 1;
161 }
162 else
26f609ff 163 ++j;
8f451ef7 164 obstack_fgrow1 (oout, "%6d", table_data[i]);
c3e23647 165 }
26f609ff 166 obstack_1grow (oout, 0);
c3e23647
RS
167}
168
169
4a120d45 170static void
d2729d44 171output_token_translations (void)
c3e23647 172{
f87685c3 173 output_table_data (&format_obstack, token_translations,
26f609ff 174 0, 1, max_user_token_number + 1);
f87685c3 175 muscle_insert ("translate", obstack_finish (&format_obstack));
342b8b6e 176 XFREE (token_translations);
c3e23647
RS
177}
178
179
4a120d45 180static void
d2729d44 181output_gram (void)
c3e23647 182{
b2ed6e58
AD
183 {
184 int i;
185 short *values = XCALLOC (short, nrules + 1);
186 for (i = 0; i < nrules + 1; ++i)
187 values[i] = rule_table[i].rhs;
f87685c3 188 output_table_data (&format_obstack, values,
b2ed6e58
AD
189 0, 1, nrules + 1);
190 XFREE (values);
191 }
192
f87685c3 193 muscle_insert ("prhs", obstack_finish (&format_obstack));
342b8b6e 194
1e9798d5 195 {
3db472b9 196 short *yyrhs;
1e9798d5 197 int i;
c3e23647 198
3db472b9 199 yyrhs = XMALLOC (short, nritems);
c3e23647 200
3db472b9
AD
201 for (i = 1; i < nritems; ++i)
202 yyrhs[i] = ritem[i] >= 0 ? ritem[i] : -1;
c3e23647 203
f87685c3 204 output_table_data (&format_obstack, yyrhs,
3db472b9 205 ritem[0], 1, nritems);
f87685c3 206 muscle_insert ("rhs", obstack_finish (&format_obstack));
26f609ff 207
1e9798d5
AD
208 XFREE (yyrhs);
209 }
796d61fb 210
4ec8e00f
MA
211#if 0
212 if (!semantic_parser)
213 obstack_sgrow (&table_obstack, "\n#endif\n");
214#endif
c3e23647
RS
215}
216
217
4a120d45 218static void
d2729d44 219output_stos (void)
c3e23647 220{
9703cc49
AD
221 int i;
222 short *values = (short *) alloca (sizeof (short) * nstates);
223 for (i = 0; i < nstates; ++i)
f693ad14 224 values[i] = state_table[i]->accessing_symbol;
f87685c3 225 output_table_data (&format_obstack, values,
26f609ff 226 0, 1, nstates);
f87685c3 227 muscle_insert ("stos", obstack_finish (&format_obstack));
c3e23647
RS
228}
229
230
4a120d45 231static void
d2729d44 232output_rule_data (void)
c3e23647 233{
6c89f1c1
AD
234 int i;
235 int j;
1e9798d5 236 short *short_tab = NULL;
c3e23647 237
e41dc700
AD
238 {
239 short *values = XCALLOC (short, nrules + 1);
240 for (i = 0; i < nrules + 1; ++i)
241 values[i] = rule_table[i].line;
f87685c3 242 output_table_data (&format_obstack, values,
e41dc700 243 0, 1, nrules + 1);
f87685c3 244 muscle_insert ("rline", obstack_finish (&format_obstack));
e41dc700
AD
245 XFREE (values);
246 }
247
c3e23647 248
1e9798d5
AD
249 j = 0;
250 for (i = 0; i < nsyms; i++)
c3e23647 251 {
92790e5b
AD
252 /* Be sure not to use twice the same quotearg slot. */
253 const char *cp =
254 quotearg_n_style (1, c_quoting_style,
255 quotearg_style (escape_quoting_style, tags[i]));
1e9798d5
AD
256 /* Width of the next token, including the two quotes, the coma
257 and the space. */
92790e5b 258 int strsize = strlen (cp) + 2;
1e9798d5
AD
259
260 if (j + strsize > 75)
c3e23647 261 {
f87685c3 262 obstack_sgrow (&format_obstack, "\n ");
1e9798d5 263 j = 2;
c3e23647
RS
264 }
265
f87685c3
AD
266 obstack_sgrow (&format_obstack, cp);
267 obstack_sgrow (&format_obstack, ", ");
1e9798d5 268 j += strsize;
c3e23647 269 }
9ee3c97b 270 /* add a NULL entry to list of tokens */
f87685c3 271 obstack_sgrow (&format_obstack, "NULL");
c3e23647 272
26f609ff 273 /* Finish table and store. */
f87685c3
AD
274 obstack_1grow (&format_obstack, 0);
275 muscle_insert ("tname", obstack_finish (&format_obstack));
e372befa 276
9ee3c97b 277 /* Output YYTOKNUM. */
f87685c3 278 output_table_data (&format_obstack, user_toknums,
26f609ff 279 0, 1, ntokens + 1);
f87685c3 280 muscle_insert ("toknum", obstack_finish (&format_obstack));
e372befa 281
9ee3c97b 282 /* Output YYR1. */
b2ed6e58
AD
283 {
284 short *values = XCALLOC (short, nrules + 1);
285 for (i = 0; i < nrules + 1; ++i)
286 values[i] = rule_table[i].lhs;
f87685c3 287 output_table_data (&format_obstack, values,
b2ed6e58 288 0, 1, nrules + 1);
f87685c3 289 muscle_insert ("r1", obstack_finish (&format_obstack));
b2ed6e58
AD
290 XFREE (values);
291 }
d019d655 292
9ee3c97b 293 /* Output YYR2. */
1e9798d5 294 short_tab = XMALLOC (short, nrules + 1);
c3e23647 295 for (i = 1; i < nrules; i++)
b2ed6e58 296 short_tab[i] = rule_table[i + 1].rhs - rule_table[i].rhs - 1;
9e7f6bbd 297 short_tab[nrules] = nritems - rule_table[nrules].rhs - 1;
f87685c3 298 output_table_data (&format_obstack, short_tab,
26f609ff 299 0, 1, nrules + 1);
f87685c3 300 muscle_insert ("r2", obstack_finish (&format_obstack));
1e9798d5 301 XFREE (short_tab);
c3e23647
RS
302}
303
6c89f1c1
AD
304/*------------------------------------------------------------------.
305| Decide what to do for each type of token if seen as the lookahead |
306| token in specified state. The value returned is used as the |
307| default action (yydefact) for the state. In addition, actrow is |
308| filled with what to do for each kind of token, index by symbol |
309| number, with zero meaning do the default action. The value |
310| MINSHORT, a very negative number, means this situation is an |
311| error. The parser recognizes this value specially. |
312| |
313| This is where conflicts are resolved. The loop over lookahead |
314| rules considered lower-numbered rules last, and the last rule |
315| considered that likes a token gets to handle it. |
316`------------------------------------------------------------------*/
c3e23647 317
4a120d45 318static int
f9507c28 319action_row (state_t *state)
c3e23647 320{
6c89f1c1 321 int i;
837491d8 322 int default_rule = 0;
f9507c28 323 reductions *redp = state->reductions;
f9507c28
AD
324 shifts *shiftp = state->shifts;
325 errs *errp = state->errs;
837491d8
AD
326 /* set nonzero to inhibit having any default reduction */
327 int nodefault = 0;
c3e23647
RS
328
329 for (i = 0; i < ntokens; i++)
330 actrow[i] = 0;
331
80dac38c 332 if (redp->nreds >= 1)
c3e23647 333 {
837491d8
AD
334 int j;
335 /* loop over all the rules available here which require
336 lookahead */
f9507c28 337 for (i = state->nlookaheads - 1; i >= 0; --i)
837491d8
AD
338 /* and find each token which the rule finds acceptable
339 to come next */
340 for (j = 0; j < ntokens; j++)
341 /* and record this rule as the rule to use if that
342 token follows. */
f9507c28
AD
343 if (BITISSET (LA (state->lookaheadsp + i), j))
344 actrow[j] = -LAruleno[state->lookaheadsp + i];
c3e23647
RS
345 }
346
36281465
AD
347 /* Now see which tokens are allowed for shifts in this state. For
348 them, record the shift as the thing to do. So shift is preferred
349 to reduce. */
d954473d 350 for (i = 0; i < shiftp->nshifts; i++)
c3e23647 351 {
837491d8
AD
352 int symbol;
353 int shift_state = shiftp->shifts[i];
d954473d
AD
354 if (!shift_state)
355 continue;
c3e23647 356
f693ad14 357 symbol = state_table[shift_state]->accessing_symbol;
c3e23647 358
d954473d
AD
359 if (ISVAR (symbol))
360 break;
c3e23647 361
d954473d 362 actrow[symbol] = shift_state;
c3e23647 363
d954473d
AD
364 /* Do not use any default reduction if there is a shift for
365 error */
366 if (symbol == error_token_number)
367 nodefault = 1;
c3e23647
RS
368 }
369
36281465
AD
370 /* See which tokens are an explicit error in this state (due to
371 %nonassoc). For them, record MINSHORT as the action. */
2cec70b9
AD
372 for (i = 0; i < errp->nerrs; i++)
373 {
374 int symbol = errp->errs[i];
375 actrow[symbol] = MINSHORT;
376 }
c3e23647 377
36281465
AD
378 /* Now find the most common reduction and make it the default action
379 for this state. */
c3e23647 380
80dac38c 381 if (redp->nreds >= 1 && !nodefault)
c3e23647 382 {
f9507c28 383 if (state->consistent)
c3e23647
RS
384 default_rule = redp->rules[0];
385 else
386 {
7a5350ba 387 int max = 0;
f9507c28 388 for (i = 0; i < state->nlookaheads; i++)
c3e23647 389 {
7a5350ba 390 int count = 0;
f9507c28 391 int rule = -LAruleno[state->lookaheadsp + i];
837491d8 392 int j;
9ee3c97b 393
c3e23647 394 for (j = 0; j < ntokens; j++)
837491d8
AD
395 if (actrow[j] == rule)
396 count++;
9ee3c97b 397
c3e23647
RS
398 if (count > max)
399 {
400 max = count;
401 default_rule = rule;
402 }
403 }
9ee3c97b 404
c3e23647
RS
405 /* actions which match the default are replaced with zero,
406 which means "use the default" */
9ee3c97b 407
c3e23647
RS
408 if (max > 0)
409 {
837491d8 410 int j;
c3e23647 411 for (j = 0; j < ntokens; j++)
837491d8
AD
412 if (actrow[j] == default_rule)
413 actrow[j] = 0;
9ee3c97b 414
ceed8467 415 default_rule = -default_rule;
c3e23647
RS
416 }
417 }
418 }
419
420 /* If have no default rule, the default is an error.
421 So replace any action which says "error" with "use default". */
422
423 if (default_rule == 0)
837491d8
AD
424 for (i = 0; i < ntokens; i++)
425 if (actrow[i] == MINSHORT)
426 actrow[i] = 0;
c3e23647 427
36281465 428 return default_rule;
c3e23647
RS
429}
430
431
4a120d45 432static void
d2729d44 433save_row (int state)
c3e23647 434{
6c89f1c1
AD
435 int i;
436 int count;
437 short *sp;
438 short *sp1;
439 short *sp2;
c3e23647
RS
440
441 count = 0;
442 for (i = 0; i < ntokens; i++)
796d61fb
AD
443 if (actrow[i] != 0)
444 count++;
c3e23647
RS
445
446 if (count == 0)
447 return;
448
d7913476
AD
449 froms[state] = sp1 = sp = XCALLOC (short, count);
450 tos[state] = sp2 = XCALLOC (short, count);
c3e23647
RS
451
452 for (i = 0; i < ntokens; i++)
796d61fb
AD
453 if (actrow[i] != 0)
454 {
455 *sp1++ = i;
456 *sp2++ = actrow[i];
457 }
c3e23647
RS
458
459 tally[state] = count;
460 width[state] = sp1[-1] - sp[0] + 1;
461}
462
463
6c89f1c1
AD
464/*------------------------------------------------------------------.
465| Figure out the actions for the specified state, indexed by |
466| lookahead token type. |
467| |
f2acea59
AD
468| The YYDEFACT table is output now. The detailed info is saved for |
469| putting into YYTABLE later. |
6c89f1c1 470`------------------------------------------------------------------*/
c3e23647 471
4a120d45 472static void
6c89f1c1 473token_actions (void)
c3e23647 474{
6c89f1c1 475 int i;
d7913476 476 short *yydefact = XCALLOC (short, nstates);
c3e23647 477
d7913476 478 actrow = XCALLOC (short, ntokens);
f2acea59 479 for (i = 0; i < nstates; ++i)
c3e23647 480 {
f9507c28 481 yydefact[i] = action_row (state_table[i]);
6c89f1c1 482 save_row (i);
c3e23647 483 }
bbb5bcc6 484
f87685c3 485 output_table_data (&format_obstack, yydefact,
26f609ff 486 yydefact[0], 1, nstates);
f87685c3 487 muscle_insert ("defact", obstack_finish (&format_obstack));
342b8b6e 488
26f609ff 489 XFREE (actrow);
d7913476 490 XFREE (yydefact);
c3e23647
RS
491}
492
493
3f96f4dc
AD
494/*-----------------------------.
495| Output the actions to OOUT. |
496`-----------------------------*/
497
498static void
f0440388 499actions_output (FILE *out, size_t *line)
3f96f4dc
AD
500{
501 int rule;
502 for (rule = 1; rule < nrules + 1; ++rule)
503 if (rule_table[rule].action)
504 {
ea52d706 505 fprintf (out, " case %d:\n", rule);
3f96f4dc
AD
506
507 if (!no_lines_flag)
ea52d706
AD
508 fprintf (out, muscle_find ("linef"),
509 rule_table[rule].action_line,
510 quotearg_style (c_quoting_style,
511 muscle_find ("filename")));
3f96f4dc
AD
512 /* As a Bison extension, add the ending semicolon. Since some
513 Yacc don't do that, help people using bison as a Yacc
514 finding their missing semicolons. */
ea52d706
AD
515 fprintf (out, "{ %s%s }\n break;\n\n",
516 rule_table[rule].action,
517 yacc_flag ? ";" : "");
f0440388 518
fbc8ecb7
MA
519 /* We always output 4 '\n' per action. */
520 *line += 4;
521 /* Plus one if !no_lines_flag. */
522 if (!no_lines_flag)
523 ++*line;
f0440388
MA
524 /* Get the number of lines written by the user. */
525 *line += get_lines_number (rule_table[rule].action);
3f96f4dc
AD
526 }
527}
528
529
f499b062
AD
530/*----------------------------.
531| Output the guards to OOUT. |
532`----------------------------*/
533
534static void
535guards_output (FILE *out, size_t *line)
536{
537 int rule;
538 for (rule = 1; rule < nrules + 1; ++rule)
539 if (rule_table[rule].action)
540 {
541 fprintf (out, " case %d:\n", rule);
542
543 if (!no_lines_flag)
544 fprintf (out, muscle_find ("linef"),
545 rule_table[rule].guard_line,
546 quotearg_style (c_quoting_style,
547 muscle_find ("filename")));
548 fprintf (out, "{ %s; }\n break;\n\n",
549 rule_table[rule].guard);
550
551 /* We always output 4 '\n' per action. */
552 *line += 4;
553 /* Plus one if !no_lines_flag. */
554 if (!no_lines_flag)
555 ++*line;
556 /* Get the number of lines written by the user. */
557 *line += get_lines_number (rule_table[rule].guard);
558 }
559}
560
561
4a120d45 562static void
d2729d44 563save_column (int symbol, int default_state)
c3e23647 564{
6c89f1c1 565 int i;
6c89f1c1
AD
566 short *sp;
567 short *sp1;
568 short *sp2;
569 int count;
837491d8 570 int symno = symbol - ntokens + nstates;
c3e23647 571
43591cec
AD
572 short begin = goto_map[symbol];
573 short end = goto_map[symbol + 1];
c3e23647
RS
574
575 count = 0;
43591cec 576 for (i = begin; i < end; i++)
796d61fb
AD
577 if (to_state[i] != default_state)
578 count++;
c3e23647
RS
579
580 if (count == 0)
581 return;
582
d7913476
AD
583 froms[symno] = sp1 = sp = XCALLOC (short, count);
584 tos[symno] = sp2 = XCALLOC (short, count);
c3e23647 585
43591cec 586 for (i = begin; i < end; i++)
796d61fb
AD
587 if (to_state[i] != default_state)
588 {
589 *sp1++ = from_state[i];
590 *sp2++ = to_state[i];
591 }
c3e23647
RS
592
593 tally[symno] = count;
594 width[symno] = sp1[-1] - sp[0] + 1;
595}
596
6c89f1c1
AD
597static int
598default_goto (int symbol)
599{
600 int i;
837491d8
AD
601 int m = goto_map[symbol];
602 int n = goto_map[symbol + 1];
603 int default_state = -1;
604 int max = 0;
6c89f1c1
AD
605
606 if (m == n)
607 return -1;
608
609 for (i = 0; i < nstates; i++)
610 state_count[i] = 0;
611
612 for (i = m; i < n; i++)
613 state_count[to_state[i]]++;
614
6c89f1c1 615 for (i = 0; i < nstates; i++)
796d61fb
AD
616 if (state_count[i] > max)
617 {
618 max = state_count[i];
619 default_state = i;
620 }
6c89f1c1
AD
621
622 return default_state;
623}
624
625
626/*-------------------------------------------------------------------.
627| Figure out what to do after reducing with each rule, depending on |
628| the saved state from before the beginning of parsing the data that |
629| matched this rule. |
630| |
631| The YYDEFGOTO table is output now. The detailed info is saved for |
632| putting into YYTABLE later. |
633`-------------------------------------------------------------------*/
634
635static void
636goto_actions (void)
637{
43591cec 638 int i;
bbb5bcc6 639 short *yydefgoto = XMALLOC (short, nsyms - ntokens);
bbb5bcc6 640
26f609ff 641 state_count = XCALLOC (short, nstates);
43591cec 642 for (i = ntokens; i < nsyms; ++i)
6c89f1c1 643 {
43591cec
AD
644 int default_state = default_goto (i);
645 save_column (i, default_state);
646 yydefgoto[i - ntokens] = default_state;
6c89f1c1
AD
647 }
648
f87685c3 649 output_table_data (&format_obstack, yydefgoto,
26f609ff 650 yydefgoto[0], 1, nsyms - ntokens);
f87685c3 651 muscle_insert ("defgoto", obstack_finish (&format_obstack));
43591cec 652
d7913476 653 XFREE (state_count);
43591cec 654 XFREE (yydefgoto);
6c89f1c1 655}
c3e23647
RS
656
657
9ee3c97b
AD
658/* The next few functions decide how to pack the actions and gotos
659 information into yytable. */
c3e23647 660
4a120d45 661static void
d2729d44 662sort_actions (void)
c3e23647 663{
6c89f1c1 664 int i;
c3e23647 665
d7913476 666 order = XCALLOC (short, nvectors);
c3e23647
RS
667 nentries = 0;
668
669 for (i = 0; i < nvectors; i++)
796d61fb
AD
670 if (tally[i] > 0)
671 {
837491d8
AD
672 int k;
673 int t = tally[i];
674 int w = width[i];
675 int j = nentries - 1;
c3e23647 676
796d61fb
AD
677 while (j >= 0 && (width[order[j]] < w))
678 j--;
c3e23647 679
796d61fb
AD
680 while (j >= 0 && (width[order[j]] == w) && (tally[order[j]] < t))
681 j--;
c3e23647 682
796d61fb
AD
683 for (k = nentries - 1; k > j; k--)
684 order[k + 1] = order[k];
c3e23647 685
796d61fb
AD
686 order[j + 1] = i;
687 nentries++;
688 }
c3e23647
RS
689}
690
691
4a120d45 692static int
d2729d44 693matching_state (int vector)
c3e23647 694{
837491d8 695 int i = order[vector];
6c89f1c1
AD
696 int t;
697 int w;
6c89f1c1 698 int prev;
c3e23647 699
c3e23647 700 if (i >= nstates)
36281465 701 return -1;
c3e23647
RS
702
703 t = tally[i];
704 w = width[i];
705
706 for (prev = vector - 1; prev >= 0; prev--)
707 {
837491d8
AD
708 int j = order[prev];
709 int k;
710 int match = 1;
711
c3e23647 712 if (width[j] != w || tally[j] != t)
36281465 713 return -1;
c3e23647 714
c3e23647 715 for (k = 0; match && k < t; k++)
796d61fb
AD
716 if (tos[j][k] != tos[i][k] || froms[j][k] != froms[i][k])
717 match = 0;
c3e23647
RS
718
719 if (match)
36281465 720 return j;
c3e23647
RS
721 }
722
36281465 723 return -1;
c3e23647
RS
724}
725
726
4a120d45 727static int
d2729d44 728pack_vector (int vector)
c3e23647 729{
837491d8 730 int i = order[vector];
6c89f1c1 731 int j;
837491d8 732 int t = tally[i];
6c89f1c1 733 int loc = 0;
837491d8
AD
734 short *from = froms[i];
735 short *to = tos[i];
c3e23647 736
340ef489 737 assert (t);
c3e23647 738
c3e23647
RS
739 for (j = lowzero - from[0]; j < MAXTABLE; j++)
740 {
837491d8
AD
741 int k;
742 int ok = 1;
c3e23647
RS
743
744 for (k = 0; ok && k < t; k++)
745 {
746 loc = j + from[k];
747 if (loc > MAXTABLE)
a0f6b076 748 fatal (_("maximum table size (%d) exceeded"), MAXTABLE);
c3e23647
RS
749
750 if (table[loc] != 0)
751 ok = 0;
752 }
753
754 for (k = 0; ok && k < vector; k++)
796d61fb
AD
755 if (pos[k] == j)
756 ok = 0;
c3e23647
RS
757
758 if (ok)
759 {
760 for (k = 0; k < t; k++)
761 {
762 loc = j + from[k];
763 table[loc] = to[k];
764 check[loc] = from[k];
765 }
766
767 while (table[lowzero] != 0)
768 lowzero++;
769
770 if (loc > high)
771 high = loc;
772
36281465 773 return j;
c3e23647
RS
774 }
775 }
275fc3ad
AD
776#define pack_vector_succeeded 0
777 assert (pack_vector_succeeded);
3843c413 778 return 0;
c3e23647
RS
779}
780
781
6c89f1c1
AD
782static void
783pack_table (void)
784{
785 int i;
786 int place;
787 int state;
788
d7913476
AD
789 base = XCALLOC (short, nvectors);
790 pos = XCALLOC (short, nentries);
791 table = XCALLOC (short, MAXTABLE);
792 check = XCALLOC (short, MAXTABLE);
6c89f1c1
AD
793
794 lowzero = 0;
795 high = 0;
796
797 for (i = 0; i < nvectors; i++)
798 base[i] = MINSHORT;
799
800 for (i = 0; i < MAXTABLE; i++)
801 check[i] = -1;
802
803 for (i = 0; i < nentries; i++)
804 {
805 state = matching_state (i);
806
807 if (state < 0)
808 place = pack_vector (i);
809 else
810 place = base[state];
811
812 pos[i] = place;
813 base[order[i]] = place;
814 }
815
816 for (i = 0; i < nvectors; i++)
817 {
796d61fb
AD
818 XFREE (froms[i]);
819 XFREE (tos[i]);
6c89f1c1
AD
820 }
821
d7913476
AD
822 XFREE (froms);
823 XFREE (tos);
824 XFREE (pos);
6c89f1c1 825}
c3e23647
RS
826
827/* the following functions output yytable, yycheck
828 and the vectors whose elements index the portion starts */
829
4a120d45 830static void
d2729d44 831output_base (void)
c3e23647 832{
26f609ff 833 /* Output pact. */
f87685c3 834 output_table_data (&format_obstack, base,
26f609ff 835 base[0], 1, nstates);
f87685c3 836 muscle_insert ("pact", obstack_finish (&format_obstack));
c3e23647 837
26f609ff 838 /* Output pgoto. */
f87685c3 839 output_table_data (&format_obstack, base,
26f609ff 840 base[nstates], nstates + 1, nvectors);
f87685c3 841 muscle_insert ("pgoto", obstack_finish (&format_obstack));
c3e23647 842
d7913476 843 XFREE (base);
c3e23647
RS
844}
845
846
4a120d45 847static void
d2729d44 848output_table (void)
c3e23647 849{
f87685c3 850 output_table_data (&format_obstack, table,
26f609ff 851 table[0], 1, high + 1);
f87685c3 852 muscle_insert ("table", obstack_finish (&format_obstack));
d7913476 853 XFREE (table);
c3e23647
RS
854}
855
856
4a120d45 857static void
d2729d44 858output_check (void)
c3e23647 859{
f87685c3 860 output_table_data (&format_obstack, check,
26f609ff 861 check[0], 1, high + 1);
f87685c3 862 muscle_insert ("check", obstack_finish (&format_obstack));
d7913476 863 XFREE (check);
c3e23647
RS
864}
865
6c89f1c1
AD
866/* compute and output yydefact, yydefgoto, yypact, yypgoto, yytable
867 and yycheck. */
868
869static void
870output_actions (void)
871{
49701457 872 int i;
6c89f1c1 873 nvectors = nstates + nvars;
c3e23647 874
d7913476
AD
875 froms = XCALLOC (short *, nvectors);
876 tos = XCALLOC (short *, nvectors);
877 tally = XCALLOC (short, nvectors);
878 width = XCALLOC (short, nvectors);
6c89f1c1
AD
879
880 token_actions ();
d7913476
AD
881 XFREE (LA);
882 XFREE (LAruleno);
6c89f1c1
AD
883
884 goto_actions ();
d7913476
AD
885 XFREE (goto_map + ntokens);
886 XFREE (from_state);
887 XFREE (to_state);
6c89f1c1
AD
888
889 sort_actions ();
890 pack_table ();
4e5caae2 891
6c89f1c1
AD
892 output_base ();
893 output_table ();
4e5caae2 894
6c89f1c1 895 output_check ();
49701457
AD
896
897 for (i = 0; i < nstates; ++i)
898 {
2cec70b9 899 free (state_table[i]->shifts);
49701457 900 XFREE (state_table[i]->reductions);
2cec70b9 901 free (state_table[i]->errs);
49701457
AD
902 free (state_table[i]);
903 }
9703cc49 904 XFREE (state_table);
6c89f1c1 905}
c3e23647 906
652def80
MA
907\f
908/*------------------------------------------------------------.
909| Copy the parser code from SKEL_FILENAME into OOUT obstack. |
910| and do the muscle substitution. |
911`------------------------------------------------------------*/
c3e23647 912
4a120d45 913static void
ea52d706 914output_parser (const char *skel_filename, FILE *out)
c3e23647 915{
6c89f1c1 916 int c;
ff61dabd 917 FILE *fskel;
897668ee
MA
918 size_t output_line;
919 size_t skeleton_line;
c3e23647 920
652def80 921 fskel = xfopen (skel_filename, "r");
ef7ddedd 922
e8cb70b9 923 /* New output code. */
897668ee
MA
924 output_line = 1;
925 skeleton_line = 1;
26f609ff
RA
926 c = getc (fskel);
927 while (c != EOF)
c3e23647 928 {
26f609ff 929 if (c != '%')
573c1d9f 930 {
26f609ff 931 if (c == '\n')
897668ee
MA
932 {
933 ++output_line;
934 ++skeleton_line;
935 }
ea52d706 936 putc (c, out);
26f609ff 937 c = getc (fskel);
bbb5bcc6 938 }
26f609ff 939 else if ((c = getc (fskel)) == '%')
bbb5bcc6 940 {
11d82f03
MA
941 /* Read the muscle. */
942 const char *muscle_key = 0;
943 const char *muscle_value = 0;
652def80 944
5b5d1929 945 while (isalnum (c = getc (fskel)) || c == '-')
11d82f03
MA
946 obstack_1grow (&muscle_obstack, c);
947 obstack_1grow (&muscle_obstack, 0);
26f609ff 948
e8cb70b9 949 /* Output the right value, or see if it's something special. */
11d82f03
MA
950 muscle_key = obstack_finish (&muscle_obstack);
951 muscle_value = muscle_find (muscle_key);
3f96f4dc 952 if (!strcmp (muscle_key, "actions"))
897668ee 953 actions_output (out, &output_line);
f499b062
AD
954 else if (!strcmp (muscle_key, "guards"))
955 guards_output (out, &output_line);
11d82f03 956 else if (!strcmp (muscle_key, "line"))
897668ee
MA
957 fprintf (out, "%d", output_line);
958 else if (!strcmp (muscle_key, "skeleton-line"))
959 fprintf (out, "%d", skeleton_line);
3f96f4dc 960 else if (muscle_value)
f0440388
MA
961 {
962 fputs (muscle_value, out);
897668ee 963 output_line += get_lines_number (muscle_value);
1fa14068 964 }
bbb5bcc6 965 else
26f609ff 966 {
ea52d706
AD
967 fputs ("%%", out);
968 fputs (muscle_key, out);
26f609ff 969 }
573c1d9f 970 }
b0cfa28a 971 else
ea52d706 972 putc ('%', out);
bbb5bcc6 973 }
26f609ff 974
e8cb70b9 975 /* End. */
ff61dabd 976 xfclose (fskel);
c3e23647
RS
977}
978
652def80
MA
979/*----------------------------------------.
980| Prepare the master parser to be output |
981`----------------------------------------*/
982
983static void
984output_master_parser (void)
985{
ea52d706 986 FILE *parser = xfopen (parser_file_name, "w");
652def80
MA
987 if (!skeleton)
988 {
989 if (semantic_parser)
990 skeleton = skeleton_find ("BISON_HAIRY", BISON_HAIRY);
991 else
992 skeleton = skeleton_find ("BISON_SIMPLE", BISON_SIMPLE);
993 }
3843c413 994 muscle_insert ("skeleton", skeleton);
f0440388 995 muscle_insert ("parser-file-name", parser_file_name);
ea52d706
AD
996
997 output_parser (skeleton, parser);
998 xfclose (parser);
652def80
MA
999}
1000
1001
26f609ff
RA
1002/* FIXME. */
1003
11d82f03
MA
1004#define MUSCLE_INSERT_INT(Key, Value) \
1005{ \
1006 obstack_fgrow1 (&muscle_obstack, "%d", Value); \
1007 obstack_1grow (&muscle_obstack, 0); \
1008 muscle_insert (Key, obstack_finish (&muscle_obstack)); \
26f609ff
RA
1009}
1010
11d82f03
MA
1011#define MUSCLE_INSERT_STRING(Key, Value) \
1012{ \
1013 obstack_sgrow (&muscle_obstack, Value); \
1014 obstack_1grow (&muscle_obstack, 0); \
1015 muscle_insert (Key, obstack_finish (&muscle_obstack)); \
26f609ff
RA
1016}
1017
11d82f03 1018#define MUSCLE_INSERT_PREFIX(Key, Value) \
26f609ff 1019{ \
11d82f03
MA
1020 obstack_fgrow2 (&muscle_obstack, "%s%s", spec_name_prefix, Value); \
1021 obstack_1grow (&muscle_obstack, 0); \
1022 muscle_insert (Key, obstack_finish (&muscle_obstack)); \
26f609ff
RA
1023}
1024
1025static void
1026prepare (void)
1027{
11d82f03
MA
1028 MUSCLE_INSERT_INT ("last", high);
1029 MUSCLE_INSERT_INT ("flag", MINSHORT);
1030 MUSCLE_INSERT_INT ("pure", pure_parser);
1031 MUSCLE_INSERT_INT ("nsym", nsyms);
1032 MUSCLE_INSERT_INT ("debug", debug_flag);
1033 MUSCLE_INSERT_INT ("final", final_state);
1034 MUSCLE_INSERT_INT ("maxtok", max_user_token_number);
c7925b99 1035 MUSCLE_INSERT_INT ("error-verbose", error_verbose);
78af9bbc 1036 MUSCLE_INSERT_STRING ("prefix", spec_name_prefix);
11d82f03
MA
1037
1038 MUSCLE_INSERT_INT ("nnts", nvars);
1039 MUSCLE_INSERT_INT ("nrules", nrules);
1040 MUSCLE_INSERT_INT ("nstates", nstates);
1041 MUSCLE_INSERT_INT ("ntokens", ntokens);
1042
5b5d1929 1043 MUSCLE_INSERT_INT ("locations-flag", locations_flag);
26f609ff 1044}
c3e23647 1045
93ede233
AD
1046
1047/*-------------------------.
1048| Output the header file. |
1049`-------------------------*/
1050
1051static void
1052header_output (void)
1053{
1054 FILE *out = xfopen (spec_defines_file, "w");
1055 char *macro_name = compute_header_macro ();
1056
1057 fprintf (out, "#ifndef %s\n", macro_name);
1058 fprintf (out, "# define %s\n\n", macro_name);
1059
1060 fputs (muscle_find ("tokendef"), out);
1061 fprintf (out, "\
1062#ifndef YYSTYPE\n\
1063typedef %s
1064yystype;\n\
1065# define YYSTYPE yystype\n\
1066#endif\n",
1067 muscle_find ("stype"));
1068
1069 if (!pure_parser)
1070 fprintf (out, "\nextern YYSTYPE %slval;\n",
1071 spec_name_prefix);
1072 if (semantic_parser)
1073 {
1074 int i;
1075
1076 for (i = ntokens; i < nsyms; i++)
1077 /* don't make these for dummy nonterminals made by gensym. */
1078 if (*tags[i] != '@')
7742ddeb 1079 fprintf (out, "# define NT%s\t%d\n", tags[i], i);
93ede233
AD
1080 }
1081
1082 fprintf (out, "\n#endif /* not %s */\n", macro_name);
1083 free (macro_name);
1084 xfclose (out);
1085}
1086
1087
6c89f1c1
AD
1088/*----------------------------------------------------------.
1089| Output the parsing tables and the parser code to ftable. |
1090`----------------------------------------------------------*/
c3e23647 1091
6c89f1c1
AD
1092void
1093output (void)
1094{
f87685c3 1095 obstack_init (&format_obstack);
dd60faec 1096
6c89f1c1 1097 output_token_translations ();
6c89f1c1 1098 output_gram ();
26f609ff 1099
d7913476 1100 XFREE (ritem);
6c89f1c1
AD
1101 if (semantic_parser)
1102 output_stos ();
1103 output_rule_data ();
0846f581 1104 XFREE (user_toknums);
6c89f1c1 1105 output_actions ();
342b8b6e 1106
26f609ff 1107 prepare ();
d1a2daf7 1108 /* Copy definitions in directive. */
5449dd0f 1109 obstack_1grow (&attrs_obstack, 0);
11d82f03 1110 muscle_insert ("prologue", obstack_finish (&attrs_obstack));
652def80 1111
93ede233 1112 /* Output the parser. */
652def80 1113 output_master_parser ();
93ede233
AD
1114 /* Output the header if needed. */
1115 if (defines_flag)
1116 header_output ();
26f609ff 1117
3f96f4dc 1118 free (rule_table + 1);
f499b062
AD
1119 obstack_free (&muscle_obstack, NULL);
1120 obstack_free (&format_obstack, NULL);
1121 obstack_free (&action_obstack, NULL);
f499b062 1122 obstack_free (&attrs_obstack, NULL);
c3e23647 1123}