2 * Copyright (c) 1989 The Regents of the University of California.
5 * This code is derived from software contributed to Berkeley by
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * 4. Neither the name of the University nor the names of its contributors
17 * may be used to endorse or promote products derived from this software
18 * without specific prior written permission.
20 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
21 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35 static char sccsid[] = "@(#)reader.c 5.7 (Berkeley) 1/20/91";
39 #include <sys/cdefs.h>
40 __FBSDID("$FreeBSD$");
47 /* The line size must be a positive integer. One hundred was chosen */
48 /* because few lines in Yacc input grammars exceed 100 characters. */
49 /* Note that if a line exceeds LINESIZE characters, the line buffer */
50 /* will be expanded to accomodate it. */
60 char saw_eof, unionized;
78 static const char line_format[] = "#line %d \"%s\"\n";
80 static void add_symbol(void);
81 static void advance_to_start(void);
82 static void cachec(int);
83 static void check_symbols(void);
84 static void copy_action(void);
85 static void copy_ident(void);
86 static void copy_text(void);
87 static void copy_union(void);
88 static void declare_expect(int);
89 static void declare_start(void);
90 static void declare_tokens(int);
91 static void declare_types(void);
92 static char *dup_line(void);
93 static void end_rule(void);
94 static void expand_items(void);
95 static void expand_rules(void);
96 static void free_tags(void);
97 static void get_line(void);
98 static bucket *get_literal(void);
99 static bucket *get_name(void);
100 static int get_number(void);
101 static char *get_tag(void);
102 static int hexval(int);
103 static void initialize_grammar(void);
104 static void insert_empty_rule(void);
105 static int is_reserved(char *);
106 static int keyword(void);
107 static int mark_symbol(void);
108 static int nextc(void);
109 static void pack_grammar(void);
110 static void pack_names(void);
111 static void pack_symbols(void);
112 static void print_grammar(void);
113 static void read_declarations(void);
114 static void read_grammar(void);
115 static void skip_comment(void);
116 static void start_rule(bucket *, int);
122 if (cinc >= cache_size)
125 cache = realloc(cache, cache_size);
126 if (cache == 0) no_space();
136 FILE *f = input_file;
140 if (saw_eof || (c = getc(f)) == EOF)
142 if (line) { free(line); line = 0; }
148 if (line == 0 || linesize != (LINESIZE + 1))
150 if (line) free(line);
151 linesize = LINESIZE + 1;
152 line = malloc(linesize);
153 if (line == 0) no_space();
161 if (c == '\n') { cptr = line; return; }
164 linesize += LINESIZE;
165 line = realloc(line, linesize);
166 if (line == 0) no_space();
185 if (line == 0) return (0);
187 while (*s != '\n') ++s;
188 p = malloc(s - line + 1);
189 if (p == 0) no_space();
193 while ((*t++ = *s++) != '\n') continue;
203 int st_lineno = lineno;
204 char *st_line = dup_line();
205 char *st_cptr = st_line + (cptr - line);
210 if (*s == '*' && s[1] == '/')
220 unterminated_comment(st_lineno, st_line, st_cptr);
248 if (line == 0) return (EOF);
274 else if (s[1] == '/')
277 if (line == 0) return (EOF);
305 if (isupper(c)) c = tolower(c);
308 else if (isdigit(c) || c == '_' || c == '.' || c == '$')
316 if (strcmp(cache, "token") == 0 || strcmp(cache, "term") == 0)
318 if (strcmp(cache, "type") == 0)
320 if (strcmp(cache, "left") == 0)
322 if (strcmp(cache, "right") == 0)
324 if (strcmp(cache, "nonassoc") == 0 || strcmp(cache, "binary") == 0)
326 if (strcmp(cache, "start") == 0)
328 if (strcmp(cache, "union") == 0)
330 if (strcmp(cache, "ident") == 0)
332 if (strcmp(cache, "expect") == 0)
340 if (c == '%' || c == '\\')
351 syntax_error(lineno, line, t_cptr);
361 FILE *f = output_file;
364 if (c == EOF) unexpected_EOF();
365 if (c != '"') syntax_error(lineno, line, cptr);
367 fprintf(f, "#ident \"");
393 int need_newline = 0;
394 int t_lineno = lineno;
395 char *t_line = dup_line();
396 char *t_cptr = t_line + (cptr - line - 2);
402 unterminated_text(t_lineno, t_line, t_cptr);
404 if (!lflag) fprintf(f, line_format, lineno, input_file_name);
416 unterminated_text(t_lineno, t_line, t_cptr);
421 int s_lineno = lineno;
422 char *s_line = dup_line();
423 char *s_cptr = s_line + (cptr - line - 1);
438 unterminated_string(s_lineno, s_line, s_cptr);
447 unterminated_string(s_lineno, s_line, s_cptr);
460 while ((c = *++cptr) != '\n')
462 if (c == '*' && cptr[1] == '/')
472 int c_lineno = lineno;
473 char *c_line = dup_line();
474 char *c_cptr = c_line + (cptr - line - 1);
482 if (c == '*' && *cptr == '/')
493 unterminated_comment(c_lineno, c_line, c_cptr);
504 if (need_newline) putc('\n', f);
525 int u_lineno = lineno;
526 char *u_line = dup_line();
527 char *u_cptr = u_line + (cptr - line - 6);
529 if (unionized) over_unionized(cptr - 6);
533 fprintf(text_file, line_format, lineno, input_file_name);
535 fprintf(text_file, "typedef union");
536 if (dflag) fprintf(union_file, "typedef union");
542 if (dflag) putc(c, union_file);
548 if (line == 0) unterminated_union(u_lineno, u_line, u_cptr);
558 fprintf(text_file, " YYSTYPE;\n");
567 int s_lineno = lineno;
568 char *s_line = dup_line();
569 char *s_cptr = s_line + (cptr - line - 1);
576 if (dflag) putc(c, union_file);
583 unterminated_string(s_lineno, s_line, s_cptr);
588 if (dflag) putc(c, union_file);
593 unterminated_string(s_lineno, s_line, s_cptr);
603 putc('*', text_file);
604 if (dflag) putc('*', union_file);
605 while ((c = *++cptr) != '\n')
607 if (c == '*' && cptr[1] == '/')
609 fprintf(text_file, "* ");
610 if (dflag) fprintf(union_file, "* ");
615 if (dflag) putc(c, union_file);
618 fprintf(text_file, "*/\n");
619 if (dflag) fprintf(union_file, "*/\n");
624 int c_lineno = lineno;
625 char *c_line = dup_line();
626 char *c_cptr = c_line + (cptr - line - 1);
628 putc('*', text_file);
629 if (dflag) putc('*', union_file);
635 if (dflag) putc(c, union_file);
636 if (c == '*' && *cptr == '/')
638 putc('/', text_file);
639 if (dflag) putc('/', union_file);
648 unterminated_comment(c_lineno, c_line, c_cptr);
663 if (c >= '0' && c <= '9')
665 if (c >= 'A' && c <= 'F')
666 return (c - 'A' + 10);
667 if (c >= 'a' && c <= 'f')
668 return (c - 'a' + 10);
681 int s_lineno = lineno;
682 char *s_line = dup_line();
683 char *s_cptr = s_line + (cptr - line);
690 if (c == quote) break;
691 if (c == '\n') unterminated_string(s_lineno, s_line, s_cptr);
694 char *c_cptr = cptr - 1;
701 if (line == 0) unterminated_string(s_lineno, s_line, s_cptr);
704 case '0': case '1': case '2': case '3':
705 case '4': case '5': case '6': case '7':
710 n = (n << 3) + (c - '0');
714 n = (n << 3) + (c - '0');
718 if (n > (int)UCHAR_MAX) illegal_character(c_cptr);
725 if (n < 0 || n >= 16)
726 illegal_character(c_cptr);
731 if (i < 0 || i >= 16) break;
734 if (n > (int)UCHAR_MAX) illegal_character(c_cptr);
739 case 'a': c = 7; break;
740 case 'b': c = '\b'; break;
741 case 'f': c = '\f'; break;
742 case 'n': c = '\n'; break;
743 case 'r': c = '\r'; break;
744 case 't': c = '\t'; break;
745 case 'v': c = '\v'; break;
754 if (s == 0) no_space();
756 for (i = 0; i < n; ++i)
765 for (i = 0; i < n; ++i)
767 c = ((unsigned char *)s)[i];
768 if (c == '\\' || c == cache[0])
780 case 7: cachec('a'); break;
781 case '\b': cachec('b'); break;
782 case '\f': cachec('f'); break;
783 case '\n': cachec('n'); break;
784 case '\r': cachec('r'); break;
785 case '\t': cachec('t'); break;
786 case '\v': cachec('v'); break;
788 cachec(((c >> 6) & 7) + '0');
789 cachec(((c >> 3) & 7) + '0');
790 cachec((c & 7) + '0');
804 if (n == 1 && bp->value == UNDEFINED)
805 bp->value = *(unsigned char *)s;
813 is_reserved(char *name)
817 if (strcmp(name, ".") == 0 ||
818 strcmp(name, "$accept") == 0 ||
819 strcmp(name, "$end") == 0)
822 if (name[0] == '$' && name[1] == '$' && isdigit(name[2]))
825 while (isdigit(*s)) ++s;
826 if (*s == NUL) return (1);
839 for (c = *cptr; IS_IDENT(c); c = *++cptr)
843 if (is_reserved(cache)) used_reserved(cache);
845 return (lookup(cache));
856 for (c = *cptr; isdigit(c); c = *++cptr)
857 n = 10*n + (c - '0');
869 int t_lineno = lineno;
870 char *t_line = dup_line();
871 char *t_cptr = t_line + (cptr - line);
875 if (c == EOF) unexpected_EOF();
876 if (!isalpha(c) && c != '_' && c != '$')
877 illegal_tag(t_lineno, t_line, t_cptr);
880 do { cachec(c); c = *++cptr; } while (IS_IDENT(c));
884 if (c == EOF) unexpected_EOF();
886 illegal_tag(t_lineno, t_line, t_cptr);
889 for (i = 0; i < ntags; ++i)
891 if (strcmp(cache, tag_table[i]) == 0)
892 return (tag_table[i]);
898 tag_table = (char **)
899 (tag_table ? realloc(tag_table, tagmax*sizeof(char *))
900 : malloc(tagmax*sizeof(char *)));
901 if (tag_table == 0) no_space();
905 if (s == 0) no_space();
907 tag_table[ntags] = s;
915 declare_tokens(int assoc)
922 if (assoc != TOKEN) ++prec;
925 if (c == EOF) unexpected_EOF();
930 if (c == EOF) unexpected_EOF();
935 if (isalpha(c) || c == '_' || c == '.' || c == '$')
937 else if (c == '\'' || c == '"')
942 if (bp == goal) tokenized_start(bp->name);
947 if (bp->tag && tag != bp->tag)
948 retyped_warning(bp->name);
954 if (bp->prec && prec != bp->prec)
955 reprec_warning(bp->name);
961 if (c == EOF) unexpected_EOF();
965 value = get_number();
966 if (bp->value != UNDEFINED && value != bp->value)
967 revalued_warning(bp->name);
970 if (c == EOF) unexpected_EOF();
977 * %expect requires special handling
978 * as it really isn't part of the yacc
979 * grammar only a flag for yacc proper.
982 declare_expect(int assoc)
986 if (assoc != EXPECT) ++prec;
989 * Stay away from nextc - doesn't
990 * detect EOL and will read to EOF.
993 if (c == EOF) unexpected_EOF();
999 SRexpect = get_number();
1003 * Looking for number before EOL.
1004 * Spaces, tabs, and numbers are ok,
1005 * words, punc., etc. are syntax errors.
1007 else if (c == '\n' || isalpha(c) || !isspace(c))
1009 syntax_error(lineno, line, cptr);
1014 if (c == EOF) unexpected_EOF();
1028 if (c == EOF) unexpected_EOF();
1029 if (c != '<') syntax_error(lineno, line, cptr);
1035 if (isalpha(c) || c == '_' || c == '.' || c == '$')
1037 else if (c == '\'' || c == '"')
1042 if (bp->tag && tag != bp->tag)
1043 retyped_warning(bp->name);
1056 if (c == EOF) unexpected_EOF();
1057 if (!isalpha(c) && c != '_' && c != '.' && c != '$')
1058 syntax_error(lineno, line, cptr);
1060 if (bp->class == TERM)
1061 terminal_start(bp->name);
1062 if (goal && goal != bp)
1063 restarted_warning();
1069 read_declarations(void)
1074 cache = malloc(cache_size);
1075 if (cache == 0) no_space();
1080 if (c == EOF) unexpected_EOF();
1081 if (c != '%') syntax_error(lineno, line, cptr);
1082 switch (k = keyword())
1123 initialize_grammar(void)
1127 pitem = malloc(maxitems*sizeof(bucket *));
1128 if (pitem == 0) no_space();
1136 plhs = malloc(maxrules*sizeof(bucket *));
1137 if (plhs == 0) no_space();
1141 rprec = malloc(maxrules*sizeof(short));
1142 if (rprec == 0) no_space();
1146 rassoc = malloc(maxrules*sizeof(char));
1147 if (rassoc == 0) no_space();
1158 pitem = realloc(pitem, maxitems*sizeof(bucket *));
1159 if (pitem == 0) no_space();
1167 plhs = realloc(plhs, maxrules*sizeof(bucket *));
1168 if (plhs == 0) no_space();
1169 rprec = realloc(rprec, maxrules*sizeof(short));
1170 if (rprec == 0) no_space();
1171 rassoc = realloc(rassoc, maxrules*sizeof(char));
1172 if (rassoc == 0) no_space();
1177 advance_to_start(void)
1187 if (c != '%') break;
1203 syntax_error(lineno, line, s_cptr);
1208 if (!isalpha(c) && c != '_' && c != '.' && c != '_')
1209 syntax_error(lineno, line, cptr);
1213 if (bp->class == TERM)
1214 terminal_start(bp->name);
1220 if (c == EOF) unexpected_EOF();
1221 if (c != ':') syntax_error(lineno, line, cptr);
1222 start_rule(bp, s_lineno);
1228 start_rule(bucket *bp, int s_lineno)
1230 if (bp->class == TERM)
1231 terminal_lhs(s_lineno);
1232 bp->class = NONTERM;
1233 if (nrules >= maxrules)
1236 rprec[nrules] = UNDEFINED;
1237 rassoc[nrules] = TOKEN;
1246 if (!last_was_action && plhs[nrules]->tag)
1248 for (i = nitems - 1; pitem[i]; --i) continue;
1249 if (pitem[i+1] == 0 || pitem[i+1]->tag != plhs[nrules]->tag)
1250 default_action_warning();
1253 last_was_action = 0;
1254 if (nitems >= maxitems) expand_items();
1262 insert_empty_rule(void)
1267 sprintf(cache, "$$%d", ++gensym);
1268 bp = make_bucket(cache);
1269 last_symbol->next = bp;
1271 bp->tag = plhs[nrules]->tag;
1272 bp->class = NONTERM;
1274 if ((nitems += 2) > maxitems)
1276 bpp = pitem + nitems - 1;
1278 while ((bpp[0] = bpp[-1])) --bpp;
1280 if (++nrules >= maxrules)
1282 plhs[nrules] = plhs[nrules-1];
1283 plhs[nrules-1] = bp;
1284 rprec[nrules] = rprec[nrules-1];
1285 rprec[nrules-1] = 0;
1286 rassoc[nrules] = rassoc[nrules-1];
1287 rassoc[nrules-1] = TOKEN;
1296 int s_lineno = lineno;
1299 if (c == '\'' || c == '"')
1308 start_rule(bp, s_lineno);
1313 if (last_was_action)
1314 insert_empty_rule();
1315 last_was_action = 0;
1317 if (++nitems > maxitems)
1319 pitem[nitems-1] = bp;
1331 FILE *f = action_file;
1332 int a_lineno = lineno;
1333 char *a_line = dup_line();
1334 char *a_cptr = a_line + (cptr - line);
1336 if (last_was_action)
1337 insert_empty_rule();
1338 last_was_action = 1;
1340 fprintf(f, "case %d:\n", nrules - 2);
1342 fprintf(f, line_format, lineno, input_file_name);
1343 if (*cptr == '=') ++cptr;
1346 for (i = nitems - 1; pitem[i]; --i) ++n;
1355 int d_lineno = lineno;
1356 char *d_line = dup_line();
1357 char *d_cptr = d_line + (cptr - line);
1364 fprintf(f, "yyval.%s", tag);
1369 else if (isdigit(c))
1372 if (i > n) dollar_warning(d_lineno, i);
1373 fprintf(f, "yyvsp[%d].%s", i - n, tag);
1377 else if (c == '-' && isdigit(cptr[1]))
1380 i = -get_number() - n;
1381 fprintf(f, "yyvsp[%d].%s", i, tag);
1386 dollar_error(d_lineno, d_line, d_cptr);
1388 else if (cptr[1] == '$')
1392 tag = plhs[nrules]->tag;
1393 if (tag == 0) untyped_lhs();
1394 fprintf(f, "yyval.%s", tag);
1397 fprintf(f, "yyval");
1401 else if (isdigit(cptr[1]))
1407 if (i <= 0 || i > n)
1409 tag = pitem[nitems + i - n - 1]->tag;
1410 if (tag == 0) untyped_rhs(i, pitem[nitems + i - n - 1]->name);
1411 fprintf(f, "yyvsp[%d].%s", i - n, tag);
1416 dollar_warning(lineno, i);
1417 fprintf(f, "yyvsp[%d]", i - n);
1421 else if (cptr[1] == '-')
1427 fprintf(f, "yyvsp[%d]", -i - n);
1431 if (isalpha(c) || c == '_' || c == '$')
1437 } while (isalnum(c) || c == '_' || c == '$');
1447 if (line) goto loop;
1448 unterminated_action(a_lineno, a_line, a_cptr);
1451 if (depth > 0) goto loop;
1452 fprintf(f, "\nbreak;\n");
1460 if (--depth > 0) goto loop;
1461 fprintf(f, "\nbreak;\n");
1467 int s_lineno = lineno;
1468 char *s_line = dup_line();
1469 char *s_cptr = s_line + (cptr - line - 1);
1482 unterminated_string(s_lineno, s_line, s_cptr);
1491 unterminated_string(s_lineno, s_line, s_cptr);
1502 while ((c = *++cptr) != '\n')
1504 if (c == '*' && cptr[1] == '/')
1514 int c_lineno = lineno;
1515 char *c_line = dup_line();
1516 char *c_cptr = c_line + (cptr - line - 1);
1524 if (c == '*' && *cptr == '/')
1535 unterminated_comment(c_lineno, c_line, c_cptr);
1554 if (c == '%' || c == '\\')
1562 else if ((c == 'p' || c == 'P') &&
1563 ((c = cptr[2]) == 'r' || c == 'R') &&
1564 ((c = cptr[3]) == 'e' || c == 'E') &&
1565 ((c = cptr[4]) == 'c' || c == 'C') &&
1566 ((c = cptr[5], !IS_IDENT(c))))
1569 syntax_error(lineno, line, cptr);
1572 if (isalpha(c) || c == '_' || c == '.' || c == '$')
1574 else if (c == '\'' || c == '"')
1578 syntax_error(lineno, line, cptr);
1582 if (rprec[nrules] != UNDEFINED && bp->prec != rprec[nrules])
1585 rprec[nrules] = bp->prec;
1586 rassoc[nrules] = bp->assoc;
1596 initialize_grammar();
1602 if (c == EOF) break;
1603 if (isalpha(c) || c == '_' || c == '.' || c == '$' || c == '\'' ||
1606 else if (c == '{' || c == '=')
1611 start_rule(plhs[nrules-1], 0);
1616 if (mark_symbol()) break;
1619 syntax_error(lineno, line, cptr);
1630 if (tag_table == 0) return;
1632 for (i = 0; i < ntags; ++i)
1634 assert(tag_table[i]);
1647 name_pool_size = 13; /* 13 == sizeof("$end") + sizeof("$accept") */
1648 for (bp = first_symbol; bp; bp = bp->next)
1649 name_pool_size += strlen(bp->name) + 1;
1650 name_pool = malloc(name_pool_size);
1651 if (name_pool == 0) no_space();
1653 strcpy(name_pool, "$accept");
1654 strcpy(name_pool+8, "$end");
1656 for (bp = first_symbol; bp; bp = bp->next)
1660 while ((*t++ = *s++)) continue;
1672 if (goal->class == UNKNOWN)
1673 undefined_goal(goal->name);
1675 for (bp = first_symbol; bp; bp = bp->next)
1677 if (bp->class == UNKNOWN)
1679 undefined_symbol_warning(bp->name);
1695 for (bp = first_symbol; bp; bp = bp->next)
1698 if (bp->class == TERM) ++ntokens;
1700 start_symbol = ntokens;
1701 nvars = nsyms - ntokens;
1703 symbol_name = malloc(nsyms*sizeof(char *));
1704 if (symbol_name == 0) no_space();
1705 symbol_value = malloc(nsyms*sizeof(short));
1706 if (symbol_value == 0) no_space();
1707 symbol_prec = malloc(nsyms*sizeof(short));
1708 if (symbol_prec == 0) no_space();
1709 symbol_assoc = malloc(nsyms);
1710 if (symbol_assoc == 0) no_space();
1712 v = malloc(nsyms*sizeof(bucket *));
1713 if (v == 0) no_space();
1716 v[start_symbol] = 0;
1719 j = start_symbol + 1;
1720 for (bp = first_symbol; bp; bp = bp->next)
1722 if (bp->class == TERM)
1727 assert(i == ntokens && j == nsyms);
1729 for (i = 1; i < ntokens; ++i)
1732 goal->index = start_symbol + 1;
1733 k = start_symbol + 2;
1743 for (i = start_symbol + 1; i < nsyms; ++i)
1753 for (i = 1; i < ntokens; ++i)
1758 for (j = k++; j > 0 && symbol_value[j-1] > n; --j)
1759 symbol_value[j] = symbol_value[j-1];
1760 symbol_value[j] = n;
1764 if (v[1]->value == UNDEFINED)
1769 for (i = 2; i < ntokens; ++i)
1771 if (v[i]->value == UNDEFINED)
1773 while (j < k && n == symbol_value[j])
1775 while (++j < k && n == symbol_value[j]) continue;
1783 symbol_name[0] = name_pool + 8;
1784 symbol_value[0] = 0;
1786 symbol_assoc[0] = TOKEN;
1787 for (i = 1; i < ntokens; ++i)
1789 symbol_name[i] = v[i]->name;
1790 symbol_value[i] = v[i]->value;
1791 symbol_prec[i] = v[i]->prec;
1792 symbol_assoc[i] = v[i]->assoc;
1794 symbol_name[start_symbol] = name_pool;
1795 symbol_value[start_symbol] = -1;
1796 symbol_prec[start_symbol] = 0;
1797 symbol_assoc[start_symbol] = TOKEN;
1798 for (++i; i < nsyms; ++i)
1801 symbol_name[k] = v[i]->name;
1802 symbol_value[k] = v[i]->value;
1803 symbol_prec[k] = v[i]->prec;
1804 symbol_assoc[k] = v[i]->assoc;
1817 ritem = malloc(nitems*sizeof(short));
1818 if (ritem == 0) no_space();
1819 rlhs = malloc(nrules*sizeof(short));
1820 if (rlhs == 0) no_space();
1821 rrhs = malloc((nrules+1)*sizeof(short));
1822 if (rrhs == 0) no_space();
1823 rprec = realloc(rprec, nrules*sizeof(short));
1824 if (rprec == 0) no_space();
1825 rassoc = realloc(rassoc, nrules);
1826 if (rassoc == 0) no_space();
1829 ritem[1] = goal->index;
1834 rlhs[2] = start_symbol;
1840 for (i = 3; i < nrules; ++i)
1842 rlhs[i] = plhs[i]->index;
1848 ritem[j] = pitem[j]->index;
1849 if (pitem[j]->class == TERM)
1851 preced = pitem[j]->prec;
1852 assoc = pitem[j]->assoc;
1858 if (rprec[i] == UNDEFINED)
1876 FILE *f = verbose_file;
1882 for (i = 2; i < nrules; ++i)
1884 if (rlhs[i] != rlhs[i-1])
1886 if (i != 2) fprintf(f, "\n");
1887 fprintf(f, "%4d %s :", i - 2, symbol_name[rlhs[i]]);
1888 spacing = strlen(symbol_name[rlhs[i]]) + 1;
1892 fprintf(f, "%4d ", i - 2);
1894 while (--j >= 0) putc(' ', f);
1898 while (ritem[k] >= 0)
1900 fprintf(f, " %s", symbol_name[ritem[k]]);
1912 write_section(banner);
1913 create_symbol_table();
1914 read_declarations();
1916 free_symbol_table();