home *** CD-ROM | disk | FTP | other *** search
/ Fresh Fish 7 / FreshFishVol7.bin / bbs / gnu / gcc-2.3.3-src.lha / GNU / src / amiga / gcc-2.3.3 / cp-parse.y < prev    next >
Text File  |  1994-02-06  |  115KB  |  3,952 lines

  1. /* YACC parser for C++ syntax.
  2.    Copyright (C) 1988, 1989 Free Software Foundation, Inc.
  3.    Hacked by Michael Tiemann (tiemann@cygnus.com)
  4.  
  5. This file is part of GNU CC.
  6.  
  7. GNU CC is free software; you can redistribute it and/or modify
  8. it under the terms of the GNU General Public License as published by
  9. the Free Software Foundation; either version 2, or (at your option)
  10. any later version.
  11.  
  12. GNU CC is distributed in the hope that it will be useful,
  13. but WITHOUT ANY WARRANTY; without even the implied warranty of
  14. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  15. GNU General Public License for more details.
  16.  
  17. You should have received a copy of the GNU General Public License
  18. along with GNU CC; see the file COPYING.  If not, write to
  19. the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
  20.  
  21.  
  22. /* This grammar is based on the GNU CC grammar.  */
  23.  
  24. /* Note: Bison automatically applies a default action of "$$ = $1" for
  25.    all derivations; this is applied before the explicit action, if one
  26.    is given.  Keep this in mind when reading the actions.  */
  27.  
  28. /* Also note: this version contains experimental exception
  29.    handling features.  They could break, change, disappear,
  30.    or otherwise exhibit volatile behavior.  Don't depend on
  31.    me (Michael Tiemann) to protect you from any negative impact
  32.    this may have on your professional, personal, or spiritual life.
  33.  
  34.    NEWS FLASH:  This version now supports the exception handling
  35.    syntax of Stroustrup's 2nd edition, if -fansi-exceptions is given.
  36.    THIS IS WORK IN PROGRESS!!!  The type of the 'throw' and the
  37.    'catch' much match EXACTLY (no inheritance support or coercions).
  38.    Also, throw-specifications of functions don't work.
  39.    Destructors aren't called correctly.  Etc, etc.  --Per Bothner.
  40.   */
  41.  
  42. %{
  43. #if defined(GATHER_STATISTICS) || defined(SPEW_DEBUG)
  44. #undef YYDEBUG
  45. #define YYDEBUG 1
  46. #endif
  47.  
  48. #include "config.h"
  49.  
  50. #include <stdio.h>
  51. #include <errno.h>
  52.  
  53. #include "tree.h"
  54. #include "input.h"
  55. #include "flags.h"
  56. #include "cp-lex.h"
  57. #include "cp-tree.h"
  58.  
  59. extern tree void_list_node;
  60. extern struct obstack permanent_obstack;
  61.  
  62. #ifndef errno
  63. extern int errno;
  64. #endif
  65.  
  66. extern int end_of_file;
  67.  
  68. void yyerror ();
  69.  
  70. /* Like YYERROR but do call yyerror.  */
  71. #define YYERROR1 { yyerror ("syntax error"); YYERROR; }
  72.  
  73. static void position_after_white_space ();
  74.  
  75. /* Contains error message to give if user tries to declare
  76.    a variable where one does not belong.  */
  77. static char *stmt_decl_msg = 0;
  78.  
  79. /* Nonzero if we have an `extern "C"' acting as an extern specifier.  */
  80. int have_extern_spec;
  81. int used_extern_spec;
  82.  
  83. void yyhook ();
  84.  
  85. /* Cons up an empty parameter list.  */
  86. #ifdef __GNUC__
  87. __inline
  88. #endif
  89. static tree
  90. empty_parms ()
  91. {
  92.   tree parms;
  93.  
  94.   if (strict_prototype)
  95.     parms = void_list_node;
  96.   else
  97.     parms = NULL_TREE;
  98.   return parms;
  99. }
  100. %}
  101.  
  102. %start program
  103.  
  104. %union {long itype; tree ttype; char *strtype; enum tree_code code; }
  105.  
  106. /* All identifiers that are not reserved words
  107.    and are not declared typedefs in the current block */
  108. %token IDENTIFIER
  109.  
  110. /* All identifiers that are declared typedefs in the current block.
  111.    In some contexts, they are treated just like IDENTIFIER,
  112.    but they can also serve as typespecs in declarations.  */
  113. %token TYPENAME
  114.  
  115. /* Qualified identifiers that end in a TYPENAME.  */
  116. %token SCOPED_TYPENAME
  117.  
  118. /* Reserved words that specify storage class.
  119.    yylval contains an IDENTIFIER_NODE which indicates which one.  */
  120. %token SCSPEC
  121.  
  122. /* Reserved words that specify type.
  123.    yylval contains an IDENTIFIER_NODE which indicates which one.  */
  124. %token TYPESPEC
  125.  
  126. /* Reserved words that qualify type: "const" or "volatile".
  127.    yylval contains an IDENTIFIER_NODE which indicates which one.  */
  128. %token TYPE_QUAL
  129.  
  130. /* Character or numeric constants.
  131.    yylval is the node for the constant.  */
  132. %token CONSTANT
  133.  
  134. /* String constants in raw form.
  135.    yylval is a STRING_CST node.  */
  136. %token STRING
  137.  
  138. /* "...", used for functions with variable arglists.  */
  139. %token ELLIPSIS
  140.  
  141. /* the reserved words */
  142. /* SCO include files test "ASM", so use something else. */
  143. %token SIZEOF ENUM /* STRUCT UNION */ IF ELSE WHILE DO FOR SWITCH CASE DEFAULT
  144. %token BREAK CONTINUE RETURN GOTO ASM_KEYWORD TYPEOF ALIGNOF HEADOF CLASSOF
  145. %token ATTRIBUTE EXTENSION LABEL
  146.  
  147. /* the reserved words... C++ extensions */
  148. %token <ttype> AGGR
  149. %token <itype> VISSPEC
  150. %token DELETE NEW OVERLOAD THIS OPERATOR
  151. %token DYNAMIC POINTSAT_LEFT_RIGHT LEFT_RIGHT TEMPLATE
  152. %token <itype> SCOPE
  153.  
  154. /* Special token created by the lexer to separate TYPENAME
  155.    from an ABSDCL.  This allows us to parse `foo (*pf)()'.  */
  156.  
  157. %token START_DECLARATOR
  158.  
  159. /* Define the operator tokens and their precedences.
  160.    The value is an integer because, if used, it is the tree code
  161.    to use in the expression made from the operator.  */
  162.  
  163. %left EMPTY            /* used to resolve s/r with epsilon */
  164.  
  165. /* Add precedence rules to solve dangling else s/r conflict */
  166. %nonassoc IF
  167. %nonassoc ELSE
  168.  
  169. %left IDENTIFIER TYPENAME TYPENAME_COLON SCSPEC TYPESPEC TYPE_QUAL ENUM AGGR
  170.  
  171. %left '{' ','
  172.  
  173. %right <code> ASSIGN '='
  174. %right <code> '?' ':' RANGE
  175. %left <code> OROR
  176. %left <code> ANDAND
  177. %left <code> '|'
  178. %left <code> '^'
  179. %left <code> '&'
  180. %left <code> MIN_MAX
  181. %left <code> EQCOMPARE
  182. %left <code> ARITHCOMPARE '<' '>'
  183. %left <code> LSHIFT RSHIFT
  184. %left <code> '+' '-'
  185. %left <code> '*' '/' '%'
  186. %right <code> UNARY PLUSPLUS MINUSMINUS
  187. %left HYPERUNARY
  188. %left <ttype> PAREN_STAR_PAREN LEFT_RIGHT
  189. %left <code> POINTSAT POINTSAT_STAR '.' DOT_STAR '(' '['
  190.  
  191. %right SCOPE            /* C++ extension */
  192. %nonassoc NEW DELETE RAISE RAISES RERAISE TRY EXCEPT CATCH THROW
  193. %nonassoc ANSI_TRY ANSI_THROW
  194. %right DYNAMIC
  195.  
  196. %type <code> unop
  197.  
  198. %type <ttype> identifier IDENTIFIER TYPENAME CONSTANT expr nonnull_exprlist
  199. %type <ttype> optional_identifier
  200. %type <ttype> expr_no_commas cast_expr unary_expr primary string STRING
  201. %type <ttype> typed_declspecs reserved_declspecs
  202. %type <ttype> typed_typespecs reserved_typespecquals
  203. %type <ttype> declmods typespec typespecqual_reserved
  204. %type <ttype> SCSPEC TYPESPEC TYPE_QUAL nonempty_type_quals maybe_type_qual
  205. %type <itype> initdecls notype_initdecls initdcl    /* C++ modification */
  206. %type <ttype> init initlist maybeasm
  207. %type <ttype> asm_operands nonnull_asm_operands asm_operand asm_clobbers
  208. %type <ttype> maybe_attribute attribute_list attrib
  209. %type <ttype> abs_member_declarator after_type_member_declarator
  210.  
  211. %type <ttype> compstmt except_stmts ansi_except_stmts
  212.  
  213. %type <ttype> declarator notype_declarator after_type_declarator
  214.  
  215. %type <ttype> structsp opt.component_decl_list component_decl_list component_decl components component_declarator
  216. %type <ttype> enumlist enumerator
  217. %type <ttype> typename absdcl absdcl1 type_quals abs_or_notype_decl
  218. %type <ttype> xexpr see_typename parmlist parms parm bad_parm
  219. %type <ttype> identifiers_or_typenames
  220.  
  221. /* C++ extensions */
  222. %type <ttype> typename_scope
  223. %token <ttype> TYPENAME_COLON TYPENAME_ELLIPSIS
  224. %token <ttype> PTYPENAME SCOPED_TYPENAME
  225. %token <ttype> PRE_PARSED_FUNCTION_DECL EXTERN_LANG_STRING ALL
  226. %token <ttype> PRE_PARSED_CLASS_DECL
  227. %type <ttype> fn.def1 /* Not really! */
  228. %type <ttype> fn.def2 return_id
  229. %type <ttype> named_class_head named_class_head_sans_basetype
  230. %type <ttype> unnamed_class_head
  231. %type <ttype> class_head base_class_list
  232. %type <itype> base_class_visibility_list
  233. %type <ttype> base_class maybe_base_class_list base_class.1
  234. %type <ttype> after_type_declarator_no_typename
  235. %type <ttype> maybe_raises raise_identifier raise_identifiers ansi_raise_identifier ansi_raise_identifiers
  236. %type <ttype> component_declarator0 scoped_id scoped_typename scoped_base_class
  237. %type <ttype> forhead.1 identifier_or_opname operator_name
  238. %type <ttype> new delete object object_star aggr
  239. /* %type <ttype> primary_no_id */
  240. %type <ttype> nonmomentary_expr
  241. %type <itype> forhead.2 initdcl0 notype_initdcl0 member_init_list
  242. %type <itype> .scope try ansi_try
  243. %type <ttype> template_header template_parm_list template_parm
  244. %type <ttype> template_type template_arg_list template_arg
  245. %type <ttype> template_instantiation template_type_name tmpl.1 tmpl.2
  246. %type <ttype> template_instantiate_once template_instantiate_some
  247. %type <itype> fn_tmpl_end
  248. /* %type <itype> try_for_typename */
  249.  
  250. /* in order to recognize aggr tags as defining and thus shadowing. */
  251. %token TYPENAME_DEFN IDENTIFIER_DEFN PTYPENAME_DEFN
  252. %type <ttype> named_class_head_sans_basetype_defn 
  253. %type <ttype> identifier_defn IDENTIFIER_DEFN TYPENAME_DEFN PTYPENAME_DEFN
  254.  
  255. %type <strtype> .pushlevel
  256.  
  257. /* cp-spew.c depends on this being the last token.  Define
  258.    any new tokens before this one!  */
  259. %token END_OF_SAVED_INPUT
  260.  
  261. %{
  262. /* List of types and structure classes of the current declaration.  */
  263. static tree current_declspecs;
  264.  
  265. /* When defining an aggregate, this is the most recent one being defined.  */
  266. static tree current_aggr;
  267.  
  268. /* 1 if we explained undeclared var errors.  */
  269. int undeclared_variable_notice;
  270.  
  271. /* Tell yyparse how to print a token's value, if yydebug is set.  */
  272.  
  273. #define YYPRINT(FILE,YYCHAR,YYLVAL) yyprint(FILE,YYCHAR,YYLVAL)
  274. extern void yyprint ();
  275. %}
  276.  
  277. %%
  278. program: /* empty */
  279.     | extdefs
  280.         { finish_file (); }
  281.     ;
  282.  
  283. /* the reason for the strange actions in this rule
  284.  is so that notype_initdecls when reached via datadef
  285.  can find a valid list of type and sc specs in $0. */
  286.  
  287. extdefs:
  288.       { $<ttype>$ = NULL_TREE; } extdef
  289.         {$<ttype>$ = NULL_TREE; }
  290.     | extdefs extdef
  291.         {$<ttype>$ = NULL_TREE; }
  292.     ;
  293.  
  294. .hush_warning:
  295.         { have_extern_spec = 1;
  296.           used_extern_spec = 0;
  297.           $<ttype>$ = NULL_TREE; }
  298.     ;
  299. .warning_ok:
  300.         { have_extern_spec = 0; }
  301.     ;
  302.  
  303. extdef:
  304.       fndef
  305.         { if (pending_inlines) do_pending_inlines (); }
  306.     | datadef
  307.         { if (pending_inlines) do_pending_inlines (); }
  308.     | template_def
  309.         { if (pending_inlines) do_pending_inlines (); }
  310.     | overloaddef
  311.     | ASM_KEYWORD '(' string ')' ';'
  312.         { if (pedantic)
  313.             pedwarn ("ANSI C++ forbids use of `asm' keyword");
  314.           if (TREE_CHAIN ($3)) $3 = combine_strings ($3);
  315.           assemble_asm ($3); }
  316.     | extern_lang_string '{' extdefs '}'
  317.         { pop_lang_context (); }
  318.     | extern_lang_string '{' '}'
  319.         { pop_lang_context (); }
  320.     | extern_lang_string .hush_warning fndef .warning_ok
  321.         { if (pending_inlines) do_pending_inlines ();
  322.           pop_lang_context (); }
  323.     | extern_lang_string .hush_warning datadef .warning_ok
  324.         { if (pending_inlines) do_pending_inlines ();
  325.           pop_lang_context (); }
  326.     ;
  327.  
  328. extern_lang_string:
  329.       EXTERN_LANG_STRING
  330.         { push_lang_context ($1); }
  331.     ;
  332.  
  333. template_header:
  334.       TEMPLATE '<'
  335.         { begin_template_parm_list (); }
  336.       template_parm_list '>'
  337.         { $$ = end_template_parm_list ($4); }
  338.     ;
  339.  
  340. template_parm_list:
  341.       template_parm
  342.         { $$ = process_template_parm (0, $1); }
  343.     | template_parm_list ',' template_parm
  344.         { $$ = process_template_parm ($1, $3); }
  345.     ;
  346.  
  347. template_parm:
  348.     /* The following rules introduce a new reduce/reduce
  349.        conflict: they are valid prefixes for a `structsp',
  350.        which means they could match a nameless parameter.
  351.        By putting them before the `parm' rule, we get
  352.        their match before considering them nameless parameter
  353.        declarations.  */
  354.       aggr identifier
  355.         {
  356.           if ($1 != class_type_node)
  357.             error ("template type parameter must use keyword `class'");
  358.           $$ = build_tree_list ($2, NULL_TREE);
  359.         }
  360.     | aggr identifier_defn ':' base_class.1
  361.         {
  362.           if ($1 != class_type_node)
  363.             error ("template type parameter must use keyword `class'");
  364.           warning ("restricted template type parameters not yet implemented");
  365.           $$ = build_tree_list ($2, $4);
  366.         }
  367.     | aggr TYPENAME_COLON base_class.1
  368.         {
  369.           if ($1 != class_type_node)
  370.             error ("template type parameter must use keyword `class'");
  371.           warning ("restricted template type parameters not yet implemented");
  372.           $$ = build_tree_list ($2, $3);
  373.         }
  374.     | parm
  375.     ;
  376.  
  377. overloaddef:
  378.       OVERLOAD ov_identifiers ';'
  379.  
  380. ov_identifiers: IDENTIFIER
  381.         { declare_overloaded ($1); }
  382.     | ov_identifiers ',' IDENTIFIER
  383.         { declare_overloaded ($3); }
  384.     ;
  385.       
  386. template_def:
  387.     /* Class template declarations go here; they aren't normal class
  388.        declarations, because we can't process the bodies yet.  */
  389.       template_header named_class_head_sans_basetype '{'
  390.         { yychar = '{'; goto template1; }
  391.      ';'
  392.     | template_header named_class_head_sans_basetype_defn '{'
  393.         { yychar = '{'; goto template1; }
  394.      ';'
  395.     | template_header named_class_head_sans_basetype ':'
  396.         { yychar = ':'; goto template1; }
  397.      ';'
  398.     | template_header named_class_head_sans_basetype_defn ':'
  399.         {
  400.           yychar = ':';
  401.         template1:
  402.           if (current_aggr == exception_type_node)
  403.             error ("template type must define an aggregate or union");
  404.           /* Maybe pedantic warning for union?
  405.              How about an enum? :-)  */
  406.           end_template_decl ($1, $2, current_aggr);
  407.           reinit_parse_for_template (yychar, $1, $2);
  408.           yychar = YYEMPTY;
  409.         }
  410.       ';'
  411.     | template_header named_class_head_sans_basetype ';'
  412.         {
  413.           end_template_decl ($1, $2, current_aggr);
  414.           /* declare $2 as template name with $1 parm list */
  415.         }
  416.     | template_header named_class_head_sans_basetype_defn ';'
  417.         {
  418.           end_template_decl ($1, $2, current_aggr);
  419.           /* declare $2 as template name with $1 parm list */
  420.         }
  421.     | template_header /* notype_initdcl0 ';' */
  422.       notype_declarator maybe_raises maybeasm maybe_attribute
  423.       fn_tmpl_end
  424.         {
  425.           tree d;
  426.           int momentary;
  427.           momentary = suspend_momentary ();
  428.           d = start_decl ($2, /*current_declspecs*/0, 0, $3);
  429.           cplus_decl_attributes (d, $5);
  430.           finish_decl (d, NULL_TREE, $4, 0);
  431.           end_template_decl ($1, d, 0);
  432.           if ($6 != ';')
  433.             reinit_parse_for_template ($6, $1, d);
  434.           resume_momentary (momentary);
  435.         }
  436.     | template_header typed_declspecs /*initdcl0*/
  437.       declarator maybe_raises maybeasm maybe_attribute
  438.       fn_tmpl_end
  439.         {
  440.           tree d;
  441.           int momentary;
  442.  
  443.           current_declspecs = $2;
  444.           momentary = suspend_momentary ();
  445.           d = start_decl ($3, current_declspecs, 0, $4);
  446.           cplus_decl_attributes (d, $6);
  447.           finish_decl (d, NULL_TREE, $5, 0);
  448.           end_exception_decls ();
  449.           end_template_decl ($1, d, 0);
  450.           if ($7 != ';')
  451.             {
  452.               reinit_parse_for_template ($7, $1, d);
  453.               yychar = YYEMPTY;
  454.             }
  455.           note_list_got_semicolon ($<ttype>2);
  456.           resume_momentary (momentary);
  457.         }
  458.     | template_header declmods declarator fn_tmpl_end
  459.         {
  460.           tree d = start_decl ($3, $<ttype>2, 0, NULL_TREE);
  461.           finish_decl (d, NULL_TREE, NULL_TREE, 0);
  462.           end_template_decl ($1, d, 0);
  463.           if ($4 != ';')
  464.             reinit_parse_for_template ($4, $1, d);
  465.         }
  466.     /* Try to recover from syntax errors in templates.  */
  467.     | template_header error '}'    { end_template_decl ($1, 0, 0); }
  468.     | template_header error ';'    { end_template_decl ($1, 0, 0); }
  469.     ;
  470.  
  471. fn_tmpl_end: '{'        { $$ = '{'; }
  472.     | ':'            { $$ = ':'; }
  473.     | ';'            { $$ = ';'; }
  474.     | '='            { $$ = '='; }
  475.     | RETURN        { $$ = RETURN; }
  476.     ;
  477.  
  478. datadef:
  479.       notype_initdecls ';'
  480.         { if (pedantic)
  481.             pedwarn ("ANSI C++ forbids data definition with no type or storage class");
  482.             else if (! flag_traditional && ! have_extern_spec)
  483.               warning ("data definition has no type or storage class"); }
  484.     | declmods notype_initdecls ';'
  485.         {}
  486.     /* Normal case to make fast: "int i;".  */
  487.     | declmods declarator ';'
  488.         { tree d;
  489.           d = start_decl ($2, $<ttype>$, 0, NULL_TREE);
  490.           finish_decl (d, NULL_TREE, NULL_TREE, 0);
  491.         }
  492.     | typed_declspecs initdecls ';'
  493.         {
  494.           end_exception_decls ();
  495.           note_list_got_semicolon ($<ttype>$);
  496.         }
  497.     /* Normal case: make this fast.  */
  498.     | typed_declspecs declarator ';'
  499.         { tree d;
  500.           d = start_decl ($2, $<ttype>$, 0, NULL_TREE);
  501.           finish_decl (d, NULL_TREE, NULL_TREE, 0);
  502.           end_exception_decls ();
  503.           note_list_got_semicolon ($<ttype>$);
  504.         }
  505.         | declmods ';'
  506.       { pedwarn ("empty declaration"); }
  507.     | typed_declspecs ';'
  508.       {
  509.         tree t = $<ttype>$;
  510.         shadow_tag (t);
  511.         if (TREE_CODE (t) == TREE_LIST
  512.         && TREE_PURPOSE (t) == NULL_TREE)
  513.           {
  514.         t = TREE_VALUE (t);
  515.         if (TREE_CODE (t) == RECORD_TYPE)
  516.           {
  517.             if (CLASSTYPE_USE_TEMPLATE (t) == 0)
  518.               CLASSTYPE_USE_TEMPLATE (t) = 2;
  519.             else if (CLASSTYPE_USE_TEMPLATE (t) == 1)
  520.               error ("override declaration for already-expanded template");
  521.           }
  522.           }
  523.         note_list_got_semicolon ($<ttype>$);
  524.       }
  525.     | error ';'
  526.     | error '}'
  527.     | ';'
  528.     ;
  529.  
  530. fndef:
  531.       fn.def1 base_init compstmt_or_error
  532.         {
  533.           finish_function (lineno, 1);
  534.           /* finish_function performs these three statements:
  535.  
  536.              expand_end_bindings (getdecls (), 1, 0);
  537.              poplevel (1, 1, 0);
  538.  
  539.              expand_end_bindings (0, 0, 0);
  540.              poplevel (0, 0, 1);
  541.              */
  542.           if ($<ttype>$) process_next_inline ($<ttype>$);
  543.         }
  544.     | fn.def1 return_init base_init compstmt_or_error
  545.         {
  546.           finish_function (lineno, 1);
  547.           /* finish_function performs these three statements:
  548.  
  549.              expand_end_bindings (getdecls (), 1, 0);
  550.              poplevel (1, 1, 0);
  551.  
  552.              expand_end_bindings (0, 0, 0);
  553.              poplevel (0, 0, 1);
  554.              */
  555.           if ($<ttype>$) process_next_inline ($<ttype>$);
  556.         }
  557.     | fn.def1 nodecls compstmt_or_error
  558.         { finish_function (lineno, 0);
  559.           if ($<ttype>$) process_next_inline ($<ttype>$); }
  560.     | fn.def1 return_init ';' nodecls compstmt_or_error
  561.         { finish_function (lineno, 0);
  562.           if ($<ttype>$) process_next_inline ($<ttype>$); }
  563.     | fn.def1 return_init nodecls compstmt_or_error
  564.         { finish_function (lineno, 0);
  565.           if ($<ttype>$) process_next_inline ($<ttype>$); }
  566.     | typed_declspecs declarator error
  567.         {}
  568.     | declmods notype_declarator error
  569.         {}
  570.     | notype_declarator error
  571.         {}
  572.     ;
  573.  
  574. fn.def1:
  575.       typed_declspecs declarator maybe_raises
  576.         { if (! start_function ($$, $2, $3, 0))
  577.             YYERROR1;
  578.           reinit_parse_for_function ();
  579.           $$ = NULL_TREE; }
  580.     | declmods notype_declarator maybe_raises
  581.         { if (! start_function ($$, $2, $3, 0))
  582.             YYERROR1;
  583.           reinit_parse_for_function ();
  584.           $$ = NULL_TREE; }
  585.     | notype_declarator maybe_raises
  586.         { if (! start_function (NULL_TREE, $$, $2, 0))
  587.             YYERROR1;
  588.           reinit_parse_for_function ();
  589.           $$ = NULL_TREE; }
  590.     | TYPENAME '(' parmlist ')' type_quals maybe_raises
  591.         { if (! start_function (NULL_TREE, build_parse_node (CALL_EXPR, $$, $3, $5), $6, 0))
  592.             YYERROR1;
  593.           reinit_parse_for_function ();
  594.           $$ = NULL_TREE; }
  595.     | scoped_typename '(' parmlist ')' type_quals maybe_raises
  596.         { if (! start_function (NULL_TREE, build_parse_node (CALL_EXPR, $$, $3, $5), $6, 0))
  597.             YYERROR1;
  598.           reinit_parse_for_function ();
  599.           $$ = NULL_TREE; }
  600.     | TYPENAME LEFT_RIGHT type_quals maybe_raises
  601.         { if (! start_function (NULL_TREE, build_parse_node (CALL_EXPR, $$, empty_parms (), $3), $4, 0))
  602.             YYERROR1;
  603.           reinit_parse_for_function ();
  604.           $$ = NULL_TREE; }
  605.     | scoped_typename LEFT_RIGHT type_quals maybe_raises
  606.         { if (! start_function (NULL_TREE, build_parse_node (CALL_EXPR, $$, empty_parms (), $3), $4, 0))
  607.             YYERROR1;
  608.           reinit_parse_for_function ();
  609.           $$ = NULL_TREE; }
  610.     | PRE_PARSED_FUNCTION_DECL
  611.         { start_function (NULL_TREE, TREE_VALUE ($$), NULL_TREE, 1);
  612.           reinit_parse_for_function (); }
  613.     ;
  614.  
  615. /* more C++ complexity */
  616. fn.def2:
  617.       typed_declspecs '(' parmlist ')' type_quals maybe_raises
  618.         {
  619.           tree decl = build_parse_node (CALL_EXPR, TREE_VALUE ($$), $3, $5);
  620.           $$ = start_method (TREE_CHAIN ($$), decl, $6);
  621.           if (! $$)
  622.             YYERROR1;
  623.           if (yychar == YYEMPTY)
  624.             yychar = YYLEX;
  625.           reinit_parse_for_method (yychar, $$); }
  626.     | typed_declspecs LEFT_RIGHT type_quals maybe_raises
  627.         {
  628.           tree decl = build_parse_node (CALL_EXPR, TREE_VALUE ($$), empty_parms (), $3);
  629.           $$ = start_method (TREE_CHAIN ($$), decl, $4);
  630.           if (! $$)
  631.             YYERROR1;
  632.           if (yychar == YYEMPTY)
  633.             yychar = YYLEX;
  634.           reinit_parse_for_method (yychar, $$); }
  635.     | typed_declspecs declarator maybe_raises
  636.         { $$ = start_method ($$, $2, $3);
  637.           if (! $$)
  638.             YYERROR1;
  639.           if (yychar == YYEMPTY)
  640.             yychar = YYLEX;
  641.           reinit_parse_for_method (yychar, $$); }
  642.     | declmods '(' parmlist ')' type_quals maybe_raises
  643.         {
  644.           tree decl = build_parse_node (CALL_EXPR, TREE_VALUE ($$), $3, $5);
  645.           $$ = start_method (TREE_CHAIN ($$), decl, $6);
  646.           if (! $$)
  647.             YYERROR1;
  648.           if (yychar == YYEMPTY)
  649.             yychar = YYLEX;
  650.           reinit_parse_for_method (yychar, $$); }
  651.     | declmods LEFT_RIGHT type_quals maybe_raises
  652.         {
  653.           tree decl = build_parse_node (CALL_EXPR, TREE_VALUE ($$), empty_parms (), $3);
  654.           $$ = start_method (TREE_CHAIN ($$), decl, $4);
  655.           if (! $$)
  656.             YYERROR1;
  657.           if (yychar == YYEMPTY)
  658.             yychar = YYLEX;
  659.           reinit_parse_for_method (yychar, $$); }
  660.     | declmods declarator maybe_raises
  661.         { $$ = start_method ($$, $2, $3);
  662.           if (! $$)
  663.             YYERROR1;
  664.           if (yychar == YYEMPTY)
  665.             yychar = YYLEX;
  666.           reinit_parse_for_method (yychar, $$); }
  667.     | notype_declarator maybe_raises
  668.         { $$ = start_method (NULL_TREE, $$, $2);
  669.           if (! $$)
  670.             YYERROR1;
  671.           if (yychar == YYEMPTY)
  672.             yychar = YYLEX;
  673.           reinit_parse_for_method (yychar, $$); }
  674.     ;
  675.  
  676. return_id: RETURN IDENTIFIER
  677.         {
  678.           if (! current_function_parms_stored)
  679.             store_parm_decls ();
  680.           $$ = $2;
  681.         }
  682.     ;
  683.  
  684. return_init: return_id
  685.         { store_return_init ($<ttype>$, NULL_TREE); }
  686.     | return_id '=' init
  687.         { store_return_init ($<ttype>$, $3); }
  688.     | return_id '(' nonnull_exprlist ')'
  689.         { store_return_init ($<ttype>$, $3); }
  690.     | return_id LEFT_RIGHT
  691.         { store_return_init ($<ttype>$, NULL_TREE); }
  692.     ;
  693.  
  694. base_init:
  695.       ':' .set_base_init member_init_list
  696.         {
  697.           if ($3 == 0)
  698.             error ("no base initializers given following ':'");
  699.           setup_vtbl_ptr ();
  700.         }
  701.     ;
  702.  
  703. .set_base_init:
  704.     /* empty */
  705.         {
  706.           if (! current_function_parms_stored)
  707.             store_parm_decls ();
  708.  
  709.           /* Flag that we are processing base and member initializers.  */
  710.           current_vtable_decl = error_mark_node;
  711.  
  712.           if (DECL_CONSTRUCTOR_P (current_function_decl))
  713.             {
  714.               /* Make a contour for the initializer list.  */
  715.               pushlevel (0);
  716.               clear_last_expr ();
  717.               expand_start_bindings (0);
  718.             }
  719.           else if (current_class_type == NULL_TREE)
  720.             error ("base initializers not allowed for non-member functions");
  721.           else if (! DECL_CONSTRUCTOR_P (current_function_decl))
  722.             error ("only constructors take base initializers");
  723.         }
  724.     ;
  725.  
  726. member_init_list:
  727.       /* empty */
  728.         { $$ = 0; }
  729.     | member_init
  730.         { $$ = 1; }
  731.     | member_init_list ',' member_init
  732.     | member_init_list error
  733.     ;
  734.  
  735. member_init: '(' nonnull_exprlist ')'
  736.         {
  737.           if (current_class_name && !flag_traditional)
  738.             pedwarn ("ANSI C++ forbids old style base class initialization",
  739.                  IDENTIFIER_POINTER (current_class_name));
  740.           expand_member_init (C_C_D, NULL_TREE, $2);
  741.         }
  742.     | LEFT_RIGHT
  743.         {
  744.           if (current_class_name && !flag_traditional)
  745.             pedwarn ("ANSI C++ forbids old style base class initialization",
  746.                  IDENTIFIER_POINTER (current_class_name));
  747.           expand_member_init (C_C_D, NULL_TREE, void_type_node);
  748.         }
  749.     | identifier '(' nonnull_exprlist ')'
  750.         {
  751.           expand_member_init (C_C_D, $<ttype>$, $3);
  752.         }
  753.     | identifier LEFT_RIGHT
  754.         { expand_member_init (C_C_D, $<ttype>$, void_type_node); }
  755.     | template_type_name '(' nonnull_exprlist ')'
  756.         { expand_member_init (C_C_D, $<ttype>$, $3); }
  757.     | template_type_name LEFT_RIGHT
  758.         { expand_member_init (C_C_D, $<ttype>$, void_type_node); }
  759.     | scoped_typename '(' nonnull_exprlist ')'
  760.         { expand_member_init (C_C_D, $<ttype>$, $3); }
  761.     | scoped_typename LEFT_RIGHT
  762.         { expand_member_init (C_C_D, $<ttype>$, void_type_node); }
  763.     | scoped_id identifier '(' nonnull_exprlist ')'
  764.         {
  765.           do_member_init ($<ttype>$, $2, $4);
  766.         }
  767.     | scoped_id identifier LEFT_RIGHT
  768.         {
  769.           do_member_init ($<ttype>$, $2, void_type_node);
  770.         }
  771.     ;
  772.  
  773. identifier:
  774.       IDENTIFIER
  775.     | TYPENAME
  776.     | PTYPENAME
  777.     ;
  778.  
  779. identifier_defn:
  780.       IDENTIFIER_DEFN
  781.     | TYPENAME_DEFN
  782.     | PTYPENAME_DEFN
  783.     ;
  784.  
  785. identifier_or_opname:
  786.       IDENTIFIER
  787.     | TYPENAME
  788.     | PTYPENAME
  789. /*    | '~' TYPENAME
  790.         { $$ = build_parse_node (BIT_NOT_EXPR, $2); }*/
  791.     /* get rid of the next line, replace it with the above */
  792.     | '~' identifier { $$ = build_parse_node (BIT_NOT_EXPR,$2);}
  793.     | operator_name
  794.     ;
  795.  
  796. template_type:
  797.       template_type_name tmpl.1 template_instantiation
  798.         {
  799.             extern tree template_type_seen_before_scope;
  800.  
  801.           if ($3) 
  802.             $$ = $3;
  803.           else if ($$ != error_mark_node)
  804.             $$ = IDENTIFIER_TYPE_VALUE ($$);
  805.           /* This is a kludge: In order to detect nested types inside
  806.            * template classes, we have to tell the lexer that it should
  807.            * try to replace a following SCOPE token with the correct
  808.            * SCOPED_TYPENAME for the nested type.  This SCOPED_TYPENAME
  809.            * token will be handled in the rule "scoped_typename".
  810.            * - niklas@appli.se */
  811.           if (yychar == SCOPE) {
  812.             template_type_seen_before_scope = TYPE_IDENTIFIER ($$);
  813.             yychar = YYLEX;
  814.           }
  815.         }
  816.     ;
  817.  
  818. template_type_name:
  819.       PTYPENAME '<' template_arg_list '>'
  820.         { $$ = lookup_template_class ($$, $3); }
  821.     | TYPENAME  '<' template_arg_list '>'
  822.         { $$ = lookup_template_class ($$, $3); }
  823.     ;
  824.  
  825. tmpl.1:
  826.     /* Expansion of template may be required, unless we're followed by
  827.        a class definition.  */
  828.       '{'    { yyungetc ('{', 1); $$ = 0; }
  829.     | ':'    { yyungetc (':', 1); $$ = 0; }
  830.     | /* empty */ %prec EMPTY
  831.                 { $$ = instantiate_class_template ($<ttype>0, 1); }
  832.     ;
  833.  
  834. tmpl.2:
  835.     /* Always do expansion if it hasn't been done already. */
  836.         { $$ = instantiate_class_template ($<ttype>0, 1); }
  837.     ;
  838.  
  839. template_arg_list:
  840.       template_arg
  841.         { $$ = build_tree_list (NULL_TREE, $$); }
  842.     | template_arg_list ',' template_arg
  843.         { $$ = chainon ($$, build_tree_list (NULL_TREE, $3)); }
  844.     ;
  845.  
  846. template_arg:
  847.       typename
  848.         { $$ = groktypename ($$); }
  849.     | expr_no_commas  %prec UNARY
  850.     ;
  851.  
  852. template_instantiate_once:
  853.       PRE_PARSED_CLASS_DECL maybe_base_class_list
  854.         {
  855.           tree t, decl, id, tmpl;
  856.  
  857.           id = TREE_VALUE ($1);
  858.           tmpl = TREE_PURPOSE (IDENTIFIER_TEMPLATE (id));
  859.           t = xref_tag (DECL_TEMPLATE_INFO (tmpl)->aggr, id, $2);
  860.           set_current_level_tags_transparency (1);
  861.           my_friendly_assert (TREE_CODE (t) == RECORD_TYPE, 257);
  862.           $<ttype>$ = t;
  863.  
  864.           /* Now, put a copy of the decl in global scope, to avoid
  865.              recursive expansion.  */
  866.           decl = IDENTIFIER_LOCAL_VALUE (id);
  867.           if (!decl)
  868.             decl = IDENTIFIER_CLASS_VALUE (id);
  869.           /* Now, put a copy of the decl in global scope, to avoid
  870.              recursive expansion.  */
  871.                   if (decl)
  872.                     {
  873.               /* Need to copy it to clear the chain pointer,
  874.              and need to get it into permanent storage.  */
  875.                       my_friendly_assert (TREE_CODE (decl) == TYPE_DECL, 258);
  876.               push_obstacks (&permanent_obstack, &permanent_obstack);
  877.                       decl = copy_node (decl);
  878.               if (DECL_LANG_SPECIFIC (decl))
  879.             copy_lang_decl (decl);
  880.               pop_obstacks ();
  881.               pushdecl_top_level (decl);
  882.             }
  883.         }
  884.       left_curly opt.component_decl_list '}'
  885.         {
  886.           extern void end_template_instantiation ();
  887.           int old_interface = interface_unknown;
  888.  
  889.           interface_unknown = 1;
  890.           $$ = finish_struct ($<ttype>3, $5, 0, 0);
  891.  
  892.           pop_obstacks ();
  893.           end_template_instantiation ($1, $<ttype>3);
  894.  
  895.                   /* Now go after the methods & class data.  */
  896.           old_interface = interface_unknown;
  897.           interface_unknown = 1;
  898.                   instantiate_member_templates ($1);
  899.           interface_unknown = old_interface;
  900.           CLASSTYPE_GOT_SEMICOLON ($$) = 1;
  901.         }
  902.     ;
  903.  
  904. template_instantiation:
  905.           /* empty */
  906.                 { $$ = NULL_TREE; }
  907.         | template_instantiate_once
  908.                 { $$ = $1; }
  909.         ;
  910.  
  911. template_instantiate_some:
  912.           /* empty */
  913.                 { $$ = NULL_TREE; /* never used from here... */}
  914.         | template_instantiate_once template_instantiate_some
  915.                 { $$ = $1; /*???*/ }
  916.         ;
  917.  
  918. unop:     '-'
  919.         { $$ = NEGATE_EXPR; }
  920.     | '+'
  921.         { $$ = CONVERT_EXPR; }
  922.     | PLUSPLUS
  923.         { $$ = PREINCREMENT_EXPR; }
  924.     | MINUSMINUS
  925.         { $$ = PREDECREMENT_EXPR; }
  926.     | '!'
  927.         { $$ = TRUTH_NOT_EXPR; }
  928.     ;
  929.  
  930. expr:      nonnull_exprlist
  931.         { $$ = build_x_compound_expr ($$); }
  932.     /* Ugly, but faster.  */
  933.     | expr_no_commas
  934.     ;
  935.  
  936. nonnull_exprlist:
  937.       expr_no_commas
  938.         { $$ = build_tree_list (NULL_TREE, $$); }
  939.     | nonnull_exprlist ',' expr_no_commas
  940.         { chainon ($$, build_tree_list (NULL_TREE, $3)); }
  941.     | nonnull_exprlist ',' error
  942.         { chainon ($$, build_tree_list (NULL_TREE, error_mark_node)); }
  943.     ;
  944.  
  945. unary_expr:
  946.       primary %prec UNARY
  947.         {
  948.           if (TREE_CODE ($$) == TYPE_EXPR)
  949.             $$ = build_component_type_expr (C_C_D, $$, NULL_TREE, 1);
  950.         }
  951.     /* __extension__ turns off -pedantic for following primary.  */
  952.     | EXTENSION
  953.         { $<itype>1 = pedantic;
  954.           pedantic = 0; }
  955.       cast_expr      %prec UNARY
  956.         { $$ = $3;
  957.           pedantic = $<itype>1; }
  958.     | '*' cast_expr   %prec UNARY
  959.         { $$ = build_x_indirect_ref ($2, "unary *"); }
  960.     | '&' cast_expr   %prec UNARY
  961.         { $$ = build_x_unary_op (ADDR_EXPR, $2); }
  962.     | '~' cast_expr   %prec UNARY
  963.         { $$ = build_x_unary_op (BIT_NOT_EXPR, $2); }
  964.     | unop cast_expr  %prec UNARY
  965.         { $$ = build_x_unary_op ($$, $2);
  966.           if ($1 == NEGATE_EXPR && TREE_CODE ($2) == INTEGER_CST)
  967.             TREE_NEGATED_INT ($$) = 1;
  968.         }
  969.     /* Refer to the address of a label as a pointer.  */
  970.     | ANDAND identifier
  971.         { tree label = lookup_label ($2);
  972.           TREE_USED (label) = 1;
  973.           $$ = build1 (ADDR_EXPR, ptr_type_node, label);
  974.           TREE_CONSTANT ($$) = 1; }
  975.     | SIZEOF unary_expr  %prec UNARY
  976.         { if (TREE_CODE ($2) == COMPONENT_REF
  977.               && DECL_BIT_FIELD (TREE_OPERAND ($2, 1)))
  978.             error ("sizeof applied to a bit-field");
  979.           /* ANSI says arrays and functions are converted inside comma.
  980.              But we can't really convert them in build_compound_expr
  981.              because that would break commas in lvalues.
  982.              So do the conversion here if operand was a comma.  */
  983.           if (TREE_CODE ($2) == COMPOUND_EXPR
  984.               && (TREE_CODE (TREE_TYPE ($2)) == ARRAY_TYPE
  985.               || TREE_CODE (TREE_TYPE ($2)) == FUNCTION_TYPE))
  986.             $2 = default_conversion ($2);
  987.           $$ = c_sizeof (TREE_TYPE ($2)); }
  988.     | SIZEOF '(' typename ')'  %prec HYPERUNARY
  989.         { $$ = c_sizeof (groktypename ($3)); }
  990.     | ALIGNOF unary_expr  %prec UNARY
  991.         { if (TREE_CODE ($2) == COMPONENT_REF
  992.               && DECL_BIT_FIELD (TREE_OPERAND ($2, 1)))
  993.             error ("`__alignof' applied to a bit-field");
  994.           if (TREE_CODE ($2) == INDIRECT_REF)
  995.             {
  996.               tree t = TREE_OPERAND ($2, 0);
  997.               tree best = t;
  998.               int bestalign = TYPE_ALIGN (TREE_TYPE (TREE_TYPE (t)));
  999.               while (TREE_CODE (t) == NOP_EXPR
  1000.                  && TREE_CODE (TREE_TYPE (TREE_OPERAND (t, 0))) == POINTER_TYPE)
  1001.             {
  1002.               int thisalign;
  1003.               t = TREE_OPERAND (t, 0);
  1004.               thisalign = TYPE_ALIGN (TREE_TYPE (TREE_TYPE (t)));
  1005.               if (thisalign > bestalign)
  1006.                 best = t, bestalign = thisalign;
  1007.             }
  1008.               $$ = c_alignof (TREE_TYPE (TREE_TYPE (best)));
  1009.             }
  1010.           else
  1011.             {
  1012.               /* ANSI says arrays and fns are converted inside comma.
  1013.              But we can't convert them in build_compound_expr
  1014.              because that would break commas in lvalues.
  1015.              So do the conversion here if operand was a comma.  */
  1016.               if (TREE_CODE ($2) == COMPOUND_EXPR
  1017.               && (TREE_CODE (TREE_TYPE ($2)) == ARRAY_TYPE
  1018.                   || TREE_CODE (TREE_TYPE ($2)) == FUNCTION_TYPE))
  1019.             $2 = default_conversion ($2);
  1020.               $$ = c_alignof (TREE_TYPE ($2));
  1021.             }
  1022.         }
  1023.     | ALIGNOF '(' typename ')'  %prec HYPERUNARY
  1024.         { $$ = c_alignof (groktypename ($3)); }
  1025.  
  1026.     | .scope new typename %prec '='
  1027.         { $$ = build_new ($2, $3, NULL_TREE, $$); }
  1028.     | .scope new '(' nonnull_exprlist ')' typename %prec '='
  1029.         { $$ = build_new ($4, $6, NULL_TREE, $$); }
  1030.     | .scope new typespec '(' nonnull_exprlist ')'
  1031.         { $$ = build_new ($2, $3, $5, $$); }
  1032.     | .scope new '(' nonnull_exprlist ')' typespec '(' nonnull_exprlist ')'
  1033.         { $$ = build_new ($4, $6, $8, $$); }
  1034.     | .scope new typespec LEFT_RIGHT
  1035.         { $$ = build_new ($2, $3, NULL_TREE, $$); }
  1036.     | .scope new '(' nonnull_exprlist ')' typespec LEFT_RIGHT
  1037.         { $$ = build_new ($4, $6, NULL_TREE, $$); }
  1038.     | .scope new typename '=' init %prec '='
  1039.         { $$ = build_new ($2, $3, $5, $$); }
  1040.     | .scope new '(' nonnull_exprlist ')' typename '=' init %prec '='
  1041.         { $$ = build_new ($4, $6, $8, $$); }
  1042.  
  1043.     /* I am not going to add placement syntax to the below complex rules
  1044.        because Ken says the syntax is illegal. (mrs) */
  1045.     /* I'm not sure why this is disallowed.  But since it is, and it
  1046.        doesn't seem difficult to catch it, let's give a message, so
  1047.        the programmer can fix it.  --Ken Raeburn  */
  1048.     | .scope new '(' typed_typespecs absdcl ')' '[' nonmomentary_expr ']'
  1049.         {
  1050.           tree absdcl, typename;
  1051.  
  1052.         illegal_new_array:
  1053.           absdcl = build_parse_node (ARRAY_REF, $5, $8);
  1054.           typename = build_decl_list ($4, absdcl);
  1055.           pedwarn ("ANSI C++ forbids array dimensions with parenthesized type");
  1056.           $$ = build_new ($2, typename, NULL_TREE, $$);
  1057.         }
  1058.     | .scope new '(' nonempty_type_quals absdcl ')' '[' nonmomentary_expr ']'
  1059.         { goto illegal_new_array; }
  1060.  
  1061.     | .scope new '(' typed_typespecs absdcl ')'
  1062.         { $$ = build_new ($2, build_decl_list ($4, $5), NULL_TREE, $$); }
  1063.     | .scope new '(' nonnull_exprlist ')' '(' typed_typespecs absdcl ')'
  1064.         { $$ = build_new ($4, build_decl_list ($7, $8), NULL_TREE, $$); }
  1065.     | .scope new '(' nonempty_type_quals absdcl ')'
  1066.         { $$ = build_new ($2, build_decl_list ($4, $5), NULL_TREE, $$); }
  1067.     | .scope new '(' nonnull_exprlist ')' '(' nonempty_type_quals absdcl ')'
  1068.         { $$ = build_new ($4, build_decl_list ($7, $8), NULL_TREE, $$); }
  1069.     /* Unswallow a ':' which is probably meant for ?: expression.  */
  1070.     | .scope new TYPENAME_COLON
  1071.         { yyungetc (':', 1); $$ = build_new ($2, $3, NULL_TREE, $$); }
  1072.     | .scope new '(' nonnull_exprlist ')' TYPENAME_COLON
  1073.         { yyungetc (':', 1); $$ = build_new ($4, $6, NULL_TREE, $$); }
  1074.  
  1075.     | delete cast_expr  %prec UNARY
  1076.         { tree expr = stabilize_reference (convert_from_reference ($2));
  1077.           tree type = TREE_TYPE (expr);
  1078.  
  1079.           if (TREE_CODE (type) != POINTER_TYPE)
  1080.             {
  1081.               error ("non-pointer type to `delete'");
  1082.               $$ = error_mark_node;
  1083.               break;
  1084.             }
  1085.           else if (integer_zerop (expr))
  1086.             {
  1087.               /* ANSI C++ June 5 1992 WP 5.3.4.  Deleting a pointer
  1088.              with the value zero is legal and has no effect.  */
  1089.               $$ = build1 (NOP_EXPR, void_type_node, expr);
  1090.               break;
  1091.             }
  1092.           else if (TREE_READONLY (TREE_TYPE (type)))
  1093.             {
  1094.               error ("`const *' cannot be deleted");
  1095.               $$ = error_mark_node;
  1096.               break;
  1097.             }
  1098.           $$ = build_delete (type, expr, integer_three_node,
  1099.                      LOOKUP_NORMAL|LOOKUP_HAS_IN_CHARGE,
  1100.                      TYPE_HAS_DESTRUCTOR (TREE_TYPE (type)),
  1101.                      0);
  1102.         }
  1103.     | delete '[' ']' cast_expr  %prec UNARY
  1104.         {
  1105.           tree exp = stabilize_reference (convert_from_reference ($4));
  1106.           tree type = TREE_TYPE (exp);
  1107.           tree elt_size = c_sizeof (type);
  1108.  
  1109.           if (yychar == YYEMPTY)
  1110.             yychar = YYLEX;
  1111.  
  1112.           if (TREE_CODE (type) == POINTER_TYPE
  1113.               && TREE_READONLY (TREE_TYPE (type)))
  1114.             {
  1115.               error ("`const *' cannot be deleted");
  1116.               $$ = error_mark_node;
  1117.               break;
  1118.             }
  1119.           $$ = build_vec_delete (exp, NULL_TREE, elt_size, NULL_TREE,
  1120.                      integer_one_node, integer_two_node);
  1121.         }
  1122.     | delete '[' expr ']' cast_expr %prec UNARY
  1123.         {
  1124.           tree maxindex = build_binary_op (MINUS_EXPR, $3,
  1125.                            integer_one_node);
  1126.           tree exp = stabilize_reference (convert_from_reference ($5));
  1127.           tree type = TREE_TYPE (exp);
  1128.           tree elt_size = c_sizeof (type);
  1129.  
  1130.           if (yychar == YYEMPTY)
  1131.             yychar = YYLEX;
  1132.  
  1133.           if (! flag_traditional)
  1134.             pedwarn ("ANSI C++ forbids array size in vector delete");
  1135.           if (TREE_CODE (type) == POINTER_TYPE
  1136.               && TREE_READONLY (TREE_TYPE (type)))
  1137.             {
  1138.               error ("`const *' cannot be deleted");
  1139.               $$ = error_mark_node;
  1140.               break;
  1141.             }
  1142.           $$ = build_vec_delete (exp, maxindex, elt_size, NULL_TREE,
  1143.                      integer_one_node, integer_two_node);
  1144.         }
  1145.     ;
  1146.  
  1147. cast_expr:
  1148.       unary_expr
  1149.     | '(' typename ')' expr_no_commas  %prec UNARY
  1150.         { tree type = groktypename ($2);
  1151.           $$ = build_c_cast (type, $4); }
  1152.     | '(' typename ')' '{' initlist maybecomma '}'  %prec UNARY
  1153.         { tree type = groktypename ($2);
  1154.           tree init = build_nt (CONSTRUCTOR, NULL_TREE, nreverse ($5));
  1155.           if (pedantic)
  1156.             pedwarn ("ANSI C++ forbids constructor-expressions");
  1157.           /* Indicate that this was a GNU C constructor expression.  */
  1158.           TREE_HAS_CONSTRUCTOR (init) = 1;
  1159.           $$ = digest_init (type, init, 0);
  1160.           if (TREE_CODE (type) == ARRAY_TYPE && TYPE_SIZE (type) == 0)
  1161.             {
  1162.               int failure = complete_array_type (type, $$, 1);
  1163.               if (failure)
  1164.             my_friendly_abort (78);
  1165.             }
  1166.         }
  1167.     | HEADOF '(' expr ')'
  1168.         { $$ = build_headof ($3); }
  1169.     | CLASSOF '(' expr ')'
  1170.         { $$ = build_classof ($3); }
  1171.     | CLASSOF '(' TYPENAME ')'
  1172.         { if (is_aggr_typedef ($3, 1))
  1173.             {
  1174.               tree type = IDENTIFIER_TYPE_VALUE ($3);
  1175.               $$ = CLASSTYPE_DOSSIER (type);
  1176.             }
  1177.           else
  1178.             $$ = error_mark_node;
  1179.         }
  1180.     ;
  1181.  
  1182. expr_no_commas:
  1183.       cast_expr
  1184.     | expr_no_commas '+' expr_no_commas
  1185.         { $$ = build_x_binary_op ($2, $$, $3); }
  1186.     | expr_no_commas '-' expr_no_commas
  1187.         { $$ = build_x_binary_op ($2, $$, $3); }
  1188.     | expr_no_commas '*' expr_no_commas
  1189.         { $$ = build_x_binary_op ($2, $$, $3); }
  1190.     | expr_no_commas '/' expr_no_commas
  1191.         { $$ = build_x_binary_op ($2, $$, $3); }
  1192.     | expr_no_commas '%' expr_no_commas
  1193.         { $$ = build_x_binary_op ($2, $$, $3); }
  1194.     | expr_no_commas LSHIFT expr_no_commas
  1195.         { $$ = build_x_binary_op ($2, $$, $3); }
  1196.     | expr_no_commas RSHIFT expr_no_commas
  1197.         { $$ = build_x_binary_op ($2, $$, $3); }
  1198.     | expr_no_commas ARITHCOMPARE expr_no_commas
  1199.         { $$ = build_x_binary_op ($2, $$, $3); }
  1200.     | expr_no_commas '<' expr_no_commas
  1201.         { $$ = build_x_binary_op (LT_EXPR, $$, $3); }
  1202.     | expr_no_commas '>' expr_no_commas
  1203.         { $$ = build_x_binary_op (GT_EXPR, $$, $3); }
  1204.     | expr_no_commas EQCOMPARE expr_no_commas
  1205.         { $$ = build_x_binary_op ($2, $$, $3); }
  1206.     | expr_no_commas MIN_MAX expr_no_commas
  1207.         { $$ = build_x_binary_op ($2, $$, $3); }
  1208.     | expr_no_commas '&' expr_no_commas
  1209.         { $$ = build_x_binary_op ($2, $$, $3); }
  1210.     | expr_no_commas '|' expr_no_commas
  1211.         { $$ = build_x_binary_op ($2, $$, $3); }
  1212.     | expr_no_commas '^' expr_no_commas
  1213.         { $$ = build_x_binary_op ($2, $$, $3); }
  1214.     | expr_no_commas ANDAND expr_no_commas
  1215.         { $$ = build_x_binary_op (TRUTH_ANDIF_EXPR, $$, $3); }
  1216.     | expr_no_commas OROR expr_no_commas
  1217.         { $$ = build_x_binary_op (TRUTH_ORIF_EXPR, $$, $3); }
  1218.     | expr_no_commas '?' xexpr ':' expr_no_commas
  1219.         { $$ = build_x_conditional_expr ($$, $3, $5); }
  1220.     | expr_no_commas '=' expr_no_commas
  1221.         { $$ = build_modify_expr ($$, NOP_EXPR, $3); }
  1222.     | expr_no_commas ASSIGN expr_no_commas
  1223.         { register tree rval;
  1224.           if (rval = build_opfncall (MODIFY_EXPR, LOOKUP_NORMAL, $$, $3,
  1225.             make_node ($2)))
  1226.             $$ = rval;
  1227.           else
  1228.             $$ = build_modify_expr ($$, $2, $3); }
  1229.     | primary DOT_STAR expr_no_commas %prec UNARY
  1230.         { $$ = build_m_component_ref ($$, build_indirect_ref ($3, 0)); }
  1231.     /* Handle general members.  */
  1232.     | object_star expr_no_commas   %prec UNARY
  1233.         { $$ = build_x_binary_op (MEMBER_REF, $$, $2); }
  1234. /* These extensions are not defined.
  1235.     | object '&' expr_no_commas   %prec UNARY
  1236.         { $$ = build_m_component_ref ($$, build_x_unary_op (ADDR_EXPR, $3)); }
  1237.     | object unop expr_no_commas  %prec UNARY
  1238.         { $$ = build_m_component_ref ($$, build_x_unary_op ($2, $3)); }
  1239.     | object '(' typename ')' expr_no_commas  %prec UNARY
  1240.         { tree type = groktypename ($3);
  1241.           $$ = build_m_component_ref ($$, build_c_cast (type, $5)); }
  1242.     | object primary_no_id  %prec UNARY
  1243.         { $$ = build_m_component_ref ($$, $2); }
  1244. */
  1245.     ;
  1246.  
  1247. primary:
  1248.     IDENTIFIER
  1249.         { $$ = do_identifier ($$); }
  1250.     | operator_name
  1251.         {
  1252.           tree op = $$;
  1253.           if (TREE_CODE (op) != IDENTIFIER_NODE)
  1254.             $$ = op;
  1255.           else
  1256.             {
  1257.               $$ = lookup_name (op, 0);
  1258.               if ($$ == NULL_TREE)
  1259.             {
  1260.               error ("operator %s not defined", operator_name_string (op));
  1261.               $$ = error_mark_node;
  1262.             }
  1263.             }
  1264.         }
  1265.     | CONSTANT
  1266.     | string
  1267.         { $$ = combine_strings ($$); }
  1268.     | '(' expr ')'
  1269.         { $$ = $2; }
  1270.     | '(' error ')'
  1271.         { $$ = error_mark_node; }
  1272.     | '('
  1273.         { if (current_function_decl == 0)
  1274.             {
  1275.               error ("braced-group within expression allowed only inside a function");
  1276.               YYERROR;
  1277.             }
  1278.           keep_next_level ();
  1279.           $<ttype>$ = expand_start_stmt_expr (); }
  1280.       compstmt ')'
  1281.         { tree rtl_exp;
  1282.           if (pedantic)
  1283.             pedwarn ("ANSI C++ forbids braced-groups within expressions");
  1284.           rtl_exp = expand_end_stmt_expr ($<ttype>2);
  1285.           /* The statements have side effects, so the group does.  */
  1286.           TREE_SIDE_EFFECTS (rtl_exp) = 1;
  1287.           /* Make a BIND_EXPR for the BLOCK already made.  */
  1288.           $$ = build (BIND_EXPR, TREE_TYPE (rtl_exp),
  1289.                   NULL_TREE, rtl_exp, $3);
  1290.           /* Remove the block from the tree at this point.
  1291.              It gets put back at the proper place
  1292.              when the BIND_EXPR is expanded.  */
  1293.           delete_block ($3);
  1294.         }
  1295.     | primary '(' nonnull_exprlist ')'
  1296.                 { /* [eichin:19911016.1902EST] */
  1297.                   $<ttype>$ = build_x_function_call ($1, $3, current_class_decl); 
  1298.                   /* here we instantiate_class_template as needed... */
  1299.                   do_pending_templates ();
  1300.                 } template_instantiate_some {
  1301.                   if (TREE_CODE ($<ttype>5) == CALL_EXPR
  1302.                       && TREE_TYPE ($<ttype>5) != void_type_node)
  1303.                 $$ = require_complete_type ($<ttype>5);
  1304.                   else
  1305.                     $$ = $<ttype>5;
  1306.                 }
  1307.     | primary LEFT_RIGHT
  1308.                 { 
  1309.         if ($$ != error_mark_node)
  1310.           {
  1311.             $$ = build_x_function_call ($$, NULL_TREE,
  1312.                         current_class_decl);
  1313.             if (TREE_CODE ($$) == CALL_EXPR
  1314.             && TREE_TYPE ($$) != void_type_node)
  1315.               $$ = require_complete_type ($$);
  1316.           }
  1317.                 }
  1318.     | primary '[' expr ']'
  1319.         {
  1320.         do_array:
  1321.           {
  1322.             tree array_expr = $$;
  1323.             tree index_exp = $3;
  1324.             tree type = TREE_TYPE (array_expr);
  1325.             if (type == error_mark_node || index_exp == error_mark_node)
  1326.               $$ = error_mark_node;
  1327.             else if (type == NULL_TREE)
  1328.               {
  1329.             /* Something has gone very wrong.  Assume we
  1330.                are mistakenly reducing an expression
  1331.                instead of a declaration.  */
  1332.             error ("parser may be lost: is there a '{' missing somewhere?");
  1333.             $$ = NULL_TREE;
  1334.               }
  1335.             else
  1336.               {
  1337.             if (TREE_CODE (type) == OFFSET_TYPE)
  1338.               type = TREE_TYPE (type);
  1339.             if (TREE_CODE (type) == REFERENCE_TYPE)
  1340.               type = TREE_TYPE (type);
  1341.  
  1342.             if (TYPE_LANG_SPECIFIC (type)
  1343.                 && TYPE_OVERLOADS_ARRAY_REF (type))
  1344.               $$ = build_opfncall (ARRAY_REF, LOOKUP_NORMAL, array_expr, index_exp);
  1345.             else if (TREE_CODE (type) == POINTER_TYPE
  1346.                  || TREE_CODE (type) == ARRAY_TYPE)
  1347.               $$ = build_array_ref (array_expr, index_exp);
  1348.             else
  1349.               {
  1350.                 type = TREE_TYPE (index_exp);
  1351.                 if (TREE_CODE (type) == OFFSET_TYPE)
  1352.                   type = TREE_TYPE (type);
  1353.                 if (TREE_CODE (type) == REFERENCE_TYPE)
  1354.                   type = TREE_TYPE (type);
  1355.                 
  1356.                 if (TYPE_LANG_SPECIFIC (type)
  1357.                 && TYPE_OVERLOADS_ARRAY_REF (type))
  1358.                   error ("array expression backwards");
  1359.                 else if (TREE_CODE (type) == POINTER_TYPE
  1360.                      || TREE_CODE (type) == ARRAY_TYPE)
  1361.                   $$ = build_array_ref (index_exp, array_expr);
  1362.                 else
  1363.                   error("[] applied to non-pointer type");
  1364.               }
  1365.               }
  1366.           }
  1367.         }
  1368.     | object identifier_or_opname  %prec UNARY
  1369.         { $$ = build_component_ref ($$, $2, NULL_TREE, 1); }
  1370.     | object scoped_id identifier_or_opname %prec UNARY
  1371.         {
  1372.           tree basetype = $2;
  1373.           if (is_aggr_typedef (basetype, 1))
  1374.             {
  1375.               basetype = IDENTIFIER_TYPE_VALUE (basetype);
  1376.  
  1377.               if ($$ == error_mark_node)
  1378.             ;
  1379.               else if (binfo_or_else (basetype, TREE_TYPE ($$)))
  1380.             $$ = build_component_ref (build_scoped_ref ($$, $2), $3, NULL_TREE, 1);
  1381.               else
  1382.             $$ = error_mark_node;
  1383.             }
  1384.           else $$ = error_mark_node;
  1385.         }
  1386.     | primary PLUSPLUS
  1387.         { $$ = build_x_unary_op (POSTINCREMENT_EXPR, $$); }
  1388.     | primary MINUSMINUS
  1389.         { $$ = build_x_unary_op (POSTDECREMENT_EXPR, $$); }
  1390.  
  1391.     /* C++ extensions */
  1392.     | THIS
  1393.         { if (current_class_decl)
  1394.             {
  1395. #ifdef WARNING_ABOUT_CCD
  1396.               TREE_USED (current_class_decl) = 1;
  1397. #endif
  1398.               $$ = current_class_decl;
  1399.             }
  1400.           else if (current_function_decl
  1401.                && DECL_STATIC_FUNCTION_P (current_function_decl))
  1402.             {
  1403.               error ("`this' is unavailable for static member functions");
  1404.               $$ = error_mark_node;
  1405.             }
  1406.           else
  1407.             {
  1408.               if (current_function_decl)
  1409.             error ("invalid use of `this' in non-member function");
  1410.               else
  1411.             error ("invalid use of `this' at top level");
  1412.               $$ = error_mark_node;
  1413.             }
  1414.         }
  1415.     | TYPE_QUAL '(' nonnull_exprlist ')'
  1416.         {
  1417.           tree type;
  1418.           tree id = $$;
  1419.  
  1420.           /* This is a C cast in C++'s `functional' notation.  */
  1421.           if ($3 == error_mark_node)
  1422.             {
  1423.               $$ = error_mark_node;
  1424.               break;
  1425.             }
  1426. #if 0
  1427.           if ($3 == NULL_TREE)
  1428.             {
  1429.               error ("cannot cast null list to type `%s'",
  1430.                      IDENTIFIER_POINTER (TYPE_NAME (id)));
  1431.               $$ = error_mark_node;
  1432.               break;
  1433.             }
  1434. #endif
  1435. #if 0
  1436.           /* type is not set! (mrs) */
  1437.           if (type == error_mark_node)
  1438.             $$ = error_mark_node;
  1439.           else
  1440. #endif
  1441.             {
  1442.               if (id == ridpointers[(int) RID_CONST])
  1443.                 type = build_type_variant (integer_type_node, 1, 0);
  1444.               else if (id == ridpointers[(int) RID_VOLATILE])
  1445.                 type = build_type_variant (integer_type_node, 0, 1);
  1446. #if 0
  1447.               /* should not be able to get here (mrs) */
  1448.               else if (id == ridpointers[(int) RID_FRIEND])
  1449.                 {
  1450.                   error ("cannot cast expression to `friend' type");
  1451.                   $$ = error_mark_node;
  1452.                   break;
  1453.                 }
  1454. #endif
  1455.               else my_friendly_abort (79);
  1456.               $$ = build_c_cast (type, build_compound_expr ($3));
  1457.             }
  1458.         }
  1459.     | typespec '(' nonnull_exprlist ')'
  1460.         { $$ = build_functional_cast ($$, $3); }
  1461.     | typespec LEFT_RIGHT
  1462.         { $$ = build_functional_cast ($$, NULL_TREE); }
  1463.     | SCOPE typespec '(' nonnull_exprlist ')'
  1464.         { $$ = build_functional_cast ($2, $4); }
  1465.     | SCOPE typespec LEFT_RIGHT
  1466.         { $$ = build_functional_cast ($2, NULL_TREE); }
  1467.     | SCOPE IDENTIFIER
  1468.         {
  1469.         do_scoped_id:
  1470.           $$ = IDENTIFIER_GLOBAL_VALUE ($2);
  1471.           if (yychar == YYEMPTY)
  1472.             yychar = YYLEX;
  1473.           if (! $$)
  1474.             {
  1475.               if (yychar == '(' || yychar == LEFT_RIGHT)
  1476.             $$ = implicitly_declare ($2);
  1477.               else
  1478.             {
  1479.               if (IDENTIFIER_GLOBAL_VALUE ($2) != error_mark_node)
  1480.                 error ("undeclared variable `%s' (first use here)",
  1481.                    IDENTIFIER_POINTER ($2));
  1482.               $$ = error_mark_node;
  1483.               /* Prevent repeated error messages.  */
  1484.               IDENTIFIER_GLOBAL_VALUE ($2) = error_mark_node;
  1485.             }
  1486.             }
  1487.           else
  1488.             {
  1489.               assemble_external ($$);
  1490.               TREE_USED ($$) = 1;
  1491.             }
  1492.           if (TREE_CODE ($$) == CONST_DECL)
  1493.             {
  1494.               /* XXX CHS - should we set TREE_USED of the constant? */
  1495.               $$ = DECL_INITIAL ($$);
  1496.               /* This is to prevent an enum whose value is 0
  1497.              from being considered a null pointer constant.  */
  1498.               $$ = build1 (NOP_EXPR, TREE_TYPE ($$), $$);
  1499.               TREE_CONSTANT ($$) = 1;
  1500.             }
  1501.  
  1502.         }
  1503.     | SCOPE operator_name
  1504.         {
  1505.           if (TREE_CODE ($2) == IDENTIFIER_NODE)
  1506.             goto do_scoped_id;
  1507.         do_scoped_operator:
  1508.           $$ = $2;
  1509.         }
  1510.     | scoped_id identifier_or_opname  %prec HYPERUNARY
  1511.         { $$ = build_offset_ref ($$, $2); }
  1512.     | scoped_id identifier_or_opname '(' nonnull_exprlist ')'
  1513.         { $$ = build_member_call ($$, $2, $4); }
  1514.     | scoped_id identifier_or_opname LEFT_RIGHT
  1515.         { $$ = build_member_call ($$, $2, NULL_TREE); }
  1516.     | object identifier_or_opname '(' nonnull_exprlist ')'
  1517.         { $$ = build_method_call ($$, $2, $4, NULL_TREE,
  1518.                       (LOOKUP_NORMAL|LOOKUP_AGGR)); }
  1519.     | object identifier_or_opname LEFT_RIGHT
  1520.         { $$ = build_method_call ($$, $2, NULL_TREE, NULL_TREE,
  1521.                       (LOOKUP_NORMAL|LOOKUP_AGGR)); }
  1522.     | object scoped_id identifier_or_opname '(' nonnull_exprlist ')'
  1523.         { $$ = build_scoped_method_call ($$, $2, $3, $5); }
  1524.     | object scoped_id identifier_or_opname LEFT_RIGHT
  1525.         { $$ = build_scoped_method_call ($$, $2, $3, NULL_TREE); }
  1526.     ;
  1527.  
  1528. /* Not needed for now.
  1529.  
  1530. primary_no_id:
  1531.       '(' expr ')'
  1532.         { $$ = $2; }
  1533.     | '(' error ')'
  1534.         { $$ = error_mark_node; }
  1535.     | '('
  1536.         { if (current_function_decl == 0)
  1537.             {
  1538.               error ("braced-group within expression allowed only inside a function");
  1539.               YYERROR;
  1540.             }
  1541.           $<ttype>$ = expand_start_stmt_expr (); }
  1542.       compstmt ')'
  1543.         { if (pedantic)
  1544.             pedwarn ("ANSI C++ forbids braced-groups within expressions");
  1545.           $$ = expand_end_stmt_expr ($<ttype>2); }
  1546.     | primary_no_id '(' nonnull_exprlist ')'
  1547.         { $$ = build_x_function_call ($$, $3, current_class_decl); }
  1548.     | primary_no_id LEFT_RIGHT
  1549.         { $$ = build_x_function_call ($$, NULL_TREE, current_class_decl); }
  1550.     | primary_no_id '[' expr ']'
  1551.         { goto do_array; }
  1552.     | primary_no_id PLUSPLUS
  1553.         { $$ = build_x_unary_op (POSTINCREMENT_EXPR, $$); }
  1554.     | primary_no_id MINUSMINUS
  1555.         { $$ = build_x_unary_op (POSTDECREMENT_EXPR, $$); }
  1556.     | SCOPE IDENTIFIER
  1557.         { goto do_scoped_id; }
  1558.     | SCOPE operator_name
  1559.         { if (TREE_CODE ($2) == IDENTIFIER_NODE)
  1560.             goto do_scoped_id;
  1561.           goto do_scoped_operator;
  1562.         }
  1563.     ;
  1564. */
  1565.  
  1566. new:      NEW
  1567.         { $$ = NULL_TREE; }
  1568.     | NEW '{' nonnull_exprlist '}'
  1569.         {
  1570.           $$ = $3;
  1571.           pedwarn ("old style placement syntax, use () instead");
  1572.         }
  1573.     | NEW DYNAMIC  %prec EMPTY
  1574.         { $$ = void_type_node; }
  1575.     | NEW DYNAMIC '(' string ')'
  1576.         { $$ = combine_strings ($4); }
  1577.     ;
  1578.  
  1579. .scope:
  1580.     /* empty  */
  1581.         { $$ = 0; }
  1582.     | SCOPE
  1583.         { $$ = 1; }
  1584.     ;
  1585.  
  1586. delete:      DELETE
  1587.         { $$ = NULL_TREE; }
  1588.     | SCOPE delete
  1589.         { if ($2)
  1590.             error ("extra `::' before `delete' ignored");
  1591.           $$ = error_mark_node;
  1592.         }
  1593.     ;
  1594.  
  1595. /* Produces a STRING_CST with perhaps more STRING_CSTs chained onto it.  */
  1596. string:
  1597.       STRING
  1598.     | string STRING
  1599.         { $$ = chainon ($$, $2); }
  1600.     ;
  1601.  
  1602. nodecls:
  1603.       /* empty */
  1604.         {
  1605.           if (! current_function_parms_stored)
  1606.             store_parm_decls ();
  1607.           setup_vtbl_ptr ();
  1608.         }
  1609.     ;
  1610.  
  1611. object:      primary '.'
  1612.         {
  1613.           if ($$ == error_mark_node)
  1614.             ;
  1615.           else
  1616.             {
  1617.               tree type = TREE_TYPE ($$);
  1618.  
  1619.               if (! PROMOTES_TO_AGGR_TYPE (type, REFERENCE_TYPE))
  1620.             {
  1621.               error ("object in '.' expression is not of aggregate type");
  1622.               $$ = error_mark_node;
  1623.             }
  1624.             }
  1625.         }
  1626.     | primary POINTSAT
  1627.         {
  1628.           $$ = build_x_arrow ($$);
  1629.         }
  1630.     ;
  1631.  
  1632. object_star: primary POINTSAT_STAR
  1633.     ;
  1634.  
  1635. decl:
  1636.       typed_declspecs initdecls ';'
  1637.         {
  1638.           resume_momentary ($2);
  1639.           note_list_got_semicolon ($<ttype>$);
  1640.         }
  1641.     /* Normal case: make this fast.  */
  1642.     | typed_declspecs declarator ';'
  1643.         { tree d;
  1644.           int yes = suspend_momentary ();
  1645.           d = start_decl ($2, $<ttype>$, 0, NULL_TREE);
  1646.           finish_decl (d, NULL_TREE, NULL_TREE, 0);
  1647.           resume_momentary (yes);
  1648.           note_list_got_semicolon ($<ttype>$);
  1649.         }
  1650.     | declmods notype_initdecls ';'
  1651.         { resume_momentary ($2); }
  1652.     /* Normal case: make this fast.  */
  1653.     | declmods declarator ';'
  1654.         { tree d;
  1655.           int yes = suspend_momentary ();
  1656.           d = start_decl ($2, $<ttype>$, 0, NULL_TREE);
  1657.           finish_decl (d, NULL_TREE, NULL_TREE, 0);
  1658.           resume_momentary (yes);
  1659.         }
  1660.     | typed_declspecs ';'
  1661.         {
  1662.           shadow_tag ($<ttype>$);
  1663.           note_list_got_semicolon ($<ttype>$);
  1664.         }
  1665.     | declmods ';'
  1666.         { warning ("empty declaration"); }
  1667.     ;
  1668.  
  1669. /* Any kind of declarator (thus, all declarators allowed
  1670.    after an explicit typespec).  */
  1671.  
  1672. declarator:
  1673.       after_type_declarator
  1674.     | notype_declarator
  1675.     | START_DECLARATOR after_type_declarator
  1676.         { $$ = $2; }
  1677.     | START_DECLARATOR notype_declarator
  1678.         { $$ = $2; }
  1679.     ;
  1680.  
  1681. /* Declspecs which contain at least one type specifier or typedef name.
  1682.    (Just `const' or `volatile' is not enough.)
  1683.    A typedef'd name following these is taken as a name to be declared.  */
  1684.  
  1685. typed_declspecs:
  1686.       typespec    %prec HYPERUNARY
  1687.         { $$ = list_hash_lookup_or_cons ($$); }
  1688.     | declmods typespec
  1689.         { $$ = hash_tree_chain ($2, $$); }
  1690.     | typespec reserved_declspecs    %prec HYPERUNARY
  1691.         { $$ = hash_tree_chain ($$, $2); }
  1692.     | declmods typespec reserved_declspecs
  1693.         { $$ = hash_tree_chain ($2, hash_chainon ($3, $$)); }
  1694.     ;
  1695.  
  1696. reserved_declspecs:  /* empty
  1697.         { $$ = NULL_TREE; } */
  1698.       typespecqual_reserved
  1699.         { $$ = build_decl_list (NULL_TREE, $$); }
  1700.     | SCSPEC
  1701.         { if (extra_warnings)
  1702.             warning ("`%s' is not at beginning of declaration",
  1703.                  IDENTIFIER_POINTER ($$));
  1704.           $$ = build_decl_list (NULL_TREE, $$); }
  1705.     | reserved_declspecs typespecqual_reserved
  1706.         { $$ = decl_tree_cons (NULL_TREE, $2, $$); }
  1707.     | reserved_declspecs SCSPEC
  1708.         { if (extra_warnings)
  1709.             warning ("`%s' is not at beginning of declaration",
  1710.                  IDENTIFIER_POINTER ($2));
  1711.           $$ = decl_tree_cons (NULL_TREE, $2, $$); }
  1712.     ;
  1713.  
  1714. /* List of just storage classes and type modifiers.
  1715.    A declaration can start with just this, but then it cannot be used
  1716.    to redeclare a typedef-name.  */
  1717.  
  1718. declmods:
  1719.       TYPE_QUAL
  1720.         { $$ = IDENTIFIER_AS_LIST ($$);
  1721.           TREE_STATIC ($$) = 1; }
  1722.     | SCSPEC
  1723.         { $$ = IDENTIFIER_AS_LIST ($$); }
  1724.     | declmods TYPE_QUAL
  1725.         { $$ = hash_tree_chain ($2, $$);
  1726.           TREE_STATIC ($$) = 1; }
  1727.     | declmods SCSPEC
  1728.         { if (extra_warnings && TREE_STATIC ($$))
  1729.             warning ("`%s' is not at beginning of declaration",
  1730.                  IDENTIFIER_POINTER ($2));
  1731.           $$ = hash_tree_chain ($2, $$);
  1732.           TREE_STATIC ($$) = TREE_STATIC ($1); }
  1733.     ;
  1734.  
  1735.  
  1736. /* Used instead of declspecs where storage classes are not allowed
  1737.    (that is, for typenames and structure components).
  1738.  
  1739.    C++ can takes storage classes for structure components.
  1740.    Don't accept a typedef-name if anything but a modifier precedes it.  */
  1741.  
  1742. typed_typespecs:
  1743.       typespec  %prec EMPTY
  1744.         { $$ = get_decl_list ($$); }
  1745.     | nonempty_type_quals typespec
  1746.         { $$ = decl_tree_cons (NULL_TREE, $2, $$); }
  1747.     | typespec reserved_typespecquals
  1748.         { $$ = decl_tree_cons (NULL_TREE, $$, $2); }
  1749.     | nonempty_type_quals typespec reserved_typespecquals
  1750.         { $$ = decl_tree_cons (NULL_TREE, $2, hash_chainon ($3, $$)); }
  1751.     ;
  1752.  
  1753. reserved_typespecquals:
  1754.       typespecqual_reserved
  1755.         { $$ = get_decl_list ($$); }
  1756.     | reserved_typespecquals typespecqual_reserved
  1757.         { $$ = decl_tree_cons (NULL_TREE, $2, $$); }
  1758.     ;
  1759.  
  1760. /* A typespec (but not a type qualifier).
  1761.    Once we have seen one of these in a declaration,
  1762.    if a typedef name appears then it is being redeclared.  */
  1763.  
  1764. typespec: structsp
  1765.     | TYPESPEC  %prec EMPTY
  1766.     | TYPENAME  %prec EMPTY
  1767.     | scoped_typename
  1768.     | TYPEOF '(' expr ')'
  1769.         { $$ = TREE_TYPE ($3);
  1770.           if (pedantic)
  1771.             pedwarn ("ANSI C++ forbids `typeof'"); }
  1772.     | TYPEOF '(' typename ')'
  1773.         { $$ = groktypename ($3);
  1774.           if (pedantic)
  1775.             pedwarn ("ANSI C++ forbids `typeof'"); }
  1776.     | template_type
  1777.     ;
  1778.  
  1779. /* A typespec that is a reserved word, or a type qualifier.  */
  1780.  
  1781. typespecqual_reserved: TYPESPEC
  1782.     | TYPE_QUAL
  1783.     | structsp
  1784.     ;
  1785.  
  1786. initdecls:
  1787.       initdcl0
  1788.     | initdecls ',' initdcl
  1789.     ;
  1790.  
  1791. notype_initdecls:
  1792.       notype_initdcl0
  1793.     | notype_initdecls ',' initdcl
  1794.     ;
  1795.  
  1796. maybeasm:
  1797.       /* empty */
  1798.         { $$ = NULL_TREE; }
  1799.     | ASM_KEYWORD '(' string ')'
  1800.         { if (TREE_CHAIN ($3)) $3 = combine_strings ($3);
  1801.           $$ = $3;
  1802.           if (pedantic)
  1803.             pedwarn ("ANSI C++ forbids use of `asm' keyword");
  1804.         }
  1805.     ;
  1806.  
  1807. initdcl0:
  1808.       declarator maybe_raises maybeasm maybe_attribute '='
  1809.         { current_declspecs = $<ttype>0;
  1810.           $<itype>5 = suspend_momentary ();
  1811.           $<ttype>$ = start_decl ($1, current_declspecs, 1, $2);
  1812.           cplus_decl_attributes ($<ttype>$, $4); }
  1813.       init
  1814. /* Note how the declaration of the variable is in effect while its init is parsed! */
  1815.         { finish_decl ($<ttype>6, $7, $3, 0);
  1816.           $$ = $<itype>5; }
  1817.     | declarator maybe_raises maybeasm maybe_attribute
  1818.         { tree d;
  1819.           current_declspecs = $<ttype>0;
  1820.           $$ = suspend_momentary ();
  1821.           d = start_decl ($1, current_declspecs, 0, $2);
  1822.           cplus_decl_attributes (d, $4);
  1823.           finish_decl (d, NULL_TREE, $3, 0); }
  1824.     ;
  1825.  
  1826. initdcl:
  1827.       declarator maybe_raises maybeasm maybe_attribute '='
  1828.         { $<ttype>$ = start_decl ($1, current_declspecs, 1, $2);
  1829.           cplus_decl_attributes ($<ttype>$, $4); }
  1830.       init
  1831. /* Note how the declaration of the variable is in effect while its init is parsed! */
  1832.         { finish_decl ($<ttype>6, $7, $3, 0); }
  1833.     | declarator maybe_raises maybeasm maybe_attribute
  1834.         { tree d = start_decl ($$, current_declspecs, 0, $2);
  1835.           cplus_decl_attributes ($<ttype>$, $4);
  1836.           finish_decl (d, NULL_TREE, $3, 0); }
  1837.     ;
  1838.  
  1839. notype_initdcl0:
  1840.       notype_declarator maybe_raises maybeasm maybe_attribute '='
  1841.         { current_declspecs = $<ttype>0;
  1842.           $<itype>5 = suspend_momentary ();
  1843.           $<ttype>$ = start_decl ($1, current_declspecs, 1, $2);
  1844.           cplus_decl_attributes ($<ttype>$, $4); }
  1845.       init
  1846. /* Note how the declaration of the variable is in effect while its init is parsed! */
  1847.         { finish_decl ($<ttype>6, $7, $3, 0);
  1848.           $$ = $<itype>5; }
  1849.     | notype_declarator maybe_raises maybeasm maybe_attribute
  1850.         { tree d;
  1851.           current_declspecs = $<ttype>0;
  1852.           $$ = suspend_momentary ();
  1853.           d = start_decl ($1, current_declspecs, 0, $2);
  1854.           cplus_decl_attributes (d, $4);
  1855.           finish_decl (d, NULL_TREE, $3, 0); }
  1856.     ;
  1857.  
  1858. /* the * rules are dummies to accept the Apollo extended syntax
  1859.    so that the header files compile. */
  1860. maybe_attribute:
  1861.     /* empty */
  1862.     { $$ = NULL_TREE; }
  1863.     | ATTRIBUTE '(' '(' attribute_list ')' ')'
  1864.         { $$ = $4; }
  1865.     ;
  1866.  
  1867. attribute_list
  1868.     : attrib
  1869.     { $$ = tree_cons (NULL_TREE, $1, NULL_TREE); }
  1870.     | attribute_list ',' attrib
  1871.     { $$ = tree_cons (NULL_TREE, $3, $1); }
  1872.     ;
  1873.  
  1874. attrib
  1875.     : IDENTIFIER
  1876.     { if (strcmp (IDENTIFIER_POINTER ($1), "packed"))
  1877.         warning ("`%s' attribute directive ignored",
  1878.              IDENTIFIER_POINTER ($1));
  1879.       $$ = $1; }
  1880.     | IDENTIFIER '(' CONSTANT ')'
  1881.     { /* if not "aligned(n)", then issue warning */
  1882.       if (strcmp (IDENTIFIER_POINTER ($1), "aligned") != 0
  1883.           || TREE_CODE ($3) != INTEGER_CST)
  1884.         {
  1885.           warning ("`%s' attribute directive ignored",
  1886.                IDENTIFIER_POINTER ($1));
  1887.           $$ = $1;
  1888.         }
  1889.       else
  1890.         $$ = tree_cons ($1, $3, NULL_TREE); }
  1891.     | IDENTIFIER '(' IDENTIFIER ',' CONSTANT ',' CONSTANT ')'
  1892.     { /* if not "format(...)", then issue warning */
  1893.       if (strcmp (IDENTIFIER_POINTER ($1), "format") != 0
  1894.           || TREE_CODE ($5) != INTEGER_CST
  1895.           || TREE_CODE ($7) != INTEGER_CST)
  1896.         {
  1897.           warning ("`%s' attribute directive ignored",
  1898.                IDENTIFIER_POINTER ($1));
  1899.           $$ = $1;
  1900.         }
  1901.       else
  1902.         $$ = tree_cons ($1, tree_cons ($3, tree_cons ($5, $7, NULL_TREE), NULL_TREE), NULL_TREE); }
  1903.     ;
  1904.  
  1905. /* A nonempty list of identifiers, including typenames.  */
  1906. identifiers_or_typenames:
  1907.     identifier
  1908.         { $$ = build_tree_list (NULL_TREE, $1); }
  1909.     | identifiers_or_typenames ',' identifier
  1910.         { $$ = chainon ($1, build_tree_list (NULL_TREE, $3)); }
  1911.     ;
  1912.  
  1913. init:
  1914.       expr_no_commas %prec '='
  1915.     | '{' '}'
  1916.         { $$ = build_nt (CONSTRUCTOR, NULL_TREE, NULL_TREE);
  1917.           TREE_HAS_CONSTRUCTOR ($$) = 1;
  1918.           if (pedantic)
  1919.             pedwarn ("ANSI C++ forbids empty initializer braces"); }
  1920.     | '{' initlist '}'
  1921.         { $$ = build_nt (CONSTRUCTOR, NULL_TREE, nreverse ($2));
  1922.           TREE_HAS_CONSTRUCTOR ($$) = 1; }
  1923.     | '{' initlist ',' '}'
  1924.         { $$ = build_nt (CONSTRUCTOR, NULL_TREE, nreverse ($2));
  1925.           TREE_HAS_CONSTRUCTOR ($$) = 1; }
  1926.     | error
  1927.         { $$ = NULL_TREE; }
  1928.     ;
  1929.  
  1930. /* This chain is built in reverse order,
  1931.    and put in forward order where initlist is used.  */
  1932. initlist:
  1933.       init
  1934.         { $$ = build_tree_list (NULL_TREE, $$); }
  1935.     | initlist ',' init
  1936.         { $$ = tree_cons (NULL_TREE, $3, $$); }
  1937.     /* These are for labeled elements.  */
  1938.     | '[' expr_no_commas ']' init
  1939.         { $$ = build_tree_list ($2, $4); }
  1940.     | initlist ',' CASE expr_no_commas ':' init
  1941.         { $$ = tree_cons ($4, $6, $$); }
  1942.     | identifier ':' init
  1943.         { $$ = build_tree_list ($$, $3); }
  1944.     | initlist ',' identifier ':' init
  1945.         { $$ = tree_cons ($3, $5, $$); }
  1946.     ;
  1947.  
  1948. structsp:
  1949.       ENUM identifier '{'
  1950.         { $<itype>3 = suspend_momentary ();
  1951.           $$ = start_enum ($2); }
  1952.       enumlist maybecomma_warn '}'
  1953.         { $$ = finish_enum ($<ttype>4, $5);
  1954.           resume_momentary ($<itype>3);
  1955.           check_for_missing_semicolon ($<ttype>4); }
  1956.     | ENUM identifier '{' '}'
  1957.         { $$ = finish_enum (start_enum ($2), NULL_TREE);
  1958.           check_for_missing_semicolon ($$); }
  1959.     | ENUM '{'
  1960.         { $<itype>2 = suspend_momentary ();
  1961.           $$ = start_enum (make_anon_name ()); }
  1962.       enumlist maybecomma_warn '}'
  1963.         { $$ = finish_enum ($<ttype>3, $4);
  1964.           resume_momentary ($<itype>1);
  1965.           check_for_missing_semicolon ($<ttype>3); }
  1966.     | ENUM '{' '}'
  1967.         { $$ = finish_enum (start_enum (make_anon_name()), NULL_TREE);
  1968.           check_for_missing_semicolon ($$); }
  1969.     | ENUM identifier
  1970.         { $$ = xref_tag (enum_type_node, $2, NULL_TREE); }
  1971.  
  1972.     /* C++ extensions, merged with C to avoid shift/reduce conflicts */
  1973.     | class_head left_curly opt.component_decl_list '}'
  1974.         {
  1975.           int semi;
  1976.           tree id;
  1977.  
  1978. #if 0
  1979.           /* Need to rework class nesting in the
  1980.              presence of nested classes, etc.  */
  1981.           shadow_tag (CLASSTYPE_AS_LIST ($$)); */
  1982. #endif
  1983.           if (yychar == YYEMPTY)
  1984.             yychar = YYLEX;
  1985.           semi = yychar == ';';
  1986.           /* finish_struct nukes this anyway; if
  1987.              finish_exception does too, then it can go. */
  1988.           if (semi)
  1989.             note_got_semicolon ($$);
  1990.  
  1991.           if (TREE_CODE ($$) == ENUMERAL_TYPE)
  1992.             /* $$ = $1 from default rule.  */;
  1993.           else if (CLASSTYPE_DECLARED_EXCEPTION ($$))
  1994.             {
  1995.               if (! semi)
  1996.             $$ = finish_exception ($$, $3);
  1997.               else
  1998.             warning ("empty exception declaration\n");
  1999.             }
  2000.           else
  2001.             {
  2002.               $$ = finish_struct ($$, $3, semi, semi);
  2003.               if (semi) note_got_semicolon ($$);
  2004.             }
  2005.  
  2006.           pop_obstacks ();
  2007.  
  2008.           id = TYPE_IDENTIFIER ($$);
  2009.           if (IDENTIFIER_TEMPLATE (id))
  2010.             {
  2011.               tree decl;
  2012.  
  2013.               /* I don't know if the copying of this TYPE_DECL is
  2014.                * really needed.  However, it's such a small per-
  2015.                * formance penalty that the extra safety is a bargain.
  2016.                * - niklas@appli.se
  2017.                */
  2018.               push_obstacks (&permanent_obstack, &permanent_obstack);
  2019.               decl = copy_node (lookup_name (id));
  2020.               if (DECL_LANG_SPECIFIC (decl))
  2021.             copy_lang_decl (decl);
  2022.               pop_obstacks ();
  2023.               undo_template_name_overload (id, 0);
  2024.               pushdecl_top_level (decl);
  2025.             }
  2026.           if (! semi)
  2027.             check_for_missing_semicolon ($$); }
  2028.     | class_head  %prec EMPTY
  2029.         {
  2030. #if 0
  2031.   /* It's no longer clear what the following error is supposed to
  2032.      accomplish.  If it turns out to be needed, add a comment why.  */
  2033.           if (TYPE_BINFO_BASETYPES ($$) && !TYPE_SIZE ($$))
  2034.             {
  2035.               error ("incomplete definition of type `%s'",
  2036.                  TYPE_NAME_STRING ($$));
  2037.               $$ = error_mark_node;
  2038.             }
  2039. #endif
  2040.         }
  2041.     ;
  2042.  
  2043. maybecomma:
  2044.       /* empty */
  2045.     | ','
  2046.     ;
  2047.  
  2048. maybecomma_warn:
  2049.       /* empty */
  2050.     | ','
  2051.         { if (pedantic)
  2052.             pedwarn ("ANSI C++ forbids comma at end of enumerator list"); }
  2053.     ;
  2054.  
  2055. aggr:      AGGR
  2056.     | DYNAMIC AGGR
  2057.         { $$ = build_tree_list (NULL_TREE, $2); }
  2058.     | DYNAMIC '(' string ')' AGGR
  2059.         { $$ = build_tree_list ($3, $5); }
  2060.     | aggr SCSPEC
  2061.         { error ("storage class specifier `%s' not allowed after struct or class", IDENTIFIER_POINTER ($2));
  2062.         }
  2063.     | aggr TYPESPEC
  2064.         { error ("type specifier `%s' not allowed after struct or class", IDENTIFIER_POINTER ($2));
  2065.         }
  2066.     | aggr TYPE_QUAL
  2067.         { error ("type qualifier `%s' not allowed after struct or class", IDENTIFIER_POINTER ($2));
  2068.         }
  2069.     | aggr AGGR
  2070.         { error ("no body nor ';' separates two class, struct or union declarations");
  2071.         }
  2072.     ;
  2073.  
  2074. named_class_head_sans_basetype:
  2075.       aggr identifier
  2076.         { aggr1: current_aggr = $$; $$ = $2; }
  2077.     | aggr template_type_name  %prec EMPTY
  2078.         { current_aggr = $$; $$ = $2; }
  2079.     | aggr TYPENAME_COLON
  2080.         { yyungetc (':', 1); goto aggr1; }
  2081.     | aggr template_type_name '{'
  2082.         { yyungetc ('{', 1);
  2083.         aggr2:
  2084.           current_aggr = $$;
  2085.           $$ = $2;
  2086.           overload_template_name ($$, 0); }
  2087.     | aggr template_type_name ':'
  2088.         { yyungetc (':', 1); goto aggr2; }
  2089.     ;
  2090.  
  2091. named_class_head_sans_basetype_defn:
  2092.       aggr identifier_defn
  2093.         { current_aggr = $$; $$ = $2; }
  2094.     ;
  2095.  
  2096. named_class_head:
  2097.       named_class_head_sans_basetype
  2098.         {
  2099.           $<ttype>$ = xref_tag (current_aggr, $1, NULL_TREE);
  2100.         }
  2101.       maybe_base_class_list %prec EMPTY
  2102.         {
  2103.           if ($3)
  2104.             $$ = xref_tag (current_aggr, $1, $3);
  2105.           else
  2106.             $$ = $<ttype>2;
  2107.         }
  2108.     |
  2109.       named_class_head_sans_basetype_defn
  2110.         {
  2111.           $<ttype>$ = xref_defn_tag (current_aggr, $1, NULL_TREE);
  2112.         }
  2113.       maybe_base_class_list %prec EMPTY
  2114.         {
  2115.           if ($3)
  2116.             $$ = xref_defn_tag (current_aggr, $1, $3);
  2117.           else
  2118.             $$ = $<ttype>2;
  2119.         }
  2120.     ;
  2121.  
  2122. unnamed_class_head: aggr '{'
  2123.         { $$ = xref_tag ($$, make_anon_name (), NULL_TREE);
  2124.           yyungetc ('{', 1); }
  2125.     ;
  2126.  
  2127. class_head: unnamed_class_head | named_class_head ;
  2128.  
  2129. maybe_base_class_list:
  2130.       /* empty */
  2131.         { $$ = NULL_TREE; }
  2132.     | ':'  %prec EMPTY
  2133.         { yyungetc(':', 1); $$ = NULL_TREE; }
  2134.     | ':' base_class_list  %prec EMPTY
  2135.         { $$ = $2; }
  2136.     ;
  2137.  
  2138. base_class_list:
  2139.       base_class
  2140.     | base_class_list ',' base_class
  2141.         { $$ = chainon ($$, $3); }
  2142.     ;
  2143.  
  2144. base_class:
  2145.       base_class.1
  2146.         { if (! is_aggr_typedef ($$, 1))
  2147.             $$ = NULL_TREE;
  2148.           else $$ = build_tree_list ((tree)visibility_default, $$); }
  2149.     | scoped_base_class
  2150.         { if (! is_aggr_typedef ($$, 1))
  2151.             $$ = NULL_TREE;
  2152.           else $$ = build_tree_list ((tree)visibility_default, $$); }
  2153.     | base_class_visibility_list base_class.1
  2154.         { if (! is_aggr_typedef ($2, 1))
  2155.             $$ = NULL_TREE;
  2156.           else $$ = build_tree_list ((tree) $$, $2); }
  2157.     | base_class_visibility_list scoped_base_class
  2158.         { if (! is_aggr_typedef ($2, 1))
  2159.             $$ = NULL_TREE;
  2160.           else $$ = build_tree_list ((tree) $$, $2); }
  2161.     ;
  2162.  
  2163. scoped_base_class:
  2164.       base_class.1 SCOPED_TYPENAME
  2165.         {
  2166.             /* Kludge!!! See rule "template_type" and the code
  2167.            * dealing with "template_type_seen_before_scope" in
  2168.            * yylex(). */
  2169.             $$ = $2;
  2170.         }
  2171.     ;
  2172. base_class.1:
  2173.       template_type_name tmpl.2 template_instantiation
  2174.         {
  2175.             extern tree template_type_seen_before_scope;
  2176.           tree id = $3 ? TYPE_IDENTIFIER ($3) : $1;
  2177.  
  2178.             /* Check the rule template_type to get this... */
  2179.           if (yychar == YYEMPTY)
  2180.             yychar = YYLEX;
  2181.           if (yychar == SCOPE) {
  2182.             template_type_seen_before_scope = id;
  2183.             yychar = YYLEX;
  2184.           }
  2185.         }
  2186.     | identifier
  2187.     ;
  2188.  
  2189. base_class_visibility_list:
  2190.       VISSPEC
  2191.     | SCSPEC
  2192.         { if ($<ttype>$ != ridpointers[(int)RID_VIRTUAL])
  2193.             sorry ("non-virtual visibility");
  2194.           $$ = visibility_default_virtual; }
  2195.     | base_class_visibility_list VISSPEC
  2196.         { int err = 0;
  2197.           if ($2 == visibility_protected)
  2198.             {
  2199.               warning ("`protected' visibility not implemented");
  2200.               $2 = visibility_public;
  2201.               err++;
  2202.             }
  2203.           else if ($2 == visibility_public)
  2204.             {
  2205.               if ($1 == visibility_private)
  2206.             {
  2207.             mixed:
  2208.               error ("base class cannot be public and private");
  2209.             }
  2210.               else if ($1 == visibility_default_virtual)
  2211.             $$ = visibility_public_virtual;
  2212.             }
  2213.           else /* $2 == visibility_private */
  2214.             {
  2215.               if ($1 == visibility_public)
  2216.             goto mixed;
  2217.               else if ($1 == visibility_default_virtual)
  2218.             $$ = visibility_private_virtual;
  2219.             }
  2220.         }
  2221.     | base_class_visibility_list SCSPEC
  2222.         { if ($2 != ridpointers[(int)RID_VIRTUAL])
  2223.             sorry ("non-virtual visibility");
  2224.           if ($$ == visibility_public)
  2225.             $$ = visibility_public_virtual;
  2226.           else if ($$ == visibility_private)
  2227.             $$ = visibility_private_virtual; }
  2228.     ;
  2229.  
  2230. left_curly: '{'
  2231.         { tree t;
  2232.           push_obstacks_nochange ();
  2233.           end_temporary_allocation ();
  2234.  
  2235.           if (! IS_AGGR_TYPE ($<ttype>0))
  2236.             {
  2237.               $<ttype>0 = make_lang_type (RECORD_TYPE);
  2238.               TYPE_NAME ($<ttype>0) = get_identifier ("erroneous type");
  2239.             }
  2240.           if (TYPE_SIZE ($<ttype>0))
  2241.             duplicate_tag_error ($<ttype>0);
  2242.                   if (TYPE_SIZE ($<ttype>0) || TYPE_BEING_DEFINED ($<ttype>0))
  2243.                     {
  2244.                       t = make_lang_type (TREE_CODE ($<ttype>0));
  2245.                       pushtag (TYPE_IDENTIFIER ($<ttype>0), t);
  2246.                       $<ttype>0 = t;
  2247.                     }
  2248.           pushclass ($<ttype>0, 0);
  2249.           TYPE_BEING_DEFINED ($<ttype>0) = 1;
  2250.           t = TYPE_IDENTIFIER ($<ttype>0);
  2251.           if (IDENTIFIER_TEMPLATE (t))
  2252.             overload_template_name (t, 1);
  2253.         }
  2254.     ;
  2255.  
  2256. opt.component_decl_list:
  2257.     /* empty */
  2258.         { $$ = NULL_TREE; }
  2259.     | component_decl_list
  2260.         { $$ = build_tree_list ((tree)visibility_default, $$); }
  2261.     | opt.component_decl_list VISSPEC ':' component_decl_list
  2262.         { $$ = chainon ($$, build_tree_list ((tree) $2, $4)); }
  2263.     | opt.component_decl_list VISSPEC ':'
  2264.     ;
  2265.  
  2266. component_decl_list:
  2267.       component_decl
  2268.         { if ($$ == void_type_node) $$ = NULL_TREE; }
  2269.     | component_decl_list component_decl
  2270.         { if ($2 != NULL_TREE && $2 != void_type_node)
  2271.             $$ = chainon ($$, $2); }
  2272.     | component_decl_list ';'
  2273.         { if (pedantic)
  2274.             pedwarn ("ANSI C++ forbids extra semicolons here"); }
  2275.     ;
  2276.  
  2277. component_decl:
  2278.       typed_declspecs components ';'
  2279.         {
  2280.         do_components:
  2281.           if ($2 == void_type_node)
  2282.             /* We just got some friends.
  2283.                They have been recorded elsewhere.  */
  2284.             $$ = NULL_TREE;
  2285.           else if ($2 == NULL_TREE)
  2286.             {
  2287.               tree t = groktypename (build_decl_list ($$, NULL_TREE));
  2288.               if (t == NULL_TREE)
  2289.             {
  2290.               error ("error in component specification");
  2291.               $$ = NULL_TREE;
  2292.             }
  2293.               else if (TREE_CODE (t) == UNION_TYPE)
  2294.             {
  2295.               /* handle anonymous unions */
  2296.               if (ANON_AGGRNAME_P (TYPE_IDENTIFIER (t)))
  2297.                 $$ = build_lang_field_decl (FIELD_DECL,
  2298.                             NULL_TREE, t);
  2299.               else
  2300.                 {
  2301.                   /* This is a local union decl with a name, but
  2302.                  no components, I think this is the right thing
  2303.                  to do.  (mrs)  */
  2304. #if 0
  2305.                   /* I copied this from below, it is probably
  2306.                  needed, but I cannot prove that to myself
  2307.                  right now, but if you find it is needed
  2308.                  please turn it on. (mrs)  */
  2309.                   if (TYPE_LANG_SPECIFIC (t)
  2310.                   && CLASSTYPE_DECLARED_EXCEPTION (t))
  2311.                 shadow_tag ($$);
  2312. #endif
  2313.                   $$ = NULL_TREE;
  2314.                 }
  2315.             }
  2316.               else if (TREE_CODE (t) == ENUMERAL_TYPE)
  2317.             $$ = grok_enum_decls (t, NULL_TREE);
  2318.               else if (TREE_CODE (t) == RECORD_TYPE)
  2319.             {
  2320.               if (TYPE_LANG_SPECIFIC (t)
  2321.                   && CLASSTYPE_DECLARED_EXCEPTION (t))
  2322.                 shadow_tag ($$);
  2323.               $$ = NULL_TREE;
  2324.             }
  2325.               else if (t != void_type_node)
  2326.             {
  2327.               error ("empty component declaration");
  2328.               $$ = NULL_TREE;
  2329.             }
  2330.               else $$ = NULL_TREE;
  2331.             }
  2332.           else
  2333.             {
  2334.               tree t = TREE_TYPE ($2);
  2335.               if (TREE_CODE (t) == ENUMERAL_TYPE && TREE_NONLOCAL_FLAG (t))
  2336.             $$ = grok_enum_decls (t, $2);
  2337.               else
  2338.             $$ = $2;
  2339.             }
  2340.           end_exception_decls ();
  2341.         }
  2342.     | typed_declspecs '(' parmlist ')' ';'
  2343.         { $$ = groktypefield ($$, $3); }
  2344.     | typed_declspecs '(' parmlist ')' '}'
  2345.         { error ("missing ';' before right brace");
  2346.           yyungetc ('}', 0);
  2347.           $$ = groktypefield ($$, $3); }
  2348.     | typed_declspecs LEFT_RIGHT ';'
  2349.         { $$ = groktypefield ($$, empty_parms ()); }
  2350.     | typed_declspecs LEFT_RIGHT '}'
  2351.         { error ("missing ';' before right brace");
  2352.           yyungetc ('}', 0);
  2353.           $$ = groktypefield ($$, empty_parms ()); }
  2354.     | declmods components ';'
  2355.         { goto do_components; }
  2356.     /* Normal case: make this fast.  */
  2357.     | declmods declarator ';'
  2358.         { $$ = grokfield ($2, $$, 0, 0, 0, 0); }
  2359.     | declmods components '}'
  2360.         { error ("missing ';' before right brace");
  2361.           yyungetc ('}', 0);
  2362.           goto do_components; }
  2363.     | declmods '(' parmlist ')' ';'
  2364.         { $$ = groktypefield ($$, $3); }
  2365.     | declmods '(' parmlist ')' '}'
  2366.         { error ("missing ';' before right brace");
  2367.           yyungetc ('}', 0);
  2368.           $$ = groktypefield ($$, $3); }
  2369.     | declmods LEFT_RIGHT ';'
  2370.         { $$ = groktypefield ($$, empty_parms ()); }
  2371.     | declmods LEFT_RIGHT '}'
  2372.         { error ("missing ';' before right brace");
  2373.           yyungetc ('}', 0);
  2374.           $$ = groktypefield ($$, empty_parms ()); }
  2375.     | ':' expr_no_commas ';'
  2376.         { $$ = grokbitfield (NULL_TREE, NULL_TREE, $2); }
  2377.     | ':' expr_no_commas '}'
  2378.         { error ("missing ';' before right brace");
  2379.           yyungetc ('}', 0);
  2380.           $$ = grokbitfield (NULL_TREE, NULL_TREE, $2); }
  2381.     | error
  2382.         { $$ = NULL_TREE; }
  2383.  
  2384.     /* C++: handle constructors, destructors and inline functions */
  2385.     /* note that INLINE is like a TYPESPEC */
  2386.     | fn.def2 ':' /* base_init compstmt */
  2387.         { $$ = finish_method ($$); }
  2388.     | fn.def2 '{' /* nodecls compstmt */
  2389.         { $$ = finish_method ($$); }
  2390.     | notype_declarator maybe_raises ';'
  2391.         { $$ = grokfield ($$, NULL_TREE, $2, NULL_TREE, NULL_TREE); }
  2392.     | notype_declarator maybe_raises '}'
  2393.         { error ("missing ';' before right brace");
  2394.           yyungetc ('}', 0);
  2395.           $$ = grokfield ($$, NULL_TREE, $2, NULL_TREE, NULL_TREE); }
  2396.     ;
  2397.  
  2398. components:
  2399.       /* empty: possibly anonymous */
  2400.         { $$ = NULL_TREE; }
  2401.     | component_declarator0
  2402.     | components ',' component_declarator
  2403.         {
  2404.           /* In this context, void_type_node encodes
  2405.              friends.  They have been recorded elsewhere.  */
  2406.           if ($$ == void_type_node)
  2407.             $$ = $3;
  2408.           else
  2409.             $$ = chainon ($$, $3);
  2410.         }
  2411.     ;
  2412.  
  2413. component_declarator0:
  2414.       declarator maybe_raises maybeasm maybe_attribute
  2415.         { current_declspecs = $<ttype>0;
  2416.           $$ = grokfield ($$, current_declspecs, $2, NULL_TREE, $3);
  2417.           cplus_decl_attributes ($$, $4); }
  2418.     | declarator maybe_raises maybeasm maybe_attribute '=' init
  2419.         { current_declspecs = $<ttype>0;
  2420.           $$ = grokfield ($$, current_declspecs, $2, $6, $3);
  2421.           cplus_decl_attributes ($$, $4); }
  2422.     | IDENTIFIER ':' expr_no_commas maybe_attribute
  2423.         { current_declspecs = $<ttype>0;
  2424.           $$ = grokbitfield ($$, current_declspecs, $3);
  2425.           cplus_decl_attributes ($$, $4); }
  2426.     | TYPENAME_COLON expr_no_commas maybe_attribute
  2427.         { current_declspecs = $<ttype>0;
  2428.           $$ = grokbitfield ($$, current_declspecs, $2);
  2429.           cplus_decl_attributes ($$, $3); }
  2430.     | ':' expr_no_commas
  2431.         { current_declspecs = $<ttype>0;
  2432.           $$ = grokbitfield (NULL_TREE, NULL_TREE, $2); }
  2433.     ;
  2434.  
  2435. component_declarator:
  2436.       declarator maybe_raises maybeasm maybe_attribute
  2437.         { $$ = grokfield ($$, current_declspecs, $2, NULL_TREE, $3);
  2438.           cplus_decl_attributes ($$, $4); }
  2439.     | declarator maybe_raises maybeasm maybe_attribute '=' init
  2440.         { $$ = grokfield ($$, current_declspecs, $2, $6, $3);
  2441.           cplus_decl_attributes ($$, $4); }
  2442.     | IDENTIFIER ':' expr_no_commas maybe_attribute
  2443.         { $$ = grokbitfield ($$, current_declspecs, $3);
  2444.           cplus_decl_attributes ($$, $4); }
  2445.     | TYPENAME_COLON expr_no_commas maybe_attribute
  2446.         { $$ = grokbitfield ($$, current_declspecs, $2);
  2447.           cplus_decl_attributes ($$, $3); }
  2448.     | ':' expr_no_commas
  2449.         { $$ = grokbitfield (NULL_TREE, NULL_TREE, $2); }
  2450.     ;
  2451.  
  2452. /* We chain the enumerators in reverse order.
  2453.    Because of the way enums are built, the order is
  2454.    insignificant.  Take advantage of this fact.  */
  2455.  
  2456. enumlist:
  2457.       enumerator
  2458.     | enumlist ',' enumerator
  2459.         { TREE_CHAIN ($3) = $$; $$ = $3; }
  2460.     ;
  2461.  
  2462. enumerator:
  2463.       identifier
  2464.         { $$ = build_enumerator ($$, NULL_TREE); }
  2465.     | identifier '=' expr_no_commas
  2466.         { $$ = build_enumerator ($$, $3); }
  2467.     ;
  2468.  
  2469. typename:
  2470.       typed_typespecs absdcl
  2471.         { $$ = build_decl_list ($$, $2); }
  2472.     | nonempty_type_quals absdcl
  2473.         { $$ = build_decl_list ($$, $2); }
  2474.     ;
  2475.  
  2476. absdcl:   /* an abstract declarator */
  2477.     /* empty */ %prec EMPTY
  2478.         { $$ = NULL_TREE; }
  2479.     | absdcl1  %prec EMPTY
  2480.     | START_DECLARATOR absdcl1  %prec EMPTY
  2481.         { $$ = $2; }
  2482.     ;
  2483.  
  2484. nonempty_type_quals:
  2485.       TYPE_QUAL
  2486.         { $$ = IDENTIFIER_AS_LIST ($$); }
  2487.     | nonempty_type_quals TYPE_QUAL
  2488.         { $$ = decl_tree_cons (NULL_TREE, $2, $$); }
  2489.     ;
  2490.  
  2491. type_quals:
  2492.       /* empty */
  2493.         { $$ = NULL_TREE; }
  2494.     | type_quals TYPE_QUAL
  2495.         { $$ = decl_tree_cons (NULL_TREE, $2, $$); }
  2496.     ;
  2497.  
  2498. /* These rules must follow the rules for function declarations
  2499.    and component declarations.  That way, longer rules are preferred.  */
  2500.  
  2501. /* An expression which will not live on the momentary obstack.  */
  2502. nonmomentary_expr:
  2503.     { $<itype>$ = suspend_momentary (); } expr
  2504.     { resume_momentary ($<itype>1); $$ = $2; }
  2505.  
  2506. /* A declarator that is allowed only after an explicit typespec.  */
  2507. /* may all be followed by prec '.' */
  2508. after_type_declarator:
  2509.       after_type_declarator '(' nonnull_exprlist ')' type_quals  %prec '.'
  2510.         { $$ = build_parse_node (CALL_EXPR, $$, $3, $5); }
  2511.     | after_type_declarator '(' parmlist ')' type_quals  %prec '.'
  2512.         { $$ = build_parse_node (CALL_EXPR, $$, $3, $5); }
  2513.     | after_type_declarator LEFT_RIGHT type_quals  %prec '.'
  2514.         { $$ = build_parse_node (CALL_EXPR, $$, empty_parms (), $3); }
  2515.     | after_type_declarator '(' error ')' type_quals  %prec '.'
  2516.         { $$ = build_parse_node (CALL_EXPR, $$, NULL_TREE, NULL_TREE); }
  2517.     | after_type_declarator '[' nonmomentary_expr ']'
  2518.         { $$ = build_parse_node (ARRAY_REF, $$, $3); }
  2519.     | after_type_declarator '[' ']'
  2520.         { $$ = build_parse_node (ARRAY_REF, $$, NULL_TREE); }
  2521.     | '(' after_type_declarator_no_typename ')'
  2522.         { $$ = $2; }
  2523.     | '(' '*' type_quals after_type_declarator ')'
  2524.         { $$ = make_pointer_declarator ($3, $4); }
  2525.     | PAREN_STAR_PAREN
  2526.         { see_typename (); }
  2527.     | after_type_member_declarator
  2528.     | '(' '&' type_quals after_type_declarator ')'
  2529.         { $$ = make_reference_declarator ($3, $4); }
  2530.     | '*' type_quals after_type_declarator  %prec UNARY
  2531.         { $$ = make_pointer_declarator ($2, $3); }
  2532.     | '&' type_quals after_type_declarator  %prec UNARY
  2533.         { $$ = make_reference_declarator ($2, $3); }
  2534.     | TYPENAME
  2535.     ;
  2536.  
  2537. after_type_declarator_no_typename:
  2538.       after_type_declarator_no_typename '(' nonnull_exprlist ')' type_quals  %prec '.'
  2539.         { $$ = build_parse_node (CALL_EXPR, $$, $3, $5); }
  2540.     | after_type_declarator_no_typename '(' parmlist ')' type_quals  %prec '.'
  2541.         { $$ = build_parse_node (CALL_EXPR, $$, $3, $5); }
  2542.     | after_type_declarator_no_typename LEFT_RIGHT type_quals  %prec '.'
  2543.         { $$ = build_parse_node (CALL_EXPR, $$, empty_parms (), $3); }
  2544.     | after_type_declarator_no_typename '(' error ')' type_quals  %prec '.'
  2545.         { $$ = build_parse_node (CALL_EXPR, $$, NULL_TREE, NULL_TREE); }
  2546.     | after_type_declarator_no_typename '[' nonmomentary_expr ']'
  2547.         { $$ = build_parse_node (ARRAY_REF, $$, $3); }
  2548.     | after_type_declarator_no_typename '[' ']'
  2549.         { $$ = build_parse_node (ARRAY_REF, $$, NULL_TREE); }
  2550.     | '(' after_type_declarator_no_typename ')'
  2551.         { $$ = $2; }
  2552.     | PAREN_STAR_PAREN
  2553.         { see_typename (); }
  2554.     | after_type_member_declarator
  2555.     | '*' type_quals after_type_declarator  %prec UNARY
  2556.         { $$ = make_pointer_declarator ($2, $3); }
  2557.     | '&' type_quals after_type_declarator  %prec UNARY
  2558.         { $$ = make_reference_declarator ($2, $3); }
  2559.     ;
  2560.  
  2561. /* A declarator allowed whether or not there has been
  2562.    an explicit typespec.  These cannot redeclare a typedef-name.  */
  2563.  
  2564. notype_declarator:
  2565.       notype_declarator '(' nonnull_exprlist ')' type_quals  %prec '.'
  2566.         { $$ = build_parse_node (CALL_EXPR, $$, $3, $5); }
  2567.     | notype_declarator '(' parmlist ')' type_quals  %prec '.'
  2568.         { $$ = build_parse_node (CALL_EXPR, $$, $3, $5); }
  2569.     | notype_declarator LEFT_RIGHT type_quals  %prec '.'
  2570.         { $$ = build_parse_node (CALL_EXPR, $$, empty_parms (), $3); }
  2571.     | notype_declarator '(' error ')' type_quals  %prec '.'
  2572.         { $$ = build_parse_node (CALL_EXPR, $$, NULL_TREE, NULL_TREE); }
  2573.     | '(' notype_declarator ')'
  2574.         { $$ = $2; }
  2575.     | '*' type_quals notype_declarator  %prec UNARY
  2576.         { $$ = make_pointer_declarator ($2, $3); }
  2577.     | '&' type_quals notype_declarator  %prec UNARY
  2578.         { $$ = make_reference_declarator ($2, $3); }
  2579.     | notype_declarator '[' nonmomentary_expr ']'
  2580.         { $$ = build_parse_node (ARRAY_REF, $$, $3); }
  2581.     | notype_declarator '[' ']'
  2582.         { $$ = build_parse_node (ARRAY_REF, $$, NULL_TREE); }
  2583.     | IDENTIFIER
  2584.         { see_typename (); }
  2585.  
  2586.     /* C++ extensions.  */
  2587.     | operator_name
  2588.         { see_typename (); }
  2589.  
  2590.     | '~' TYPENAME
  2591.         {
  2592.         destructor_name:
  2593.           see_typename ();
  2594.           $$ = build_parse_node (BIT_NOT_EXPR, $2);
  2595.         }
  2596.     | '~' IDENTIFIER
  2597.         { goto destructor_name; }
  2598.         | '~' PTYPENAME
  2599.                 { goto destructor_name; }
  2600.     | scoped_id see_typename notype_declarator  %prec '('
  2601.         { see_typename ();
  2602.           if (TREE_CODE ($$) != SCOPE_REF)
  2603.             $$ = build_push_scope ($$, $3);
  2604.           else if (TREE_OPERAND ($$, 1) == NULL_TREE)
  2605.             TREE_OPERAND ($$, 1) = $3;
  2606.           else
  2607.             $$ = build_parse_node (SCOPE_REF, $$, $3);
  2608.         }
  2609.     | scoped_id see_typename TYPENAME  %prec '('
  2610.         { $$ = build_push_scope ($$, $3); }
  2611.     | scoped_id see_typename TYPENAME '(' nonnull_exprlist ')' type_quals  %prec '.'
  2612.         { $$ = build_push_scope ($$, build_parse_node (CALL_EXPR, $3, $5, $7)); }
  2613.     | scoped_id see_typename TYPENAME '(' parmlist ')' type_quals  %prec '.'
  2614.         { $$ = build_push_scope ($$, build_parse_node (CALL_EXPR, $3, $5, $7)); }
  2615.     | scoped_id see_typename TYPENAME LEFT_RIGHT type_quals  %prec '.'
  2616.         { $$ = build_push_scope ($$, build_parse_node (CALL_EXPR, $3, empty_parms (), $5)); }
  2617.     | scoped_id see_typename TYPENAME '(' error ')' type_quals  %prec '.'
  2618.         { $$ = build_push_scope ($$, build_parse_node (CALL_EXPR, $3, NULL_TREE, NULL_TREE)); }
  2619.     /* For constructor templates.  */
  2620.     | scoped_id see_typename PTYPENAME  %prec '('
  2621.         { $$ = build_push_scope ($$, $3); }
  2622.     | scoped_id see_typename PTYPENAME '(' nonnull_exprlist ')' type_quals  %prec '.'
  2623.         { $$ = build_push_scope ($$, build_parse_node (CALL_EXPR, $3, $5, $7)); }
  2624.     | scoped_id see_typename PTYPENAME '(' parmlist ')' type_quals  %prec '.'
  2625.         { $$ = build_push_scope ($$, build_parse_node (CALL_EXPR, $3, $5, $7)); }
  2626.     | scoped_id see_typename PTYPENAME LEFT_RIGHT type_quals  %prec '.'
  2627.         { $$ = build_push_scope ($$, build_parse_node (CALL_EXPR, $3, empty_parms (), $5)); }
  2628.     | scoped_id see_typename PTYPENAME '(' error ')' type_quals  %prec '.'
  2629.         { $$ = build_push_scope ($$, build_parse_node (CALL_EXPR, $3, NULL_TREE, NULL_TREE)); }
  2630.     | SCOPE see_typename notype_declarator
  2631.         { $$ = build_parse_node (SCOPE_REF, NULL_TREE, $3); }
  2632.     ;
  2633.  
  2634. scoped_id:    typename_scope
  2635.         { $$ = resolve_scope_to_name (NULL_TREE, $$);
  2636.           if ($$ == NULL_TREE)
  2637.             {
  2638.               error ("undefined explicitly scoped type");
  2639.               $$ = error_mark_node; 
  2640.             }
  2641.         }
  2642.     | template_type SCOPE /* try_for_typename %prec EMPTY */
  2643.         {
  2644.                   if ($$ == error_mark_node)
  2645.                     /* leave it alone */;
  2646.                   else
  2647.             {
  2648.               $$ = resolve_scope_to_name (NULL_TREE, TYPE_IDENTIFIER ($$));
  2649.               if ($$ == NULL_TREE)
  2650.             {
  2651.               error ("undefined explicitly scoped type");
  2652.               $$ = error_mark_node; 
  2653.             }
  2654.             }
  2655. /*                  if ($3) popclass (1); */
  2656.         }
  2657.     ;
  2658.  
  2659. typename_scope:
  2660.     TYPENAME SCOPE;
  2661.  
  2662. scoped_typename: SCOPED_TYPENAME
  2663.     | template_type SCOPED_TYPENAME
  2664.         {
  2665.             /* Kludge!!! See rule "template_type" and the code
  2666.            * dealing with "template_type_seen_before_scope" in
  2667.            * yylex(). */
  2668.           $$ = $2;
  2669.         }
  2670. /*    | template_type SCOPE try_for_typename TYPENAME
  2671.         {
  2672.                   if ($$ == error_mark_node)
  2673.                     ;
  2674.           else
  2675.             {
  2676.                       $$ = build_parse_node (SCOPE_REF,
  2677.                                              TYPE_IDENTIFIER ($$),
  2678.                                              $4);
  2679.                     }
  2680.           if ($3) popclass (1);
  2681.         } */
  2682.     ;
  2683.  
  2684. absdcl1:  /* a nonempty abstract declarator */
  2685.       '(' absdcl1 ')'
  2686.         { see_typename ();
  2687.           $$ = $2; }
  2688.       /* `(typedef)1' is `int'.  */
  2689.     | '*' type_quals absdcl1  %prec EMPTY
  2690.         { $$ = make_pointer_declarator ($2, $3); }
  2691.     | '*' type_quals  %prec EMPTY
  2692.         { $$ = make_pointer_declarator ($2, NULL_TREE); }
  2693.     | PAREN_STAR_PAREN
  2694.         { see_typename (); }
  2695.     | '(' abs_member_declarator ')'
  2696.         { $$ = $2; }
  2697.     | '&' type_quals absdcl1 %prec EMPTY
  2698.         { $$ = make_reference_declarator ($2, $3); }
  2699.     | '&' type_quals %prec EMPTY
  2700.         { $$ = make_reference_declarator ($2, NULL_TREE); }
  2701.     | absdcl1 '(' parmlist ')' type_quals  %prec '.'
  2702.         { $$ = build_parse_node (CALL_EXPR, $$, $3, $5); }
  2703.     | absdcl1 LEFT_RIGHT type_quals  %prec '.'
  2704.         { $$ = build_parse_node (CALL_EXPR, $$, empty_parms (), $3); }
  2705.     | absdcl1 '[' nonmomentary_expr ']'  %prec '.'
  2706.         { $$ = build_parse_node (ARRAY_REF, $$, $3); }
  2707.     | absdcl1 '[' ']'  %prec '.'
  2708.         { $$ = build_parse_node (ARRAY_REF, $$, NULL_TREE); }
  2709.     | '(' parmlist ')' type_quals  %prec '.'
  2710.         { $$ = build_parse_node (CALL_EXPR, NULL_TREE, $2, $4); }
  2711.     | LEFT_RIGHT type_quals  %prec '.'
  2712.         { $$ = build_parse_node (CALL_EXPR, NULL_TREE, empty_parms (), $2); }
  2713.     | '[' nonmomentary_expr ']'  %prec '.'
  2714.         { $$ = build_parse_node (ARRAY_REF, NULL_TREE, $2); }
  2715.     | '[' ']'  %prec '.'
  2716.         { $$ = build_parse_node (ARRAY_REF, NULL_TREE, NULL_TREE); }
  2717.     ;
  2718.  
  2719. abs_member_declarator:
  2720.       scoped_id '*' type_quals
  2721.         { tree t;
  2722.           t = $$;
  2723.           while (TREE_OPERAND (t, 1))
  2724.             t = TREE_OPERAND (t, 1);
  2725.           TREE_OPERAND (t, 1) = build_parse_node (INDIRECT_REF, 0);
  2726.         }
  2727.     | scoped_id '*' type_quals absdcl1
  2728.         { tree t;
  2729.           t = $$;
  2730.           while (TREE_OPERAND (t, 1))
  2731.             t = TREE_OPERAND (t, 1);
  2732.           TREE_OPERAND (t, 1) = build_parse_node (INDIRECT_REF, $4);
  2733.         }
  2734.     | scoped_id '&' type_quals
  2735.         { tree t;
  2736.           t = $$;
  2737.           while (TREE_OPERAND (t, 1))
  2738.             t = TREE_OPERAND (t, 1);
  2739.           TREE_OPERAND (t, 1) = build_parse_node (ADDR_EXPR, 0);
  2740.         }
  2741.     | scoped_id '&' type_quals absdcl1
  2742.         { tree t;
  2743.           t = $$;
  2744.           while (TREE_OPERAND (t, 1))
  2745.             t = TREE_OPERAND (t, 1);
  2746.           TREE_OPERAND (t, 1) = build_parse_node (ADDR_EXPR, $4);
  2747.         }
  2748.     ;
  2749.  
  2750. after_type_member_declarator:
  2751.       scoped_id see_typename '*' type_quals after_type_declarator
  2752.         { tree t;
  2753.           t = $$;
  2754.           while (TREE_OPERAND (t, 1))
  2755.             t = TREE_OPERAND (t, 1);
  2756.           TREE_OPERAND (t, 1) = build_parse_node (INDIRECT_REF, $5);
  2757.         }
  2758.     | scoped_id see_typename '&' type_quals after_type_declarator
  2759.         { tree t;
  2760.           t = $$;
  2761.           while (TREE_OPERAND (t, 1))
  2762.             t = TREE_OPERAND (t, 1);
  2763.           TREE_OPERAND (t, 1) = build_parse_node (ADDR_EXPR, $5);
  2764.         }
  2765.     ;
  2766.  
  2767. /* For C++, decls and stmts can be intermixed, so we don't need to
  2768.    have a special rule that won't start parsing the stmt section
  2769.    until we have a stmt that parses without errors.  */
  2770.  
  2771. stmts:
  2772.       stmt
  2773.     | errstmt
  2774.     | stmts stmt
  2775.     | stmts errstmt
  2776.     ;
  2777.  
  2778. errstmt:  error ';'
  2779.     ;
  2780.  
  2781. /* build the LET_STMT node before parsing its contents,
  2782.   so that any LET_STMTs within the context can have their display pointers
  2783.   set up to point at this one.  */
  2784.  
  2785. .pushlevel:  /* empty */
  2786.         { emit_line_note (input_filename, lineno);
  2787.           pushlevel (0);
  2788.           clear_last_expr ();
  2789.           push_momentary ();
  2790.           expand_start_bindings (0);
  2791.           $$ = stmt_decl_msg;
  2792.           stmt_decl_msg = 0; }
  2793.     ;
  2794.  
  2795. /* Read zero or more forward-declarations for labels
  2796.    that nested functions can jump to.  */
  2797. maybe_label_decls:
  2798.       /* empty */
  2799.     | label_decls
  2800.         { if (pedantic)
  2801.             pedwarn ("ANSI C++ forbids label declarations"); }
  2802.     ;
  2803.  
  2804. label_decls:
  2805.       label_decl
  2806.     | label_decls label_decl
  2807.     ;
  2808.  
  2809. label_decl:
  2810.       LABEL identifiers_or_typenames ';'
  2811.         { tree link;
  2812.           for (link = $2; link; link = TREE_CHAIN (link))
  2813.             {
  2814.               tree label = shadow_label (TREE_VALUE (link));
  2815.               C_DECLARED_LABEL_FLAG (label) = 1;
  2816.               declare_nonlocal_label (label);
  2817.             }
  2818.         }
  2819.     ;
  2820.  
  2821. /* This is the body of a function definition.
  2822.    It causes syntax errors to ignore to the next openbrace.  */
  2823. compstmt_or_error:
  2824.       compstmt
  2825.         {}
  2826.     | error compstmt
  2827.     ;
  2828.  
  2829. compstmt: '{' '}'
  2830.         { $$ = convert (void_type_node, integer_zero_node); }
  2831.     | '{' .pushlevel maybe_label_decls stmts '}'
  2832.         { pop_implicit_try_blocks (NULL_TREE);
  2833.           stmt_decl_msg = $2;
  2834.           expand_end_bindings (getdecls (), kept_level_p (), 1);
  2835.           $$ = poplevel (kept_level_p (), 1, 0);
  2836.           pop_momentary (); }
  2837.     | '{' .pushlevel maybe_label_decls error '}'
  2838.         { pop_implicit_try_blocks (NULL_TREE);
  2839.           stmt_decl_msg = $2;
  2840.           expand_end_bindings (getdecls (), kept_level_p (), 1);
  2841.           $$ = poplevel (kept_level_p (), 0, 0);
  2842.           pop_momentary (); }
  2843.     ;
  2844.  
  2845. simple_if:
  2846.       IF '(' expr ')'
  2847.         { emit_line_note (input_filename, lineno);
  2848.           expand_start_cond (truthvalue_conversion ($3), 0);
  2849.           stmt_decl_msg = "if"; }
  2850.       stmt
  2851.         { stmt_decl_msg = 0; }
  2852.     ;
  2853.  
  2854. stmt:
  2855.       compstmt
  2856.         { finish_stmt (); }
  2857.     | decl
  2858.         { if (stmt_decl_msg)
  2859.             error ("declaration after %s invalid", stmt_decl_msg);
  2860.           stmt_decl_msg = 0;
  2861.           finish_stmt (); }
  2862.     | expr ';'
  2863.         {
  2864.             tree expr = $1;
  2865.           emit_line_note (input_filename, lineno);
  2866.           /* Do default conversion if safe and possibly important,
  2867.              in case within ({...}).  */
  2868.           if ((TREE_CODE (TREE_TYPE (expr)) == ARRAY_TYPE
  2869.                && lvalue_p (expr))
  2870.               || TREE_CODE (TREE_TYPE (expr)) == FUNCTION_TYPE)
  2871.             expr = default_conversion (expr);
  2872.           cplus_expand_expr_stmt (expr);
  2873.           clear_momentary ();
  2874.           finish_stmt (); }
  2875.     | simple_if ELSE
  2876.         { expand_start_else ();
  2877.           stmt_decl_msg = "else"; }
  2878.       stmt
  2879.         { expand_end_cond ();
  2880.           stmt_decl_msg = 0;
  2881.           finish_stmt (); }
  2882.     | simple_if %prec IF
  2883.         { expand_end_cond ();
  2884.           stmt_decl_msg = 0;
  2885.           finish_stmt (); }
  2886.     | WHILE
  2887.         { emit_nop ();
  2888.           emit_line_note (input_filename, lineno);
  2889.           expand_start_loop (1); }
  2890.       '(' expr ')'
  2891.         { expand_exit_loop_if_false (0, truthvalue_conversion ($4));
  2892.           stmt_decl_msg = "while"; }
  2893.       stmt
  2894.         { 
  2895.           expand_end_loop ();
  2896.           stmt_decl_msg = 0;
  2897.           finish_stmt (); }
  2898.     | DO
  2899.         { emit_nop ();
  2900.           emit_line_note (input_filename, lineno);
  2901.           expand_start_loop_continue_elsewhere (1);
  2902.           stmt_decl_msg = "do"; }
  2903.       stmt WHILE
  2904.         { stmt_decl_msg = 0;
  2905.           expand_loop_continue_here (); }
  2906.       '(' expr ')' ';'
  2907.         { emit_line_note (input_filename, lineno);
  2908.           expand_exit_loop_if_false (0, truthvalue_conversion ($7));
  2909.           expand_end_loop ();
  2910.           clear_momentary ();
  2911.           finish_stmt (); }
  2912.     | forhead.1
  2913.         { emit_nop ();
  2914.           emit_line_note (input_filename, lineno);
  2915.           if ($1) cplus_expand_expr_stmt ($1);
  2916.           expand_start_loop_continue_elsewhere (1); }
  2917.       xexpr ';'
  2918.         { emit_line_note (input_filename, lineno);
  2919.           if ($3) expand_exit_loop_if_false (0, truthvalue_conversion ($3)); }
  2920.       xexpr ')'
  2921.         /* Don't let the tree nodes for $6 be discarded
  2922.            by clear_momentary during the parsing of the next stmt.  */
  2923.         { push_momentary ();
  2924.           stmt_decl_msg = "for"; }
  2925.       stmt
  2926.         { emit_line_note (input_filename, lineno);
  2927.           expand_loop_continue_here ();
  2928.           if ($6) cplus_expand_expr_stmt ($6);
  2929.           pop_momentary ();
  2930.           expand_end_loop ();
  2931.           stmt_decl_msg = 0;
  2932.           finish_stmt (); }
  2933.     | forhead.2
  2934.         { emit_nop ();
  2935.           emit_line_note (input_filename, lineno);
  2936.           expand_start_loop_continue_elsewhere (1); }
  2937.       xexpr ';'
  2938.         { emit_line_note (input_filename, lineno);
  2939.           if ($3) expand_exit_loop_if_false (0, truthvalue_conversion ($3)); }
  2940.       xexpr ')'
  2941.         /* Don't let the tree nodes for $6 be discarded
  2942.            by clear_momentary during the parsing of the next stmt.  */
  2943.         { push_momentary ();
  2944.           stmt_decl_msg = "for";
  2945.           $<itype>7 = lineno; }
  2946.       stmt
  2947.         { emit_line_note (input_filename, $<itype>7);
  2948.           expand_loop_continue_here ();
  2949.           if ($6) cplus_expand_expr_stmt ($6);
  2950.           pop_momentary ();
  2951.           expand_end_loop ();
  2952.           pop_implicit_try_blocks (NULL_TREE);
  2953.           if ($1)
  2954.             {
  2955.               register int keep = $1 > 0;
  2956.               if (keep) expand_end_bindings (0, keep, 1);
  2957.               poplevel (keep, 1, 0);
  2958.               pop_momentary ();
  2959.             }
  2960.           stmt_decl_msg = 0;
  2961.           finish_stmt ();
  2962.         }
  2963.     | SWITCH '(' expr ')'
  2964.         { emit_line_note (input_filename, lineno);
  2965.           c_expand_start_case ($3);
  2966.           /* Don't let the tree nodes for $3 be discarded by
  2967.              clear_momentary during the parsing of the next stmt.  */
  2968.           push_momentary ();
  2969.           stmt_decl_msg = "switch"; }
  2970.       stmt
  2971.         { expand_end_case ($3);
  2972.           pop_momentary ();
  2973.           stmt_decl_msg = 0;
  2974.           finish_stmt (); }
  2975.     | CASE expr ':'
  2976.         { register tree value = $2;
  2977.           register tree label
  2978.             = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE);
  2979.  
  2980.           /* build_c_cast puts on a NOP_EXPR to make a non-lvalue.
  2981.              Strip such NOP_EXPRs.  */
  2982.           if (TREE_CODE (value) == NOP_EXPR
  2983.               && TREE_TYPE (value) == TREE_TYPE (TREE_OPERAND (value, 0)))
  2984.             value = TREE_OPERAND (value, 0);
  2985.  
  2986.           if (TREE_READONLY_DECL_P (value))
  2987.             {
  2988.               value = decl_constant_value (value);
  2989.               /* build_c_cast puts on a NOP_EXPR to make a non-lvalue.
  2990.              Strip such NOP_EXPRs.  */
  2991.               if (TREE_CODE (value) == NOP_EXPR
  2992.               && TREE_TYPE (value) == TREE_TYPE (TREE_OPERAND (value, 0)))
  2993.             value = TREE_OPERAND (value, 0);
  2994.             }
  2995.           value = fold (value);
  2996.  
  2997.           if (TREE_CODE (value) != INTEGER_CST
  2998.               && value != error_mark_node)
  2999.             {
  3000.               error ("case label does not reduce to an integer constant");
  3001.               value = error_mark_node;
  3002.             }
  3003.           else
  3004.             /* Promote char or short to int.  */
  3005.             value = default_conversion (value);
  3006.           if (value != error_mark_node)
  3007.             {
  3008.               tree duplicate;
  3009.               int success = pushcase (value, label, &duplicate);
  3010.               if (success == 1)
  3011.             error ("case label not within a switch statement");
  3012.               else if (success == 2)
  3013.             {
  3014.               error ("duplicate case value");
  3015.               error_with_decl (duplicate, "this is the first entry for that value");
  3016.             }
  3017.               else if (success == 3)
  3018.             warning ("case value out of range");
  3019.               else if (success == 5)
  3020.             error ("case label within scope of cleanup or variable array");
  3021.             }
  3022.           define_case_label (label);
  3023.         }
  3024.       stmt
  3025.     | CASE expr RANGE expr ':'
  3026.         { register tree value1 = $2;
  3027.           register tree value2 = $4;
  3028.           register tree label
  3029.             = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE);
  3030.  
  3031.           if (pedantic)
  3032.             pedwarn ("ANSI C++ forbids range expressions in switch statement");
  3033.  
  3034.           /* build_c_cast puts on a NOP_EXPR to make a non-lvalue.
  3035.              Strip such NOP_EXPRs.  */
  3036.           if (TREE_CODE (value1) == NOP_EXPR
  3037.               && TREE_TYPE (value1) == TREE_TYPE (TREE_OPERAND (value1, 0)))
  3038.             value1 = TREE_OPERAND (value1, 0);
  3039.  
  3040.           if (TREE_READONLY_DECL_P (value1))
  3041.             {
  3042.               value1 = decl_constant_value (value1);
  3043.               /* build_c_cast puts on a NOP_EXPR to make a non-lvalue.
  3044.              Strip such NOP_EXPRs.  */
  3045.               if (TREE_CODE (value1) == NOP_EXPR
  3046.               && TREE_TYPE (value1) == TREE_TYPE (TREE_OPERAND (value1, 0)))
  3047.             value1 = TREE_OPERAND (value1, 0);
  3048.             }
  3049.           value1 = fold (value1);
  3050.  
  3051.           /* build_c_cast puts on a NOP_EXPR to make a non-lvalue.
  3052.              Strip such NOP_EXPRs.  */
  3053.           if (TREE_CODE (value2) == NOP_EXPR
  3054.               && TREE_TYPE (value2) == TREE_TYPE (TREE_OPERAND (value2, 0)))
  3055.             value2 = TREE_OPERAND (value2, 0);
  3056.  
  3057.           if (TREE_READONLY_DECL_P (value2))
  3058.             {
  3059.               value2 = decl_constant_value (value2);
  3060.               /* build_c_cast puts on a NOP_EXPR to make a non-lvalue.
  3061.              Strip such NOP_EXPRs.  */
  3062.               if (TREE_CODE (value2) == NOP_EXPR
  3063.               && TREE_TYPE (value2) == TREE_TYPE (TREE_OPERAND (value2, 0)))
  3064.             value2 = TREE_OPERAND (value2, 0);
  3065.             }
  3066.           value2 = fold (value2);
  3067.  
  3068.  
  3069.           if (TREE_CODE (value1) != INTEGER_CST
  3070.               && value1 != error_mark_node)
  3071.             {
  3072.               error ("case label does not reduce to an integer constant");
  3073.               value1 = error_mark_node;
  3074.             }
  3075.           if (TREE_CODE (value2) != INTEGER_CST
  3076.               && value2 != error_mark_node)
  3077.             {
  3078.               error ("case label does not reduce to an integer constant");
  3079.               value2 = error_mark_node;
  3080.             }
  3081.           if (value1 != error_mark_node
  3082.               && value2 != error_mark_node)
  3083.             {
  3084.               tree duplicate;
  3085.               int success = pushcase_range (value1, value2, label,
  3086.                             &duplicate);
  3087.               if (success == 1)
  3088.             error ("case label not within a switch statement");
  3089.               else if (success == 2)
  3090.             {
  3091.               error ("duplicate (or overlapping) case value");
  3092.               error_with_decl (duplicate, "this is the first entry overlapping that value");
  3093.             }
  3094.               else if (success == 3)
  3095.             warning ("case value out of range");
  3096.               else if (success == 4)
  3097.             warning ("empty range specified");
  3098.               else if (success == 5)
  3099.             error ("case label within scope of cleanup or variable array");
  3100.             }
  3101.           define_case_label (label);
  3102.         }
  3103.       stmt
  3104.     | DEFAULT ':'
  3105.         {
  3106.           tree duplicate;
  3107.           register tree label
  3108.             = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE);
  3109.           int success = pushcase (NULL_TREE, label, &duplicate);
  3110.           if (success == 1)
  3111.             error ("default label not within a switch statement");
  3112.           else if (success == 2)
  3113.             {
  3114.               error ("multiple default labels in one switch");
  3115.               error_with_decl (duplicate, "this is the first default label");
  3116.             }
  3117.           define_case_label (NULL_TREE);
  3118.         }
  3119.       stmt
  3120.     | BREAK ';'
  3121.         { emit_line_note (input_filename, lineno);
  3122.           if ( ! expand_exit_something ())
  3123.             error ("break statement not within loop or switch"); }
  3124.     | CONTINUE ';'
  3125.         { emit_line_note (input_filename, lineno);
  3126.           if (! expand_continue_loop (0))
  3127.             error ("continue statement not within a loop"); }
  3128.     | RETURN ';'
  3129.         { emit_line_note (input_filename, lineno);
  3130.           c_expand_return (NULL_TREE); }
  3131.     | RETURN expr ';'
  3132.         { emit_line_note (input_filename, lineno);
  3133.           c_expand_return ($2);
  3134.           finish_stmt ();
  3135.         }
  3136.     | ASM_KEYWORD maybe_type_qual '(' string ')' ';'
  3137.         { if (TREE_CHAIN ($4)) $4 = combine_strings ($4);
  3138.           emit_line_note (input_filename, lineno);
  3139.           expand_asm ($4);
  3140.           finish_stmt ();
  3141.         }
  3142.     /* This is the case with just output operands.  */
  3143.     | ASM_KEYWORD maybe_type_qual '(' string ':' asm_operands ')' ';'
  3144.         { if (TREE_CHAIN ($4)) $4 = combine_strings ($4);
  3145.           emit_line_note (input_filename, lineno);
  3146.           c_expand_asm_operands ($4, $6, NULL_TREE, NULL_TREE,
  3147.                      $2 == ridpointers[(int)RID_VOLATILE],
  3148.                      input_filename, lineno);
  3149.           finish_stmt ();
  3150.         }
  3151.     /* This is the case with input operands as well.  */
  3152.     | ASM_KEYWORD maybe_type_qual '(' string ':' asm_operands ':' asm_operands ')' ';'
  3153.         { if (TREE_CHAIN ($4)) $4 = combine_strings ($4);
  3154.           emit_line_note (input_filename, lineno);
  3155.           c_expand_asm_operands ($4, $6, $8, NULL_TREE,
  3156.                      $2 == ridpointers[(int)RID_VOLATILE],
  3157.                      input_filename, lineno);
  3158.           finish_stmt ();
  3159.         }
  3160.     /* This is the case with clobbered registers as well.  */
  3161.     | ASM_KEYWORD maybe_type_qual '(' string ':' asm_operands ':'
  3162.         asm_operands ':' asm_clobbers ')' ';'
  3163.         { if (TREE_CHAIN ($4)) $4 = combine_strings ($4);
  3164.           emit_line_note (input_filename, lineno);
  3165.           c_expand_asm_operands ($4, $6, $8, $10,
  3166.                      $2 == ridpointers[(int)RID_VOLATILE],
  3167.                      input_filename, lineno);
  3168.           finish_stmt ();
  3169.         }
  3170.     | GOTO '*' expr ';'
  3171.         { emit_line_note (input_filename, lineno);
  3172.           expand_computed_goto ($3); }
  3173.     | GOTO identifier ';'
  3174.         { tree decl;
  3175.           emit_line_note (input_filename, lineno);
  3176.           decl = lookup_label ($2);
  3177.           TREE_USED (decl) = 1;
  3178.           expand_goto (decl); }
  3179.     | label_colon stmt
  3180.         { finish_stmt (); }
  3181.     | label_colon '}'
  3182.         { error ("label must be followed by statement");
  3183.           yyungetc ('}', 0);
  3184.           finish_stmt (); }
  3185.     | ';'
  3186.         { finish_stmt (); }
  3187.  
  3188.     /* Exception handling extensions.  */
  3189.     | ANSI_THROW ';' { cplus_expand_throw (NULL_TREE); }
  3190.     | ANSI_THROW expr ';' { cplus_expand_throw ($2); }
  3191.     | THROW raise_identifier '(' nonnull_exprlist ')' ';'
  3192.         { cplus_expand_raise ($2, $4, NULL_TREE, 0);
  3193.           finish_stmt (); }
  3194.     | THROW raise_identifier LEFT_RIGHT ';'
  3195.         { cplus_expand_raise ($2, NULL_TREE, NULL_TREE, 0);
  3196.           finish_stmt (); }
  3197.     | RAISE raise_identifier '(' nonnull_exprlist ')' ';'
  3198.         { cplus_expand_raise ($2, $4, NULL_TREE, 0);
  3199.           finish_stmt (); }
  3200.     | RAISE raise_identifier LEFT_RIGHT ';'
  3201.         { cplus_expand_raise ($2, NULL_TREE, NULL_TREE, 0);
  3202.           finish_stmt (); }
  3203.     | RAISE identifier ';'
  3204.         { cplus_expand_reraise ($2);
  3205.           finish_stmt (); }
  3206.     | try EXCEPT identifier '{'
  3207.         {
  3208.           tree decl = cplus_expand_end_try ($1);
  3209.           $<ttype>2 = current_exception_type;
  3210.           $<ttype>4 = current_exception_decl;
  3211.           $<ttype>$ = current_exception_object;
  3212.           cplus_expand_start_except ($3, decl);
  3213.           pushlevel (0);
  3214.           clear_last_expr ();
  3215.           push_momentary ();
  3216.           expand_start_bindings (0);
  3217.           stmt_decl_msg = 0;
  3218.         }
  3219.       except_stmts '}'
  3220.         {
  3221.           tree decls = getdecls ();
  3222.           /* If there is a default exception to handle,
  3223.              handle it here.  */
  3224.           if ($6)
  3225.             {
  3226.               tree decl = build_decl (CPLUS_CATCH_DECL, NULL_TREE, 0);
  3227.               tree block;
  3228.  
  3229.               pushlevel (1);
  3230.               expand_start_bindings (0);
  3231.               expand_expr ($6, 0, 0, 0);
  3232.               expand_end_bindings (0, 1, 0);
  3233.               block = poplevel (1, 0, 0);
  3234.  
  3235.               /* This is a catch block.  */
  3236.               TREE_LANG_FLAG_2 (block) = 1;
  3237.               BLOCK_VARS (block) = decl;
  3238.             }
  3239.  
  3240.           expand_end_bindings (decls, decls != 0, 1);
  3241.           poplevel (decls != 0, 1, 0);
  3242.           pop_momentary ();
  3243.           current_exception_type = $<ttype>2;
  3244.           current_exception_decl = $<ttype>4;
  3245.           current_exception_object = $<ttype>5;
  3246.           cplus_expand_end_except ($6);
  3247.         }
  3248.     | try error
  3249.         {
  3250.           cplus_expand_end_try ($1);
  3251.           /* These are the important actions of
  3252.              `cplus_expand_end_except' which we must emulate.  */
  3253.           if (expand_escape_except ())
  3254.             expand_end_except ();
  3255.           expand_end_bindings (0, 0, 1);
  3256.           poplevel (0, 0, 0);
  3257.         }
  3258.     | ansi_try ansi_dummy ansi_dummy
  3259.         {
  3260.           tree decl = cplus_expand_end_try ($1);
  3261.           $<ttype>2 = current_exception_type;
  3262.           $<ttype>3 = current_exception_decl;
  3263.           $<ttype>$ = current_exception_object;
  3264.           cplus_expand_start_except (NULL, decl);
  3265.           pushlevel (0);
  3266.           clear_last_expr ();
  3267.           push_momentary ();
  3268.           expand_start_bindings (0);
  3269.           stmt_decl_msg = 0;
  3270.         }
  3271.       ansi_except_stmts
  3272.         {
  3273.           tree decls = getdecls ();
  3274.           /* If there is a default exception to handle,
  3275.              handle it here.  */
  3276.           if ($5)
  3277.             {
  3278.               tree decl = build_decl (CPLUS_CATCH_DECL, NULL_TREE, 0);
  3279.               tree block;
  3280.  
  3281.               pushlevel (1);
  3282.               expand_start_bindings (0);
  3283.               expand_expr ($5, 0, 0, 0);
  3284.               expand_end_bindings (0, 1, 0);
  3285.               block = poplevel (1, 0, 0);
  3286.  
  3287.               /* This is a catch block.  */
  3288.               TREE_LANG_FLAG_2 (block) = 1;
  3289.               BLOCK_VARS (block) = decl;
  3290.             }
  3291.  
  3292.           expand_end_bindings (decls, decls != 0, 1);
  3293.           poplevel (decls != 0, 1, 0);
  3294.           pop_momentary ();
  3295.           current_exception_type = $<ttype>2;
  3296.           current_exception_decl = $<ttype>3;
  3297.           current_exception_object = $<ttype>4;
  3298.           cplus_expand_end_except ($5);
  3299.         }
  3300.     | try RERAISE raise_identifiers /* ';' checked for at bottom.  */
  3301.         { tree name = get_identifier ("(compiler error)");
  3302.           tree orig_ex_type = current_exception_type;
  3303.           tree orig_ex_decl = current_exception_decl;
  3304.           tree orig_ex_obj = current_exception_object;
  3305.           tree decl = cplus_expand_end_try ($1), decls;
  3306.  
  3307.           /* Start hidden EXCEPT.  */
  3308.           cplus_expand_start_except (name, decl);
  3309.           pushlevel (0);
  3310.           clear_last_expr ();
  3311.           push_momentary ();
  3312.           expand_start_bindings (0);
  3313.           stmt_decl_msg = 0;
  3314.  
  3315.           /* This sets up the reraise.  */
  3316.           cplus_expand_reraise ($3);
  3317.  
  3318.           decls = getdecls ();
  3319.           expand_end_bindings (decls, decls != 0, 1);
  3320.           poplevel (decls != 0, 1, 0);
  3321.           pop_momentary ();
  3322.           current_exception_type = orig_ex_type;
  3323.           current_exception_decl = orig_ex_decl;
  3324.           current_exception_object = orig_ex_obj;
  3325.           /* This will reraise for us.  */
  3326.           cplus_expand_end_except (error_mark_node);
  3327.           if (yychar == YYEMPTY)
  3328.             yychar = YYLEX;
  3329.           if (yychar != ';')
  3330.             error ("missing ';' after reraise statement");
  3331.         }
  3332.     | try  %prec EMPTY
  3333.         { yyerror ("`except' missing after `try' statement");
  3334.           /* Terminate the binding contour started by special
  3335.              code in `.pushlevel'.  Automagically pops off
  3336.              the conditional we started for `try' stmt.  */
  3337.           cplus_expand_end_try ($1);
  3338.           expand_end_bindings (0, 0, 1);
  3339.           poplevel (0, 0, 0);
  3340.           pop_momentary ();
  3341.           YYERROR; }
  3342.     ;
  3343.  
  3344. try:      try_head '}'
  3345.         /* An empty try block is degenerate, but it's better to
  3346.            do extra work here than to do all the special-case work
  3347.            everywhere else.  */
  3348.         {
  3349.           $$ = 1;
  3350.           pop_implicit_try_blocks (NULL_TREE);
  3351.         }
  3352.     | try_head stmts '}'
  3353.         {
  3354.           $$ = 1;
  3355.           pop_implicit_try_blocks (NULL_TREE);
  3356.         }
  3357.     | try_head error '}'
  3358.         {
  3359.           $$ = 0;
  3360.           pop_implicit_try_blocks (NULL_TREE);
  3361.         }
  3362.     ;
  3363.  
  3364. label_colon:
  3365.       IDENTIFIER ':'
  3366.         { tree label;
  3367.         do_label:
  3368.           label = define_label (input_filename, lineno, $1);
  3369.           if (label)
  3370.             expand_label (label);
  3371.         }
  3372.     | PTYPENAME ':'
  3373.         { goto do_label; }
  3374.     | TYPENAME_COLON
  3375.         { tree label = define_label (input_filename, lineno, $1);
  3376.           if (label)
  3377.             expand_label (label);
  3378.         }
  3379.     ;
  3380.  
  3381. try_head: TRY '{' { cplus_expand_start_try (0); } .pushlevel
  3382.  
  3383. ansi_try:      ansi_try_head '}'
  3384.         /* An empty try block is degenerate, but it's better to
  3385.            do extra work here than to do all the special-case work
  3386.            everywhere else.  */
  3387.         {
  3388.           $$ = 1;
  3389.           pop_implicit_try_blocks (NULL_TREE);
  3390.         }
  3391.     | ansi_try_head stmts '}'
  3392.         {
  3393.           $$ = 1;
  3394.           pop_implicit_try_blocks (NULL_TREE);
  3395.         }
  3396.     | ansi_try_head error '}'
  3397.         {
  3398.           $$ = 0;
  3399.           pop_implicit_try_blocks (NULL_TREE);
  3400.         }
  3401.     ;
  3402.  
  3403. ansi_dummy: ; /* Temporary place-holder. */
  3404. ansi_try_head: ANSI_TRY '{' { cplus_expand_start_try (0); } .pushlevel
  3405.  
  3406. except_stmts:
  3407.       /* empty */
  3408.         { $$ = NULL_TREE; }
  3409.     | except_stmts raise_identifier
  3410.         {
  3411.           tree type = lookup_exception_type (current_class_type, current_class_name, $2);
  3412.           if (type == NULL_TREE)
  3413.             {
  3414.               error ("`%s' is not an exception type",
  3415.                  IDENTIFIER_POINTER (TREE_VALUE ($2)));
  3416.               current_exception_type = NULL_TREE;
  3417.               TREE_TYPE (current_exception_object) = error_mark_node;
  3418.             }
  3419.           else
  3420.             {
  3421.               current_exception_type = type;
  3422.               /* In-place union.  */
  3423.               TREE_TYPE (current_exception_object) = type;
  3424.             }
  3425.           $2 = cplus_expand_start_catch ($2);
  3426.           pushlevel (1);
  3427.           expand_start_bindings (0);
  3428.         }
  3429.       compstmt
  3430.         {
  3431.           expand_end_bindings (0, 1, 0);
  3432.           $4 = poplevel (1, 0, 0);
  3433.  
  3434.           cplus_expand_end_catch (0);
  3435.  
  3436.           /* Mark this as a catch block.  */
  3437.           TREE_LANG_FLAG_2 ($4) = 1;
  3438.           if ($2 != error_mark_node)
  3439.             {
  3440.               tree decl = build_decl (CPLUS_CATCH_DECL, DECL_NAME ($2), 0);
  3441.               DECL_RTL (decl) = DECL_RTL ($2);
  3442.               TREE_CHAIN (decl) = BLOCK_VARS ($4);
  3443.               BLOCK_VARS ($4) = decl;
  3444.             }
  3445.         }
  3446.     | except_stmts DEFAULT
  3447.         {
  3448.           if ($1)
  3449.             error ("duplicate default in exception handler");
  3450.           current_exception_type = NULL_TREE;
  3451.           /* Takes it right out of scope.  */
  3452.           TREE_TYPE (current_exception_object) = error_mark_node;
  3453.  
  3454.           if (! expand_catch_default ())
  3455.             compiler_error ("default catch botch");
  3456.  
  3457.           /* The default exception is handled as the
  3458.              last in the chain of exceptions handled.  */
  3459.           do_pending_stack_adjust ();
  3460.           start_sequence ();
  3461.           $1 = make_node (RTL_EXPR);
  3462.           TREE_TYPE ($1) = void_type_node;
  3463.         }
  3464.       compstmt
  3465.         {
  3466.           extern struct rtx_def *get_insns ();
  3467.           do_pending_stack_adjust ();
  3468.           if (! expand_catch (NULL_TREE))
  3469.             compiler_error ("except nesting botch");
  3470.           if (! expand_end_catch ())
  3471.             compiler_error ("except nesting botch");
  3472.           RTL_EXPR_SEQUENCE ($1) = get_insns ();
  3473.           if ($4)
  3474.             {
  3475.               /* Mark this block as the default catch block.  */
  3476.               TREE_LANG_FLAG_1 ($4) = 1;
  3477.               TREE_LANG_FLAG_2 ($4) = 1;
  3478.             }
  3479.           end_sequence ();
  3480.         }
  3481.     ;
  3482.  
  3483. optional_identifier:
  3484.       /* empty */
  3485.         { $$ = NULL_TREE; }
  3486.     | identifier ;
  3487.  
  3488. ansi_except_stmts:
  3489.       /* empty */
  3490.         { $$ = NULL_TREE; }
  3491.     | ansi_except_stmts CATCH '(' typename optional_identifier ')'
  3492.         {
  3493.           extern tree ansi_expand_start_catch ();
  3494.           extern tree cplus_exception_name ();
  3495.           tree type = groktypename ($4);
  3496.           current_exception_type = type;
  3497.           /* In-place union.  */
  3498.           if ($5)
  3499.             {
  3500.               tree tmp;
  3501.               tmp = pushdecl (build_decl (VAR_DECL, $5, type));
  3502.               current_exception_object =
  3503.                   build1 (INDIRECT_REF, type, tmp);
  3504.              }
  3505.           $4 = ansi_expand_start_catch(type);
  3506.           pushlevel (1);
  3507.           expand_start_bindings (0);
  3508.         }
  3509.       compstmt
  3510.         {
  3511.           expand_end_bindings (0, 1, 0);
  3512.           $8 = poplevel (1, 0, 0);
  3513.  
  3514.           cplus_expand_end_catch (0);
  3515.  
  3516.           /* Mark this as a catch block.  */
  3517.           TREE_LANG_FLAG_2 ($8) = 1;
  3518.           if ($4 != error_mark_node)
  3519.             {
  3520.               tree decl = build_decl (CPLUS_CATCH_DECL, DECL_NAME ($4), 0);
  3521.               DECL_RTL (decl) = DECL_RTL ($4);
  3522.               TREE_CHAIN (decl) = BLOCK_VARS ($8);
  3523.               BLOCK_VARS ($8) = decl;
  3524.             }
  3525.         }
  3526.     ;
  3527.  
  3528. forhead.1:
  3529.       FOR '(' ';'
  3530.         { $$ = NULL_TREE; }
  3531.     | FOR '(' expr ';'
  3532.         { $$ = $3; }
  3533.     | FOR '(' '{' '}'
  3534.         { $$ = NULL_TREE; }
  3535.     ;
  3536.  
  3537. forhead.2:
  3538.       FOR '(' decl
  3539.         { $$ = 0; }
  3540.     | FOR '(' error ';'
  3541.         { $$ = 0; }
  3542.     | FOR '(' '{' .pushlevel stmts '}'
  3543.         { $$ = 1; }
  3544.     | FOR '(' '{' .pushlevel error '}'
  3545.         { $$ = -1; }
  3546.     ;
  3547.  
  3548. /* Either a type-qualifier or nothing.  First thing in an `asm' statement.  */
  3549.  
  3550. maybe_type_qual:
  3551.     /* empty */
  3552.         { if (pedantic)
  3553.             pedwarn ("ANSI C++ forbids use of `asm' keyword");
  3554.           emit_line_note (input_filename, lineno); }
  3555.     | TYPE_QUAL
  3556.         { if (pedantic)
  3557.             pedwarn ("ANSI C++ forbids use of `asm' keyword");
  3558.           emit_line_note (input_filename, lineno); }
  3559.     ;
  3560.  
  3561. xexpr:
  3562.     /* empty */
  3563.         { $$ = NULL_TREE; }
  3564.     | expr
  3565.     | error
  3566.         { $$ = NULL_TREE; }
  3567.     ;
  3568.  
  3569. /* These are the operands other than the first string and colon
  3570.    in  asm ("addextend %2,%1": "=dm" (x), "0" (y), "g" (*x))  */
  3571. asm_operands: /* empty */
  3572.         { $$ = NULL_TREE; }
  3573.     | nonnull_asm_operands
  3574.     ;
  3575.  
  3576. nonnull_asm_operands:
  3577.       asm_operand
  3578.     | nonnull_asm_operands ',' asm_operand
  3579.         { $$ = chainon ($$, $3); }
  3580.     ;
  3581.  
  3582. asm_operand:
  3583.       STRING '(' expr ')'
  3584.         { $$ = build_tree_list ($$, $3); }
  3585.     ;
  3586.  
  3587. asm_clobbers:
  3588.       STRING
  3589.         { $$ = tree_cons (NULL_TREE, $$, NULL_TREE); }
  3590.     | asm_clobbers ',' STRING
  3591.         { $$ = tree_cons (NULL_TREE, $3, $$); }
  3592.     ;
  3593.  
  3594. /* This is what appears inside the parens in a function declarator.
  3595.    Its value is represented in the format that grokdeclarator expects.
  3596.  
  3597.    In C++, declaring a function with no parameters
  3598.    means that that function takes *no* parameters.  */
  3599. parmlist:  /* empty */
  3600.         {
  3601.           if (strict_prototype)
  3602.             $$ = void_list_node;
  3603.           else
  3604.             $$ = NULL_TREE;
  3605.         }
  3606.     | parms
  3607.           {
  3608.           $$ = chainon ($$, void_list_node);
  3609.           TREE_PARMLIST ($$) = 1;
  3610.         }
  3611.     | parms ',' ELLIPSIS
  3612.         {
  3613.           TREE_PARMLIST ($$) = 1;
  3614.         }
  3615.     /* C++ allows an ellipsis without a separating ',' */
  3616.     | parms ELLIPSIS
  3617.         {
  3618.           TREE_PARMLIST ($$) = 1;
  3619.         }
  3620.     | ELLIPSIS
  3621.         {
  3622.           /* ARM $8.2.5 has this as a boxed-off comment.  */
  3623.           if (pedantic)
  3624.             warning ("use of `...' without a first argument is non-portable");
  3625.           $$ = NULL_TREE;
  3626.         }
  3627.     | TYPENAME_ELLIPSIS
  3628.         {
  3629.           TREE_PARMLIST ($$) = 1;
  3630.         }
  3631.     | parms TYPENAME_ELLIPSIS
  3632.         {
  3633.           TREE_PARMLIST ($$) = 1;
  3634.         }
  3635.     | parms ':'
  3636.         {
  3637.           /* This helps us recover from really nasty
  3638.              parse errors, for example, a missing right
  3639.              parenthesis.  */
  3640.           yyerror ("possibly missing ')'");
  3641.           $$ = chainon ($$, void_list_node);
  3642.           TREE_PARMLIST ($$) = 1;
  3643.           yyungetc (':', 0);
  3644.           yychar = ')';
  3645.         }
  3646.     ;
  3647.  
  3648. /* A nonempty list of parameter declarations or type names.  */
  3649. parms:
  3650.       parm
  3651.         { $$ = build_tree_list (NULL_TREE, $$); }
  3652.     | parm '=' init
  3653.         { $$ = build_tree_list ($3, $$); }
  3654.     | parms ',' parm
  3655.         { $$ = chainon ($$, build_tree_list (NULL_TREE, $3)); }
  3656.     | parms ',' parm '=' init
  3657.         { $$ = chainon ($$, build_tree_list ($5, $3)); }
  3658.     | parms ',' bad_parm
  3659.         { $$ = chainon ($$, build_tree_list (NULL_TREE, $3)); }
  3660.     | parms ',' bad_parm '=' init
  3661.         { $$ = chainon ($$, build_tree_list ($5, $3)); }
  3662.     ;
  3663.  
  3664. /* A single parameter declaration or parameter type name,
  3665.    as found in a parmlist.  The first four cases make up for 10%
  3666.    of the time spent parsing C++.  We cannot use them because
  3667.    of `int id[]' which won't get parsed properly.  */
  3668. parm:
  3669. /*
  3670.       typed_declspecs dont_see_typename '*' IDENTIFIER
  3671.         { $$ = build_tree_list ($$, build_parse_node (INDIRECT_REF, $4));
  3672.           see_typename (); }
  3673.     | typed_declspecs dont_see_typename '&' IDENTIFIER
  3674.         { $$ = build_tree_list ($$, build_parse_node (ADDR_EXPR, $4));
  3675.           see_typename (); }
  3676.     | TYPENAME IDENTIFIER
  3677.         { $$ = build_tree_list (list_hash_lookup_or_cons ($$), $2);  }
  3678.     | TYPESPEC IDENTIFIER
  3679.         { $$ = build_tree_list (list_hash_lookup_or_cons ($$), $2); }
  3680.     | */
  3681.       typed_declspecs dont_see_typename abs_or_notype_decl
  3682.         { $$ = build_tree_list ($$, $3);
  3683.           see_typename (); }
  3684.     | declmods dont_see_typename abs_or_notype_decl
  3685.         { $$ = build_tree_list ($$, $3);
  3686.           see_typename (); }
  3687.     ;
  3688.  
  3689. abs_or_notype_decl: absdcl
  3690.     | notype_declarator
  3691.     | START_DECLARATOR notype_declarator
  3692.         { $$ = $2; }
  3693.     ;
  3694.  
  3695. see_typename: type_quals
  3696.     { see_typename (); }
  3697.     ;
  3698.  
  3699. dont_see_typename: /* empty */
  3700.     { dont_see_typename (); }
  3701.     ;
  3702.  
  3703. /*
  3704. try_for_typename:
  3705.         {
  3706.       if ($<ttype>-1 == error_mark_node)
  3707.             $$ = 0;
  3708.           else
  3709.             {
  3710.               $$ = 1;
  3711.               pushclass ($<ttype>-1, 1);
  3712.             }
  3713.         }
  3714.     ;
  3715. */
  3716.  
  3717. bad_parm:
  3718.       abs_or_notype_decl
  3719.         {
  3720.           warning ("type specifier omitted for parameter");
  3721.           $$ = build_tree_list (TREE_PURPOSE (TREE_VALUE ($<ttype>-1)), $$);
  3722.         }
  3723.     ;
  3724.  
  3725. maybe_raises:
  3726.       /* empty */
  3727.         { $$ = NULL_TREE; }
  3728.     | RAISES raise_identifiers  %prec EMPTY
  3729.         { $$ = $2; }
  3730.     | ANSI_THROW '(' ansi_raise_identifiers  ')' %prec EMPTY
  3731.         { $$ = $3; }
  3732.     ;
  3733.  
  3734. raise_identifier:
  3735.       ALL
  3736.         { $$ = void_list_node; }
  3737.     | IDENTIFIER
  3738.         { $$ = build_decl_list (NULL_TREE, $$); }
  3739.     | TYPENAME
  3740.         { $$ = build_decl_list (NULL_TREE, $$); }
  3741.     | SCOPE IDENTIFIER
  3742.         { $$ = build_decl_list (void_type_node, $2); }
  3743.     | SCOPE TYPENAME
  3744.         { $$ = build_decl_list (void_type_node, $2); }
  3745.     | scoped_id IDENTIFIER
  3746.         { $$ = build_decl_list ($$, $2); }
  3747.     | scoped_typename
  3748.     ;
  3749.  
  3750. ansi_raise_identifier:
  3751.       typename
  3752.         { $$ = build_decl_list (NULL_TREE, $$); }
  3753.     ;
  3754.  
  3755. raise_identifiers:
  3756.       raise_identifier
  3757.     | raise_identifiers ',' raise_identifier
  3758.         {
  3759.             TREE_CHAIN ($3) = $$;
  3760.           $$ = $3;
  3761.         }
  3762.     ;
  3763.  
  3764. ansi_raise_identifiers:
  3765.       ansi_raise_identifier
  3766.     | ansi_raise_identifiers ',' ansi_raise_identifier
  3767.         {
  3768.             TREE_CHAIN ($3) = $$;
  3769.           $$ = $3;
  3770.         }
  3771.     ;
  3772.  
  3773. operator_name:
  3774.       OPERATOR '*'
  3775.         { $$ = ansi_opname[MULT_EXPR]; }
  3776.     | OPERATOR '/'
  3777.         { $$ = ansi_opname[TRUNC_DIV_EXPR]; }
  3778.     | OPERATOR '%'
  3779.         { $$ = ansi_opname[TRUNC_MOD_EXPR]; }
  3780.     | OPERATOR '+'
  3781.         { $$ = ansi_opname[PLUS_EXPR]; }
  3782.     | OPERATOR '-'
  3783.         { $$ = ansi_opname[MINUS_EXPR]; }
  3784.     | OPERATOR '&'
  3785.         { $$ = ansi_opname[BIT_AND_EXPR]; }
  3786.     | OPERATOR '|'
  3787.         { $$ = ansi_opname[BIT_IOR_EXPR]; }
  3788.     | OPERATOR '^'
  3789.         { $$ = ansi_opname[BIT_XOR_EXPR]; }
  3790.     | OPERATOR '~'
  3791.         { $$ = ansi_opname[BIT_NOT_EXPR]; }
  3792.     | OPERATOR ','
  3793.         { $$ = ansi_opname[COMPOUND_EXPR]; }
  3794.     | OPERATOR ARITHCOMPARE
  3795.         { $$ = ansi_opname[$2]; }
  3796.     | OPERATOR '<'
  3797.         { $$ = ansi_opname[LT_EXPR]; }
  3798.     | OPERATOR '>'
  3799.         { $$ = ansi_opname[GT_EXPR]; }
  3800.     | OPERATOR EQCOMPARE
  3801.         { $$ = ansi_opname[$2]; }
  3802.     | OPERATOR ASSIGN
  3803.         { $$ = ansi_assopname[$2]; }
  3804.     | OPERATOR '='
  3805.         {
  3806.           $$ = ansi_opname [MODIFY_EXPR];
  3807.           if (current_class_type)
  3808.             {
  3809.               TYPE_HAS_ASSIGNMENT (current_class_type) = 1;
  3810.               TYPE_GETS_ASSIGNMENT (current_class_type) = 1;
  3811.             }
  3812.         }
  3813.     | OPERATOR LSHIFT
  3814.         { $$ = ansi_opname[$2]; }
  3815.     | OPERATOR RSHIFT
  3816.         { $$ = ansi_opname[$2]; }
  3817.     | OPERATOR PLUSPLUS
  3818.         { $$ = ansi_opname[POSTINCREMENT_EXPR]; }
  3819.     | OPERATOR MINUSMINUS
  3820.         { $$ = ansi_opname[PREDECREMENT_EXPR]; }
  3821.     | OPERATOR ANDAND
  3822.         { $$ = ansi_opname[TRUTH_ANDIF_EXPR]; }
  3823.     | OPERATOR OROR
  3824.         { $$ = ansi_opname[TRUTH_ORIF_EXPR]; }
  3825.     | OPERATOR '!'
  3826.         { $$ = ansi_opname[TRUTH_NOT_EXPR]; }
  3827.     | OPERATOR '?' ':'
  3828.         { $$ = ansi_opname[COND_EXPR]; }
  3829.     | OPERATOR MIN_MAX
  3830.         { $$ = ansi_opname[$2]; }
  3831.     | OPERATOR POINTSAT  %prec EMPTY
  3832.         { $$ = ansi_opname[COMPONENT_REF];
  3833.           if (current_class_type)
  3834.             {
  3835.               tree t = current_class_type;
  3836.               while (t)
  3837.             {
  3838.               TYPE_OVERLOADS_ARROW (t) = 1;
  3839.               t = TYPE_NEXT_VARIANT (t);
  3840.             }
  3841.             }
  3842.         }
  3843.     | OPERATOR POINTSAT_STAR  %prec EMPTY
  3844.         { $$ = ansi_opname[MEMBER_REF];
  3845.           if (current_class_type)
  3846.             {
  3847.               tree t = current_class_type;
  3848.               while (t)
  3849.             {
  3850.               TYPE_OVERLOADS_ARROW (t) = 1;
  3851.               t = TYPE_NEXT_VARIANT (t);
  3852.             }
  3853.             }
  3854.         }
  3855.     | OPERATOR POINTSAT_LEFT_RIGHT type_quals  %prec '.'
  3856.         {
  3857.           if (yychar == YYEMPTY)
  3858.             yychar = YYLEX;
  3859.           if (yychar == '(' || yychar == LEFT_RIGHT)
  3860.             {
  3861.               $$ = ansi_opname[METHOD_CALL_EXPR];
  3862.               if (current_class_type)
  3863.             {
  3864.               tree t = current_class_type;
  3865.               while (t)
  3866.                 {
  3867.                   TYPE_OVERLOADS_METHOD_CALL_EXPR (t) = 1;
  3868.                   t = TYPE_NEXT_VARIANT (t);
  3869.                 }
  3870.             }
  3871.             }
  3872.           else
  3873.             {
  3874.               $$ = build_parse_node (CALL_EXPR, ansi_opname[COMPONENT_REF], void_list_node, $3);
  3875.               if (current_class_type)
  3876.             {
  3877.               tree t = current_class_type;
  3878.               while (t)
  3879.                 {
  3880.                   TYPE_OVERLOADS_ARROW (t) = 1;
  3881.                   t = TYPE_NEXT_VARIANT (t);
  3882.                 }
  3883.             }
  3884.             }
  3885.         }
  3886.     | OPERATOR LEFT_RIGHT
  3887.         { $$ = ansi_opname[CALL_EXPR];
  3888.           if (current_class_type)
  3889.             {
  3890.               tree t = current_class_type;
  3891.               while (t)
  3892.             {
  3893.               TYPE_OVERLOADS_CALL_EXPR (t) = 1;
  3894.               t = TYPE_NEXT_VARIANT (t);
  3895.             }
  3896.             }
  3897.         }
  3898.     | OPERATOR '[' ']'
  3899.         { $$ = ansi_opname[ARRAY_REF];
  3900.           if (current_class_type)
  3901.             {
  3902.               tree t = current_class_type;
  3903.               while (t)
  3904.             {
  3905.               TYPE_OVERLOADS_ARRAY_REF (t) = 1;
  3906.               t = TYPE_NEXT_VARIANT (t);
  3907.             }
  3908.             }
  3909.         }
  3910.     | OPERATOR NEW
  3911.         {
  3912.           $$ = ansi_opname[NEW_EXPR];
  3913.           if (current_class_type)
  3914.             {
  3915.               tree t = current_class_type;
  3916.               while (t)
  3917.             {
  3918.               TREE_GETS_NEW (t) = 1;
  3919.               t = TYPE_NEXT_VARIANT (t);
  3920.             }
  3921.             }
  3922.         }
  3923.     | OPERATOR DELETE
  3924.         {
  3925.           $$ = ansi_opname[DELETE_EXPR];
  3926.           if (current_class_type)
  3927.             {
  3928.               tree t = current_class_type;
  3929.               while (t)
  3930.             {
  3931.               TREE_GETS_DELETE (t) = 1;
  3932.               t = TYPE_NEXT_VARIANT (t);
  3933.             }
  3934.             }
  3935.         }
  3936.  
  3937.     /* These should do `groktypename' and set up TREE_HAS_X_CONVERSION
  3938.        here, rather than doing it in class.c .  */
  3939.     | OPERATOR typed_typespecs absdcl
  3940.         { $$ = build1 (TYPE_EXPR, $2, $3); }
  3941.     | OPERATOR error
  3942.         { $$ = ansi_opname[ERROR_MARK]; }
  3943.     ;
  3944.  
  3945. %%
  3946.  
  3947. tree
  3948. get_current_declspecs ()
  3949. {
  3950.   return current_declspecs;
  3951. }
  3952.