character set. */
bool translate_strings_p;
+ /* TRUE if we are presently parsing the body of a function, but not
+ a local class. */
+ bool in_function_body;
+
/* If non-NULL, then we are parsing a construct where new type
definitions are not permitted. The string stored here will be
issued as an error message if a type is defined. */
/* String literals should be translated to the execution character set. */
parser->translate_strings_p = true;
+ /* We are not parsing a function body. */
+ parser->in_function_body = false;
+
/* The unparsed function queue is empty. */
parser->unparsed_functions_queues = build_tree_list (NULL_TREE, NULL_TREE);
int i = ({ int j = 3; j + 1; });
at class or namespace scope. */
- if (!at_function_scope_p ())
+ if (!parser->in_function_body)
error ("statement-expressions are allowed only inside functions");
/* Start the statement-expression. */
expr = begin_stmt_expr ();
too. Doing that means that we have to treat the `::' operator as
two `:' tokens. */
if (cp_parser_allow_gnu_extensions_p (parser)
- && at_function_scope_p ()
+ && parser->in_function_body
&& (cp_lexer_next_token_is (parser->lexer, CPP_COLON)
|| cp_lexer_next_token_is (parser->lexer, CPP_SCOPE)))
{
cp_parser_require (parser, CPP_SEMICOLON, "`;'");
/* Create the ASM_EXPR. */
- if (at_function_scope_p ())
+ if (parser->in_function_body)
{
asm_stmt = finish_asm_stmt (volatile_p, string, outputs,
inputs, clobbers);
/* Normally, the array bound must be an integral constant
expression. However, as an extension, we allow VLAs
in function scopes. */
- else if (!at_function_scope_p ())
+ else if (!parser->in_function_body)
{
error ("array bound is not an integer constant");
bounds = error_mark_node;
int has_trailing_semicolon;
bool nested_name_specifier_p;
unsigned saved_num_template_parameter_lists;
+ bool saved_in_function_body;
tree old_scope = NULL_TREE;
tree scope = NULL_TREE;
saved_num_template_parameter_lists
= parser->num_template_parameter_lists;
parser->num_template_parameter_lists = 0;
+ /* We are not in a function body. */
+ saved_in_function_body = parser->in_function_body;
+ parser->in_function_body = false;
/* Start the class. */
if (nested_name_specifier_p)
/* Put back any saved access checks. */
pop_deferring_access_checks ();
- /* Restore the count of active template-parameter-lists. */
+ /* Restore saved state. */
+ parser->in_function_body = saved_in_function_body;
parser->num_template_parameter_lists
= saved_num_template_parameter_lists;
/* The common case is that this is not a constructor declarator, so
try to avoid doing lots of work if at all possible. It's not
valid declare a constructor at function scope. */
- if (at_function_scope_p ())
+ if (parser->in_function_body)
return false;
/* And only certain tokens can begin a constructor declarator. */
next_token = cp_lexer_peek_token (parser->lexer);
tree fn;
bool ctor_initializer_p = false;
bool saved_in_unbraced_linkage_specification_p;
+ bool saved_in_function_body;
unsigned saved_num_template_parameter_lists;
+ saved_in_function_body = parser->in_function_body;
+ parser->in_function_body = true;
/* If the next token is `return', then the code may be trying to
make use of the "named return value" extension that G++ used to
support. */
= saved_in_unbraced_linkage_specification_p;
parser->num_template_parameter_lists
= saved_num_template_parameter_lists;
+ parser->in_function_body = saved_in_function_body;
return fn;
}