1 # Checking GLR Parsing: Regression Tests -*- Autotest -*-
3 # Copyright (C) 2002-2003, 2005-2007, 2009-2012 Free Software
6 # This program is free software: you can redistribute it and/or modify
7 # it under the terms of the GNU General Public License as published by
8 # the Free Software Foundation, either version 3 of the License, or
9 # (at your option) any later version.
11 # This program is distributed in the hope that it will be useful,
12 # but WITHOUT ANY WARRANTY; without even the implied warranty of
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 # GNU General Public License for more details.
16 # You should have received a copy of the GNU General Public License
17 # along with this program. If not, see <http://www.gnu.org/licenses/>.
19 AT_BANNER([[GLR Regression Tests]])
21 ## --------------------------- ##
22 ## Badly Collapsed GLR States. ##
23 ## --------------------------- ##
25 AT_SETUP([Badly Collapsed GLR States])
27 AT_BISON_OPTION_PUSHDEFS
28 AT_DATA_GRAMMAR([glr-regr1.y],
29 [[/* Regression Test: Improper state compression */
30 /* Reported by Scott McPeak */
38 static YYSTYPE exprMerge (YYSTYPE x0, YYSTYPE x1);
47 /* -------- productions ------ */
50 StartSymbol: E { $$=0; } %merge <exprMerge>
53 E: E 'P' E { $$=1; printf("E -> E 'P' E\n"); } %merge <exprMerge>
54 | 'B' { $$=2; printf("E -> 'B'\n"); } %merge <exprMerge>
59 /* ---------- C code ----------- */
62 static YYSTYPE exprMerge (YYSTYPE x0, YYSTYPE x1)
70 const char *input = NULL;
73 main (int argc, const char* argv[])
88 AT_BISON_OPTION_POPDEFS
90 AT_BISON_CHECK([[-o glr-regr1.c glr-regr1.y]], 0, [],
91 [glr-regr1.y: conflicts: 1 shift/reduce
93 AT_COMPILE([glr-regr1])
94 AT_PARSER_CHECK([[./glr-regr1 BPBPB]], 0,
108 ## ------------------------------------------------------------ ##
109 ## Improper handling of embedded actions and $-N in GLR parsers ##
110 ## ------------------------------------------------------------ ##
112 AT_SETUP([Improper handling of embedded actions and dollar(-N) in GLR parsers])
114 AT_BISON_OPTION_PUSHDEFS
115 AT_DATA_GRAMMAR([glr-regr2a.y],
116 [[/* Regression Test: Improper handling of embedded actions and $-N */
117 /* Reported by S. Eken */
120 #define YYSTYPE char *
137 { printf ("Variable: '%s'\n", $2); }
140 | 's' var_list 't' 'e'
141 { printf ("Varlist: '%s'\n", $2); free ($2); }
142 | 's' var 't' var_printer 'x'
156 char *s = (char *) realloc ($1, strlen ($1) + 1 + strlen ($3) + 1);
165 { printf ("Variable: '%s'\n", $-1); }
176 assert (!feof (stdin));
177 switch (fscanf (input, " %1[a-z,]", buf))
186 if (fscanf (input, "%49s", buf) != 1)
188 assert (strlen (buf) < sizeof buf - 1);
189 s = (char *) malloc (strlen (buf) + 1);
196 main (int argc, char **argv)
199 if (argc == 2 && !(input = fopen (argv[1], "r")))
201 int res = yyparse ();
202 if (argc == 2 && fclose (input))
207 AT_BISON_OPTION_POPDEFS
209 AT_BISON_CHECK([[-o glr-regr2a.c glr-regr2a.y]], 0, [],
210 [glr-regr2a.y: conflicts: 2 shift/reduce
212 AT_COMPILE([glr-regr2a])
214 AT_DATA([input1.txt],
215 [[s VARIABLE_1 t v x q
217 AT_PARSER_CHECK([[./glr-regr2a input1.txt]], 0,
218 [[Variable: 'VARIABLE_1'
221 AT_DATA([input2.txt],
222 [[s VARIABLE_1 , ANOTHER_VARIABLE_2 t e
224 AT_PARSER_CHECK([[./glr-regr2a input2.txt]],
226 [[Varlist: 'VARIABLE_1,ANOTHER_VARIABLE_2'
229 AT_DATA([input3.txt],
232 AT_PARSER_CHECK([[./glr-regr2a input3.txt]], 0,
233 [[Variable: 'VARIABLE_3'
239 ## ------------------------------------------------------------ ##
240 ## Improper merging of GLR delayed action sets ##
241 ## ------------------------------------------------------------ ##
243 AT_SETUP([Improper merging of GLR delayed action sets])
245 AT_BISON_OPTION_PUSHDEFS
246 AT_DATA_GRAMMAR([glr-regr3.y],
247 [[/* Regression Test: Improper merging of GLR delayed action sets. */
248 /* Reported by M. Rosien */
256 static int MergeRule (int x0, int x1);
260 #define RULE(x) (1 << (x))
267 %token P1 P2 T1 T2 T3 T4 O1 O2
271 S : P1 T4 O2 NT6 P2 { printf ("Result: %x\n", $4); }
274 NT1 : P1 T1 O1 T2 P2 { $$ = RULE(2); } %merge<MergeRule>
277 NT2 : NT1 { $$ = RULE(3); } %merge<MergeRule>
278 | P1 NT1 O1 T3 P2 { $$ = RULE(4); } %merge<MergeRule>
281 NT3 : T3 { $$ = RULE(5); } %merge<MergeRule>
282 | P1 NT1 O1 T3 P2 { $$ = RULE(6); } %merge<MergeRule>
285 NT4 : NT3 { $$ = RULE(7); } %merge<MergeRule>
286 | NT2 { $$ = RULE(8); } %merge<MergeRule>
287 | P1 NT2 O1 NT3 P2 { $$ = RULE(9); } %merge<MergeRule>
290 NT5 : NT4 { $$ = RULE(10); } %merge<MergeRule>
293 NT6 : P1 NT1 O1 T3 P2 { $$ = RULE(11) | $2; } %merge<MergeRule>
294 | NT5 { $$ = RULE(12) | $1; } %merge<MergeRule>
300 MergeRule (int x0, int x1)
306 FILE *input = YY_NULL;
308 int P[] = { P1, P2 };
309 int O[] = { O1, O2 };
310 int T[] = { T1, T2, T3, T4 };
315 assert (!feof (stdin));
316 if (fscanf (input, "%2s", inp) == EOF)
320 case 'p': return P[inp[1] - '1'];
321 case 't': return T[inp[1] - '1'];
322 case 'o': return O[inp[1] - '1'];
328 main(int argc, char* argv[])
331 if (argc == 2 && !(input = fopen (argv[1], "r")))
333 int res = yyparse ();
334 if (argc == 2 && fclose (input))
339 AT_BISON_OPTION_POPDEFS
341 AT_BISON_CHECK([[-o glr-regr3.c glr-regr3.y]], 0, [],
342 [glr-regr3.y: conflicts: 1 shift/reduce, 1 reduce/reduce
344 AT_COMPILE([glr-regr3])
347 [[p1 t4 o2 p1 p1 t1 o1 t2 p2 o1 t3 p2 p2
349 AT_PARSER_CHECK([[./glr-regr3 input.txt]],
357 ## ------------------------------------------------------------------------- ##
358 ## Duplicate representation of merged trees. See ##
359 ## <http://lists.gnu.org/archive/html/help-bison/2005-07/msg00013.html>. ##
360 ## ------------------------------------------------------------------------- ##
362 AT_SETUP([Duplicate representation of merged trees])
364 AT_BISON_OPTION_PUSHDEFS
365 AT_DATA_GRAMMAR([glr-regr4.y],
367 %union { char *ptr; }
368 %type <ptr> S A A1 A2 B
375 static char *merge (YYSTYPE, YYSTYPE);
376 static char *make_value (char const *, char const *);
379 static char *ptrs[100];
380 static char **ptrs_next = ptrs;
385 tree: S { printf ("%s\n", $1); } ;
388 A %merge<merge> { $$ = make_value ("S", $1); }
389 | B %merge<merge> { $$ = make_value ("S", $1); }
393 A1 %merge<merge> { $$ = make_value ("A", $1); }
394 | A2 %merge<merge> { $$ = make_value ("A", $1); }
397 A1: 'a' { $$ = make_value ("A1", "'a'"); } ;
398 A2: 'a' { $$ = make_value ("A2", "'a'"); } ;
399 B: 'a' { $$ = make_value ("B", "'a'"); } ;
403 ]AT_YYLEX_DEFINE(["a"])[
408 int status = yyparse ();
409 while (ptrs_next != ptrs)
415 make_value (char const *parent, char const *child)
417 char const format[] = "%s <- %s";
418 char *value = *ptrs_next++ =
419 (char *) malloc (strlen (parent) + strlen (child) + sizeof format);
420 sprintf (value, format, parent, child);
425 merge (YYSTYPE s1, YYSTYPE s2)
427 char const format[] = "merge{ %s and %s }";
428 char *value = *ptrs_next++ =
429 (char *) malloc (strlen (s1.ptr) + strlen (s2.ptr) + sizeof format);
430 sprintf (value, format, s1.ptr, s2.ptr);
434 AT_BISON_OPTION_POPDEFS
436 AT_BISON_CHECK([[-o glr-regr4.c glr-regr4.y]], 0, [],
437 [glr-regr4.y: conflicts: 1 reduce/reduce
439 AT_COMPILE([glr-regr4])
441 AT_PARSER_CHECK([[./glr-regr4]], 0,
442 [[merge{ S <- merge{ A <- A1 <- 'a' and A <- A2 <- 'a' } and S <- B <- 'a' }
448 ## -------------------------------------------------------------------------- ##
449 ## User destructor for unresolved GLR semantic value. See ##
450 ## <http://lists.gnu.org/archive/html/bison-patches/2005-08/msg00016.html>. ##
451 ## -------------------------------------------------------------------------- ##
453 AT_SETUP([User destructor for unresolved GLR semantic value])
455 AT_BISON_OPTION_PUSHDEFS
456 AT_DATA_GRAMMAR([glr-regr5.y],
463 enum { MAGIC_VALUE = -1057808125 }; /* originally chosen at random */
467 %union { int value; }
471 if ($$ != MAGIC_VALUE)
473 fprintf (stderr, "Bad destructor call.\n");
481 'a' { $$ = MAGIC_VALUE; }
482 | 'a' { $$ = MAGIC_VALUE; }
486 ]AT_YYLEX_DEFINE(["a"])[
491 return yyparse () != 1;
494 AT_BISON_OPTION_POPDEFS
496 AT_BISON_CHECK([[-o glr-regr5.c glr-regr5.y]], 0, [],
497 [glr-regr5.y: conflicts: 1 reduce/reduce
499 AT_COMPILE([glr-regr5])
501 AT_PARSER_CHECK([[./glr-regr5]], 0, [],
508 ## -------------------------------------------------------------------------- ##
509 ## User destructor after an error during a split parse. See ##
510 ## <http://lists.gnu.org/archive/html/bison-patches/2005-08/msg00029.html>. ##
511 ## -------------------------------------------------------------------------- ##
513 AT_SETUP([User destructor after an error during a split parse])
515 AT_BISON_OPTION_PUSHDEFS
516 AT_DATA_GRAMMAR([glr-regr6.y],
526 %union { int value; }
530 printf ("Destructor called.\n");
539 ]AT_YYLEX_DEFINE(["a"])[
543 return yyparse () != 1;
546 AT_BISON_OPTION_POPDEFS
548 AT_BISON_CHECK([[-o glr-regr6.c glr-regr6.y]], 0, [],
549 [glr-regr6.y: conflicts: 1 reduce/reduce
551 AT_COMPILE([glr-regr6])
553 AT_PARSER_CHECK([[./glr-regr6]], 0,
562 ## ------------------------------------------------------------------------- ##
563 ## Duplicated user destructor for lookahead. See ##
564 ## <http://lists.gnu.org/archive/html/bison-patches/2005-08/msg00035.html>. ##
565 ## ------------------------------------------------------------------------- ##
567 AT_SETUP([Duplicated user destructor for lookahead])
569 AT_BISON_OPTION_PUSHDEFS
570 AT_DATA_GRAMMAR([glr-regr7.y],
577 #define YYSTACKEXPANDABLE 0
578 typedef struct count_node {
580 struct count_node *prev;
582 static count_node *tail;
586 %union { count_node *node; }
591 fprintf (stderr, "Destructor called on same value twice.\n");
609 yylval.node = (count_node*) malloc (sizeof *yylval.node);
612 fprintf (stderr, "Test inconclusive.\n");
615 yylval.node->count = 0;
616 yylval.node->prev = tail;
625 int status = yyparse ();
628 count_node *prev = tail->prev;
635 AT_BISON_OPTION_POPDEFS
637 AT_BISON_CHECK([[-o glr-regr7.c glr-regr7.y]], 0, [],
638 [glr-regr7.y: conflicts: 2 reduce/reduce
640 AT_COMPILE([glr-regr7])
642 AT_PARSER_CHECK([[./glr-regr7]], 2, [],
649 ## ------------------------------------------------------------------------- ##
650 ## Incorrect default location for empty right-hand sides. Adapted from bug ##
651 ## report by Claudia Hermann. ##
652 ## See http://lists.gnu.org/archive/html/bug-bison/2005-10/msg00069.html and ##
653 ## http://lists.gnu.org/archive/html/bug-bison/2005-10/msg00072.html ##
654 ## ------------------------------------------------------------------------- ##
656 AT_SETUP([Incorrectly initialized location for empty right-hand side in GLR])
658 AT_BISON_OPTION_PUSHDEFS
659 AT_DATA_GRAMMAR([glr-regr8.y],
677 PortClause : T_PORT InterfaceDeclaration T_PORT
678 { printf("%d/%d - %d/%d - %d/%d\n",
679 @1.first_column, @1.last_column,
680 @2.first_column, @2.last_column,
681 @3.first_column, @3.last_column); }
684 InterfaceDeclaration : OptConstantWord %dprec 1
685 | OptSignalWord %dprec 2
688 OptConstantWord : /* empty */
692 OptSignalWord : /* empty */
693 { printf("empty: %d/%d\n", @$.first_column, @$.last_column); }
710 yylloc.first_column = 1;
711 yylloc.last_column = 9;
714 yylloc.first_column = 13;
715 yylloc.last_column = 17;
729 AT_BISON_OPTION_POPDEFS
731 AT_BISON_CHECK([[-o glr-regr8.c glr-regr8.y]], 0, [],
732 [glr-regr8.y: conflicts: 1 reduce/reduce
734 AT_COMPILE([glr-regr8])
736 AT_PARSER_CHECK([[./glr-regr8]], 0,
745 ## ------------------------------------------------------------------------- ##
746 ## No users destructors if stack 0 deleted. See ##
747 ## <http://lists.gnu.org/archive/html/bison-patches/2005-09/msg00109.html>. ##
748 ## ------------------------------------------------------------------------- ##
750 AT_SETUP([No users destructors if stack 0 deleted])
752 AT_BISON_OPTION_PUSHDEFS
753 AT_DATA_GRAMMAR([glr-regr9.y],
760 # define YYSTACKEXPANDABLE 0
761 static int tokens = 0;
762 static int destructors = 0;
767 %union { int dummy; }
777 ambig0 'a' { destructors += 2; USE ($2); }
778 | ambig1 start { destructors += 1; }
779 | ambig2 start { destructors += 1; }
800 exit_status = yyparse ();
801 if (tokens != destructors)
803 fprintf (stderr, "Tokens = %d, Destructors = %d\n", tokens, destructors);
809 AT_BISON_OPTION_POPDEFS
811 AT_BISON_CHECK([[-o glr-regr9.c glr-regr9.y]], 0, [],
812 [glr-regr9.y: conflicts: 1 reduce/reduce
814 AT_COMPILE([glr-regr9])
816 AT_PARSER_CHECK([[./glr-regr9]], 0, [],
823 ## ------------------------------------------------------------------------- ##
824 ## Corrupted semantic options if user action cuts parse. ##
825 ## ------------------------------------------------------------------------- ##
827 AT_SETUP([Corrupted semantic options if user action cuts parse])
829 AT_BISON_OPTION_PUSHDEFS
830 AT_DATA_GRAMMAR([glr-regr10.y],
837 #define GARBAGE_SIZE 50
838 static char garbage[GARBAGE_SIZE];
842 %union { char *ptr; }
848 %dprec 2 { $$ = garbage; YYACCEPT; }
849 | %dprec 1 { $$ = garbage; YYACCEPT; }
860 for (i = 0; i < GARBAGE_SIZE; i+=1)
865 AT_BISON_OPTION_POPDEFS
867 AT_BISON_CHECK([[-o glr-regr10.c glr-regr10.y]], 0, [],
868 [glr-regr10.y: conflicts: 1 reduce/reduce
870 AT_COMPILE([glr-regr10])
872 AT_PARSER_CHECK([[./glr-regr10]], 0, [], [])
877 ## ------------------------------------------------------------------------- ##
878 ## Undesirable destructors if user action cuts parse. ##
879 ## ------------------------------------------------------------------------- ##
881 AT_SETUP([Undesirable destructors if user action cuts parse])
883 AT_BISON_OPTION_PUSHDEFS
884 AT_DATA_GRAMMAR([glr-regr11.y],
890 static int destructors = 0;
895 %union { int dummy; }
897 %destructor { destructors += 1; } 'a'
902 'a' %dprec 2 { USE ($1); destructors += 1; YYACCEPT; }
903 | 'a' %dprec 1 { USE ($1); destructors += 1; YYACCEPT; }
909 ]AT_YYLEX_DEFINE(["a"])[
914 int exit_status = yyparse ();
915 if (destructors != 1)
917 fprintf (stderr, "Destructor calls: %d\n", destructors);
923 AT_BISON_OPTION_POPDEFS
925 AT_BISON_CHECK([[-o glr-regr11.c glr-regr11.y]], 0, [],
926 [glr-regr11.y: conflicts: 1 reduce/reduce
928 AT_COMPILE([glr-regr11])
930 AT_PARSER_CHECK([[./glr-regr11]], 0, [], [])
935 ## ------------------------------------------------------------------------- ##
936 ## Leaked semantic values if user action cuts parse. ##
937 ## ------------------------------------------------------------------------- ##
939 AT_SETUP([Leaked semantic values if user action cuts parse])
941 AT_BISON_OPTION_PUSHDEFS
942 AT_DATA_GRAMMAR([glr-regr12.y],
945 %union { int dummy; }
946 %token PARENT_RHS_AFTER
947 %type <dummy> parent_rhs_before merged PARENT_RHS_AFTER
948 %destructor { parent_rhs_before_value = 0; } parent_rhs_before
949 %destructor { merged_value = 0; } merged
950 %destructor { parent_rhs_after_value = 0; } PARENT_RHS_AFTER
955 static int merge (YYSTYPE, YYSTYPE);
958 static int parent_rhs_before_value = 0;
959 static int merged_value = 0;
960 static int parent_rhs_after_value = 0;
974 parent_rhs_after_value = 0;
979 parent_rhs_before merged PARENT_RHS_AFTER {
981 parent_rhs_before_value = 0;
983 parent_rhs_after_value = 0;
990 parent_rhs_before_value = 1;
999 | cut %merge<merge> {
1005 cut: { YYACCEPT; } ;
1010 merge (YYSTYPE s1, YYSTYPE s2)
1013 char dummy = s1.dummy + s2.dummy;
1018 ]AT_YYLEX_DEFINE([{ PARENT_RHS_AFTER, 0 }],
1019 [if (res == PARENT_RHS_AFTER)
1020 parent_rhs_after_value = 1;])[
1025 int exit_status = yyparse ();
1026 if (parent_rhs_before_value)
1028 fprintf (stderr, "`parent_rhs_before' destructor not called.\n");
1033 fprintf (stderr, "`merged' destructor not called.\n");
1036 if (parent_rhs_after_value)
1038 fprintf (stderr, "`PARENT_RHS_AFTER' destructor not called.\n");
1044 AT_BISON_OPTION_POPDEFS
1046 AT_BISON_CHECK([[-o glr-regr12.c glr-regr12.y]], 0, [],
1047 [glr-regr12.y: conflicts: 1 shift/reduce, 1 reduce/reduce
1049 AT_COMPILE([glr-regr12])
1051 AT_PARSER_CHECK([[./glr-regr12]], 0, [], [])
1056 ## ------------------------------------------------------------------------- ##
1057 ## Incorrect lookahead during deterministic GLR. See ##
1058 ## <http://lists.gnu.org/archive/html/help-bison/2005-07/msg00017.html> and ##
1059 ## <http://lists.gnu.org/archive/html/bison-patches/2006-01/msg00060.html>. ##
1060 ## ------------------------------------------------------------------------- ##
1062 AT_SETUP([Incorrect lookahead during deterministic GLR])
1064 AT_BISON_OPTION_PUSHDEFS
1065 AT_DATA_GRAMMAR([glr-regr13.y],
1068 - Defaulted state with initial yychar: yychar == YYEMPTY.
1069 - Nondefaulted state: yychar != YYEMPTY.
1070 - Defaulted state after lookahead: yychar != YYEMPTY.
1071 - Defaulted state after shift: yychar == YYEMPTY.
1072 - User action changing the lookahead. */
1077 ]AT_YYERROR_DECLARE[
1079 static void print_lookahead (char const *);
1083 %union { char value; }
1084 %type <value> 'a' 'b'
1091 defstate_init defstate_shift 'b' change_lookahead 'a' {
1093 print_lookahead ("start <- defstate_init defstate_shift 'b'");
1098 print_lookahead ("defstate_init <- empty string");
1102 nondefstate defstate_look 'a' {
1104 print_lookahead ("defstate_shift <- nondefstate defstate_look 'a'");
1109 print_lookahead ("defstate_look <- empty string");
1114 print_lookahead ("nondefstate <- empty string");
1118 print_lookahead ("nondefstate <- 'b'");
1130 ]AT_YYLEX_DEFINE(["ab"],
1131 [yylval.value = res + 'A' - 'a'])[
1134 print_lookahead (char const *reduction)
1136 printf ("%s:\n yychar=", reduction);
1137 if (yychar == YYEMPTY)
1139 else if (yychar == YYEOF)
1143 printf ("'%c', yylval='", yychar);
1144 if (yylval.value > ' ')
1145 printf ("%c", yylval.value);
1146 printf ("', yylloc=(%d,%d),(%d,%d)",
1147 yylloc.first_line, yylloc.first_column,
1148 yylloc.last_line, yylloc.last_column);
1156 yychar = '#'; /* Not a token in the grammar. */
1161 AT_BISON_OPTION_POPDEFS
1163 AT_BISON_CHECK([[-o glr-regr13.c glr-regr13.y]], 0, [], [])
1164 AT_COMPILE([glr-regr13])
1166 AT_PARSER_CHECK([[./glr-regr13]], 0,
1167 [defstate_init <- empty string:
1169 nondefstate <- empty string:
1170 yychar='a', yylval='A', yylloc=(1,1),(1,1)
1171 defstate_look <- empty string:
1172 yychar='a', yylval='A', yylloc=(1,1),(1,1)
1173 defstate_shift <- nondefstate defstate_look 'a':
1175 start <- defstate_init defstate_shift 'b':
1182 ## ------------------------------------------------------------------------- ##
1183 ## Incorrect lookahead during nondeterministic GLR. ##
1184 ## ------------------------------------------------------------------------- ##
1186 AT_SETUP([Incorrect lookahead during nondeterministic GLR])
1188 AT_BISON_OPTION_PUSHDEFS
1189 AT_DATA_GRAMMAR([glr-regr14.y],
1192 - Conflicting actions (split-off parse, which copies lookahead need,
1193 which is necessarily yytrue) and nonconflicting actions (non-split-off
1194 parse) for nondefaulted state: yychar != YYEMPTY.
1195 - Merged deferred actions (lookahead need and RHS from different stack
1196 than the target state) and nonmerged deferred actions (same stack).
1197 - Defaulted state after lookahead: yychar != YYEMPTY.
1198 - Defaulted state after shift: yychar == YYEMPTY.
1199 - yychar != YYEMPTY but lookahead need is yyfalse (a previous stack has
1200 seen the lookahead but current stack has not).
1201 - Exceeding stack capacity (stack explosion), and thus reallocating
1202 lookahead need array.
1203 Note that it does not seem possible to see the initial yychar value during
1204 nondeterministic operation since:
1205 - In order to preserve the initial yychar, only defaulted states may be
1207 - If only defaulted states are entered, there are no conflicts, so
1208 nondeterministic operation does not start. */
1210 %union { char value; }
1216 ]AT_YYERROR_DECLARE[
1218 static void print_lookahead (char const *);
1219 static char merge (union YYSTYPE, union YYSTYPE);
1223 %type <value> 'a' 'b' 'c' 'd' stack_explosion
1230 merge 'c' stack_explosion {
1232 print_lookahead ("start <- merge 'c' stack_explosion");
1236 /* When merging the 2 deferred actions, the lookahead needs are different. */
1238 nonconflict1 'a' 'b' nonconflict2 %dprec 1 {
1240 print_lookahead ("merge <- nonconflict1 'a' 'b' nonconflict2");
1242 | conflict defstate_look 'a' nonconflict2 'b' defstate_shift %dprec 2 {
1244 print_lookahead ("merge <- conflict defstate_look 'a' nonconflict2 'b'"
1251 print_lookahead ("nonconflict1 <- empty string");
1256 print_lookahead ("nonconflict2 <- empty string");
1260 print_lookahead ("nonconflict2 <- 'a'");
1265 print_lookahead ("conflict <- empty string");
1270 print_lookahead ("defstate_look <- empty string");
1274 /* yychar != YYEMPTY but lookahead need is yyfalse. */
1277 print_lookahead ("defstate_shift <- empty string");
1283 | alt1 stack_explosion %merge<merge> { $$ = $2; }
1284 | alt2 stack_explosion %merge<merge> { $$ = $2; }
1285 | alt3 stack_explosion %merge<merge> { $$ = $2; }
1290 if (yychar != 'd' && yychar != YYEOF)
1292 fprintf (stderr, "Incorrect lookahead during stack explosion.\n");
1299 if (yychar != 'd' && yychar != YYEOF)
1301 fprintf (stderr, "Incorrect lookahead during stack explosion.\n");
1308 if (yychar != 'd' && yychar != YYEOF)
1310 fprintf (stderr, "Incorrect lookahead during stack explosion.\n");
1316 if (yychar != YYEMPTY)
1319 "Found lookahead where shouldn't during stack explosion.\n");
1330 static char const input[] = "abcdddd";
1331 static size_t toknum;
1332 assert (toknum < sizeof input);
1333 yylloc.first_line = yylloc.last_line = 1;
1334 yylloc.first_column = yylloc.last_column = toknum + 1;
1335 yylval.value = input[toknum] + 'A' - 'a';
1336 return input[toknum++];
1340 print_lookahead (char const *reduction)
1342 printf ("%s:\n yychar=", reduction);
1343 if (yychar == YYEMPTY)
1345 else if (yychar == YYEOF)
1349 printf ("'%c', yylval='", yychar);
1350 if (yylval.value > ' ')
1351 printf ("%c", yylval.value);
1352 printf ("', yylloc=(%d,%d),(%d,%d)",
1353 yylloc.first_line, yylloc.first_column,
1354 yylloc.last_line, yylloc.last_column);
1360 merge (union YYSTYPE s1, union YYSTYPE s2)
1362 char dummy = s1.value + s2.value;
1369 yychar = '#'; /* Not a token in the grammar. */
1374 AT_BISON_OPTION_POPDEFS
1376 AT_BISON_CHECK([[-o glr-regr14.c glr-regr14.y]], 0, [],
1377 [glr-regr14.y: conflicts: 3 reduce/reduce
1379 AT_COMPILE([glr-regr14])
1381 AT_PARSER_CHECK([[./glr-regr14]], 0,
1382 [conflict <- empty string:
1383 yychar='a', yylval='A', yylloc=(1,1),(1,1)
1384 defstate_look <- empty string:
1385 yychar='a', yylval='A', yylloc=(1,1),(1,1)
1386 nonconflict2 <- empty string:
1387 yychar='b', yylval='B', yylloc=(1,2),(1,2)
1388 defstate_shift <- empty string:
1390 merge <- conflict defstate_look 'a' nonconflict2 'b' defstate_shift:
1392 start <- merge 'c' stack_explosion:
1399 ## ------------------------------------------------------------------------- ##
1400 ## Leaked semantic values when reporting ambiguity. ##
1401 ## ------------------------------------------------------------------------- ##
1403 AT_SETUP([Leaked semantic values when reporting ambiguity])
1405 AT_BISON_OPTION_PUSHDEFS
1406 AT_DATA_GRAMMAR([glr-regr15.y],
1409 %destructor { parent_rhs_before_value = 0; } parent_rhs_before
1412 # include <stdlib.h>
1413 ]AT_YYERROR_DECLARE[
1415 static int parent_rhs_before_value = 0;
1426 /* This stack must be merged into the other stacks *last* (added at the
1427 beginning of the semantic options list) so that yyparse will choose to clean
1428 it up rather than the tree for which some semantic actions have been
1429 performed. Thus, if yyreportAmbiguity longjmp's to yyparse, the values from
1430 those other trees are not cleaned up. */
1434 parent_rhs_before ambiguity {
1436 parent_rhs_before_value = 0;
1443 parent_rhs_before_value = 1;
1447 ambiguity: ambiguity1 | ambiguity2 ;
1458 int exit_status = yyparse () != 1;
1459 if (parent_rhs_before_value)
1461 fprintf (stderr, "`parent_rhs_before' destructor not called.\n");
1467 AT_BISON_OPTION_POPDEFS
1469 AT_BISON_CHECK([[-o glr-regr15.c glr-regr15.y]], 0, [],
1470 [glr-regr15.y: conflicts: 2 reduce/reduce
1472 AT_COMPILE([glr-regr15])
1474 AT_PARSER_CHECK([[./glr-regr15]], 0, [],
1475 [syntax is ambiguous
1481 ## ------------------------------------------------------------------------- ##
1482 ## Leaked lookahead after nondeterministic parse syntax error. ##
1483 ## ------------------------------------------------------------------------- ##
1485 AT_SETUP([Leaked lookahead after nondeterministic parse syntax error])
1487 AT_BISON_OPTION_PUSHDEFS
1488 AT_DATA_GRAMMAR([glr-regr16.y],
1491 %destructor { lookahead_value = 0; } 'b'
1494 # include <stdlib.h>
1495 # include <assert.h>
1496 ]AT_YYERROR_DECLARE[
1498 static int lookahead_value = 0;
1504 start: alt1 'a' | alt2 'a' ;
1511 ]AT_YYLEX_DEFINE(["ab"],
1513 lookahead_value = 1])[
1518 int exit_status = yyparse () != 1;
1519 if (lookahead_value)
1521 fprintf (stderr, "Lookahead destructor not called.\n");
1527 AT_BISON_OPTION_POPDEFS
1529 AT_BISON_CHECK([[-o glr-regr16.c glr-regr16.y]], 0, [],
1530 [glr-regr16.y: conflicts: 1 reduce/reduce
1532 AT_COMPILE([glr-regr16])
1534 AT_PARSER_CHECK([[./glr-regr16]], 0, [],
1541 ## ------------------------------------------------------------------------- ##
1542 ## Uninitialized location when reporting ambiguity. ##
1543 ## ------------------------------------------------------------------------- ##
1545 AT_SETUP([Uninitialized location when reporting ambiguity])
1547 AT_BISON_OPTION_PUSHDEFS([%glr-parser %locations %define api.pure])
1549 AT_DATA_GRAMMAR([glr-regr17.y],
1556 %union { int dummy; }
1559 ]AT_YYERROR_DECLARE[
1565 /* Tests the case of an empty RHS that has inherited the location of the
1566 previous nonterminal, which is unresolved. That location is reported as the
1567 last position of the ambiguity. */
1568 start: ambig1 empty1 | ambig2 empty2 ;
1570 /* Tests multiple levels of yyresolveLocations recursion. */
1571 ambig1: sub_ambig1 | sub_ambig2 ;
1572 ambig2: sub_ambig1 | sub_ambig2 ;
1574 /* Tests the case of a non-empty RHS as well as the case of an empty RHS that
1575 has inherited the initial location. The empty RHS's location is reported as
1576 the first position in the ambiguity. */
1577 sub_ambig1: empty1 'a' 'b' ;
1578 sub_ambig2: empty2 'a' 'b' ;
1583 # include <assert.h>
1587 yylex (YYSTYPE *lvalp, YYLTYPE *llocp)
1589 static char const input[] = "ab";
1590 static size_t toknum;
1591 assert (toknum < sizeof input);
1593 llocp->first_line = llocp->last_line = 2;
1594 llocp->first_column = toknum + 1;
1595 llocp->last_column = llocp->first_column + 1;
1596 return input[toknum++];
1602 return yyparse () != 1;
1605 AT_BISON_OPTION_POPDEFS
1607 AT_BISON_CHECK([[-o glr-regr17.c glr-regr17.y]], 0, [],
1608 [glr-regr17.y: conflicts: 3 reduce/reduce
1610 AT_COMPILE([glr-regr17])
1612 AT_PARSER_CHECK([[./glr-regr17]], 0, [],
1613 [1.1-2.2: syntax is ambiguous
1619 ## -------------------------------------------------------------##
1620 ## Missed %merge type warnings when LHS type is declared later. ##
1621 ## -------------------------------------------------------------##
1623 AT_SETUP([Missed %merge type warnings when LHS type is declared later])
1625 AT_BISON_OPTION_PUSHDEFS
1626 AT_DATA_GRAMMAR([glr-regr18.y],
1631 ]AT_YYERROR_DECLARE[
1643 sym1: sym2 %merge<merge> { $$ = $1; } ;
1644 sym2: sym3 %merge<merge> { $$ = $1; } ;
1645 sym3: %merge<merge> { $$ = 0; } ;
1660 AT_BISON_OPTION_POPDEFS
1662 AT_BISON_CHECK([[-o glr-regr18.c glr-regr18.y]], 1, [],
1663 [glr-regr18.y:26.18-24: error: result type clash on merge function 'merge': <type2> != <type1>
1664 glr-regr18.y:25.18-24: previous declaration
1665 glr-regr18.y:27.13-19: error: result type clash on merge function 'merge': <type3> != <type2>
1666 glr-regr18.y:26.18-24: previous declaration
1672 ## ------------------- ##
1673 ## Ambiguity reports. ##
1674 ## ------------------- ##
1676 AT_SETUP([Ambiguity reports])
1678 AT_BISON_OPTION_PUSHDEFS
1679 AT_DATA_GRAMMAR([input.y],
1684 ]AT_YYERROR_DECLARE[
1699 ]AT_YYLEX_DEFINE(["abc"])[
1705 return !!yyparse ();
1708 AT_BISON_OPTION_POPDEFS
1710 AT_BISON_CHECK([[-o input.c input.y]], 0, [],
1711 [input.y: conflicts: 1 reduce/reduce
1715 AT_PARSER_CHECK([[./input]], 1, [],
1718 Reading a token: Next token is token 'a' ()
1719 Shifting token 'a' ()
1721 Reading a token: Next token is token 'b' ()
1722 Shifting token 'b' ()
1724 Reducing stack 0 by rule 3 (line 25):
1728 Reading a token: Next token is token 'c' ()
1729 Shifting token 'c' ()
1731 Reducing stack 0 by rule 4 (line 26):
1734 Reading a token: Now at end of input.
1735 Stack 0 Entering state 7
1736 Now at end of input.
1737 Splitting off stack 1 from 0.
1738 Reduced stack 1 by rule #2; action deferred. Now in state 2.
1739 Stack 1 Entering state 2
1740 Now at end of input.
1741 Reduced stack 0 by rule #1; action deferred. Now in state 2.
1742 Merging stack 0 into stack 1.
1743 Stack 1 Entering state 2
1744 Now at end of input.
1745 Removing dead stacks.
1746 Rename stack 1 -> 0.
1747 On stack 0, shifting token $end ()
1748 Stack 0 now in state #5
1751 start -> <Rule 1, tokens 1 .. 3>
1758 start -> <Rule 2, tokens 1 .. 3>
1765 Cleanup: popping token $end ()
1766 Cleanup: popping unresolved nterm start ()
1767 Cleanup: popping nterm d ()
1768 Cleanup: popping token 'c' ()
1769 Cleanup: popping nterm b ()
1770 Cleanup: popping token 'a' ()