OSDN Git Service

* expr.c (java_array_data_offset): Removed function.
[pf3gnuchains/gcc-fork.git] / gcc / java / parse.y
1 /* Source code parsing and tree node generation for the GNU compiler
2    for the Java(TM) language.
3    Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002 Free Software Foundation, Inc.
4    Contributed by Alexandre Petit-Bianco (apbianco@cygnus.com)
5
6 This file is part of GNU CC.
7
8 GNU CC 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 GNU CC 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 GNU CC; see the file COPYING.  If not, write to
20 the Free Software Foundation, 59 Temple Place - Suite 330,
21 Boston, MA 02111-1307, 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 and issues a tree node image
28 suitable for code generation (byte code and targeted CPU assembly
29 language).
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 The following modifications were brought to the original grammar:
36
37 method_body: added the rule '| block SC_TK'
38 static_initializer: added the rule 'static block SC_TK'. 
39
40 Note: All the extra rules described above should go away when the
41       empty_statement rule will work.
42
43 statement_nsi: 'nsi' should be read no_short_if.
44
45 Some rules have been modified to support JDK1.1 inner classes
46 definitions and other extensions.  */
47
48 %{
49 #include "config.h"
50 #include "system.h"
51 #include <dirent.h>
52 #include "tree.h"
53 #include "rtl.h"
54 #include "obstack.h"
55 #include "toplev.h"
56 #include "flags.h"
57 #include "java-tree.h"
58 #include "jcf.h"
59 #include "lex.h"
60 #include "parse.h"
61 #include "zipfile.h"
62 #include "convert.h"
63 #include "buffer.h"
64 #include "xref.h"
65 #include "function.h"
66 #include "except.h"
67 #include "ggc.h"
68
69 #ifndef DIR_SEPARATOR
70 #define DIR_SEPARATOR '/'
71 #endif
72
73 /* Local function prototypes */
74 static char *java_accstring_lookup PARAMS ((int));
75 static void  classitf_redefinition_error PARAMS ((const char *,tree, tree, tree));
76 static void  variable_redefinition_error PARAMS ((tree, tree, tree, int));
77 static tree  create_class PARAMS ((int, tree, tree, tree));
78 static tree  create_interface PARAMS ((int, tree, tree));
79 static void  end_class_declaration PARAMS ((int));
80 static tree  find_field PARAMS ((tree, tree));
81 static tree lookup_field_wrapper PARAMS ((tree, tree));
82 static int   duplicate_declaration_error_p PARAMS ((tree, tree, tree));
83 static void  register_fields PARAMS ((int, tree, tree));
84 static tree parser_qualified_classname PARAMS ((tree));
85 static int  parser_check_super PARAMS ((tree, tree, tree));
86 static int  parser_check_super_interface PARAMS ((tree, tree, tree));
87 static void check_modifiers_consistency PARAMS ((int));
88 static tree lookup_cl PARAMS ((tree));
89 static tree lookup_java_method2 PARAMS ((tree, tree, int));
90 static tree method_header PARAMS ((int, tree, tree, tree));
91 static void fix_method_argument_names PARAMS ((tree ,tree));
92 static tree method_declarator PARAMS ((tree, tree));
93 static void parse_warning_context PARAMS ((tree cl, const char *msg, ...))
94   ATTRIBUTE_PRINTF_2;
95 static void issue_warning_error_from_context PARAMS ((tree, const char *msg, va_list))
96   ATTRIBUTE_PRINTF (2, 0);
97 static void parse_ctor_invocation_error PARAMS ((void));
98 static tree parse_jdk1_1_error PARAMS ((const char *));
99 static void complete_class_report_errors PARAMS ((jdep *));
100 static int process_imports PARAMS ((void));
101 static void read_import_dir PARAMS ((tree));
102 static int find_in_imports_on_demand PARAMS ((tree, tree));
103 static void find_in_imports PARAMS ((tree, tree));
104 static void check_inner_class_access PARAMS ((tree, tree, tree));
105 static int check_pkg_class_access PARAMS ((tree, tree, bool));
106 static void register_package PARAMS ((tree));
107 static tree resolve_package PARAMS ((tree, tree *));
108 static tree lookup_package_type PARAMS ((const char *, int));
109 static tree resolve_class PARAMS ((tree, tree, tree, tree));
110 static void declare_local_variables PARAMS ((int, tree, tree));
111 static void dump_java_tree PARAMS ((enum tree_dump_index, tree));
112 static void source_start_java_method PARAMS ((tree));
113 static void source_end_java_method PARAMS ((void));
114 static tree find_name_in_single_imports PARAMS ((tree));
115 static void check_abstract_method_header PARAMS ((tree));
116 static tree lookup_java_interface_method2 PARAMS ((tree, tree));
117 static tree resolve_expression_name PARAMS ((tree, tree *));
118 static tree maybe_create_class_interface_decl PARAMS ((tree, tree, tree, tree));
119 static int check_class_interface_creation PARAMS ((int, int, tree, 
120                                                   tree, tree, tree));
121 static tree patch_method_invocation PARAMS ((tree, tree, tree, int,
122                                             int *, tree *));
123 static int breakdown_qualified PARAMS ((tree *, tree *, tree));
124 static int in_same_package PARAMS ((tree, tree));
125 static tree resolve_and_layout PARAMS ((tree, tree));
126 static tree qualify_and_find PARAMS ((tree, tree, tree));
127 static tree resolve_no_layout PARAMS ((tree, tree));
128 static int invocation_mode PARAMS ((tree, int));
129 static tree find_applicable_accessible_methods_list PARAMS ((int, tree, 
130                                                             tree, tree));
131 static void search_applicable_methods_list PARAMS ((int, tree, tree, tree, 
132                                                    tree *, tree *));
133 static tree find_most_specific_methods_list PARAMS ((tree));
134 static int argument_types_convertible PARAMS ((tree, tree));
135 static tree patch_invoke PARAMS ((tree, tree, tree));
136 static int maybe_use_access_method PARAMS ((int, tree *, tree *));
137 static tree lookup_method_invoke PARAMS ((int, tree, tree, tree, tree));
138 static tree register_incomplete_type PARAMS ((int, tree, tree, tree));
139 static tree check_inner_circular_reference PARAMS ((tree, tree));
140 static tree check_circular_reference PARAMS ((tree));
141 static tree obtain_incomplete_type PARAMS ((tree));
142 static tree java_complete_lhs PARAMS ((tree));
143 static tree java_complete_tree PARAMS ((tree));
144 static tree maybe_generate_pre_expand_clinit PARAMS ((tree));
145 static int analyze_clinit_body PARAMS ((tree, tree));
146 static int maybe_yank_clinit PARAMS ((tree));
147 static void start_complete_expand_method PARAMS ((tree));
148 static void java_complete_expand_method PARAMS ((tree));
149 static void java_expand_method_bodies PARAMS ((tree));
150 static int  unresolved_type_p PARAMS ((tree, tree *));
151 static void create_jdep_list PARAMS ((struct parser_ctxt *));
152 static tree build_expr_block PARAMS ((tree, tree));
153 static tree enter_block PARAMS ((void));
154 static tree exit_block PARAMS ((void));
155 static tree lookup_name_in_blocks PARAMS ((tree));
156 static void maybe_absorb_scoping_blocks PARAMS ((void));
157 static tree build_method_invocation PARAMS ((tree, tree));
158 static tree build_new_invocation PARAMS ((tree, tree));
159 static tree build_assignment PARAMS ((int, int, tree, tree));
160 static tree build_binop PARAMS ((enum tree_code, int, tree, tree));
161 static tree patch_assignment PARAMS ((tree, tree));
162 static tree patch_binop PARAMS ((tree, tree, tree));
163 static tree build_unaryop PARAMS ((int, int, tree));
164 static tree build_incdec PARAMS ((int, int, tree, int));
165 static tree patch_unaryop PARAMS ((tree, tree));
166 static tree build_cast PARAMS ((int, tree, tree));
167 static tree build_null_of_type PARAMS ((tree));
168 static tree patch_cast PARAMS ((tree, tree));
169 static int valid_ref_assignconv_cast_p PARAMS ((tree, tree, int));
170 static int valid_builtin_assignconv_identity_widening_p PARAMS ((tree, tree));
171 static int valid_cast_to_p PARAMS ((tree, tree));
172 static int valid_method_invocation_conversion_p PARAMS ((tree, tree));
173 static tree try_builtin_assignconv PARAMS ((tree, tree, tree));
174 static tree try_reference_assignconv PARAMS ((tree, tree));
175 static tree build_unresolved_array_type PARAMS ((tree));
176 static int build_type_name_from_array_name PARAMS ((tree, tree *));
177 static tree build_array_from_name PARAMS ((tree, tree, tree, tree *));
178 static tree build_array_ref PARAMS ((int, tree, tree));
179 static tree patch_array_ref PARAMS ((tree));
180 static tree make_qualified_name PARAMS ((tree, tree, int));
181 static tree merge_qualified_name PARAMS ((tree, tree));
182 static tree make_qualified_primary PARAMS ((tree, tree, int));
183 static int resolve_qualified_expression_name PARAMS ((tree, tree *, 
184                                                      tree *, tree *));
185 static void qualify_ambiguous_name PARAMS ((tree));
186 static tree resolve_field_access PARAMS ((tree, tree *, tree *));
187 static tree build_newarray_node PARAMS ((tree, tree, int));
188 static tree patch_newarray PARAMS ((tree));
189 static tree resolve_type_during_patch PARAMS ((tree));
190 static tree build_this PARAMS ((int));
191 static tree build_wfl_wrap PARAMS ((tree, int));
192 static tree build_return PARAMS ((int, tree));
193 static tree patch_return PARAMS ((tree));
194 static tree maybe_access_field PARAMS ((tree, tree, tree));
195 static int complete_function_arguments PARAMS ((tree));
196 static int check_for_static_method_reference PARAMS ((tree, tree, tree, 
197                                                       tree, tree));
198 static int not_accessible_p PARAMS ((tree, tree, tree, int));
199 static void check_deprecation PARAMS ((tree, tree));
200 static int class_in_current_package PARAMS ((tree));
201 static tree build_if_else_statement PARAMS ((int, tree, tree, tree));
202 static tree patch_if_else_statement PARAMS ((tree));
203 static tree add_stmt_to_compound PARAMS ((tree, tree, tree));
204 static tree add_stmt_to_block PARAMS ((tree, tree, tree));
205 static tree patch_exit_expr PARAMS ((tree));
206 static tree build_labeled_block PARAMS ((int, tree));
207 static tree finish_labeled_statement PARAMS ((tree, tree));
208 static tree build_bc_statement PARAMS ((int, int, tree));
209 static tree patch_bc_statement PARAMS ((tree));
210 static tree patch_loop_statement PARAMS ((tree));
211 static tree build_new_loop PARAMS ((tree));
212 static tree build_loop_body PARAMS ((int, tree, int));
213 static tree finish_loop_body PARAMS ((int, tree, tree, int));
214 static tree build_debugable_stmt PARAMS ((int, tree));
215 static tree finish_for_loop PARAMS ((int, tree, tree, tree));
216 static tree patch_switch_statement PARAMS ((tree));
217 static tree string_constant_concatenation PARAMS ((tree, tree));
218 static tree build_string_concatenation PARAMS ((tree, tree));
219 static tree patch_string_cst PARAMS ((tree));
220 static tree patch_string PARAMS ((tree));
221 static tree encapsulate_with_try_catch PARAMS ((int, tree, tree, tree));
222 static tree build_try_statement PARAMS ((int, tree, tree));
223 static tree build_try_finally_statement PARAMS ((int, tree, tree));
224 static tree patch_try_statement PARAMS ((tree));
225 static tree patch_synchronized_statement PARAMS ((tree, tree));
226 static tree patch_throw_statement PARAMS ((tree, tree));
227 static void check_thrown_exceptions PARAMS ((int, tree));
228 static int check_thrown_exceptions_do PARAMS ((tree));
229 static void purge_unchecked_exceptions PARAMS ((tree));
230 static bool ctors_unchecked_throws_clause_p PARAMS ((tree));
231 static void check_throws_clauses PARAMS ((tree, tree, tree));
232 static void finish_method_declaration PARAMS ((tree));
233 static tree build_super_invocation PARAMS ((tree));
234 static int verify_constructor_circularity PARAMS ((tree, tree));
235 static char *constructor_circularity_msg PARAMS ((tree, tree));
236 static tree build_this_super_qualified_invocation PARAMS ((int, tree, tree,
237                                                           int, int));
238 static const char *get_printable_method_name PARAMS ((tree));
239 static tree patch_conditional_expr PARAMS ((tree, tree, tree));
240 static tree generate_finit PARAMS ((tree));
241 static tree generate_instinit PARAMS ((tree));
242 static tree build_instinit_invocation PARAMS ((tree));
243 static void fix_constructors PARAMS ((tree));
244 static tree build_alias_initializer_parameter_list PARAMS ((int, tree,
245                                                             tree, int *));
246 static void craft_constructor PARAMS ((tree, tree));
247 static int verify_constructor_super PARAMS ((tree));
248 static tree create_artificial_method PARAMS ((tree, int, tree, tree, tree));
249 static void start_artificial_method_body PARAMS ((tree));
250 static void end_artificial_method_body PARAMS ((tree));
251 static int check_method_redefinition PARAMS ((tree, tree));
252 static int check_method_types_complete PARAMS ((tree));
253 static void java_check_regular_methods PARAMS ((tree));
254 static void java_check_abstract_methods PARAMS ((tree));
255 static void unreachable_stmt_error PARAMS ((tree));
256 static tree find_expr_with_wfl PARAMS ((tree));
257 static void missing_return_error PARAMS ((tree));
258 static tree build_new_array_init PARAMS ((int, tree));
259 static tree patch_new_array_init PARAMS ((tree, tree));
260 static tree maybe_build_array_element_wfl PARAMS ((tree));
261 static int array_constructor_check_entry PARAMS ((tree, tree));
262 static const char *purify_type_name PARAMS ((const char *));
263 static tree fold_constant_for_init PARAMS ((tree, tree));
264 static tree strip_out_static_field_access_decl PARAMS ((tree));
265 static jdeplist *reverse_jdep_list PARAMS ((struct parser_ctxt *));
266 static void static_ref_err PARAMS ((tree, tree, tree));
267 static void parser_add_interface PARAMS ((tree, tree, tree));
268 static void add_superinterfaces PARAMS ((tree, tree));
269 static tree jdep_resolve_class PARAMS ((jdep *));
270 static int note_possible_classname PARAMS ((const char *, int));
271 static void java_complete_expand_classes PARAMS ((void));
272 static void java_complete_expand_class PARAMS ((tree));
273 static void java_complete_expand_methods PARAMS ((tree));
274 static tree cut_identifier_in_qualified PARAMS ((tree));
275 static tree java_stabilize_reference PARAMS ((tree));
276 static tree do_unary_numeric_promotion PARAMS ((tree));
277 static char * operator_string PARAMS ((tree));
278 static tree do_merge_string_cste PARAMS ((tree, const char *, int, int));
279 static tree merge_string_cste PARAMS ((tree, tree, int));
280 static tree java_refold PARAMS ((tree));
281 static int java_decl_equiv PARAMS ((tree, tree));
282 static int binop_compound_p PARAMS ((enum tree_code));
283 static tree search_loop PARAMS ((tree));
284 static int labeled_block_contains_loop_p PARAMS ((tree, tree));
285 static int check_abstract_method_definitions PARAMS ((int, tree, tree));
286 static void java_check_abstract_method_definitions PARAMS ((tree));
287 static void java_debug_context_do PARAMS ((int));
288 static void java_parser_context_push_initialized_field PARAMS ((void));
289 static void java_parser_context_pop_initialized_field PARAMS ((void));
290 static tree reorder_static_initialized PARAMS ((tree));
291 static void java_parser_context_suspend PARAMS ((void));
292 static void java_parser_context_resume PARAMS ((void));
293 static int pop_current_osb PARAMS ((struct parser_ctxt *));
294
295 /* JDK 1.1 work. FIXME */
296
297 static tree maybe_make_nested_class_name PARAMS ((tree));
298 static void make_nested_class_name PARAMS ((tree));
299 static void set_nested_class_simple_name_value PARAMS ((tree, int));
300 static void link_nested_class_to_enclosing PARAMS ((void));
301 static tree resolve_inner_class PARAMS ((struct hash_table *, tree, tree *,
302                                          tree *, tree));
303 static tree find_as_inner_class PARAMS ((tree, tree, tree));
304 static tree find_as_inner_class_do PARAMS ((tree, tree));
305 static int check_inner_class_redefinition PARAMS ((tree, tree));
306
307 static tree build_thisn_assign PARAMS ((void));
308 static tree build_current_thisn PARAMS ((tree));
309 static tree build_access_to_thisn PARAMS ((tree, tree, int));
310 static tree maybe_build_thisn_access_method PARAMS ((tree));
311
312 static tree build_outer_field_access PARAMS ((tree, tree));
313 static tree build_outer_field_access_methods PARAMS ((tree));
314 static tree build_outer_field_access_expr PARAMS ((int, tree, tree, 
315                                                   tree, tree));
316 static tree build_outer_method_access_method PARAMS ((tree));
317 static tree build_new_access_id PARAMS ((void));
318 static tree build_outer_field_access_method PARAMS ((tree, tree, tree,
319                                                     tree, tree));
320
321 static int outer_field_access_p PARAMS ((tree, tree));
322 static int outer_field_expanded_access_p PARAMS ((tree, tree *, 
323                                                  tree *, tree *));
324 static tree outer_field_access_fix PARAMS ((tree, tree, tree));
325 static tree build_incomplete_class_ref PARAMS ((int, tree));
326 static tree patch_incomplete_class_ref PARAMS ((tree));
327 static tree create_anonymous_class PARAMS ((int, tree));
328 static void patch_anonymous_class PARAMS ((tree, tree, tree));
329 static void add_inner_class_fields PARAMS ((tree, tree));
330
331 static tree build_dot_class_method PARAMS ((tree));
332 static tree build_dot_class_method_invocation PARAMS ((tree));
333 static void create_new_parser_context PARAMS ((int));
334 static void mark_parser_ctxt PARAMS ((void *));
335 static tree maybe_build_class_init_for_field PARAMS ((tree, tree));
336
337 static bool attach_init_test_initialization_flags PARAMS ((struct hash_entry *,
338                                                           PTR));
339 static bool emit_test_initialization PARAMS ((struct hash_entry *, PTR));
340
341 /* Number of error found so far. */
342 int java_error_count; 
343 /* Number of warning found so far. */
344 int java_warning_count;
345 /* Tell when not to fold, when doing xrefs */
346 int do_not_fold;
347 /* Cyclic inheritance report, as it can be set by layout_class */
348 const char *cyclic_inheritance_report;
349  
350 /* The current parser context */
351 struct parser_ctxt *ctxp;
352
353 /* List of things that were analyzed for which code will be generated */
354 struct parser_ctxt *ctxp_for_generation = NULL;
355
356 /* binop_lookup maps token to tree_code. It is used where binary
357    operations are involved and required by the parser. RDIV_EXPR
358    covers both integral/floating point division. The code is changed
359    once the type of both operator is worked out.  */
360
361 static const enum tree_code binop_lookup[19] = 
362   { 
363     PLUS_EXPR, MINUS_EXPR, MULT_EXPR, RDIV_EXPR, TRUNC_MOD_EXPR,
364     LSHIFT_EXPR, RSHIFT_EXPR, URSHIFT_EXPR, 
365     BIT_AND_EXPR, BIT_XOR_EXPR, BIT_IOR_EXPR,
366     TRUTH_ANDIF_EXPR, TRUTH_ORIF_EXPR,
367     EQ_EXPR, NE_EXPR, GT_EXPR, GE_EXPR, LT_EXPR, LE_EXPR,
368    };
369 #define BINOP_LOOKUP(VALUE)                                             \
370   binop_lookup [((VALUE) - PLUS_TK) % ARRAY_SIZE (binop_lookup)]
371
372 /* This is the end index for binary operators that can also be used
373    in compound assignements. */
374 #define BINOP_COMPOUND_CANDIDATES 11
375
376 /* The "$L" identifier we use to create labels.  */
377 static tree label_id = NULL_TREE;
378
379 /* The "StringBuffer" identifier used for the String `+' operator. */
380 static tree wfl_string_buffer = NULL_TREE; 
381
382 /* The "append" identifier used for String `+' operator.  */
383 static tree wfl_append = NULL_TREE;
384
385 /* The "toString" identifier used for String `+' operator. */
386 static tree wfl_to_string = NULL_TREE;
387
388 /* The "java.lang" import qualified name.  */
389 static tree java_lang_id = NULL_TREE;
390
391 /* The generated `inst$' identifier used for generated enclosing
392    instance/field access functions.  */
393 static tree inst_id = NULL_TREE;
394
395 /* The "java.lang.Cloneable" qualified name.  */
396 static tree java_lang_cloneable = NULL_TREE;
397
398 /* The "java.io.Serializable" qualified name.  */
399 static tree java_io_serializable = NULL_TREE; 
400
401 /* Context and flag for static blocks */
402 static tree current_static_block = NULL_TREE;
403
404 /* The generated `write_parm_value$' identifier.  */
405 static tree wpv_id;
406
407 /* The list of all packages we've seen so far */
408 static tree package_list = NULL_TREE;
409  
410 /* Hold THIS for the scope of the current method decl.  */
411 static tree current_this;
412
413 /* Hold a list of catch clauses list. The first element of this list is
414    the list of the catch clauses of the currently analysed try block. */
415 static tree currently_caught_type_list;
416
417 /* This holds a linked list of all the case labels for the current
418    switch statement.  It is only used when checking to see if there
419    are duplicate labels.  FIXME: probably this should just be attached
420    to the switch itself; then it could be referenced via
421    `ctxp->current_loop'.  */
422 static tree case_label_list; 
423
424 static tree src_parse_roots[1];
425
426 /* All classes seen from source code */
427 #define gclass_list src_parse_roots[0]
428
429 /* Check modifiers. If one doesn't fit, retrieve it in its declaration
430    line and point it out.  */
431 /* Should point out the one that don't fit. ASCII/unicode, going
432    backward. FIXME */
433
434 #define check_modifiers(__message, __value, __mask) do {        \
435   if ((__value) & ~(__mask))                                    \
436     {                                                           \
437       int i, remainder = (__value) & ~(__mask);                 \
438       for (i = 0; i <= 10; i++)                                 \
439         if ((1 << i) & remainder)                               \
440           parse_error_context (ctxp->modifier_ctx [i], (__message), \
441                                java_accstring_lookup (1 << i)); \
442     }                                                           \
443 } while (0)
444
445 %}
446
447 %union {
448   tree node;
449   int sub_token;
450   struct {
451     int token;
452     int location;
453   } operator;
454   int value;
455 }
456
457 %{
458 #include "lex.c"
459 %}
460
461 %pure_parser
462
463 /* Things defined here have to match the order of what's in the
464    binop_lookup table.  */
465
466 %token   PLUS_TK         MINUS_TK        MULT_TK         DIV_TK    REM_TK
467 %token   LS_TK           SRS_TK          ZRS_TK
468 %token   AND_TK          XOR_TK          OR_TK
469 %token   BOOL_AND_TK BOOL_OR_TK 
470 %token   EQ_TK NEQ_TK GT_TK GTE_TK LT_TK LTE_TK
471
472 /* This maps to the same binop_lookup entry than the token above */
473
474 %token   PLUS_ASSIGN_TK  MINUS_ASSIGN_TK MULT_ASSIGN_TK DIV_ASSIGN_TK
475 %token   REM_ASSIGN_TK   
476 %token   LS_ASSIGN_TK    SRS_ASSIGN_TK   ZRS_ASSIGN_TK
477 %token   AND_ASSIGN_TK   XOR_ASSIGN_TK   OR_ASSIGN_TK
478
479
480 /* Modifier TOKEN have to be kept in this order. Don't scramble it */
481
482 %token   PUBLIC_TK       PRIVATE_TK         PROTECTED_TK
483 %token   STATIC_TK       FINAL_TK           SYNCHRONIZED_TK
484 %token   VOLATILE_TK     TRANSIENT_TK       NATIVE_TK
485 %token   PAD_TK          ABSTRACT_TK        STRICT_TK
486 %token   MODIFIER_TK
487
488 /* Keep those two in order, too */
489 %token   DECR_TK INCR_TK
490
491 /* From now one, things can be in any order */
492
493 %token   DEFAULT_TK      IF_TK              THROW_TK
494 %token   BOOLEAN_TK      DO_TK              IMPLEMENTS_TK
495 %token   THROWS_TK       BREAK_TK           IMPORT_TK       
496 %token   ELSE_TK         INSTANCEOF_TK      RETURN_TK
497 %token   VOID_TK         CATCH_TK           INTERFACE_TK
498 %token   CASE_TK         EXTENDS_TK         FINALLY_TK
499 %token   SUPER_TK        WHILE_TK           CLASS_TK
500 %token   SWITCH_TK       CONST_TK           TRY_TK
501 %token   FOR_TK          NEW_TK             CONTINUE_TK
502 %token   GOTO_TK         PACKAGE_TK         THIS_TK
503
504 %token   BYTE_TK         SHORT_TK           INT_TK            LONG_TK
505 %token   CHAR_TK         INTEGRAL_TK
506
507 %token   FLOAT_TK        DOUBLE_TK          FP_TK
508
509 %token   ID_TK
510
511 %token   REL_QM_TK         REL_CL_TK NOT_TK  NEG_TK
512
513 %token   ASSIGN_ANY_TK   ASSIGN_TK
514 %token   OP_TK  CP_TK  OCB_TK  CCB_TK  OSB_TK  CSB_TK  SC_TK  C_TK DOT_TK
515
516 %token   STRING_LIT_TK   CHAR_LIT_TK        INT_LIT_TK        FP_LIT_TK
517 %token   TRUE_TK         FALSE_TK           BOOL_LIT_TK       NULL_TK
518
519 %type    <value>        modifiers MODIFIER_TK final synchronized
520
521 %type    <node>         super ID_TK identifier
522 %type    <node>         name simple_name qualified_name
523 %type    <node>         type_declaration compilation_unit
524                         field_declaration method_declaration extends_interfaces
525                         interfaces interface_type_list
526                         class_member_declaration
527                         import_declarations package_declaration 
528                         type_declarations interface_body
529                         interface_member_declaration constant_declaration
530                         interface_member_declarations interface_type
531                         abstract_method_declaration interface_type_list
532 %type    <node>         class_body_declaration class_member_declaration
533                         static_initializer constructor_declaration block
534 %type    <node>         class_body_declarations constructor_header
535 %type    <node>         class_or_interface_type class_type class_type_list
536                         constructor_declarator explicit_constructor_invocation
537 %type    <node>         dim_expr dim_exprs this_or_super throws
538
539 %type    <node>         variable_declarator_id variable_declarator
540                         variable_declarators variable_initializer
541                         variable_initializers constructor_body
542                         array_initializer
543
544 %type    <node>         class_body block_end constructor_block_end
545 %type    <node>         statement statement_without_trailing_substatement
546                         labeled_statement if_then_statement label_decl
547                         if_then_else_statement while_statement for_statement
548                         statement_nsi labeled_statement_nsi do_statement
549                         if_then_else_statement_nsi while_statement_nsi
550                         for_statement_nsi statement_expression_list for_init
551                         for_update statement_expression expression_statement
552                         primary_no_new_array expression primary
553                         array_creation_expression array_type
554                         class_instance_creation_expression field_access
555                         method_invocation array_access something_dot_new
556                         argument_list postfix_expression while_expression 
557                         post_increment_expression post_decrement_expression
558                         unary_expression_not_plus_minus unary_expression
559                         pre_increment_expression pre_decrement_expression
560                         unary_expression_not_plus_minus cast_expression
561                         multiplicative_expression additive_expression
562                         shift_expression relational_expression 
563                         equality_expression and_expression 
564                         exclusive_or_expression inclusive_or_expression
565                         conditional_and_expression conditional_or_expression
566                         conditional_expression assignment_expression
567                         left_hand_side assignment for_header for_begin
568                         constant_expression do_statement_begin empty_statement
569                         switch_statement synchronized_statement throw_statement
570                         try_statement switch_expression switch_block
571                         catches catch_clause catch_clause_parameter finally
572                         anonymous_class_creation trap_overflow_corner_case
573 %type    <node>         return_statement break_statement continue_statement
574
575 %type    <operator>     ASSIGN_TK      MULT_ASSIGN_TK  DIV_ASSIGN_TK  
576 %type    <operator>     REM_ASSIGN_TK  PLUS_ASSIGN_TK  MINUS_ASSIGN_TK
577 %type    <operator>     LS_ASSIGN_TK   SRS_ASSIGN_TK   ZRS_ASSIGN_TK
578 %type    <operator>     AND_ASSIGN_TK  XOR_ASSIGN_TK   OR_ASSIGN_TK
579 %type    <operator>     ASSIGN_ANY_TK  assignment_operator
580 %token   <operator>     EQ_TK GTE_TK ZRS_TK SRS_TK GT_TK LTE_TK LS_TK 
581 %token   <operator>     BOOL_AND_TK AND_TK BOOL_OR_TK OR_TK INCR_TK PLUS_TK
582 %token   <operator>     DECR_TK MINUS_TK MULT_TK DIV_TK XOR_TK REM_TK NEQ_TK
583 %token   <operator>     NEG_TK REL_QM_TK REL_CL_TK NOT_TK LT_TK OCB_TK CCB_TK
584 %token   <operator>     OP_TK OSB_TK DOT_TK THROW_TK INSTANCEOF_TK
585 %type    <operator>     THIS_TK SUPER_TK RETURN_TK BREAK_TK CONTINUE_TK 
586 %type    <operator>     CASE_TK DEFAULT_TK TRY_TK CATCH_TK SYNCHRONIZED_TK
587 %type    <operator>     NEW_TK
588
589 %type    <node>         method_body 
590         
591 %type    <node>         literal INT_LIT_TK FP_LIT_TK BOOL_LIT_TK CHAR_LIT_TK
592                         STRING_LIT_TK NULL_TK VOID_TK
593
594 %type    <node>         IF_TK WHILE_TK FOR_TK
595
596 %type    <node>         formal_parameter_list formal_parameter
597                         method_declarator method_header
598
599 %type    <node>         primitive_type reference_type type 
600                         BOOLEAN_TK INTEGRAL_TK FP_TK
601
602 /* Added or modified JDK 1.1 rule types  */
603 %type    <node>         type_literals
604
605 %%
606 /* 19.2 Production from 2.3: The Syntactic Grammar  */
607 goal:
608                 {
609                   /* Register static variables with the garbage
610                      collector.  */
611                   ggc_add_tree_root (&label_id, 1);
612                   ggc_add_tree_root (&wfl_string_buffer, 1);
613                   ggc_add_tree_root (&wfl_append, 1);
614                   ggc_add_tree_root (&wfl_to_string, 1);
615                   ggc_add_tree_root (&java_lang_id, 1);
616                   ggc_add_tree_root (&inst_id, 1);
617                   ggc_add_tree_root (&java_lang_cloneable, 1);
618                   ggc_add_tree_root (&java_io_serializable, 1);
619                   ggc_add_tree_root (&current_static_block, 1);
620                   ggc_add_tree_root (&wpv_id, 1);
621                   ggc_add_tree_root (&package_list, 1);
622                   ggc_add_tree_root (&current_this, 1);
623                   ggc_add_tree_root (&currently_caught_type_list, 1);
624                   ggc_add_tree_root (&case_label_list, 1);
625                   ggc_add_root (&ctxp, 1, 
626                                 sizeof (struct parser_ctxt *),
627                                 mark_parser_ctxt);
628                   ggc_add_root (&ctxp_for_generation, 1, 
629                                 sizeof (struct parser_ctxt *),
630                                 mark_parser_ctxt);
631                 }
632         compilation_unit
633                 {}
634 ;
635
636 /* 19.3 Productions from 3: Lexical structure  */
637 literal:
638         INT_LIT_TK
639 |       FP_LIT_TK
640 |       BOOL_LIT_TK
641 |       CHAR_LIT_TK
642 |       STRING_LIT_TK
643 |       NULL_TK
644 ;
645
646 /* 19.4 Productions from 4: Types, Values and Variables  */
647 type:
648         primitive_type
649 |       reference_type
650 ;
651
652 primitive_type:
653         INTEGRAL_TK
654 |       FP_TK
655 |       BOOLEAN_TK
656 ;
657
658 reference_type:
659         class_or_interface_type
660 |       array_type
661 ;
662
663 class_or_interface_type:
664         name
665 ;
666
667 class_type:
668         class_or_interface_type /* Default rule */
669 ;
670
671 interface_type:
672          class_or_interface_type
673 ;
674
675 array_type:
676         primitive_type dims
677                 { 
678                   int osb = pop_current_osb (ctxp);
679                   tree t = build_java_array_type (($1), -1);
680                   while (--osb)
681                     t = build_unresolved_array_type (t);
682                   $$ = t;
683                 }
684 |       name dims
685                 { 
686                   int osb = pop_current_osb (ctxp);
687                   tree t = $1;
688                   while (osb--)
689                     t = build_unresolved_array_type (t);
690                   $$ = t;
691                 }
692 ;
693
694 /* 19.5 Productions from 6: Names  */
695 name:
696         simple_name             /* Default rule */
697 |       qualified_name          /* Default rule */
698 ;
699
700 simple_name:
701         identifier              /* Default rule */
702 ;
703
704 qualified_name:
705         name DOT_TK identifier
706                 { $$ = make_qualified_name ($1, $3, $2.location); }
707 ;
708
709 identifier:
710         ID_TK
711 ;
712
713 /* 19.6: Production from 7: Packages  */
714 compilation_unit:
715                 {$$ = NULL;}
716 |       package_declaration
717 |       import_declarations
718 |       type_declarations
719 |       package_declaration import_declarations
720 |       package_declaration type_declarations
721 |       import_declarations type_declarations
722 |       package_declaration import_declarations type_declarations
723 ;
724
725 import_declarations:
726         import_declaration
727                 {
728                   $$ = NULL;
729                 }
730 |       import_declarations import_declaration
731                 {
732                   $$ = NULL;
733                 }
734 ;
735
736 type_declarations:
737         type_declaration
738 |       type_declarations type_declaration
739 ;
740
741 package_declaration:
742         PACKAGE_TK name SC_TK
743                 { 
744                   ctxp->package = EXPR_WFL_NODE ($2);
745                   register_package (ctxp->package);
746                 }
747 |       PACKAGE_TK error
748                 {yyerror ("Missing name"); RECOVER;}
749 |       PACKAGE_TK name error
750                 {yyerror ("';' expected"); RECOVER;}
751 ;
752
753 import_declaration:
754         single_type_import_declaration
755 |       type_import_on_demand_declaration
756 ;
757
758 single_type_import_declaration:
759         IMPORT_TK name SC_TK
760                 {
761                   tree name = EXPR_WFL_NODE ($2), last_name;
762                   int   i = IDENTIFIER_LENGTH (name)-1;
763                   const char *last = &IDENTIFIER_POINTER (name)[i];
764                   while (last != IDENTIFIER_POINTER (name))
765                     {
766                       if (last [0] == '.')
767                         break;
768                       last--;
769                     }
770                   last_name = get_identifier (++last);
771                   if (IS_A_SINGLE_IMPORT_CLASSFILE_NAME_P (last_name))
772                     {
773                       tree err = find_name_in_single_imports (last_name);
774                       if (err && err != name)
775                         parse_error_context
776                           ($2, "Ambiguous class: `%s' and `%s'",
777                            IDENTIFIER_POINTER (name), 
778                            IDENTIFIER_POINTER (err));
779                       else
780                         REGISTER_IMPORT ($2, last_name);
781                     }
782                   else
783                     REGISTER_IMPORT ($2, last_name);
784                 }
785 |       IMPORT_TK error
786                 {yyerror ("Missing name"); RECOVER;}
787 |       IMPORT_TK name error
788                 {yyerror ("';' expected"); RECOVER;}
789 ;
790
791 type_import_on_demand_declaration:
792         IMPORT_TK name DOT_TK MULT_TK SC_TK
793                 {
794                   tree name = EXPR_WFL_NODE ($2);
795                   tree it;
796                   /* Search for duplicates. */
797                   for (it = ctxp->import_demand_list; it; it = TREE_CHAIN (it))
798                     if (EXPR_WFL_NODE (TREE_PURPOSE (it)) == name)
799                       break;
800                   /* Don't import the same thing more than once, just ignore
801                      duplicates (7.5.2) */
802                   if (! it)
803                     {
804                       read_import_dir ($2);
805                       ctxp->import_demand_list = 
806                         chainon (ctxp->import_demand_list,
807                                  build_tree_list ($2, NULL_TREE));
808                     }
809                 }
810 |       IMPORT_TK name DOT_TK error
811                 {yyerror ("'*' expected"); RECOVER;}
812 |       IMPORT_TK name DOT_TK MULT_TK error
813                 {yyerror ("';' expected"); RECOVER;}
814 ;
815
816 type_declaration:
817         class_declaration
818                 { end_class_declaration (0); }
819 |       interface_declaration
820                 { end_class_declaration (0); }
821 |       empty_statement
822 |       error
823                 {
824                   YYERROR_NOW;
825                   yyerror ("Class or interface declaration expected");
826                 }
827 ;
828
829 /* 19.7 Shortened from the original:
830    modifiers: modifier | modifiers modifier
831    modifier: any of public...  */
832 modifiers:
833         MODIFIER_TK
834                 {
835                   $$ = (1 << $1);
836                 }
837 |       modifiers MODIFIER_TK
838                 {
839                   int acc = (1 << $2);
840                   if ($$ & acc)
841                     parse_error_context 
842                       (ctxp->modifier_ctx [$2], "Modifier `%s' declared twice",
843                        java_accstring_lookup (acc));
844                   else
845                     {
846                       $$ |= acc;
847                     }
848                 }
849 ;
850
851 /* 19.8.1 Production from $8.1: Class Declaration */
852 class_declaration:
853         modifiers CLASS_TK identifier super interfaces
854                 { create_class ($1, $3, $4, $5); }
855         class_body
856 |       CLASS_TK identifier super interfaces 
857                 { create_class (0, $2, $3, $4); }
858         class_body
859 |       modifiers CLASS_TK error
860                 {yyerror ("Missing class name"); RECOVER;}
861 |       CLASS_TK error
862                 {yyerror ("Missing class name"); RECOVER;}
863 |       CLASS_TK identifier error
864                 {
865                   if (!ctxp->class_err) yyerror ("'{' expected"); 
866                   DRECOVER(class1);
867                 }
868 |       modifiers CLASS_TK identifier error
869                 {if (!ctxp->class_err) yyerror ("'{' expected"); RECOVER;}
870 ;
871
872 super:
873                 { $$ = NULL; }
874 |       EXTENDS_TK class_type
875                 { $$ = $2; }
876 |       EXTENDS_TK class_type error
877                 {yyerror ("'{' expected"); ctxp->class_err=1;}
878 |       EXTENDS_TK error
879                 {yyerror ("Missing super class name"); ctxp->class_err=1;}
880 ;
881
882 interfaces:
883                 { $$ = NULL_TREE; }
884 |       IMPLEMENTS_TK interface_type_list
885                 { $$ = $2; }
886 |       IMPLEMENTS_TK error
887                 {
888                   ctxp->class_err=1;
889                   yyerror ("Missing interface name"); 
890                 }
891 ;
892
893 interface_type_list:
894         interface_type
895                 { 
896                   ctxp->interface_number = 1;
897                   $$ = build_tree_list ($1, NULL_TREE);
898                 }
899 |       interface_type_list C_TK interface_type
900                 { 
901                   ctxp->interface_number++;
902                   $$ = chainon ($1, build_tree_list ($3, NULL_TREE));
903                 }
904 |       interface_type_list C_TK error
905                 {yyerror ("Missing interface name"); RECOVER;}
906 ;
907
908 class_body:
909         OCB_TK CCB_TK
910                 { 
911                   /* Store the location of the `}' when doing xrefs */
912                   if (flag_emit_xref)
913                     DECL_END_SOURCE_LINE (GET_CPC ()) = 
914                       EXPR_WFL_ADD_COL ($2.location, 1);
915                   $$ = GET_CPC ();
916                 }
917 |       OCB_TK class_body_declarations CCB_TK
918                 { 
919                   /* Store the location of the `}' when doing xrefs */
920                   if (flag_emit_xref)
921                     DECL_END_SOURCE_LINE (GET_CPC ()) = 
922                       EXPR_WFL_ADD_COL ($3.location, 1);
923                   $$ = GET_CPC ();
924                 }
925 ;
926
927 class_body_declarations:
928         class_body_declaration
929 |       class_body_declarations class_body_declaration
930 ;
931
932 class_body_declaration:
933         class_member_declaration
934 |       static_initializer
935 |       constructor_declaration
936 |       block                   /* Added, JDK1.1, instance initializer */
937                 {
938                   if ($1 != empty_stmt_node)
939                     {
940                       TREE_CHAIN ($1) = CPC_INSTANCE_INITIALIZER_STMT (ctxp);
941                       SET_CPC_INSTANCE_INITIALIZER_STMT (ctxp, $1);
942                     }
943                 }
944 ;
945
946 class_member_declaration:
947         field_declaration
948 |       method_declaration
949 |       class_declaration       /* Added, JDK1.1 inner classes */
950                 { end_class_declaration (1); }
951 |       interface_declaration   /* Added, JDK1.1 inner interfaces */
952                 { end_class_declaration (1); }
953 |       empty_statement
954 ;
955
956 /* 19.8.2 Productions from 8.3: Field Declarations  */
957 field_declaration:
958         type variable_declarators SC_TK
959                 { register_fields (0, $1, $2); }
960 |       modifiers type variable_declarators SC_TK
961                 {
962                   check_modifiers 
963                     ("Illegal modifier `%s' for field declaration",
964                      $1, FIELD_MODIFIERS);
965                   check_modifiers_consistency ($1);
966                   register_fields ($1, $2, $3);
967                 }
968 ;
969
970 variable_declarators:
971         /* Should we use build_decl_list () instead ? FIXME */
972         variable_declarator     /* Default rule */
973 |       variable_declarators C_TK variable_declarator
974                 { $$ = chainon ($1, $3); }
975 |       variable_declarators C_TK error
976                 {yyerror ("Missing term"); RECOVER;}
977 ;
978
979 variable_declarator:
980         variable_declarator_id
981                 { $$ = build_tree_list ($1, NULL_TREE); }
982 |       variable_declarator_id ASSIGN_TK variable_initializer
983                 { 
984                   if (java_error_count)
985                     $3 = NULL_TREE;
986                   $$ = build_tree_list 
987                     ($1, build_assignment ($2.token, $2.location, $1, $3));
988                 }
989 |       variable_declarator_id ASSIGN_TK error
990                 {
991                   yyerror ("Missing variable initializer");
992                   $$ = build_tree_list ($1, NULL_TREE);
993                   RECOVER;
994                 }
995 |       variable_declarator_id ASSIGN_TK variable_initializer error
996                 {
997                   yyerror ("';' expected");
998                   $$ = build_tree_list ($1, NULL_TREE);
999                   RECOVER;
1000                 }
1001 ;
1002
1003 variable_declarator_id:
1004         identifier
1005 |       variable_declarator_id OSB_TK CSB_TK
1006                 { $$ = build_unresolved_array_type ($1); }
1007 |       identifier error
1008                 {yyerror ("Invalid declaration"); DRECOVER(vdi);}
1009 |       variable_declarator_id OSB_TK error
1010                 { 
1011                   tree node = java_lval.node;
1012                   if (node && (TREE_CODE (node) == INTEGER_CST
1013                                || TREE_CODE (node) == EXPR_WITH_FILE_LOCATION))
1014                     yyerror ("Can't specify array dimension in a declaration");
1015                   else
1016                     yyerror ("']' expected");
1017                   DRECOVER(vdi);
1018                 }
1019 |       variable_declarator_id CSB_TK error
1020                 {yyerror ("Unbalanced ']'"); DRECOVER(vdi);}
1021 ;
1022
1023 variable_initializer:
1024         expression
1025 |       array_initializer
1026 ;
1027
1028 /* 19.8.3 Productions from 8.4: Method Declarations  */
1029 method_declaration:
1030         method_header 
1031                 {
1032                   current_function_decl = $1;
1033                   if (current_function_decl
1034                       && TREE_CODE (current_function_decl) == FUNCTION_DECL)
1035                     source_start_java_method (current_function_decl);
1036                   else
1037                     current_function_decl = NULL_TREE;
1038                 }
1039         method_body
1040                 { finish_method_declaration ($3); }
1041 |       method_header error
1042                 {YYNOT_TWICE yyerror ("'{' expected"); RECOVER;}
1043 ;
1044
1045 method_header:  
1046         type method_declarator throws
1047                 { $$ = method_header (0, $1, $2, $3); }
1048 |       VOID_TK method_declarator throws
1049                 { $$ = method_header (0, void_type_node, $2, $3); }
1050 |       modifiers type method_declarator throws
1051                 { $$ = method_header ($1, $2, $3, $4); }
1052 |       modifiers VOID_TK method_declarator throws
1053                 { $$ = method_header ($1, void_type_node, $3, $4); }
1054 |       type error
1055                 {
1056                   yyerror ("Invalid method declaration, method name required");
1057                   RECOVER;
1058                 }
1059 |       modifiers type error
1060                 {RECOVER;}
1061 |       VOID_TK error
1062                 {yyerror ("Identifier expected"); RECOVER;}
1063 |       modifiers VOID_TK error
1064                 {yyerror ("Identifier expected"); RECOVER;}
1065 |       modifiers error
1066                 {
1067                   yyerror ("Invalid method declaration, return type required");
1068                   RECOVER;
1069                 }
1070 ;
1071
1072 method_declarator:
1073         identifier OP_TK CP_TK
1074                 { 
1075                   ctxp->formal_parameter_number = 0;
1076                   $$ = method_declarator ($1, NULL_TREE);
1077                 }
1078 |       identifier OP_TK formal_parameter_list CP_TK
1079                 { $$ = method_declarator ($1, $3); }
1080 |       method_declarator OSB_TK CSB_TK
1081                 {
1082                   EXPR_WFL_LINECOL (wfl_operator) = $2.location;
1083                   TREE_PURPOSE ($1) = 
1084                     build_unresolved_array_type (TREE_PURPOSE ($1));
1085                   parse_warning_context 
1086                     (wfl_operator, 
1087                      "Discouraged form of returned type specification");
1088                 }
1089 |       identifier OP_TK error
1090                 {yyerror ("')' expected"); DRECOVER(method_declarator);}
1091 |       method_declarator OSB_TK error
1092                 {yyerror ("']' expected"); RECOVER;}
1093 ;
1094
1095 formal_parameter_list:
1096         formal_parameter
1097                 {
1098                   ctxp->formal_parameter_number = 1;
1099                 }
1100 |       formal_parameter_list C_TK formal_parameter
1101                 {
1102                   ctxp->formal_parameter_number += 1;
1103                   $$ = chainon ($1, $3);
1104                 }
1105 |       formal_parameter_list C_TK error
1106                 { yyerror ("Missing formal parameter term"); RECOVER; }
1107 ;
1108
1109 formal_parameter:
1110         type variable_declarator_id
1111                 {
1112                   $$ = build_tree_list ($2, $1);
1113                 }
1114 |       final type variable_declarator_id /* Added, JDK1.1 final parms */
1115                 { 
1116                   $$ = build_tree_list ($3, $2);
1117                   ARG_FINAL_P ($$) = 1;
1118                 }
1119 |       type error
1120                 {
1121                   yyerror ("Missing identifier"); RECOVER;
1122                   $$ = NULL_TREE;
1123                 }
1124 |       final type error
1125                 {
1126                   yyerror ("Missing identifier"); RECOVER;
1127                   $$ = NULL_TREE;
1128                 }
1129 ;
1130
1131 final:
1132         modifiers
1133                 {
1134                   check_modifiers ("Illegal modifier `%s'. Only `final' was expected here",
1135                                    $1, ACC_FINAL);
1136                   if ($1 != ACC_FINAL)
1137                     MODIFIER_WFL (FINAL_TK) = build_wfl_node (NULL_TREE);
1138                 }
1139 ;
1140
1141 throws:
1142                 { $$ = NULL_TREE; }
1143 |       THROWS_TK class_type_list
1144                 { $$ = $2; }
1145 |       THROWS_TK error
1146                 {yyerror ("Missing class type term"); RECOVER;}
1147 ;
1148
1149 class_type_list:
1150         class_type
1151                 { $$ = build_tree_list ($1, $1); }
1152 |       class_type_list C_TK class_type
1153                 { $$ = tree_cons ($3, $3, $1); }
1154 |       class_type_list C_TK error
1155                 {yyerror ("Missing class type term"); RECOVER;}
1156 ;
1157
1158 method_body:
1159         block
1160 |       SC_TK { $$ = NULL_TREE; }
1161 ;
1162
1163 /* 19.8.4 Productions from 8.5: Static Initializers  */
1164 static_initializer:
1165         static block
1166                 {
1167                   TREE_CHAIN ($2) = CPC_STATIC_INITIALIZER_STMT (ctxp);
1168                   SET_CPC_STATIC_INITIALIZER_STMT (ctxp, $2);
1169                   current_static_block = NULL_TREE;
1170                 }
1171 ;
1172
1173 static:                         /* Test lval.sub_token here */
1174         modifiers
1175                 {
1176                   check_modifiers ("Illegal modifier `%s' for static initializer", $1, ACC_STATIC);
1177                   /* Can't have a static initializer in an innerclass */
1178                   if ($1 | ACC_STATIC &&
1179                       GET_CPC_LIST () && !TOPLEVEL_CLASS_DECL_P (GET_CPC ()))
1180                     parse_error_context 
1181                       (MODIFIER_WFL (STATIC_TK),
1182                        "Can't define static initializer in class `%s'. Static initializer can only be defined in top-level classes",
1183                        IDENTIFIER_POINTER (DECL_NAME (GET_CPC ())));
1184                   SOURCE_FRONTEND_DEBUG (("Modifiers: %d", $1));
1185                 }
1186 ;
1187
1188 /* 19.8.5 Productions from 8.6: Constructor Declarations  */
1189 constructor_declaration:
1190         constructor_header
1191                 {
1192                   current_function_decl = $1;
1193                   source_start_java_method (current_function_decl);
1194                 }
1195         constructor_body
1196                 { finish_method_declaration ($3); }
1197 ;
1198
1199 constructor_header:
1200         constructor_declarator throws
1201                 { $$ = method_header (0, NULL_TREE, $1, $2); }
1202 |       modifiers constructor_declarator throws
1203                 { $$ = method_header ($1, NULL_TREE, $2, $3); }
1204 ;
1205
1206 constructor_declarator:
1207         simple_name OP_TK CP_TK
1208                 { 
1209                   ctxp->formal_parameter_number = 0;  
1210                   $$ = method_declarator ($1, NULL_TREE);
1211                 }
1212 |       simple_name OP_TK formal_parameter_list CP_TK
1213                 { $$ = method_declarator ($1, $3); }
1214 ;
1215
1216 constructor_body:
1217         /* Unlike regular method, we always need a complete (empty)
1218            body so we can safely perform all the required code
1219            addition (super invocation and field initialization) */
1220         block_begin constructor_block_end
1221                 { 
1222                   BLOCK_EXPR_BODY ($2) = empty_stmt_node;
1223                   $$ = $2;
1224                 }
1225 |       block_begin explicit_constructor_invocation constructor_block_end
1226                 { $$ = $3; }
1227 |       block_begin block_statements constructor_block_end
1228                 { $$ = $3; }
1229 |       block_begin explicit_constructor_invocation block_statements constructor_block_end
1230                 { $$ = $4; }
1231 ;
1232
1233 constructor_block_end:
1234         block_end
1235 ;
1236
1237 /* Error recovery for that rule moved down expression_statement: rule.  */
1238 explicit_constructor_invocation:
1239         this_or_super OP_TK CP_TK SC_TK
1240                 { 
1241                   $$ = build_method_invocation ($1, NULL_TREE); 
1242                   $$ = build_debugable_stmt (EXPR_WFL_LINECOL ($1), $$);
1243                   $$ = java_method_add_stmt (current_function_decl, $$);
1244                 }
1245 |       this_or_super OP_TK argument_list CP_TK SC_TK
1246                 { 
1247                   $$ = build_method_invocation ($1, $3); 
1248                   $$ = build_debugable_stmt (EXPR_WFL_LINECOL ($1), $$);
1249                   $$ = java_method_add_stmt (current_function_decl, $$);
1250                 }
1251         /* Added, JDK1.1 inner classes. Modified because the rule
1252            'primary' couldn't work.  */
1253 |       name DOT_TK SUPER_TK OP_TK argument_list CP_TK SC_TK
1254                 {$$ = parse_jdk1_1_error ("explicit constructor invocation"); }
1255 |       name DOT_TK SUPER_TK OP_TK CP_TK SC_TK
1256                 {$$ = parse_jdk1_1_error ("explicit constructor invocation"); }
1257 ;
1258
1259 this_or_super:                  /* Added, simplifies error diagnostics */
1260         THIS_TK
1261                 {
1262                   tree wfl = build_wfl_node (this_identifier_node);
1263                   EXPR_WFL_LINECOL (wfl) = $1.location;
1264                   $$ = wfl;
1265                 }
1266 |       SUPER_TK
1267                 {
1268                   tree wfl = build_wfl_node (super_identifier_node);
1269                   EXPR_WFL_LINECOL (wfl) = $1.location;
1270                   $$ = wfl;
1271                 }
1272 ;
1273
1274 /* 19.9 Productions from 9: Interfaces  */
1275 /* 19.9.1 Productions from 9.1: Interfaces Declarations  */
1276 interface_declaration:
1277         INTERFACE_TK identifier
1278                 { create_interface (0, $2, NULL_TREE); }
1279         interface_body
1280 |       modifiers INTERFACE_TK identifier
1281                 { create_interface ($1, $3, NULL_TREE); }
1282         interface_body
1283 |       INTERFACE_TK identifier extends_interfaces
1284                 { create_interface (0, $2, $3); }
1285         interface_body
1286 |       modifiers INTERFACE_TK identifier extends_interfaces
1287                 { create_interface ($1, $3, $4); }
1288         interface_body
1289 |       INTERFACE_TK identifier error
1290                 {yyerror ("'{' expected"); RECOVER;}
1291 |       modifiers INTERFACE_TK identifier error
1292                 {yyerror ("'{' expected"); RECOVER;}
1293 ;
1294
1295 extends_interfaces:
1296         EXTENDS_TK interface_type
1297                 { 
1298                   ctxp->interface_number = 1;
1299                   $$ = build_tree_list ($2, NULL_TREE);
1300                 }
1301 |       extends_interfaces C_TK interface_type
1302                 { 
1303                   ctxp->interface_number++;
1304                   $$ = chainon ($1, build_tree_list ($3, NULL_TREE));
1305                 }
1306 |       EXTENDS_TK error
1307                 {yyerror ("Invalid interface type"); RECOVER;}
1308 |       extends_interfaces C_TK error
1309                 {yyerror ("Missing term"); RECOVER;}
1310 ;
1311
1312 interface_body:
1313         OCB_TK CCB_TK
1314                 { $$ = NULL_TREE; }
1315 |       OCB_TK interface_member_declarations CCB_TK
1316                 { $$ = NULL_TREE; }
1317 ;
1318
1319 interface_member_declarations:
1320         interface_member_declaration
1321 |       interface_member_declarations interface_member_declaration
1322 ;
1323
1324 interface_member_declaration:
1325         constant_declaration
1326 |       abstract_method_declaration
1327 |       class_declaration       /* Added, JDK1.1 inner classes */
1328                 { end_class_declaration (1); }
1329 |       interface_declaration   /* Added, JDK1.1 inner interfaces */
1330                 { end_class_declaration (1); }
1331 ;
1332
1333 constant_declaration:
1334         field_declaration
1335 ;
1336
1337 abstract_method_declaration:
1338         method_header SC_TK
1339                 { 
1340                   check_abstract_method_header ($1);
1341                   current_function_decl = NULL_TREE; /* FIXME ? */
1342                 }
1343 |       method_header error
1344                 {yyerror ("';' expected"); RECOVER;}
1345 ;
1346
1347 /* 19.10 Productions from 10: Arrays  */
1348 array_initializer:
1349         OCB_TK CCB_TK
1350                 { $$ = build_new_array_init ($1.location, NULL_TREE); }
1351 |       OCB_TK C_TK CCB_TK
1352                 { $$ = build_new_array_init ($1.location, NULL_TREE); }
1353 |       OCB_TK variable_initializers CCB_TK
1354                 { $$ = build_new_array_init ($1.location, $2); }
1355 |       OCB_TK variable_initializers C_TK CCB_TK
1356                 { $$ = build_new_array_init ($1.location, $2); }
1357 ;
1358
1359 variable_initializers:
1360         variable_initializer
1361                 { 
1362                   $$ = tree_cons (maybe_build_array_element_wfl ($1), 
1363                                   $1, NULL_TREE);
1364                 }
1365 |       variable_initializers C_TK variable_initializer
1366                 {
1367                   $$ = tree_cons (maybe_build_array_element_wfl ($3), $3, $1);
1368                 }
1369 |       variable_initializers C_TK error
1370                 {yyerror ("Missing term"); RECOVER;}
1371 ;
1372
1373 /* 19.11 Production from 14: Blocks and Statements  */
1374 block:
1375         OCB_TK CCB_TK
1376                 { 
1377                   /* Store the location of the `}' when doing xrefs */
1378                   if (current_function_decl && flag_emit_xref)
1379                     DECL_END_SOURCE_LINE (current_function_decl) = 
1380                       EXPR_WFL_ADD_COL ($2.location, 1);
1381                   $$ = empty_stmt_node; 
1382                 }
1383 |       block_begin block_statements block_end
1384                 { $$ = $3; }
1385 ;
1386
1387 block_begin:
1388         OCB_TK
1389                 { enter_block (); }
1390 ;
1391
1392 block_end:
1393         CCB_TK
1394                 { 
1395                   maybe_absorb_scoping_blocks ();
1396                   /* Store the location of the `}' when doing xrefs */
1397                   if (current_function_decl && flag_emit_xref)
1398                     DECL_END_SOURCE_LINE (current_function_decl) = 
1399                       EXPR_WFL_ADD_COL ($1.location, 1);                  
1400                   $$ = exit_block ();
1401                   if (!BLOCK_SUBBLOCKS ($$))
1402                     BLOCK_SUBBLOCKS ($$) = empty_stmt_node;
1403                 }
1404 ;
1405
1406 block_statements:
1407         block_statement
1408 |       block_statements block_statement
1409 ;
1410
1411 block_statement:
1412         local_variable_declaration_statement
1413 |       statement
1414                 { java_method_add_stmt (current_function_decl, $1); }
1415 |       class_declaration       /* Added, JDK1.1 local classes */
1416                 { 
1417                   LOCAL_CLASS_P (TREE_TYPE (GET_CPC ())) = 1;
1418                   end_class_declaration (1);
1419                 }
1420 ;
1421
1422 local_variable_declaration_statement:
1423         local_variable_declaration SC_TK /* Can't catch missing ';' here */
1424 ;
1425
1426 local_variable_declaration:
1427         type variable_declarators
1428                 { declare_local_variables (0, $1, $2); }
1429 |       final type variable_declarators /* Added, JDK1.1 final locals */
1430                 { declare_local_variables ($1, $2, $3); }
1431 ;
1432
1433 statement:
1434         statement_without_trailing_substatement
1435 |       labeled_statement
1436 |       if_then_statement
1437 |       if_then_else_statement
1438 |       while_statement
1439 |       for_statement
1440                 { $$ = exit_block (); }
1441 ;
1442
1443 statement_nsi:
1444         statement_without_trailing_substatement
1445 |       labeled_statement_nsi
1446 |       if_then_else_statement_nsi
1447 |       while_statement_nsi
1448 |       for_statement_nsi
1449                 { $$ = exit_block (); }
1450 ;
1451
1452 statement_without_trailing_substatement:
1453         block
1454 |       empty_statement
1455 |       expression_statement
1456 |       switch_statement
1457 |       do_statement
1458 |       break_statement
1459 |       continue_statement
1460 |       return_statement
1461 |       synchronized_statement
1462 |       throw_statement
1463 |       try_statement
1464 ;
1465
1466 empty_statement:
1467         SC_TK
1468                 { 
1469                   if (flag_extraneous_semicolon 
1470                       && ! current_static_block 
1471                       && (! current_function_decl || 
1472                           /* Verify we're not in a inner class declaration */
1473                           (GET_CPC () != TYPE_NAME
1474                            (DECL_CONTEXT (current_function_decl)))))
1475                            
1476                     {
1477                       EXPR_WFL_SET_LINECOL (wfl_operator, lineno, -1);
1478                       parse_warning_context (wfl_operator, "An empty declaration is a deprecated feature that should not be used");
1479                     }
1480                   $$ = empty_stmt_node;
1481                 }
1482 ;
1483
1484 label_decl:
1485         identifier REL_CL_TK
1486                 {
1487                   $$ = build_labeled_block (EXPR_WFL_LINECOL ($1), 
1488                                             EXPR_WFL_NODE ($1));
1489                   pushlevel (2);
1490                   push_labeled_block ($$);
1491                   PUSH_LABELED_BLOCK ($$);
1492                 }
1493 ;
1494
1495 labeled_statement:
1496         label_decl statement
1497                 { $$ = finish_labeled_statement ($1, $2); }
1498 |       identifier error
1499                 {yyerror ("':' expected"); RECOVER;}
1500 ;
1501
1502 labeled_statement_nsi:
1503         label_decl statement_nsi
1504                 { $$ = finish_labeled_statement ($1, $2); }
1505 ;
1506
1507 /* We concentrate here a bunch of error handling rules that we couldn't write
1508    earlier, because expression_statement catches a missing ';'.  */
1509 expression_statement:
1510         statement_expression SC_TK
1511                 {
1512                   /* We have a statement. Generate a WFL around it so
1513                      we can debug it */
1514                   $$ = build_expr_wfl ($1, input_filename, lineno, 0);
1515                   /* We know we have a statement, so set the debug
1516                      info to be eventually generate here. */
1517                   $$ = JAVA_MAYBE_GENERATE_DEBUG_INFO ($$);
1518                 }
1519 |       error SC_TK 
1520                 {
1521                   YYNOT_TWICE yyerror ("Invalid expression statement");
1522                   DRECOVER (expr_stmt);
1523                 }
1524 |       error OCB_TK
1525                 {
1526                   YYNOT_TWICE yyerror ("Invalid expression statement");
1527                   DRECOVER (expr_stmt);
1528                 }
1529 |       error CCB_TK
1530                 {
1531                   YYNOT_TWICE yyerror ("Invalid expression statement");
1532                   DRECOVER (expr_stmt);
1533                 }
1534 |       this_or_super OP_TK error
1535                 {yyerror ("')' expected"); RECOVER;}
1536 |       this_or_super OP_TK CP_TK error
1537                 {
1538                   parse_ctor_invocation_error ();
1539                   RECOVER;
1540                 }
1541 |       this_or_super OP_TK argument_list error
1542                 {yyerror ("')' expected"); RECOVER;}
1543 |       this_or_super OP_TK argument_list CP_TK error
1544                 {
1545                   parse_ctor_invocation_error ();
1546                   RECOVER;
1547                 }
1548 |       name DOT_TK SUPER_TK error
1549                 {yyerror ("'(' expected"); RECOVER;}
1550 |       name DOT_TK SUPER_TK OP_TK error
1551                 {yyerror ("')' expected"); RECOVER;}
1552 |       name DOT_TK SUPER_TK OP_TK argument_list error
1553                 {yyerror ("')' expected"); RECOVER;}
1554 |       name DOT_TK SUPER_TK OP_TK argument_list CP_TK error
1555                 {yyerror ("';' expected"); RECOVER;}
1556 |       name DOT_TK SUPER_TK OP_TK CP_TK error
1557                 {yyerror ("';' expected"); RECOVER;}
1558 ;
1559
1560 statement_expression: 
1561         assignment
1562 |       pre_increment_expression
1563 |       pre_decrement_expression
1564 |       post_increment_expression
1565 |       post_decrement_expression
1566 |       method_invocation
1567 |       class_instance_creation_expression
1568 ;
1569
1570 if_then_statement:
1571         IF_TK OP_TK expression CP_TK statement
1572                 { 
1573                   $$ = build_if_else_statement ($2.location, $3, 
1574                                                 $5, NULL_TREE);
1575                 }
1576 |       IF_TK error
1577                 {yyerror ("'(' expected"); RECOVER;}
1578 |       IF_TK OP_TK error
1579                 {yyerror ("Missing term"); RECOVER;}
1580 |       IF_TK OP_TK expression error
1581                 {yyerror ("')' expected"); RECOVER;}
1582 ;
1583
1584 if_then_else_statement:
1585         IF_TK OP_TK expression CP_TK statement_nsi ELSE_TK statement
1586                 { $$ = build_if_else_statement ($2.location, $3, $5, $7); }
1587 ;
1588
1589 if_then_else_statement_nsi:
1590         IF_TK OP_TK expression CP_TK statement_nsi ELSE_TK statement_nsi
1591                 { $$ = build_if_else_statement ($2.location, $3, $5, $7); }
1592 ;
1593
1594 switch_statement:
1595         switch_expression
1596                 {
1597                   enter_block ();
1598                 }
1599         switch_block
1600                 { 
1601                   /* Make into "proper list" of COMPOUND_EXPRs.
1602                      I.e. make the last statement also have its own
1603                      COMPOUND_EXPR. */
1604                   maybe_absorb_scoping_blocks ();
1605                   TREE_OPERAND ($1, 1) = exit_block ();
1606                   $$ = build_debugable_stmt (EXPR_WFL_LINECOL ($1), $1);
1607                 }
1608 ;
1609
1610 switch_expression:
1611         SWITCH_TK OP_TK expression CP_TK
1612                 { 
1613                   $$ = build (SWITCH_EXPR, NULL_TREE, $3, NULL_TREE);
1614                   EXPR_WFL_LINECOL ($$) = $2.location;
1615                 }
1616 |       SWITCH_TK error
1617                 {yyerror ("'(' expected"); RECOVER;}
1618 |       SWITCH_TK OP_TK error
1619                 {yyerror ("Missing term or ')'"); DRECOVER(switch_statement);}
1620 |       SWITCH_TK OP_TK expression CP_TK error
1621                 {yyerror ("'{' expected"); RECOVER;}
1622 ;
1623
1624 /* Default assignment is there to avoid type node on switch_block
1625    node. */
1626
1627 switch_block:
1628         OCB_TK CCB_TK
1629                 { $$ = NULL_TREE; }
1630 |       OCB_TK switch_labels CCB_TK
1631                 { $$ = NULL_TREE; }
1632 |       OCB_TK switch_block_statement_groups CCB_TK
1633                 { $$ = NULL_TREE; }
1634 |       OCB_TK switch_block_statement_groups switch_labels CCB_TK
1635                 { $$ = NULL_TREE; }
1636 ;
1637
1638 switch_block_statement_groups: 
1639         switch_block_statement_group
1640 |       switch_block_statement_groups switch_block_statement_group
1641 ;
1642
1643 switch_block_statement_group:
1644         switch_labels block_statements
1645 ;
1646
1647 switch_labels:
1648         switch_label
1649 |       switch_labels switch_label
1650 ;
1651
1652 switch_label:
1653         CASE_TK constant_expression REL_CL_TK
1654                 { 
1655                   tree lab = build1 (CASE_EXPR, NULL_TREE, $2);
1656                   EXPR_WFL_LINECOL (lab) = $1.location;
1657                   java_method_add_stmt (current_function_decl, lab);
1658                 }
1659 |       DEFAULT_TK REL_CL_TK
1660                 { 
1661                   tree lab = build (DEFAULT_EXPR, NULL_TREE, NULL_TREE);
1662                   EXPR_WFL_LINECOL (lab) = $1.location;
1663                   java_method_add_stmt (current_function_decl, lab);
1664                 }
1665 |       CASE_TK error
1666                 {yyerror ("Missing or invalid constant expression"); RECOVER;}
1667 |       CASE_TK constant_expression error
1668                 {yyerror ("':' expected"); RECOVER;}
1669 |       DEFAULT_TK error
1670                 {yyerror ("':' expected"); RECOVER;}
1671 ;
1672
1673 while_expression:
1674         WHILE_TK OP_TK expression CP_TK
1675                 { 
1676                   tree body = build_loop_body ($2.location, $3, 0);
1677                   $$ = build_new_loop (body);
1678                 }
1679 ;
1680
1681 while_statement:
1682         while_expression statement
1683                 { $$ = finish_loop_body (0, NULL_TREE, $2, 0); }
1684 |       WHILE_TK error
1685                 {YYERROR_NOW; yyerror ("'(' expected"); RECOVER;}
1686 |       WHILE_TK OP_TK error
1687                 {yyerror ("Missing term and ')' expected"); RECOVER;}
1688 |       WHILE_TK OP_TK expression error
1689                 {yyerror ("')' expected"); RECOVER;}
1690 ;
1691
1692 while_statement_nsi:
1693         while_expression statement_nsi
1694                 { $$ = finish_loop_body (0, NULL_TREE, $2, 0); }
1695 ;
1696
1697 do_statement_begin:
1698         DO_TK
1699                 { 
1700                   tree body = build_loop_body (0, NULL_TREE, 1);
1701                   $$ = build_new_loop (body);
1702                 }
1703         /* Need error handing here. FIXME */
1704 ;
1705
1706 do_statement: 
1707         do_statement_begin statement WHILE_TK OP_TK expression CP_TK SC_TK
1708                 { $$ = finish_loop_body ($4.location, $5, $2, 1); }
1709 ;
1710
1711 for_statement:
1712         for_begin SC_TK expression SC_TK for_update CP_TK statement
1713                 {
1714                   if (TREE_CODE_CLASS (TREE_CODE ($3)) == 'c')
1715                     $3 = build_wfl_node ($3);
1716                   $$ = finish_for_loop (EXPR_WFL_LINECOL ($3), $3, $5, $7);
1717                 }
1718 |       for_begin SC_TK SC_TK for_update CP_TK statement
1719                 { 
1720                   $$ = finish_for_loop (0, NULL_TREE, $4, $6);
1721                   /* We have not condition, so we get rid of the EXIT_EXPR */
1722                   LOOP_EXPR_BODY_CONDITION_EXPR (LOOP_EXPR_BODY ($$), 0) = 
1723                     empty_stmt_node;
1724                 }
1725 |       for_begin SC_TK error
1726                 {yyerror ("Invalid control expression"); RECOVER;}
1727 |       for_begin SC_TK expression SC_TK error
1728                 {yyerror ("Invalid update expression"); RECOVER;}
1729 |       for_begin SC_TK SC_TK error
1730                 {yyerror ("Invalid update expression"); RECOVER;}
1731 ;
1732
1733 for_statement_nsi:
1734         for_begin SC_TK expression SC_TK for_update CP_TK statement_nsi
1735                 { $$ = finish_for_loop (EXPR_WFL_LINECOL ($3), $3, $5, $7);}
1736 |       for_begin SC_TK SC_TK for_update CP_TK statement_nsi
1737                 { 
1738                   $$ = finish_for_loop (0, NULL_TREE, $4, $6);
1739                   /* We have not condition, so we get rid of the EXIT_EXPR */
1740                   LOOP_EXPR_BODY_CONDITION_EXPR (LOOP_EXPR_BODY ($$), 0) = 
1741                     empty_stmt_node;
1742                 }
1743 ;
1744
1745 for_header:
1746         FOR_TK OP_TK
1747                 { 
1748                   /* This scope defined for local variable that may be
1749                      defined within the scope of the for loop */
1750                   enter_block (); 
1751                 }
1752 |       FOR_TK error
1753                 {yyerror ("'(' expected"); DRECOVER(for_1);}
1754 |       FOR_TK OP_TK error
1755                 {yyerror ("Invalid init statement"); RECOVER;}
1756 ;
1757
1758 for_begin:
1759         for_header for_init
1760                 { 
1761                   /* We now declare the loop body. The loop is
1762                      declared as a for loop. */
1763                   tree body = build_loop_body (0, NULL_TREE, 0);
1764                   $$ =  build_new_loop (body);
1765                   FOR_LOOP_P ($$) = 1;
1766                   /* The loop is added to the current block the for
1767                      statement is defined within */
1768                   java_method_add_stmt (current_function_decl, $$);
1769                 }
1770 ;
1771 for_init:                       /* Can be empty */
1772                 { $$ = empty_stmt_node; }
1773 |       statement_expression_list
1774                 { 
1775                   /* Init statement recorded within the previously
1776                      defined block scope */
1777                   $$ = java_method_add_stmt (current_function_decl, $1);
1778                 }
1779 |       local_variable_declaration
1780                 { 
1781                   /* Local variable are recorded within the previously
1782                      defined block scope */
1783                   $$ = NULL_TREE;
1784                 }
1785 |       statement_expression_list error
1786                 {yyerror ("';' expected"); DRECOVER(for_init_1);}
1787 ;
1788
1789 for_update:                     /* Can be empty */
1790                 {$$ = empty_stmt_node;}
1791 |       statement_expression_list
1792                 { $$ = build_debugable_stmt (BUILD_LOCATION (), $1); }
1793 ;
1794
1795 statement_expression_list:
1796         statement_expression
1797                 { $$ = add_stmt_to_compound (NULL_TREE, NULL_TREE, $1); }
1798 |       statement_expression_list C_TK statement_expression
1799                 { $$ = add_stmt_to_compound ($1, NULL_TREE, $3); }
1800 |       statement_expression_list C_TK error
1801                 {yyerror ("Missing term"); RECOVER;}
1802 ;
1803
1804 break_statement:
1805         BREAK_TK SC_TK
1806                 { $$ = build_bc_statement ($1.location, 1, NULL_TREE); }
1807 |       BREAK_TK identifier SC_TK
1808                 { $$ = build_bc_statement ($1.location, 1, $2); }
1809 |       BREAK_TK error
1810                 {yyerror ("Missing term"); RECOVER;}
1811 |       BREAK_TK identifier error
1812                 {yyerror ("';' expected"); RECOVER;}
1813 ;
1814
1815 continue_statement:
1816         CONTINUE_TK SC_TK
1817                 { $$ = build_bc_statement ($1.location, 0, NULL_TREE); }
1818 |       CONTINUE_TK identifier SC_TK
1819                 { $$ = build_bc_statement ($1.location, 0, $2); }
1820 |       CONTINUE_TK error
1821                 {yyerror ("Missing term"); RECOVER;}
1822 |       CONTINUE_TK identifier error
1823                 {yyerror ("';' expected"); RECOVER;}
1824 ;
1825
1826 return_statement:
1827         RETURN_TK SC_TK
1828                 { $$ = build_return ($1.location, NULL_TREE); }
1829 |       RETURN_TK expression SC_TK
1830                 { $$ = build_return ($1.location, $2); }
1831 |       RETURN_TK error
1832                 {yyerror ("Missing term"); RECOVER;}
1833 |       RETURN_TK expression error
1834                 {yyerror ("';' expected"); RECOVER;}
1835 ;
1836
1837 throw_statement:
1838         THROW_TK expression SC_TK
1839                 { 
1840                   $$ = build1 (THROW_EXPR, NULL_TREE, $2);
1841                   EXPR_WFL_LINECOL ($$) = $1.location;
1842                 }
1843 |       THROW_TK error
1844                 {yyerror ("Missing term"); RECOVER;}
1845 |       THROW_TK expression error
1846                 {yyerror ("';' expected"); RECOVER;}
1847 ;
1848
1849 synchronized_statement:
1850         synchronized OP_TK expression CP_TK block
1851                 { 
1852                   $$ = build (SYNCHRONIZED_EXPR, NULL_TREE, $3, $5);
1853                   EXPR_WFL_LINECOL ($$) = 
1854                     EXPR_WFL_LINECOL (MODIFIER_WFL (SYNCHRONIZED_TK));
1855                 }
1856 |       synchronized OP_TK expression CP_TK error
1857                 {yyerror ("'{' expected"); RECOVER;}
1858 |       synchronized error
1859                 {yyerror ("'(' expected"); RECOVER;}
1860 |       synchronized OP_TK error CP_TK
1861                 {yyerror ("Missing term"); RECOVER;}
1862 |       synchronized OP_TK error
1863                 {yyerror ("Missing term"); RECOVER;}
1864 ;
1865
1866 synchronized:
1867         modifiers
1868                 {
1869                   check_modifiers (
1870              "Illegal modifier `%s'. Only `synchronized' was expected here",
1871                                    $1, ACC_SYNCHRONIZED);
1872                   if ($1 != ACC_SYNCHRONIZED)
1873                     MODIFIER_WFL (SYNCHRONIZED_TK) = 
1874                       build_wfl_node (NULL_TREE);
1875                 }
1876 ;
1877
1878 try_statement:
1879         TRY_TK block catches
1880                 { $$ = build_try_statement ($1.location, $2, $3); }
1881 |       TRY_TK block finally
1882                 { $$ = build_try_finally_statement ($1.location, $2, $3); }
1883 |       TRY_TK block catches finally
1884                 { $$ = build_try_finally_statement 
1885                     ($1.location, build_try_statement ($1.location,
1886                                                        $2, $3), $4);
1887                 }
1888 |       TRY_TK error
1889                 {yyerror ("'{' expected"); DRECOVER (try_statement);}
1890 ;
1891
1892 catches:
1893         catch_clause
1894 |       catches catch_clause
1895                 { 
1896                   TREE_CHAIN ($2) = $1;
1897                   $$ = $2;
1898                 }
1899 ;
1900
1901 catch_clause:
1902         catch_clause_parameter block
1903                 { 
1904                   java_method_add_stmt (current_function_decl, $2);
1905                   exit_block ();
1906                   $$ = $1;
1907                 }
1908
1909 catch_clause_parameter:
1910         CATCH_TK OP_TK formal_parameter CP_TK
1911                 { 
1912                   /* We add a block to define a scope for
1913                      formal_parameter (CCBP). The formal parameter is
1914                      declared initialized by the appropriate function
1915                      call */
1916                   tree ccpb = enter_block ();
1917                   tree init = build_assignment
1918                     (ASSIGN_TK, $2.location, TREE_PURPOSE ($3), 
1919                      build (JAVA_EXC_OBJ_EXPR, ptr_type_node));
1920                   declare_local_variables (0, TREE_VALUE ($3),
1921                                            build_tree_list (TREE_PURPOSE ($3),
1922                                                             init));
1923                   $$ = build1 (CATCH_EXPR, NULL_TREE, ccpb);
1924                   EXPR_WFL_LINECOL ($$) = $1.location;
1925                 }
1926 |       CATCH_TK error
1927                 {yyerror ("'(' expected"); RECOVER; $$ = NULL_TREE;}
1928 |       CATCH_TK OP_TK error 
1929                 {
1930                   yyerror ("Missing term or ')' expected"); 
1931                   RECOVER; $$ = NULL_TREE;
1932                 }
1933 |       CATCH_TK OP_TK error CP_TK /* That's for () */
1934                 {yyerror ("Missing term"); RECOVER; $$ = NULL_TREE;}
1935 ;
1936
1937 finally:
1938         FINALLY_TK block
1939                 { $$ = $2; }
1940 |       FINALLY_TK error
1941                 {yyerror ("'{' expected"); RECOVER; }
1942 ;
1943
1944 /* 19.12 Production from 15: Expressions  */
1945 primary:
1946         primary_no_new_array
1947 |       array_creation_expression
1948 ;
1949
1950 primary_no_new_array:
1951         literal
1952 |       THIS_TK
1953                 { $$ = build_this ($1.location); }
1954 |       OP_TK expression CP_TK
1955                 {$$ = $2;}
1956 |       class_instance_creation_expression
1957 |       field_access
1958 |       method_invocation
1959 |       array_access
1960 |       type_literals
1961         /* Added, JDK1.1 inner classes. Documentation is wrong
1962            refering to a 'ClassName' (class_name) rule that doesn't
1963            exist. Used name: instead.  */
1964 |       name DOT_TK THIS_TK
1965                 { 
1966                   tree wfl = build_wfl_node (this_identifier_node);
1967                   $$ = make_qualified_primary ($1, wfl, EXPR_WFL_LINECOL ($1));
1968                 }
1969 |       OP_TK expression error 
1970                 {yyerror ("')' expected"); RECOVER;}
1971 |       name DOT_TK error
1972                 {yyerror ("'class' or 'this' expected" ); RECOVER;}
1973 |       primitive_type DOT_TK error
1974                 {yyerror ("'class' expected" ); RECOVER;}
1975 |       VOID_TK DOT_TK error
1976                 {yyerror ("'class' expected" ); RECOVER;}
1977 ;
1978
1979 type_literals:
1980         name DOT_TK CLASS_TK
1981                 { $$ = build_incomplete_class_ref ($2.location, $1); }
1982 |       array_type DOT_TK CLASS_TK
1983                 { $$ = build_incomplete_class_ref ($2.location, $1); }
1984 |       primitive_type DOT_TK CLASS_TK
1985                 { $$ = build_incomplete_class_ref ($2.location, $1); }
1986 |       VOID_TK DOT_TK CLASS_TK
1987                 { 
1988                    $$ = build_incomplete_class_ref ($2.location,
1989                                                    void_type_node);
1990                 }
1991 ;
1992
1993 class_instance_creation_expression:
1994         NEW_TK class_type OP_TK argument_list CP_TK
1995                 { $$ = build_new_invocation ($2, $4); }
1996 |       NEW_TK class_type OP_TK CP_TK
1997                 { $$ = build_new_invocation ($2, NULL_TREE); }
1998 |       anonymous_class_creation
1999         /* Added, JDK1.1 inner classes, modified to use name or
2000            primary instead of primary solely which couldn't work in
2001            all situations.  */
2002 |       something_dot_new identifier OP_TK CP_TK
2003                 { 
2004                   tree ctor = build_new_invocation ($2, NULL_TREE);
2005                   $$ = make_qualified_primary ($1, ctor, 
2006                                                EXPR_WFL_LINECOL ($1));
2007                 }
2008 |       something_dot_new identifier OP_TK CP_TK class_body
2009 |       something_dot_new identifier OP_TK argument_list CP_TK
2010                 { 
2011                   tree ctor = build_new_invocation ($2, $4);
2012                   $$ = make_qualified_primary ($1, ctor, 
2013                                                EXPR_WFL_LINECOL ($1));
2014                 }
2015 |       something_dot_new identifier OP_TK argument_list CP_TK class_body
2016 |       NEW_TK error SC_TK 
2017                 {yyerror ("'(' expected"); DRECOVER(new_1);}
2018 |       NEW_TK class_type error
2019                 {yyerror ("'(' expected"); RECOVER;}
2020 |       NEW_TK class_type OP_TK error
2021                 {yyerror ("')' or term expected"); RECOVER;}
2022 |       NEW_TK class_type OP_TK argument_list error
2023                 {yyerror ("')' expected"); RECOVER;}
2024 |       something_dot_new error
2025                 {YYERROR_NOW; yyerror ("Identifier expected"); RECOVER;}
2026 |       something_dot_new identifier error
2027                 {yyerror ("'(' expected"); RECOVER;}
2028 ;
2029
2030 /* Created after JDK1.1 rules originally added to
2031    class_instance_creation_expression, but modified to use
2032    'class_type' instead of 'TypeName' (type_name) which is mentionned
2033    in the documentation but doesn't exist. */
2034
2035 anonymous_class_creation:
2036         NEW_TK class_type OP_TK argument_list CP_TK 
2037                 { create_anonymous_class ($1.location, $2); }
2038         class_body
2039                 { 
2040                   tree id = build_wfl_node (DECL_NAME (GET_CPC ()));
2041                   EXPR_WFL_LINECOL (id) = EXPR_WFL_LINECOL ($2);
2042
2043                   end_class_declaration (1);
2044
2045                   /* Now we can craft the new expression */
2046                   $$ = build_new_invocation (id, $4);
2047
2048                   /* Note that we can't possibly be here if
2049                      `class_type' is an interface (in which case the
2050                      anonymous class extends Object and implements
2051                      `class_type', hence its constructor can't have
2052                      arguments.) */
2053
2054                   /* Otherwise, the innerclass must feature a
2055                      constructor matching `argument_list'. Anonymous
2056                      classes are a bit special: it's impossible to
2057                      define constructor for them, hence constructors
2058                      must be generated following the hints provided by
2059                      the `new' expression. Whether a super constructor
2060                      of that nature exists or not is to be verified
2061                      later on in verify_constructor_super. 
2062
2063                      It's during the expansion of a `new' statement
2064                      refering to an anonymous class that a ctor will
2065                      be generated for the anonymous class, with the
2066                      right arguments. */
2067
2068                 }
2069 |       NEW_TK class_type OP_TK CP_TK 
2070                 { create_anonymous_class ($1.location, $2); }
2071         class_body         
2072                 { 
2073                   tree id = build_wfl_node (DECL_NAME (GET_CPC ()));
2074                   EXPR_WFL_LINECOL (id) = EXPR_WFL_LINECOL ($2);
2075
2076                   end_class_declaration (1);
2077
2078                   /* Now we can craft the new expression. The
2079                      statement doesn't need to be remember so that a
2080                      constructor can be generated, since its signature
2081                      is already known. */
2082                   $$ = build_new_invocation (id, NULL_TREE);
2083                 }
2084 ;
2085
2086 something_dot_new:              /* Added, not part of the specs. */
2087         name DOT_TK NEW_TK
2088                 { $$ = $1; }
2089 |       primary DOT_TK NEW_TK
2090                 { $$ = $1; }
2091 ;
2092
2093 argument_list:
2094         expression
2095                 { 
2096                   $$ = tree_cons (NULL_TREE, $1, NULL_TREE);
2097                   ctxp->formal_parameter_number = 1; 
2098                 }
2099 |       argument_list C_TK expression
2100                 {
2101                   ctxp->formal_parameter_number += 1;
2102                   $$ = tree_cons (NULL_TREE, $3, $1);
2103                 }
2104 |       argument_list C_TK error
2105                 {yyerror ("Missing term"); RECOVER;}
2106 ;
2107
2108 array_creation_expression:
2109         NEW_TK primitive_type dim_exprs
2110                 { $$ = build_newarray_node ($2, $3, 0); }
2111 |       NEW_TK class_or_interface_type dim_exprs
2112                 { $$ = build_newarray_node ($2, $3, 0); }
2113 |       NEW_TK primitive_type dim_exprs dims
2114                 { $$ = build_newarray_node ($2, $3, pop_current_osb (ctxp));}
2115 |       NEW_TK class_or_interface_type dim_exprs dims
2116                 { $$ = build_newarray_node ($2, $3, pop_current_osb (ctxp));}
2117         /* Added, JDK1.1 anonymous array. Initial documentation rule
2118            modified */
2119 |       NEW_TK class_or_interface_type dims array_initializer
2120                 {
2121                   char *sig;
2122                   int osb = pop_current_osb (ctxp);
2123                   while (osb--)
2124                     obstack_grow (&temporary_obstack, "[]", 2);
2125                   obstack_1grow (&temporary_obstack, '\0');
2126                   sig = obstack_finish (&temporary_obstack);
2127                   $$ = build (NEW_ANONYMOUS_ARRAY_EXPR, NULL_TREE,
2128                               $2, get_identifier (sig), $4);
2129                 }
2130 |       NEW_TK primitive_type dims array_initializer
2131                 { 
2132                   int osb = pop_current_osb (ctxp);
2133                   tree type = $2;
2134                   while (osb--)
2135                     type = build_java_array_type (type, -1);
2136                   $$ = build (NEW_ANONYMOUS_ARRAY_EXPR, NULL_TREE, 
2137                               build_pointer_type (type), NULL_TREE, $4);
2138                 }
2139 |       NEW_TK error CSB_TK
2140                 {yyerror ("'[' expected"); DRECOVER ("]");}
2141 |       NEW_TK error OSB_TK
2142                 {yyerror ("']' expected"); RECOVER;}
2143 ;
2144
2145 dim_exprs:
2146         dim_expr
2147                 { $$ = build_tree_list (NULL_TREE, $1); }
2148 |       dim_exprs dim_expr
2149                 { $$ = tree_cons (NULL_TREE, $2, $$); }
2150 ;
2151
2152 dim_expr:
2153         OSB_TK expression CSB_TK
2154                 { 
2155                   if (JNUMERIC_TYPE_P (TREE_TYPE ($2)))
2156                     {
2157                       $2 = build_wfl_node ($2);
2158                       TREE_TYPE ($2) = NULL_TREE;
2159                     }
2160                   EXPR_WFL_LINECOL ($2) = $1.location;
2161                   $$ = $2;
2162                 }
2163 |       OSB_TK expression error
2164                 {yyerror ("']' expected"); RECOVER;}
2165 |       OSB_TK error
2166                 {
2167                   yyerror ("Missing term");
2168                   yyerror ("']' expected");
2169                   RECOVER;
2170                 }
2171 ;
2172
2173 dims:                           
2174         OSB_TK CSB_TK
2175                 { 
2176                   int allocate = 0;
2177                   /* If not initialized, allocate memory for the osb
2178                      numbers stack */
2179                   if (!ctxp->osb_limit)
2180                     {
2181                       allocate = ctxp->osb_limit = 32;
2182                       ctxp->osb_depth = -1;
2183                     }
2184                   /* If capacity overflown, reallocate a bigger chunk */
2185                   else if (ctxp->osb_depth+1 == ctxp->osb_limit)
2186                     allocate = ctxp->osb_limit << 1;
2187                   
2188                   if (allocate)
2189                     {
2190                       allocate *= sizeof (int);
2191                       if (ctxp->osb_number)
2192                         ctxp->osb_number = (int *)xrealloc (ctxp->osb_number,
2193                                                             allocate);
2194                       else
2195                         ctxp->osb_number = (int *)xmalloc (allocate);
2196                     }
2197                   ctxp->osb_depth++;
2198                   CURRENT_OSB (ctxp) = 1;
2199                 }
2200 |       dims OSB_TK CSB_TK
2201                 { CURRENT_OSB (ctxp)++; }
2202 |       dims OSB_TK error
2203                 { yyerror ("']' expected"); RECOVER;}
2204 ;
2205
2206 field_access:
2207         primary DOT_TK identifier
2208                 { $$ = make_qualified_primary ($1, $3, $2.location); }
2209                 /*  FIXME - REWRITE TO: 
2210                 { $$ = build_binop (COMPONENT_REF, $2.location, $1, $3); } */
2211 |       SUPER_TK DOT_TK identifier
2212                 {
2213                   tree super_wfl = build_wfl_node (super_identifier_node);
2214                   EXPR_WFL_LINECOL (super_wfl) = $1.location;
2215                   $$ = make_qualified_name (super_wfl, $3, $2.location);
2216                 }
2217 |       SUPER_TK error
2218                 {yyerror ("Field expected"); DRECOVER (super_field_acces);}
2219 ;
2220
2221 method_invocation:
2222         name OP_TK CP_TK
2223                 { $$ = build_method_invocation ($1, NULL_TREE); }
2224 |       name OP_TK argument_list CP_TK
2225                 { $$ = build_method_invocation ($1, $3); }
2226 |       primary DOT_TK identifier OP_TK CP_TK
2227                 { 
2228                   if (TREE_CODE ($1) == THIS_EXPR)
2229                     $$ = build_this_super_qualified_invocation 
2230                       (1, $3, NULL_TREE, 0, $2.location);
2231                   else
2232                     {
2233                       tree invok = build_method_invocation ($3, NULL_TREE);
2234                       $$ = make_qualified_primary ($1, invok, $2.location);
2235                     }
2236                 }
2237 |       primary DOT_TK identifier OP_TK argument_list CP_TK
2238                 { 
2239                   if (TREE_CODE ($1) == THIS_EXPR)
2240                     $$ = build_this_super_qualified_invocation 
2241                       (1, $3, $5, 0, $2.location);
2242                   else
2243                     {
2244                       tree invok = build_method_invocation ($3, $5);
2245                       $$ = make_qualified_primary ($1, invok, $2.location);
2246                     }
2247                 }
2248 |       SUPER_TK DOT_TK identifier OP_TK CP_TK
2249                 { 
2250                   $$ = build_this_super_qualified_invocation 
2251                     (0, $3, NULL_TREE, $1.location, $2.location);
2252                 }
2253 |       SUPER_TK DOT_TK identifier OP_TK argument_list CP_TK
2254                 {
2255                   $$ = build_this_super_qualified_invocation 
2256                     (0, $3, $5, $1.location, $2.location);
2257                 }
2258         /* Screws up thing. I let it here until I'm convinced it can
2259            be removed. FIXME
2260 |       primary DOT_TK error
2261                 {yyerror ("'(' expected"); DRECOVER(bad);} */
2262 |       SUPER_TK DOT_TK error CP_TK
2263                 { yyerror ("'(' expected"); DRECOVER (method_invocation); }
2264 |       SUPER_TK DOT_TK error DOT_TK
2265                 { yyerror ("'(' expected"); DRECOVER (method_invocation); }
2266 ;
2267
2268 array_access:
2269         name OSB_TK expression CSB_TK
2270                 { $$ = build_array_ref ($2.location, $1, $3); }
2271 |       primary_no_new_array OSB_TK expression CSB_TK
2272                 { $$ = build_array_ref ($2.location, $1, $3); }
2273 |       name OSB_TK error
2274                 {
2275                   yyerror ("Missing term and ']' expected");
2276                   DRECOVER(array_access);
2277                 }
2278 |       name OSB_TK expression error
2279                 {
2280                   yyerror ("']' expected");
2281                   DRECOVER(array_access);
2282                 }
2283 |       primary_no_new_array OSB_TK error
2284                 {
2285                   yyerror ("Missing term and ']' expected");
2286                   DRECOVER(array_access);
2287                 }
2288 |       primary_no_new_array OSB_TK expression error
2289                 {
2290                   yyerror ("']' expected");
2291                   DRECOVER(array_access);
2292                 }
2293 ;
2294
2295 postfix_expression:
2296         primary
2297 |       name
2298 |       post_increment_expression
2299 |       post_decrement_expression
2300 ;
2301
2302 post_increment_expression:
2303         postfix_expression INCR_TK
2304                 { $$ = build_incdec ($2.token, $2.location, $1, 1); }
2305 ;
2306
2307 post_decrement_expression:
2308         postfix_expression DECR_TK
2309                 { $$ = build_incdec ($2.token, $2.location, $1, 1); }
2310 ;
2311
2312 trap_overflow_corner_case:
2313         pre_increment_expression
2314 |       pre_decrement_expression
2315 |       PLUS_TK unary_expression
2316                 {$$ = build_unaryop ($1.token, $1.location, $2); }
2317 |       unary_expression_not_plus_minus
2318 |       PLUS_TK error
2319                 {yyerror ("Missing term"); RECOVER}
2320 ;
2321
2322 unary_expression:
2323         trap_overflow_corner_case
2324                 {
2325                   error_if_numeric_overflow ($1);
2326                   $$ = $1;
2327                 }
2328 |       MINUS_TK trap_overflow_corner_case
2329                 {$$ = build_unaryop ($1.token, $1.location, $2); }
2330 |       MINUS_TK error
2331                 {yyerror ("Missing term"); RECOVER}
2332 ;
2333
2334 pre_increment_expression:
2335         INCR_TK unary_expression
2336                 {$$ = build_incdec ($1.token, $1.location, $2, 0); }
2337 |       INCR_TK error
2338                 {yyerror ("Missing term"); RECOVER}
2339 ;
2340
2341 pre_decrement_expression:
2342         DECR_TK unary_expression
2343                 {$$ = build_incdec ($1.token, $1.location, $2, 0); }
2344 |       DECR_TK error
2345                 {yyerror ("Missing term"); RECOVER}
2346 ;
2347
2348 unary_expression_not_plus_minus:
2349         postfix_expression
2350 |       NOT_TK unary_expression
2351                 {$$ = build_unaryop ($1.token, $1.location, $2); }
2352 |       NEG_TK unary_expression
2353                 {$$ = build_unaryop ($1.token, $1.location, $2); }
2354 |       cast_expression
2355 |       NOT_TK error
2356                 {yyerror ("Missing term"); RECOVER}
2357 |       NEG_TK error
2358                 {yyerror ("Missing term"); RECOVER}
2359 ;
2360
2361 cast_expression:                /* Error handling here is potentially weak */
2362         OP_TK primitive_type dims CP_TK unary_expression
2363                 { 
2364                   tree type = $2;
2365                   int osb = pop_current_osb (ctxp);
2366                   while (osb--)
2367                     type = build_java_array_type (type, -1);
2368                   $$ = build_cast ($1.location, type, $5); 
2369                 }
2370 |       OP_TK primitive_type CP_TK unary_expression
2371                 { $$ = build_cast ($1.location, $2, $4); }
2372 |       OP_TK expression CP_TK unary_expression_not_plus_minus
2373                 { $$ = build_cast ($1.location, $2, $4); }
2374 |       OP_TK name dims CP_TK unary_expression_not_plus_minus
2375                 { 
2376                   const char *ptr;
2377                   int osb = pop_current_osb (ctxp); 
2378                   obstack_grow (&temporary_obstack, 
2379                                 IDENTIFIER_POINTER (EXPR_WFL_NODE ($2)),
2380                                 IDENTIFIER_LENGTH (EXPR_WFL_NODE ($2)));
2381                   while (osb--)
2382                     obstack_grow (&temporary_obstack, "[]", 2);
2383                   obstack_1grow (&temporary_obstack, '\0');
2384                   ptr = obstack_finish (&temporary_obstack);
2385                   EXPR_WFL_NODE ($2) = get_identifier (ptr);
2386                   $$ = build_cast ($1.location, $2, $5);
2387                 }
2388 |       OP_TK primitive_type OSB_TK error
2389                 {yyerror ("']' expected, invalid type expression");}
2390 |       OP_TK error
2391                 {
2392                   YYNOT_TWICE yyerror ("Invalid type expression"); RECOVER;
2393                   RECOVER;
2394                 }
2395 |       OP_TK primitive_type dims CP_TK error
2396                 {yyerror ("Missing term"); RECOVER;}
2397 |       OP_TK primitive_type CP_TK error
2398                 {yyerror ("Missing term"); RECOVER;}
2399 |       OP_TK name dims CP_TK error
2400                 {yyerror ("Missing term"); RECOVER;}
2401 ;
2402
2403 multiplicative_expression:
2404         unary_expression
2405 |       multiplicative_expression MULT_TK unary_expression
2406                 { 
2407                   $$ = build_binop (BINOP_LOOKUP ($2.token), 
2408                                     $2.location, $1, $3);
2409                 }
2410 |       multiplicative_expression DIV_TK unary_expression
2411                 {
2412                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2413                                     $1, $3); 
2414                 }
2415 |       multiplicative_expression REM_TK unary_expression
2416                 {
2417                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2418                                     $1, $3); 
2419                 }
2420 |       multiplicative_expression MULT_TK error
2421                 {yyerror ("Missing term"); RECOVER;}
2422 |       multiplicative_expression DIV_TK error
2423                 {yyerror ("Missing term"); RECOVER;}
2424 |       multiplicative_expression REM_TK error
2425                 {yyerror ("Missing term"); RECOVER;}
2426 ;
2427
2428 additive_expression:
2429         multiplicative_expression
2430 |       additive_expression PLUS_TK multiplicative_expression
2431                 {
2432                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2433                                     $1, $3); 
2434                 }
2435 |       additive_expression MINUS_TK multiplicative_expression
2436                 {
2437                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2438                                     $1, $3); 
2439                 }
2440 |       additive_expression PLUS_TK error
2441                 {yyerror ("Missing term"); RECOVER;}
2442 |       additive_expression MINUS_TK error
2443                 {yyerror ("Missing term"); RECOVER;}
2444 ;
2445
2446 shift_expression:
2447         additive_expression
2448 |       shift_expression LS_TK additive_expression
2449                 {
2450                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2451                                     $1, $3); 
2452                 }
2453 |       shift_expression SRS_TK additive_expression
2454                 {
2455                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2456                                     $1, $3); 
2457                 }
2458 |       shift_expression ZRS_TK additive_expression
2459                 {
2460                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2461                                     $1, $3); 
2462                 }
2463 |       shift_expression LS_TK error
2464                 {yyerror ("Missing term"); RECOVER;}
2465 |       shift_expression SRS_TK error
2466                 {yyerror ("Missing term"); RECOVER;}
2467 |       shift_expression ZRS_TK error
2468                 {yyerror ("Missing term"); RECOVER;}
2469 ;
2470
2471 relational_expression:
2472         shift_expression
2473 |       relational_expression LT_TK shift_expression
2474                 {
2475                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2476                                     $1, $3); 
2477                 }
2478 |       relational_expression GT_TK shift_expression
2479                 {
2480                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2481                                     $1, $3); 
2482                 }
2483 |       relational_expression LTE_TK shift_expression
2484                 {
2485                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2486                                     $1, $3); 
2487                 }
2488 |       relational_expression GTE_TK shift_expression
2489                 {
2490                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2491                                     $1, $3); 
2492                 }
2493 |       relational_expression INSTANCEOF_TK reference_type
2494                 { $$ = build_binop (INSTANCEOF_EXPR, $2.location, $1, $3); }
2495 |       relational_expression LT_TK error
2496                 {yyerror ("Missing term"); RECOVER;}
2497 |       relational_expression GT_TK error
2498                 {yyerror ("Missing term"); RECOVER;}
2499 |       relational_expression LTE_TK error
2500                 {yyerror ("Missing term"); RECOVER;}
2501 |       relational_expression GTE_TK error
2502                 {yyerror ("Missing term"); RECOVER;}
2503 |       relational_expression INSTANCEOF_TK error
2504                 {yyerror ("Invalid reference type"); RECOVER;}
2505 ;
2506
2507 equality_expression:
2508         relational_expression
2509 |       equality_expression EQ_TK relational_expression
2510                 {
2511                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2512                                     $1, $3); 
2513                 }
2514 |       equality_expression NEQ_TK relational_expression
2515                 {
2516                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2517                                     $1, $3); 
2518                 }
2519 |       equality_expression EQ_TK error
2520                 {yyerror ("Missing term"); RECOVER;}
2521 |       equality_expression NEQ_TK error
2522                 {yyerror ("Missing term"); RECOVER;}
2523 ;
2524
2525 and_expression:
2526         equality_expression
2527 |       and_expression AND_TK equality_expression
2528                 {
2529                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2530                                     $1, $3); 
2531                 }
2532 |       and_expression AND_TK error
2533                 {yyerror ("Missing term"); RECOVER;}
2534 ;
2535
2536 exclusive_or_expression:
2537         and_expression
2538 |       exclusive_or_expression XOR_TK and_expression
2539                 {
2540                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2541                                     $1, $3); 
2542                 }
2543 |       exclusive_or_expression XOR_TK error
2544                 {yyerror ("Missing term"); RECOVER;}
2545 ;
2546
2547 inclusive_or_expression:
2548         exclusive_or_expression
2549 |       inclusive_or_expression OR_TK exclusive_or_expression
2550                 {
2551                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2552                                     $1, $3); 
2553                 }
2554 |       inclusive_or_expression OR_TK error
2555                 {yyerror ("Missing term"); RECOVER;}
2556 ;
2557
2558 conditional_and_expression:
2559         inclusive_or_expression
2560 |       conditional_and_expression BOOL_AND_TK inclusive_or_expression
2561                 {
2562                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2563                                     $1, $3); 
2564                 }
2565 |       conditional_and_expression BOOL_AND_TK error
2566                 {yyerror ("Missing term"); RECOVER;}
2567 ;
2568
2569 conditional_or_expression:
2570         conditional_and_expression
2571 |       conditional_or_expression BOOL_OR_TK conditional_and_expression
2572                 {
2573                   $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2574                                     $1, $3); 
2575                 }
2576 |       conditional_or_expression BOOL_OR_TK error
2577                 {yyerror ("Missing term"); RECOVER;}
2578 ;
2579
2580 conditional_expression:         /* Error handling here is weak */
2581         conditional_or_expression
2582 |       conditional_or_expression REL_QM_TK expression REL_CL_TK conditional_expression
2583                 {
2584                   $$ = build (CONDITIONAL_EXPR, NULL_TREE, $1, $3, $5);
2585                   EXPR_WFL_LINECOL ($$) = $2.location;
2586                 }
2587 |       conditional_or_expression REL_QM_TK REL_CL_TK error
2588                 {
2589                   YYERROR_NOW;
2590                   yyerror ("Missing term");
2591                   DRECOVER (1);
2592                 }
2593 |       conditional_or_expression REL_QM_TK error
2594                 {yyerror ("Missing term"); DRECOVER (2);}
2595 |       conditional_or_expression REL_QM_TK expression REL_CL_TK error
2596                 {yyerror ("Missing term"); DRECOVER (3);}
2597 ;
2598
2599 assignment_expression:
2600         conditional_expression
2601 |       assignment
2602 ;
2603
2604 assignment:
2605         left_hand_side assignment_operator assignment_expression
2606                 { $$ = build_assignment ($2.token, $2.location, $1, $3); }
2607 |       left_hand_side assignment_operator error
2608                 {
2609                   YYNOT_TWICE yyerror ("Missing term");
2610                   DRECOVER (assign);
2611                 }
2612 ;
2613
2614 left_hand_side:
2615         name
2616 |       field_access
2617 |       array_access
2618 ;
2619
2620 assignment_operator:
2621         ASSIGN_ANY_TK
2622 |       ASSIGN_TK
2623 ;
2624
2625 expression:
2626         assignment_expression
2627 ;
2628
2629 constant_expression:
2630         expression
2631 ;
2632
2633 %%
2634
2635 /* Helper function to retrieve an OSB count. Should be used when the
2636    `dims:' rule is being used.  */
2637
2638 static int
2639 pop_current_osb (ctxp)
2640      struct parser_ctxt *ctxp;
2641 {
2642   int to_return;
2643
2644   if (ctxp->osb_depth < 0)
2645     abort ();
2646   
2647   to_return = CURRENT_OSB (ctxp);
2648   ctxp->osb_depth--;
2649   
2650   return to_return;
2651 }
2652
2653 \f
2654
2655 /* This section of the code deal with save/restoring parser contexts.
2656    Add mode documentation here. FIXME */
2657
2658 /* Helper function. Create a new parser context. With
2659    COPY_FROM_PREVIOUS set to a non zero value, content of the previous
2660    context is copied, otherwise, the new context is zeroed. The newly
2661    created context becomes the current one.  */
2662
2663 static void
2664 create_new_parser_context (copy_from_previous)
2665     int copy_from_previous;
2666 {
2667   struct parser_ctxt *new;
2668
2669   new =  (struct parser_ctxt *)xmalloc(sizeof (struct parser_ctxt));
2670   if (copy_from_previous)
2671     {
2672       memcpy ((PTR)new, (PTR)ctxp, sizeof (struct parser_ctxt));
2673       new->saved_data_ctx = 1;
2674     }
2675   else
2676     memset ((PTR) new, 0, sizeof (struct parser_ctxt));
2677       
2678   new->next = ctxp;
2679   ctxp = new;
2680 }
2681
2682 /* Create a new parser context and make it the current one. */
2683
2684 void
2685 java_push_parser_context ()
2686 {
2687   create_new_parser_context (0);
2688 }  
2689
2690 void 
2691 java_pop_parser_context (generate)
2692      int generate;
2693 {
2694   tree current;
2695   struct parser_ctxt *toFree, *next;
2696
2697   if (!ctxp)
2698     return;
2699
2700   toFree = ctxp;
2701   next = ctxp->next;
2702   if (next)
2703     {
2704       lineno = ctxp->lineno;
2705       current_class = ctxp->class_type;
2706     }
2707
2708   /* If the old and new lexers differ, then free the old one.  */
2709   if (ctxp->lexer && next && ctxp->lexer != next->lexer)
2710     java_destroy_lexer (ctxp->lexer);
2711
2712   /* Set the single import class file flag to 0 for the current list
2713      of imported things */
2714   for (current = ctxp->import_list; current; current = TREE_CHAIN (current))
2715     IS_A_SINGLE_IMPORT_CLASSFILE_NAME_P (TREE_VALUE (current)) = 0;
2716
2717   /* And restore those of the previous context */
2718   if ((ctxp = next))            /* Assignment is really meant here */
2719     for (current = ctxp->import_list; current; current = TREE_CHAIN (current))
2720       IS_A_SINGLE_IMPORT_CLASSFILE_NAME_P (TREE_VALUE (current)) = 1;
2721   
2722   /* If we pushed a context to parse a class intended to be generated,
2723      we keep it so we can remember the class. What we could actually
2724      do is to just update a list of class names.  */
2725   if (generate)
2726     {
2727       toFree->next = ctxp_for_generation;
2728       ctxp_for_generation = toFree;
2729     }
2730   else
2731     free (toFree);
2732 }
2733
2734 /* Create a parser context for the use of saving some global
2735    variables.  */
2736
2737 void
2738 java_parser_context_save_global ()
2739 {
2740   if (!ctxp)
2741     {
2742       java_push_parser_context ();
2743       ctxp->saved_data_ctx = 1;
2744     }
2745
2746   /* If this context already stores data, create a new one suitable
2747      for data storage. */
2748   else if (ctxp->saved_data)
2749     create_new_parser_context (1);
2750
2751   ctxp->lineno = lineno;
2752   ctxp->class_type = current_class;
2753   ctxp->filename = input_filename;
2754   ctxp->function_decl = current_function_decl;
2755   ctxp->saved_data = 1;
2756 }
2757
2758 /* Restore some global variables from the previous context. Make the
2759    previous context the current one.  */
2760
2761 void
2762 java_parser_context_restore_global ()
2763 {
2764   lineno = ctxp->lineno;
2765   current_class = ctxp->class_type;
2766   input_filename = ctxp->filename;
2767   if (wfl_operator)
2768     {
2769       tree s;
2770       BUILD_FILENAME_IDENTIFIER_NODE (s, input_filename);
2771       EXPR_WFL_FILENAME_NODE (wfl_operator) = s;
2772     }
2773   current_function_decl = ctxp->function_decl;
2774   ctxp->saved_data = 0;
2775   if (ctxp->saved_data_ctx)
2776     java_pop_parser_context (0);
2777 }
2778
2779 /* Suspend vital data for the current class/function being parsed so
2780    that an other class can be parsed. Used to let local/anonymous
2781    classes be parsed.  */
2782
2783 static void
2784 java_parser_context_suspend ()
2785 {
2786   /* This makes debugging through java_debug_context easier */
2787   static const char *const name = "<inner buffer context>";
2788
2789   /* Duplicate the previous context, use it to save the globals we're
2790      interested in */
2791   create_new_parser_context (1);
2792   ctxp->function_decl = current_function_decl;
2793   ctxp->class_type = current_class;
2794
2795   /* Then create a new context which inherits all data from the
2796      previous one. This will be the new current context  */
2797   create_new_parser_context (1);
2798
2799   /* Help debugging */
2800   ctxp->next->filename = name;
2801 }
2802
2803 /* Resume vital data for the current class/function being parsed so
2804    that an other class can be parsed. Used to let local/anonymous
2805    classes be parsed.  The trick is the data storing file position
2806    informations must be restored to their current value, so parsing
2807    can resume as if no context was ever saved. */
2808
2809 static void
2810 java_parser_context_resume ()
2811 {
2812   struct parser_ctxt *old = ctxp;             /* This one is to be discarded */
2813   struct parser_ctxt *saver = old->next;      /* This one contain saved info */
2814   struct parser_ctxt *restored = saver->next; /* This one is the old current */
2815
2816   /* We need to inherit the list of classes to complete/generate */
2817   restored->classd_list = old->classd_list;
2818   restored->class_list = old->class_list;
2819
2820   /* Restore the current class and function from the saver */
2821   current_class = saver->class_type;
2822   current_function_decl = saver->function_decl;
2823
2824   /* Retrive the restored context */
2825   ctxp = restored;
2826
2827   /* Re-installed the data for the parsing to carry on */
2828   memcpy (&ctxp->marker_begining, &old->marker_begining, 
2829           (size_t)(&ctxp->marker_end - &ctxp->marker_begining));
2830
2831   /* Buffer context can now be discarded */
2832   free (saver);
2833   free (old);
2834 }
2835
2836 /* Add a new anchor node to which all statement(s) initializing static
2837    and non static initialized upon declaration field(s) will be
2838    linked.  */
2839
2840 static void
2841 java_parser_context_push_initialized_field ()
2842 {
2843   tree node;
2844
2845   node = build_tree_list (NULL_TREE, NULL_TREE);
2846   TREE_CHAIN (node) = CPC_STATIC_INITIALIZER_LIST (ctxp);
2847   CPC_STATIC_INITIALIZER_LIST (ctxp) = node;
2848
2849   node = build_tree_list (NULL_TREE, NULL_TREE);
2850   TREE_CHAIN (node) = CPC_INITIALIZER_LIST (ctxp);
2851   CPC_INITIALIZER_LIST (ctxp) = node;
2852
2853   node = build_tree_list (NULL_TREE, NULL_TREE);
2854   TREE_CHAIN (node) = CPC_INSTANCE_INITIALIZER_LIST (ctxp);
2855   CPC_INSTANCE_INITIALIZER_LIST (ctxp) = node;
2856 }
2857
2858 /* Pop the lists of initialized field. If this lists aren't empty,
2859    remember them so we can use it to create and populate the finit$
2860    or <clinit> functions. */
2861
2862 static void
2863 java_parser_context_pop_initialized_field ()
2864 {
2865   tree stmts;
2866   tree class_type = TREE_TYPE (GET_CPC ());
2867
2868   if (CPC_INITIALIZER_LIST (ctxp))
2869     {
2870       stmts = CPC_INITIALIZER_STMT (ctxp);
2871       CPC_INITIALIZER_LIST (ctxp) = TREE_CHAIN (CPC_INITIALIZER_LIST (ctxp));
2872       if (stmts && !java_error_count)
2873         TYPE_FINIT_STMT_LIST (class_type) = reorder_static_initialized (stmts);
2874     }
2875
2876   if (CPC_STATIC_INITIALIZER_LIST (ctxp))
2877     {
2878       stmts = CPC_STATIC_INITIALIZER_STMT (ctxp);
2879       CPC_STATIC_INITIALIZER_LIST (ctxp) = 
2880         TREE_CHAIN (CPC_STATIC_INITIALIZER_LIST (ctxp));
2881       /* Keep initialization in order to enforce 8.5 */
2882       if (stmts && !java_error_count)
2883         TYPE_CLINIT_STMT_LIST (class_type) = nreverse (stmts);
2884     }
2885
2886   /* JDK 1.1 instance initializers */
2887   if (CPC_INSTANCE_INITIALIZER_LIST (ctxp))
2888     {
2889       stmts = CPC_INSTANCE_INITIALIZER_STMT (ctxp);
2890       CPC_INSTANCE_INITIALIZER_LIST (ctxp) = 
2891         TREE_CHAIN (CPC_INSTANCE_INITIALIZER_LIST (ctxp));
2892       if (stmts && !java_error_count)
2893         TYPE_II_STMT_LIST (class_type) = nreverse (stmts);
2894     }
2895 }
2896
2897 static tree
2898 reorder_static_initialized (list)
2899      tree list;
2900 {
2901   /* We have to keep things in order. The alias initializer have to
2902      come first, then the initialized regular field, in reverse to
2903      keep them in lexical order. */
2904   tree marker, previous = NULL_TREE;
2905   for (marker = list; marker; previous = marker, marker = TREE_CHAIN (marker))
2906     if (TREE_CODE (marker) == TREE_LIST 
2907         && !TREE_VALUE (marker) && !TREE_PURPOSE (marker))
2908       break;
2909   
2910   /* No static initialized, the list is fine as is */
2911   if (!previous)
2912     list = TREE_CHAIN (marker);
2913
2914   /* No marker? reverse the whole list */
2915   else if (!marker)
2916     list = nreverse (list);
2917
2918   /* Otherwise, reverse what's after the marker and the new reordered
2919      sublist will replace the marker. */
2920   else
2921     {
2922       TREE_CHAIN (previous) = NULL_TREE;
2923       list = nreverse (list);
2924       list = chainon (TREE_CHAIN (marker), list);
2925     }
2926   return list;
2927 }
2928
2929 /* Helper functions to dump the parser context stack.  */
2930
2931 #define TAB_CONTEXT(C) \
2932   {int i; for (i = 0; i < (C); i++) fputc (' ', stderr);}
2933
2934 static void
2935 java_debug_context_do (tab)
2936      int tab;
2937 {
2938   struct parser_ctxt *copy = ctxp;
2939   while (copy)
2940     {
2941       TAB_CONTEXT (tab);
2942       fprintf (stderr, "ctxt: 0x%0lX\n", (unsigned long)copy);
2943       TAB_CONTEXT (tab);
2944       fprintf (stderr, "filename: %s\n", copy->filename);
2945       TAB_CONTEXT (tab);
2946       fprintf (stderr, "lineno: %d\n", copy->lineno);
2947       TAB_CONTEXT (tab);
2948       fprintf (stderr, "package: %s\n",
2949                (copy->package ? 
2950                 IDENTIFIER_POINTER (copy->package) : "<none>"));
2951       TAB_CONTEXT (tab);
2952       fprintf (stderr, "context for saving: %d\n", copy->saved_data_ctx);
2953       TAB_CONTEXT (tab);
2954       fprintf (stderr, "saved data: %d\n", copy->saved_data);
2955       copy = copy->next;
2956       tab += 2;
2957     }
2958 }
2959
2960 /* Dump the stacked up parser contexts. Intended to be called from a
2961    debugger.  */
2962
2963 void
2964 java_debug_context ()
2965 {
2966   java_debug_context_do (0);
2967 }
2968
2969 \f
2970
2971 /* Flag for the error report routine to issue the error the first time
2972    it's called (overriding the default behavior which is to drop the
2973    first invocation and honor the second one, taking advantage of a
2974    richer context.  */
2975 static int force_error = 0;
2976
2977 /* Reporting an constructor invocation error.  */
2978 static void
2979 parse_ctor_invocation_error ()
2980 {
2981   if (DECL_CONSTRUCTOR_P (current_function_decl))
2982     yyerror ("Constructor invocation must be first thing in a constructor"); 
2983   else
2984     yyerror ("Only constructors can invoke constructors");
2985 }
2986
2987 /* Reporting JDK1.1 features not implemented.  */
2988
2989 static tree
2990 parse_jdk1_1_error (msg)
2991     const char *msg;
2992 {
2993   sorry (": `%s' JDK1.1(TM) feature", msg);
2994   java_error_count++;
2995   return empty_stmt_node;
2996 }
2997
2998 static int do_warning = 0;
2999
3000 void
3001 yyerror (msg)
3002      const char *msg;
3003 {
3004   static java_lc elc;
3005   static int  prev_lineno;
3006   static const char *prev_msg;
3007
3008   int save_lineno;
3009   char *remainder, *code_from_source;
3010   
3011   if (!force_error && prev_lineno == lineno)
3012     return;
3013
3014   /* Save current error location but report latter, when the context is
3015      richer.  */
3016   if (ctxp->java_error_flag == 0)
3017     {
3018       ctxp->java_error_flag = 1;
3019       elc = ctxp->elc;
3020       /* Do something to use the previous line if we're reaching the
3021          end of the file... */
3022 #ifdef VERBOSE_SKELETON
3023       printf ("* Error detected (%s)\n", (msg ? msg : "(null)"));
3024 #endif
3025       return;
3026     }
3027
3028   /* Ignore duplicate message on the same line. BTW, this is dubious. FIXME */
3029   if (!force_error && msg == prev_msg && prev_lineno == elc.line)
3030     return;
3031
3032   ctxp->java_error_flag = 0;
3033   if (do_warning)
3034     java_warning_count++;
3035   else
3036     java_error_count++;
3037   
3038   if (elc.col == 0 && msg && msg[1] == ';')
3039     {
3040       elc.col  = ctxp->p_line->char_col-1;
3041       elc.line = ctxp->p_line->lineno;
3042     }
3043
3044   save_lineno = lineno;
3045   prev_lineno = lineno = elc.line;
3046   prev_msg = msg;
3047
3048   code_from_source = java_get_line_col (ctxp->filename, elc.line, elc.col);
3049   obstack_grow0 (&temporary_obstack, 
3050                  code_from_source, strlen (code_from_source));
3051   remainder = obstack_finish (&temporary_obstack);
3052   if (do_warning)
3053     warning ("%s.\n%s", msg, remainder);
3054   else
3055     error ("%s.\n%s", msg, remainder);
3056
3057   /* This allow us to cheaply avoid an extra 'Invalid expression
3058      statement' error report when errors have been already reported on
3059      the same line. This occurs when we report an error but don't have
3060      a synchronization point other than ';', which
3061      expression_statement is the only one to take care of.  */
3062   ctxp->prevent_ese = lineno = save_lineno;
3063 }
3064
3065 static void
3066 issue_warning_error_from_context (cl, msg, ap)
3067      tree cl;
3068      const char *msg;
3069      va_list ap;
3070 {
3071   const char *saved, *saved_input_filename;
3072   char buffer [4096];
3073   vsprintf (buffer, msg, ap);
3074   force_error = 1;
3075
3076   ctxp->elc.line = EXPR_WFL_LINENO (cl);
3077   ctxp->elc.col  = (EXPR_WFL_COLNO (cl) == 0xfff ? -1 : 
3078                     (EXPR_WFL_COLNO (cl) == 0xffe ? -2 : EXPR_WFL_COLNO (cl)));
3079
3080   /* We have a CL, that's a good reason for using it if it contains data */
3081   saved = ctxp->filename;
3082   if (TREE_CODE (cl) == EXPR_WITH_FILE_LOCATION && EXPR_WFL_FILENAME_NODE (cl))
3083     ctxp->filename = EXPR_WFL_FILENAME (cl);
3084   saved_input_filename = input_filename;
3085   input_filename = ctxp->filename;
3086   java_error (NULL);
3087   java_error (buffer);
3088   ctxp->filename = saved;
3089   input_filename = saved_input_filename;
3090   force_error = 0;
3091 }
3092
3093 /* Issue an error message at a current source line CL */
3094
3095 void
3096 parse_error_context VPARAMS ((tree cl, const char *msg, ...))
3097 {
3098   VA_OPEN (ap, msg);
3099   VA_FIXEDARG (ap, tree, cl);
3100   VA_FIXEDARG (ap, const char *, msg);
3101   issue_warning_error_from_context (cl, msg, ap);
3102   VA_CLOSE (ap);
3103 }
3104
3105 /* Issue a warning at a current source line CL */
3106
3107 static void
3108 parse_warning_context VPARAMS ((tree cl, const char *msg, ...))
3109 {
3110   VA_OPEN (ap, msg);
3111   VA_FIXEDARG (ap, tree, cl);
3112   VA_FIXEDARG (ap, const char *, msg);
3113
3114   force_error = do_warning = 1;
3115   issue_warning_error_from_context (cl, msg, ap);
3116   do_warning = force_error = 0;
3117   VA_CLOSE (ap);
3118 }
3119
3120 static tree
3121 find_expr_with_wfl (node)
3122      tree node;
3123 {
3124   while (node)
3125     {
3126       char code;
3127       tree to_return;
3128
3129       switch (TREE_CODE (node))
3130         {
3131         case BLOCK:
3132           node = BLOCK_EXPR_BODY (node);
3133           continue;
3134
3135         case COMPOUND_EXPR:
3136           to_return = find_expr_with_wfl (TREE_OPERAND (node, 0));
3137           if (to_return)
3138             return to_return;
3139           node = TREE_OPERAND (node, 1);
3140           continue;
3141
3142         case LOOP_EXPR:
3143           node = TREE_OPERAND (node, 0);
3144           continue;
3145           
3146         case LABELED_BLOCK_EXPR:
3147           node = TREE_OPERAND (node, 1);
3148           continue;
3149
3150         default:
3151           code = TREE_CODE_CLASS (TREE_CODE (node));
3152           if (((code == '1') || (code == '2') || (code == 'e'))
3153               && EXPR_WFL_LINECOL (node))
3154             return node;
3155           return NULL_TREE;
3156         }
3157     }
3158   return NULL_TREE;
3159 }
3160
3161 /* Issue a missing return statement error. Uses METHOD to figure the
3162    last line of the method the error occurs in.  */
3163
3164 static void
3165 missing_return_error (method)
3166      tree method;
3167 {
3168   EXPR_WFL_SET_LINECOL (wfl_operator, DECL_SOURCE_LINE_LAST (method), -2);
3169   parse_error_context (wfl_operator, "Missing return statement");
3170 }
3171
3172 /* Issue an unreachable statement error. From NODE, find the next
3173    statement to report appropriately.  */
3174 static void
3175 unreachable_stmt_error (node)
3176      tree node;
3177 {
3178   /* Browse node to find the next expression node that has a WFL. Use
3179      the location to report the error */
3180   if (TREE_CODE (node) == COMPOUND_EXPR)
3181     node = find_expr_with_wfl (TREE_OPERAND (node, 1));
3182   else
3183     node = find_expr_with_wfl (node);
3184
3185   if (node)
3186     {
3187       EXPR_WFL_SET_LINECOL (wfl_operator, EXPR_WFL_LINENO (node), -2);
3188       parse_error_context (wfl_operator, "Unreachable statement");
3189     }
3190   else
3191     abort ();
3192 }
3193
3194 int
3195 java_report_errors ()
3196 {
3197   if (java_error_count)
3198     fprintf (stderr, "%d error%s", 
3199              java_error_count, (java_error_count == 1 ? "" : "s"));
3200   if (java_warning_count)
3201     fprintf (stderr, "%s%d warning%s", (java_error_count ? ", " : ""),
3202              java_warning_count, (java_warning_count == 1 ? "" : "s"));
3203   if (java_error_count || java_warning_count)
3204     putc ('\n', stderr);
3205   return java_error_count;
3206 }
3207
3208 static char *
3209 java_accstring_lookup (flags)
3210      int flags;
3211 {
3212   static char buffer [80];
3213 #define COPY_RETURN(S) {strcpy (buffer, S); return buffer;}
3214
3215   /* Access modifier looked-up first for easier report on forbidden
3216      access. */
3217   if (flags & ACC_PUBLIC) COPY_RETURN ("public");
3218   if (flags & ACC_PRIVATE) COPY_RETURN ("private");
3219   if (flags & ACC_PROTECTED) COPY_RETURN ("protected");
3220   if (flags & ACC_STATIC) COPY_RETURN ("static");
3221   if (flags & ACC_FINAL) COPY_RETURN ("final");
3222   if (flags & ACC_SYNCHRONIZED) COPY_RETURN ("synchronized");
3223   if (flags & ACC_VOLATILE) COPY_RETURN ("volatile");
3224   if (flags & ACC_TRANSIENT) COPY_RETURN ("transient");
3225   if (flags & ACC_NATIVE) COPY_RETURN ("native");
3226   if (flags & ACC_INTERFACE) COPY_RETURN ("interface");
3227   if (flags & ACC_ABSTRACT) COPY_RETURN ("abstract");
3228
3229   buffer [0] = '\0';
3230   return buffer;
3231 #undef COPY_RETURN
3232 }
3233
3234 /* Issuing error messages upon redefinition of classes, interfaces or
3235    variables. */
3236
3237 static void
3238 classitf_redefinition_error (context, id, decl, cl)
3239      const char *context;
3240      tree id, decl, cl;
3241 {
3242   parse_error_context (cl, "%s `%s' already defined in %s:%d", 
3243                        context, IDENTIFIER_POINTER (id), 
3244                        DECL_SOURCE_FILE (decl), DECL_SOURCE_LINE (decl));
3245   /* Here we should point out where its redefined. It's a unicode. FIXME */
3246 }
3247
3248 static void
3249 variable_redefinition_error (context, name, type, line)
3250      tree context, name, type;
3251      int line;
3252 {
3253   const char *type_name;
3254
3255   /* Figure a proper name for type. We might haven't resolved it */
3256   if (TREE_CODE (type) == POINTER_TYPE && !TREE_TYPE (type))
3257     type_name = IDENTIFIER_POINTER (TYPE_NAME (type));
3258   else
3259     type_name = lang_printable_name (type, 0);
3260
3261   parse_error_context (context,
3262                        "Variable `%s' is already defined in this method and was declared `%s %s' at line %d", 
3263                        IDENTIFIER_POINTER (name),
3264                        type_name, IDENTIFIER_POINTER (name), line);
3265 }
3266
3267 /* If ANAME is terminated with `[]', it indicates an array. This
3268    function returns the number of `[]' found and if this number is
3269    greater than zero, it extracts the array type name and places it in
3270    the node pointed to by TRIMMED unless TRIMMED is null.  */
3271
3272 static int
3273 build_type_name_from_array_name (aname, trimmed)
3274      tree aname;
3275      tree *trimmed;
3276 {
3277   const char *name = IDENTIFIER_POINTER (aname);
3278   int len = IDENTIFIER_LENGTH (aname);
3279   int array_dims;
3280
3281   STRING_STRIP_BRACKETS (name, len, array_dims);
3282
3283   if (array_dims && trimmed)
3284     *trimmed = get_identifier_with_length (name, len);
3285
3286   return array_dims;
3287 }
3288
3289 static tree
3290 build_array_from_name (type, type_wfl, name, ret_name)
3291      tree type, type_wfl, name, *ret_name;
3292 {
3293   int more_dims = 0;
3294
3295   /* Eventually get more dims */
3296   more_dims = build_type_name_from_array_name (name, &name);
3297   
3298   /* If we have, then craft a new type for this variable */
3299   if (more_dims)
3300     {
3301       tree save = type;
3302
3303       /* If we have a pointer, use its type */
3304       if (TREE_CODE (type) == POINTER_TYPE)
3305         type = TREE_TYPE (type);
3306
3307       /* Building the first dimension of a primitive type uses this
3308          function */
3309       if (JPRIMITIVE_TYPE_P (type))
3310         {
3311           type = build_java_array_type (type, -1);
3312           more_dims--;
3313         }
3314       /* Otherwise, if we have a WFL for this type, use it (the type
3315          is already an array on an unresolved type, and we just keep
3316          on adding dimensions) */
3317       else if (type_wfl)
3318         {
3319           type = type_wfl;
3320           more_dims += build_type_name_from_array_name (TYPE_NAME (save),
3321                                                         NULL);
3322         }
3323
3324       /* Add all the dimensions */
3325       while (more_dims--)
3326         type = build_unresolved_array_type (type);
3327
3328       /* The type may have been incomplete in the first place */
3329       if (type_wfl)
3330         type = obtain_incomplete_type (type);
3331     }
3332
3333   if (ret_name)
3334     *ret_name = name;
3335   return type;
3336 }
3337
3338 /* Build something that the type identifier resolver will identify as
3339    being an array to an unresolved type. TYPE_WFL is a WFL on a
3340    identifier. */
3341
3342 static tree
3343 build_unresolved_array_type (type_or_wfl)
3344      tree type_or_wfl;
3345 {
3346   const char *ptr;
3347   tree wfl;
3348
3349   /* TYPE_OR_WFL might be an array on a resolved type. In this case,
3350      just create a array type */
3351   if (TREE_CODE (type_or_wfl) == RECORD_TYPE)
3352     return build_java_array_type (type_or_wfl, -1);
3353
3354   obstack_grow (&temporary_obstack,
3355                  IDENTIFIER_POINTER (EXPR_WFL_NODE (type_or_wfl)),
3356                  IDENTIFIER_LENGTH (EXPR_WFL_NODE (type_or_wfl)));
3357   obstack_grow0 (&temporary_obstack, "[]", 2);
3358   ptr = obstack_finish (&temporary_obstack);
3359   wfl = build_expr_wfl (get_identifier (ptr),
3360                         EXPR_WFL_FILENAME (type_or_wfl),
3361                         EXPR_WFL_LINENO (type_or_wfl),
3362                         EXPR_WFL_COLNO (type_or_wfl));
3363   /* Re-install the existing qualifications so that the type can be
3364      resolved properly. */
3365   EXPR_WFL_QUALIFICATION (wfl) = EXPR_WFL_QUALIFICATION (type_or_wfl);
3366   return wfl;
3367 }
3368
3369 static void
3370 parser_add_interface (class_decl, interface_decl, wfl)
3371      tree class_decl, interface_decl, wfl;
3372 {
3373   if (maybe_add_interface (TREE_TYPE (class_decl), TREE_TYPE (interface_decl)))
3374     parse_error_context (wfl, "Interface `%s' repeated",
3375                          IDENTIFIER_POINTER (DECL_NAME (interface_decl)));
3376 }
3377
3378 /* Bulk of common class/interface checks. Return 1 if an error was
3379    encountered. TAG is 0 for a class, 1 for an interface.  */
3380
3381 static int
3382 check_class_interface_creation (is_interface, flags, raw_name, qualified_name, decl, cl)
3383      int is_interface, flags;
3384      tree raw_name, qualified_name, decl, cl;
3385 {
3386   tree node;
3387   int sca = 0;                  /* Static class allowed */
3388   int icaf = 0;                 /* Inner class allowed flags */
3389   int uaaf = CLASS_MODIFIERS;   /* Usually allowed access flags */
3390
3391   if (!quiet_flag)
3392     fprintf (stderr, " %s%s %s", 
3393              (CPC_INNER_P () ? "inner" : ""),
3394              (is_interface ? "interface" : "class"), 
3395              IDENTIFIER_POINTER (qualified_name));
3396
3397   /* Scope of an interface/class type name:
3398        - Can't be imported by a single type import
3399        - Can't already exists in the package */
3400   if (IS_A_SINGLE_IMPORT_CLASSFILE_NAME_P (raw_name)
3401       && (node = find_name_in_single_imports (raw_name))
3402       && !CPC_INNER_P ())
3403     {
3404       parse_error_context 
3405         (cl, "%s name `%s' clashes with imported type `%s'",
3406          (is_interface ? "Interface" : "Class"),
3407          IDENTIFIER_POINTER (raw_name), IDENTIFIER_POINTER (node));
3408       return 1;
3409     }
3410   if (decl && CLASS_COMPLETE_P (decl))
3411     {
3412       classitf_redefinition_error ((is_interface ? "Interface" : "Class"), 
3413                                    qualified_name, decl, cl);
3414       return 1;
3415     }
3416
3417   if (check_inner_class_redefinition (raw_name, cl))
3418     return 1;
3419
3420   /* If public, file name should match class/interface name, except
3421      when dealing with an inner class */
3422   if (!CPC_INNER_P () && (flags & ACC_PUBLIC ))
3423     {
3424       const char *f;
3425
3426       /* Contains OS dependent assumption on path separator. FIXME */
3427       for (f = &input_filename [strlen (input_filename)]; 
3428            f != input_filename && f[0] != '/' && f[0] != DIR_SEPARATOR;
3429            f--)
3430         ;
3431       if (f[0] == '/' || f[0] == DIR_SEPARATOR)
3432         f++;
3433       if (strncmp (IDENTIFIER_POINTER (raw_name), 
3434                    f , IDENTIFIER_LENGTH (raw_name)) ||
3435           f [IDENTIFIER_LENGTH (raw_name)] != '.')
3436         parse_error_context
3437           (cl, "Public %s `%s' must be defined in a file called `%s.java'", 
3438                              (is_interface ? "interface" : "class"),
3439                              IDENTIFIER_POINTER (qualified_name),
3440                              IDENTIFIER_POINTER (raw_name));
3441     }
3442
3443   /* Static classes can be declared only in top level classes. Note:
3444      once static, a inner class is a top level class. */
3445   if (flags & ACC_STATIC)
3446     {
3447       /* Catch the specific error of declaring an class inner class
3448          with no toplevel enclosing class. Prevent check_modifiers from
3449          complaining a second time */
3450       if (CPC_INNER_P () && !TOPLEVEL_CLASS_DECL_P (GET_CPC()))
3451         {
3452           parse_error_context (cl, "Inner class `%s' can't be static. Static classes can only occur in interfaces and top-level classes", 
3453                                IDENTIFIER_POINTER (qualified_name));
3454           sca = ACC_STATIC;
3455         }
3456       /* Else, in the context of a top-level class declaration, let
3457          `check_modifiers' do its job, otherwise, give it a go */
3458       else
3459         sca = (GET_CPC_LIST () ? ACC_STATIC : 0);
3460     }
3461
3462   /* Inner classes can be declared private or protected
3463      within their enclosing classes. */
3464   if (CPC_INNER_P ())
3465     {
3466       /* A class which is local to a block can't be public, private,
3467          protected or static. But it is created final, so allow this
3468          one. */
3469       if (current_function_decl)
3470         icaf = sca = uaaf = ACC_FINAL;
3471       else
3472         {
3473           check_modifiers_consistency (flags);
3474           icaf = ACC_PROTECTED;
3475           if (! CLASS_INTERFACE (GET_CPC ()))
3476             icaf |= ACC_PRIVATE;
3477         }
3478     }
3479
3480   if (is_interface) 
3481     {
3482       if (CPC_INNER_P ())
3483         uaaf = INTERFACE_INNER_MODIFIERS;
3484       else
3485         uaaf = INTERFACE_MODIFIERS;
3486       
3487       check_modifiers ("Illegal modifier `%s' for interface declaration", 
3488                        flags, uaaf);
3489     }
3490   else
3491     check_modifiers ((current_function_decl ?
3492                       "Illegal modifier `%s' for local class declaration" :
3493                       "Illegal modifier `%s' for class declaration"),
3494                      flags, uaaf|sca|icaf);
3495   return 0;
3496 }
3497
3498 static void
3499 make_nested_class_name (cpc_list)
3500      tree cpc_list;
3501 {
3502   tree name;
3503
3504   if (!cpc_list)
3505     return;
3506   else
3507     make_nested_class_name (TREE_CHAIN (cpc_list));
3508
3509   /* Pick the qualified name when dealing with the first upmost
3510      enclosing class */
3511   name = (TREE_CHAIN (cpc_list) ? 
3512           TREE_PURPOSE (cpc_list) : DECL_NAME (TREE_VALUE (cpc_list)));
3513   obstack_grow (&temporary_obstack,
3514                 IDENTIFIER_POINTER (name), IDENTIFIER_LENGTH (name));
3515   obstack_1grow (&temporary_obstack, '$');
3516 }
3517
3518 /* Can't redefine a class already defined in an earlier scope. */
3519
3520 static int
3521 check_inner_class_redefinition (raw_name, cl)
3522      tree raw_name, cl;
3523 {
3524   tree scope_list;
3525
3526   for (scope_list = GET_CPC_LIST (); scope_list; 
3527        scope_list = GET_NEXT_ENCLOSING_CPC (scope_list))
3528     if (raw_name == GET_CPC_UN_NODE (scope_list))
3529       {
3530         parse_error_context 
3531           (cl, "The class name `%s' is already defined in this scope. An inner class may not have the same simple name as any of its enclosing classes",
3532            IDENTIFIER_POINTER (raw_name));
3533         return 1;
3534       }
3535   return 0;
3536 }
3537
3538 /* Tries to find a decl for CLASS_TYPE within ENCLOSING. If we fail,
3539    we remember ENCLOSING and SUPER.  */
3540
3541 static tree
3542 resolve_inner_class (circularity_hash, cl, enclosing, super, class_type)
3543      struct hash_table *circularity_hash;
3544      tree cl, *enclosing, *super, class_type;
3545 {
3546   tree local_enclosing = *enclosing;
3547   tree local_super = NULL_TREE;
3548
3549   while (local_enclosing)
3550     {
3551       tree intermediate, decl;
3552
3553       hash_lookup (circularity_hash, 
3554                    (const  hash_table_key) local_enclosing, TRUE, NULL);
3555
3556       if ((decl = find_as_inner_class (local_enclosing, class_type, cl)))
3557         return decl;
3558
3559       intermediate = local_enclosing;
3560       /* Explore enclosing contexts. */
3561       while (INNER_CLASS_DECL_P (intermediate))
3562         {
3563           intermediate = DECL_CONTEXT (intermediate);
3564           if ((decl = find_as_inner_class (intermediate, class_type, cl)))
3565             return decl;
3566         }
3567
3568       /* Now go to the upper classes, bail out if necessary. We will
3569          analyze the returned SUPER and act accordingly (see
3570          do_resolve_class.) */
3571       local_super = CLASSTYPE_SUPER (TREE_TYPE (local_enclosing));
3572       if (!local_super || local_super == object_type_node)
3573         break;
3574
3575       if (TREE_CODE (local_super) == POINTER_TYPE)
3576         local_super = do_resolve_class (NULL, local_super, NULL, NULL);
3577       else
3578         local_super = TYPE_NAME (local_super);
3579
3580       /* We may not have checked for circular inheritance yet, so do so
3581          here to prevent an infinite loop. */
3582       if (hash_lookup (circularity_hash,
3583                        (const hash_table_key) local_super, FALSE, NULL))
3584         {
3585           if (!cl)
3586             cl = lookup_cl (local_enclosing);
3587           
3588           parse_error_context
3589             (cl, "Cyclic inheritance involving %s",
3590              IDENTIFIER_POINTER (DECL_NAME (local_enclosing)));
3591           local_enclosing = NULL_TREE;
3592         }
3593       else
3594         local_enclosing = local_super;
3595     }
3596
3597   /* We failed. Return LOCAL_SUPER and LOCAL_ENCLOSING. */
3598   *super = local_super;
3599   *enclosing = local_enclosing;
3600
3601   return NULL_TREE;
3602 }
3603
3604 /* Within ENCLOSING, find a decl for NAME and return it. NAME can be
3605    qualified. */
3606
3607 static tree
3608 find_as_inner_class (enclosing, name, cl)
3609      tree enclosing, name, cl;
3610 {
3611   tree qual, to_return;
3612   if (!enclosing)
3613     return NULL_TREE;
3614
3615   name = TYPE_NAME (name);
3616
3617   /* First search: within the scope of `enclosing', search for name */
3618   if (QUALIFIED_P (name) && cl && EXPR_WFL_NODE (cl) == name)
3619     qual = EXPR_WFL_QUALIFICATION (cl);
3620   else if (cl)
3621     qual = build_tree_list (cl, NULL_TREE);
3622   else
3623     qual = build_tree_list (build_expr_wfl (name, NULL, 0, 0), NULL_TREE);
3624   
3625   if ((to_return = find_as_inner_class_do (qual, enclosing)))
3626     return to_return;
3627
3628   /* We're dealing with a qualified name. Try to resolve thing until
3629      we get something that is an enclosing class. */
3630   if (QUALIFIED_P (name) && cl && EXPR_WFL_NODE (cl) == name)
3631     {
3632       tree acc = NULL_TREE, decl = NULL_TREE, ptr;
3633
3634       for (qual = EXPR_WFL_QUALIFICATION (cl); qual && !decl; 
3635            qual = TREE_CHAIN (qual))
3636         {
3637           acc = merge_qualified_name (acc, 
3638                                       EXPR_WFL_NODE (TREE_PURPOSE (qual)));
3639           BUILD_PTR_FROM_NAME (ptr, acc);
3640           decl = do_resolve_class (NULL_TREE, ptr, NULL_TREE, cl);
3641         }
3642
3643       /* A NULL qual and a decl means that the search ended
3644          successfully?!? We have to do something then. FIXME */
3645       
3646       if (decl)
3647         enclosing = decl;
3648       else
3649         qual = EXPR_WFL_QUALIFICATION (cl);
3650     }
3651   /* Otherwise, create a qual for the other part of the resolution. */
3652   else
3653     qual = build_tree_list (build_expr_wfl (name, NULL, 0, 0), NULL_TREE);
3654   
3655   return find_as_inner_class_do (qual, enclosing);
3656 }
3657
3658 /* We go inside the list of sub classes and try to find a way
3659    through. */
3660
3661 static tree
3662 find_as_inner_class_do (qual, enclosing)
3663      tree qual, enclosing;
3664 {
3665   if (!qual)
3666     return NULL_TREE;
3667
3668   for (; qual && enclosing; qual = TREE_CHAIN (qual))
3669     {
3670       tree name_to_match = EXPR_WFL_NODE (TREE_PURPOSE (qual));
3671       tree next_enclosing = NULL_TREE;
3672       tree inner_list;
3673
3674       for (inner_list = DECL_INNER_CLASS_LIST (enclosing);
3675            inner_list; inner_list = TREE_CHAIN (inner_list))
3676         {
3677           if (TREE_VALUE (inner_list) == name_to_match)
3678             {
3679               next_enclosing = TREE_PURPOSE (inner_list);
3680               break;
3681             }
3682         }
3683       enclosing = next_enclosing;
3684     }
3685
3686   return (!qual && enclosing ? enclosing : NULL_TREE);
3687 }
3688
3689 /* Reach all inner classes and tie their unqualified name to a
3690    DECL. */
3691
3692 static void
3693 set_nested_class_simple_name_value (outer, set)
3694      tree outer;
3695      int set;
3696 {
3697   tree l;
3698
3699   for (l = DECL_INNER_CLASS_LIST (outer); l; l = TREE_CHAIN (l))
3700     IDENTIFIER_GLOBAL_VALUE (TREE_VALUE (l)) = (set ? 
3701                                                 TREE_PURPOSE (l) : NULL_TREE);
3702 }
3703
3704 static void
3705 link_nested_class_to_enclosing ()
3706 {
3707   if (GET_ENCLOSING_CPC ())
3708     {
3709       tree enclosing = GET_ENCLOSING_CPC_CONTEXT ();
3710       DECL_INNER_CLASS_LIST (enclosing) = 
3711         tree_cons (GET_CPC (), GET_CPC_UN (),
3712                    DECL_INNER_CLASS_LIST (enclosing));
3713     }
3714 }
3715
3716 static tree
3717 maybe_make_nested_class_name (name)
3718      tree name;
3719 {
3720   tree id = NULL_TREE;
3721
3722   if (CPC_INNER_P ())
3723     {
3724       make_nested_class_name (GET_CPC_LIST ());
3725       obstack_grow0 (&temporary_obstack,
3726                      IDENTIFIER_POINTER (name), 
3727                      IDENTIFIER_LENGTH (name));
3728       id = get_identifier (obstack_finish (&temporary_obstack));
3729       if (ctxp->package)
3730         QUALIFIED_P (id) = 1;
3731     }
3732   return id;
3733 }
3734
3735 /* If DECL is NULL, create and push a new DECL, record the current
3736    line CL and do other maintenance things.  */
3737
3738 static tree
3739 maybe_create_class_interface_decl (decl, raw_name, qualified_name, cl)
3740      tree decl, raw_name, qualified_name, cl;
3741 {
3742   if (!decl)
3743     decl = push_class (make_class (), qualified_name);
3744
3745   /* Take care of the file and line business */
3746   DECL_SOURCE_FILE (decl) = EXPR_WFL_FILENAME (cl);
3747   /* If we're emiting xrefs, store the line/col number information */
3748   if (flag_emit_xref)
3749     DECL_SOURCE_LINE (decl) = EXPR_WFL_LINECOL (cl);
3750   else
3751     DECL_SOURCE_LINE (decl) = EXPR_WFL_LINENO (cl);
3752   CLASS_FROM_SOURCE_P (TREE_TYPE (decl)) = 1;
3753   CLASS_PARSED_P (TREE_TYPE (decl)) = 1;
3754   CLASS_FROM_CURRENTLY_COMPILED_P (TREE_TYPE (decl)) =
3755     IS_A_COMMAND_LINE_FILENAME_P (EXPR_WFL_FILENAME_NODE (cl));
3756
3757   PUSH_CPC (decl, raw_name);
3758   DECL_CONTEXT (decl) = GET_ENCLOSING_CPC_CONTEXT ();
3759
3760   /* Link the declaration to the already seen ones */
3761   TREE_CHAIN (decl) = ctxp->class_list;
3762   ctxp->class_list = decl;
3763
3764   /* Create a new nodes in the global lists */
3765   gclass_list = tree_cons (NULL_TREE, decl, gclass_list);
3766   all_class_list = tree_cons (NULL_TREE, decl, all_class_list);
3767
3768   /* Install a new dependency list element */
3769   create_jdep_list (ctxp);
3770
3771   SOURCE_FRONTEND_DEBUG (("Defining class/interface %s", 
3772                           IDENTIFIER_POINTER (qualified_name)));
3773   return decl;
3774 }
3775
3776 static void
3777 add_superinterfaces (decl, interface_list)
3778      tree decl, interface_list;
3779 {
3780   tree node;
3781   /* Superinterface(s): if present and defined, parser_check_super_interface ()
3782      takes care of ensuring that:
3783        - This is an accessible interface type,
3784        - Circularity detection.
3785    parser_add_interface is then called. If present but not defined,
3786    the check operation is delayed until the super interface gets
3787    defined.  */
3788   for (node = interface_list; node; node = TREE_CHAIN (node))
3789     {
3790       tree current = TREE_PURPOSE (node);
3791       tree idecl = IDENTIFIER_CLASS_VALUE (EXPR_WFL_NODE (current));
3792       if (idecl && CLASS_LOADED_P (TREE_TYPE (idecl)))
3793         {
3794           if (!parser_check_super_interface (idecl, decl, current))
3795             parser_add_interface (decl, idecl, current);
3796         }
3797       else
3798         register_incomplete_type (JDEP_INTERFACE,
3799                                   current, decl, NULL_TREE);
3800     }
3801 }
3802
3803 /* Create an interface in pass1 and return its decl. Return the
3804    interface's decl in pass 2.  */
3805
3806 static tree
3807 create_interface (flags, id, super)
3808      int flags;
3809      tree id, super;
3810 {
3811   tree raw_name = EXPR_WFL_NODE (id);
3812   tree q_name = parser_qualified_classname (raw_name);
3813   tree decl = IDENTIFIER_CLASS_VALUE (q_name);
3814
3815   /* Certain syntax errors are making SUPER be like ID. Avoid this
3816      case. */
3817   if (ctxp->class_err && id == super)
3818     super = NULL;
3819
3820   EXPR_WFL_NODE (id) = q_name;  /* Keep source location, even if refined. */
3821
3822   /* Basic checks: scope, redefinition, modifiers */ 
3823   if (check_class_interface_creation (1, flags, raw_name, q_name, decl, id))
3824     {
3825       PUSH_ERROR ();
3826       return NULL_TREE;
3827     }
3828
3829   /* Suspend the current parsing context if we're parsing an inner
3830      interface */
3831   if (CPC_INNER_P ())
3832     {
3833       java_parser_context_suspend ();
3834       /* Interface members are public. */
3835       if (CLASS_INTERFACE (GET_CPC ()))
3836         flags |= ACC_PUBLIC;
3837     }
3838
3839   /* Push a new context for (static) initialized upon declaration fields */
3840   java_parser_context_push_initialized_field ();
3841
3842   /* Interface modifiers check
3843        - public/abstract allowed (already done at that point)
3844        - abstract is obsolete (comes first, it's a warning, or should be)
3845        - Can't use twice the same (checked in the modifier rule) */
3846   if ((flags & ACC_ABSTRACT) && flag_redundant)
3847     parse_warning_context 
3848       (MODIFIER_WFL (ABSTRACT_TK),
3849        "Redundant use of `abstract' modifier. Interface `%s' is implicitly abstract", IDENTIFIER_POINTER (raw_name));
3850
3851   /* Create a new decl if DECL is NULL, otherwise fix it */
3852   decl = maybe_create_class_interface_decl (decl, raw_name, q_name, id);
3853
3854   /* Set super info and mark the class a complete */
3855   set_super_info (ACC_INTERFACE | flags, TREE_TYPE (decl), 
3856                   object_type_node, ctxp->interface_number);
3857   ctxp->interface_number = 0;
3858   CLASS_COMPLETE_P (decl) = 1;
3859   add_superinterfaces (decl, super);
3860
3861   return decl;
3862 }
3863
3864 /* Anonymous class counter. Will be reset to 1 every time a non
3865    anonymous class gets created. */
3866 static int anonymous_class_counter = 1;
3867
3868 /* Patch anonymous class CLASS, by either extending or implementing
3869    DEP.  */
3870
3871 static void
3872 patch_anonymous_class (type_decl, class_decl, wfl)
3873     tree type_decl, class_decl, wfl;
3874 {
3875   tree class = TREE_TYPE (class_decl);
3876   tree type =  TREE_TYPE (type_decl);
3877   tree binfo = TYPE_BINFO (class);
3878
3879   /* If it's an interface, implement it */
3880   if (CLASS_INTERFACE (type_decl))
3881     {
3882       tree s_binfo;
3883       int length;
3884
3885       if (parser_check_super_interface (type_decl, class_decl, wfl))
3886         return;
3887
3888       s_binfo = TREE_VEC_ELT (BINFO_BASETYPES (TYPE_BINFO (class)), 0);
3889       length = TREE_VEC_LENGTH (TYPE_BINFO_BASETYPES (class))+1;
3890       TYPE_BINFO_BASETYPES (class) = make_tree_vec (length);
3891       TREE_VEC_ELT (BINFO_BASETYPES (TYPE_BINFO (class)), 0) = s_binfo;
3892       /* And add the interface */
3893       parser_add_interface (class_decl, type_decl, wfl);
3894     }
3895   /* Otherwise, it's a type we want to extend */
3896   else
3897     {
3898       if (parser_check_super (type_decl, class_decl, wfl))
3899         return;
3900       BINFO_TYPE (TREE_VEC_ELT (BINFO_BASETYPES (binfo), 0)) = type;
3901     }
3902 }
3903
3904 static tree
3905 create_anonymous_class (location, type_name)
3906     int location;
3907     tree type_name;
3908 {
3909   char buffer [80];
3910   tree super = NULL_TREE, itf = NULL_TREE;
3911   tree id, type_decl, class;
3912
3913   /* The unqualified name of the anonymous class. It's just a number. */
3914   sprintf (buffer, "%d", anonymous_class_counter++);
3915   id = build_wfl_node (get_identifier (buffer));
3916   EXPR_WFL_LINECOL (id) = location;
3917
3918   /* We know about the type to extend/implement. We go ahead */
3919   if ((type_decl = IDENTIFIER_CLASS_VALUE (EXPR_WFL_NODE (type_name))))
3920     {
3921       /* Create a class which either implements on extends the designated
3922          class. The class bears an innacessible name. */
3923       if (CLASS_INTERFACE (type_decl))
3924         {
3925           /* It's OK to modify it here. It's been already used and
3926              shouldn't be reused */
3927           ctxp->interface_number = 1;
3928           /* Interfaces should presented as a list of WFLs */
3929           itf = build_tree_list (type_name, NULL_TREE);
3930         }
3931       else
3932         super = type_name;
3933     }
3934
3935   class = create_class (ACC_FINAL, id, super, itf);
3936
3937   /* We didn't know anything about the stuff. We register a dependence. */
3938   if (!type_decl)
3939     register_incomplete_type (JDEP_ANONYMOUS, type_name, class, NULL_TREE);
3940
3941   ANONYMOUS_CLASS_P (TREE_TYPE (class)) = 1;
3942   return class;
3943 }
3944
3945 /* Create a class in pass1 and return its decl. Return class
3946    interface's decl in pass 2.  */
3947
3948 static tree
3949 create_class (flags, id, super, interfaces)
3950      int flags;
3951      tree id, super, interfaces;
3952 {
3953   tree raw_name = EXPR_WFL_NODE (id);
3954   tree class_id, decl;
3955   tree super_decl_type;
3956
3957   /* Certain syntax errors are making SUPER be like ID. Avoid this
3958      case. */
3959   if (ctxp->class_err && id == super)
3960     super = NULL;
3961
3962   class_id = parser_qualified_classname (raw_name);
3963   decl = IDENTIFIER_CLASS_VALUE (class_id);
3964   EXPR_WFL_NODE (id) = class_id;
3965
3966   /* Basic check: scope, redefinition, modifiers */
3967   if (check_class_interface_creation (0, flags, raw_name, class_id, decl, id))
3968     {
3969       PUSH_ERROR ();
3970       return NULL_TREE;
3971     }
3972   
3973   /* Suspend the current parsing context if we're parsing an inner
3974      class or an anonymous class. */
3975   if (CPC_INNER_P ())
3976     {
3977       java_parser_context_suspend ();
3978       /* Interface members are public. */
3979       if (CLASS_INTERFACE (GET_CPC ()))
3980         flags |= ACC_PUBLIC;
3981     }
3982     
3983   /* Push a new context for (static) initialized upon declaration fields */
3984   java_parser_context_push_initialized_field ();
3985
3986   /* Class modifier check: 
3987        - Allowed modifier (already done at that point)
3988        - abstract AND final forbidden 
3989        - Public classes defined in the correct file */
3990   if ((flags & ACC_ABSTRACT) && (flags & ACC_FINAL))
3991     parse_error_context
3992       (id, "Class `%s' can't be declared both abstract and final",
3993        IDENTIFIER_POINTER (raw_name));
3994
3995   /* Create a new decl if DECL is NULL, otherwise fix it */
3996   decl = maybe_create_class_interface_decl (decl, raw_name, class_id, id);
3997
3998   /* If SUPER exists, use it, otherwise use Object */
3999   if (super)
4000     {
4001       /* Can't extend java.lang.Object */
4002       if (TREE_TYPE (IDENTIFIER_CLASS_VALUE (class_id)) == object_type_node)
4003         {
4004           parse_error_context (id, "Can't extend `java.lang.Object'");
4005           return NULL_TREE;
4006         }
4007
4008       super_decl_type = 
4009         register_incomplete_type (JDEP_SUPER, super, decl, NULL_TREE);
4010     }
4011   else if (TREE_TYPE (decl) != object_type_node)
4012     super_decl_type = object_type_node;
4013   /* We're defining java.lang.Object */
4014   else
4015     super_decl_type = NULL_TREE;
4016
4017   /* A class nested in an interface is implicitly static. */
4018   if (INNER_CLASS_DECL_P (decl)
4019       && CLASS_INTERFACE (TYPE_NAME (TREE_TYPE (DECL_CONTEXT (decl)))))
4020     {
4021       flags |= ACC_STATIC;
4022     }
4023
4024   /* Set super info and mark the class as complete. */
4025   set_super_info (flags, TREE_TYPE (decl), super_decl_type, 
4026                   ctxp->interface_number);
4027   ctxp->interface_number = 0;
4028   CLASS_COMPLETE_P (decl) = 1;
4029   add_superinterfaces (decl, interfaces);
4030
4031   /* Add the private this$<n> field, Replicate final locals still in
4032      scope as private final fields mangled like val$<local_name>.
4033      This doesn't not occur for top level (static) inner classes. */
4034   if (PURE_INNER_CLASS_DECL_P (decl))
4035     add_inner_class_fields (decl, current_function_decl);
4036
4037   /* If doing xref, store the location at which the inherited class
4038      (if any) was seen. */
4039   if (flag_emit_xref && super)
4040     DECL_INHERITED_SOURCE_LINE (decl) = EXPR_WFL_LINECOL (super);
4041
4042   /* Eventually sets the @deprecated tag flag */
4043   CHECK_DEPRECATED (decl);
4044
4045   /* Reset the anonymous class counter when declaring non inner classes */
4046   if (!INNER_CLASS_DECL_P (decl))
4047     anonymous_class_counter = 1;
4048
4049   return decl;
4050 }
4051
4052 /* End a class declaration: register the statements used to create
4053    finit$ and <clinit>, pop the current class and resume the prior
4054    parser context if necessary.  */
4055
4056 static void
4057 end_class_declaration (resume)
4058      int resume;
4059 {
4060   /* If an error occurred, context weren't pushed and won't need to be
4061      popped by a resume. */
4062   int no_error_occurred = ctxp->next && GET_CPC () != error_mark_node;
4063
4064   if (GET_CPC () != error_mark_node)
4065     dump_java_tree (TDI_class, GET_CPC ());
4066
4067   java_parser_context_pop_initialized_field ();
4068   POP_CPC ();
4069   if (resume && no_error_occurred)
4070     java_parser_context_resume ();
4071
4072   /* We're ending a class declaration, this is a good time to reset
4073      the interface cout. Note that might have been already done in
4074      create_interface, but if at that time an inner class was being
4075      dealt with, the interface count was reset in a context created
4076      for the sake of handling inner classes declaration. */
4077   ctxp->interface_number = 0;
4078 }
4079
4080 static void
4081 add_inner_class_fields (class_decl, fct_decl)
4082      tree class_decl;
4083      tree fct_decl;
4084 {
4085   tree block, marker, f;
4086
4087   f = add_field (TREE_TYPE (class_decl),
4088                  build_current_thisn (TREE_TYPE (class_decl)),
4089                  build_pointer_type (TREE_TYPE (DECL_CONTEXT (class_decl))), 
4090                  ACC_PRIVATE);
4091   FIELD_THISN (f) = 1;
4092
4093   if (!fct_decl)
4094     return;
4095     
4096   for (block = GET_CURRENT_BLOCK (fct_decl); 
4097        block && TREE_CODE (block) == BLOCK; block = BLOCK_SUPERCONTEXT (block))
4098     {
4099       tree decl;
4100       for (decl = BLOCK_EXPR_DECLS (block); decl; decl = TREE_CHAIN (decl))
4101         {
4102           tree name, pname;
4103           tree wfl, init, list;
4104           
4105           /* Avoid non final arguments. */
4106           if (!LOCAL_FINAL_P (decl))
4107             continue;
4108           
4109           MANGLE_OUTER_LOCAL_VARIABLE_NAME (name, DECL_NAME (decl));
4110           MANGLE_ALIAS_INITIALIZER_PARAMETER_NAME_ID (pname, DECL_NAME (decl));
4111           wfl = build_wfl_node (name);
4112           init = build_wfl_node (pname);
4113           /* Build an initialization for the field: it will be
4114              initialized by a parameter added to finit$, bearing a
4115              mangled name of the field itself (param$<n>.) The
4116              parameter is provided to finit$ by the constructor
4117              invoking it (hence the constructor will also feature a
4118              hidden parameter, set to the value of the outer context
4119              local at the time the inner class is created.)
4120              
4121              Note: we take into account all possible locals that can
4122              be accessed by the inner class. It's actually not trivial
4123              to minimize these aliases down to the ones really
4124              used. One way to do that would be to expand all regular
4125              methods first, then finit$ to get a picture of what's
4126              used.  It works with the exception that we would have to
4127              go back on all constructor invoked in regular methods to
4128              have their invokation reworked (to include the right amount
4129              of alias initializer parameters.)
4130
4131              The only real way around, I think, is a first pass to
4132              identify locals really used in the inner class. We leave
4133              the flag FIELD_LOCAL_ALIAS_USED around for that future
4134              use.
4135              
4136              On the other hand, it only affect local inner classes,
4137              whose constructors (and finit$ call) will be featuring
4138              unecessary arguments. It's easy for a developper to keep
4139              this number of parameter down by using the `final'
4140              keyword only when necessary. For the time being, we can
4141              issue a warning on unecessary finals. FIXME */
4142           init = build_assignment (ASSIGN_TK, EXPR_WFL_LINECOL (wfl), 
4143                                    wfl, init);
4144
4145           /* Register the field. The TREE_LIST holding the part
4146              initialized/initializer will be marked ARG_FINAL_P so
4147              that the created field can be marked
4148              FIELD_LOCAL_ALIAS. */
4149           list = build_tree_list (wfl, init);
4150           ARG_FINAL_P (list) = 1;
4151           register_fields (ACC_PRIVATE | ACC_FINAL, TREE_TYPE (decl), list);
4152         }
4153     }
4154
4155   if (!CPC_INITIALIZER_STMT (ctxp))
4156     return;
4157
4158   /* If we ever registered an alias field, insert and marker to
4159      remeber where the list ends. The second part of the list (the one
4160      featuring initialized fields) so it can be later reversed to
4161      enforce 8.5. The marker will be removed during that operation. */
4162   marker = build_tree_list (NULL_TREE, NULL_TREE);
4163   TREE_CHAIN (marker) = CPC_INITIALIZER_STMT (ctxp);
4164   SET_CPC_INITIALIZER_STMT (ctxp, marker);
4165 }
4166
4167 /* Can't use lookup_field () since we don't want to load the class and
4168    can't set the CLASS_LOADED_P flag */
4169
4170 static tree
4171 find_field (class, name)
4172      tree class;
4173      tree name;
4174 {
4175   tree decl;
4176   for (decl = TYPE_FIELDS (class); decl; decl = TREE_CHAIN (decl))
4177     {
4178       if (DECL_NAME (decl) == name)
4179         return decl;
4180     }
4181   return NULL_TREE;
4182 }
4183
4184 /* Wrap around lookup_field that doesn't potentially upset the value
4185    of CLASS */
4186
4187 static tree
4188 lookup_field_wrapper (class, name)
4189      tree class, name;
4190 {
4191   tree type = class;
4192   tree decl = NULL_TREE;
4193   java_parser_context_save_global ();
4194
4195   /* Last chance: if we're within the context of an inner class, we
4196      might be trying to access a local variable defined in an outer
4197      context. We try to look for it now. */
4198   if (INNER_CLASS_TYPE_P (class) && TREE_CODE (name) == IDENTIFIER_NODE)
4199     {
4200       tree new_name;
4201       MANGLE_OUTER_LOCAL_VARIABLE_NAME (new_name, name);
4202       decl = lookup_field (&type, new_name);
4203       if (decl && decl != error_mark_node)
4204         FIELD_LOCAL_ALIAS_USED (decl) = 1;
4205     }
4206   if (!decl || decl == error_mark_node)
4207     {
4208       type = class;
4209       decl = lookup_field (&type, name);
4210     }
4211
4212   java_parser_context_restore_global ();
4213   return decl == error_mark_node ? NULL : decl;
4214 }
4215
4216 /* Find duplicate field within the same class declarations and report
4217    the error. Returns 1 if a duplicated field was found, 0
4218    otherwise.  */
4219
4220 static int
4221 duplicate_declaration_error_p (new_field_name, new_type, cl)
4222      tree new_field_name, new_type, cl;
4223 {
4224   /* This might be modified to work with method decl as well */
4225   tree decl = find_field (TREE_TYPE (GET_CPC ()), new_field_name);
4226   if (decl)
4227     {
4228       char *t1 = xstrdup (purify_type_name
4229                          ((TREE_CODE (new_type) == POINTER_TYPE 
4230                            && TREE_TYPE (new_type) == NULL_TREE) ?
4231                           IDENTIFIER_POINTER (TYPE_NAME (new_type)) :
4232                           lang_printable_name (new_type, 1)));
4233       /* The type may not have been completed by the time we report
4234          the error */
4235       char *t2 = xstrdup (purify_type_name
4236                          ((TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE 
4237                            && TREE_TYPE (TREE_TYPE (decl)) == NULL_TREE) ?
4238                           IDENTIFIER_POINTER (TYPE_NAME (TREE_TYPE (decl))) :
4239                           lang_printable_name (TREE_TYPE (decl), 1)));
4240       parse_error_context 
4241         (cl , "Duplicate variable declaration: `%s %s' was `%s %s' (%s:%d)", 
4242          t1, IDENTIFIER_POINTER (new_field_name),
4243          t2, IDENTIFIER_POINTER (DECL_NAME (decl)),
4244          DECL_SOURCE_FILE (decl), DECL_SOURCE_LINE (decl));
4245       free (t1);
4246       free (t2);
4247       return 1;
4248     }
4249   return 0;
4250 }
4251
4252 /* Field registration routine. If TYPE doesn't exist, field
4253    declarations are linked to the undefined TYPE dependency list, to
4254    be later resolved in java_complete_class () */
4255
4256 static void
4257 register_fields (flags, type, variable_list)
4258      int flags;
4259      tree type, variable_list;
4260 {
4261   tree current, saved_type;
4262   tree class_type = NULL_TREE;
4263   int saved_lineno = lineno;
4264   int must_chain = 0;
4265   tree wfl = NULL_TREE;
4266
4267   if (GET_CPC ())
4268     class_type = TREE_TYPE (GET_CPC ());
4269
4270   if (!class_type || class_type == error_mark_node)
4271     return;
4272
4273   /* If we're adding fields to interfaces, those fields are public,
4274      static, final */
4275   if (CLASS_INTERFACE (TYPE_NAME (class_type)))
4276     {
4277       OBSOLETE_MODIFIER_WARNING (MODIFIER_WFL (PUBLIC_TK),
4278                                  flags, ACC_PUBLIC, "interface field(s)");
4279       OBSOLETE_MODIFIER_WARNING (MODIFIER_WFL (STATIC_TK),
4280                                  flags, ACC_STATIC, "interface field(s)");
4281       OBSOLETE_MODIFIER_WARNING (MODIFIER_WFL (FINAL_TK),
4282                                  flags, ACC_FINAL, "interface field(s)");
4283       check_modifiers ("Illegal interface member modifier `%s'", flags,
4284                        INTERFACE_FIELD_MODIFIERS);
4285       flags |= (ACC_PUBLIC | ACC_STATIC | ACC_FINAL);
4286     }
4287
4288   /* Obtain a suitable type for resolution, if necessary */
4289   SET_TYPE_FOR_RESOLUTION (type, wfl, must_chain);
4290
4291   /* If TYPE is fully resolved and we don't have a reference, make one */
4292   PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
4293
4294   for (current = variable_list, saved_type = type; current; 
4295        current = TREE_CHAIN (current), type = saved_type)
4296     {
4297       tree real_type;
4298       tree field_decl;
4299       tree cl = TREE_PURPOSE (current);
4300       tree init = TREE_VALUE (current);
4301       tree current_name = EXPR_WFL_NODE (cl);
4302
4303       /* Can't declare non-final static fields in inner classes */
4304       if ((flags & ACC_STATIC) && !TOPLEVEL_CLASS_TYPE_P (class_type)
4305           && !(flags & ACC_FINAL))
4306         parse_error_context 
4307           (cl, "Field `%s' can't be static in inner class `%s' unless it is final",
4308            IDENTIFIER_POINTER (EXPR_WFL_NODE (cl)),
4309            lang_printable_name (class_type, 0));
4310
4311       /* Process NAME, as it may specify extra dimension(s) for it */
4312       type = build_array_from_name (type, wfl, current_name, &current_name);
4313
4314       /* Type adjustment. We may have just readjusted TYPE because
4315          the variable specified more dimensions. Make sure we have
4316          a reference if we can and don't have one already. Also
4317          change the name if we have an init. */
4318       if (type != saved_type)
4319         {
4320           PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
4321           if (init)
4322             EXPR_WFL_NODE (TREE_OPERAND (init, 0)) = current_name;
4323         }
4324
4325       real_type = GET_REAL_TYPE (type);
4326       /* Check for redeclarations */
4327       if (duplicate_declaration_error_p (current_name, real_type, cl))
4328         continue;
4329
4330       /* Set lineno to the line the field was found and create a
4331          declaration for it. Eventually sets the @deprecated tag flag. */
4332       if (flag_emit_xref)
4333         lineno = EXPR_WFL_LINECOL (cl);
4334       else
4335         lineno = EXPR_WFL_LINENO (cl);
4336       field_decl = add_field (class_type, current_name, real_type, flags);
4337       CHECK_DEPRECATED (field_decl);
4338
4339       /* If the field denotes a final instance variable, then we
4340          allocate a LANG_DECL_SPECIFIC part to keep track of its
4341          initialization. We also mark whether the field was
4342          initialized upon its declaration. We don't do that if the
4343          created field is an alias to a final local. */
4344       if (!ARG_FINAL_P (current) && (flags & ACC_FINAL))
4345         {
4346           MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC (field_decl);
4347           DECL_FIELD_FINAL_WFL (field_decl) = cl;
4348         }
4349
4350       /* If the couple initializer/initialized is marked ARG_FINAL_P,
4351          we mark the created field FIELD_LOCAL_ALIAS, so that we can
4352          hide parameters to this inner class finit$ and
4353          constructors. It also means that the field isn't final per
4354          say. */
4355       if (ARG_FINAL_P (current))
4356         {
4357           FIELD_LOCAL_ALIAS (field_decl) = 1;
4358           FIELD_FINAL (field_decl) = 0;
4359         }
4360       
4361       /* Check if we must chain. */
4362       if (must_chain)
4363         register_incomplete_type (JDEP_FIELD, wfl, field_decl, type);
4364           
4365       /* If we have an initialization value tied to the field */
4366       if (init)
4367         {
4368           /* The field is declared static */
4369           if (flags & ACC_STATIC)
4370             {
4371               /* We include the field and its initialization part into
4372                  a list used to generate <clinit>. After <clinit> is
4373                  walked, field initializations will be processed and
4374                  fields initialized with known constants will be taken
4375                  out of <clinit> and have their DECL_INITIAL set
4376                  appropriately. */
4377               TREE_CHAIN (init) = CPC_STATIC_INITIALIZER_STMT (ctxp);
4378               SET_CPC_STATIC_INITIALIZER_STMT (ctxp, init);
4379               if (TREE_OPERAND (init, 1) 
4380                   && TREE_CODE (TREE_OPERAND (init, 1)) == NEW_ARRAY_INIT)
4381                 TREE_STATIC (TREE_OPERAND (init, 1)) = 1;
4382             }
4383           /* A non-static field declared with an immediate initialization is
4384              to be initialized in <init>, if any.  This field is remembered
4385              to be processed at the time of the generation of <init>. */
4386           else
4387             {
4388               TREE_CHAIN (init) = CPC_INITIALIZER_STMT (ctxp);
4389               SET_CPC_INITIALIZER_STMT (ctxp, init);
4390             }
4391           MODIFY_EXPR_FROM_INITIALIZATION_P (init) = 1;
4392           DECL_INITIAL (field_decl) = TREE_OPERAND (init, 1);
4393         }
4394     }
4395   lineno = saved_lineno;
4396 }
4397
4398 /* Generate finit$, using the list of initialized fields to populate
4399    its body. finit$'s parameter(s) list is adjusted to include the
4400    one(s) used to initialized the field(s) caching outer context
4401    local(s).  */
4402
4403 static tree
4404 generate_finit (class_type)
4405      tree class_type;
4406 {
4407   int count = 0;
4408   tree list = TYPE_FINIT_STMT_LIST (class_type);
4409   tree mdecl, current, parms;
4410
4411   parms = build_alias_initializer_parameter_list (AIPL_FUNCTION_CREATION, 
4412                                                   class_type, NULL_TREE, 
4413                                                   &count);
4414   CRAFTED_PARAM_LIST_FIXUP (parms);
4415   mdecl = create_artificial_method (class_type, ACC_PRIVATE, void_type_node,
4416                                     finit_identifier_node, parms);
4417   fix_method_argument_names (parms, mdecl);
4418   layout_class_method (class_type, CLASSTYPE_SUPER (class_type),
4419                        mdecl, NULL_TREE);
4420   DECL_FUNCTION_NAP (mdecl) = count;
4421   start_artificial_method_body (mdecl);
4422
4423   for (current = list; current; current = TREE_CHAIN (current))
4424     java_method_add_stmt (mdecl, 
4425                           build_debugable_stmt (EXPR_WFL_LINECOL (current), 
4426                                                 current));
4427   end_artificial_method_body (mdecl);
4428   return mdecl;
4429 }
4430
4431 /* Generate a function to run the instance initialization code. The
4432    private method is called `instinit$'. Unless we're dealing with an
4433    anonymous class, we determine whether all ctors of CLASS_TYPE
4434    declare a checked exception in their `throws' clause in order to
4435    see whether it's necessary to encapsulate the instance initializer
4436    statements in a try/catch/rethrow sequence.  */
4437
4438 static tree
4439 generate_instinit (class_type)
4440      tree class_type;
4441 {
4442   tree current;
4443   tree compound = NULL_TREE;
4444   tree parms = tree_cons (this_identifier_node,
4445                           build_pointer_type (class_type), end_params_node);
4446   tree mdecl = create_artificial_method (class_type, ACC_PRIVATE,
4447                                          void_type_node,
4448                                          instinit_identifier_node, parms);
4449
4450   layout_class_method (class_type, CLASSTYPE_SUPER (class_type),
4451                        mdecl, NULL_TREE);
4452
4453   /* Gather all the statements in a compound */
4454   for (current = TYPE_II_STMT_LIST (class_type); 
4455        current; current = TREE_CHAIN (current))
4456     compound = add_stmt_to_compound (compound, NULL_TREE, current);
4457
4458   /* We need to encapsulate COMPOUND by a try/catch statement to
4459      rethrow exceptions that might occur in the instance initializer.
4460      We do that only if all ctors of CLASS_TYPE are set to catch a
4461      checked exception. This doesn't apply to anonymous classes (since
4462      they don't have declared ctors.) */
4463   if (!ANONYMOUS_CLASS_P (class_type) && 
4464       ctors_unchecked_throws_clause_p (class_type))
4465     {
4466       compound = encapsulate_with_try_catch (0, exception_type_node, compound, 
4467                                              build1 (THROW_EXPR, NULL_TREE,
4468                                                      build_wfl_node (wpv_id)));
4469       DECL_FUNCTION_THROWS (mdecl) = build_tree_list (NULL_TREE,
4470                                                       exception_type_node);
4471     }
4472
4473   start_artificial_method_body (mdecl);
4474   java_method_add_stmt (mdecl, compound);
4475   end_artificial_method_body (mdecl);
4476
4477   return mdecl;
4478 }
4479
4480 /* FIXME */
4481 static tree
4482 build_instinit_invocation (class_type)
4483      tree class_type;
4484 {
4485   tree to_return = NULL_TREE;
4486
4487   if (TYPE_II_STMT_LIST (class_type))
4488     {
4489       tree parm = build_tree_list (NULL_TREE,
4490                                    build_wfl_node (this_identifier_node));
4491       to_return =
4492         build_method_invocation (build_wfl_node (instinit_identifier_node),
4493                                  parm);
4494     }
4495   return to_return;
4496 }
4497
4498 /* Shared accros method_declarator and method_header to remember the
4499    patch stage that was reached during the declaration of the method.
4500    A method DECL is built differently is there is no patch
4501    (JDEP_NO_PATCH) or a patch (JDEP_METHOD or JDEP_METHOD_RETURN)
4502    pending on the currently defined method.  */
4503
4504 static int patch_stage;
4505
4506 /* Check the method declaration and add the method to its current
4507    class.  If the argument list is known to contain incomplete types,
4508    the method is partially added and the registration will be resume
4509    once the method arguments resolved. If TYPE is NULL, we're dealing
4510    with a constructor.  */
4511
4512 static tree
4513 method_header (flags, type, mdecl, throws)
4514      int flags;
4515      tree type, mdecl, throws;
4516 {
4517   tree type_wfl = NULL_TREE;
4518   tree meth_name = NULL_TREE;
4519   tree current, orig_arg, this_class = NULL;
4520   tree id, meth;
4521   int saved_lineno;
4522   int constructor_ok = 0, must_chain;
4523   int count;
4524
4525   if (mdecl == error_mark_node)
4526     return error_mark_node;
4527   meth = TREE_VALUE (mdecl);
4528   id = TREE_PURPOSE (mdecl);
4529   
4530   check_modifiers_consistency (flags);
4531
4532   if (GET_CPC ())
4533     this_class = TREE_TYPE (GET_CPC ());
4534
4535   if (!this_class || this_class == error_mark_node)
4536     return NULL_TREE;
4537   
4538   /* There are some forbidden modifiers for an abstract method and its
4539      class must be abstract as well.  */
4540   if (type && (flags & ACC_ABSTRACT))
4541     {
4542       ABSTRACT_CHECK (flags, ACC_PRIVATE, id, "Private");
4543       ABSTRACT_CHECK (flags, ACC_STATIC, id, "Static");
4544       ABSTRACT_CHECK (flags, ACC_FINAL, id, "Final");
4545       ABSTRACT_CHECK (flags, ACC_NATIVE, id, "Native");
4546       ABSTRACT_CHECK (flags, ACC_SYNCHRONIZED, id, "Synchronized");
4547       ABSTRACT_CHECK (flags, ACC_STRICT, id, "Strictfp");
4548       if (!CLASS_ABSTRACT (TYPE_NAME (this_class))
4549           && !CLASS_INTERFACE (TYPE_NAME (this_class)))
4550         parse_error_context 
4551           (id, "Class `%s' must be declared abstract to define abstract method `%s'", 
4552            IDENTIFIER_POINTER (DECL_NAME (GET_CPC ())),
4553            IDENTIFIER_POINTER (EXPR_WFL_NODE (id)));
4554     }
4555
4556   /* Things to be checked when declaring a constructor */
4557   if (!type)
4558     {
4559       int ec = java_error_count;
4560       /* 8.6: Constructor declarations: we might be trying to define a
4561          method without specifying a return type. */
4562       if (EXPR_WFL_NODE (id) != GET_CPC_UN ())
4563         parse_error_context 
4564           (id, "Invalid method declaration, return type required");
4565       /* 8.6.3: Constructor modifiers */
4566       else
4567         {
4568           JCONSTRUCTOR_CHECK (flags, ACC_ABSTRACT, id, "abstract");
4569           JCONSTRUCTOR_CHECK (flags, ACC_STATIC, id, "static");
4570           JCONSTRUCTOR_CHECK (flags, ACC_FINAL, id, "final");
4571           JCONSTRUCTOR_CHECK (flags, ACC_NATIVE, id, "native");
4572           JCONSTRUCTOR_CHECK (flags, ACC_SYNCHRONIZED, id, "synchronized");
4573           JCONSTRUCTOR_CHECK (flags, ACC_STRICT, id, "strictfp");
4574         }
4575       /* If we found error here, we don't consider it's OK to tread
4576          the method definition as a constructor, for the rest of this
4577          function */
4578       if (ec == java_error_count)
4579         constructor_ok = 1;
4580     }
4581
4582   /* Method declared within the scope of an interface are implicitly
4583      abstract and public. Conflicts with other erroneously provided
4584      modifiers are checked right after. */
4585
4586   if (CLASS_INTERFACE (TYPE_NAME (this_class)))
4587     {
4588       /* If FLAGS isn't set because of a modifier, turn the
4589          corresponding modifier WFL to NULL so we issue a warning on
4590          the obsolete use of the modifier */
4591       if (!(flags & ACC_PUBLIC))
4592         MODIFIER_WFL (PUBLIC_TK) = NULL;
4593       if (!(flags & ACC_ABSTRACT))
4594         MODIFIER_WFL (ABSTRACT_TK) = NULL;
4595       flags |= ACC_PUBLIC;
4596       flags |= ACC_ABSTRACT;
4597     }
4598
4599   /* Inner class can't declare static methods */
4600   if ((flags & ACC_STATIC) && !TOPLEVEL_CLASS_TYPE_P (this_class))
4601     {
4602       parse_error_context 
4603         (id, "Method `%s' can't be static in inner class `%s'. Only members of interfaces and top-level classes can be static",
4604          IDENTIFIER_POINTER (EXPR_WFL_NODE (id)),
4605          lang_printable_name (this_class, 0));
4606     }
4607
4608   /* Modifiers context reset moved up, so abstract method declaration
4609      modifiers can be later checked.  */
4610
4611   /* Set constructor returned type to void and method name to <init>,
4612      unless we found an error identifier the constructor (in which
4613      case we retain the original name) */
4614   if (!type)
4615     {
4616       type = void_type_node;
4617       if (constructor_ok)
4618         meth_name = init_identifier_node;
4619     }
4620   else
4621     meth_name = EXPR_WFL_NODE (id);
4622
4623   /* Do the returned type resolution and registration if necessary */
4624   SET_TYPE_FOR_RESOLUTION (type, type_wfl, must_chain);
4625
4626   if (meth_name)
4627     type = build_array_from_name (type, type_wfl, meth_name, &meth_name);
4628   EXPR_WFL_NODE (id) = meth_name;
4629   PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
4630
4631   if (must_chain)
4632     {
4633       patch_stage = JDEP_METHOD_RETURN;
4634       register_incomplete_type (patch_stage, type_wfl, id, type);
4635       TREE_TYPE (meth) = GET_REAL_TYPE (type);
4636     }
4637   else
4638     TREE_TYPE (meth) = type;
4639
4640   saved_lineno = lineno;
4641   /* When defining an abstract or interface method, the curly
4642      bracket at level 1 doesn't exist because there is no function
4643      body */
4644   lineno = (ctxp->first_ccb_indent1 ? ctxp->first_ccb_indent1 : 
4645             EXPR_WFL_LINENO (id));
4646
4647   /* Remember the original argument list */
4648   orig_arg = TYPE_ARG_TYPES (meth);
4649
4650   if (patch_stage)              /* includes ret type and/or all args */
4651     {
4652       jdep *jdep;
4653       meth = add_method_1 (this_class, flags, meth_name, meth);
4654       /* Patch for the return type */
4655       if (patch_stage == JDEP_METHOD_RETURN)
4656         {
4657           jdep = CLASSD_LAST (ctxp->classd_list);
4658           JDEP_GET_PATCH (jdep) = &TREE_TYPE (TREE_TYPE (meth));
4659         }
4660       /* This is the stop JDEP. METH allows the function's signature
4661          to be computed. */
4662       register_incomplete_type (JDEP_METHOD_END, NULL_TREE, meth, NULL_TREE);
4663     }
4664   else
4665     meth = add_method (this_class, flags, meth_name, 
4666                        build_java_signature (meth));
4667
4668   /* Remember final parameters */
4669   MARK_FINAL_PARMS (meth, orig_arg);
4670
4671   /* Fix the method argument list so we have the argument name
4672      information */
4673   fix_method_argument_names (orig_arg, meth);
4674
4675   /* Register the parameter number and re-install the current line
4676      number */
4677   DECL_MAX_LOCALS (meth) = ctxp->formal_parameter_number+1;
4678   lineno = saved_lineno;
4679
4680   /* Register exception specified by the `throws' keyword for
4681      resolution and set the method decl appropriate field to the list.
4682      Note: the grammar ensures that what we get here are class
4683      types. */
4684   if (throws)
4685     {
4686       throws = nreverse (throws);
4687       for (current = throws; current; current = TREE_CHAIN (current))
4688         {
4689           register_incomplete_type (JDEP_EXCEPTION, TREE_VALUE (current),
4690                                     NULL_TREE, NULL_TREE);
4691           JDEP_GET_PATCH (CLASSD_LAST (ctxp->classd_list)) = 
4692             &TREE_VALUE (current);
4693         }
4694       DECL_FUNCTION_THROWS (meth) = throws;
4695     }
4696
4697   if (TREE_TYPE (GET_CPC ()) != object_type_node)
4698     DECL_FUNCTION_WFL (meth) = id;
4699
4700   /* Set the flag if we correctly processed a constructor */
4701   if (constructor_ok)
4702     {
4703       DECL_CONSTRUCTOR_P (meth) = 1;
4704       /* Compute and store the number of artificial parameters declared
4705          for this constructor */
4706       for (count = 0, current = TYPE_FIELDS (this_class); current; 
4707            current = TREE_CHAIN (current))
4708         if (FIELD_LOCAL_ALIAS (current))
4709           count++;
4710       DECL_FUNCTION_NAP (meth) = count;
4711     }
4712
4713   /* Eventually set the @deprecated tag flag */
4714   CHECK_DEPRECATED (meth);
4715
4716   /* If doing xref, store column and line number information instead
4717      of the line number only. */
4718   if (flag_emit_xref)
4719     DECL_SOURCE_LINE (meth) = EXPR_WFL_LINECOL (id);
4720
4721   return meth;
4722 }
4723
4724 static void
4725 fix_method_argument_names (orig_arg, meth)
4726     tree orig_arg, meth;
4727 {
4728   tree arg = TYPE_ARG_TYPES (TREE_TYPE (meth));
4729   if (TREE_CODE (TREE_TYPE (meth)) == METHOD_TYPE)
4730     {
4731       TREE_PURPOSE (arg) = this_identifier_node;
4732       arg = TREE_CHAIN (arg);
4733     }
4734   while (orig_arg != end_params_node)
4735     {
4736       TREE_PURPOSE (arg) = TREE_PURPOSE (orig_arg);
4737       orig_arg = TREE_CHAIN (orig_arg);
4738       arg = TREE_CHAIN (arg);
4739     }
4740 }
4741
4742 /* Complete the method declaration with METHOD_BODY.  */
4743
4744 static void
4745 finish_method_declaration (method_body)
4746      tree method_body;
4747 {
4748   int flags;
4749
4750   if (!current_function_decl)
4751     return;
4752
4753   flags = get_access_flags_from_decl (current_function_decl);
4754
4755   /* 8.4.5 Method Body */
4756   if ((flags & ACC_ABSTRACT || flags & ACC_NATIVE) && method_body)
4757     {
4758       tree name = DECL_NAME (current_function_decl);
4759       parse_error_context (DECL_FUNCTION_WFL (current_function_decl), 
4760                            "%s method `%s' can't have a body defined",
4761                            (METHOD_NATIVE (current_function_decl) ?
4762                             "Native" : "Abstract"),
4763                            IDENTIFIER_POINTER (name));
4764       method_body = NULL_TREE;
4765     }
4766   else if (!(flags & ACC_ABSTRACT) && !(flags & ACC_NATIVE) && !method_body)
4767     {
4768       tree name = DECL_NAME (current_function_decl);
4769       parse_error_context
4770         (DECL_FUNCTION_WFL (current_function_decl), 
4771          "Non native and non abstract method `%s' must have a body defined",
4772          IDENTIFIER_POINTER (name));
4773       method_body = NULL_TREE;
4774     }
4775
4776   if (flag_emit_class_files && method_body 
4777       && TREE_CODE (method_body) == NOP_EXPR 
4778       && TREE_TYPE (current_function_decl) 
4779       && TREE_TYPE (TREE_TYPE (current_function_decl)) == void_type_node)
4780     method_body = build1 (RETURN_EXPR, void_type_node, NULL);
4781
4782   BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (current_function_decl)) = method_body;
4783   maybe_absorb_scoping_blocks ();
4784   /* Exit function's body */
4785   exit_block ();
4786   /* Merge last line of the function with first line, directly in the
4787      function decl. It will be used to emit correct debug info. */
4788   if (!flag_emit_xref)
4789     DECL_SOURCE_LINE_MERGE (current_function_decl, ctxp->last_ccb_indent1);
4790
4791   /* Since function's argument's list are shared, reset the
4792      ARG_FINAL_P parameter that might have been set on some of this
4793      function parameters. */
4794   UNMARK_FINAL_PARMS (current_function_decl);
4795   
4796   /* So we don't have an irrelevant function declaration context for
4797      the next static block we'll see. */
4798   current_function_decl = NULL_TREE;
4799 }
4800
4801 /* Build a an error message for constructor circularity errors.  */
4802
4803 static char *
4804 constructor_circularity_msg (from, to)
4805      tree from, to;
4806 {
4807   static char string [4096];
4808   char *t = xstrdup (lang_printable_name (from, 0));
4809   sprintf (string, "`%s' invokes `%s'", t, lang_printable_name (to, 0));
4810   free (t);
4811   return string;
4812 }
4813
4814 /* Verify a circular call to METH. Return 1 if an error is found, 0
4815    otherwise.  */
4816
4817 static int
4818 verify_constructor_circularity (meth, current)
4819      tree meth, current;
4820 {
4821   static tree list = NULL_TREE;
4822   static int initialized_p;
4823   tree c;
4824
4825   /* If we haven't already registered LIST with the garbage collector,
4826      do so now.  */
4827   if (!initialized_p)
4828     {
4829       ggc_add_tree_root (&list, 1);
4830       initialized_p = 1;
4831     }
4832
4833   for (c = DECL_CONSTRUCTOR_CALLS (current); c; c = TREE_CHAIN (c))
4834     {
4835       if (TREE_VALUE (c) == meth)
4836         {
4837           char *t;
4838           if (list)
4839             {
4840               tree liste;
4841               list = nreverse (list);
4842               for (liste = list; liste; liste = TREE_CHAIN (liste))
4843                 {
4844                   parse_error_context 
4845                     (TREE_PURPOSE (TREE_PURPOSE (liste)), "%s",
4846                      constructor_circularity_msg
4847                       (TREE_VALUE (liste), TREE_VALUE (TREE_PURPOSE (liste)))); 
4848                   java_error_count--;
4849                 }
4850             }
4851           t = xstrdup (lang_printable_name (meth, 0));
4852           parse_error_context (TREE_PURPOSE (c), 
4853                                "%s: recursive invocation of constructor `%s'",
4854                                constructor_circularity_msg (current, meth), t);
4855           free (t);
4856           list = NULL_TREE;
4857           return 1;
4858         }
4859     }
4860   for (c = DECL_CONSTRUCTOR_CALLS (current); c; c = TREE_CHAIN (c))
4861     {
4862       list = tree_cons (c, current, list);
4863       if (verify_constructor_circularity (meth, TREE_VALUE (c)))
4864         return 1;
4865       list = TREE_CHAIN (list);
4866     }
4867   return 0;
4868 }
4869
4870 /* Check modifiers that can be declared but exclusively */
4871
4872 static void
4873 check_modifiers_consistency (flags)
4874      int flags;
4875 {
4876   int acc_count = 0;
4877   tree cl = NULL_TREE;
4878
4879   THIS_MODIFIER_ONLY (flags, ACC_PUBLIC, PUBLIC_TK, acc_count, cl);
4880   THIS_MODIFIER_ONLY (flags, ACC_PRIVATE, PRIVATE_TK, acc_count, cl);
4881   THIS_MODIFIER_ONLY (flags, ACC_PROTECTED, PROTECTED_TK, acc_count, cl);
4882   if (acc_count > 1)
4883     parse_error_context
4884       (cl, "Inconsistent member declaration.  At most one of `public', `private', or `protected' may be specified");
4885
4886   acc_count = 0;
4887   cl = NULL_TREE;
4888   THIS_MODIFIER_ONLY (flags, ACC_FINAL, FINAL_TK, acc_count, cl);
4889   THIS_MODIFIER_ONLY (flags, ACC_VOLATILE, VOLATILE_TK, acc_count, cl);
4890   if (acc_count > 1)
4891     parse_error_context (cl,
4892                          "Inconsistent member declaration.  At most one of `final' or `volatile' may be specified");
4893 }
4894
4895 /* Check the methode header METH for abstract specifics features */
4896
4897 static void
4898 check_abstract_method_header (meth)
4899      tree meth;
4900 {
4901   int flags = get_access_flags_from_decl (meth);
4902
4903   OBSOLETE_MODIFIER_WARNING2 (MODIFIER_WFL (ABSTRACT_TK), flags,
4904                               ACC_ABSTRACT, "abstract method",
4905                               IDENTIFIER_POINTER (DECL_NAME (meth)));
4906   OBSOLETE_MODIFIER_WARNING2 (MODIFIER_WFL (PUBLIC_TK), flags, 
4907                               ACC_PUBLIC, "abstract method",
4908                               IDENTIFIER_POINTER (DECL_NAME (meth)));
4909
4910   check_modifiers ("Illegal modifier `%s' for interface method",
4911                   flags, INTERFACE_METHOD_MODIFIERS);
4912 }
4913
4914 /* Create a FUNCTION_TYPE node and start augmenting it with the
4915    declared function arguments. Arguments type that can't be resolved
4916    are left as they are, but the returned node is marked as containing
4917    incomplete types.  */
4918
4919 static tree
4920 method_declarator (id, list)
4921      tree id, list;
4922 {
4923   tree arg_types = NULL_TREE, current, node;
4924   tree meth = make_node (FUNCTION_TYPE);
4925   jdep *jdep;
4926
4927   patch_stage = JDEP_NO_PATCH;
4928
4929   if (GET_CPC () == error_mark_node)
4930     return error_mark_node;
4931
4932   /* If we're dealing with an inner class constructor, we hide the
4933      this$<n> decl in the name field of its parameter declaration.  We
4934      also might have to hide the outer context local alias
4935      initializers. Not done when the class is a toplevel class. */
4936   if (PURE_INNER_CLASS_DECL_P (GET_CPC ()) 
4937       && EXPR_WFL_NODE (id) == GET_CPC_UN ())
4938     {
4939       tree aliases_list, type, thisn;
4940       /* First the aliases, linked to the regular parameters */
4941       aliases_list =
4942         build_alias_initializer_parameter_list (AIPL_FUNCTION_DECLARATION, 
4943                                                 TREE_TYPE (GET_CPC ()),
4944                                                 NULL_TREE, NULL);
4945       list = chainon (nreverse (aliases_list), list);
4946
4947       /* Then this$<n> */
4948       type = TREE_TYPE (DECL_CONTEXT (GET_CPC ()));
4949       thisn = build_current_thisn (TREE_TYPE (GET_CPC ()));
4950       list = tree_cons (build_wfl_node (thisn), build_pointer_type (type),
4951                         list);
4952     }
4953   
4954   for (current = list; current; current = TREE_CHAIN (current))
4955     {
4956       int must_chain = 0;
4957       tree wfl_name = TREE_PURPOSE (current);
4958       tree type = TREE_VALUE (current);
4959       tree name = EXPR_WFL_NODE (wfl_name);
4960       tree already, arg_node;
4961       tree type_wfl = NULL_TREE;
4962       tree real_type;
4963
4964       /* Obtain a suitable type for resolution, if necessary */
4965       SET_TYPE_FOR_RESOLUTION (type, type_wfl, must_chain);
4966
4967       /* Process NAME, as it may specify extra dimension(s) for it */
4968       type = build_array_from_name (type, type_wfl, name, &name);
4969       EXPR_WFL_NODE (wfl_name) = name;
4970
4971       real_type = GET_REAL_TYPE (type);
4972       if (TREE_CODE (real_type) == RECORD_TYPE)
4973         {
4974           real_type = promote_type (real_type);
4975           if (TREE_CODE (type) == TREE_LIST)
4976             TREE_PURPOSE (type) = real_type;
4977         }
4978
4979       /* Check redefinition */
4980       for (already = arg_types; already; already = TREE_CHAIN (already))
4981         if (TREE_PURPOSE (already) == name)
4982           {
4983             parse_error_context
4984               (wfl_name, "Variable `%s' is used more than once in the argument list of method `%s'",
4985                IDENTIFIER_POINTER (name),
4986                IDENTIFIER_POINTER (EXPR_WFL_NODE (id)));
4987             break;
4988           }
4989
4990       /* If we've an incomplete argument type, we know there is a location
4991          to patch when the type get resolved, later.  */
4992       jdep = NULL;
4993       if (must_chain)
4994         {
4995           patch_stage = JDEP_METHOD;
4996           type = register_incomplete_type (patch_stage, 
4997                                            type_wfl, wfl_name, type);
4998           jdep = CLASSD_LAST (ctxp->classd_list);
4999           JDEP_MISC (jdep) = id;
5000         }
5001
5002       /* The argument node: a name and a (possibly) incomplete type.  */
5003       arg_node = build_tree_list (name, real_type);
5004       /* Remeber arguments declared final. */
5005       ARG_FINAL_P (arg_node) = ARG_FINAL_P (current);
5006       
5007       if (jdep)
5008         JDEP_GET_PATCH (jdep) = &TREE_VALUE (arg_node);
5009       TREE_CHAIN (arg_node) = arg_types;
5010       arg_types = arg_node;
5011     }
5012   TYPE_ARG_TYPES (meth) = chainon (nreverse (arg_types), end_params_node);
5013   node = build_tree_list (id, meth);
5014   return node;
5015 }
5016
5017 static int
5018 unresolved_type_p (wfl, returned)
5019      tree wfl;
5020      tree *returned;
5021      
5022 {
5023   if (TREE_CODE (wfl) == EXPR_WITH_FILE_LOCATION)
5024     {
5025       if (returned)
5026         {
5027           tree decl = IDENTIFIER_CLASS_VALUE (EXPR_WFL_NODE (wfl));
5028           if (decl && current_class && (decl == TYPE_NAME (current_class)))
5029             *returned = TREE_TYPE (decl);
5030           else if (GET_CPC_UN () == EXPR_WFL_NODE (wfl))
5031             *returned = TREE_TYPE (GET_CPC ());
5032           else
5033             *returned = NULL_TREE;
5034         }
5035       return 1;
5036     }
5037   if (returned)
5038     *returned = wfl;
5039   return 0;
5040 }
5041
5042 /* From NAME, build a qualified identifier node using the
5043    qualification from the current package definition. */
5044
5045 static tree
5046 parser_qualified_classname (name)
5047      tree name;
5048 {
5049   tree nested_class_name;
5050
5051   if ((nested_class_name = maybe_make_nested_class_name (name)))
5052     return nested_class_name;
5053
5054   if (ctxp->package)
5055     return merge_qualified_name (ctxp->package, name);
5056   else 
5057     return name;
5058 }
5059
5060 /* Called once the type a interface extends is resolved. Returns 0 if
5061    everything is OK.  */
5062
5063 static int
5064 parser_check_super_interface (super_decl, this_decl, this_wfl)
5065      tree super_decl, this_decl, this_wfl;
5066 {
5067   tree super_type = TREE_TYPE (super_decl);
5068
5069   /* Has to be an interface */
5070   if (!CLASS_INTERFACE (super_decl))
5071     {
5072       parse_error_context 
5073         (this_wfl, "Can't use %s `%s' to implement/extend %s `%s'",
5074          (TYPE_ARRAY_P (super_type) ? "array" : "class"),
5075          IDENTIFIER_POINTER (DECL_NAME (super_decl)),
5076          (CLASS_INTERFACE (TYPE_NAME (TREE_TYPE (this_decl))) ? 
5077           "interface" : "class"),
5078          IDENTIFIER_POINTER (DECL_NAME (this_decl)));
5079       return 1;
5080     }
5081
5082   /* Check top-level interface access. Inner classes are subject to member 
5083      access rules (6.6.1). */
5084   if (! INNER_CLASS_P (super_type)
5085       && check_pkg_class_access (DECL_NAME (super_decl),
5086                                  lookup_cl (this_decl), true))
5087     return 1;
5088
5089   SOURCE_FRONTEND_DEBUG (("Completing interface %s with %s",
5090                           IDENTIFIER_POINTER (DECL_NAME (this_decl)),
5091                           IDENTIFIER_POINTER (DECL_NAME (super_decl))));
5092   return 0;
5093 }
5094
5095 /* Makes sure that SUPER_DECL is suitable to extend THIS_DECL. Returns
5096    0 if everthing is OK.  */
5097
5098 static int
5099 parser_check_super (super_decl, this_decl, wfl)
5100      tree super_decl, this_decl, wfl;
5101 {
5102   tree super_type = TREE_TYPE (super_decl);
5103
5104   /* SUPER should be a CLASS (neither an array nor an interface) */
5105   if (TYPE_ARRAY_P (super_type) || CLASS_INTERFACE (TYPE_NAME (super_type)))
5106     {
5107       parse_error_context 
5108         (wfl, "Class `%s' can't subclass %s `%s'",
5109          IDENTIFIER_POINTER (DECL_NAME (this_decl)),
5110          (CLASS_INTERFACE (TYPE_NAME (super_type)) ? "interface" : "array"),
5111          IDENTIFIER_POINTER (DECL_NAME (super_decl)));
5112       return 1;
5113     }
5114
5115   if (CLASS_FINAL (TYPE_NAME (super_type)))
5116     {
5117       parse_error_context (wfl, "Can't subclass final classes: %s",
5118                            IDENTIFIER_POINTER (DECL_NAME (super_decl)));
5119       return 1;
5120     }
5121
5122   /* Check top-level class scope. Inner classes are subject to member access
5123      rules (6.6.1). */
5124   if (! INNER_CLASS_P (super_type)
5125       && (check_pkg_class_access (DECL_NAME (super_decl), wfl, true)))
5126     return 1;
5127   
5128   SOURCE_FRONTEND_DEBUG (("Completing class %s with %s",
5129                           IDENTIFIER_POINTER (DECL_NAME (this_decl)),
5130                           IDENTIFIER_POINTER (DECL_NAME (super_decl))));
5131   return 0;
5132 }
5133
5134 /* Create a new dependency list and link it (in a LIFO manner) to the
5135    CTXP list of type dependency list.  */
5136
5137 static void
5138 create_jdep_list (ctxp)
5139      struct parser_ctxt *ctxp;
5140 {
5141   jdeplist *new = (jdeplist *)xmalloc (sizeof (jdeplist));      
5142   new->first = new->last = NULL;
5143   new->next = ctxp->classd_list;
5144   ctxp->classd_list = new;
5145 }
5146
5147 static jdeplist *
5148 reverse_jdep_list (ctxp)
5149      struct parser_ctxt *ctxp;
5150 {
5151   register jdeplist *prev = NULL, *current, *next;
5152   for (current = ctxp->classd_list; current; current = next)
5153     {
5154       next = current->next;
5155       current->next = prev;
5156       prev = current;
5157     }
5158   return prev;
5159 }
5160
5161 /* Create a fake pointer based on the ID stored in
5162    TYPE_NAME. TYPE_NAME can be a WFL or a incomplete type asking to be
5163    registered again. */
5164
5165 static tree
5166 obtain_incomplete_type (type_name)
5167      tree type_name;
5168 {
5169   tree ptr = NULL_TREE, name;
5170
5171   if (TREE_CODE (type_name) == EXPR_WITH_FILE_LOCATION)
5172     name = EXPR_WFL_NODE (type_name);
5173   else if (INCOMPLETE_TYPE_P (type_name))
5174     name = TYPE_NAME (type_name);
5175   else
5176     abort ();
5177
5178   BUILD_PTR_FROM_NAME (ptr, name);
5179   layout_type (ptr);
5180
5181   return ptr;
5182 }
5183
5184 /* Register a incomplete type whose name is WFL. Reuse PTR if PTR is
5185    non NULL instead of computing a new fake type based on WFL. The new
5186    dependency is inserted in the current type dependency list, in FIFO
5187    manner.  */
5188
5189 static tree
5190 register_incomplete_type (kind, wfl, decl, ptr)
5191      int kind;
5192      tree wfl, decl, ptr;
5193 {
5194   jdep *new = (jdep *)xmalloc (sizeof (jdep));
5195
5196   if (!ptr && kind != JDEP_METHOD_END) /* JDEP_METHOD_END is a mere marker */
5197     ptr = obtain_incomplete_type (wfl);
5198
5199   JDEP_KIND (new) = kind;
5200   JDEP_DECL (new) = decl;
5201   JDEP_TO_RESOLVE (new) = ptr;
5202   JDEP_WFL (new) = wfl;
5203   JDEP_CHAIN (new) = NULL;
5204   JDEP_MISC (new) = NULL_TREE;
5205   /* For some dependencies, set the enclosing class of the current
5206      class to be the enclosing context */
5207   if ((kind == JDEP_INTERFACE  || kind == JDEP_ANONYMOUS)
5208       && GET_ENCLOSING_CPC ())
5209     JDEP_ENCLOSING (new) = TREE_VALUE (GET_ENCLOSING_CPC ());
5210   else if (kind == JDEP_SUPER)
5211     JDEP_ENCLOSING (new) = (GET_ENCLOSING_CPC () ? 
5212                             TREE_VALUE (GET_ENCLOSING_CPC ()) : NULL_TREE);
5213   else
5214     JDEP_ENCLOSING (new) = GET_CPC ();
5215   JDEP_GET_PATCH (new) = (tree *)NULL;
5216
5217   JDEP_INSERT (ctxp->classd_list, new);
5218
5219   return ptr;
5220 }
5221
5222 /* This checks for circular references with innerclasses. We start
5223    from SOURCE and should never reach TARGET. Extended/implemented
5224    types in SOURCE have their enclosing context checked not to reach
5225    TARGET. When the last enclosing context of SOURCE is reached, its
5226    extended/implemented types are also checked not to reach TARGET.
5227    In case of error, WFL of the offending type is returned; NULL_TREE
5228    otherwise.  */
5229
5230 static tree
5231 check_inner_circular_reference (source, target)
5232      tree source;
5233      tree target;
5234 {
5235   tree basetype_vec = TYPE_BINFO_BASETYPES (source);
5236   tree ctx, cl;
5237   int i;
5238
5239   if (!basetype_vec)
5240     return NULL_TREE;
5241   
5242   for (i = 0; i < TREE_VEC_LENGTH (basetype_vec); i++)
5243     {
5244       tree su = BINFO_TYPE (TREE_VEC_ELT (basetype_vec, i));
5245
5246       if (inherits_from_p (su, target))
5247         return lookup_cl (TYPE_NAME (su));
5248       
5249       for (ctx = DECL_CONTEXT (TYPE_NAME (su)); ctx; ctx = DECL_CONTEXT (ctx))
5250         {
5251           /* An enclosing context shouldn't be TARGET */
5252           if (ctx == TYPE_NAME (target))
5253             return lookup_cl (TYPE_NAME (su));
5254
5255           /* When we reach the enclosing last context, start a check
5256              on it, with the same target */
5257           if (! DECL_CONTEXT (ctx) &&
5258               (cl = check_inner_circular_reference (TREE_TYPE (ctx), target)))
5259             return cl;
5260         }
5261     }
5262   return NULL_TREE;
5263 }
5264
5265 /* Explore TYPE's `extends' clause member(s) and return the WFL of the
5266    offending type if a circularity is detected. NULL_TREE is returned
5267    otherwise. TYPE can be an interface or a class.   */
5268
5269 static tree
5270 check_circular_reference (type)
5271      tree type;
5272 {
5273   tree basetype_vec = TYPE_BINFO_BASETYPES (type);
5274   int i;
5275
5276   if (!basetype_vec)
5277     return NULL_TREE;
5278
5279   if (! CLASS_INTERFACE (TYPE_NAME (type)))
5280     {
5281       if (inherits_from_p (CLASSTYPE_SUPER (type), type))
5282         return lookup_cl (TYPE_NAME (type));
5283       return NULL_TREE;
5284     }
5285     
5286   for (i = 0; i < TREE_VEC_LENGTH (basetype_vec); i++)
5287     {
5288       tree vec_elt = TREE_VEC_ELT (basetype_vec, i);
5289       if (vec_elt && BINFO_TYPE (vec_elt) != object_type_node
5290           && interface_of_p (type, BINFO_TYPE (vec_elt)))
5291         return lookup_cl (TYPE_NAME (BINFO_TYPE (vec_elt)));
5292     }
5293   return NULL_TREE;
5294 }
5295
5296 void
5297 java_check_circular_reference ()
5298 {
5299   tree current;
5300   for (current = ctxp->class_list; current; current = TREE_CHAIN (current))
5301     {
5302       tree type = TREE_TYPE (current);
5303       tree cl;
5304
5305       cl = check_circular_reference (type);
5306       if (! cl)
5307         cl = check_inner_circular_reference (type, type);
5308       if (cl)
5309         parse_error_context (cl, "Cyclic class inheritance%s",
5310                              (cyclic_inheritance_report ?
5311                               cyclic_inheritance_report : ""));
5312     }
5313 }
5314
5315 /* Augment the parameter list PARM with parameters crafted to
5316    initialize outer context locals aliases. Through ARTIFICIAL, a
5317    count is kept of the number of crafted parameters. MODE governs
5318    what eventually gets created: something suitable for a function
5319    creation or a function invocation, either the constructor or
5320    finit$.  */
5321
5322 static tree
5323 build_alias_initializer_parameter_list (mode, class_type, parm, artificial)
5324     int mode;
5325     tree class_type, parm;
5326     int *artificial;
5327 {
5328   tree field;
5329   tree additional_parms = NULL_TREE;
5330
5331   for (field = TYPE_FIELDS (class_type); field; field = TREE_CHAIN (field))
5332     if (FIELD_LOCAL_ALIAS (field))
5333       {
5334         const char *buffer = IDENTIFIER_POINTER (DECL_NAME (field));
5335         tree purpose = NULL_TREE, value = NULL_TREE, name = NULL_TREE;
5336         tree mangled_id;
5337
5338         switch (mode)
5339           {
5340           case AIPL_FUNCTION_DECLARATION:
5341             MANGLE_ALIAS_INITIALIZER_PARAMETER_NAME_STR (mangled_id, 
5342                                                          &buffer [4]);
5343             purpose = build_wfl_node (mangled_id);
5344             if (TREE_CODE (TREE_TYPE (field)) == POINTER_TYPE)
5345               value = build_wfl_node (TYPE_NAME (TREE_TYPE (field)));
5346             else
5347               value = TREE_TYPE (field);
5348             break;
5349
5350           case AIPL_FUNCTION_CREATION:
5351             MANGLE_ALIAS_INITIALIZER_PARAMETER_NAME_STR (purpose,
5352                                                          &buffer [4]);
5353             value = TREE_TYPE (field);
5354             break;
5355
5356           case AIPL_FUNCTION_FINIT_INVOCATION:
5357             MANGLE_ALIAS_INITIALIZER_PARAMETER_NAME_STR (mangled_id, 
5358                                                          &buffer [4]);
5359             /* Now, this is wrong. purpose should always be the NAME
5360                of something and value its matching value (decl, type,
5361                etc...) FIXME -- but there is a lot to fix. */
5362
5363             /* When invoked for this kind of operation, we already
5364                know whether a field is used or not. */
5365             purpose = TREE_TYPE (field);
5366             value = build_wfl_node (mangled_id);
5367             break;
5368
5369           case AIPL_FUNCTION_CTOR_INVOCATION:
5370             /* There are two case: the constructor invokation happends
5371                outside the local inner, in which case, locales from the outer
5372                context are directly used.
5373
5374                Otherwise, we fold to using the alias directly. */
5375             if (class_type == current_class)
5376               value = field;
5377             else
5378               {
5379                 name = get_identifier (&buffer[4]);
5380                 value = IDENTIFIER_LOCAL_VALUE (name);
5381               }
5382             break;
5383           }
5384         additional_parms = tree_cons (purpose, value, additional_parms);
5385         if (artificial)
5386           *artificial +=1;
5387       }
5388   if (additional_parms)
5389     {
5390       if (ANONYMOUS_CLASS_P (class_type) 
5391           && mode == AIPL_FUNCTION_CTOR_INVOCATION)
5392         additional_parms = nreverse (additional_parms);
5393       parm = chainon (additional_parms, parm);
5394     }
5395
5396    return parm;
5397 }
5398
5399 /* Craft a constructor for CLASS_DECL -- what we should do when none
5400    where found. ARGS is non NULL when a special signature must be
5401    enforced. This is the case for anonymous classes.  */
5402
5403 static void
5404 craft_constructor (class_decl, args)
5405      tree class_decl, args;
5406 {
5407   tree class_type = TREE_TYPE (class_decl);
5408   tree parm = NULL_TREE;
5409   int flags = (get_access_flags_from_decl (class_decl) & ACC_PUBLIC ?
5410                ACC_PUBLIC : 0);
5411   int i = 0, artificial = 0;
5412   tree decl, ctor_name;
5413   char buffer [80];
5414   
5415   /* The constructor name is <init> unless we're dealing with an
5416      anonymous class, in which case the name will be fixed after having
5417      be expanded. */
5418   if (ANONYMOUS_CLASS_P (class_type))
5419     ctor_name = DECL_NAME (class_decl);
5420   else
5421     ctor_name = init_identifier_node;
5422
5423   /* If we're dealing with an inner class constructor, we hide the
5424      this$<n> decl in the name field of its parameter declaration. */
5425   if (PURE_INNER_CLASS_TYPE_P (class_type))
5426     {
5427       tree type = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (class_type)));
5428       parm = tree_cons (build_current_thisn (class_type),
5429                         build_pointer_type (type), parm);
5430
5431       /* Some more arguments to be hidden here. The values of the local
5432          variables of the outer context that the inner class needs to see. */
5433       parm = build_alias_initializer_parameter_list (AIPL_FUNCTION_CREATION,
5434                                                      class_type, parm, 
5435                                                      &artificial);
5436     }
5437
5438   /* Then if there are any args to be enforced, enforce them now */
5439   for (; args && args != end_params_node; args = TREE_CHAIN (args))
5440     {
5441       sprintf (buffer, "parm%d", i++);
5442       parm = tree_cons (get_identifier (buffer), TREE_VALUE (args), parm);
5443     }
5444
5445   CRAFTED_PARAM_LIST_FIXUP (parm);
5446   decl = create_artificial_method (class_type, flags, void_type_node, 
5447                                    ctor_name, parm);
5448   fix_method_argument_names (parm, decl);
5449   /* Now, mark the artificial parameters. */
5450   DECL_FUNCTION_NAP (decl) = artificial;
5451   DECL_FUNCTION_SYNTHETIC_CTOR (decl) = DECL_CONSTRUCTOR_P (decl) = 1;
5452 }
5453
5454
5455 /* Fix the constructors. This will be called right after circular
5456    references have been checked. It is necessary to fix constructors
5457    early even if no code generation will take place for that class:
5458    some generated constructor might be required by the class whose
5459    compilation triggered this one to be simply loaded.  */
5460
5461 void
5462 java_fix_constructors ()
5463 {
5464   tree current;
5465
5466   for (current = ctxp->class_list; current; current = TREE_CHAIN (current))
5467     {
5468       tree class_type = TREE_TYPE (current);
5469       int saw_ctor = 0;
5470       tree decl;
5471
5472       if (CLASS_INTERFACE (TYPE_NAME (class_type)))
5473         continue;
5474
5475       current_class = class_type;
5476       for (decl = TYPE_METHODS (class_type); decl; decl = TREE_CHAIN (decl))
5477         {
5478           if (DECL_CONSTRUCTOR_P (decl))
5479             {
5480               fix_constructors (decl);
5481               saw_ctor = 1;
5482             }
5483         }
5484
5485       /* Anonymous class constructor can't be generated that early. */
5486       if (!saw_ctor && !ANONYMOUS_CLASS_P (class_type))
5487         craft_constructor (current, NULL_TREE);
5488     }
5489 }
5490
5491 /* safe_layout_class just makes sure that we can load a class without
5492    disrupting the current_class, input_file, lineno, etc, information
5493    about the class processed currently.  */
5494
5495 void
5496 safe_layout_class (class)
5497      tree class;
5498 {
5499   tree save_current_class = current_class;
5500   const char *save_input_filename = input_filename;
5501   int save_lineno = lineno;
5502
5503   layout_class (class);
5504
5505   current_class = save_current_class;
5506   input_filename = save_input_filename;
5507   lineno = save_lineno;
5508 }
5509
5510 static tree
5511 jdep_resolve_class (dep)
5512      jdep *dep;
5513 {
5514   tree decl;
5515
5516   if (JDEP_RESOLVED_P (dep))
5517     decl = JDEP_RESOLVED_DECL (dep);
5518   else
5519     {
5520       decl = resolve_class (JDEP_ENCLOSING (dep), JDEP_TO_RESOLVE (dep),
5521                             JDEP_DECL (dep), JDEP_WFL (dep));
5522       JDEP_RESOLVED (dep, decl);
5523     }
5524     
5525   if (!decl)
5526     complete_class_report_errors (dep);
5527   else if (PURE_INNER_CLASS_DECL_P (decl))
5528     {
5529       tree inner = TREE_TYPE (decl);
5530       if (! CLASS_LOADED_P (inner))
5531         {
5532           safe_layout_class (inner);
5533           if (TYPE_SIZE (inner) == error_mark_node)
5534             TYPE_SIZE (inner) = NULL_TREE;
5535         }
5536       check_inner_class_access (decl, JDEP_ENCLOSING (dep), JDEP_WFL (dep));
5537     }
5538   return decl;
5539 }
5540
5541 /* Complete unsatisfied class declaration and their dependencies */
5542
5543 void
5544 java_complete_class ()
5545 {
5546   tree cclass;
5547   jdeplist *cclassd;
5548   int error_found;
5549   tree type;
5550
5551   /* Process imports */
5552   process_imports ();
5553
5554   /* Rever things so we have the right order */
5555   ctxp->class_list = nreverse (ctxp->class_list);
5556   ctxp->classd_list = reverse_jdep_list (ctxp);
5557
5558   for (cclassd = ctxp->classd_list, cclass = ctxp->class_list; 
5559        cclass && cclassd; 
5560        cclass = TREE_CHAIN (cclass), cclassd = CLASSD_CHAIN (cclassd))
5561     {
5562       jdep *dep;
5563
5564       /* We keep the compilation unit imports in the class so that
5565          they can be used later to resolve type dependencies that
5566          aren't necessary to solve now. */
5567       TYPE_IMPORT_LIST (TREE_TYPE (cclass)) = ctxp->import_list;
5568       TYPE_IMPORT_DEMAND_LIST (TREE_TYPE (cclass)) = ctxp->import_demand_list;
5569
5570       for (dep = CLASSD_FIRST (cclassd); dep; dep = JDEP_CHAIN (dep))
5571         {
5572           tree decl;
5573           if (!(decl = jdep_resolve_class (dep)))
5574             continue;
5575
5576           /* Now it's time to patch */
5577           switch (JDEP_KIND (dep))
5578             {
5579             case JDEP_SUPER:
5580               /* Simply patch super */
5581               if (parser_check_super (decl, JDEP_DECL (dep), JDEP_WFL (dep)))
5582                 continue;
5583               BINFO_TYPE (TREE_VEC_ELT (BINFO_BASETYPES (TYPE_BINFO 
5584                 (TREE_TYPE (JDEP_DECL (dep)))), 0)) = TREE_TYPE (decl);
5585               break;
5586
5587             case JDEP_FIELD:
5588               {
5589                 /* We do part of the job done in add_field */
5590                 tree field_decl = JDEP_DECL (dep);
5591                 tree field_type = TREE_TYPE (decl);
5592                 if (TREE_CODE (field_type) == RECORD_TYPE)
5593                   field_type = promote_type (field_type);
5594                 TREE_TYPE (field_decl) = field_type;
5595                 DECL_ALIGN (field_decl) = 0;
5596                 DECL_USER_ALIGN (field_decl) = 0;
5597                 layout_decl (field_decl, 0);
5598                 SOURCE_FRONTEND_DEBUG 
5599                   (("Completed field/var decl `%s' with `%s'",
5600                     IDENTIFIER_POINTER (DECL_NAME (field_decl)),
5601                     IDENTIFIER_POINTER (DECL_NAME (decl))));
5602                 break;
5603               }
5604             case JDEP_METHOD:   /* We start patching a method */
5605             case JDEP_METHOD_RETURN:
5606               error_found = 0;
5607               while (1)
5608                 {
5609                   if (decl)
5610                     {
5611                       type = TREE_TYPE(decl);
5612                       if (TREE_CODE (type) == RECORD_TYPE)
5613                         type = promote_type (type);
5614                       JDEP_APPLY_PATCH (dep, type);
5615                       SOURCE_FRONTEND_DEBUG 
5616                         (((JDEP_KIND (dep) == JDEP_METHOD_RETURN ?
5617                            "Completing fct `%s' with ret type `%s'":
5618                            "Completing arg `%s' with type `%s'"),
5619                           IDENTIFIER_POINTER (EXPR_WFL_NODE 
5620                                               (JDEP_DECL_WFL (dep))),
5621                           IDENTIFIER_POINTER (DECL_NAME (decl))));
5622                     }
5623                   else
5624                     error_found = 1;
5625                   dep = JDEP_CHAIN (dep);
5626                   if (JDEP_KIND (dep) == JDEP_METHOD_END)
5627                     break;
5628                   else
5629                     decl = jdep_resolve_class (dep);
5630                 }
5631               if (!error_found)
5632                 {
5633                   tree mdecl = JDEP_DECL (dep), signature;
5634                   /* Recompute and reset the signature, check first that
5635                      all types are now defined. If they're not,
5636                      don't build the signature. */
5637                   if (check_method_types_complete (mdecl))
5638                     {
5639                       signature = build_java_signature (TREE_TYPE (mdecl));
5640                       set_java_signature (TREE_TYPE (mdecl), signature);
5641                     }
5642                 }
5643               else
5644                 continue;
5645               break;
5646
5647             case JDEP_INTERFACE:
5648               if (parser_check_super_interface (decl, JDEP_DECL (dep),
5649                                                 JDEP_WFL (dep)))
5650                 continue;
5651               parser_add_interface (JDEP_DECL (dep), decl, JDEP_WFL (dep));
5652               break;
5653
5654             case JDEP_PARM:
5655             case JDEP_VARIABLE:
5656               type = TREE_TYPE(decl);
5657               if (TREE_CODE (type) == RECORD_TYPE)
5658                 type = promote_type (type);
5659               JDEP_APPLY_PATCH (dep, type);
5660               break;
5661
5662             case JDEP_TYPE:
5663               JDEP_APPLY_PATCH (dep, TREE_TYPE (decl));
5664               SOURCE_FRONTEND_DEBUG 
5665                 (("Completing a random type dependency on a '%s' node",
5666                   tree_code_name [TREE_CODE (JDEP_DECL (dep))]));
5667               break;
5668
5669             case JDEP_EXCEPTION:
5670               JDEP_APPLY_PATCH (dep, TREE_TYPE (decl));
5671               SOURCE_FRONTEND_DEBUG 
5672                 (("Completing `%s' `throws' argument node",
5673                   IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_WFL (dep)))));
5674               break;
5675
5676             case JDEP_ANONYMOUS:
5677               patch_anonymous_class (decl, JDEP_DECL (dep), JDEP_WFL (dep));
5678               break;
5679
5680             default:
5681               abort ();
5682             }
5683         }
5684     }
5685   return;
5686 }
5687
5688 /* Resolve class CLASS_TYPE. Handle the case of trying to resolve an
5689    array.  */
5690
5691 static tree
5692 resolve_class (enclosing, class_type, decl, cl)
5693      tree enclosing, class_type, decl, cl;
5694 {
5695   tree tname = TYPE_NAME (class_type);
5696   tree resolved_type = TREE_TYPE (class_type);
5697   int array_dims = 0;
5698   tree resolved_type_decl;
5699   
5700   if (resolved_type != NULL_TREE)
5701     {
5702       tree resolved_type_decl = TYPE_NAME (resolved_type);
5703       if (resolved_type_decl == NULL_TREE
5704           || TREE_CODE (resolved_type_decl) == IDENTIFIER_NODE)
5705         {
5706           resolved_type_decl = build_decl (TYPE_DECL,
5707                                            TYPE_NAME (class_type),
5708                                            resolved_type);
5709         }
5710       return resolved_type_decl;
5711     }
5712
5713   /* 1- Check to see if we have an array. If true, find what we really
5714      want to resolve  */
5715   if ((array_dims = build_type_name_from_array_name (tname,
5716                                                      &TYPE_NAME (class_type))))
5717     WFL_STRIP_BRACKET (cl, cl);
5718
5719   /* 2- Resolve the bare type */
5720   if (!(resolved_type_decl = do_resolve_class (enclosing, class_type, 
5721                                                decl, cl)))
5722     return NULL_TREE;
5723   resolved_type = TREE_TYPE (resolved_type_decl);
5724
5725   /* 3- If we have and array, reconstruct the array down to its nesting */
5726   if (array_dims)
5727     {
5728       for (; array_dims; array_dims--)
5729         resolved_type = build_java_array_type (resolved_type, -1);
5730       resolved_type_decl = TYPE_NAME (resolved_type);
5731     }
5732   TREE_TYPE (class_type) = resolved_type;
5733   return resolved_type_decl;
5734 }
5735
5736 /* Effectively perform the resolution of class CLASS_TYPE. DECL or CL
5737    are used to report error messages. Do not try to replace TYPE_NAME
5738    (class_type) by a variable, since it is changed by
5739    find_in_imports{_on_demand} and (but it doesn't really matter)
5740    qualify_and_find.  */
5741
5742 tree
5743 do_resolve_class (enclosing, class_type, decl, cl)
5744      tree enclosing, class_type, decl, cl;
5745 {
5746   tree new_class_decl = NULL_TREE, super = NULL_TREE;
5747   tree saved_enclosing_type = enclosing ? TREE_TYPE (enclosing) : NULL_TREE;
5748   struct hash_table _ht, *circularity_hash = &_ht;
5749
5750   /* This hash table is used to register the classes we're going
5751      through when searching the current class as an inner class, in
5752      order to detect circular references. Remember to free it before
5753      returning the section 0- of this function. */
5754   hash_table_init (circularity_hash, hash_newfunc,
5755                    java_hash_hash_tree_node, java_hash_compare_tree_node);
5756
5757   /* 0- Search in the current class as an inner class.
5758      Maybe some code here should be added to load the class or
5759      something, at least if the class isn't an inner class and ended
5760      being loaded from class file. FIXME. */
5761   while (enclosing)
5762     {
5763       new_class_decl = resolve_inner_class (circularity_hash, cl, &enclosing,
5764                                             &super, class_type);
5765       if (new_class_decl)
5766         break;
5767
5768       /* If we haven't found anything because SUPER reached Object and
5769          ENCLOSING happens to be an innerclass, try the enclosing context. */
5770       if ((!super || super == object_type_node) && 
5771           enclosing && INNER_CLASS_DECL_P (enclosing))
5772         enclosing = DECL_CONTEXT (enclosing);
5773       else
5774         enclosing = NULL_TREE;
5775     }
5776
5777   hash_table_free (circularity_hash);
5778
5779   if (new_class_decl)
5780     return new_class_decl;
5781
5782   /* 1- Check for the type in single imports. This will change
5783      TYPE_NAME() if something relevant is found */
5784   find_in_imports (saved_enclosing_type, class_type);
5785
5786   /* 2- And check for the type in the current compilation unit */
5787   if ((new_class_decl = IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type))))
5788     {
5789       if (!CLASS_LOADED_P (TREE_TYPE (new_class_decl)) &&
5790           !CLASS_FROM_SOURCE_P (TREE_TYPE (new_class_decl)))
5791         load_class (TYPE_NAME (class_type), 0);
5792       return IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type));
5793     }
5794
5795   /* 3- Search according to the current package definition */
5796   if (!QUALIFIED_P (TYPE_NAME (class_type)))
5797     {
5798       if ((new_class_decl = qualify_and_find (class_type, ctxp->package,
5799                                              TYPE_NAME (class_type))))
5800         return new_class_decl;
5801     }
5802
5803   /* 4- Check the import on demands. Don't allow bar.baz to be
5804      imported from foo.* */
5805   if (!QUALIFIED_P (TYPE_NAME (class_type)))
5806     if (find_in_imports_on_demand (saved_enclosing_type, class_type))
5807       return NULL_TREE;
5808
5809   /* If found in find_in_imports_on_demant, the type has already been
5810      loaded. */
5811   if ((new_class_decl = IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type))))
5812     return new_class_decl;
5813
5814   /* 5- Try with a name qualified with the package name we've seen so far */
5815   if (!QUALIFIED_P (TYPE_NAME (class_type)))
5816     {
5817       tree package;
5818
5819       /* If there is a current package (ctxp->package), it's the first
5820          element of package_list and we can skip it. */
5821       for (package = (ctxp->package ? 
5822                       TREE_CHAIN (package_list) : package_list);
5823            package; package = TREE_CHAIN (package))
5824         if ((new_class_decl = qualify_and_find (class_type,
5825                                                TREE_PURPOSE (package), 
5826                                                TYPE_NAME (class_type))))
5827           return new_class_decl;
5828     }
5829
5830   /* 5- Check an other compilation unit that bears the name of type */
5831   load_class (TYPE_NAME (class_type), 0);
5832   
5833   if (!cl)
5834     cl = lookup_cl (decl);
5835   
5836   /* If we don't have a value for CL, then we're being called recursively. 
5837      We can't check package access just yet, but it will be taken care of
5838      by the caller. */
5839   if (cl)
5840     {
5841       if (check_pkg_class_access (TYPE_NAME (class_type), cl, true))
5842         return NULL_TREE;
5843     }
5844   
5845   /* 6- Last call for a resolution */
5846   return IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type));
5847 }
5848
5849 static tree
5850 qualify_and_find (class_type, package, name)
5851      tree class_type, package, name;
5852 {
5853   tree new_qualified = merge_qualified_name (package, name);
5854   tree new_class_decl;
5855
5856   if (!IDENTIFIER_CLASS_VALUE (new_qualified))
5857     load_class (new_qualified, 0);
5858   if ((new_class_decl = IDENTIFIER_CLASS_VALUE (new_qualified)))
5859     {
5860       if (!CLASS_LOADED_P (TREE_TYPE (new_class_decl)) &&
5861           !CLASS_FROM_SOURCE_P (TREE_TYPE (new_class_decl)))
5862         load_class (new_qualified, 0);
5863       TYPE_NAME (class_type) = new_qualified;
5864       return IDENTIFIER_CLASS_VALUE (new_qualified);
5865     }
5866   return NULL_TREE;
5867 }
5868
5869 /* Resolve NAME and lay it out (if not done and if not the current
5870    parsed class). Return a decl node. This function is meant to be
5871    called when type resolution is necessary during the walk pass.  */
5872
5873 static tree
5874 resolve_and_layout (something, cl)
5875      tree something;
5876      tree cl;
5877 {
5878   tree decl, decl_type;
5879
5880   /* Don't do that on the current class */
5881   if (something == current_class)
5882     return TYPE_NAME (current_class);
5883
5884   /* Don't do anything for void and other primitive types */
5885   if (JPRIMITIVE_TYPE_P (something) || something == void_type_node)
5886     return NULL_TREE;
5887
5888   /* Pointer types can be reall pointer types or fake pointers. When
5889      finding a real pointer, recheck for primitive types */
5890   if (TREE_CODE (something) == POINTER_TYPE)
5891     {
5892       if (TREE_TYPE (something))
5893         {
5894           something = TREE_TYPE (something);
5895           if (JPRIMITIVE_TYPE_P (something) || something == void_type_node)
5896             return NULL_TREE;
5897         }
5898       else
5899         something = TYPE_NAME (something);
5900     }
5901
5902   /* Don't do anything for arrays of primitive types */
5903   if (TREE_CODE (something) == RECORD_TYPE && TYPE_ARRAY_P (something)
5904       && JPRIMITIVE_TYPE_P (TYPE_ARRAY_ELEMENT (something)))
5905     return NULL_TREE;
5906
5907   /* Something might be a WFL */
5908   if (TREE_CODE (something) == EXPR_WITH_FILE_LOCATION)
5909     something = EXPR_WFL_NODE (something);
5910
5911   /* Otherwise, if something is not and IDENTIFIER_NODE, it can be a a
5912      TYPE_DECL or a real TYPE */
5913   else if (TREE_CODE (something) != IDENTIFIER_NODE)
5914     something = (TREE_CODE (TYPE_NAME (something)) == TYPE_DECL ?
5915             DECL_NAME (TYPE_NAME (something)) : TYPE_NAME (something));
5916
5917   if (!(decl = resolve_no_layout (something, cl)))
5918     return NULL_TREE;
5919
5920   /* Resolve and layout if necessary */
5921   decl_type = TREE_TYPE (decl);
5922   layout_class_methods (decl_type);
5923   /* Check methods */
5924   if (CLASS_FROM_SOURCE_P (decl_type))
5925     java_check_methods (decl);
5926   /* Layout the type if necessary */ 
5927   if (decl_type != current_class && !CLASS_LOADED_P (decl_type))
5928     safe_layout_class (decl_type);
5929
5930   return decl;
5931 }
5932
5933 /* Resolve a class, returns its decl but doesn't perform any
5934    layout. The current parsing context is saved and restored */
5935
5936 static tree
5937 resolve_no_layout (name, cl)
5938      tree name, cl;
5939 {
5940   tree ptr, decl;
5941   BUILD_PTR_FROM_NAME (ptr, name);
5942   java_parser_context_save_global ();
5943   decl = resolve_class (TYPE_NAME (current_class), ptr, NULL_TREE, cl);
5944   java_parser_context_restore_global ();
5945   
5946   return decl;
5947 }
5948
5949 /* Called when reporting errors. Skip the '[]'s in a complex array
5950    type description that failed to be resolved. purify_type_name can't
5951    use an identifier tree.  */
5952
5953 static const char *
5954 purify_type_name (name)
5955      const char *name;
5956 {
5957   int len = strlen (name);
5958   int bracket_found;
5959
5960   STRING_STRIP_BRACKETS (name, len, bracket_found);
5961   if (bracket_found)
5962     {
5963       char *stripped_name = xmemdup (name, len, len+1);
5964       stripped_name [len] = '\0';
5965       return stripped_name;
5966     }
5967   return name;
5968 }
5969
5970 /* The type CURRENT refers to can't be found. We print error messages.  */
5971
5972 static void
5973 complete_class_report_errors (dep)
5974      jdep *dep;
5975 {
5976   const char *name;
5977
5978   if (!JDEP_WFL (dep))
5979     return;
5980
5981   name = IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_WFL (dep)));
5982   switch (JDEP_KIND (dep))
5983     {
5984     case JDEP_SUPER:
5985       parse_error_context  
5986         (JDEP_WFL (dep), "Superclass `%s' of class `%s' not found",
5987          purify_type_name (name),
5988          IDENTIFIER_POINTER (DECL_NAME (JDEP_DECL (dep))));
5989       break;
5990     case JDEP_FIELD:
5991       parse_error_context
5992         (JDEP_WFL (dep), "Type `%s' not found in declaration of field `%s'",
5993          purify_type_name (name),
5994          IDENTIFIER_POINTER (DECL_NAME (JDEP_DECL (dep))));
5995       break;
5996     case JDEP_METHOD:           /* Covers arguments */
5997       parse_error_context
5998         (JDEP_WFL (dep), "Type `%s' not found in the declaration of the argument `%s' of method `%s'",
5999          purify_type_name (name),
6000          IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_DECL_WFL (dep))),
6001          IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_MISC (dep))));
6002       break;
6003     case JDEP_METHOD_RETURN:    /* Covers return type */
6004       parse_error_context
6005         (JDEP_WFL (dep), "Type `%s' not found in the declaration of the return type of method `%s'", 
6006          purify_type_name (name),
6007          IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_DECL_WFL (dep))));
6008       break;
6009     case JDEP_INTERFACE:
6010       parse_error_context
6011         (JDEP_WFL (dep), "Superinterface `%s' of %s `%s' not found",
6012          IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_WFL (dep))),
6013          (CLASS_OR_INTERFACE (JDEP_DECL (dep), "class", "interface")),
6014          IDENTIFIER_POINTER (DECL_NAME (JDEP_DECL (dep))));
6015       break;
6016     case JDEP_VARIABLE:
6017       parse_error_context
6018         (JDEP_WFL (dep), "Type `%s' not found in the declaration of the local variable `%s'", 
6019          purify_type_name (IDENTIFIER_POINTER 
6020                            (EXPR_WFL_NODE (JDEP_WFL (dep)))),
6021          IDENTIFIER_POINTER (DECL_NAME (JDEP_DECL (dep))));
6022       break;
6023     case JDEP_EXCEPTION:        /* As specified by `throws' */
6024       parse_error_context 
6025           (JDEP_WFL (dep), "Class `%s' not found in `throws'",
6026          IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_WFL (dep))));
6027       break;
6028     default:
6029       /* Fix for -Wall. Just break doing nothing. The error will be
6030          caught later */
6031       break;
6032     }
6033 }
6034
6035 /* Return a static string containing the DECL prototype string. If
6036    DECL is a constructor, use the class name instead of the form
6037    <init> */
6038
6039 static const char *
6040 get_printable_method_name (decl)
6041      tree decl;
6042 {
6043   const char *to_return;
6044   tree name = NULL_TREE;
6045
6046   if (DECL_CONSTRUCTOR_P (decl))
6047     {
6048       name = DECL_NAME (decl);
6049       DECL_NAME (decl) = DECL_NAME (TYPE_NAME (DECL_CONTEXT (decl)));
6050     }
6051       
6052   to_return = lang_printable_name (decl, 0);
6053   if (DECL_CONSTRUCTOR_P (decl))
6054     DECL_NAME (decl) = name;
6055   
6056   return to_return;
6057 }
6058
6059 /* Track method being redefined inside the same class. As a side
6060    effect, set DECL_NAME to an IDENTIFIER (prior entering this
6061    function it's a FWL, so we can track errors more accurately.)  */
6062
6063 static int
6064 check_method_redefinition (class, method)
6065      tree class, method;
6066 {
6067   tree redef, sig;
6068
6069   /* There's no need to verify <clinit> and finit$ and instinit$ */
6070   if (DECL_CLINIT_P (method)
6071       || DECL_FINIT_P (method) || DECL_INSTINIT_P (method))
6072     return 0;
6073
6074   sig = TYPE_ARGUMENT_SIGNATURE (TREE_TYPE (method));
6075   for (redef = TYPE_METHODS (class); redef; redef = TREE_CHAIN (redef))
6076     {
6077       if (redef == method)
6078         break;
6079       if (DECL_NAME (redef) == DECL_NAME (method)
6080           && sig == TYPE_ARGUMENT_SIGNATURE (TREE_TYPE (redef))
6081           && !DECL_ARTIFICIAL (method))
6082         {
6083           parse_error_context 
6084             (DECL_FUNCTION_WFL (method), "Duplicate %s declaration `%s'",
6085              (DECL_CONSTRUCTOR_P (redef) ? "constructor" : "method"),
6086              get_printable_method_name (redef));
6087           return 1;
6088         }
6089     }
6090   return 0;
6091 }
6092
6093 /* Return 1 if check went ok, 0 otherwise.  */
6094 static int
6095 check_abstract_method_definitions (do_interface, class_decl, type)
6096      int do_interface;
6097      tree class_decl, type;
6098 {
6099   tree class = TREE_TYPE (class_decl);
6100   tree method, end_type;
6101   int ok = 1;
6102
6103   end_type = (do_interface ? object_type_node : type);
6104   for (method = TYPE_METHODS (type); method; method = TREE_CHAIN (method))
6105     {
6106       tree other_super, other_method, method_sig, method_name;
6107       int found = 0;
6108       int end_type_reached = 0;
6109       
6110       if (!METHOD_ABSTRACT (method) || METHOD_FINAL (method))
6111         continue;
6112       
6113       /* Now verify that somewhere in between TYPE and CLASS,
6114          abstract method METHOD gets a non abstract definition
6115          that is inherited by CLASS.  */
6116       
6117       method_sig = build_java_signature (TREE_TYPE (method));
6118       method_name = DECL_NAME (method);
6119       if (TREE_CODE (method_name) == EXPR_WITH_FILE_LOCATION)
6120         method_name = EXPR_WFL_NODE (method_name);
6121
6122       other_super = class;
6123       do {
6124         if (other_super == end_type)
6125           end_type_reached = 1;
6126         
6127         /* Method search */
6128         for (other_method = TYPE_METHODS (other_super); other_method;
6129             other_method = TREE_CHAIN (other_method))
6130           {
6131             tree s = build_java_signature (TREE_TYPE (other_method));
6132             tree other_name = DECL_NAME (other_method);
6133             
6134             if (TREE_CODE (other_name) == EXPR_WITH_FILE_LOCATION)
6135               other_name = EXPR_WFL_NODE (other_name);
6136             if (!DECL_CLINIT_P (other_method)
6137                 && !DECL_CONSTRUCTOR_P (other_method)
6138                 && method_name == other_name
6139                 && method_sig == s
6140                 && !METHOD_ABSTRACT (other_method))
6141              {
6142                found = 1;
6143                break;
6144              }
6145           }
6146         other_super = CLASSTYPE_SUPER (other_super);
6147       } while (!end_type_reached);
6148  
6149       /* Report that abstract METHOD didn't find an implementation
6150          that CLASS can use. */
6151       if (!found)
6152         {
6153           char *t = xstrdup (lang_printable_name 
6154                             (TREE_TYPE (TREE_TYPE (method)), 0));
6155           tree ccn = DECL_NAME (TYPE_NAME (DECL_CONTEXT (method)));
6156           
6157           parse_error_context 
6158             (lookup_cl (class_decl),
6159              "Class `%s' doesn't define the abstract method `%s %s' from %s `%s'. This method must be defined or %s `%s' must be declared abstract",
6160              IDENTIFIER_POINTER (DECL_NAME (class_decl)),
6161              t, lang_printable_name (method, 0), 
6162              (CLASS_INTERFACE (TYPE_NAME (DECL_CONTEXT (method))) ? 
6163               "interface" : "class"),
6164              IDENTIFIER_POINTER (ccn),
6165              (CLASS_INTERFACE (class_decl) ? "interface" : "class"),
6166              IDENTIFIER_POINTER (DECL_NAME (class_decl)));
6167           ok = 0;
6168           free (t);
6169         }
6170     }
6171
6172   if (ok && do_interface)
6173     {
6174       /* Check for implemented interfaces. */
6175       int i;
6176       tree vector = TYPE_BINFO_BASETYPES (type);
6177       for (i = 1; ok && vector && i < TREE_VEC_LENGTH (vector); i++)
6178         {
6179           tree super = BINFO_TYPE (TREE_VEC_ELT (vector, i));
6180           ok = check_abstract_method_definitions (1, class_decl, super);
6181         }
6182     }
6183
6184   return ok;
6185 }
6186
6187 /* Check that CLASS_DECL somehow implements all inherited abstract
6188    methods.  */
6189
6190 static void
6191 java_check_abstract_method_definitions (class_decl)
6192      tree class_decl;
6193 {
6194   tree class = TREE_TYPE (class_decl);
6195   tree super, vector;
6196   int i;
6197
6198   if (CLASS_ABSTRACT (class_decl))
6199     return;
6200
6201   /* Check for inherited types */
6202   super = class;
6203   do {
6204     super = CLASSTYPE_SUPER (super);
6205     check_abstract_method_definitions (0, class_decl, super);
6206   } while (super != object_type_node);
6207
6208   /* Check for implemented interfaces. */
6209   vector = TYPE_BINFO_BASETYPES (class);
6210   for (i = 1; i < TREE_VEC_LENGTH (vector); i++)
6211     {
6212       super = BINFO_TYPE (TREE_VEC_ELT (vector, i));
6213       check_abstract_method_definitions (1, class_decl, super);
6214     }
6215 }
6216
6217 /* Check all the types method DECL uses and return 1 if all of them
6218    are now complete, 0 otherwise. This is used to check whether its
6219    safe to build a method signature or not.  */
6220
6221 static int
6222 check_method_types_complete (decl)
6223      tree decl;
6224 {
6225   tree type = TREE_TYPE (decl);
6226   tree args;
6227
6228   if (!INCOMPLETE_TYPE_P (TREE_TYPE (type)))
6229     return 0;
6230   
6231   args = TYPE_ARG_TYPES (type);
6232   if (TREE_CODE (type) == METHOD_TYPE)
6233     args = TREE_CHAIN (args);
6234   for (; args != end_params_node; args = TREE_CHAIN (args))
6235     if (INCOMPLETE_TYPE_P (TREE_VALUE (args)))
6236       return 0;
6237
6238   return 1;
6239 }
6240
6241 /* Visible interface to check methods contained in CLASS_DECL */
6242
6243 void
6244 java_check_methods (class_decl)
6245      tree class_decl;
6246 {
6247   if (CLASS_METHOD_CHECKED_P (TREE_TYPE (class_decl)))
6248     return;
6249
6250   if (CLASS_INTERFACE (class_decl))
6251     java_check_abstract_methods (class_decl);
6252   else
6253     java_check_regular_methods (class_decl);
6254   
6255   CLASS_METHOD_CHECKED_P (TREE_TYPE (class_decl)) = 1;
6256 }
6257
6258 /* Check all the methods of CLASS_DECL. Methods are first completed
6259    then checked according to regular method existence rules.  If no
6260    constructor for CLASS_DECL were encountered, then build its
6261    declaration.  */
6262
6263 static void
6264 java_check_regular_methods (class_decl)
6265      tree class_decl;
6266 {
6267   int saw_constructor = ANONYMOUS_CLASS_P (TREE_TYPE (class_decl));
6268   tree method;
6269   tree class = CLASS_TO_HANDLE_TYPE (TREE_TYPE (class_decl));
6270   tree found = NULL_TREE;
6271   tree mthrows;
6272
6273   /* It is not necessary to check methods defined in java.lang.Object */
6274   if (class == object_type_node)
6275     return;
6276
6277   if (!TYPE_NVIRTUALS (class))
6278     TYPE_METHODS (class) = nreverse (TYPE_METHODS (class));
6279
6280   /* Should take interfaces into account. FIXME */
6281   for (method = TYPE_METHODS (class); method; method = TREE_CHAIN (method))
6282     {
6283       tree sig;
6284       tree method_wfl = DECL_FUNCTION_WFL (method);
6285       int aflags;
6286
6287       /* Check for redefinitions */
6288       if (check_method_redefinition (class, method))
6289         continue;
6290
6291       /* If we see one constructor a mark so we don't generate the
6292          default one. Also skip other verifications: constructors
6293          can't be inherited hence hiden or overriden */
6294      if (DECL_CONSTRUCTOR_P (method))
6295        {
6296          saw_constructor = 1;
6297          continue;
6298        }
6299
6300       /* We verify things thrown by the method. They must inherits from
6301          java.lang.Throwable */
6302       for (mthrows = DECL_FUNCTION_THROWS (method);
6303            mthrows; mthrows = TREE_CHAIN (mthrows))
6304         {
6305           if (!inherits_from_p (TREE_VALUE (mthrows), throwable_type_node))
6306             parse_error_context 
6307               (TREE_PURPOSE (mthrows), "Class `%s' in `throws' clause must be a subclass of class `java.lang.Throwable'",
6308                IDENTIFIER_POINTER 
6309                  (DECL_NAME (TYPE_NAME (TREE_VALUE (mthrows)))));
6310         }
6311
6312       sig = build_java_argument_signature (TREE_TYPE (method));
6313       found = lookup_argument_method2 (class, DECL_NAME (method), sig);
6314
6315       /* Inner class can't declare static methods */
6316       if (METHOD_STATIC (method) && !TOPLEVEL_CLASS_DECL_P (class_decl))
6317         {
6318           char *t = xstrdup (lang_printable_name (class, 0));
6319           parse_error_context 
6320             (method_wfl, "Method `%s' can't be static in inner class `%s'. Only members of interfaces and top-level classes can be static",
6321              lang_printable_name (method, 0), t);
6322           free (t);
6323         }
6324
6325       /* Nothing overrides or it's a private method. */
6326       if (!found)
6327         continue;
6328       if (METHOD_PRIVATE (found))
6329         {
6330           found = NULL_TREE;
6331           continue;
6332         }
6333
6334       /* If `found' is declared in an interface, make sure the
6335          modifier matches. */
6336       if (CLASS_INTERFACE (TYPE_NAME (DECL_CONTEXT (found))) 
6337           && clinit_identifier_node != DECL_NAME (found)
6338           && !METHOD_PUBLIC (method))
6339         {
6340           tree found_decl = TYPE_NAME (DECL_CONTEXT (found));
6341           parse_error_context (method_wfl, "Class `%s' must override `%s' with a public method in order to implement interface `%s'",
6342                                IDENTIFIER_POINTER (DECL_NAME (class_decl)),
6343                                lang_printable_name (method, 0),
6344                                IDENTIFIER_POINTER (DECL_NAME (found_decl)));
6345         }
6346
6347       /* Can't override a method with the same name and different return
6348          types. */
6349       if (TREE_TYPE (TREE_TYPE (found)) != TREE_TYPE (TREE_TYPE (method)))
6350         {
6351           char *t = xstrdup 
6352             (lang_printable_name (TREE_TYPE (TREE_TYPE (found)), 0));
6353           parse_error_context 
6354             (method_wfl,
6355              "Method `%s' was defined with return type `%s' in class `%s'", 
6356              lang_printable_name (found, 0), t,
6357              IDENTIFIER_POINTER 
6358                (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
6359           free (t);
6360         }
6361
6362       aflags = get_access_flags_from_decl (found);
6363
6364       /* Can't override final. Can't override static. */
6365       if (METHOD_FINAL (found) || METHOD_STATIC (found))
6366         {
6367           /* Static *can* override static */
6368           if (METHOD_STATIC (found) && METHOD_STATIC (method))
6369             continue;
6370           parse_error_context 
6371             (method_wfl,
6372              "%s methods can't be overriden. Method `%s' is %s in class `%s'",
6373              (METHOD_FINAL (found) ? "Final" : "Static"),
6374              lang_printable_name (found, 0),
6375              (METHOD_FINAL (found) ? "final" : "static"),
6376              IDENTIFIER_POINTER
6377                (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
6378           continue;
6379         }
6380
6381       /* Static method can't override instance method. */
6382       if (METHOD_STATIC (method))
6383         {
6384           parse_error_context 
6385             (method_wfl,
6386              "Instance methods can't be overriden by a static method. Method `%s' is an instance method in class `%s'",
6387              lang_printable_name (found, 0),
6388              IDENTIFIER_POINTER
6389                (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
6390           continue;
6391         }
6392
6393       /* - Overriding/hiding public must be public
6394          - Overriding/hiding protected must be protected or public
6395          - If the overriden or hidden method has default (package)
6396            access, then the overriding or hiding method must not be
6397            private; otherwise, a compile-time error occurs.  If
6398            `found' belongs to an interface, things have been already
6399            taken care of.  */
6400       if (!CLASS_INTERFACE (TYPE_NAME (DECL_CONTEXT (found)))
6401           && ((METHOD_PUBLIC (found) && !METHOD_PUBLIC (method))
6402               || (METHOD_PROTECTED (found) 
6403                   && !(METHOD_PUBLIC (method) || METHOD_PROTECTED (method)))
6404               || (!(aflags & (ACC_PUBLIC | ACC_PRIVATE | ACC_STATIC))
6405                   && METHOD_PRIVATE (method))))
6406         {
6407           parse_error_context 
6408             (method_wfl,
6409              "Methods can't be overridden to be more private. Method `%s' is not %s in class `%s'", lang_printable_name (method, 0),
6410              (METHOD_PUBLIC (method) ? "public" : 
6411               (METHOD_PRIVATE (method) ? "private" : "protected")),
6412              IDENTIFIER_POINTER (DECL_NAME 
6413                                  (TYPE_NAME (DECL_CONTEXT (found)))));
6414           continue;
6415         }
6416
6417       /* Overriding methods must have compatible `throws' clauses on checked
6418          exceptions, if any */
6419       check_throws_clauses (method, method_wfl, found);
6420
6421       /* Inheriting multiple methods with the same signature. FIXME */
6422     }
6423   
6424   if (!TYPE_NVIRTUALS (class))
6425     TYPE_METHODS (class) = nreverse (TYPE_METHODS (class));
6426
6427   /* Search for inherited abstract method not yet implemented in this
6428      class.  */
6429   java_check_abstract_method_definitions (class_decl);
6430
6431   if (!saw_constructor)
6432     abort ();
6433 }
6434
6435 /* Return a non zero value if the `throws' clause of METHOD (if any)
6436    is incompatible with the `throws' clause of FOUND (if any).  */
6437
6438 static void
6439 check_throws_clauses (method, method_wfl, found)
6440      tree method, method_wfl, found;
6441 {
6442   tree mthrows, fthrows;
6443
6444   /* Can't check these things with class loaded from bytecode. FIXME */
6445   if (!CLASS_FROM_SOURCE_P (DECL_CONTEXT (found)))
6446     return;
6447
6448   for (mthrows = DECL_FUNCTION_THROWS (method);
6449        mthrows; mthrows = TREE_CHAIN (mthrows))
6450     {
6451       /* We don't verify unchecked expressions */
6452       if (IS_UNCHECKED_EXCEPTION_P (TREE_VALUE (mthrows)))
6453         continue;
6454       /* Checked expression must be compatible */
6455       for (fthrows = DECL_FUNCTION_THROWS (found); 
6456            fthrows; fthrows = TREE_CHAIN (fthrows))
6457         if (inherits_from_p (TREE_VALUE (mthrows), TREE_VALUE (fthrows)))
6458           break;
6459       if (!fthrows)
6460         {
6461           parse_error_context 
6462             (method_wfl, "Invalid checked exception class `%s' in `throws' clause. The exception must be a subclass of an exception thrown by `%s' from class `%s'",
6463              IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (TREE_VALUE (mthrows)))),
6464              lang_printable_name (found, 0),
6465              IDENTIFIER_POINTER 
6466                (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
6467         }
6468     }
6469 }
6470
6471 /* Check abstract method of interface INTERFACE */
6472
6473 static void
6474 java_check_abstract_methods (interface_decl)
6475      tree interface_decl;
6476 {
6477   int i, n;
6478   tree method, basetype_vec, found;
6479   tree interface = TREE_TYPE (interface_decl);
6480
6481   for (method = TYPE_METHODS (interface); method; method = TREE_CHAIN (method))
6482     {
6483       /* 2- Check for double definition inside the defining interface */
6484       if (check_method_redefinition (interface, method))
6485         continue;
6486
6487       /* 3- Overriding is OK as far as we preserve the return type and
6488          the thrown exceptions (FIXME) */
6489       found = lookup_java_interface_method2 (interface, method);
6490       if (found)
6491         {
6492           char *t;
6493           t = xstrdup (lang_printable_name (TREE_TYPE (TREE_TYPE (found)), 0));
6494           parse_error_context 
6495             (DECL_FUNCTION_WFL (found),
6496              "Method `%s' was defined with return type `%s' in class `%s'",
6497              lang_printable_name (found, 0), t,
6498              IDENTIFIER_POINTER 
6499                (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
6500           free (t);
6501           continue;
6502         }
6503     }
6504
6505   /* 4- Inherited methods can't differ by their returned types */
6506   if (!(basetype_vec = TYPE_BINFO_BASETYPES (interface)))
6507     return;
6508   n = TREE_VEC_LENGTH (basetype_vec);
6509   for (i = 0; i < n; i++)
6510     {
6511       tree sub_interface_method, sub_interface;
6512       tree vec_elt = TREE_VEC_ELT (basetype_vec, i);
6513       if (!vec_elt)
6514         continue;
6515       sub_interface = BINFO_TYPE (vec_elt);
6516       for (sub_interface_method = TYPE_METHODS (sub_interface); 
6517            sub_interface_method;
6518            sub_interface_method = TREE_CHAIN (sub_interface_method))
6519         {
6520           found = lookup_java_interface_method2 (interface, 
6521                                                  sub_interface_method);
6522           if (found && (found != sub_interface_method))
6523             {
6524               parse_error_context 
6525                 (lookup_cl (sub_interface_method),
6526                  "Interface `%s' inherits method `%s' from interface `%s'. This method is redefined with a different return type in interface `%s'",
6527                  IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (interface))),
6528                  lang_printable_name (found, 0),
6529                  IDENTIFIER_POINTER 
6530                    (DECL_NAME (TYPE_NAME 
6531                                (DECL_CONTEXT (sub_interface_method)))),
6532                  IDENTIFIER_POINTER 
6533                    (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
6534             }
6535         }
6536     }
6537 }
6538
6539 /* Lookup methods in interfaces using their name and partial
6540    signature. Return a matching method only if their types differ.  */
6541
6542 static tree
6543 lookup_java_interface_method2 (class, method_decl)
6544      tree class, method_decl;
6545 {
6546   int i, n;
6547   tree basetype_vec = TYPE_BINFO_BASETYPES (class), to_return;
6548
6549   if (!basetype_vec)
6550     return NULL_TREE;
6551
6552   n = TREE_VEC_LENGTH (basetype_vec);
6553   for (i = 0; i < n; i++)
6554     {
6555       tree vec_elt = TREE_VEC_ELT (basetype_vec, i), to_return;
6556       if ((BINFO_TYPE (vec_elt) != object_type_node)
6557           && (to_return = 
6558               lookup_java_method2 (BINFO_TYPE (vec_elt), method_decl, 1)))
6559         return to_return;
6560     }
6561   for (i = 0; i < n; i++)
6562     {
6563       to_return = lookup_java_interface_method2 
6564         (BINFO_TYPE (TREE_VEC_ELT (basetype_vec, i)), method_decl);
6565       if (to_return)
6566         return to_return;
6567     }
6568
6569   return NULL_TREE;
6570 }
6571
6572 /* Lookup method using their name and partial signature. Return a
6573    matching method only if their types differ.  */
6574
6575 static tree
6576 lookup_java_method2 (clas, method_decl, do_interface)
6577      tree clas, method_decl;
6578      int do_interface;
6579 {
6580   tree method, method_signature, method_name, method_type, name;
6581
6582   method_signature = build_java_argument_signature (TREE_TYPE (method_decl));
6583   name = DECL_NAME (method_decl);
6584   method_name = (TREE_CODE (name) == EXPR_WITH_FILE_LOCATION ? 
6585                  EXPR_WFL_NODE (name) : name);
6586   method_type = TREE_TYPE (TREE_TYPE (method_decl));
6587
6588   while (clas != NULL_TREE)
6589     {
6590       for (method = TYPE_METHODS (clas);
6591            method != NULL_TREE;  method = TREE_CHAIN (method))
6592         {
6593           tree method_sig = build_java_argument_signature (TREE_TYPE (method));
6594           tree name = DECL_NAME (method);
6595           if ((TREE_CODE (name) == EXPR_WITH_FILE_LOCATION ?
6596                EXPR_WFL_NODE (name) : name) == method_name
6597               && method_sig == method_signature 
6598               && TREE_TYPE (TREE_TYPE (method)) != method_type)
6599             return method;
6600         }
6601       clas = (do_interface ? NULL_TREE : CLASSTYPE_SUPER (clas));
6602     }
6603   return NULL_TREE;
6604 }
6605
6606 /* Return the line that matches DECL line number, and try its best to
6607    position the column number. Used during error reports.  */
6608
6609 static tree
6610 lookup_cl (decl)
6611      tree decl;
6612 {
6613   static tree cl = NULL_TREE;
6614   char *line, *found;
6615   
6616   if (!decl)
6617     return NULL_TREE;
6618
6619   if (cl == NULL_TREE)
6620     {
6621       cl = build_expr_wfl (NULL_TREE, NULL, 0, 0);
6622       ggc_add_tree_root (&cl, 1);
6623     }
6624
6625   EXPR_WFL_FILENAME_NODE (cl) = get_identifier (DECL_SOURCE_FILE (decl));
6626   EXPR_WFL_SET_LINECOL (cl, DECL_SOURCE_LINE_FIRST (decl), -1);
6627
6628   line = java_get_line_col (EXPR_WFL_FILENAME (cl), 
6629                             EXPR_WFL_LINENO (cl), EXPR_WFL_COLNO (cl));
6630
6631   found = strstr ((const char *)line, 
6632                   (const char *)IDENTIFIER_POINTER (DECL_NAME (decl)));
6633   if (found)
6634     EXPR_WFL_SET_LINECOL (cl, EXPR_WFL_LINENO (cl), found - line);
6635
6636   return cl;
6637 }
6638
6639 /* Look for a simple name in the single-type import list */
6640
6641 static tree
6642 find_name_in_single_imports (name)
6643      tree name;
6644 {
6645   tree node;
6646
6647   for (node = ctxp->import_list; node; node = TREE_CHAIN (node))
6648     if (TREE_VALUE (node) == name)
6649       return (EXPR_WFL_NODE (TREE_PURPOSE (node)));
6650
6651   return NULL_TREE;
6652 }
6653
6654 /* Process all single-type import. */
6655
6656 static int
6657 process_imports ()
6658 {
6659   tree import;
6660   int error_found;
6661
6662   for (import = ctxp->import_list; import; import = TREE_CHAIN (import))
6663     {
6664       tree to_be_found = EXPR_WFL_NODE (TREE_PURPOSE (import));
6665       char *original_name;
6666
6667       obstack_grow0 (&temporary_obstack,
6668                      IDENTIFIER_POINTER (to_be_found),
6669                      IDENTIFIER_LENGTH (to_be_found));
6670       original_name = obstack_finish (&temporary_obstack);
6671
6672       /* Don't load twice something already defined. */
6673       if (IDENTIFIER_CLASS_VALUE (to_be_found))
6674         continue;
6675       
6676       while (1)
6677         {
6678           tree left;
6679
6680           QUALIFIED_P (to_be_found) = 1;
6681           load_class (to_be_found, 0);
6682           error_found =
6683             check_pkg_class_access (to_be_found, TREE_PURPOSE (import), true);
6684           
6685           /* We found it, we can bail out */
6686           if (IDENTIFIER_CLASS_VALUE (to_be_found))
6687             break;
6688
6689           /* We haven't found it. Maybe we're trying to access an
6690              inner class.  The only way for us to know is to try again
6691              after having dropped a qualifier. If we can't break it further,
6692              we have an error. */
6693           if (breakdown_qualified (&left, NULL, to_be_found))
6694             break;
6695
6696           to_be_found = left;
6697         }
6698       if (!IDENTIFIER_CLASS_VALUE (to_be_found))
6699         {
6700           parse_error_context (TREE_PURPOSE (import),
6701                                "Class or interface `%s' not found in import",
6702                                original_name);
6703           error_found = 1;
6704         }
6705
6706       obstack_free (&temporary_obstack, original_name);
6707       if (error_found)
6708         return 1;
6709     }
6710   return 0;
6711 }
6712
6713 /* Possibly find and mark a class imported by a single-type import
6714    statement.  */
6715
6716 static void
6717 find_in_imports (enclosing_type, class_type)
6718      tree enclosing_type;
6719      tree class_type;
6720 {
6721   tree import = (enclosing_type ? TYPE_IMPORT_LIST (enclosing_type) : 
6722                  ctxp->import_list);
6723   while (import)
6724     {
6725       if (TREE_VALUE (import) == TYPE_NAME (class_type))
6726         {
6727           TYPE_NAME (class_type) = EXPR_WFL_NODE (TREE_PURPOSE (import));
6728           QUALIFIED_P (TYPE_NAME (class_type)) = 1;
6729           return;
6730         }
6731       import = TREE_CHAIN (import);
6732     }
6733 }
6734
6735 static int
6736 note_possible_classname (name, len)
6737      const char *name;
6738      int len;
6739 {
6740   tree node;
6741   if (len > 5 && strncmp (&name [len-5], ".java", 5) == 0)
6742     len = len - 5;
6743   else if (len > 6 && strncmp (&name [len-6], ".class", 6) == 0)
6744     len = len - 6;
6745   else
6746     return 0;
6747   node = ident_subst (name, len, "", '/', '.', "");
6748   IS_A_CLASSFILE_NAME (node) = 1; /* Or soon to be */
6749   QUALIFIED_P (node) = strchr (name, '/') ? 1 : 0;
6750   return 1;
6751 }
6752
6753 /* Read a import directory, gathering potential match for further type
6754    references. Indifferently reads a filesystem or a ZIP archive
6755    directory.  */
6756
6757 static void
6758 read_import_dir (wfl)
6759      tree wfl;
6760 {
6761   tree package_id = EXPR_WFL_NODE (wfl);
6762   const char *package_name = IDENTIFIER_POINTER (package_id);
6763   int package_length = IDENTIFIER_LENGTH (package_id);
6764   DIR *dirp = NULL;
6765   JCF *saved_jcf = current_jcf;
6766
6767   int found = 0;
6768   int k;
6769   void *entry;
6770   struct buffer filename[1];
6771
6772   if (IS_AN_IMPORT_ON_DEMAND_P (package_id))
6773     return;
6774   IS_AN_IMPORT_ON_DEMAND_P (package_id) = 1;
6775
6776   BUFFER_INIT (filename);
6777   buffer_grow (filename, package_length + 100);
6778
6779   for (entry = jcf_path_start (); entry != NULL; entry = jcf_path_next (entry))
6780     {
6781       const char *entry_name = jcf_path_name (entry);
6782       int entry_length = strlen (entry_name);
6783       if (jcf_path_is_zipfile (entry))
6784         {
6785           ZipFile *zipf;
6786           buffer_grow (filename, entry_length);
6787           memcpy (filename->data, entry_name, entry_length - 1);
6788           filename->data[entry_length-1] = '\0';
6789           zipf = opendir_in_zip (filename->data, jcf_path_is_system (entry));
6790           if (zipf == NULL)
6791             error ("malformed .zip archive in CLASSPATH: %s", entry_name);
6792           else
6793             {
6794               ZipDirectory *zipd = (ZipDirectory *) zipf->central_directory;
6795               BUFFER_RESET (filename);
6796               for (k = 0; k < package_length; k++)
6797                 {
6798                   char ch = package_name[k];
6799                   *filename->ptr++ = ch == '.' ? '/' : ch;
6800                 }
6801               *filename->ptr++ = '/';
6802
6803               for (k = 0; k < zipf->count;  k++, zipd = ZIPDIR_NEXT (zipd))
6804                 {
6805                   const char *current_entry = ZIPDIR_FILENAME (zipd);
6806                   int current_entry_len = zipd->filename_length;
6807
6808                   if (current_entry_len >= BUFFER_LENGTH (filename)
6809                       && strncmp (filename->data, current_entry, 
6810                                   BUFFER_LENGTH (filename)) != 0)
6811                     continue;
6812                   found |= note_possible_classname (current_entry,
6813                                                     current_entry_len);
6814                 }
6815             }
6816         }
6817       else
6818         {
6819           BUFFER_RESET (filename);
6820           buffer_grow (filename, entry_length + package_length + 4);
6821           strcpy (filename->data, entry_name);
6822           filename->ptr = filename->data + entry_length;
6823           for (k = 0; k < package_length; k++)
6824             {
6825               char ch = package_name[k];
6826               *filename->ptr++ = ch == '.' ? '/' : ch;
6827             }
6828           *filename->ptr = '\0';
6829
6830           dirp = opendir (filename->data);
6831           if (dirp == NULL)
6832             continue;
6833           *filename->ptr++ = '/';
6834           for (;;)
6835             {
6836               int len; 
6837               const char *d_name;
6838               struct dirent *direntp = readdir (dirp);
6839               if (!direntp)
6840                 break;
6841               d_name = direntp->d_name;
6842               len = strlen (direntp->d_name);
6843               buffer_grow (filename, len+1);
6844               strcpy (filename->ptr, d_name);
6845               found |= note_possible_classname (filename->data + entry_length,
6846                                                 package_length+len+1);
6847             }
6848           if (dirp)
6849             closedir (dirp);
6850         }
6851     }
6852
6853   free (filename->data);
6854
6855   /* Here we should have a unified way of retrieving an entry, to be
6856      indexed. */
6857   if (!found)
6858     {
6859       static int first = 1;
6860       if (first)
6861         {
6862           error ("Can't find default package `%s'. Check the CLASSPATH environment variable and the access to the archives", package_name);
6863           java_error_count++;
6864           first = 0;
6865         }
6866       else
6867         parse_error_context (wfl, "Package `%s' not found in import",
6868                              package_name);
6869       current_jcf = saved_jcf;
6870       return;
6871     }
6872   current_jcf = saved_jcf;
6873 }
6874
6875 /* Possibly find a type in the import on demands specified
6876    types. Returns 1 if an error occurred, 0 otherwise. Run through the
6877    entire list, to detected potential double definitions.  */
6878                  
6879 static int
6880 find_in_imports_on_demand (enclosing_type, class_type)
6881      tree enclosing_type;
6882      tree class_type;
6883 {
6884   tree class_type_name = TYPE_NAME (class_type);
6885   tree import = (enclosing_type ? TYPE_IMPORT_DEMAND_LIST (enclosing_type) :
6886                   ctxp->import_demand_list);
6887   tree cl = NULL_TREE;
6888   int seen_once = -1;   /* -1 when not set, 1 if seen once, >1 otherwise. */
6889   int to_return = -1;   /* -1 when not set, 0 or 1 otherwise */
6890   tree node;
6891
6892   for (; import; import = TREE_CHAIN (import))
6893     {
6894       int saved_lineno = lineno;
6895       int access_check;
6896       const char *id_name;
6897       tree decl, type_name_copy;
6898
6899       obstack_grow (&temporary_obstack, 
6900                     IDENTIFIER_POINTER (EXPR_WFL_NODE (TREE_PURPOSE (import))),
6901                     IDENTIFIER_LENGTH (EXPR_WFL_NODE (TREE_PURPOSE (import))));
6902       obstack_1grow (&temporary_obstack, '.');
6903       obstack_grow0 (&temporary_obstack, 
6904                      IDENTIFIER_POINTER (class_type_name),
6905                      IDENTIFIER_LENGTH (class_type_name));
6906       id_name = obstack_finish (&temporary_obstack);
6907               
6908       if (! (node = maybe_get_identifier (id_name)))
6909         continue;
6910
6911       /* Setup lineno so that it refers to the line of the import (in
6912          case we parse a class file and encounter errors */
6913       lineno = EXPR_WFL_LINENO (TREE_PURPOSE (import));
6914
6915       type_name_copy = TYPE_NAME (class_type);
6916       TYPE_NAME (class_type) = node;
6917       QUALIFIED_P (node) = 1;
6918       decl = IDENTIFIER_CLASS_VALUE (node);
6919       access_check = -1;
6920       /* If there is no DECL set for the class or if the class isn't
6921          loaded and not seen in source yet, then load */
6922       if (!decl || (!CLASS_LOADED_P (TREE_TYPE (decl))
6923                     && !CLASS_FROM_SOURCE_P (TREE_TYPE (decl))))
6924         {
6925           load_class (node, 0);
6926           decl = IDENTIFIER_CLASS_VALUE (node);
6927         }
6928       if (decl && ! INNER_CLASS_P (TREE_TYPE (decl)))
6929         access_check = check_pkg_class_access (node, TREE_PURPOSE (import),
6930                                                false);
6931       else
6932         /* 6.6.1: Inner classes are subject to member access rules. */
6933         access_check = 0;
6934
6935       lineno = saved_lineno;
6936
6937       /* If the loaded class is not accessible or couldn't be loaded,
6938          we restore the original TYPE_NAME and process the next
6939          import. */
6940       if (access_check || !decl)
6941         {
6942           TYPE_NAME (class_type) = type_name_copy;
6943           continue;
6944         }
6945       
6946       /* If the loaded class is accessible, we keep a tab on it to
6947          detect and report multiple inclusions. */
6948       if (IS_A_CLASSFILE_NAME (node))
6949         {
6950           if (seen_once < 0)
6951             {
6952               cl = TREE_PURPOSE (import);
6953               seen_once = 1;
6954             }
6955           else if (seen_once >= 0)
6956             {
6957               tree location = (cl ? cl : TREE_PURPOSE (import));
6958               tree package = (cl ? EXPR_WFL_NODE (cl) : 
6959                               EXPR_WFL_NODE (TREE_PURPOSE (import)));
6960               seen_once++;
6961               parse_error_context 
6962                 (location,
6963                  "Type `%s' also potentially defined in package `%s'",
6964                  IDENTIFIER_POINTER (TYPE_NAME (class_type)), 
6965                  IDENTIFIER_POINTER (package));
6966             }
6967         }
6968       to_return = access_check;
6969     }
6970
6971   if (seen_once == 1)
6972     return to_return;
6973   else
6974     return (seen_once < 0 ? 0 : seen_once); /* It's ok not to have found */
6975 }
6976
6977 /* Add package NAME to the list of package encountered so far. To
6978    speed up class lookup in do_resolve_class, we make sure a
6979    particular package is added only once.  */
6980
6981 static void
6982 register_package (name)
6983      tree name;
6984 {
6985   static struct hash_table _pht, *pht = NULL;
6986
6987   if (!pht)
6988     {
6989       hash_table_init (&_pht, hash_newfunc, 
6990                        java_hash_hash_tree_node, java_hash_compare_tree_node);
6991       pht = &_pht;
6992     }
6993   
6994   if (!hash_lookup (pht, (const hash_table_key) name, FALSE, NULL))
6995     {
6996       package_list = chainon (package_list, build_tree_list (name, NULL));
6997       hash_lookup (pht, (const hash_table_key) name, TRUE, NULL);
6998     }
6999 }
7000
7001 static tree
7002 resolve_package (pkg, next)
7003      tree pkg, *next;
7004 {
7005   tree current, acc;
7006   tree type_name = NULL_TREE;
7007   const char *name = IDENTIFIER_POINTER (EXPR_WFL_NODE (pkg));
7008
7009   /* The trick is to determine when the package name stops and were
7010      the name of something contained in the package starts. Then we
7011      return a fully qualified name of what we want to get. */
7012
7013   /* Do a quick search on well known package names */
7014   if (!strncmp (name, "java.lang.reflect", 17))
7015     {
7016       *next = 
7017         TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (EXPR_WFL_QUALIFICATION (pkg))));
7018       type_name = lookup_package_type (name, 17);
7019     }
7020   else if (!strncmp (name, "java.lang", 9))
7021     {
7022       *next = TREE_CHAIN (TREE_CHAIN (EXPR_WFL_QUALIFICATION (pkg)));
7023       type_name = lookup_package_type (name, 9);
7024     }
7025
7026   /* If we found something here, return */
7027   if (type_name)
7028     return type_name; 
7029
7030   *next = EXPR_WFL_QUALIFICATION (pkg);
7031
7032   /* Try to progressively construct a type name */
7033   if (TREE_CODE (pkg) == EXPR_WITH_FILE_LOCATION)
7034     for (acc = NULL_TREE, current = EXPR_WFL_QUALIFICATION (pkg); 
7035          current; current = TREE_CHAIN (current))
7036       {
7037         /* If we don't have what we're expecting, exit now. TYPE_NAME
7038            will be null and the error caught later. */
7039         if (TREE_CODE (QUAL_WFL (current)) != EXPR_WITH_FILE_LOCATION)
7040           break;
7041         acc = merge_qualified_name (acc, EXPR_WFL_NODE (QUAL_WFL (current)));
7042         if ((type_name = resolve_no_layout (acc, NULL_TREE)))
7043           {
7044             type_name = acc;
7045             /* resolve_package should be used in a loop, hence we
7046                point at this one to naturally process the next one at
7047                the next iteration. */
7048             *next = current;
7049             break;
7050           }
7051       }
7052   return type_name;
7053 }
7054
7055 static tree
7056 lookup_package_type (name, from)
7057      const char *name;
7058      int from;
7059 {
7060   char subname [128];
7061   const char *sub = &name[from+1];
7062   while (*sub != '.' && *sub)
7063     sub++;
7064   strncpy (subname, name, sub-name);
7065   subname [sub-name] = '\0';
7066   return get_identifier (subname);
7067 }
7068
7069 /* Check accessibility of inner classes according to member access rules. 
7070    DECL is the inner class, ENCLOSING_DECL is the class from which the
7071    access is being attempted. */
7072
7073 static void
7074 check_inner_class_access (decl, enclosing_decl, cl)
7075      tree decl, enclosing_decl, cl;
7076 {
7077   const char *access;
7078   tree enclosing_decl_type;
7079
7080   /* We don't issue an error message when CL is null. CL can be null
7081      as a result of processing a JDEP crafted by source_start_java_method
7082      for the purpose of patching its parm decl. But the error would
7083      have been already trapped when fixing the method's signature.
7084      DECL can also be NULL in case of earlier errors. */
7085   if (!decl || !cl)
7086     return;
7087
7088   enclosing_decl_type = TREE_TYPE (enclosing_decl);
7089
7090   if (CLASS_PRIVATE (decl))
7091     {
7092       /* Access is permitted only within the body of the top-level
7093          class in which DECL is declared. */
7094       tree top_level = decl;
7095       while (DECL_CONTEXT (top_level))
7096         top_level = DECL_CONTEXT (top_level);      
7097       while (DECL_CONTEXT (enclosing_decl))
7098         enclosing_decl = DECL_CONTEXT (enclosing_decl);
7099       if (top_level == enclosing_decl)
7100         return;      
7101       access = "private";
7102     }
7103   else if (CLASS_PROTECTED (decl))
7104     {
7105       tree decl_context;
7106       /* Access is permitted from within the same package... */
7107       if (in_same_package (decl, enclosing_decl))
7108         return;
7109       
7110       /* ... or from within the body of a subtype of the context in which
7111          DECL is declared. */
7112       decl_context = DECL_CONTEXT (decl);
7113       while (enclosing_decl)
7114         {
7115           if (CLASS_INTERFACE (decl))
7116             {
7117               if (interface_of_p (TREE_TYPE (decl_context), 
7118                                   enclosing_decl_type))
7119                 return;
7120             }
7121           else
7122             {
7123               /* Eww. The order of the arguments is different!! */
7124               if (inherits_from_p (enclosing_decl_type, 
7125                                    TREE_TYPE (decl_context)))
7126                 return;
7127             }
7128           enclosing_decl = DECL_CONTEXT (enclosing_decl);
7129         }      
7130       access = "protected";
7131     }
7132   else if (! CLASS_PUBLIC (decl))
7133     {
7134       /* Access is permitted only from within the same package as DECL. */
7135       if (in_same_package (decl, enclosing_decl))
7136         return;
7137       access = "non-public";
7138     }
7139   else
7140     /* Class is public. */
7141     return;
7142
7143   parse_error_context (cl, "Nested %s %s is %s; cannot be accessed from here",
7144                        (CLASS_INTERFACE (decl) ? "interface" : "class"),
7145                        lang_printable_name (decl, 0), access);
7146 }
7147
7148 /* Accessibility check for top-level classes. If CLASS_NAME is in a
7149    foreign package, it must be PUBLIC. Return 0 if no access
7150    violations were found, 1 otherwise. If VERBOSE is true and an error
7151    was found, it is reported and accounted for.  */
7152
7153 static int
7154 check_pkg_class_access (class_name, cl, verbose)
7155      tree class_name;
7156      tree cl;
7157      bool verbose;
7158 {
7159   tree type;
7160
7161   if (!IDENTIFIER_CLASS_VALUE (class_name))
7162     return 0;
7163
7164   if (!(type = TREE_TYPE (IDENTIFIER_CLASS_VALUE (class_name))))
7165     return 0;
7166
7167   if (!CLASS_PUBLIC (TYPE_NAME (type)))
7168     {
7169       /* Access to a private class within the same package is
7170          allowed. */
7171       tree l, r;
7172       breakdown_qualified (&l, &r, class_name);
7173       if (!QUALIFIED_P (class_name) && !ctxp->package)
7174         /* Both in the empty package. */
7175         return 0;
7176       if (l == ctxp->package)
7177         /* Both in the same package. */
7178         return 0;
7179
7180       if (verbose)
7181         parse_error_context 
7182           (cl, "Can't access %s `%s'. Only public classes and interfaces in other packages can be accessed",
7183            (CLASS_INTERFACE (TYPE_NAME (type)) ? "interface" : "class"),
7184            IDENTIFIER_POINTER (class_name));
7185       return 1;
7186     }
7187   return 0;
7188 }
7189
7190 /* Local variable declaration. */
7191
7192 static void
7193 declare_local_variables (modifier, type, vlist)
7194      int modifier;
7195      tree type;
7196      tree vlist;
7197 {
7198   tree decl, current, saved_type;
7199   tree type_wfl = NULL_TREE;
7200   int must_chain = 0;
7201   int final_p = 0;
7202
7203   /* Push a new block if statements were seen between the last time we
7204      pushed a block and now. Keep a count of blocks to close */
7205   if (BLOCK_EXPR_BODY (GET_CURRENT_BLOCK (current_function_decl)))
7206     {
7207       tree b = enter_block ();
7208       BLOCK_IS_IMPLICIT (b) = 1;
7209     }
7210
7211   if (modifier)
7212     {
7213       int i;
7214       for (i = 0; i <= 10; i++) if (1 << i & modifier) break;
7215       if (modifier == ACC_FINAL)
7216         final_p = 1;
7217       else 
7218         {
7219           parse_error_context 
7220             (ctxp->modifier_ctx [i], 
7221              "Only `final' is allowed as a local variables modifier");
7222           return;
7223         }
7224     }
7225
7226   /* Obtain an incomplete type if TYPE is not complete. TYPE_WFL will
7227      hold the TYPE value if a new incomplete has to be created (as
7228      opposed to being found already existing and reused). */
7229   SET_TYPE_FOR_RESOLUTION (type, type_wfl, must_chain);
7230
7231   /* If TYPE is fully resolved and we don't have a reference, make one */
7232   PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
7233
7234   /* Go through all the declared variables */
7235   for (current = vlist, saved_type = type; current;
7236        current = TREE_CHAIN (current), type = saved_type)
7237     {
7238       tree other, real_type;
7239       tree wfl  = TREE_PURPOSE (current);
7240       tree name = EXPR_WFL_NODE (wfl);
7241       tree init = TREE_VALUE (current);
7242
7243       /* Process NAME, as it may specify extra dimension(s) for it */
7244       type = build_array_from_name (type, type_wfl, name, &name);
7245
7246       /* Variable redefinition check */
7247       if ((other = lookup_name_in_blocks (name)))
7248         {
7249           variable_redefinition_error (wfl, name, TREE_TYPE (other),
7250                                        DECL_SOURCE_LINE (other));
7251           continue;
7252         }
7253
7254       /* Type adjustment. We may have just readjusted TYPE because
7255          the variable specified more dimensions. Make sure we have
7256          a reference if we can and don't have one already. */
7257       PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
7258
7259       real_type = GET_REAL_TYPE (type);
7260       /* Never layout this decl. This will be done when its scope
7261          will be entered */
7262       decl = build_decl (VAR_DECL, name, real_type);
7263       MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC (decl);
7264       DECL_FINAL (decl) = final_p;
7265       BLOCK_CHAIN_DECL (decl);
7266       
7267       /* If doing xreferencing, replace the line number with the WFL
7268          compound value */
7269       if (flag_emit_xref)
7270         DECL_SOURCE_LINE (decl) = EXPR_WFL_LINECOL (wfl);
7271       
7272       /* Don't try to use an INIT statement when an error was found */
7273       if (init && java_error_count)
7274         init = NULL_TREE;
7275       
7276       /* Add the initialization function to the current function's code */
7277       if (init)
7278         {
7279           /* Name might have been readjusted */
7280           EXPR_WFL_NODE (TREE_OPERAND (init, 0)) = name;
7281           MODIFY_EXPR_FROM_INITIALIZATION_P (init) = 1;
7282           java_method_add_stmt (current_function_decl,
7283                                 build_debugable_stmt (EXPR_WFL_LINECOL (init),
7284                                                       init));
7285         }
7286     
7287       /* Setup dependency the type of the decl */
7288       if (must_chain)
7289         {
7290           jdep *dep;
7291           register_incomplete_type (JDEP_VARIABLE, type_wfl, decl, type);
7292           dep = CLASSD_LAST (ctxp->classd_list);
7293           JDEP_GET_PATCH (dep) = &TREE_TYPE (decl);
7294         }
7295     }
7296   SOURCE_FRONTEND_DEBUG (("Defined locals"));
7297 }
7298
7299 /* Called during parsing. Build decls from argument list.  */
7300
7301 static void
7302 source_start_java_method (fndecl)
7303      tree fndecl;
7304 {
7305   tree tem;
7306   tree parm_decl;
7307   int i;
7308
7309   if (!fndecl)
7310     return;
7311
7312   current_function_decl = fndecl;
7313
7314   /* New scope for the function */
7315   enter_block ();
7316   for (tem = TYPE_ARG_TYPES (TREE_TYPE (fndecl)), i = 0;
7317        tem != end_params_node; tem = TREE_CHAIN (tem), i++)
7318     {
7319       tree type = TREE_VALUE (tem);
7320       tree name = TREE_PURPOSE (tem);
7321       
7322       /* If type is incomplete. Create an incomplete decl and ask for
7323          the decl to be patched later */
7324       if (INCOMPLETE_TYPE_P (type))
7325         {
7326           jdep *jdep;
7327           tree real_type = GET_REAL_TYPE (type);
7328           parm_decl = build_decl (PARM_DECL, name, real_type);
7329           type = obtain_incomplete_type (type);
7330           register_incomplete_type (JDEP_PARM, NULL_TREE, NULL_TREE, type);
7331           jdep = CLASSD_LAST (ctxp->classd_list);
7332           JDEP_MISC (jdep) = name;
7333           JDEP_GET_PATCH (jdep) = &TREE_TYPE (parm_decl);
7334         }
7335       else
7336         parm_decl = build_decl (PARM_DECL, name, type);
7337
7338       /* Remember if a local variable was declared final (via its
7339          TREE_LIST of type/name.) Set DECL_FINAL accordingly. */
7340       if (ARG_FINAL_P (tem))
7341         {
7342           MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC (parm_decl);
7343           DECL_FINAL (parm_decl) = 1;
7344         }
7345
7346       BLOCK_CHAIN_DECL (parm_decl);
7347     }
7348   tem = BLOCK_EXPR_DECLS (DECL_FUNCTION_BODY (current_function_decl));
7349   BLOCK_EXPR_DECLS (DECL_FUNCTION_BODY (current_function_decl)) =
7350     nreverse (tem);
7351   DECL_ARG_SLOT_COUNT (current_function_decl) = i;
7352   DECL_MAX_LOCALS (current_function_decl) = i;
7353 }
7354
7355 /* Called during parsing. Creates an artificial method declaration.  */
7356
7357 static tree
7358 create_artificial_method (class, flags, type, name, args)
7359      tree class;
7360      int flags;
7361      tree type, name, args;
7362 {
7363   tree mdecl;
7364
7365   java_parser_context_save_global ();
7366   lineno = 0;                                                               
7367   mdecl = make_node (FUNCTION_TYPE);                                
7368   TREE_TYPE (mdecl) = type;
7369   TYPE_ARG_TYPES (mdecl) = args;
7370   mdecl = add_method (class, flags, name, build_java_signature (mdecl)); 
7371   java_parser_context_restore_global ();
7372   DECL_ARTIFICIAL (mdecl) = 1;                                      
7373   return mdecl;
7374 }
7375
7376 /* Starts the body if an artificial method.  */
7377
7378 static void
7379 start_artificial_method_body (mdecl)
7380      tree mdecl;
7381 {
7382   DECL_SOURCE_LINE (mdecl) = 1;
7383   DECL_SOURCE_LINE_MERGE (mdecl, 1);
7384   source_start_java_method (mdecl);
7385   enter_block ();
7386 }
7387
7388 static void
7389 end_artificial_method_body (mdecl)
7390      tree mdecl;
7391 {
7392   /* exit_block modifies DECL_FUNCTION_BODY (current_function_decl).
7393      It has to be evaluated first. (if mdecl is current_function_decl,
7394      we have an undefined behavior if no temporary variable is used.) */
7395   tree b = exit_block ();
7396   BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (mdecl)) = b;
7397   exit_block ();
7398 }
7399
7400 /* Dump a tree of some kind.  This is a convenience wrapper for the
7401    dump_* functions in tree-dump.c.  */
7402 static void
7403 dump_java_tree (phase, t)
7404      enum tree_dump_index phase;
7405      tree t;
7406 {
7407   FILE *stream;
7408   int flags;
7409
7410   stream = dump_begin (phase, &flags);
7411   if (stream)
7412     {
7413       dump_node (t, flags, stream);
7414       dump_end (phase, stream);
7415     }
7416 }
7417
7418 /* Terminate a function and expand its body.  */
7419
7420 static void
7421 source_end_java_method ()
7422 {
7423   tree fndecl = current_function_decl;
7424
7425   if (!fndecl)
7426     return;
7427
7428   java_parser_context_save_global ();
7429   lineno = ctxp->last_ccb_indent1;
7430
7431   /* Turn function bodies with only a NOP expr null, so they don't get
7432      generated at all and we won't get warnings when using the -W
7433      -Wall flags. */
7434   if (BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (fndecl)) == empty_stmt_node)
7435     BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (fndecl)) = NULL_TREE;
7436
7437   /* We've generated all the trees for this function, and it has been
7438      patched.  Dump it to a file if the user requested it.  */
7439   dump_java_tree (TDI_original, fndecl);
7440
7441   /* Generate function's code */
7442   if (BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (fndecl))
7443       && ! flag_emit_class_files
7444       && ! flag_emit_xref)
7445     expand_expr_stmt (BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (fndecl)));
7446
7447   /* pop out of its parameters */
7448   pushdecl_force_head (DECL_ARGUMENTS (fndecl));
7449   poplevel (1, 0, 1);
7450   BLOCK_SUPERCONTEXT (DECL_INITIAL (fndecl)) = fndecl;
7451
7452   /* Generate rtl for function exit.  */
7453   if (! flag_emit_class_files && ! flag_emit_xref)
7454     {
7455       lineno = DECL_SOURCE_LINE_LAST (fndecl);
7456       expand_function_end (input_filename, lineno, 0);
7457
7458       /* Run the optimizers and output assembler code for this function. */
7459       rest_of_compilation (fndecl);
7460     }
7461
7462   current_function_decl = NULL_TREE;
7463   java_parser_context_restore_global ();
7464 }
7465
7466 /* Record EXPR in the current function block. Complements compound
7467    expression second operand if necessary.  */
7468
7469 tree
7470 java_method_add_stmt (fndecl, expr)
7471      tree fndecl, expr;
7472 {
7473   if (!GET_CURRENT_BLOCK (fndecl))
7474     return NULL_TREE;
7475   return add_stmt_to_block (GET_CURRENT_BLOCK (fndecl), NULL_TREE, expr);
7476 }
7477
7478 static tree
7479 add_stmt_to_block (b, type, stmt)
7480      tree b, type, stmt;
7481 {
7482   tree body = BLOCK_EXPR_BODY (b), c;
7483   
7484   if (java_error_count)
7485     return body;
7486     
7487   if ((c = add_stmt_to_compound (body, type, stmt)) == body)
7488     return body;
7489
7490   BLOCK_EXPR_BODY (b) = c;
7491   TREE_SIDE_EFFECTS (c) = 1;
7492   return c;
7493 }
7494
7495 /* Add STMT to EXISTING if possible, otherwise create a new
7496    COMPOUND_EXPR and add STMT to it. */
7497
7498 static tree
7499 add_stmt_to_compound (existing, type, stmt)
7500      tree existing, type, stmt;
7501 {
7502   if (existing)
7503     return build (COMPOUND_EXPR, type, existing, stmt);
7504   else
7505     return stmt;
7506 }
7507
7508 void java_layout_seen_class_methods ()
7509 {
7510   tree previous_list = all_class_list;
7511   tree end = NULL_TREE;
7512   tree current;
7513
7514   while (1)
7515     {
7516       for (current = previous_list; 
7517            current != end; current = TREE_CHAIN (current))
7518         layout_class_methods (TREE_TYPE (TREE_VALUE (current)));
7519       
7520       if (previous_list != all_class_list)
7521         {
7522           end = previous_list;
7523           previous_list = all_class_list;
7524         }
7525       else
7526         break;
7527     }
7528 }
7529
7530 void
7531 java_reorder_fields ()
7532 {
7533   static tree stop_reordering = NULL_TREE;
7534   static int initialized_p;
7535   tree current;
7536
7537   /* Register STOP_REORDERING with the garbage collector.  */
7538   if (!initialized_p)
7539     {
7540       ggc_add_tree_root (&stop_reordering, 1);
7541       initialized_p = 1;
7542     }
7543
7544   for (current = gclass_list; current; current = TREE_CHAIN (current))
7545     {
7546       current_class = TREE_TYPE (TREE_VALUE (current));
7547
7548       if (current_class == stop_reordering)
7549         break;
7550
7551       /* Reverse the fields, but leave the dummy field in front.
7552          Fields are already ordered for Object and Class */
7553       if (TYPE_FIELDS (current_class) && current_class != object_type_node
7554           && current_class != class_type_node)
7555       {
7556         /* If the dummy field is there, reverse the right fields and
7557            just layout the type for proper fields offset */
7558         if (!DECL_NAME (TYPE_FIELDS (current_class)))
7559           {
7560             tree fields = TYPE_FIELDS (current_class);
7561             TREE_CHAIN (fields) = nreverse (TREE_CHAIN (fields));
7562             TYPE_SIZE (current_class) = NULL_TREE;
7563           }
7564         /* We don't have a dummy field, we need to layout the class,
7565            after having reversed the fields */
7566         else
7567           {
7568             TYPE_FIELDS (current_class) = 
7569               nreverse (TYPE_FIELDS (current_class));
7570             TYPE_SIZE (current_class) = NULL_TREE;
7571           }
7572       }
7573     }
7574   /* There are cases were gclass_list will be empty. */
7575   if (gclass_list)
7576     stop_reordering = TREE_TYPE (TREE_VALUE (gclass_list));
7577 }
7578
7579 /* Layout the methods of all classes loaded in one way or another.
7580    Check methods of source parsed classes. Then reorder the
7581    fields and layout the classes or the type of all source parsed
7582    classes */
7583
7584 void
7585 java_layout_classes ()
7586 {
7587   tree current;
7588   int save_error_count = java_error_count;
7589
7590   /* Layout the methods of all classes seen so far */
7591   java_layout_seen_class_methods ();
7592   java_parse_abort_on_error ();
7593   all_class_list = NULL_TREE;
7594
7595   /* Then check the methods of all parsed classes */
7596   for (current = gclass_list; current; current = TREE_CHAIN (current))
7597     if (CLASS_FROM_SOURCE_P (TREE_TYPE (TREE_VALUE (current))))
7598       java_check_methods (TREE_VALUE (current));
7599   java_parse_abort_on_error ();
7600
7601   for (current = gclass_list; current; current = TREE_CHAIN (current))
7602     {
7603       current_class = TREE_TYPE (TREE_VALUE (current));
7604       layout_class (current_class);
7605
7606       /* Error reported by the caller */
7607       if (java_error_count)
7608         return;
7609     }
7610
7611   /* We might have reloaded classes durign the process of laying out
7612      classes for code generation. We must layout the methods of those
7613      late additions, as constructor checks might use them */
7614   java_layout_seen_class_methods ();
7615   java_parse_abort_on_error ();
7616 }
7617
7618 /* Expand methods in the current set of classes rememebered for
7619    generation.  */
7620
7621 static void
7622 java_complete_expand_classes ()
7623 {
7624   tree current;
7625
7626   do_not_fold = flag_emit_xref;
7627
7628   for (current = ctxp->class_list; current; current = TREE_CHAIN (current))
7629     if (!INNER_CLASS_DECL_P (current))
7630       java_complete_expand_class (current);
7631 }
7632
7633 /* Expand the methods found in OUTER, starting first by OUTER's inner
7634    classes, if any.  */
7635
7636 static void
7637 java_complete_expand_class (outer)
7638      tree outer;
7639 {
7640   tree inner_list;
7641
7642   set_nested_class_simple_name_value (outer, 1); /* Set */
7643
7644   /* We need to go after all inner classes and start expanding them,
7645      starting with most nested ones. We have to do that because nested
7646      classes might add functions to outer classes */
7647
7648   for (inner_list = DECL_INNER_CLASS_LIST (outer);
7649        inner_list; inner_list = TREE_CHAIN (inner_list))
7650     java_complete_expand_class (TREE_PURPOSE (inner_list));
7651
7652   java_complete_expand_methods (outer);
7653   set_nested_class_simple_name_value (outer, 0); /* Reset */
7654 }
7655
7656 /* Expand methods registered in CLASS_DECL. The general idea is that
7657    we expand regular methods first. This allows us get an estimate on
7658    how outer context local alias fields are really used so we can add
7659    to the constructor just enough code to initialize them properly (it
7660    also lets us generate finit$ correctly.) Then we expand the
7661    constructors and then <clinit>.  */
7662
7663 static void
7664 java_complete_expand_methods (class_decl)
7665      tree class_decl;
7666 {
7667   tree clinit, decl, first_decl;
7668
7669   current_class = TREE_TYPE (class_decl);
7670
7671   /* Initialize a new constant pool */
7672   init_outgoing_cpool ();
7673
7674   /* Pre-expand <clinit> to figure whether we really need it or
7675      not. If we do need it, we pre-expand the static fields so they're
7676      ready to be used somewhere else. <clinit> will be fully expanded
7677      after we processed the constructors. */
7678   first_decl = TYPE_METHODS (current_class);
7679   clinit = maybe_generate_pre_expand_clinit (current_class);
7680
7681   /* Then generate finit$ (if we need to) because constructors will
7682    try to use it.*/
7683   if (TYPE_FINIT_STMT_LIST (current_class))
7684     java_complete_expand_method (generate_finit (current_class));
7685
7686   /* Then generate instinit$ (if we need to) because constructors will
7687      try to use it. */
7688   if (TYPE_II_STMT_LIST (current_class))
7689     java_complete_expand_method (generate_instinit (current_class));
7690
7691   /* Now do the constructors */
7692   for (decl = first_decl ; !java_error_count && decl; decl = TREE_CHAIN (decl))
7693     {
7694       int no_body;
7695
7696       if (!DECL_CONSTRUCTOR_P (decl))
7697         continue;
7698       
7699       no_body = !DECL_FUNCTION_BODY (decl);
7700       /* Don't generate debug info on line zero when expanding a
7701          generated constructor. */
7702       if (no_body)
7703         restore_line_number_status (1);
7704
7705       java_complete_expand_method (decl);
7706
7707       if (no_body)
7708         restore_line_number_status (0);
7709     }
7710
7711   /* First, do the ordinary methods. */
7712   for (decl = first_decl; decl; decl = TREE_CHAIN (decl))
7713     {
7714       /* Ctors aren't part of this batch. */
7715       if (DECL_CONSTRUCTOR_P (decl) || DECL_CLINIT_P (decl))
7716         continue;
7717       
7718       /* Skip abstract or native methods -- but do handle native
7719          methods when generating JNI stubs.  */
7720       if (METHOD_ABSTRACT (decl) || (! flag_jni && METHOD_NATIVE (decl)))
7721         {
7722           DECL_FUNCTION_BODY (decl) = NULL_TREE;
7723           continue;
7724         }
7725
7726       if (METHOD_NATIVE (decl))
7727         {
7728           tree body;
7729           current_function_decl = decl;
7730           body = build_jni_stub (decl);
7731           BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (decl)) = body;
7732         }
7733
7734       java_complete_expand_method (decl);
7735     }
7736
7737   /* If there is indeed a <clinit>, fully expand it now */
7738   if (clinit)
7739     {
7740       /* Prevent the use of `this' inside <clinit> */
7741       ctxp->explicit_constructor_p = 1;
7742       java_complete_expand_method (clinit);
7743       ctxp->explicit_constructor_p = 0;
7744     }
7745   
7746   /* We might have generated a class$ that we now want to expand */
7747   if (TYPE_DOT_CLASS (current_class))
7748     java_complete_expand_method (TYPE_DOT_CLASS (current_class));
7749
7750   /* Now verify constructor circularity (stop after the first one we
7751      prove wrong.) */
7752   if (!CLASS_INTERFACE (class_decl))
7753     for (decl = TYPE_METHODS (current_class); decl; decl = TREE_CHAIN (decl))
7754       if (DECL_CONSTRUCTOR_P (decl) 
7755           && verify_constructor_circularity (decl, decl))
7756         break;
7757
7758   /* Save the constant pool. We'll need to restore it later. */
7759   TYPE_CPOOL (current_class) = outgoing_cpool;
7760 }
7761
7762 /* Attempt to create <clinit>. Pre-expand static fields so they can be
7763    safely used in some other methods/constructors.  */
7764
7765 static tree
7766 maybe_generate_pre_expand_clinit (class_type)
7767      tree class_type;
7768 {
7769   tree current, mdecl;
7770
7771   if (!TYPE_CLINIT_STMT_LIST (class_type))
7772     return NULL_TREE;
7773
7774   /* Go through all static fields and pre expand them */
7775   for (current = TYPE_FIELDS (class_type); current; 
7776        current = TREE_CHAIN (current))
7777     if (FIELD_STATIC (current))
7778       build_field_ref (NULL_TREE, class_type, DECL_NAME (current));
7779
7780   /* Then build the <clinit> method */
7781   mdecl = create_artificial_method (class_type, ACC_STATIC, void_type_node,
7782                                     clinit_identifier_node, end_params_node);
7783   layout_class_method (class_type, CLASSTYPE_SUPER (class_type),
7784                        mdecl, NULL_TREE);
7785   start_artificial_method_body (mdecl);
7786
7787   /* We process the list of assignment we produced as the result of
7788      the declaration of initialized static field and add them as
7789      statement to the <clinit> method. */
7790   for (current = TYPE_CLINIT_STMT_LIST (class_type); current;
7791        current = TREE_CHAIN (current))
7792     {
7793       tree stmt = current;
7794       /* We build the assignment expression that will initialize the
7795          field to its value. There are strict rules on static
7796          initializers (8.5). FIXME */
7797       if (TREE_CODE (stmt) != BLOCK && stmt != empty_stmt_node)
7798         stmt = build_debugable_stmt (EXPR_WFL_LINECOL (stmt), stmt);
7799       java_method_add_stmt (mdecl, stmt);
7800     }
7801
7802   end_artificial_method_body (mdecl);
7803
7804   /* Now we want to place <clinit> as the last method (because we need
7805      it at least for interface so that it doesn't interfere with the
7806      dispatch table based lookup. */
7807   if (TREE_CHAIN (TYPE_METHODS (class_type)))
7808     {
7809       current = TREE_CHAIN (TYPE_METHODS (class_type));
7810       TYPE_METHODS (class_type) = current;
7811
7812       while (TREE_CHAIN (current))
7813         current = TREE_CHAIN (current);
7814
7815       TREE_CHAIN (current) = mdecl;
7816       TREE_CHAIN (mdecl) = NULL_TREE;
7817     }
7818
7819   return mdecl;
7820 }
7821
7822 /* Analyzes a method body and look for something that isn't a
7823    MODIFY_EXPR with a constant value.  */
7824
7825 static int
7826 analyze_clinit_body (this_class, bbody)
7827      tree this_class, bbody;
7828 {
7829   while (bbody)
7830     switch (TREE_CODE (bbody))
7831       {
7832       case BLOCK:
7833         bbody = BLOCK_EXPR_BODY (bbody);
7834         break;
7835         
7836       case EXPR_WITH_FILE_LOCATION:
7837         bbody = EXPR_WFL_NODE (bbody);
7838         break;
7839         
7840       case COMPOUND_EXPR:
7841         if (analyze_clinit_body (this_class, TREE_OPERAND (bbody, 0)))
7842           return 1;
7843         bbody = TREE_OPERAND (bbody, 1);
7844         break;
7845         
7846       case MODIFY_EXPR:
7847         /* If we're generating to class file and we're dealing with an
7848            array initialization, we return 1 to keep <clinit> */
7849         if (TREE_CODE (TREE_OPERAND (bbody, 1)) == NEW_ARRAY_INIT
7850             && flag_emit_class_files)
7851           return 1;
7852
7853         /* There are a few cases where we're required to keep
7854            <clinit>:
7855            - If this is an assignment whose operand is not constant,
7856            - If this is an assignment to a non-initialized field,
7857            - If this field is not a member of the current class.
7858         */
7859         return (! TREE_CONSTANT (TREE_OPERAND (bbody, 1))
7860                 || ! DECL_INITIAL (TREE_OPERAND (bbody, 0))
7861                 || DECL_CONTEXT (TREE_OPERAND (bbody, 0)) != this_class);
7862
7863       default:
7864         return 1;
7865       }
7866   return 0;
7867 }
7868
7869
7870 /* See whether we could get rid of <clinit>. Criteria are: all static
7871    final fields have constant initial values and the body of <clinit>
7872    is empty. Return 1 if <clinit> was discarded, 0 otherwise. */
7873
7874 static int
7875 maybe_yank_clinit (mdecl)
7876      tree mdecl;
7877 {
7878   tree type, current;
7879   tree fbody, bbody;
7880   
7881   if (!DECL_CLINIT_P (mdecl))
7882     return 0;
7883
7884   /* If the body isn't empty, then we keep <clinit>. Note that if
7885      we're emitting classfiles, this isn't enough not to rule it
7886      out. */
7887   fbody = DECL_FUNCTION_BODY (mdecl);
7888   bbody = BLOCK_EXPR_BODY (fbody);
7889   if (bbody && bbody != error_mark_node)
7890     bbody = BLOCK_EXPR_BODY (bbody);
7891   else
7892     return 0;
7893   if (bbody && ! flag_emit_class_files && bbody != empty_stmt_node)
7894     return 0;
7895
7896   type = DECL_CONTEXT (mdecl);
7897   current = TYPE_FIELDS (type);
7898
7899   for (current = (current ? TREE_CHAIN (current) : current); 
7900        current; current = TREE_CHAIN (current))
7901     {
7902       tree f_init;
7903
7904       /* We're not interested in non-static fields.  */
7905       if (!FIELD_STATIC (current))
7906         continue;
7907
7908       /* Nor in fields without initializers. */
7909       f_init = DECL_INITIAL (current);
7910       if (f_init == NULL_TREE)
7911         continue;
7912
7913       /* Anything that isn't String or a basic type is ruled out -- or
7914          if we know how to deal with it (when doing things natively) we
7915          should generated an empty <clinit> so that SUID are computed
7916          correctly. */
7917       if (! JSTRING_TYPE_P (TREE_TYPE (current))
7918           && ! JNUMERIC_TYPE_P (TREE_TYPE (current)))
7919         return 0;
7920
7921       if (! FIELD_FINAL (current) || ! TREE_CONSTANT (f_init))
7922         return 0;
7923     }
7924
7925   /* Now we analyze the method body and look for something that
7926      isn't a MODIFY_EXPR */
7927   if (bbody != empty_stmt_node && analyze_clinit_body (type, bbody))
7928     return 0;
7929
7930   /* Get rid of <clinit> in the class' list of methods */
7931   if (TYPE_METHODS (type) == mdecl)
7932     TYPE_METHODS (type) = TREE_CHAIN (mdecl);
7933   else
7934     for (current = TYPE_METHODS (type); current; 
7935          current = TREE_CHAIN (current))
7936       if (TREE_CHAIN (current) == mdecl)
7937         {
7938           TREE_CHAIN (current) = TREE_CHAIN (mdecl);
7939           break;
7940         }
7941
7942   return 1;
7943 }
7944
7945 /* Install the argument from MDECL. Suitable to completion and
7946    expansion of mdecl's body.  */
7947
7948 static void
7949 start_complete_expand_method (mdecl)
7950      tree mdecl;
7951 {
7952   tree tem;
7953
7954   pushlevel (1);                /* Prepare for a parameter push */
7955   tem = BLOCK_EXPR_DECLS (DECL_FUNCTION_BODY (current_function_decl));
7956   DECL_ARGUMENTS (mdecl) = tem;
7957
7958   for (; tem; tem = TREE_CHAIN (tem))
7959     {
7960       /* TREE_CHAIN (tem) will change after pushdecl. */ 
7961       tree next = TREE_CHAIN (tem);
7962       tree type = TREE_TYPE (tem);
7963       if (PROMOTE_PROTOTYPES
7964           && TYPE_PRECISION (type) < TYPE_PRECISION (integer_type_node)
7965           && INTEGRAL_TYPE_P (type))
7966         type = integer_type_node;
7967       DECL_ARG_TYPE (tem) = type;
7968       layout_decl (tem, 0);
7969       pushdecl (tem);
7970       /* Re-install the next so that the list is kept and the loop
7971          advances. */
7972       TREE_CHAIN (tem) = next;
7973     }
7974   pushdecl_force_head (DECL_ARGUMENTS (mdecl));
7975   lineno = DECL_SOURCE_LINE_FIRST (mdecl);
7976   build_result_decl (mdecl);
7977 }
7978
7979
7980 /* Complete and expand a method.  */
7981
7982 static void
7983 java_complete_expand_method (mdecl)
7984      tree mdecl;
7985 {
7986   tree fbody, block_body, exception_copy;
7987
7988   current_function_decl = mdecl;
7989   /* Fix constructors before expanding them */
7990   if (DECL_CONSTRUCTOR_P (mdecl))
7991     fix_constructors (mdecl);
7992   
7993   /* Expand functions that have a body */
7994   if (!DECL_FUNCTION_BODY (mdecl))
7995     return;
7996
7997   fbody = DECL_FUNCTION_BODY (mdecl);
7998   block_body = BLOCK_EXPR_BODY (fbody);
7999   exception_copy = NULL_TREE;
8000
8001   current_function_decl = mdecl;
8002
8003   if (! quiet_flag)
8004     fprintf (stderr, " [%s.",
8005              lang_printable_name (DECL_CONTEXT (mdecl), 0));
8006   announce_function (mdecl);
8007   if (! quiet_flag)
8008     fprintf (stderr, "]");
8009   
8010   /* Prepare the function for tree completion */
8011   start_complete_expand_method (mdecl);
8012
8013   /* Install the current this */
8014   current_this = (!METHOD_STATIC (mdecl) ? 
8015                   BLOCK_EXPR_DECLS (DECL_FUNCTION_BODY (mdecl)) : NULL_TREE);
8016
8017   /* Purge the `throws' list of unchecked exceptions (we save a copy
8018      of the list and re-install it later.) */
8019   exception_copy = copy_list (DECL_FUNCTION_THROWS (mdecl));
8020   purge_unchecked_exceptions (mdecl);
8021   
8022   /* Install exceptions thrown with `throws' */
8023   PUSH_EXCEPTIONS (DECL_FUNCTION_THROWS (mdecl));
8024   
8025   if (block_body != NULL_TREE)
8026     {
8027       block_body = java_complete_tree (block_body);
8028       
8029       /* Before we check initialization, attached all class initialization
8030          variable to the block_body */
8031       hash_traverse (&DECL_FUNCTION_INIT_TEST_TABLE (mdecl),
8032                      attach_init_test_initialization_flags, block_body);
8033       
8034       if (! flag_emit_xref && ! METHOD_NATIVE (mdecl))
8035         {
8036           check_for_initialization (block_body, mdecl);
8037           
8038           /* Go through all the flags marking the initialization of
8039              static variables and see whether they're definitively
8040              assigned, in which case the type is remembered as
8041              definitively initialized in MDECL. */
8042           if (STATIC_CLASS_INIT_OPT_P ())
8043             {
8044               /* Always register the context as properly initialized in
8045                  MDECL. This used with caution helps removing extra
8046                  initialization of self. */
8047               if (METHOD_STATIC (mdecl))
8048                 hash_lookup (&DECL_FUNCTION_INITIALIZED_CLASS_TABLE (mdecl),
8049                              (hash_table_key) DECL_CONTEXT (mdecl),
8050                              TRUE, NULL);
8051             }
8052         }
8053       ctxp->explicit_constructor_p = 0;
8054     }
8055   
8056   BLOCK_EXPR_BODY (fbody) = block_body;
8057   
8058   /* If we saw a return but couldn't evaluate it properly, we'll have
8059      an error_mark_node here. */
8060   if (block_body != error_mark_node
8061       && (block_body == NULL_TREE || CAN_COMPLETE_NORMALLY (block_body))
8062       && TREE_CODE (TREE_TYPE (TREE_TYPE (mdecl))) != VOID_TYPE
8063       && !flag_emit_xref)
8064     missing_return_error (current_function_decl);
8065
8066   /* See if we can get rid of <clinit> if MDECL happens to be <clinit> */
8067   maybe_yank_clinit (mdecl);
8068
8069   /* Pop the current level, with special measures if we found errors. */
8070   if (java_error_count)
8071     pushdecl_force_head (DECL_ARGUMENTS (mdecl));
8072   poplevel (1, 0, 1);
8073
8074   /* Pop the exceptions and sanity check */
8075   POP_EXCEPTIONS();
8076   if (currently_caught_type_list)
8077     abort ();
8078
8079   /* Restore the copy of the list of exceptions if emitting xrefs. */
8080   DECL_FUNCTION_THROWS (mdecl) = exception_copy;
8081 }
8082
8083 /* For with each class for which there's code to generate. */
8084
8085 static void
8086 java_expand_method_bodies (class)
8087      tree class;
8088 {
8089   tree decl;
8090   for (decl = TYPE_METHODS (class); decl; decl = TREE_CHAIN (decl))
8091     {
8092       if (!DECL_FUNCTION_BODY (decl))
8093         continue;
8094
8095       current_function_decl = decl;
8096
8097       /* It's time to assign the variable flagging static class
8098          initialization based on which classes invoked static methods
8099          are definitely initializing. This should be flagged. */
8100       if (STATIC_CLASS_INIT_OPT_P ())
8101         {
8102           tree list = DECL_FUNCTION_STATIC_METHOD_INVOCATION_COMPOUND (decl);
8103           for (; list != NULL_TREE;  list = TREE_CHAIN (list))
8104             {
8105               /* Executed for each statement calling a static function.
8106                  LIST is a TREE_LIST whose PURPOSE is the called function
8107                  and VALUE is a compound whose second operand can be patched
8108                  with static class initialization flag assignments.  */
8109
8110               tree called_method = TREE_PURPOSE (list);
8111               tree compound = TREE_VALUE (list);
8112               tree assignment_compound_list
8113                 = build_tree_list (called_method, NULL);
8114
8115               /* For each class definitely initialized in
8116                  CALLED_METHOD, fill ASSIGNMENT_COMPOUND with
8117                  assignment to the class initialization flag. */
8118               hash_traverse (&DECL_FUNCTION_INITIALIZED_CLASS_TABLE (called_method),
8119                              emit_test_initialization,
8120                              assignment_compound_list);
8121
8122               if (TREE_VALUE (assignment_compound_list))
8123                 TREE_OPERAND (compound, 1)
8124                   = TREE_VALUE (assignment_compound_list);
8125             }
8126         }
8127
8128       /* Prepare the function for RTL expansion */  
8129       start_complete_expand_method (decl);
8130
8131       /* Expand function start, generate initialization flag
8132          assignment, and handle synchronized methods. */
8133       complete_start_java_method (decl);
8134
8135       /* Expand the rest of the function body and terminate
8136          expansion. */
8137       source_end_java_method ();
8138     }
8139 }
8140
8141 \f
8142
8143 /* This section of the code deals with accessing enclosing context
8144    fields either directly by using the relevant access to this$<n> or
8145    by invoking an access method crafted for that purpose.  */
8146
8147 /* Build the necessary access from an inner class to an outer
8148    class. This routine could be optimized to cache previous result
8149    (decl, current_class and returned access).  When an access method
8150    needs to be generated, it always takes the form of a read. It might
8151    be later turned into a write by calling outer_field_access_fix.  */
8152
8153 static tree
8154 build_outer_field_access (id, decl)
8155      tree id, decl;
8156 {
8157   tree access = NULL_TREE;
8158   tree ctx = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (current_class)));
8159   tree decl_ctx = DECL_CONTEXT (decl);
8160
8161   /* If the immediate enclosing context of the current class is the
8162      field decl's class or inherits from it; build the access as
8163      `this$<n>.<field>'. Note that we will break the `private' barrier
8164      if we're not emitting bytecodes. */
8165   if ((ctx == decl_ctx || inherits_from_p (ctx, decl_ctx))
8166       && (!FIELD_PRIVATE (decl) || !flag_emit_class_files ))
8167     {
8168       tree thisn = build_current_thisn (current_class);
8169       access = make_qualified_primary (build_wfl_node (thisn), 
8170                                        id, EXPR_WFL_LINECOL (id));
8171     }
8172   /* Otherwise, generate access methods to outer this and access the
8173      field (either using an access method or by direct access.) */
8174   else
8175     {
8176       int lc = EXPR_WFL_LINECOL (id);
8177
8178       /* Now we chain the required number of calls to the access$0 to
8179          get a hold to the enclosing instance we need, and then we
8180          build the field access. */
8181       access = build_access_to_thisn (current_class, decl_ctx, lc);
8182
8183       /* If the field is private and we're generating bytecode, then
8184          we generate an access method */
8185       if (FIELD_PRIVATE (decl) && flag_emit_class_files )
8186         {
8187           tree name = build_outer_field_access_methods (decl);
8188           access = build_outer_field_access_expr (lc, decl_ctx,
8189                                                   name, access, NULL_TREE);
8190         }
8191       /* Otherwise we use `access$(this$<j>). ... access$(this$<i>).<field>'.
8192          Once again we break the `private' access rule from a foreign
8193          class. */
8194       else
8195         access = make_qualified_primary (access, id, lc);
8196     }
8197   return resolve_expression_name (access, NULL);
8198 }
8199
8200 /* Return a non zero value if NODE describes an outer field inner
8201    access.  */
8202
8203 static int
8204 outer_field_access_p (type, decl)
8205     tree type, decl;
8206 {
8207   if (!INNER_CLASS_TYPE_P (type) 
8208       || TREE_CODE (decl) != FIELD_DECL
8209       || DECL_CONTEXT (decl) == type)
8210     return 0;
8211   
8212   /* If the inner class extends the declaration context of the field
8213      we're try to acces, then this isn't an outer field access */
8214   if (inherits_from_p (type, DECL_CONTEXT (decl)))
8215     return 0;
8216
8217   for (type = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (type))); ;
8218        type = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (type))))
8219     {
8220       if (type == DECL_CONTEXT (decl))
8221         return 1;
8222
8223       if (!DECL_CONTEXT (TYPE_NAME (type)))
8224         {
8225           /* Before we give up, see whether the field is inherited from
8226              the enclosing context we're considering. */
8227           if (inherits_from_p (type, DECL_CONTEXT (decl)))
8228             return 1;
8229           break;
8230         }
8231     }
8232
8233   return 0;
8234 }
8235
8236 /* Return a non zero value if NODE represents an outer field inner
8237    access that was been already expanded. As a side effect, it returns
8238    the name of the field being accessed and the argument passed to the
8239    access function, suitable for a regeneration of the access method
8240    call if necessary. */
8241
8242 static int
8243 outer_field_expanded_access_p (node, name, arg_type, arg)
8244     tree node, *name, *arg_type, *arg;
8245 {
8246   int identified = 0;
8247
8248   if (TREE_CODE (node) != CALL_EXPR)
8249     return 0;
8250
8251   /* Well, gcj generates slightly different tree nodes when compiling
8252      to native or bytecodes. It's the case for function calls. */
8253
8254   if (flag_emit_class_files 
8255       && TREE_CODE (node) == CALL_EXPR
8256       && OUTER_FIELD_ACCESS_IDENTIFIER_P (DECL_NAME (TREE_OPERAND (node, 0))))
8257     identified = 1;
8258   else if (!flag_emit_class_files)
8259     {
8260       node = TREE_OPERAND (node, 0);
8261       
8262       if (node && TREE_OPERAND (node, 0)
8263           && TREE_CODE (TREE_OPERAND (node, 0)) == ADDR_EXPR)
8264         {
8265           node = TREE_OPERAND (node, 0);
8266           if (TREE_OPERAND (node, 0)
8267               && TREE_CODE (TREE_OPERAND (node, 0)) == FUNCTION_DECL
8268               && (OUTER_FIELD_ACCESS_IDENTIFIER_P 
8269                   (DECL_NAME (TREE_OPERAND (node, 0)))))
8270             identified = 1;
8271         }
8272     }
8273
8274   if (identified && name && arg_type && arg)
8275     {
8276       tree argument = TREE_OPERAND (node, 1);
8277       *name = DECL_NAME (TREE_OPERAND (node, 0));
8278       *arg_type = TREE_TYPE (TREE_TYPE (TREE_VALUE (argument)));
8279       *arg = TREE_VALUE (argument);
8280     }
8281   return identified;
8282 }
8283
8284 /* Detect in NODE an outer field read access from an inner class and
8285    transform it into a write with RHS as an argument. This function is
8286    called from the java_complete_lhs when an assignment to a LHS can
8287    be identified. */
8288
8289 static tree
8290 outer_field_access_fix (wfl, node, rhs)
8291     tree wfl, node, rhs;
8292 {
8293   tree name, arg_type, arg;
8294   
8295   if (outer_field_expanded_access_p (node, &name, &arg_type, &arg))
8296     {
8297       node = build_outer_field_access_expr (EXPR_WFL_LINECOL (wfl), 
8298                                             arg_type, name, arg, rhs);
8299       return java_complete_tree (node);
8300     }
8301   return NULL_TREE;
8302 }
8303
8304 /* Construct the expression that calls an access method:
8305      <type>.access$<n>(<arg1> [, <arg2>]); 
8306
8307    ARG2 can be NULL and will be omitted in that case. It will denote a
8308    read access.  */
8309
8310 static tree
8311 build_outer_field_access_expr (lc, type, access_method_name, arg1, arg2)
8312     int lc;
8313     tree type, access_method_name, arg1, arg2;
8314 {
8315   tree args, cn, access;
8316
8317   args = arg1 ? arg1 : 
8318     build_wfl_node (build_current_thisn (current_class));
8319   args = build_tree_list (NULL_TREE, args);
8320
8321   if (arg2)
8322     args = tree_cons (NULL_TREE, arg2, args);
8323
8324   access = build_method_invocation (build_wfl_node (access_method_name), args);
8325   cn = build_wfl_node (DECL_NAME (TYPE_NAME (type)));
8326   return make_qualified_primary (cn, access, lc);
8327 }
8328
8329 static tree
8330 build_new_access_id ()
8331 {
8332   static int access_n_counter = 1;
8333   char buffer [128];
8334
8335   sprintf (buffer, "access$%d", access_n_counter++);
8336   return get_identifier (buffer);
8337 }
8338
8339 /* Create the static access functions for the outer field DECL. We define a
8340    read:
8341      TREE_TYPE (<field>) access$<n> (DECL_CONTEXT (<field>) inst$) {
8342        return inst$.field;
8343      }
8344    and a write access:
8345      TREE_TYPE (<field>) access$<n> (DECL_CONTEXT (<field>) inst$,
8346                                      TREE_TYPE (<field>) value$) {
8347        return inst$.field = value$;
8348      }
8349    We should have a usage flags on the DECL so we can lazily turn the ones
8350    we're using for code generation. FIXME.
8351 */
8352
8353 static tree
8354 build_outer_field_access_methods (decl)
8355     tree decl;
8356 {
8357   tree id, args, stmt, mdecl;
8358   
8359   if (FIELD_INNER_ACCESS_P (decl))
8360     return FIELD_INNER_ACCESS (decl);
8361
8362   MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC (decl);
8363  
8364   /* Create the identifier and a function named after it. */
8365   id = build_new_access_id ();
8366
8367   /* The identifier is marked as bearing the name of a generated write
8368      access function for outer field accessed from inner classes. */
8369   OUTER_FIELD_ACCESS_IDENTIFIER_P (id) = 1;
8370
8371   /* Create the read access */
8372   args = build_tree_list (inst_id, build_pointer_type (DECL_CONTEXT (decl)));
8373   TREE_CHAIN (args) = end_params_node;
8374   stmt = make_qualified_primary (build_wfl_node (inst_id),
8375                                  build_wfl_node (DECL_NAME (decl)), 0);
8376   stmt = build_return (0, stmt);
8377   mdecl = build_outer_field_access_method (DECL_CONTEXT (decl), 
8378                                            TREE_TYPE (decl), id, args, stmt);
8379   DECL_FUNCTION_ACCESS_DECL (mdecl) = decl;
8380
8381   /* Create the write access method. No write access for final variable */
8382   if (!FIELD_FINAL (decl))
8383     {
8384       args = build_tree_list (inst_id, 
8385                               build_pointer_type (DECL_CONTEXT (decl)));
8386       TREE_CHAIN (args) = build_tree_list (wpv_id, TREE_TYPE (decl));
8387       TREE_CHAIN (TREE_CHAIN (args)) = end_params_node;
8388       stmt = make_qualified_primary (build_wfl_node (inst_id),
8389                                      build_wfl_node (DECL_NAME (decl)), 0);
8390       stmt = build_return (0, build_assignment (ASSIGN_TK, 0, stmt,
8391                                                 build_wfl_node (wpv_id)));
8392       mdecl = build_outer_field_access_method (DECL_CONTEXT (decl), 
8393                                                TREE_TYPE (decl), id, 
8394                                                args, stmt);
8395     }
8396   DECL_FUNCTION_ACCESS_DECL (mdecl) = decl;
8397
8398   /* Return the access name */
8399   return FIELD_INNER_ACCESS (decl) = id;
8400 }
8401
8402 /* Build an field access method NAME.  */
8403
8404 static tree 
8405 build_outer_field_access_method (class, type, name, args, body)
8406     tree class, type, name, args, body;
8407 {
8408   tree saved_current_function_decl, mdecl;
8409
8410   /* Create the method */
8411   mdecl = create_artificial_method (class, ACC_STATIC, type, name, args);
8412   fix_method_argument_names (args, mdecl);
8413   layout_class_method (class, NULL_TREE, mdecl, NULL_TREE);
8414
8415   /* Attach the method body. */
8416   saved_current_function_decl = current_function_decl;
8417   start_artificial_method_body (mdecl);
8418   java_method_add_stmt (mdecl, body);
8419   end_artificial_method_body (mdecl);
8420   current_function_decl = saved_current_function_decl;
8421
8422   return mdecl;
8423 }
8424
8425 \f
8426 /* This section deals with building access function necessary for
8427    certain kinds of method invocation from inner classes.  */
8428
8429 static tree
8430 build_outer_method_access_method (decl)
8431     tree decl;
8432 {
8433   tree saved_current_function_decl, mdecl;
8434   tree args = NULL_TREE, call_args = NULL_TREE;
8435   tree carg, id, body, class;
8436   char buffer [80];
8437   int parm_id_count = 0;
8438
8439   /* Test this abort with an access to a private field */
8440   if (!strcmp (IDENTIFIER_POINTER (DECL_NAME (decl)), "access$"))
8441     abort ();
8442
8443   /* Check the cache first */
8444   if (DECL_FUNCTION_INNER_ACCESS (decl))
8445     return DECL_FUNCTION_INNER_ACCESS (decl);
8446
8447   class = DECL_CONTEXT (decl);
8448
8449   /* Obtain an access identifier and mark it */
8450   id = build_new_access_id ();
8451   OUTER_FIELD_ACCESS_IDENTIFIER_P (id) = 1;
8452
8453   carg = TYPE_ARG_TYPES (TREE_TYPE (decl));
8454   /* Create the arguments, as much as the original */
8455   for (; carg && carg != end_params_node; 
8456        carg = TREE_CHAIN (carg))
8457     {
8458       sprintf (buffer, "write_parm_value$%d", parm_id_count++);
8459       args = chainon (args, build_tree_list (get_identifier (buffer), 
8460                                              TREE_VALUE (carg)));
8461     }
8462   args = chainon (args, end_params_node);
8463
8464   /* Create the method */
8465   mdecl = create_artificial_method (class, ACC_STATIC, 
8466                                     TREE_TYPE (TREE_TYPE (decl)), id, args);
8467   layout_class_method (class, NULL_TREE, mdecl, NULL_TREE);
8468   /* There is a potential bug here. We should be able to use
8469      fix_method_argument_names, but then arg names get mixed up and
8470      eventually a constructor will have its this$0 altered and the
8471      outer context won't be assignment properly. The test case is
8472      stub.java FIXME */
8473   TYPE_ARG_TYPES (TREE_TYPE (mdecl)) = args;
8474
8475   /* Attach the method body. */
8476   saved_current_function_decl = current_function_decl;
8477   start_artificial_method_body (mdecl);
8478
8479   /* The actual method invocation uses the same args. When invoking a
8480      static methods that way, we don't want to skip the first
8481      argument. */
8482   carg = args;
8483   if (!METHOD_STATIC (decl))
8484     carg = TREE_CHAIN (carg);
8485   for (; carg && carg != end_params_node; carg = TREE_CHAIN (carg))
8486     call_args = tree_cons (NULL_TREE, build_wfl_node (TREE_PURPOSE (carg)),
8487                            call_args);
8488
8489   body = build_method_invocation (build_wfl_node (DECL_NAME (decl)), 
8490                                   call_args);
8491   if (!METHOD_STATIC (decl))
8492     body = make_qualified_primary (build_wfl_node (TREE_PURPOSE (args)), 
8493                                    body, 0);
8494   if (TREE_TYPE (TREE_TYPE (decl)) != void_type_node)
8495     body = build_return (0, body);
8496   java_method_add_stmt (mdecl,body);
8497   end_artificial_method_body (mdecl);
8498   current_function_decl = saved_current_function_decl;
8499
8500   /* Back tag the access function so it know what it accesses */
8501   DECL_FUNCTION_ACCESS_DECL (decl) = mdecl;
8502
8503   /* Tag the current method so it knows it has an access generated */
8504   return DECL_FUNCTION_INNER_ACCESS (decl) = mdecl;
8505 }
8506
8507 \f
8508 /* This section of the code deals with building expressions to access
8509    the enclosing instance of an inner class. The enclosing instance is
8510    kept in a generated field called this$<n>, with <n> being the
8511    inner class nesting level (starting from 0.)  */
8512     
8513 /* Build an access to a given this$<n>, always chaining access call to
8514    others. Access methods to this$<n> are build on the fly if
8515    necessary. This CAN'T be used to solely access this$<n-1> from
8516    this$<n> (which alway yield to special cases and optimization, see
8517    for example build_outer_field_access).  */
8518
8519 static tree
8520 build_access_to_thisn (from, to, lc)
8521      tree from, to;
8522      int lc;
8523 {
8524   tree access = NULL_TREE;
8525
8526   while (from != to)
8527     {
8528       if (!access)
8529         {
8530           access = build_current_thisn (from);
8531           access = build_wfl_node (access);
8532         }
8533       else
8534         {
8535           tree access0_wfl, cn;
8536
8537           maybe_build_thisn_access_method (from);
8538           access0_wfl = build_wfl_node (access0_identifier_node);
8539           cn = build_wfl_node (DECL_NAME (TYPE_NAME (from)));
8540           EXPR_WFL_LINECOL (access0_wfl) = lc;
8541           access = build_tree_list (NULL_TREE, access);
8542           access = build_method_invocation (access0_wfl, access);
8543           access = make_qualified_primary (cn, access, lc);
8544         }
8545
8546       /* if FROM isn't an inter class, that's fine, we've done
8547          enough. What we're looking for can be accessed from there. */
8548       from = DECL_CONTEXT (TYPE_NAME (from));
8549       if (!from)
8550         break;
8551       from = TREE_TYPE (from);
8552     }
8553   return access;
8554 }
8555
8556 /* Build an access function to the this$<n> local to TYPE. NULL_TREE
8557    is returned if nothing needs to be generated. Otherwise, the method
8558    generated and a method decl is returned.  
8559
8560    NOTE: These generated methods should be declared in a class file
8561    attribute so that they can't be referred to directly.  */
8562
8563 static tree
8564 maybe_build_thisn_access_method (type)
8565     tree type;
8566 {
8567   tree mdecl, args, stmt, rtype;
8568   tree saved_current_function_decl;
8569
8570   /* If TYPE is a top-level class, no access method is required.
8571      If there already is such an access method, bail out. */
8572   if (CLASS_ACCESS0_GENERATED_P (type) || !PURE_INNER_CLASS_TYPE_P (type))
8573     return NULL_TREE;
8574
8575   /* We generate the method. The method looks like:
8576      static <outer_of_type> access$0 (<type> inst$) { return inst$.this$<n>; }
8577   */
8578   args = build_tree_list (inst_id, build_pointer_type (type));
8579   TREE_CHAIN (args) = end_params_node;
8580   rtype = build_pointer_type (TREE_TYPE (DECL_CONTEXT (TYPE_NAME (type))));
8581   mdecl = create_artificial_method (type, ACC_STATIC, rtype,
8582                                     access0_identifier_node, args);
8583   fix_method_argument_names (args, mdecl);
8584   layout_class_method (type, NULL_TREE, mdecl, NULL_TREE);
8585   stmt = build_current_thisn (type);
8586   stmt = make_qualified_primary (build_wfl_node (inst_id), 
8587                                  build_wfl_node (stmt), 0);
8588   stmt = build_return (0, stmt);
8589
8590   saved_current_function_decl = current_function_decl;
8591   start_artificial_method_body (mdecl);
8592   java_method_add_stmt (mdecl, stmt);
8593   end_artificial_method_body (mdecl);
8594   current_function_decl = saved_current_function_decl;
8595
8596   CLASS_ACCESS0_GENERATED_P (type) = 1;
8597
8598   return mdecl;
8599 }
8600
8601 /* Craft an correctly numbered `this$<n>'string. this$0 is used for
8602    the first level of innerclassing. this$1 for the next one, etc...
8603    This function can be invoked with TYPE to NULL, available and then
8604    has to count the parser context.  */
8605
8606 static tree
8607 build_current_thisn (type)
8608     tree type;
8609 {
8610   static int saved_i = -1;
8611   static tree saved_thisn = NULL_TREE;
8612   static tree saved_type = NULL_TREE;
8613   static int saved_type_i = 0;
8614   static int initialized_p;
8615   tree decl;
8616   char buffer [24];
8617   int i = 0;
8618
8619   /* Register SAVED_THISN and SAVED_TYPE with the garbage collector.  */
8620   if (!initialized_p)
8621     {
8622       ggc_add_tree_root (&saved_thisn, 1);
8623       ggc_add_tree_root (&saved_type, 1);
8624       initialized_p = 1;
8625     }
8626
8627   if (type)
8628     {
8629       if (type == saved_type)
8630         i = saved_type_i;
8631       else
8632         {
8633           for (i = -1, decl = DECL_CONTEXT (TYPE_NAME (type)); 
8634                decl; decl = DECL_CONTEXT (decl), i++)
8635             ;
8636       
8637           saved_type = type;
8638           saved_type_i = i;
8639         }
8640     }
8641   else
8642     i = list_length (GET_CPC_LIST ())-2;
8643
8644   if (i == saved_i)
8645     return saved_thisn;
8646     
8647   sprintf (buffer, "this$%d", i);
8648   saved_i = i;
8649   saved_thisn = get_identifier (buffer);
8650   return saved_thisn;
8651 }
8652
8653 /* Return the assignement to the hidden enclosing context `this$<n>'
8654    by the second incoming parameter to the innerclass constructor. The
8655    form used is `this.this$<n> = this$<n>;'.  */
8656
8657 static tree
8658 build_thisn_assign ()
8659 {
8660   if (current_class && PURE_INNER_CLASS_TYPE_P (current_class))
8661     {
8662       tree thisn = build_current_thisn (current_class);
8663       tree lhs = make_qualified_primary (build_wfl_node (this_identifier_node),
8664                                          build_wfl_node (thisn), 0);
8665       tree rhs = build_wfl_node (thisn);
8666       EXPR_WFL_SET_LINECOL (lhs, lineno, 0);
8667       return build_assignment (ASSIGN_TK, EXPR_WFL_LINECOL (lhs), lhs, rhs);
8668     }
8669   return NULL_TREE;
8670 }
8671
8672 \f
8673 /* Building the synthetic `class$' used to implement the `.class' 1.1
8674    extension for non primitive types. This method looks like:
8675
8676     static Class class$(String type) throws NoClassDefFoundError
8677     {
8678       try {return (java.lang.Class.forName (String));}
8679       catch (ClassNotFoundException e) {
8680         throw new NoClassDefFoundError(e.getMessage());}
8681     } */
8682
8683 static tree
8684 build_dot_class_method (class)
8685      tree class;
8686 {
8687 #define BWF(S) build_wfl_node (get_identifier ((S)))
8688 #define MQN(X,Y) make_qualified_name ((X), (Y), 0)
8689   tree args, tmp, saved_current_function_decl, mdecl;
8690   tree stmt, throw_stmt;
8691
8692   static tree get_message_wfl, type_parm_wfl;
8693
8694   if (!get_message_wfl)
8695     {
8696       get_message_wfl = build_wfl_node (get_identifier ("getMessage"));
8697       type_parm_wfl = build_wfl_node (get_identifier ("type$"));
8698       ggc_add_tree_root (&get_message_wfl, 1);
8699       ggc_add_tree_root (&type_parm_wfl, 1);
8700     }
8701
8702   /* Build the arguments */
8703   args = build_tree_list (get_identifier ("type$"),
8704                           build_pointer_type (string_type_node));
8705   TREE_CHAIN (args) = end_params_node;
8706
8707   /* Build the qualified name java.lang.Class.forName */
8708   tmp = MQN (MQN (MQN (BWF ("java"), 
8709                        BWF ("lang")), BWF ("Class")), BWF ("forName"));
8710   load_class (class_not_found_type_node, 1);
8711   load_class (no_class_def_found_type_node, 1);
8712   
8713   /* Create the "class$" function */
8714   mdecl = create_artificial_method (class, ACC_STATIC, 
8715                                     build_pointer_type (class_type_node),
8716                                     classdollar_identifier_node, args);
8717   DECL_FUNCTION_THROWS (mdecl) = 
8718     build_tree_list (NULL_TREE, no_class_def_found_type_node);
8719
8720   /* We start by building the try block. We need to build:
8721        return (java.lang.Class.forName (type)); */
8722   stmt = build_method_invocation (tmp, 
8723                                   build_tree_list (NULL_TREE, type_parm_wfl));
8724   stmt = build_return (0, stmt);
8725
8726   /* Now onto the catch block. We start by building the expression
8727      throwing a new exception: throw new NoClassDefFoundError (_.getMessage) */
8728   throw_stmt = make_qualified_name (build_wfl_node (wpv_id), 
8729                                     get_message_wfl, 0);
8730   throw_stmt = build_method_invocation (throw_stmt, NULL_TREE);
8731   
8732   /* Build new NoClassDefFoundError (_.getMessage) */
8733   throw_stmt = build_new_invocation 
8734     (build_wfl_node (get_identifier ("NoClassDefFoundError")),
8735      build_tree_list (build_pointer_type (string_type_node), throw_stmt));
8736
8737   /* Build the throw, (it's too early to use BUILD_THROW) */
8738   throw_stmt = build1 (THROW_EXPR, NULL_TREE, throw_stmt);
8739
8740   /* Encapsulate STMT in a try block. The catch clause executes THROW_STMT */
8741   stmt = encapsulate_with_try_catch (0, class_not_found_type_node,
8742                                      stmt, throw_stmt);
8743
8744   fix_method_argument_names (args, mdecl);
8745   layout_class_method (class, NULL_TREE, mdecl, NULL_TREE);
8746   saved_current_function_decl = current_function_decl;
8747   start_artificial_method_body (mdecl);
8748   java_method_add_stmt (mdecl, stmt);
8749   end_artificial_method_body (mdecl);
8750   current_function_decl = saved_current_function_decl;
8751   TYPE_DOT_CLASS (class) = mdecl;
8752
8753   return mdecl;
8754 }
8755
8756 static tree
8757 build_dot_class_method_invocation (type)
8758      tree type;
8759 {
8760   tree sig_id, s;
8761
8762   if (TYPE_ARRAY_P (type))
8763     sig_id = build_java_signature (type);
8764   else
8765     sig_id = DECL_NAME (TYPE_NAME (type));
8766
8767   /* Ensure that the proper name separator is used */
8768   sig_id = unmangle_classname (IDENTIFIER_POINTER (sig_id),
8769                                IDENTIFIER_LENGTH (sig_id));
8770
8771   s = build_string (IDENTIFIER_LENGTH (sig_id), 
8772                     IDENTIFIER_POINTER (sig_id));
8773   return build_method_invocation (build_wfl_node (classdollar_identifier_node),
8774                                   build_tree_list (NULL_TREE, s));
8775 }
8776
8777 /* This section of the code deals with constructor.  */
8778
8779 /* Craft a body for default constructor. Patch existing constructor
8780    bodies with call to super() and field initialization statements if
8781    necessary.  */
8782
8783 static void
8784 fix_constructors (mdecl)
8785      tree mdecl;
8786 {
8787   tree iii;                     /* Instance Initializer Invocation */
8788   tree body = DECL_FUNCTION_BODY (mdecl);
8789   tree thisn_assign, compound = NULL_TREE;
8790   tree class_type = DECL_CONTEXT (mdecl);
8791
8792   if (DECL_FIXED_CONSTRUCTOR_P (mdecl))
8793     return;
8794   DECL_FIXED_CONSTRUCTOR_P (mdecl) = 1;
8795
8796   if (!body)
8797     {
8798       /* It is an error for the compiler to generate a default
8799          constructor if the superclass doesn't have a constructor that
8800          takes no argument, or the same args for an anonymous class */
8801       if (verify_constructor_super (mdecl))
8802         {
8803           tree sclass_decl = TYPE_NAME (CLASSTYPE_SUPER (class_type));
8804           tree save = DECL_NAME (mdecl);
8805           const char *n = IDENTIFIER_POINTER (DECL_NAME (sclass_decl));
8806           DECL_NAME (mdecl) = DECL_NAME (sclass_decl);
8807           parse_error_context
8808             (lookup_cl (TYPE_NAME (class_type)), 
8809              "No constructor matching `%s' found in class `%s'",
8810              lang_printable_name (mdecl, 0), n);
8811           DECL_NAME (mdecl) = save;
8812         }
8813       
8814       /* The constructor body must be crafted by hand. It's the
8815          constructor we defined when we realize we didn't have the
8816          CLASSNAME() constructor */
8817       start_artificial_method_body (mdecl);
8818       
8819       /* Insert an assignment to the this$<n> hidden field, if
8820          necessary */
8821       if ((thisn_assign = build_thisn_assign ()))
8822         java_method_add_stmt (mdecl, thisn_assign);
8823
8824       /* We don't generate a super constructor invocation if we're
8825          compiling java.lang.Object. build_super_invocation takes care
8826          of that. */
8827       java_method_add_stmt (mdecl, build_super_invocation (mdecl));
8828
8829       /* FIXME */
8830       if ((iii = build_instinit_invocation (class_type)))
8831         java_method_add_stmt (mdecl, iii);
8832
8833       end_artificial_method_body (mdecl);
8834     }
8835   /* Search for an explicit constructor invocation */
8836   else 
8837     {
8838       int found = 0;
8839       int invokes_this = 0;
8840       tree found_call = NULL_TREE;
8841       tree main_block = BLOCK_EXPR_BODY (body);
8842       
8843       while (body)
8844         switch (TREE_CODE (body))
8845           {
8846           case CALL_EXPR:
8847             found = CALL_EXPLICIT_CONSTRUCTOR_P (body);
8848             if (CALL_THIS_CONSTRUCTOR_P (body))
8849               invokes_this = 1;
8850             body = NULL_TREE;
8851             break;
8852           case COMPOUND_EXPR:
8853           case EXPR_WITH_FILE_LOCATION:
8854             found_call = body;
8855             body = TREE_OPERAND (body, 0);
8856             break;
8857           case BLOCK:
8858             found_call = body;
8859             body = BLOCK_EXPR_BODY (body);
8860             break;
8861           default:
8862             found = 0;
8863             body = NULL_TREE;
8864           }
8865
8866       /* Generate the assignment to this$<n>, if necessary */
8867       if ((thisn_assign = build_thisn_assign ()))
8868         compound = add_stmt_to_compound (compound, NULL_TREE, thisn_assign);
8869
8870       /* The constructor is missing an invocation of super() */
8871       if (!found)
8872         compound = add_stmt_to_compound (compound, NULL_TREE,
8873                                          build_super_invocation (mdecl));
8874       /* Explicit super() invokation should take place before the
8875          instance initializer blocks. */
8876       else
8877         {
8878           compound = add_stmt_to_compound (compound, NULL_TREE,
8879                                            TREE_OPERAND (found_call, 0));
8880           TREE_OPERAND (found_call, 0) = empty_stmt_node;
8881         }
8882       
8883       DECL_INIT_CALLS_THIS (mdecl) = invokes_this;
8884
8885       /* Insert the instance initializer block right after. */
8886       if (!invokes_this && (iii = build_instinit_invocation (class_type)))
8887         compound = add_stmt_to_compound (compound, NULL_TREE, iii);
8888
8889       /* Fix the constructor main block if we're adding extra stmts */
8890       if (compound)
8891         {
8892           compound = add_stmt_to_compound (compound, NULL_TREE,
8893                                            BLOCK_EXPR_BODY (main_block));
8894           BLOCK_EXPR_BODY (main_block) = compound;
8895         }
8896     }
8897 }
8898
8899 /* Browse constructors in the super class, searching for a constructor
8900    that doesn't take any argument. Return 0 if one is found, 1
8901    otherwise.  If the current class is an anonymous inner class, look
8902    for something that has the same signature. */
8903
8904 static int
8905 verify_constructor_super (mdecl)
8906      tree mdecl;
8907 {
8908   tree class = CLASSTYPE_SUPER (current_class);
8909   int super_inner = PURE_INNER_CLASS_TYPE_P (class);
8910   tree sdecl;
8911
8912   if (!class)
8913     return 0;
8914
8915   if (ANONYMOUS_CLASS_P (current_class))
8916     {
8917       tree mdecl_arg_type;
8918       SKIP_THIS_AND_ARTIFICIAL_PARMS (mdecl_arg_type, mdecl);
8919       for (sdecl = TYPE_METHODS (class); sdecl; sdecl = TREE_CHAIN (sdecl))
8920         if (DECL_CONSTRUCTOR_P (sdecl))
8921           {
8922             tree m_arg_type;
8923             tree arg_type = TREE_CHAIN (TYPE_ARG_TYPES (TREE_TYPE (sdecl)));
8924             if (super_inner)
8925               arg_type = TREE_CHAIN (arg_type);
8926             for (m_arg_type = mdecl_arg_type; 
8927                  (arg_type != end_params_node 
8928                   && m_arg_type != end_params_node);
8929                  arg_type = TREE_CHAIN (arg_type), 
8930                    m_arg_type = TREE_CHAIN (m_arg_type))
8931               if (!valid_method_invocation_conversion_p 
8932                      (TREE_VALUE (arg_type),
8933                       TREE_VALUE (m_arg_type)))
8934                 break;
8935
8936             if (arg_type == end_params_node && m_arg_type == end_params_node)
8937               return 0;
8938           }
8939     }
8940   else
8941     {
8942       for (sdecl = TYPE_METHODS (class); sdecl; sdecl = TREE_CHAIN (sdecl))
8943         {
8944           tree arg = TREE_CHAIN (TYPE_ARG_TYPES (TREE_TYPE (sdecl)));
8945           if (super_inner)
8946             arg = TREE_CHAIN (arg);
8947           if (DECL_CONSTRUCTOR_P (sdecl) && arg == end_params_node)
8948             return 0;
8949         }
8950     }
8951   return 1;
8952 }
8953
8954 /* Generate code for all context remembered for code generation.  */
8955
8956 void
8957 java_expand_classes ()
8958 {
8959   int save_error_count = 0;
8960   static struct parser_ctxt *cur_ctxp = NULL;
8961
8962   java_parse_abort_on_error ();
8963   if (!(ctxp = ctxp_for_generation))
8964     return;
8965   java_layout_classes ();
8966   java_parse_abort_on_error ();
8967
8968   for (cur_ctxp = ctxp_for_generation; cur_ctxp; cur_ctxp = cur_ctxp->next)
8969     {
8970       ctxp = cur_ctxp;
8971       input_filename = ctxp->filename;
8972       lang_init_source (2);            /* Error msgs have method prototypes */
8973       java_complete_expand_classes (); /* Complete and expand classes */
8974       java_parse_abort_on_error ();
8975     }
8976   input_filename = main_input_filename;
8977
8978   /* Find anonymous classes and expand their constructor, now they
8979      have been fixed. */
8980   for (cur_ctxp = ctxp_for_generation; cur_ctxp; cur_ctxp = cur_ctxp->next)
8981     {
8982       tree current;
8983       ctxp = cur_ctxp;
8984       for (current = ctxp->class_list; current; current = TREE_CHAIN (current))
8985         {
8986           current_class = TREE_TYPE (current);
8987           if (ANONYMOUS_CLASS_P (current_class))
8988             {
8989               tree d;
8990               for (d = TYPE_METHODS (current_class); d; d = TREE_CHAIN (d))
8991                 {
8992                   if (DECL_CONSTRUCTOR_P (d))
8993                     {
8994                       restore_line_number_status (1);
8995                       java_complete_expand_method (d);
8996                       restore_line_number_status (0);
8997                       break;    /* We now there are no other ones */
8998                     }
8999                 }
9000             }
9001         }
9002     }
9003
9004   /* If we've found error at that stage, don't try to generate
9005      anything, unless we're emitting xrefs or checking the syntax only
9006      (but not using -fsyntax-only for the purpose of generating
9007      bytecode. */
9008   if (java_error_count && !flag_emit_xref 
9009       && (!flag_syntax_only && !flag_emit_class_files))
9010     return;
9011
9012   /* Now things are stable, go for generation of the class data. */
9013
9014   /* We pessimistically marked all fields external until we knew
9015      what set of classes we were planning to compile.  Now mark
9016      those that will be generated locally as not external.  */
9017   for (cur_ctxp = ctxp_for_generation; cur_ctxp; cur_ctxp = cur_ctxp->next)
9018     {
9019       tree current;
9020       ctxp = cur_ctxp;
9021       for (current = ctxp->class_list; current; current = TREE_CHAIN (current))
9022         {
9023           tree class = TREE_TYPE (current);
9024           tree field;
9025           for (field = TYPE_FIELDS (class); field ; field = TREE_CHAIN (field))
9026             if (FIELD_STATIC (field))
9027               DECL_EXTERNAL (field) = 0;
9028         }
9029     }
9030
9031   /* Compile the classes.  */
9032   for (cur_ctxp = ctxp_for_generation; cur_ctxp; cur_ctxp = cur_ctxp->next)
9033     {
9034       tree current;
9035       ctxp = cur_ctxp;
9036       for (current = ctxp->class_list; current; current = TREE_CHAIN (current))
9037         {
9038           current_class = TREE_TYPE (current);
9039           outgoing_cpool = TYPE_CPOOL (current_class);
9040           if (flag_emit_class_files)
9041             write_classfile (current_class);
9042           if (flag_emit_xref)
9043             expand_xref (current_class);
9044           else if (! flag_syntax_only)
9045             {
9046               java_expand_method_bodies (current_class);
9047               finish_class ();
9048             }
9049         }
9050     }
9051 }
9052
9053 /* Wrap non WFL PRIMARY around a WFL and set EXPR_WFL_QUALIFICATION to
9054    a tree list node containing RIGHT. Fore coming RIGHTs will be
9055    chained to this hook. LOCATION contains the location of the
9056    separating `.' operator.  */
9057
9058 static tree
9059 make_qualified_primary (primary, right, location)
9060      tree primary, right;
9061      int location;
9062 {
9063   tree wfl;
9064
9065   if (TREE_CODE (primary) != EXPR_WITH_FILE_LOCATION)
9066     wfl = build_wfl_wrap (primary, location);
9067   else
9068     {
9069       wfl = primary;
9070       /* If wfl wasn't qualified, we build a first anchor */
9071       if (!EXPR_WFL_QUALIFICATION (wfl))
9072         EXPR_WFL_QUALIFICATION (wfl) = build_tree_list (wfl, NULL_TREE);
9073     }
9074
9075   /* And chain them */
9076   EXPR_WFL_LINECOL (right) = location;
9077   chainon (EXPR_WFL_QUALIFICATION (wfl), build_tree_list (right, NULL_TREE));
9078   PRIMARY_P (wfl) =  1;
9079   return wfl;
9080 }
9081
9082 /* Simple merge of two name separated by a `.' */
9083
9084 static tree
9085 merge_qualified_name (left, right)
9086      tree left, right;
9087 {
9088   tree node;
9089   if (!left && !right)
9090     return NULL_TREE;
9091
9092   if (!left)
9093     return right;
9094
9095   if (!right)
9096     return left;
9097
9098   obstack_grow (&temporary_obstack, IDENTIFIER_POINTER (left),
9099                 IDENTIFIER_LENGTH (left));
9100   obstack_1grow (&temporary_obstack, '.');
9101   obstack_grow0 (&temporary_obstack, IDENTIFIER_POINTER (right),
9102                  IDENTIFIER_LENGTH (right));
9103   node =  get_identifier (obstack_base (&temporary_obstack));
9104   obstack_free (&temporary_obstack, obstack_base (&temporary_obstack));
9105   QUALIFIED_P (node) = 1;
9106   return node;
9107 }
9108
9109 /* Merge the two parts of a qualified name into LEFT.  Set the
9110    location information of the resulting node to LOCATION, usually
9111    inherited from the location information of the `.' operator. */
9112
9113 static tree
9114 make_qualified_name (left, right, location)
9115      tree left, right;
9116      int location;
9117 {
9118 #ifdef USE_COMPONENT_REF
9119   tree node = build (COMPONENT_REF, NULL_TREE, left, right);
9120   EXPR_WFL_LINECOL (node) = location;
9121   return node;
9122 #else
9123   tree left_id = EXPR_WFL_NODE (left);
9124   tree right_id = EXPR_WFL_NODE (right);
9125   tree wfl, merge;
9126
9127   merge = merge_qualified_name (left_id, right_id);
9128
9129   /* Left wasn't qualified and is now qualified */
9130   if (!QUALIFIED_P (left_id))
9131     {
9132       tree wfl = build_expr_wfl (left_id, ctxp->filename, 0, 0);
9133       EXPR_WFL_LINECOL (wfl) = EXPR_WFL_LINECOL (left);
9134       EXPR_WFL_QUALIFICATION (left) = build_tree_list (wfl, NULL_TREE);
9135     }
9136   
9137   wfl = build_expr_wfl (right_id, ctxp->filename, 0, 0);
9138   EXPR_WFL_LINECOL (wfl) = location;
9139   chainon (EXPR_WFL_QUALIFICATION (left), build_tree_list (wfl, NULL_TREE));
9140
9141   EXPR_WFL_NODE (left) = merge;
9142   return left;
9143 #endif
9144 }
9145
9146 /* Extract the last identifier component of the qualified in WFL. The
9147    last identifier is removed from the linked list */
9148
9149 static tree
9150 cut_identifier_in_qualified (wfl)
9151      tree wfl;
9152 {
9153   tree q;
9154   tree previous = NULL_TREE;
9155   for (q = EXPR_WFL_QUALIFICATION (wfl); ; previous = q, q = TREE_CHAIN (q))
9156     if (!TREE_CHAIN (q))
9157       {
9158         if (!previous)
9159           /* Operating on a non qualified qualified WFL.  */
9160           abort ();
9161
9162         TREE_CHAIN (previous) = NULL_TREE;
9163         return TREE_PURPOSE (q);
9164       }
9165 }
9166
9167 /* Resolve the expression name NAME. Return its decl.  */
9168
9169 static tree
9170 resolve_expression_name (id, orig)
9171      tree id;
9172      tree *orig;
9173 {
9174   tree name = EXPR_WFL_NODE (id);
9175   tree decl;
9176
9177   /* 6.5.5.1: Simple expression names */
9178   if (!PRIMARY_P (id) && !QUALIFIED_P (name))
9179     {
9180       /* 15.13.1: NAME can appear within the scope of a local variable
9181          declaration */
9182       if ((decl = IDENTIFIER_LOCAL_VALUE (name)))
9183         return decl;
9184
9185       /* 15.13.1: NAME can appear within a class declaration */
9186       else 
9187         {
9188           decl = lookup_field_wrapper (current_class, name);
9189           if (decl)
9190             {
9191               tree access = NULL_TREE;
9192               int fs = FIELD_STATIC (decl);
9193
9194               /* If we're accessing an outer scope local alias, make
9195                  sure we change the name of the field we're going to
9196                  build access to. */
9197               if (FIELD_LOCAL_ALIAS_USED (decl))
9198                 name = DECL_NAME (decl);
9199
9200               /* Instance variable (8.3.1.1) can't appear within
9201                  static method, static initializer or initializer for
9202                  a static variable. */
9203               if (!fs && METHOD_STATIC (current_function_decl))
9204                 {
9205                   static_ref_err (id, name, current_class);
9206                   return error_mark_node;
9207                 }
9208               /* Instance variables can't appear as an argument of
9209                  an explicit constructor invocation */
9210               if (!fs && ctxp->explicit_constructor_p
9211                   && !enclosing_context_p (DECL_CONTEXT (decl), current_class))
9212                 {
9213                   parse_error_context
9214                     (id, "Can't reference `%s' before the superclass constructor has been called", IDENTIFIER_POINTER (name));
9215                   return error_mark_node;
9216                 }
9217
9218               /* If we're processing an inner class and we're trying
9219                  to access a field belonging to an outer class, build
9220                  the access to the field */
9221               if (!fs && outer_field_access_p (current_class, decl))
9222                 {
9223                   if (CLASS_STATIC (TYPE_NAME (current_class)))
9224                     {
9225                       static_ref_err (id, DECL_NAME (decl), current_class);
9226                       return error_mark_node;
9227                     }
9228                   access = build_outer_field_access (id, decl);
9229                   if (orig)
9230                     *orig = access;
9231                   return access;
9232                 }
9233
9234               /* Otherwise build what it takes to access the field */
9235               access = build_field_ref ((fs ? NULL_TREE : current_this),
9236                                         DECL_CONTEXT (decl), name);
9237               if (fs)
9238                 access = maybe_build_class_init_for_field (decl, access);
9239               /* We may be asked to save the real field access node */
9240               if (orig)
9241                 *orig = access;
9242               /* And we return what we got */
9243               return access;
9244             }
9245           /* Fall down to error report on undefined variable */
9246         }
9247     }
9248   /* 6.5.5.2 Qualified Expression Names */
9249   else
9250     {
9251       if (orig)
9252         *orig = NULL_TREE;
9253       qualify_ambiguous_name (id);
9254       /* 15.10.1 Field Access Using a Primary and/or Expression Name */
9255       /* 15.10.2: Accessing Superclass Members using super */
9256       return resolve_field_access (id, orig, NULL);
9257     }
9258
9259   /* We've got an error here */
9260   if (INNER_CLASS_TYPE_P (current_class))
9261     parse_error_context (id, 
9262                          "Local variable `%s' can't be accessed from within the inner class `%s' unless it is declared final",
9263                          IDENTIFIER_POINTER (name),
9264                          IDENTIFIER_POINTER (DECL_NAME
9265                                              (TYPE_NAME (current_class))));
9266   else
9267     parse_error_context (id, "Undefined variable `%s'", 
9268                          IDENTIFIER_POINTER (name));
9269
9270   return error_mark_node;
9271 }
9272
9273 static void
9274 static_ref_err (wfl, field_id, class_type)
9275     tree wfl, field_id, class_type;
9276 {
9277   parse_error_context 
9278     (wfl, 
9279      "Can't make a static reference to nonstatic variable `%s' in class `%s'",
9280      IDENTIFIER_POINTER (field_id), 
9281      IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (class_type))));
9282 }
9283
9284 /* 15.10.1 Field Access Using a Primary and/or Expression Name.
9285    We return something suitable to generate the field access. We also
9286    return the field decl in FIELD_DECL and its type in FIELD_TYPE.  If
9287    recipient's address can be null. */
9288
9289 static tree
9290 resolve_field_access (qual_wfl, field_decl, field_type)
9291      tree qual_wfl;
9292      tree *field_decl, *field_type;
9293 {
9294   int is_static = 0;
9295   tree field_ref;
9296   tree decl, where_found, type_found;
9297
9298   if (resolve_qualified_expression_name (qual_wfl, &decl,
9299                                          &where_found, &type_found))
9300     return error_mark_node;
9301
9302   /* Resolve the LENGTH field of an array here */
9303   if (DECL_P (decl) && DECL_NAME (decl) == length_identifier_node 
9304       && type_found && TYPE_ARRAY_P (type_found) 
9305       && ! flag_emit_class_files && ! flag_emit_xref)
9306     {
9307       tree length = build_java_array_length_access (where_found);
9308       field_ref = length;
9309
9310       /* In case we're dealing with a static array, we need to
9311          initialize its class before the array length can be fetched.
9312          It's also a good time to create a DECL_RTL for the field if
9313          none already exists, otherwise if the field was declared in a
9314          class found in an external file and hasn't been (and won't
9315          be) accessed for its value, none will be created. */
9316       if (TREE_CODE (where_found) == VAR_DECL && FIELD_STATIC (where_found))
9317         {
9318           build_static_field_ref (where_found);
9319           field_ref = build_class_init (DECL_CONTEXT (where_found), field_ref);
9320         }
9321     }
9322   /* We might have been trying to resolve field.method(). In which
9323      case, the resolution is over and decl is the answer */
9324   else if (JDECL_P (decl) && IDENTIFIER_LOCAL_VALUE (DECL_NAME (decl)) == decl)
9325     field_ref = decl;
9326   else if (JDECL_P (decl))
9327     {
9328       if (!type_found)
9329         type_found = DECL_CONTEXT (decl);
9330       is_static = FIELD_STATIC (decl);
9331       field_ref = build_field_ref ((is_static && !flag_emit_xref? 
9332                                     NULL_TREE : where_found), 
9333                                    type_found, DECL_NAME (decl));
9334       if (field_ref == error_mark_node)
9335         return error_mark_node;
9336       if (is_static)
9337         field_ref = maybe_build_class_init_for_field (decl, field_ref);
9338     }
9339   else
9340     field_ref = decl;
9341
9342   if (field_decl)
9343     *field_decl = decl;
9344   if (field_type)
9345     *field_type = (QUAL_DECL_TYPE (decl) ? 
9346                    QUAL_DECL_TYPE (decl) : TREE_TYPE (decl));
9347   return field_ref;
9348 }
9349
9350 /* If NODE is an access to f static field, strip out the class
9351    initialization part and return the field decl, otherwise, return
9352    NODE. */
9353
9354 static tree
9355 strip_out_static_field_access_decl (node)
9356     tree node;
9357 {
9358   if (TREE_CODE (node) == COMPOUND_EXPR)
9359     {
9360       tree op1 = TREE_OPERAND (node, 1);
9361       if (TREE_CODE (op1) == COMPOUND_EXPR)
9362          {
9363            tree call = TREE_OPERAND (op1, 0);
9364            if (TREE_CODE (call) == CALL_EXPR
9365                && TREE_CODE (TREE_OPERAND (call, 0)) == ADDR_EXPR
9366                && TREE_OPERAND (TREE_OPERAND (call, 0), 0)
9367                == soft_initclass_node)
9368              return TREE_OPERAND (op1, 1);
9369          }
9370       else if (JDECL_P (op1))
9371         return op1;
9372     }
9373   return node;
9374 }
9375
9376 /* 6.5.5.2: Qualified Expression Names */
9377
9378 static int
9379 resolve_qualified_expression_name (wfl, found_decl, where_found, type_found)
9380      tree wfl;
9381      tree *found_decl, *type_found, *where_found;
9382 {
9383   int from_type = 0;            /* Field search initiated from a type */
9384   int from_super = 0, from_cast = 0, from_qualified_this = 0;
9385   int previous_call_static = 0;
9386   int is_static;
9387   tree decl = NULL_TREE, type = NULL_TREE, q;
9388   /* For certain for of inner class instantiation */
9389   tree saved_current, saved_this;               
9390 #define RESTORE_THIS_AND_CURRENT_CLASS                          \
9391   { current_class = saved_current; current_this = saved_this;}
9392
9393   *type_found = *where_found = NULL_TREE;
9394
9395   for (q = EXPR_WFL_QUALIFICATION (wfl); q; q = TREE_CHAIN (q))
9396     {
9397       tree qual_wfl = QUAL_WFL (q);
9398       tree ret_decl;            /* for EH checking */
9399       int location;             /* for EH checking */
9400
9401       /* 15.10.1 Field Access Using a Primary */
9402       switch (TREE_CODE (qual_wfl))
9403         {
9404         case CALL_EXPR:
9405         case NEW_CLASS_EXPR:
9406           /* If the access to the function call is a non static field,
9407              build the code to access it. */
9408           if (JDECL_P (decl) && !FIELD_STATIC (decl))
9409             {
9410               decl = maybe_access_field (decl, *where_found, 
9411                                          DECL_CONTEXT (decl));
9412               if (decl == error_mark_node)
9413                 return 1;
9414             }
9415
9416           /* And code for the function call */
9417           if (complete_function_arguments (qual_wfl))
9418             return 1;
9419
9420           /* We might have to setup a new current class and a new this
9421              for the search of an inner class, relative to the type of
9422              a expression resolved as `decl'. The current values are
9423              saved and restored shortly after */
9424           saved_current = current_class;
9425           saved_this = current_this;
9426           if (decl 
9427               && (TREE_CODE (qual_wfl) == NEW_CLASS_EXPR
9428                   || from_qualified_this))
9429             {
9430               /* If we still have `from_qualified_this', we have the form
9431                  <T>.this.f() and we need to build <T>.this */
9432               if (from_qualified_this)
9433                 {
9434                   decl = build_access_to_thisn (current_class, type, 0);
9435                   decl = java_complete_tree (decl);
9436                   type = TREE_TYPE (TREE_TYPE (decl));
9437                 }
9438               current_class = type;
9439               current_this = decl;
9440               from_qualified_this = 0;
9441             }
9442
9443           if (from_super && TREE_CODE (qual_wfl) == CALL_EXPR)
9444             CALL_USING_SUPER (qual_wfl) = 1;
9445           location = (TREE_CODE (qual_wfl) == CALL_EXPR ?
9446                       EXPR_WFL_LINECOL (TREE_OPERAND (qual_wfl, 0)) : 0);
9447           *where_found = patch_method_invocation (qual_wfl, decl, type,
9448                                                   from_super,
9449                                                   &is_static, &ret_decl);
9450           if (*where_found == error_mark_node)
9451             {
9452               RESTORE_THIS_AND_CURRENT_CLASS;
9453               return 1;
9454             }
9455           *type_found = type = QUAL_DECL_TYPE (*where_found);
9456
9457           /* If we're creating an inner class instance, check for that
9458              an enclosing instance is in scope */
9459           if (TREE_CODE (qual_wfl) == NEW_CLASS_EXPR
9460               && INNER_ENCLOSING_SCOPE_CHECK (type))
9461             {
9462               parse_error_context 
9463                 (qual_wfl, "No enclosing instance for inner class `%s' is in scope%s",
9464                  lang_printable_name (type, 0),
9465                  (!current_this ? "" :
9466                   "; an explicit one must be provided when creating this inner class"));
9467               RESTORE_THIS_AND_CURRENT_CLASS;
9468               return 1;
9469             }
9470
9471           /* In case we had to change then to resolve a inner class
9472              instantiation using a primary qualified by a `new' */
9473           RESTORE_THIS_AND_CURRENT_CLASS;
9474
9475           /* EH check. No check on access$<n> functions */
9476           if (location 
9477               && !OUTER_FIELD_ACCESS_IDENTIFIER_P 
9478                     (DECL_NAME (current_function_decl)))
9479             check_thrown_exceptions (location, ret_decl);
9480
9481           /* If the previous call was static and this one is too,
9482              build a compound expression to hold the two (because in
9483              that case, previous function calls aren't transported as
9484              forcoming function's argument. */
9485           if (previous_call_static && is_static)
9486             {
9487               decl = build (COMPOUND_EXPR, TREE_TYPE (*where_found),
9488                             decl, *where_found);
9489               TREE_SIDE_EFFECTS (decl) = 1;
9490             }
9491           else
9492             {
9493               previous_call_static = is_static;
9494               decl = *where_found;
9495             }
9496           from_type = 0;
9497           continue;
9498
9499         case NEW_ARRAY_EXPR:
9500         case NEW_ANONYMOUS_ARRAY_EXPR:
9501           *where_found = decl = java_complete_tree (qual_wfl);
9502           if (decl == error_mark_node)
9503             return 1;
9504           *type_found = type = QUAL_DECL_TYPE (decl);
9505           continue;
9506
9507         case CONVERT_EXPR:
9508           *where_found = decl = java_complete_tree (qual_wfl);
9509           if (decl == error_mark_node)
9510             return 1;
9511           *type_found = type = QUAL_DECL_TYPE (decl);
9512           from_cast = 1;
9513           continue;
9514
9515         case CONDITIONAL_EXPR:
9516         case STRING_CST:
9517         case MODIFY_EXPR:
9518           *where_found = decl = java_complete_tree (qual_wfl);
9519           if (decl == error_mark_node)
9520             return 1;
9521           *type_found = type = QUAL_DECL_TYPE (decl);
9522           continue;
9523
9524         case ARRAY_REF:
9525           /* If the access to the function call is a non static field,
9526              build the code to access it. */
9527           if (JDECL_P (decl) && !FIELD_STATIC (decl))
9528             {
9529               decl = maybe_access_field (decl, *where_found, type);
9530               if (decl == error_mark_node)
9531                 return 1;
9532             }
9533           /* And code for the array reference expression */
9534           decl = java_complete_tree (qual_wfl);
9535           if (decl == error_mark_node)
9536             return 1;
9537           type = QUAL_DECL_TYPE (decl);
9538           continue;
9539
9540         case PLUS_EXPR:
9541           if ((decl = java_complete_tree (qual_wfl)) == error_mark_node)
9542             return 1;
9543           if ((type = patch_string (decl)))
9544             decl = type;
9545           *where_found = QUAL_RESOLUTION (q) = decl;
9546           *type_found = type = TREE_TYPE (decl);
9547           break;
9548
9549         case CLASS_LITERAL:
9550           if ((decl = java_complete_tree (qual_wfl)) == error_mark_node)
9551             return 1;
9552           *where_found = QUAL_RESOLUTION (q) = decl;
9553           *type_found = type = TREE_TYPE (decl);
9554           break;
9555
9556         default:
9557           /* Fix for -Wall Just go to the next statement. Don't
9558              continue */
9559           break;
9560         }
9561
9562       /* If we fall here, we weren't processing a (static) function call. */
9563       previous_call_static = 0;
9564
9565       /* It can be the keyword THIS */
9566       if (TREE_CODE (qual_wfl) == EXPR_WITH_FILE_LOCATION
9567           && EXPR_WFL_NODE (qual_wfl) == this_identifier_node)
9568         {
9569           if (!current_this)
9570             {
9571               parse_error_context 
9572                 (wfl, "Keyword `this' used outside allowed context");
9573               return 1;
9574             }
9575           if (ctxp->explicit_constructor_p
9576               && type == current_class)
9577             {
9578               parse_error_context (wfl, "Can't reference `this' before the superclass constructor has been called");
9579               return 1;
9580             }
9581           /* We have to generate code for intermediate access */
9582           if (!from_type || TREE_TYPE (TREE_TYPE (current_this)) == type)
9583             {
9584               *where_found = decl = current_this;
9585               *type_found = type = QUAL_DECL_TYPE (decl);
9586             }
9587           /* We're trying to access the this from somewhere else. Make sure
9588              it's allowed before doing so. */
9589           else
9590             {
9591               if (!enclosing_context_p (type, current_class))
9592                 {
9593                   char *p  = xstrdup (lang_printable_name (type, 0));
9594                   parse_error_context (qual_wfl, "Can't use variable `%s.this': type `%s' isn't an outer type of type `%s'", 
9595                                        p, p, 
9596                                        lang_printable_name (current_class, 0));
9597                   free (p);
9598                   return 1;
9599                 }
9600               from_qualified_this = 1;
9601               /* If there's nothing else after that, we need to
9602                  produce something now, otherwise, the section of the
9603                  code that needs to produce <T>.this will generate
9604                  what is necessary. */
9605               if (!TREE_CHAIN (q))
9606                 {
9607                   decl = build_access_to_thisn (current_class, type, 0);
9608                   *where_found = decl = java_complete_tree (decl);
9609                   *type_found = type = TREE_TYPE (decl);
9610                 }
9611             }
9612
9613           from_type = 0;
9614           continue;
9615         }
9616
9617       /* 15.10.2 Accessing Superclass Members using SUPER */
9618       if (TREE_CODE (qual_wfl) == EXPR_WITH_FILE_LOCATION
9619           && EXPR_WFL_NODE (qual_wfl) == super_identifier_node)
9620         {
9621           tree node;
9622           /* Check on the restricted use of SUPER */
9623           if (METHOD_STATIC (current_function_decl)
9624               || current_class == object_type_node)
9625             {
9626               parse_error_context 
9627                 (wfl, "Keyword `super' used outside allowed context");
9628               return 1;
9629             }
9630           /* Otherwise, treat SUPER as (SUPER_CLASS)THIS */
9631           node = build_cast (EXPR_WFL_LINECOL (qual_wfl), 
9632                              CLASSTYPE_SUPER (current_class),
9633                              build_this (EXPR_WFL_LINECOL (qual_wfl)));
9634           *where_found = decl = java_complete_tree (node);
9635           if (decl == error_mark_node)
9636             return 1;
9637           *type_found = type = QUAL_DECL_TYPE (decl);
9638           from_super = from_type = 1;
9639           continue;
9640         }
9641
9642       /* 15.13.1: Can't search for field name in packages, so we
9643          assume a variable/class name was meant. */
9644       if (RESOLVE_PACKAGE_NAME_P (qual_wfl))
9645         {
9646           tree name = resolve_package (wfl, &q);
9647           if (name)
9648             {
9649               tree list;
9650               *where_found = decl = resolve_no_layout (name, qual_wfl);
9651               /* We want to be absolutely sure that the class is laid
9652                  out. We're going to search something inside it. */
9653               *type_found = type = TREE_TYPE (decl);
9654               layout_class (type);
9655               from_type = 1;
9656
9657               /* Fix them all the way down, if any are left. */
9658               if (q)
9659                 {
9660                   list = TREE_CHAIN (q);
9661                   while (list)
9662                     {
9663                       RESOLVE_EXPRESSION_NAME_P (QUAL_WFL (list)) = 1;
9664                       RESOLVE_PACKAGE_NAME_P (QUAL_WFL (list)) = 0;
9665                       list = TREE_CHAIN (list);
9666                     }
9667                 }
9668             }
9669           else
9670             {
9671               if (from_super || from_cast)
9672                 parse_error_context 
9673                   ((from_cast ? qual_wfl : wfl),
9674                    "No variable `%s' defined in class `%s'",
9675                    IDENTIFIER_POINTER (EXPR_WFL_NODE (qual_wfl)),
9676                    lang_printable_name (type, 0));
9677               else
9678                 parse_error_context
9679                   (qual_wfl, "Undefined variable or class name: `%s'",
9680                    IDENTIFIER_POINTER (EXPR_WFL_NODE (qual_wfl)));
9681               return 1;
9682             }
9683         }
9684
9685       /* We have a type name. It's been already resolved when the
9686          expression was qualified. */
9687       else if (RESOLVE_TYPE_NAME_P (qual_wfl) && QUAL_RESOLUTION (q))
9688         {
9689           decl = QUAL_RESOLUTION (q);
9690
9691           /* Sneak preview. If next we see a `new', we're facing a
9692              qualification with resulted in a type being selected
9693              instead of a field.  Report the error */
9694           if(TREE_CHAIN (q) 
9695              && TREE_CODE (TREE_PURPOSE (TREE_CHAIN (q))) == NEW_CLASS_EXPR)
9696             {
9697               parse_error_context (qual_wfl, "Undefined variable `%s'",
9698                                    IDENTIFIER_POINTER (EXPR_WFL_NODE (wfl)));
9699               return 1;
9700             }
9701
9702           if (not_accessible_p (TREE_TYPE (decl), decl, type, 0))
9703             {
9704               parse_error_context 
9705                 (qual_wfl, "Can't access %s field `%s.%s' from `%s'",
9706                  java_accstring_lookup (get_access_flags_from_decl (decl)),
9707                  GET_TYPE_NAME (type),
9708                  IDENTIFIER_POINTER (DECL_NAME (decl)),
9709                  IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (current_class))));
9710               return 1;
9711             }
9712           check_deprecation (qual_wfl, decl);
9713
9714           type = TREE_TYPE (decl);
9715           from_type = 1;
9716         }
9717       /* We resolve an expression name */
9718       else 
9719         {
9720           tree field_decl = NULL_TREE;
9721
9722           /* If there exists an early resolution, use it. That occurs
9723              only once and we know that there are more things to
9724              come. Don't do that when processing something after SUPER
9725              (we need more thing to be put in place below */
9726           if (!from_super && QUAL_RESOLUTION (q))
9727             {
9728               decl = QUAL_RESOLUTION (q);
9729               if (!type)
9730                 {
9731                   if (TREE_CODE (decl) == FIELD_DECL && !FIELD_STATIC (decl))
9732                     {
9733                       if (current_this)
9734                         *where_found = current_this;
9735                       else
9736                         {
9737                           static_ref_err (qual_wfl, DECL_NAME (decl),
9738                                           current_class);
9739                           return 1;
9740                         }
9741                       if (outer_field_access_p (current_class, decl))
9742                         decl = build_outer_field_access (qual_wfl, decl);
9743                     }
9744                   else
9745                     {
9746                       *where_found = TREE_TYPE (decl);
9747                       if (TREE_CODE (*where_found) == POINTER_TYPE)
9748                         *where_found = TREE_TYPE (*where_found);
9749                     }
9750                 }
9751             }
9752
9753           /* Report and error if we're using a numerical litteral as a
9754              qualifier. It can only be an INTEGER_CST. */
9755           else if (TREE_CODE (qual_wfl) == INTEGER_CST)
9756             {
9757               parse_error_context
9758                 (wfl, "Can't use type `%s' as a qualifier",
9759                  lang_printable_name (TREE_TYPE (qual_wfl), 0));
9760               return 1;
9761             }
9762
9763           /* We have to search for a field, knowing the type of its
9764              container. The flag FROM_TYPE indicates that we resolved
9765              the last member of the expression as a type name, which
9766              means that for the resolution of this field, we'll look
9767              for other errors than if it was resolved as a member of
9768              an other field. */
9769           else
9770             {
9771               int is_static;
9772               tree field_decl_type; /* For layout */
9773
9774               if (!from_type && !JREFERENCE_TYPE_P (type))
9775                 {
9776                   parse_error_context 
9777                     (qual_wfl, "Attempt to reference field `%s' in `%s %s'",
9778                      IDENTIFIER_POINTER (EXPR_WFL_NODE (qual_wfl)),
9779                      lang_printable_name (type, 0),
9780                      IDENTIFIER_POINTER (DECL_NAME (field_decl)));
9781                   return 1;
9782                 }
9783               
9784               field_decl = lookup_field_wrapper (type,
9785                                                  EXPR_WFL_NODE (qual_wfl));
9786
9787               /* Maybe what we're trying to access to is an inner
9788                  class, only if decl is a TYPE_DECL. */
9789               if (!field_decl && TREE_CODE (decl) == TYPE_DECL)
9790                 {
9791                   tree ptr, inner_decl;
9792
9793                   BUILD_PTR_FROM_NAME (ptr, EXPR_WFL_NODE (qual_wfl));
9794                   inner_decl = resolve_class (decl, ptr, NULL_TREE, qual_wfl);
9795                   if (inner_decl)
9796                     {
9797                       check_inner_class_access (inner_decl, decl, qual_wfl); 
9798                       type = TREE_TYPE (inner_decl);
9799                       decl = inner_decl;
9800                       from_type = 1;
9801                       continue;
9802                     }
9803                 }
9804
9805               if (field_decl == NULL_TREE)
9806                 {
9807                   parse_error_context 
9808                     (qual_wfl, "No variable `%s' defined in type `%s'",
9809                      IDENTIFIER_POINTER (EXPR_WFL_NODE (qual_wfl)), 
9810                      GET_TYPE_NAME (type));
9811                   return 1;
9812                 }
9813               if (field_decl == error_mark_node)
9814                 return 1;
9815
9816               /* Layout the type of field_decl, since we may need
9817                  it. Don't do primitive types or loaded classes. The
9818                  situation of non primitive arrays may not handled
9819                  properly here. FIXME */
9820               if (TREE_CODE (TREE_TYPE (field_decl)) == POINTER_TYPE)
9821                 field_decl_type = TREE_TYPE (TREE_TYPE (field_decl));
9822               else
9823                 field_decl_type = TREE_TYPE (field_decl);
9824               if (!JPRIMITIVE_TYPE_P (field_decl_type) 
9825                   && !CLASS_LOADED_P (field_decl_type)
9826                   && !TYPE_ARRAY_P (field_decl_type))
9827                 resolve_and_layout (field_decl_type, NULL_TREE);
9828               
9829               /* Check on accessibility here */
9830               if (not_accessible_p (current_class, field_decl,
9831                                     DECL_CONTEXT (field_decl), from_super))
9832                 {
9833                   parse_error_context 
9834                     (qual_wfl,
9835                      "Can't access %s field `%s.%s' from `%s'",
9836                      java_accstring_lookup 
9837                        (get_access_flags_from_decl (field_decl)),
9838                      GET_TYPE_NAME (type),
9839                      IDENTIFIER_POINTER (DECL_NAME (field_decl)),
9840                      IDENTIFIER_POINTER 
9841                        (DECL_NAME (TYPE_NAME (current_class))));
9842                   return 1;
9843                 }
9844               check_deprecation (qual_wfl, field_decl);
9845               
9846               /* There are things to check when fields are accessed
9847                  from type. There are no restrictions on a static
9848                  declaration of the field when it is accessed from an
9849                  interface */
9850               is_static = FIELD_STATIC (field_decl);
9851               if (!from_super && from_type 
9852                   && !TYPE_INTERFACE_P (type) 
9853                   && !is_static 
9854                   && (current_function_decl 
9855                       && METHOD_STATIC (current_function_decl)))
9856                 {
9857                   static_ref_err (qual_wfl, EXPR_WFL_NODE (qual_wfl), type);
9858                   return 1;
9859                 }
9860               from_cast = from_super = 0;
9861
9862               /* It's an access from a type but it isn't static, we
9863                  make it relative to `this'. */
9864               if (!is_static && from_type)
9865                 decl = current_this;
9866
9867               /* If we need to generate something to get a proper
9868                  handle on what this field is accessed from, do it
9869                  now. */
9870               if (!is_static)
9871                 {
9872                   decl = maybe_access_field (decl, *where_found, *type_found);
9873                   if (decl == error_mark_node)
9874                     return 1;
9875                 }
9876
9877               /* We want to keep the location were found it, and the type
9878                  we found. */
9879               *where_found = decl;
9880               *type_found = type;
9881
9882               /* Generate the correct expression for field access from
9883                  qualified this */
9884               if (from_qualified_this)
9885                 {
9886                   field_decl = build_outer_field_access (qual_wfl, field_decl);
9887                   from_qualified_this = 0;
9888                 }
9889
9890               /* This is the decl found and eventually the next one to
9891                  search from */
9892               decl = field_decl;
9893             }
9894           from_type = 0;
9895           type = QUAL_DECL_TYPE (decl);
9896
9897           /* Sneak preview. If decl is qualified by a `new', report
9898              the error here to be accurate on the peculiar construct */
9899           if (TREE_CHAIN (q) 
9900               && TREE_CODE (TREE_PURPOSE (TREE_CHAIN (q))) == NEW_CLASS_EXPR
9901               && !JREFERENCE_TYPE_P (type))
9902             {
9903               parse_error_context (qual_wfl, "Attempt to reference field `new' in a `%s'", 
9904                                    lang_printable_name (type, 0));
9905               return 1;
9906             }
9907         }
9908       /* `q' might have changed due to a after package resolution
9909          re-qualification */
9910       if (!q)
9911         break;
9912     }
9913   *found_decl = decl;
9914   return 0;
9915 }
9916
9917 /* 6.6 Qualified name and access control. Returns 1 if MEMBER (a decl)
9918    can't be accessed from REFERENCE (a record type). If MEMBER
9919    features a protected access, we then use WHERE which, if non null,
9920    holds the type of MEMBER's access that is checked against
9921    6.6.2.1. This function should be used when decl is a field or a
9922    method.  */
9923
9924 static int
9925 not_accessible_p (reference, member, where, from_super)
9926      tree reference, member;
9927      tree where;
9928      int from_super;
9929 {
9930   int access_flag = get_access_flags_from_decl (member);
9931
9932   /* Inner classes are processed by check_inner_class_access */
9933   if (INNER_CLASS_TYPE_P (reference))
9934     return 0;
9935
9936   /* Access always granted for members declared public */
9937   if (access_flag & ACC_PUBLIC)
9938     return 0;
9939   
9940   /* Check access on protected members */
9941   if (access_flag & ACC_PROTECTED)
9942     {
9943       /* Access granted if it occurs from within the package
9944          containing the class in which the protected member is
9945          declared */
9946       if (class_in_current_package (DECL_CONTEXT (member)))
9947         return 0;
9948
9949       /* If accessed with the form `super.member', then access is granted */
9950       if (from_super)
9951         return 0;
9952
9953       /* If where is active, access was made through a
9954          qualifier. Access is granted if the type of the qualifier is
9955          or is a sublass of the type the access made from (6.6.2.1.)  */
9956       if (where && !inherits_from_p (reference, where))
9957         return 1;
9958
9959       /* Otherwise, access is granted if occurring from the class where
9960          member is declared or a subclass of it. Find the right
9961          context to perform the check */
9962       if (PURE_INNER_CLASS_TYPE_P (reference))
9963         {
9964           while (INNER_CLASS_TYPE_P (reference))
9965             {
9966               if (inherits_from_p (reference, DECL_CONTEXT (member)))
9967                 return 0;
9968               reference = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (reference)));
9969             }
9970         }
9971       if (inherits_from_p (reference, DECL_CONTEXT (member)))
9972         return 0;
9973       return 1;
9974     }
9975
9976   /* Check access on private members. Access is granted only if it
9977      occurs from within the class in which it is declared -- that does
9978      it for innerclasses too. */
9979   if (access_flag & ACC_PRIVATE)
9980     {
9981       if (reference == DECL_CONTEXT (member))
9982         return 0;
9983       if (enclosing_context_p (reference, DECL_CONTEXT (member)))
9984         return 0;
9985       return 1;
9986     }
9987
9988   /* Default access are permitted only when occurring within the
9989      package in which the type (REFERENCE) is declared. In other words,
9990      REFERENCE is defined in the current package */
9991   if (ctxp->package)
9992     return !class_in_current_package (reference);
9993
9994   /* Otherwise, access is granted */
9995   return 0;
9996 }
9997
9998 /* Test deprecated decl access.  */
9999 static void
10000 check_deprecation (wfl, decl)
10001      tree wfl, decl;
10002 {
10003   const char *file = DECL_SOURCE_FILE (decl);
10004   /* Complain if the field is deprecated and the file it was defined
10005      in isn't compiled at the same time the file which contains its
10006      use is */
10007   if (DECL_DEPRECATED (decl) 
10008       && !IS_A_COMMAND_LINE_FILENAME_P (get_identifier (file)))
10009     {
10010       char the [20];
10011       switch (TREE_CODE (decl))
10012         {
10013         case FUNCTION_DECL:
10014           strcpy (the, "method");
10015           break;
10016         case FIELD_DECL:
10017         case VAR_DECL:
10018           strcpy (the, "field");
10019           break;
10020         case TYPE_DECL:
10021           parse_warning_context (wfl, "The class `%s' has been deprecated",
10022                                  IDENTIFIER_POINTER (DECL_NAME (decl)));
10023           return;
10024         default:
10025           abort ();
10026         }
10027       /* Don't issue a message if the context as been deprecated as a
10028          whole. */
10029       if (! CLASS_DEPRECATED (TYPE_NAME (DECL_CONTEXT (decl))))
10030         parse_warning_context 
10031           (wfl, "The %s `%s' in class `%s' has been deprecated", 
10032            the, lang_printable_name (decl, 0),
10033            IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (DECL_CONTEXT (decl)))));
10034     }
10035 }
10036
10037 /* Returns 1 if class was declared in the current package, 0 otherwise */
10038
10039 static int
10040 class_in_current_package (class)
10041      tree class;
10042 {
10043   static tree cache = NULL_TREE;
10044   int qualified_flag;
10045   tree left;
10046
10047   if (cache == class)
10048     return 1;
10049
10050   qualified_flag = QUALIFIED_P (DECL_NAME (TYPE_NAME (class)));
10051
10052   /* If the current package is empty and the name of CLASS is
10053      qualified, class isn't in the current package.  If there is a
10054      current package and the name of the CLASS is not qualified, class
10055      isn't in the current package */
10056   if ((!ctxp->package && qualified_flag) || (ctxp->package && !qualified_flag))
10057     return 0;
10058
10059   /* If there is not package and the name of CLASS isn't qualified,
10060      they belong to the same unnamed package */
10061   if (!ctxp->package && !qualified_flag)
10062     return 1;
10063
10064   /* Compare the left part of the name of CLASS with the package name */
10065   breakdown_qualified (&left, NULL, DECL_NAME (TYPE_NAME (class)));
10066   if (ctxp->package == left)
10067     {
10068       static int initialized_p;
10069       /* Register CACHE with the garbage collector.  */
10070       if (!initialized_p)
10071         {
10072           ggc_add_tree_root (&cache, 1);
10073           initialized_p = 1;
10074         }
10075
10076       cache = class;
10077       return 1;
10078     }
10079   return 0;
10080 }
10081
10082 /* This function may generate code to access DECL from WHERE. This is
10083    done only if certain conditions meet.  */
10084
10085 static tree
10086 maybe_access_field (decl, where, type)
10087   tree decl, where, type;
10088 {
10089   if (TREE_CODE (decl) == FIELD_DECL && decl != current_this
10090       && !FIELD_STATIC (decl))
10091     decl = build_field_ref (where ? where : current_this, 
10092                             (type ? type : DECL_CONTEXT (decl)),
10093                             DECL_NAME (decl));
10094   return decl;
10095 }
10096
10097 /* Build a method invocation, by patching PATCH. If non NULL
10098    and according to the situation, PRIMARY and WHERE may be
10099    used. IS_STATIC is set to 1 if the invoked function is static. */
10100
10101 static tree
10102 patch_method_invocation (patch, primary, where, from_super,
10103                         is_static, ret_decl)
10104      tree patch, primary, where;
10105      int from_super;
10106      int *is_static;
10107      tree *ret_decl;
10108 {
10109   tree wfl = TREE_OPERAND (patch, 0);
10110   tree args = TREE_OPERAND (patch, 1);
10111   tree name = EXPR_WFL_NODE (wfl);
10112   tree list;
10113   int is_static_flag = 0;
10114   int is_super_init = 0;
10115   tree this_arg = NULL_TREE;
10116   int is_array_clone_call = 0;
10117   
10118   /* Should be overriden if everything goes well. Otherwise, if
10119      something fails, it should keep this value. It stop the
10120      evaluation of a bogus assignment. See java_complete_tree,
10121      MODIFY_EXPR: for the reasons why we sometimes want to keep on
10122      evaluating an assignment */
10123   TREE_TYPE (patch) = error_mark_node;
10124
10125   /* Since lookup functions are messing with line numbers, save the
10126      context now.  */
10127   java_parser_context_save_global ();
10128
10129   /* 15.11.1: Compile-Time Step 1: Determine Class or Interface to Search */
10130
10131   /* Resolution of qualified name, excluding constructors */
10132   if (QUALIFIED_P (name) && !CALL_CONSTRUCTOR_P (patch))
10133     {
10134       tree identifier, identifier_wfl, type, resolved;
10135       /* Extract the last IDENTIFIER of the qualified
10136          expression. This is a wfl and we will use it's location
10137          data during error report. */
10138       identifier_wfl = cut_identifier_in_qualified (wfl);
10139       identifier = EXPR_WFL_NODE (identifier_wfl);
10140       
10141       /* Given the context, IDENTIFIER is syntactically qualified
10142          as a MethodName. We need to qualify what's before */
10143       qualify_ambiguous_name (wfl);
10144       resolved = resolve_field_access (wfl, NULL, NULL);
10145
10146       if (TREE_CODE (resolved) == VAR_DECL && FIELD_STATIC (resolved)
10147          && FIELD_FINAL (resolved) 
10148          && !inherits_from_p (DECL_CONTEXT (resolved), current_class)
10149          && !flag_emit_class_files && !flag_emit_xref)
10150        resolved = build_class_init (DECL_CONTEXT (resolved), resolved);
10151
10152       if (resolved == error_mark_node)
10153         PATCH_METHOD_RETURN_ERROR ();
10154
10155       type = GET_SKIP_TYPE (resolved);
10156       resolve_and_layout (type, NULL_TREE);
10157       
10158       if (JPRIMITIVE_TYPE_P (type))
10159         {
10160           parse_error_context
10161             (identifier_wfl,
10162              "Can't invoke a method on primitive type `%s'",
10163              IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (type))));
10164           PATCH_METHOD_RETURN_ERROR ();         
10165         }
10166
10167       list = lookup_method_invoke (0, identifier_wfl, type, identifier, args);
10168       args = nreverse (args);
10169
10170       /* We're resolving a call from a type */
10171       if (TREE_CODE (resolved) == TYPE_DECL)
10172         {
10173           if (CLASS_INTERFACE (resolved))
10174             {
10175               parse_error_context
10176                 (identifier_wfl,
10177                 "Can't make static reference to method `%s' in interface `%s'",
10178                  IDENTIFIER_POINTER (identifier), 
10179                  IDENTIFIER_POINTER (name));
10180               PATCH_METHOD_RETURN_ERROR ();
10181             }
10182           if (list && !METHOD_STATIC (list))
10183             {
10184               char *fct_name = xstrdup (lang_printable_name (list, 0));
10185               parse_error_context 
10186                 (identifier_wfl,
10187                  "Can't make static reference to method `%s %s' in class `%s'",
10188                  lang_printable_name (TREE_TYPE (TREE_TYPE (list)), 0), 
10189                  fct_name, IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (type))));
10190               free (fct_name);
10191               PATCH_METHOD_RETURN_ERROR ();
10192             }
10193         }
10194       else
10195         this_arg = primary = resolved;
10196       
10197       if (TYPE_ARRAY_P (type) && identifier == get_identifier ("clone"))
10198         is_array_clone_call = 1;
10199       
10200       /* IDENTIFIER_WFL will be used to report any problem further */
10201       wfl = identifier_wfl;
10202     }
10203   /* Resolution of simple names, names generated after a primary: or
10204      constructors */
10205   else
10206     {
10207       tree class_to_search = NULL_TREE;
10208       int lc;                   /* Looking for Constructor */
10209       
10210       /* We search constructor in their target class */
10211       if (CALL_CONSTRUCTOR_P (patch))
10212         {
10213           if (TREE_CODE (patch) == NEW_CLASS_EXPR)
10214             class_to_search = EXPR_WFL_NODE (wfl);
10215           else if (EXPR_WFL_NODE (TREE_OPERAND (patch, 0)) == 
10216                    this_identifier_node)
10217             class_to_search = NULL_TREE;
10218           else if (EXPR_WFL_NODE (TREE_OPERAND (patch, 0)) ==
10219                    super_identifier_node)
10220             {
10221               is_super_init = 1;
10222               if (CLASSTYPE_SUPER (current_class))
10223                 class_to_search = 
10224                   DECL_NAME (TYPE_NAME (CLASSTYPE_SUPER (current_class)));
10225               else
10226                 {
10227                   parse_error_context (wfl, "Can't invoke super constructor on java.lang.Object");
10228                   PATCH_METHOD_RETURN_ERROR ();
10229                 }
10230             }
10231
10232           /* Class to search is NULL if we're searching the current one */
10233           if (class_to_search)
10234             {
10235               class_to_search = resolve_and_layout (class_to_search, wfl);
10236
10237               if (!class_to_search)
10238                 {
10239                   parse_error_context 
10240                     (wfl, "Class `%s' not found in type declaration",
10241                      IDENTIFIER_POINTER (EXPR_WFL_NODE (wfl)));
10242                   PATCH_METHOD_RETURN_ERROR ();
10243                 }
10244               
10245               /* Can't instantiate an abstract class, but we can
10246                  invoke it's constructor. It's use within the `new'
10247                  context is denied here. */
10248               if (CLASS_ABSTRACT (class_to_search) 
10249                   && TREE_CODE (patch) == NEW_CLASS_EXPR)
10250                 {
10251                   parse_error_context 
10252                     (wfl, "Class `%s' is an abstract class. It can't be instantiated",
10253                      IDENTIFIER_POINTER (EXPR_WFL_NODE (wfl)));
10254                   PATCH_METHOD_RETURN_ERROR ();
10255                 }
10256
10257               class_to_search = TREE_TYPE (class_to_search);
10258             }
10259           else
10260             class_to_search = current_class;
10261           lc = 1;
10262         }
10263       /* This is a regular search in the local class, unless an
10264          alternate class is specified. */
10265       else
10266         {
10267           if (where != NULL_TREE)
10268             class_to_search = where;
10269           else if (QUALIFIED_P (name))
10270             class_to_search = current_class;
10271           else
10272             {
10273               class_to_search = current_class;
10274
10275               for (;;)
10276                 {
10277                   if (has_method (class_to_search, name))
10278                     break;
10279                   if (! INNER_CLASS_TYPE_P (class_to_search))
10280                     {
10281                       parse_error_context (wfl,
10282                                            "No method named `%s' in scope",
10283                                            IDENTIFIER_POINTER (name));
10284                       PATCH_METHOD_RETURN_ERROR ();
10285                     }
10286                   class_to_search
10287                     = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (class_to_search)));
10288                 }
10289             }
10290           lc = 0;
10291         }
10292
10293       /* NAME is a simple identifier or comes from a primary. Search
10294          in the class whose declaration contain the method being
10295          invoked. */
10296       resolve_and_layout (class_to_search, NULL_TREE);
10297
10298       list = lookup_method_invoke (lc, wfl, class_to_search, name, args);
10299       /* Don't continue if no method were found, as the next statement
10300          can't be executed then. */
10301       if (!list)
10302         PATCH_METHOD_RETURN_ERROR ();
10303       
10304       if (TYPE_ARRAY_P (class_to_search)
10305           && DECL_NAME (list) == get_identifier ("clone"))
10306         is_array_clone_call = 1;
10307
10308       /* Check for static reference if non static methods */
10309       if (check_for_static_method_reference (wfl, patch, list, 
10310                                              class_to_search, primary))
10311         PATCH_METHOD_RETURN_ERROR ();
10312
10313       /* Check for inner classes creation from illegal contexts */
10314       if (lc && (INNER_CLASS_TYPE_P (class_to_search)
10315                  && !CLASS_STATIC (TYPE_NAME (class_to_search)))
10316           && INNER_ENCLOSING_SCOPE_CHECK (class_to_search)
10317           && !DECL_INIT_P (current_function_decl))
10318         {
10319           parse_error_context 
10320             (wfl, "No enclosing instance for inner class `%s' is in scope%s",
10321              lang_printable_name (class_to_search, 0),
10322              (!current_this ? "" :
10323               "; an explicit one must be provided when creating this inner class"));
10324           PATCH_METHOD_RETURN_ERROR ();
10325         }
10326
10327       /* Non static methods are called with the current object extra
10328          argument. If patch a `new TYPE()', the argument is the value
10329          returned by the object allocator. If method is resolved as a
10330          primary, use the primary otherwise use the current THIS. */
10331       args = nreverse (args);
10332       if (TREE_CODE (patch) != NEW_CLASS_EXPR)
10333         {
10334           this_arg = primary ? primary : current_this;
10335
10336           /* If we're using an access method, things are different.
10337              There are two familly of cases:
10338
10339              1) We're not generating bytecodes:
10340
10341              - LIST is non static. It's invocation is transformed from
10342                x(a1,...,an) into this$<n>.x(a1,....an).
10343              - LIST is static. It's invocation is transformed from
10344                x(a1,...,an) into TYPE_OF(this$<n>).x(a1,....an)
10345
10346              2) We're generating bytecodes:
10347              
10348              - LIST is non static. It's invocation is transformed from
10349                x(a1,....,an) into access$<n>(this$<n>,a1,...,an).
10350              - LIST is static. It's invocation is transformed from
10351                x(a1,....,an) into TYPE_OF(this$<n>).x(a1,....an).
10352
10353              Of course, this$<n> can be abitrary complex, ranging from
10354              this$0 (the immediate outer context) to 
10355              access$0(access$0(...(this$0))). 
10356              
10357              maybe_use_access_method returns a non zero value if the
10358              this_arg has to be moved into the (then generated) stub
10359              argument list. In the meantime, the selected function
10360              might have be replaced by a generated stub. */
10361           if (!primary &&
10362               maybe_use_access_method (is_super_init, &list, &this_arg))
10363             {
10364               args = tree_cons (NULL_TREE, this_arg, args);
10365               this_arg = NULL_TREE; /* So it doesn't get chained twice */
10366             }
10367         }
10368     }
10369
10370   /* Merge point of all resolution schemes. If we have nothing, this
10371      is an error, already signaled */
10372   if (!list) 
10373     PATCH_METHOD_RETURN_ERROR ();
10374
10375   /* Check accessibility, position the is_static flag, build and
10376      return the call */
10377   if (not_accessible_p (DECL_CONTEXT (current_function_decl), list,
10378                         (primary ? TREE_TYPE (TREE_TYPE (primary)) : 
10379                          NULL_TREE), from_super)
10380       /* Calls to clone() on array types are permitted as a special-case. */
10381       && !is_array_clone_call)
10382     {
10383       const char *const fct_name = IDENTIFIER_POINTER (DECL_NAME (list));
10384       const char *const access =
10385         java_accstring_lookup (get_access_flags_from_decl (list));
10386       const char *const klass =
10387         IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (DECL_CONTEXT (list))));
10388       const char *const refklass =
10389         IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (current_class)));
10390       const char *const what = (DECL_CONSTRUCTOR_P (list)
10391                                 ? "constructor" : "method");
10392       /* FIXME: WFL yields the wrong message here but I don't know
10393          what else to use.  */
10394       parse_error_context (wfl,
10395                            "Can't access %s %s `%s.%s' from `%s'",
10396                            access, what, klass, fct_name, refklass);
10397       PATCH_METHOD_RETURN_ERROR ();
10398     }
10399
10400   /* Deprecation check: check whether the method being invoked or the
10401      instance-being-created's type are deprecated. */
10402   if (TREE_CODE (patch) == NEW_CLASS_EXPR)
10403     check_deprecation (wfl, TYPE_NAME (DECL_CONTEXT (list)));
10404   else
10405     check_deprecation (wfl, list);
10406
10407   /* If invoking a innerclass constructor, there are hidden parameters
10408      to pass */
10409   if (TREE_CODE (patch) == NEW_CLASS_EXPR 
10410       && PURE_INNER_CLASS_TYPE_P (DECL_CONTEXT (list)))
10411     {
10412       /* And make sure we add the accessed local variables to be saved
10413          in field aliases. */
10414       args = build_alias_initializer_parameter_list
10415         (AIPL_FUNCTION_CTOR_INVOCATION, DECL_CONTEXT (list), args, NULL);
10416
10417       /* Secretly pass the current_this/primary as a second argument */
10418       if (primary || current_this)
10419         {
10420           tree extra_arg;
10421           tree this_type = (current_this ?
10422                             TREE_TYPE (TREE_TYPE (current_this)) : NULL_TREE);
10423           /* Method's (list) enclosing context */
10424           tree mec = DECL_CONTEXT (TYPE_NAME (DECL_CONTEXT (list)));
10425           /* If we have a primary, use it. */
10426           if (primary)
10427             extra_arg = primary;
10428           /* The current `this' is an inner class but isn't a direct
10429              enclosing context for the inner class we're trying to
10430              create. Build an access to the proper enclosing context
10431              and use it. */
10432           else if (current_this && PURE_INNER_CLASS_TYPE_P (this_type)
10433                    && this_type != TREE_TYPE (mec))
10434             {
10435
10436               extra_arg = build_access_to_thisn (current_class,
10437                                                  TREE_TYPE (mec), 0);
10438               extra_arg = java_complete_tree (extra_arg);
10439             }
10440           /* Otherwise, just use the current `this' as an enclosing
10441              context. */
10442           else
10443             extra_arg = current_this;
10444           args = tree_cons (NULL_TREE, extra_arg, args);
10445         }
10446       else
10447         args = tree_cons (NULL_TREE, integer_zero_node, args);
10448     }
10449
10450   /* This handles the situation where a constructor invocation needs
10451      to have an enclosing context passed as a second parameter (the
10452      constructor is one of an inner class. We extract it from the
10453      current function.  */
10454   if ((is_super_init || 
10455        (TREE_CODE (patch) == CALL_EXPR && name == this_identifier_node))
10456       && PURE_INNER_CLASS_TYPE_P (DECL_CONTEXT (list)))
10457     {
10458       tree enclosing_decl = DECL_CONTEXT (TYPE_NAME (current_class));
10459       tree extra_arg;
10460
10461       if (ANONYMOUS_CLASS_P (current_class) || !DECL_CONTEXT (enclosing_decl))
10462         {
10463           extra_arg = DECL_FUNCTION_BODY (current_function_decl);
10464           extra_arg = TREE_CHAIN (BLOCK_EXPR_DECLS (extra_arg));
10465         }
10466       else
10467         {
10468           tree dest = TREE_TYPE (DECL_CONTEXT (enclosing_decl));
10469           extra_arg = 
10470             build_access_to_thisn (TREE_TYPE (enclosing_decl), dest, 0);
10471           extra_arg = java_complete_tree (extra_arg);
10472         }
10473       args = tree_cons (NULL_TREE, extra_arg, args);
10474     }
10475
10476   is_static_flag = METHOD_STATIC (list);
10477   if (! is_static_flag && this_arg != NULL_TREE)
10478     args = tree_cons (NULL_TREE, this_arg, args);
10479
10480   /* In the context of an explicit constructor invocation, we can't
10481      invoke any method relying on `this'. Exceptions are: we're
10482      invoking a static function, primary exists and is not the current
10483      this, we're creating a new object. */
10484   if (ctxp->explicit_constructor_p 
10485       && !is_static_flag 
10486       && (!primary || primary == current_this)
10487       && (TREE_CODE (patch) != NEW_CLASS_EXPR))
10488     {
10489       parse_error_context (wfl, "Can't reference `this' before the superclass constructor has been called");
10490       PATCH_METHOD_RETURN_ERROR ();
10491     }
10492   java_parser_context_restore_global ();
10493   if (is_static) 
10494     *is_static = is_static_flag;
10495   /* Sometimes, we want the decl of the selected method. Such as for
10496      EH checking */
10497   if (ret_decl)
10498     *ret_decl = list;
10499   patch = patch_invoke (patch, list, args);
10500
10501   /* Now is a good time to insert the call to finit$ */
10502   if (is_super_init && CLASS_HAS_FINIT_P (current_class))
10503     {
10504       tree finit_parms, finit_call;
10505       
10506       /* Prepare to pass hidden parameters to finit$, if any. */
10507       finit_parms = build_alias_initializer_parameter_list 
10508         (AIPL_FUNCTION_FINIT_INVOCATION, current_class, NULL_TREE, NULL);
10509       
10510       finit_call = 
10511         build_method_invocation (build_wfl_node (finit_identifier_node),
10512                                  finit_parms);
10513
10514       /* Generate the code used to initialize fields declared with an
10515          initialization statement and build a compound statement along
10516          with the super constructor invocation. */
10517       CAN_COMPLETE_NORMALLY (patch) = 1;
10518       patch = build (COMPOUND_EXPR, void_type_node, patch,
10519                      java_complete_tree (finit_call));
10520     }
10521   return patch;
10522 }
10523
10524 /* Check that we're not trying to do a static reference to a method in
10525    non static method. Return 1 if it's the case, 0 otherwise. */
10526
10527 static int
10528 check_for_static_method_reference (wfl, node, method, where, primary)
10529      tree wfl, node, method, where, primary;
10530 {
10531   if (METHOD_STATIC (current_function_decl) 
10532       && !METHOD_STATIC (method) && !primary && !CALL_CONSTRUCTOR_P (node))
10533     {
10534       char *fct_name = xstrdup (lang_printable_name (method, 0));
10535       parse_error_context 
10536         (wfl, "Can't make static reference to method `%s %s' in class `%s'", 
10537          lang_printable_name (TREE_TYPE (TREE_TYPE (method)), 0), fct_name,
10538          IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (where))));
10539       free (fct_name);
10540       return 1;
10541     }
10542   return 0;
10543 }
10544
10545 /* Fix the invocation of *MDECL if necessary in the case of a
10546    invocation from an inner class. *THIS_ARG might be modified
10547    appropriately and an alternative access to *MDECL might be
10548    returned.  */
10549
10550 static int
10551 maybe_use_access_method (is_super_init, mdecl, this_arg)
10552      int is_super_init;
10553      tree *mdecl, *this_arg;
10554 {
10555   tree ctx;
10556   tree md = *mdecl, ta = *this_arg;
10557   int to_return = 0;
10558   int non_static_context = !METHOD_STATIC (md);
10559
10560   if (is_super_init 
10561       || DECL_CONTEXT (md) == current_class
10562       || !PURE_INNER_CLASS_TYPE_P (current_class) 
10563       || DECL_FINIT_P (md)
10564       || DECL_INSTINIT_P (md))
10565     return 0;
10566   
10567   /* If we're calling a method found in an enclosing class, generate
10568      what it takes to retrieve the right this. Don't do that if we're
10569      invoking a static method. Note that if MD's type is unrelated to
10570      CURRENT_CLASS, then the current this can be used. */
10571
10572   if (non_static_context && DECL_CONTEXT (md) != object_type_node)
10573     {
10574       ctx = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (current_class)));
10575       if (inherits_from_p (ctx, DECL_CONTEXT (md)))
10576         {
10577           ta = build_current_thisn (current_class);
10578           ta = build_wfl_node (ta);
10579         }
10580       else
10581         {
10582           tree type = ctx;
10583           while (type)
10584             {
10585               maybe_build_thisn_access_method (type);
10586               if (inherits_from_p (type, DECL_CONTEXT (md)))
10587                 {
10588                   ta = build_access_to_thisn (ctx, type, 0);
10589                   break;
10590                 }
10591               type = (DECL_CONTEXT (TYPE_NAME (type)) ? 
10592                       TREE_TYPE (DECL_CONTEXT (TYPE_NAME (type))) : NULL_TREE);
10593             }
10594         }
10595       ta = java_complete_tree (ta);
10596     }
10597
10598   /* We might have to use an access method to get to MD. We can
10599      break the method access rule as far as we're not generating
10600      bytecode */
10601   if (METHOD_PRIVATE (md) && flag_emit_class_files)
10602     {
10603       md = build_outer_method_access_method (md);
10604       to_return = 1;
10605     }
10606
10607   *mdecl = md;
10608   *this_arg = ta;
10609
10610   /* Returnin a non zero value indicates we were doing a non static
10611      method invokation that is now a static invocation. It will have
10612      callee displace `this' to insert it in the regular argument
10613      list. */
10614   return (non_static_context && to_return);
10615 }
10616
10617 /* Patch an invoke expression METHOD and ARGS, based on its invocation
10618    mode.  */
10619
10620 static tree
10621 patch_invoke (patch, method, args)
10622      tree patch, method, args;
10623 {
10624   tree dtable, func;
10625   tree original_call, t, ta;
10626   tree check = NULL_TREE;
10627
10628   /* Last step for args: convert build-in types. If we're dealing with
10629      a new TYPE() type call, the first argument to the constructor
10630      isn't found in the incoming argument list, but delivered by
10631      `new' */
10632   t = TYPE_ARG_TYPES (TREE_TYPE (method));
10633   if (TREE_CODE (patch) == NEW_CLASS_EXPR)
10634     t = TREE_CHAIN (t);
10635   for (ta = args; t != end_params_node && ta; 
10636        t = TREE_CHAIN (t), ta = TREE_CHAIN (ta))
10637     if (JPRIMITIVE_TYPE_P (TREE_TYPE (TREE_VALUE (ta))) &&
10638         TREE_TYPE (TREE_VALUE (ta)) != TREE_VALUE (t))
10639       TREE_VALUE (ta) = convert (TREE_VALUE (t), TREE_VALUE (ta));
10640
10641   /* Resolve unresolved returned type isses */
10642   t = TREE_TYPE (TREE_TYPE (method));
10643   if (TREE_CODE (t) == POINTER_TYPE && !CLASS_LOADED_P (TREE_TYPE (t)))
10644     resolve_and_layout (TREE_TYPE (t), NULL);
10645
10646   if (flag_emit_class_files || flag_emit_xref)
10647     func = method;
10648   else
10649     {
10650       switch (invocation_mode (method, CALL_USING_SUPER (patch)))
10651         {
10652         case INVOKE_VIRTUAL:
10653           dtable = invoke_build_dtable (0, args);
10654           func = build_invokevirtual (dtable, method);
10655           break;
10656
10657         case INVOKE_NONVIRTUAL:
10658           /* If the object for the method call is null, we throw an
10659              exception.  We don't do this if the object is the current
10660              method's `this'.  In other cases we just rely on an
10661              optimization pass to eliminate redundant checks.  */
10662           if (TREE_VALUE (args) != current_this)
10663             {
10664               /* We use a save_expr here to make sure we only evaluate
10665                  the new `self' expression once.  */
10666               tree save_arg = save_expr (TREE_VALUE (args));
10667               TREE_VALUE (args) = save_arg;
10668               check = java_check_reference (save_arg, 1);
10669             }
10670           /* Fall through.  */
10671
10672         case INVOKE_SUPER:
10673         case INVOKE_STATIC:
10674           {
10675             tree signature = build_java_signature (TREE_TYPE (method));
10676             func = build_known_method_ref (method, TREE_TYPE (method),
10677                                            DECL_CONTEXT (method),
10678                                            signature, args);
10679           }
10680           break;
10681
10682         case INVOKE_INTERFACE:
10683           dtable = invoke_build_dtable (1, args);
10684           func = build_invokeinterface (dtable, method);
10685           break;
10686
10687         default:
10688           abort ();
10689         }
10690
10691       /* Ensure self_type is initialized, (invokestatic). FIXME */
10692       func = build1 (NOP_EXPR, build_pointer_type (TREE_TYPE (method)), func);
10693     }
10694
10695   TREE_TYPE (patch) = TREE_TYPE (TREE_TYPE (method));
10696   TREE_OPERAND (patch, 0) = func;
10697   TREE_OPERAND (patch, 1) = args;
10698   patch = check_for_builtin (method, patch);
10699   original_call = patch;
10700
10701   /* We're processing a `new TYPE ()' form. New is called and its
10702      returned value is the first argument to the constructor. We build
10703      a COMPOUND_EXPR and use saved expression so that the overall NEW
10704      expression value is a pointer to a newly created and initialized
10705      class. */
10706   if (TREE_CODE (original_call) == NEW_CLASS_EXPR)
10707     {
10708       tree class = DECL_CONTEXT (method);
10709       tree c1, saved_new, size, new;
10710       tree alloc_node;
10711
10712       if (flag_emit_class_files || flag_emit_xref)
10713         {
10714           TREE_TYPE (patch) = build_pointer_type (class);
10715           return patch;
10716         }
10717       if (!TYPE_SIZE (class))
10718         safe_layout_class (class);
10719       size = size_in_bytes (class);
10720       alloc_node =
10721         (class_has_finalize_method (class) ? alloc_object_node
10722                                            : alloc_no_finalizer_node);
10723       new = build (CALL_EXPR, promote_type (class),
10724                    build_address_of (alloc_node),
10725                    tree_cons (NULL_TREE, build_class_ref (class),
10726                               build_tree_list (NULL_TREE, 
10727                                                size_in_bytes (class))),
10728                    NULL_TREE);
10729       saved_new = save_expr (new);
10730       c1 = build_tree_list (NULL_TREE, saved_new);
10731       TREE_CHAIN (c1) = TREE_OPERAND (original_call, 1);
10732       TREE_OPERAND (original_call, 1) = c1;
10733       TREE_SET_CODE (original_call, CALL_EXPR);
10734       patch = build (COMPOUND_EXPR, TREE_TYPE (new), patch, saved_new);
10735     }
10736
10737   /* If CHECK is set, then we are building a check to see if the object
10738      is NULL.  */
10739   if (check != NULL_TREE)
10740     {
10741       patch = build (COMPOUND_EXPR, TREE_TYPE (patch), check, patch);
10742       TREE_SIDE_EFFECTS (patch) = 1;
10743     }
10744
10745   /* In order to be able to modify PATCH later, we SAVE_EXPR it and
10746      put it as the first expression of a COMPOUND_EXPR. The second
10747      expression being an empty statement to be later patched if
10748      necessary. We remember a TREE_LIST (the PURPOSE is the method,
10749      the VALUE is the compound) in a hashtable and return a
10750      COMPOUND_EXPR built so that the result of the evaluation of the
10751      original PATCH node is returned. */
10752   if (STATIC_CLASS_INIT_OPT_P ()
10753       && current_function_decl && METHOD_STATIC (method))
10754     {
10755       tree list;
10756       tree fndecl = current_function_decl;
10757       tree save = save_expr (patch);
10758       tree type = TREE_TYPE (patch);
10759
10760       patch = build (COMPOUND_EXPR, type, save, empty_stmt_node);
10761       list = tree_cons (method, patch,
10762                         DECL_FUNCTION_STATIC_METHOD_INVOCATION_COMPOUND (fndecl));
10763
10764       DECL_FUNCTION_STATIC_METHOD_INVOCATION_COMPOUND (fndecl) = list;
10765
10766       patch = build (COMPOUND_EXPR, type, patch, save);
10767     }
10768
10769   return patch;
10770 }
10771
10772 static int
10773 invocation_mode (method, super)
10774      tree method;
10775      int super;
10776 {
10777   int access = get_access_flags_from_decl (method);
10778
10779   if (super)
10780     return INVOKE_SUPER;
10781
10782   if (access & ACC_STATIC)
10783     return INVOKE_STATIC;
10784
10785   /* We have to look for a constructor before we handle nonvirtual
10786      calls; otherwise the constructor will look nonvirtual.  */
10787   if (DECL_CONSTRUCTOR_P (method))
10788     return INVOKE_STATIC;
10789
10790   if (access & ACC_FINAL || access & ACC_PRIVATE)
10791     return INVOKE_NONVIRTUAL;
10792
10793   if (CLASS_FINAL (TYPE_NAME (DECL_CONTEXT (method))))
10794     return INVOKE_NONVIRTUAL;
10795
10796   if (CLASS_INTERFACE (TYPE_NAME (DECL_CONTEXT (method))))
10797     return INVOKE_INTERFACE;
10798
10799   return INVOKE_VIRTUAL;
10800 }
10801
10802 /* Retrieve a refined list of matching methods. It covers the step
10803    15.11.2 (Compile-Time Step 2) */
10804
10805 static tree
10806 lookup_method_invoke (lc, cl, class, name, arg_list)
10807      int lc;
10808      tree cl;
10809      tree class, name, arg_list;
10810 {
10811   tree atl = end_params_node;           /* Arg Type List */
10812   tree method, signature, list, node;
10813   const char *candidates;               /* Used for error report */
10814   char *dup;
10815
10816   /* Fix the arguments */
10817   for (node = arg_list; node; node = TREE_CHAIN (node))
10818     {
10819       tree current_arg = TREE_TYPE (TREE_VALUE (node));
10820       /* Non primitive type may have to be resolved */
10821       if (!JPRIMITIVE_TYPE_P (current_arg))
10822         resolve_and_layout (current_arg, NULL_TREE);
10823       /* And promoted */
10824       if (TREE_CODE (current_arg) == RECORD_TYPE)
10825         current_arg = promote_type (current_arg);
10826       atl = tree_cons (NULL_TREE, current_arg, atl);
10827     }
10828
10829   /* Presto. If we're dealing with an anonymous class and a
10830      constructor call, generate the right constructor now, since we
10831      know the arguments' types. */
10832
10833   if (lc && ANONYMOUS_CLASS_P (class))
10834     craft_constructor (TYPE_NAME (class), atl);
10835
10836   /* Find all candidates and then refine the list, searching for the
10837      most specific method. */
10838   list = find_applicable_accessible_methods_list (lc, class, name, atl);
10839   list = find_most_specific_methods_list (list);
10840   if (list && !TREE_CHAIN (list))
10841     return TREE_VALUE (list);
10842
10843   /* Issue an error. List candidates if any. Candidates are listed
10844      only if accessible (non accessible methods may end-up here for
10845      the sake of a better error report). */
10846   candidates = NULL;
10847   if (list)
10848     {
10849       tree current;
10850       obstack_grow (&temporary_obstack, ". Candidates are:\n", 18);
10851       for (current = list; current; current = TREE_CHAIN (current))
10852         {
10853           tree cm = TREE_VALUE (current);
10854           char string [4096];
10855           if (!cm || not_accessible_p (class, cm, NULL_TREE, 0))
10856             continue;
10857           sprintf 
10858             (string, "  `%s' in `%s'%s",
10859              get_printable_method_name (cm),
10860              IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (DECL_CONTEXT (cm)))),
10861              (TREE_CHAIN (current) ? "\n" : ""));
10862           obstack_grow (&temporary_obstack, string, strlen (string));
10863         }
10864       obstack_1grow (&temporary_obstack, '\0');
10865       candidates = obstack_finish (&temporary_obstack);
10866     }
10867   /* Issue the error message */
10868   method = make_node (FUNCTION_TYPE);
10869   TYPE_ARG_TYPES (method) = atl;
10870   signature = build_java_argument_signature (method);
10871   dup = xstrdup (lang_printable_name (class, 0));
10872   parse_error_context (cl, "Can't find %s `%s(%s)' in type `%s'%s",
10873                        (lc ? "constructor" : "method"),
10874                        (lc ? dup : IDENTIFIER_POINTER (name)),
10875                        IDENTIFIER_POINTER (signature), dup,
10876                        (candidates ? candidates : ""));
10877   free (dup);
10878   return NULL_TREE;
10879 }
10880
10881 /* 15.11.2.1: Find Methods that are Applicable and Accessible. LC is 1
10882    when we're looking for a constructor. */
10883
10884 static tree
10885 find_applicable_accessible_methods_list (lc, class, name, arglist)
10886      int lc;
10887      tree class, name, arglist;
10888 {
10889   static struct hash_table t, *searched_classes = NULL;
10890   static int search_not_done = 0;
10891   tree list = NULL_TREE, all_list = NULL_TREE;
10892
10893   /* Check the hash table to determine if this class has been searched 
10894      already. */
10895   if (searched_classes)
10896     {
10897       if (hash_lookup (searched_classes, 
10898                       (const hash_table_key) class, FALSE, NULL))
10899        return NULL;
10900     }
10901   else
10902     {
10903       hash_table_init (&t, hash_newfunc, java_hash_hash_tree_node,
10904                       java_hash_compare_tree_node);
10905       searched_classes = &t;
10906     }
10907     
10908   search_not_done++;
10909   hash_lookup (searched_classes, 
10910                (const hash_table_key) class, TRUE, NULL);
10911
10912   if (!CLASS_LOADED_P (class) && !CLASS_FROM_SOURCE_P (class))
10913     {
10914       load_class (class, 1);
10915       safe_layout_class (class);
10916     }
10917
10918   /* Search interfaces */
10919   if (TREE_CODE (TYPE_NAME (class)) == TYPE_DECL 
10920       && CLASS_INTERFACE (TYPE_NAME (class)))
10921     {
10922       int i, n;
10923       tree basetype_vec = TYPE_BINFO_BASETYPES (class);
10924       search_applicable_methods_list (lc, TYPE_METHODS (class), 
10925                                       name, arglist, &list, &all_list);
10926       n = TREE_VEC_LENGTH (basetype_vec);
10927       for (i = 1; i < n; i++)
10928         {
10929           tree t = BINFO_TYPE (TREE_VEC_ELT (basetype_vec, i));
10930           tree rlist;
10931
10932           rlist = find_applicable_accessible_methods_list (lc,  t, name, 
10933                                                            arglist);
10934           list = chainon (rlist, list);
10935         }
10936     }
10937   /* Search classes */
10938   else
10939     {
10940       search_applicable_methods_list (lc, TYPE_METHODS (class), 
10941                                       name, arglist, &list, &all_list);
10942
10943       /* When looking finit$, class$ or instinit$, we turn LC to 1 so
10944          that we only search in class. Note that we should have found
10945          something at this point. */
10946       if (ID_FINIT_P (name) || ID_CLASSDOLLAR_P (name) || ID_INSTINIT_P (name))
10947         {
10948           lc = 1;
10949           if (!list)
10950             abort ();
10951         }
10952
10953       /* We must search all interfaces of this class */
10954       if (!lc)
10955       {
10956         tree basetype_vec = TYPE_BINFO_BASETYPES (class);
10957         int n = TREE_VEC_LENGTH (basetype_vec), i;
10958         for (i = 1; i < n; i++)
10959           {
10960             tree t = BINFO_TYPE (TREE_VEC_ELT (basetype_vec, i));
10961             if (t != object_type_node)
10962               {
10963                 tree rlist
10964                   = find_applicable_accessible_methods_list (lc, t,
10965                                                              name, arglist);
10966                 list = chainon (rlist, list);
10967               }
10968           }
10969       }
10970
10971       /* Search superclass */
10972       if (!lc && CLASSTYPE_SUPER (class) != NULL_TREE)
10973         {
10974           tree rlist;
10975           class = CLASSTYPE_SUPER (class);
10976           rlist = find_applicable_accessible_methods_list (lc, class, 
10977                                                            name, arglist);
10978           list = chainon (rlist, list);
10979         }
10980     }
10981
10982   search_not_done--;
10983
10984   /* We're done. Reset the searched classes list and finally search
10985      java.lang.Object if it wasn't searched already. */
10986   if (!search_not_done)
10987     {
10988       if (!lc
10989           && TYPE_METHODS (object_type_node)
10990           && !hash_lookup (searched_classes, 
10991                            (const hash_table_key) object_type_node, 
10992                            FALSE, NULL))
10993         {
10994           search_applicable_methods_list (lc, 
10995                                           TYPE_METHODS (object_type_node),
10996                                           name, arglist, &list, &all_list);
10997         }
10998       hash_table_free (searched_classes);
10999       searched_classes = NULL;
11000     }
11001
11002   /* Either return the list obtained or all selected (but
11003      inaccessible) methods for better error report. */
11004   return (!list ? all_list : list);
11005 }
11006
11007 /* Effectively search for the appropriate method in method */
11008
11009 static void 
11010 search_applicable_methods_list (lc, method, name, arglist, list, all_list)
11011      int lc;
11012      tree method, name, arglist;
11013      tree *list, *all_list;
11014 {
11015   for (; method; method = TREE_CHAIN (method))
11016     {
11017       /* When dealing with constructor, stop here, otherwise search
11018          other classes */
11019       if (lc && !DECL_CONSTRUCTOR_P (method))
11020         continue;
11021       else if (!lc && (DECL_CONSTRUCTOR_P (method) 
11022                        || (DECL_NAME (method) != name)))
11023         continue;
11024
11025       if (argument_types_convertible (method, arglist))
11026         {
11027           /* Retain accessible methods only */
11028           if (!not_accessible_p (DECL_CONTEXT (current_function_decl), 
11029                                  method, NULL_TREE, 0))
11030             *list = tree_cons (NULL_TREE, method, *list);
11031           else
11032             /* Also retain all selected method here */
11033             *all_list = tree_cons (NULL_TREE, method, *list);
11034         }
11035     }
11036 }
11037
11038 /* 15.11.2.2 Choose the Most Specific Method */
11039
11040 static tree
11041 find_most_specific_methods_list (list)
11042      tree list;
11043 {
11044   int max = 0;
11045   int abstract, candidates;
11046   tree current, new_list = NULL_TREE;
11047   for (current = list; current; current = TREE_CHAIN (current))
11048     {
11049       tree method;
11050       DECL_SPECIFIC_COUNT (TREE_VALUE (current)) = 0;
11051
11052       for (method = list; method; method = TREE_CHAIN (method))
11053         {
11054           tree method_v, current_v;
11055           /* Don't test a method against itself */
11056           if (method == current)
11057             continue;
11058
11059           method_v = TREE_VALUE (method);
11060           current_v = TREE_VALUE (current);
11061
11062           /* Compare arguments and location where methods where declared */
11063           if (argument_types_convertible (method_v, current_v))
11064             {
11065               if (valid_method_invocation_conversion_p 
11066                   (DECL_CONTEXT (method_v), DECL_CONTEXT (current_v))
11067                   || (INNER_CLASS_TYPE_P (DECL_CONTEXT (current_v))
11068                       && enclosing_context_p (DECL_CONTEXT (method_v),
11069                                               DECL_CONTEXT (current_v))))
11070                 {
11071                   int v = (DECL_SPECIFIC_COUNT (current_v) += 
11072                     (INNER_CLASS_TYPE_P (DECL_CONTEXT (current_v)) ? 2 : 1));
11073                   max = (v > max ? v : max);
11074                 }
11075             }
11076         }
11077     }
11078
11079   /* Review the list and select the maximally specific methods */
11080   for (current = list, abstract = -1, candidates = -1;
11081        current; current = TREE_CHAIN (current))
11082     if (DECL_SPECIFIC_COUNT (TREE_VALUE (current)) == max)
11083       {
11084         new_list = tree_cons (NULL_TREE, TREE_VALUE (current), new_list);
11085         abstract += (METHOD_ABSTRACT (TREE_VALUE (current)) ? 1 : 0);
11086         candidates++;
11087       }
11088
11089   /* If we have several and they're all abstract, just pick the
11090      closest one. */
11091   if (candidates > 0 && (candidates == abstract))
11092     {
11093       new_list = nreverse (new_list);
11094       TREE_CHAIN (new_list) = NULL_TREE;
11095     }
11096
11097   /* We have several (we couldn't find a most specific), all but one
11098      are abstract, we pick the only non abstract one. */
11099   if (candidates > 0 && (candidates == abstract+1))
11100     {
11101       for (current = new_list; current; current = TREE_CHAIN (current))
11102         if (!METHOD_ABSTRACT (TREE_VALUE (current)))
11103           {
11104             TREE_CHAIN (current) = NULL_TREE;
11105             new_list = current;
11106           }
11107     }
11108
11109   /* If we can't find one, lower expectations and try to gather multiple
11110      maximally specific methods */
11111   while (!new_list && max)
11112     {
11113       while (--max > 0)
11114         {
11115           if (DECL_SPECIFIC_COUNT (TREE_VALUE (current)) == max)
11116             new_list = tree_cons (NULL_TREE, TREE_VALUE (current), new_list);
11117         }
11118     }
11119
11120   return new_list;
11121 }
11122
11123 /* Make sure that the type of each M2_OR_ARGLIST arguments can be
11124    converted by method invocation conversion (5.3) to the type of the
11125    corresponding parameter of M1. Implementation expects M2_OR_ARGLIST
11126    to change less often than M1. */
11127
11128 static int
11129 argument_types_convertible (m1, m2_or_arglist)
11130     tree m1, m2_or_arglist;
11131 {
11132   static tree m2_arg_value = NULL_TREE;
11133   static tree m2_arg_cache = NULL_TREE;
11134   static int initialized_p;
11135
11136   register tree m1_arg, m2_arg;
11137
11138   /* Register M2_ARG_VALUE and M2_ARG_CACHE with the garbage
11139      collector.  */
11140   if (!initialized_p)
11141     {
11142       ggc_add_tree_root (&m2_arg_value, 1);
11143       ggc_add_tree_root (&m2_arg_cache, 1);
11144       initialized_p = 1;
11145     }
11146
11147   SKIP_THIS_AND_ARTIFICIAL_PARMS (m1_arg, m1)
11148
11149   if (m2_arg_value == m2_or_arglist)
11150     m2_arg = m2_arg_cache;
11151   else
11152     {
11153       /* M2_OR_ARGLIST can be a function DECL or a raw list of
11154          argument types */
11155       if (m2_or_arglist && TREE_CODE (m2_or_arglist) == FUNCTION_DECL)
11156         {
11157           m2_arg = TYPE_ARG_TYPES (TREE_TYPE (m2_or_arglist));
11158           if (!METHOD_STATIC (m2_or_arglist))
11159             m2_arg = TREE_CHAIN (m2_arg);
11160         }
11161       else
11162         m2_arg = m2_or_arglist;
11163
11164       m2_arg_value = m2_or_arglist;
11165       m2_arg_cache = m2_arg;
11166     }
11167
11168   while (m1_arg != end_params_node && m2_arg != end_params_node)
11169     {
11170       resolve_and_layout (TREE_VALUE (m1_arg), NULL_TREE);
11171       if (!valid_method_invocation_conversion_p (TREE_VALUE (m1_arg),
11172                                                  TREE_VALUE (m2_arg)))
11173         break;
11174       m1_arg = TREE_CHAIN (m1_arg);
11175       m2_arg = TREE_CHAIN (m2_arg);
11176     }
11177   return m1_arg == end_params_node && m2_arg == end_params_node;
11178 }
11179
11180 /* Qualification routines */
11181
11182 static void
11183 qualify_ambiguous_name (id)
11184      tree id;
11185 {
11186   tree qual, qual_wfl, name = NULL_TREE, decl, ptr_type = NULL_TREE,
11187     saved_current_class;
11188   int again, super_found = 0, this_found = 0, new_array_found = 0;
11189   int code;
11190
11191   /* We first qualify the first element, then derive qualification of
11192      others based on the first one. If the first element is qualified
11193      by a resolution (field or type), this resolution is stored in the
11194      QUAL_RESOLUTION of the qual element being examined. We need to
11195      save the current_class since the use of SUPER might change the
11196      its value. */
11197   saved_current_class = current_class;
11198   qual = EXPR_WFL_QUALIFICATION (id);
11199   do {
11200
11201     /* Simple qualified expression feature a qual_wfl that is a
11202        WFL. Expression derived from a primary feature more complicated
11203        things like a CALL_EXPR. Expression from primary need to be
11204        worked out to extract the part on which the qualification will
11205        take place. */
11206     qual_wfl = QUAL_WFL (qual);
11207     switch (TREE_CODE (qual_wfl))
11208       {
11209       case CALL_EXPR:
11210         qual_wfl = TREE_OPERAND (qual_wfl, 0);
11211         if (TREE_CODE (qual_wfl) != EXPR_WITH_FILE_LOCATION)
11212           {
11213             qual = EXPR_WFL_QUALIFICATION (qual_wfl);
11214             qual_wfl = QUAL_WFL (qual);
11215           }
11216         break;
11217       case NEW_ARRAY_EXPR:
11218       case NEW_ANONYMOUS_ARRAY_EXPR:
11219         qual = TREE_CHAIN (qual);
11220         again = new_array_found = 1;
11221         continue;
11222       case CONVERT_EXPR:
11223         break;
11224       case NEW_CLASS_EXPR:
11225         qual_wfl = TREE_OPERAND (qual_wfl, 0);
11226         break;
11227       case ARRAY_REF:
11228         while (TREE_CODE (qual_wfl) == ARRAY_REF)
11229           qual_wfl = TREE_OPERAND (qual_wfl, 0);
11230         break;
11231       case STRING_CST:
11232         qual = TREE_CHAIN (qual);
11233         qual_wfl = QUAL_WFL (qual);
11234         break;
11235       case CLASS_LITERAL:
11236         qual = TREE_CHAIN (qual);
11237         qual_wfl = QUAL_WFL (qual);
11238       break;
11239       default:
11240         /* Fix for -Wall. Just break doing nothing */
11241         break;
11242       }
11243
11244     ptr_type = current_class;
11245     again = 0;
11246     code = TREE_CODE (qual_wfl);
11247
11248     /* Pos evaluation: non WFL leading expression nodes */
11249     if (code == CONVERT_EXPR
11250         && TREE_CODE (TREE_TYPE (qual_wfl)) == EXPR_WITH_FILE_LOCATION)
11251       name = EXPR_WFL_NODE (TREE_TYPE (qual_wfl));
11252
11253     else if (code == INTEGER_CST)
11254       name = qual_wfl;
11255     
11256     else if (code == CONVERT_EXPR &&
11257              TREE_CODE (TREE_OPERAND (qual_wfl, 0)) == EXPR_WITH_FILE_LOCATION)
11258       name = TREE_OPERAND (qual_wfl, 0);
11259     
11260     else if ((code == ARRAY_REF || code == CALL_EXPR || code == MODIFY_EXPR) &&
11261              TREE_CODE (TREE_OPERAND (qual_wfl, 0)) == EXPR_WITH_FILE_LOCATION)
11262       name = EXPR_WFL_NODE (TREE_OPERAND (qual_wfl, 0));
11263
11264     else if (code == TREE_LIST)
11265       name = EXPR_WFL_NODE (TREE_PURPOSE (qual_wfl));
11266
11267     else if (code == STRING_CST || code == CONDITIONAL_EXPR 
11268              || code == PLUS_EXPR)
11269       {
11270         qual = TREE_CHAIN (qual);
11271         qual_wfl = QUAL_WFL (qual);
11272         again = 1;
11273       }
11274     else
11275       {
11276         name = EXPR_WFL_NODE (qual_wfl);
11277         if (!name)
11278           {
11279             qual = EXPR_WFL_QUALIFICATION (qual_wfl);
11280             again = 1;
11281           }
11282       }
11283
11284     /* If we have a THIS (from a primary), we set the context accordingly */
11285     if (name == this_identifier_node)
11286       {
11287         /* This isn't really elegant. One more added irregularity
11288            before I start using COMPONENT_REF (hopefully very soon.)  */
11289         if (TREE_CODE (TREE_PURPOSE (qual)) == ARRAY_REF
11290             && TREE_CODE (TREE_OPERAND (TREE_PURPOSE (qual), 0)) ==
11291                EXPR_WITH_FILE_LOCATION
11292             && EXPR_WFL_NODE (TREE_OPERAND (TREE_PURPOSE (qual), 0)) == 
11293                this_identifier_node)
11294             {
11295               qual = TREE_OPERAND (TREE_PURPOSE (qual), 0);
11296               qual = EXPR_WFL_QUALIFICATION (qual);
11297             }
11298         qual = TREE_CHAIN (qual);
11299         qual_wfl = QUAL_WFL (qual);
11300         if (TREE_CODE (qual_wfl) == CALL_EXPR)
11301           again = 1;
11302         else if (TREE_CODE (qual_wfl) == EXPR_WITH_FILE_LOCATION)
11303           name = EXPR_WFL_NODE (qual_wfl);
11304         else if (TREE_CODE (qual_wfl) == NEW_CLASS_EXPR)
11305           name = TREE_OPERAND (qual_wfl, 0);
11306         this_found = 1;
11307       }
11308     /* If we have a SUPER, we set the context accordingly */
11309     if (name == super_identifier_node)
11310       {
11311         current_class = CLASSTYPE_SUPER (ptr_type);
11312         /* Check that there is such a thing as a super class. If not,
11313            return.  The error will be caught later on, during the
11314            resolution */
11315         if (!current_class)
11316           {
11317             current_class = saved_current_class;
11318             return;
11319           }
11320         qual = TREE_CHAIN (qual);
11321         /* Do one more interation to set things up */
11322         super_found = again = 1;
11323       }
11324   } while (again);
11325   
11326   /* If name appears within the scope of a local variable declaration
11327      or parameter declaration, then it is an expression name. We don't
11328      carry this test out if we're in the context of the use of SUPER
11329      or THIS */
11330   if (!this_found && !super_found 
11331       && TREE_CODE (name) != STRING_CST && TREE_CODE (name) != INTEGER_CST
11332       && (decl = IDENTIFIER_LOCAL_VALUE (name)))
11333     {
11334       RESOLVE_EXPRESSION_NAME_P (qual_wfl) = 1;
11335       QUAL_RESOLUTION (qual) = decl;
11336     }
11337
11338   /* If within the class/interface NAME was found to be used there
11339      exists a (possibly inherited) field named NAME, then this is an
11340      expression name. If we saw a NEW_ARRAY_EXPR before and want to
11341      address length, it is OK. */
11342   else if ((decl = lookup_field_wrapper (ptr_type, name))
11343            || name == length_identifier_node)
11344     {
11345       RESOLVE_EXPRESSION_NAME_P (qual_wfl) = 1;
11346       QUAL_RESOLUTION (qual) = (new_array_found ? NULL_TREE : decl);
11347     }
11348
11349   /* We reclassify NAME as yielding to a type name resolution if:
11350      - NAME is a class/interface declared within the compilation
11351        unit containing NAME,
11352      - NAME is imported via a single-type-import declaration,
11353      - NAME is declared in an another compilation unit of the package
11354        of the compilation unit containing NAME,
11355      - NAME is declared by exactly on type-import-on-demand declaration
11356      of the compilation unit containing NAME. 
11357      - NAME is actually a STRING_CST.
11358      This can't happen if the expression was qualified by `this.' */
11359   else if (! this_found &&
11360            (TREE_CODE (name) == STRING_CST ||
11361             TREE_CODE (name) == INTEGER_CST ||
11362             (decl = resolve_and_layout (name, NULL_TREE))))
11363     {
11364       RESOLVE_TYPE_NAME_P (qual_wfl) = 1;
11365       QUAL_RESOLUTION (qual) = decl;
11366     }
11367
11368   /* Method call, array references and cast are expression name */
11369   else if (TREE_CODE (QUAL_WFL (qual)) == CALL_EXPR
11370            || TREE_CODE (QUAL_WFL (qual)) == ARRAY_REF
11371            || TREE_CODE (QUAL_WFL (qual)) == CONVERT_EXPR
11372            || TREE_CODE (QUAL_WFL (qual)) == MODIFY_EXPR)
11373     RESOLVE_EXPRESSION_NAME_P (qual_wfl) = 1;
11374
11375   /* Check here that NAME isn't declared by more than one
11376      type-import-on-demand declaration of the compilation unit
11377      containing NAME. FIXME */
11378
11379   /* Otherwise, NAME is reclassified as a package name */
11380   else 
11381     RESOLVE_PACKAGE_NAME_P (qual_wfl) = 1;
11382
11383   /* Propagate the qualification accross other components of the
11384      qualified name */
11385   for (qual = TREE_CHAIN (qual); qual;
11386        qual_wfl = QUAL_WFL (qual), qual = TREE_CHAIN (qual))
11387     {
11388       if (RESOLVE_PACKAGE_NAME_P (qual_wfl))
11389         RESOLVE_PACKAGE_NAME_P (QUAL_WFL (qual)) = 1;
11390       else 
11391         RESOLVE_EXPRESSION_NAME_P (QUAL_WFL (qual)) = 1;
11392     }
11393
11394   /* Store the global qualification for the ambiguous part of ID back
11395      into ID fields */
11396   if (RESOLVE_EXPRESSION_NAME_P (qual_wfl))
11397     RESOLVE_EXPRESSION_NAME_P (id) = 1;
11398   else if (RESOLVE_TYPE_NAME_P (qual_wfl))
11399     RESOLVE_TYPE_NAME_P (id) = 1;
11400   else if (RESOLVE_PACKAGE_NAME_P (qual_wfl))
11401     RESOLVE_PACKAGE_NAME_P (id) = 1;
11402
11403   /* Restore the current class */
11404   current_class = saved_current_class;
11405 }
11406
11407 static int
11408 breakdown_qualified (left, right, source)
11409     tree *left, *right, source;
11410 {
11411   char *p, *base;
11412   int   l = IDENTIFIER_LENGTH (source);
11413
11414   base = alloca (l + 1);
11415   memcpy (base, IDENTIFIER_POINTER (source), l + 1);
11416
11417   /* Breakdown NAME into REMAINDER . IDENTIFIER */
11418   p = base + l - 1;
11419   while (*p != '.' && p != base)
11420     p--;
11421
11422   /* We didn't find a '.'. Return an error */
11423   if (p == base)
11424     return 1;
11425
11426   *p = '\0';
11427   if (right)
11428     *right = get_identifier (p+1);
11429   *left = get_identifier (base);
11430   
11431   return 0;
11432 }
11433
11434 /* Return TRUE if two classes are from the same package. */
11435
11436 static int
11437 in_same_package (name1, name2)
11438   tree name1, name2;
11439 {
11440   tree tmp;
11441   tree pkg1;
11442   tree pkg2;
11443   
11444   if (TREE_CODE (name1) == TYPE_DECL)
11445     name1 = DECL_NAME (name1);
11446   if (TREE_CODE (name2) == TYPE_DECL)
11447     name2 = DECL_NAME (name2);
11448
11449   if (QUALIFIED_P (name1) != QUALIFIED_P (name2))
11450     /* One in empty package. */
11451     return 0;
11452
11453   if (QUALIFIED_P (name1) == 0 && QUALIFIED_P (name2) == 0)
11454     /* Both in empty package. */
11455     return 1;
11456
11457   breakdown_qualified (&pkg1, &tmp, name1);
11458   breakdown_qualified (&pkg2, &tmp, name2);
11459   
11460   return (pkg1 == pkg2);
11461 }
11462
11463 /* Patch tree nodes in a function body. When a BLOCK is found, push
11464    local variable decls if present.
11465    Same as java_complete_lhs, but does resolve static finals to values. */
11466
11467 static tree
11468 java_complete_tree (node)
11469      tree node;
11470 {
11471   node = java_complete_lhs (node);
11472   if (JDECL_P (node) && CLASS_FINAL_VARIABLE_P (node)
11473       && DECL_INITIAL (node) != NULL_TREE
11474       && !flag_emit_xref)
11475     {
11476       tree value = DECL_INITIAL (node);
11477       DECL_INITIAL (node) = NULL_TREE;
11478       value = fold_constant_for_init (value, node);
11479       DECL_INITIAL (node) = value;
11480       if (value != NULL_TREE)
11481         {
11482           /* fold_constant_for_init sometimes widens the original type
11483              of the constant (i.e. byte to int). It's not desirable,
11484              especially if NODE is a function argument. */
11485           if ((TREE_CODE (value) == INTEGER_CST
11486                || TREE_CODE (value) == REAL_CST)
11487               && TREE_TYPE (node) != TREE_TYPE (value))
11488             return convert (TREE_TYPE (node), value);
11489           else
11490             return value;
11491         }
11492     }
11493   return node;
11494 }
11495
11496 static tree
11497 java_stabilize_reference (node)
11498      tree node;
11499 {
11500   if (TREE_CODE (node) == COMPOUND_EXPR)
11501     {
11502       tree op0 = TREE_OPERAND (node, 0);
11503       tree op1 = TREE_OPERAND (node, 1);
11504       TREE_OPERAND (node, 0) = save_expr (op0);
11505       TREE_OPERAND (node, 1) = java_stabilize_reference (op1);
11506       return node;
11507     }
11508   return stabilize_reference (node);
11509 }
11510
11511 /* Patch tree nodes in a function body. When a BLOCK is found, push
11512    local variable decls if present.
11513    Same as java_complete_tree, but does not resolve static finals to values. */
11514
11515 static tree
11516 java_complete_lhs (node)
11517      tree node;
11518 {
11519   tree nn, cn, wfl_op1, wfl_op2, wfl_op3;
11520   int flag;
11521
11522   /* CONVERT_EXPR always has its type set, even though it needs to be
11523      worked out. */
11524   if (TREE_TYPE (node) && TREE_CODE (node) != CONVERT_EXPR)
11525     return node;
11526
11527   /* The switch block implements cases processing container nodes
11528      first.  Contained nodes are always written back. Leaves come
11529      next and return a value. */
11530   switch (TREE_CODE (node))
11531     {
11532     case BLOCK:
11533
11534       /* 1- Block section.
11535          Set the local values on decl names so we can identify them
11536          faster when they're referenced. At that stage, identifiers
11537          are legal so we don't check for declaration errors. */
11538       for (cn = BLOCK_EXPR_DECLS (node); cn; cn = TREE_CHAIN (cn))
11539         {
11540           DECL_CONTEXT (cn) = current_function_decl;
11541           IDENTIFIER_LOCAL_VALUE (DECL_NAME (cn)) = cn;
11542         }
11543       if (BLOCK_EXPR_BODY (node) == NULL_TREE)
11544           CAN_COMPLETE_NORMALLY (node) = 1;
11545       else
11546         {
11547           tree stmt = BLOCK_EXPR_BODY (node);
11548           tree *ptr;
11549           int error_seen = 0;
11550           if (TREE_CODE (stmt) == COMPOUND_EXPR)
11551             {
11552               /* Re-order from (((A; B); C); ...; Z) to 
11553                  (A; (B; (C ; (...; Z)))).
11554                  This makes it easier to scan the statements left-to-right
11555                  without using recursion (which might overflow the stack
11556                  if the block has many statements. */
11557               for (;;)
11558                 {
11559                   tree left = TREE_OPERAND (stmt, 0);
11560                   if (TREE_CODE (left) != COMPOUND_EXPR)
11561                     break;
11562                   TREE_OPERAND (stmt, 0) = TREE_OPERAND (left, 1);
11563                   TREE_OPERAND (left, 1) = stmt;
11564                   stmt = left;
11565                 }
11566               BLOCK_EXPR_BODY (node) = stmt;
11567             }
11568
11569           /* Now do the actual complete, without deep recursion for
11570              long blocks. */
11571           ptr = &BLOCK_EXPR_BODY (node);
11572           while (TREE_CODE (*ptr) == COMPOUND_EXPR
11573                  && TREE_OPERAND (*ptr, 1) != empty_stmt_node)
11574             {
11575               tree cur = java_complete_tree (TREE_OPERAND (*ptr, 0));
11576               tree *next = &TREE_OPERAND (*ptr, 1);
11577               TREE_OPERAND (*ptr, 0) = cur;
11578               if (cur == empty_stmt_node)
11579                 {
11580                   /* Optimization;  makes it easier to detect empty bodies.
11581                      Most useful for <clinit> with all-constant initializer. */
11582                   *ptr = *next;
11583                   continue;
11584                 }
11585               if (TREE_CODE (cur) == ERROR_MARK)
11586                 error_seen++;
11587               else if (! CAN_COMPLETE_NORMALLY (cur))
11588                 {
11589                   wfl_op2 = *next;
11590                   for (;;)
11591                     {
11592                       if (TREE_CODE (wfl_op2) == BLOCK)
11593                         wfl_op2 = BLOCK_EXPR_BODY (wfl_op2);
11594                       else if (TREE_CODE (wfl_op2) == COMPOUND_EXPR)
11595                         wfl_op2 = TREE_OPERAND (wfl_op2, 0);
11596                       else
11597                         break;
11598                     }
11599                   if (TREE_CODE (wfl_op2) != CASE_EXPR
11600                       && TREE_CODE (wfl_op2) != DEFAULT_EXPR)
11601                     unreachable_stmt_error (*ptr);
11602                 }
11603               ptr = next;
11604             }
11605           *ptr = java_complete_tree (*ptr);
11606
11607           if (TREE_CODE (*ptr) == ERROR_MARK || error_seen > 0)
11608             return error_mark_node;
11609           CAN_COMPLETE_NORMALLY (node) = CAN_COMPLETE_NORMALLY (*ptr);
11610         }
11611       /* Turn local bindings to null */
11612       for (cn = BLOCK_EXPR_DECLS (node); cn; cn = TREE_CHAIN (cn))
11613         IDENTIFIER_LOCAL_VALUE (DECL_NAME (cn)) = NULL_TREE;
11614
11615       TREE_TYPE (node) = void_type_node;
11616       break;
11617
11618       /* 2- They are expressions but ultimately deal with statements */
11619
11620     case THROW_EXPR:
11621       wfl_op1 = TREE_OPERAND (node, 0);
11622       COMPLETE_CHECK_OP_0 (node);
11623       /* 14.19 A throw statement cannot complete normally. */
11624       CAN_COMPLETE_NORMALLY (node) = 0;
11625       return patch_throw_statement (node, wfl_op1);
11626
11627     case SYNCHRONIZED_EXPR:
11628       wfl_op1 = TREE_OPERAND (node, 0);
11629       return patch_synchronized_statement (node, wfl_op1);
11630
11631     case TRY_EXPR:
11632       return patch_try_statement (node);
11633
11634     case TRY_FINALLY_EXPR:
11635       COMPLETE_CHECK_OP_0 (node);
11636       COMPLETE_CHECK_OP_1 (node);
11637       if (TREE_OPERAND (node, 0) == empty_stmt_node)
11638         return TREE_OPERAND (node, 1);
11639       if (TREE_OPERAND (node, 1) == empty_stmt_node)
11640         return TREE_OPERAND (node, 0);
11641       CAN_COMPLETE_NORMALLY (node)
11642         = (CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 0))
11643            && CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 1)));
11644       TREE_TYPE (node) = TREE_TYPE (TREE_OPERAND (node, 0));
11645       return node;
11646
11647     case LABELED_BLOCK_EXPR:
11648       PUSH_LABELED_BLOCK (node);
11649       if (LABELED_BLOCK_BODY (node))
11650         COMPLETE_CHECK_OP_1 (node);
11651       TREE_TYPE (node) = void_type_node;
11652       POP_LABELED_BLOCK ();
11653
11654       if (LABELED_BLOCK_BODY (node) == empty_stmt_node)
11655         {
11656           LABELED_BLOCK_BODY (node) = NULL_TREE;
11657           CAN_COMPLETE_NORMALLY (node) = 1;
11658         }
11659       else if (CAN_COMPLETE_NORMALLY (LABELED_BLOCK_BODY (node)))
11660         CAN_COMPLETE_NORMALLY (node) = 1;
11661       return node;
11662
11663     case EXIT_BLOCK_EXPR:
11664       /* We don't complete operand 1, because it's the return value of
11665          the EXIT_BLOCK_EXPR which doesn't exist it Java */
11666       return patch_bc_statement (node);
11667
11668     case CASE_EXPR:
11669       cn = java_complete_tree (TREE_OPERAND (node, 0));
11670       if (cn == error_mark_node)
11671         return cn;
11672
11673       /* First, the case expression must be constant. Values of final
11674          fields are accepted. */
11675       cn = fold (cn);
11676       if ((TREE_CODE (cn) == COMPOUND_EXPR || TREE_CODE (cn) == COMPONENT_REF)
11677           && JDECL_P (TREE_OPERAND (cn, 1))
11678           && FIELD_FINAL (TREE_OPERAND (cn, 1))
11679           && DECL_INITIAL (TREE_OPERAND (cn, 1)))
11680         {
11681           cn = fold_constant_for_init (DECL_INITIAL (TREE_OPERAND (cn, 1)),
11682                                        TREE_OPERAND (cn, 1));
11683         }
11684       /* Accept final locals too. */
11685       else if (TREE_CODE (cn) == VAR_DECL && DECL_FINAL (cn))
11686         cn = fold_constant_for_init (DECL_INITIAL (cn), cn);
11687
11688       if (!TREE_CONSTANT (cn) && !flag_emit_xref)
11689         {
11690           EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
11691           parse_error_context (node, "Constant expression required");
11692           return error_mark_node;
11693         }
11694
11695       nn = ctxp->current_loop;
11696
11697       /* It must be assignable to the type of the switch expression. */
11698       if (!try_builtin_assignconv (NULL_TREE, 
11699                                    TREE_TYPE (TREE_OPERAND (nn, 0)), cn))
11700         {
11701           EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
11702           parse_error_context 
11703             (wfl_operator,
11704              "Incompatible type for case. Can't convert `%s' to `int'",
11705              lang_printable_name (TREE_TYPE (cn), 0));
11706           return error_mark_node;
11707         }
11708
11709       cn = fold (convert (int_type_node, cn));
11710       TREE_CONSTANT_OVERFLOW (cn) = 0;
11711       CAN_COMPLETE_NORMALLY (cn) = 1;
11712
11713       /* Save the label on a list so that we can later check for
11714          duplicates.  */
11715       case_label_list = tree_cons (node, cn, case_label_list);
11716
11717       /* Multiple instance of a case label bearing the same value is
11718          checked later. The case expression is all right so far. */
11719       if (TREE_CODE (cn) == VAR_DECL)
11720         cn = DECL_INITIAL (cn);
11721       TREE_OPERAND (node, 0) = cn;
11722       TREE_TYPE (node) = void_type_node;
11723       CAN_COMPLETE_NORMALLY (node) = 1;
11724       TREE_SIDE_EFFECTS (node) = 1;
11725       break;
11726
11727     case DEFAULT_EXPR:
11728       nn = ctxp->current_loop;
11729       /* Only one default label is allowed per switch statement */
11730       if (SWITCH_HAS_DEFAULT (nn))
11731         {
11732           EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
11733           parse_error_context (wfl_operator, 
11734                                "Duplicate case label: `default'");
11735           return error_mark_node;
11736         }
11737       else
11738         SWITCH_HAS_DEFAULT (nn) = 1;
11739       TREE_TYPE (node) = void_type_node;
11740       TREE_SIDE_EFFECTS (node) = 1;
11741       CAN_COMPLETE_NORMALLY (node) = 1;
11742       break;
11743
11744     case SWITCH_EXPR:
11745     case LOOP_EXPR:
11746       PUSH_LOOP (node);
11747       /* Check whether the loop was enclosed in a labeled
11748          statement. If not, create one, insert the loop in it and
11749          return the node */
11750       nn = patch_loop_statement (node);
11751
11752       /* Anyways, walk the body of the loop */
11753       if (TREE_CODE (node) == LOOP_EXPR)
11754         TREE_OPERAND (node, 0) = java_complete_tree (TREE_OPERAND (node, 0));
11755       /* Switch statement: walk the switch expression and the cases */
11756       else
11757         node = patch_switch_statement (node);
11758
11759       if (node == error_mark_node || TREE_OPERAND (node, 0) == error_mark_node)
11760         nn = error_mark_node;
11761       else
11762         {
11763           TREE_TYPE (nn) = TREE_TYPE (node) = void_type_node;
11764           /* If we returned something different, that's because we
11765              inserted a label. Pop the label too. */
11766           if (nn != node)
11767             {
11768               if (CAN_COMPLETE_NORMALLY (node))
11769                 CAN_COMPLETE_NORMALLY (nn) = 1;
11770               POP_LABELED_BLOCK ();
11771             }
11772         }
11773       POP_LOOP ();
11774       return nn;
11775
11776     case EXIT_EXPR:
11777       TREE_OPERAND (node, 0) = java_complete_tree (TREE_OPERAND (node, 0));
11778       return patch_exit_expr (node);
11779
11780     case COND_EXPR:
11781       /* Condition */
11782       TREE_OPERAND (node, 0) = java_complete_tree (TREE_OPERAND (node, 0));
11783       if (TREE_OPERAND (node, 0) == error_mark_node)
11784         return error_mark_node;
11785       /* then-else branches */
11786       TREE_OPERAND (node, 1) = java_complete_tree (TREE_OPERAND (node, 1));
11787       if (TREE_OPERAND (node, 1) == error_mark_node)
11788         return error_mark_node;
11789       TREE_OPERAND (node, 2) = java_complete_tree (TREE_OPERAND (node, 2));
11790       if (TREE_OPERAND (node, 2) == error_mark_node)
11791         return error_mark_node;
11792       return patch_if_else_statement (node);
11793       break;
11794
11795     case CONDITIONAL_EXPR:
11796       /* Condition */
11797       wfl_op1 = TREE_OPERAND (node, 0);
11798       COMPLETE_CHECK_OP_0 (node);
11799       wfl_op2 = TREE_OPERAND (node, 1);
11800       COMPLETE_CHECK_OP_1 (node);
11801       wfl_op3 = TREE_OPERAND (node, 2);
11802       COMPLETE_CHECK_OP_2 (node);
11803       return patch_conditional_expr (node, wfl_op1, wfl_op2);
11804
11805       /* 3- Expression section */
11806     case COMPOUND_EXPR:
11807       wfl_op2 = TREE_OPERAND (node, 1);
11808       TREE_OPERAND (node, 0) = nn = 
11809         java_complete_tree (TREE_OPERAND (node, 0));
11810       if (wfl_op2 == empty_stmt_node)
11811         CAN_COMPLETE_NORMALLY (node) = CAN_COMPLETE_NORMALLY (nn);
11812       else
11813         {
11814           if (! CAN_COMPLETE_NORMALLY (nn) && TREE_CODE (nn) != ERROR_MARK)
11815             {
11816               /* An unreachable condition in a do-while statement
11817                  is *not* (technically) an unreachable statement. */
11818               nn = wfl_op2;
11819               if (TREE_CODE (nn) == EXPR_WITH_FILE_LOCATION)
11820                 nn = EXPR_WFL_NODE (nn);
11821               if (TREE_CODE (nn) != EXIT_EXPR)
11822                 {
11823                   SET_WFL_OPERATOR (wfl_operator, node, wfl_op2);
11824                   parse_error_context (wfl_operator, "Unreachable statement");
11825                 }
11826             }
11827           TREE_OPERAND (node, 1) = java_complete_tree (TREE_OPERAND (node, 1));
11828           if (TREE_OPERAND (node, 1) == error_mark_node)
11829             return error_mark_node;
11830           /* Even though we might allow the case where the first
11831              operand doesn't return normally, we still should compute
11832              CAN_COMPLETE_NORMALLY correctly.  */
11833           CAN_COMPLETE_NORMALLY (node)
11834             = (CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 0))
11835                && CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 1)));
11836         }
11837       TREE_TYPE (node) = TREE_TYPE (TREE_OPERAND (node, 1));
11838       break;
11839
11840     case RETURN_EXPR:
11841       /* CAN_COMPLETE_NORMALLY (node) = 0; */
11842       return patch_return (node);
11843
11844     case EXPR_WITH_FILE_LOCATION:
11845       if (!EXPR_WFL_NODE (node) /* Or a PRIMARY flag ? */
11846           || TREE_CODE (EXPR_WFL_NODE (node)) == IDENTIFIER_NODE)
11847         {
11848           tree wfl = node;
11849           node = resolve_expression_name (node, NULL);
11850           if (node == error_mark_node)
11851             return node;
11852           /* Keep line number information somewhere were it doesn't
11853              disrupt the completion process. */
11854           if (flag_emit_xref && TREE_CODE (node) != CALL_EXPR)
11855             {
11856               EXPR_WFL_NODE (wfl) = TREE_OPERAND (node, 1);
11857               TREE_OPERAND (node, 1) = wfl;
11858             }
11859           CAN_COMPLETE_NORMALLY (node) = 1;
11860         }
11861       else
11862         {
11863           tree body;
11864           int save_lineno = lineno;
11865           lineno = EXPR_WFL_LINENO (node);
11866           body = java_complete_tree (EXPR_WFL_NODE (node));
11867           lineno = save_lineno;
11868           EXPR_WFL_NODE (node) = body;
11869           TREE_SIDE_EFFECTS (node) = TREE_SIDE_EFFECTS (body);
11870           CAN_COMPLETE_NORMALLY (node) = CAN_COMPLETE_NORMALLY (body);
11871           if (body == empty_stmt_node || TREE_CONSTANT (body))
11872             {
11873               /* Makes it easier to constant fold, detect empty bodies. */
11874               return body;
11875             }
11876           if (body == error_mark_node)
11877             {
11878               /* Its important for the evaluation of assignment that
11879                  this mark on the TREE_TYPE is propagated. */
11880               TREE_TYPE (node) = error_mark_node;
11881               return error_mark_node;
11882             }
11883           else
11884             TREE_TYPE (node) = TREE_TYPE (EXPR_WFL_NODE (node));
11885           
11886         }
11887       break;
11888
11889     case NEW_ARRAY_EXPR:
11890       /* Patch all the dimensions */
11891       flag = 0;
11892       for (cn = TREE_OPERAND (node, 1); cn; cn = TREE_CHAIN (cn))
11893         {
11894           int location = EXPR_WFL_LINECOL (TREE_VALUE (cn));
11895           tree dim = convert (int_type_node, 
11896                               java_complete_tree (TREE_VALUE (cn)));
11897           if (dim == error_mark_node)
11898             {
11899               flag = 1;
11900               continue;
11901             }
11902           else
11903             {
11904               TREE_VALUE (cn) = dim;
11905               /* Setup the location of the current dimension, for
11906                  later error report. */
11907               TREE_PURPOSE (cn) = 
11908                 build_expr_wfl (NULL_TREE, input_filename, 0, 0);
11909               EXPR_WFL_LINECOL (TREE_PURPOSE (cn)) = location;
11910             }
11911         }
11912       /* They complete the array creation expression, if no errors
11913          were found. */
11914       CAN_COMPLETE_NORMALLY (node) = 1;
11915       return (flag ? error_mark_node
11916               : force_evaluation_order (patch_newarray (node)));
11917
11918     case NEW_ANONYMOUS_ARRAY_EXPR:
11919       /* Create the array type if necessary. */
11920       if (ANONYMOUS_ARRAY_DIMS_SIG (node))
11921         {
11922           tree type = ANONYMOUS_ARRAY_BASE_TYPE (node);
11923           if (!(type = resolve_type_during_patch (type)))
11924             return error_mark_node;
11925           type = build_array_from_name (type, NULL_TREE,
11926                                         ANONYMOUS_ARRAY_DIMS_SIG (node), NULL);
11927           ANONYMOUS_ARRAY_BASE_TYPE (node) = build_pointer_type (type);
11928         }
11929       node = patch_new_array_init (ANONYMOUS_ARRAY_BASE_TYPE (node),
11930                                    ANONYMOUS_ARRAY_INITIALIZER (node));
11931       if (node == error_mark_node)
11932         return error_mark_node;
11933       CAN_COMPLETE_NORMALLY (node) = 1;
11934       return node;
11935
11936     case NEW_CLASS_EXPR:
11937     case CALL_EXPR:
11938       /* Complete function's argument(s) first */
11939       if (complete_function_arguments (node))
11940         return error_mark_node;
11941       else
11942         {
11943           tree decl, wfl = TREE_OPERAND (node, 0);
11944           int in_this = CALL_THIS_CONSTRUCTOR_P (node);
11945           int from_super = (EXPR_WFL_NODE (TREE_OPERAND (node, 0)) ==
11946                            super_identifier_node);
11947
11948           node = patch_method_invocation (node, NULL_TREE, NULL_TREE,
11949                                           from_super, 0, &decl);
11950           if (node == error_mark_node)
11951             return error_mark_node;
11952
11953           check_thrown_exceptions (EXPR_WFL_LINECOL (node), decl);
11954           /* If we call this(...), register signature and positions */
11955           if (in_this)
11956             DECL_CONSTRUCTOR_CALLS (current_function_decl) = 
11957               tree_cons (wfl, decl, 
11958                          DECL_CONSTRUCTOR_CALLS (current_function_decl));
11959           CAN_COMPLETE_NORMALLY (node) = 1;
11960           return force_evaluation_order (node);
11961         }
11962
11963     case MODIFY_EXPR:
11964       /* Save potential wfls */
11965       wfl_op1 = TREE_OPERAND (node, 0);
11966       TREE_OPERAND (node, 0) = nn = java_complete_lhs (wfl_op1);
11967       
11968       if (MODIFY_EXPR_FROM_INITIALIZATION_P (node)
11969           && TREE_CODE (nn) == VAR_DECL && TREE_STATIC (nn)
11970           && DECL_INITIAL (nn) != NULL_TREE)
11971         {
11972           tree value;
11973           
11974           value = fold_constant_for_init (nn, nn);
11975
11976           /* When we have a primitype type, or a string and we're not
11977              emitting a class file, we actually don't want to generate
11978              anything for the assignment. */
11979           if (value != NULL_TREE &&
11980               (JPRIMITIVE_TYPE_P (TREE_TYPE (value)) || 
11981                (TREE_TYPE (value) == string_ptr_type_node &&
11982                 ! flag_emit_class_files)))
11983             {
11984               /* Prepare node for patch_assignment */
11985               TREE_OPERAND (node, 1) = value;
11986               /* Call patch assignment to verify the assignment */
11987               if (patch_assignment (node, wfl_op1) == error_mark_node)
11988                 return error_mark_node;
11989               /* Set DECL_INITIAL properly (a conversion might have
11990                  been decided by patch_assignment) and return the
11991                  empty statement. */
11992               else
11993                 {
11994                   tree patched = patch_string (TREE_OPERAND (node, 1));
11995                   if (patched)
11996                     DECL_INITIAL (nn) = patched;
11997                   else
11998                     DECL_INITIAL (nn) = TREE_OPERAND (node, 1);
11999                   DECL_FIELD_FINAL_IUD (nn) = 1;
12000                   return empty_stmt_node;
12001                 }
12002             }
12003           if (! flag_emit_class_files)
12004             DECL_INITIAL (nn) = NULL_TREE;
12005         }
12006       wfl_op2 = TREE_OPERAND (node, 1);
12007
12008       if (TREE_OPERAND (node, 0) == error_mark_node)
12009         return error_mark_node;
12010
12011       flag = COMPOUND_ASSIGN_P (wfl_op2);
12012       if (flag)
12013         {
12014           /* This might break when accessing outer field from inner
12015              class. TESTME, FIXME */
12016           tree lvalue = java_stabilize_reference (TREE_OPERAND (node, 0)); 
12017
12018           /* Hand stabilize the lhs on both places */
12019           TREE_OPERAND (node, 0) = lvalue;
12020           TREE_OPERAND (TREE_OPERAND (node, 1), 0) = 
12021             (flag_emit_class_files ? lvalue : save_expr (lvalue));
12022
12023           /* 15.25.2.a: Left hand is not an array access. FIXME */
12024           /* Now complete the RHS. We write it back later on. */
12025           nn = java_complete_tree (TREE_OPERAND (node, 1));
12026
12027           if ((cn = patch_string (nn)))
12028             nn = cn;
12029
12030           /* The last part of the rewrite for E1 op= E2 is to have 
12031              E1 = (T)(E1 op E2), with T being the type of E1. */
12032           nn = java_complete_tree (build_cast (EXPR_WFL_LINECOL (wfl_op2), 
12033                                                TREE_TYPE (lvalue), nn));
12034
12035           /* If the assignment is compound and has reference type,
12036              then ensure the LHS has type String and nothing else.  */
12037           if (JREFERENCE_TYPE_P (TREE_TYPE (lvalue))
12038               && ! JSTRING_TYPE_P (TREE_TYPE (lvalue)))
12039             parse_error_context (wfl_op2,
12040                                  "Incompatible type for `+='. Can't convert `%s' to `java.lang.String'",
12041                                  lang_printable_name (TREE_TYPE (lvalue), 0));
12042
12043           /* 15.25.2.b: Left hand is an array access. FIXME */
12044         }
12045
12046       /* If we're about to patch a NEW_ARRAY_INIT, we call a special
12047          function to complete this RHS. Note that a NEW_ARRAY_INIT
12048          might have been already fully expanded if created as a result
12049          of processing an anonymous array initializer. We avoid doing
12050          the operation twice by testing whether the node already bears
12051          a type. */
12052       else if (TREE_CODE (wfl_op2) == NEW_ARRAY_INIT && !TREE_TYPE (wfl_op2))
12053         nn = patch_new_array_init (TREE_TYPE (TREE_OPERAND (node, 0)),
12054                                    TREE_OPERAND (node, 1));
12055       /* Otherwise we simply complete the RHS */
12056       else
12057         nn = java_complete_tree (TREE_OPERAND (node, 1));
12058
12059       if (nn == error_mark_node)
12060         return error_mark_node;
12061
12062       /* Write back the RHS as we evaluated it. */
12063       TREE_OPERAND (node, 1) = nn;
12064
12065       /* In case we're handling = with a String as a RHS, we need to
12066          produce a String out of the RHS (it might still be a
12067          STRING_CST or a StringBuffer at this stage */
12068       if ((nn = patch_string (TREE_OPERAND (node, 1))))
12069         TREE_OPERAND (node, 1) = nn;
12070
12071       if ((nn = outer_field_access_fix (wfl_op1, TREE_OPERAND (node, 0),
12072                                         TREE_OPERAND (node, 1))))
12073         {
12074           /* We return error_mark_node if outer_field_access_fix
12075              detects we write into a final. */
12076           if (nn == error_mark_node)
12077             return error_mark_node;
12078           node = nn;
12079         }
12080       else
12081         {
12082           node = patch_assignment (node, wfl_op1);
12083           /* Reorganize the tree if necessary. */
12084           if (flag && (!JREFERENCE_TYPE_P (TREE_TYPE (node)) 
12085                        || JSTRING_P (TREE_TYPE (node))))
12086             node = java_refold (node);
12087         }
12088
12089       /* Seek to set DECL_INITIAL to a proper value, since it might have
12090          undergone a conversion in patch_assignment. We do that only when
12091          it's necessary to have DECL_INITIAL properly set. */
12092       nn = TREE_OPERAND (node, 0);
12093       if (TREE_CODE (nn) == VAR_DECL 
12094           && DECL_INITIAL (nn) && CONSTANT_VALUE_P (DECL_INITIAL (nn))
12095           && FIELD_STATIC (nn) && FIELD_FINAL (nn) 
12096           && (JPRIMITIVE_TYPE_P (TREE_TYPE (nn))
12097               || TREE_TYPE (nn) == string_ptr_type_node))
12098         DECL_INITIAL (nn) = TREE_OPERAND (node, 1);
12099
12100       CAN_COMPLETE_NORMALLY (node) = 1;
12101       return node;
12102
12103     case MULT_EXPR:
12104     case PLUS_EXPR:
12105     case MINUS_EXPR:
12106     case LSHIFT_EXPR:
12107     case RSHIFT_EXPR:
12108     case URSHIFT_EXPR:
12109     case BIT_AND_EXPR:
12110     case BIT_XOR_EXPR:
12111     case BIT_IOR_EXPR:
12112     case TRUNC_MOD_EXPR:
12113     case TRUNC_DIV_EXPR:
12114     case RDIV_EXPR:
12115     case TRUTH_ANDIF_EXPR:
12116     case TRUTH_ORIF_EXPR:
12117     case EQ_EXPR: 
12118     case NE_EXPR:
12119     case GT_EXPR:
12120     case GE_EXPR:
12121     case LT_EXPR:
12122     case LE_EXPR:
12123       /* Operands 0 and 1 are WFL in certain cases only. patch_binop
12124          knows how to handle those cases. */
12125       wfl_op1 = TREE_OPERAND (node, 0);
12126       wfl_op2 = TREE_OPERAND (node, 1);
12127
12128       CAN_COMPLETE_NORMALLY (node) = 1;
12129       /* Don't complete string nodes if dealing with the PLUS operand. */
12130       if (TREE_CODE (node) != PLUS_EXPR || !JSTRING_P (wfl_op1))
12131         {
12132           nn = java_complete_tree (wfl_op1);
12133           if (nn == error_mark_node)
12134             return error_mark_node;
12135
12136           TREE_OPERAND (node, 0) = nn;
12137         }
12138       if (TREE_CODE (node) != PLUS_EXPR || !JSTRING_P (wfl_op2))
12139         {
12140           nn = java_complete_tree (wfl_op2);
12141           if (nn == error_mark_node)
12142             return error_mark_node;
12143
12144           TREE_OPERAND (node, 1) = nn;
12145         }
12146       return force_evaluation_order (patch_binop (node, wfl_op1, wfl_op2));
12147
12148     case INSTANCEOF_EXPR:
12149       wfl_op1 = TREE_OPERAND (node, 0);
12150       COMPLETE_CHECK_OP_0 (node);
12151       if (flag_emit_xref)
12152         {
12153           TREE_TYPE (node) = boolean_type_node;
12154           return node;
12155         }
12156       return patch_binop (node, wfl_op1, TREE_OPERAND (node, 1));
12157
12158     case UNARY_PLUS_EXPR:
12159     case NEGATE_EXPR:
12160     case TRUTH_NOT_EXPR:
12161     case BIT_NOT_EXPR:
12162     case PREDECREMENT_EXPR:
12163     case PREINCREMENT_EXPR:
12164     case POSTDECREMENT_EXPR:
12165     case POSTINCREMENT_EXPR:
12166     case CONVERT_EXPR:
12167       /* There are cases were wfl_op1 is a WFL. patch_unaryop knows
12168          how to handle those cases. */
12169       wfl_op1 = TREE_OPERAND (node, 0);
12170       CAN_COMPLETE_NORMALLY (node) = 1;
12171       TREE_OPERAND (node, 0) = java_complete_tree (wfl_op1);
12172       if (TREE_OPERAND (node, 0) == error_mark_node)
12173         return error_mark_node;
12174       node = patch_unaryop (node, wfl_op1);
12175       CAN_COMPLETE_NORMALLY (node) = 1;
12176       break;
12177
12178     case ARRAY_REF:
12179       /* There are cases were wfl_op1 is a WFL. patch_array_ref knows
12180          how to handle those cases. */
12181       wfl_op1 = TREE_OPERAND (node, 0);
12182       TREE_OPERAND (node, 0) = java_complete_tree (wfl_op1);
12183       if (TREE_OPERAND (node, 0) == error_mark_node)
12184         return error_mark_node;
12185       if (!flag_emit_class_files && !flag_emit_xref)
12186         TREE_OPERAND (node, 0) = save_expr (TREE_OPERAND (node, 0));
12187       /* The same applies to wfl_op2 */
12188       wfl_op2 = TREE_OPERAND (node, 1);
12189       TREE_OPERAND (node, 1) = java_complete_tree (wfl_op2);
12190       if (TREE_OPERAND (node, 1) == error_mark_node)
12191         return error_mark_node;
12192       if (!flag_emit_class_files && !flag_emit_xref)
12193         TREE_OPERAND (node, 1) = save_expr (TREE_OPERAND (node, 1));
12194       return patch_array_ref (node);
12195
12196     case RECORD_TYPE:
12197       return node;;
12198
12199     case COMPONENT_REF:
12200       /* The first step in the re-write of qualified name handling.  FIXME.
12201          So far, this is only to support PRIMTYPE.class -> PRIMCLASS.TYPE. */
12202       TREE_OPERAND (node, 0) = java_complete_tree (TREE_OPERAND (node, 0));
12203       if (TREE_CODE (TREE_OPERAND (node, 0)) == RECORD_TYPE)
12204         {
12205           tree name = TREE_OPERAND (node, 1);
12206           tree field = lookup_field_wrapper (TREE_OPERAND (node, 0), name);
12207           if (field == NULL_TREE)
12208             {
12209               error ("missing static field `%s'", IDENTIFIER_POINTER (name));
12210               return error_mark_node;
12211             }
12212           if (! FIELD_STATIC (field))
12213             {
12214               error ("not a static field `%s'", IDENTIFIER_POINTER (name));
12215               return error_mark_node;
12216             }
12217           return field;
12218         }
12219       else
12220         abort ();
12221       break;
12222
12223     case THIS_EXPR:
12224       /* Can't use THIS in a static environment */
12225       if (!current_this)
12226         {
12227           EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
12228           parse_error_context (wfl_operator,
12229                                "Keyword `this' used outside allowed context");
12230           TREE_TYPE (node) = error_mark_node;
12231           return error_mark_node;
12232         }
12233       if (ctxp->explicit_constructor_p)
12234         {
12235           EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
12236           parse_error_context 
12237             (wfl_operator, "Can't reference `this' or `super' before the superclass constructor has been called");
12238           TREE_TYPE (node) = error_mark_node;
12239           return error_mark_node;
12240         }
12241       return current_this;
12242       
12243     case CLASS_LITERAL:
12244       CAN_COMPLETE_NORMALLY (node) = 1;
12245       node = patch_incomplete_class_ref (node);
12246       if (node == error_mark_node)
12247         return error_mark_node;
12248       break;
12249
12250     default:
12251       CAN_COMPLETE_NORMALLY (node) = 1;
12252       /* Ok: may be we have a STRING_CST or a crafted `StringBuffer'
12253          and it's time to turn it into the appropriate String object */
12254       if ((nn = patch_string (node)))
12255         node = nn;
12256       else
12257         internal_error ("No case for %s", tree_code_name [TREE_CODE (node)]);
12258     }
12259   return node;
12260 }
12261
12262 /* Complete function call's argument. Return a non zero value is an
12263    error was found.  */
12264
12265 static int
12266 complete_function_arguments (node)
12267      tree node;
12268 {
12269   int flag = 0;
12270   tree cn;
12271
12272   ctxp->explicit_constructor_p += (CALL_EXPLICIT_CONSTRUCTOR_P (node) ? 1 : 0);
12273   for (cn = TREE_OPERAND (node, 1); cn; cn = TREE_CHAIN (cn))
12274     {
12275       tree wfl = TREE_VALUE (cn), parm, temp;
12276       parm = java_complete_tree (wfl);
12277
12278       if (parm == error_mark_node)
12279         {
12280           flag = 1;
12281           continue;
12282         }
12283       /* If have a string literal that we haven't transformed yet or a
12284          crafted string buffer, as a result of use of the the String
12285          `+' operator. Build `parm.toString()' and expand it. */
12286       if ((temp = patch_string (parm)))
12287         parm = temp;
12288
12289       TREE_VALUE (cn) = parm;
12290     }
12291   ctxp->explicit_constructor_p -= (CALL_EXPLICIT_CONSTRUCTOR_P (node) ? 1 : 0);
12292   return flag;
12293 }
12294
12295 /* Sometimes (for loops and variable initialized during their
12296    declaration), we want to wrap a statement around a WFL and turn it
12297    debugable.  */
12298
12299 static tree
12300 build_debugable_stmt (location, stmt)
12301     int location;
12302     tree stmt;
12303 {
12304   if (TREE_CODE (stmt) != EXPR_WITH_FILE_LOCATION)
12305     {
12306       stmt = build_expr_wfl (stmt, input_filename, 0, 0);
12307       EXPR_WFL_LINECOL (stmt) = location;
12308     }
12309   JAVA_MAYBE_GENERATE_DEBUG_INFO (stmt);
12310   return stmt;
12311 }
12312
12313 static tree
12314 build_expr_block (body, decls)
12315      tree body, decls;
12316 {
12317   tree node = make_node (BLOCK);
12318   BLOCK_EXPR_DECLS (node) = decls;
12319   BLOCK_EXPR_BODY (node) = body;
12320   if (body)
12321     TREE_TYPE (node) = TREE_TYPE (body);
12322   TREE_SIDE_EFFECTS (node) = 1;
12323   return node;
12324 }
12325
12326 /* Create a new function block and link it appropriately to current
12327    function block chain */
12328
12329 static tree
12330 enter_block ()
12331 {
12332   tree b = build_expr_block (NULL_TREE, NULL_TREE);
12333
12334   /* Link block B supercontext to the previous block. The current
12335      function DECL is used as supercontext when enter_a_block is called
12336      for the first time for a given function. The current function body
12337      (DECL_FUNCTION_BODY) is set to be block B.  */
12338
12339   tree fndecl = current_function_decl; 
12340
12341   if (!fndecl) {
12342     BLOCK_SUPERCONTEXT (b) = current_static_block;
12343     current_static_block = b;
12344   }
12345
12346   else if (!DECL_FUNCTION_BODY (fndecl))
12347     {
12348       BLOCK_SUPERCONTEXT (b) = fndecl;
12349       DECL_FUNCTION_BODY (fndecl) = b;
12350     }
12351   else
12352     {
12353       BLOCK_SUPERCONTEXT (b) = DECL_FUNCTION_BODY (fndecl);
12354       DECL_FUNCTION_BODY (fndecl) = b;
12355     }
12356   return b;
12357 }
12358
12359 /* Exit a block by changing the current function body
12360    (DECL_FUNCTION_BODY) to the current block super context, only if
12361    the block being exited isn't the method's top level one.  */
12362
12363 static tree
12364 exit_block ()
12365 {
12366   tree b;
12367   if (current_function_decl)
12368     {
12369       b = DECL_FUNCTION_BODY (current_function_decl);
12370       if (BLOCK_SUPERCONTEXT (b) != current_function_decl)
12371         DECL_FUNCTION_BODY (current_function_decl) = BLOCK_SUPERCONTEXT (b);
12372     }
12373   else
12374     {
12375       b = current_static_block;
12376
12377       if (BLOCK_SUPERCONTEXT (b))
12378         current_static_block = BLOCK_SUPERCONTEXT (b);
12379     }
12380   return b;
12381 }
12382
12383 /* Lookup for NAME in the nested function's blocks, all the way up to
12384    the current toplevel one. It complies with Java's local variable
12385    scoping rules.  */
12386
12387 static tree
12388 lookup_name_in_blocks (name)
12389      tree name;
12390 {
12391   tree b = GET_CURRENT_BLOCK (current_function_decl);
12392
12393   while (b != current_function_decl)
12394     {
12395       tree current;
12396
12397       /* Paranoid sanity check. To be removed */
12398       if (TREE_CODE (b) != BLOCK)
12399         abort ();
12400
12401       for (current = BLOCK_EXPR_DECLS (b); current; 
12402            current = TREE_CHAIN (current))
12403         if (DECL_NAME (current) == name)
12404           return current;
12405       b = BLOCK_SUPERCONTEXT (b);
12406     }
12407   return NULL_TREE;
12408 }
12409
12410 static void
12411 maybe_absorb_scoping_blocks ()
12412 {
12413   while (BLOCK_IS_IMPLICIT (GET_CURRENT_BLOCK (current_function_decl)))
12414     {
12415       tree b = exit_block ();
12416       java_method_add_stmt (current_function_decl, b);
12417       SOURCE_FRONTEND_DEBUG (("Absorbing scoping block at line %d", lineno));
12418     }
12419 }
12420
12421 \f
12422 /* This section of the source is reserved to build_* functions that
12423    are building incomplete tree nodes and the patch_* functions that
12424    are completing them.  */
12425
12426 /* Wrap a non WFL node around a WFL.  */
12427
12428 static tree
12429 build_wfl_wrap (node, location)
12430     tree node;
12431     int location;
12432 {
12433   tree wfl, node_to_insert = node;
12434   
12435   /* We want to process THIS . xxx symbolicaly, to keep it consistent
12436      with the way we're processing SUPER. A THIS from a primary as a
12437      different form than a SUPER. Turn THIS into something symbolic */
12438   if (TREE_CODE (node) == THIS_EXPR)
12439     node_to_insert = wfl = build_wfl_node (this_identifier_node);
12440   else
12441     wfl = build_expr_wfl (NULL_TREE, ctxp->filename, 0, 0);
12442
12443   EXPR_WFL_LINECOL (wfl) = location;
12444   EXPR_WFL_QUALIFICATION (wfl) = build_tree_list (node_to_insert, NULL_TREE);
12445   return wfl;
12446 }
12447
12448 /* Build a super() constructor invocation. Returns empty_stmt_node if
12449    we're currently dealing with the class java.lang.Object. */
12450
12451 static tree
12452 build_super_invocation (mdecl)
12453      tree mdecl;
12454 {
12455   if (DECL_CONTEXT (mdecl) == object_type_node)
12456     return empty_stmt_node;
12457   else
12458     {
12459       tree super_wfl = build_wfl_node (super_identifier_node);
12460       tree a = NULL_TREE, t;
12461       /* If we're dealing with an anonymous class, pass the arguments
12462          of the crafted constructor along. */
12463       if (ANONYMOUS_CLASS_P (DECL_CONTEXT (mdecl)))
12464         {
12465           SKIP_THIS_AND_ARTIFICIAL_PARMS (t, mdecl);
12466           for (; t != end_params_node; t = TREE_CHAIN (t))
12467             a = tree_cons (NULL_TREE, build_wfl_node (TREE_PURPOSE (t)), a);
12468         }
12469       return build_method_invocation (super_wfl, a);
12470     }
12471 }
12472
12473 /* Build a SUPER/THIS qualified method invocation.  */
12474
12475 static tree
12476 build_this_super_qualified_invocation (use_this, name, args, lloc, rloc)
12477      int use_this;
12478      tree name, args;
12479      int lloc, rloc;
12480 {
12481   tree invok;
12482   tree wfl = 
12483     build_wfl_node (use_this ? this_identifier_node : super_identifier_node);
12484   EXPR_WFL_LINECOL (wfl) = lloc;
12485   invok = build_method_invocation (name, args);
12486   return make_qualified_primary (wfl, invok, rloc);
12487 }
12488
12489 /* Build an incomplete CALL_EXPR node. */
12490
12491 static tree
12492 build_method_invocation (name, args)
12493     tree name;
12494     tree args;
12495 {
12496   tree call = build (CALL_EXPR, NULL_TREE, name, args, NULL_TREE);
12497   TREE_SIDE_EFFECTS (call) = 1;
12498   EXPR_WFL_LINECOL (call) = EXPR_WFL_LINECOL (name);
12499   return call;
12500 }
12501
12502 /* Build an incomplete new xxx(...) node. */
12503
12504 static tree
12505 build_new_invocation (name, args)
12506     tree name, args;
12507 {
12508   tree call = build (NEW_CLASS_EXPR, NULL_TREE, name, args, NULL_TREE);
12509   TREE_SIDE_EFFECTS (call) = 1;
12510   EXPR_WFL_LINECOL (call) = EXPR_WFL_LINECOL (name);
12511   return call;
12512 }
12513
12514 /* Build an incomplete assignment expression. */
12515
12516 static tree
12517 build_assignment (op, op_location, lhs, rhs)
12518      int op, op_location;
12519      tree lhs, rhs;
12520 {
12521   tree assignment;
12522   /* Build the corresponding binop if we deal with a Compound
12523      Assignment operator. Mark the binop sub-tree as part of a
12524      Compound Assignment expression */
12525   if (op != ASSIGN_TK)
12526     {
12527       rhs = build_binop (BINOP_LOOKUP (op), op_location, lhs, rhs);
12528       COMPOUND_ASSIGN_P (rhs) = 1;
12529     }
12530   assignment = build (MODIFY_EXPR, NULL_TREE, lhs, rhs);
12531   TREE_SIDE_EFFECTS (assignment) = 1;
12532   EXPR_WFL_LINECOL (assignment) = op_location;
12533   return assignment;
12534 }
12535
12536 /* Print an INTEGER_CST node in a static buffer, and return the buffer. */
12537
12538 char *
12539 print_int_node (node)
12540     tree node;
12541 {
12542   static char buffer [80];
12543   if (TREE_CONSTANT_OVERFLOW (node))
12544     sprintf (buffer, "<overflow>");
12545     
12546   if (TREE_INT_CST_HIGH (node) == 0)
12547     sprintf (buffer, HOST_WIDE_INT_PRINT_UNSIGNED,
12548              TREE_INT_CST_LOW (node));
12549   else if (TREE_INT_CST_HIGH (node) == -1
12550            && TREE_INT_CST_LOW (node) != 0)
12551     {
12552       buffer [0] = '-';
12553       sprintf (&buffer [1], HOST_WIDE_INT_PRINT_UNSIGNED,
12554                -TREE_INT_CST_LOW (node));
12555     }
12556   else
12557     sprintf (buffer, HOST_WIDE_INT_PRINT_DOUBLE_HEX,
12558              TREE_INT_CST_HIGH (node), TREE_INT_CST_LOW (node));
12559
12560   return buffer;
12561 }
12562
12563 \f
12564 /* Return 1 if an assignment to a FINAL is attempted in a non suitable
12565    context.  */
12566
12567 /* 15.25 Assignment operators. */
12568
12569 static tree
12570 patch_assignment (node, wfl_op1)
12571      tree node;
12572      tree wfl_op1;
12573 {
12574   tree rhs = TREE_OPERAND (node, 1);
12575   tree lvalue = TREE_OPERAND (node, 0), llvalue;
12576   tree lhs_type = NULL_TREE, rhs_type, new_rhs = NULL_TREE;
12577   int error_found = 0;
12578   int lvalue_from_array = 0;
12579   int is_return = 0;
12580
12581   EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
12582
12583   /* Lhs can be a named variable */
12584   if (JDECL_P (lvalue))
12585     {
12586       lhs_type = TREE_TYPE (lvalue);
12587     }
12588   /* Or Lhs can be an array access. */
12589   else if (TREE_CODE (lvalue) == ARRAY_REF)
12590     {
12591       lhs_type = TREE_TYPE (lvalue);
12592       lvalue_from_array = 1;
12593     }
12594   /* Or a field access */
12595   else if (TREE_CODE (lvalue) == COMPONENT_REF)
12596     lhs_type = TREE_TYPE (lvalue);
12597   /* Or a function return slot */
12598   else if (TREE_CODE (lvalue) == RESULT_DECL)
12599     {
12600       /* If the return type is an integral type, then we create the
12601          RESULT_DECL with a promoted type, but we need to do these
12602          checks against the unpromoted type to ensure type safety.  So
12603          here we look at the real type, not the type of the decl we
12604          are modifying.  */
12605       lhs_type = TREE_TYPE (TREE_TYPE (current_function_decl));
12606       is_return = 1;
12607     }
12608   /* Otherwise, we might want to try to write into an optimized static
12609      final, this is an of a different nature, reported further on. */
12610   else if (TREE_CODE (wfl_op1) == EXPR_WITH_FILE_LOCATION
12611            && resolve_expression_name (wfl_op1, &llvalue))
12612     {
12613       lhs_type = TREE_TYPE (lvalue);
12614     }
12615   else 
12616     {
12617       parse_error_context (wfl_op1, "Invalid left hand side of assignment");
12618       error_found = 1;
12619     }
12620
12621   rhs_type = TREE_TYPE (rhs);
12622
12623   /* 5.1 Try the assignment conversion for builtin type. */
12624   new_rhs = try_builtin_assignconv (wfl_op1, lhs_type, rhs);
12625
12626   /* 5.2 If it failed, try a reference conversion */
12627   if (!new_rhs && (new_rhs = try_reference_assignconv (lhs_type, rhs)))
12628     lhs_type = promote_type (rhs_type);
12629
12630   /* 15.25.2 If we have a compound assignment, convert RHS into the
12631      type of the LHS */
12632   else if (COMPOUND_ASSIGN_P (TREE_OPERAND (node, 1)))
12633     new_rhs = convert (lhs_type, rhs);
12634
12635   /* Explicit cast required. This is an error */
12636   if (!new_rhs)
12637     {
12638       char *t1 = xstrdup (lang_printable_name (TREE_TYPE (rhs), 0));
12639       char *t2 = xstrdup (lang_printable_name (lhs_type, 0));
12640       tree wfl;
12641       char operation [32];      /* Max size known */
12642
12643       /* If the assignment is part of a declaration, we use the WFL of
12644          the declared variable to point out the error and call it a
12645          declaration problem. If the assignment is a genuine =
12646          operator, we call is a operator `=' problem, otherwise we
12647          call it an assignment problem. In both of these last cases,
12648          we use the WFL of the operator to indicate the error. */
12649
12650       if (MODIFY_EXPR_FROM_INITIALIZATION_P (node))
12651         {
12652           wfl = wfl_op1;
12653           strcpy (operation, "declaration");
12654         }
12655       else
12656         {
12657           wfl = wfl_operator;
12658           if (COMPOUND_ASSIGN_P (TREE_OPERAND (node, 1)))
12659             strcpy (operation, "assignment");
12660           else if (is_return)
12661             strcpy (operation, "`return'");
12662           else
12663             strcpy (operation, "`='");
12664         }
12665
12666       if (!valid_cast_to_p (rhs_type, lhs_type))
12667         parse_error_context
12668           (wfl, "Incompatible type for %s. Can't convert `%s' to `%s'",
12669            operation, t1, t2);
12670       else
12671         parse_error_context (wfl, "Incompatible type for %s. Explicit cast needed to convert `%s' to `%s'",
12672                              operation, t1, t2);
12673       free (t1); free (t2);
12674       error_found = 1;
12675     }
12676
12677   if (error_found)
12678     return error_mark_node;
12679
12680   /* If we're processing a `return' statement, promote the actual type
12681      to the promoted type.  */
12682   if (is_return)
12683     new_rhs = convert (TREE_TYPE (lvalue), new_rhs);
12684
12685   /* 10.10: Array Store Exception runtime check */
12686   if (!flag_emit_class_files
12687       && !flag_emit_xref
12688       && lvalue_from_array 
12689       && JREFERENCE_TYPE_P (TYPE_ARRAY_ELEMENT (lhs_type)))
12690     {
12691       tree array, store_check, base, index_expr;
12692
12693       /* Get the INDIRECT_REF. */
12694       array = TREE_OPERAND (TREE_OPERAND (lvalue, 0), 0);
12695       /* Get the array pointer expr. */
12696       array = TREE_OPERAND (array, 0);
12697       store_check = build_java_arraystore_check (array, new_rhs);
12698       
12699       index_expr = TREE_OPERAND (lvalue, 1);
12700       
12701       if (TREE_CODE (index_expr) == COMPOUND_EXPR)
12702         {
12703           /* A COMPOUND_EXPR here is a bounds check. The bounds check must 
12704              happen before the store check, so prepare to insert the store
12705              check within the second operand of the existing COMPOUND_EXPR. */
12706           base = index_expr;
12707         }
12708       else
12709         base = lvalue;
12710       
12711       index_expr = TREE_OPERAND (base, 1);
12712       TREE_OPERAND (base, 1) = build (COMPOUND_EXPR, TREE_TYPE (index_expr), 
12713                                       store_check, index_expr);
12714     }
12715
12716   /* Final locals can be used as case values in switch
12717      statement. Prepare them for this eventuality. */
12718   if (TREE_CODE (lvalue) == VAR_DECL 
12719       && DECL_FINAL (lvalue)
12720       && TREE_CONSTANT (new_rhs)
12721       && IDENTIFIER_LOCAL_VALUE (DECL_NAME (lvalue))
12722       && JINTEGRAL_TYPE_P (TREE_TYPE (lvalue))
12723       )
12724     {
12725       TREE_CONSTANT (lvalue) = 1;
12726       DECL_INITIAL (lvalue) = new_rhs;
12727     }
12728
12729   TREE_OPERAND (node, 0) = lvalue;
12730   TREE_OPERAND (node, 1) = new_rhs;
12731   TREE_TYPE (node) = lhs_type;
12732   return node;
12733 }
12734
12735 /* Check that type SOURCE can be cast into type DEST. If the cast
12736    can't occur at all, return NULL; otherwise, return a possibly
12737    modified rhs.  */
12738
12739 static tree
12740 try_reference_assignconv (lhs_type, rhs)
12741      tree lhs_type, rhs;
12742 {
12743   tree new_rhs = NULL_TREE;
12744   tree rhs_type = TREE_TYPE (rhs);
12745
12746   if (!JPRIMITIVE_TYPE_P (rhs_type) && JREFERENCE_TYPE_P (lhs_type))
12747     {
12748       /* `null' may be assigned to any reference type */
12749       if (rhs == null_pointer_node)
12750         new_rhs = null_pointer_node;
12751       /* Try the reference assignment conversion */
12752       else if (valid_ref_assignconv_cast_p (rhs_type, lhs_type, 0))
12753         new_rhs = rhs;
12754       /* This is a magic assignment that we process differently */
12755       else if (TREE_CODE (rhs) == JAVA_EXC_OBJ_EXPR)
12756         new_rhs = rhs;
12757     }
12758   return new_rhs;
12759 }
12760
12761 /* Check that RHS can be converted into LHS_TYPE by the assignment
12762    conversion (5.2), for the cases of RHS being a builtin type. Return
12763    NULL_TREE if the conversion fails or if because RHS isn't of a
12764    builtin type. Return a converted RHS if the conversion is possible.  */
12765
12766 static tree
12767 try_builtin_assignconv (wfl_op1, lhs_type, rhs)
12768      tree wfl_op1, lhs_type, rhs;
12769 {
12770   tree new_rhs = NULL_TREE;
12771   tree rhs_type = TREE_TYPE (rhs);
12772
12773   /* Handle boolean specially.  */
12774   if (TREE_CODE (rhs_type) == BOOLEAN_TYPE
12775       || TREE_CODE (lhs_type) == BOOLEAN_TYPE)
12776     {
12777       if (TREE_CODE (rhs_type) == BOOLEAN_TYPE
12778           && TREE_CODE (lhs_type) == BOOLEAN_TYPE)
12779         new_rhs = rhs;
12780     }
12781
12782   /* Zero accepted everywhere */
12783   else if (TREE_CODE (rhs) == INTEGER_CST 
12784       && TREE_INT_CST_HIGH (rhs) == 0 && TREE_INT_CST_LOW (rhs) == 0
12785       && JPRIMITIVE_TYPE_P (rhs_type))
12786     new_rhs = convert (lhs_type, rhs);
12787
12788   /* 5.1.1 Try Identity Conversion,
12789      5.1.2 Try Widening Primitive Conversion */
12790   else if (valid_builtin_assignconv_identity_widening_p (lhs_type, rhs_type))
12791     new_rhs = convert (lhs_type, rhs);
12792
12793   /* Try a narrowing primitive conversion (5.1.3): 
12794        - expression is a constant expression of type int AND
12795        - variable is byte, short or char AND
12796        - The value of the expression is representable in the type of the 
12797          variable */
12798   else if (rhs_type == int_type_node && TREE_CONSTANT (rhs)
12799            && (lhs_type == byte_type_node || lhs_type == char_type_node
12800                || lhs_type == short_type_node))
12801     {
12802       if (int_fits_type_p (rhs, lhs_type))
12803         new_rhs = convert (lhs_type, rhs);
12804       else if (wfl_op1)         /* Might be called with a NULL */
12805         parse_warning_context 
12806           (wfl_op1, "Constant expression `%s' too wide for narrowing primitive conversion to `%s'", 
12807            print_int_node (rhs), lang_printable_name (lhs_type, 0));
12808       /* Reported a warning that will turn into an error further
12809          down, so we don't return */
12810     }
12811
12812   return new_rhs;
12813 }
12814
12815 /* Return 1 if RHS_TYPE can be converted to LHS_TYPE by identity
12816    conversion (5.1.1) or widening primitive conversion (5.1.2).  Return
12817    0 is the conversion test fails.  This implements parts the method
12818    invocation convertion (5.3).  */
12819
12820 static int
12821 valid_builtin_assignconv_identity_widening_p (lhs_type, rhs_type)
12822      tree lhs_type, rhs_type;
12823 {
12824   /* 5.1.1: This is the identity conversion part. */
12825   if (lhs_type == rhs_type)
12826     return 1;
12827
12828   /* Reject non primitive types and boolean conversions.  */
12829   if (!JNUMERIC_TYPE_P (lhs_type) || !JNUMERIC_TYPE_P (rhs_type))
12830     return 0;
12831
12832   /* 5.1.2: widening primitive conversion. byte, even if it's smaller
12833      than a char can't be converted into a char. Short can't too, but
12834      the < test below takes care of that */
12835   if (lhs_type == char_type_node && rhs_type == byte_type_node)
12836     return 0;
12837
12838   /* Accept all promoted type here. Note, we can't use <= in the test
12839      below, because we still need to bounce out assignments of short
12840      to char and the likes */
12841   if (lhs_type == int_type_node
12842       && (rhs_type == promoted_byte_type_node
12843           || rhs_type == promoted_short_type_node
12844           || rhs_type == promoted_char_type_node
12845           || rhs_type == promoted_boolean_type_node))
12846     return 1;
12847
12848   /* From here, an integral is widened if its precision is smaller
12849      than the precision of the LHS or if the LHS is a floating point
12850      type, or the RHS is a float and the RHS a double. */
12851   if ((JINTEGRAL_TYPE_P (rhs_type) && JINTEGRAL_TYPE_P (lhs_type) 
12852        && (TYPE_PRECISION (rhs_type) < TYPE_PRECISION (lhs_type)))
12853       || (JINTEGRAL_TYPE_P (rhs_type) && JFLOAT_TYPE_P (lhs_type))
12854       || (rhs_type == float_type_node && lhs_type == double_type_node))
12855     return 1;
12856
12857   return 0;
12858 }
12859
12860 /* Check that something of SOURCE type can be assigned or cast to
12861    something of DEST type at runtime. Return 1 if the operation is
12862    valid, 0 otherwise. If CAST is set to 1, we're treating the case
12863    were SOURCE is cast into DEST, which borrows a lot of the
12864    assignment check. */
12865
12866 static int
12867 valid_ref_assignconv_cast_p (source, dest, cast)
12868      tree source;
12869      tree dest;
12870      int cast;
12871 {
12872   /* SOURCE or DEST might be null if not from a declared entity. */
12873   if (!source || !dest)
12874     return 0;
12875   if (JNULLP_TYPE_P (source))
12876     return 1;
12877   if (TREE_CODE (source) == POINTER_TYPE)
12878     source = TREE_TYPE (source);
12879   if (TREE_CODE (dest) == POINTER_TYPE)
12880     dest = TREE_TYPE (dest);
12881
12882   /* If source and dest are being compiled from bytecode, they may need to
12883      be loaded. */
12884   if (CLASS_P (source) && !CLASS_LOADED_P (source))
12885     {
12886       load_class (source, 1);
12887       safe_layout_class (source);
12888     }
12889   if (CLASS_P (dest) && !CLASS_LOADED_P (dest))
12890     {
12891       load_class (dest, 1);
12892       safe_layout_class (dest);
12893     }
12894
12895   /* Case where SOURCE is a class type */
12896   if (TYPE_CLASS_P (source))
12897     {
12898       if (TYPE_CLASS_P (dest))
12899         return  (source == dest 
12900                  || inherits_from_p (source, dest)
12901                  || (cast && inherits_from_p (dest, source)));
12902       if (TYPE_INTERFACE_P (dest))
12903         {
12904           /* If doing a cast and SOURCE is final, the operation is
12905              always correct a compile time (because even if SOURCE
12906              does not implement DEST, a subclass of SOURCE might). */
12907           if (cast && !CLASS_FINAL (TYPE_NAME (source)))
12908             return 1;
12909           /* Otherwise, SOURCE must implement DEST */
12910           return interface_of_p (dest, source);
12911         }
12912       /* DEST is an array, cast permited if SOURCE is of Object type */
12913       return (cast && source == object_type_node ? 1 : 0);
12914     }
12915   if (TYPE_INTERFACE_P (source))
12916     {
12917       if (TYPE_CLASS_P (dest))
12918         {
12919           /* If not casting, DEST must be the Object type */
12920           if (!cast)
12921             return dest == object_type_node;
12922           /* We're doing a cast. The cast is always valid is class
12923              DEST is not final, otherwise, DEST must implement SOURCE */
12924           else if (!CLASS_FINAL (TYPE_NAME (dest)))
12925             return 1;
12926           else
12927             return interface_of_p (source, dest);
12928         }
12929       if (TYPE_INTERFACE_P (dest))
12930         {
12931           /* If doing a cast, then if SOURCE and DEST contain method
12932              with the same signature but different return type, then
12933              this is a (compile time) error */
12934           if (cast)
12935             {
12936               tree method_source, method_dest;
12937               tree source_type;
12938               tree source_sig;
12939               tree source_name;
12940               for (method_source = TYPE_METHODS (source); method_source; 
12941                    method_source = TREE_CHAIN (method_source))
12942                 {
12943                   source_sig = 
12944                     build_java_argument_signature (TREE_TYPE (method_source));
12945                   source_type = TREE_TYPE (TREE_TYPE (method_source));
12946                   source_name = DECL_NAME (method_source);
12947                   for (method_dest = TYPE_METHODS (dest);
12948                        method_dest; method_dest = TREE_CHAIN (method_dest))
12949                     if (source_sig == 
12950                         build_java_argument_signature (TREE_TYPE (method_dest))
12951                         && source_name == DECL_NAME (method_dest)
12952                         && source_type != TREE_TYPE (TREE_TYPE (method_dest)))
12953                       return 0;
12954                 }
12955               return 1;
12956             }
12957           else
12958             return source == dest || interface_of_p (dest, source);
12959         }
12960       else
12961         {
12962           /* Array */
12963           return (cast
12964                   && (DECL_NAME (TYPE_NAME (source)) == java_lang_cloneable
12965                       || (DECL_NAME (TYPE_NAME (source))
12966                           == java_io_serializable)));
12967         }
12968     }
12969   if (TYPE_ARRAY_P (source))
12970     {
12971       if (TYPE_CLASS_P (dest))
12972         return dest == object_type_node;
12973       /* Can't cast an array to an interface unless the interface is
12974          java.lang.Cloneable or java.io.Serializable.  */
12975       if (TYPE_INTERFACE_P (dest))
12976         return (DECL_NAME (TYPE_NAME (dest)) == java_lang_cloneable
12977                 || DECL_NAME (TYPE_NAME (dest)) == java_io_serializable);
12978       else                      /* Arrays */
12979         {
12980           tree source_element_type = TYPE_ARRAY_ELEMENT (source);
12981           tree dest_element_type = TYPE_ARRAY_ELEMENT (dest);
12982           
12983           /* In case of severe errors, they turn out null */
12984           if (!dest_element_type || !source_element_type)
12985             return 0;
12986           if (source_element_type == dest_element_type)
12987             return 1;
12988           return valid_ref_assignconv_cast_p (source_element_type,
12989                                               dest_element_type, cast);
12990         }
12991       return 0;
12992     }
12993   return 0;
12994 }
12995
12996 static int
12997 valid_cast_to_p (source, dest)
12998      tree source;
12999      tree dest;
13000 {
13001   if (TREE_CODE (source) == POINTER_TYPE)
13002     source = TREE_TYPE (source);
13003   if (TREE_CODE (dest) == POINTER_TYPE)
13004     dest = TREE_TYPE (dest);
13005
13006   if (TREE_CODE (source) == RECORD_TYPE && TREE_CODE (dest) == RECORD_TYPE)
13007     return valid_ref_assignconv_cast_p (source, dest, 1);
13008
13009   else if (JNUMERIC_TYPE_P (source) && JNUMERIC_TYPE_P (dest))
13010     return 1;
13011
13012   else if (TREE_CODE (source) == BOOLEAN_TYPE
13013            && TREE_CODE (dest) == BOOLEAN_TYPE)
13014     return 1;
13015
13016   return 0;
13017 }
13018
13019 static tree
13020 do_unary_numeric_promotion (arg)
13021      tree arg;
13022 {
13023   tree type = TREE_TYPE (arg);
13024   if ((TREE_CODE (type) == INTEGER_TYPE && TYPE_PRECISION (type) < 32)
13025       || TREE_CODE (type) == CHAR_TYPE)
13026     arg = convert (int_type_node, arg);
13027   return arg;
13028 }
13029
13030 /* Return a non zero value if SOURCE can be converted into DEST using
13031    the method invocation conversion rule (5.3).  */
13032 static int
13033 valid_method_invocation_conversion_p (dest, source)
13034      tree dest, source;
13035 {
13036   return ((JPRIMITIVE_TYPE_P (source) && JPRIMITIVE_TYPE_P (dest)
13037            && valid_builtin_assignconv_identity_widening_p (dest, source))
13038           || ((JREFERENCE_TYPE_P (source) || JNULLP_TYPE_P (source))
13039               && (JREFERENCE_TYPE_P (dest) || JNULLP_TYPE_P (dest))
13040               && valid_ref_assignconv_cast_p (source, dest, 0)));
13041 }
13042
13043 /* Build an incomplete binop expression. */
13044
13045 static tree
13046 build_binop (op, op_location, op1, op2)
13047      enum tree_code op;
13048      int op_location;
13049      tree op1, op2;
13050 {
13051   tree binop = build (op, NULL_TREE, op1, op2);
13052   TREE_SIDE_EFFECTS (binop) = 1;
13053   /* Store the location of the operator, for better error report. The
13054      string of the operator will be rebuild based on the OP value. */
13055   EXPR_WFL_LINECOL (binop) = op_location;
13056   return binop;
13057 }
13058
13059 /* Build the string of the operator retained by NODE. If NODE is part
13060    of a compound expression, add an '=' at the end of the string. This
13061    function is called when an error needs to be reported on an
13062    operator. The string is returned as a pointer to a static character
13063    buffer. */
13064
13065 static char *
13066 operator_string (node)
13067      tree node;
13068 {
13069 #define BUILD_OPERATOR_STRING(S)                                        \
13070   {                                                                     \
13071     sprintf (buffer, "%s%s", S, (COMPOUND_ASSIGN_P (node) ? "=" : "")); \
13072     return buffer;                                                      \
13073   }
13074   
13075   static char buffer [10];
13076   switch (TREE_CODE (node))
13077     {
13078     case MULT_EXPR: BUILD_OPERATOR_STRING ("*");
13079     case RDIV_EXPR: BUILD_OPERATOR_STRING ("/");
13080     case TRUNC_MOD_EXPR: BUILD_OPERATOR_STRING ("%");
13081     case PLUS_EXPR: BUILD_OPERATOR_STRING ("+");
13082     case MINUS_EXPR: BUILD_OPERATOR_STRING ("-");
13083     case LSHIFT_EXPR: BUILD_OPERATOR_STRING ("<<");
13084     case RSHIFT_EXPR: BUILD_OPERATOR_STRING (">>");
13085     case URSHIFT_EXPR: BUILD_OPERATOR_STRING (">>>");
13086     case BIT_AND_EXPR: BUILD_OPERATOR_STRING ("&");
13087     case BIT_XOR_EXPR: BUILD_OPERATOR_STRING ("^");
13088     case BIT_IOR_EXPR: BUILD_OPERATOR_STRING ("|");
13089     case TRUTH_ANDIF_EXPR: BUILD_OPERATOR_STRING ("&&");
13090     case TRUTH_ORIF_EXPR: BUILD_OPERATOR_STRING ("||");
13091     case EQ_EXPR: BUILD_OPERATOR_STRING ("==");
13092     case NE_EXPR: BUILD_OPERATOR_STRING ("!=");
13093     case GT_EXPR: BUILD_OPERATOR_STRING (">");
13094     case GE_EXPR: BUILD_OPERATOR_STRING (">=");
13095     case LT_EXPR: BUILD_OPERATOR_STRING ("<");
13096     case LE_EXPR: BUILD_OPERATOR_STRING ("<=");
13097     case UNARY_PLUS_EXPR: BUILD_OPERATOR_STRING ("+");
13098     case NEGATE_EXPR: BUILD_OPERATOR_STRING ("-");
13099     case TRUTH_NOT_EXPR: BUILD_OPERATOR_STRING ("!");
13100     case BIT_NOT_EXPR: BUILD_OPERATOR_STRING ("~");
13101     case PREINCREMENT_EXPR:     /* Fall through */
13102     case POSTINCREMENT_EXPR: BUILD_OPERATOR_STRING ("++");
13103     case PREDECREMENT_EXPR:     /* Fall through */
13104     case POSTDECREMENT_EXPR: BUILD_OPERATOR_STRING ("--");
13105     default:
13106       internal_error ("unregistered operator %s",
13107                       tree_code_name [TREE_CODE (node)]);
13108     }
13109   return NULL;
13110 #undef BUILD_OPERATOR_STRING
13111 }
13112
13113 /* Return 1 if VAR_ACCESS1 is equivalent to VAR_ACCESS2.  */
13114
13115 static int
13116 java_decl_equiv (var_acc1, var_acc2)
13117      tree var_acc1, var_acc2;
13118 {
13119   if (JDECL_P (var_acc1))
13120     return (var_acc1 == var_acc2);
13121   
13122   return (TREE_CODE (var_acc1) == COMPONENT_REF
13123           && TREE_CODE (var_acc2) == COMPONENT_REF
13124           && TREE_OPERAND (TREE_OPERAND (var_acc1, 0), 0)
13125              == TREE_OPERAND (TREE_OPERAND (var_acc2, 0), 0)
13126           && TREE_OPERAND (var_acc1, 1) == TREE_OPERAND (var_acc2, 1));
13127 }
13128
13129 /* Return a non zero value if CODE is one of the operators that can be
13130    used in conjunction with the `=' operator in a compound assignment.  */
13131
13132 static int
13133 binop_compound_p (code)
13134     enum tree_code code;
13135 {
13136   int i;
13137   for (i = 0; i < BINOP_COMPOUND_CANDIDATES; i++)
13138     if (binop_lookup [i] == code)
13139       break;
13140
13141   return i < BINOP_COMPOUND_CANDIDATES;
13142 }
13143
13144 /* Reorganize after a fold to get SAVE_EXPR to generate what we want.  */
13145
13146 static tree
13147 java_refold (t)
13148      tree t;
13149 {
13150   tree c, b, ns, decl;
13151
13152   if (TREE_CODE (t) != MODIFY_EXPR)
13153     return t;
13154
13155   c = TREE_OPERAND (t, 1);
13156   if (! (c && TREE_CODE (c) == COMPOUND_EXPR
13157          && TREE_CODE (TREE_OPERAND (c, 0)) == MODIFY_EXPR
13158          && binop_compound_p (TREE_CODE (TREE_OPERAND (c, 1)))))
13159     return t;
13160
13161   /* Now the left branch of the binary operator. */
13162   b = TREE_OPERAND (TREE_OPERAND (c, 1), 0);
13163   if (! (b && TREE_CODE (b) == NOP_EXPR 
13164          && TREE_CODE (TREE_OPERAND (b, 0)) == SAVE_EXPR))
13165     return t;
13166
13167   ns = TREE_OPERAND (TREE_OPERAND (b, 0), 0);
13168   if (! (ns && TREE_CODE (ns) == NOP_EXPR
13169          && TREE_CODE (TREE_OPERAND (ns, 0)) == SAVE_EXPR))
13170     return t;
13171
13172   decl = TREE_OPERAND (TREE_OPERAND (ns, 0), 0);
13173   if ((JDECL_P (decl) || TREE_CODE (decl) == COMPONENT_REF)
13174       /* It's got to be the an equivalent decl */
13175       && java_decl_equiv (decl, TREE_OPERAND (TREE_OPERAND (c, 0), 0)))
13176     {
13177       /* Shorten the NOP_EXPR/SAVE_EXPR path. */
13178       TREE_OPERAND (TREE_OPERAND (c, 1), 0) = TREE_OPERAND (ns, 0);
13179       /* Substitute the COMPOUND_EXPR by the BINOP_EXPR */
13180       TREE_OPERAND (t, 1) = TREE_OPERAND (c, 1);
13181       /* Change the right part of the BINOP_EXPR */
13182       TREE_OPERAND (TREE_OPERAND (t, 1), 1) = TREE_OPERAND (c, 0);
13183     }
13184
13185   return t;
13186 }
13187
13188 /* Binary operators (15.16 up to 15.18). We return error_mark_node on
13189    errors but we modify NODE so that it contains the type computed
13190    according to the expression, when it's fixed. Otherwise, we write
13191    error_mark_node as the type. It allows us to further the analysis
13192    of remaining nodes and detects more errors in certain cases.  */
13193
13194 static tree
13195 patch_binop (node, wfl_op1, wfl_op2)
13196      tree node;
13197      tree wfl_op1;
13198      tree wfl_op2;
13199 {
13200   tree op1 = TREE_OPERAND (node, 0);
13201   tree op2 = TREE_OPERAND (node, 1);
13202   tree op1_type = TREE_TYPE (op1);
13203   tree op2_type = TREE_TYPE (op2);
13204   tree prom_type = NULL_TREE, cn;
13205   enum tree_code code = TREE_CODE (node);
13206
13207   /* If 1, tell the routine that we have to return error_mark_node
13208      after checking for the initialization of the RHS */
13209   int error_found = 0;
13210
13211   EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
13212
13213   /* If either op<n>_type are NULL, this might be early signs of an
13214      error situation, unless it's too early to tell (in case we're
13215      handling a `+', `==', `!=' or `instanceof'.) We want to set op<n>_type
13216      correctly so the error can be later on reported accurately. */
13217   if (! (code == PLUS_EXPR || code == NE_EXPR 
13218          || code == EQ_EXPR || code == INSTANCEOF_EXPR))
13219     {
13220       tree n;
13221       if (! op1_type)
13222         {
13223           n = java_complete_tree (op1);
13224           op1_type = TREE_TYPE (n);
13225         }
13226       if (! op2_type)
13227         {
13228           n = java_complete_tree (op2);
13229           op2_type = TREE_TYPE (n);
13230         }
13231     }
13232
13233   switch (code)
13234     {
13235     /* 15.16 Multiplicative operators */
13236     case MULT_EXPR:             /* 15.16.1 Multiplication Operator * */
13237     case RDIV_EXPR:             /* 15.16.2 Division Operator / */
13238     case TRUNC_DIV_EXPR:        /* 15.16.2 Integral type Division Operator / */
13239     case TRUNC_MOD_EXPR:        /* 15.16.3 Remainder operator % */
13240       if (!JNUMERIC_TYPE_P (op1_type) || !JNUMERIC_TYPE_P (op2_type))
13241         {
13242           if (!JNUMERIC_TYPE_P (op1_type))
13243             ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op1_type);
13244           if (!JNUMERIC_TYPE_P (op2_type) && (op1_type != op2_type))
13245             ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op2_type);
13246           TREE_TYPE (node) = error_mark_node;
13247           error_found = 1;
13248           break;
13249         }
13250       prom_type = binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
13251
13252       /* Detect integral division by zero */
13253       if ((code == RDIV_EXPR || code == TRUNC_MOD_EXPR)
13254           && TREE_CODE (prom_type) == INTEGER_TYPE
13255           && (op2 == integer_zero_node || op2 == long_zero_node ||
13256               (TREE_CODE (op2) == INTEGER_CST &&
13257                ! TREE_INT_CST_LOW (op2)  && ! TREE_INT_CST_HIGH (op2))))
13258         {
13259           parse_warning_context (wfl_operator, "Evaluating this expression will result in an arithmetic exception being thrown");
13260           TREE_CONSTANT (node) = 0;
13261         }
13262           
13263       /* Change the division operator if necessary */
13264       if (code == RDIV_EXPR && TREE_CODE (prom_type) == INTEGER_TYPE)
13265         TREE_SET_CODE (node, TRUNC_DIV_EXPR);
13266
13267       /* Before divisions as is disapear, try to simplify and bail if
13268          applicable, otherwise we won't perform even simple
13269          simplifications like (1-1)/3. We can't do that with floating
13270          point number, folds can't handle them at this stage. */
13271       if (code == RDIV_EXPR && TREE_CONSTANT (op1) && TREE_CONSTANT (op2)
13272           && JINTEGRAL_TYPE_P (op1) && JINTEGRAL_TYPE_P (op2))
13273         {
13274           TREE_TYPE (node) = prom_type;
13275           node = fold (node);
13276           if (TREE_CODE (node) != code)
13277             return node;
13278         }
13279
13280       if (TREE_CODE (prom_type) == INTEGER_TYPE
13281           && flag_use_divide_subroutine
13282           && ! flag_emit_class_files
13283           && (code == RDIV_EXPR || code == TRUNC_MOD_EXPR))
13284         return build_java_soft_divmod (TREE_CODE (node), prom_type, op1, op2);
13285  
13286       /* This one is more complicated. FLOATs are processed by a
13287          function call to soft_fmod. Duplicate the value of the
13288          COMPOUND_ASSIGN_P flag. */
13289       if (code == TRUNC_MOD_EXPR)
13290         {
13291           tree mod = build_java_binop (TRUNC_MOD_EXPR, prom_type, op1, op2);
13292           COMPOUND_ASSIGN_P (mod) = COMPOUND_ASSIGN_P (node);
13293           TREE_SIDE_EFFECTS (mod)
13294             = TREE_SIDE_EFFECTS (op1) | TREE_SIDE_EFFECTS (op2);
13295           return mod;
13296         }
13297       break;
13298
13299     /* 15.17 Additive Operators */
13300     case PLUS_EXPR:             /* 15.17.1 String Concatenation Operator + */
13301
13302       /* Operation is valid if either one argument is a string
13303          constant, a String object or a StringBuffer crafted for the
13304          purpose of the a previous usage of the String concatenation
13305          operator */
13306
13307       if (TREE_CODE (op1) == STRING_CST 
13308           || TREE_CODE (op2) == STRING_CST
13309           || JSTRING_TYPE_P (op1_type)
13310           || JSTRING_TYPE_P (op2_type)
13311           || IS_CRAFTED_STRING_BUFFER_P (op1)
13312           || IS_CRAFTED_STRING_BUFFER_P (op2))
13313         return build_string_concatenation (op1, op2);
13314
13315     case MINUS_EXPR:            /* 15.17.2 Additive Operators (+ and -) for
13316                                    Numeric Types */
13317       if (!JNUMERIC_TYPE_P (op1_type) || !JNUMERIC_TYPE_P (op2_type))
13318         {
13319           if (!JNUMERIC_TYPE_P (op1_type))
13320             ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op1_type);
13321           if (!JNUMERIC_TYPE_P (op2_type) && (op1_type != op2_type))
13322             ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op2_type);
13323           TREE_TYPE (node) = error_mark_node;
13324           error_found = 1;
13325           break;
13326         }
13327       prom_type = binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
13328       break;
13329
13330     /* 15.18 Shift Operators */
13331     case LSHIFT_EXPR:
13332     case RSHIFT_EXPR:
13333     case URSHIFT_EXPR:
13334       if (!JINTEGRAL_TYPE_P (op1_type) || !JINTEGRAL_TYPE_P (op2_type))
13335         {
13336           if (!JINTEGRAL_TYPE_P (op1_type))
13337             ERROR_CAST_NEEDED_TO_INTEGRAL (wfl_operator, node, op1_type);
13338           else
13339             {
13340               if (JNUMERIC_TYPE_P (op2_type))
13341                 parse_error_context (wfl_operator,
13342                                      "Incompatible type for `%s'. Explicit cast needed to convert shift distance from `%s' to integral",
13343                                      operator_string (node),
13344                                      lang_printable_name (op2_type, 0));
13345               else
13346                 parse_error_context (wfl_operator,
13347                                      "Incompatible type for `%s'. Can't convert shift distance from `%s' to integral", 
13348                                      operator_string (node),
13349                                      lang_printable_name (op2_type, 0));
13350             }
13351           TREE_TYPE (node) = error_mark_node;
13352           error_found = 1;
13353           break;
13354         }
13355
13356       /* Unary numeric promotion (5.6.1) is performed on each operand
13357          separately */
13358       op1 = do_unary_numeric_promotion (op1);
13359       op2 = do_unary_numeric_promotion (op2);
13360
13361       /* The type of the shift expression is the type of the promoted
13362          type of the left-hand operand */
13363       prom_type = TREE_TYPE (op1);
13364
13365       /* Shift int only up to 0x1f and long up to 0x3f */
13366       if (prom_type == int_type_node)
13367         op2 = fold (build (BIT_AND_EXPR, int_type_node, op2, 
13368                            build_int_2 (0x1f, 0)));
13369       else
13370         op2 = fold (build (BIT_AND_EXPR, int_type_node, op2, 
13371                            build_int_2 (0x3f, 0)));
13372
13373       /* The >>> operator is a >> operating on unsigned quantities */
13374       if (code == URSHIFT_EXPR && ! flag_emit_class_files)
13375         {
13376           tree to_return;
13377           tree utype = unsigned_type (prom_type);
13378           op1 = convert (utype, op1);
13379           TREE_SET_CODE (node, RSHIFT_EXPR);
13380           TREE_OPERAND (node, 0) = op1;
13381           TREE_OPERAND (node, 1) = op2;
13382           TREE_TYPE (node) = utype;
13383           to_return = convert (prom_type, node);
13384           /* Copy the original value of the COMPOUND_ASSIGN_P flag */
13385           COMPOUND_ASSIGN_P (to_return) = COMPOUND_ASSIGN_P (node);
13386           TREE_SIDE_EFFECTS (to_return)
13387             = TREE_SIDE_EFFECTS (op1) | TREE_SIDE_EFFECTS (op2);
13388           return to_return;
13389         }
13390       break;
13391
13392       /* 15.19.1 Type Comparison Operator instaceof */
13393     case INSTANCEOF_EXPR:
13394
13395       TREE_TYPE (node) = boolean_type_node;
13396
13397       if (!(op2_type = resolve_type_during_patch (op2)))
13398         return error_mark_node;
13399
13400       /* The first operand must be a reference type or the null type */
13401       if (!JREFERENCE_TYPE_P (op1_type) && op1 != null_pointer_node)
13402         error_found = 1;        /* Error reported further below */
13403
13404       /* The second operand must be a reference type */
13405       if (!JREFERENCE_TYPE_P (op2_type))
13406         {
13407           SET_WFL_OPERATOR (wfl_operator, node, wfl_op2);
13408           parse_error_context
13409             (wfl_operator, "Invalid argument `%s' for `instanceof'",
13410              lang_printable_name (op2_type, 0));
13411           error_found = 1;
13412         }
13413
13414       if (!error_found && valid_ref_assignconv_cast_p (op1_type, op2_type, 1))
13415         {
13416           /* If the first operand is null, the result is always false */
13417           if (op1 == null_pointer_node)
13418             return boolean_false_node;
13419           else if (flag_emit_class_files)
13420             {
13421               TREE_OPERAND (node, 1) = op2_type;
13422               TREE_SIDE_EFFECTS (node) = TREE_SIDE_EFFECTS (op1);
13423               return node;
13424             }
13425           /* Otherwise we have to invoke instance of to figure it out */
13426           else
13427             return build_instanceof (op1, op2_type);
13428         }
13429       /* There is no way the expression operand can be an instance of
13430          the type operand. This is a compile time error. */
13431       else
13432         {
13433           char *t1 = xstrdup (lang_printable_name (op1_type, 0));
13434           SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
13435           parse_error_context 
13436             (wfl_operator, "Impossible for `%s' to be instance of `%s'",
13437              t1, lang_printable_name (op2_type, 0));
13438           free (t1);
13439           error_found = 1;
13440         }
13441       
13442       break;
13443
13444       /* 15.21 Bitwise and Logical Operators */
13445     case BIT_AND_EXPR:
13446     case BIT_XOR_EXPR:
13447     case BIT_IOR_EXPR:
13448       if (JINTEGRAL_TYPE_P (op1_type) && JINTEGRAL_TYPE_P (op2_type))
13449         /* Binary numeric promotion is performed on both operand and the
13450            expression retain that type */
13451         prom_type = binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
13452
13453       else if (TREE_CODE (op1_type) == BOOLEAN_TYPE 
13454                && TREE_CODE (op1_type) == BOOLEAN_TYPE)
13455         /* The type of the bitwise operator expression is BOOLEAN */
13456         prom_type = boolean_type_node;
13457       else
13458         {
13459           if (!JINTEGRAL_TYPE_P (op1_type))
13460             ERROR_CAST_NEEDED_TO_INTEGRAL (wfl_operator, node, op1_type);
13461           if (!JINTEGRAL_TYPE_P (op2_type) && (op1_type != op2_type))
13462             ERROR_CAST_NEEDED_TO_INTEGRAL (wfl_operator, node, op2_type);
13463           TREE_TYPE (node) = error_mark_node;
13464           error_found = 1;
13465           /* Insert a break here if adding thing before the switch's
13466              break for this case */
13467         }
13468       break;
13469
13470       /* 15.22 Conditional-And Operator */
13471     case TRUTH_ANDIF_EXPR:
13472       /* 15.23 Conditional-Or Operator */
13473     case TRUTH_ORIF_EXPR:
13474       /* Operands must be of BOOLEAN type */
13475       if (TREE_CODE (op1_type) != BOOLEAN_TYPE || 
13476           TREE_CODE (op2_type) != BOOLEAN_TYPE)
13477         {
13478           if (TREE_CODE (op1_type) != BOOLEAN_TYPE)
13479             ERROR_CANT_CONVERT_TO_BOOLEAN (wfl_operator, node, op1_type);
13480           if (TREE_CODE (op2_type) != BOOLEAN_TYPE && (op1_type != op2_type))
13481             ERROR_CANT_CONVERT_TO_BOOLEAN (wfl_operator, node, op2_type);
13482           TREE_TYPE (node) = boolean_type_node;
13483           error_found = 1;
13484           break;
13485         }
13486       else if (integer_zerop (op1))
13487         {
13488           return code == TRUTH_ANDIF_EXPR ? op1 : op2;
13489         }
13490       else if (integer_onep (op1))
13491         {
13492           return code == TRUTH_ANDIF_EXPR ? op2 : op1;
13493         }
13494       /* The type of the conditional operators is BOOLEAN */
13495       prom_type = boolean_type_node;
13496       break;
13497
13498       /* 15.19.1 Numerical Comparison Operators <, <=, >, >= */
13499     case LT_EXPR:
13500     case GT_EXPR:
13501     case LE_EXPR:
13502     case GE_EXPR:
13503       /* The type of each of the operands must be a primitive numeric
13504          type */
13505       if (!JNUMERIC_TYPE_P (op1_type) || ! JNUMERIC_TYPE_P (op2_type))
13506         {
13507           if (!JNUMERIC_TYPE_P (op1_type))
13508             ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op1_type);
13509           if (!JNUMERIC_TYPE_P (op2_type) && (op1_type != op2_type))
13510             ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op2_type);
13511           TREE_TYPE (node) = boolean_type_node;
13512           error_found = 1;
13513           break;
13514         }
13515       /* Binary numeric promotion is performed on the operands */
13516       binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
13517       /* The type of the relation expression is always BOOLEAN */
13518       prom_type = boolean_type_node;
13519       break;
13520
13521       /* 15.20 Equality Operator */
13522     case EQ_EXPR:
13523     case NE_EXPR:
13524       /* It's time for us to patch the strings. */
13525       if ((cn = patch_string (op1))) 
13526        {
13527          op1 = cn;
13528          op1_type = TREE_TYPE (op1);
13529        }
13530       if ((cn = patch_string (op2))) 
13531        {
13532          op2 = cn;
13533          op2_type = TREE_TYPE (op2);
13534        }
13535       
13536       /* 15.20.1 Numerical Equality Operators == and != */
13537       /* Binary numeric promotion is performed on the operands */
13538       if (JNUMERIC_TYPE_P (op1_type) && JNUMERIC_TYPE_P (op2_type))
13539         binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
13540       
13541       /* 15.20.2 Boolean Equality Operators == and != */
13542       else if (TREE_CODE (op1_type) == BOOLEAN_TYPE &&
13543           TREE_CODE (op2_type) == BOOLEAN_TYPE)
13544         ;                       /* Nothing to do here */
13545       
13546       /* 15.20.3 Reference Equality Operators == and != */
13547       /* Types have to be either references or the null type. If
13548          they're references, it must be possible to convert either
13549          type to the other by casting conversion. */
13550       else if (op1 == null_pointer_node || op2 == null_pointer_node 
13551                || (JREFERENCE_TYPE_P (op1_type) && JREFERENCE_TYPE_P (op2_type)
13552                    && (valid_ref_assignconv_cast_p (op1_type, op2_type, 1)
13553                        || valid_ref_assignconv_cast_p (op2_type, 
13554                                                        op1_type, 1))))
13555         ;                       /* Nothing to do here */
13556           
13557       /* Else we have an error figure what can't be converted into
13558          what and report the error */
13559       else
13560         {
13561           char *t1;
13562           t1 = xstrdup (lang_printable_name (op1_type, 0));
13563           parse_error_context 
13564             (wfl_operator,
13565              "Incompatible type for `%s'. Can't convert `%s' to `%s'",
13566              operator_string (node), t1, 
13567              lang_printable_name (op2_type, 0));
13568           free (t1);
13569           TREE_TYPE (node) = boolean_type_node;
13570           error_found = 1;
13571           break;
13572         }
13573       prom_type = boolean_type_node;
13574       break;
13575     default:
13576       abort ();
13577     }
13578
13579   if (error_found)
13580     return error_mark_node;
13581
13582   TREE_OPERAND (node, 0) = op1;
13583   TREE_OPERAND (node, 1) = op2;
13584   TREE_TYPE (node) = prom_type;
13585   TREE_SIDE_EFFECTS (node) = TREE_SIDE_EFFECTS (op1) | TREE_SIDE_EFFECTS (op2);
13586   
13587   if (flag_emit_xref)
13588     return node;
13589
13590   /* fold does not respect side-effect order as required for Java but not C.
13591    * Also, it sometimes create SAVE_EXPRs which are bad when emitting
13592    * bytecode.
13593    */
13594   if (flag_emit_class_files ? (TREE_CONSTANT (op1) && TREE_CONSTANT (op2))
13595       : ! TREE_SIDE_EFFECTS (node))
13596     node = fold (node);
13597   return node;
13598 }
13599
13600 /* Concatenate the STRING_CST CSTE and STRING. When AFTER is a non
13601    zero value, the value of CSTE comes after the valude of STRING */
13602
13603 static tree
13604 do_merge_string_cste (cste, string, string_len, after)
13605      tree cste;
13606      const char *string;
13607      int string_len, after;
13608 {
13609   const char *old = TREE_STRING_POINTER (cste);
13610   int old_len = TREE_STRING_LENGTH (cste);
13611   int len = old_len + string_len;
13612   char *new = alloca (len+1);
13613
13614   if (after)
13615     {
13616       memcpy (new, string, string_len);
13617       memcpy (&new [string_len], old, old_len);
13618     }
13619   else
13620     {
13621       memcpy (new, old, old_len);
13622       memcpy (&new [old_len], string, string_len);
13623     }
13624   new [len] = '\0';
13625   return build_string (len, new);
13626 }
13627
13628 /* Tries to merge OP1 (a STRING_CST) and OP2 (if suitable). Return a
13629    new STRING_CST on success, NULL_TREE on failure */
13630
13631 static tree
13632 merge_string_cste (op1, op2, after)
13633      tree op1, op2;
13634      int after;
13635 {
13636   /* Handle two string constants right away */
13637   if (TREE_CODE (op2) == STRING_CST)
13638     return do_merge_string_cste (op1, TREE_STRING_POINTER (op2), 
13639                                  TREE_STRING_LENGTH (op2), after);
13640   
13641   /* Reasonable integer constant can be treated right away */
13642   if (TREE_CODE (op2) == INTEGER_CST && !TREE_CONSTANT_OVERFLOW (op2))
13643     {
13644       static const char *const boolean_true = "true";
13645       static const char *const boolean_false = "false";
13646       static const char *const null_pointer = "null";
13647       char ch[3];
13648       const char *string;
13649       
13650       if (op2 == boolean_true_node)
13651         string = boolean_true;
13652       else if (op2 == boolean_false_node)
13653         string = boolean_false;
13654       else if (op2 == null_pointer_node)
13655         string = null_pointer;
13656       else if (TREE_TYPE (op2) == char_type_node)
13657         {
13658           ch[0] = (char )TREE_INT_CST_LOW (op2);
13659           ch[1] = '\0';
13660           string = ch;
13661         }
13662       else
13663           string = print_int_node (op2);
13664       
13665       return do_merge_string_cste (op1, string, strlen (string), after);
13666     }
13667   return NULL_TREE;
13668 }
13669
13670 /* Tries to statically concatenate OP1 and OP2 if possible. Either one
13671    has to be a STRING_CST and the other part must be a STRING_CST or a
13672    INTEGRAL constant. Return a new STRING_CST if the operation
13673    succeed, NULL_TREE otherwise.
13674
13675    If the case we want to optimize for space, we might want to return
13676    NULL_TREE for each invocation of this routine. FIXME */
13677
13678 static tree
13679 string_constant_concatenation (op1, op2)
13680      tree op1, op2;
13681 {
13682   if (TREE_CODE (op1) == STRING_CST || (TREE_CODE (op2) == STRING_CST))
13683     {
13684       tree string, rest;
13685       int invert;
13686       
13687       string = (TREE_CODE (op1) == STRING_CST ? op1 : op2);
13688       rest   = (string == op1 ? op2 : op1);
13689       invert = (string == op1 ? 0 : 1 );
13690       
13691       /* Walk REST, only if it looks reasonable */
13692       if (TREE_CODE (rest) != STRING_CST
13693           && !IS_CRAFTED_STRING_BUFFER_P (rest)
13694           && !JSTRING_TYPE_P (TREE_TYPE (rest))
13695           && TREE_CODE (rest) == EXPR_WITH_FILE_LOCATION)
13696         {
13697           rest = java_complete_tree (rest);
13698           if (rest == error_mark_node)
13699             return error_mark_node;
13700           rest = fold (rest);
13701         }
13702       return merge_string_cste (string, rest, invert);
13703     }
13704   return NULL_TREE;
13705 }
13706
13707 /* Implement the `+' operator. Does static optimization if possible,
13708    otherwise create (if necessary) and append elements to a
13709    StringBuffer. The StringBuffer will be carried around until it is
13710    used for a function call or an assignment. Then toString() will be
13711    called on it to turn it into a String object. */
13712
13713 static tree
13714 build_string_concatenation (op1, op2)
13715      tree op1, op2;
13716 {
13717   tree result;
13718   int side_effects = TREE_SIDE_EFFECTS (op1) | TREE_SIDE_EFFECTS (op2);
13719
13720   if (flag_emit_xref)
13721     return build (PLUS_EXPR, string_type_node, op1, op2);
13722   
13723   /* Try to do some static optimization */
13724   if ((result = string_constant_concatenation (op1, op2)))
13725     return result;
13726
13727   /* Discard empty strings on either side of the expression */
13728   if (TREE_CODE (op1) == STRING_CST && TREE_STRING_LENGTH (op1) == 0)
13729     {
13730       op1 = op2;
13731       op2 = NULL_TREE;
13732     }
13733   else if (TREE_CODE (op2) == STRING_CST && TREE_STRING_LENGTH (op2) == 0)
13734     op2 = NULL_TREE;
13735
13736   /* If operands are string constant, turn then into object references */
13737   if (TREE_CODE (op1) == STRING_CST)
13738     op1 = patch_string_cst (op1);
13739   if (op2 && TREE_CODE (op2) == STRING_CST)
13740     op2 = patch_string_cst (op2);
13741
13742   /* If either one of the constant is null and the other non null
13743      operand is a String object, return it. */
13744   if (JSTRING_TYPE_P (TREE_TYPE (op1)) && !op2)
13745     return op1;
13746
13747   /* If OP1 isn't already a StringBuffer, create and
13748      initialize a new one */
13749   if (!IS_CRAFTED_STRING_BUFFER_P (op1))
13750     {
13751       /* Two solutions here: 
13752          1) OP1 is a constant string reference, we call new StringBuffer(OP1)
13753          2) OP1 is something else, we call new StringBuffer().append(OP1).  */
13754       if (TREE_CONSTANT (op1) && JSTRING_TYPE_P (TREE_TYPE (op1)))
13755         op1 = BUILD_STRING_BUFFER (op1);
13756       else
13757         {
13758           tree aNew = BUILD_STRING_BUFFER (NULL_TREE);
13759           op1 = make_qualified_primary (aNew, BUILD_APPEND (op1), 0);
13760         }
13761     }
13762
13763   if (op2)
13764     {
13765       /* OP1 is no longer the last node holding a crafted StringBuffer */
13766       IS_CRAFTED_STRING_BUFFER_P (op1) = 0;
13767       /* Create a node for `{new...,xxx}.append (op2)' */
13768       if (op2)
13769         op1 = make_qualified_primary (op1, BUILD_APPEND (op2), 0);
13770     }
13771
13772   /* Mark the last node holding a crafted StringBuffer */
13773   IS_CRAFTED_STRING_BUFFER_P (op1) = 1;
13774
13775   TREE_SIDE_EFFECTS (op1) = side_effects;
13776   return op1;
13777 }
13778
13779 /* Patch the string node NODE. NODE can be a STRING_CST of a crafted
13780    StringBuffer. If no string were found to be patched, return
13781    NULL. */
13782
13783 static tree
13784 patch_string (node)
13785     tree node;
13786 {
13787   if (node == error_mark_node)
13788     return error_mark_node;
13789   if (TREE_CODE (node) == STRING_CST)
13790     return patch_string_cst (node);
13791   else if (IS_CRAFTED_STRING_BUFFER_P (node))
13792     {
13793       int saved = ctxp->explicit_constructor_p;
13794       tree invoke = build_method_invocation (wfl_to_string, NULL_TREE);
13795       tree ret;
13796       /* Temporary disable forbid the use of `this'. */
13797       ctxp->explicit_constructor_p = 0;
13798       ret = java_complete_tree (make_qualified_primary (node, invoke, 0));
13799       /* String concatenation arguments must be evaluated in order too. */
13800       ret = force_evaluation_order (ret);
13801       /* Restore it at its previous value */
13802       ctxp->explicit_constructor_p = saved;
13803       return ret;
13804     }
13805   return NULL_TREE;
13806 }
13807
13808 /* Build the internal representation of a string constant.  */
13809
13810 static tree
13811 patch_string_cst (node)
13812      tree node;
13813 {
13814   int location;
13815   if (! flag_emit_class_files)
13816     {
13817       node = get_identifier (TREE_STRING_POINTER (node));
13818       location = alloc_name_constant (CONSTANT_String, node);
13819       node = build_ref_from_constant_pool (location);
13820     }
13821   TREE_TYPE (node) = string_ptr_type_node;
13822   TREE_CONSTANT (node) = 1;
13823   return node;
13824 }
13825
13826 /* Build an incomplete unary operator expression. */
13827
13828 static tree
13829 build_unaryop (op_token, op_location, op1)
13830      int op_token, op_location;
13831      tree op1;
13832 {
13833   enum tree_code op;
13834   tree unaryop;
13835   switch (op_token)
13836     {
13837     case PLUS_TK: op = UNARY_PLUS_EXPR; break;
13838     case MINUS_TK: op = NEGATE_EXPR; break;
13839     case NEG_TK: op = TRUTH_NOT_EXPR; break;
13840     case NOT_TK: op = BIT_NOT_EXPR; break;
13841     default: abort ();
13842     }
13843
13844   unaryop = build1 (op, NULL_TREE, op1);
13845   TREE_SIDE_EFFECTS (unaryop) = 1;
13846   /* Store the location of the operator, for better error report. The
13847      string of the operator will be rebuild based on the OP value. */
13848   EXPR_WFL_LINECOL (unaryop) = op_location;
13849   return unaryop;
13850 }
13851
13852 /* Special case for the ++/-- operators, since they require an extra
13853    argument to build, which is set to NULL and patched
13854    later. IS_POST_P is 1 if the operator, 0 otherwise.  */
13855
13856 static tree
13857 build_incdec (op_token, op_location, op1, is_post_p)
13858      int op_token, op_location;
13859      tree op1;
13860      int is_post_p;
13861 {
13862   static const enum tree_code lookup [2][2] = 
13863     {
13864       { PREDECREMENT_EXPR, PREINCREMENT_EXPR, },
13865       { POSTDECREMENT_EXPR, POSTINCREMENT_EXPR, },
13866     };
13867   tree node = build (lookup [is_post_p][(op_token - DECR_TK)], 
13868                      NULL_TREE, op1, NULL_TREE);
13869   TREE_SIDE_EFFECTS (node) = 1;
13870   /* Store the location of the operator, for better error report. The
13871      string of the operator will be rebuild based on the OP value. */
13872   EXPR_WFL_LINECOL (node) = op_location;
13873   return node;
13874 }     
13875
13876 /* Build an incomplete cast operator, based on the use of the
13877    CONVERT_EXPR. Note that TREE_TYPE of the constructed node is
13878    set. java_complete_tree is trained to walk a CONVERT_EXPR even
13879    though its type is already set.  */
13880
13881 static tree
13882 build_cast (location, type, exp)
13883      int location;
13884      tree type, exp;
13885 {
13886   tree node = build1 (CONVERT_EXPR, type, exp);
13887   EXPR_WFL_LINECOL (node) = location;
13888   return node;
13889 }
13890
13891 /* Build an incomplete class reference operator.  */
13892 static tree
13893 build_incomplete_class_ref (location, class_name)
13894     int location;
13895     tree class_name;
13896 {
13897   tree node = build1 (CLASS_LITERAL, NULL_TREE, class_name);
13898   EXPR_WFL_LINECOL (node) = location;
13899   return node;
13900 }
13901
13902 /* Complete an incomplete class reference operator.  */
13903 static tree
13904 patch_incomplete_class_ref (node)
13905     tree node;
13906 {
13907   tree type = TREE_OPERAND (node, 0);
13908   tree ref_type;
13909
13910   if (!(ref_type = resolve_type_during_patch (type)))
13911     return error_mark_node;
13912
13913   if (!flag_emit_class_files || JPRIMITIVE_TYPE_P (ref_type))
13914     {
13915       tree dot = build_class_ref (ref_type);
13916       /* A class referenced by `foo.class' is initialized.  */
13917       if (!flag_emit_class_files)
13918        dot = build_class_init (ref_type, dot);
13919       return java_complete_tree (dot);
13920     }
13921
13922   /* If we're emitting class files and we have to deal with non
13923      primitive types, we invoke (and consider generating) the
13924      synthetic static method `class$'. */
13925   if (!TYPE_DOT_CLASS (current_class))
13926       build_dot_class_method (current_class);
13927   ref_type = build_dot_class_method_invocation (ref_type);
13928   return java_complete_tree (ref_type);
13929 }
13930
13931 /* 15.14 Unary operators. We return error_mark_node in case of error,
13932    but preserve the type of NODE if the type is fixed.  */
13933
13934 static tree
13935 patch_unaryop (node, wfl_op)
13936      tree node;
13937      tree wfl_op;
13938 {
13939   tree op = TREE_OPERAND (node, 0);
13940   tree op_type = TREE_TYPE (op);
13941   tree prom_type = NULL_TREE, value, decl;
13942   int outer_field_flag = 0;
13943   int code = TREE_CODE (node);
13944   int error_found = 0;
13945
13946   EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
13947
13948   switch (code)
13949     {
13950       /* 15.13.2 Postfix Increment Operator ++ */
13951     case POSTINCREMENT_EXPR:
13952       /* 15.13.3 Postfix Increment Operator -- */
13953     case POSTDECREMENT_EXPR:
13954       /* 15.14.1 Prefix Increment Operator ++ */
13955     case PREINCREMENT_EXPR:
13956       /* 15.14.2 Prefix Decrement Operator -- */
13957     case PREDECREMENT_EXPR:
13958       op = decl = strip_out_static_field_access_decl (op);
13959       outer_field_flag = outer_field_expanded_access_p (op, NULL, NULL, NULL);
13960       /* We might be trying to change an outer field accessed using
13961          access method. */
13962       if (outer_field_flag)
13963         {
13964           /* Retrieve the decl of the field we're trying to access. We
13965              do that by first retrieving the function we would call to
13966              access the field. It has been already verified that this
13967              field isn't final */
13968           if (flag_emit_class_files)
13969             decl = TREE_OPERAND (op, 0);
13970           else
13971             decl = TREE_OPERAND (TREE_OPERAND (TREE_OPERAND (op, 0), 0), 0);
13972           decl = DECL_FUNCTION_ACCESS_DECL (decl);
13973         }
13974       /* We really should have a JAVA_ARRAY_EXPR to avoid this */
13975       else if (!JDECL_P (decl) 
13976           && TREE_CODE (decl) != COMPONENT_REF
13977           && !(flag_emit_class_files && TREE_CODE (decl) == ARRAY_REF)
13978           && TREE_CODE (decl) != INDIRECT_REF
13979           && !(TREE_CODE (decl) == COMPOUND_EXPR
13980                && TREE_OPERAND (decl, 1)
13981                && (TREE_CODE (TREE_OPERAND (decl, 1)) == INDIRECT_REF)))
13982         {
13983           TREE_TYPE (node) = error_mark_node;
13984           error_found = 1;
13985         }
13986       
13987       /* From now on, we know that op if a variable and that it has a
13988          valid wfl. We use wfl_op to locate errors related to the
13989          ++/-- operand. */
13990       if (!JNUMERIC_TYPE_P (op_type))
13991         {
13992           parse_error_context
13993             (wfl_op, "Invalid argument type `%s' to `%s'",
13994              lang_printable_name (op_type, 0), operator_string (node));
13995           TREE_TYPE (node) = error_mark_node;
13996           error_found = 1;
13997         }
13998       else
13999         {
14000           /* Before the addition, binary numeric promotion is performed on
14001              both operands, if really necessary */
14002           if (JINTEGRAL_TYPE_P (op_type))
14003             {
14004               value = build_int_2 (1, 0);
14005               TREE_TYPE (value) = TREE_TYPE (node) = op_type;
14006             }
14007           else
14008             {
14009               value = build_int_2 (1, 0);
14010               TREE_TYPE (node) = 
14011                 binary_numeric_promotion (op_type, 
14012                                           TREE_TYPE (value), &op, &value);
14013             }
14014
14015           /* We remember we might be accessing an outer field */
14016           if (outer_field_flag)
14017             {
14018               /* We re-generate an access to the field */
14019               value = build (PLUS_EXPR, TREE_TYPE (op), 
14020                              build_outer_field_access (wfl_op, decl), value);
14021                                                     
14022               /* And we patch the original access$() into a write 
14023                  with plus_op as a rhs */
14024               return outer_field_access_fix (node, op, value);
14025             }
14026
14027           /* And write back into the node. */
14028           TREE_OPERAND (node, 0) = op;
14029           TREE_OPERAND (node, 1) = value;
14030           /* Convert the overall back into its original type, if
14031              necessary, and return */
14032           if (JINTEGRAL_TYPE_P (op_type))
14033             return fold (node);
14034           else
14035             return fold (convert (op_type, node));
14036         }
14037       break;
14038
14039       /* 15.14.3 Unary Plus Operator + */
14040     case UNARY_PLUS_EXPR:
14041       /* 15.14.4 Unary Minus Operator - */
14042     case NEGATE_EXPR:
14043       if (!JNUMERIC_TYPE_P (op_type))
14044         {
14045           ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op_type);
14046           TREE_TYPE (node) = error_mark_node;
14047           error_found = 1;
14048         }
14049       /* Unary numeric promotion is performed on operand */
14050       else
14051         {
14052           op = do_unary_numeric_promotion (op);
14053           prom_type = TREE_TYPE (op);
14054           if (code == UNARY_PLUS_EXPR)
14055             return fold (op);
14056         }
14057       break;
14058
14059       /* 15.14.5 Bitwise Complement Operator ~ */
14060     case BIT_NOT_EXPR:
14061       if (!JINTEGRAL_TYPE_P (op_type))
14062         {
14063           ERROR_CAST_NEEDED_TO_INTEGRAL (wfl_operator, node, op_type);
14064           TREE_TYPE (node) = error_mark_node;
14065           error_found = 1;
14066         }
14067       else
14068         {
14069           op = do_unary_numeric_promotion (op);
14070           prom_type = TREE_TYPE (op);
14071         }
14072       break;
14073
14074       /* 15.14.6 Logical Complement Operator ! */
14075     case TRUTH_NOT_EXPR:
14076       if (TREE_CODE (op_type) != BOOLEAN_TYPE)
14077         {
14078           ERROR_CANT_CONVERT_TO_BOOLEAN (wfl_operator, node, op_type);
14079           /* But the type is known. We will report an error if further
14080              attempt of a assignment is made with this rhs */
14081           TREE_TYPE (node) = boolean_type_node;
14082           error_found = 1;
14083         }
14084       else
14085         prom_type = boolean_type_node;
14086       break;
14087
14088       /* 15.15 Cast Expression */
14089     case CONVERT_EXPR:
14090       value = patch_cast (node, wfl_operator);
14091       if (value == error_mark_node)
14092         {
14093           /* If this cast is part of an assignment, we tell the code
14094              that deals with it not to complain about a mismatch,
14095              because things have been cast, anyways */
14096           TREE_TYPE (node) = error_mark_node;
14097           error_found = 1;
14098         }
14099       else
14100         {
14101           value = fold (value);
14102           TREE_SIDE_EFFECTS (value) = TREE_SIDE_EFFECTS (op);
14103           return value;
14104         }
14105       break;
14106     }
14107   
14108   if (error_found)
14109     return error_mark_node;
14110
14111   /* There are cases where node has been replaced by something else
14112      and we don't end up returning here: UNARY_PLUS_EXPR,
14113      CONVERT_EXPR, {POST,PRE}{INCR,DECR}EMENT_EXPR. */
14114   TREE_OPERAND (node, 0) = fold (op);
14115   TREE_TYPE (node) = prom_type;
14116   TREE_SIDE_EFFECTS (node) = TREE_SIDE_EFFECTS (op);
14117   return fold (node);
14118 }
14119
14120 /* Generic type resolution that sometimes takes place during node
14121    patching. Returned the resolved type or generate an error
14122    message. Return the resolved type or NULL_TREE.  */
14123
14124 static tree
14125 resolve_type_during_patch (type)
14126      tree type;
14127 {
14128   if (unresolved_type_p (type, NULL))
14129     {
14130       tree type_decl = resolve_and_layout (EXPR_WFL_NODE (type), type);
14131       if (!type_decl)
14132         {
14133           parse_error_context (type, 
14134                                "Class `%s' not found in type declaration",
14135                                IDENTIFIER_POINTER (EXPR_WFL_NODE (type)));
14136           return NULL_TREE;
14137         }
14138       return TREE_TYPE (type_decl);
14139     }
14140   return type;
14141 }
14142 /* 5.5 Casting Conversion. error_mark_node is returned if an error is
14143    found. Otherwise NODE or something meant to replace it is returned.  */
14144
14145 static tree
14146 patch_cast (node, wfl_op)
14147      tree node;
14148      tree wfl_op;
14149 {
14150   tree op = TREE_OPERAND (node, 0);
14151   tree cast_type = TREE_TYPE (node);
14152   tree patched, op_type;
14153   char *t1;
14154
14155   /* Some string patching might be necessary at this stage */
14156   if ((patched = patch_string (op)))
14157     TREE_OPERAND (node, 0) = op = patched;
14158   op_type = TREE_TYPE (op);
14159
14160   /* First resolve OP_TYPE if unresolved */
14161   if (!(cast_type = resolve_type_during_patch (cast_type)))
14162     return error_mark_node;
14163
14164   /* Check on cast that are proven correct at compile time */
14165   if (JNUMERIC_TYPE_P (cast_type) && JNUMERIC_TYPE_P (op_type))
14166     {
14167       /* Same type */
14168       if (cast_type == op_type)
14169         return node;
14170
14171       /* float and double type are converted to the original type main
14172          variant and then to the target type. */
14173       if (JFLOAT_TYPE_P (op_type) && TREE_CODE (cast_type) == CHAR_TYPE)
14174         op = convert (integer_type_node, op);
14175
14176       /* Try widening/narowwing convertion. Potentially, things need
14177          to be worked out in gcc so we implement the extreme cases
14178          correctly. fold_convert() needs to be fixed. */
14179       return convert (cast_type, op);
14180     }
14181
14182   /* It's also valid to cast a boolean into a boolean */
14183   if (op_type == boolean_type_node && cast_type == boolean_type_node)
14184     return node;
14185
14186   /* null can be casted to references */
14187   if (op == null_pointer_node && JREFERENCE_TYPE_P (cast_type))
14188     return build_null_of_type (cast_type);
14189
14190   /* The remaining legal casts involve conversion between reference
14191      types. Check for their compile time correctness. */
14192   if (JREFERENCE_TYPE_P (op_type) && JREFERENCE_TYPE_P (cast_type) 
14193       && valid_ref_assignconv_cast_p (op_type, cast_type, 1))
14194     {
14195       TREE_TYPE (node) = promote_type (cast_type);
14196       /* Now, the case can be determined correct at compile time if
14197          OP_TYPE can be converted into CAST_TYPE by assignment
14198          conversion (5.2) */
14199
14200       if (valid_ref_assignconv_cast_p (op_type, cast_type, 0))
14201         {
14202           TREE_SET_CODE (node, NOP_EXPR);
14203           return node;
14204         }
14205
14206       if (flag_emit_class_files)
14207         {
14208           TREE_SET_CODE (node, CONVERT_EXPR);
14209           return node;
14210         }
14211
14212       /* The cast requires a run-time check */
14213       return build (CALL_EXPR, promote_type (cast_type),
14214                     build_address_of (soft_checkcast_node),
14215                     tree_cons (NULL_TREE, build_class_ref (cast_type),
14216                                build_tree_list (NULL_TREE, op)),
14217                     NULL_TREE);
14218     }
14219
14220   /* Any other casts are proven incorrect at compile time */
14221   t1 = xstrdup (lang_printable_name (op_type, 0));
14222   parse_error_context (wfl_op, "Invalid cast from `%s' to `%s'",
14223                        t1, lang_printable_name (cast_type, 0));
14224   free (t1);
14225   return error_mark_node;
14226 }
14227
14228 /* Build a null constant and give it the type TYPE.  */
14229
14230 static tree
14231 build_null_of_type (type)
14232      tree type;
14233 {
14234   tree node = build_int_2 (0, 0);
14235   TREE_TYPE (node) = promote_type (type);
14236   return node;
14237 }
14238
14239 /* Build an ARRAY_REF incomplete tree node. Note that operand 1 isn't
14240    a list of indices. */
14241 static tree
14242 build_array_ref (location, array, index)
14243      int location;
14244      tree array, index;
14245 {
14246   tree node = build (ARRAY_REF, NULL_TREE, array, index);
14247   EXPR_WFL_LINECOL (node) = location;
14248   return node;
14249 }
14250
14251 /* 15.12 Array Access Expression */
14252
14253 static tree
14254 patch_array_ref (node)
14255      tree node;
14256 {
14257   tree array = TREE_OPERAND (node, 0);
14258   tree array_type  = TREE_TYPE (array);
14259   tree index = TREE_OPERAND (node, 1);
14260   tree index_type = TREE_TYPE (index);
14261   int error_found = 0;
14262
14263   EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
14264
14265   if (TREE_CODE (array_type) == POINTER_TYPE)
14266     array_type = TREE_TYPE (array_type);
14267
14268   /* The array reference must be an array */
14269   if (!TYPE_ARRAY_P (array_type))
14270     {
14271       parse_error_context 
14272         (wfl_operator,
14273          "`[]' can only be applied to arrays. It can't be applied to `%s'",
14274          lang_printable_name (array_type, 0));
14275       TREE_TYPE (node) = error_mark_node;
14276       error_found = 1;
14277     }
14278
14279   /* The array index undergoes unary numeric promotion. The promoted
14280      type must be int */
14281   index = do_unary_numeric_promotion (index);
14282   if (TREE_TYPE (index) != int_type_node)
14283     {
14284       if (valid_cast_to_p (index_type, int_type_node))
14285         parse_error_context (wfl_operator,
14286    "Incompatible type for `[]'. Explicit cast needed to convert `%s' to `int'",
14287                              lang_printable_name (index_type, 0));
14288       else
14289         parse_error_context (wfl_operator,
14290           "Incompatible type for `[]'. Can't convert `%s' to `int'",
14291                              lang_printable_name (index_type, 0));
14292       TREE_TYPE (node) = error_mark_node;
14293       error_found = 1;
14294     }
14295
14296   if (error_found)
14297     return error_mark_node;
14298
14299   array_type = TYPE_ARRAY_ELEMENT (array_type);
14300
14301   if (flag_emit_class_files || flag_emit_xref)
14302     {
14303       TREE_OPERAND (node, 0) = array;
14304       TREE_OPERAND (node, 1) = index;
14305     }
14306   else
14307     node = build_java_arrayaccess (array, array_type, index);
14308   TREE_TYPE (node) = array_type;
14309   return node;
14310 }
14311
14312 /* 15.9 Array Creation Expressions */
14313
14314 static tree
14315 build_newarray_node (type, dims, extra_dims)
14316      tree type;
14317      tree dims;
14318      int extra_dims;
14319 {
14320   tree node =
14321     build (NEW_ARRAY_EXPR, NULL_TREE, type, nreverse (dims), 
14322            build_int_2 (extra_dims, 0));
14323   return node;
14324 }
14325
14326 static tree
14327 patch_newarray (node)
14328      tree node;
14329 {
14330   tree type = TREE_OPERAND (node, 0);
14331   tree dims = TREE_OPERAND (node, 1);
14332   tree cdim, array_type;
14333   int error_found = 0;
14334   int ndims = 0;
14335   int xdims = TREE_INT_CST_LOW (TREE_OPERAND (node, 2));
14336
14337   /* Dimension types are verified. It's better for the types to be
14338      verified in order. */
14339   for (cdim = dims, ndims = 0; cdim; cdim = TREE_CHAIN (cdim), ndims++ )
14340     {
14341       int dim_error = 0;
14342       tree dim = TREE_VALUE (cdim);
14343
14344       /* Dim might have been saved during its evaluation */
14345       dim = (TREE_CODE (dim) == SAVE_EXPR ? TREE_OPERAND (dim, 0) : dim);
14346
14347       /* The type of each specified dimension must be an integral type. */
14348       if (!JINTEGRAL_TYPE_P (TREE_TYPE (dim)))
14349         dim_error = 1;
14350
14351       /* Each expression undergoes an unary numeric promotion (5.6.1) and the
14352          promoted type must be int. */
14353       else
14354         {
14355           dim = do_unary_numeric_promotion (dim);
14356           if (TREE_TYPE (dim) != int_type_node)
14357             dim_error = 1;
14358         }
14359
14360       /* Report errors on types here */
14361       if (dim_error)
14362         {
14363           parse_error_context 
14364             (TREE_PURPOSE (cdim), 
14365              "Incompatible type for dimension in array creation expression. %s convert `%s' to `int'", 
14366              (valid_cast_to_p (TREE_TYPE (dim), int_type_node) ?
14367               "Explicit cast needed to" : "Can't"),
14368              lang_printable_name (TREE_TYPE (dim), 0));
14369           error_found = 1;
14370         }
14371
14372       TREE_PURPOSE (cdim) = NULL_TREE;
14373     }
14374
14375   /* Resolve array base type if unresolved */
14376   if (!(type = resolve_type_during_patch (type)))
14377     error_found = 1;
14378
14379   if (error_found)
14380     {
14381       /* We don't want further evaluation of this bogus array creation
14382          operation */
14383       TREE_TYPE (node) = error_mark_node;
14384       return error_mark_node;
14385     }
14386
14387   /* Set array_type to the actual (promoted) array type of the result. */
14388   if (TREE_CODE (type) == RECORD_TYPE)
14389     type = build_pointer_type (type);
14390   while (--xdims >= 0)
14391     {
14392       type = promote_type (build_java_array_type (type, -1));
14393     }
14394   dims = nreverse (dims);
14395   array_type = type;
14396   for (cdim = dims; cdim; cdim = TREE_CHAIN (cdim))
14397     {
14398       type = array_type;
14399       array_type
14400         = build_java_array_type (type,
14401                                  TREE_CODE (cdim) == INTEGER_CST
14402                                  ? (HOST_WIDE_INT) TREE_INT_CST_LOW (cdim)
14403                                  : -1);
14404       array_type = promote_type (array_type);
14405     }
14406   dims = nreverse (dims);
14407
14408   /* The node is transformed into a function call. Things are done
14409      differently according to the number of dimensions. If the number
14410      of dimension is equal to 1, then the nature of the base type
14411      (primitive or not) matters. */
14412   if (ndims == 1)
14413     return build_new_array (type, TREE_VALUE (dims));
14414   
14415   /* Can't reuse what's already written in expr.c because it uses the
14416      JVM stack representation. Provide a build_multianewarray. FIXME */
14417   return build (CALL_EXPR, array_type,
14418                 build_address_of (soft_multianewarray_node),
14419                 tree_cons (NULL_TREE, build_class_ref (TREE_TYPE (array_type)),
14420                            tree_cons (NULL_TREE, 
14421                                       build_int_2 (ndims, 0), dims )),
14422                 NULL_TREE);
14423 }
14424
14425 /* 10.6 Array initializer.  */
14426
14427 /* Build a wfl for array element that don't have one, so we can
14428    pin-point errors.  */
14429
14430 static tree
14431 maybe_build_array_element_wfl (node)
14432      tree node;
14433 {
14434   if (TREE_CODE (node) != EXPR_WITH_FILE_LOCATION)
14435     return build_expr_wfl (NULL_TREE, ctxp->filename,
14436                            ctxp->elc.line, ctxp->elc.prev_col);
14437   else
14438     return NULL_TREE;
14439 }
14440
14441 /* Build a NEW_ARRAY_INIT that features a CONSTRUCTOR node. This makes
14442    identification of initialized arrays easier to detect during walk
14443    and expansion.  */
14444
14445 static tree
14446 build_new_array_init (location, values)
14447      int location;
14448      tree values;
14449 {
14450   tree constructor = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, values);
14451   tree to_return = build1 (NEW_ARRAY_INIT, NULL_TREE, constructor);
14452   EXPR_WFL_LINECOL (to_return) = location;
14453   return to_return;
14454 }
14455
14456 /* Expand a NEW_ARRAY_INIT node. Return error_mark_node if an error
14457    occurred.  Otherwise return NODE after having set its type
14458    appropriately.  */
14459
14460 static tree
14461 patch_new_array_init (type, node)
14462      tree type, node;
14463 {
14464   int error_seen = 0;
14465   tree current, element_type;
14466   HOST_WIDE_INT length;
14467   int all_constant = 1;
14468   tree init = TREE_OPERAND (node, 0);
14469
14470   if (TREE_CODE (type) != POINTER_TYPE || ! TYPE_ARRAY_P (TREE_TYPE (type)))
14471     {
14472       parse_error_context (node,
14473                            "Invalid array initializer for non-array type `%s'",
14474                            lang_printable_name (type, 1));
14475       return error_mark_node;
14476     }
14477   type = TREE_TYPE (type);
14478   element_type = TYPE_ARRAY_ELEMENT (type);
14479
14480   CONSTRUCTOR_ELTS (init) = nreverse (CONSTRUCTOR_ELTS (init));
14481
14482   for (length = 0, current = CONSTRUCTOR_ELTS (init);
14483        current;  length++, current = TREE_CHAIN (current))
14484     {
14485       tree elt = TREE_VALUE (current);
14486       if (elt == NULL_TREE || TREE_CODE (elt) != NEW_ARRAY_INIT)
14487         {
14488           error_seen |= array_constructor_check_entry (element_type, current);
14489           elt = TREE_VALUE (current);
14490           /* When compiling to native code, STRING_CST is converted to
14491              INDIRECT_REF, but still with a TREE_CONSTANT flag. */
14492           if (! TREE_CONSTANT (elt) || TREE_CODE (elt) == INDIRECT_REF)
14493             all_constant = 0;
14494         }
14495       else
14496         {
14497           TREE_VALUE (current) = patch_new_array_init (element_type, elt);
14498           TREE_PURPOSE (current) = NULL_TREE;
14499           all_constant = 0;
14500         }
14501       if (elt && TREE_CODE (elt) == TREE_LIST 
14502           && TREE_VALUE (elt) == error_mark_node)
14503         error_seen = 1;
14504     }
14505
14506   if (error_seen)
14507     return error_mark_node;
14508
14509   /* Create a new type. We can't reuse the one we have here by
14510      patching its dimension because it originally is of dimension -1
14511      hence reused by gcc. This would prevent triangular arrays. */
14512   type = build_java_array_type (element_type, length);
14513   TREE_TYPE (init) = TREE_TYPE (TREE_CHAIN (TREE_CHAIN (TYPE_FIELDS (type))));
14514   TREE_TYPE (node) = promote_type (type);
14515   TREE_CONSTANT (init) = all_constant;
14516   TREE_CONSTANT (node) = all_constant;
14517   return node;
14518 }
14519
14520 /* Verify that one entry of the initializer element list can be
14521    assigned to the array base type. Report 1 if an error occurred, 0
14522    otherwise.  */
14523
14524 static int
14525 array_constructor_check_entry (type, entry)
14526      tree type, entry;
14527 {
14528   char *array_type_string = NULL;       /* For error reports */
14529   tree value, type_value, new_value, wfl_value, patched;
14530   int error_seen = 0;
14531
14532   new_value = NULL_TREE;
14533   wfl_value = TREE_VALUE (entry);
14534
14535   value = java_complete_tree (TREE_VALUE (entry));
14536   /* patch_string return error_mark_node if arg is error_mark_node */
14537   if ((patched = patch_string (value)))
14538     value = patched;
14539   if (value == error_mark_node)
14540     return 1;
14541   
14542   type_value = TREE_TYPE (value);
14543   
14544   /* At anytime, try_builtin_assignconv can report a warning on
14545      constant overflow during narrowing. */
14546   SET_WFL_OPERATOR (wfl_operator, TREE_PURPOSE (entry), wfl_value);
14547   new_value = try_builtin_assignconv (wfl_operator, type, value);
14548   if (!new_value && (new_value = try_reference_assignconv (type, value)))
14549     type_value = promote_type (type);
14550
14551   /* Check and report errors */
14552   if (!new_value)
14553     {
14554       const char *const msg = (!valid_cast_to_p (type_value, type) ?
14555                    "Can't" : "Explicit cast needed to");
14556       if (!array_type_string)
14557         array_type_string = xstrdup (lang_printable_name (type, 1));
14558       parse_error_context 
14559         (wfl_operator, "Incompatible type for array. %s convert `%s' to `%s'",
14560          msg, lang_printable_name (type_value, 1), array_type_string);
14561       error_seen = 1;
14562     }
14563   
14564   if (new_value)
14565     TREE_VALUE (entry) = new_value;
14566
14567   if (array_type_string)
14568     free (array_type_string);
14569
14570   TREE_PURPOSE (entry) = NULL_TREE;
14571   return error_seen;
14572 }
14573
14574 static tree
14575 build_this (location)
14576      int location;
14577 {
14578   tree node = build_wfl_node (this_identifier_node);
14579   TREE_SET_CODE (node, THIS_EXPR);
14580   EXPR_WFL_LINECOL (node) = location;
14581   return node;
14582 }
14583
14584 /* 14.15 The return statement. It builds a modify expression that
14585    assigns the returned value to the RESULT_DECL that hold the value
14586    to be returned. */
14587
14588 static tree
14589 build_return (location, op)
14590      int location;
14591      tree op;
14592 {
14593   tree node = build1 (RETURN_EXPR, NULL_TREE, op);
14594   EXPR_WFL_LINECOL (node) = location;
14595   node = build_debugable_stmt (location, node);
14596   return node;
14597 }
14598
14599 static tree
14600 patch_return (node)
14601      tree node;
14602 {
14603   tree return_exp = TREE_OPERAND (node, 0);
14604   tree meth = current_function_decl;
14605   tree mtype = TREE_TYPE (TREE_TYPE (current_function_decl));
14606   int error_found = 0;
14607
14608   TREE_TYPE (node) = error_mark_node;
14609   EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
14610
14611   /* It's invalid to have a return value within a function that is
14612      declared with the keyword void or that is a constructor */
14613   if (return_exp && (mtype == void_type_node || DECL_CONSTRUCTOR_P (meth)))
14614     error_found = 1;
14615
14616   /* It's invalid to use a return statement in a static block */
14617   if (DECL_CLINIT_P (current_function_decl))
14618     error_found = 1;
14619
14620   /* It's invalid to have a no return value within a function that
14621      isn't declared with the keyword `void' */
14622   if (!return_exp && (mtype != void_type_node && !DECL_CONSTRUCTOR_P (meth)))
14623     error_found = 2;
14624   
14625   if (DECL_INSTINIT_P (current_function_decl))
14626     error_found = 1;
14627
14628   if (error_found)
14629     {
14630       if (DECL_INSTINIT_P (current_function_decl))
14631         parse_error_context (wfl_operator,
14632                              "`return' inside instance initializer");
14633         
14634       else if (DECL_CLINIT_P (current_function_decl))
14635         parse_error_context (wfl_operator,
14636                              "`return' inside static initializer");
14637
14638       else if (!DECL_CONSTRUCTOR_P (meth))
14639         {
14640           char *t = xstrdup (lang_printable_name (mtype, 0));
14641           parse_error_context (wfl_operator, 
14642                                "`return' with%s value from `%s %s'",
14643                                (error_found == 1 ? "" : "out"), 
14644                                t, lang_printable_name (meth, 0));
14645           free (t);
14646         }
14647       else
14648         parse_error_context (wfl_operator, 
14649                              "`return' with value from constructor `%s'",
14650                              lang_printable_name (meth, 0));
14651       return error_mark_node;
14652     }
14653
14654   /* If we have a return_exp, build a modify expression and expand
14655      it. Note: at that point, the assignment is declared valid, but we
14656      may want to carry some more hacks */
14657   if (return_exp)
14658     {
14659       tree exp = java_complete_tree (return_exp);
14660       tree modify, patched;
14661
14662       if ((patched = patch_string (exp)))
14663         exp = patched;
14664       
14665       modify = build (MODIFY_EXPR, NULL_TREE, DECL_RESULT (meth), exp);
14666       EXPR_WFL_LINECOL (modify) = EXPR_WFL_LINECOL (node);
14667       modify = java_complete_tree (modify);
14668
14669       if (modify != error_mark_node)
14670         {
14671           TREE_SIDE_EFFECTS (modify) = 1;
14672           TREE_OPERAND (node, 0) = modify;
14673         }
14674       else
14675         return error_mark_node;
14676     }
14677   TREE_TYPE (node) = void_type_node;
14678   TREE_SIDE_EFFECTS (node) = 1;
14679   return node;
14680 }
14681
14682 /* 14.8 The if Statement */
14683
14684 static tree
14685 build_if_else_statement (location, expression, if_body, else_body)
14686      int location;
14687      tree expression, if_body, else_body;
14688 {
14689   tree node;
14690   if (!else_body)
14691     else_body = empty_stmt_node;
14692   node = build (COND_EXPR, NULL_TREE, expression, if_body, else_body);
14693   EXPR_WFL_LINECOL (node) = location;
14694   node = build_debugable_stmt (location, node);
14695   return node;
14696 }
14697
14698 static tree
14699 patch_if_else_statement (node)
14700      tree node;
14701 {
14702   tree expression = TREE_OPERAND (node, 0);
14703   int can_complete_normally
14704     = (CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 1))
14705        | CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 2)));
14706
14707   TREE_TYPE (node) = error_mark_node;
14708   EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
14709
14710   /* The type of expression must be boolean */
14711   if (TREE_TYPE (expression) != boolean_type_node
14712       && TREE_TYPE (expression) != promoted_boolean_type_node)
14713     {
14714       parse_error_context 
14715         (wfl_operator, 
14716          "Incompatible type for `if'. Can't convert `%s' to `boolean'", 
14717          lang_printable_name (TREE_TYPE (expression), 0));
14718       return error_mark_node;
14719     }
14720   
14721   if (TREE_CODE (expression) == INTEGER_CST)
14722     {
14723       if (integer_zerop (expression))
14724         node = TREE_OPERAND (node, 2);
14725       else
14726         node = TREE_OPERAND (node, 1);
14727       if (CAN_COMPLETE_NORMALLY (node) != can_complete_normally)
14728         {
14729           node = build (COMPOUND_EXPR, void_type_node, node, empty_stmt_node);
14730           CAN_COMPLETE_NORMALLY (node) = can_complete_normally;
14731         }
14732       return node;
14733     }
14734   TREE_TYPE (node) = void_type_node;
14735   TREE_SIDE_EFFECTS (node) = 1;
14736   CAN_COMPLETE_NORMALLY (node) = can_complete_normally;
14737   return node;
14738 }
14739
14740 /* 14.6 Labeled Statements */
14741
14742 /* Action taken when a lableled statement is parsed. a new
14743    LABELED_BLOCK_EXPR is created. No statement is attached to the
14744    label, yet.  LABEL can be NULL_TREE for artificially-generated blocks. */
14745
14746 static tree
14747 build_labeled_block (location, label)
14748      int location;
14749      tree label;
14750 {
14751   tree label_name ;
14752   tree label_decl, node;
14753   if (label == NULL_TREE || label == continue_identifier_node)
14754     label_name = label;
14755   else
14756     {
14757       label_name = merge_qualified_name (label_id, label);
14758       /* Issue an error if we try to reuse a label that was previously
14759          declared */
14760       if (IDENTIFIER_LOCAL_VALUE (label_name))
14761         {
14762           EXPR_WFL_LINECOL (wfl_operator) = location;
14763           parse_error_context (wfl_operator,
14764             "Declaration of `%s' shadows a previous label declaration",
14765                                IDENTIFIER_POINTER (label));
14766           EXPR_WFL_LINECOL (wfl_operator) = 
14767             EXPR_WFL_LINECOL (IDENTIFIER_LOCAL_VALUE (label_name));
14768           parse_error_context (wfl_operator,
14769             "This is the location of the previous declaration of label `%s'",
14770                                IDENTIFIER_POINTER (label));
14771           java_error_count--;
14772         }
14773     }
14774
14775   label_decl = create_label_decl (label_name);
14776   node = build (LABELED_BLOCK_EXPR, NULL_TREE, label_decl, NULL_TREE);
14777   EXPR_WFL_LINECOL (node) = location;
14778   TREE_SIDE_EFFECTS (node) = 1;
14779   return node;
14780 }
14781
14782 /* A labeled statement LBE is attached a statement.  */
14783
14784 static tree
14785 finish_labeled_statement (lbe, statement)
14786      tree lbe;                  /* Labeled block expr */
14787      tree statement;
14788 {
14789   /* In anyways, tie the loop to its statement */
14790   LABELED_BLOCK_BODY (lbe) = statement;
14791   pop_labeled_block ();
14792   POP_LABELED_BLOCK ();
14793   return lbe;
14794 }
14795
14796 /* 14.10, 14.11, 14.12 Loop Statements */
14797
14798 /* Create an empty LOOP_EXPR and make it the last in the nested loop
14799    list. */
14800
14801 static tree
14802 build_new_loop (loop_body)
14803      tree loop_body;
14804 {
14805   tree loop =  build (LOOP_EXPR, NULL_TREE, loop_body);
14806   TREE_SIDE_EFFECTS (loop) = 1;
14807   PUSH_LOOP (loop);
14808   return loop;
14809 }
14810
14811 /* Create a loop body according to the following structure:
14812      COMPOUND_EXPR
14813        COMPOUND_EXPR            (loop main body)
14814          EXIT_EXPR              (this order is for while/for loops.
14815          LABELED_BLOCK_EXPR      the order is reversed for do loops)
14816            LABEL_DECL           (a continue occurring here branches at the 
14817            BODY                  end of this labeled block)
14818        INCREMENT                (if any)
14819
14820   REVERSED, if non zero, tells that the loop condition expr comes
14821   after the body, like in the do-while loop.
14822
14823   To obtain a loop, the loop body structure described above is
14824   encapsulated within a LOOP_EXPR surrounded by a LABELED_BLOCK_EXPR:
14825
14826    LABELED_BLOCK_EXPR
14827      LABEL_DECL                   (use this label to exit the loop)
14828      LOOP_EXPR
14829        <structure described above> */
14830
14831 static tree
14832 build_loop_body (location, condition, reversed)
14833      int location;
14834      tree condition;
14835      int reversed;
14836 {
14837   tree first, second, body;
14838
14839   condition = build (EXIT_EXPR, NULL_TREE, condition); /* Force walk */
14840   EXPR_WFL_LINECOL (condition) = location; /* For accurate error report */
14841   condition = build_debugable_stmt (location, condition);
14842   TREE_SIDE_EFFECTS (condition) = 1;
14843
14844   body = build_labeled_block (0, continue_identifier_node);
14845   first = (reversed ? body : condition);
14846   second = (reversed ? condition : body);
14847   return 
14848     build (COMPOUND_EXPR, NULL_TREE, 
14849            build (COMPOUND_EXPR, NULL_TREE, first, second), empty_stmt_node);
14850 }
14851
14852 /* Install CONDITION (if any) and loop BODY (using REVERSED to tell
14853    their order) on the current loop. Unlink the current loop from the
14854    loop list.  */
14855
14856 static tree
14857 finish_loop_body (location, condition, body, reversed)
14858      int location;
14859      tree condition, body;
14860      int reversed;
14861 {
14862   tree to_return = ctxp->current_loop;
14863   tree loop_body = LOOP_EXPR_BODY (to_return);
14864   if (condition)
14865     {
14866       tree cnode = LOOP_EXPR_BODY_CONDITION_EXPR (loop_body, reversed);
14867       /* We wrapped the EXIT_EXPR around a WFL so we can debug it.
14868          The real EXIT_EXPR is one operand further. */
14869       EXPR_WFL_LINECOL (cnode) = location;
14870       /* This one is for accurate error reports */
14871       EXPR_WFL_LINECOL (TREE_OPERAND (cnode, 0)) = location;
14872       TREE_OPERAND (TREE_OPERAND (cnode, 0), 0) = condition;
14873     }
14874   LOOP_EXPR_BODY_BODY_EXPR (loop_body, reversed) = body;
14875   POP_LOOP ();
14876   return to_return;
14877 }
14878
14879 /* Tailored version of finish_loop_body for FOR loops, when FOR
14880    loops feature the condition part */
14881
14882 static tree
14883 finish_for_loop (location, condition, update, body)
14884     int location;
14885     tree condition, update, body;
14886 {
14887   /* Put the condition and the loop body in place */
14888   tree loop = finish_loop_body (location, condition, body, 0);
14889   /* LOOP is the current loop which has been now popped of the loop
14890      stack. Install the update block */
14891   LOOP_EXPR_BODY_UPDATE_BLOCK (LOOP_EXPR_BODY (loop)) = update;
14892   return loop;
14893 }
14894
14895 /* Try to find the loop a block might be related to. This comprises
14896    the case where the LOOP_EXPR is found as the second operand of a
14897    COMPOUND_EXPR, because the loop happens to have an initialization
14898    part, then expressed as the first operand of the COMPOUND_EXPR. If
14899    the search finds something, 1 is returned. Otherwise, 0 is
14900    returned. The search is assumed to start from a
14901    LABELED_BLOCK_EXPR's block.  */
14902
14903 static tree
14904 search_loop (statement)
14905     tree statement;
14906 {
14907   if (TREE_CODE (statement) == LOOP_EXPR)
14908     return statement;
14909
14910   if (TREE_CODE (statement) == BLOCK)
14911     statement = BLOCK_SUBBLOCKS (statement);
14912   else
14913     return NULL_TREE;
14914
14915   if (statement && TREE_CODE (statement) == COMPOUND_EXPR)
14916     while (statement && TREE_CODE (statement) == COMPOUND_EXPR)
14917       statement = TREE_OPERAND (statement, 1);
14918
14919   return (TREE_CODE (statement) == LOOP_EXPR
14920           && FOR_LOOP_P (statement) ? statement : NULL_TREE);
14921 }
14922
14923 /* Return 1 if LOOP can be found in the labeled block BLOCK. 0 is
14924    returned otherwise.  */
14925
14926 static int
14927 labeled_block_contains_loop_p (block, loop)
14928     tree block, loop;
14929 {
14930   if (!block)
14931     return 0;
14932
14933   if (LABELED_BLOCK_BODY (block) == loop)
14934     return 1;
14935
14936   if (FOR_LOOP_P (loop) && search_loop (LABELED_BLOCK_BODY (block)) == loop)
14937     return 1;
14938
14939   return 0;
14940 }
14941
14942 /* If the loop isn't surrounded by a labeled statement, create one and
14943    insert LOOP as its body.  */
14944
14945 static tree
14946 patch_loop_statement (loop)
14947      tree loop;
14948 {
14949   tree loop_label;
14950
14951   TREE_TYPE (loop) = void_type_node;
14952   if (labeled_block_contains_loop_p (ctxp->current_labeled_block, loop))
14953     return loop;
14954
14955   loop_label = build_labeled_block (0, NULL_TREE);
14956   /* LOOP is an EXPR node, so it should have a valid EXPR_WFL_LINECOL
14957      that LOOP_LABEL could enquire about, for a better accuracy. FIXME */
14958   LABELED_BLOCK_BODY (loop_label) = loop;
14959   PUSH_LABELED_BLOCK (loop_label);
14960   return loop_label;
14961 }
14962
14963 /* 14.13, 14.14: break and continue Statements */
14964
14965 /* Build a break or a continue statement. a null NAME indicates an
14966    unlabeled break/continue statement.  */
14967
14968 static tree
14969 build_bc_statement (location, is_break, name)
14970      int location, is_break;
14971      tree name;
14972 {
14973   tree break_continue, label_block_expr = NULL_TREE;
14974
14975   if (name)
14976     {
14977       if (!(label_block_expr = IDENTIFIER_LOCAL_VALUE 
14978             (merge_qualified_name (label_id, EXPR_WFL_NODE (name)))))
14979         /* Null means that we don't have a target for this named
14980            break/continue. In this case, we make the target to be the
14981            label name, so that the error can be reported accuratly in
14982            patch_bc_statement. */
14983         label_block_expr = EXPR_WFL_NODE (name);
14984     }
14985   /* Unlabeled break/continue will be handled during the
14986      break/continue patch operation */
14987   break_continue 
14988     = build (EXIT_BLOCK_EXPR, NULL_TREE, label_block_expr, NULL_TREE);
14989
14990   IS_BREAK_STMT_P (break_continue) = is_break;
14991   TREE_SIDE_EFFECTS (break_continue) = 1;
14992   EXPR_WFL_LINECOL (break_continue) = location;
14993   break_continue = build_debugable_stmt (location, break_continue);
14994   return break_continue;
14995 }
14996
14997 /* Verification of a break/continue statement. */
14998
14999 static tree
15000 patch_bc_statement (node)
15001      tree node;
15002 {
15003   tree bc_label = EXIT_BLOCK_LABELED_BLOCK (node), target_stmt;
15004   tree labeled_block = ctxp->current_labeled_block;
15005   EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
15006  
15007   /* Having an identifier here means that the target is unknown. */
15008   if (bc_label != NULL_TREE && TREE_CODE (bc_label) == IDENTIFIER_NODE)
15009     {
15010       parse_error_context (wfl_operator, "No label definition found for `%s'",
15011                            IDENTIFIER_POINTER (bc_label));
15012       return error_mark_node;
15013     }
15014   if (! IS_BREAK_STMT_P (node))
15015     {
15016       /* It's a continue statement. */
15017       for (;; labeled_block = TREE_CHAIN (labeled_block))
15018         {
15019           if (labeled_block == NULL_TREE)
15020             {
15021               if (bc_label == NULL_TREE)
15022                 parse_error_context (wfl_operator,
15023                                      "`continue' must be in loop");
15024               else
15025                 parse_error_context 
15026                   (wfl_operator, "continue label `%s' does not name a loop",
15027                    IDENTIFIER_POINTER (bc_label));
15028               return error_mark_node;
15029             }
15030           if ((DECL_NAME (LABELED_BLOCK_LABEL (labeled_block))
15031                == continue_identifier_node)
15032               && (bc_label == NULL_TREE
15033                   || TREE_CHAIN (labeled_block) == bc_label))
15034             {
15035               bc_label = labeled_block;
15036               break;
15037             }
15038         }
15039     }
15040   else if (!bc_label)
15041     { 
15042       for (;; labeled_block = TREE_CHAIN (labeled_block))
15043         {
15044           if (labeled_block == NULL_TREE)
15045             {
15046               parse_error_context (wfl_operator,
15047                                      "`break' must be in loop or switch");
15048               return error_mark_node;
15049             }
15050           target_stmt = LABELED_BLOCK_BODY (labeled_block);
15051           if (TREE_CODE (target_stmt) == SWITCH_EXPR
15052               || search_loop (target_stmt))
15053             {
15054               bc_label = labeled_block;
15055               break;
15056             }
15057         }
15058     }
15059
15060   EXIT_BLOCK_LABELED_BLOCK (node) = bc_label;
15061   CAN_COMPLETE_NORMALLY (bc_label) = 1;
15062
15063   /* Our break/continue don't return values. */
15064   TREE_TYPE (node) = void_type_node;
15065   /* Encapsulate the break within a compound statement so that it's
15066      expanded all the times by expand_expr (and not clobbered
15067      sometimes, like after a if statement) */
15068   node = add_stmt_to_compound (NULL_TREE, void_type_node, node);
15069   TREE_SIDE_EFFECTS (node) = 1;
15070   return node;
15071 }
15072
15073 /* Process the exit expression belonging to a loop. Its type must be
15074    boolean.  */
15075
15076 static tree
15077 patch_exit_expr (node)
15078      tree node;
15079 {
15080   tree expression = TREE_OPERAND (node, 0);
15081   TREE_TYPE (node) = error_mark_node;
15082   EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
15083
15084   /* The type of expression must be boolean */
15085   if (TREE_TYPE (expression) != boolean_type_node)
15086     {
15087       parse_error_context 
15088         (wfl_operator, 
15089     "Incompatible type for loop conditional. Can't convert `%s' to `boolean'", 
15090          lang_printable_name (TREE_TYPE (expression), 0));
15091       return error_mark_node;
15092     }
15093   /* Now we know things are allright, invert the condition, fold and
15094      return */
15095   TREE_OPERAND (node, 0) = 
15096     fold (build1 (TRUTH_NOT_EXPR, boolean_type_node, expression));
15097
15098   if (! integer_zerop (TREE_OPERAND (node, 0))
15099       && ctxp->current_loop != NULL_TREE
15100       && TREE_CODE (ctxp->current_loop) == LOOP_EXPR)
15101     CAN_COMPLETE_NORMALLY (ctxp->current_loop) = 1;
15102   if (! integer_onep (TREE_OPERAND (node, 0)))
15103     CAN_COMPLETE_NORMALLY (node) = 1;
15104
15105
15106   TREE_TYPE (node) = void_type_node;
15107   return node;
15108 }
15109
15110 /* 14.9 Switch statement */
15111
15112 static tree
15113 patch_switch_statement (node)
15114      tree node;
15115 {
15116   tree se = TREE_OPERAND (node, 0), se_type;
15117   tree save, iter;
15118
15119   /* Complete the switch expression */
15120   se = TREE_OPERAND (node, 0) = java_complete_tree (se);
15121   se_type = TREE_TYPE (se);
15122   /* The type of the switch expression must be char, byte, short or
15123      int */
15124   if (! JINTEGRAL_TYPE_P (se_type) || se_type == long_type_node)
15125     {
15126       EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
15127       parse_error_context (wfl_operator,
15128           "Incompatible type for `switch'. Can't convert `%s' to `int'",
15129                            lang_printable_name (se_type, 0));
15130       /* This is what java_complete_tree will check */
15131       TREE_OPERAND (node, 0) = error_mark_node;
15132       return error_mark_node;
15133     }
15134
15135   /* Save and restore the outer case label list.  */
15136   save = case_label_list;
15137   case_label_list = NULL_TREE;
15138
15139   TREE_OPERAND (node, 1) = java_complete_tree (TREE_OPERAND (node, 1));
15140
15141   /* See if we've found a duplicate label.  We can't leave this until
15142      code generation, because in `--syntax-only' and `-C' modes we
15143      don't do ordinary code generation.  */
15144   for (iter = case_label_list; iter != NULL_TREE; iter = TREE_CHAIN (iter))
15145     {
15146       HOST_WIDE_INT val = TREE_INT_CST_LOW (TREE_VALUE (iter));
15147       tree subiter;
15148       for (subiter = TREE_CHAIN (iter);
15149            subiter != NULL_TREE;
15150            subiter = TREE_CHAIN (subiter))
15151         {
15152           HOST_WIDE_INT subval = TREE_INT_CST_LOW (TREE_VALUE (subiter));
15153           if (val == subval)
15154             {
15155               EXPR_WFL_LINECOL (wfl_operator)
15156                 = EXPR_WFL_LINECOL (TREE_PURPOSE (iter));
15157               /* The case_label_list is in reverse order, so print the
15158                  outer label first.  */
15159               parse_error_context (wfl_operator, "duplicate case label: `"
15160                                    HOST_WIDE_INT_PRINT_DEC "'", subval);
15161               EXPR_WFL_LINECOL (wfl_operator)
15162                 = EXPR_WFL_LINECOL (TREE_PURPOSE (subiter));
15163               parse_error_context (wfl_operator, "original label is here");
15164
15165               break;
15166             }
15167         }
15168     }
15169
15170   case_label_list = save;
15171
15172   /* Ready to return */
15173   if (TREE_CODE (TREE_OPERAND (node, 1)) == ERROR_MARK)
15174     {
15175       TREE_TYPE (node) = error_mark_node;
15176       return error_mark_node;
15177     }
15178   TREE_TYPE (node) = void_type_node;
15179   TREE_SIDE_EFFECTS (node) = 1;
15180   CAN_COMPLETE_NORMALLY (node)
15181     = CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 1)) 
15182       || ! SWITCH_HAS_DEFAULT (node);
15183   return node;
15184 }
15185
15186 /* 14.18 The try/catch statements */
15187
15188 /* Encapsulate TRY_STMTS' in a try catch sequence. The catch clause
15189    catches TYPE and executes CATCH_STMTS.  */
15190
15191 static tree
15192 encapsulate_with_try_catch (location, type, try_stmts, catch_stmts)
15193      int location;
15194      tree type, try_stmts, catch_stmts;
15195 {
15196   tree try_block, catch_clause_param, catch_block, catch;
15197
15198   /* First build a try block */
15199   try_block = build_expr_block (try_stmts, NULL_TREE);
15200
15201   /* Build a catch block: we need a catch clause parameter */
15202   catch_clause_param = build_decl (VAR_DECL, 
15203                                    wpv_id, build_pointer_type (type));
15204   /* And a block */
15205   catch_block = build_expr_block (NULL_TREE, catch_clause_param);
15206   
15207   /* Initialize the variable and store in the block */
15208   catch = build (MODIFY_EXPR, NULL_TREE, catch_clause_param,
15209                  build (JAVA_EXC_OBJ_EXPR, ptr_type_node));
15210   add_stmt_to_block (catch_block, NULL_TREE, catch);
15211
15212   /* Add the catch statements */
15213   add_stmt_to_block (catch_block, NULL_TREE, catch_stmts);
15214
15215   /* Now we can build a CATCH_EXPR */
15216   catch_block = build1 (CATCH_EXPR, NULL_TREE, catch_block);
15217
15218   return build_try_statement (location, try_block, catch_block);
15219 }
15220
15221 static tree
15222 build_try_statement (location, try_block, catches)
15223      int location;
15224      tree try_block, catches;
15225 {
15226   tree node = build (TRY_EXPR, NULL_TREE, try_block, catches);
15227   EXPR_WFL_LINECOL (node) = location;
15228   return node;
15229 }
15230
15231 static tree
15232 build_try_finally_statement (location, try_block, finally)
15233      int location;
15234      tree try_block, finally;
15235 {
15236   tree node = build (TRY_FINALLY_EXPR, NULL_TREE, try_block, finally);
15237   EXPR_WFL_LINECOL (node) = location;
15238   return node;
15239 }
15240
15241 static tree
15242 patch_try_statement (node)
15243      tree node;
15244 {
15245   int error_found = 0;
15246   tree try = TREE_OPERAND (node, 0);
15247   /* Exception handlers are considered in left to right order */
15248   tree catch = nreverse (TREE_OPERAND (node, 1));
15249   tree current, caught_type_list = NULL_TREE;
15250
15251   /* Check catch clauses, if any. Every time we find an error, we try
15252      to process the next catch clause. We process the catch clause before
15253      the try block so that when processing the try block we can check thrown
15254      exceptions againts the caught type list. */
15255   for (current = catch; current; current = TREE_CHAIN (current))
15256     {
15257       tree carg_decl, carg_type;
15258       tree sub_current, catch_block, catch_clause;
15259       int unreachable;
15260
15261       /* At this point, the structure of the catch clause is
15262            CATCH_EXPR           (catch node)
15263              BLOCK              (with the decl of the parameter)
15264                COMPOUND_EXPR
15265                  MODIFY_EXPR   (assignment of the catch parameter)
15266                  BLOCK          (catch clause block)
15267        */
15268       catch_clause = TREE_OPERAND (current, 0);
15269       carg_decl = BLOCK_EXPR_DECLS (catch_clause);
15270       carg_type = TREE_TYPE (TREE_TYPE (carg_decl));
15271
15272       /* Catch clauses can't have more than one parameter declared,
15273          but it's already enforced by the grammar. Make sure that the
15274          only parameter of the clause statement in of class Throwable
15275          or a subclass of Throwable, but that was done earlier. The
15276          catch clause parameter type has also been resolved. */
15277       
15278       /* Just make sure that the catch clause parameter type inherits
15279          from java.lang.Throwable */
15280       if (!inherits_from_p (carg_type, throwable_type_node))
15281         {
15282           EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (current);
15283           parse_error_context (wfl_operator,
15284                                "Can't catch class `%s'. Catch clause parameter type must be a subclass of class `java.lang.Throwable'",
15285                                lang_printable_name (carg_type, 0));
15286           error_found = 1;
15287           continue;
15288         }
15289       
15290       /* Partial check for unreachable catch statement: The catch
15291          clause is reachable iff is no earlier catch block A in
15292          the try statement such that the type of the catch
15293          clause's parameter is the same as or a subclass of the
15294          type of A's parameter */
15295       unreachable = 0;
15296       for (sub_current = catch;
15297            sub_current != current; sub_current = TREE_CHAIN (sub_current))
15298         {
15299           tree sub_catch_clause, decl;
15300           sub_catch_clause = TREE_OPERAND (sub_current, 0);
15301           decl = BLOCK_EXPR_DECLS (sub_catch_clause);
15302
15303           if (inherits_from_p (carg_type, TREE_TYPE (TREE_TYPE (decl))))
15304             {
15305               EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (current);
15306               parse_error_context 
15307                 (wfl_operator,
15308                  "`catch' not reached because of the catch clause at line %d",
15309                  EXPR_WFL_LINENO (sub_current));
15310               unreachable = error_found = 1;
15311               break;
15312             }
15313         }
15314       /* Complete the catch clause block */
15315       catch_block = java_complete_tree (TREE_OPERAND (current, 0));
15316       if (catch_block == error_mark_node)
15317         {
15318           error_found = 1;
15319           continue;
15320         }
15321       if (CAN_COMPLETE_NORMALLY (catch_block))
15322         CAN_COMPLETE_NORMALLY (node) = 1;
15323       TREE_OPERAND (current, 0) = catch_block;
15324
15325       if (unreachable)
15326         continue;
15327
15328       /* Things to do here: the exception must be thrown */
15329
15330       /* Link this type to the caught type list */
15331       caught_type_list = tree_cons (NULL_TREE, carg_type, caught_type_list);
15332     }
15333
15334   PUSH_EXCEPTIONS (caught_type_list);
15335   if ((try = java_complete_tree (try)) == error_mark_node)
15336     error_found = 1;
15337   if (CAN_COMPLETE_NORMALLY (try))
15338     CAN_COMPLETE_NORMALLY (node) = 1;
15339   POP_EXCEPTIONS ();
15340
15341   /* Verification ends here */
15342   if (error_found) 
15343     return error_mark_node;
15344
15345   TREE_OPERAND (node, 0) = try;
15346   TREE_OPERAND (node, 1) = catch;
15347   TREE_TYPE (node) = void_type_node;
15348   return node;
15349 }
15350
15351 /* 14.17 The synchronized Statement */
15352
15353 static tree
15354 patch_synchronized_statement (node, wfl_op1)
15355     tree node, wfl_op1;
15356 {
15357   tree expr = java_complete_tree (TREE_OPERAND (node, 0));
15358   tree block = TREE_OPERAND (node, 1);
15359
15360   tree tmp, enter, exit, expr_decl, assignment;
15361
15362   if (expr == error_mark_node)
15363     {
15364       block = java_complete_tree (block);
15365       return expr;
15366     }
15367
15368   /* We might be trying to synchronize on a STRING_CST */
15369   if ((tmp = patch_string (expr)))
15370     expr = tmp;
15371
15372   /* The TYPE of expr must be a reference type */
15373   if (!JREFERENCE_TYPE_P (TREE_TYPE (expr)))
15374     {
15375       SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
15376       parse_error_context (wfl_operator, "Incompatible type for `synchronized'. Can't convert `%s' to `java.lang.Object'",
15377                            lang_printable_name (TREE_TYPE (expr), 0));
15378       return error_mark_node;
15379     }
15380
15381   if (flag_emit_xref)
15382     {
15383       TREE_OPERAND (node, 0) = expr;
15384       TREE_OPERAND (node, 1) = java_complete_tree (block);
15385       CAN_COMPLETE_NORMALLY (node) = 1;
15386       return node;
15387     }
15388
15389   /* Generate a try-finally for the synchronized statement, except
15390      that the handler that catches all throw exception calls
15391      _Jv_MonitorExit and then rethrow the exception.
15392      The synchronized statement is then implemented as:
15393      TRY 
15394        {
15395          _Jv_MonitorEnter (expression)
15396          synchronized_block
15397          _Jv_MonitorExit (expression)
15398        }
15399      CATCH_ALL
15400        {
15401          e = _Jv_exception_info ();
15402          _Jv_MonitorExit (expression)
15403          Throw (e);
15404        } */
15405
15406   expr_decl = build_decl (VAR_DECL, generate_name (), TREE_TYPE (expr));
15407   BUILD_MONITOR_ENTER (enter, expr_decl);
15408   BUILD_MONITOR_EXIT (exit, expr_decl);
15409   CAN_COMPLETE_NORMALLY (enter) = 1;
15410   CAN_COMPLETE_NORMALLY (exit) = 1;
15411   assignment = build (MODIFY_EXPR, NULL_TREE, expr_decl, expr);
15412   TREE_SIDE_EFFECTS (assignment) = 1;
15413   node = build (COMPOUND_EXPR, NULL_TREE,
15414                 build (COMPOUND_EXPR, NULL_TREE, assignment, enter),
15415                 build (TRY_FINALLY_EXPR, NULL_TREE, block, exit));
15416   node = build_expr_block (node, expr_decl);
15417
15418   return java_complete_tree (node);
15419 }
15420
15421 /* 14.16 The throw Statement */
15422
15423 static tree
15424 patch_throw_statement (node, wfl_op1)
15425     tree node, wfl_op1;
15426 {
15427   tree expr = TREE_OPERAND (node, 0);
15428   tree type = TREE_TYPE (expr);
15429   int unchecked_ok = 0, tryblock_throws_ok = 0;
15430
15431   /* Thrown expression must be assignable to java.lang.Throwable */
15432   if (!try_reference_assignconv (throwable_type_node, expr))
15433     {
15434       SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
15435       parse_error_context (wfl_operator,
15436     "Can't throw `%s'; it must be a subclass of class `java.lang.Throwable'",
15437                            lang_printable_name (type, 0));
15438       /* If the thrown expression was a reference, we further the
15439          compile-time check. */
15440       if (!JREFERENCE_TYPE_P (type))
15441         return error_mark_node;
15442     }
15443
15444   /* At least one of the following must be true */
15445
15446   /* The type of the throw expression is a not checked exception,
15447      i.e. is a unchecked expression. */
15448   unchecked_ok = IS_UNCHECKED_EXCEPTION_P (TREE_TYPE (type));
15449
15450   SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
15451   /* An instance can't throw a checked exception unless that exception
15452      is explicitly declared in the `throws' clause of each
15453      constructor. This doesn't apply to anonymous classes, since they
15454      don't have declared constructors. */
15455   if (!unchecked_ok 
15456       && DECL_INSTINIT_P (current_function_decl)
15457       && !ANONYMOUS_CLASS_P (current_class))
15458     {
15459       tree current;
15460       for (current = TYPE_METHODS (current_class); current; 
15461            current = TREE_CHAIN (current))
15462         if (DECL_CONSTRUCTOR_P (current) 
15463             && !check_thrown_exceptions_do (TREE_TYPE (expr)))
15464           {
15465             parse_error_context (wfl_operator, "Checked exception `%s' can't be thrown in instance initializer (not all declared constructor are declaring it in their `throws' clause)", 
15466                                  lang_printable_name (TREE_TYPE (expr), 0));
15467             return error_mark_node;
15468           }
15469     }
15470
15471   /* Throw is contained in a try statement and at least one catch
15472      clause can receive the thrown expression or the current method is
15473      declared to throw such an exception. Or, the throw statement is
15474      contained in a method or constructor declaration and the type of
15475      the Expression is assignable to at least one type listed in the
15476      throws clause the declaration. */
15477   if (!unchecked_ok)
15478     tryblock_throws_ok = check_thrown_exceptions_do (TREE_TYPE (expr));
15479   if (!(unchecked_ok || tryblock_throws_ok))
15480     {
15481       /* If there is a surrounding try block that has no matching
15482          clatch clause, report it first. A surrounding try block exits
15483          only if there is something after the list of checked
15484          exception thrown by the current function (if any). */
15485       if (IN_TRY_BLOCK_P ())
15486         parse_error_context (wfl_operator, "Checked exception `%s' can't be caught by any of the catch clause(s) of the surrounding `try' block",
15487                              lang_printable_name (type, 0));
15488       /* If we have no surrounding try statement and the method doesn't have
15489          any throws, report it now. FIXME */
15490
15491       /* We report that the exception can't be throw from a try block
15492          in all circumstances but when the `throw' is inside a static
15493          block. */
15494       else if (!EXCEPTIONS_P (currently_caught_type_list) 
15495                && !tryblock_throws_ok)
15496         {
15497           if (DECL_CLINIT_P (current_function_decl))
15498             parse_error_context (wfl_operator,
15499                    "Checked exception `%s' can't be thrown in initializer",
15500                                  lang_printable_name (type, 0));
15501           else
15502             parse_error_context (wfl_operator,
15503                    "Checked exception `%s' isn't thrown from a `try' block", 
15504                                  lang_printable_name (type, 0));
15505         }
15506       /* Otherwise, the current method doesn't have the appropriate
15507          throws declaration */
15508       else
15509         parse_error_context (wfl_operator, "Checked exception `%s' doesn't match any of current method's `throws' declaration(s)", 
15510                              lang_printable_name (type, 0));
15511       return error_mark_node;
15512     }
15513
15514   if (! flag_emit_class_files && ! flag_emit_xref)
15515     BUILD_THROW (node, expr);
15516
15517   /* If doing xrefs, keep the location where the `throw' was seen. */
15518   if (flag_emit_xref)
15519     EXPR_WFL_LINECOL (node) = EXPR_WFL_LINECOL (wfl_op1);
15520   return node;
15521 }
15522
15523 /* Check that exception said to be thrown by method DECL can be
15524    effectively caught from where DECL is invoked.  */
15525
15526 static void
15527 check_thrown_exceptions (location, decl)
15528      int location;
15529      tree decl;
15530 {
15531   tree throws;
15532   /* For all the unchecked exceptions thrown by DECL */
15533   for (throws = DECL_FUNCTION_THROWS (decl); throws; 
15534        throws = TREE_CHAIN (throws)) 
15535     if (!check_thrown_exceptions_do (TREE_VALUE (throws)))
15536       {
15537 #if 1
15538         /* Temporary hack to suppresses errors about cloning arrays. FIXME */
15539         if (DECL_NAME (decl) == get_identifier ("clone"))
15540           continue;
15541 #endif
15542         EXPR_WFL_LINECOL (wfl_operator) = location;
15543         if (DECL_FINIT_P (current_function_decl))
15544           parse_error_context
15545             (wfl_operator, "Exception `%s' can't be thrown in initializer",
15546              lang_printable_name (TREE_VALUE (throws), 0));
15547         else 
15548           {
15549             parse_error_context 
15550               (wfl_operator, "Exception `%s' must be caught, or it must be declared in the `throws' clause of `%s'", 
15551                lang_printable_name (TREE_VALUE (throws), 0),
15552                (DECL_INIT_P (current_function_decl) ?
15553                 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (current_class))) :
15554                 IDENTIFIER_POINTER (DECL_NAME (current_function_decl))));
15555           }
15556       }
15557 }
15558
15559 /* Return 1 if checked EXCEPTION is caught at the current nesting level of
15560    try-catch blocks, OR is listed in the `throws' clause of the
15561    current method.  */
15562
15563 static int
15564 check_thrown_exceptions_do (exception)
15565      tree exception;
15566 {
15567   tree list = currently_caught_type_list;
15568   resolve_and_layout (exception, NULL_TREE);
15569   /* First, all the nested try-catch-finally at that stage. The
15570      last element contains `throws' clause exceptions, if any. */
15571   if (IS_UNCHECKED_EXCEPTION_P (exception))
15572     return 1;
15573   while (list)
15574     {
15575       tree caught;
15576       for (caught = TREE_VALUE (list); caught; caught = TREE_CHAIN (caught))
15577         if (valid_ref_assignconv_cast_p (exception, TREE_VALUE (caught), 0))
15578           return 1;
15579       list = TREE_CHAIN (list);
15580     }
15581   return 0;
15582 }
15583
15584 static void
15585 purge_unchecked_exceptions (mdecl)
15586      tree mdecl;
15587 {
15588   tree throws = DECL_FUNCTION_THROWS (mdecl);
15589   tree new = NULL_TREE;
15590
15591   while (throws)
15592     {
15593       tree next = TREE_CHAIN (throws);
15594       if (!IS_UNCHECKED_EXCEPTION_P (TREE_VALUE (throws)))
15595         {
15596           TREE_CHAIN (throws) = new;
15597           new = throws;
15598         }
15599       throws = next;
15600     }
15601   /* List is inverted here, but it doesn't matter */
15602   DECL_FUNCTION_THROWS (mdecl) = new;
15603 }
15604
15605 /* This function goes over all of CLASS_TYPE ctors and checks whether
15606    each of them features at least one unchecked exception in its
15607    `throws' clause. If it's the case, it returns `true', `false'
15608    otherwise.  */
15609
15610 static bool
15611 ctors_unchecked_throws_clause_p (class_type)
15612      tree class_type;
15613 {
15614   tree current;
15615
15616   for (current = TYPE_METHODS (class_type); current;
15617        current = TREE_CHAIN (current))
15618     {
15619       bool ctu = false; /* Ctor Throws Unchecked */
15620       if (DECL_CONSTRUCTOR_P (current))
15621         {
15622           tree throws;
15623           for (throws = DECL_FUNCTION_THROWS (current); throws && !ctu;
15624                throws = TREE_CHAIN (throws))
15625             if (inherits_from_p (TREE_VALUE (throws), exception_type_node))
15626               ctu = true;
15627         }
15628       /* We return false as we found one ctor that is unfit. */
15629       if (!ctu && DECL_CONSTRUCTOR_P (current))
15630         return false;
15631     }
15632   /* All ctors feature at least one unchecked exception in their
15633      `throws' clause. */
15634   return true;
15635 }
15636
15637 /* 15.24 Conditional Operator ?: */
15638
15639 static tree
15640 patch_conditional_expr (node, wfl_cond, wfl_op1)
15641      tree node, wfl_cond, wfl_op1;
15642 {
15643   tree cond = TREE_OPERAND (node, 0);
15644   tree op1 = TREE_OPERAND (node, 1);
15645   tree op2 = TREE_OPERAND (node, 2);
15646   tree resulting_type = NULL_TREE;
15647   tree t1, t2, patched;
15648   int error_found = 0;
15649
15650   /* Operands of ?: might be StringBuffers crafted as a result of a
15651      string concatenation. Obtain a descent operand here.  */
15652   if ((patched = patch_string (op1)))
15653     TREE_OPERAND (node, 1) = op1 = patched;
15654   if ((patched = patch_string (op2)))
15655     TREE_OPERAND (node, 2) = op2 = patched;
15656
15657   t1 = TREE_TYPE (op1);
15658   t2 = TREE_TYPE (op2);
15659
15660   /* The first expression must be a boolean */
15661   if (TREE_TYPE (cond) != boolean_type_node)
15662     {
15663       SET_WFL_OPERATOR (wfl_operator, node, wfl_cond);
15664       parse_error_context (wfl_operator,
15665                "Incompatible type for `?:'. Can't convert `%s' to `boolean'",
15666                            lang_printable_name (TREE_TYPE (cond), 0));
15667       error_found = 1;
15668     }
15669
15670   /* Second and third can be numeric, boolean (i.e. primitive),
15671      references or null. Anything else results in an error */
15672   if (!((JNUMERIC_TYPE_P (t1) && JNUMERIC_TYPE_P (t2))
15673         || ((JREFERENCE_TYPE_P (t1) || op1 == null_pointer_node) 
15674             && (JREFERENCE_TYPE_P (t2) || op2 == null_pointer_node))
15675         || (t1 == boolean_type_node && t2 == boolean_type_node)))
15676     error_found = 1;
15677
15678   /* Determine the type of the conditional expression. Same types are
15679      easy to deal with */
15680   else if (t1 == t2)
15681     resulting_type = t1;
15682
15683   /* There are different rules for numeric types */
15684   else if (JNUMERIC_TYPE_P (t1))
15685     {
15686       /* if byte/short found, the resulting type is short */
15687       if ((t1 == byte_type_node && t2 == short_type_node)
15688           || (t1 == short_type_node && t2 == byte_type_node))
15689         resulting_type = short_type_node;
15690
15691       /* If t1 is a constant int and t2 is of type byte, short or char
15692          and t1's value fits in t2, then the resulting type is t2 */
15693       else if ((t1 == int_type_node && TREE_CONSTANT (TREE_OPERAND (node, 1)))
15694           && JBSC_TYPE_P (t2) && int_fits_type_p (TREE_OPERAND (node, 1), t2))
15695         resulting_type = t2;
15696
15697       /* If t2 is a constant int and t1 is of type byte, short or char
15698          and t2's value fits in t1, then the resulting type is t1 */
15699       else if ((t2 == int_type_node && TREE_CONSTANT (TREE_OPERAND (node, 2)))
15700           && JBSC_TYPE_P (t1) && int_fits_type_p (TREE_OPERAND (node, 2), t1))
15701         resulting_type = t1;
15702
15703       /* Otherwise, binary numeric promotion is applied and the
15704          resulting type is the promoted type of operand 1 and 2 */
15705       else 
15706         resulting_type = binary_numeric_promotion (t1, t2, 
15707                                                    &TREE_OPERAND (node, 1), 
15708                                                    &TREE_OPERAND (node, 2));
15709     }
15710
15711   /* Cases of a reference and a null type */
15712   else if (JREFERENCE_TYPE_P (t1) && op2 == null_pointer_node)
15713     resulting_type = t1;
15714
15715   else if (JREFERENCE_TYPE_P (t2) && op1 == null_pointer_node)
15716     resulting_type = t2;
15717
15718   /* Last case: different reference types. If a type can be converted
15719      into the other one by assignment conversion, the latter
15720      determines the type of the expression */
15721   else if ((resulting_type = try_reference_assignconv (t1, op2)))
15722     resulting_type = promote_type (t1);
15723
15724   else if ((resulting_type = try_reference_assignconv (t2, op1)))
15725     resulting_type = promote_type (t2);
15726
15727   /* If we don't have any resulting type, we're in trouble */
15728   if (!resulting_type)
15729     {
15730       char *t = xstrdup (lang_printable_name (t1, 0));
15731       SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
15732       parse_error_context (wfl_operator,
15733                  "Incompatible type for `?:'. Can't convert `%s' to `%s'",
15734                            t, lang_printable_name (t2, 0));
15735       free (t);
15736       error_found = 1;
15737     }
15738
15739   if (error_found)
15740     {
15741       TREE_TYPE (node) = error_mark_node;
15742       return error_mark_node;
15743     }
15744
15745   TREE_TYPE (node) = resulting_type;
15746   TREE_SET_CODE (node, COND_EXPR);
15747   CAN_COMPLETE_NORMALLY (node) = 1;
15748   return node;
15749 }
15750
15751 /* Wrap EXPR with code to initialize DECL's class, if appropriate. */
15752
15753 static tree
15754 maybe_build_class_init_for_field (decl, expr)
15755     tree decl, expr;
15756 {
15757   tree clas = DECL_CONTEXT (decl);
15758   if (flag_emit_class_files || flag_emit_xref)
15759     return expr;
15760
15761   if (TREE_CODE (decl) == VAR_DECL && FIELD_STATIC (decl)
15762       && FIELD_FINAL (decl))
15763     {
15764       tree init = DECL_INITIAL (decl);
15765       if (init != NULL_TREE)
15766         init = fold_constant_for_init (init, decl);
15767       if (init != NULL_TREE && CONSTANT_VALUE_P (init))
15768         return expr;
15769     }
15770
15771   return build_class_init (clas, expr);
15772 }
15773
15774 /* Try to constant fold NODE.
15775    If NODE is not a constant expression, return NULL_EXPR.
15776    CONTEXT is a static final VAR_DECL whose initializer we are folding. */
15777
15778 static tree
15779 fold_constant_for_init (node, context)
15780      tree node;
15781      tree context;
15782 {
15783   tree op0, op1, val;
15784   enum tree_code code = TREE_CODE (node);
15785
15786   switch (code)
15787     {
15788     case STRING_CST:
15789     case INTEGER_CST:
15790     case REAL_CST:
15791       return node;
15792
15793     case PLUS_EXPR:
15794     case MINUS_EXPR:
15795     case MULT_EXPR:
15796     case TRUNC_MOD_EXPR:
15797     case RDIV_EXPR:
15798     case LSHIFT_EXPR:
15799     case RSHIFT_EXPR:
15800     case URSHIFT_EXPR:
15801     case BIT_AND_EXPR:
15802     case BIT_XOR_EXPR:
15803     case BIT_IOR_EXPR:
15804     case TRUTH_ANDIF_EXPR:
15805     case TRUTH_ORIF_EXPR:
15806     case EQ_EXPR: 
15807     case NE_EXPR:
15808     case GT_EXPR:
15809     case GE_EXPR:
15810     case LT_EXPR:
15811     case LE_EXPR:
15812       op0 = TREE_OPERAND (node, 0);
15813       op1 = TREE_OPERAND (node, 1);
15814       val = fold_constant_for_init (op0, context);
15815       if (val == NULL_TREE || ! TREE_CONSTANT (val))
15816         return NULL_TREE;
15817       TREE_OPERAND (node, 0) = val;
15818       val = fold_constant_for_init (op1, context);
15819       if (val == NULL_TREE || ! TREE_CONSTANT (val))
15820         return NULL_TREE;
15821       TREE_OPERAND (node, 1) = val;
15822       return patch_binop (node, op0, op1);
15823
15824     case UNARY_PLUS_EXPR:
15825     case NEGATE_EXPR:
15826     case TRUTH_NOT_EXPR:
15827     case BIT_NOT_EXPR:
15828     case CONVERT_EXPR:
15829       op0 = TREE_OPERAND (node, 0);
15830       val = fold_constant_for_init (op0, context);
15831       if (val == NULL_TREE || ! TREE_CONSTANT (val))
15832         return NULL_TREE;
15833       TREE_OPERAND (node, 0) = val;
15834       return patch_unaryop (node, op0);
15835       break;
15836
15837     case COND_EXPR:
15838       val = fold_constant_for_init (TREE_OPERAND (node, 0), context);
15839       if (val == NULL_TREE || ! TREE_CONSTANT (val))
15840         return NULL_TREE;
15841       TREE_OPERAND (node, 0) = val;
15842       val = fold_constant_for_init (TREE_OPERAND (node, 1), context);
15843       if (val == NULL_TREE || ! TREE_CONSTANT (val))
15844         return NULL_TREE;
15845       TREE_OPERAND (node, 1) = val;
15846       val = fold_constant_for_init (TREE_OPERAND (node, 2), context);
15847       if (val == NULL_TREE || ! TREE_CONSTANT (val))
15848         return NULL_TREE;
15849       TREE_OPERAND (node, 2) = val;
15850       return integer_zerop (TREE_OPERAND (node, 0)) ? TREE_OPERAND (node, 1)
15851         : TREE_OPERAND (node, 2);
15852
15853     case VAR_DECL:
15854     case FIELD_DECL:
15855       if (! FIELD_FINAL (node)
15856           || DECL_INITIAL (node) == NULL_TREE)
15857         return NULL_TREE;
15858       val = DECL_INITIAL (node);
15859       /* Guard against infinite recursion. */
15860       DECL_INITIAL (node) = NULL_TREE;
15861       val = fold_constant_for_init (val, node);
15862       DECL_INITIAL (node) = val;
15863       return val;
15864
15865     case EXPR_WITH_FILE_LOCATION:
15866       /* Compare java_complete_tree and resolve_expression_name. */
15867       if (!EXPR_WFL_NODE (node) /* Or a PRIMARY flag ? */
15868           || TREE_CODE (EXPR_WFL_NODE (node)) == IDENTIFIER_NODE)
15869         {
15870           tree name = EXPR_WFL_NODE (node);
15871           tree decl;
15872           if (PRIMARY_P (node))
15873             return NULL_TREE;
15874           else if (! QUALIFIED_P (name))
15875             {
15876               decl = lookup_field_wrapper (DECL_CONTEXT (context), name);
15877               if (decl == NULL_TREE 
15878                   || (! FIELD_STATIC (decl) && ! FIELD_FINAL (decl)))
15879                 return NULL_TREE;
15880               return fold_constant_for_init (decl, decl);
15881             }
15882           else
15883             {
15884               /* Install the proper context for the field resolution.
15885                  The prior context is restored once the name is
15886                  properly qualified. */
15887               tree saved_current_class = current_class;
15888               /* Wait until the USE_COMPONENT_REF re-write.  FIXME. */
15889               current_class = DECL_CONTEXT (context);
15890               qualify_ambiguous_name (node);
15891               current_class = saved_current_class;
15892               if (resolve_field_access (node, &decl, NULL)
15893                   && decl != NULL_TREE)
15894                 return fold_constant_for_init (decl, decl);
15895               return NULL_TREE;
15896             }
15897         }
15898       else
15899         {
15900           op0 = TREE_OPERAND (node, 0);
15901           val = fold_constant_for_init (op0, context);
15902           if (val == NULL_TREE || ! TREE_CONSTANT (val))
15903             return NULL_TREE;
15904           TREE_OPERAND (node, 0) = val;
15905           return val;
15906         }
15907
15908 #ifdef USE_COMPONENT_REF
15909     case IDENTIFIER:
15910     case COMPONENT_REF:
15911       ?;
15912 #endif
15913
15914     default:
15915       return NULL_TREE;
15916     }
15917 }
15918
15919 #ifdef USE_COMPONENT_REF
15920 /* Context is 'T' for TypeName, 'P' for PackageName,
15921    'M' for MethodName, 'E' for ExpressionName, and 'A' for AmbiguousName. */
15922
15923 tree
15924 resolve_simple_name (name, context)
15925      tree name;
15926      int context;
15927 {
15928 }
15929
15930 tree
15931 resolve_qualified_name (name, context)
15932      tree name;
15933      int context;
15934 {
15935 }
15936 #endif
15937
15938 /* Mark P, which is really a `struct parser_ctxt **' for GC.  */
15939
15940 static void
15941 mark_parser_ctxt (p)
15942      void *p;
15943 {
15944   struct parser_ctxt *pc = *((struct parser_ctxt **) p);
15945   int i;
15946
15947   if (!pc)
15948     return;
15949
15950 #ifndef JC1_LITE
15951   for (i = 0; i < 11; ++i)
15952     ggc_mark_tree (pc->modifier_ctx[i]);
15953   ggc_mark_tree (pc->class_type);
15954   ggc_mark_tree (pc->function_decl);
15955   ggc_mark_tree (pc->package);
15956   ggc_mark_tree (pc->class_list);
15957   ggc_mark_tree (pc->current_parsed_class);
15958   ggc_mark_tree (pc->current_parsed_class_un);
15959   ggc_mark_tree (pc->non_static_initialized);
15960   ggc_mark_tree (pc->static_initialized);
15961   ggc_mark_tree (pc->instance_initializers);
15962   ggc_mark_tree (pc->import_list);
15963   ggc_mark_tree (pc->import_demand_list);
15964   ggc_mark_tree (pc->current_loop);
15965   ggc_mark_tree (pc->current_labeled_block);
15966 #endif /* JC1_LITE */
15967
15968   if (pc->next)
15969     mark_parser_ctxt (&pc->next);
15970 }
15971
15972 void
15973 init_src_parse ()
15974 {
15975   /* Register roots with the garbage collector.  */
15976   ggc_add_tree_root (src_parse_roots, sizeof (src_parse_roots) / sizeof(tree));
15977 }
15978
15979 \f
15980
15981 /* This section deals with the functions that are called when tables
15982    recording class initialization information are traversed.  */
15983
15984 /* Attach to PTR (a block) the declaration found in ENTRY. */
15985
15986 static bool
15987 attach_init_test_initialization_flags (entry, ptr)
15988      struct hash_entry *entry;
15989      PTR ptr;
15990 {
15991   tree block = (tree)ptr;
15992   struct init_test_hash_entry *ite = (struct init_test_hash_entry *) entry;
15993   
15994   TREE_CHAIN (ite->init_test_decl) = BLOCK_EXPR_DECLS (block);
15995   BLOCK_EXPR_DECLS (block) = ite->init_test_decl;
15996   return true;
15997 }
15998
15999 /* This function is called for each classes that is known definitely
16000    assigned when a given static method was called. This function
16001    augments a compound expression (INFO) storing all assignment to
16002    initialized static class flags if a flag already existed, otherwise
16003    a new one is created.  */
16004
16005 static bool
16006 emit_test_initialization (entry, info)
16007      struct hash_entry *entry;
16008      PTR info;
16009 {
16010   tree l = (tree) info;
16011   tree decl, init;
16012
16013   struct init_test_hash_entry *ite = (struct init_test_hash_entry *)
16014     hash_lookup (&DECL_FUNCTION_INIT_TEST_TABLE (current_function_decl),
16015                  entry->key,
16016                  current_function_decl != TREE_PURPOSE (l), NULL);
16017
16018   /* If we haven't found a flag and we're dealing with self registered
16019      with current_function_decl, then don't do anything. Self is
16020      always added as definitely initialized but this information is
16021      valid only if used outside the current function. */
16022   if (! ite)
16023     return true;
16024
16025   /* If we don't have a variable, create one and install it. */
16026   if (! ite->init_test_decl)
16027     {
16028       tree block;
16029       
16030       decl = build_decl (VAR_DECL, NULL_TREE, boolean_type_node);
16031       MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC (decl);
16032       LOCAL_CLASS_INITIALIZATION_FLAG (decl) = 1;
16033       DECL_CONTEXT (decl) = current_function_decl;
16034       DECL_INITIAL (decl) = boolean_true_node;
16035
16036       /* The trick is to find the right context for it. */
16037       block = BLOCK_SUBBLOCKS (GET_CURRENT_BLOCK (current_function_decl));
16038       TREE_CHAIN (decl) = BLOCK_EXPR_DECLS (block);
16039       BLOCK_EXPR_DECLS (block) = decl;
16040       ite->init_test_decl = decl;
16041     }
16042   else
16043     decl = ite->init_test_decl;
16044
16045   /* Now simply augment the compound that holds all the assignments
16046      pertaining to this method invocation. */
16047   init = build (MODIFY_EXPR, boolean_type_node, decl, boolean_true_node);
16048   TREE_SIDE_EFFECTS (init) = 1;
16049   TREE_VALUE (l) = add_stmt_to_compound (TREE_VALUE (l), void_type_node, init);
16050   TREE_SIDE_EFFECTS (TREE_VALUE (l)) = 1;
16051
16052   return true;
16053 }