/* YACC parser for C++ syntax.
- Copyright (C) 1988, 89, 93-98, 1999 Free Software Foundation, Inc.
+ Copyright (C) 1988, 1989, 1993, 1994, 1995, 1996, 1997, 1998,
+ 1999, 2000 Free Software Foundation, Inc.
Hacked by Michael Tiemann (tiemann@cygnus.com)
This file is part of GNU CC.
#include "output.h"
#include "except.h"
#include "toplev.h"
+#include "ggc.h"
/* Since parsers are distinct for each language, put the language string
definition here. (fnf) */
-char *language_string = "GNU C++";
+const char * const language_string = "GNU C++";
extern struct obstack permanent_obstack;
error message if the user supplies an empty conditional expression. */
static const char *cond_stmt_keyword;
-static tree empty_parms PROTO((void));
-static int parse_decl PROTO((tree, tree, tree, int, tree *));
-
/* Nonzero if we have an `extern "C"' acting as an extern specifier. */
int have_extern_spec;
int used_extern_spec;
+/* List of types and structure classes of the current declaration. */
+static tree current_declspecs;
+
+/* List of prefix attributes in effect.
+ Prefix attributes are parsed by the reserved_declspecs and declmods
+ rules. They create a list that contains *both* declspecs and attrs. */
+/* ??? It is not clear yet that all cases where an attribute can now appear in
+ a declspec list have been updated. */
+static tree prefix_attributes;
+
+/* When defining an aggregate, this is the kind of the most recent one
+ being defined. (For example, this might be class_type_node.) */
+static tree current_aggr;
+
+/* When defining an enumeration, this is the type of the enumeration. */
+static tree current_enum_type;
+
+static tree empty_parms PARAMS ((void));
+static tree parse_decl0 PARAMS ((tree, tree, tree, tree, int));
+static tree parse_decl PARAMS ((tree, tree, int));
+static void parse_end_decl PARAMS ((tree, tree, tree));
+static tree parse_field0 PARAMS ((tree, tree, tree, tree, tree, tree));
+static tree parse_field PARAMS ((tree, tree, tree, tree));
+static tree parse_bitfield0 PARAMS ((tree, tree, tree, tree, tree));
+static tree parse_bitfield PARAMS ((tree, tree, tree));
+static tree parse_method PARAMS ((tree, tree, tree));
+static void frob_specs PARAMS ((tree, tree));
+
/* Cons up an empty parameter list. */
-#ifdef __GNUC__
-__inline
-#endif
-static tree
+static inline tree
empty_parms ()
{
tree parms;
return parms;
}
+/* Record the decl-specifiers, attributes and type lookups from the
+ decl-specifier-seq in a declaration. */
+
+static void
+frob_specs (specs_attrs, lookups)
+ tree specs_attrs, lookups;
+{
+ save_type_access_control (lookups);
+ split_specs_attrs (specs_attrs, ¤t_declspecs, &prefix_attributes);
+ if (current_declspecs
+ && TREE_CODE (current_declspecs) != TREE_LIST)
+ current_declspecs = build_decl_list (NULL_TREE, current_declspecs);
+ if (have_extern_spec && !used_extern_spec)
+ {
+ current_declspecs = decl_tree_cons (NULL_TREE,
+ get_identifier ("extern"),
+ current_declspecs);
+ used_extern_spec = 1;
+ }
+}
+
+static tree
+parse_decl (declarator, attributes, initialized)
+ tree declarator, attributes;
+ int initialized;
+{
+ return start_decl (declarator, current_declspecs, initialized,
+ attributes, prefix_attributes);
+}
+
+static tree
+parse_decl0 (declarator, specs_attrs, lookups, attributes, initialized)
+ tree declarator, specs_attrs, lookups, attributes;
+ int initialized;
+{
+ frob_specs (specs_attrs, lookups);
+ return parse_decl (declarator, attributes, initialized);
+}
+
+static void
+parse_end_decl (decl, init, asmspec)
+ tree decl, init, asmspec;
+{
+ /* If decl is NULL_TREE, then this was a variable declaration using
+ () syntax for the initializer, so we handled it in grokdeclarator. */
+ if (decl)
+ decl_type_access_control (decl);
+ cp_finish_decl (decl, init, asmspec, init ? LOOKUP_ONLYCONVERTING : 0);
+}
+
+static tree
+parse_field (declarator, attributes, asmspec, init)
+ tree declarator, attributes, asmspec, init;
+{
+ tree d = grokfield (declarator, current_declspecs, init, asmspec,
+ build_tree_list (attributes, prefix_attributes));
+ decl_type_access_control (d);
+ return d;
+}
+
+static tree
+parse_field0 (declarator, specs_attrs, lookups, attributes, asmspec, init)
+ tree declarator, specs_attrs, lookups, attributes, asmspec, init;
+{
+ frob_specs (specs_attrs, lookups);
+ return parse_field (declarator, attributes, asmspec, init);
+}
+
+static tree
+parse_bitfield (declarator, attributes, width)
+ tree declarator, attributes, width;
+{
+ tree d = grokbitfield (declarator, current_declspecs, width);
+ cplus_decl_attributes (d, attributes, prefix_attributes);
+ decl_type_access_control (d);
+ return d;
+}
+
+static tree
+parse_bitfield0 (declarator, specs_attrs, lookups, attributes, width)
+ tree declarator, specs_attrs, lookups, attributes, width;
+{
+ frob_specs (specs_attrs, lookups);
+ return parse_bitfield (declarator, attributes, width);
+}
+
+static tree
+parse_method (declarator, specs_attrs, lookups)
+ tree declarator, specs_attrs, lookups;
+{
+ tree d;
+ frob_specs (specs_attrs, lookups);
+ d = start_method (current_declspecs, declarator, prefix_attributes);
+ decl_type_access_control (d);
+ return d;
+}
+
+void
+cp_parse_init ()
+{
+ ggc_add_tree_root (¤t_declspecs, 1);
+ ggc_add_tree_root (&prefix_attributes, 1);
+ ggc_add_tree_root (¤t_aggr, 1);
+ ggc_add_tree_root (¤t_enum_type, 1);
+}
%}
%start program
-%union {long itype; tree ttype; char *strtype; enum tree_code code; flagged_type_tree ftype; }
+%union {
+ long itype;
+ tree ttype;
+ char *strtype;
+ enum tree_code code;
+ flagged_type_tree ftype;
+ struct pending_inline *pi;
+}
/* All identifiers that are not reserved words
and are not declared typedefs in the current block */
%type <ttype> expr_no_commas cast_expr unary_expr primary string STRING
%type <ttype> reserved_declspecs boolean.literal
%type <ttype> reserved_typespecquals
-%type <ttype> declmods
%type <ttype> SCSPEC TYPESPEC CV_QUALIFIER maybe_cv_qualifier
-%type <itype> initdecls notype_initdecls initdcl /* C++ modification */
%type <ttype> init initlist maybeasm maybe_init defarg defarg1
%type <ttype> asm_operands nonnull_asm_operands asm_operand asm_clobbers
%type <ttype> maybe_attribute attributes attribute attribute_list attrib
%type <ttype> component_declarator component_declarator0
%type <ttype> notype_component_declarator notype_component_declarator0
%type <ttype> after_type_component_declarator after_type_component_declarator0
-%type <ttype> enumlist_opt enumlist enumerator
%type <ttype> absdcl cv_qualifiers
%type <ttype> direct_abstract_declarator conversion_declarator
%type <ttype> new_declarator direct_new_declarator
%type <ftype> type_id new_type_id typed_typespecs typespec typed_declspecs
%type <ftype> typed_declspecs1 type_specifier_seq nonempty_cv_qualifiers
%type <ftype> structsp typespecqual_reserved parm named_parm full_parm
+%type <ftype> declmods
%type <itype> extension
/* C++ extensions */
%token <ttype> PTYPENAME
-%token <ttype> PRE_PARSED_FUNCTION_DECL EXTERN_LANG_STRING ALL
+%token <ttype> EXTERN_LANG_STRING ALL
%token <ttype> PRE_PARSED_CLASS_DECL DEFARG DEFARG_MARKER
+%token <pi> PRE_PARSED_FUNCTION_DECL
%type <ttype> component_constructor_declarator
-%type <ttype> fn.def2 return_id fn.defpen constructor_declarator
+%type <ttype> fn.def2 return_id constructor_declarator
+%type <pi> fn.defpen
%type <itype> ctor_initializer_opt function_try_block
%type <ttype> named_class_head_sans_basetype
%type <ftype> class_head named_class_head
%type <ttype> exception_specification_opt ansi_raise_identifier ansi_raise_identifiers
%type <ttype> operator_name
%type <ttype> object aggr
-%type <itype> new delete .begin_new_placement
+%type <itype> new delete
/* %type <ttype> primary_no_id */
-%type <ttype> nonmomentary_expr maybe_parmlist
-%type <itype> initdcl0 notype_initdcl0 member_init_list initdcl0_innards
+%type <ttype> maybe_parmlist
+%type <itype> member_init_list
%type <ttype> template_header template_parm_list template_parm
%type <ttype> template_type_parm template_template_parm
%type <code> template_close_bracket
%token TYPENAME_DEFN IDENTIFIER_DEFN PTYPENAME_DEFN
%type <ttype> named_class_head_sans_basetype_defn
%type <ttype> identifier_defn IDENTIFIER_DEFN TYPENAME_DEFN PTYPENAME_DEFN
-
+%type <ttype> handler_args
%type <ttype> self_template_type .finish_template_type
%token NSNAME
%token END_OF_SAVED_INPUT
\f
%{
-/* List of types and structure classes of the current declaration. */
-static tree current_declspecs;
-
-/* List of prefix attributes in effect.
- Prefix attributes are parsed by the reserved_declspecs and declmods
- rules. They create a list that contains *both* declspecs and attrs. */
-/* ??? It is not clear yet that all cases where an attribute can now appear in
- a declspec list have been updated. */
-static tree prefix_attributes;
-
-/* When defining an aggregate, this is the kind of the most recent one
- being defined. (For example, this might be class_type_node.) */
-static tree current_aggr;
-
-/* When defining an enumeration, this is the type of the enumeration. */
-static tree current_enum_type;
-
/* Tell yyparse how to print a token's value, if yydebug is set. */
-
#define YYPRINT(FILE,YYCHAR,YYLVAL) yyprint(FILE,YYCHAR,YYLVAL)
-extern void yyprint PROTO((FILE *, int, YYSTYPE));
-extern tree combine_strings PROTO((tree));
-
-static int
-parse_decl(declarator, specs_attrs, attributes, initialized, decl)
- tree declarator;
- tree specs_attrs;
- tree attributes;
- int initialized;
- tree* decl;
-{
- int sm;
-
- split_specs_attrs (specs_attrs, ¤t_declspecs, &prefix_attributes);
- if (current_declspecs
- && TREE_CODE (current_declspecs) != TREE_LIST)
- current_declspecs = build_decl_list (NULL_TREE, current_declspecs);
- if (have_extern_spec && !used_extern_spec)
- {
- current_declspecs = decl_tree_cons (NULL_TREE,
- get_identifier ("extern"),
- current_declspecs);
- used_extern_spec = 1;
- }
- sm = suspend_momentary ();
- *decl = start_decl (declarator, current_declspecs, initialized,
- attributes, prefix_attributes);
- return sm;
-}
+extern void yyprint PARAMS ((FILE *, int, YYSTYPE));
%}
\f
%%
extdefs:
{ $<ttype>$ = NULL_TREE; }
lang_extdef
- { $<ttype>$ = NULL_TREE; }
+ { $<ttype>$ = NULL_TREE; ggc_collect (); }
| extdefs lang_extdef
- { $<ttype>$ = NULL_TREE; }
+ { $<ttype>$ = NULL_TREE; ggc_collect (); }
;
extdefs_opt:
;
lang_extdef:
- { if (pending_lang_change) do_pending_lang_change(); }
+ { if (pending_lang_change) do_pending_lang_change();
+ type_lookups = NULL_TREE; }
extdef
{ if (! toplevel_bindings_p ())
pop_everything (); }
fndef:
fn.def1 maybe_return_init ctor_initializer_opt compstmt_or_error
- { finish_function (lineno, (int)$3, 0); }
+ { expand_body (finish_function (lineno, (int)$3)); }
| fn.def1 maybe_return_init function_try_block
- {
- int nested = (hack_decl_function_context
- (current_function_decl) != NULL_TREE);
- finish_function (lineno, (int)$3, nested);
- }
+ { expand_body (finish_function (lineno, (int)$3)); }
| fn.def1 maybe_return_init error
{ }
;
fn.def1:
typed_declspecs declarator
- { if (!begin_function_definition ($1.t, $2))
+ { check_for_new_type ("return type", $1);
+ if (!begin_function_definition ($1.t, $2))
YYERROR1; }
| declmods notype_declarator
- { if (!begin_function_definition ($1, $2))
+ { if (!begin_function_definition ($1.t, $2))
YYERROR1; }
| notype_declarator
{ if (!begin_function_definition (NULL_TREE, $1))
YYERROR1; }
| declmods constructor_declarator
- { if (!begin_function_definition ($1, $2))
+ { if (!begin_function_definition ($1.t, $2))
YYERROR1; }
| constructor_declarator
{ if (!begin_function_definition (NULL_TREE, $1))
reduce/reduce conflict introduced by these rules. */
fn.def2:
declmods component_constructor_declarator
- { tree specs, attrs;
- split_specs_attrs ($1, &specs, &attrs);
- attrs = build_tree_list (attrs, NULL_TREE);
- $$ = start_method (specs, $2, attrs);
+ { $$ = parse_method ($2, $1.t, $1.lookups);
rest_of_mdef:
if (! $$)
YYERROR1;
yychar = YYLEX;
reinit_parse_for_method (yychar, $$); }
| component_constructor_declarator
- { $$ = start_method (NULL_TREE, $1, NULL_TREE);
+ { $$ = parse_method ($1, NULL_TREE, NULL_TREE);
goto rest_of_mdef; }
| typed_declspecs declarator
- { tree specs, attrs;
- split_specs_attrs ($1.t, &specs, &attrs);
- attrs = build_tree_list (attrs, NULL_TREE);
- $$ = start_method (specs, $2, attrs); goto rest_of_mdef; }
+ { $$ = parse_method ($2, $1.t, $1.lookups); goto rest_of_mdef;}
| declmods notype_declarator
- { tree specs, attrs;
- split_specs_attrs ($1, &specs, &attrs);
- attrs = build_tree_list (attrs, NULL_TREE);
- $$ = start_method (specs, $2, attrs); goto rest_of_mdef; }
+ { $$ = parse_method ($2, $1.t, $1.lookups); goto rest_of_mdef;}
| notype_declarator
- { $$ = start_method (NULL_TREE, $$, NULL_TREE);
+ { $$ = parse_method ($1, NULL_TREE, NULL_TREE);
goto rest_of_mdef; }
| declmods constructor_declarator
- { tree specs, attrs;
- split_specs_attrs ($1, &specs, &attrs);
- attrs = build_tree_list (attrs, NULL_TREE);
- $$ = start_method (specs, $2, attrs); goto rest_of_mdef; }
+ { $$ = parse_method ($2, $1.t, $1.lookups); goto rest_of_mdef;}
| constructor_declarator
- { $$ = start_method (NULL_TREE, $$, NULL_TREE);
+ { $$ = parse_method ($1, NULL_TREE, NULL_TREE);
goto rest_of_mdef; }
;
store_parm_decls ();
if (DECL_CONSTRUCTOR_P (current_function_decl))
- {
- /* Make a contour for the initializer list. */
- pushlevel (0);
- clear_last_expr ();
- expand_start_bindings (0);
- }
+ /* Make a contour for the initializer list. */
+ do_pushlevel ();
else if (current_class_type == NULL_TREE)
error ("base initializers not allowed for non-member functions");
else if (! DECL_CONSTRUCTOR_P (current_function_decl))
| typename_sub LEFT_RIGHT
{ expand_member_init (current_class_ref, TYPE_MAIN_DECL ($1),
void_type_node); }
+ | error
;
identifier:
paren_expr_or_null:
LEFT_RIGHT
- { error ("ANSI C++ forbids an empty condition for `%s'",
+ { error ("ISO C++ forbids an empty condition for `%s'",
cond_stmt_keyword);
$$ = integer_zero_node; }
| '(' expr ')'
paren_cond_or_null:
LEFT_RIGHT
- { error ("ANSI C++ forbids an empty condition for `%s'",
+ { error ("ISO C++ forbids an empty condition for `%s'",
cond_stmt_keyword);
$$ = integer_zero_node; }
| '(' condition ')'
}
}
current_declspecs = $1.t;
- $<itype>5 = suspend_momentary ();
- $<ttype>$ = start_decl ($<ttype>2, current_declspecs, 1,
- $4, /*prefix_attributes*/ NULL_TREE);
+ $<ttype>$ = parse_decl ($<ttype>2, $4, 1);
}
init
{
- cp_finish_decl ($<ttype>6, $7, $4, 1, LOOKUP_ONLYCONVERTING);
- resume_momentary ($<itype>5);
+ parse_end_decl ($<ttype>6, $7, $4);
$$ = convert_from_reference ($<ttype>6);
if (TREE_CODE (TREE_TYPE ($$)) == ARRAY_TYPE)
cp_error ("definition of array `%#D' in condition", $$);
nontrivial_exprlist:
expr_no_commas ',' expr_no_commas
- { $$ = expr_tree_cons (NULL_TREE, $$,
- build_expr_list (NULL_TREE, $3)); }
+ { $$ = tree_cons (NULL_TREE, $$,
+ build_tree_list (NULL_TREE, $3)); }
| expr_no_commas ',' error
- { $$ = expr_tree_cons (NULL_TREE, $$,
- build_expr_list (NULL_TREE, error_mark_node)); }
+ { $$ = tree_cons (NULL_TREE, $$,
+ build_tree_list (NULL_TREE, error_mark_node)); }
| nontrivial_exprlist ',' expr_no_commas
- { chainon ($$, build_expr_list (NULL_TREE, $3)); }
+ { chainon ($$, build_tree_list (NULL_TREE, $3)); }
| nontrivial_exprlist ',' error
- { chainon ($$, build_expr_list (NULL_TREE, error_mark_node)); }
+ { chainon ($$, build_tree_list (NULL_TREE, error_mark_node)); }
;
nonnull_exprlist:
expr_no_commas
- { $$ = build_expr_list (NULL_TREE, $$); }
+ { $$ = build_tree_list (NULL_TREE, $$); }
| nontrivial_exprlist
;
/* Refer to the address of a label as a pointer. */
| ANDAND identifier
{ if (pedantic)
- pedwarn ("ANSI C++ forbids `&&'");
+ pedwarn ("ISO C++ forbids `&&'");
$$ = finish_label_address_expr ($2); }
| SIZEOF unary_expr %prec UNARY
{ $$ = expr_sizeof ($2); }
| new new_placement new_type_id new_initializer
{ $$ = build_new ($2, $3.t, $4, $1);
check_for_new_type ("new", $3); }
- /* The .begin_new_placement in the following rules is
- necessary to avoid shift/reduce conflicts that lead to
- mis-parsing some expressions. Of course, these constructs
- are not really new-placement and it is bogus to call
- begin_new_placement. But, the parser cannot always tell at this
- point whether the next thing is an expression or a type-id,
- so there is nothing we can do. Fortunately,
- begin_new_placement does nothing harmful. When we rewrite
- the parser, this lossage should be removed, of course. */
- | new '(' .begin_new_placement type_id .finish_new_placement
+ | new '(' type_id ')'
%prec EMPTY
- { $$ = build_new (NULL_TREE, groktypename($4.t),
+ { $$ = build_new (NULL_TREE, groktypename($3.t),
NULL_TREE, $1);
+ check_for_new_type ("new", $3); }
+ | new '(' type_id ')' new_initializer
+ { $$ = build_new (NULL_TREE, groktypename($3.t), $5, $1);
+ check_for_new_type ("new", $3); }
+ | new new_placement '(' type_id ')' %prec EMPTY
+ { $$ = build_new ($2, groktypename($4.t), NULL_TREE, $1);
check_for_new_type ("new", $4); }
- | new '(' .begin_new_placement type_id .finish_new_placement
- new_initializer
- { $$ = build_new (NULL_TREE, groktypename($4.t), $6, $1);
+ | new new_placement '(' type_id ')' new_initializer
+ { $$ = build_new ($2, groktypename($4.t), $6, $1);
check_for_new_type ("new", $4); }
- | new new_placement '(' .begin_new_placement type_id
- .finish_new_placement %prec EMPTY
- { $$ = build_new ($2, groktypename($5.t), NULL_TREE, $1);
- check_for_new_type ("new", $5); }
- | new new_placement '(' .begin_new_placement type_id
- .finish_new_placement new_initializer
- { $$ = build_new ($2, groktypename($5.t), $7, $1);
- check_for_new_type ("new", $5); }
| delete cast_expr %prec UNARY
{ $$ = delete_sanity ($2, NULL_TREE, 0, $1); }
| IMAGPART cast_expr %prec UNARY
{ $$ = build_x_unary_op (IMAGPART_EXPR, $2); }
| VA_ARG '(' expr_no_commas ',' type_id ')'
- { $$ = build_va_arg ($3, groktypename ($5.t));
+ { $$ = build_x_va_arg ($3, groktypename ($5.t));
check_for_new_type ("__builtin_va_arg", $5); }
;
- /* Note this rule is not suitable for use in new_placement
- since it uses NULL_TREE as the argument to
- finish_new_placement. This rule serves only to avoid
- reduce/reduce conflicts in unary_expr. See the comments
- there on the use of begin/finish_new_placement. */
-.finish_new_placement:
- ')'
- { finish_new_placement (NULL_TREE, $<itype>-1); }
-
-.begin_new_placement:
- { $$ = begin_new_placement (); }
-
new_placement:
- '(' .begin_new_placement nonnull_exprlist ')'
- { $$ = finish_new_placement ($3, $2); }
- | '{' .begin_new_placement nonnull_exprlist '}'
+ '(' nonnull_exprlist ')'
+ { $$ = $2; }
+ | '{' nonnull_exprlist '}'
{ cp_pedwarn ("old style placement syntax, use () instead");
- $$ = finish_new_placement ($3, $2); }
+ $$ = $2; }
;
new_initializer:
| '=' init
{
if (pedantic)
- pedwarn ("ANSI C++ forbids initialization of new expression with `='");
+ pedwarn ("ISO C++ forbids initialization of new expression with `='");
if (TREE_CODE ($2) != TREE_LIST
&& TREE_CODE ($2) != CONSTRUCTOR)
- $$ = build_expr_list (NULL_TREE, $2);
+ $$ = build_tree_list (NULL_TREE, $2);
else
$$ = $2;
}
tree init = build_nt (CONSTRUCTOR, NULL_TREE,
nreverse ($3));
if (pedantic)
- pedwarn ("ANSI C++ forbids constructor-expressions");
+ pedwarn ("ISO C++ forbids constructor-expressions");
/* Indicate that this was a GNU C constructor expression. */
TREE_HAS_CONSTRUCTOR (init) = 1;
| boolean.literal
| string
{
- if (processing_template_decl)
- push_obstacks (&permanent_obstack, &permanent_obstack);
$$ = combine_strings ($$);
/* combine_strings doesn't set up TYPE_MAIN_VARIANT of
a const array the way we want, so fix it. */
TREE_TYPE ($$) = build_cplus_array_type
(TREE_TYPE (TREE_TYPE ($$)),
TYPE_DOMAIN (TREE_TYPE ($$)));
- if (processing_template_decl)
- pop_obstacks ();
}
| '(' expr ')'
{ $$ = finish_parenthesized_expr ($2); }
YYERROR;
}
if (pedantic)
- pedwarn ("ANSI C++ forbids braced-groups within expressions");
+ pedwarn ("ISO C++ forbids braced-groups within expressions");
$<ttype>$ = begin_stmt_expr ();
}
compstmt ')'
- { $$ = finish_stmt_expr ($<ttype>2, $3); }
+ { $$ = finish_stmt_expr ($<ttype>2); }
/* Koenig lookup support
We could store lastiddecl in $1 to avoid another lookup,
but that would result in many additional reduce/reduce conflicts. */
`const (3)' is equivalent to `const int (3)'. */
tree type;
- if ($3 == error_mark_node)
- {
- $$ = error_mark_node;
- break;
- }
-
- type = cp_build_qualified_type (integer_type_node,
- cp_type_qual_from_rid ($1));
- $$ = build_c_cast (type, build_compound_expr ($3));
+ type = hash_tree_cons (NULL_TREE, $1, NULL_TREE);
+ type = groktypename (build_decl_list (type, NULL_TREE));
+ $$ = build_functional_cast (type, $3);
}
| functional_cast
| DYNAMIC_CAST '<' type_id '>' '(' expr ')'
check_for_new_type ("const_cast", $3);
$$ = build_const_cast (type, $6); }
| TYPEID '(' expr ')'
- { $$ = build_x_typeid ($3); }
+ { $$ = build_typeid ($3); }
| TYPEID '(' type_id ')'
{ tree type = groktypename ($3.t);
check_for_new_type ("typeid", $3);
{ $$ = build_x_component_ref ($$, $2, NULL_TREE, 1); }
| object overqualified_id %prec UNARY
{ if (processing_template_decl)
- $$ = build_min_nt (COMPONENT_REF, $1, copy_to_permanent ($2));
+ $$ = build_min_nt (COMPONENT_REF, $1, $2);
else
$$ = build_object_ref ($$, OP0 ($2), OP1 ($2)); }
| object unqualified_id '(' nonnull_exprlist ')'
$<ttype>$ = expand_start_stmt_expr (); }
compstmt ')'
{ if (pedantic)
- pedwarn ("ANSI C++ forbids braced-groups within expressions");
+ pedwarn ("ISO C++ forbids braced-groups within expressions");
$$ = expand_end_stmt_expr ($<ttype>2); }
| primary_no_id '(' nonnull_exprlist ')'
{ $$ = build_x_function_call ($$, $3, current_class_ref); }
decl:
typespec initdecls ';'
{
- resume_momentary ($2);
if ($1.t && IS_AGGR_TYPE_CODE (TREE_CODE ($1.t)))
note_got_semicolon ($1.t);
}
| typed_declspecs initdecls ';'
{
- resume_momentary ($2);
note_list_got_semicolon ($1.t);
}
| declmods notype_initdecls ';'
- { resume_momentary ($2); }
+ {}
| typed_declspecs ';'
{
shadow_tag ($1.t);
NULL_TREE); }
;
-/* ANSI type-id (8.1) */
+/* ISO type-id (8.1) */
type_id:
typed_typespecs absdcl
{ $$.t = build_decl_list ($1.t, $2);
typed_declspecs:
typed_typespecs %prec EMPTY
+ { $$.lookups = type_lookups; }
| typed_declspecs1
+ { $$.lookups = type_lookups; }
;
typed_declspecs1:
declmods typespec
- { $$.t = decl_tree_cons (NULL_TREE, $2.t, $1);
+ { $$.t = decl_tree_cons (NULL_TREE, $2.t, $1.t);
$$.new_type_flag = $2.new_type_flag; }
| typespec reserved_declspecs %prec HYPERUNARY
{ $$.t = decl_tree_cons (NULL_TREE, $1.t, $2);
{ $$.t = decl_tree_cons (NULL_TREE, $1.t, chainon ($2, $3));
$$.new_type_flag = $1.new_type_flag; }
| declmods typespec reserved_declspecs
- { $$.t = decl_tree_cons (NULL_TREE, $2.t, chainon ($3, $1));
+ { $$.t = decl_tree_cons (NULL_TREE, $2.t, chainon ($3, $1.t));
$$.new_type_flag = $2.new_type_flag; }
| declmods typespec reserved_typespecquals
- { $$.t = decl_tree_cons (NULL_TREE, $2.t, chainon ($3, $1));
+ { $$.t = decl_tree_cons (NULL_TREE, $2.t, chainon ($3, $1.t));
$$.new_type_flag = $2.new_type_flag; }
| declmods typespec reserved_typespecquals reserved_declspecs
{ $$.t = decl_tree_cons (NULL_TREE, $2.t,
- chainon ($3, chainon ($4, $1)));
+ chainon ($3, chainon ($4, $1.t)));
$$.new_type_flag = $2.new_type_flag; }
;
declmods:
nonempty_cv_qualifiers %prec EMPTY
- { $$ = $1.t; TREE_STATIC ($$) = 1; }
+ { $$.lookups = NULL_TREE; TREE_STATIC ($$.t) = 1; }
| SCSPEC
- { $$ = hash_tree_cons (NULL_TREE, $$, NULL_TREE); }
+ {
+ $$.t = hash_tree_cons (NULL_TREE, $1, NULL_TREE);
+ $$.new_type_flag = 0; $$.lookups = NULL_TREE;
+ }
| declmods CV_QUALIFIER
- { $$ = hash_tree_cons (NULL_TREE, $2, $$);
- TREE_STATIC ($$) = 1; }
+ {
+ $$.t = hash_tree_cons (NULL_TREE, $2, $1.t);
+ TREE_STATIC ($$.t) = 1;
+ }
| declmods SCSPEC
- { if (extra_warnings && TREE_STATIC ($$))
+ {
+ if (extra_warnings && TREE_STATIC ($$.t))
warning ("`%s' is not at beginning of declaration",
IDENTIFIER_POINTER ($2));
- $$ = hash_tree_cons (NULL_TREE, $2, $$);
- TREE_STATIC ($$) = TREE_STATIC ($1); }
+ $$.t = hash_tree_cons (NULL_TREE, $2, $1.t);
+ TREE_STATIC ($$.t) = TREE_STATIC ($1.t);
+ }
| declmods attributes
- { $$ = hash_tree_cons ($2, NULL_TREE, $1); }
+ { $$.t = hash_tree_cons ($2, NULL_TREE, $1.t); }
| attributes %prec EMPTY
- { $$ = hash_tree_cons ($1, NULL_TREE, NULL_TREE); }
+ {
+ $$.t = hash_tree_cons ($1, NULL_TREE, NULL_TREE);
+ $$.new_type_flag = 0; $$.lookups = NULL_TREE;
+ }
;
/* Used instead of declspecs where storage classes are not allowed
$$.new_type_flag = $1.new_type_flag; }
| nonempty_cv_qualifiers typespec reserved_typespecquals
{ $$.t = decl_tree_cons (NULL_TREE, $2.t, chainon ($3, $1.t));
- $$.new_type_flag = $1.new_type_flag; }
+ $$.new_type_flag = $2.new_type_flag; }
;
reserved_typespecquals:
typespec:
structsp
+ { $$.lookups = NULL_TREE; }
| TYPESPEC %prec EMPTY
- { $$.t = $1; $$.new_type_flag = 0; }
+ { $$.t = $1; $$.new_type_flag = 0; $$.lookups = NULL_TREE; }
| complete_type_name
- { $$.t = $1; $$.new_type_flag = 0; }
+ { $$.t = $1; $$.new_type_flag = 0; $$.lookups = NULL_TREE; }
| TYPEOF '(' expr ')'
{ $$.t = finish_typeof ($3);
- $$.new_type_flag = 0; }
+ $$.new_type_flag = 0; $$.lookups = NULL_TREE; }
| TYPEOF '(' type_id ')'
{ $$.t = groktypename ($3.t);
- $$.new_type_flag = 0; }
+ $$.new_type_flag = 0; $$.lookups = NULL_TREE; }
| SIGOF '(' expr ')'
{ tree type = TREE_TYPE ($3);
- $$.new_type_flag = 0;
+ $$.new_type_flag = 0; $$.lookups = NULL_TREE;
if (IS_AGGR_TYPE (type))
{
sorry ("sigof type specifier");
| SIGOF '(' type_id ')'
{ tree type = groktypename ($3.t);
- $$.new_type_flag = 0;
+ $$.new_type_flag = 0; $$.lookups = NULL_TREE;
if (IS_AGGR_TYPE (type))
{
sorry ("sigof type specifier");
initdcl:
declarator maybeasm maybe_attribute '='
- { $<ttype>$ = start_decl ($<ttype>1, current_declspecs, 1,
- $3, prefix_attributes); }
+ { $<ttype>$ = parse_decl ($<ttype>1, $3, 1); }
init
/* Note how the declaration of the variable is in effect while its init is parsed! */
- { cp_finish_decl ($<ttype>5, $6, $2, 1, LOOKUP_ONLYCONVERTING); }
+ { parse_end_decl ($<ttype>5, $6, $2); }
| declarator maybeasm maybe_attribute
- { $<ttype>$ = start_decl ($<ttype>1, current_declspecs, 0,
- $3, prefix_attributes);
- cp_finish_decl ($<ttype>$, NULL_TREE, $2, 1, 0); }
+ {
+ $<ttype>$ = parse_decl ($<ttype>1, $3, 0);
+ parse_end_decl ($<ttype>$, NULL_TREE, $2);
+ }
;
/* This rule assumes a certain configuration of the parser stack.
we need that reduce so we prefer fn.def1 when appropriate. */
initdcl0_innards:
maybe_attribute '='
- { $<itype>2 = parse_decl ($<ttype>-1, $<ttype>-2,
- $1, 1, &$<ttype>$); }
+ { $<ttype>$ = parse_decl0 ($<ttype>-1, $<ftype>-2.t,
+ $<ftype>-2.lookups, $1, 1); }
/* Note how the declaration of the variable is in effect
while its init is parsed! */
init
- { cp_finish_decl ($<ttype>3, $4, $<ttype>0, 1,
- LOOKUP_ONLYCONVERTING);
- $$ = $<itype>2; }
+ { parse_end_decl ($<ttype>3, $4, $<ttype>0); }
| maybe_attribute
- { tree d;
- $$ = parse_decl ($<ttype>-1, $<ttype>-2, $1, 0, &d);
- cp_finish_decl (d, NULL_TREE, $<ttype>0, 1, 0); }
+ { tree d = parse_decl0 ($<ttype>-1, $<ftype>-2.t,
+ $<ftype>-2.lookups, $1, 0);
+ parse_end_decl (d, NULL_TREE, $<ttype>0); }
;
initdcl0:
declarator maybeasm initdcl0_innards
- { $$ = $3; }
-
+ {}
+ ;
+
notype_initdcl0:
notype_declarator maybeasm initdcl0_innards
- { $$ = $3; }
+ {}
;
nomods_initdcl0:
initdcl0_innards
{}
| constructor_declarator maybeasm maybe_attribute
- { tree d;
- parse_decl($1, NULL_TREE, $3, 0, &d);
- cp_finish_decl (d, NULL_TREE, $2, 1, 0); }
+ { tree d = parse_decl0 ($1, NULL_TREE, NULL_TREE, $3, 0);
+ parse_end_decl (d, NULL_TREE, $2); }
;
/* the * rules are dummies to accept the Apollo extended syntax
init
{ $$ = build_tree_list (NULL_TREE, $$); }
| initlist ',' init
- { $$ = expr_tree_cons (NULL_TREE, $3, $$); }
+ { $$ = tree_cons (NULL_TREE, $3, $$); }
/* These are for labeled elements. */
| '[' expr_no_commas ']' init
- { $$ = build_expr_list ($2, $4); }
+ { $$ = build_tree_list ($2, $4); }
| identifier ':' init
- { $$ = build_expr_list ($$, $3); }
+ { $$ = build_tree_list ($$, $3); }
| initlist ',' identifier ':' init
- { $$ = expr_tree_cons ($3, $5, $$); }
+ { $$ = tree_cons ($3, $5, $$); }
;
fn.defpen:
PRE_PARSED_FUNCTION_DECL
- { start_function (NULL_TREE, TREE_VALUE ($1),
- NULL_TREE, 2);
+ { start_function (NULL_TREE, $1->fndecl, NULL_TREE,
+ (SF_DEFAULT | SF_PRE_PARSED
+ | SF_INCLASS_INLINE));
reinit_parse_for_function (); }
pending_inline:
fn.defpen maybe_return_init ctor_initializer_opt compstmt_or_error
{
- int nested = (hack_decl_function_context
- (current_function_decl) != NULL_TREE);
- finish_function (lineno, (int)$3 | 2, nested);
+ expand_body (finish_function (lineno, (int)$3 | 2));
process_next_inline ($1);
}
| fn.defpen maybe_return_init function_try_block
{
- int nested = (hack_decl_function_context
- (current_function_decl) != NULL_TREE);
- finish_function (lineno, (int)$3 | 2, nested);
+ expand_body (finish_function (lineno, (int)$3 | 2));
process_next_inline ($1);
}
| fn.defpen maybe_return_init error
- { process_next_inline ($1); }
+ {
+ finish_function (lineno, 2);
+ process_next_inline ($1); }
;
pending_inlines:
structsp:
ENUM identifier '{'
- { $<itype>3 = suspend_momentary ();
- $<ttype>$ = current_enum_type;
+ { $<ttype>$ = current_enum_type;
current_enum_type = start_enum ($2); }
enumlist_opt '}'
- { TYPE_VALUES (current_enum_type) = $5;
- $$.t = finish_enum (current_enum_type);
+ { $$.t = finish_enum (current_enum_type);
$$.new_type_flag = 1;
current_enum_type = $<ttype>4;
- resume_momentary ((int) $<itype>3);
check_for_missing_semicolon ($$.t); }
| ENUM '{'
- { $<itype>2 = suspend_momentary ();
- $<ttype>$ = current_enum_type;
+ { $<ttype>$ = current_enum_type;
current_enum_type = start_enum (make_anon_name ()); }
enumlist_opt '}'
- { TYPE_VALUES (current_enum_type) = $4;
- $$.t = finish_enum (current_enum_type);
+ { $$.t = finish_enum (current_enum_type);
$$.new_type_flag = 1;
current_enum_type = $<ttype>3;
- resume_momentary ((int) $<itype>1);
check_for_missing_semicolon ($$.t); }
| ENUM identifier
{ $$.t = xref_tag (enum_type_node, $2, 1);
else
{
$$.t = $1.t;
- /* struct B: public A; is not accepted by the WP grammar. */
- if (TYPE_BINFO_BASETYPES ($$.t) && !TYPE_SIZE ($$.t)
+ /* struct B: public A; is not accepted by the standard grammar. */
+ if (CLASS_TYPE_P ($$.t)
+ && TYPE_BINFO_BASETYPES ($$.t)
+ && !COMPLETE_TYPE_P ($$.t)
&& ! TYPE_BEING_DEFINED ($$.t))
cp_error ("base clause without member specification for `%#T'",
$$.t);
base_class.1:
typename_sub
- { if ($$ != error_mark_node) $$ = TYPE_MAIN_DECL ($1); }
+ { if ($$ == error_mark_node)
+ ;
+ else if (!TYPE_P ($$))
+ $$ = error_mark_node;
+ else
+ $$ = TYPE_MAIN_DECL ($1); }
| nonnested_type
;
| declmods notype_components
{
if (!$2)
- grok_x_components ($1);
+ grok_x_components ($1.t);
$$ = NULL_TREE;
}
| notype_declarator maybeasm maybe_attribute maybe_init
parmlist? */
| declmods component_constructor_declarator maybeasm maybe_attribute maybe_init
{ tree specs, attrs;
- split_specs_attrs ($1, &specs, &attrs);
+ split_specs_attrs ($1.t, &specs, &attrs);
$$ = grokfield ($2, specs, $5, $3,
build_tree_list ($4, attrs)); }
| component_constructor_declarator maybeasm maybe_attribute maybe_init
after_type_component_declarator0:
after_type_declarator maybeasm maybe_attribute maybe_init
- { split_specs_attrs ($<ttype>0, ¤t_declspecs,
- &prefix_attributes);
- $<ttype>0 = current_declspecs;
- $$ = grokfield ($$, current_declspecs, $4, $2,
- build_tree_list ($3, prefix_attributes)); }
+ { $$ = parse_field0 ($1, $<ftype>0.t, $<ftype>0.lookups,
+ $3, $2, $4); }
| TYPENAME ':' expr_no_commas maybe_attribute
- { split_specs_attrs ($<ttype>0, ¤t_declspecs,
- &prefix_attributes);
- $<ttype>0 = current_declspecs;
- $$ = grokbitfield ($$, current_declspecs, $3);
- cplus_decl_attributes ($$, $4, prefix_attributes); }
+ { $$ = parse_bitfield0 ($1, $<ftype>0.t, $<ftype>0.lookups,
+ $4, $3); }
;
notype_component_declarator0:
notype_declarator maybeasm maybe_attribute maybe_init
- { split_specs_attrs ($<ttype>0, ¤t_declspecs,
- &prefix_attributes);
- $<ttype>0 = current_declspecs;
- $$ = grokfield ($$, current_declspecs, $4, $2,
- build_tree_list ($3, prefix_attributes)); }
+ { $$ = parse_field0 ($1, $<ftype>0.t, $<ftype>0.lookups,
+ $3, $2, $4); }
| constructor_declarator maybeasm maybe_attribute maybe_init
- { split_specs_attrs ($<ttype>0, ¤t_declspecs,
- &prefix_attributes);
- $<ttype>0 = current_declspecs;
- $$ = grokfield ($$, current_declspecs, $4, $2,
- build_tree_list ($3, prefix_attributes)); }
+ { $$ = parse_field0 ($1, $<ftype>0.t, $<ftype>0.lookups,
+ $3, $2, $4); }
| IDENTIFIER ':' expr_no_commas maybe_attribute
- { split_specs_attrs ($<ttype>0, ¤t_declspecs,
- &prefix_attributes);
- $<ttype>0 = current_declspecs;
- $$ = grokbitfield ($$, current_declspecs, $3);
- cplus_decl_attributes ($$, $4, prefix_attributes); }
+ { $$ = parse_bitfield0 ($1, $<ftype>0.t, $<ftype>0.lookups,
+ $4, $3); }
| ':' expr_no_commas maybe_attribute
- { split_specs_attrs ($<ttype>0, ¤t_declspecs,
- &prefix_attributes);
- $<ttype>0 = current_declspecs;
- $$ = grokbitfield (NULL_TREE, current_declspecs, $2);
- cplus_decl_attributes ($$, $3, prefix_attributes); }
+ { $$ = parse_bitfield0 (NULL_TREE, $<ftype>0.t,
+ $<ftype>0.lookups, $3, $2); }
;
after_type_component_declarator:
after_type_declarator maybeasm maybe_attribute maybe_init
- { $$ = grokfield ($$, current_declspecs, $4, $2,
- build_tree_list ($3, prefix_attributes)); }
+ { $$ = parse_field ($1, $3, $2, $4); }
| TYPENAME ':' expr_no_commas maybe_attribute
- { $$ = grokbitfield ($$, current_declspecs, $3);
- cplus_decl_attributes ($$, $4, prefix_attributes); }
+ { $$ = parse_bitfield ($1, $4, $3); }
;
notype_component_declarator:
notype_declarator maybeasm maybe_attribute maybe_init
- { $$ = grokfield ($$, current_declspecs, $4, $2,
- build_tree_list ($3, prefix_attributes)); }
+ { $$ = parse_field ($1, $3, $2, $4); }
| IDENTIFIER ':' expr_no_commas maybe_attribute
- { $$ = grokbitfield ($$, current_declspecs, $3);
- cplus_decl_attributes ($$, $4, prefix_attributes); }
+ { $$ = parse_bitfield ($1, $4, $3); }
| ':' expr_no_commas maybe_attribute
- { $$ = grokbitfield (NULL_TREE, current_declspecs, $2);
- cplus_decl_attributes ($$, $3, prefix_attributes); }
+ { $$ = parse_bitfield (NULL_TREE, $3, $2); }
;
enumlist_opt:
enumlist maybecomma_warn
| maybecomma_warn
- { $$ = NULL_TREE; }
;
/* We chain the enumerators in reverse order.
enumlist:
enumerator
| enumlist ',' enumerator
- { TREE_CHAIN ($3) = $$; $$ = $3; }
;
enumerator:
identifier
- { $$ = build_enumerator ($$, NULL_TREE, current_enum_type); }
+ { build_enumerator ($1, NULL_TREE, current_enum_type); }
| identifier '=' expr_no_commas
- { $$ = build_enumerator ($$, $3, current_enum_type); }
+ { build_enumerator ($1, $3, current_enum_type); }
;
-/* ANSI new-type-id (5.3.4) */
+/* ISO new-type-id (5.3.4) */
new_type_id:
type_specifier_seq new_declarator
{ $$.t = build_decl_list ($1.t, $2);
{ $$.t = build_decl_list ($1.t, NULL_TREE);
$$.new_type_flag = $1.new_type_flag; }
/* GNU extension to allow arrays of arbitrary types with
- non-constant dimension. For the use of begin_new_placement
- here, see the comments in unary_expr above. */
- | '(' .begin_new_placement type_id .finish_new_placement
- '[' expr ']'
+ non-constant dimension. */
+ | '(' type_id ')' '[' expr ']'
{
if (pedantic)
- pedwarn ("ANSI C++ forbids array dimensions with parenthesized type in new");
- $$.t = build_parse_node (ARRAY_REF, TREE_VALUE ($3.t), $6);
- $$.t = build_decl_list (TREE_PURPOSE ($3.t), $$.t);
- $$.new_type_flag = $3.new_type_flag;
+ pedwarn ("ISO C++ forbids array dimensions with parenthesized type in new");
+ $$.t = build_parse_node (ARRAY_REF, TREE_VALUE ($2.t), $5);
+ $$.t = build_decl_list (TREE_PURPOSE ($2.t), $$.t);
+ $$.new_type_flag = $2.new_type_flag;
}
;
/* These rules must follow the rules for function declarations
and component declarations. That way, longer rules are preferred. */
-suspend_mom:
- /* empty */
- { $<itype>$ = suspend_momentary (); }
-
-/* An expression which will not live on the momentary obstack. */
-nonmomentary_expr:
- suspend_mom expr
- { resume_momentary ((int) $<itype>1); $$ = $2; }
- ;
-
/* An expression which will not live on the momentary obstack. */
maybe_parmlist:
- suspend_mom '(' nonnull_exprlist ')'
- { resume_momentary ((int) $<itype>1); $$ = $3; }
- | suspend_mom '(' parmlist ')'
- { resume_momentary ((int) $<itype>1); $$ = $3; }
- | suspend_mom LEFT_RIGHT
- { resume_momentary ((int) $<itype>1); $$ = empty_parms (); }
- | suspend_mom '(' error ')'
- { resume_momentary ((int) $<itype>1); $$ = NULL_TREE; }
+ '(' nonnull_exprlist ')'
+ { $$ = $2; }
+ | '(' parmlist ')'
+ { $$ = $2; }
+ | LEFT_RIGHT
+ { $$ = empty_parms (); }
+ | '(' error ')'
+ { $$ = NULL_TREE; }
;
/* A declarator that is allowed only after an explicit typespec. */
direct_after_type_declarator:
direct_after_type_declarator maybe_parmlist cv_qualifiers exception_specification_opt %prec '.'
{ $$ = make_call_declarator ($$, $2, $3, $4); }
- | direct_after_type_declarator '[' nonmomentary_expr ']'
+ | direct_after_type_declarator '[' expr ']'
{ $$ = build_parse_node (ARRAY_REF, $$, $3); }
| direct_after_type_declarator '[' ']'
{ $$ = build_parse_node (ARRAY_REF, $$, NULL_TREE); }
{ $$ = make_call_declarator ($$, $2, $3, $4); }
| '(' complex_notype_declarator ')'
{ $$ = $2; }
- | direct_notype_declarator '[' nonmomentary_expr ']'
+ | direct_notype_declarator '[' expr ']'
{ $$ = build_parse_node (ARRAY_REF, $$, $3); }
| direct_notype_declarator '[' ']'
{ $$ = build_parse_node (ARRAY_REF, $$, NULL_TREE); }
| typespec fcast_or_absdcl %prec EMPTY
{ $$ = reparse_absdcl_as_expr ($1.t, $2); }
;
+
type_name:
TYPENAME
| SELFNAME
| nested_name_specifier nested_name_specifier_1
{ $$ = $2; }
| nested_name_specifier TEMPLATE explicit_template_type SCOPE
- { got_scope = $$ = make_typename_type ($1, $3); }
+ { got_scope = $$
+ = make_typename_type ($1, $3, /*complain=*/1); }
;
/* Why the @#$%^& do type_name and notype_identifier need to be expanded
typename_sub0:
typename_sub1 identifier %prec EMPTY
{
- if (TREE_CODE_CLASS (TREE_CODE ($1)) == 't')
- $$ = make_typename_type ($1, $2);
+ if (TYPE_P ($1))
+ $$ = make_typename_type ($1, $2, /*complain=*/1);
else if (TREE_CODE ($2) == IDENTIFIER_NODE)
cp_error ("`%T' is not a class or namespace", $2);
else
| typename_sub1 template_type %prec EMPTY
{ $$ = TREE_TYPE ($2); }
| typename_sub1 explicit_template_type %prec EMPTY
- { $$ = make_typename_type ($1, $2); }
+ { $$ = make_typename_type ($1, $2, /*complain=*/1); }
| typename_sub1 TEMPLATE explicit_template_type %prec EMPTY
- { $$ = make_typename_type ($1, $3); }
+ { $$ = make_typename_type ($1, $3, /*complain=*/1); }
;
typename_sub1:
}
| typename_sub1 typename_sub2
{
- if (TREE_CODE_CLASS (TREE_CODE ($1)) == 't')
- $$ = make_typename_type ($1, $2);
+ if (TYPE_P ($1))
+ $$ = make_typename_type ($1, $2, /*complain=*/1);
else if (TREE_CODE ($2) == IDENTIFIER_NODE)
cp_error ("`%T' is not a class or namespace", $2);
else
}
}
| typename_sub1 explicit_template_type SCOPE
- { got_scope = $$ = make_typename_type ($1, $2); }
+ { got_scope = $$
+ = make_typename_type ($1, $2, /*complain=*/1); }
| typename_sub1 TEMPLATE explicit_template_type SCOPE
- { got_scope = $$ = make_typename_type ($1, $3); }
+ { got_scope = $$
+ = make_typename_type ($1, $3, /*complain=*/1); }
;
typename_sub2:
{ got_scope = void_type_node; }
;
-/* ANSI new-declarator (5.3.4) */
+/* ISO new-declarator (5.3.4) */
new_declarator:
'*' cv_qualifiers new_declarator
{ $$ = make_pointer_declarator ($2, $3); }
| direct_new_declarator %prec EMPTY
;
-/* ANSI direct-new-declarator (5.3.4) */
+/* ISO direct-new-declarator (5.3.4) */
direct_new_declarator:
'[' expr ']'
{ $$ = build_parse_node (ARRAY_REF, NULL_TREE, $2); }
- | direct_new_declarator '[' nonmomentary_expr ']'
+ | direct_new_declarator '[' expr ']'
{ $$ = build_parse_node (ARRAY_REF, $$, $3); }
;
}
;
-/* ANSI abstract-declarator (8.1) */
+/* ISO abstract-declarator (8.1) */
absdcl:
'*' nonempty_cv_qualifiers absdcl_intern
{ $$ = make_pointer_declarator ($2.t, $3); }
| direct_abstract_declarator %prec EMPTY
;
-/* ANSI direct-abstract-declarator (8.1) */
+/* ISO direct-abstract-declarator (8.1) */
direct_abstract_declarator:
'(' absdcl_intern ')'
{ $$ = $2; }
{ $$ = make_call_declarator ($$, $3, $5, $6); }
| direct_abstract_declarator LEFT_RIGHT cv_qualifiers exception_specification_opt %prec '.'
{ $$ = make_call_declarator ($$, empty_parms (), $3, $4); }
- | direct_abstract_declarator '[' nonmomentary_expr ']' %prec '.'
+ | direct_abstract_declarator '[' expr ']' %prec '.'
{ $$ = build_parse_node (ARRAY_REF, $$, $3); }
| direct_abstract_declarator '[' ']' %prec '.'
{ $$ = build_parse_node (ARRAY_REF, $$, NULL_TREE); }
{ set_quals_and_spec ($$, $2, $3); }
| fcast_or_absdcl cv_qualifiers exception_specification_opt %prec '.'
{ set_quals_and_spec ($$, $2, $3); }
- | '[' nonmomentary_expr ']' %prec '.'
+ | '[' expr ']' %prec '.'
{ $$ = build_parse_node (ARRAY_REF, NULL_TREE, $2); }
| '[' ']' %prec '.'
{ $$ = build_parse_node (ARRAY_REF, NULL_TREE, NULL_TREE); }
/* empty */
| label_decls
{ if (pedantic)
- pedwarn ("ANSI C++ forbids label declarations"); }
+ pedwarn ("ISO C++ forbids label declarations"); }
;
label_decls:
already_scoped_stmt
{ finish_for_stmt ($9, $<ttype>2); }
| SWITCH
- { begin_switch_stmt (); }
+ { $<ttype>$ = begin_switch_stmt (); }
'(' condition ')'
- { $<ttype>$ = finish_switch_cond ($4); }
+ { finish_switch_cond ($4, $<ttype>2); }
implicitly_scoped_stmt
- { finish_switch_stmt ($4, $<ttype>6); }
+ { finish_switch_stmt ($4, $<ttype>2); }
| CASE expr_no_commas ':'
{ finish_case_label ($2, NULL_TREE); }
stmt
/* This is the case with input operands as well. */
| asm_keyword maybe_cv_qualifier '(' string ':' asm_operands ':' asm_operands ')' ';'
{ finish_asm_stmt ($2, $4, $6, $8, NULL_TREE); }
+ | asm_keyword maybe_cv_qualifier '(' string SCOPE asm_operands ')' ';'
+ { finish_asm_stmt ($2, $4, NULL_TREE, $6, NULL_TREE); }
/* This is the case with clobbered registers as well. */
| asm_keyword maybe_cv_qualifier '(' string ':' asm_operands ':'
asm_operands ':' asm_clobbers ')' ';'
{ finish_asm_stmt ($2, $4, $6, $8, $10); }
+ | asm_keyword maybe_cv_qualifier '(' string SCOPE asm_operands ':'
+ asm_clobbers ')' ';'
+ { finish_asm_stmt ($2, $4, NULL_TREE, $6, $8); }
+ | asm_keyword maybe_cv_qualifier '(' string ':' asm_operands SCOPE
+ asm_clobbers ')' ';'
+ { finish_asm_stmt ($2, $4, $6, NULL_TREE, $8); }
| GOTO '*' expr ';'
{
if (pedantic)
- pedwarn ("ANSI C++ forbids computed gotos");
+ pedwarn ("ISO C++ forbids computed gotos");
finish_goto_stmt ($3);
}
| GOTO identifier ';'
{ finish_goto_stmt ($2); }
| label_colon stmt
- { finish_stmt (); }
| label_colon '}'
{ error ("label must be followed by statement");
- yyungetc ('}', 0);
- finish_stmt (); }
+ yyungetc ('}', 0); }
| ';'
{ finish_stmt (); }
| try_block
CATCH
{ $<ttype>$ = begin_handler(); }
handler_args
- { finish_handler_parms ($<ttype>2); }
+ { $<ttype>$ = finish_handler_parms ($3, $<ttype>2); }
compstmt
- { finish_handler ($<ttype>2); }
+ { finish_handler ($<ttype>4, $<ttype>2); }
;
type_specifier_seq:
handler_args:
'(' ELLIPSIS ')'
- { expand_start_catch_block (NULL_TREE); }
+ { $$ = NULL_TREE; }
/* This doesn't allow reference parameters, the below does.
| '(' type_specifier_seq absdcl ')'
{ check_for_new_type ("inside exception declarations", $2);
| '(' parm ')'
{
check_for_new_type ("inside exception declarations", $2);
- start_handler_parms (TREE_PURPOSE ($2.t),
- TREE_VALUE ($2.t));
+ $$ = start_handler_parms (TREE_PURPOSE ($2.t),
+ TREE_VALUE ($2.t));
}
;
| decl
| '{' compstmtend
{ if (pedantic)
- pedwarn ("ANSI C++ forbids compound statements inside for initializations");
+ pedwarn ("ISO C++ forbids compound statements inside for initializations");
}
;
maybe_cv_qualifier:
/* empty */
- { emit_line_note (input_filename, lineno);
- $$ = NULL_TREE; }
+ { $$ = NULL_TREE; }
| CV_QUALIFIER
- { emit_line_note (input_filename, lineno); }
;
xexpr:
$$.t = build_tree_list (specs, NULL_TREE);
$$.new_type_flag = $1.new_type_flag; }
| declmods notype_declarator
- { tree specs = strip_attrs ($1);
+ { tree specs = strip_attrs ($1.t);
$$.t = build_tree_list (specs, $2);
$$.new_type_flag = 0; }
;