]> git.saurik.com Git - bison.git/blame - src/scan-skel.l
obstacks: simplifications
[bison.git] / src / scan-skel.l
CommitLineData
be2a1a68 1/* Scan Bison Skeletons. -*- C -*-
353d3eb6 2
139c548a 3 Copyright (C) 2001-2012 Free Software Foundation, Inc.
1239777d
AD
4
5 This file is part of Bison, the GNU Compiler Compiler.
6
f16b0819
PE
7 This program is free software: you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation, either version 3 of the License, or
10 (at your option) any later version.
1239777d 11
f16b0819
PE
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
9b3add5b 16
1239777d 17 You should have received a copy of the GNU General Public License
f16b0819 18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
9b3add5b 19
8d90395d 20%option nodefault noyywrap noinput nounput never-interactive debug
aed7fd9b 21%option prefix="skel_" outfile="lex.yy.c"
9b3add5b 22
aed7fd9b 23%{
4f6e011e
PE
24/* Work around a bug in flex 2.5.31. See Debian bug 333231
25 <http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=333231>. */
26#undef skel_wrap
27#define skel_wrap() 1
28
f9bfc42a 29#define FLEX_PREFIX(Id) skel_ ## Id
0305d25e 30#include <src/flex-scanner.h>
353d3eb6 31
cb48f191 32#include <dirname.h>
353d3eb6
PE
33#include <error.h>
34#include <quotearg.h>
35
0305d25e
AD
36#include <src/complain.h>
37#include <src/getargs.h>
38#include <src/files.h>
39#include <src/scan-skel.h>
dc9701e8 40
08af01c2
JD
41#define YY_DECL static int skel_lex (void)
42YY_DECL;
06f01bc4 43
c5e3e510 44#define QPUTS(String) \
68cae94e 45 fputs (quotearg_style (c_quoting_style, String), yyout)
c5e3e510 46
3eb82471
JD
47static void at_directive_perform (int at_directive_argc,
48 char *at_directive_argv[],
49 char **outnamep, int *out_linenop);
50static void fail_for_at_directive_too_many_args (char const *at_directive_name);
51static void fail_for_at_directive_too_few_args (char const *at_directive_name);
08af01c2 52static void fail_for_invalid_at (char const *at);
aed7fd9b 53%}
08af01c2 54
3eb82471 55%x SC_AT_DIRECTIVE_ARGS
08af01c2
JD
56%x SC_AT_DIRECTIVE_SKIP_WS
57
9b3add5b 58%%
e9683cfd
PE
59
60%{
84f6a6ca 61 int out_lineno PACIFY_CC (= 0);
e9683cfd 62 char *outname = NULL;
3eb82471
JD
63
64 /* Currently, only the @warn, @complain, @fatal, @warn_at, @complain_at, and
65 @fatal_at directives take multiple arguments, and the last three already
66 can't take more than 7. at_directive_argv[0] is the directive name. */
67 #define AT_DIRECTIVE_ARGC_MAX 8
68 int at_directive_argc = 0;
69 char *at_directive_argv[AT_DIRECTIVE_ARGC_MAX];
e9683cfd
PE
70%}
71
7dc4a694
JD
72"@@" fputc ('@', yyout);
73"@{" fputc ('[', yyout);
74"@}" fputc (']', yyout);
4d24ffb7
AD
75"@`" continue; /* Used by b4_cat in ../data/bison.m4. */
76@\n continue;
e9683cfd 77
3fc65ead 78"@oline@" fprintf (yyout, "%d", out_lineno + 1);
c5e3e510 79"@ofile@" QPUTS (outname);
bd9d212b 80
08af01c2
JD
81@[a-z_]+"(" {
82 yytext[yyleng-1] = '\0';
3eb82471 83 obstack_grow (&obstack_for_string, yytext, yyleng);
6fbe73b6 84 at_directive_argv[at_directive_argc++] = obstack_finish (&obstack_for_string);
3eb82471 85 BEGIN SC_AT_DIRECTIVE_ARGS;
bd9d212b 86}
e9683cfd 87
3fc16193 88 /* This pattern must not match more than the previous @ patterns. */
7dc4a694 89@[^@{}`(\n]* fail_for_invalid_at (yytext);
e9690142
JD
90\n out_lineno++; ECHO;
91[^@\n]+ ECHO;
e9683cfd 92
dbfcf7a8 93<INITIAL><<EOF>> {
7ec5ab2e
PE
94 if (outname)
95 {
96 free (outname);
97 xfclose (yyout);
98 }
99 return EOF;
100}
08af01c2 101
4d24ffb7
AD
102<SC_AT_DIRECTIVE_ARGS>
103{
104 [^@]+ STRING_GROW;
08af01c2 105
4d24ffb7
AD
106 "@@" obstack_1grow (&obstack_for_string, '@');
107 "@{" obstack_1grow (&obstack_for_string, '[');
108 "@}" obstack_1grow (&obstack_for_string, ']');
109 "@`" continue; /* For starting an argument that begins with whitespace. */
110 @\n continue;
08af01c2
JD
111
112 @[,)] {
113 if (at_directive_argc >= AT_DIRECTIVE_ARGC_MAX)
3eb82471 114 fail_for_at_directive_too_many_args (at_directive_argv[0]);
08af01c2 115
08af01c2 116 at_directive_argv[at_directive_argc++] =
6fbe73b6 117 obstack_finish0 (&obstack_for_string);
08af01c2
JD
118
119 /* Like M4, skip whitespace after a comma. */
120 if (yytext[1] == ',')
121 BEGIN SC_AT_DIRECTIVE_SKIP_WS;
122 else
123 {
3eb82471
JD
124 at_directive_perform (at_directive_argc, at_directive_argv,
125 &outname, &out_lineno);
08af01c2
JD
126 obstack_free (&obstack_for_string, at_directive_argv[0]);
127 at_directive_argc = 0;
08af01c2
JD
128 BEGIN INITIAL;
129 }
130 }
131
4d24ffb7 132 @.? fail_for_invalid_at (yytext);
08af01c2
JD
133}
134
4d24ffb7
AD
135<SC_AT_DIRECTIVE_SKIP_WS>
136{
137 [ \t\r\n] continue;
3eb82471 138 . { yyless (0); BEGIN SC_AT_DIRECTIVE_ARGS; }
08af01c2
JD
139}
140
4d24ffb7
AD
141<SC_AT_DIRECTIVE_ARGS,SC_AT_DIRECTIVE_SKIP_WS>
142{
08af01c2 143 <<EOF>> {
6fb8b256
VS
144 complain (fatal, _("unclosed %s directive in skeleton"),
145 at_directive_argv[0]);
08af01c2
JD
146 }
147}
148
9b3add5b 149%%
536545f3 150
2cdb2a7b
PE
151/*------------------------.
152| Scan a Bison skeleton. |
153`------------------------*/
536545f3 154
536545f3 155void
2cdb2a7b 156scan_skel (FILE *in)
536545f3 157{
08af01c2
JD
158 static bool initialized = false;
159 if (!initialized)
160 {
161 initialized = true;
162 obstack_init (&obstack_for_string);
163 }
2cdb2a7b 164 skel_in = in;
c5e3e510 165 skel__flex_debug = trace_flag & trace_skeleton;
536545f3 166 skel_lex ();
536545f3 167}
bd9d212b 168
3fc65ead
JD
169void
170skel_scanner_free (void)
171{
172 obstack_free (&obstack_for_string, 0);
3eb82471
JD
173 /* Reclaim Flex's buffers. */
174 yylex_destroy ();
3fc65ead
JD
175}
176
f39ab286
JD
177static void
178at_directive_perform (int at_directive_argc,
179 char *at_directive_argv[],
180 char **outnamep, int *out_linenop)
3fc65ead 181{
f518dbaf 182 if (STREQ (at_directive_argv[0], "@basename"))
3fc65ead 183 {
3eb82471
JD
184 if (at_directive_argc > 2)
185 fail_for_at_directive_too_many_args (at_directive_argv[0]);
186 fputs (last_component (at_directive_argv[1]), yyout);
3fc65ead 187 }
f518dbaf
AD
188 else if (STREQ (at_directive_argv[0], "@warn")
189 || STREQ (at_directive_argv[0], "@complain")
190 || STREQ (at_directive_argv[0], "@fatal"))
3fc65ead 191 {
6fb8b256 192 warnings complaint_flag;
3eb82471 193 switch (at_directive_argv[0][1])
3fc65ead 194 {
6fb8b256
VS
195 case 'w': complaint_flag = Wother; break;
196 case 'c': complaint_flag = complaint; break;
197 case 'f': complaint_flag = fatal; break;
198 default: aver (false); break;
3fc65ead
JD
199 }
200 switch (at_directive_argc)
201 {
87b0a375 202 case 2:
6fb8b256 203 complain (complaint_flag, "%s", _(at_directive_argv[1]));
3fc65ead 204 break;
87b0a375 205 case 3:
6fb8b256
VS
206 complain (complaint_flag, _(at_directive_argv[1]),
207 at_directive_argv[2]);
3fc65ead 208 break;
87b0a375 209 case 4:
6fb8b256
VS
210 complain (complaint_flag, _(at_directive_argv[1]),
211 at_directive_argv[2], at_directive_argv[3]);
3fc65ead 212 break;
87b0a375 213 case 5:
6fb8b256
VS
214 complain (complaint_flag, _(at_directive_argv[1]),
215 at_directive_argv[2], at_directive_argv[3],
216 at_directive_argv[4]);
3fc65ead 217 break;
87b0a375 218 case 6:
6fb8b256
VS
219 complain (complaint_flag, _(at_directive_argv[1]),
220 at_directive_argv[2], at_directive_argv[3],
221 at_directive_argv[4], at_directive_argv[5]);
3fc65ead
JD
222 break;
223 default:
3eb82471 224 fail_for_at_directive_too_many_args (at_directive_argv[0]);
3fc65ead
JD
225 break;
226 }
227 }
f518dbaf
AD
228 else if (STREQ (at_directive_argv[0], "@warn_at")
229 || STREQ (at_directive_argv[0], "@complain_at")
230 || STREQ (at_directive_argv[0], "@fatal_at"))
3fc65ead 231 {
6fb8b256 232 warnings complaint_flag;
3fc65ead 233 location loc;
3eb82471
JD
234 if (at_directive_argc < 4)
235 fail_for_at_directive_too_few_args (at_directive_argv[0]);
236 switch (at_directive_argv[0][1])
3fc65ead 237 {
6fb8b256
VS
238 case 'w': complaint_flag = Wother; break;
239 case 'c': complaint_flag = complaint; break;
240 case 'f': complaint_flag = fatal; break;
241 default: aver (false); break;
3fc65ead 242 }
3eb82471
JD
243 boundary_set_from_string (&loc.start, at_directive_argv[1]);
244 boundary_set_from_string (&loc.end, at_directive_argv[2]);
3fc65ead
JD
245 switch (at_directive_argc)
246 {
87b0a375 247 case 4:
6fb8b256 248 complain_at (loc, complaint_flag, "%s", _(at_directive_argv[3]));
3fc65ead 249 break;
87b0a375 250 case 5:
6fb8b256
VS
251 complain_at (loc, complaint_flag, _(at_directive_argv[3]),
252 at_directive_argv[4]);
3fc65ead 253 break;
87b0a375 254 case 6:
6fb8b256
VS
255 complain_at (loc, complaint_flag, _(at_directive_argv[3]),
256 at_directive_argv[4], at_directive_argv[5]);
3fc65ead 257 break;
87b0a375 258 case 7:
6fb8b256
VS
259 complain_at (loc, complaint_flag, _(at_directive_argv[3]),
260 at_directive_argv[4], at_directive_argv[5],
261 at_directive_argv[6]);
3fc65ead 262 break;
87b0a375 263 case 8:
6fb8b256
VS
264 complain_at (loc, complaint_flag, _(at_directive_argv[3]),
265 at_directive_argv[4], at_directive_argv[5],
266 at_directive_argv[6], at_directive_argv[7]);
3fc65ead
JD
267 break;
268 default:
3eb82471 269 fail_for_at_directive_too_many_args (at_directive_argv[0]);
3fc65ead
JD
270 break;
271 }
272 }
f518dbaf 273 else if (STREQ (at_directive_argv[0], "@output"))
3fc65ead 274 {
3eb82471
JD
275 if (at_directive_argc > 2)
276 fail_for_at_directive_too_many_args (at_directive_argv[0]);
3fc65ead
JD
277 if (*outnamep)
278 {
279 free (*outnamep);
280 xfclose (yyout);
281 }
3eb82471 282 *outnamep = xstrdup (at_directive_argv[1]);
f39ab286 283 output_file_name_check (outnamep);
3fc65ead
JD
284 yyout = xfopen (*outnamep, "w");
285 *out_linenop = 1;
286 }
287 else
3eb82471 288 fail_for_invalid_at (at_directive_argv[0]);
3fc65ead
JD
289}
290
291static void
3eb82471 292fail_for_at_directive_too_few_args (char const *at_directive_name)
3fc65ead 293{
6fb8b256 294 complain (fatal, _("too few arguments for %s directive in skeleton"),
3fc65ead
JD
295 at_directive_name);
296}
297
08af01c2 298static void
3eb82471 299fail_for_at_directive_too_many_args (char const *at_directive_name)
bd9d212b 300{
6fb8b256
VS
301 complain (fatal, _("too many arguments for %s directive in skeleton"),
302 at_directive_name);
08af01c2
JD
303}
304
305static void
306fail_for_invalid_at (char const *at)
307{
6fb8b256 308 complain (fatal, "invalid @ in skeleton: %s", at);
08af01c2 309}