home *** CD-ROM | disk | FTP | other *** search
/ InfoMagic Source Code 1993 July / THE_SOURCE_CODE_CD_ROM.iso / gnu / gcc-2.4.5 / cp-parse.y < prev    next >
Encoding:
Text File  |  1993-04-26  |  113.5 KB  |  3,971 lines

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