/* Input parser for bison
- Copyright (C) 1984, 1986, 1989, 1992 Free Software Foundation, Inc.
+ Copyright (C) 1984, 86, 89, 92, 98, 2000 Free Software Foundation, Inc.
-This file is part of Bison, the GNU Compiler Compiler.
+ This file is part of Bison, the GNU Compiler Compiler.
-Bison is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2, or (at your option)
-any later version.
+ Bison is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
-Bison is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-GNU General Public License for more details.
+ Bison is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with Bison; see the file COPYING. If not, write to
-the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
+ You should have received a copy of the GNU General Public License
+ along with Bison; see the file COPYING. If not, write to
+ the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ Boston, MA 02111-1307, USA. */
-/* read in the grammar specification and record it in the format described in gram.h.
- All guards are copied into the fguard file and all actions into faction,
- in each case forming the body of a C function (yyguard or yyaction)
- which contains a switch statement to decide which guard or action to execute.
+/* Read in the grammar specification and record it in the format
+ described in gram.h. All guards are copied into the fguard file
+ and all actions into faction, in each case forming the body of a C
+ function (yyguard or yyaction) which contains a switch statement to
+ decide which guard or action to execute.
-The entry point is reader(). */
+ The entry point is reader (). */
#include <stdio.h>
-#include <ctype.h>
#include "system.h"
#include "files.h"
#include "alloc.h"
extern int numval;
extern int expected_conflicts;
extern char *token_buffer;
-
-extern void init_lex();
-extern void tabinit();
-extern void output_headers();
-extern void output_trailers();
-extern void free_symtab();
-extern void open_extra_files();
-extern char *int_to_string();
-extern void fatal();
-extern void fatals();
-extern void warn();
-extern void warni();
-extern void warns();
-extern void warnss();
-extern void warnsss();
-extern void unlex();
-extern void done();
-
-extern int skip_white_space();
-extern int parse_percent_token();
-extern int lex();
-
-void reader_output_yylsp();
-void read_declarations();
-void copy_definition();
-void parse_token_decl();
-void parse_start_decl();
-void parse_type_decl();
-void parse_assoc_decl();
-void parse_union_decl();
-void parse_expect_decl();
-void parse_thong_decl();
-void copy_action();
-void readgram();
-void record_rule_line();
-void packsymbols();
-void output_token_defines();
-void packgram();
-int read_signed_integer();
-static int get_type();
+extern int maxtoken;
+
+extern void init_lex PARAMS((void));
+extern char *grow_token_buffer PARAMS((char *));
+extern void tabinit PARAMS((void));
+extern void output_headers PARAMS((void));
+extern void output_trailers PARAMS((void));
+extern void free_symtab PARAMS((void));
+extern void open_extra_files PARAMS((void));
+extern char *int_to_string PARAMS((int));
+extern char *printable_version PARAMS((int));
+extern void fatal PARAMS((char *));
+extern void fatals PARAMS((char *, char *));
+extern void warn PARAMS((char *));
+extern void warni PARAMS((char *, int));
+extern void warns PARAMS((char *, char *));
+extern void warnss PARAMS((char *, char *, char *));
+extern void warnsss PARAMS((char *, char *, char *, char *));
+extern void unlex PARAMS((int));
+extern void done PARAMS((int));
+
+extern int skip_white_space PARAMS((void));
+extern int parse_percent_token PARAMS((void));
+extern int lex PARAMS((void));
typedef
struct symbol_list
symbol_list;
+void reader PARAMS((void));
+void reader_output_yylsp PARAMS((FILE *));
+void read_declarations PARAMS((void));
+void copy_definition PARAMS((void));
+void parse_token_decl PARAMS((int, int));
+void parse_start_decl PARAMS((void));
+void parse_type_decl PARAMS((void));
+void parse_assoc_decl PARAMS((int));
+void parse_union_decl PARAMS((void));
+void parse_expect_decl PARAMS((void));
+char *get_type_name PARAMS((int, symbol_list *));
+void copy_guard PARAMS((symbol_list *, int));
+void parse_thong_decl PARAMS((void));
+void copy_action PARAMS((symbol_list *, int));
+bucket *gensym PARAMS((void));
+void readgram PARAMS((void));
+void record_rule_line PARAMS((void));
+void packsymbols PARAMS((void));
+void output_token_defines PARAMS((FILE *));
+void packgram PARAMS((void));
+int read_signed_integer PARAMS((FILE *));
+
+#if 0
+static int get_type PARAMS((void));
+#endif
int lineno;
symbol_list *grammar;
static int gensym_count; /* incremented for each generated symbol */
static bucket *errtoken;
+static bucket *undeftoken;
/* Nonzero if any action or guard uses the @n construct. */
static int yylsp_needed;
-extern char *version_string;
-
static void
-skip_to_char(target)
- int target;
+skip_to_char (int target)
{
int c;
if (target == '\n')
void
-reader()
+reader (void)
{
start_flag = 0;
startval = NULL; /* start symbol not specified yet. */
errtoken->user_token_number = 256; /* Value specified by posix. */
/* construct a token that represents all undefined literal tokens. */
/* it is always token number 2. */
- getsym("$undefined.")->class = STOKEN;
+ undeftoken = getsym("$undefined.");
+ undeftoken->class = STOKEN;
+ undeftoken->user_token_number = 2;
/* Read the declaration section. Copy %{ ... %} groups to ftable and fdefines file.
Also notice any %token, %left, etc. found there. */
if (noparserflag)
infile);
else
fprintf(ftable, "\n/* A Bison parser, made from %s\n", infile);
- fprintf(ftable, " by %s */\n\n", version_string);
+ fprintf(ftable, " by %s */\n\n", VERSION_STRING);
fprintf(ftable, "#define YYBISON 1 /* Identify Bison output. */\n\n");
read_declarations();
/* start writing the guard and action files, if they are needed. */
}
void
-reader_output_yylsp(f)
- FILE *f;
+reader_output_yylsp (FILE *f)
{
if (yylsp_needed)
fprintf(f, LTYPESTR);
}
-/* read from finput until %% is seen. Discard the %%.
-Handle any % declarations,
-and copy the contents of any %{ ... %} groups to fattrs. */
+/* Read from finput until `%%' is seen. Discard the `%%'. Handle any
+ `%' declarations, and copy the contents of any `%{ ... %}' groups
+ to fattrs. */
void
-read_declarations ()
+read_declarations (void)
{
register int c;
register int tok;
The %{ has already been read. Return after reading the %}. */
void
-copy_definition ()
+copy_definition (void)
{
register int c;
register int match;
For %nterm, the arguments are reversed. */
void
-parse_token_decl (what_is, what_is_not)
- int what_is, what_is_not;
+parse_token_decl (int what_is, int what_is_not)
{
register int token = 0;
register char *typename = 0;
for (;;)
{
- if(ungetc(skip_white_space(), finput) == '%')
+ int tmp_char = ungetc (skip_white_space (), finput);
+
+ if (tmp_char == '%')
return;
+ if (tmp_char == EOF)
+ fatals ("Premature EOF after %s", token_buffer);
+
token = lex();
if (token == COMMA)
{
*/
void
-parse_thong_decl ()
+parse_thong_decl (void)
{
register int token;
register struct bucket *symbol;
/* parse what comes after %start */
void
-parse_start_decl ()
+parse_start_decl (void)
{
if (start_flag)
warn(_("multiple %start declarations"));
/* read in a %type declaration and record its information for get_type_name to access */
void
-parse_type_decl ()
+parse_type_decl (void)
{
register int k;
register char *name;
for (;;)
{
register int t;
+ int tmp_char = ungetc (skip_white_space (), finput);
- if(ungetc(skip_white_space(), finput) == '%')
+ if (tmp_char == '%')
return;
+ if (tmp_char == EOF)
+ fatals ("Premature EOF after %s", token_buffer);
t = lex();
/* assoc is either LEFT_ASSOC, RIGHT_ASSOC or NON_ASSOC. */
void
-parse_assoc_decl (assoc)
-int assoc;
+parse_assoc_decl (int assoc)
{
register int k;
register char *name = NULL;
for (;;)
{
register int t;
+ int tmp_char = ungetc (skip_white_space (), finput);
- if(ungetc(skip_white_space(), finput) == '%')
+ if (tmp_char == '%')
return;
+ if (tmp_char == EOF)
+ fatals ("Premature EOF after %s", token_buffer);
t = lex();
definition of YYSTYPE, the type of elements of the parser value stack. */
void
-parse_union_decl()
+parse_union_decl (void)
{
register int c;
register int count;
shift-reduce conflicts. */
void
-parse_expect_decl()
+parse_expect_decl (void)
{
register int c;
register int count;
/* Get the data type (alternative in the union) of the value for symbol n in rule rule. */
char *
-get_type_name(n, rule)
-int n;
-symbol_list *rule;
+get_type_name (int n, symbol_list *rule)
{
static char *msg = N_("invalid $ value");
}
-/* after %guard is seen in the input file,
-copy the actual guard into the guards file.
-If the guard is followed by an action, copy that into the actions file.
-stack_offset is the number of values in the current rule so far,
-which says where to find $0 with respect to the top of the stack,
-for the simple parser in which the stack is not popped until after the guard is run. */
+/* After `%guard' is seen in the input file, copy the actual guard
+ into the guards file. If the guard is followed by an action, copy
+ that into the actions file. STACK_OFFSET is the number of values
+ in the current rule so far, which says where to find `$0' with
+ respect to the top of the stack, for the simple parser in which the
+ stack is not popped until after the guard is run. */
void
-copy_guard(rule, stack_offset)
-symbol_list *rule;
-int stack_offset;
+copy_guard (symbol_list *rule, int stack_offset)
{
register int c;
register int n;
fprintf(fguard, "\ncase %d:\n", nrules);
if (!nolinesflag)
- fprintf(fguard, "#line %d \"%s\"\n", lineno, infile);
+ fprintf (fguard, "#line %d \"%s\"\n", lineno, infile);
putc('{', fguard);
count = 0;
register char *cp = token_buffer;
while ((c = getc(finput)) != '>' && c > 0)
- *cp++ = c;
+ {
+ if (cp == token_buffer + maxtoken)
+ cp = grow_token_buffer(cp);
+
+ *cp++ = c;
+ }
*cp = 0;
type_name = token_buffer;
if (c == '$')
{
fprintf(fguard, "yyval");
- if (!type_name) type_name = rule->sym->type_name;
+ if (!type_name)
+ type_name = rule->sym->type_name;
if (type_name)
fprintf(fguard, ".%s", type_name);
if(!type_name && typed)
warns(_("$$ of `%s' has no declared type"), rule->sym->tag);
}
-
else if (isdigit(c) || c == '-')
{
ungetc (c, finput);
- n = read_signed_integer(finput);
- c = getc(finput);
+ n = read_signed_integer (finput);
+ c = getc (finput);
if (!type_name && n > 0)
type_name = get_type_name(n, rule);
continue;
}
else
- warni(_("$%s is invalid"), printable_version(c));
+ warns(_("$%s is invalid"), printable_version(c));
break;
}
else
{
- warni(_("@%s is invalid"), printable_version(c));
+ warns(_("@%s is invalid"), printable_version(c));
n = 1;
}
-/* Assuming that a { has just been seen, copy everything up to the matching }
-into the actions file.
-stack_offset is the number of values in the current rule so far,
-which says where to find $0 with respect to the top of the stack. */
+/* Assuming that a `{' has just been seen, copy everything up to the
+ matching `}' into the actions file. STACK_OFFSET is the number of
+ values in the current rule so far, which says where to find `$0'
+ with respect to the top of the stack. */
void
-copy_action(rule, stack_offset)
-symbol_list *rule;
-int stack_offset;
+copy_action (symbol_list *rule, int stack_offset)
{
register int c;
register int n;
int cplus_comment;
/* offset is always 0 if parser has already popped the stack pointer */
- if (semantic_parser) stack_offset = 0;
+ if (semantic_parser)
+ stack_offset = 0;
- fprintf(faction, "\ncase %d:\n", nrules);
+ fprintf (faction, "\ncase %d:\n", nrules);
if (!nolinesflag)
- fprintf(faction, "#line %d \"%s\"\n", lineno, infile);
- putc('{', faction);
+ fprintf (faction, "#line %d \"%s\"\n", lineno, infile);
+ putc ('{', faction);
count = 1;
c = getc(finput);
register char *cp = token_buffer;
while ((c = getc(finput)) != '>' && c > 0)
- *cp++ = c;
+ {
+ if (cp == token_buffer + maxtoken)
+ cp = grow_token_buffer(cp);
+
+ *cp++ = c;
+ }
*cp = 0;
type_name = token_buffer;
value_components_used = 1;
if (c == '$')
{
fprintf(faction, "yyval");
- if (!type_name) type_name = get_type_name(0, rule);
+ if (!type_name)
+ type_name = get_type_name(0, rule);
if (type_name)
fprintf(faction, ".%s", type_name);
if(!type_name && typed)
- warns(_("$$ of `%s' has no declared type"), rule->sym->tag);
+ warns(_("$$ of `%s' has no declared type"),
+ rule->sym->tag);
}
else if (isdigit(c) || c == '-')
{
continue;
}
else
- warni(_("$%s is invalid"), printable_version(c));
+ warns(_("$%s is invalid"), printable_version(c));
break;
whose name cannot conflict with the user's names. */
bucket *
-gensym()
+gensym (void)
{
register bucket *sym;
labelled by the rule number they apply to. */
void
-readgram()
+readgram (void)
{
register int t;
- register bucket *lhs;
+ register bucket *lhs = NULL;
register symbol_list *p;
register symbol_list *p1;
register bucket *bp;
void
-record_rule_line ()
+record_rule_line (void)
{
/* Record each rule's source line number in rline table. */
if (nrules >= rline_allocated)
{
rline_allocated = nrules * 2;
- rline = (short *) xrealloc (rline,
- rline_allocated * sizeof (short));
+ rline = (short *) xrealloc ((char *) rline,
+ rline_allocated * sizeof (short));
}
rline[nrules] = lineno;
}
+#if 0
/* read in a %type declaration and record its information for get_type_name to access */
/* this is unused. it is only called from the #if 0 part of readgram */
static int
-get_type()
+get_type (void)
{
register int k;
register int t;
}
}
}
-
+#endif
/* assign symbol numbers, and write definition of token names into fdefines.
Set up vectors tags and sprec of names and precedences of symbols. */
void
-packsymbols()
+packsymbols (void)
{
register bucket *bp;
register int tokno = 1;
The value is the user token number.
*/
void
-output_token_defines(file)
-FILE *file;
+output_token_defines (FILE *file)
{
bucket *bp;
register char *cp, *symbol;
/* convert the rules into the representation using rrhs, rlhs and ritems. */
void
-packgram()
+packgram (void)
{
register int itemno;
register int ruleno;
/* Read a signed integer from STREAM and return its value. */
int
-read_signed_integer (stream)
- FILE *stream;
+read_signed_integer (FILE *stream)
{
register int c = getc(stream);
register int sign = 1;