mirror of
https://git.savannah.gnu.org/git/bison.git
synced 2026-03-09 12:23:04 +00:00
* src/muscle_tab.h (MUSCLE_INSERT_INT, MUSCLE_INSERT_STRING)
(MUSCLE_INSERT_PREFIX): ...to there. * src/output.c (MUSCLE_INSERT_INT, MUSCLE_INSERT_STRING) (MUSCLE_INSERT_PREFIX): Move from here... * src/bison.hairy: Add a section directive. Put braces around muscle names. This parser skeleton is still broken, but Bison should not choke on a bad muscle 'syntax'. * src/bison.simple: Add a section directive. Put braces around muscle names. * src/files.h (strsuffix, stringappend): Add declarations. (tab_extension): Add declaration. (short_base_name): Add declaration. * src/files.c (strsuffix, stringappend): No longer static. These functions are used in the skeleton parser. (tab_extension): New. (compute_base_names): Use the computations done in this function to guess if the generated parsers should have '.tab' in their names. (short_base_name): No longer static. * src/output.c (output_skeleton): New. (output): Disable call to output_master_parser, and give a try to a new skeleton handling system. (guards_output, actions_output): No longer static. (token_definitions_output, get_lines_number): No longer static. * configure.in: Use AM_PROG_LEX and AC_PROG_YACC. * src/Makefile.am (bison_SOURCES): Add scan-skel.l and parse-skel.y. * src/parse-skel.y: New file. * src/scan-skel.l: New file.
This commit is contained in:
39
ChangeLog
39
ChangeLog
@@ -1,3 +1,42 @@
|
||||
2001-12-30 Robert Anisko <robert.anisko@epita.fr>
|
||||
|
||||
* src/muscle_tab.h (MUSCLE_INSERT_INT, MUSCLE_INSERT_STRING)
|
||||
(MUSCLE_INSERT_PREFIX): ...to there.
|
||||
* src/output.c (MUSCLE_INSERT_INT, MUSCLE_INSERT_STRING)
|
||||
(MUSCLE_INSERT_PREFIX): Move from here...
|
||||
|
||||
* src/bison.hairy: Add a section directive. Put braces around muscle
|
||||
names. This parser skeleton is still broken, but Bison should not
|
||||
choke on a bad muscle 'syntax'.
|
||||
* src/bison.simple: Add a section directive. Put braces around muscle
|
||||
names.
|
||||
|
||||
* src/files.h (strsuffix, stringappend): Add declarations.
|
||||
(tab_extension): Add declaration.
|
||||
(short_base_name): Add declaration.
|
||||
|
||||
* src/files.c (strsuffix, stringappend): No longer static. These
|
||||
functions are used in the skeleton parser.
|
||||
(tab_extension): New.
|
||||
(compute_base_names): Use the computations done in this function
|
||||
to guess if the generated parsers should have '.tab' in their
|
||||
names.
|
||||
(short_base_name): No longer static.
|
||||
|
||||
* src/output.c (output_skeleton): New.
|
||||
(output): Disable call to output_master_parser, and give a try to
|
||||
a new skeleton handling system.
|
||||
(guards_output, actions_output): No longer static.
|
||||
(token_definitions_output, get_lines_number): No longer static.
|
||||
|
||||
* configure.in: Use AM_PROG_LEX and AC_PROG_YACC.
|
||||
|
||||
* src/Makefile.am (bison_SOURCES): Add scan-skel.l and
|
||||
parse-skel.y.
|
||||
|
||||
* src/parse-skel.y: New file.
|
||||
* src/scan-skel.l: New file.
|
||||
|
||||
2001-12-29 Akim Demaille <akim@epita.fr>
|
||||
|
||||
%name-prefix is broken.
|
||||
|
||||
@@ -35,6 +35,8 @@ AC_SUBST([GCC])
|
||||
|
||||
# Checks for programs.
|
||||
AC_PROG_CC
|
||||
AM_PROG_LEX
|
||||
AC_PROG_YACC
|
||||
AC_MINIX
|
||||
AC_ISC_POSIX
|
||||
AM_PROG_CC_STDC
|
||||
|
||||
@@ -23,6 +23,7 @@ DEFS = @DEFS@ \
|
||||
-DLOCALEDIR=\"$(datadir)/locale\"
|
||||
|
||||
CFLAGS = @CFLAGS@ $(WARNING_CFLAGS)
|
||||
YFLAGS = "-dv"
|
||||
|
||||
# libintl.h in is build/intl, intl/libgettext.h in src/,
|
||||
# config.h in build/.
|
||||
@@ -43,7 +44,8 @@ bison_SOURCES = LR0.c closure.c complain.c conflicts.c \
|
||||
print_graph.h print_graph.c \
|
||||
muscle_tab.h muscle_tab.c \
|
||||
options.h options.c \
|
||||
print.c reader.c reduce.c symtab.c warshall.c vcg.c
|
||||
print.c reader.c reduce.c symtab.c warshall.c vcg.c \
|
||||
parse-skel.y scan-skel.l
|
||||
|
||||
EXTRA_bison_SOURCES = vmsgetargs.c
|
||||
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
%%{section} %%{body} %%".c" %%{yacc}
|
||||
/* -*- C -*- */
|
||||
|
||||
/* YYERROR and YYCOST are set by guards. If yyerror is set to a
|
||||
@@ -332,4 +333,4 @@ yyerrlab:
|
||||
goto yyresume;
|
||||
}
|
||||
|
||||
%%actions
|
||||
%%{actions}
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
%%{section} %%{body} %%".c" %%{yacc}
|
||||
/* -*- C -*- */
|
||||
|
||||
/* A Bison parser, made from %%filename
|
||||
by GNU bison %%version. */
|
||||
/* A Bison parser, made from %%{filename}
|
||||
by GNU bison %%{version}. */
|
||||
|
||||
/* Skeleton output parser for bison,
|
||||
Copyright 1984, 1989, 1990, 2000, 2001 Free Software Foundation, Inc.
|
||||
@@ -35,31 +36,31 @@
|
||||
#define YYBISON 1
|
||||
|
||||
/* Pure parsers. */
|
||||
#define YYPURE %%pure
|
||||
#define YYPURE %%{pure}
|
||||
|
||||
/* Using locations. */
|
||||
#define YYLSP_NEEDED %%locations-flag
|
||||
#define YYLSP_NEEDED %%{locations-flag}
|
||||
|
||||
/* If NAME_PREFIX is specified substitute the variables and functions
|
||||
names. */
|
||||
#define yyparse %%prefix##parse
|
||||
#define yylex %%prefix##lex
|
||||
#define yyerror %%prefix##error
|
||||
#define yylval %%prefix##lval
|
||||
#define yychar %%prefix##char
|
||||
#define yydebug %%prefix##debug
|
||||
#define yynerrs %%prefix##nerrs
|
||||
#define yyparse %%{prefix}parse
|
||||
#define yylex %%{prefix}lex
|
||||
#define yyerror %%{prefix}error
|
||||
#define yylval %%{prefix}lval
|
||||
#define yychar %%{prefix}char
|
||||
#define yydebug %%{prefix}debug
|
||||
#define yynerrs %%{prefix}nerrs
|
||||
#if YYLSP_NEEDED
|
||||
# define yylloc %%prefix##lloc
|
||||
# define yylloc %%{prefix}lloc
|
||||
#endif
|
||||
|
||||
|
||||
/* Copy the user declarations. */
|
||||
%%prologue
|
||||
%%{prologue}
|
||||
|
||||
/* Enabling traces. */
|
||||
#ifndef YYDEBUG
|
||||
# define YYDEBUG %%debug
|
||||
# define YYDEBUG %%{debug}
|
||||
#endif
|
||||
|
||||
/* Enabling verbose error messages. */
|
||||
@@ -67,11 +68,11 @@
|
||||
# undef YYERROR_VERBOSE
|
||||
# define YYERROR_VERBOSE 1
|
||||
#else
|
||||
# define YYERROR_VERBOSE %%error-verbose
|
||||
# define YYERROR_VERBOSE %%{error-verbose}
|
||||
#endif
|
||||
|
||||
#ifndef YYSTYPE
|
||||
typedef %%stype yystype;
|
||||
typedef %%{stype} yystype;
|
||||
# define YYSTYPE yystype
|
||||
#endif
|
||||
|
||||
@@ -83,11 +84,11 @@ typedef struct yyltype
|
||||
int last_line;
|
||||
int last_column;
|
||||
} yyltype;
|
||||
# define YYLTYPE %%ltype
|
||||
# define YYLTYPE %%{ltype}
|
||||
#endif
|
||||
|
||||
/* Line %%skeleton-line of %%skeleton. */
|
||||
#line %%line "%%parser-file-name"
|
||||
/* Line %%{skeleton-line} of %%{skeleton}. */
|
||||
#line %%{line} "%%{parser-file-name}"
|
||||
|
||||
/* All symbols defined below should begin with yy or YY, to avoid
|
||||
infringing on user name space. This should be done even for local
|
||||
@@ -184,30 +185,30 @@ union yyalloc
|
||||
#endif /* ! defined (yyoverflow) || YYERROR_VERBOSE */
|
||||
|
||||
/* Tokens. */
|
||||
%%tokendef
|
||||
%%{tokendef}
|
||||
|
||||
/* YYFINAL -- State number of the termination state. */
|
||||
#define YYFINAL %%final
|
||||
#define YYFLAG %%flag
|
||||
#define YYLAST %%last
|
||||
#define YYFINAL %%{final}
|
||||
#define YYFLAG %%{flag}
|
||||
#define YYLAST %%{last}
|
||||
|
||||
/* YYNTOKENS -- Number of terminals. */
|
||||
#define YYNTOKENS %%ntokens
|
||||
#define YYNTOKENS %%{ntokens}
|
||||
/* YYNNTS -- Number of nonterminals. */
|
||||
#define YYNNTS %%nnts
|
||||
#define YYNNTS %%{nnts}
|
||||
/* YYNRULES -- Number of rules. */
|
||||
#define YYNRULES %%nrules
|
||||
#define YYNRULES %%{nrules}
|
||||
/* YYNRULES -- Number of states. */
|
||||
#define YYNSTATES %%nstates
|
||||
#define YYMAXUTOK %%maxtok
|
||||
#define YYNSTATES %%{nstates}
|
||||
#define YYMAXUTOK %%{maxtok}
|
||||
|
||||
/* YYTRANSLATE(YYLEX) -- Bison symbol number corresponding to YYLEX. */
|
||||
#define YYTRANSLATE(x) ((unsigned)(x) <= %%maxtok ? yytranslate[x] : %%nsym)
|
||||
#define YYTRANSLATE(x) ((unsigned)(x) <= %%{maxtok} ? yytranslate[x] : %%{nsym})
|
||||
|
||||
/* YYTRANSLATE[YYLEX] -- Bison symbol number corresponding to YYLEX. */
|
||||
static const char yytranslate[] =
|
||||
{
|
||||
%%translate
|
||||
%%{translate}
|
||||
};
|
||||
|
||||
#if YYDEBUG
|
||||
@@ -215,19 +216,19 @@ static const char yytranslate[] =
|
||||
YYRHS. */
|
||||
static const short yyprhs[] =
|
||||
{
|
||||
%%prhs
|
||||
%%{prhs}
|
||||
};
|
||||
|
||||
/* YYRHS -- A `-1'-separated list of the rules' RHS. */
|
||||
static const short yyrhs[] =
|
||||
{
|
||||
%%rhs
|
||||
%%{rhs}
|
||||
};
|
||||
|
||||
/* YYRLINE[YYN] -- source line where rule number YYN was defined. */
|
||||
static const short yyrline[] =
|
||||
{
|
||||
%%rline
|
||||
%%{rline}
|
||||
};
|
||||
#endif
|
||||
|
||||
@@ -236,26 +237,26 @@ static const short yyrline[] =
|
||||
First, the terminals, then, starting at YYNTOKENS, nonterminals. */
|
||||
static const char *const yytname[] =
|
||||
{
|
||||
%%tname
|
||||
%%{tname}
|
||||
};
|
||||
#endif
|
||||
|
||||
/* YYTOKNUM[YYN] -- Index in YYTNAME corresponding to YYLEX. */
|
||||
static const short yytoknum[] =
|
||||
{
|
||||
%%toknum
|
||||
%%{toknum}
|
||||
};
|
||||
|
||||
/* YYR1[YYN] -- Symbol number of symbol that rule YYN derives. */
|
||||
static const short yyr1[] =
|
||||
{
|
||||
%%r1
|
||||
%%{r1}
|
||||
};
|
||||
|
||||
/* YYR2[YYN] -- Number of symbols composing right hand side of rule YYN. */
|
||||
static const short yyr2[] =
|
||||
{
|
||||
%%r2
|
||||
%%{r2}
|
||||
};
|
||||
|
||||
/* YYDEFACT[S] -- default rule to reduce with in state S when YYTABLE
|
||||
@@ -263,26 +264,26 @@ static const short yyr2[] =
|
||||
error. */
|
||||
static const short yydefact[] =
|
||||
{
|
||||
%%defact
|
||||
%%{defact}
|
||||
};
|
||||
|
||||
/* YYPGOTO[NTERM-NUM]. */
|
||||
static const short yydefgoto[] =
|
||||
{
|
||||
%%defgoto
|
||||
%%{defgoto}
|
||||
};
|
||||
|
||||
/* YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing
|
||||
STATE-NUM. */
|
||||
static const short yypact[] =
|
||||
{
|
||||
%%pact
|
||||
%%{pact}
|
||||
};
|
||||
|
||||
/* YYPGOTO[NTERM-NUM]. */
|
||||
static const short yypgoto[] =
|
||||
{
|
||||
%%pgoto
|
||||
%%{pgoto}
|
||||
};
|
||||
|
||||
/* YYTABLE[YYPACT[STATE-NUM]]. What to do in state STATE-NUM. If
|
||||
@@ -290,12 +291,12 @@ static const short yypgoto[] =
|
||||
number is the opposite. If zero, do what YYDEFACT says. */
|
||||
static const short yytable[] =
|
||||
{
|
||||
%%table
|
||||
%%{table}
|
||||
};
|
||||
|
||||
static const short yycheck[] =
|
||||
{
|
||||
%%check
|
||||
%%{check}
|
||||
};
|
||||
|
||||
|
||||
@@ -419,7 +420,7 @@ int yydebug;
|
||||
|
||||
/* YYINITDEPTH -- initial size of the parser's stacks. */
|
||||
#ifndef YYINITDEPTH
|
||||
# define YYINITDEPTH %%initdepth
|
||||
# define YYINITDEPTH %%{initdepth}
|
||||
#endif
|
||||
|
||||
/* YYMAXDEPTH -- maximum size the stacks can grow to (effective only
|
||||
@@ -434,7 +435,7 @@ int yydebug;
|
||||
#endif
|
||||
|
||||
#ifndef YYMAXDEPTH
|
||||
# define YYMAXDEPTH %%maxdepth
|
||||
# define YYMAXDEPTH %%{maxdepth}
|
||||
#endif
|
||||
|
||||
|
||||
@@ -903,11 +904,11 @@ yyreduce:
|
||||
#endif
|
||||
switch (yyn)
|
||||
{
|
||||
%%actions
|
||||
%%{actions}
|
||||
}
|
||||
|
||||
/* Line %%skeleton-line of %%skeleton. */
|
||||
#line %%line "%%parser-file-name"
|
||||
/* Line %%{skeleton-line} of %%{skeleton}. */
|
||||
#line %%{line} "%%{parser-file-name}"
|
||||
|
||||
yyvsp -= yylen;
|
||||
yyssp -= yylen;
|
||||
@@ -1138,4 +1139,4 @@ yyreturn:
|
||||
return yyresult;
|
||||
}
|
||||
|
||||
%%epilogue
|
||||
%%{epilogue}
|
||||
|
||||
21
src/files.c
21
src/files.c
@@ -51,19 +51,22 @@ char *infile = NULL;
|
||||
char *attrsfile = NULL;
|
||||
|
||||
static char *base_name = NULL;
|
||||
static char *short_base_name = NULL;
|
||||
char *short_base_name = NULL;
|
||||
|
||||
/* C source file extension (the parser source). */
|
||||
const char *src_extension = NULL;
|
||||
/* Header file extension (if option ``-d'' is specified). */
|
||||
const char *header_extension = NULL;
|
||||
|
||||
/* Should we insert '.tab' in yacc-compatible parsers? */
|
||||
int tab_extension = 0;
|
||||
|
||||
|
||||
/*--------------------------.
|
||||
| Is SUFFIX ending STRING? |
|
||||
`--------------------------*/
|
||||
|
||||
static int
|
||||
int
|
||||
strsuffix (const char *string, const char *suffix)
|
||||
{
|
||||
size_t string_len = strlen (string);
|
||||
@@ -80,7 +83,7 @@ strsuffix (const char *string, const char *suffix)
|
||||
| STRING1, and STRING2. |
|
||||
`-----------------------------------------------------------------*/
|
||||
|
||||
static char *
|
||||
char*
|
||||
stringappend (const char *string1, const char *string2)
|
||||
{
|
||||
size_t len = strlen (string1) + strlen (string2);
|
||||
@@ -334,6 +337,11 @@ compute_base_names (void)
|
||||
short_base_length -= 4;
|
||||
short_base_name = strndup (spec_outfile, short_base_length);
|
||||
|
||||
/* FIXME: This is a quick and dirty way for me to find out if we
|
||||
should .tab or not, using the computations above. */
|
||||
if (strcmp (base_name, short_base_name))
|
||||
tab_extension = 1;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -360,6 +368,10 @@ compute_base_names (void)
|
||||
if (ext_index)
|
||||
compute_exts_from_gf (infile + ext_index);
|
||||
|
||||
/* It seems that when only a prefix is given, '.tab' should always be
|
||||
used. */
|
||||
tab_extension = 1;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -393,6 +405,9 @@ compute_base_names (void)
|
||||
strlen (short_base_name) + strlen (EXT_TAB) + 1);
|
||||
stpcpy (stpcpy (base_name, short_base_name), EXT_TAB);
|
||||
|
||||
/* By default, Bison should insert '.tab' were needed. */
|
||||
tab_extension = 1;
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
14
src/files.h
14
src/files.h
@@ -68,4 +68,18 @@ char *compute_header_macro PARAMS ((void));
|
||||
|
||||
const char *skeleton_find PARAMS ((const char *envvar,
|
||||
const char *skeleton_name));
|
||||
|
||||
/* Is SUFFIX ending STRING? */
|
||||
int strsuffix (const char* string, const char* suffix);
|
||||
|
||||
/* Return a newly allocated string composed of the concatenation of
|
||||
STRING1, and STRING2. */
|
||||
char* stringappend (const char* string1, const char* string2);
|
||||
|
||||
/* Should we insert '.tab' in yacc-compatible parsers? */
|
||||
extern int tab_extension;
|
||||
|
||||
/* Prefix used to generate output files names. */
|
||||
extern char* short_base_name;
|
||||
|
||||
#endif /* !FILES_H_ */
|
||||
|
||||
@@ -33,4 +33,26 @@ void muscle_init PARAMS ((void));
|
||||
void muscle_insert PARAMS ((const char *key, const char *value));
|
||||
const char *muscle_find PARAMS ((const char *key));
|
||||
|
||||
#define MUSCLE_INSERT_INT(Key, Value) \
|
||||
{ \
|
||||
obstack_fgrow1 (&muscle_obstack, "%d", Value); \
|
||||
obstack_1grow (&muscle_obstack, 0); \
|
||||
muscle_insert (Key, obstack_finish (&muscle_obstack)); \
|
||||
}
|
||||
|
||||
#define MUSCLE_INSERT_STRING(Key, Value) \
|
||||
{ \
|
||||
obstack_sgrow (&muscle_obstack, Value); \
|
||||
obstack_1grow (&muscle_obstack, 0); \
|
||||
muscle_insert (Key, obstack_finish (&muscle_obstack)); \
|
||||
}
|
||||
|
||||
#define MUSCLE_INSERT_PREFIX(Key, Value) \
|
||||
{ \
|
||||
obstack_fgrow2 (&muscle_obstack, "%s%s", \
|
||||
spec_name_prefix ? spec_name_prefix : "yy", Value); \
|
||||
obstack_1grow (&muscle_obstack, 0); \
|
||||
muscle_insert (Key, obstack_finish (&muscle_obstack)); \
|
||||
}
|
||||
|
||||
#endif /* not MUSCLE_TAB_H_ */
|
||||
|
||||
56
src/output.c
56
src/output.c
@@ -125,7 +125,7 @@ static struct obstack format_obstack;
|
||||
int error_verbose = 0;
|
||||
|
||||
/* Returns the number of lines of S. */
|
||||
static size_t
|
||||
size_t
|
||||
get_lines_number (const char *s)
|
||||
{
|
||||
size_t lines = 0;
|
||||
@@ -503,7 +503,7 @@ token_actions (void)
|
||||
| Output the actions to OOUT. |
|
||||
`-----------------------------*/
|
||||
|
||||
static void
|
||||
void
|
||||
actions_output (FILE *out, size_t *line)
|
||||
{
|
||||
int rule;
|
||||
@@ -539,7 +539,7 @@ actions_output (FILE *out, size_t *line)
|
||||
| Output the guards to OOUT. |
|
||||
`----------------------------*/
|
||||
|
||||
static void
|
||||
void
|
||||
guards_output (FILE *out, size_t *line)
|
||||
{
|
||||
int rule;
|
||||
@@ -571,7 +571,7 @@ guards_output (FILE *out, size_t *line)
|
||||
| Output the tokens definition to OOUT. |
|
||||
`---------------------------------------*/
|
||||
|
||||
static void
|
||||
void
|
||||
token_definitions_output (FILE *out, size_t *line)
|
||||
{
|
||||
int i;
|
||||
@@ -1042,6 +1042,11 @@ static void
|
||||
output_master_parser (void)
|
||||
{
|
||||
FILE *parser = xfopen (parser_file_name, "w");
|
||||
|
||||
/* FIXME: Remove the two following lines. */
|
||||
printf ("Test: %s\n", infile);
|
||||
printf ("Test: %s\n", parser_file_name);
|
||||
|
||||
if (!skeleton)
|
||||
{
|
||||
if (semantic_parser)
|
||||
@@ -1056,29 +1061,24 @@ output_master_parser (void)
|
||||
xfclose (parser);
|
||||
}
|
||||
|
||||
/* Call the skeleton parser. */
|
||||
|
||||
/* FIXME. */
|
||||
static
|
||||
void
|
||||
output_skeleton ()
|
||||
{
|
||||
/* Find the right skeleton file. */
|
||||
if (!skeleton)
|
||||
{
|
||||
if (semantic_parser)
|
||||
skeleton = skeleton_find ("BISON_HAIRY", BISON_HAIRY);
|
||||
else
|
||||
skeleton = skeleton_find ("BISON_SIMPLE", BISON_SIMPLE);
|
||||
}
|
||||
|
||||
#define MUSCLE_INSERT_INT(Key, Value) \
|
||||
{ \
|
||||
obstack_fgrow1 (&muscle_obstack, "%d", Value); \
|
||||
obstack_1grow (&muscle_obstack, 0); \
|
||||
muscle_insert (Key, obstack_finish (&muscle_obstack)); \
|
||||
}
|
||||
|
||||
#define MUSCLE_INSERT_STRING(Key, Value) \
|
||||
{ \
|
||||
obstack_sgrow (&muscle_obstack, Value); \
|
||||
obstack_1grow (&muscle_obstack, 0); \
|
||||
muscle_insert (Key, obstack_finish (&muscle_obstack)); \
|
||||
}
|
||||
|
||||
#define MUSCLE_INSERT_PREFIX(Key, Value) \
|
||||
{ \
|
||||
obstack_fgrow2 (&muscle_obstack, "%s%s", \
|
||||
spec_name_prefix ? spec_name_prefix : "yy", Value); \
|
||||
obstack_1grow (&muscle_obstack, 0); \
|
||||
muscle_insert (Key, obstack_finish (&muscle_obstack)); \
|
||||
/* Parse the skeleton file and output the needed parsers. */
|
||||
muscle_insert ("skeleton", skeleton);
|
||||
process_skeleton (infile, skeleton);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -1102,7 +1102,6 @@ prepare (void)
|
||||
MUSCLE_INSERT_INT ("locations-flag", locations_flag);
|
||||
}
|
||||
|
||||
|
||||
/*-------------------------.
|
||||
| Output the header file. |
|
||||
`-------------------------*/
|
||||
@@ -1188,8 +1187,13 @@ output (void)
|
||||
obstack_1grow (&attrs_obstack, 0);
|
||||
muscle_insert ("prologue", obstack_finish (&attrs_obstack));
|
||||
|
||||
/* Process the selected skeleton file. */
|
||||
output_skeleton ();
|
||||
|
||||
/* Output the parser. */
|
||||
#if 0
|
||||
output_master_parser ();
|
||||
#endif
|
||||
/* Output the header if needed. */
|
||||
if (defines_flag)
|
||||
header_output ();
|
||||
|
||||
176
src/parse-skel.y
Normal file
176
src/parse-skel.y
Normal file
@@ -0,0 +1,176 @@
|
||||
%{
|
||||
|
||||
#include "system.h"
|
||||
#include "obstack.h"
|
||||
#include "files.h"
|
||||
|
||||
#include "muscle_tab.h"
|
||||
|
||||
#define YYDEBUG 1
|
||||
#define YYERROR_VERBOSE 1
|
||||
|
||||
extern FILE* yyin;
|
||||
extern int yylineno;
|
||||
|
||||
char* prefix = NULL;
|
||||
FILE* parser = NULL;
|
||||
|
||||
size_t output_line;
|
||||
size_t skeleton_line;
|
||||
|
||||
extern struct obstack muscle_obstack;
|
||||
|
||||
%}
|
||||
|
||||
%union
|
||||
{
|
||||
char* muscle;
|
||||
char* string;
|
||||
char character;
|
||||
int yacc;
|
||||
}
|
||||
|
||||
%token< muscle > MUSCLE
|
||||
%token< string > STRING
|
||||
%token< character > CHARACTER
|
||||
|
||||
%token LINE
|
||||
%token SLINE
|
||||
|
||||
%token YACC
|
||||
%token SECTION
|
||||
|
||||
%token GUARDS
|
||||
%token TOKENS
|
||||
%token ACTIONS
|
||||
|
||||
%type< yacc > section.yacc
|
||||
|
||||
%start skeleton
|
||||
|
||||
%%
|
||||
|
||||
skeleton : /* Empty. */ { }
|
||||
| section skeleton { }
|
||||
;
|
||||
|
||||
section : section.header section.body { }
|
||||
;
|
||||
|
||||
section.header : SECTION gb MUSCLE gb STRING gb section.yacc gb '\n'
|
||||
{
|
||||
char* name = 0;
|
||||
char* limit = 0;
|
||||
char* suffix = $5;
|
||||
|
||||
/* Close the previous parser. */
|
||||
if (parser)
|
||||
parser = (xfclose (parser), NULL);
|
||||
|
||||
/* If the following section should be named with the yacc-style, and it's
|
||||
suffix is of the form 'something.h' or 'something.c', then add '.tab' in
|
||||
the middle of the suffix. */
|
||||
if (tab_extension && $7 && (strsuffix (suffix, ".h") ||
|
||||
strsuffix (suffix, ".c")))
|
||||
{
|
||||
size_t prefix_len = strlen (prefix);
|
||||
size_t suffix_len = strlen (suffix);
|
||||
|
||||
/* Allocate enough space to insert '.tab'. */
|
||||
name = XMALLOC (char, prefix_len + suffix_len + 5);
|
||||
limit = strrchr (suffix, '.');
|
||||
if (!limit)
|
||||
limit = suffix;
|
||||
|
||||
/* Prefix is 'X', suffix is 'Y.Z'. Name will be 'XY.tab.Z'. */
|
||||
{
|
||||
char* cp = 0;
|
||||
cp = stpcpy (name, prefix);
|
||||
cp = stpncpy (cp, suffix, limit - suffix);
|
||||
cp = stpcpy (cp, ".tab");
|
||||
cp = stpcpy (cp, limit);
|
||||
}
|
||||
}
|
||||
else
|
||||
name = stringappend (prefix, suffix);
|
||||
|
||||
/* Prepare the next parser to be output. */
|
||||
parser = xfopen (name, "w");
|
||||
MUSCLE_INSERT_STRING ("parser-file-name", name);
|
||||
XFREE (name);
|
||||
|
||||
++skeleton_line;
|
||||
}
|
||||
;
|
||||
|
||||
section.yacc : /* Empty. */ { $$ = 0; }
|
||||
| YACC { $$ = 1; }
|
||||
;
|
||||
|
||||
section.body
|
||||
: /* Empty. */ { }
|
||||
| section.body '\n' { fputc ('\n', parser); ++output_line; ++skeleton_line; }
|
||||
| section.body LINE { fprintf (parser, "%d", output_line); }
|
||||
| section.body SLINE { fprintf (parser, "%d", skeleton_line); }
|
||||
| section.body GUARDS { guards_output (parser, &output_line); }
|
||||
| section.body TOKENS { token_definitions_output (parser, &output_line); }
|
||||
| section.body ACTIONS { actions_output (parser, &output_line); }
|
||||
| section.body CHARACTER { fputc ($2, parser); }
|
||||
| section.body MUSCLE {
|
||||
const char* value = muscle_find ($2);
|
||||
if (value)
|
||||
{
|
||||
fputs (value, parser);
|
||||
output_line += get_lines_number (value);
|
||||
}
|
||||
else
|
||||
{
|
||||
fprintf (parser, "%%{%s}", $2);
|
||||
merror ($2);
|
||||
}
|
||||
}
|
||||
;
|
||||
|
||||
gb : /* Empty. */ { }
|
||||
| gb CHARACTER { /* Do not echo garbage characters. */ }
|
||||
;
|
||||
|
||||
%%
|
||||
|
||||
int
|
||||
merror (const char* error)
|
||||
{
|
||||
printf ("line %d: %%{%s} undeclared.\n", skeleton_line, error);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
yyerror (const char* error)
|
||||
{
|
||||
printf ("line %d: %s.\n", yylineno, error);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
process_skeleton (const char* grammar,
|
||||
const char* skeleton)
|
||||
{
|
||||
const char* limit = 0;
|
||||
|
||||
/* Compute prefix. Actually, it seems that the processing I need here is
|
||||
done in compute_base_names, and the result stored in short_base_name. */
|
||||
prefix = short_base_name;
|
||||
|
||||
/* Prepare a few things. */
|
||||
output_line = 1;
|
||||
skeleton_line = 1;
|
||||
|
||||
/* Output. */
|
||||
yyin = fopen (skeleton, "r");
|
||||
yydebug = 0;
|
||||
yyparse ();
|
||||
|
||||
/* Close the last parser. */
|
||||
if (parser)
|
||||
parser = (xfclose (parser), NULL);
|
||||
}
|
||||
55
src/scan-skel.l
Normal file
55
src/scan-skel.l
Normal file
@@ -0,0 +1,55 @@
|
||||
%{
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "parse-skel.h"
|
||||
|
||||
%}
|
||||
|
||||
%option nounput
|
||||
%option noyywrap
|
||||
%option yylineno
|
||||
|
||||
%%
|
||||
|
||||
"%%{line}" { return LINE; }
|
||||
"%%{skeleton-line}" { return SLINE; }
|
||||
|
||||
"%%{yacc}" { return YACC; }
|
||||
"%%{section}" { return SECTION; }
|
||||
|
||||
"%%{guards}" { return GUARDS; }
|
||||
"%%{actions}" { return ACTIONS; }
|
||||
"%%{tokendef}" { return TOKENS; }
|
||||
|
||||
"%%{"[a-zA-Z][0-9a-zA-Z_-]+"}" { /* Muscle. */
|
||||
size_t len = strlen (yytext);
|
||||
yylval.string = (char*) malloc (len - 3);
|
||||
strncpy (yylval.string, yytext + 3, len - 4);
|
||||
yylval.string[len - 4] = 0;
|
||||
return MUSCLE;
|
||||
}
|
||||
|
||||
"%%\"".*"\"" { /* String. */
|
||||
size_t len = strlen (yytext);
|
||||
yylval.string = (char*) malloc (len - 3);
|
||||
strncpy (yylval.string, yytext + 3, len - 4);
|
||||
yylval.string[len - 4] = 0;
|
||||
return STRING;
|
||||
}
|
||||
|
||||
<<EOF>> { /* End of file. */
|
||||
return 0;
|
||||
}
|
||||
|
||||
"\n" { /* End of line. */
|
||||
return '\n';
|
||||
}
|
||||
|
||||
. { /* Character. */
|
||||
yylval.character = *yytext;
|
||||
return CHARACTER;
|
||||
}
|
||||
|
||||
%%
|
||||
Reference in New Issue
Block a user