mirror of
https://git.savannah.gnu.org/git/bison.git
synced 2026-03-11 13:23:04 +00:00
glr.cc, yacc.c: initialize yylloc properly
There are several issues to address here. One is that yylloc should be initialized when possible. Another is that the push parser needs to update yypushed_loc when the user modified it. And if the parser starts by a reduction of an empty, it uses the first location on the stack, which, therefore, must also be initialized to this initial location. This is getting complex, especially since because initializing a global (impure interface) is different from initializing a local variable. To simplify, the local yylloc is not initialized during its definition. * data/c.m4 (b4_yyloc_default_define): Replace by... (b4_yyloc_default): this. Adjust dependencies. * data/glr.cc: Initialize yylloc. * data/yacc.c (b4_declare_scanner_communication_variables): Initialize yylloc during its definition. Don't define yyloc_default. (yypush_parse): The location formal is not const, as we might initialize it. (yyparse): Define yyloc_default. Use it before running the user initial action. Possibly update the first location on the stack, and the pushed location after the user initial action. * tests/actions.at (Initial locations): Check that the initial location is correct.
This commit is contained in:
14
data/c.m4
14
data/c.m4
@@ -673,12 +673,11 @@ m4_define([b4_yy_location_print_define],
|
||||
#endif]])
|
||||
])
|
||||
|
||||
# b4_yyloc_default_define
|
||||
# -----------------------
|
||||
# Define yyloc_default, which can be used to initialize location
|
||||
# variables.
|
||||
m4_define([b4_yyloc_default_define],
|
||||
[[static YYLTYPE yyloc_default
|
||||
# b4_yyloc_default
|
||||
# ----------------
|
||||
# Expand to a possible default value for yylloc.
|
||||
m4_define([b4_yyloc_default],
|
||||
[[
|
||||
# if defined ]b4_api_PREFIX[LTYPE_IS_TRIVIAL && ]b4_api_PREFIX[LTYPE_IS_TRIVIAL
|
||||
= { ]m4_join([, ],
|
||||
m4_defn([b4_location_initial_line]),
|
||||
@@ -686,5 +685,4 @@ m4_define([b4_yyloc_default_define],
|
||||
m4_defn([b4_location_initial_line]),
|
||||
m4_defn([b4_location_initial_column]))[ }
|
||||
# endif
|
||||
;]dnl
|
||||
])
|
||||
]])
|
||||
|
||||
@@ -226,8 +226,8 @@ b4_percent_code_get([[top]])[
|
||||
right-hand sides. Unlike the standard yacc.c template, here we set
|
||||
the default value of $$ to a zeroed-out value. Since the default
|
||||
value is undefined, this behavior is technically correct. */
|
||||
static YYSTYPE yyval_default;]b4_locations_if([
|
||||
b4_yyloc_default_define])[
|
||||
static YYSTYPE yyval_default;]b4_locations_if([[
|
||||
static YYLTYPE yyloc_default][]b4_yyloc_default;])[
|
||||
|
||||
/* Copy the second part of user declarations. */
|
||||
]b4_user_post_prologue
|
||||
|
||||
@@ -87,12 +87,17 @@ m4_define([b4_yy_symbol_print_generate],
|
||||
]b4_parse_param_use[]dnl
|
||||
[ yyparser.yy_symbol_print_ (yytype, yyvaluep]b4_locations_if([, yylocationp])[);
|
||||
}
|
||||
]])
|
||||
]])[
|
||||
|
||||
# Hijack the initial action to initialize the locations.
|
||||
]b4_locations_if([b4_percent_define_ifdef([[location_type]], [],
|
||||
[m4_define([b4_initial_action],
|
||||
[yylloc.initialize ();]m4_ifdef([b4_initial_action], [
|
||||
m4_defn([b4_initial_action])]))])])[
|
||||
|
||||
# Hijack the post prologue to insert early definition of YYLLOC_DEFAULT
|
||||
# and declaration of yyerror.
|
||||
m4_append([b4_post_prologue],
|
||||
]m4_append([b4_post_prologue],
|
||||
[b4_syncline([@oline@], [@ofile@])[
|
||||
]b4_yylloc_default_define[
|
||||
#define YYRHSLOC(Rhs, K) ((Rhs)[K].yystate.yyloc)
|
||||
|
||||
21
data/yacc.c
21
data/yacc.c
@@ -181,8 +181,7 @@ int yychar;
|
||||
#else
|
||||
/* Default value used for initialization, for pacifying older GCCs
|
||||
or non-GCC compilers. */
|
||||
static YYSTYPE yyval_default;]b4_locations_if([
|
||||
b4_yyloc_default_define])[
|
||||
static YYSTYPE yyval_default;
|
||||
# define YY_INITIAL_VALUE(Value) = Value
|
||||
#endif]])[
|
||||
#ifndef YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN
|
||||
@@ -197,7 +196,8 @@ b4_yyloc_default_define])[
|
||||
YYSTYPE yylval YY_INITIAL_VALUE(yyval_default);]b4_locations_if([[
|
||||
|
||||
/* Location data for the lookahead symbol. */
|
||||
YYLTYPE yylloc YY_INITIAL_VALUE(yyloc_default);]])b4_pure_if([], [[
|
||||
YYLTYPE yylloc][]b4_yyloc_default[;
|
||||
]])b4_pure_if([], [[
|
||||
|
||||
/* Number of syntax errors so far. */
|
||||
int yynerrs;]])])
|
||||
@@ -265,7 +265,7 @@ typedef struct ]b4_prefix[pstate ]b4_prefix[pstate;
|
||||
[[b4_prefix[pstate *ps]], [[ps]]]b4_pure_if([,
|
||||
[[[int pushed_char]], [[pushed_char]]],
|
||||
[[b4_api_PREFIX[STYPE const *pushed_val]], [[pushed_val]]]b4_locations_if([,
|
||||
[[b4_api_PREFIX[LTYPE const *pushed_loc]], [[pushed_loc]]]])])m4_ifset([b4_parse_param], [,
|
||||
[[b4_api_PREFIX[LTYPE *pushed_loc]], [[pushed_loc]]]])])m4_ifset([b4_parse_param], [,
|
||||
b4_parse_param]))
|
||||
b4_pull_if([b4_c_function_decl([b4_prefix[pull_parse]], [[int]],
|
||||
[[b4_prefix[pstate *ps]], [[ps]]]m4_ifset([b4_parse_param], [,
|
||||
@@ -1409,7 +1409,7 @@ b4_c_function_def([[yyparse]], [[int]], b4_parse_param)[
|
||||
yypstate *yyps_local;]b4_pure_if([[
|
||||
int yychar;
|
||||
YYSTYPE yylval;]b4_locations_if([[
|
||||
YYLTYPE yylloc;]])])[
|
||||
YYLTYPE yylloc][]b4_yyloc_default[;]])])[
|
||||
if (yyps)
|
||||
yyps_local = yyps;
|
||||
else
|
||||
@@ -1489,7 +1489,7 @@ b4_c_function_def([[yyparse]], [[int]], b4_parse_param)[
|
||||
[[[yypstate *yyps]], [[yyps]]]b4_pure_if([,
|
||||
[[[int yypushed_char]], [[yypushed_char]]],
|
||||
[[[YYSTYPE const *yypushed_val]], [[yypushed_val]]]b4_locations_if([,
|
||||
[[[YYLTYPE const *yypushed_loc]], [[yypushed_loc]]]])])m4_ifset([b4_parse_param], [,
|
||||
[[[YYLTYPE *yypushed_loc]], [[yypushed_loc]]]])])m4_ifset([b4_parse_param], [,
|
||||
b4_parse_param]))], [[
|
||||
|
||||
|
||||
@@ -1556,16 +1556,17 @@ b4_c_function_def([[yyparse]], [[int]], b4_parse_param)[
|
||||
yyerrstatus = 0;
|
||||
yynerrs = 0;
|
||||
yychar = YYEMPTY; /* Cause a token to be read. */
|
||||
]m4_ifdef([b4_initial_action],[
|
||||
]m4_ifdef([b4_initial_action], [
|
||||
b4_dollar_pushdef([m4_define([b4_dollar_dollar_used])yylval], [],
|
||||
[m4_define([b4_at_dollar_used])yylloc])dnl
|
||||
[m4_define([b4_at_dollar_used])dnl
|
||||
b4_push_if([b4_pure_if([*])yypushed_loc], [yylloc])])dnl
|
||||
/* User initialization code. */
|
||||
b4_user_initial_action
|
||||
b4_dollar_popdef[]dnl
|
||||
m4_ifdef([b4_dollar_dollar_used],[[ yyvsp[0] = yylval;
|
||||
]])dnl
|
||||
m4_ifdef([b4_at_dollar_used], [[ yylsp[0] = yylloc;
|
||||
]])])dnl
|
||||
b4_locations_if([[ yylsp[0] = ]b4_push_if([b4_pure_if([*])yypushed_loc], [yylloc])[;
|
||||
]])dnl
|
||||
[ goto yysetstate;
|
||||
|
||||
/*------------------------------------------------------------.
|
||||
|
||||
Reference in New Issue
Block a user