]> git.saurik.com Git - bison.git/blame - src/parse-gram.y
maint: address syntax-check errors.
[bison.git] / src / parse-gram.y
CommitLineData
12ffdd28 1%{/* Bison Grammar Parser -*- C -*-
a737b216 2
c932d613 3 Copyright (C) 2002-2012 Free Software Foundation, Inc.
e9955c83
AD
4
5 This file is part of Bison, the GNU Compiler Compiler.
6
f16b0819 7 This program is free software: you can redistribute it and/or modify
e9955c83 8 it under the terms of the GNU General Public License as published by
f16b0819 9 the Free Software Foundation, either version 3 of the License, or
e9955c83
AD
10 (at your option) any later version.
11
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.
16
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/>. */
e9955c83 19
2cec9080 20#include <config.h>
e9955c83 21#include "system.h"
3d2cbc26 22
457bf919 23#include "c-ctype.h"
b275314e 24#include "complain.h"
3d2cbc26 25#include "conflicts.h"
e9955c83
AD
26#include "files.h"
27#include "getargs.h"
e9955c83 28#include "gram.h"
23ec25b7 29#include "muscle-tab.h"
d5e8574b 30#include "named-ref.h"
ca407bdf 31#include "quotearg.h"
e9955c83 32#include "reader.h"
3d2cbc26 33#include "symlist.h"
e9071366
AD
34#include "scan-gram.h"
35#include "scan-code.h"
e54ec80c 36#include "xmemdup0.h"
e9955c83 37
b7295522
PE
38#define YYLLOC_DEFAULT(Current, Rhs, N) (Current) = lloc_default (Rhs, N)
39static YYLTYPE lloc_default (YYLTYPE const *, int);
4cdb01db 40
b233d555 41#define YY_LOCATION_PRINT(File, Loc) \
f0064700 42 location_print (File, Loc)
b233d555 43
b50d2359
AD
44static void version_check (location const *loc, char const *version);
45
6e649e65 46/* Request detailed syntax error messages, and pass them to GRAM_ERROR.
ad8a3efc 47 FIXME: depends on the undocumented availability of YYLLOC. */
e9955c83
AD
48#undef yyerror
49#define yyerror(Msg) \
f0064700 50 gram_error (&yylloc, Msg)
3d2cbc26 51static void gram_error (location const *, char const *);
e9955c83 52
33ad1a9c
PE
53static char const *char_name (char);
54
2ce4ed68
AD
55/** Add a lex-param or a parse-param.
56 *
57 * \param type \a lex_param or \a parse_param
58 * \param decl the formal argument
59 * \param loc the location in the source.
60 */
61static void add_param (char const *type, char *decl, location loc);
62
1773ceee 63
04098407 64static symbol_class current_class = unknown_sym;
ddc8ede1 65static uniqstr current_type = NULL;
8f462efe 66static symbol *current_lhs_symbol;
877519f8 67static location current_lhs_location;
7685e2f7 68static named_ref *current_lhs_named_ref;
04098407 69static int current_prec = 0;
d42cf844 70
8f462efe
AD
71/** Set the new current left-hand side symbol, possibly common
72 * to several right-hand side parts of rule.
73 */
74static
75void
76current_lhs(symbol *sym, location loc, named_ref *ref)
77{
78 current_lhs_symbol = sym;
79 current_lhs_location = loc;
80 /* In order to simplify memory management, named references for lhs
81 are always assigned by deep copy into the current symbol_list
82 node. This is because a single named-ref in the grammar may
83 result in several uses when the user factors lhs between several
84 rules using "|". Therefore free the parser's original copy. */
85 free (current_lhs_named_ref);
86 current_lhs_named_ref = ref;
87}
88
89
cb48f191
PE
90#define YYTYPE_INT16 int_fast16_t
91#define YYTYPE_INT8 int_fast8_t
92#define YYTYPE_UINT16 uint_fast16_t
93#define YYTYPE_UINT8 uint_fast8_t
e9955c83
AD
94%}
95
12ffdd28 96%debug
e73ac5a0
AD
97%define api.prefix "gram_"
98%define api.pure
99%define parse.lac full
12ffdd28 100%defines
12ffdd28 101%error-verbose
219741d8 102%expect 0
e73ac5a0
AD
103%locations
104%verbose
12ffdd28 105
cd3684cf
AD
106%initial-action
107{
108 /* Bison's grammar can initial empty locations, hence a default
109 location is needed. */
4a678af8
JD
110 boundary_set (&@$.start, current_file, 1, 1);
111 boundary_set (&@$.end, current_file, 1, 1);
cd3684cf 112}
e9955c83 113
e9955c83
AD
114%union
115{
3d2cbc26
PE
116 symbol *symbol;
117 symbol_list *list;
e9955c83 118 int integer;
eb095650
PE
119 char const *chars;
120 char *code;
3d2cbc26
PE
121 assoc assoc;
122 uniqstr uniqstr;
58d7a1a1 123 unsigned char character;
7685e2f7 124 named_ref *named_ref;
e9955c83
AD
125};
126
f9a85a15 127/* Define the tokens together with their human representation. */
3d38c03a
AD
128%token GRAM_EOF 0 "end of file"
129%token STRING "string"
3d38c03a 130%token INT "integer"
e9955c83 131
9280d3ef
AD
132%token PERCENT_TOKEN "%token"
133%token PERCENT_NTERM "%nterm"
366eea36 134
9280d3ef 135%token PERCENT_TYPE "%type"
e9071366
AD
136%token PERCENT_DESTRUCTOR "%destructor"
137%token PERCENT_PRINTER "%printer"
366eea36 138
9280d3ef
AD
139%token PERCENT_LEFT "%left"
140%token PERCENT_RIGHT "%right"
141%token PERCENT_NONASSOC "%nonassoc"
04e60654 142
3d38c03a
AD
143%token PERCENT_PREC "%prec"
144%token PERCENT_DPREC "%dprec"
145%token PERCENT_MERGE "%merge"
e9955c83 146
e9955c83 147
ae7453f2
AD
148/*----------------------.
149| Global Declarations. |
150`----------------------*/
151
152%token
136a0f76 153 PERCENT_CODE "%code"
cd3684cf 154 PERCENT_DEBUG "%debug"
39a06c25 155 PERCENT_DEFAULT_PREC "%default-prec"
cd3684cf
AD
156 PERCENT_DEFINE "%define"
157 PERCENT_DEFINES "%defines"
158 PERCENT_ERROR_VERBOSE "%error-verbose"
159 PERCENT_EXPECT "%expect"
d6328241 160 PERCENT_EXPECT_RR "%expect-rr"
cd3684cf
AD
161 PERCENT_FILE_PREFIX "%file-prefix"
162 PERCENT_GLR_PARSER "%glr-parser"
e9071366 163 PERCENT_INITIAL_ACTION "%initial-action"
0e021770 164 PERCENT_LANGUAGE "%language"
e9071366 165 PERCENT_LEX_PARAM "%lex-param"
cd3684cf
AD
166 PERCENT_LOCATIONS "%locations"
167 PERCENT_NAME_PREFIX "%name-prefix"
22fccf95 168 PERCENT_NO_DEFAULT_PREC "%no-default-prec"
cd3684cf
AD
169 PERCENT_NO_LINES "%no-lines"
170 PERCENT_NONDETERMINISTIC_PARSER
f0064700 171 "%nondeterministic-parser"
cd3684cf 172 PERCENT_OUTPUT "%output"
e9071366 173 PERCENT_PARSE_PARAM "%parse-param"
cd3684cf 174 PERCENT_PURE_PARSER "%pure-parser"
f0064700 175 PERCENT_REQUIRE "%require"
cd3684cf
AD
176 PERCENT_SKELETON "%skeleton"
177 PERCENT_START "%start"
178 PERCENT_TOKEN_TABLE "%token-table"
179 PERCENT_VERBOSE "%verbose"
180 PERCENT_YACC "%yacc"
ae7453f2 181;
e9955c83 182
58d7a1a1 183%token BRACED_CODE "{...}"
42ec0ae1 184%token BRACKETED_ID "[identifier]"
58d7a1a1
AD
185%token CHAR "char"
186%token EPILOGUE "epilogue"
3d38c03a 187%token EQUAL "="
3d38c03a 188%token ID "identifier"
b7295522 189%token ID_COLON "identifier:"
e9955c83 190%token PERCENT_PERCENT "%%"
58d7a1a1 191%token PIPE "|"
3d38c03a 192%token PROLOGUE "%{...%}"
58d7a1a1
AD
193%token SEMICOLON ";"
194%token TYPE "type"
12e35840 195%token TYPE_TAG_ANY "<*>"
3ebecc24 196%token TYPE_TAG_NONE "<>"
58d7a1a1
AD
197
198%type <character> CHAR
33ad1a9c 199%printer { fputs (char_name ($$), stderr); } CHAR
3d38c03a 200
2ce4ed68 201/* braceless is not to be used for rule or symbol actions, as it
7c0c6181 202 calls code_props_plain_init. */
6afc30cc 203%type <chars> STRING "%{...%}" EPILOGUE braceless content.opt
eb095650 204%type <code> "{...}"
33ad1a9c 205%printer { fputs (quotearg_style (c_quoting_style, $$), stderr); }
eb095650 206 STRING
2ce4ed68 207%printer { fprintf (stderr, "{\n%s\n}", $$); }
6afc30cc 208 braceless content.opt "{...}" "%{...%}" EPILOGUE
58d7a1a1 209
42ec0ae1
JD
210%type <uniqstr> BRACKETED_ID ID ID_COLON TYPE variable
211%printer { fputs ($$, stderr); } <uniqstr>
212%printer { fprintf (stderr, "[%s]", $$); } BRACKETED_ID
58d7a1a1 213%printer { fprintf (stderr, "%s:", $$); } ID_COLON
42ec0ae1 214%printer { fprintf (stderr, "<%s>", $$); } TYPE
58d7a1a1 215
e9955c83 216%type <integer> INT
42ec0ae1 217%printer { fprintf (stderr, "%d", $$); } <integer>
58d7a1a1 218
42ec0ae1
JD
219%type <symbol> id id_colon string_as_id symbol symbol.prec
220%printer { fprintf (stderr, "%s", $$->tag); } <symbol>
58d7a1a1
AD
221%printer { fprintf (stderr, "%s:", $$->tag); } id_colon
222
2c569025 223%type <assoc> precedence_declarator
ab7f29f8 224%type <list> symbols.1 symbols.prec generic_symlist generic_symlist_item
42ec0ae1
JD
225%type <named_ref> named_ref.opt
226
e9955c83 227%%
2c569025 228
8efe435c 229input:
2ce4ed68 230 prologue_declarations "%%" grammar epilogue.opt
e9955c83
AD
231;
232
2c569025
AD
233
234 /*------------------------------------.
235 | Declarations: before the first %%. |
236 `------------------------------------*/
237
2ce4ed68 238prologue_declarations:
e9955c83 239 /* Nothing */
2ce4ed68 240| prologue_declarations prologue_declaration
e9955c83
AD
241;
242
2ce4ed68 243prologue_declaration:
2c569025 244 grammar_declaration
7c0c6181
JD
245| "%{...%}"
246 {
247 code_props plain_code;
248 code_props_plain_init (&plain_code, $1, @1);
249 code_props_translate_code (&plain_code);
250 gram_scanner_last_string_free ();
7ecec4dd
JD
251 muscle_code_grow (union_seen ? "post_prologue" : "pre_prologue",
252 plain_code.code, @1);
7c0c6181
JD
253 code_scanner_last_string_free ();
254 }
e0992e54 255| "%debug" { debug = true; }
16dc6a9e 256| "%define" variable content.opt
7eb8a0bc 257 {
34d41938
JD
258 muscle_percent_define_insert ($2, @2, $3,
259 MUSCLE_PERCENT_DEFINE_GRAMMAR_FILE);
7eb8a0bc 260 }
2ce4ed68 261| "%defines" { defines_flag = true; }
02975b9a
JD
262| "%defines" STRING
263 {
264 defines_flag = true;
265 spec_defines_file = xstrdup ($2);
266 }
2ce4ed68
AD
267| "%error-verbose" { error_verbose = true; }
268| "%expect" INT { expected_sr_conflicts = $2; }
269| "%expect-rr" INT { expected_rr_conflicts = $2; }
02975b9a
JD
270| "%file-prefix" STRING { spec_file_prefix = $2; }
271| "%file-prefix" "=" STRING { spec_file_prefix = $3; } /* deprecated */
cd3684cf 272| "%glr-parser"
c66dfadd
PE
273 {
274 nondeterministic_parser = true;
275 glr_parser = true;
276 }
e9071366 277| "%initial-action" "{...}"
c66dfadd 278 {
7c0c6181
JD
279 code_props action;
280 code_props_symbol_action_init (&action, $2, @2);
281 code_props_translate_code (&action);
282 gram_scanner_last_string_free ();
283 muscle_code_grow ("initial_action", action.code, @2);
284 code_scanner_last_string_free ();
c66dfadd 285 }
e186a284 286| "%language" STRING { language_argmatch ($2, grammar_prio, @1); }
2ce4ed68
AD
287| "%lex-param" "{...}" { add_param ("lex_param", $2, @2); }
288| "%locations" { locations_flag = true; }
02975b9a
JD
289| "%name-prefix" STRING { spec_name_prefix = $2; }
290| "%name-prefix" "=" STRING { spec_name_prefix = $3; } /* deprecated */
2ce4ed68
AD
291| "%no-lines" { no_lines_flag = true; }
292| "%nondeterministic-parser" { nondeterministic_parser = true; }
02975b9a
JD
293| "%output" STRING { spec_outfile = $2; }
294| "%output" "=" STRING { spec_outfile = $3; } /* deprecated */
2ce4ed68 295| "%parse-param" "{...}" { add_param ("parse_param", $2, @2); }
d9df47b6
JD
296| "%pure-parser"
297 {
298 /* %pure-parser is deprecated in favor of `%define api.pure', so use
299 `%define api.pure' in a backward-compatible manner here. First, don't
300 complain if %pure-parser is specified multiple times. */
301 if (!muscle_find_const ("percent_define(api.pure)"))
34d41938
JD
302 muscle_percent_define_insert ("api.pure", @1, "",
303 MUSCLE_PERCENT_DEFINE_GRAMMAR_FILE);
d9df47b6
JD
304 /* In all cases, use api.pure now so that the backend doesn't complain if
305 the skeleton ignores api.pure, but do warn now if there's a previous
306 conflicting definition from an actual %define. */
307 if (!muscle_percent_define_flag_if ("api.pure"))
34d41938
JD
308 muscle_percent_define_insert ("api.pure", @1, "",
309 MUSCLE_PERCENT_DEFINE_GRAMMAR_FILE);
d9df47b6 310 }
2ce4ed68 311| "%require" STRING { version_check (&@2, $2); }
a7867f53
JD
312| "%skeleton" STRING
313 {
314 char const *skeleton_user = $2;
d143e9c3 315 if (mbschr (skeleton_user, '/'))
a7867f53
JD
316 {
317 size_t dir_length = strlen (current_file);
318 char *skeleton_build;
319 while (dir_length && current_file[dir_length - 1] != '/')
320 --dir_length;
321 while (dir_length && current_file[dir_length - 1] == '/')
322 --dir_length;
323 skeleton_build =
324 xmalloc (dir_length + 1 + strlen (skeleton_user) + 1);
325 if (dir_length > 0)
326 {
bb3b912b 327 memcpy (skeleton_build, current_file, dir_length);
a7867f53
JD
328 skeleton_build[dir_length++] = '/';
329 }
330 strcpy (skeleton_build + dir_length, skeleton_user);
331 skeleton_user = uniqstr_new (skeleton_build);
332 free (skeleton_build);
333 }
e186a284 334 skeleton_arg (skeleton_user, grammar_prio, @1);
a7867f53 335 }
2ce4ed68 336| "%token-table" { token_table_flag = true; }
ef1b4273 337| "%verbose" { report_flag |= report_states; }
2ce4ed68 338| "%yacc" { yacc_flag = true; }
cd3684cf 339| /*FIXME: Err? What is this horror doing here? */ ";"
e9955c83
AD
340;
341
2c569025
AD
342grammar_declaration:
343 precedence_declaration
344| symbol_declaration
e9955c83
AD
345| "%start" symbol
346 {
8efe435c 347 grammar_start_symbol_set ($2, @2);
e9955c83 348 }
3be03b13 349| "%destructor" "{...}" generic_symlist
9280d3ef 350 {
1c292035
AD
351 code_props code;
352 code_props_symbol_action_init (&code, $2, @2);
353 code_props_translate_code (&code);
354 {
355 symbol_list *list;
356 for (list = $3; list; list = list->next)
357 symbol_list_destructor_set (list, &code);
358 symbol_list_free ($3);
359 }
9280d3ef 360 }
3be03b13 361| "%printer" "{...}" generic_symlist
366eea36 362 {
1c292035
AD
363 code_props code;
364 code_props_symbol_action_init (&code, $2, @2);
365 code_props_translate_code (&code);
366 {
367 symbol_list *list;
368 for (list = $3; list; list = list->next)
369 symbol_list_printer_set (list, &code);
370 symbol_list_free ($3);
371 }
366eea36 372 }
22fccf95 373| "%default-prec"
39a06c25 374 {
22fccf95
PE
375 default_prec = true;
376 }
377| "%no-default-prec"
378 {
379 default_prec = false;
39a06c25 380 }
8e0a5e9e
JD
381| "%code" braceless
382 {
9611cfa2
JD
383 /* Do not invoke muscle_percent_code_grow here since it invokes
384 muscle_user_name_list_grow. */
592d0b1e 385 muscle_code_grow ("percent_code()", $2, @2);
8e0a5e9e
JD
386 code_scanner_last_string_free ();
387 }
16dc6a9e 388| "%code" ID braceless
8e0a5e9e 389 {
9611cfa2 390 muscle_percent_code_grow ($2, @2, $3, @3);
8e0a5e9e 391 code_scanner_last_string_free ();
8e0a5e9e 392 }
2c569025
AD
393;
394
58d7a1a1
AD
395
396/*----------*
397 | %union. |
398 *----------*/
399
400%token PERCENT_UNION "%union";
401
402union_name:
403 /* Nothing. */ {}
404| ID { muscle_code_grow ("union_name", $1, @1); }
405;
406
407grammar_declaration:
7ecec4dd 408 "%union" union_name braceless
58d7a1a1 409 {
ddc8ede1 410 union_seen = true;
7ecec4dd
JD
411 muscle_code_grow ("stype", $3, @3);
412 code_scanner_last_string_free ();
58d7a1a1
AD
413 }
414;
415
416
417
418
2c569025
AD
419symbol_declaration:
420 "%nterm" { current_class = nterm_sym; } symbol_defs.1
e9955c83
AD
421 {
422 current_class = unknown_sym;
423 current_type = NULL;
424 }
2c569025 425| "%token" { current_class = token_sym; } symbol_defs.1
e9955c83 426 {
2c569025 427 current_class = unknown_sym;
e9955c83
AD
428 current_type = NULL;
429 }
1e0bab92 430| "%type" TYPE symbols.1
e9955c83 431 {
3d2cbc26 432 symbol_list *list;
4f82b42a 433 tag_seen = true;
1e0bab92 434 for (list = $3; list; list = list->next)
3be03b13 435 symbol_type_set (list->content.sym, $2, @2);
dafdc66f 436 symbol_list_free ($3);
e9955c83
AD
437 }
438;
439
2c569025 440precedence_declaration:
ab7f29f8 441 precedence_declarator type.opt symbols.prec
1e0bab92 442 {
3d2cbc26 443 symbol_list *list;
1e0bab92
AD
444 ++current_prec;
445 for (list = $3; list; list = list->next)
446 {
3be03b13
JD
447 symbol_type_set (list->content.sym, current_type, @2);
448 symbol_precedence_set (list->content.sym, current_prec, $1, @1);
1e0bab92 449 }
dafdc66f 450 symbol_list_free ($3);
1e0bab92
AD
451 current_type = NULL;
452 }
e9955c83
AD
453;
454
2c569025 455precedence_declarator:
e9955c83
AD
456 "%left" { $$ = left_assoc; }
457| "%right" { $$ = right_assoc; }
458| "%nonassoc" { $$ = non_assoc; }
459;
460
461type.opt:
87fbb0bf 462 /* Nothing. */ { current_type = NULL; }
ddc8ede1 463| TYPE { current_type = $1; tag_seen = true; }
e9955c83
AD
464;
465
ab7f29f8
JD
466/* Just like symbols.1 but accept INT for the sake of POSIX. */
467symbols.prec:
468 symbol.prec
469 { $$ = symbol_list_sym_new ($1, @1); }
470| symbols.prec symbol.prec
471 { $$ = symbol_list_prepend ($1, symbol_list_sym_new ($2, @2)); }
472;
473
474symbol.prec:
475 symbol { $$ = $1; }
476 | symbol INT { $$ = $1; symbol_user_token_number_set ($1, $2, @2); }
477 ;
478
3be03b13 479/* One or more symbols to be %typed. */
1e0bab92 480symbols.1:
3be03b13
JD
481 symbol
482 { $$ = symbol_list_sym_new ($1, @1); }
483| symbols.1 symbol
484 { $$ = symbol_list_prepend ($1, symbol_list_sym_new ($2, @2)); }
485;
486
487generic_symlist:
488 generic_symlist_item { $$ = $1; }
489| generic_symlist generic_symlist_item { $$ = symbol_list_prepend ($1, $2); }
490;
491
492generic_symlist_item:
493 symbol { $$ = symbol_list_sym_new ($1, @1); }
494| TYPE { $$ = symbol_list_type_new ($1, @1); }
12e35840 495| "<*>" { $$ = symbol_list_default_tagged_new (@1); }
3ebecc24 496| "<>" { $$ = symbol_list_default_tagless_new (@1); }
e9955c83
AD
497;
498
e9955c83
AD
499/* One token definition. */
500symbol_def:
501 TYPE
502 {
503 current_type = $1;
ddc8ede1 504 tag_seen = true;
e9955c83 505 }
58d7a1a1 506| id
e9955c83 507 {
073f9288 508 symbol_class_set ($1, current_class, @1, true);
1a31ed21 509 symbol_type_set ($1, current_type, @1);
e9955c83 510 }
58d7a1a1 511| id INT
e9955c83 512 {
073f9288 513 symbol_class_set ($1, current_class, @1, true);
1a31ed21 514 symbol_type_set ($1, current_type, @1);
e776192e 515 symbol_user_token_number_set ($1, $2, @2);
e9955c83 516 }
58d7a1a1 517| id string_as_id
e9955c83 518 {
073f9288 519 symbol_class_set ($1, current_class, @1, true);
1a31ed21 520 symbol_type_set ($1, current_type, @1);
a5d50994 521 symbol_make_alias ($1, $2, @$);
e9955c83 522 }
58d7a1a1 523| id INT string_as_id
e9955c83 524 {
073f9288 525 symbol_class_set ($1, current_class, @1, true);
1a31ed21 526 symbol_type_set ($1, current_type, @1);
e776192e 527 symbol_user_token_number_set ($1, $2, @2);
a5d50994 528 symbol_make_alias ($1, $3, @$);
e9955c83
AD
529 }
530;
531
532/* One or more symbol definitions. */
533symbol_defs.1:
534 symbol_def
e9955c83 535| symbol_defs.1 symbol_def
e9955c83
AD
536;
537
2c569025
AD
538
539 /*------------------------------------------.
540 | The grammar section: between the two %%. |
541 `------------------------------------------*/
542
543grammar:
1921f1d7
AD
544 rules_or_grammar_declaration
545| grammar rules_or_grammar_declaration
546;
547
548/* As a Bison extension, one can use the grammar declarations in the
b7295522 549 body of the grammar. */
1921f1d7 550rules_or_grammar_declaration:
e9955c83 551 rules
8d0a98bb 552| grammar_declaration ";"
b275314e
AD
553| error ";"
554 {
555 yyerrok;
556 }
e9955c83
AD
557;
558
559rules:
8f462efe
AD
560 id_colon named_ref.opt { current_lhs ($1, @1, $2); } rhses.1
561 {
562 /* Free the current lhs. */
563 current_lhs (0, @1, 0);
564 }
e9955c83
AD
565;
566
567rhses.1:
8f3596a6
AD
568 rhs { grammar_current_rule_end (@1); }
569| rhses.1 "|" rhs { grammar_current_rule_end (@3); }
8d0a98bb 570| rhses.1 ";"
e9955c83
AD
571;
572
573rhs:
574 /* Nothing. */
8f462efe 575 { grammar_current_rule_begin (current_lhs_symbol, current_lhs_location,
7685e2f7
AR
576 current_lhs_named_ref); }
577| rhs symbol named_ref.opt
578 { grammar_current_rule_symbol_append ($2, @2, $3); }
579| rhs "{...}" named_ref.opt
580 { grammar_current_rule_action_append ($2, @2, $3); }
e9955c83 581| rhs "%prec" symbol
e776192e 582 { grammar_current_rule_prec_set ($3, @3); }
676385e2
PH
583| rhs "%dprec" INT
584 { grammar_current_rule_dprec_set ($3, @3); }
585| rhs "%merge" TYPE
586 { grammar_current_rule_merge_set ($3, @3); }
e9955c83
AD
587;
588
7685e2f7 589named_ref.opt:
d5e8574b 590 /* Nothing. */ { $$ = 0; }
7685e2f7 591|
d5e8574b 592 BRACKETED_ID { $$ = named_ref_new($1, @1); }
7685e2f7
AR
593;
594
58d7a1a1 595
16dc6a9e
JD
596/*----------------------------*
597 | variable and content.opt. |
598 *---------------------------*/
599
ae618dcc
JD
600/* The STRING form of variable is deprecated and is not M4-friendly.
601 For example, M4 fails for `%define "[" "value"'. */
16dc6a9e
JD
602variable:
603 ID
663ce7bb
AD
604| STRING { $$ = uniqstr_new ($1); }
605;
2ce4ed68 606
592d0b1e 607/* Some content or empty by default. */
2ce4ed68 608content.opt:
663ce7bb 609 /* Nothing. */ { $$ = ""; }
f37495f6 610| ID { $$ = $1; }
6afc30cc 611| STRING
2ce4ed68
AD
612;
613
614
6afc30cc
JD
615/*-------------*
616 | braceless. |
617 *-------------*/
618
2ce4ed68
AD
619braceless:
620 "{...}"
621 {
7c0c6181 622 code_props plain_code;
2ce4ed68 623 $1[strlen ($1) - 1] = '\n';
7c0c6181
JD
624 code_props_plain_init (&plain_code, $1+1, @1);
625 code_props_translate_code (&plain_code);
626 gram_scanner_last_string_free ();
627 $$ = plain_code.code;
2ce4ed68
AD
628 }
629;
630
631
58d7a1a1
AD
632/*---------------*
633 | Identifiers. |
634 *---------------*/
635
33ad1a9c
PE
636/* Identifiers are returned as uniqstr values by the scanner.
637 Depending on their use, we may need to make them genuine symbols. */
58d7a1a1
AD
638
639id:
33ad1a9c 640 ID
203b9274 641 { $$ = symbol_from_uniqstr ($1, @1); }
33ad1a9c
PE
642| CHAR
643 {
644 $$ = symbol_get (char_name ($1), @1);
645 symbol_class_set ($$, token_sym, @1, false);
646 symbol_user_token_number_set ($$, $1, @1);
647 }
58d7a1a1
AD
648;
649
650id_colon:
203b9274 651 ID_COLON { $$ = symbol_from_uniqstr ($1, @1); }
58d7a1a1
AD
652;
653
654
e9955c83 655symbol:
58d7a1a1
AD
656 id
657| string_as_id
e9955c83
AD
658;
659
ca407bdf 660/* A string used as an ID: quote it. */
e9955c83
AD
661string_as_id:
662 STRING
663 {
ca407bdf 664 $$ = symbol_get (quotearg_style (c_quoting_style, $1), @1);
db89d400 665 symbol_class_set ($$, token_sym, @1, false);
e9955c83
AD
666 }
667;
668
e9955c83
AD
669epilogue.opt:
670 /* Nothing. */
e9955c83
AD
671| "%%" EPILOGUE
672 {
7c0c6181
JD
673 code_props plain_code;
674 code_props_plain_init (&plain_code, $2, @2);
675 code_props_translate_code (&plain_code);
e9071366 676 gram_scanner_last_string_free ();
7c0c6181
JD
677 muscle_code_grow ("epilogue", plain_code.code, @2);
678 code_scanner_last_string_free ();
e9955c83
AD
679 }
680;
681
e9955c83 682%%
b7295522
PE
683
684
685/* Return the location of the left-hand side of a rule whose
686 right-hand side is RHS[1] ... RHS[N]. Ignore empty nonterminals in
687 the right-hand side, and return an empty location equal to the end
688 boundary of RHS[0] if the right-hand side is empty. */
689
690static YYLTYPE
691lloc_default (YYLTYPE const *rhs, int n)
692{
693 int i;
a737b216 694 YYLTYPE loc;
62cb8a99
PE
695
696 /* SGI MIPSpro 7.4.1m miscompiles "loc.start = loc.end = rhs[n].end;".
697 The bug is fixed in 7.4.2m, but play it safe for now. */
698 loc.start = rhs[n].end;
699 loc.end = rhs[n].end;
b7295522 700
77315a51 701 /* Ignore empty nonterminals the start of the right-hand side.
5320ca4d
PE
702 Do not bother to ignore them at the end of the right-hand side,
703 since empty nonterminals have the same end as their predecessors. */
b7295522
PE
704 for (i = 1; i <= n; i++)
705 if (! equal_boundaries (rhs[i].start, rhs[i].end))
706 {
a737b216 707 loc.start = rhs[i].start;
b7295522
PE
708 break;
709 }
710
a737b216 711 return loc;
b7295522
PE
712}
713
714
715/* Add a lex-param or a parse-param (depending on TYPE) with
716 declaration DECL and location LOC. */
717
1773ceee 718static void
e9ce5688 719add_param (char const *type, char *decl, location loc)
1773ceee 720{
ead9e56e 721 static char const alphanum[26 + 26 + 1 + 10] =
1773ceee
PE
722 "abcdefghijklmnopqrstuvwxyz"
723 "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
ead9e56e
PE
724 "_"
725 "0123456789";
1773ceee 726 char const *name_start = NULL;
e9ce5688 727 char *p;
1773ceee 728
e503aa60
AD
729 /* Stop on last actual character. */
730 for (p = decl; p[1]; p++)
ead9e56e
PE
731 if ((p == decl
732 || ! memchr (alphanum, p[-1], sizeof alphanum))
733 && memchr (alphanum, p[0], sizeof alphanum - 10))
1773ceee
PE
734 name_start = p;
735
ead9e56e
PE
736 /* Strip the surrounding '{' and '}', and any blanks just inside
737 the braces. */
c9d546b2 738 --p;
457bf919 739 while (c_isspace ((unsigned char) *p))
c9d546b2 740 --p;
e503aa60 741 p[1] = '\0';
c9d546b2 742 ++decl;
457bf919 743 while (c_isspace ((unsigned char) *decl))
c9d546b2 744 ++decl;
e9ce5688 745
1773ceee
PE
746 if (! name_start)
747 complain_at (loc, _("missing identifier in parameter declaration"));
748 else
749 {
60457f30 750 char *name = xmemdup0 (name_start, strspn (name_start, alphanum));
1773ceee
PE
751 muscle_pair_list_grow (type, decl, name);
752 free (name);
753 }
754
e9071366 755 gram_scanner_last_string_free ();
1773ceee
PE
756}
757
2ce4ed68 758
b50d2359
AD
759static void
760version_check (location const *loc, char const *version)
761{
762 if (strverscmp (version, PACKAGE_VERSION) > 0)
9b8a5ce0
AD
763 {
764 complain_at (*loc, "require bison %s, but have %s",
dd561157 765 version, PACKAGE_VERSION);
da209f94 766 exit (EX_MISMATCH);
9b8a5ce0 767 }
b50d2359
AD
768}
769
1fec91df 770static void
3d2cbc26 771gram_error (location const *loc, char const *msg)
e9955c83 772{
ad8a3efc 773 complain_at (*loc, "%s", msg);
e9955c83 774}
e9ce5688
PE
775
776char const *
777token_name (int type)
778{
fc01665e 779 return yytname[YYTRANSLATE (type)];
e9ce5688 780}
33ad1a9c
PE
781
782static char const *
783char_name (char c)
784{
785 if (c == '\'')
786 return "'\\''";
787 else
788 {
789 char buf[4];
790 buf[0] = '\''; buf[1] = c; buf[2] = '\''; buf[3] = '\0';
791 return quotearg_style (escape_quoting_style, buf);
792 }
793}