OSDN Git Service

PR middle-end/24912
[pf3gnuchains/gcc-fork.git] / gcc / java / parse-scan.y
1 /* Parser grammar for quick source code scan of Java(TM) language programs.
2    Copyright (C) 1998, 1999, 2000, 2002, 2003, 2004, 2005
3    Free Software Foundation, Inc.
4    Contributed by Alexandre Petit-Bianco (apbianco@cygnus.com)
5
6 This file is part of GCC.
7
8 GCC is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
11 any later version.
12
13 GCC is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING.  If not, write to
20 the Free Software Foundation, 51 Franklin Street, Fifth Floor,
21 Boston, MA 02110-1301, USA.
22
23 Java and all Java-based marks are trademarks or registered trademarks
24 of Sun Microsystems, Inc. in the United States and other countries.
25 The Free Software Foundation is independent of Sun Microsystems, Inc.  */
26
27 /* This file parses Java source code. Action can be further completed
28 to achieve a desired behavior. This file isn't part of the Java
29 language gcc front end.
30
31 The grammar conforms to the Java grammar described in "The Java(TM)
32 Language Specification. J. Gosling, B. Joy, G. Steele. Addison Wesley
33 1996, ISBN 0-201-63451-1"
34
35 Some rules have been modified to support JDK1.1 inner classes
36 definitions and other extensions.  */
37
38 %{
39 #define JC1_LITE
40
41 #include "config.h"
42 #include "system.h"
43 #include "coretypes.h"
44 #include "tm.h"
45 #include "obstack.h"
46 #include "toplev.h"
47
48 extern FILE *finput, *out;
49  
50  const char *main_input_filename;
51
52 /* Obstack for the lexer.  */
53 struct obstack temporary_obstack;
54
55 /* The current parser context.  */
56 struct parser_ctxt *ctxp;
57
58 /* Error and warning counts, because they're used elsewhere  */
59 int java_error_count;
60 int java_warning_count;
61
62 /* Tweak default rules when necessary.  */
63 static int absorber;
64 #define USE_ABSORBER absorber = 0
65
66 /* Keep track of the current package name.  */
67 static const char *package_name;
68
69 /* Keep track of whether things have be listed before.  */
70 static int previous_output;
71
72 /* Record modifier uses  */
73 static int modifier_value;
74
75 /* Record (almost) cyclomatic complexity.  */
76 static int complexity; 
77
78 /* Keeps track of number of bracket pairs after a variable declarator
79    id.  */
80 static int bracket_count; 
81
82 /* Numbers anonymous classes */
83 static int anonymous_count;
84
85 /* This is used to record the current class context.  */
86 struct class_context
87 {
88   char *name;
89   struct class_context *next;
90 };
91
92 /* The global class context.  */
93 static struct class_context *current_class_context;
94
95 /* A special constant used to represent an anonymous context.  */
96 static const char *anonymous_context = "ANONYMOUS";
97
98 /* Count of method depth.  */
99 static int method_depth; 
100
101 /* Record a method declaration  */
102 struct method_declarator {
103   const char *method_name;
104   const char *args;
105 };
106 #define NEW_METHOD_DECLARATOR(D,N,A)                                         \
107 {                                                                            \
108   (D) = xmalloc (sizeof (struct method_declarator));                         \
109   (D)->method_name = (N);                                                    \
110   (D)->args = (A);                                                           \
111 }
112
113 /* Two actions for this grammar */
114 static int make_class_name_recursive (struct obstack *stack,
115                                       struct class_context *ctx);
116 static char *get_class_name (void);
117 static void report_class_declaration (const char *);
118 static void report_main_declaration (struct method_declarator *);
119 static void push_class_context (const char *);
120 static void pop_class_context (void);
121
122 void report (void); 
123
124 #include "lex.h"
125 #include "parse.h"
126 %}
127
128 %union {
129   char *node;
130   struct method_declarator *declarator;
131   int value;                    /* For modifiers */
132 }
133
134 %{
135 extern int flag_assert;
136
137 #include "lex.c"
138 %}
139
140 %pure_parser
141
142 /* Things defined here have to match the order of what's in the
143    binop_lookup table.  */
144
145 %token   PLUS_TK         MINUS_TK        MULT_TK         DIV_TK    REM_TK
146 %token   LS_TK           SRS_TK          ZRS_TK
147 %token   AND_TK          XOR_TK          OR_TK
148 %token   BOOL_AND_TK BOOL_OR_TK 
149 %token   EQ_TK NEQ_TK GT_TK GTE_TK LT_TK LTE_TK
150
151 /* This maps to the same binop_lookup entry than the token above */
152
153 %token   PLUS_ASSIGN_TK  MINUS_ASSIGN_TK MULT_ASSIGN_TK DIV_ASSIGN_TK
154 %token   REM_ASSIGN_TK   
155 %token   LS_ASSIGN_TK    SRS_ASSIGN_TK   ZRS_ASSIGN_TK
156 %token   AND_ASSIGN_TK   XOR_ASSIGN_TK   OR_ASSIGN_TK
157
158
159 /* Modifier TOKEN have to be kept in this order. Don't scramble it */
160
161 %token   PUBLIC_TK       PRIVATE_TK         PROTECTED_TK
162 %token   STATIC_TK       FINAL_TK           SYNCHRONIZED_TK
163 %token   VOLATILE_TK     TRANSIENT_TK       NATIVE_TK
164 %token   PAD_TK          ABSTRACT_TK        MODIFIER_TK
165 %token   STRICT_TK
166
167 /* Keep those two in order, too */
168 %token   DECR_TK INCR_TK
169
170 /* From now one, things can be in any order */
171
172 %token   DEFAULT_TK      IF_TK              THROW_TK
173 %token   BOOLEAN_TK      DO_TK              IMPLEMENTS_TK
174 %token   THROWS_TK       BREAK_TK           IMPORT_TK       
175 %token   ELSE_TK         INSTANCEOF_TK      RETURN_TK
176 %token   VOID_TK         CATCH_TK           INTERFACE_TK
177 %token   CASE_TK         EXTENDS_TK         FINALLY_TK
178 %token   SUPER_TK        WHILE_TK           CLASS_TK
179 %token   SWITCH_TK       CONST_TK           TRY_TK
180 %token   FOR_TK          NEW_TK             CONTINUE_TK
181 %token   GOTO_TK         PACKAGE_TK         THIS_TK
182 %token   ASSERT_TK
183
184 %token   BYTE_TK         SHORT_TK           INT_TK            LONG_TK
185 %token   CHAR_TK         INTEGRAL_TK
186
187 %token   FLOAT_TK        DOUBLE_TK          FP_TK
188
189 %token   ID_TK
190
191 %token   REL_QM_TK         REL_CL_TK NOT_TK  NEG_TK
192
193 %token   ASSIGN_ANY_TK   ASSIGN_TK
194 %token   OP_TK  CP_TK  OCB_TK  CCB_TK  OSB_TK  CSB_TK  SC_TK  C_TK DOT_TK
195
196 %token   STRING_LIT_TK   CHAR_LIT_TK        INT_LIT_TK        FP_LIT_TK
197 %token   TRUE_TK         FALSE_TK           BOOL_LIT_TK       NULL_TK
198
199 %type <node> ID_TK identifier name simple_name qualified_name type
200              primitive_type reference_type array_type formal_parameter_list
201              formal_parameter class_or_interface_type class_type interface_type
202 %type <declarator> method_declarator
203 %type <value>      MODIFIER_TK
204
205 %%
206 /* 19.2 Production from 2.3: The Syntactic Grammar  */
207 goal:
208         compilation_unit
209 ;
210
211 /* 19.3 Productions from 3: Lexical structure  */
212 literal:
213         INT_LIT_TK
214 |       FP_LIT_TK
215 |       BOOL_LIT_TK
216 |       CHAR_LIT_TK
217 |       STRING_LIT_TK
218 |       NULL_TK
219 ;
220
221 /* 19.4 Productions from 4: Types, Values and Variables  */
222 type:
223         primitive_type
224 |       reference_type
225 ;
226
227 primitive_type:
228         INTEGRAL_TK
229                 {
230                   /* use preset global here. FIXME */
231                   $$ = xstrdup ("int");
232                 }
233 |       FP_TK
234                 {
235                   /* use preset global here. FIXME */
236                   $$ = xstrdup ("double");
237                 }
238 |       BOOLEAN_TK
239                 {
240                   /* use preset global here. FIXME */
241                   $$ = xstrdup ("boolean");
242                 }
243 ;
244
245 reference_type:
246         class_or_interface_type
247 |       array_type
248 ;
249
250 class_or_interface_type:
251         name
252 ;
253
254 class_type:
255         class_or_interface_type /* Default rule */
256 ;
257
258 interface_type:
259          class_or_interface_type
260 ;
261
262 array_type:
263         primitive_type dims
264                 {
265                   while (bracket_count-- > 0) 
266                     $$ = concat ("[", $1, NULL);
267                 }
268 |       name dims
269                 {
270                   while (bracket_count-- > 0) 
271                     $$ = concat ("[", $1, NULL);
272                 }
273 ;
274
275 /* 19.5 Productions from 6: Names  */
276 name:
277         simple_name             /* Default rule */
278 |       qualified_name          /* Default rule */
279 ;
280
281 simple_name:
282         identifier              /* Default rule */
283 ;
284
285 qualified_name:
286         name DOT_TK identifier
287                 { 
288                   $$ = concat ($1, ".", $3, NULL);
289                 }
290 ;
291
292 identifier:
293         ID_TK
294 ;
295
296 /* 19.6: Production from 7: Packages  */
297 compilation_unit:
298 |       package_declaration
299 |       import_declarations
300 |       type_declarations
301 |       package_declaration import_declarations
302 |       package_declaration type_declarations
303 |       import_declarations type_declarations
304 |       package_declaration import_declarations type_declarations
305 ;
306
307 import_declarations:
308         import_declaration
309 |       import_declarations import_declaration
310 ;
311
312 type_declarations:
313         type_declaration
314 |       type_declarations type_declaration
315 ;
316
317 package_declaration:
318         PACKAGE_TK name SC_TK
319                 { package_name = $2; }
320 ;
321
322 import_declaration:
323         single_type_import_declaration
324 |       type_import_on_demand_declaration
325 ;
326
327 single_type_import_declaration:
328         IMPORT_TK name SC_TK
329 ;
330
331 type_import_on_demand_declaration:
332         IMPORT_TK name DOT_TK MULT_TK SC_TK
333 ;
334
335 type_declaration:
336         class_declaration
337 |       interface_declaration
338 |       empty_statement
339 ;
340
341 /* 19.7 Shortened from the original:
342    modifiers: modifier | modifiers modifier
343    modifier: any of public...  */
344 modifiers:
345         MODIFIER_TK
346                 { 
347                   if ($1 == PUBLIC_TK)
348                     modifier_value++;
349                   if ($1 == STATIC_TK)
350                     modifier_value++;
351                   USE_ABSORBER;
352                 }       
353 |       modifiers MODIFIER_TK
354                 { 
355                   if ($2 == PUBLIC_TK)
356                     modifier_value++;
357                   if ($2 == STATIC_TK)
358                     modifier_value++;
359                   USE_ABSORBER;
360                 }       
361 ;
362
363 /* 19.8.1 Production from $8.1: Class Declaration */
364 class_declaration:
365         modifiers CLASS_TK identifier super interfaces 
366                 { 
367                   report_class_declaration($3);
368                   modifier_value = 0;
369                 }
370         class_body
371 |       CLASS_TK identifier super interfaces 
372                 { report_class_declaration($2); }
373         class_body
374 ;
375
376 super:
377 |       EXTENDS_TK class_type
378 ;
379
380 interfaces:
381 |       IMPLEMENTS_TK interface_type_list
382 ;
383
384 interface_type_list:
385         interface_type
386                 { USE_ABSORBER; }
387 |       interface_type_list C_TK interface_type
388                 { USE_ABSORBER; }
389 ;
390
391 class_body:
392         OCB_TK CCB_TK
393                 { pop_class_context (); }
394 |       OCB_TK class_body_declarations CCB_TK
395                 { pop_class_context (); }
396 ;
397
398 class_body_declarations:
399         class_body_declaration
400 |       class_body_declarations class_body_declaration
401 ;
402
403 class_body_declaration:
404         class_member_declaration
405 |       static_initializer
406 |       constructor_declaration
407 |       block                   /* Added, JDK1.1, instance initializer */
408 ;
409
410 class_member_declaration:
411         field_declaration
412 |       method_declaration
413 |       class_declaration       /* Added, JDK1.1 inner classes */
414 |       interface_declaration   /* Added, JDK1.1 inner classes */
415 |       empty_statement
416 ;
417
418 /* 19.8.2 Productions from 8.3: Field Declarations  */
419 field_declaration:
420         type variable_declarators SC_TK
421                 { USE_ABSORBER; }
422 |       modifiers type variable_declarators SC_TK
423                 { modifier_value = 0; }
424 ;
425
426 variable_declarators:
427         /* Should we use build_decl_list () instead ? FIXME */
428         variable_declarator     /* Default rule */
429 |       variable_declarators C_TK variable_declarator
430 ;
431
432 variable_declarator:
433         variable_declarator_id
434 |       variable_declarator_id ASSIGN_TK variable_initializer
435 ;
436
437 variable_declarator_id:
438         identifier
439                 { bracket_count = 0; USE_ABSORBER; }
440 |       variable_declarator_id OSB_TK CSB_TK
441                 { ++bracket_count; }
442 ;
443
444 variable_initializer:
445         expression
446 |       array_initializer
447 ;
448
449 /* 19.8.3 Productions from 8.4: Method Declarations  */
450 method_declaration:
451         method_header
452                 { ++method_depth; }
453         method_body
454                 { --method_depth; }
455 ;
456
457 method_header:  
458         type method_declarator throws
459                 { USE_ABSORBER; }
460 |       VOID_TK method_declarator throws
461 |       modifiers type method_declarator throws
462                 { modifier_value = 0; }
463 |       modifiers VOID_TK method_declarator throws
464                 { 
465                   report_main_declaration ($3);
466                   modifier_value = 0;
467                 }
468 ;
469
470 method_declarator:
471         identifier OP_TK CP_TK
472                 { 
473                   struct method_declarator *d;
474                   NEW_METHOD_DECLARATOR (d, $1, NULL);
475                   $$ = d;
476                 }
477 |       identifier OP_TK formal_parameter_list CP_TK
478                 { 
479                   struct method_declarator *d;
480                   NEW_METHOD_DECLARATOR (d, $1, $3);
481                   $$ = d;
482                 }
483 |       method_declarator OSB_TK CSB_TK
484 ;
485
486 formal_parameter_list:
487         formal_parameter
488 |       formal_parameter_list C_TK formal_parameter
489                 {
490                   $$ = concat ($1, ",", $3, NULL);
491                 }
492 ;
493
494 formal_parameter:
495         type variable_declarator_id
496                 { 
497                   USE_ABSORBER;
498                   if (bracket_count)
499                     {
500                       int i;
501                       char *n = xmalloc (bracket_count + 1 + strlen ($$));
502                       for (i = 0; i < bracket_count; ++i)
503                         n[i] = '[';
504                       strcpy (n + bracket_count, $$);
505                       $$ = n;
506                     }
507                   else
508                     $$ = $1;
509                 }
510 |       modifiers type variable_declarator_id /* Added, JDK1.1 final locals */
511                 {
512                   if (bracket_count)
513                     {
514                       int i;
515                       char *n = xmalloc (bracket_count + 1 + strlen ($2));
516                       for (i = 0; i < bracket_count; ++i)
517                         n[i] = '[';
518                       strcpy (n + bracket_count, $2);
519                       $$ = n;
520                     }
521                   else
522                     $$ = $2;
523                 }
524 ;
525
526 throws:
527 |       THROWS_TK class_type_list
528 ;
529
530 class_type_list:
531         class_type
532                 { USE_ABSORBER; }
533 |       class_type_list C_TK class_type
534                 { USE_ABSORBER; }
535 ;
536
537 method_body:
538         block
539 |       SC_TK
540 ;
541
542 /* 19.8.4 Productions from 8.5: Static Initializers  */
543 static_initializer:
544         static block
545 ;
546
547 static:                         /* Test lval.sub_token here */
548         MODIFIER_TK
549                 { USE_ABSORBER; }
550 ;
551
552 /* 19.8.5 Productions from 8.6: Constructor Declarations  */
553 /* NOTE FOR FURTHER WORK ON CONSTRUCTORS:
554    - If a forbidden modifier is found, the error is either the use of
555      a forbidden modifier for a constructor OR bogus attempt to declare a
556      method without having specified the return type. FIXME */
557 constructor_declaration:
558         constructor_declarator throws constructor_body
559 |       modifiers constructor_declarator throws constructor_body
560                 { modifier_value = 0; }
561 /* extra SC_TK, FIXME */
562 |       constructor_declarator throws constructor_body SC_TK
563 /* extra SC_TK, FIXME */
564 |       modifiers constructor_declarator throws constructor_body SC_TK
565                 { modifier_value = 0; }
566 /* I'm not happy with the SC_TK addition. It isn't in the grammar and should
567    probably be matched by and empty statement. But it doesn't work. FIXME */
568 ;
569
570 constructor_declarator:
571         simple_name OP_TK CP_TK
572                 { USE_ABSORBER; }
573 |       simple_name OP_TK formal_parameter_list CP_TK
574                 { USE_ABSORBER; }
575 ;
576
577 constructor_body:
578         OCB_TK CCB_TK
579 |       OCB_TK explicit_constructor_invocation CCB_TK
580 |       OCB_TK block_statements CCB_TK
581 |       OCB_TK explicit_constructor_invocation block_statements CCB_TK
582 ;
583
584 /* Error recovery for that rule moved down expression_statement: rule.  */
585 explicit_constructor_invocation:
586         this_or_super OP_TK CP_TK SC_TK
587 |       this_or_super OP_TK argument_list CP_TK SC_TK
588         /* Added, JDK1.1 inner classes. Modified because the rule
589            'primary' couldn't work.  */
590 |       name DOT_TK SUPER_TK OP_TK argument_list CP_TK SC_TK
591                 { USE_ABSORBER; }
592 |       name DOT_TK SUPER_TK OP_TK CP_TK SC_TK
593                 { USE_ABSORBER; }
594 ;
595
596 this_or_super:                  /* Added, simplifies error diagnostics */
597         THIS_TK
598 |       SUPER_TK
599 ;
600
601 /* 19.9 Productions from 9: Interfaces  */
602 /* 19.9.1 Productions from 9.1: Interfaces Declarations  */
603 interface_declaration:
604         INTERFACE_TK identifier
605                 { report_class_declaration ($2); modifier_value = 0; }
606         interface_body
607 |       modifiers INTERFACE_TK identifier
608                 { report_class_declaration ($3); modifier_value = 0; }
609         interface_body
610 |       INTERFACE_TK identifier extends_interfaces
611                 { report_class_declaration ($2); modifier_value = 0; }
612         interface_body
613 |       modifiers INTERFACE_TK identifier extends_interfaces
614                 { report_class_declaration ($3); modifier_value = 0; }
615         interface_body
616 ;
617
618 extends_interfaces:
619         EXTENDS_TK interface_type
620 |       extends_interfaces C_TK interface_type
621 ;
622
623 interface_body:
624         OCB_TK CCB_TK
625                 { pop_class_context (); }
626 |       OCB_TK interface_member_declarations CCB_TK
627                 { pop_class_context (); }
628 ;
629
630 interface_member_declarations:
631         interface_member_declaration
632 |       interface_member_declarations interface_member_declaration
633 ;
634
635 interface_member_declaration:
636         constant_declaration
637 |       abstract_method_declaration
638 |       class_declaration       /* Added, JDK1.1 inner classes */
639 |       interface_declaration   /* Added, JDK1.1 inner classes */
640 |       empty_statement
641 ;
642
643 constant_declaration:
644         field_declaration
645 ;
646
647 abstract_method_declaration:
648         method_header SC_TK
649 ;
650
651 /* 19.10 Productions from 10: Arrays  */
652 array_initializer:
653         OCB_TK CCB_TK
654 |       OCB_TK variable_initializers CCB_TK
655 |       OCB_TK C_TK CCB_TK
656 |       OCB_TK variable_initializers C_TK CCB_TK
657 ;
658
659 variable_initializers:
660         variable_initializer
661 |       variable_initializers C_TK variable_initializer
662 ;
663
664 /* 19.11 Production from 14: Blocks and Statements  */
665 block:
666         OCB_TK CCB_TK
667 |       OCB_TK block_statements CCB_TK
668 ;
669
670 block_statements:
671         block_statement
672 |       block_statements block_statement
673 ;
674
675 block_statement:
676         local_variable_declaration_statement
677 |       statement
678 |       class_declaration       /* Added, JDK1.1 inner classes */
679 ;
680
681 local_variable_declaration_statement:
682         local_variable_declaration SC_TK /* Can't catch missing ';' here */
683 ;
684
685 local_variable_declaration:
686         type variable_declarators
687                 { USE_ABSORBER; }
688 |       modifiers type variable_declarators /* Added, JDK1.1 final locals */
689                 { modifier_value = 0; }
690 ;
691
692 statement:
693         statement_without_trailing_substatement
694 |       labeled_statement
695 |       if_then_statement
696 |       if_then_else_statement
697 |       while_statement
698 |       for_statement
699 ;
700
701 statement_nsi:
702         statement_without_trailing_substatement
703 |       labeled_statement_nsi
704 |       if_then_else_statement_nsi
705 |       while_statement_nsi
706 |       for_statement_nsi
707 ;
708
709 statement_without_trailing_substatement:
710         block
711 |       empty_statement
712 |       expression_statement
713 |       switch_statement
714 |       do_statement
715 |       break_statement
716 |       continue_statement
717 |       return_statement
718 |       synchronized_statement
719 |       throw_statement
720 |       try_statement
721 |       assert_statement
722 ;
723
724 empty_statement:
725         SC_TK
726 ;
727
728 label_decl:
729         identifier REL_CL_TK
730                 { USE_ABSORBER; }
731 ;
732
733 labeled_statement:
734         label_decl statement
735 ;
736
737 labeled_statement_nsi:
738         label_decl statement_nsi
739 ;
740
741 /* We concentrate here a bunch of error handling rules that we couldn't write
742    earlier, because expression_statement catches a missing ';'.  */
743 expression_statement:
744         statement_expression SC_TK
745 ;
746
747 statement_expression: 
748         assignment
749 |       pre_increment_expression
750 |       pre_decrement_expression
751 |       post_increment_expression
752 |       post_decrement_expression
753 |       method_invocation
754 |       class_instance_creation_expression
755 ;
756
757 if_then_statement:
758         IF_TK OP_TK expression CP_TK statement { ++complexity; }
759 ;
760
761 if_then_else_statement:
762         IF_TK OP_TK expression CP_TK statement_nsi ELSE_TK statement
763         { ++complexity; }
764 ;
765
766 if_then_else_statement_nsi:
767         IF_TK OP_TK expression CP_TK statement_nsi ELSE_TK statement_nsi
768         { ++complexity; }
769 ;
770
771 switch_statement:
772         SWITCH_TK OP_TK expression CP_TK switch_block
773 ;
774
775 switch_block:
776         OCB_TK CCB_TK
777 |       OCB_TK switch_labels CCB_TK
778 |       OCB_TK switch_block_statement_groups CCB_TK
779 |       OCB_TK switch_block_statement_groups switch_labels CCB_TK
780 ;
781
782 switch_block_statement_groups: 
783         switch_block_statement_group
784 |       switch_block_statement_groups switch_block_statement_group
785 ;
786
787 switch_block_statement_group:
788         switch_labels block_statements { ++complexity; }
789 ;
790
791
792 switch_labels:
793         switch_label
794 |       switch_labels switch_label
795 ;
796
797 switch_label:
798         CASE_TK constant_expression REL_CL_TK
799 |       DEFAULT_TK REL_CL_TK
800 ;
801
802 while_expression:
803         WHILE_TK OP_TK expression CP_TK { ++complexity; }
804 ;
805
806 while_statement:
807         while_expression statement
808 ;
809
810 while_statement_nsi:
811         while_expression statement_nsi
812 ;
813
814 do_statement_begin:
815         DO_TK
816 ;
817
818 do_statement: 
819         do_statement_begin statement WHILE_TK OP_TK expression CP_TK SC_TK
820         { ++complexity; }
821 ;
822
823 for_statement:
824         for_begin SC_TK expression SC_TK for_update CP_TK statement
825 |       for_begin SC_TK SC_TK for_update CP_TK statement
826 ;
827
828 for_statement_nsi:
829         for_begin SC_TK expression SC_TK for_update CP_TK statement_nsi
830 |       for_begin SC_TK SC_TK for_update CP_TK statement_nsi
831 ;
832
833 for_header:
834         FOR_TK OP_TK
835 ;
836
837 for_begin:
838         for_header for_init { ++complexity; }
839 ;
840 for_init:                       /* Can be empty */
841 |       statement_expression_list
842 |       local_variable_declaration
843 ;
844
845 for_update:                     /* Can be empty */
846 |       statement_expression_list
847 ;
848
849 statement_expression_list:
850         statement_expression
851 |       statement_expression_list C_TK statement_expression
852 ;
853
854 break_statement:
855         BREAK_TK SC_TK
856 |       BREAK_TK identifier SC_TK
857 ;
858
859 /* `continue' with a label is considered for complexity but ordinary
860    continue is not.  */
861 continue_statement:
862         CONTINUE_TK SC_TK
863         |       CONTINUE_TK identifier SC_TK { ++complexity; }
864 ;
865
866 return_statement:
867         RETURN_TK SC_TK
868 |       RETURN_TK expression SC_TK
869 ;
870
871 throw_statement:
872         THROW_TK expression SC_TK { ++complexity; }
873 ;
874
875 assert_statement:
876         ASSERT_TK expression REL_CL_TK expression SC_TK
877 |       ASSERT_TK expression SC_TK
878 |       ASSERT_TK error
879                 {yyerror ("Missing term"); RECOVER;}
880 |       ASSERT_TK expression error
881                 {yyerror ("';' expected"); RECOVER;}
882 ;
883 synchronized_statement:
884         synchronized OP_TK expression CP_TK block
885 |       synchronized OP_TK expression CP_TK error
886 ;
887
888 synchronized:                   /* Test lval.sub_token here */
889         MODIFIER_TK
890                 { USE_ABSORBER; }
891 ;
892
893 try_statement:
894         TRY_TK block catches
895 |       TRY_TK block finally
896 |       TRY_TK block catches finally
897 ;
898
899 catches:
900         catch_clause
901 |       catches catch_clause
902 ;
903
904 catch_clause:
905         CATCH_TK OP_TK formal_parameter CP_TK block { ++complexity; }
906 ;
907
908 finally:
909         FINALLY_TK block { ++complexity; }
910 ;
911
912 /* 19.12 Production from 15: Expressions  */
913 primary:
914         primary_no_new_array
915 |       array_creation_expression
916 ;
917
918 primary_no_new_array:
919         literal
920 |       THIS_TK
921 |       OP_TK expression CP_TK
922 |       class_instance_creation_expression
923 |       field_access
924 |       method_invocation
925 |       array_access
926 |       type_literals
927         /* Added, JDK1.1 inner classes. Documentation is wrong
928            referring to a 'ClassName' (class_name) rule that doesn't
929            exist. Used name instead.  */
930 |       name DOT_TK THIS_TK
931                 { USE_ABSORBER; }
932 ;
933
934 type_literals:
935         name DOT_TK CLASS_TK
936                 { USE_ABSORBER; }
937 |       array_type DOT_TK CLASS_TK
938                 { USE_ABSORBER; }
939 |       primitive_type DOT_TK CLASS_TK
940                 { USE_ABSORBER; }
941 |       VOID_TK DOT_TK CLASS_TK
942                 { USE_ABSORBER; }
943 ;
944
945 class_instance_creation_expression:
946         NEW_TK class_type OP_TK argument_list CP_TK
947 |       NEW_TK class_type OP_TK CP_TK
948 |       anonymous_class_creation
949 |       something_dot_new identifier OP_TK CP_TK
950 |       something_dot_new identifier OP_TK CP_TK class_body
951 |       something_dot_new identifier OP_TK argument_list CP_TK
952 |       something_dot_new identifier OP_TK argument_list CP_TK class_body
953 ;
954
955 anonymous_class_creation:
956         NEW_TK class_type OP_TK CP_TK
957                 { report_class_declaration (anonymous_context); }
958         class_body         
959 |       NEW_TK class_type OP_TK argument_list CP_TK
960                 { report_class_declaration (anonymous_context); }
961         class_body
962 ;
963
964 something_dot_new:              /* Added, not part of the specs. */
965         name DOT_TK NEW_TK
966                 { USE_ABSORBER; }
967 |       primary DOT_TK NEW_TK
968 ;
969
970 argument_list:
971         expression
972 |       argument_list C_TK expression
973 |       argument_list C_TK error
974 ;
975
976 array_creation_expression:
977         NEW_TK primitive_type dim_exprs
978 |       NEW_TK class_or_interface_type dim_exprs
979 |       NEW_TK primitive_type dim_exprs dims
980 |       NEW_TK class_or_interface_type dim_exprs dims
981         /* Added, JDK1.1 anonymous array. Initial documentation rule
982            modified */
983 |       NEW_TK class_or_interface_type dims array_initializer
984 |       NEW_TK primitive_type dims array_initializer
985 ;
986
987 dim_exprs:
988         dim_expr
989 |       dim_exprs dim_expr
990 ;
991
992 dim_expr:
993         OSB_TK expression CSB_TK
994 ;
995
996 dims:                           
997         OSB_TK CSB_TK
998                 { bracket_count = 1; }
999 |       dims OSB_TK CSB_TK
1000                 { bracket_count++; }
1001 ;
1002
1003 field_access:
1004         primary DOT_TK identifier
1005 |       SUPER_TK DOT_TK identifier
1006 ;
1007
1008 /* We include method invocation in the complexity measure on the
1009    theory that most method calls are virtual and therefore involve a
1010    decision point.  */
1011 method_invocation:
1012         name OP_TK CP_TK
1013                 { USE_ABSORBER; ++complexity; }
1014 |       name OP_TK argument_list CP_TK
1015                 { USE_ABSORBER; ++complexity; }
1016 |       primary DOT_TK identifier OP_TK CP_TK { ++complexity; }
1017 |       primary DOT_TK identifier OP_TK argument_list CP_TK { ++complexity; }
1018 |       SUPER_TK DOT_TK identifier OP_TK CP_TK { ++complexity; }
1019 |       SUPER_TK DOT_TK identifier OP_TK argument_list CP_TK { ++complexity; }
1020 ;
1021
1022 array_access:
1023         name OSB_TK expression CSB_TK
1024                 { USE_ABSORBER; }
1025 |       primary_no_new_array OSB_TK expression CSB_TK
1026 ;
1027
1028 postfix_expression:
1029         primary
1030 |       name
1031                 { USE_ABSORBER; }
1032 |       post_increment_expression
1033 |       post_decrement_expression
1034 ;
1035
1036 post_increment_expression:
1037         postfix_expression INCR_TK
1038 ;
1039
1040 post_decrement_expression:
1041         postfix_expression DECR_TK
1042 ;
1043
1044 unary_expression:
1045         pre_increment_expression
1046 |       pre_decrement_expression
1047 |       PLUS_TK unary_expression
1048 |       MINUS_TK unary_expression
1049 |       unary_expression_not_plus_minus
1050 ;
1051
1052 pre_increment_expression:
1053         INCR_TK unary_expression
1054 ;
1055
1056 pre_decrement_expression:
1057         DECR_TK unary_expression
1058 ;
1059
1060 unary_expression_not_plus_minus:
1061         postfix_expression
1062 |       NOT_TK unary_expression
1063 |       NEG_TK unary_expression
1064 |       cast_expression
1065 ;
1066
1067 cast_expression:                /* Error handling here is potentially weak */
1068         OP_TK primitive_type dims CP_TK unary_expression
1069 |       OP_TK primitive_type CP_TK unary_expression
1070 |       OP_TK expression CP_TK unary_expression_not_plus_minus
1071 |       OP_TK name dims CP_TK unary_expression_not_plus_minus
1072 ;
1073
1074 multiplicative_expression:
1075         unary_expression
1076 |       multiplicative_expression MULT_TK unary_expression
1077 |       multiplicative_expression DIV_TK unary_expression
1078 |       multiplicative_expression REM_TK unary_expression
1079 ;
1080
1081 additive_expression:
1082         multiplicative_expression
1083 |       additive_expression PLUS_TK multiplicative_expression
1084 |       additive_expression MINUS_TK multiplicative_expression
1085 ;
1086
1087 shift_expression:
1088         additive_expression
1089 |       shift_expression LS_TK additive_expression
1090 |       shift_expression SRS_TK additive_expression
1091 |       shift_expression ZRS_TK additive_expression
1092 ;
1093
1094 relational_expression:
1095         shift_expression
1096 |       relational_expression LT_TK shift_expression
1097 |       relational_expression GT_TK shift_expression
1098 |       relational_expression LTE_TK shift_expression
1099 |       relational_expression GTE_TK shift_expression
1100 |       relational_expression INSTANCEOF_TK reference_type
1101 ;
1102
1103 equality_expression:
1104         relational_expression
1105 |       equality_expression EQ_TK relational_expression
1106 |       equality_expression NEQ_TK relational_expression
1107 ;
1108
1109 and_expression:
1110         equality_expression
1111 |       and_expression AND_TK equality_expression
1112 ;
1113
1114 exclusive_or_expression:
1115         and_expression
1116 |       exclusive_or_expression XOR_TK and_expression
1117 ;
1118
1119 inclusive_or_expression:
1120         exclusive_or_expression
1121 |       inclusive_or_expression OR_TK exclusive_or_expression
1122 ;
1123
1124 conditional_and_expression:
1125         inclusive_or_expression
1126 |       conditional_and_expression BOOL_AND_TK inclusive_or_expression
1127         { ++complexity; }
1128 ;
1129
1130 conditional_or_expression:
1131         conditional_and_expression
1132 |       conditional_or_expression BOOL_OR_TK conditional_and_expression
1133         { ++complexity; }
1134 ;
1135
1136 conditional_expression:         /* Error handling here is weak */
1137         conditional_or_expression
1138 |       conditional_or_expression REL_QM_TK expression REL_CL_TK conditional_expression
1139         { ++complexity; }
1140 ;
1141
1142 assignment_expression:
1143         conditional_expression
1144 |       assignment
1145 ;
1146
1147 assignment:
1148         left_hand_side assignment_operator assignment_expression
1149 ;
1150
1151 left_hand_side:
1152         name
1153                 { USE_ABSORBER; }
1154 |       field_access
1155 |       array_access
1156 ;
1157
1158 assignment_operator:
1159         ASSIGN_ANY_TK
1160 |       ASSIGN_TK
1161 ;
1162
1163 expression:
1164         assignment_expression
1165 ;
1166
1167 constant_expression:
1168         expression
1169 ;
1170
1171 %%
1172 \f
1173 /* Create a new parser context */
1174
1175 void
1176 java_push_parser_context (void)
1177 {
1178   struct parser_ctxt *new = xcalloc (1, sizeof (struct parser_ctxt));
1179
1180   new->next = ctxp;
1181   ctxp = new;
1182 }  
1183
1184 static void
1185 push_class_context (const char *name)
1186 {
1187   struct class_context *ctx;
1188
1189   ctx = xmalloc (sizeof (struct class_context));
1190   ctx->name = (char *) name;
1191   ctx->next = current_class_context;
1192   current_class_context = ctx;
1193 }
1194
1195 static void
1196 pop_class_context (void)
1197 {
1198   struct class_context *ctx;
1199
1200   if (current_class_context == NULL)
1201     return;
1202
1203   ctx = current_class_context->next;
1204   if (current_class_context->name != anonymous_context)
1205     free (current_class_context->name);
1206   free (current_class_context);
1207
1208   current_class_context = ctx;
1209   if (current_class_context == NULL)
1210     anonymous_count = 0;
1211 }
1212
1213 /* Recursively construct the class name.  This is just a helper
1214    function for get_class_name().  */
1215 static int
1216 make_class_name_recursive (struct obstack *stack, struct class_context *ctx)
1217 {
1218   if (! ctx)
1219     return 0;
1220
1221   make_class_name_recursive (stack, ctx->next);
1222
1223   /* Replace an anonymous context with the appropriate counter value.  */
1224   if (ctx->name == anonymous_context)
1225     {
1226       char buf[50];
1227       ++anonymous_count;
1228       sprintf (buf, "%d", anonymous_count);
1229       ctx->name = xstrdup (buf);
1230     }
1231
1232   obstack_grow (stack, ctx->name, strlen (ctx->name));
1233   obstack_1grow (stack, '$');
1234
1235   return ISDIGIT (ctx->name[0]);
1236 }
1237
1238 /* Return a newly allocated string holding the name of the class.  */
1239 static char *
1240 get_class_name (void)
1241 {
1242   char *result;
1243   int last_was_digit;
1244   struct obstack name_stack;
1245
1246   obstack_init (&name_stack);
1247
1248   /* Duplicate the logic of parse.y:maybe_make_nested_class_name().  */
1249   last_was_digit = make_class_name_recursive (&name_stack,
1250                                               current_class_context->next);
1251
1252   if (! last_was_digit
1253       && method_depth
1254       && current_class_context->name != anonymous_context)
1255     {
1256       char buf[50];
1257       ++anonymous_count;
1258       sprintf (buf, "%d", anonymous_count);
1259       obstack_grow (&name_stack, buf, strlen (buf));
1260       obstack_1grow (&name_stack, '$');
1261     }
1262
1263   if (current_class_context->name == anonymous_context)
1264     {
1265       char buf[50];
1266       ++anonymous_count;
1267       sprintf (buf, "%d", anonymous_count);
1268       current_class_context->name = xstrdup (buf);
1269       obstack_grow0 (&name_stack, buf, strlen (buf));
1270     }
1271   else
1272     obstack_grow0 (&name_stack, current_class_context->name,
1273                    strlen (current_class_context->name));
1274
1275   result = xstrdup (obstack_finish (&name_stack));
1276   obstack_free (&name_stack, NULL);
1277
1278   return result;
1279 }
1280
1281 /* Actions defined here */
1282
1283 static void
1284 report_class_declaration (const char * name)
1285 {
1286   extern int flag_dump_class, flag_list_filename;
1287
1288   push_class_context (name);
1289   if (flag_dump_class)
1290     {
1291       char *name = get_class_name ();
1292
1293       if (!previous_output)
1294         {
1295           if (flag_list_filename)
1296             fprintf (out, "%s: ", main_input_filename);
1297           previous_output = 1;
1298         }
1299
1300       if (package_name)
1301         fprintf (out, "%s.%s ", package_name, name);
1302       else
1303         fprintf (out, "%s ", name);
1304
1305       free (name);
1306     }
1307 }
1308
1309 static void
1310 report_main_declaration (struct method_declarator *declarator)
1311 {
1312   extern int flag_find_main;
1313
1314   if (flag_find_main
1315       && modifier_value == 2
1316       && !strcmp (declarator->method_name, "main") 
1317       && declarator->args 
1318       && declarator->args [0] == '[' 
1319       && (! strcmp (declarator->args+1, "String")
1320           || ! strcmp (declarator->args + 1, "java.lang.String"))
1321       && current_class_context)
1322     {
1323       if (!previous_output)
1324         {
1325           char *name = get_class_name ();
1326           if (package_name)
1327             fprintf (out, "%s.%s ", package_name, name);
1328           else
1329             fprintf (out, "%s", name);
1330           free (name);
1331           previous_output = 1;
1332         }
1333     }
1334 }
1335
1336 void
1337 report (void)
1338 {
1339   extern int flag_complexity;
1340   if (flag_complexity)
1341     fprintf (out, "%s %d\n", main_input_filename, complexity);
1342 }
1343
1344 /* Reset global status used by the report functions.  */
1345
1346 void
1347 reset_report (void)
1348 {
1349   previous_output = 0;
1350   package_name = NULL;
1351   current_class_context = NULL;
1352   complexity = 0;
1353 }
1354
1355 void
1356 yyerror (const char *msg ATTRIBUTE_UNUSED)
1357 {
1358   fprintf (stderr, "%s: %s\n", main_input_filename, msg);
1359   exit (1);
1360 }
1361
1362 #ifdef __XGETTEXT__
1363 /* Depending on the version of Bison used to compile this grammar,
1364    it may issue generic diagnostics spelled "syntax error" or
1365    "parse error".  To prevent this from changing the translation
1366    template randomly, we list all the variants of this particular
1367    diagnostic here.  Translators: there is no fine distinction
1368    between diagnostics with "syntax error" in them, and diagnostics
1369    with "parse error" in them.  It's okay to give them both the same
1370    translation.  */
1371 const char d1[] = N_("syntax error");
1372 const char d2[] = N_("parse error");
1373 const char d3[] = N_("syntax error; also virtual memory exhausted");
1374 const char d4[] = N_("parse error; also virtual memory exhausted");
1375 const char d5[] = N_("syntax error: cannot back up");
1376 const char d6[] = N_("parse error: cannot back up");
1377 #endif