(all output patterns): Use new capabilities of arm_print_operand to
[official-gcc.git] / gcc / c-parse.in
blobd3c6cad4b68511e2dfb143edd250c84b231e0dd6
1 /* YACC parser for C syntax and for Objective C.  -*-c-*-
2    Copyright (C) 1987, 88, 89, 92, 93, 1994 Free Software Foundation, Inc.
4 This file is part of GNU CC.
6 GNU CC is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
11 GNU CC is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with GNU CC; see the file COPYING.  If not, write to
18 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
20 /* This file defines the grammar of C and that of Objective C.
21    ifobjc ... end ifobjc  conditionals contain code for Objective C only.
22    ifc ... end ifc  conditionals contain code for C only.
23    Sed commands in Makefile.in are used to convert this file into
24    c-parse.y and into objc-parse.y.  */
26 /* To whomever it may concern: I have heard that such a thing was once
27 written by AT&T, but I have never seen it.  */
29 ifobjc
30 %expect 22
31 end ifobjc
32 ifc
33 %expect 10
35 /* These are the 10 conflicts you should get in parse.output;
36    the state numbers may vary if minor changes in the grammar are made.
38 State 41 contains 1 shift/reduce conflict.  (Two ways to recover from error.)
39 State 97 contains 1 shift/reduce conflict.  (Two ways to recover from error.)
40 State 104 contains 1 shift/reduce conflict.  (Two ways to recover from error.)
41 State 108 contains 1 shift/reduce conflict.  (Two ways to recover from error.)
42 State 124 contains 1 shift/reduce conflict.  (See comment at component_decl.)
43 State 191 contains 1 shift/reduce conflict.  (Two ways to recover from error.)
44 State 204 contains 1 shift/reduce conflict.  (Two ways to recover from error.)
45 State 210 contains 1 shift/reduce conflict.  (Two ways to recover from error.)
46 State 449 contains 2 shift/reduce conflicts.  (Four ways to parse this.)
48 end ifc
51 #include <stdio.h>
52 #include <errno.h>
53 #include <setjmp.h>
55 #include "config.h"
56 #include "tree.h"
57 #include "input.h"
58 #include "c-lex.h"
59 #include "c-tree.h"
60 #include "flags.h"
62 #ifdef MULTIBYTE_CHARS
63 #include <stdlib.h>
64 #include <locale.h>
65 #endif
67 ifobjc
68 #include "objc-act.h"
69 end ifobjc
71 /* Since parsers are distinct for each language, put the language string
72    definition here.  */
73 ifobjc
74 char *language_string = "GNU Obj-C";
75 end ifobjc
76 ifc
77 char *language_string = "GNU C";
78 end ifc
80 #ifndef errno
81 extern int errno;
82 #endif
84 void yyerror ();
86 /* Like YYERROR but do call yyerror.  */
87 #define YYERROR1 { yyerror ("syntax error"); YYERROR; }
89 /* Cause the `yydebug' variable to be defined.  */
90 #define YYDEBUG 1
93 %start program
95 %union {long itype; tree ttype; enum tree_code code;
96         char *filename; int lineno; }
98 /* All identifiers that are not reserved words
99    and are not declared typedefs in the current block */
100 %token IDENTIFIER
102 /* All identifiers that are declared typedefs in the current block.
103    In some contexts, they are treated just like IDENTIFIER,
104    but they can also serve as typespecs in declarations.  */
105 %token TYPENAME
107 /* Reserved words that specify storage class.
108    yylval contains an IDENTIFIER_NODE which indicates which one.  */
109 %token SCSPEC
111 /* Reserved words that specify type.
112    yylval contains an IDENTIFIER_NODE which indicates which one.  */
113 %token TYPESPEC
115 /* Reserved words that qualify type: "const" or "volatile".
116    yylval contains an IDENTIFIER_NODE which indicates which one.  */
117 %token TYPE_QUAL
119 /* Character or numeric constants.
120    yylval is the node for the constant.  */
121 %token CONSTANT
123 /* String constants in raw form.
124    yylval is a STRING_CST node.  */
125 %token STRING
127 /* "...", used for functions with variable arglists.  */
128 %token ELLIPSIS
130 /* the reserved words */
131 /* SCO include files test "ASM", so use something else. */
132 %token SIZEOF ENUM STRUCT UNION IF ELSE WHILE DO FOR SWITCH CASE DEFAULT
133 %token BREAK CONTINUE RETURN GOTO ASM_KEYWORD TYPEOF ALIGNOF ALIGN
134 %token ATTRIBUTE EXTENSION LABEL
135 %token REALPART IMAGPART
137 /* Add precedence rules to solve dangling else s/r conflict */
138 %nonassoc IF
139 %nonassoc ELSE
141 /* Define the operator tokens and their precedences.
142    The value is an integer because, if used, it is the tree code
143    to use in the expression made from the operator.  */
145 %right <code> ASSIGN '='
146 %right <code> '?' ':'
147 %left <code> OROR
148 %left <code> ANDAND
149 %left <code> '|'
150 %left <code> '^'
151 %left <code> '&'
152 %left <code> EQCOMPARE
153 %left <code> ARITHCOMPARE
154 %left <code> LSHIFT RSHIFT
155 %left <code> '+' '-'
156 %left <code> '*' '/' '%'
157 %right <code> UNARY PLUSPLUS MINUSMINUS
158 %left HYPERUNARY
159 %left <code> POINTSAT '.' '(' '['
161 /* The Objective-C keywords.  These are included in C and in
162    Objective C, so that the token codes are the same in both.  */
163 %token INTERFACE IMPLEMENTATION END SELECTOR DEFS ENCODE
164 %token CLASSNAME PUBLIC PRIVATE PROTECTED PROTOCOL OBJECTNAME CLASS ALIAS
166 /* Objective-C string constants in raw form.
167    yylval is an OBJC_STRING_CST node.  */
168 %token OBJC_STRING
171 %type <code> unop
173 %type <ttype> identifier IDENTIFIER TYPENAME CONSTANT expr nonnull_exprlist exprlist
174 %type <ttype> expr_no_commas cast_expr unary_expr primary string STRING
175 %type <ttype> typed_declspecs reserved_declspecs
176 %type <ttype> typed_typespecs reserved_typespecquals
177 %type <ttype> declmods typespec typespecqual_reserved
178 %type <ttype> SCSPEC TYPESPEC TYPE_QUAL nonempty_type_quals maybe_type_qual
179 %type <ttype> initdecls notype_initdecls initdcl notype_initdcl
180 %type <ttype> init maybeasm
181 %type <ttype> asm_operands nonnull_asm_operands asm_operand asm_clobbers
182 %type <ttype> maybe_attribute attributes attribute attribute_list attrib
183 %type <ttype> any_word
185 %type <ttype> compstmt
187 %type <ttype> declarator
188 %type <ttype> notype_declarator after_type_declarator
189 %type <ttype> parm_declarator
191 %type <ttype> structsp component_decl_list component_decl_list2
192 %type <ttype> component_decl components component_declarator
193 %type <ttype> enumlist enumerator
194 %type <ttype> typename absdcl absdcl1 type_quals
195 %type <ttype> xexpr parms parm identifiers
197 %type <ttype> parmlist parmlist_1 parmlist_2
198 %type <ttype> parmlist_or_identifiers parmlist_or_identifiers_1
199 %type <ttype> identifiers_or_typenames
201 %type <itype> setspecs
203 %type <filename> save_filename
204 %type <lineno> save_lineno
206 ifobjc
207 /* the Objective-C nonterminals */
209 %type <ttype> ivar_decl_list ivar_decls ivar_decl ivars ivar_declarator
210 %type <ttype> methoddecl unaryselector keywordselector selector
211 %type <ttype> keyworddecl receiver objcmessageexpr messageargs
212 %type <ttype> keywordexpr keywordarglist keywordarg
213 %type <ttype> myparms myparm optparmlist reservedwords objcselectorexpr
214 %type <ttype> selectorarg keywordnamelist keywordname objcencodeexpr
215 %type <ttype> objc_string protocolrefs identifier_list objcprotocolexpr
216 %type <ttype> CLASSNAME OBJC_STRING OBJECTNAME
217 end ifobjc
220 /* Number of statements (loosely speaking) seen so far.  */
221 static int stmt_count;
223 /* Input file and line number of the end of the body of last simple_if;
224    used by the stmt-rule immediately after simple_if returns.  */
225 static char *if_stmt_file;
226 static int if_stmt_line;
228 /* List of types and structure classes of the current declaration.  */
229 static tree current_declspecs;
231 /* Stack of saved values of current_declspecs.  */
232 static tree declspec_stack;
234 /* 1 if we explained undeclared var errors.  */
235 static int undeclared_variable_notice;
237 ifobjc
238 /* Objective-C specific information */
240 tree objc_interface_context;
241 tree objc_implementation_context;
242 tree objc_method_context;
243 tree objc_ivar_chain;
244 tree objc_ivar_context;
245 enum tree_code objc_inherit_code;
246 int objc_receiver_context;
247 int objc_public_flag;
249 end ifobjc
251 /* Tell yyparse how to print a token's value, if yydebug is set.  */
253 #define YYPRINT(FILE,YYCHAR,YYLVAL) yyprint(FILE,YYCHAR,YYLVAL)
254 extern void yyprint ();
258 program: /* empty */
259                 { if (pedantic)
260                     pedwarn ("ANSI C forbids an empty source file");
261 ifobjc
262                   objc_finish ();
263 end ifobjc
264                 }
265         | extdefs
266                 {
267                   /* In case there were missing closebraces,
268                      get us back to the global binding level.  */
269                   while (! global_bindings_p ())
270                     poplevel (0, 0, 0);
271 ifobjc
272                   objc_finish ();
273 end ifobjc
274                 }
275         ;
277 /* the reason for the strange actions in this rule
278  is so that notype_initdecls when reached via datadef
279  can find a valid list of type and sc specs in $0. */
281 extdefs:
282         {$<ttype>$ = NULL_TREE; } extdef
283         | extdefs {$<ttype>$ = NULL_TREE; } extdef
284         ;
286 extdef:
287         fndef
288         | datadef
289 ifobjc
290         | objcdef
291 end ifobjc
292         | ASM_KEYWORD '(' expr ')' ';'
293                 { STRIP_NOPS ($3);
294                   if ((TREE_CODE ($3) == ADDR_EXPR
295                        && TREE_CODE (TREE_OPERAND ($3, 0)) == STRING_CST)
296                       || TREE_CODE ($3) == STRING_CST)
297                     assemble_asm ($3);
298                   else
299                     error ("argument of `asm' is not a constant string"); }
300         ;
302 datadef:
303           setspecs notype_initdecls ';'
304                 { if (pedantic)
305                     error ("ANSI C forbids data definition with no type or storage class");
306                   else if (!flag_traditional)
307                     warning ("data definition has no type or storage class"); }
308         | declmods setspecs notype_initdecls ';'
309           {}
310         | typed_declspecs setspecs initdecls ';'
311           {}
312         | declmods ';'
313           { pedwarn ("empty declaration"); }
314         | typed_declspecs ';'
315           { shadow_tag ($1); }
316         | error ';'
317         | error '}'
318         | ';'
319                 { if (pedantic)
320                     pedwarn ("ANSI C does not allow extra `;' outside of a function"); }
321         ;
323 fndef:
324           typed_declspecs setspecs declarator
325                 { if (! start_function ($1, $3, 0))
326                     YYERROR1;
327                   reinit_parse_for_function (); }
328           xdecls
329                 { store_parm_decls (); }
330           compstmt_or_error
331                 { finish_function (0); }
332         | typed_declspecs setspecs declarator error
333                 { }
334         | declmods setspecs notype_declarator
335                 { if (! start_function ($1, $3, 0))
336                     YYERROR1;
337                   reinit_parse_for_function (); }
338           xdecls
339                 { store_parm_decls (); }
340           compstmt_or_error
341                 { finish_function (0); }
342         | declmods setspecs notype_declarator error
343                 { }
344         | setspecs notype_declarator
345                 { if (! start_function (NULL_TREE, $2, 0))
346                     YYERROR1;
347                   reinit_parse_for_function (); }
348           xdecls
349                 { store_parm_decls (); }
350           compstmt_or_error
351                 { finish_function (0); }
352         | setspecs notype_declarator error
353                 { }
354         ;
356 identifier:
357         IDENTIFIER
358         | TYPENAME
359 ifobjc
360         | OBJECTNAME
361         | CLASSNAME
362 end ifobjc
363         ;
365 unop:     '&'
366                 { $$ = ADDR_EXPR; }
367         | '-'
368                 { $$ = NEGATE_EXPR; }
369         | '+'
370                 { $$ = CONVERT_EXPR; }
371         | PLUSPLUS
372                 { $$ = PREINCREMENT_EXPR; }
373         | MINUSMINUS
374                 { $$ = PREDECREMENT_EXPR; }
375         | '~'
376                 { $$ = BIT_NOT_EXPR; }
377         | '!'
378                 { $$ = TRUTH_NOT_EXPR; }
379         ;
381 expr:   nonnull_exprlist
382                 { $$ = build_compound_expr ($1); }
383         ;
385 exprlist:
386           /* empty */
387                 { $$ = NULL_TREE; }
388         | nonnull_exprlist
389         ;
391 nonnull_exprlist:
392         expr_no_commas
393                 { $$ = build_tree_list (NULL_TREE, $1); }
394         | nonnull_exprlist ',' expr_no_commas
395                 { chainon ($1, build_tree_list (NULL_TREE, $3)); }
396         ;
398 unary_expr:
399         primary
400         | '*' cast_expr   %prec UNARY
401                 { $$ = build_indirect_ref ($2, "unary *"); }
402         /* __extension__ turns off -pedantic for following primary.  */
403         | EXTENSION
404                 { $<itype>1 = pedantic;
405                   pedantic = 0; }
406           cast_expr       %prec UNARY
407                 { $$ = $3;
408                   pedantic = $<itype>1; }
409         | unop cast_expr  %prec UNARY
410                 { $$ = build_unary_op ($1, $2, 0);
411                   overflow_warning ($$); }
412         /* Refer to the address of a label as a pointer.  */
413         | ANDAND identifier
414                 { tree label = lookup_label ($2);
415                   if (label == 0)
416                     $$ = null_pointer_node;
417                   else
418                     {
419                       TREE_USED (label) = 1;
420                       $$ = build1 (ADDR_EXPR, ptr_type_node, label);
421                       TREE_CONSTANT ($$) = 1;
422                     }
423                 }
424 /* This seems to be impossible on some machines, so let's turn it off.
425    You can use __builtin_next_arg to find the anonymous stack args.
426         | '&' ELLIPSIS
427                 { tree types = TYPE_ARG_TYPES (TREE_TYPE (current_function_decl));
428                   $$ = error_mark_node;
429                   if (TREE_VALUE (tree_last (types)) == void_type_node)
430                     error ("`&...' used in function with fixed number of arguments");
431                   else
432                     {
433                       if (pedantic)
434                         pedwarn ("ANSI C forbids `&...'");
435                       $$ = tree_last (DECL_ARGUMENTS (current_function_decl));
436                       $$ = build_unary_op (ADDR_EXPR, $$, 0);
437                     } }
439         | SIZEOF unary_expr  %prec UNARY
440                 { if (TREE_CODE ($2) == COMPONENT_REF
441                       && DECL_BIT_FIELD (TREE_OPERAND ($2, 1)))
442                     error ("`sizeof' applied to a bit-field");
443                   $$ = c_sizeof (TREE_TYPE ($2)); }
444         | SIZEOF '(' typename ')'  %prec HYPERUNARY
445                 { $$ = c_sizeof (groktypename ($3)); }
446         | ALIGNOF unary_expr  %prec UNARY
447                 { $$ = c_alignof_expr ($2); }
448         | ALIGNOF '(' typename ')'  %prec HYPERUNARY
449                 { $$ = c_alignof (groktypename ($3)); }
450         | REALPART cast_expr %prec UNARY
451                 { $$ = build_unary_op (REALPART_EXPR, $2, 0); }
452         | IMAGPART cast_expr %prec UNARY
453                 { $$ = build_unary_op (IMAGPART_EXPR, $2, 0); }
454         ;
456 cast_expr:
457         unary_expr
458         | '(' typename ')' cast_expr  %prec UNARY
459                 { tree type = groktypename ($2);
460                   $$ = build_c_cast (type, $4); }
461         | '(' typename ')' '{' 
462                 { start_init (NULL_TREE, NULL, 0);
463                   $2 = groktypename ($2);
464                   really_start_incremental_init ($2); }
465           initlist_maybe_comma '}'  %prec UNARY
466                 { char *name;
467                   tree result = pop_init_level (0);
468                   tree type = $2;
469                   finish_init ();
471                   if (pedantic)
472                     pedwarn ("ANSI C forbids constructor expressions");
473                   if (TYPE_NAME (type) != 0)
474                     {
475                       if (TREE_CODE (TYPE_NAME (type)) == IDENTIFIER_NODE)
476                         name = IDENTIFIER_POINTER (TYPE_NAME (type));
477                       else
478                         name = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (type)));
479                     }
480                   else
481                     name = "";
482                   $$ = result;
483                   if (TREE_CODE (type) == ARRAY_TYPE && TYPE_SIZE (type) == 0)
484                     {
485                       int failure = complete_array_type (type, $$, 1);
486                       if (failure)
487                         abort ();
488                     }
489                 }
490         ;
492 expr_no_commas:
493           cast_expr
494         | expr_no_commas '+' expr_no_commas
495                 { $$ = parser_build_binary_op ($2, $1, $3); }
496         | expr_no_commas '-' expr_no_commas
497                 { $$ = parser_build_binary_op ($2, $1, $3); }
498         | expr_no_commas '*' expr_no_commas
499                 { $$ = parser_build_binary_op ($2, $1, $3); }
500         | expr_no_commas '/' expr_no_commas
501                 { $$ = parser_build_binary_op ($2, $1, $3); }
502         | expr_no_commas '%' expr_no_commas
503                 { $$ = parser_build_binary_op ($2, $1, $3); }
504         | expr_no_commas LSHIFT expr_no_commas
505                 { $$ = parser_build_binary_op ($2, $1, $3); }
506         | expr_no_commas RSHIFT expr_no_commas
507                 { $$ = parser_build_binary_op ($2, $1, $3); }
508         | expr_no_commas ARITHCOMPARE expr_no_commas
509                 { $$ = parser_build_binary_op ($2, $1, $3); }
510         | expr_no_commas EQCOMPARE expr_no_commas
511                 { $$ = parser_build_binary_op ($2, $1, $3); }
512         | expr_no_commas '&' expr_no_commas
513                 { $$ = parser_build_binary_op ($2, $1, $3); }
514         | expr_no_commas '|' expr_no_commas
515                 { $$ = parser_build_binary_op ($2, $1, $3); }
516         | expr_no_commas '^' expr_no_commas
517                 { $$ = parser_build_binary_op ($2, $1, $3); }
518         | expr_no_commas ANDAND expr_no_commas
519                 { $$ = parser_build_binary_op (TRUTH_ANDIF_EXPR, $1, $3); }
520         | expr_no_commas OROR expr_no_commas
521                 { $$ = parser_build_binary_op (TRUTH_ORIF_EXPR, $1, $3); }
522         | expr_no_commas '?' xexpr ':' expr_no_commas
523                 { $$ = build_conditional_expr ($1, $3, $5); }
524         | expr_no_commas '=' expr_no_commas
525                 { $$ = build_modify_expr ($1, NOP_EXPR, $3);
526                   C_SET_EXP_ORIGINAL_CODE ($$, MODIFY_EXPR); }
527         | expr_no_commas ASSIGN expr_no_commas
528                 { $$ = build_modify_expr ($1, $2, $3);
529                   /* This inhibits warnings in truthvalue_conversion.  */
530                   C_SET_EXP_ORIGINAL_CODE ($$, ERROR_MARK); }
531         ;
533 primary:
534         IDENTIFIER
535                 {
536                   $$ = lastiddecl;
537                   if (!$$ || $$ == error_mark_node)
538                     {
539                       if (yychar == YYEMPTY)
540                         yychar = YYLEX;
541                       if (yychar == '(')
542                         {
543 ifobjc
544                           tree decl;
546                           if (objc_receiver_context
547                               && ! (objc_receiver_context
548                                     && strcmp (IDENTIFIER_POINTER ($1), "super")))
549                             /* we have a message to super */
550                             $$ = get_super_receiver ();
551                           else if (objc_method_context
552                                    && (decl = is_ivar (objc_ivar_chain, $1)))
553                             {
554                               if (is_private (decl))
555                                 $$ = error_mark_node;
556                               else
557                                 $$ = build_ivar_reference ($1);
558                             }
559                           else
560 end ifobjc
561                             {
562                               /* Ordinary implicit function declaration.  */
563                               $$ = implicitly_declare ($1);
564                               assemble_external ($$);
565                               TREE_USED ($$) = 1;
566                             }
567                         }
568                       else if (current_function_decl == 0)
569                         {
570                           error ("`%s' undeclared here (not in a function)",
571                                  IDENTIFIER_POINTER ($1));
572                           $$ = error_mark_node;
573                         }
574                       else
575                         {
576 ifobjc
577                           tree decl;
579                           if (objc_receiver_context
580                               && ! strcmp (IDENTIFIER_POINTER ($1), "super"))
581                             /* we have a message to super */
582                             $$ = get_super_receiver ();
583                           else if (objc_method_context
584                                    && (decl = is_ivar (objc_ivar_chain, $1)))
585                             {
586                               if (is_private (decl))
587                                 $$ = error_mark_node;
588                               else
589                                 $$ = build_ivar_reference ($1);
590                             }
591                           else
592 end ifobjc
593                             {
594                               if (IDENTIFIER_GLOBAL_VALUE ($1) != error_mark_node
595                                   || IDENTIFIER_ERROR_LOCUS ($1) != current_function_decl)
596                                 {
597                                   error ("`%s' undeclared (first use this function)",
598                                          IDENTIFIER_POINTER ($1));
600                                   if (! undeclared_variable_notice)
601                                     {
602                                       error ("(Each undeclared identifier is reported only once");
603                                       error ("for each function it appears in.)");
604                                       undeclared_variable_notice = 1;
605                                     }
606                                 }
607                               $$ = error_mark_node;
608                               /* Prevent repeated error messages.  */
609                               IDENTIFIER_GLOBAL_VALUE ($1) = error_mark_node;
610                               IDENTIFIER_ERROR_LOCUS ($1) = current_function_decl;
611                             }
612                         }
613                     }
614                   else if (TREE_TYPE ($$) == error_mark_node)
615                     $$ = error_mark_node;
616                   else if (C_DECL_ANTICIPATED ($$))
617                     {
618                       /* The first time we see a build-in function used,
619                          if it has not been declared.  */
620                       C_DECL_ANTICIPATED ($$) = 0;
621                       if (yychar == YYEMPTY)
622                         yychar = YYLEX;
623                       if (yychar == '(')
624                         {
625                           /* Omit the implicit declaration we
626                              would ordinarily do, so we don't lose
627                              the actual built in type.
628                              But print a diagnostic for the mismatch.  */
629 ifobjc
630                           if (objc_method_context
631                               && is_ivar (objc_ivar_chain, $1))
632                             error ("Instance variable `%s' implicitly declared as function",
633                                    IDENTIFIER_POINTER (DECL_NAME ($$)));
634                           else
635 end ifobjc
636                             if (TREE_CODE ($$) != FUNCTION_DECL)
637                               error ("`%s' implicitly declared as function",
638                                      IDENTIFIER_POINTER (DECL_NAME ($$)));
639                           else if ((TYPE_MODE (TREE_TYPE (TREE_TYPE ($$)))
640                                     != TYPE_MODE (integer_type_node))
641                                    && (TREE_TYPE (TREE_TYPE ($$))
642                                        != void_type_node))
643                             pedwarn ("type mismatch in implicit declaration for built-in function `%s'",
644                                      IDENTIFIER_POINTER (DECL_NAME ($$)));
645                           /* If it really returns void, change that to int.  */
646                           if (TREE_TYPE (TREE_TYPE ($$)) == void_type_node)
647                             TREE_TYPE ($$)
648                               = build_function_type (integer_type_node,
649                                                      TYPE_ARG_TYPES (TREE_TYPE ($$)));
650                         }
651                       else
652                         pedwarn ("built-in function `%s' used without declaration",
653                                  IDENTIFIER_POINTER (DECL_NAME ($$)));
655                       /* Do what we would ordinarily do when a fn is used.  */
656                       assemble_external ($$);
657                       TREE_USED ($$) = 1;
658                     }
659                   else
660                     {
661                       assemble_external ($$);
662                       TREE_USED ($$) = 1;
663 ifobjc
664                       /* we have a definition - still check if iVariable */
666                       if (!objc_receiver_context
667                           || (objc_receiver_context
668                               && strcmp (IDENTIFIER_POINTER ($1), "super")))
669                         {
670                           tree decl;
672                           if (objc_method_context
673                               && (decl = is_ivar (objc_ivar_chain, $1)))
674                             {
675                               if (IDENTIFIER_LOCAL_VALUE ($1))
676                                 warning ("local declaration of `%s' hides instance variable",
677                                          IDENTIFIER_POINTER ($1));
678                               else
679                                 {
680                                   if (is_private (decl))
681                                     $$ = error_mark_node;
682                                   else
683                                     $$ = build_ivar_reference ($1);
684                                 }
685                             }
686                         }
687                       else /* we have a message to super */
688                         $$ = get_super_receiver ();
689 end ifobjc
690                     }
692                   if (TREE_CODE ($$) == CONST_DECL)
693                     {
694                       $$ = DECL_INITIAL ($$);
695                       /* This is to prevent an enum whose value is 0
696                          from being considered a null pointer constant.  */
697                       $$ = build1 (NOP_EXPR, TREE_TYPE ($$), $$);
698                       TREE_CONSTANT ($$) = 1;
699                     }
700                 }
701         | CONSTANT
702         | string
703                 { $$ = combine_strings ($1); }
704         | '(' expr ')'
705                 { char class = TREE_CODE_CLASS (TREE_CODE ($2));
706                   if (class == 'e' || class == '1'
707                       || class == '2' || class == '<')
708                     C_SET_EXP_ORIGINAL_CODE ($2, ERROR_MARK);
709                   $$ = $2; }
710         | '(' error ')'
711                 { $$ = error_mark_node; }
712         | '('
713                 { if (current_function_decl == 0)
714                     {
715                       error ("braced-group within expression allowed only inside a function");
716                       YYERROR;
717                     }
718                   /* We must force a BLOCK for this level
719                      so that, if it is not expanded later,
720                      there is a way to turn off the entire subtree of blocks
721                      that are contained in it.  */
722                   keep_next_level ();
723                   push_iterator_stack ();
724                   push_label_level ();
725                   $<ttype>$ = expand_start_stmt_expr (); }
726           compstmt ')'
727                 { tree rtl_exp;
728                   if (pedantic)
729                     pedwarn ("ANSI C forbids braced-groups within expressions");
730                   pop_iterator_stack ();
731                   pop_label_level ();
732                   rtl_exp = expand_end_stmt_expr ($<ttype>2);
733                   /* The statements have side effects, so the group does.  */
734                   TREE_SIDE_EFFECTS (rtl_exp) = 1;
736                   if (TREE_CODE ($3) == BLOCK)
737                     {
738                       /* Make a BIND_EXPR for the BLOCK already made.  */
739                       $$ = build (BIND_EXPR, TREE_TYPE (rtl_exp),
740                                   NULL_TREE, rtl_exp, $3);
741                       /* Remove the block from the tree at this point.
742                          It gets put back at the proper place
743                          when the BIND_EXPR is expanded.  */
744                       delete_block ($3);
745                     }
746                   else
747                     $$ = $3;
748                 }
749         | primary '(' exprlist ')'   %prec '.'
750                 { $$ = build_function_call ($1, $3); }
751         | primary '[' expr ']'   %prec '.'
752                 { $$ = build_array_ref ($1, $3); }
753         | primary '.' identifier
754                 {
755 ifobjc
756                   if (doing_objc_thang)
757                     {
758                       if (is_public ($1, $3))
759                         $$ = build_component_ref ($1, $3);
760                       else
761                         $$ = error_mark_node;
762                     }
763                   else
764 end ifobjc
765                     $$ = build_component_ref ($1, $3);
766                 }
767         | primary POINTSAT identifier
768                 {
769                   tree expr = build_indirect_ref ($1, "->");
771 ifobjc
772                   if (doing_objc_thang)
773                     {
774                       if (is_public (expr, $3))
775                         $$ = build_component_ref (expr, $3);
776                       else
777                         $$ = error_mark_node;
778                     }
779                   else
780 end ifobjc
781                     $$ = build_component_ref (expr, $3);
782                 }
783         | primary PLUSPLUS
784                 { $$ = build_unary_op (POSTINCREMENT_EXPR, $1, 0); }
785         | primary MINUSMINUS
786                 { $$ = build_unary_op (POSTDECREMENT_EXPR, $1, 0); }
787 ifobjc
788         | objcmessageexpr
789                 { $$ = build_message_expr ($1); }
790         | objcselectorexpr
791                 { $$ = build_selector_expr ($1); }
792         | objcprotocolexpr
793                 { $$ = build_protocol_expr ($1); }
794         | objcencodeexpr
795                 { $$ = build_encode_expr ($1); }
796         | objc_string
797                 { $$ = build_objc_string_object ($1); }
798 end ifobjc
799         ;
801 /* Produces a STRING_CST with perhaps more STRING_CSTs chained onto it.  */
802 string:
803           STRING
804         | string STRING
805                 { $$ = chainon ($1, $2); }
806         ;
808 ifobjc
809 /* Produces an OBJC_STRING_CST with prehaps more OBJC_STRING_CSTs chained
810    onto it.  */
811 objc_string:
812           OBJC_STRING
813         | objc_string OBJC_STRING
814                 { $$ = chainon ($1, $2); }
815         ;
816 end ifobjc
818 xdecls:
819         /* empty */
820         | datadecls
821         | datadecls ELLIPSIS
822                 /* ... is used here to indicate a varargs function.  */
823                 { c_mark_varargs ();
824                   if (pedantic)
825                     pedwarn ("ANSI C does not permit use of `varargs.h'"); }
826         ;
828 /* The following are analogous to lineno_decl, decls and decl
829    except that they do not allow nested functions.
830    They are used for old-style parm decls.  */
831 lineno_datadecl:
832           save_filename save_lineno datadecl
833                 { }
834         ;
836 datadecls:
837         lineno_datadecl
838         | errstmt
839         | datadecls lineno_datadecl
840         | lineno_datadecl errstmt
841         ;
843 datadecl:
844         typed_declspecs setspecs initdecls ';'
845                 { current_declspecs = TREE_VALUE (declspec_stack);
846                   declspec_stack = TREE_CHAIN (declspec_stack);
847                   resume_momentary ($2); }
848         | declmods setspecs notype_initdecls ';'
849                 { current_declspecs = TREE_VALUE (declspec_stack);
850                   declspec_stack = TREE_CHAIN (declspec_stack);
851                   resume_momentary ($2); }
852         | typed_declspecs ';'
853                 { shadow_tag_warned ($1, 1);
854                   pedwarn ("empty declaration"); }
855         | declmods ';'
856                 { pedwarn ("empty declaration"); }
857         ;
859 /* This combination which saves a lineno before a decl
860    is the normal thing to use, rather than decl itself.
861    This is to avoid shift/reduce conflicts in contexts
862    where statement labels are allowed.  */
863 lineno_decl:
864           save_filename save_lineno decl
865                 { }
866         ;
868 decls:
869         lineno_decl
870         | errstmt
871         | decls lineno_decl
872         | lineno_decl errstmt
873         ;
875 /* records the type and storage class specs to use for processing
876    the declarators that follow.
877    Maintains a stack of outer-level values of current_declspecs,
878    for the sake of parm declarations nested in function declarators.  */
879 setspecs: /* empty */
880                 { $$ = suspend_momentary ();
881                   pending_xref_error ();
882                   declspec_stack = tree_cons (NULL_TREE, current_declspecs,
883                                               declspec_stack);
884                   current_declspecs = $<ttype>0; }
885         ;
887 decl:
888         typed_declspecs setspecs initdecls ';'
889                 { current_declspecs = TREE_VALUE (declspec_stack);
890                   declspec_stack = TREE_CHAIN (declspec_stack);
891                   resume_momentary ($2); }
892         | declmods setspecs notype_initdecls ';'
893                 { current_declspecs = TREE_VALUE (declspec_stack);
894                   declspec_stack = TREE_CHAIN (declspec_stack);
895                   resume_momentary ($2); }
896         | typed_declspecs setspecs nested_function
897                 { current_declspecs = TREE_VALUE (declspec_stack);
898                   declspec_stack = TREE_CHAIN (declspec_stack);
899                   resume_momentary ($2); }
900         | declmods setspecs notype_nested_function
901                 { current_declspecs = TREE_VALUE (declspec_stack);
902                   declspec_stack = TREE_CHAIN (declspec_stack);
903                   resume_momentary ($2); }
904         | typed_declspecs ';'
905                 { shadow_tag ($1); }
906         | declmods ';'
907                 { pedwarn ("empty declaration"); }
908         ;
910 /* Declspecs which contain at least one type specifier or typedef name.
911    (Just `const' or `volatile' is not enough.)
912    A typedef'd name following these is taken as a name to be declared.  */
914 typed_declspecs:
915           typespec reserved_declspecs
916                 { $$ = tree_cons (NULL_TREE, $1, $2); }
917         | declmods typespec reserved_declspecs
918                 { $$ = chainon ($3, tree_cons (NULL_TREE, $2, $1)); }
919         ;
921 reserved_declspecs:  /* empty */
922                 { $$ = NULL_TREE; }
923         | reserved_declspecs typespecqual_reserved
924                 { $$ = tree_cons (NULL_TREE, $2, $1); }
925         | reserved_declspecs SCSPEC
926                 { if (extra_warnings)
927                     warning ("`%s' is not at beginning of declaration",
928                              IDENTIFIER_POINTER ($2));
929                   $$ = tree_cons (NULL_TREE, $2, $1); }
930         ;
932 /* List of just storage classes and type modifiers.
933    A declaration can start with just this, but then it cannot be used
934    to redeclare a typedef-name.  */
936 declmods:
937           TYPE_QUAL
938                 { $$ = tree_cons (NULL_TREE, $1, NULL_TREE);
939                   TREE_STATIC ($$) = 1; }
940         | SCSPEC
941                 { $$ = tree_cons (NULL_TREE, $1, NULL_TREE); }
942         | declmods TYPE_QUAL
943                 { $$ = tree_cons (NULL_TREE, $2, $1);
944                   TREE_STATIC ($$) = 1; }
945         | declmods SCSPEC
946                 { if (extra_warnings && TREE_STATIC ($1))
947                     warning ("`%s' is not at beginning of declaration",
948                              IDENTIFIER_POINTER ($2));
949                   $$ = tree_cons (NULL_TREE, $2, $1);
950                   TREE_STATIC ($$) = TREE_STATIC ($1); }
951         ;
954 /* Used instead of declspecs where storage classes are not allowed
955    (that is, for typenames and structure components).
956    Don't accept a typedef-name if anything but a modifier precedes it.  */
958 typed_typespecs:
959           typespec reserved_typespecquals
960                 { $$ = tree_cons (NULL_TREE, $1, $2); }
961         | nonempty_type_quals typespec reserved_typespecquals
962                 { $$ = chainon ($3, tree_cons (NULL_TREE, $2, $1)); }
963         ;
965 reserved_typespecquals:  /* empty */
966                 { $$ = NULL_TREE; }
967         | reserved_typespecquals typespecqual_reserved
968                 { $$ = tree_cons (NULL_TREE, $2, $1); }
969         ;
971 /* A typespec (but not a type qualifier).
972    Once we have seen one of these in a declaration,
973    if a typedef name appears then it is being redeclared.  */
975 typespec: TYPESPEC
976         | structsp
977         | TYPENAME
978                 { /* For a typedef name, record the meaning, not the name.
979                      In case of `foo foo, bar;'.  */
980                   $$ = lookup_name ($1); }
981 ifobjc
982         | CLASSNAME protocolrefs
983                 { $$ = get_static_reference ($1, $2); }
984         | OBJECTNAME protocolrefs
985                 { $$ = get_object_reference ($2); }
986 end ifobjc
987         | TYPEOF '(' expr ')'
988                 { $$ = TREE_TYPE ($3); }
989         | TYPEOF '(' typename ')'
990                 { $$ = groktypename ($3); }
991         ;
993 /* A typespec that is a reserved word, or a type qualifier.  */
995 typespecqual_reserved: TYPESPEC
996         | TYPE_QUAL
997         | structsp
998         ;
1000 initdecls:
1001         initdcl
1002         | initdecls ',' initdcl
1003         ;
1005 notype_initdecls:
1006         notype_initdcl
1007         | notype_initdecls ',' initdcl
1008         ;
1010 maybeasm:
1011           /* empty */
1012                 { $$ = NULL_TREE; }
1013         | ASM_KEYWORD '(' string ')'
1014                 { if (TREE_CHAIN ($3)) $3 = combine_strings ($3);
1015                   $$ = $3;
1016                 }
1017         ;
1019 initdcl:
1020           declarator maybeasm maybe_attribute '='
1021                 { $<ttype>$ = start_decl ($1, current_declspecs, 1);
1022                   decl_attributes ($<ttype>$, $3);
1023                   start_init ($<ttype>$, $2, global_bindings_p ()); }
1024           init
1025 /* Note how the declaration of the variable is in effect while its init is parsed! */
1026                 { finish_init ();
1027                   decl_attributes ($<ttype>5, $3);
1028                   finish_decl ($<ttype>5, $6, $2); }
1029         | declarator maybeasm maybe_attribute
1030                 { tree d = start_decl ($1, current_declspecs, 0);
1031                   decl_attributes (d, $3);
1032                   finish_decl (d, NULL_TREE, $2); }
1033         ;
1035 notype_initdcl:
1036           notype_declarator maybeasm maybe_attribute '='
1037                 { $<ttype>$ = start_decl ($1, current_declspecs, 1);
1038                   decl_attributes ($<ttype>$, $3);
1039                   start_init ($<ttype>$, $2, global_bindings_p ()); }
1040           init
1041 /* Note how the declaration of the variable is in effect while its init is parsed! */
1042                 { finish_init ();
1043                   decl_attributes ($<ttype>5, $3);
1044                   finish_decl ($<ttype>5, $6, $2); }
1045         | notype_declarator maybeasm maybe_attribute
1046                 { tree d = start_decl ($1, current_declspecs, 0);
1047                   decl_attributes (d, $3);
1048                   finish_decl (d, NULL_TREE, $2); }
1049         ;
1050 /* the * rules are dummies to accept the Apollo extended syntax
1051    so that the header files compile. */
1052 maybe_attribute:
1053       /* empty */
1054                 { $$ = NULL_TREE; }
1055         | attributes
1056                 { $$ = $1; }
1057         ;
1059 attributes:
1060       attribute
1061                 { $$ = $1; }
1062         | attributes attribute
1063                 { $$ = chainon ($1, $2); }
1064         ;
1066 attribute:
1067       ATTRIBUTE '(' '(' attribute_list ')' ')'
1068                 { $$ = $4; }
1069         ;
1071 attribute_list:
1072       attrib
1073                 { $$ = build_tree_list (NULL_TREE, $1); }
1074         | attribute_list ',' attrib
1075                 { $$ = chainon ($1, build_tree_list (NULL_TREE, $3)); }
1076         ;
1078 attrib:
1079     /* empty */
1080                 { $$ = NULL_TREE; }
1081         | any_word
1082                 { $$ = $1; }
1083         | any_word '(' IDENTIFIER ')'
1084                 { $$ = tree_cons ($1, NULL_TREE,
1085                                   build_tree_list (NULL_TREE, $3)); }
1086         | any_word '(' IDENTIFIER ',' nonnull_exprlist ')'
1087                 { $$ = tree_cons ($1, NULL_TREE,
1088                                   tree_cons (NULL_TREE, $3, $5)); }
1089         | any_word '(' nonnull_exprlist ')'
1090                 { $$ = tree_cons ($1, NULL_TREE, $3); }
1091         ;
1093 /* This still leaves out most reserved keywords,
1094    shouldn't we include them?  */
1096 any_word:
1097           identifier
1098         | SCSPEC
1099         | TYPESPEC
1100         | TYPE_QUAL
1101         ;
1103 /* Initializers.  `init' is the entry point.  */
1105 init:
1106         expr_no_commas
1107         | '{'
1108                 { really_start_incremental_init (NULL_TREE);
1109                   /* Note that the call to clear_momentary
1110                      is in process_init_element.  */
1111                   push_momentary (); }
1112           initlist_maybe_comma '}'
1113                 { $$ = pop_init_level (0);
1114                   if ($$ == error_mark_node
1115                       && ! (yychar == STRING || yychar == CONSTANT))
1116                     pop_momentary ();
1117                   else
1118                     pop_momentary_nofree (); }
1120         | error
1121                 { $$ = error_mark_node; }
1122         ;
1124 /* `initlist_maybe_comma' is the guts of an initializer in braces.  */
1125 initlist_maybe_comma:
1126           /* empty */
1127                 { if (pedantic)
1128                     pedwarn ("ANSI C forbids empty initializer braces"); }
1129         | initlist1 maybecomma
1130         ;
1132 initlist1:
1133           initelt
1134         | initlist1 ',' initelt
1135         ;
1137 /* `initelt' is a single element of an initializer.
1138    It may use braces.  */
1139 initelt:
1140         expr_no_commas
1141                 { process_init_element ($1); }
1142         | '{' 
1143                 { push_init_level (0); }
1144           initlist_maybe_comma '}'
1145                 { process_init_element (pop_init_level (0)); }
1146         | error
1147         /* These are for labeled elements.  The syntax for an array element
1148            initializer conflicts with the syntax for an Objective-C message,
1149            so don't include these productions in the Objective-C grammer.  */
1151         | '[' expr_no_commas ELLIPSIS expr_no_commas ']' '='
1152                 { set_init_index ($2, $4); }
1153           initelt
1154         | '[' expr_no_commas ']' '='
1155                 { set_init_index ($2, NULL_TREE); }
1156           initelt
1157 end ifc
1158         | identifier ':'
1159                 { set_init_label ($1); }
1160           initelt
1161         | '.' identifier '='
1162                 { set_init_label ($2); }
1163           initelt
1164         ;
1166 nested_function:
1167           declarator
1168                 { push_c_function_context ();
1169                   if (! start_function (current_declspecs, $1, 1))
1170                     {
1171                       pop_c_function_context ();
1172                       YYERROR1;
1173                     }
1174                   reinit_parse_for_function ();
1175                   store_parm_decls (); }
1176 /* This used to use compstmt_or_error.
1177    That caused a bug with input `f(g) int g {}',
1178    where the use of YYERROR1 above caused an error
1179    which then was handled by compstmt_or_error.
1180    There followed a repeated execution of that same rule,
1181    which called YYERROR1 again, and so on.  */
1182           compstmt
1183                 { finish_function (1);
1184                   pop_c_function_context (); }
1185         ;
1187 notype_nested_function:
1188           notype_declarator
1189                 { push_c_function_context ();
1190                   if (! start_function (current_declspecs, $1, 1))
1191                     {
1192                       pop_c_function_context ();
1193                       YYERROR1;
1194                     }
1195                   reinit_parse_for_function ();
1196                   store_parm_decls (); }
1197 /* This used to use compstmt_or_error.
1198    That caused a bug with input `f(g) int g {}',
1199    where the use of YYERROR1 above caused an error
1200    which then was handled by compstmt_or_error.
1201    There followed a repeated execution of that same rule,
1202    which called YYERROR1 again, and so on.  */
1203           compstmt
1204                 { finish_function (1);
1205                   pop_c_function_context (); }
1206         ;
1208 /* Any kind of declarator (thus, all declarators allowed
1209    after an explicit typespec).  */
1211 declarator:
1212           after_type_declarator
1213         | notype_declarator
1214         ;
1216 /* A declarator that is allowed only after an explicit typespec.  */
1218 after_type_declarator:
1219           '(' after_type_declarator ')'
1220                 { $$ = $2; }
1221         | after_type_declarator '(' parmlist_or_identifiers  %prec '.'
1222                 { $$ = build_nt (CALL_EXPR, $1, $3, NULL_TREE); }
1223 /*      | after_type_declarator '(' error ')'  %prec '.'
1224                 { $$ = build_nt (CALL_EXPR, $1, NULL_TREE, NULL_TREE);
1225                   poplevel (0, 0, 0); }  */
1226         | after_type_declarator '[' expr ']'  %prec '.'
1227                 { $$ = build_nt (ARRAY_REF, $1, $3); }
1228         | after_type_declarator '[' ']'  %prec '.'
1229                 { $$ = build_nt (ARRAY_REF, $1, NULL_TREE); }
1230         | '*' type_quals after_type_declarator  %prec UNARY
1231                 { $$ = make_pointer_declarator ($2, $3); }
1232         | TYPENAME
1233 ifobjc
1234         | OBJECTNAME
1235 end ifobjc
1236         ;
1238 /* Kinds of declarator that can appear in a parameter list
1239    in addition to notype_declarator.  This is like after_type_declarator
1240    but does not allow a typedef name in parentheses as an identifier
1241    (because it would conflict with a function with that typedef as arg).  */
1243 parm_declarator:
1244           parm_declarator '(' parmlist_or_identifiers  %prec '.'
1245                 { $$ = build_nt (CALL_EXPR, $1, $3, NULL_TREE); }
1246 /*      | parm_declarator '(' error ')'  %prec '.'
1247                 { $$ = build_nt (CALL_EXPR, $1, NULL_TREE, NULL_TREE);
1248                   poplevel (0, 0, 0); }  */
1249         | parm_declarator '[' expr ']'  %prec '.'
1250                 { $$ = build_nt (ARRAY_REF, $1, $3); }
1251         | parm_declarator '[' ']'  %prec '.'
1252                 { $$ = build_nt (ARRAY_REF, $1, NULL_TREE); }
1253         | '*' type_quals parm_declarator  %prec UNARY
1254                 { $$ = make_pointer_declarator ($2, $3); }
1255         | TYPENAME
1256         ;
1258 /* A declarator allowed whether or not there has been
1259    an explicit typespec.  These cannot redeclare a typedef-name.  */
1261 notype_declarator:
1262           notype_declarator '(' parmlist_or_identifiers  %prec '.'
1263                 { $$ = build_nt (CALL_EXPR, $1, $3, NULL_TREE); }
1264 /*      | notype_declarator '(' error ')'  %prec '.'
1265                 { $$ = build_nt (CALL_EXPR, $1, NULL_TREE, NULL_TREE);
1266                   poplevel (0, 0, 0); }  */
1267         | '(' notype_declarator ')'
1268                 { $$ = $2; }
1269         | '*' type_quals notype_declarator  %prec UNARY
1270                 { $$ = make_pointer_declarator ($2, $3); }
1271         | notype_declarator '[' expr ']'  %prec '.'
1272                 { $$ = build_nt (ARRAY_REF, $1, $3); }
1273         | notype_declarator '[' ']'  %prec '.'
1274                 { $$ = build_nt (ARRAY_REF, $1, NULL_TREE); }
1275         | IDENTIFIER
1276         ;
1278 structsp:
1279           STRUCT identifier '{'
1280                 { $$ = start_struct (RECORD_TYPE, $2);
1281                   /* Start scope of tag before parsing components.  */
1282                 }
1283           component_decl_list '}'
1284                 { $$ = finish_struct ($<ttype>4, $5);
1285                   /* Really define the structure.  */
1286                 }
1287         | STRUCT '{' component_decl_list '}'
1288                 { $$ = finish_struct (start_struct (RECORD_TYPE, NULL_TREE),
1289                                       $3); }
1290         | STRUCT identifier
1291                 { $$ = xref_tag (RECORD_TYPE, $2); }
1292         | UNION identifier '{'
1293                 { $$ = start_struct (UNION_TYPE, $2); }
1294           component_decl_list '}'
1295                 { $$ = finish_struct ($<ttype>4, $5); }
1296         | UNION '{' component_decl_list '}'
1297                 { $$ = finish_struct (start_struct (UNION_TYPE, NULL_TREE),
1298                                       $3); }
1299         | UNION identifier
1300                 { $$ = xref_tag (UNION_TYPE, $2); }
1301         | ENUM identifier '{'
1302                 { $<itype>3 = suspend_momentary ();
1303                   $$ = start_enum ($2); }
1304           enumlist maybecomma_warn '}'
1305                 { $$ = finish_enum ($<ttype>4, nreverse ($5));
1306                   resume_momentary ($<itype>3); }
1307         | ENUM '{'
1308                 { $<itype>2 = suspend_momentary ();
1309                   $$ = start_enum (NULL_TREE); }
1310           enumlist maybecomma_warn '}'
1311                 { $$ = finish_enum ($<ttype>3, nreverse ($4));
1312                   resume_momentary ($<itype>2); }
1313         | ENUM identifier
1314                 { $$ = xref_tag (ENUMERAL_TYPE, $2); }
1315         ;
1317 maybecomma:
1318           /* empty */
1319         | ','
1320         ;
1322 maybecomma_warn:
1323           /* empty */
1324         | ','
1325                 { if (pedantic) pedwarn ("comma at end of enumerator list"); }
1326         ;
1328 component_decl_list:
1329           component_decl_list2
1330                 { $$ = $1; }
1331         | component_decl_list2 component_decl
1332                 { $$ = chainon ($1, $2);
1333                   pedwarn ("no semicolon at end of struct or union"); }
1334         ;
1336 component_decl_list2:   /* empty */
1337                 { $$ = NULL_TREE; }
1338         | component_decl_list2 component_decl ';'
1339                 { $$ = chainon ($1, $2); }
1340         | component_decl_list2 ';'
1341                 { if (pedantic)
1342                     pedwarn ("extra semicolon in struct or union specified"); }
1343 ifobjc
1344         /* foo(sizeof(struct{ @defs(ClassName)})); */
1345         | DEFS '(' CLASSNAME ')'
1346                 {
1347                   tree interface = lookup_interface ($3);
1349                   if (interface)
1350                     $$ = get_class_ivars (interface);
1351                   else
1352                     {
1353                       error ("Cannot find interface declaration for `%s'",
1354                              IDENTIFIER_POINTER ($3));
1355                       $$ = NULL_TREE;
1356                     }
1357                 }
1358 end ifobjc
1359         ;
1361 /* There is a shift-reduce conflict here, because `components' may
1362    start with a `typename'.  It happens that shifting (the default resolution)
1363    does the right thing, because it treats the `typename' as part of
1364    a `typed_typespecs'.
1366    It is possible that this same technique would allow the distinction
1367    between `notype_initdecls' and `initdecls' to be eliminated.
1368    But I am being cautious and not trying it.  */
1370 component_decl:
1371           typed_typespecs setspecs components
1372                 { $$ = $3;
1373                   current_declspecs = TREE_VALUE (declspec_stack);
1374                   declspec_stack = TREE_CHAIN (declspec_stack);
1375                   resume_momentary ($2); }
1376         | typed_typespecs
1377                 { if (pedantic)
1378                     pedwarn ("ANSI C forbids member declarations with no members");
1379                   shadow_tag($1);
1380                   $$ = NULL_TREE; }
1381         | nonempty_type_quals setspecs components
1382                 { $$ = $3;
1383                   current_declspecs = TREE_VALUE (declspec_stack);
1384                   declspec_stack = TREE_CHAIN (declspec_stack);
1385                   resume_momentary ($2); }
1386         | nonempty_type_quals
1387                 { if (pedantic)
1388                     pedwarn ("ANSI C forbids member declarations with no members");
1389                   shadow_tag($1);
1390                   $$ = NULL_TREE; }
1391         | error
1392                 { $$ = NULL_TREE; }
1393         ;
1395 components:
1396           component_declarator
1397         | components ',' component_declarator
1398                 { $$ = chainon ($1, $3); }
1399         ;
1401 component_declarator:
1402           save_filename save_lineno declarator maybe_attribute
1403                 { $$ = grokfield ($1, $2, $3, current_declspecs, NULL_TREE);
1404                   decl_attributes ($$, $4); }
1405         | save_filename save_lineno
1406           declarator ':' expr_no_commas maybe_attribute
1407                 { $$ = grokfield ($1, $2, $3, current_declspecs, $5);
1408                   decl_attributes ($$, $6); }
1409         | save_filename save_lineno ':' expr_no_commas maybe_attribute
1410                 { $$ = grokfield ($1, $2, NULL_TREE, current_declspecs, $4);
1411                   decl_attributes ($$, $5); }
1412         ;
1414 /* We chain the enumerators in reverse order.
1415    They are put in forward order where enumlist is used.
1416    (The order used to be significant, but no longer is so.
1417    However, we still maintain the order, just to be clean.)  */
1419 enumlist:
1420           enumerator
1421         | enumlist ',' enumerator
1422                 { $$ = chainon ($3, $1); }
1423         | error
1424                 { $$ = error_mark_node; }
1425         ;
1428 enumerator:
1429           identifier
1430                 { $$ = build_enumerator ($1, NULL_TREE); }
1431         | identifier '=' expr_no_commas
1432                 { $$ = build_enumerator ($1, $3); }
1433         ;
1435 typename:
1436         typed_typespecs absdcl
1437                 { $$ = build_tree_list ($1, $2); }
1438         | nonempty_type_quals absdcl
1439                 { $$ = build_tree_list ($1, $2); }
1440         ;
1442 absdcl:   /* an absolute declarator */
1443         /* empty */
1444                 { $$ = NULL_TREE; }
1445         | absdcl1
1446         ;
1448 nonempty_type_quals:
1449           TYPE_QUAL
1450                 { $$ = tree_cons (NULL_TREE, $1, NULL_TREE); }
1451         | nonempty_type_quals TYPE_QUAL
1452                 { $$ = tree_cons (NULL_TREE, $2, $1); }
1453         ;
1455 type_quals:
1456           /* empty */
1457                 { $$ = NULL_TREE; }
1458         | type_quals TYPE_QUAL
1459                 { $$ = tree_cons (NULL_TREE, $2, $1); }
1460         ;
1462 absdcl1:  /* a nonempty absolute declarator */
1463           '(' absdcl1 ')'
1464                 { $$ = $2; }
1465           /* `(typedef)1' is `int'.  */
1466         | '*' type_quals absdcl1  %prec UNARY
1467                 { $$ = make_pointer_declarator ($2, $3); }
1468         | '*' type_quals  %prec UNARY
1469                 { $$ = make_pointer_declarator ($2, NULL_TREE); }
1470         | absdcl1 '(' parmlist  %prec '.'
1471                 { $$ = build_nt (CALL_EXPR, $1, $3, NULL_TREE); }
1472         | absdcl1 '[' expr ']'  %prec '.'
1473                 { $$ = build_nt (ARRAY_REF, $1, $3); }
1474         | absdcl1 '[' ']'  %prec '.'
1475                 { $$ = build_nt (ARRAY_REF, $1, NULL_TREE); }
1476         | '(' parmlist  %prec '.'
1477                 { $$ = build_nt (CALL_EXPR, NULL_TREE, $2, NULL_TREE); }
1478         | '[' expr ']'  %prec '.'
1479                 { $$ = build_nt (ARRAY_REF, NULL_TREE, $2); }
1480         | '[' ']'  %prec '.'
1481                 { $$ = build_nt (ARRAY_REF, NULL_TREE, NULL_TREE); }
1482         ;
1484 /* at least one statement, the first of which parses without error.  */
1485 /* stmts is used only after decls, so an invalid first statement
1486    is actually regarded as an invalid decl and part of the decls.  */
1488 stmts:
1489           lineno_stmt_or_label
1490         | stmts lineno_stmt_or_label
1491         | stmts errstmt
1492         ;
1494 xstmts:
1495         /* empty */
1496         | stmts
1497         ;
1499 errstmt:  error ';'
1500         ;
1502 pushlevel:  /* empty */
1503                 { emit_line_note (input_filename, lineno);
1504                   pushlevel (0);
1505                   clear_last_expr ();
1506                   push_momentary ();
1507                   expand_start_bindings (0);
1508 ifobjc
1509                   if (objc_method_context)
1510                     add_objc_decls ();
1511 end ifobjc
1512                 }
1513         ;
1515 /* Read zero or more forward-declarations for labels
1516    that nested functions can jump to.  */
1517 maybe_label_decls:
1518           /* empty */
1519         | label_decls
1520                 { if (pedantic)
1521                     pedwarn ("ANSI C forbids label declarations"); }
1522         ;
1524 label_decls:
1525           label_decl
1526         | label_decls label_decl
1527         ;
1529 label_decl:
1530           LABEL identifiers_or_typenames ';'
1531                 { tree link;
1532                   for (link = $2; link; link = TREE_CHAIN (link))
1533                     {
1534                       tree label = shadow_label (TREE_VALUE (link));
1535                       C_DECLARED_LABEL_FLAG (label) = 1;
1536                       declare_nonlocal_label (label);
1537                     }
1538                 }
1539         ;
1541 /* This is the body of a function definition.
1542    It causes syntax errors to ignore to the next openbrace.  */
1543 compstmt_or_error:
1544           compstmt
1545                 {}
1546         | error compstmt
1547         ;
1549 compstmt: '{' '}'
1550                 { $$ = convert (void_type_node, integer_zero_node); }
1551         | '{' pushlevel maybe_label_decls decls xstmts '}'
1552                 { emit_line_note (input_filename, lineno);
1553                   expand_end_bindings (getdecls (), 1, 0);
1554                   $$ = poplevel (1, 1, 0);
1555                   if (yychar == CONSTANT || yychar == STRING)
1556                     pop_momentary_nofree ();
1557                   else
1558                     pop_momentary (); }
1559         | '{' pushlevel maybe_label_decls error '}'
1560                 { emit_line_note (input_filename, lineno);
1561                   expand_end_bindings (getdecls (), kept_level_p (), 0);
1562                   $$ = poplevel (kept_level_p (), 0, 0);
1563                   if (yychar == CONSTANT || yychar == STRING)
1564                     pop_momentary_nofree ();
1565                   else
1566                     pop_momentary (); }
1567         | '{' pushlevel maybe_label_decls stmts '}'
1568                 { emit_line_note (input_filename, lineno);
1569                   expand_end_bindings (getdecls (), kept_level_p (), 0);
1570                   $$ = poplevel (kept_level_p (), 0, 0);
1571                   if (yychar == CONSTANT || yychar == STRING)
1572                     pop_momentary_nofree ();
1573                   else
1574                     pop_momentary (); }
1575         ;
1577 /* Value is number of statements counted as of the closeparen.  */
1578 simple_if:
1579           if_prefix lineno_labeled_stmt
1580 /* Make sure expand_end_cond is run once
1581    for each call to expand_start_cond.
1582    Otherwise a crash is likely.  */
1583         | if_prefix error
1584         ;
1586 if_prefix:
1587           IF '(' expr ')'
1588                 { emit_line_note ($<filename>-1, $<lineno>0);
1589                   expand_start_cond (truthvalue_conversion ($3), 0);
1590                   $<itype>$ = stmt_count;
1591                   if_stmt_file = $<filename>-1;
1592                   if_stmt_line = $<lineno>0;
1593                   position_after_white_space (); }
1594         ;
1596 /* This is a subroutine of stmt.
1597    It is used twice, once for valid DO statements
1598    and once for catching errors in parsing the end test.  */
1599 do_stmt_start:
1600           DO
1601                 { stmt_count++;
1602                   emit_line_note ($<filename>-1, $<lineno>0);
1603                   /* See comment in `while' alternative, above.  */
1604                   emit_nop ();
1605                   expand_start_loop_continue_elsewhere (1);
1606                   position_after_white_space (); }
1607           lineno_labeled_stmt WHILE
1608                 { expand_loop_continue_here (); }
1609         ;
1611 save_filename:
1612                 { $$ = input_filename; }
1613         ;
1615 save_lineno:
1616                 { $$ = lineno; }
1617         ;
1619 lineno_labeled_stmt:
1620           save_filename save_lineno stmt
1621                 { }
1622 /*      | save_filename save_lineno error
1623                 { }
1625         | save_filename save_lineno label lineno_labeled_stmt
1626                 { }
1627         ;
1629 lineno_stmt_or_label:
1630           save_filename save_lineno stmt_or_label
1631                 { }
1632         ;
1634 stmt_or_label:
1635           stmt
1636         | label
1637                 { int next;
1638                   position_after_white_space ();
1639                   next = getc (finput);
1640                   ungetc (next, finput);
1641                   if (pedantic && next == '}')
1642                     pedwarn ("ANSI C forbids label at end of compound statement");
1643                 }
1644         ;
1646 /* Parse a single real statement, not including any labels.  */
1647 stmt:
1648           compstmt
1649                 { stmt_count++; }
1650         | all_iter_stmt 
1651         | expr ';'
1652                 { stmt_count++;
1653                   emit_line_note ($<filename>-1, $<lineno>0);
1654 /* It appears that this should not be done--that a non-lvalue array
1655    shouldn't get an error if the value isn't used.
1656    Section 3.2.2.1 says that an array lvalue gets converted to a pointer
1657    if it appears as a top-level expression,
1658    but says nothing about non-lvalue arrays.  */
1659 #if 0
1660                   /* Call default_conversion to get an error
1661                      on referring to a register array if pedantic.  */
1662                   if (TREE_CODE (TREE_TYPE ($1)) == ARRAY_TYPE
1663                       || TREE_CODE (TREE_TYPE ($1)) == FUNCTION_TYPE)
1664                     $1 = default_conversion ($1);
1665 #endif
1666                   iterator_expand ($1);
1667                   clear_momentary (); }
1668         | simple_if ELSE
1669                 { expand_start_else ();
1670                   $<itype>1 = stmt_count;
1671                   position_after_white_space (); }
1672           lineno_labeled_stmt
1673                 { expand_end_cond ();
1674                   if (extra_warnings && stmt_count == $<itype>1)
1675                     warning ("empty body in an else-statement"); }
1676         | simple_if %prec IF
1677                 { expand_end_cond ();
1678                   /* This warning is here instead of in simple_if, because we
1679                      do not want a warning if an empty if is followed by an
1680                      else statement.  */
1681                   if (extra_warnings && stmt_count == $<itype>1)
1682                     warning_with_file_and_line (if_stmt_file, if_stmt_line,
1683                                                 "empty body in an if-statement"); }
1684 /* Make sure expand_end_cond is run once
1685    for each call to expand_start_cond.
1686    Otherwise a crash is likely.  */
1687         | simple_if ELSE error
1688                 { expand_end_cond (); }
1689         | WHILE
1690                 { stmt_count++;
1691                   emit_line_note ($<filename>-1, $<lineno>0);
1692                   /* The emit_nop used to come before emit_line_note,
1693                      but that made the nop seem like part of the preceding line.
1694                      And that was confusing when the preceding line was
1695                      inside of an if statement and was not really executed.
1696                      I think it ought to work to put the nop after the line number.
1697                      We will see.  --rms, July 15, 1991.  */
1698                   emit_nop (); }
1699           '(' expr ')'
1700                 { /* Don't start the loop till we have succeeded
1701                      in parsing the end test.  This is to make sure
1702                      that we end every loop we start.  */
1703                   expand_start_loop (1);
1704                   emit_line_note (input_filename, lineno);
1705                   expand_exit_loop_if_false (NULL_PTR,
1706                                              truthvalue_conversion ($4));
1707                   position_after_white_space (); }
1708           lineno_labeled_stmt
1709                 { expand_end_loop (); }
1710         | do_stmt_start
1711           '(' expr ')' ';'
1712                 { emit_line_note (input_filename, lineno);
1713                   expand_exit_loop_if_false (NULL_PTR,
1714                                              truthvalue_conversion ($3));
1715                   expand_end_loop ();
1716                   clear_momentary (); }
1717 /* This rule is needed to make sure we end every loop we start.  */
1718         | do_stmt_start error
1719                 { expand_end_loop ();
1720                   clear_momentary (); }
1721         | FOR
1722           '(' xexpr ';'
1723                 { stmt_count++;
1724                   emit_line_note ($<filename>-1, $<lineno>0);
1725                   /* See comment in `while' alternative, above.  */
1726                   emit_nop ();
1727                   if ($3) c_expand_expr_stmt ($3);
1728                   /* Next step is to call expand_start_loop_continue_elsewhere,
1729                      but wait till after we parse the entire for (...).
1730                      Otherwise, invalid input might cause us to call that
1731                      fn without calling expand_end_loop.  */
1732                 }
1733           xexpr ';'
1734                 /* Can't emit now; wait till after expand_start_loop...  */
1735                 { $<lineno>7 = lineno;
1736                   $<filename>$ = input_filename; }
1737           xexpr ')'
1738                 { 
1739                   /* Start the loop.  Doing this after parsing
1740                      all the expressions ensures we will end the loop.  */
1741                   expand_start_loop_continue_elsewhere (1);
1742                   /* Emit the end-test, with a line number.  */
1743                   emit_line_note ($<filename>8, $<lineno>7);
1744                   if ($6)
1745                     expand_exit_loop_if_false (NULL_PTR,
1746                                                truthvalue_conversion ($6));
1747                   /* Don't let the tree nodes for $9 be discarded by
1748                      clear_momentary during the parsing of the next stmt.  */
1749                   push_momentary ();
1750                   $<lineno>7 = lineno;
1751                   $<filename>8 = input_filename;
1752                   position_after_white_space (); }
1753           lineno_labeled_stmt
1754                 { /* Emit the increment expression, with a line number.  */
1755                   emit_line_note ($<filename>8, $<lineno>7);
1756                   expand_loop_continue_here ();
1757                   if ($9)
1758                     c_expand_expr_stmt ($9);
1759                   if (yychar == CONSTANT || yychar == STRING)
1760                     pop_momentary_nofree ();
1761                   else
1762                     pop_momentary ();
1763                   expand_end_loop (); }
1764         | SWITCH '(' expr ')'
1765                 { stmt_count++;
1766                   emit_line_note ($<filename>-1, $<lineno>0);
1767                   c_expand_start_case ($3);
1768                   /* Don't let the tree nodes for $3 be discarded by
1769                      clear_momentary during the parsing of the next stmt.  */
1770                   push_momentary ();
1771                   position_after_white_space (); }
1772           lineno_labeled_stmt
1773                 { expand_end_case ($3);
1774                   if (yychar == CONSTANT || yychar == STRING)
1775                     pop_momentary_nofree ();
1776                   else
1777                     pop_momentary (); }
1778         | BREAK ';'
1779                 { stmt_count++;
1780                   emit_line_note ($<filename>-1, $<lineno>0);
1781                   if ( ! expand_exit_something ())
1782                     error ("break statement not within loop or switch"); }
1783         | CONTINUE ';'
1784                 { stmt_count++;
1785                   emit_line_note ($<filename>-1, $<lineno>0);
1786                   if (! expand_continue_loop (NULL_PTR))
1787                     error ("continue statement not within a loop"); }
1788         | RETURN ';'
1789                 { stmt_count++;
1790                   emit_line_note ($<filename>-1, $<lineno>0);
1791                   c_expand_return (NULL_TREE); }
1792         | RETURN expr ';'
1793                 { stmt_count++;
1794                   emit_line_note ($<filename>-1, $<lineno>0);
1795                   c_expand_return ($2); }
1796         | ASM_KEYWORD maybe_type_qual '(' expr ')' ';'
1797                 { stmt_count++;
1798                   emit_line_note ($<filename>-1, $<lineno>0);
1799                   STRIP_NOPS ($4);
1800                   if ((TREE_CODE ($4) == ADDR_EXPR
1801                        && TREE_CODE (TREE_OPERAND ($4, 0)) == STRING_CST)
1802                       || TREE_CODE ($4) == STRING_CST)
1803                     expand_asm ($4);
1804                   else
1805                     error ("argument of `asm' is not a constant string"); }
1806         /* This is the case with just output operands.  */
1807         | ASM_KEYWORD maybe_type_qual '(' expr ':' asm_operands ')' ';'
1808                 { stmt_count++;
1809                   emit_line_note ($<filename>-1, $<lineno>0);
1810                   c_expand_asm_operands ($4, $6, NULL_TREE, NULL_TREE,
1811                                          $2 == ridpointers[(int)RID_VOLATILE],
1812                                          input_filename, lineno); }
1813         /* This is the case with input operands as well.  */
1814         | ASM_KEYWORD maybe_type_qual '(' expr ':' asm_operands ':' asm_operands ')' ';'
1815                 { stmt_count++;
1816                   emit_line_note ($<filename>-1, $<lineno>0);
1817                   c_expand_asm_operands ($4, $6, $8, NULL_TREE,
1818                                          $2 == ridpointers[(int)RID_VOLATILE],
1819                                          input_filename, lineno); }
1820         /* This is the case with clobbered registers as well.  */
1821         | ASM_KEYWORD maybe_type_qual '(' expr ':' asm_operands ':'
1822           asm_operands ':' asm_clobbers ')' ';'
1823                 { stmt_count++;
1824                   emit_line_note ($<filename>-1, $<lineno>0);
1825                   c_expand_asm_operands ($4, $6, $8, $10,
1826                                          $2 == ridpointers[(int)RID_VOLATILE],
1827                                          input_filename, lineno); }
1828         | GOTO identifier ';'
1829                 { tree decl;
1830                   stmt_count++;
1831                   emit_line_note ($<filename>-1, $<lineno>0);
1832                   decl = lookup_label ($2);
1833                   if (decl != 0)
1834                     {
1835                       TREE_USED (decl) = 1;
1836                       expand_goto (decl);
1837                     }
1838                 }
1839         | GOTO '*' expr ';'
1840                 { stmt_count++;
1841                   emit_line_note ($<filename>-1, $<lineno>0);
1842                   expand_computed_goto (convert (ptr_type_node, $3)); }
1843         | ';'
1844         ;
1846 all_iter_stmt:
1847           all_iter_stmt_simple
1848 /*      | all_iter_stmt_with_decl */
1849         ;
1851 all_iter_stmt_simple:
1852           FOR '(' primary ')' 
1853           {
1854             /* The value returned by this action is  */
1855             /*      1 if everything is OK */ 
1856             /*      0 in case of error or already bound iterator */
1858             $<itype>$ = 0;
1859             if (TREE_CODE ($3) != VAR_DECL)
1860               error ("invalid `for (ITERATOR)' syntax");
1861             else if (! ITERATOR_P ($3))
1862               error ("`%s' is not an iterator",
1863                      IDENTIFIER_POINTER (DECL_NAME ($3)));
1864             else if (ITERATOR_BOUND_P ($3))
1865               error ("`for (%s)' inside expansion of same iterator",
1866                      IDENTIFIER_POINTER (DECL_NAME ($3)));
1867             else
1868               {
1869                 $<itype>$ = 1;
1870                 iterator_for_loop_start ($3);
1871               }
1872           }
1873           lineno_labeled_stmt
1874           {
1875             if ($<itype>5)
1876               iterator_for_loop_end ($3);
1877           }
1879 /*  This really should allow any kind of declaration,
1880     for generality.  Fix it before turning it back on.
1882 all_iter_stmt_with_decl:
1883           FOR '(' ITERATOR pushlevel setspecs iterator_spec ')' 
1884           {
1885 */          /* The value returned by this action is  */
1886             /*      1 if everything is OK */ 
1887             /*      0 in case of error or already bound iterator */
1889             iterator_for_loop_start ($6);
1890           }
1891           lineno_labeled_stmt
1892           {
1893             iterator_for_loop_end ($6);
1894             emit_line_note (input_filename, lineno);
1895             expand_end_bindings (getdecls (), 1, 0);
1896             $<ttype>$ = poplevel (1, 1, 0);
1897             if (yychar == CONSTANT || yychar == STRING)
1898               pop_momentary_nofree ();
1899             else
1900               pop_momentary ();     
1901           }
1904 /* Any kind of label, including jump labels and case labels.
1905    ANSI C accepts labels only before statements, but we allow them
1906    also at the end of a compound statement.  */
1908 label:    CASE expr_no_commas ':'
1909                 { register tree value = check_case_value ($2);
1910                   register tree label
1911                     = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE);
1913                   stmt_count++;
1915                   if (value != error_mark_node)
1916                     {
1917                       tree duplicate;
1918                       int success = pushcase (value, convert_and_check,
1919                                               label, &duplicate);
1920                       if (success == 1)
1921                         error ("case label not within a switch statement");
1922                       else if (success == 2)
1923                         {
1924                           error ("duplicate case value");
1925                           error_with_decl (duplicate, "this is the first entry for that value");
1926                         }
1927                       else if (success == 3)
1928                         warning ("case value out of range");
1929                       else if (success == 5)
1930                         error ("case label within scope of cleanup or variable array");
1931                     }
1932                   position_after_white_space (); }
1933         | CASE expr_no_commas ELLIPSIS expr_no_commas ':'
1934                 { register tree value1 = check_case_value ($2);
1935                   register tree value2 = check_case_value ($4);
1936                   register tree label
1937                     = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE);
1939                   stmt_count++;
1941                   if (value1 != error_mark_node && value2 != error_mark_node)
1942                     {
1943                       tree duplicate;
1944                       int success = pushcase_range (value1, value2,
1945                                                     convert_and_check, label,
1946                                                     &duplicate);
1947                       if (success == 1)
1948                         error ("case label not within a switch statement");
1949                       else if (success == 2)
1950                         {
1951                           error ("duplicate case value");
1952                           error_with_decl (duplicate, "this is the first entry for that value");
1953                         }
1954                       else if (success == 3)
1955                         warning ("case value out of range");
1956                       else if (success == 4)
1957                         warning ("empty case range");
1958                       else if (success == 5)
1959                         error ("case label within scope of cleanup or variable array");
1960                     }
1961                   position_after_white_space (); }
1962         | DEFAULT ':'
1963                 {
1964                   tree duplicate;
1965                   register tree label
1966                     = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE);
1967                   int success = pushcase (NULL_TREE, 0, label, &duplicate);
1968                   stmt_count++;
1969                   if (success == 1)
1970                     error ("default label not within a switch statement");
1971                   else if (success == 2)
1972                     {
1973                       error ("multiple default labels in one switch");
1974                       error_with_decl (duplicate, "this is the first default label");
1975                     }
1976                   position_after_white_space (); }
1977         | identifier ':'
1978                 { tree label = define_label (input_filename, lineno, $1);
1979                   stmt_count++;
1980                   emit_nop ();
1981                   if (label)
1982                     expand_label (label);
1983                   position_after_white_space (); }
1984         ;
1986 /* Either a type-qualifier or nothing.  First thing in an `asm' statement.  */
1988 maybe_type_qual:
1989         /* empty */
1990                 { emit_line_note (input_filename, lineno);
1991                   $$ = NULL_TREE; }
1992         | TYPE_QUAL
1993                 { emit_line_note (input_filename, lineno); }
1994         ;
1996 xexpr:
1997         /* empty */
1998                 { $$ = NULL_TREE; }
1999         | expr
2000         ;
2002 /* These are the operands other than the first string and colon
2003    in  asm ("addextend %2,%1": "=dm" (x), "0" (y), "g" (*x))  */
2004 asm_operands: /* empty */
2005                 { $$ = NULL_TREE; }
2006         | nonnull_asm_operands
2007         ;
2009 nonnull_asm_operands:
2010           asm_operand
2011         | nonnull_asm_operands ',' asm_operand
2012                 { $$ = chainon ($1, $3); }
2013         ;
2015 asm_operand:
2016           STRING '(' expr ')'
2017                 { $$ = build_tree_list ($1, $3); }
2018         ;
2020 asm_clobbers:
2021           string
2022                 { $$ = tree_cons (NULL_TREE, combine_strings ($1), NULL_TREE); }
2023         | asm_clobbers ',' string
2024                 { $$ = tree_cons (NULL_TREE, combine_strings ($3), $1); }
2025         ;
2027 /* This is what appears inside the parens in a function declarator.
2028    Its value is a list of ..._TYPE nodes.  */
2029 parmlist:
2030                 { pushlevel (0);
2031                   clear_parm_order ();
2032                   declare_parm_level (0); }
2033           parmlist_1
2034                 { $$ = $2;
2035                   parmlist_tags_warning ();
2036                   poplevel (0, 0, 0); }
2037         ;
2039 parmlist_1:
2040           parmlist_2 ')'
2041         | parms ';'
2042                 { tree parm;
2043                   if (pedantic)
2044                     pedwarn ("ANSI C forbids forward parameter declarations");
2045                   /* Mark the forward decls as such.  */
2046                   for (parm = getdecls (); parm; parm = TREE_CHAIN (parm))
2047                     TREE_ASM_WRITTEN (parm) = 1;
2048                   clear_parm_order (); }
2049           parmlist_1
2050                 { $$ = $4; }
2051         | error ')'
2052                 { $$ = tree_cons (NULL_TREE, NULL_TREE, NULL_TREE); }
2053         ;
2055 /* This is what appears inside the parens in a function declarator.
2056    Is value is represented in the format that grokdeclarator expects.  */
2057 parmlist_2:  /* empty */
2058                 { $$ = get_parm_info (0); }
2059         | ELLIPSIS
2060                 { $$ = get_parm_info (0);
2061                   if (pedantic)
2062                     pedwarn ("ANSI C requires a named argument before `...'");
2063                 }
2064         | parms
2065                 { $$ = get_parm_info (1); }
2066         | parms ',' ELLIPSIS
2067                 { $$ = get_parm_info (0); }
2068         ;
2070 parms:
2071         parm
2072                 { push_parm_decl ($1); }
2073         | parms ',' parm
2074                 { push_parm_decl ($3); }
2075         ;
2077 /* A single parameter declaration or parameter type name,
2078    as found in a parmlist.  */
2079 parm:
2080           typed_declspecs parm_declarator
2081                 { $$ = build_tree_list ($1, $2) ; }
2082         | typed_declspecs notype_declarator
2083                 { $$ = build_tree_list ($1, $2) ; }
2084         | typed_declspecs absdcl
2085                 { $$ = build_tree_list ($1, $2); }
2086         | declmods notype_declarator
2087                 { $$ = build_tree_list ($1, $2) ; }
2088         | declmods absdcl
2089                 { $$ = build_tree_list ($1, $2); }
2090         ;
2092 /* This is used in a function definition
2093    where either a parmlist or an identifier list is ok.
2094    Its value is a list of ..._TYPE nodes or a list of identifiers.  */
2095 parmlist_or_identifiers:
2096                 { pushlevel (0);
2097                   clear_parm_order ();
2098                   declare_parm_level (1); }
2099           parmlist_or_identifiers_1
2100                 { $$ = $2;
2101                   parmlist_tags_warning ();
2102                   poplevel (0, 0, 0); }
2103         ;
2105 parmlist_or_identifiers_1:
2106           parmlist_1
2107         | identifiers ')'
2108                 { tree t;
2109                   for (t = $1; t; t = TREE_CHAIN (t))
2110                     if (TREE_VALUE (t) == NULL_TREE)
2111                       error ("`...' in old-style identifier list");
2112                   $$ = tree_cons (NULL_TREE, NULL_TREE, $1); }
2113         ;
2115 /* A nonempty list of identifiers.  */
2116 identifiers:
2117         IDENTIFIER
2118                 { $$ = build_tree_list (NULL_TREE, $1); }
2119         | identifiers ',' IDENTIFIER
2120                 { $$ = chainon ($1, build_tree_list (NULL_TREE, $3)); }
2121         ;
2123 /* A nonempty list of identifiers, including typenames.  */
2124 identifiers_or_typenames:
2125         identifier
2126                 { $$ = build_tree_list (NULL_TREE, $1); }
2127         | identifiers_or_typenames ',' identifier
2128                 { $$ = chainon ($1, build_tree_list (NULL_TREE, $3)); }
2129         ;
2131 ifobjc
2132 /* Objective-C productions.  */
2134 objcdef:
2135           classdef
2136         | classdecl
2137         | aliasdecl
2138         | protocoldef
2139         | methoddef
2140         | END
2141                 {
2142                   if (objc_implementation_context)
2143                     {
2144                       finish_class (objc_implementation_context);
2145                       objc_ivar_chain = NULL_TREE;
2146                       objc_implementation_context = NULL_TREE;
2147                     }
2148                   else
2149                     warning ("`@end' must appear in an implementation context");
2150                 }
2151         ;
2153 /* A nonempty list of identifiers.  */
2154 identifier_list:
2155         identifier
2156                 { $$ = build_tree_list (NULL_TREE, $1); }
2157         | identifier_list ',' identifier
2158                 { $$ = chainon ($1, build_tree_list (NULL_TREE, $3)); }
2159         ;
2161 classdecl:
2162           CLASS identifier_list ';'
2163                 {
2164                   objc_declare_class ($2);
2165                 }
2167 aliasdecl:
2168           ALIAS identifier identifier ';'
2169                 {
2170                   objc_declare_alias ($2, $3);
2171                 }
2173 classdef:
2174           INTERFACE identifier protocolrefs '{'
2175                 {
2176                   objc_interface_context = objc_ivar_context
2177                     = start_class (CLASS_INTERFACE_TYPE, $2, NULL_TREE, $3);
2178                   objc_public_flag = 0;
2179                 }
2180           ivar_decl_list '}'
2181                 {
2182                   continue_class (objc_interface_context);
2183                 }
2184           methodprotolist
2185           END
2186                 {
2187                   finish_class (objc_interface_context);
2188                   objc_interface_context = NULL_TREE;
2189                 }
2191         | INTERFACE identifier protocolrefs
2192                 {
2193                   objc_interface_context
2194                     = start_class (CLASS_INTERFACE_TYPE, $2, NULL_TREE, $3);
2195                   continue_class (objc_interface_context);
2196                 }
2197           methodprotolist
2198           END
2199                 {
2200                   finish_class (objc_interface_context);
2201                   objc_interface_context = NULL_TREE;
2202                 }
2204         | INTERFACE identifier ':' identifier protocolrefs '{'
2205                 {
2206                   objc_interface_context = objc_ivar_context
2207                     = start_class (CLASS_INTERFACE_TYPE, $2, $4, $5);
2208                   objc_public_flag = 0;
2209                 }
2210           ivar_decl_list '}'
2211                 {
2212                   continue_class (objc_interface_context);
2213                 }
2214           methodprotolist
2215           END
2216                 {
2217                   finish_class (objc_interface_context);
2218                   objc_interface_context = NULL_TREE;
2219                 }
2221         | INTERFACE identifier ':' identifier protocolrefs
2222                 {
2223                   objc_interface_context
2224                     = start_class (CLASS_INTERFACE_TYPE, $2, $4, $5);
2225                   continue_class (objc_interface_context);
2226                 }
2227           methodprotolist
2228           END
2229                 {
2230                   finish_class (objc_interface_context);
2231                   objc_interface_context = NULL_TREE;
2232                 }
2234         | IMPLEMENTATION identifier '{'
2235                 {
2236                   objc_implementation_context = objc_ivar_context
2237                     = start_class (CLASS_IMPLEMENTATION_TYPE, $2, NULL_TREE, NULL_TREE);
2238                   objc_public_flag = 0;
2239                 }
2240           ivar_decl_list '}'
2241                 {
2242                   objc_ivar_chain
2243                     = continue_class (objc_implementation_context);
2244                 }
2246         | IMPLEMENTATION identifier
2247                 {
2248                   objc_implementation_context
2249                     = start_class (CLASS_IMPLEMENTATION_TYPE, $2, NULL_TREE, NULL_TREE);
2250                   objc_ivar_chain
2251                     = continue_class (objc_implementation_context);
2252                 }
2254         | IMPLEMENTATION identifier ':' identifier '{'
2255                 {
2256                   objc_implementation_context = objc_ivar_context
2257                     = start_class (CLASS_IMPLEMENTATION_TYPE, $2, $4, NULL_TREE);
2258                   objc_public_flag = 0;
2259                 }
2260           ivar_decl_list '}'
2261                 {
2262                   objc_ivar_chain
2263                     = continue_class (objc_implementation_context);
2264                 }
2266         | IMPLEMENTATION identifier ':' identifier
2267                 {
2268                   objc_implementation_context
2269                     = start_class (CLASS_IMPLEMENTATION_TYPE, $2, $4, NULL_TREE);
2270                   objc_ivar_chain
2271                     = continue_class (objc_implementation_context);
2272                 }
2274         | INTERFACE identifier '(' identifier ')' protocolrefs
2275                 {
2276                   objc_interface_context
2277                     = start_class (CATEGORY_INTERFACE_TYPE, $2, $4, $6);
2278                   continue_class (objc_interface_context);
2279                 }
2280           methodprotolist
2281           END
2282                 {
2283                   finish_class (objc_interface_context);
2284                   objc_interface_context = NULL_TREE;
2285                 }
2287         | IMPLEMENTATION identifier '(' identifier ')'
2288                 {
2289                   objc_implementation_context
2290                     = start_class (CATEGORY_IMPLEMENTATION_TYPE, $2, $4, NULL_TREE);
2291                   objc_ivar_chain
2292                     = continue_class (objc_implementation_context);
2293                 }
2294         ;
2296 protocoldef:
2297           PROTOCOL identifier protocolrefs
2298                 {
2299                   remember_protocol_qualifiers ();
2300                   objc_interface_context
2301                     = start_protocol(PROTOCOL_INTERFACE_TYPE, $2, $3);
2302                 }
2303           methodprotolist END
2304                 {
2305                   forget_protocol_qualifiers();
2306                   finish_protocol(objc_interface_context);
2307                   objc_interface_context = NULL_TREE;
2308                 }
2309         ;
2311 protocolrefs:
2312           /* empty */
2313                 {
2314                   $$ = NULL_TREE;
2315                 }
2316         | ARITHCOMPARE identifier_list ARITHCOMPARE
2317                 {
2318                   if ($1 == LT_EXPR && $3 == GT_EXPR)
2319                     $$ = $2;
2320                   else
2321                     YYERROR1;
2322                 }
2323         ;
2325 ivar_decl_list:
2326           ivar_decl_list visibility_spec ivar_decls
2327         | ivar_decls
2328         ;
2330 visibility_spec:
2331           PRIVATE { objc_public_flag = 2; }
2332         | PROTECTED { objc_public_flag = 0; }
2333         | PUBLIC { objc_public_flag = 1; }
2334         ;
2336 ivar_decls:
2337           /* empty */
2338                 {
2339                   $$ = NULL_TREE;
2340                 }
2341         | ivar_decls ivar_decl ';'
2342         | ivar_decls ';'
2343                 {
2344                   if (pedantic)
2345                     pedwarn ("extra semicolon in struct or union specified");
2346                 }
2347         ;
2350 /* There is a shift-reduce conflict here, because `components' may
2351    start with a `typename'.  It happens that shifting (the default resolution)
2352    does the right thing, because it treats the `typename' as part of
2353    a `typed_typespecs'.
2355    It is possible that this same technique would allow the distinction
2356    between `notype_initdecls' and `initdecls' to be eliminated.
2357    But I am being cautious and not trying it.  */
2359 ivar_decl:
2360         typed_typespecs setspecs ivars
2361                 {
2362                   $$ = $3;
2363                   resume_momentary ($2);
2364                 }
2365         | nonempty_type_quals setspecs ivars
2366                 {
2367                   $$ = $3;
2368                   resume_momentary ($2);
2369                 }
2370         | error
2371                 { $$ = NULL_TREE; }
2372         ;
2374 ivars:
2375           /* empty */
2376                 { $$ = NULL_TREE; }
2377         | ivar_declarator
2378         | ivars ',' ivar_declarator
2379         ;
2381 ivar_declarator:
2382           declarator
2383                 {
2384                   $$ = add_instance_variable (objc_ivar_context,
2385                                               objc_public_flag,
2386                                               $1, current_declspecs,
2387                                               NULL_TREE);
2388                 }
2389         | declarator ':' expr_no_commas
2390                 {
2391                   $$ = add_instance_variable (objc_ivar_context,
2392                                               objc_public_flag,
2393                                               $1, current_declspecs, $3);
2394                 }
2395         | ':' expr_no_commas
2396                 {
2397                   $$ = add_instance_variable (objc_ivar_context,
2398                                               objc_public_flag,
2399                                               NULL_TREE,
2400                                               current_declspecs, $2);
2401                 }
2402         ;
2404 methoddef:
2405           '+'
2406                 {
2407                   remember_protocol_qualifiers ();
2408                   if (objc_implementation_context)
2409                     objc_inherit_code = CLASS_METHOD_DECL;
2410                   else
2411                     fatal ("method definition not in class context");
2412                 }
2413           methoddecl
2414                 {
2415                   forget_protocol_qualifiers ();
2416                   add_class_method (objc_implementation_context, $3);
2417                   start_method_def ($3);
2418                   objc_method_context = $3;
2419                 }
2420           optarglist
2421                 {
2422                   continue_method_def ();
2423                 }
2424           compstmt_or_error
2425                 {
2426                   finish_method_def ();
2427                   objc_method_context = NULL_TREE;
2428                 }
2430         | '-'
2431                 {
2432                   remember_protocol_qualifiers ();
2433                   if (objc_implementation_context)
2434                     objc_inherit_code = INSTANCE_METHOD_DECL;
2435                   else
2436                     fatal ("method definition not in class context");
2437                 }
2438           methoddecl
2439                 {
2440                   forget_protocol_qualifiers ();
2441                   add_instance_method (objc_implementation_context, $3);
2442                   start_method_def ($3);
2443                   objc_method_context = $3;
2444                 }
2445           optarglist
2446                 {
2447                   continue_method_def ();
2448                 }
2449           compstmt_or_error
2450                 {
2451                   finish_method_def ();
2452                   objc_method_context = NULL_TREE;
2453                 }
2454         ;
2456 /* the reason for the strange actions in this rule
2457  is so that notype_initdecls when reached via datadef
2458  can find a valid list of type and sc specs in $0. */
2460 methodprotolist:
2461           /* empty  */
2462         | {$<ttype>$ = NULL_TREE; } methodprotolist2
2463         ;
2465 methodprotolist2:                /* eliminates a shift/reduce conflict */
2466            methodproto
2467         |  datadef
2468         | methodprotolist2 methodproto
2469         | methodprotolist2 {$<ttype>$ = NULL_TREE; } datadef
2470         ;
2472 semi_or_error:
2473           ';'
2474         | error
2475         ;
2477 methodproto:
2478           '+'
2479                 {
2480                   objc_inherit_code = CLASS_METHOD_DECL;
2481                 }
2482           methoddecl
2483                 {
2484                   add_class_method (objc_interface_context, $3);
2485                 }
2486           semi_or_error
2488         | '-'
2489                 {
2490                   objc_inherit_code = INSTANCE_METHOD_DECL;
2491                 }
2492           methoddecl
2493                 {
2494                   add_instance_method (objc_interface_context, $3);
2495                 }
2496           semi_or_error
2497         ;
2499 methoddecl:
2500           '(' typename ')' unaryselector
2501                 {
2502                   $$ = build_method_decl (objc_inherit_code, $2, $4, NULL_TREE);
2503                 }
2505         | unaryselector
2506                 {
2507                   $$ = build_method_decl (objc_inherit_code, NULL_TREE, $1, NULL_TREE);
2508                 }
2510         | '(' typename ')' keywordselector optparmlist
2511                 {
2512                   $$ = build_method_decl (objc_inherit_code, $2, $4, $5);
2513                 }
2515         | keywordselector optparmlist
2516                 {
2517                   $$ = build_method_decl (objc_inherit_code, NULL_TREE, $1, $2);
2518                 }
2519         ;
2521 /* "optarglist" assumes that start_method_def has already been called...
2522    if it is not, the "xdecls" will not be placed in the proper scope */
2524 optarglist:
2525           /* empty */
2526         | ';' myxdecls
2527         ;
2529 /* to get around the following situation: "int foo (int a) int b; {}" that
2530    is synthesized when parsing "- a:a b:b; id c; id d; { ... }" */
2532 myxdecls:
2533           /* empty */
2534         | mydecls
2535         ;
2537 mydecls:
2538         mydecl
2539         | errstmt
2540         | mydecls mydecl
2541         | mydecl errstmt
2542         ;
2544 mydecl:
2545         typed_declspecs setspecs myparms ';'
2546                 { resume_momentary ($2); }
2547         | typed_declspecs ';'
2548                 { shadow_tag ($1); }
2549         | declmods ';'
2550                 { pedwarn ("empty declaration"); }
2551         ;
2553 myparms:
2554         myparm
2555                 { push_parm_decl ($1); }
2556         | myparms ',' myparm
2557                 { push_parm_decl ($3); }
2558         ;
2560 /* A single parameter declaration or parameter type name,
2561    as found in a parmlist. DOES NOT ALLOW AN INITIALIZER OR ASMSPEC */
2563 myparm:
2564           parm_declarator
2565                 { $$ = build_tree_list (current_declspecs, $1)  ; }
2566         | notype_declarator
2567                 { $$ = build_tree_list (current_declspecs, $1)  ; }
2568         | absdcl
2569                 { $$ = build_tree_list (current_declspecs, $1)  ; }
2570         ;
2572 optparmlist:
2573           /* empty */
2574                 {
2575                   $$ = NULL_TREE;
2576                 }
2577         | ',' ELLIPSIS
2578                 {
2579                   /* oh what a kludge! */
2580                   $$ = (tree)1;
2581                 }
2582         | ','
2583                 {
2584                   pushlevel (0);
2585                 }
2586           parmlist_2
2587                 {
2588                   /* returns a tree list node generated by get_parm_info */
2589                   $$ = $3;
2590                   poplevel (0, 0, 0);
2591                 }
2592         ;
2594 unaryselector:
2595           selector
2596         ;
2598 keywordselector:
2599           keyworddecl
2601         | keywordselector keyworddecl
2602                 {
2603                   $$ = chainon ($1, $2);
2604                 }
2605         ;
2607 selector:
2608           IDENTIFIER
2609         | TYPENAME
2610         | OBJECTNAME
2611         | reservedwords
2612         ;
2614 reservedwords:
2615           ENUM { $$ = get_identifier (token_buffer); }
2616         | STRUCT { $$ = get_identifier (token_buffer); }
2617         | UNION { $$ = get_identifier (token_buffer); }
2618         | IF { $$ = get_identifier (token_buffer); }
2619         | ELSE { $$ = get_identifier (token_buffer); }
2620         | WHILE { $$ = get_identifier (token_buffer); }
2621         | DO { $$ = get_identifier (token_buffer); }
2622         | FOR { $$ = get_identifier (token_buffer); }
2623         | SWITCH { $$ = get_identifier (token_buffer); }
2624         | CASE { $$ = get_identifier (token_buffer); }
2625         | DEFAULT { $$ = get_identifier (token_buffer); }
2626         | BREAK { $$ = get_identifier (token_buffer); }
2627         | CONTINUE { $$ = get_identifier (token_buffer); }
2628         | RETURN  { $$ = get_identifier (token_buffer); }
2629         | GOTO { $$ = get_identifier (token_buffer); }
2630         | ASM_KEYWORD { $$ = get_identifier (token_buffer); }
2631         | SIZEOF { $$ = get_identifier (token_buffer); }
2632         | TYPEOF { $$ = get_identifier (token_buffer); }
2633         | ALIGNOF { $$ = get_identifier (token_buffer); }
2634         | TYPESPEC | TYPE_QUAL
2635         ;
2637 keyworddecl:
2638           selector ':' '(' typename ')' identifier
2639                 {
2640                   $$ = build_keyword_decl ($1, $4, $6);
2641                 }
2643         | selector ':' identifier
2644                 {
2645                   $$ = build_keyword_decl ($1, NULL_TREE, $3);
2646                 }
2648         | ':' '(' typename ')' identifier
2649                 {
2650                   $$ = build_keyword_decl (NULL_TREE, $3, $5);
2651                 }
2653         | ':' identifier
2654                 {
2655                   $$ = build_keyword_decl (NULL_TREE, NULL_TREE, $2);
2656                 }
2657         ;
2659 messageargs:
2660           selector
2661         | keywordarglist
2662         ;
2664 keywordarglist:
2665           keywordarg
2666         | keywordarglist keywordarg
2667                 {
2668                   $$ = chainon ($1, $2);
2669                 }
2670         ;
2673 keywordexpr:
2674           nonnull_exprlist
2675                 {
2676                   if (TREE_CHAIN ($1) == NULL_TREE)
2677                     /* just return the expr., remove a level of indirection */
2678                     $$ = TREE_VALUE ($1);
2679                   else
2680                     /* we have a comma expr., we will collapse later */
2681                     $$ = $1;
2682                 }
2683         ;
2685 keywordarg:
2686           selector ':' keywordexpr
2687                 {
2688                   $$ = build_tree_list ($1, $3);
2689                 }
2690         | ':' keywordexpr
2691                 {
2692                   $$ = build_tree_list (NULL_TREE, $2);
2693                 }
2694         ;
2696 receiver:
2697           expr
2698         | CLASSNAME
2699                 {
2700                   $$ = get_class_reference ($1);
2701                 }
2702         ;
2704 objcmessageexpr:
2705           '['
2706                 { objc_receiver_context = 1; }
2707           receiver
2708                 { objc_receiver_context = 0; }
2709           messageargs ']'
2710                 {
2711                   $$ = build_tree_list ($3, $5);
2712                 }
2713         ;
2715 selectorarg:
2716           selector
2717         | keywordnamelist
2718         ;
2720 keywordnamelist:
2721           keywordname
2722         | keywordnamelist keywordname
2723                 {
2724                   $$ = chainon ($1, $2);
2725                 }
2726         ;
2728 keywordname:
2729           selector ':'
2730                 {
2731                   $$ = build_tree_list ($1, NULL_TREE);
2732                 }
2733         | ':'
2734                 {
2735                   $$ = build_tree_list (NULL_TREE, NULL_TREE);
2736                 }
2737         ;
2739 objcselectorexpr:
2740           SELECTOR '(' selectorarg ')'
2741                 {
2742                   $$ = $3;
2743                 }
2744         ;
2746 objcprotocolexpr:
2747           PROTOCOL '(' identifier ')'
2748                 {
2749                   $$ = $3;
2750                 }
2751         ;
2753 /* extension to support C-structures in the archiver */
2755 objcencodeexpr:
2756           ENCODE '(' typename ')'
2757                 {
2758                   $$ = groktypename ($3);
2759                 }
2760         ;
2762 end ifobjc