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