]> gcc.gnu.org Git - gcc.git/blame - gcc/java/parse.y
sparc.md (movtf reg/reg split): Don't generate SUBREGs by hand, gen the appropriate...
[gcc.git] / gcc / java / parse.y
CommitLineData
e04a16fb
AG
1/* Source code parsing and tree node generation for the GNU compiler
2 for the Java(TM) language.
e511adc0 3 Copyright (C) 1997, 1998, 1999 Free Software Foundation, Inc.
e04a16fb
AG
4 Contributed by Alexandre Petit-Bianco (apbianco@cygnus.com)
5
6This file is part of GNU CC.
7
8GNU CC is free software; you can redistribute it and/or modify
9it under the terms of the GNU General Public License as published by
10the Free Software Foundation; either version 2, or (at your option)
11any later version.
12
13GNU CC is distributed in the hope that it will be useful,
14but WITHOUT ANY WARRANTY; without even the implied warranty of
15MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16GNU General Public License for more details.
17
18You should have received a copy of the GNU General Public License
19along with GNU CC; see the file COPYING. If not, write to
20the Free Software Foundation, 59 Temple Place - Suite 330,
21Boston, MA 02111-1307, USA.
22
23Java and all Java-based marks are trademarks or registered trademarks
24of Sun Microsystems, Inc. in the United States and other countries.
25The Free Software Foundation is independent of Sun Microsystems, Inc. */
26
27/* This file parses java source code and issues a tree node image
28suitable for code generation (byte code and targeted CPU assembly
29language).
30
31The grammar conforms to the Java grammar described in "The Java(TM)
32Language Specification. J. Gosling, B. Joy, G. Steele. Addison Wesley
331996, ISBN 0-201-63451-1"
34
35The following modifications were brought to the original grammar:
36
37method_body: added the rule '| block SC_TK'
e04a16fb
AG
38static_initializer: added the rule 'static block SC_TK'.
39
40Note: All the extra rules described above should go away when the
41 empty_statement rule will work.
42
43statement_nsi: 'nsi' should be read no_short_if.
44
45Some rules have been modified to support JDK1.1 inner classes
46definitions and other extensions. */
47
48%{
e04a16fb 49#include "config.h"
36635152
GS
50#include "system.h"
51#include <dirent.h>
e04a16fb
AG
52#include "tree.h"
53#include "rtl.h"
54#include "obstack.h"
0a2138e2 55#include "toplev.h"
e04a16fb
AG
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"
5e942c50 62#include "convert.h"
63a212ed 63#include "buffer.h"
f099f336 64#include "xref.h"
b384405b 65#include "function.h"
138657ec 66#include "except.h"
0ae70c6a 67#include "defaults.h"
e04a16fb 68
fa322ab5
TT
69#ifndef DIR_SEPARATOR
70#define DIR_SEPARATOR '/'
71#endif
72
82371d41
APB
73/* Local function prototypes */
74static char *java_accstring_lookup PROTO ((int));
49f48c71 75static void classitf_redefinition_error PROTO ((const char *,tree, tree, tree));
82371d41 76static void variable_redefinition_error PROTO ((tree, tree, tree, int));
49f48c71 77static void check_modifiers PROTO ((const char *, int, int));
82371d41
APB
78static tree create_class PROTO ((int, tree, tree, tree));
79static tree create_interface PROTO ((int, tree, tree));
80static tree find_field PROTO ((tree, tree));
81static tree lookup_field_wrapper PROTO ((tree, tree));
82static int duplicate_declaration_error_p PROTO ((tree, tree, tree));
83static void register_fields PROTO ((int, tree, tree));
84static tree parser_qualified_classname PROTO ((tree));
85static int parser_check_super PROTO ((tree, tree, tree));
86static int parser_check_super_interface PROTO ((tree, tree, tree));
87static void check_modifiers_consistency PROTO ((int));
88static tree lookup_cl PROTO ((tree));
89static tree lookup_java_method2 PROTO ((tree, tree, int));
90static tree method_header PROTO ((int, tree, tree, tree));
91static void fix_method_argument_names PROTO ((tree ,tree));
92static tree method_declarator PROTO ((tree, tree));
d4476be2
KG
93static void parse_warning_context PVPROTO ((tree cl, const char *msg, ...))
94 ATTRIBUTE_PRINTF_2;
95static void issue_warning_error_from_context PROTO ((tree, const char *msg, va_list));
8119c720 96static void parse_ctor_invocation_error PROTO ((void));
49f48c71 97static tree parse_jdk1_1_error PROTO ((const char *));
82371d41
APB
98static void complete_class_report_errors PROTO ((jdep *));
99static int process_imports PROTO ((void));
100static void read_import_dir PROTO ((tree));
101static int find_in_imports_on_demand PROTO ((tree));
102static int find_in_imports PROTO ((tree));
103static int check_pkg_class_access PROTO ((tree, tree));
104static tree resolve_package PROTO ((tree, tree *));
49f48c71
KG
105static tree lookup_package_type PROTO ((const char *, int));
106static tree lookup_package_type_and_set_next PROTO ((const char *, int, tree *));
82371d41 107static tree resolve_class PROTO ((tree, tree, tree));
82371d41
APB
108static void declare_local_variables PROTO ((int, tree, tree));
109static void source_start_java_method PROTO ((tree));
110static void source_end_java_method PROTO ((void));
111static void expand_start_java_method PROTO ((tree));
112static tree find_name_in_single_imports PROTO ((tree));
113static void check_abstract_method_header PROTO ((tree));
114static tree lookup_java_interface_method2 PROTO ((tree, tree));
115static tree resolve_expression_name PROTO ((tree, tree *));
116static tree maybe_create_class_interface_decl PROTO ((tree, tree, tree));
117static int check_class_interface_creation PROTO ((int, int, tree,
118 tree, tree, tree));
119static tree patch_method_invocation PROTO ((tree, tree, tree,
89e09b9a 120 int *, tree *));
82371d41
APB
121static int breakdown_qualified PROTO ((tree *, tree *, tree));
122static tree resolve_and_layout PROTO ((tree, tree));
123static tree resolve_no_layout PROTO ((tree, tree));
124static int invocation_mode PROTO ((tree, int));
125static tree find_applicable_accessible_methods_list PROTO ((int, tree,
126 tree, tree));
1982388a
APB
127static void search_applicable_methods_list PROTO ((int, tree, tree, tree,
128 tree *, tree *));
82371d41
APB
129static tree find_most_specific_methods_list PROTO ((tree));
130static int argument_types_convertible PROTO ((tree, tree));
89e09b9a 131static tree patch_invoke PROTO ((tree, tree, tree));
82371d41
APB
132static tree lookup_method_invoke PROTO ((int, tree, tree, tree, tree));
133static tree register_incomplete_type PROTO ((int, tree, tree, tree));
134static tree obtain_incomplete_type PROTO ((tree));
5b09b33e 135static tree java_complete_lhs PROTO ((tree));
82371d41
APB
136static tree java_complete_tree PROTO ((tree));
137static void java_complete_expand_method PROTO ((tree));
138static int unresolved_type_p PROTO ((tree, tree *));
139static void create_jdep_list PROTO ((struct parser_ctxt *));
140static tree build_expr_block PROTO ((tree, tree));
141static tree enter_block PROTO ((void));
142static tree enter_a_block PROTO ((tree));
143static tree exit_block PROTO ((void));
144static tree lookup_name_in_blocks PROTO ((tree));
145static void maybe_absorb_scoping_blocks PROTO ((void));
146static tree build_method_invocation PROTO ((tree, tree));
147static tree build_new_invocation PROTO ((tree, tree));
148static tree build_assignment PROTO ((int, int, tree, tree));
149static tree build_binop PROTO ((enum tree_code, int, tree, tree));
150static int check_final_assignment PROTO ((tree ,tree));
151static tree patch_assignment PROTO ((tree, tree, tree ));
152static tree patch_binop PROTO ((tree, tree, tree));
153static tree build_unaryop PROTO ((int, int, tree));
154static tree build_incdec PROTO ((int, int, tree, int));
155static tree patch_unaryop PROTO ((tree, tree));
156static tree build_cast PROTO ((int, tree, tree));
157static tree build_null_of_type PROTO ((tree));
158static tree patch_cast PROTO ((tree, tree));
159static int valid_ref_assignconv_cast_p PROTO ((tree, tree, int));
160static int valid_builtin_assignconv_identity_widening_p PROTO ((tree, tree));
161static int valid_cast_to_p PROTO ((tree, tree));
162static int valid_method_invocation_conversion_p PROTO ((tree, tree));
163static tree try_builtin_assignconv PROTO ((tree, tree, tree));
164static tree try_reference_assignconv PROTO ((tree, tree));
165static tree build_unresolved_array_type PROTO ((tree));
166static tree build_array_from_name PROTO ((tree, tree, tree, tree *));
167static tree build_array_ref PROTO ((int, tree, tree));
168static tree patch_array_ref PROTO ((tree));
169static tree make_qualified_name PROTO ((tree, tree, int));
170static tree merge_qualified_name PROTO ((tree, tree));
171static tree make_qualified_primary PROTO ((tree, tree, int));
172static int resolve_qualified_expression_name PROTO ((tree, tree *,
173 tree *, tree *));
174static void qualify_ambiguous_name PROTO ((tree));
175static void maybe_generate_clinit PROTO ((void));
176static tree resolve_field_access PROTO ((tree, tree *, tree *));
177static tree build_newarray_node PROTO ((tree, tree, int));
178static tree patch_newarray PROTO ((tree));
179static tree resolve_type_during_patch PROTO ((tree));
180static tree build_this PROTO ((int));
181static tree build_return PROTO ((int, tree));
182static tree patch_return PROTO ((tree));
183static tree maybe_access_field PROTO ((tree, tree, tree));
184static int complete_function_arguments PROTO ((tree));
185static int check_for_static_method_reference PROTO ((tree, tree, tree, tree, tree));
186static int not_accessible_p PROTO ((tree, tree, int));
187static void check_deprecation PROTO ((tree, tree));
188static int class_in_current_package PROTO ((tree));
189static tree build_if_else_statement PROTO ((int, tree, tree, tree));
190static tree patch_if_else_statement PROTO ((tree));
191static tree add_stmt_to_compound PROTO ((tree, tree, tree));
192static tree add_stmt_to_block PROTO ((tree, tree, tree));
193static tree patch_exit_expr PROTO ((tree));
194static tree build_labeled_block PROTO ((int, tree));
b635eb2f 195static tree finish_labeled_statement PROTO ((tree, tree));
82371d41
APB
196static tree build_bc_statement PROTO ((int, int, tree));
197static tree patch_bc_statement PROTO ((tree));
198static tree patch_loop_statement PROTO ((tree));
199static tree build_new_loop PROTO ((tree));
200static tree build_loop_body PROTO ((int, tree, int));
b635eb2f 201static tree finish_loop_body PROTO ((int, tree, tree, int));
82371d41 202static tree build_debugable_stmt PROTO ((int, tree));
b635eb2f 203static tree finish_for_loop PROTO ((int, tree, tree, tree));
82371d41
APB
204static tree patch_switch_statement PROTO ((tree));
205static tree string_constant_concatenation PROTO ((tree, tree));
206static tree build_string_concatenation PROTO ((tree, tree));
207static tree patch_string_cst PROTO ((tree));
208static tree patch_string PROTO ((tree));
a7d8d81f
PB
209static tree build_try_statement PROTO ((int, tree, tree));
210static tree build_try_finally_statement PROTO ((int, tree, tree));
82371d41
APB
211static tree patch_try_statement PROTO ((tree));
212static tree patch_synchronized_statement PROTO ((tree, tree));
213static tree patch_throw_statement PROTO ((tree, tree));
214static void check_thrown_exceptions PROTO ((int, tree));
215static int check_thrown_exceptions_do PROTO ((tree));
216static void purge_unchecked_exceptions PROTO ((tree));
217static void check_throws_clauses PROTO ((tree, tree, tree));
b635eb2f 218static void finish_method_declaration PROTO ((tree));
49f48c71 219static tree build_super_invocation PROTO ((void));
82371d41
APB
220static int verify_constructor_circularity PROTO ((tree, tree));
221static char *constructor_circularity_msg PROTO ((tree, tree));
222static tree build_this_super_qualified_invocation PROTO ((int, tree, tree,
223 int, int));
49f48c71 224static const char *get_printable_method_name PROTO ((tree));
82371d41 225static tree patch_conditional_expr PROTO ((tree, tree, tree));
49f48c71 226static void maybe_generate_finit PROTO ((void));
82371d41 227static void fix_constructors PROTO ((tree));
49f48c71 228static int verify_constructor_super PROTO ((void));
82371d41
APB
229static tree create_artificial_method PROTO ((tree, int, tree, tree, tree));
230static void start_artificial_method_body PROTO ((tree));
231static void end_artificial_method_body PROTO ((tree));
82371d41
APB
232static int check_method_redefinition PROTO ((tree, tree));
233static int reset_method_name PROTO ((tree));
234static void java_check_regular_methods PROTO ((tree));
235static void java_check_abstract_methods PROTO ((tree));
236static tree maybe_build_primttype_type_ref PROTO ((tree, tree));
237static void unreachable_stmt_error PROTO ((tree));
238static tree find_expr_with_wfl PROTO ((tree));
239static void missing_return_error PROTO ((tree));
f8976021
APB
240static tree build_new_array_init PROTO ((int, tree));
241static tree patch_new_array_init PROTO ((tree, tree));
f8976021
APB
242static tree maybe_build_array_element_wfl PROTO ((tree));
243static int array_constructor_check_entry PROTO ((tree, tree));
49f48c71 244static const char *purify_type_name PROTO ((const char *));
5b09b33e 245static tree fold_constant_for_init PROTO ((tree, tree));
e28cd97b 246static tree strip_out_static_field_access_decl PROTO ((tree));
7e21fe59 247static jdeplist *reverse_jdep_list PROTO ((struct parser_ctxt *));
7f10c2e2 248static void static_ref_err PROTO ((tree, tree, tree));
49f48c71
KG
249static void parser_add_interface PROTO ((tree, tree, tree));
250static void add_superinterfaces PROTO ((tree, tree));
251static tree jdep_resolve_class PROTO ((jdep *));
252static int note_possible_classname PROTO ((const char *, int));
253static void java_complete_expand_methods PROTO ((void));
254static void java_expand_finals PROTO ((void));
255static tree cut_identifier_in_qualified PROTO ((tree));
256static tree java_stabilize_reference PROTO ((tree));
257static tree do_unary_numeric_promotion PROTO ((tree));
258static char * operator_string PROTO ((tree));
259static tree do_merge_string_cste PROTO ((tree, const char *, int, int));
260static tree merge_string_cste PROTO ((tree, tree, int));
5cbdba64 261static tree java_refold PROTO ((tree));
be245ac0
KG
262static int java_decl_equiv PROTO ((tree, tree));
263static int binop_compound_p PROTO ((enum tree_code));
264static tree search_loop PROTO ((tree));
265static int labeled_block_contains_loop_p PROTO ((tree, tree));
d593dd8c
KG
266static void check_abstract_method_definitions PROTO ((int, tree, tree));
267static void java_check_abstract_method_definitions PROTO ((tree));
82371d41 268
e04a16fb
AG
269/* Number of error found so far. */
270int java_error_count;
271/* Number of warning found so far. */
272int java_warning_count;
ce6e9147
APB
273/* Tell when not to fold, when doing xrefs */
274int do_not_fold;
e04a16fb
AG
275
276/* The current parser context */
d4370213 277struct parser_ctxt *ctxp;
e04a16fb 278
d4370213 279/* List of things that were analyzed for which code will be generated */
b351b287
APB
280static struct parser_ctxt *ctxp_for_generation = NULL;
281
e04a16fb
AG
282/* binop_lookup maps token to tree_code. It is used where binary
283 operations are involved and required by the parser. RDIV_EXPR
284 covers both integral/floating point division. The code is changed
285 once the type of both operator is worked out. */
286
287static enum tree_code binop_lookup[19] =
288 {
289 PLUS_EXPR, MINUS_EXPR, MULT_EXPR, RDIV_EXPR, TRUNC_MOD_EXPR,
290 LSHIFT_EXPR, RSHIFT_EXPR, URSHIFT_EXPR,
291 BIT_AND_EXPR, BIT_XOR_EXPR, BIT_IOR_EXPR,
292 TRUTH_ANDIF_EXPR, TRUTH_ORIF_EXPR,
293 EQ_EXPR, NE_EXPR, GT_EXPR, GE_EXPR, LT_EXPR, LE_EXPR,
294 };
295#define BINOP_LOOKUP(VALUE) \
296 binop_lookup [((VALUE) - PLUS_TK)% \
297 (sizeof (binop_lookup) / sizeof (binop_lookup[0]))]
298
5cbdba64
APB
299/* This is the end index for binary operators that can also be used
300 in compound assignements. */
301#define BINOP_COMPOUND_CANDIDATES 11
302
e04a16fb
AG
303/* Fake WFL used to report error message. It is initialized once if
304 needed and reused with it's location information is overriden. */
15fdcfe9 305tree wfl_operator = NULL_TREE;
e04a16fb
AG
306
307/* The "$L" identifier we use to create labels. */
b67d701b
PB
308static tree label_id = NULL_TREE;
309
310/* The "StringBuffer" identifier used for the String `+' operator. */
311static tree wfl_string_buffer = NULL_TREE;
312
313/* The "append" identifier used for String `+' operator. */
314static tree wfl_append = NULL_TREE;
315
316/* The "toString" identifier used for String `+' operator. */
317static tree wfl_to_string = NULL_TREE;
ba179f9f
APB
318
319/* The "java.lang" import qualified name. */
320static tree java_lang_id = NULL_TREE;
09ed0f70
APB
321
322/* The "java.lang.Cloneable" qualified name. */
323static tree java_lang_cloneable = NULL_TREE;
f099f336
APB
324
325/* Context and flag for static blocks */
326static tree current_static_block = NULL_TREE;
327
e04a16fb
AG
328%}
329
330%union {
331 tree node;
332 int sub_token;
333 struct {
334 int token;
335 int location;
336 } operator;
337 int value;
338}
339
9ee9b555
KG
340%{
341#include "lex.c"
342%}
343
e04a16fb
AG
344%pure_parser
345
346/* Things defined here have to match the order of what's in the
347 binop_lookup table. */
348
349%token PLUS_TK MINUS_TK MULT_TK DIV_TK REM_TK
350%token LS_TK SRS_TK ZRS_TK
351%token AND_TK XOR_TK OR_TK
352%token BOOL_AND_TK BOOL_OR_TK
353%token EQ_TK NEQ_TK GT_TK GTE_TK LT_TK LTE_TK
354
355/* This maps to the same binop_lookup entry than the token above */
356
357%token PLUS_ASSIGN_TK MINUS_ASSIGN_TK MULT_ASSIGN_TK DIV_ASSIGN_TK
358%token REM_ASSIGN_TK
359%token LS_ASSIGN_TK SRS_ASSIGN_TK ZRS_ASSIGN_TK
360%token AND_ASSIGN_TK XOR_ASSIGN_TK OR_ASSIGN_TK
361
362
363/* Modifier TOKEN have to be kept in this order. Don't scramble it */
364
365%token PUBLIC_TK PRIVATE_TK PROTECTED_TK
366%token STATIC_TK FINAL_TK SYNCHRONIZED_TK
367%token VOLATILE_TK TRANSIENT_TK NATIVE_TK
368%token PAD_TK ABSTRACT_TK MODIFIER_TK
369
370/* Keep those two in order, too */
371%token DECR_TK INCR_TK
372
373/* From now one, things can be in any order */
374
375%token DEFAULT_TK IF_TK THROW_TK
376%token BOOLEAN_TK DO_TK IMPLEMENTS_TK
377%token THROWS_TK BREAK_TK IMPORT_TK
378%token ELSE_TK INSTANCEOF_TK RETURN_TK
379%token VOID_TK CATCH_TK INTERFACE_TK
380%token CASE_TK EXTENDS_TK FINALLY_TK
381%token SUPER_TK WHILE_TK CLASS_TK
382%token SWITCH_TK CONST_TK TRY_TK
383%token FOR_TK NEW_TK CONTINUE_TK
384%token GOTO_TK PACKAGE_TK THIS_TK
385
386%token BYTE_TK SHORT_TK INT_TK LONG_TK
387%token CHAR_TK INTEGRAL_TK
388
389%token FLOAT_TK DOUBLE_TK FP_TK
390
391%token ID_TK
392
393%token REL_QM_TK REL_CL_TK NOT_TK NEG_TK
394
395%token ASSIGN_ANY_TK ASSIGN_TK
396%token OP_TK CP_TK OCB_TK CCB_TK OSB_TK CSB_TK SC_TK C_TK DOT_TK
397
398%token STRING_LIT_TK CHAR_LIT_TK INT_LIT_TK FP_LIT_TK
399%token TRUE_TK FALSE_TK BOOL_LIT_TK NULL_TK
400
401%type <value> modifiers MODIFIER_TK
402
403%type <node> super ID_TK identifier
404%type <node> name simple_name qualified_name
405%type <node> class_declaration type_declaration compilation_unit
406 field_declaration method_declaration extends_interfaces
407 interfaces interface_type_list
408 interface_declaration class_member_declaration
409 import_declarations package_declaration
410 type_declarations interface_body
411 interface_member_declaration constant_declaration
412 interface_member_declarations interface_type
413 abstract_method_declaration interface_type_list
414%type <node> class_body_declaration class_member_declaration
415 static_initializer constructor_declaration block
22eed1e6 416%type <node> class_body_declarations constructor_header
e04a16fb
AG
417%type <node> class_or_interface_type class_type class_type_list
418 constructor_declarator explicit_constructor_invocation
b9f7e36c 419%type <node> dim_expr dim_exprs this_or_super throws
e04a16fb
AG
420
421%type <node> variable_declarator_id variable_declarator
422 variable_declarators variable_initializer
22eed1e6 423 variable_initializers constructor_body
ac825856 424 array_initializer
e04a16fb 425
2e5eb5c5 426%type <node> class_body block_end constructor_block_end
e04a16fb
AG
427%type <node> statement statement_without_trailing_substatement
428 labeled_statement if_then_statement label_decl
429 if_then_else_statement while_statement for_statement
430 statement_nsi labeled_statement_nsi do_statement
431 if_then_else_statement_nsi while_statement_nsi
432 for_statement_nsi statement_expression_list for_init
433 for_update statement_expression expression_statement
434 primary_no_new_array expression primary
435 array_creation_expression array_type
436 class_instance_creation_expression field_access
437 method_invocation array_access something_dot_new
438 argument_list postfix_expression while_expression
439 post_increment_expression post_decrement_expression
440 unary_expression_not_plus_minus unary_expression
441 pre_increment_expression pre_decrement_expression
442 unary_expression_not_plus_minus cast_expression
443 multiplicative_expression additive_expression
444 shift_expression relational_expression
445 equality_expression and_expression
446 exclusive_or_expression inclusive_or_expression
447 conditional_and_expression conditional_or_expression
448 conditional_expression assignment_expression
449 left_hand_side assignment for_header for_begin
450 constant_expression do_statement_begin empty_statement
b67d701b 451 switch_statement synchronized_statement throw_statement
f8976021 452 try_statement switch_expression switch_block
15fdcfe9 453 catches catch_clause catch_clause_parameter finally
e04a16fb
AG
454%type <node> return_statement break_statement continue_statement
455
456%type <operator> ASSIGN_TK MULT_ASSIGN_TK DIV_ASSIGN_TK
457%type <operator> REM_ASSIGN_TK PLUS_ASSIGN_TK MINUS_ASSIGN_TK
458%type <operator> LS_ASSIGN_TK SRS_ASSIGN_TK ZRS_ASSIGN_TK
459%type <operator> AND_ASSIGN_TK XOR_ASSIGN_TK OR_ASSIGN_TK
460%type <operator> ASSIGN_ANY_TK assignment_operator
461%token <operator> EQ_TK GTE_TK ZRS_TK SRS_TK GT_TK LTE_TK LS_TK
462%token <operator> BOOL_AND_TK AND_TK BOOL_OR_TK OR_TK INCR_TK PLUS_TK
463%token <operator> DECR_TK MINUS_TK MULT_TK DIV_TK XOR_TK REM_TK NEQ_TK
7f10c2e2 464%token <operator> NEG_TK REL_QM_TK REL_CL_TK NOT_TK LT_TK OCB_TK CCB_TK
5e942c50 465%token <operator> OP_TK OSB_TK DOT_TK THROW_TK INSTANCEOF_TK
b9f7e36c
APB
466%type <operator> THIS_TK SUPER_TK RETURN_TK BREAK_TK CONTINUE_TK
467%type <operator> CASE_TK DEFAULT_TK TRY_TK CATCH_TK SYNCHRONIZED_TK
e04a16fb
AG
468
469%type <node> method_body
470
471%type <node> literal INT_LIT_TK FP_LIT_TK BOOL_LIT_TK CHAR_LIT_TK
472 STRING_LIT_TK NULL_TK VOID_TK
473
474%type <node> IF_TK WHILE_TK FOR_TK
475
476%type <node> formal_parameter_list formal_parameter
477 method_declarator method_header
478
479%type <node> primitive_type reference_type type
480 BOOLEAN_TK INTEGRAL_TK FP_TK
481
482%%
483/* 19.2 Production from 2.3: The Syntactic Grammar */
484goal:
485 compilation_unit
486 {}
487;
488
489/* 19.3 Productions from 3: Lexical structure */
490literal:
491 INT_LIT_TK
492| FP_LIT_TK
493| BOOL_LIT_TK
494| CHAR_LIT_TK
495| STRING_LIT_TK
496| NULL_TK
497;
498
499/* 19.4 Productions from 4: Types, Values and Variables */
500type:
501 primitive_type
502| reference_type
503;
504
505primitive_type:
506 INTEGRAL_TK
507| FP_TK
508| BOOLEAN_TK
509;
510
511reference_type:
512 class_or_interface_type
513| array_type
514;
515
516class_or_interface_type:
517 name
518;
519
520class_type:
521 class_or_interface_type /* Default rule */
522;
523
524interface_type:
525 class_or_interface_type
526;
527
528array_type:
529 primitive_type OSB_TK CSB_TK
530 {
531 $$ = build_java_array_type ($1, -1);
532 CLASS_LOADED_P ($$) = 1;
533 }
534| name OSB_TK CSB_TK
535 { $$ = build_unresolved_array_type ($1); }
536| array_type OSB_TK CSB_TK
537 { $$ = build_unresolved_array_type ($1); }
538| primitive_type OSB_TK error
539 {RULE ("']' expected"); RECOVER;}
540| array_type OSB_TK error
541 {RULE ("']' expected"); RECOVER;}
542;
543
544/* 19.5 Productions from 6: Names */
545name:
546 simple_name /* Default rule */
547| qualified_name /* Default rule */
548;
549
550simple_name:
551 identifier /* Default rule */
552;
553
554qualified_name:
555 name DOT_TK identifier
556 { $$ = make_qualified_name ($1, $3, $2.location); }
557;
558
559identifier:
560 ID_TK
561;
562
563/* 19.6: Production from 7: Packages */
564compilation_unit:
565 {$$ = NULL;}
566| package_declaration
567| import_declarations
568| type_declarations
569| package_declaration import_declarations
570| package_declaration type_declarations
571| import_declarations type_declarations
572| package_declaration import_declarations type_declarations
573;
574
575import_declarations:
576 import_declaration
577 {
578 $$ = NULL;
579 }
580| import_declarations import_declaration
581 {
582 $$ = NULL;
583 }
584;
585
586type_declarations:
587 type_declaration
588| type_declarations type_declaration
589;
590
591package_declaration:
592 PACKAGE_TK name SC_TK
593 { ctxp->package = EXPR_WFL_NODE ($2); }
594| PACKAGE_TK error
595 {yyerror ("Missing name"); RECOVER;}
596| PACKAGE_TK name error
597 {yyerror ("';' expected"); RECOVER;}
598;
599
600import_declaration:
601 single_type_import_declaration
602| type_import_on_demand_declaration
603;
604
605single_type_import_declaration:
606 IMPORT_TK name SC_TK
607 {
608 tree name = EXPR_WFL_NODE ($2), node, last_name;
609 int i = IDENTIFIER_LENGTH (name)-1;
49f48c71 610 const char *last = &IDENTIFIER_POINTER (name)[i];
e04a16fb
AG
611 while (last != IDENTIFIER_POINTER (name))
612 {
613 if (last [0] == '.')
614 break;
615 last--;
616 }
617 last_name = get_identifier (++last);
618 if (IS_A_SINGLE_IMPORT_CLASSFILE_NAME_P (last_name))
619 {
620 tree err = find_name_in_single_imports (last_name);
621 if (err && err != name)
622 parse_error_context
623 ($2, "Ambiguous class: `%s' and `%s'",
624 IDENTIFIER_POINTER (name),
625 IDENTIFIER_POINTER (err));
5e942c50
APB
626 else
627 REGISTER_IMPORT ($2, last_name)
e04a16fb
AG
628 }
629 else
5e942c50 630 REGISTER_IMPORT ($2, last_name);
e04a16fb
AG
631 }
632| IMPORT_TK error
633 {yyerror ("Missing name"); RECOVER;}
634| IMPORT_TK name error
635 {yyerror ("';' expected"); RECOVER;}
636;
637
638type_import_on_demand_declaration:
639 IMPORT_TK name DOT_TK MULT_TK SC_TK
640 {
641 tree name = EXPR_WFL_NODE ($2);
ba179f9f
APB
642 /* Don't import java.lang.* twice. */
643 if (name != java_lang_id)
644 {
645 tree node = build_tree_list ($2, NULL_TREE);
646 read_import_dir ($2);
647 TREE_CHAIN (node) = ctxp->import_demand_list;
648 ctxp->import_demand_list = node;
649 }
e04a16fb
AG
650 }
651| IMPORT_TK name DOT_TK error
652 {yyerror ("'*' expected"); RECOVER;}
653| IMPORT_TK name DOT_TK MULT_TK error
654 {yyerror ("';' expected"); RECOVER;}
655;
656
657type_declaration:
658 class_declaration
659 {
22eed1e6 660 maybe_generate_finit ();
7525cc04 661 maybe_generate_clinit ();
e04a16fb
AG
662 $$ = $1;
663 }
664| interface_declaration
7f1d4866
APB
665 {
666 maybe_generate_clinit ();
667 $$ = $1;
668 }
e04a16fb
AG
669| SC_TK
670 { $$ = NULL; }
671| error
672 {
673 YYERROR_NOW;
674 yyerror ("Class or interface declaration expected");
675 }
676;
677
678/* 19.7 Shortened from the original:
679 modifiers: modifier | modifiers modifier
680 modifier: any of public... */
681modifiers:
682 MODIFIER_TK
683 {
684 $$ = (1 << $1);
685 }
686| modifiers MODIFIER_TK
687 {
688 int acc = (1 << $2);
689 if ($$ & acc)
690 parse_error_context
691 (ctxp->modifier_ctx [$2], "Modifier `%s' declared twice",
692 java_accstring_lookup (acc));
693 else
694 {
695 $$ |= acc;
696 }
697 }
698;
699
700/* 19.8.1 Production from $8.1: Class Declaration */
701class_declaration:
702 modifiers CLASS_TK identifier super interfaces
703 { create_class ($1, $3, $4, $5); }
704 class_body
705 {
706 $$ = $7;
707 }
708| CLASS_TK identifier super interfaces
709 { create_class (0, $2, $3, $4); }
710 class_body
711 {
712 $$ = $6;
713 }
714| modifiers CLASS_TK error
715 {yyerror ("Missing class name"); RECOVER;}
716| CLASS_TK error
717 {yyerror ("Missing class name"); RECOVER;}
718| CLASS_TK identifier error
0b4d333e
APB
719 {
720 if (!ctxp->class_err) yyerror ("'{' expected");
721 DRECOVER(class1);
722 }
e04a16fb
AG
723| modifiers CLASS_TK identifier error
724 {if (!ctxp->class_err) yyerror ("'{' expected"); RECOVER;}
725;
726
727super:
728 { $$ = NULL; }
729| EXTENDS_TK class_type
730 { $$ = $2; }
731| EXTENDS_TK class_type error
732 {yyerror ("'{' expected"); ctxp->class_err=1;}
733| EXTENDS_TK error
734 {yyerror ("Missing super class name"); ctxp->class_err=1;}
735;
736
737interfaces:
738 { $$ = NULL_TREE; }
739| IMPLEMENTS_TK interface_type_list
740 { $$ = $2; }
741| IMPLEMENTS_TK error
742 {
743 ctxp->class_err=1;
744 yyerror ("Missing interface name");
745 }
746;
747
748interface_type_list:
749 interface_type
750 {
751 ctxp->interface_number = 1;
752 $$ = build_tree_list ($1, NULL_TREE);
753 }
754| interface_type_list C_TK interface_type
755 {
756 ctxp->interface_number++;
757 $$ = chainon ($1, build_tree_list ($3, NULL_TREE));
758 }
759| interface_type_list C_TK error
760 {yyerror ("Missing interface name"); RECOVER;}
761;
762
763class_body:
764 OCB_TK CCB_TK
7f10c2e2
APB
765 {
766 /* Store the location of the `}' when doing xrefs */
767 if (flag_emit_xref)
768 DECL_END_SOURCE_LINE (ctxp->current_parsed_class) =
769 EXPR_WFL_ADD_COL ($2.location, 1);
770 $$ = ctxp->current_parsed_class;
771 }
e04a16fb 772| OCB_TK class_body_declarations CCB_TK
7f10c2e2
APB
773 {
774 /* Store the location of the `}' when doing xrefs */
775 if (flag_emit_xref)
776 DECL_END_SOURCE_LINE (ctxp->current_parsed_class) =
777 EXPR_WFL_ADD_COL ($3.location, 1);
778 $$ = ctxp->current_parsed_class;
779 }
e04a16fb
AG
780;
781
782class_body_declarations:
783 class_body_declaration
784| class_body_declarations class_body_declaration
785;
786
787class_body_declaration:
788 class_member_declaration
789| static_initializer
790| constructor_declaration
791| block /* Added, JDK1.1, instance initializer */
b67d701b 792 { $$ = parse_jdk1_1_error ("instance initializer"); }
e04a16fb
AG
793;
794
795class_member_declaration:
796 field_declaration
0b4d333e
APB
797| field_declaration SC_TK
798 { $$ = $1; }
e04a16fb
AG
799| method_declaration
800| class_declaration /* Added, JDK1.1 inner classes */
b67d701b 801 { $$ = parse_jdk1_1_error ("inner classe declaration"); }
e04a16fb 802| interface_declaration /* Added, JDK1.1 inner classes */
b67d701b 803 { $$ = parse_jdk1_1_error ("inner interface declaration"); }
e04a16fb
AG
804;
805
806/* 19.8.2 Productions from 8.3: Field Declarations */
807field_declaration:
808 type variable_declarators SC_TK
809 { register_fields (0, $1, $2); }
810| modifiers type variable_declarators SC_TK
811 {
e04a16fb
AG
812 check_modifiers
813 ("Illegal modifier `%s' for field declaration",
814 $1, FIELD_MODIFIERS);
815 check_modifiers_consistency ($1);
816 register_fields ($1, $2, $3);
817 }
818;
819
820variable_declarators:
821 /* Should we use build_decl_list () instead ? FIXME */
822 variable_declarator /* Default rule */
823| variable_declarators C_TK variable_declarator
824 { $$ = chainon ($1, $3); }
825| variable_declarators C_TK error
826 {yyerror ("Missing term"); RECOVER;}
827;
828
829variable_declarator:
830 variable_declarator_id
831 { $$ = build_tree_list ($1, NULL_TREE); }
832| variable_declarator_id ASSIGN_TK variable_initializer
833 {
834 if (java_error_count)
835 $3 = NULL_TREE;
836 $$ = build_tree_list
837 ($1, build_assignment ($2.token, $2.location, $1, $3));
838 }
839| variable_declarator_id ASSIGN_TK error
840 {
841 yyerror ("Missing variable initializer");
842 $$ = build_tree_list ($1, NULL_TREE);
843 RECOVER;
844 }
845| variable_declarator_id ASSIGN_TK variable_initializer error
846 {
847 yyerror ("';' expected");
848 $$ = build_tree_list ($1, NULL_TREE);
849 RECOVER;
850 }
851;
852
853variable_declarator_id:
854 identifier
855| variable_declarator_id OSB_TK CSB_TK
c583dd46 856 { $$ = build_unresolved_array_type ($1); }
e04a16fb
AG
857| identifier error
858 {yyerror ("Invalid declaration"); DRECOVER(vdi);}
859| variable_declarator_id OSB_TK error
860 {yyerror ("']' expected"); DRECOVER(vdi);}
861| variable_declarator_id CSB_TK error
862 {yyerror ("Unbalanced ']'"); DRECOVER(vdi);}
863;
864
865variable_initializer:
866 expression
867| array_initializer
e04a16fb
AG
868;
869
870/* 19.8.3 Productions from 8.4: Method Declarations */
871method_declaration:
872 method_header
873 {
874 current_function_decl = $1;
875 source_start_java_method (current_function_decl);
876 }
877 method_body
b635eb2f 878 { finish_method_declaration ($3); }
e04a16fb
AG
879| method_header error
880 {YYNOT_TWICE yyerror ("'{' expected"); RECOVER;}
881;
882
883method_header:
884 type method_declarator throws
b9f7e36c 885 { $$ = method_header (0, $1, $2, $3); }
e04a16fb 886| VOID_TK method_declarator throws
b9f7e36c 887 { $$ = method_header (0, void_type_node, $2, $3); }
e04a16fb 888| modifiers type method_declarator throws
b9f7e36c 889 { $$ = method_header ($1, $2, $3, $4); }
e04a16fb 890| modifiers VOID_TK method_declarator throws
b9f7e36c 891 { $$ = method_header ($1, void_type_node, $3, $4); }
e04a16fb 892| type error
efa0a23f
APB
893 {
894 yyerror ("Invalid method declaration, method name required");
895 RECOVER;
896 }
e04a16fb
AG
897| modifiers type error
898 {RECOVER;}
899| VOID_TK error
900 {yyerror ("Identifier expected"); RECOVER;}
901| modifiers VOID_TK error
902 {yyerror ("Identifier expected"); RECOVER;}
903| modifiers error
904 {
905 yyerror ("Invalid method declaration, return type required");
906 RECOVER;
907 }
908;
909
910method_declarator:
911 identifier OP_TK CP_TK
912 { $$ = method_declarator ($1, NULL_TREE); }
913| identifier OP_TK formal_parameter_list CP_TK
914 { $$ = method_declarator ($1, $3); }
915| method_declarator OSB_TK CSB_TK
916 {
1886c9d8
APB
917 EXPR_WFL_LINECOL (wfl_operator) = $2.location;
918 TREE_PURPOSE ($1) =
919 build_unresolved_array_type (TREE_PURPOSE ($1));
920 parse_warning_context
921 (wfl_operator,
922 "Discouraged form of returned type specification");
e04a16fb
AG
923 }
924| identifier OP_TK error
925 {yyerror ("')' expected"); DRECOVER(method_declarator);}
926| method_declarator OSB_TK error
927 {yyerror ("']' expected"); RECOVER;}
928;
929
930formal_parameter_list:
931 formal_parameter
932 {
933 ctxp->formal_parameter_number = 1;
934 }
935| formal_parameter_list C_TK formal_parameter
936 {
937 ctxp->formal_parameter_number += 1;
938 $$ = chainon ($1, $3);
939 }
940| formal_parameter_list C_TK error
941 {yyerror ("Missing formal parameter term"); RECOVER;}
942;
943
944formal_parameter:
945 type variable_declarator_id
946 {
947 $$ = build_tree_list ($2, $1);
948 }
c877974e 949| modifiers type variable_declarator_id /* Added, JDK1.1 final parms */
5256aa37
APB
950 {
951 parse_jdk1_1_error ("final parameters");
952 $$ = build_tree_list ($3, $2);
953 }
e04a16fb
AG
954| type error
955 {yyerror ("Missing identifier"); RECOVER;}
956| modifiers type error
957 {
958 SOURCE_FRONTEND_DEBUG (("Modifiers: %d", $1));
959 yyerror ("Missing identifier"); RECOVER;
960 }
961;
962
963throws:
b9f7e36c 964 { $$ = NULL_TREE; }
e04a16fb 965| THROWS_TK class_type_list
b9f7e36c 966 { $$ = $2; }
e04a16fb
AG
967| THROWS_TK error
968 {yyerror ("Missing class type term"); RECOVER;}
969;
970
971class_type_list:
972 class_type
c877974e 973 { $$ = build_tree_list ($1, $1); }
e04a16fb 974| class_type_list C_TK class_type
c877974e 975 { $$ = tree_cons ($3, $3, $1); }
e04a16fb
AG
976| class_type_list C_TK error
977 {yyerror ("Missing class type term"); RECOVER;}
978;
979
980method_body:
981 block
982| block SC_TK
983| SC_TK
984 { $$ = NULL_TREE; } /* Probably not the right thing to do. */
985;
986
987/* 19.8.4 Productions from 8.5: Static Initializers */
988static_initializer:
989 static block
990 {
f099f336
APB
991 TREE_CHAIN ($2) = ctxp->static_initialized;
992 ctxp->static_initialized = $2;
e04a16fb
AG
993 }
994| static block SC_TK /* Shouldn't be here. FIXME */
995 {
f099f336
APB
996 TREE_CHAIN ($2) = ctxp->static_initialized;
997 ctxp->static_initialized = $2;
e04a16fb
AG
998 }
999;
1000
1001static: /* Test lval.sub_token here */
1002 MODIFIER_TK
1003 {
1004 SOURCE_FRONTEND_DEBUG (("Modifiers: %d", $1));
1005 }
1006;
1007
1008/* 19.8.5 Productions from 8.6: Constructor Declarations */
e04a16fb 1009constructor_declaration:
22eed1e6 1010 constructor_header
e04a16fb 1011 {
22eed1e6
APB
1012 current_function_decl = $1;
1013 source_start_java_method (current_function_decl);
e04a16fb 1014 }
22eed1e6 1015 constructor_body
b635eb2f 1016 { finish_method_declaration ($3); }
22eed1e6
APB
1017;
1018
1019constructor_header:
1020 constructor_declarator throws
1021 { $$ = method_header (0, NULL_TREE, $1, $2); }
1022| modifiers constructor_declarator throws
1023 { $$ = method_header ($1, NULL_TREE, $2, $3); }
e04a16fb
AG
1024;
1025
1026constructor_declarator:
1027 simple_name OP_TK CP_TK
22eed1e6 1028 { $$ = method_declarator ($1, NULL_TREE); }
e04a16fb 1029| simple_name OP_TK formal_parameter_list CP_TK
22eed1e6 1030 { $$ = method_declarator ($1, $3); }
e04a16fb
AG
1031;
1032
1033constructor_body:
22eed1e6
APB
1034 /* Unlike regular method, we always need a complete (empty)
1035 body so we can safely perform all the required code
1036 addition (super invocation and field initialization) */
2e5eb5c5 1037 block_begin constructor_block_end
22eed1e6 1038 {
9bbc7d9f 1039 BLOCK_EXPR_BODY ($2) = empty_stmt_node;
22eed1e6
APB
1040 $$ = $2;
1041 }
2e5eb5c5 1042| block_begin explicit_constructor_invocation constructor_block_end
22eed1e6 1043 { $$ = $3; }
2e5eb5c5 1044| block_begin block_statements constructor_block_end
22eed1e6 1045 { $$ = $3; }
2e5eb5c5 1046| block_begin explicit_constructor_invocation block_statements constructor_block_end
22eed1e6 1047 { $$ = $4; }
e04a16fb
AG
1048;
1049
2e5eb5c5
APB
1050constructor_block_end:
1051 block_end
1052| block_end SC_TK
1053
e04a16fb
AG
1054/* Error recovery for that rule moved down expression_statement: rule. */
1055explicit_constructor_invocation:
1056 this_or_super OP_TK CP_TK SC_TK
22eed1e6
APB
1057 {
1058 $$ = build_method_invocation ($1, NULL_TREE);
1059 $$ = build_debugable_stmt (EXPR_WFL_LINECOL ($1), $$);
1060 $$ = java_method_add_stmt (current_function_decl, $$);
1061 }
e04a16fb 1062| this_or_super OP_TK argument_list CP_TK SC_TK
22eed1e6
APB
1063 {
1064 $$ = build_method_invocation ($1, $3);
1065 $$ = build_debugable_stmt (EXPR_WFL_LINECOL ($1), $$);
1066 $$ = java_method_add_stmt (current_function_decl, $$);
1067 }
e04a16fb
AG
1068 /* Added, JDK1.1 inner classes. Modified because the rule
1069 'primary' couldn't work. */
1070| name DOT_TK SUPER_TK OP_TK argument_list CP_TK SC_TK
b67d701b 1071 {$$ = parse_jdk1_1_error ("explicit constructor invocation"); }
e04a16fb 1072| name DOT_TK SUPER_TK OP_TK CP_TK SC_TK
b67d701b 1073 {$$ = parse_jdk1_1_error ("explicit constructor invocation"); }
e04a16fb
AG
1074;
1075
1076this_or_super: /* Added, simplifies error diagnostics */
1077 THIS_TK
1078 {
9ee9b555 1079 tree wfl = build_wfl_node (this_identifier_node);
e04a16fb
AG
1080 EXPR_WFL_LINECOL (wfl) = $1.location;
1081 $$ = wfl;
1082 }
1083| SUPER_TK
1084 {
9ee9b555 1085 tree wfl = build_wfl_node (super_identifier_node);
e04a16fb
AG
1086 EXPR_WFL_LINECOL (wfl) = $1.location;
1087 $$ = wfl;
1088 }
1089;
1090
1091/* 19.9 Productions from 9: Interfaces */
1092/* 19.9.1 Productions from 9.1: Interfaces Declarations */
1093interface_declaration:
1094 INTERFACE_TK identifier
1095 { create_interface (0, $2, NULL_TREE); }
1096 interface_body
1097 {
1098 $$ = $4;
1099 }
1100| modifiers INTERFACE_TK identifier
1101 { create_interface ($1, $3, NULL_TREE); }
1102 interface_body
1103 {
1104 $$ = $5;
1105 }
1106| INTERFACE_TK identifier extends_interfaces
1107 { create_interface (0, $2, $3); }
1108 interface_body
1109 {
1110 $$ = $5;
1111 }
1112| modifiers INTERFACE_TK identifier extends_interfaces
1113 { create_interface ($1, $3, $4); }
1114 interface_body
1115 {
1116 $$ = $6;
1117 }
1118| INTERFACE_TK identifier error
0b4d333e 1119 {yyerror ("'{' expected"); RECOVER;}
e04a16fb 1120| modifiers INTERFACE_TK identifier error
0b4d333e 1121 {yyerror ("'{' expected"); RECOVER;}
e04a16fb
AG
1122;
1123
1124extends_interfaces:
1125 EXTENDS_TK interface_type
1126 {
1127 ctxp->interface_number = 1;
1128 $$ = build_tree_list ($2, NULL_TREE);
1129 }
1130| extends_interfaces C_TK interface_type
1131 {
1132 ctxp->interface_number++;
1133 $$ = chainon ($1, build_tree_list ($3, NULL_TREE));
1134 }
1135| EXTENDS_TK error
1136 {yyerror ("Invalid interface type"); RECOVER;}
1137| extends_interfaces C_TK error
1138 {yyerror ("Missing term"); RECOVER;}
1139;
1140
1141interface_body:
1142 OCB_TK CCB_TK
1143 { $$ = NULL_TREE; }
1144| OCB_TK interface_member_declarations CCB_TK
1145 { $$ = NULL_TREE; }
1146;
1147
1148interface_member_declarations:
1149 interface_member_declaration
1150| interface_member_declarations interface_member_declaration
1151;
1152
1153interface_member_declaration:
1154 constant_declaration
1155| abstract_method_declaration
1156| class_declaration /* Added, JDK1.1 inner classes */
b67d701b 1157 { $$ = parse_jdk1_1_error ("inner class declaration"); }
e04a16fb 1158| interface_declaration /* Added, JDK1.1 inner classes */
b67d701b 1159 { $$ = parse_jdk1_1_error ("inner interface declaration"); }
e04a16fb
AG
1160;
1161
1162constant_declaration:
1163 field_declaration
1164;
1165
1166abstract_method_declaration:
1167 method_header SC_TK
1168 {
1169 check_abstract_method_header ($1);
1170 current_function_decl = NULL_TREE; /* FIXME ? */
1171 }
1172| method_header error
1173 {yyerror ("';' expected"); RECOVER;}
1174;
1175
1176/* 19.10 Productions from 10: Arrays */
1177array_initializer:
1178 OCB_TK CCB_TK
1179ebc2 1179 { $$ = build_new_array_init ($1.location, NULL_TREE); }
e04a16fb 1180| OCB_TK variable_initializers CCB_TK
f8976021 1181 { $$ = build_new_array_init ($1.location, $2); }
e04a16fb 1182| OCB_TK variable_initializers C_TK CCB_TK
f8976021 1183 { $$ = build_new_array_init ($1.location, $2); }
e04a16fb
AG
1184;
1185
1186variable_initializers:
1187 variable_initializer
f8976021
APB
1188 {
1189 $$ = tree_cons (maybe_build_array_element_wfl ($1),
1190 $1, NULL_TREE);
1191 }
e04a16fb 1192| variable_initializers C_TK variable_initializer
1179ebc2
APB
1193 {
1194 $$ = tree_cons (maybe_build_array_element_wfl ($3), $3, $1);
1195 }
e04a16fb
AG
1196| variable_initializers C_TK error
1197 {yyerror ("Missing term"); RECOVER;}
1198;
1199
1200/* 19.11 Production from 14: Blocks and Statements */
1201block:
1202 OCB_TK CCB_TK
7f10c2e2
APB
1203 {
1204 /* Store the location of the `}' when doing xrefs */
1205 if (current_function_decl && flag_emit_xref)
1206 DECL_END_SOURCE_LINE (current_function_decl) =
1207 EXPR_WFL_ADD_COL ($2.location, 1);
1208 $$ = empty_stmt_node;
1209 }
22eed1e6
APB
1210| block_begin block_statements block_end
1211 { $$ = $3; }
1212;
1213
1214block_begin:
1215 OCB_TK
e04a16fb 1216 { enter_block (); }
22eed1e6
APB
1217;
1218
1219block_end:
e04a16fb
AG
1220 CCB_TK
1221 {
1222 maybe_absorb_scoping_blocks ();
7f10c2e2
APB
1223 /* Store the location of the `}' when doing xrefs */
1224 if (current_function_decl && flag_emit_xref)
1225 DECL_END_SOURCE_LINE (current_function_decl) =
1226 EXPR_WFL_ADD_COL ($1.location, 1);
e04a16fb
AG
1227 $$ = exit_block ();
1228 }
1229;
1230
1231block_statements:
1232 block_statement
1233| block_statements block_statement
1234;
1235
1236block_statement:
1237 local_variable_declaration_statement
1238| statement
15fdcfe9 1239 { java_method_add_stmt (current_function_decl, $1); }
e04a16fb 1240| class_declaration /* Added, JDK1.1 inner classes */
15fdcfe9 1241 { parse_jdk1_1_error ("inner class declaration"); }
e04a16fb
AG
1242;
1243
1244local_variable_declaration_statement:
1245 local_variable_declaration SC_TK /* Can't catch missing ';' here */
1246;
1247
1248local_variable_declaration:
1249 type variable_declarators
1250 { declare_local_variables (0, $1, $2); }
1251| modifiers type variable_declarators /* Added, JDK1.1 final locals */
1252 { declare_local_variables ($1, $2, $3); }
1253;
1254
1255statement:
1256 statement_without_trailing_substatement
1257| labeled_statement
e04a16fb 1258| if_then_statement
e04a16fb 1259| if_then_else_statement
e04a16fb 1260| while_statement
e04a16fb 1261| for_statement
cd9643f7 1262 { $$ = exit_block (); }
e04a16fb
AG
1263;
1264
1265statement_nsi:
1266 statement_without_trailing_substatement
1267| labeled_statement_nsi
e04a16fb 1268| if_then_else_statement_nsi
e04a16fb 1269| while_statement_nsi
e04a16fb 1270| for_statement_nsi
9dd939b2 1271 { $$ = exit_block (); }
e04a16fb
AG
1272;
1273
1274statement_without_trailing_substatement:
1275 block
e04a16fb 1276| empty_statement
e04a16fb 1277| expression_statement
e04a16fb 1278| switch_statement
e04a16fb 1279| do_statement
e04a16fb 1280| break_statement
e04a16fb 1281| continue_statement
e04a16fb
AG
1282| return_statement
1283| synchronized_statement
e04a16fb 1284| throw_statement
e04a16fb 1285| try_statement
e04a16fb
AG
1286;
1287
1288empty_statement:
1289 SC_TK
9bbc7d9f 1290 { $$ = empty_stmt_node; }
e04a16fb
AG
1291;
1292
1293label_decl:
1294 identifier REL_CL_TK
1295 {
1296 $$ = build_labeled_block (EXPR_WFL_LINECOL ($1),
0a2138e2 1297 EXPR_WFL_NODE ($1));
e04a16fb
AG
1298 pushlevel (2);
1299 push_labeled_block ($$);
1300 PUSH_LABELED_BLOCK ($$);
1301 }
1302;
1303
1304labeled_statement:
1305 label_decl statement
b635eb2f 1306 { $$ = finish_labeled_statement ($1, $2); }
e04a16fb
AG
1307| identifier error
1308 {yyerror ("':' expected"); RECOVER;}
1309;
1310
1311labeled_statement_nsi:
1312 label_decl statement_nsi
b635eb2f 1313 { $$ = finish_labeled_statement ($1, $2); }
e04a16fb
AG
1314;
1315
1316/* We concentrate here a bunch of error handling rules that we couldn't write
1317 earlier, because expression_statement catches a missing ';'. */
1318expression_statement:
1319 statement_expression SC_TK
1320 {
1321 /* We have a statement. Generate a WFL around it so
1322 we can debug it */
1323 $$ = build_expr_wfl ($1, input_filename, lineno, 0);
1324 /* We know we have a statement, so set the debug
1325 info to be eventually generate here. */
1326 $$ = JAVA_MAYBE_GENERATE_DEBUG_INFO ($$);
1327 }
1328| error SC_TK
1329 {
1330 if (ctxp->prevent_ese != lineno)
1331 yyerror ("Invalid expression statement");
1332 DRECOVER (expr_stmt);
1333 }
1334| error OCB_TK
1335 {
1336 if (ctxp->prevent_ese != lineno)
1337 yyerror ("Invalid expression statement");
1338 DRECOVER (expr_stmt);
1339 }
1340| error CCB_TK
1341 {
1342 if (ctxp->prevent_ese != lineno)
1343 yyerror ("Invalid expression statement");
1344 DRECOVER (expr_stmt);
1345 }
1346| this_or_super OP_TK error
1347 {yyerror ("')' expected"); RECOVER;}
1348| this_or_super OP_TK CP_TK error
22eed1e6 1349 {
8119c720 1350 parse_ctor_invocation_error ();
22eed1e6
APB
1351 RECOVER;
1352 }
e04a16fb
AG
1353| this_or_super OP_TK argument_list error
1354 {yyerror ("')' expected"); RECOVER;}
1355| this_or_super OP_TK argument_list CP_TK error
22eed1e6 1356 {
8119c720 1357 parse_ctor_invocation_error ();
22eed1e6
APB
1358 RECOVER;
1359 }
e04a16fb
AG
1360| name DOT_TK SUPER_TK error
1361 {yyerror ("'(' expected"); RECOVER;}
1362| name DOT_TK SUPER_TK OP_TK error
1363 {yyerror ("')' expected"); RECOVER;}
1364| name DOT_TK SUPER_TK OP_TK argument_list error
1365 {yyerror ("')' expected"); RECOVER;}
1366| name DOT_TK SUPER_TK OP_TK argument_list CP_TK error
1367 {yyerror ("';' expected"); RECOVER;}
1368| name DOT_TK SUPER_TK OP_TK CP_TK error
1369 {yyerror ("';' expected"); RECOVER;}
1370;
1371
1372statement_expression:
1373 assignment
1374| pre_increment_expression
e04a16fb 1375| pre_decrement_expression
e04a16fb 1376| post_increment_expression
e04a16fb 1377| post_decrement_expression
e04a16fb
AG
1378| method_invocation
1379| class_instance_creation_expression
e04a16fb
AG
1380;
1381
1382if_then_statement:
1383 IF_TK OP_TK expression CP_TK statement
2aa11e97
APB
1384 {
1385 $$ = build_if_else_statement ($2.location, $3,
1386 $5, NULL_TREE);
1387 }
e04a16fb
AG
1388| IF_TK error
1389 {yyerror ("'(' expected"); RECOVER;}
1390| IF_TK OP_TK error
1391 {yyerror ("Missing term"); RECOVER;}
1392| IF_TK OP_TK expression error
1393 {yyerror ("')' expected"); RECOVER;}
1394;
1395
1396if_then_else_statement:
1397 IF_TK OP_TK expression CP_TK statement_nsi ELSE_TK statement
2aa11e97 1398 { $$ = build_if_else_statement ($2.location, $3, $5, $7); }
e04a16fb
AG
1399;
1400
1401if_then_else_statement_nsi:
1402 IF_TK OP_TK expression CP_TK statement_nsi ELSE_TK statement_nsi
2aa11e97 1403 { $$ = build_if_else_statement ($2.location, $3, $5, $7); }
e04a16fb
AG
1404;
1405
1406switch_statement:
15fdcfe9
PB
1407 switch_expression
1408 {
1409 enter_block ();
1410 }
1411 switch_block
b67d701b 1412 {
15fdcfe9 1413 /* Make into "proper list" of COMPOUND_EXPRs.
f8976021
APB
1414 I.e. make the last statment also have its own
1415 COMPOUND_EXPR. */
15fdcfe9
PB
1416 maybe_absorb_scoping_blocks ();
1417 TREE_OPERAND ($1, 1) = exit_block ();
b67d701b
PB
1418 $$ = build_debugable_stmt (EXPR_WFL_LINECOL ($1), $1);
1419 }
1420;
1421
1422switch_expression:
1423 SWITCH_TK OP_TK expression CP_TK
1424 {
1425 $$ = build (SWITCH_EXPR, NULL_TREE, $3, NULL_TREE);
1426 EXPR_WFL_LINECOL ($$) = $2.location;
1427 }
e04a16fb
AG
1428| SWITCH_TK error
1429 {yyerror ("'(' expected"); RECOVER;}
1430| SWITCH_TK OP_TK error
1431 {yyerror ("Missing term or ')'"); DRECOVER(switch_statement);}
1432| SWITCH_TK OP_TK expression CP_TK error
1433 {yyerror ("'{' expected"); RECOVER;}
1434;
1435
f8976021
APB
1436/* Default assignment is there to avoid type node on switch_block
1437 node. */
1438
e04a16fb
AG
1439switch_block:
1440 OCB_TK CCB_TK
f8976021 1441 { $$ = NULL_TREE; }
e04a16fb 1442| OCB_TK switch_labels CCB_TK
f8976021 1443 { $$ = NULL_TREE; }
e04a16fb 1444| OCB_TK switch_block_statement_groups CCB_TK
f8976021 1445 { $$ = NULL_TREE; }
e04a16fb 1446| OCB_TK switch_block_statement_groups switch_labels CCB_TK
f8976021 1447 { $$ = NULL_TREE; }
e04a16fb
AG
1448;
1449
1450switch_block_statement_groups:
1451 switch_block_statement_group
1452| switch_block_statement_groups switch_block_statement_group
1453;
1454
1455switch_block_statement_group:
15fdcfe9 1456 switch_labels block_statements
e04a16fb
AG
1457;
1458
e04a16fb
AG
1459switch_labels:
1460 switch_label
1461| switch_labels switch_label
1462;
1463
1464switch_label:
1465 CASE_TK constant_expression REL_CL_TK
b67d701b 1466 {
15fdcfe9
PB
1467 tree lab = build1 (CASE_EXPR, NULL_TREE, $2);
1468 EXPR_WFL_LINECOL (lab) = $1.location;
1469 java_method_add_stmt (current_function_decl, lab);
b67d701b 1470 }
e04a16fb 1471| DEFAULT_TK REL_CL_TK
b67d701b 1472 {
15fdcfe9
PB
1473 tree lab = build1 (DEFAULT_EXPR, NULL_TREE, NULL_TREE);
1474 EXPR_WFL_LINECOL (lab) = $1.location;
1475 java_method_add_stmt (current_function_decl, lab);
b67d701b 1476 }
e04a16fb
AG
1477| CASE_TK error
1478 {yyerror ("Missing or invalid constant expression"); RECOVER;}
1479| CASE_TK constant_expression error
1480 {yyerror ("':' expected"); RECOVER;}
1481| DEFAULT_TK error
1482 {yyerror ("':' expected"); RECOVER;}
1483;
1484
1485while_expression:
1486 WHILE_TK OP_TK expression CP_TK
1487 {
1488 tree body = build_loop_body ($2.location, $3, 0);
1489 $$ = build_new_loop (body);
1490 }
1491;
1492
1493while_statement:
1494 while_expression statement
b635eb2f 1495 { $$ = finish_loop_body (0, NULL_TREE, $2, 0); }
e04a16fb
AG
1496| WHILE_TK error
1497 {YYERROR_NOW; yyerror ("'(' expected"); RECOVER;}
1498| WHILE_TK OP_TK error
1499 {yyerror ("Missing term and ')' expected"); RECOVER;}
1500| WHILE_TK OP_TK expression error
1501 {yyerror ("')' expected"); RECOVER;}
1502;
1503
1504while_statement_nsi:
1505 while_expression statement_nsi
b635eb2f 1506 { $$ = finish_loop_body (0, NULL_TREE, $2, 0); }
e04a16fb
AG
1507;
1508
1509do_statement_begin:
1510 DO_TK
1511 {
1512 tree body = build_loop_body (0, NULL_TREE, 1);
1513 $$ = build_new_loop (body);
1514 }
1515 /* Need error handing here. FIXME */
1516;
1517
1518do_statement:
1519 do_statement_begin statement WHILE_TK OP_TK expression CP_TK SC_TK
b635eb2f 1520 { $$ = finish_loop_body ($4.location, $5, $2, 1); }
e04a16fb
AG
1521;
1522
1523for_statement:
1524 for_begin SC_TK expression SC_TK for_update CP_TK statement
b635eb2f 1525 { $$ = finish_for_loop (EXPR_WFL_LINECOL ($3), $3, $5, $7); }
e04a16fb
AG
1526| for_begin SC_TK SC_TK for_update CP_TK statement
1527 {
b635eb2f 1528 $$ = finish_for_loop (0, NULL_TREE, $4, $6);
e04a16fb
AG
1529 /* We have not condition, so we get rid of the EXIT_EXPR */
1530 LOOP_EXPR_BODY_CONDITION_EXPR (LOOP_EXPR_BODY ($$), 0) =
9bbc7d9f 1531 empty_stmt_node;
e04a16fb
AG
1532 }
1533| for_begin SC_TK error
1534 {yyerror ("Invalid control expression"); RECOVER;}
1535| for_begin SC_TK expression SC_TK error
1536 {yyerror ("Invalid update expression"); RECOVER;}
1537| for_begin SC_TK SC_TK error
1538 {yyerror ("Invalid update expression"); RECOVER;}
1539;
1540
1541for_statement_nsi:
1542 for_begin SC_TK expression SC_TK for_update CP_TK statement_nsi
b635eb2f 1543 { $$ = finish_for_loop (EXPR_WFL_LINECOL ($3), $3, $5, $7);}
e04a16fb
AG
1544| for_begin SC_TK SC_TK for_update CP_TK statement_nsi
1545 {
b635eb2f 1546 $$ = finish_for_loop (0, NULL_TREE, $4, $6);
e04a16fb
AG
1547 /* We have not condition, so we get rid of the EXIT_EXPR */
1548 LOOP_EXPR_BODY_CONDITION_EXPR (LOOP_EXPR_BODY ($$), 0) =
9bbc7d9f 1549 empty_stmt_node;
e04a16fb
AG
1550 }
1551;
1552
1553for_header:
1554 FOR_TK OP_TK
1555 {
1556 /* This scope defined for local variable that may be
1557 defined within the scope of the for loop */
1558 enter_block ();
1559 }
1560| FOR_TK error
1561 {yyerror ("'(' expected"); DRECOVER(for_1);}
1562| FOR_TK OP_TK error
1563 {yyerror ("Invalid init statement"); RECOVER;}
1564;
1565
1566for_begin:
1567 for_header for_init
1568 {
1569 /* We now declare the loop body. The loop is
1570 declared as a for loop. */
1571 tree body = build_loop_body (0, NULL_TREE, 0);
1572 $$ = build_new_loop (body);
1573 IS_FOR_LOOP_P ($$) = 1;
1574 /* The loop is added to the current block the for
1575 statement is defined within */
1576 java_method_add_stmt (current_function_decl, $$);
1577 }
1578;
1579for_init: /* Can be empty */
9bbc7d9f 1580 { $$ = empty_stmt_node; }
e04a16fb
AG
1581| statement_expression_list
1582 {
1583 /* Init statement recorded within the previously
1584 defined block scope */
1585 $$ = java_method_add_stmt (current_function_decl, $1);
1586 }
1587| local_variable_declaration
1588 {
1589 /* Local variable are recorded within the previously
1590 defined block scope */
1591 $$ = NULL_TREE;
1592 }
1593| statement_expression_list error
1594 {yyerror ("';' expected"); DRECOVER(for_init_1);}
1595;
1596
1597for_update: /* Can be empty */
9bbc7d9f 1598 {$$ = empty_stmt_node;}
e04a16fb
AG
1599| statement_expression_list
1600 { $$ = build_debugable_stmt (BUILD_LOCATION (), $1); }
1601;
1602
1603statement_expression_list:
1604 statement_expression
1605 { $$ = add_stmt_to_compound (NULL_TREE, NULL_TREE, $1); }
1606| statement_expression_list C_TK statement_expression
1607 { $$ = add_stmt_to_compound ($1, NULL_TREE, $3); }
1608| statement_expression_list C_TK error
1609 {yyerror ("Missing term"); RECOVER;}
1610;
1611
1612break_statement:
1613 BREAK_TK SC_TK
1614 { $$ = build_bc_statement ($1.location, 1, NULL_TREE); }
1615| BREAK_TK identifier SC_TK
1616 { $$ = build_bc_statement ($1.location, 1, $2); }
1617| BREAK_TK error
1618 {yyerror ("Missing term"); RECOVER;}
1619| BREAK_TK identifier error
1620 {yyerror ("';' expected"); RECOVER;}
1621;
1622
1623continue_statement:
1624 CONTINUE_TK SC_TK
1625 { $$ = build_bc_statement ($1.location, 0, NULL_TREE); }
1626| CONTINUE_TK identifier SC_TK
1627 { $$ = build_bc_statement ($1.location, 0, $2); }
1628| CONTINUE_TK error
1629 {yyerror ("Missing term"); RECOVER;}
1630| CONTINUE_TK identifier error
1631 {yyerror ("';' expected"); RECOVER;}
1632;
1633
1634return_statement:
1635 RETURN_TK SC_TK
1636 { $$ = build_return ($1.location, NULL_TREE); }
1637| RETURN_TK expression SC_TK
1638 { $$ = build_return ($1.location, $2); }
1639| RETURN_TK error
1640 {yyerror ("Missing term"); RECOVER;}
1641| RETURN_TK expression error
1642 {yyerror ("';' expected"); RECOVER;}
1643;
1644
1645throw_statement:
1646 THROW_TK expression SC_TK
b9f7e36c
APB
1647 {
1648 $$ = build1 (THROW_EXPR, NULL_TREE, $2);
1649 EXPR_WFL_LINECOL ($$) = $1.location;
1650 }
e04a16fb
AG
1651| THROW_TK error
1652 {yyerror ("Missing term"); RECOVER;}
1653| THROW_TK expression error
1654 {yyerror ("';' expected"); RECOVER;}
1655;
1656
1657synchronized_statement:
1658 synchronized OP_TK expression CP_TK block
b9f7e36c
APB
1659 {
1660 $$ = build (SYNCHRONIZED_EXPR, NULL_TREE, $3, $5);
1661 EXPR_WFL_LINECOL ($$) =
1662 EXPR_WFL_LINECOL (MODIFIER_WFL (SYNCHRONIZED_TK));
1663 }
e04a16fb
AG
1664| synchronized OP_TK expression CP_TK error
1665 {yyerror ("'{' expected"); RECOVER;}
1666| synchronized error
1667 {yyerror ("'(' expected"); RECOVER;}
1668| synchronized OP_TK error CP_TK
1669 {yyerror ("Missing term"); RECOVER;}
1670| synchronized OP_TK error
1671 {yyerror ("Missing term"); RECOVER;}
1672;
1673
b9f7e36c 1674synchronized:
efa0a23f 1675 modifiers
e04a16fb 1676 {
efa0a23f
APB
1677 check_modifiers ("Illegal modifier `%s'. Only "
1678 "`synchronized' was expected here",
1679 $1, ACC_SYNCHRONIZED);
1680 if ($1 != ACC_SYNCHRONIZED)
1681 MODIFIER_WFL (SYNCHRONIZED_TK) =
1682 build_wfl_node (NULL_TREE);
e04a16fb
AG
1683 }
1684;
1685
1686try_statement:
1687 TRY_TK block catches
a7d8d81f 1688 { $$ = build_try_statement ($1.location, $2, $3); }
e04a16fb 1689| TRY_TK block finally
a7d8d81f 1690 { $$ = build_try_finally_statement ($1.location, $2, $3); }
e04a16fb 1691| TRY_TK block catches finally
2aa11e97
APB
1692 { $$ = build_try_finally_statement
1693 ($1.location, build_try_statement ($1.location,
1694 $2, $3), $4);
1695 }
e04a16fb
AG
1696| TRY_TK error
1697 {yyerror ("'{' expected"); DRECOVER (try_statement);}
1698;
1699
1700catches:
1701 catch_clause
1702| catches catch_clause
b67d701b
PB
1703 {
1704 TREE_CHAIN ($2) = $1;
1705 $$ = $2;
1706 }
e04a16fb
AG
1707;
1708
1709catch_clause:
b67d701b
PB
1710 catch_clause_parameter block
1711 {
1712 java_method_add_stmt (current_function_decl, $2);
1713 exit_block ();
1714 $$ = $1;
1715 }
1716
1717catch_clause_parameter:
1718 CATCH_TK OP_TK formal_parameter CP_TK
1719 {
1720 /* We add a block to define a scope for
1721 formal_parameter (CCBP). The formal parameter is
1722 declared initialized by the appropriate function
1723 call */
1724 tree ccpb = enter_block ();
1725 tree init = build_assignment (ASSIGN_TK, $2.location,
1726 TREE_PURPOSE ($3),
1727 soft_exceptioninfo_call_node);
1728 declare_local_variables (0, TREE_VALUE ($3),
1729 build_tree_list (TREE_PURPOSE ($3),
1730 init));
1731 $$ = build1 (CATCH_EXPR, NULL_TREE, ccpb);
1732 EXPR_WFL_LINECOL ($$) = $1.location;
1733 }
e04a16fb 1734| CATCH_TK error
97f30284 1735 {yyerror ("'(' expected"); RECOVER; $$ = NULL_TREE;}
e04a16fb 1736| CATCH_TK OP_TK error
97f30284
APB
1737 {
1738 yyerror ("Missing term or ')' expected");
1739 RECOVER; $$ = NULL_TREE;
1740 }
b67d701b 1741| CATCH_TK OP_TK error CP_TK /* That's for () */
97f30284 1742 {yyerror ("Missing term"); RECOVER; $$ = NULL_TREE;}
e04a16fb
AG
1743;
1744
1745finally:
1746 FINALLY_TK block
a7d8d81f 1747 { $$ = $2; }
e04a16fb
AG
1748| FINALLY_TK error
1749 {yyerror ("'{' expected"); RECOVER; }
1750;
1751
1752/* 19.12 Production from 15: Expressions */
1753primary:
1754 primary_no_new_array
1755| array_creation_expression
1756;
1757
1758primary_no_new_array:
1759 literal
1760| THIS_TK
1761 { $$ = build_this ($1.location); }
1762| OP_TK expression CP_TK
1763 {$$ = $2;}
1764| class_instance_creation_expression
1765| field_access
1766| method_invocation
1767| array_access
1768 /* type DOT_TK CLASS_TK doens't work. So we split the rule
1769 'type' into its components. Missing is something for array,
1770 which will complete the reference_type part. FIXME */
1771| name DOT_TK CLASS_TK /* Added, JDK1.1 class literals */
c877974e 1772 { $$ = parse_jdk1_1_error ("named class literals"); }
e04a16fb 1773| primitive_type DOT_TK CLASS_TK /* Added, JDK1.1 class literals */
c877974e 1774 { $$ = build_class_ref ($1); }
e04a16fb 1775| VOID_TK DOT_TK CLASS_TK /* Added, JDK1.1 class literals */
c877974e 1776 { $$ = build_class_ref (void_type_node); }
e04a16fb
AG
1777 /* Added, JDK1.1 inner classes. Documentation is wrong
1778 refering to a 'ClassName' (class_name) rule that doesn't
1779 exist. Used name instead. */
1780| name DOT_TK THIS_TK
b67d701b 1781 { $$ = parse_jdk1_1_error ("class literals"); }
e04a16fb
AG
1782| OP_TK expression error
1783 {yyerror ("')' expected"); RECOVER;}
1784| name DOT_TK error
1785 {yyerror ("'class' or 'this' expected" ); RECOVER;}
1786| primitive_type DOT_TK error
1787 {yyerror ("'class' expected" ); RECOVER;}
1788| VOID_TK DOT_TK error
1789 {yyerror ("'class' expected" ); RECOVER;}
1790;
1791
1792class_instance_creation_expression:
1793 NEW_TK class_type OP_TK argument_list CP_TK
b67d701b 1794 { $$ = build_new_invocation ($2, $4); }
e04a16fb 1795| NEW_TK class_type OP_TK CP_TK
b67d701b 1796 { $$ = build_new_invocation ($2, NULL_TREE); }
e04a16fb
AG
1797 /* Added, JDK1.1 inner classes but modified to use
1798 'class_type' instead of 'TypeName' (type_name) mentionned
1799 in the documentation but doesn't exist. */
1800| NEW_TK class_type OP_TK argument_list CP_TK class_body
b67d701b 1801 { $$ = parse_jdk1_1_error ("inner class instance creation"); }
e04a16fb 1802| NEW_TK class_type OP_TK CP_TK class_body
b67d701b 1803 { $$ = parse_jdk1_1_error ("inner class instance creation"); }
e04a16fb
AG
1804 /* Added, JDK1.1 inner classes, modified to use name or
1805 primary instead of primary solely which couldn't work in
1806 all situations. */
1807| something_dot_new identifier OP_TK CP_TK
1808| something_dot_new identifier OP_TK CP_TK class_body
1809| something_dot_new identifier OP_TK argument_list CP_TK
1810| something_dot_new identifier OP_TK argument_list CP_TK class_body
1811| NEW_TK error SC_TK
1812 {yyerror ("'(' expected"); DRECOVER(new_1);}
1813| NEW_TK class_type error
1814 {yyerror ("'(' expected"); RECOVER;}
1815| NEW_TK class_type OP_TK error
1816 {yyerror ("')' or term expected"); RECOVER;}
1817| NEW_TK class_type OP_TK argument_list error
1818 {yyerror ("')' expected"); RECOVER;}
1819| something_dot_new error
1820 {YYERROR_NOW; yyerror ("Identifier expected"); RECOVER;}
1821| something_dot_new identifier error
1822 {yyerror ("'(' expected"); RECOVER;}
1823;
1824
1825something_dot_new: /* Added, not part of the specs. */
1826 name DOT_TK NEW_TK
1827| primary DOT_TK NEW_TK
1828;
1829
1830argument_list:
1831 expression
1832 {
1833 $$ = tree_cons (NULL_TREE, $1, NULL_TREE);
1834 ctxp->formal_parameter_number = 1;
1835 }
1836| argument_list C_TK expression
1837 {
1838 ctxp->formal_parameter_number += 1;
1839 $$ = tree_cons (NULL_TREE, $3, $1);
1840 }
1841| argument_list C_TK error
1842 {yyerror ("Missing term"); RECOVER;}
1843;
1844
1845array_creation_expression:
1846 NEW_TK primitive_type dim_exprs
1847 { $$ = build_newarray_node ($2, $3, 0); }
1848| NEW_TK class_or_interface_type dim_exprs
1849 { $$ = build_newarray_node ($2, $3, 0); }
1850| NEW_TK primitive_type dim_exprs dims
ba179f9f 1851 { $$ = build_newarray_node ($2, $3, CURRENT_OSB (ctxp));}
e04a16fb 1852| NEW_TK class_or_interface_type dim_exprs dims
ba179f9f 1853 { $$ = build_newarray_node ($2, $3, CURRENT_OSB (ctxp));}
e04a16fb
AG
1854 /* Added, JDK1.1 anonymous array. Initial documentation rule
1855 modified */
1856| NEW_TK class_or_interface_type dims array_initializer
b67d701b 1857 { $$ = parse_jdk1_1_error ("anonymous array"); }
e04a16fb 1858| NEW_TK primitive_type dims array_initializer
b67d701b 1859 { $$ = parse_jdk1_1_error ("anonymous array"); }
e04a16fb
AG
1860| NEW_TK error CSB_TK
1861 {yyerror ("'[' expected"); DRECOVER ("]");}
1862| NEW_TK error OSB_TK
1863 {yyerror ("']' expected"); RECOVER;}
1864;
1865
1866dim_exprs:
1867 dim_expr
1868 { $$ = build_tree_list (NULL_TREE, $1); }
1869| dim_exprs dim_expr
1870 { $$ = tree_cons (NULL_TREE, $2, $$); }
1871;
1872
1873dim_expr:
1874 OSB_TK expression CSB_TK
1875 {
1876 EXPR_WFL_LINECOL ($2) = $1.location;
1877 $$ = $2;
1878 }
1879| OSB_TK expression error
1880 {yyerror ("']' expected"); RECOVER;}
1881| OSB_TK error
1882 {
1883 yyerror ("Missing term");
1884 yyerror ("']' expected");
1885 RECOVER;
1886 }
1887;
1888
1889dims:
1890 OSB_TK CSB_TK
ba179f9f
APB
1891 {
1892 int allocate = 0;
1893 /* If not initialized, allocate memory for the osb
1894 numbers stack */
1895 if (!ctxp->osb_limit)
1896 {
1897 allocate = ctxp->osb_limit = 32;
1898 ctxp->osb_depth = -1;
1899 }
1900 /* If capacity overflown, reallocate a bigger chuck */
1901 else if (ctxp->osb_depth+1 == ctxp->osb_limit)
1902 allocate = ctxp->osb_limit << 1;
1903
1904 if (allocate)
1905 {
1906 allocate *= sizeof (int);
1907 if (ctxp->osb_number)
1908 ctxp->osb_number = (int *)xrealloc (ctxp->osb_number,
1909 allocate);
1910 else
1911 ctxp->osb_number = (int *)xmalloc (allocate);
1912 }
1913 ctxp->osb_depth++;
1914 CURRENT_OSB (ctxp) = 1;
1915 }
e04a16fb 1916| dims OSB_TK CSB_TK
ba179f9f 1917 { CURRENT_OSB (ctxp)++; }
e04a16fb
AG
1918| dims OSB_TK error
1919 { yyerror ("']' expected"); RECOVER;}
1920;
1921
1922field_access:
1923 primary DOT_TK identifier
1924 { $$ = make_qualified_primary ($1, $3, $2.location); }
9bbc7d9f
PB
1925 /* FIXME - REWRITE TO:
1926 { $$ = build_binop (COMPONENT_REF, $2.location, $1, $3); } */
e04a16fb
AG
1927| SUPER_TK DOT_TK identifier
1928 {
1929 tree super_wfl =
9ee9b555 1930 build_wfl_node (super_identifier_node);
e04a16fb
AG
1931 EXPR_WFL_LINECOL (super_wfl) = $1.location;
1932 $$ = make_qualified_name (super_wfl, $3, $2.location);
1933 }
1934| SUPER_TK error
1935 {yyerror ("Field expected"); DRECOVER (super_field_acces);}
1936;
1937
1938method_invocation:
1939 name OP_TK CP_TK
1940 { $$ = build_method_invocation ($1, NULL_TREE); }
1941| name OP_TK argument_list CP_TK
1942 { $$ = build_method_invocation ($1, $3); }
1943| primary DOT_TK identifier OP_TK CP_TK
1944 {
22eed1e6
APB
1945 if (TREE_CODE ($1) == THIS_EXPR)
1946 $$ = build_this_super_qualified_invocation
1947 (1, $3, NULL_TREE, 0, $2.location);
1948 else
1949 {
1950 tree invok = build_method_invocation ($3, NULL_TREE);
1951 $$ = make_qualified_primary ($1, invok, $2.location);
1952 }
e04a16fb
AG
1953 }
1954| primary DOT_TK identifier OP_TK argument_list CP_TK
1955 {
22eed1e6
APB
1956 if (TREE_CODE ($1) == THIS_EXPR)
1957 $$ = build_this_super_qualified_invocation
1958 (1, $3, $5, 0, $2.location);
1959 else
1960 {
1961 tree invok = build_method_invocation ($3, $5);
1962 $$ = make_qualified_primary ($1, invok, $2.location);
1963 }
e04a16fb
AG
1964 }
1965| SUPER_TK DOT_TK identifier OP_TK CP_TK
22eed1e6
APB
1966 {
1967 $$ = build_this_super_qualified_invocation
1968 (0, $3, NULL_TREE, $1.location, $2.location);
e04a16fb
AG
1969 }
1970| SUPER_TK DOT_TK identifier OP_TK argument_list CP_TK
1971 {
22eed1e6
APB
1972 $$ = build_this_super_qualified_invocation
1973 (0, $3, $5, $1.location, $2.location);
e04a16fb
AG
1974 }
1975 /* Screws up thing. I let it here until I'm convinced it can
1976 be removed. FIXME
1977| primary DOT_TK error
1978 {yyerror ("'(' expected"); DRECOVER(bad);} */
1979| SUPER_TK DOT_TK error CP_TK
1980 { yyerror ("'(' expected"); DRECOVER (method_invocation); }
1981| SUPER_TK DOT_TK error DOT_TK
1982 { yyerror ("'(' expected"); DRECOVER (method_invocation); }
1983;
1984
1985array_access:
1986 name OSB_TK expression CSB_TK
1987 { $$ = build_array_ref ($2.location, $1, $3); }
1988| primary_no_new_array OSB_TK expression CSB_TK
1989 { $$ = build_array_ref ($2.location, $1, $3); }
1990| name OSB_TK error
1991 {
1992 yyerror ("Missing term and ']' expected");
1993 DRECOVER(array_access);
1994 }
1995| name OSB_TK expression error
1996 {
1997 yyerror ("']' expected");
1998 DRECOVER(array_access);
1999 }
2000| primary_no_new_array OSB_TK error
2001 {
2002 yyerror ("Missing term and ']' expected");
2003 DRECOVER(array_access);
2004 }
2005| primary_no_new_array OSB_TK expression error
2006 {
2007 yyerror ("']' expected");
2008 DRECOVER(array_access);
2009 }
2010;
2011
2012postfix_expression:
2013 primary
2014| name
2015| post_increment_expression
2016| post_decrement_expression
2017;
2018
2019post_increment_expression:
2020 postfix_expression INCR_TK
2021 { $$ = build_incdec ($2.token, $2.location, $1, 1); }
2022;
2023
2024post_decrement_expression:
2025 postfix_expression DECR_TK
2026 { $$ = build_incdec ($2.token, $2.location, $1, 1); }
2027;
2028
2029unary_expression:
2030 pre_increment_expression
2031| pre_decrement_expression
2032| PLUS_TK unary_expression
2033 {$$ = build_unaryop ($1.token, $1.location, $2); }
2034| MINUS_TK unary_expression
2035 {$$ = build_unaryop ($1.token, $1.location, $2); }
2036| unary_expression_not_plus_minus
2037| PLUS_TK error
2038 {yyerror ("Missing term"); RECOVER}
2039| MINUS_TK error
2040 {yyerror ("Missing term"); RECOVER}
2041;
2042
2043pre_increment_expression:
2044 INCR_TK unary_expression
2045 {$$ = build_incdec ($1.token, $1.location, $2, 0); }
2046| INCR_TK error
2047 {yyerror ("Missing term"); RECOVER}
2048;
2049
2050pre_decrement_expression:
2051 DECR_TK unary_expression
2052 {$$ = build_incdec ($1.token, $1.location, $2, 0); }
2053| DECR_TK error
2054 {yyerror ("Missing term"); RECOVER}
2055;
2056
2057unary_expression_not_plus_minus:
2058 postfix_expression
2059| NOT_TK unary_expression
2060 {$$ = build_unaryop ($1.token, $1.location, $2); }
2061| NEG_TK unary_expression
2062 {$$ = build_unaryop ($1.token, $1.location, $2); }
2063| cast_expression
2064| NOT_TK error
2065 {yyerror ("Missing term"); RECOVER}
2066| NEG_TK error
2067 {yyerror ("Missing term"); RECOVER}
2068;
2069
2070cast_expression: /* Error handling here is potentially weak */
2071 OP_TK primitive_type dims CP_TK unary_expression
2072 {
2073 tree type = $2;
ba179f9f 2074 while (CURRENT_OSB (ctxp)--)
e04a16fb 2075 type = build_java_array_type (type, -1);
ba179f9f 2076 ctxp->osb_depth--;
e04a16fb
AG
2077 $$ = build_cast ($1.location, type, $5);
2078 }
2079| OP_TK primitive_type CP_TK unary_expression
2080 { $$ = build_cast ($1.location, $2, $4); }
2081| OP_TK expression CP_TK unary_expression_not_plus_minus
2082 { $$ = build_cast ($1.location, $2, $4); }
2083| OP_TK name dims CP_TK unary_expression_not_plus_minus
2084 {
49f48c71 2085 const char *ptr;
ba179f9f 2086 while (CURRENT_OSB (ctxp)--)
e04a16fb 2087 obstack_1grow (&temporary_obstack, '[');
ba179f9f 2088 ctxp->osb_depth--;
e04a16fb
AG
2089 obstack_grow0 (&temporary_obstack,
2090 IDENTIFIER_POINTER (EXPR_WFL_NODE ($2)),
2091 IDENTIFIER_LENGTH (EXPR_WFL_NODE ($2)));
2092 ptr = obstack_finish (&temporary_obstack);
2093 EXPR_WFL_NODE ($2) = get_identifier (ptr);
2094 $$ = build_cast ($1.location, $2, $5);
2095 }
2096| OP_TK primitive_type OSB_TK error
2097 {yyerror ("']' expected, invalid type expression");}
2098| OP_TK error
2099 {
2100 if (ctxp->prevent_ese != lineno)
2101 yyerror ("Invalid type expression"); RECOVER;
2102 RECOVER;
2103 }
2104| OP_TK primitive_type dims CP_TK error
2105 {yyerror ("Missing term"); RECOVER;}
2106| OP_TK primitive_type CP_TK error
2107 {yyerror ("Missing term"); RECOVER;}
2108| OP_TK name dims CP_TK error
2109 {yyerror ("Missing term"); RECOVER;}
2110;
2111
2112multiplicative_expression:
2113 unary_expression
2114| multiplicative_expression MULT_TK unary_expression
2115 {
2116 $$ = build_binop (BINOP_LOOKUP ($2.token),
2117 $2.location, $1, $3);
2118 }
2119| multiplicative_expression DIV_TK unary_expression
2120 {
2121 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2122 $1, $3);
2123 }
2124| multiplicative_expression REM_TK unary_expression
2125 {
2126 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2127 $1, $3);
2128 }
2129| multiplicative_expression MULT_TK error
2130 {yyerror ("Missing term"); RECOVER;}
2131| multiplicative_expression DIV_TK error
2132 {yyerror ("Missing term"); RECOVER;}
2133| multiplicative_expression REM_TK error
2134 {yyerror ("Missing term"); RECOVER;}
2135;
2136
2137additive_expression:
2138 multiplicative_expression
2139| additive_expression PLUS_TK multiplicative_expression
2140 {
2141 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2142 $1, $3);
2143 }
2144| additive_expression MINUS_TK multiplicative_expression
2145 {
2146 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2147 $1, $3);
2148 }
2149| additive_expression PLUS_TK error
2150 {yyerror ("Missing term"); RECOVER;}
2151| additive_expression MINUS_TK error
2152 {yyerror ("Missing term"); RECOVER;}
2153;
2154
2155shift_expression:
2156 additive_expression
2157| shift_expression LS_TK additive_expression
2158 {
2159 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2160 $1, $3);
2161 }
2162| shift_expression SRS_TK additive_expression
2163 {
2164 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2165 $1, $3);
2166 }
2167| shift_expression ZRS_TK additive_expression
2168 {
2169 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2170 $1, $3);
2171 }
2172| shift_expression LS_TK error
2173 {yyerror ("Missing term"); RECOVER;}
2174| shift_expression SRS_TK error
2175 {yyerror ("Missing term"); RECOVER;}
2176| shift_expression ZRS_TK error
2177 {yyerror ("Missing term"); RECOVER;}
2178;
2179
2180relational_expression:
2181 shift_expression
2182| relational_expression LT_TK shift_expression
2183 {
2184 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2185 $1, $3);
2186 }
2187| relational_expression GT_TK shift_expression
2188 {
2189 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2190 $1, $3);
2191 }
2192| relational_expression LTE_TK shift_expression
2193 {
2194 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2195 $1, $3);
2196 }
2197| relational_expression GTE_TK shift_expression
2198 {
2199 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2200 $1, $3);
2201 }
2202| relational_expression INSTANCEOF_TK reference_type
5e942c50 2203 { $$ = build_binop (INSTANCEOF_EXPR, $2.location, $1, $3); }
e04a16fb
AG
2204| relational_expression LT_TK error
2205 {yyerror ("Missing term"); RECOVER;}
2206| relational_expression GT_TK error
2207 {yyerror ("Missing term"); RECOVER;}
2208| relational_expression LTE_TK error
2209 {yyerror ("Missing term"); RECOVER;}
2210| relational_expression GTE_TK error
2211 {yyerror ("Missing term"); RECOVER;}
2212| relational_expression INSTANCEOF_TK error
2213 {yyerror ("Invalid reference type"); RECOVER;}
2214;
2215
2216equality_expression:
2217 relational_expression
2218| equality_expression EQ_TK relational_expression
2219 {
2220 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2221 $1, $3);
2222 }
2223| equality_expression NEQ_TK relational_expression
2224 {
2225 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2226 $1, $3);
2227 }
2228| equality_expression EQ_TK error
2229 {yyerror ("Missing term"); RECOVER;}
2230| equality_expression NEQ_TK error
2231 {yyerror ("Missing term"); RECOVER;}
2232;
2233
2234and_expression:
2235 equality_expression
2236| and_expression AND_TK equality_expression
2237 {
2238 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2239 $1, $3);
2240 }
2241| and_expression AND_TK error
2242 {yyerror ("Missing term"); RECOVER;}
2243;
2244
2245exclusive_or_expression:
2246 and_expression
2247| exclusive_or_expression XOR_TK and_expression
2248 {
2249 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2250 $1, $3);
2251 }
2252| exclusive_or_expression XOR_TK error
2253 {yyerror ("Missing term"); RECOVER;}
2254;
2255
2256inclusive_or_expression:
2257 exclusive_or_expression
2258| inclusive_or_expression OR_TK exclusive_or_expression
2259 {
2260 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2261 $1, $3);
2262 }
2263| inclusive_or_expression OR_TK error
2264 {yyerror ("Missing term"); RECOVER;}
2265;
2266
2267conditional_and_expression:
2268 inclusive_or_expression
2269| conditional_and_expression BOOL_AND_TK inclusive_or_expression
2270 {
2271 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2272 $1, $3);
2273 }
2274| conditional_and_expression BOOL_AND_TK error
2275 {yyerror ("Missing term"); RECOVER;}
2276;
2277
2278conditional_or_expression:
2279 conditional_and_expression
2280| conditional_or_expression BOOL_OR_TK conditional_and_expression
2281 {
2282 $$ = build_binop (BINOP_LOOKUP ($2.token), $2.location,
2283 $1, $3);
2284 }
2285| conditional_or_expression BOOL_OR_TK error
2286 {yyerror ("Missing term"); RECOVER;}
2287;
2288
2289conditional_expression: /* Error handling here is weak */
2290 conditional_or_expression
2291| conditional_or_expression REL_QM_TK expression REL_CL_TK conditional_expression
22eed1e6
APB
2292 {
2293 $$ = build (CONDITIONAL_EXPR, NULL_TREE, $1, $3, $5);
2294 EXPR_WFL_LINECOL ($$) = $2.location;
2295 }
e04a16fb
AG
2296| conditional_or_expression REL_QM_TK REL_CL_TK error
2297 {
2298 YYERROR_NOW;
2299 yyerror ("Missing term");
2300 DRECOVER (1);
2301 }
2302| conditional_or_expression REL_QM_TK error
2303 {yyerror ("Missing term"); DRECOVER (2);}
2304| conditional_or_expression REL_QM_TK expression REL_CL_TK error
2305 {yyerror ("Missing term"); DRECOVER (3);}
2306;
2307
2308assignment_expression:
2309 conditional_expression
2310| assignment
2311;
2312
2313assignment:
2314 left_hand_side assignment_operator assignment_expression
2315 { $$ = build_assignment ($2.token, $2.location, $1, $3); }
2316| left_hand_side assignment_operator error
2317 {
2318 if (ctxp->prevent_ese != lineno)
2319 yyerror ("Missing term");
2320 DRECOVER (assign);
2321 }
2322;
2323
2324left_hand_side:
2325 name
2326| field_access
2327| array_access
2328;
2329
2330assignment_operator:
2331 ASSIGN_ANY_TK
2332| ASSIGN_TK
2333;
2334
2335expression:
2336 assignment_expression
2337;
2338
2339constant_expression:
2340 expression
2341;
2342
2343%%
2344\f
2345
e04a16fb
AG
2346/* Flag for the error report routine to issue the error the first time
2347 it's called (overriding the default behavior which is to drop the
2348 first invocation and honor the second one, taking advantage of a
2349 richer context. */
2350static int force_error = 0;
2351
2352/* Create a new parser context and make it the current one. */
2353
2354void
2355java_push_parser_context ()
2356{
2357 struct parser_ctxt *new =
23a79c61 2358 (struct parser_ctxt *)xmalloc(sizeof (struct parser_ctxt));
e04a16fb 2359
4504ead1 2360 bzero ((PTR) new, sizeof (struct parser_ctxt));
e04a16fb
AG
2361 new->next = ctxp;
2362 ctxp = new;
2363 if (ctxp->next)
5e942c50
APB
2364 {
2365 ctxp->incomplete_class = ctxp->next->incomplete_class;
2366 ctxp->gclass_list = ctxp->next->gclass_list;
2367 }
e04a16fb
AG
2368}
2369
22eed1e6
APB
2370/* If the first file of a file list was a class file, no context
2371 exists for a source file to be parsed. This boolean remembers that
2372 java_parser_context_save_global might have created a dummy one, so
2373 that java_parser_context_restore_global can pop it. */
2374static int extra_ctxp_pushed_p = 0;
2375
e04a16fb
AG
2376void
2377java_parser_context_save_global ()
2378{
22eed1e6
APB
2379 if (!ctxp)
2380 {
2381 java_push_parser_context ();
2382 extra_ctxp_pushed_p = 1;
2383 }
e04a16fb
AG
2384 ctxp->finput = finput;
2385 ctxp->lineno = lineno;
2386 ctxp->current_class = current_class;
2387 ctxp->filename = input_filename;
2388 ctxp->current_function_decl = current_function_decl;
2389}
2390
2391void
2392java_parser_context_restore_global ()
2393{
2394 finput = ctxp->finput;
2395 lineno = ctxp->lineno;
2396 current_class = ctxp->current_class;
2397 input_filename = ctxp->filename;
2398 current_function_decl = ctxp->current_function_decl;
23a79c61 2399 if (!ctxp->next && extra_ctxp_pushed_p)
22eed1e6
APB
2400 {
2401 java_pop_parser_context (0);
2402 extra_ctxp_pushed_p = 0;
2403 }
e04a16fb
AG
2404}
2405
2406void
b351b287
APB
2407java_pop_parser_context (generate)
2408 int generate;
e04a16fb
AG
2409{
2410 tree current;
5e942c50 2411 struct parser_ctxt *toFree, *next;
e04a16fb 2412
5e942c50
APB
2413 if (!ctxp)
2414 return;
2415
2416 toFree = ctxp;
2417 next = ctxp->next;
e04a16fb
AG
2418 if (next)
2419 {
2420 next->incomplete_class = ctxp->incomplete_class;
5e942c50 2421 next->gclass_list = ctxp->gclass_list;
e04a16fb
AG
2422 lineno = ctxp->lineno;
2423 finput = ctxp->finput;
2424 current_class = ctxp->current_class;
2425 }
2426
2427 /* Set the single import class file flag to 0 for the current list
2428 of imported things */
2429 for (current = ctxp->import_list; current; current = TREE_CHAIN (current))
2430 IS_A_SINGLE_IMPORT_CLASSFILE_NAME_P (TREE_PURPOSE (current)) = 0;
2431
2432 /* And restore those of the previous context */
0a2138e2 2433 if ((ctxp = next)) /* Assignment is really meant here */
e04a16fb
AG
2434 for (current = ctxp->import_list; current; current = TREE_CHAIN (current))
2435 IS_A_SINGLE_IMPORT_CLASSFILE_NAME_P (TREE_PURPOSE (current)) = 1;
2436
b351b287
APB
2437 if (generate)
2438 {
2439 toFree->next = ctxp_for_generation;
2440 ctxp_for_generation = toFree;
2441 }
2442 else
2443 free (toFree);
e04a16fb
AG
2444}
2445
8119c720
APB
2446/* Reporting an constructor invocation error. */
2447static void
2448parse_ctor_invocation_error ()
2449{
2450 if (DECL_CONSTRUCTOR_P (current_function_decl))
2451 yyerror ("Constructor invocation must be first thing in a constructor");
2452 else
2453 yyerror ("Only constructors can invoke constructors");
2454}
2455
2456/* Reporting JDK1.1 features not implemented. */
b67d701b
PB
2457
2458static tree
2459parse_jdk1_1_error (msg)
49f48c71 2460 const char *msg;
b67d701b
PB
2461{
2462 sorry (": `%s' JDK1.1(TM) feature", msg);
2463 java_error_count++;
9bbc7d9f 2464 return empty_stmt_node;
b67d701b
PB
2465}
2466
e04a16fb
AG
2467static int do_warning = 0;
2468
2469void
2470yyerror (msg)
49f48c71 2471 const char *msg;
e04a16fb
AG
2472{
2473 static java_lc elc;
2474 static int prev_lineno;
49f48c71 2475 static const char *prev_msg;
e04a16fb 2476
0a2138e2 2477 int save_lineno;
e04a16fb
AG
2478 char *remainder, *code_from_source;
2479 extern struct obstack temporary_obstack;
2480
2481 if (!force_error && prev_lineno == lineno)
2482 return;
2483
2484 /* Save current error location but report latter, when the context is
2485 richer. */
2486 if (ctxp->java_error_flag == 0)
2487 {
2488 ctxp->java_error_flag = 1;
2489 elc = ctxp->elc;
2490 /* Do something to use the previous line if we're reaching the
2491 end of the file... */
2492#ifdef VERBOSE_SKELETON
2493 printf ("* Error detected (%s)\n", (msg ? msg : "(null)"));
2494#endif
2495 return;
2496 }
2497
2498 /* Ignore duplicate message on the same line. BTW, this is dubious. FIXME */
2499 if (!force_error && msg == prev_msg && prev_lineno == elc.line)
2500 return;
2501
2502 ctxp->java_error_flag = 0;
2503 if (do_warning)
2504 java_warning_count++;
2505 else
2506 java_error_count++;
2507
2508 if (elc.col == 0 && msg[1] == ';')
2509 {
2510 elc.col = ctxp->p_line->char_col-1;
2511 elc.line = ctxp->p_line->lineno;
2512 }
2513
2514 save_lineno = lineno;
2515 prev_lineno = lineno = elc.line;
2516 prev_msg = msg;
2517
2518 code_from_source = java_get_line_col (ctxp->filename, elc.line, elc.col);
2519 obstack_grow0 (&temporary_obstack,
2520 code_from_source, strlen (code_from_source));
2521 remainder = obstack_finish (&temporary_obstack);
2522 if (do_warning)
2523 warning ("%s.\n%s", msg, remainder);
2524 else
2525 error ("%s.\n%s", msg, remainder);
2526
2527 /* This allow us to cheaply avoid an extra 'Invalid expression
2528 statement' error report when errors have been already reported on
2529 the same line. This occurs when we report an error but don't have
2530 a synchronization point other than ';', which
2531 expression_statement is the only one to take care of. */
2532 ctxp->prevent_ese = lineno = save_lineno;
2533}
2534
2535static void
15fdcfe9 2536issue_warning_error_from_context (cl, msg, ap)
5e942c50 2537 tree cl;
d4476be2 2538 const char *msg;
15fdcfe9 2539 va_list ap;
5e942c50 2540{
1886c9d8 2541 char *saved, *saved_input_filename;
15fdcfe9
PB
2542 char buffer [4096];
2543 vsprintf (buffer, msg, ap);
2544 force_error = 1;
5e942c50
APB
2545
2546 ctxp->elc.line = EXPR_WFL_LINENO (cl);
82371d41
APB
2547 ctxp->elc.col = (EXPR_WFL_COLNO (cl) == 0xfff ? -1 :
2548 (EXPR_WFL_COLNO (cl) == 0xffe ? -2 : EXPR_WFL_COLNO (cl)));
5e942c50
APB
2549
2550 /* We have a CL, that's a good reason for using it if it contains data */
2551 saved = ctxp->filename;
2552 if (TREE_CODE (cl) == EXPR_WITH_FILE_LOCATION && EXPR_WFL_FILENAME_NODE (cl))
2553 ctxp->filename = EXPR_WFL_FILENAME (cl);
1886c9d8
APB
2554 saved_input_filename = input_filename;
2555 input_filename = ctxp->filename;
15fdcfe9
PB
2556 java_error (NULL);
2557 java_error (buffer);
5e942c50 2558 ctxp->filename = saved;
1886c9d8 2559 input_filename = saved_input_filename;
15fdcfe9 2560 force_error = 0;
5e942c50
APB
2561}
2562
e04a16fb
AG
2563/* Issue an error message at a current source line CL */
2564
15fdcfe9 2565void
d4476be2 2566parse_error_context VPROTO ((tree cl, const char *msg, ...))
e04a16fb 2567{
d4476be2 2568#ifndef ANSI_PROTOTYPES
e04a16fb 2569 tree cl;
d4476be2 2570 const char *msg;
e04a16fb 2571#endif
e04a16fb
AG
2572 va_list ap;
2573
2574 VA_START (ap, msg);
d4476be2 2575#ifndef ANSI_PROTOTYPES
e04a16fb 2576 cl = va_arg (ap, tree);
d4476be2 2577 msg = va_arg (ap, const char *);
e04a16fb 2578#endif
15fdcfe9
PB
2579 issue_warning_error_from_context (cl, msg, ap);
2580 va_end (ap);
e04a16fb
AG
2581}
2582
2583/* Issue a warning at a current source line CL */
2584
2585static void
d4476be2 2586parse_warning_context VPROTO ((tree cl, const char *msg, ...))
e04a16fb 2587{
d4476be2 2588#ifndef ANSI_PROTOTYPES
e04a16fb 2589 tree cl;
d4476be2 2590 const char *msg;
e04a16fb 2591#endif
e04a16fb
AG
2592 va_list ap;
2593
2594 VA_START (ap, msg);
d4476be2 2595#ifndef ANSI_PROTOTYPES
e04a16fb 2596 cl = va_arg (ap, tree);
d4476be2 2597 msg = va_arg (ap, const char *);
e04a16fb 2598#endif
e04a16fb 2599
c877974e 2600 force_error = do_warning = 1;
15fdcfe9 2601 issue_warning_error_from_context (cl, msg, ap);
c877974e 2602 do_warning = force_error = 0;
15fdcfe9 2603 va_end (ap);
e04a16fb
AG
2604}
2605
82371d41
APB
2606static tree
2607find_expr_with_wfl (node)
2608 tree node;
2609{
2610 while (node)
2611 {
2612 char code;
2613 tree to_return;
2614
2615 switch (TREE_CODE (node))
2616 {
2617 case BLOCK:
c0d87ff6
PB
2618 node = BLOCK_EXPR_BODY (node);
2619 continue;
82371d41
APB
2620
2621 case COMPOUND_EXPR:
2622 to_return = find_expr_with_wfl (TREE_OPERAND (node, 0));
2623 if (to_return)
2624 return to_return;
c0d87ff6
PB
2625 node = TREE_OPERAND (node, 1);
2626 continue;
82371d41
APB
2627
2628 case LOOP_EXPR:
c0d87ff6
PB
2629 node = TREE_OPERAND (node, 0);
2630 continue;
82371d41
APB
2631
2632 case LABELED_BLOCK_EXPR:
c0d87ff6
PB
2633 node = TREE_OPERAND (node, 1);
2634 continue;
2635
82371d41
APB
2636 default:
2637 code = TREE_CODE_CLASS (TREE_CODE (node));
2638 if (((code == '1') || (code == '2') || (code == 'e'))
2639 && EXPR_WFL_LINECOL (node))
2640 return node;
ba179f9f 2641 return NULL_TREE;
82371d41
APB
2642 }
2643 }
2644 return NULL_TREE;
2645}
2646
2647/* Issue a missing return statement error. Uses METHOD to figure the
2648 last line of the method the error occurs in. */
2649
2650static void
2651missing_return_error (method)
2652 tree method;
2653{
2654 EXPR_WFL_SET_LINECOL (wfl_operator, DECL_SOURCE_LINE_LAST (method), -2);
2655 parse_error_context (wfl_operator, "Missing return statement");
2656}
2657
2658/* Issue an unreachable statement error. From NODE, find the next
2659 statement to report appropriately. */
2660static void
2661unreachable_stmt_error (node)
2662 tree node;
2663{
2664 /* Browse node to find the next expression node that has a WFL. Use
2665 the location to report the error */
2666 if (TREE_CODE (node) == COMPOUND_EXPR)
2667 node = find_expr_with_wfl (TREE_OPERAND (node, 1));
2668 else
2669 node = find_expr_with_wfl (node);
2670
2671 if (node)
2672 {
2673 EXPR_WFL_SET_LINECOL (wfl_operator, EXPR_WFL_LINENO (node), -2);
2674 parse_error_context (wfl_operator, "Unreachable statement");
2675 }
2676 else
2677 fatal ("Can't get valid statement - unreachable_stmt_error");
2678}
2679
c877974e 2680int
e04a16fb
AG
2681java_report_errors ()
2682{
2683 if (java_error_count)
2684 fprintf (stderr, "%d error%s",
2685 java_error_count, (java_error_count == 1 ? "" : "s"));
2686 if (java_warning_count)
2687 fprintf (stderr, "%s%d warning%s", (java_error_count ? ", " : ""),
2688 java_warning_count, (java_warning_count == 1 ? "" : "s"));
2689 if (java_error_count || java_warning_count)
2690 putc ('\n', stderr);
c877974e 2691 return java_error_count;
e04a16fb
AG
2692}
2693
2694static char *
2695java_accstring_lookup (flags)
2696 int flags;
2697{
2698 static char buffer [80];
2699#define COPY_RETURN(S) {strcpy (buffer, S); return buffer;}
2700
2701 /* Access modifier looked-up first for easier report on forbidden
2702 access. */
2703 if (flags & ACC_PUBLIC) COPY_RETURN ("public");
2704 if (flags & ACC_PRIVATE) COPY_RETURN ("private");
2705 if (flags & ACC_PROTECTED) COPY_RETURN ("protected");
2706 if (flags & ACC_STATIC) COPY_RETURN ("static");
2707 if (flags & ACC_FINAL) COPY_RETURN ("final");
2708 if (flags & ACC_SYNCHRONIZED) COPY_RETURN ("synchronized");
2709 if (flags & ACC_VOLATILE) COPY_RETURN ("volatile");
2710 if (flags & ACC_TRANSIENT) COPY_RETURN ("transient");
2711 if (flags & ACC_NATIVE) COPY_RETURN ("native");
2712 if (flags & ACC_INTERFACE) COPY_RETURN ("interface");
2713 if (flags & ACC_ABSTRACT) COPY_RETURN ("abstract");
2714
2715 buffer [0] = '\0';
2716 return buffer;
2717#undef COPY_RETURN
2718}
2719
b67d701b
PB
2720/* Issuing error messages upon redefinition of classes, interfaces or
2721 variables. */
2722
e04a16fb 2723static void
b67d701b 2724classitf_redefinition_error (context, id, decl, cl)
49f48c71 2725 const char *context;
e04a16fb
AG
2726 tree id, decl, cl;
2727{
2728 parse_error_context (cl, "%s `%s' already defined in %s:%d",
2729 context, IDENTIFIER_POINTER (id),
2730 DECL_SOURCE_FILE (decl), DECL_SOURCE_LINE (decl));
2731 /* Here we should point out where its redefined. It's a unicode. FIXME */
2732}
2733
b67d701b
PB
2734static void
2735variable_redefinition_error (context, name, type, line)
2736 tree context, name, type;
2737 int line;
2738{
49f48c71 2739 const char *type_name;
b67d701b
PB
2740
2741 /* Figure a proper name for type. We might haven't resolved it */
c877974e
APB
2742 if (TREE_CODE (type) == POINTER_TYPE && !TREE_TYPE (type))
2743 type_name = IDENTIFIER_POINTER (TYPE_NAME (type));
b67d701b 2744 else
0a2138e2 2745 type_name = lang_printable_name (type, 0);
b67d701b
PB
2746
2747 parse_error_context (context,
2748 "Variable `%s' is already defined in this method and "
2749 "was declared `%s %s' at line %d",
2750 IDENTIFIER_POINTER (name),
2751 type_name, IDENTIFIER_POINTER (name), line);
2752}
2753
c583dd46
APB
2754static tree
2755build_array_from_name (type, type_wfl, name, ret_name)
2756 tree type, type_wfl, name, *ret_name;
2757{
2758 int more_dims = 0;
49f48c71 2759 const char *string;
c583dd46
APB
2760
2761 /* Eventually get more dims */
2762 string = IDENTIFIER_POINTER (name);
2763 while (string [more_dims] == '[')
2764 more_dims++;
2765
2766 /* If we have, then craft a new type for this variable */
2767 if (more_dims)
2768 {
c0d87ff6 2769 name = get_identifier (&string [more_dims]);
c583dd46 2770
34f4db93
APB
2771 /* If we have a pointer, use its type */
2772 if (TREE_CODE (type) == POINTER_TYPE)
2773 type = TREE_TYPE (type);
c583dd46
APB
2774
2775 /* Building the first dimension of a primitive type uses this
2776 function */
2777 if (JPRIMITIVE_TYPE_P (type))
2778 {
2779 type = build_java_array_type (type, -1);
22eed1e6 2780 CLASS_LOADED_P (type) = 1;
c583dd46
APB
2781 more_dims--;
2782 }
2783 /* Otherwise, if we have a WFL for this type, use it (the type
2784 is already an array on an unresolved type, and we just keep
2785 on adding dimensions) */
2786 else if (type_wfl)
2787 type = type_wfl;
2788
2789 /* Add all the dimensions */
2790 while (more_dims--)
2791 type = build_unresolved_array_type (type);
2792
2793 /* The type may have been incomplete in the first place */
2794 if (type_wfl)
2795 type = obtain_incomplete_type (type);
2796 }
2797
2798 *ret_name = name;
2799 return type;
2800}
2801
e04a16fb
AG
2802/* Build something that the type identifier resolver will identify as
2803 being an array to an unresolved type. TYPE_WFL is a WFL on a
2804 identifier. */
2805
2806static tree
2807build_unresolved_array_type (type_or_wfl)
2808 tree type_or_wfl;
2809{
49f48c71 2810 const char *ptr;
e04a16fb 2811
1886c9d8 2812 /* TYPE_OR_WFL might be an array on a resolved type. In this case,
e04a16fb
AG
2813 just create a array type */
2814 if (TREE_CODE (type_or_wfl) == RECORD_TYPE)
2815 {
2816 tree type = build_java_array_type (type_or_wfl, -1);
2817 CLASS_LOADED_P (type) = CLASS_LOADED_P (type_or_wfl);
2818 return type;
2819 }
2820
2821 obstack_1grow (&temporary_obstack, '[');
2822 obstack_grow0 (&temporary_obstack,
2823 IDENTIFIER_POINTER (EXPR_WFL_NODE (type_or_wfl)),
2824 IDENTIFIER_LENGTH (EXPR_WFL_NODE (type_or_wfl)));
2825 ptr = obstack_finish (&temporary_obstack);
2826 return build_expr_wfl (get_identifier (ptr),
2827 EXPR_WFL_FILENAME (type_or_wfl),
2828 EXPR_WFL_LINENO (type_or_wfl),
2829 EXPR_WFL_COLNO (type_or_wfl));
2830}
2831
2832/* Check modifiers. If one doesn't fit, retrieve it in its declaration line
2833 and point it out. */
2834
2835static void
2836check_modifiers (message, value, mask)
49f48c71 2837 const char *message;
e04a16fb
AG
2838 int value;
2839 int mask;
2840{
2841 /* Should point out the one that don't fit. ASCII/unicode,
2842 going backward. FIXME */
2843 if (value & ~mask)
2844 {
2845 int i, remainder = value & ~mask;
2846 for (i = 0; i <= 10; i++)
2847 if ((1 << i) & remainder)
2848 parse_error_context (ctxp->modifier_ctx [i], message,
2849 java_accstring_lookup (1 << i));
2850 }
2851}
2852
2853static void
2854parser_add_interface (class_decl, interface_decl, wfl)
2855 tree class_decl, interface_decl, wfl;
2856{
2857 if (maybe_add_interface (TREE_TYPE (class_decl), TREE_TYPE (interface_decl)))
2858 parse_error_context (wfl, "Interface `%s' repeated",
2859 IDENTIFIER_POINTER (DECL_NAME (interface_decl)));
2860}
2861
2862/* Bulk of common class/interface checks. Return 1 if an error was
2863 encountered. TAG is 0 for a class, 1 for an interface. */
2864
2865static int
2866check_class_interface_creation (is_interface, flags, raw_name, qualified_name, decl, cl)
2867 int is_interface, flags;
2868 tree raw_name, qualified_name, decl, cl;
2869{
2870 tree node;
2871
2872 if (!quiet_flag)
2873 fprintf (stderr, " %s %s", (is_interface ? "interface" : "class"),
2874 IDENTIFIER_POINTER (qualified_name));
2875
2876 /* Scope of an interface/class type name:
2877 - Can't be imported by a single type import
2878 - Can't already exists in the package */
2879 if (IS_A_SINGLE_IMPORT_CLASSFILE_NAME_P (raw_name)
2880 && (node = find_name_in_single_imports (raw_name)))
2881 {
2882 parse_error_context
2883 (cl, "%s name `%s' clashes with imported type `%s'",
2884 (is_interface ? "Interface" : "Class"),
2885 IDENTIFIER_POINTER (raw_name), IDENTIFIER_POINTER (node));
2886 return 1;
2887 }
2888 if (decl && CLASS_COMPLETE_P (decl))
2889 {
b67d701b
PB
2890 classitf_redefinition_error ((is_interface ? "Interface" : "Class"),
2891 qualified_name, decl, cl);
e04a16fb
AG
2892 return 1;
2893 }
2894
2895 /* If public, file name should match class/interface name */
2896 if (flags & ACC_PUBLIC)
2897 {
49f48c71 2898 const char *f;
e04a16fb
AG
2899
2900 /* Contains OS dependent assumption on path separator. FIXME */
2901 for (f = &input_filename [strlen (input_filename)];
fa322ab5
TT
2902 f != input_filename && f[0] != '/' && f[0] != DIR_SEPARATOR;
2903 f--)
2904 ;
847fe791 2905 if (f[0] == '/' || f[0] == DIR_SEPARATOR)
e04a16fb
AG
2906 f++;
2907 if (strncmp (IDENTIFIER_POINTER (raw_name),
2908 f , IDENTIFIER_LENGTH (raw_name)) ||
2909 f [IDENTIFIER_LENGTH (raw_name)] != '.')
2910 parse_error_context (cl, "Public %s `%s' must be defined in a file "
2911 "called `%s.java'",
2912 (is_interface ? "interface" : "class"),
2913 IDENTIFIER_POINTER (qualified_name),
2914 IDENTIFIER_POINTER (raw_name));
2915 }
2916
2917 check_modifiers ((is_interface ?
2918 "Illegal modifier `%s' for interface declaration" :
2919 "Illegal modifier `%s' for class declaration"), flags,
2920 (is_interface ? INTERFACE_MODIFIERS : CLASS_MODIFIERS));
2921 return 0;
2922}
2923
2924/* If DECL is NULL, create and push a new DECL, record the current
2925 line CL and do other maintenance things. */
2926
2927static tree
2928maybe_create_class_interface_decl (decl, qualified_name, cl)
2929 tree decl, qualified_name, cl;
2930{
5e942c50 2931 if (!decl)
e04a16fb
AG
2932 decl = push_class (make_class (), qualified_name);
2933
2934 /* Take care of the file and line business */
2935 DECL_SOURCE_FILE (decl) = EXPR_WFL_FILENAME (cl);
f099f336
APB
2936 /* If we're emiting xrefs, store the line/col number information */
2937 if (flag_emit_xref)
2938 DECL_SOURCE_LINE (decl) = EXPR_WFL_LINECOL (cl);
2939 else
2940 DECL_SOURCE_LINE (decl) = EXPR_WFL_LINENO (cl);
e04a16fb 2941 CLASS_FROM_SOURCE_P (TREE_TYPE (decl)) = 1;
b351b287
APB
2942 CLASS_FROM_CURRENTLY_COMPILED_SOURCE_P (TREE_TYPE (decl)) =
2943 IS_A_COMMAND_LINE_FILENAME_P (EXPR_WFL_FILENAME_NODE (cl));
e04a16fb
AG
2944
2945 ctxp->current_parsed_class = decl;
2946
2947 /* Link the declaration to the already seen ones */
2948 TREE_CHAIN (decl) = ctxp->class_list;
2949 ctxp->class_list = decl;
5e942c50 2950
23a79c61 2951 /* Create a new nodes in the global lists */
5e942c50 2952 ctxp->gclass_list = tree_cons (NULL_TREE, decl, ctxp->gclass_list);
23a79c61 2953 all_class_list = tree_cons (NULL_TREE, decl, all_class_list);
5e942c50 2954
e04a16fb
AG
2955 /* Install a new dependency list element */
2956 create_jdep_list (ctxp);
2957
2958 SOURCE_FRONTEND_DEBUG (("Defining class/interface %s",
2959 IDENTIFIER_POINTER (qualified_name)));
2960 return decl;
2961}
2962
2963static void
2964add_superinterfaces (decl, interface_list)
2965 tree decl, interface_list;
2966{
2967 tree node;
2968 /* Superinterface(s): if present and defined, parser_check_super_interface ()
2969 takes care of ensuring that:
2970 - This is an accessible interface type,
2971 - Circularity detection.
2972 parser_add_interface is then called. If present but not defined,
2973 the check operation is delayed until the super interface gets
2974 defined. */
2975 for (node = interface_list; node; node = TREE_CHAIN (node))
2976 {
15fdcfe9 2977 tree current = TREE_PURPOSE (node);
5e942c50
APB
2978 tree idecl = IDENTIFIER_CLASS_VALUE (EXPR_WFL_NODE (current));
2979 if (idecl && CLASS_LOADED_P (TREE_TYPE (idecl)))
e04a16fb 2980 {
5e942c50
APB
2981 if (!parser_check_super_interface (idecl, decl, current))
2982 parser_add_interface (decl, idecl, current);
e04a16fb
AG
2983 }
2984 else
2985 register_incomplete_type (JDEP_INTERFACE,
2986 current, decl, NULL_TREE);
2987 }
2988}
2989
2990/* Create an interface in pass1 and return its decl. Return the
2991 interface's decl in pass 2. */
2992
2993static tree
2994create_interface (flags, id, super)
2995 int flags;
2996 tree id, super;
2997{
e04a16fb
AG
2998 tree raw_name = EXPR_WFL_NODE (id);
2999 tree q_name = parser_qualified_classname (id);
3000 tree decl = IDENTIFIER_CLASS_VALUE (q_name);
3001
3002 EXPR_WFL_NODE (id) = q_name; /* Keep source location, even if refined. */
3003
3004 /* Basic checks: scope, redefinition, modifiers */
3005 if (check_class_interface_creation (1, flags, raw_name, q_name, decl, id))
3006 return NULL_TREE;
3007
3008 /* Interface modifiers check
3009 - public/abstract allowed (already done at that point)
3010 - abstract is obsolete (comes first, it's a warning, or should be)
3011 - Can't use twice the same (checked in the modifier rule) */
c877974e 3012 if ((flags & ACC_ABSTRACT) && flag_redundant)
e04a16fb
AG
3013 parse_warning_context
3014 (MODIFIER_WFL (ABSTRACT_TK),
c877974e 3015 "Redundant use of `abstract' modifier. Interface `%s' is implicitely "
e04a16fb 3016 "abstract", IDENTIFIER_POINTER (raw_name));
e04a16fb
AG
3017
3018 /* Create a new decl if DECL is NULL, otherwise fix it */
3019 decl = maybe_create_class_interface_decl (decl, q_name, id);
3020
3021 /* Set super info and mark the class a complete */
2aa11e97 3022 set_super_info (ACC_INTERFACE | flags, TREE_TYPE (decl),
e04a16fb
AG
3023 object_type_node, ctxp->interface_number);
3024 ctxp->interface_number = 0;
3025 CLASS_COMPLETE_P (decl) = 1;
3026 add_superinterfaces (decl, super);
3027
3028 return decl;
3029}
3030
3031/* Create an class in pass1 and return its decl. Return class
3032 interface's decl in pass 2. */
3033
3034static tree
3035create_class (flags, id, super, interfaces)
3036 int flags;
3037 tree id, super, interfaces;
3038{
e04a16fb
AG
3039 tree raw_name = EXPR_WFL_NODE (id);
3040 tree class_id, decl;
9ee9b555 3041 tree super_decl_type;
e04a16fb
AG
3042
3043 class_id = parser_qualified_classname (id);
3044 decl = IDENTIFIER_CLASS_VALUE (class_id);
5e942c50 3045 ctxp->current_parsed_class_un = EXPR_WFL_NODE (id);
e04a16fb
AG
3046 EXPR_WFL_NODE (id) = class_id;
3047
3048 /* Basic check: scope, redefinition, modifiers */
3049 if (check_class_interface_creation (0, flags, raw_name, class_id, decl, id))
3050 return NULL_TREE;
3051
3052 /* Class modifier check:
3053 - Allowed modifier (already done at that point)
3054 - abstract AND final forbidden
3055 - Public classes defined in the correct file */
3056 if ((flags & ACC_ABSTRACT) && (flags & ACC_FINAL))
3057 parse_error_context (id, "Class `%s' can't be declared both abstract "
3058 "and final", IDENTIFIER_POINTER (raw_name));
3059
3060 /* Create a new decl if DECL is NULL, otherwise fix it */
3061 decl = maybe_create_class_interface_decl (decl, class_id, id);
3062
3063 /* If SUPER exists, use it, otherwise use Object */
3064 if (super)
3065 {
3066 /* Can't extend java.lang.Object */
3067 if (TREE_TYPE (IDENTIFIER_CLASS_VALUE (class_id)) == object_type_node)
3068 {
3069 parse_error_context (id, "Can't extend `java.lang.Object'");
3070 return NULL_TREE;
3071 }
3072
2c3199bc
PB
3073 super_decl_type =
3074 register_incomplete_type (JDEP_SUPER, super, decl, NULL_TREE);
e04a16fb
AG
3075 }
3076 else if (TREE_TYPE (decl) != object_type_node)
3077 super_decl_type = object_type_node;
3078 /* We're defining java.lang.Object */
3079 else
3080 super_decl_type = NULL_TREE;
3081
3082 /* Set super info and mark the class a complete */
3083 set_super_info (flags, TREE_TYPE (decl), super_decl_type,
3084 ctxp->interface_number);
3085 ctxp->interface_number = 0;
3086 CLASS_COMPLETE_P (decl) = 1;
3087 add_superinterfaces (decl, interfaces);
3088
7f10c2e2
APB
3089 /* If doing xref, store the location at which the inherited class
3090 (if any) was seen. */
3091 if (flag_emit_xref && super)
3092 DECL_INHERITED_SOURCE_LINE (decl) = EXPR_WFL_LINECOL (super);
3093
5e942c50
APB
3094 /* Eventually sets the @deprecated tag flag */
3095 CHECK_DEPRECATED (decl);
3096
e04a16fb
AG
3097 return decl;
3098}
3099
3100/* Can't use lookup_field () since we don't want to load the class and
3101 can't set the CLASS_LOADED_P flag */
3102
3103static tree
3104find_field (class, name)
3105 tree class;
3106 tree name;
3107{
3108 tree decl;
3109 for (decl = TYPE_FIELDS (class); decl; decl = TREE_CHAIN (decl))
3110 {
3111 if (DECL_NAME (decl) == name)
3112 return decl;
3113 }
3114 return NULL_TREE;
3115}
3116
3117/* Wrap around lookup_field that doesn't potentially upset the value
3118 of CLASS */
3119
3120static tree
3121lookup_field_wrapper (class, name)
3122 tree class, name;
3123{
3124 tree type = class;
5b09b33e 3125 tree decl;
c877974e 3126 java_parser_context_save_global ();
5b09b33e 3127 decl = lookup_field (&type, name);
c877974e 3128 java_parser_context_restore_global ();
93024893 3129 return decl == error_mark_node ? NULL : decl;
e04a16fb
AG
3130}
3131
3132/* Find duplicate field within the same class declarations and report
c583dd46
APB
3133 the error. Returns 1 if a duplicated field was found, 0
3134 otherwise. */
e04a16fb
AG
3135
3136static int
c583dd46 3137duplicate_declaration_error_p (new_field_name, new_type, cl)
0a2138e2 3138 tree new_field_name, new_type, cl;
e04a16fb
AG
3139{
3140 /* This might be modified to work with method decl as well */
3141 tree decl = find_field (TREE_TYPE (ctxp->current_parsed_class),
3142 new_field_name);
3143 if (decl)
3144 {
c2e3db92 3145 char *t1 = xstrdup (purify_type_name
4a5f66c3
APB
3146 ((TREE_CODE (new_type) == POINTER_TYPE
3147 && TREE_TYPE (new_type) == NULL_TREE) ?
3148 IDENTIFIER_POINTER (TYPE_NAME (new_type)) :
3149 lang_printable_name (new_type, 1)));
c877974e
APB
3150 /* The type may not have been completed by the time we report
3151 the error */
c2e3db92 3152 char *t2 = xstrdup (purify_type_name
4a5f66c3 3153 ((TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE
c877974e
APB
3154 && TREE_TYPE (TREE_TYPE (decl)) == NULL_TREE) ?
3155 IDENTIFIER_POINTER (TYPE_NAME (TREE_TYPE (decl))) :
3156 lang_printable_name (TREE_TYPE (decl), 1)));
e04a16fb
AG
3157 parse_error_context
3158 (cl , "Duplicate variable declaration: `%s %s' was `%s %s' (%s:%d)",
3159 t1, IDENTIFIER_POINTER (new_field_name),
3160 t2, IDENTIFIER_POINTER (DECL_NAME (decl)),
3161 DECL_SOURCE_FILE (decl), DECL_SOURCE_LINE (decl));
3162 free (t1);
3163 free (t2);
c583dd46 3164 return 1;
e04a16fb 3165 }
c583dd46 3166 return 0;
e04a16fb
AG
3167}
3168
3169/* Field registration routine. If TYPE doesn't exist, field
3170 declarations are linked to the undefined TYPE dependency list, to
3171 be later resolved in java_complete_class () */
3172
3173static void
3174register_fields (flags, type, variable_list)
3175 int flags;
3176 tree type, variable_list;
3177{
c583dd46 3178 tree current, saved_type;
e04a16fb
AG
3179 tree class_type = TREE_TYPE (ctxp->current_parsed_class);
3180 int saved_lineno = lineno;
3181 int must_chain = 0;
3182 tree wfl = NULL_TREE;
3183
3184 /* If we're adding fields to interfaces, those fields are public,
3185 static, final */
3186 if (CLASS_INTERFACE (TYPE_NAME (class_type)))
3187 {
3188 OBSOLETE_MODIFIER_WARNING (MODIFIER_WFL (PUBLIC_TK),
3189 flags, ACC_PUBLIC,
3190 "%s", "interface field(s)");
3191 OBSOLETE_MODIFIER_WARNING (MODIFIER_WFL (STATIC_TK),
3192 flags, ACC_STATIC,
3193 "%s", "interface field(s)");
3194 OBSOLETE_MODIFIER_WARNING (MODIFIER_WFL (FINAL_TK),
3195 flags, ACC_FINAL, "%s", "interface field(s)");
3196 check_modifiers ("Illegal interface member modifier `%s'", flags,
3197 INTERFACE_FIELD_MODIFIERS);
3198 flags |= (ACC_PUBLIC | ACC_STATIC | ACC_FINAL);
3199 }
3200
c583dd46
APB
3201 /* Obtain a suitable type for resolution, if necessary */
3202 SET_TYPE_FOR_RESOLUTION (type, wfl, must_chain);
3203
3204 /* If TYPE is fully resolved and we don't have a reference, make one */
1886c9d8 3205 PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
e04a16fb 3206
c583dd46
APB
3207 for (current = variable_list, saved_type = type; current;
3208 current = TREE_CHAIN (current), type = saved_type)
e04a16fb 3209 {
c877974e 3210 tree real_type;
c583dd46 3211 tree field_decl;
e04a16fb
AG
3212 tree cl = TREE_PURPOSE (current);
3213 tree init = TREE_VALUE (current);
3214 tree current_name = EXPR_WFL_NODE (cl);
3215
c583dd46
APB
3216 /* Process NAME, as it may specify extra dimension(s) for it */
3217 type = build_array_from_name (type, wfl, current_name, &current_name);
3218
c583dd46
APB
3219 /* Type adjustment. We may have just readjusted TYPE because
3220 the variable specified more dimensions. Make sure we have
22eed1e6
APB
3221 a reference if we can and don't have one already. Also
3222 change the name if we have an init. */
3223 if (type != saved_type)
3224 {
1886c9d8 3225 PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
22eed1e6
APB
3226 if (init)
3227 EXPR_WFL_NODE (TREE_OPERAND (init, 0)) = current_name;
3228 }
e04a16fb 3229
c877974e
APB
3230 real_type = GET_REAL_TYPE (type);
3231 /* Check for redeclarations */
3232 if (duplicate_declaration_error_p (current_name, real_type, cl))
3233 continue;
3234
c583dd46 3235 /* Set lineno to the line the field was found and create a
5e942c50 3236 declaration for it. Eventually sets the @deprecated tag flag. */
f099f336
APB
3237 if (flag_emit_xref)
3238 lineno = EXPR_WFL_LINECOL (cl);
3239 else
3240 lineno = EXPR_WFL_LINENO (cl);
c877974e 3241 field_decl = add_field (class_type, current_name, real_type, flags);
5e942c50 3242 CHECK_DEPRECATED (field_decl);
c583dd46
APB
3243
3244 /* Check if we must chain. */
3245 if (must_chain)
3246 register_incomplete_type (JDEP_FIELD, wfl, field_decl, type);
e04a16fb 3247
c583dd46
APB
3248 /* If we have an initialization value tied to the field */
3249 if (init)
3250 {
3251 /* The field is declared static */
e04a16fb 3252 if (flags & ACC_STATIC)
e04a16fb 3253 {
7525cc04
APB
3254 /* We include the field and its initialization part into
3255 a list used to generate <clinit>. After <clinit> is
ba179f9f
APB
3256 walked, field initializations will be processed and
3257 fields initialized with known constants will be taken
3258 out of <clinit> and have their DECL_INITIAL set
7525cc04
APB
3259 appropriately. */
3260 TREE_CHAIN (init) = ctxp->static_initialized;
3261 ctxp->static_initialized = init;
7f10c2e2
APB
3262 if (TREE_OPERAND (init, 1)
3263 && TREE_CODE (TREE_OPERAND (init, 1)) == NEW_ARRAY_INIT)
5bba4807 3264 TREE_STATIC (TREE_OPERAND (init, 1)) = 1;
e04a16fb 3265 }
5e942c50
APB
3266 /* A non-static field declared with an immediate initialization is
3267 to be initialized in <init>, if any. This field is remembered
3268 to be processed at the time of the generation of <init>. */
c583dd46
APB
3269 else
3270 {
3271 TREE_CHAIN (init) = ctxp->non_static_initialized;
3272 ctxp->non_static_initialized = init;
3273 }
5b09b33e 3274 MODIFY_EXPR_FROM_INITIALIZATION_P (init) = 1;
8576f094 3275 DECL_INITIAL (field_decl) = TREE_OPERAND (init, 1);
e04a16fb
AG
3276 }
3277 }
3278 lineno = saved_lineno;
3279}
3280
89e09b9a 3281/* Generate the method $finit$ that initializes fields initialized
22eed1e6
APB
3282 upon declaration. */
3283
3284static void
3285maybe_generate_finit ()
3286{
3287 tree mdecl, current;
3288
3289 if (!ctxp->non_static_initialized || java_error_count)
3290 return;
3291
3292 mdecl = create_artificial_method (TREE_TYPE (ctxp->current_parsed_class),
89e09b9a 3293 ACC_PRIVATE, void_type_node,
de4c7b02 3294 finit_identifier_node, end_params_node);
22eed1e6
APB
3295 start_artificial_method_body (mdecl);
3296
3297 ctxp->non_static_initialized = nreverse (ctxp->non_static_initialized);
3298 for (current = ctxp->non_static_initialized; current;
3299 current = TREE_CHAIN (current))
3300 java_method_add_stmt (mdecl,
3301 build_debugable_stmt (EXPR_WFL_LINECOL (current),
3302 current));
3303
3304 end_artificial_method_body (mdecl);
3305 CLASS_HAS_FINIT_P (TREE_TYPE (ctxp->current_parsed_class)) = 1;
3306 ctxp->non_static_initialized = NULL_TREE;
3307}
3308
e04a16fb
AG
3309/* Check whether it is necessary to generate a <clinit> for the class
3310 we just parsed. */
3311
3312static void
3313maybe_generate_clinit ()
3314{
22eed1e6 3315 tree mdecl, c;
e04a16fb
AG
3316
3317 if (!ctxp->static_initialized || java_error_count)
3318 return;
3319
22eed1e6
APB
3320 mdecl = create_artificial_method (TREE_TYPE (ctxp->current_parsed_class),
3321 ACC_STATIC, void_type_node,
de4c7b02 3322 clinit_identifier_node, end_params_node);
22eed1e6 3323 start_artificial_method_body (mdecl);
e04a16fb
AG
3324
3325 /* Keep initialization in order to enforce 8.5 */
3326 ctxp->static_initialized = nreverse (ctxp->static_initialized);
3327
3328 /* We process the list of assignment we produced as the result of
3329 the declaration of initialized static field and add them as
3330 statement to the <clinit> method. */
3331 for (c = ctxp->static_initialized; c; c = TREE_CHAIN (c))
3332 {
3333 /* We build the assignment expression that will initialize the
3334 field to its value. There are strict rules on static
3335 initializers (8.5). FIXME */
22eed1e6
APB
3336 java_method_add_stmt (mdecl,
3337 build_debugable_stmt (EXPR_WFL_LINECOL (c), c));
e04a16fb
AG
3338 }
3339
22eed1e6 3340 end_artificial_method_body (mdecl);
e04a16fb
AG
3341 ctxp->static_initialized = NULL_TREE;
3342}
3343
3344/* Shared accros method_declarator and method_header to remember the
3345 patch stage that was reached during the declaration of the method.
3346 A method DECL is built differently is there is no patch
3347 (JDEP_NO_PATCH) or a patch (JDEP_METHOD or JDEP_METHOD_RETURN)
3348 pending on the currently defined method. */
3349
3350static int patch_stage;
3351
3352/* Check the method declaration and add the method to its current
3353 class. If the argument list is known to contain incomplete types,
3354 the method is partially added and the registration will be resume
22eed1e6
APB
3355 once the method arguments resolved. If TYPE is NULL, we're dealing
3356 with a constructor. */
e04a16fb
AG
3357
3358static tree
3359method_header (flags, type, mdecl, throws)
3360 int flags;
3361 tree type, mdecl, throws;
3362{
3363 tree meth = TREE_VALUE (mdecl);
3364 tree id = TREE_PURPOSE (mdecl);
1886c9d8 3365 tree type_wfl = NULL_TREE;
79d13333
APB
3366 tree meth_name = NULL_TREE;
3367 tree current, orig_arg, this_class;
e04a16fb 3368 int saved_lineno;
1886c9d8 3369 int constructor_ok = 0, must_chain;
e04a16fb
AG
3370
3371 check_modifiers_consistency (flags);
79d13333
APB
3372
3373 if (ctxp->current_parsed_class)
3374 this_class = TREE_TYPE (ctxp->current_parsed_class);
3375 else
3376 return NULL_TREE;
e04a16fb
AG
3377
3378 /* There are some forbidden modifiers for an abstract method and its
3379 class must be abstract as well. */
22eed1e6 3380 if (type && (flags & ACC_ABSTRACT))
e04a16fb
AG
3381 {
3382 ABSTRACT_CHECK (flags, ACC_PRIVATE, id, "Private");
3383 ABSTRACT_CHECK (flags, ACC_STATIC, id, "Static");
3384 ABSTRACT_CHECK (flags, ACC_FINAL, id, "Final");
3385 ABSTRACT_CHECK (flags, ACC_NATIVE, id, "Native");
3386 ABSTRACT_CHECK (flags, ACC_SYNCHRONIZED,id, "Synchronized");
2aa11e97
APB
3387 if (!CLASS_ABSTRACT (TYPE_NAME (this_class))
3388 && !CLASS_INTERFACE (TYPE_NAME (this_class)))
e04a16fb
AG
3389 parse_error_context
3390 (id, "Class `%s' must be declared abstract to define abstract "
3391 "method `%s'",
3392 IDENTIFIER_POINTER (DECL_NAME (ctxp->current_parsed_class)),
3393 IDENTIFIER_POINTER (EXPR_WFL_NODE (id)));
3394 }
22eed1e6
APB
3395 /* Things to be checked when declaring a constructor */
3396 if (!type)
3397 {
3398 int ec = java_error_count;
3399 /* 8.6: Constructor declarations: we might be trying to define a
3400 method without specifying a return type. */
5e942c50 3401 if (EXPR_WFL_NODE (id) != ctxp->current_parsed_class_un)
22eed1e6
APB
3402 parse_error_context
3403 (id, "Invalid method declaration, return type required");
3404 /* 8.6.3: Constructor modifiers */
3405 else
3406 {
3407 JCONSTRUCTOR_CHECK (flags, ACC_ABSTRACT, id, "abstract");
3408 JCONSTRUCTOR_CHECK (flags, ACC_STATIC, id, "static");
3409 JCONSTRUCTOR_CHECK (flags, ACC_FINAL, id, "final");
3410 JCONSTRUCTOR_CHECK (flags, ACC_NATIVE, id, "native");
3411 JCONSTRUCTOR_CHECK (flags, ACC_SYNCHRONIZED, id, "synchronized");
3412 }
3413 /* If we found error here, we don't consider it's OK to tread
3414 the method definition as a constructor, for the rest of this
3415 function */
3416 if (ec == java_error_count)
3417 constructor_ok = 1;
3418 }
e04a16fb
AG
3419
3420 /* Method declared within the scope of an interface are implicitly
3421 abstract and public. Conflicts with other erroneously provided
c0d87ff6 3422 modifiers are checked right after. */
e04a16fb
AG
3423
3424 if (CLASS_INTERFACE (TYPE_NAME (this_class)))
3425 {
3426 /* If FLAGS isn't set because of a modifier, turn the
3427 corresponding modifier WFL to NULL so we issue a warning on
3428 the obsolete use of the modifier */
3429 if (!(flags & ACC_PUBLIC))
3430 MODIFIER_WFL (PUBLIC_TK) = NULL;
3431 if (!(flags & ACC_ABSTRACT))
3432 MODIFIER_WFL (ABSTRACT_TK) = NULL;
3433 flags |= ACC_PUBLIC;
3434 flags |= ACC_ABSTRACT;
3435 }
3436
3437 /* Modifiers context reset moved up, so abstract method declaration
3438 modifiers can be later checked. */
3439
22eed1e6
APB
3440 /* Set constructor returned type to void and method name to <init>,
3441 unless we found an error identifier the constructor (in which
3442 case we retain the original name) */
3443 if (!type)
3444 {
3445 type = void_type_node;
3446 if (constructor_ok)
3447 meth_name = init_identifier_node;
3448 }
3449 else
3450 meth_name = EXPR_WFL_NODE (id);
e04a16fb 3451
1886c9d8
APB
3452 /* Do the returned type resolution and registration if necessary */
3453 SET_TYPE_FOR_RESOLUTION (type, type_wfl, must_chain);
3454
4a5f66c3
APB
3455 if (meth_name)
3456 type = build_array_from_name (type, type_wfl, meth_name, &meth_name);
1886c9d8
APB
3457 EXPR_WFL_NODE (id) = meth_name;
3458 PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
3459
3460 if (must_chain)
e04a16fb 3461 {
1886c9d8
APB
3462 patch_stage = JDEP_METHOD_RETURN;
3463 register_incomplete_type (patch_stage, type_wfl, id, type);
3464 TREE_TYPE (meth) = GET_REAL_TYPE (type);
e04a16fb
AG
3465 }
3466 else
1886c9d8 3467 TREE_TYPE (meth) = type;
e04a16fb
AG
3468
3469 saved_lineno = lineno;
3470 /* When defining an abstract or interface method, the curly
3471 bracket at level 1 doesn't exist because there is no function
3472 body */
3473 lineno = (ctxp->first_ccb_indent1 ? ctxp->first_ccb_indent1 :
3474 EXPR_WFL_LINENO (id));
3475
5e942c50
APB
3476 /* Remember the original argument list */
3477 orig_arg = TYPE_ARG_TYPES (meth);
3478
e04a16fb
AG
3479 if (patch_stage) /* includes ret type and/or all args */
3480 {
3481 jdep *jdep;
3482 meth = add_method_1 (this_class, flags, meth_name, meth);
3483 /* Patch for the return type */
3484 if (patch_stage == JDEP_METHOD_RETURN)
3485 {
3486 jdep = CLASSD_LAST (ctxp->classd_list);
3487 JDEP_GET_PATCH (jdep) = &TREE_TYPE (TREE_TYPE (meth));
3488 }
3489 /* This is the stop JDEP. METH allows the function's signature
3490 to be computed. */
3491 register_incomplete_type (JDEP_METHOD_END, NULL_TREE, meth, NULL_TREE);
3492 }
3493 else
5e942c50
APB
3494 meth = add_method (this_class, flags, meth_name,
3495 build_java_signature (meth));
3496
3497 /* Fix the method argument list so we have the argument name
3498 information */
3499 fix_method_argument_names (orig_arg, meth);
3500
3501 /* Register the parameter number and re-install the current line
3502 number */
e04a16fb
AG
3503 DECL_MAX_LOCALS (meth) = ctxp->formal_parameter_number+1;
3504 lineno = saved_lineno;
b9f7e36c
APB
3505
3506 /* Register exception specified by the `throws' keyword for
3507 resolution and set the method decl appropriate field to the list.
3508 Note: the grammar ensures that what we get here are class
3509 types. */
3510 if (throws)
3511 {
3512 throws = nreverse (throws);
3513 for (current = throws; current; current = TREE_CHAIN (current))
3514 {
3515 register_incomplete_type (JDEP_EXCEPTION, TREE_VALUE (current),
3516 NULL_TREE, NULL_TREE);
3517 JDEP_GET_PATCH (CLASSD_LAST (ctxp->classd_list)) =
3518 &TREE_VALUE (current);
3519 }
3520 DECL_FUNCTION_THROWS (meth) = throws;
3521 }
3522
e04a16fb
AG
3523 /* We set the DECL_NAME to ID so we can track the location where
3524 the function was declared. This allow us to report
3525 redefinition error accurately. When method are verified,
3526 DECL_NAME is reinstalled properly (using the content of the
3527 WFL node ID) (see check_method_redefinition). We don't do that
22eed1e6
APB
3528 when Object is being defined. Constructor <init> names will be
3529 reinstalled the same way. */
e04a16fb
AG
3530 if (TREE_TYPE (ctxp->current_parsed_class) != object_type_node)
3531 DECL_NAME (meth) = id;
22eed1e6
APB
3532
3533 /* Set the flag if we correctly processed a constructor */
3534 if (constructor_ok)
3535 DECL_CONSTRUCTOR_P (meth) = 1;
3536
5e942c50
APB
3537 /* Eventually set the @deprecated tag flag */
3538 CHECK_DEPRECATED (meth);
3539
7f10c2e2
APB
3540 /* If doing xref, store column and line number information instead
3541 of the line number only. */
3542 if (flag_emit_xref)
3543 DECL_SOURCE_LINE (meth) = EXPR_WFL_LINECOL (id);
3544
e04a16fb
AG
3545 return meth;
3546}
3547
5e942c50
APB
3548static void
3549fix_method_argument_names (orig_arg, meth)
3550 tree orig_arg, meth;
3551{
3552 tree arg = TYPE_ARG_TYPES (TREE_TYPE (meth));
3553 if (TREE_CODE (TREE_TYPE (meth)) == METHOD_TYPE)
3554 {
3555 TREE_PURPOSE (arg) = this_identifier_node;
3556 arg = TREE_CHAIN (arg);
3557 }
de4c7b02 3558 while (orig_arg != end_params_node)
5e942c50
APB
3559 {
3560 TREE_PURPOSE (arg) = TREE_PURPOSE (orig_arg);
3561 orig_arg = TREE_CHAIN (orig_arg);
3562 arg = TREE_CHAIN (arg);
3563 }
3564}
3565
22eed1e6
APB
3566/* Complete the method declaration with METHOD_BODY. */
3567
3568static void
b635eb2f 3569finish_method_declaration (method_body)
22eed1e6
APB
3570 tree method_body;
3571{
79d13333
APB
3572 int flags;
3573
3574 if (!current_function_decl)
3575 return;
3576
3577 flags = get_access_flags_from_decl (current_function_decl);
5256aa37
APB
3578
3579 /* 8.4.5 Method Body */
3580 if ((flags & ACC_ABSTRACT || flags & ACC_NATIVE) && method_body)
3581 {
3582 tree wfl = DECL_NAME (current_function_decl);
3583 parse_error_context (wfl,
3584 "%s method `%s' can't have a body defined",
3585 (METHOD_NATIVE (current_function_decl) ?
3586 "Native" : "Abstract"),
3587 IDENTIFIER_POINTER (EXPR_WFL_NODE (wfl)));
3588 method_body = NULL_TREE;
3589 }
3590 else if (!(flags & ACC_ABSTRACT) && !(flags & ACC_NATIVE) && !method_body)
3591 {
3592 tree wfl = DECL_NAME (current_function_decl);
3593 parse_error_context (wfl,
3594 "Non native and non abstract method `%s' must "
3595 "have a body defined",
3596 IDENTIFIER_POINTER (EXPR_WFL_NODE (wfl)));
3597 method_body = NULL_TREE;
3598 }
3599
2c56429a
APB
3600 if (flag_emit_class_files && method_body
3601 && TREE_CODE (method_body) == NOP_EXPR
3602 && TREE_TYPE (current_function_decl)
3603 && TREE_TYPE (TREE_TYPE (current_function_decl)) == void_type_node)
3604 method_body = build1 (RETURN_EXPR, void_type_node, NULL);
3605
22eed1e6
APB
3606 BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (current_function_decl)) = method_body;
3607 maybe_absorb_scoping_blocks ();
3608 /* Exit function's body */
3609 exit_block ();
3610 /* Merge last line of the function with first line, directly in the
3611 function decl. It will be used to emit correct debug info. */
7f10c2e2
APB
3612 if (!flag_emit_xref)
3613 DECL_SOURCE_LINE_MERGE (current_function_decl, ctxp->last_ccb_indent1);
f099f336
APB
3614 /* So we don't have an irrelevant function declaration context for
3615 the next static block we'll see. */
3616 current_function_decl = NULL_TREE;
22eed1e6
APB
3617}
3618
3619/* Build a an error message for constructor circularity errors. */
3620
3621static char *
3622constructor_circularity_msg (from, to)
3623 tree from, to;
3624{
3625 static char string [4096];
c2e3db92 3626 char *t = xstrdup (lang_printable_name (from, 0));
22eed1e6
APB
3627 sprintf (string, "`%s' invokes `%s'", t, lang_printable_name (to, 0));
3628 free (t);
3629 return string;
3630}
3631
3632/* Verify a circular call to METH. Return 1 if an error is found, 0
3633 otherwise. */
3634
3635static int
3636verify_constructor_circularity (meth, current)
3637 tree meth, current;
3638{
3639 static tree list = NULL_TREE;
3640 tree c;
3641 for (c = DECL_CONSTRUCTOR_CALLS (current); c; c = TREE_CHAIN (c))
3642 {
3643 if (TREE_VALUE (c) == meth)
3644 {
3645 char *t;
3646 if (list)
3647 {
3648 tree liste;
3649 list = nreverse (list);
3650 for (liste = list; liste; liste = TREE_CHAIN (liste))
3651 {
3652 parse_error_context
3653 (TREE_PURPOSE (TREE_PURPOSE (liste)),
3654 constructor_circularity_msg
3655 (TREE_VALUE (liste), TREE_VALUE (TREE_PURPOSE (liste))));
3656 java_error_count--;
3657 }
3658 }
c2e3db92 3659 t = xstrdup (lang_printable_name (meth, 0));
22eed1e6
APB
3660 parse_error_context (TREE_PURPOSE (c),
3661 "%s: recursive invocation of constructor `%s'",
3662 constructor_circularity_msg (current, meth), t);
3663 free (t);
3664 list = NULL_TREE;
3665 return 1;
3666 }
3667 }
3668 for (c = DECL_CONSTRUCTOR_CALLS (current); c; c = TREE_CHAIN (c))
3669 {
3670 list = tree_cons (c, current, list);
3671 if (verify_constructor_circularity (meth, TREE_VALUE (c)))
3672 return 1;
3673 list = TREE_CHAIN (list);
3674 }
3675 return 0;
3676}
3677
e04a16fb
AG
3678/* Check modifiers that can be declared but exclusively */
3679
3680static void
3681check_modifiers_consistency (flags)
3682 int flags;
3683{
3684 int acc_count = 0;
3685 tree cl = NULL_TREE;
3686
3687 THIS_MODIFIER_ONLY (flags, ACC_PUBLIC, 0, acc_count, cl);
3688 THIS_MODIFIER_ONLY (flags, ACC_PRIVATE, 1, acc_count, cl);
3689 THIS_MODIFIER_ONLY (flags, ACC_PROTECTED, 2, acc_count, cl);
3690 if (acc_count > 1)
3691 parse_error_context
3692 (cl, "Inconsistent member declaration. At most one of `public', "
3693 "`private', or `protected' may be specified");
3694}
3695
3696/* Check the methode header METH for abstract specifics features */
3697
3698static void
3699check_abstract_method_header (meth)
3700 tree meth;
3701{
3702 int flags = get_access_flags_from_decl (meth);
3703 /* DECL_NAME might still be a WFL node */
c877974e 3704 tree name = GET_METHOD_NAME (meth);
e04a16fb
AG
3705
3706 OBSOLETE_MODIFIER_WARNING (MODIFIER_WFL (ABSTRACT_TK), flags,
3707 ACC_ABSTRACT, "abstract method `%s'",
3708 IDENTIFIER_POINTER (name));
3709 OBSOLETE_MODIFIER_WARNING (MODIFIER_WFL (PUBLIC_TK), flags,
3710 ACC_PUBLIC, "abstract method `%s'",
3711 IDENTIFIER_POINTER (name));
3712
3713 check_modifiers ("Illegal modifier `%s' for interface method",
3714 flags, INTERFACE_METHOD_MODIFIERS);
3715}
3716
3717/* Create a FUNCTION_TYPE node and start augmenting it with the
3718 declared function arguments. Arguments type that can't be resolved
3719 are left as they are, but the returned node is marked as containing
3720 incomplete types. */
3721
3722static tree
3723method_declarator (id, list)
3724 tree id, list;
3725{
3726 tree arg_types = NULL_TREE, current, node;
3727 tree meth = make_node (FUNCTION_TYPE);
3728 jdep *jdep;
e04a16fb
AG
3729
3730 patch_stage = JDEP_NO_PATCH;
3731
3732 for (current = list; current; current = TREE_CHAIN (current))
3733 {
c583dd46 3734 int must_chain = 0;
e04a16fb
AG
3735 tree wfl_name = TREE_PURPOSE (current);
3736 tree type = TREE_VALUE (current);
3737 tree name = EXPR_WFL_NODE (wfl_name);
c583dd46
APB
3738 tree already, arg_node;
3739 tree type_wfl = NULL_TREE;
23a79c61 3740 tree real_type;
c583dd46
APB
3741
3742 /* Obtain a suitable type for resolution, if necessary */
3743 SET_TYPE_FOR_RESOLUTION (type, type_wfl, must_chain);
3744
3745 /* Process NAME, as it may specify extra dimension(s) for it */
3746 type = build_array_from_name (type, type_wfl, name, &name);
3747 EXPR_WFL_NODE (wfl_name) = name;
e04a16fb 3748
23a79c61
APB
3749 real_type = GET_REAL_TYPE (type);
3750 if (TREE_CODE (real_type) == RECORD_TYPE)
3751 {
3752 real_type = promote_type (real_type);
3753 if (TREE_CODE (type) == TREE_LIST)
3754 TREE_PURPOSE (type) = real_type;
3755 }
5e942c50 3756
e04a16fb
AG
3757 /* Check redefinition */
3758 for (already = arg_types; already; already = TREE_CHAIN (already))
3759 if (TREE_PURPOSE (already) == name)
3760 {
3761 parse_error_context
3762 (wfl_name, "Variable `%s' is used more than once in the "
3763 "argument list of method `%s'", IDENTIFIER_POINTER (name),
3764 IDENTIFIER_POINTER (EXPR_WFL_NODE (id)));
3765 break;
3766 }
3767
3768 /* If we've an incomplete argument type, we know there is a location
3769 to patch when the type get resolved, later. */
3770 jdep = NULL;
c583dd46 3771 if (must_chain)
e04a16fb 3772 {
c583dd46
APB
3773 patch_stage = JDEP_METHOD;
3774 type = register_incomplete_type (patch_stage,
3775 type_wfl, wfl_name, type);
3776 jdep = CLASSD_LAST (ctxp->classd_list);
3777 JDEP_MISC (jdep) = id;
e04a16fb 3778 }
c583dd46 3779
e04a16fb 3780 /* The argument node: a name and a (possibly) incomplete type */
23a79c61 3781 arg_node = build_tree_list (name, real_type);
e04a16fb
AG
3782 if (jdep)
3783 JDEP_GET_PATCH (jdep) = &TREE_VALUE (arg_node);
3784 TREE_CHAIN (arg_node) = arg_types;
3785 arg_types = arg_node;
3786 }
de4c7b02 3787 TYPE_ARG_TYPES (meth) = chainon (nreverse (arg_types), end_params_node);
e04a16fb
AG
3788 node = build_tree_list (id, meth);
3789 return node;
3790}
3791
3792static int
3793unresolved_type_p (wfl, returned)
3794 tree wfl;
3795 tree *returned;
3796
3797{
3798 if (TREE_CODE (wfl) == EXPR_WITH_FILE_LOCATION)
3799 {
3800 tree decl = IDENTIFIER_CLASS_VALUE (EXPR_WFL_NODE (wfl));
3801 if (returned)
3802 *returned = (decl ? TREE_TYPE (decl) : NULL_TREE);
3803 return 1;
3804 }
3805 if (returned)
3806 *returned = wfl;
3807 return 0;
3808}
3809
3810/* From NAME, build a qualified identifier node using the
3811 qualification from the current package definition. */
3812
3813static tree
3814parser_qualified_classname (name)
3815 tree name;
3816{
3817 if (ctxp->package)
3818 return merge_qualified_name (ctxp->package, EXPR_WFL_NODE (name));
3819 else
3820 return EXPR_WFL_NODE (name);
3821}
3822
3823/* Called once the type a interface extends is resolved. Returns 0 if
3824 everything is OK. */
3825
3826static int
3827parser_check_super_interface (super_decl, this_decl, this_wfl)
3828 tree super_decl, this_decl, this_wfl;
3829{
3830 tree super_type = TREE_TYPE (super_decl);
3831
3832 /* Has to be an interface */
3833 if (!CLASS_INTERFACE (TYPE_NAME (TREE_TYPE (super_decl))))
3834 {
3835 parse_error_context
3836 (this_wfl, "Can't use %s `%s' to implement/extend %s `%s'",
3837 (TYPE_ARRAY_P (super_type) ? "array" : "class"),
3838 IDENTIFIER_POINTER (DECL_NAME (super_decl)),
3839 (CLASS_INTERFACE (TYPE_NAME (TREE_TYPE (this_decl))) ?
3840 "interface" : "class"),
3841 IDENTIFIER_POINTER (DECL_NAME (this_decl)));
3842 return 1;
3843 }
3844
3845 /* Check scope: same package OK, other package: OK if public */
3846 if (check_pkg_class_access (DECL_NAME (super_decl), lookup_cl (this_decl)))
3847 return 1;
3848
3849 SOURCE_FRONTEND_DEBUG (("Completing interface %s with %s",
3850 IDENTIFIER_POINTER (DECL_NAME (this_decl)),
3851 IDENTIFIER_POINTER (DECL_NAME (super_decl))));
3852 return 0;
3853}
3854
3855/* Makes sure that SUPER_DECL is suitable to extend THIS_DECL. Returns
3856 0 if everthing is OK. */
3857
3858static int
3859parser_check_super (super_decl, this_decl, wfl)
3860 tree super_decl, this_decl, wfl;
3861{
e04a16fb
AG
3862 tree super_type = TREE_TYPE (super_decl);
3863
3864 /* SUPER should be a CLASS (neither an array nor an interface) */
3865 if (TYPE_ARRAY_P (super_type) || CLASS_INTERFACE (TYPE_NAME (super_type)))
3866 {
3867 parse_error_context
3868 (wfl, "Class `%s' can't subclass %s `%s'",
3869 IDENTIFIER_POINTER (DECL_NAME (this_decl)),
3870 (CLASS_INTERFACE (TYPE_NAME (super_type)) ? "interface" : "array"),
3871 IDENTIFIER_POINTER (DECL_NAME (super_decl)));
3872 return 1;
3873 }
3874
3875 if (CLASS_FINAL (TYPE_NAME (super_type)))
3876 {
3877 parse_error_context (wfl, "Can't subclass final classes: %s",
3878 IDENTIFIER_POINTER (DECL_NAME (super_decl)));
3879 return 1;
3880 }
3881
3882 /* Check scope: same package OK, other package: OK if public */
3883 if (check_pkg_class_access (DECL_NAME (super_decl), wfl))
3884 return 1;
3885
3886 SOURCE_FRONTEND_DEBUG (("Completing class %s with %s",
3887 IDENTIFIER_POINTER (DECL_NAME (this_decl)),
3888 IDENTIFIER_POINTER (DECL_NAME (super_decl))));
3889 return 0;
3890}
3891
3892/* Create a new dependency list and link it (in a LIFO manner) to the
3893 CTXP list of type dependency list. */
3894
3895static void
3896create_jdep_list (ctxp)
3897 struct parser_ctxt *ctxp;
3898{
23a79c61 3899 jdeplist *new = (jdeplist *)xmalloc (sizeof (jdeplist));
e04a16fb
AG
3900 new->first = new->last = NULL;
3901 new->next = ctxp->classd_list;
3902 ctxp->classd_list = new;
3903}
3904
3905static jdeplist *
3906reverse_jdep_list (ctxp)
3907 struct parser_ctxt *ctxp;
3908{
3909 register jdeplist *prev = NULL, *current, *next;
3910 for (current = ctxp->classd_list; current; current = next)
3911 {
3912 next = current->next;
3913 current->next = prev;
3914 prev = current;
3915 }
3916 return prev;
3917}
3918
23a79c61
APB
3919/* Create a fake pointer based on the ID stored in
3920 TYPE_NAME. TYPE_NAME can be a WFL or a incomplete type asking to be
3921 registered again. */
e04a16fb
AG
3922
3923static tree
23a79c61
APB
3924obtain_incomplete_type (type_name)
3925 tree type_name;
e04a16fb 3926{
23a79c61
APB
3927 tree ptr, name;
3928
3929 if (TREE_CODE (type_name) == EXPR_WITH_FILE_LOCATION)
3930 name = EXPR_WFL_NODE (type_name);
3931 else if (INCOMPLETE_TYPE_P (type_name))
3932 name = TYPE_NAME (type_name);
3933 else
3934 fatal ("invalid type name - obtain_incomplete_type");
e04a16fb
AG
3935
3936 for (ptr = ctxp->incomplete_class; ptr; ptr = TREE_CHAIN (ptr))
78d21f92 3937 if (TYPE_NAME (ptr) == name)
e04a16fb
AG
3938 break;
3939
3940 if (!ptr)
3941 {
e04a16fb 3942 push_obstacks (&permanent_obstack, &permanent_obstack);
78d21f92
PB
3943 BUILD_PTR_FROM_NAME (ptr, name);
3944 layout_type (ptr);
e04a16fb
AG
3945 pop_obstacks ();
3946 TREE_CHAIN (ptr) = ctxp->incomplete_class;
3947 ctxp->incomplete_class = ptr;
3948 }
3949
3950 return ptr;
3951}
3952
3953/* Register a incomplete type whose name is WFL. Reuse PTR if PTR is
3954 non NULL instead of computing a new fake type based on WFL. The new
3955 dependency is inserted in the current type dependency list, in FIFO
3956 manner. */
3957
3958static tree
3959register_incomplete_type (kind, wfl, decl, ptr)
3960 int kind;
3961 tree wfl, decl, ptr;
3962{
23a79c61 3963 jdep *new = (jdep *)xmalloc (sizeof (jdep));
e04a16fb 3964
e04a16fb
AG
3965 if (!ptr && kind != JDEP_METHOD_END) /* JDEP_METHOD_END is a mere marker */
3966 ptr = obtain_incomplete_type (wfl);
3967
3968 JDEP_KIND (new) = kind;
3969 JDEP_DECL (new) = decl;
3970 JDEP_SOLV (new) = ptr;
3971 JDEP_WFL (new) = wfl;
3972 JDEP_CHAIN (new) = NULL;
3973 JDEP_MISC (new) = NULL_TREE;
3974 JDEP_GET_PATCH (new) = (tree *)NULL;
3975
3976 JDEP_INSERT (ctxp->classd_list, new);
3977
3978 return ptr;
3979}
3980
3981void
3982java_check_circular_reference ()
3983{
3984 tree current;
3985 for (current = ctxp->class_list; current; current = TREE_CHAIN (current))
3986 {
3987 tree type = TREE_TYPE (current);
3988 if (CLASS_INTERFACE (TYPE_NAME (type)))
3989 {
3990 /* Check all interfaces this class extends */
3991 tree basetype_vec = TYPE_BINFO_BASETYPES (type);
3992 int n, i;
3993
3994 if (!basetype_vec)
3995 return;
3996 n = TREE_VEC_LENGTH (basetype_vec);
3997 for (i = 0; i < n; i++)
3998 {
3999 tree vec_elt = TREE_VEC_ELT (basetype_vec, i);
4000 if (vec_elt && BINFO_TYPE (vec_elt) != object_type_node
4001 && interface_of_p (type, BINFO_TYPE (vec_elt)))
4002 parse_error_context (lookup_cl (current),
4003 "Cyclic interface inheritance");
4004 }
4005 }
4006 else
4007 if (inherits_from_p (CLASSTYPE_SUPER (type), type))
4008 parse_error_context (lookup_cl (current),
4009 "Cyclic class inheritance");
4010 }
4011}
4012
23a79c61
APB
4013/* safe_layout_class just makes sure that we can load a class without
4014 disrupting the current_class, input_file, lineno, etc, information
4015 about the class processed currently. */
4016
e04a16fb
AG
4017void
4018safe_layout_class (class)
4019 tree class;
4020{
4021 tree save_current_class = current_class;
4022 char *save_input_filename = input_filename;
4023 int save_lineno = lineno;
5e942c50 4024
e04a16fb 4025 push_obstacks (&permanent_obstack, &permanent_obstack);
5e942c50 4026
e04a16fb
AG
4027 layout_class (class);
4028 pop_obstacks ();
5e942c50 4029
e04a16fb
AG
4030 current_class = save_current_class;
4031 input_filename = save_input_filename;
4032 lineno = save_lineno;
4033 CLASS_LOADED_P (class) = 1;
4034}
4035
4036static tree
4037jdep_resolve_class (dep)
4038 jdep *dep;
4039{
4040 tree decl;
4041
23a79c61
APB
4042 if (JDEP_RESOLVED_P (dep))
4043 decl = JDEP_RESOLVED_DECL (dep);
4044 else
e04a16fb 4045 {
23a79c61
APB
4046 decl = resolve_class (JDEP_TO_RESOLVE (dep),
4047 JDEP_DECL (dep), JDEP_WFL (dep));
e04a16fb
AG
4048 JDEP_RESOLVED (dep, decl);
4049 }
23a79c61 4050
e04a16fb 4051 if (!decl)
23a79c61
APB
4052 complete_class_report_errors (dep);
4053
e04a16fb
AG
4054 return decl;
4055}
4056
4057/* Complete unsatisfied class declaration and their dependencies */
4058
4059void
4060java_complete_class ()
4061{
e04a16fb
AG
4062 tree cclass;
4063 jdeplist *cclassd;
4064 int error_found;
b67d701b 4065 tree type;
e04a16fb
AG
4066
4067 push_obstacks (&permanent_obstack, &permanent_obstack);
4068
4069 /* Process imports and reverse the import on demand list */
4070 process_imports ();
4071 if (ctxp->import_demand_list)
4072 ctxp->import_demand_list = nreverse (ctxp->import_demand_list);
4073
4074 /* Rever things so we have the right order */
4075 ctxp->class_list = nreverse (ctxp->class_list);
4076 ctxp->classd_list = reverse_jdep_list (ctxp);
c877974e 4077
e04a16fb
AG
4078 for (cclassd = ctxp->classd_list, cclass = ctxp->class_list;
4079 cclass && cclassd;
4080 cclass = TREE_CHAIN (cclass), cclassd = CLASSD_CHAIN (cclassd))
4081 {
4082 jdep *dep;
4083 for (dep = CLASSD_FIRST (cclassd); dep; dep = JDEP_CHAIN (dep))
4084 {
4085 tree decl;
e04a16fb
AG
4086 if (!(decl = jdep_resolve_class (dep)))
4087 continue;
4088
4089 /* Now it's time to patch */
4090 switch (JDEP_KIND (dep))
4091 {
4092 case JDEP_SUPER:
4093 /* Simply patch super */
4094 if (parser_check_super (decl, JDEP_DECL (dep), JDEP_WFL (dep)))
4095 continue;
4096 BINFO_TYPE (TREE_VEC_ELT (BINFO_BASETYPES (TYPE_BINFO
4097 (TREE_TYPE (JDEP_DECL (dep)))), 0)) = TREE_TYPE (decl);
4098 break;
4099
4100 case JDEP_FIELD:
4101 {
4102 /* We do part of the job done in add_field */
4103 tree field_decl = JDEP_DECL (dep);
4104 tree field_type = TREE_TYPE (decl);
4105 push_obstacks (&permanent_obstack, &permanent_obstack);
e04a16fb 4106 if (TREE_CODE (field_type) == RECORD_TYPE)
e04a16fb
AG
4107 field_type = promote_type (field_type);
4108 pop_obstacks ();
4109 TREE_TYPE (field_decl) = field_type;
5e942c50
APB
4110 DECL_ALIGN (field_decl) = 0;
4111 layout_decl (field_decl, 0);
e04a16fb
AG
4112 SOURCE_FRONTEND_DEBUG
4113 (("Completed field/var decl `%s' with `%s'",
4114 IDENTIFIER_POINTER (DECL_NAME (field_decl)),
4115 IDENTIFIER_POINTER (DECL_NAME (decl))));
4116 break;
4117 }
4118 case JDEP_METHOD: /* We start patching a method */
4119 case JDEP_METHOD_RETURN:
4120 error_found = 0;
4121 while (1)
4122 {
4123 if (decl)
4124 {
b67d701b
PB
4125 type = TREE_TYPE(decl);
4126 if (TREE_CODE (type) == RECORD_TYPE)
4127 type = promote_type (type);
e04a16fb
AG
4128 JDEP_APPLY_PATCH (dep, type);
4129 SOURCE_FRONTEND_DEBUG
4130 (((JDEP_KIND (dep) == JDEP_METHOD_RETURN ?
4131 "Completing fct `%s' with ret type `%s'":
4132 "Completing arg `%s' with type `%s'"),
4133 IDENTIFIER_POINTER (EXPR_WFL_NODE
4134 (JDEP_DECL_WFL (dep))),
4135 IDENTIFIER_POINTER (DECL_NAME (decl))));
4136 }
4137 else
4138 error_found = 1;
4139 dep = JDEP_CHAIN (dep);
4140 if (JDEP_KIND (dep) == JDEP_METHOD_END)
4141 break;
4142 else
4143 decl = jdep_resolve_class (dep);
4144 }
4145 if (!error_found)
4146 {
4147 tree mdecl = JDEP_DECL (dep), signature;
4148 push_obstacks (&permanent_obstack, &permanent_obstack);
4149 /* Recompute and reset the signature */
4150 signature = build_java_signature (TREE_TYPE (mdecl));
4151 set_java_signature (TREE_TYPE (mdecl), signature);
4152 pop_obstacks ();
4153 }
4154 else
4155 continue;
4156 break;
4157
4158 case JDEP_INTERFACE:
4159 if (parser_check_super_interface (decl, JDEP_DECL (dep),
4160 JDEP_WFL (dep)))
4161 continue;
4162 parser_add_interface (JDEP_DECL (dep), decl, JDEP_WFL (dep));
4163 break;
4164
b67d701b 4165 case JDEP_PARM:
e04a16fb 4166 case JDEP_VARIABLE:
b67d701b
PB
4167 type = TREE_TYPE(decl);
4168 if (TREE_CODE (type) == RECORD_TYPE)
4169 type = promote_type (type);
4170 JDEP_APPLY_PATCH (dep, type);
e04a16fb
AG
4171 break;
4172
4173 case JDEP_TYPE:
4174 JDEP_APPLY_PATCH (dep, TREE_TYPE (decl));
4175 SOURCE_FRONTEND_DEBUG
4176 (("Completing a random type dependency on a '%s' node",
4177 tree_code_name [TREE_CODE (JDEP_DECL (dep))]));
4178 break;
4179
b9f7e36c 4180 case JDEP_EXCEPTION:
c877974e
APB
4181 JDEP_APPLY_PATCH (dep, TREE_TYPE (decl));
4182 SOURCE_FRONTEND_DEBUG
4183 (("Completing `%s' `throws' argument node",
4184 IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_WFL (dep)))));
b9f7e36c
APB
4185 break;
4186
e04a16fb 4187 default:
0a2138e2
APB
4188 fatal ("Can't handle patch code %d - java_complete_class",
4189 JDEP_KIND (dep));
e04a16fb
AG
4190 }
4191 }
4192 }
4193 pop_obstacks ();
4194 return;
4195}
4196
4197/* Resolve class CLASS_TYPE. Handle the case of trying to resolve an
4198 array. */
4199
4200static tree
4201resolve_class (class_type, decl, cl)
4202 tree class_type, decl, cl;
4203{
49f48c71
KG
4204 const char *name = IDENTIFIER_POINTER (TYPE_NAME (class_type));
4205 const char *base = name;
78d21f92
PB
4206 tree resolved_type = TREE_TYPE (class_type);
4207 tree resolved_type_decl;
e04a16fb 4208
78d21f92
PB
4209 if (resolved_type != NULL_TREE)
4210 {
4211 tree resolved_type_decl = TYPE_NAME (resolved_type);
4212 if (resolved_type_decl == NULL_TREE
4213 || TREE_CODE (resolved_type_decl) == IDENTIFIER_NODE)
4214 {
4215 resolved_type_decl = build_decl (TYPE_DECL,
4216 TYPE_NAME (class_type),
4217 resolved_type);
4218 }
4219 return resolved_type_decl;
4220 }
4221
e04a16fb
AG
4222 /* 1- Check to see if we have an array. If true, find what we really
4223 want to resolve */
4224 while (name[0] == '[')
4225 name++;
4226 if (base != name)
4227 TYPE_NAME (class_type) = get_identifier (name);
4228
4229 /* 2- Resolve the bare type */
4230 if (!(resolved_type_decl = do_resolve_class (class_type, decl, cl)))
4231 return NULL_TREE;
4232 resolved_type = TREE_TYPE (resolved_type_decl);
4233
4234 /* 3- If we have and array, reconstruct the array down to its nesting */
4235 if (base != name)
4236 {
4237 while (base != name)
4238 {
4239 if (TREE_CODE (resolved_type) == RECORD_TYPE)
4240 resolved_type = promote_type (resolved_type);
4241 resolved_type = build_java_array_type (resolved_type, -1);
c583dd46 4242 CLASS_LOADED_P (resolved_type) = 1;
e04a16fb
AG
4243 name--;
4244 }
4245 /* Build a fake decl for this, since this is what is expected to
4246 be returned. */
4247 resolved_type_decl =
4248 build_decl (TYPE_DECL, TYPE_NAME (resolved_type), resolved_type);
4249 /* Figure how those two things are important for error report. FIXME */
4250 DECL_SOURCE_LINE (resolved_type_decl) = 0;
4251 DECL_SOURCE_FILE (resolved_type_decl) = input_filename;
78d21f92 4252 TYPE_NAME (class_type) = TYPE_NAME (resolved_type);
e04a16fb 4253 }
78d21f92 4254 TREE_TYPE (class_type) = resolved_type;
e04a16fb
AG
4255 return resolved_type_decl;
4256}
4257
4258/* Effectively perform the resolution of class CLASS_TYPE. DECL or CL
4259 are used to report error messages. */
4260
78d21f92 4261tree
e04a16fb
AG
4262do_resolve_class (class_type, decl, cl)
4263 tree class_type;
4264 tree decl;
4265 tree cl;
4266{
4267 tree new_class_decl;
4268 tree original_name = NULL_TREE;
4269
4270 /* Do not try to replace TYPE_NAME (class_type) by a variable, since
4271 its is changed by find_in_imports{_on_demand} */
4272
4273 /* 1- Check for the type in single imports */
4274 if (find_in_imports (class_type))
4275 return NULL_TREE;
4276
4277 /* 2- And check for the type in the current compilation unit. If it fails,
4278 try with a name qualified with the package name if appropriate. */
e04a16fb
AG
4279 if ((new_class_decl = IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type))))
4280 {
4281 if (!CLASS_LOADED_P (TREE_TYPE (new_class_decl)) &&
4282 !CLASS_FROM_SOURCE_P (TREE_TYPE (new_class_decl)))
4283 load_class (TYPE_NAME (class_type), 0);
4284 return IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type));
4285 }
4286
4287 original_name = TYPE_NAME (class_type);
4288 if (!QUALIFIED_P (TYPE_NAME (class_type)) && ctxp->package)
4289 TYPE_NAME (class_type) = merge_qualified_name (ctxp->package,
4290 TYPE_NAME (class_type));
bc3ca41b 4291#if 1
5e942c50
APB
4292 if (!(new_class_decl = IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type))))
4293 load_class (TYPE_NAME (class_type), 0);
e04a16fb
AG
4294 if ((new_class_decl = IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type))))
4295 {
4296 if (!CLASS_LOADED_P (TREE_TYPE (new_class_decl)) &&
4297 !CLASS_FROM_SOURCE_P (TREE_TYPE (new_class_decl)))
4298 load_class (TYPE_NAME (class_type), 0);
4299 return IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type));
4300 }
bc3ca41b
PB
4301#else
4302 new_name = TYPE_NAME (class_type);
4303 if ((new_class_decl = IDENTIFIER_CLASS_VALUE (new_name)) != NULL_TREE)
4304 {
4305 if (!CLASS_LOADED_P (TREE_TYPE (new_class_decl)) &&
4306 !CLASS_FROM_SOURCE_P (TREE_TYPE (new_class_decl)))
4307 load_class (new_name, 0);
4308 return IDENTIFIER_CLASS_VALUE (new_name);
4309 }
4310 else
4311 {
4312 tree class = read_class (new_name);
4313 if (class != NULL_TREE)
4314 {
4315 tree decl = IDENTIFIER_CLASS_VALUE (new_name);
4316 if (decl == NULL_TREE)
4317 decl = push_class (class, new_name);
4318 return decl;
4319 }
4320 }
4321#endif
e04a16fb
AG
4322 TYPE_NAME (class_type) = original_name;
4323
4324 /* 3- Check an other compilation unit that bears the name of type */
4325 load_class (TYPE_NAME (class_type), 0);
4326 if (check_pkg_class_access (TYPE_NAME (class_type),
4327 (cl ? cl : lookup_cl (decl))))
4328 return NULL_TREE;
4329
4330 if ((new_class_decl = IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type))))
4331 return new_class_decl;
4332
4333 /* 4- Check the import on demands. Don't allow bar.baz to be
4334 imported from foo.* */
4335 if (!QUALIFIED_P (TYPE_NAME (class_type)))
4336 if (find_in_imports_on_demand (class_type))
4337 return NULL_TREE;
4338
4339 /* 5- Last call for a resolution */
4340 return IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type));
4341}
4342
4343/* Resolve NAME and lay it out (if not done and if not the current
23a79c61
APB
4344 parsed class). Return a decl node. This function is meant to be
4345 called when type resolution is necessary during the walk pass. */
e04a16fb
AG
4346
4347static tree
c877974e
APB
4348resolve_and_layout (something, cl)
4349 tree something;
e04a16fb
AG
4350 tree cl;
4351{
c877974e
APB
4352 tree decl;
4353
23a79c61
APB
4354 /* Don't do that on the current class */
4355 if (something == current_class)
4356 return TYPE_NAME (current_class);
c877974e 4357
23a79c61 4358 /* Don't do anything for void and other primitive types */
c877974e
APB
4359 if (JPRIMITIVE_TYPE_P (something) || something == void_type_node)
4360 return NULL_TREE;
4361
23a79c61
APB
4362 /* Pointer types can be reall pointer types or fake pointers. When
4363 finding a real pointer, recheck for primitive types */
4364 if (TREE_CODE (something) == POINTER_TYPE)
4365 {
4366 if (TREE_TYPE (something))
4367 {
4368 something = TREE_TYPE (something);
4369 if (JPRIMITIVE_TYPE_P (something) || something == void_type_node)
4370 return NULL_TREE;
4371 }
4372 else
4373 something = TYPE_NAME (something);
4374 }
4375
4376 /* Don't do anything for arrays of primitive types */
4377 if (TREE_CODE (something) == RECORD_TYPE && TYPE_ARRAY_P (something)
4378 && JPRIMITIVE_TYPE_P (TYPE_ARRAY_ELEMENT (something)))
4379 return NULL_TREE;
4380
4381 /* If something is not and IDENTIFIER_NODE, it can be a a TYPE_DECL
4382 or a real TYPE */
c877974e
APB
4383 if (TREE_CODE (something) != IDENTIFIER_NODE)
4384 something = (TREE_CODE (TYPE_NAME (something)) == TYPE_DECL ?
4385 DECL_NAME (TYPE_NAME (something)) : TYPE_NAME (something));
4386
23a79c61
APB
4387 if (!(decl = resolve_no_layout (something, cl)))
4388 return NULL_TREE;
4389
4390 /* Resolve and layout if necessary */
4391 layout_class_methods (TREE_TYPE (decl));
7705e9db
APB
4392 /* Check methods, but only once */
4393 if (CLASS_FROM_SOURCE_P (TREE_TYPE (decl))
4394 && !CLASS_LOADED_P (TREE_TYPE (decl)))
23a79c61
APB
4395 CHECK_METHODS (decl);
4396 if (TREE_TYPE (decl) != current_class && !CLASS_LOADED_P (TREE_TYPE (decl)))
e04a16fb 4397 safe_layout_class (TREE_TYPE (decl));
23a79c61 4398
e04a16fb
AG
4399 return decl;
4400}
4401
4402/* Resolve a class, returns its decl but doesn't perform any
4403 layout. The current parsing context is saved and restored */
4404
4405static tree
4406resolve_no_layout (name, cl)
4407 tree name, cl;
4408{
4409 tree ptr, decl;
4410 BUILD_PTR_FROM_NAME (ptr, name);
4411 java_parser_context_save_global ();
4412 decl = resolve_class (ptr, NULL_TREE, cl);
4413 java_parser_context_restore_global ();
4414
4415 return decl;
4416}
4417
23a79c61
APB
4418/* Called when reporting errors. Skip leader '[' in a complex array
4419 type description that failed to be resolved. */
e04a16fb 4420
49f48c71 4421static const char *
e04a16fb 4422purify_type_name (name)
49f48c71 4423 const char *name;
e04a16fb
AG
4424{
4425 while (*name && *name == '[')
4426 name++;
4427 return name;
4428}
4429
4430/* The type CURRENT refers to can't be found. We print error messages. */
4431
4432static void
4433complete_class_report_errors (dep)
4434 jdep *dep;
4435{
49f48c71 4436 const char *name;
23a79c61
APB
4437
4438 if (!JDEP_WFL (dep))
4439 return;
4440
4441 name = IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_WFL (dep)));
e04a16fb
AG
4442 switch (JDEP_KIND (dep))
4443 {
4444 case JDEP_SUPER:
4445 parse_error_context
4446 (JDEP_WFL (dep), "Superclass `%s' of class `%s' not found",
23a79c61 4447 purify_type_name (name),
e04a16fb
AG
4448 IDENTIFIER_POINTER (DECL_NAME (JDEP_DECL (dep))));
4449 break;
4450 case JDEP_FIELD:
4451 parse_error_context
4452 (JDEP_WFL (dep), "Type `%s' not found in declaration of field `%s'",
23a79c61 4453 purify_type_name (name),
e04a16fb
AG
4454 IDENTIFIER_POINTER (DECL_NAME (JDEP_DECL (dep))));
4455 break;
4456 case JDEP_METHOD: /* Covers arguments */
4457 parse_error_context
4458 (JDEP_WFL (dep), "Type `%s' not found in the declaration of the "
4459 "argument `%s' of method `%s'",
23a79c61 4460 purify_type_name (name),
e04a16fb
AG
4461 IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_DECL_WFL (dep))),
4462 IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_MISC (dep))));
4463 break;
4464 case JDEP_METHOD_RETURN: /* Covers return type */
4465 parse_error_context
4466 (JDEP_WFL (dep), "Type `%s' not found in the declaration of the "
4467 "return type of method `%s'",
23a79c61 4468 purify_type_name (name),
e04a16fb
AG
4469 IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_DECL_WFL (dep))));
4470 break;
4471 case JDEP_INTERFACE:
4472 parse_error_context
4473 (JDEP_WFL (dep), "Superinterface `%s' of %s `%s' not found",
4474 IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_WFL (dep))),
4475 (CLASS_OR_INTERFACE (JDEP_DECL (dep), "class", "interface")),
4476 IDENTIFIER_POINTER (DECL_NAME (JDEP_DECL (dep))));
4477 break;
4478 case JDEP_VARIABLE:
4479 parse_error_context
4480 (JDEP_WFL (dep), "Type `%s' not found in the declaration of the "
4481 "local variable `%s'",
b67d701b
PB
4482 purify_type_name (IDENTIFIER_POINTER
4483 (EXPR_WFL_NODE (JDEP_WFL (dep)))),
e04a16fb
AG
4484 IDENTIFIER_POINTER (DECL_NAME (JDEP_DECL (dep))));
4485 break;
b9f7e36c
APB
4486 case JDEP_EXCEPTION: /* As specified by `throws' */
4487 parse_error_context
4488 (JDEP_WFL (dep), "Class `%s' not found in `throws'",
4489 IDENTIFIER_POINTER (EXPR_WFL_NODE (JDEP_WFL (dep))));
4490 break;
0a2138e2
APB
4491 default:
4492 /* Fix for -Wall. Just break doing nothing. The error will be
4493 caught later */
4494 break;
e04a16fb
AG
4495 }
4496}
4497
4498/* Check uninitialized final. */
4499
4500void
4501java_check_final ()
4502{
4503}
4504
22eed1e6
APB
4505/* Return a static string containing the DECL prototype string. If
4506 DECL is a constructor, use the class name instead of the form
4507 <init> */
4508
49f48c71 4509static const char *
22eed1e6
APB
4510get_printable_method_name (decl)
4511 tree decl;
4512{
49f48c71 4513 const char *to_return;
9ee9b555 4514 tree name = NULL_TREE;
22eed1e6
APB
4515
4516 if (DECL_CONSTRUCTOR_P (decl))
4517 {
4518 name = DECL_NAME (decl);
5e942c50 4519 DECL_NAME (decl) = DECL_NAME (TYPE_NAME (DECL_CONTEXT (decl)));
22eed1e6
APB
4520 }
4521
4522 to_return = lang_printable_name (decl, 0);
4523 if (DECL_CONSTRUCTOR_P (decl))
4524 DECL_NAME (decl) = name;
4525
4526 return to_return;
4527}
4528
5e942c50
APB
4529/* Reinstall the proper DECL_NAME on METHOD. Return 0 if the method
4530 nevertheless needs to be verfied, 1 otherwise. */
4531
4532static int
4533reset_method_name (method)
4534 tree method;
4535{
7f1d4866 4536 if (!IS_CLINIT (method) && DECL_NAME (method) != finit_identifier_node)
5e942c50
APB
4537 {
4538 /* NAME is just the plain name when Object is being defined */
4539 if (DECL_CONTEXT (method) != object_type_node)
c877974e
APB
4540 DECL_NAME (method) = (DECL_CONSTRUCTOR_P (method) ?
4541 init_identifier_node : GET_METHOD_NAME (method));
5e942c50
APB
4542 return 0;
4543 }
4544 else
4545 return 1;
4546}
4547
c877974e
APB
4548/* Return the name of METHOD_DECL, when DECL_NAME is a WFL */
4549
4550tree
4551java_get_real_method_name (method_decl)
4552 tree method_decl;
4553{
4554 tree method_name = DECL_NAME (method_decl);
4555 if (DECL_CONSTRUCTOR_P (method_decl))
4556 return init_identifier_node;
82371d41
APB
4557
4558 /* Explain here why METHOD_DECL doesn't have the DECL_CONSTRUCTUR_P
4559 and still can be a constructor. FIXME */
4560
23a79c61
APB
4561 /* Don't confuse method only bearing the name of their class as
4562 constructors */
82371d41
APB
4563 else if (!CLASS_FROM_SOURCE_P (DECL_CONTEXT (method_decl))
4564 && ctxp
4565 && ctxp->current_parsed_class_un == EXPR_WFL_NODE (method_name)
23a79c61
APB
4566 && get_access_flags_from_decl (method_decl) <= ACC_PROTECTED
4567 && TREE_TYPE (TREE_TYPE (method_decl)) == void_type_node)
c877974e
APB
4568 return init_identifier_node;
4569 else
4570 return EXPR_WFL_NODE (method_name);
4571}
4572
22eed1e6
APB
4573/* Track method being redefined inside the same class. As a side
4574 effect, set DECL_NAME to an IDENTIFIER (prior entering this
d77613be 4575 function it's a FWL, so we can track errors more accurately.) */
22eed1e6 4576
e04a16fb
AG
4577static int
4578check_method_redefinition (class, method)
4579 tree class, method;
4580{
4581 tree redef, name;
4582 tree cl = DECL_NAME (method);
c3f2a476 4583 tree sig = TYPE_ARGUMENT_SIGNATURE (TREE_TYPE (method));
ba179f9f
APB
4584 /* decl name of artificial <clinit> and $finit$ doesn't need to be
4585 fixed and checked */
5e942c50
APB
4586
4587 /* Reset the method name before running the check. If it returns 1,
4588 the method doesn't need to be verified with respect to method
4589 redeclaration and we return 0 */
4590 if (reset_method_name (method))
e04a16fb 4591 return 0;
5e942c50
APB
4592
4593 name = DECL_NAME (method);
e04a16fb
AG
4594 for (redef = TYPE_METHODS (class); redef; redef = TREE_CHAIN (redef))
4595 {
c3f2a476 4596 if (redef == method)
e04a16fb 4597 break;
c3f2a476
APB
4598 if (DECL_NAME (redef) == name
4599 && sig == TYPE_ARGUMENT_SIGNATURE (TREE_TYPE (redef)))
e04a16fb 4600 {
22eed1e6
APB
4601 parse_error_context
4602 (cl, "Duplicate %s declaration `%s'",
4603 (DECL_CONSTRUCTOR_P (redef) ? "constructor" : "method"),
4604 get_printable_method_name (redef));
e04a16fb
AG
4605 return 1;
4606 }
4607 }
4608 return 0;
4609}
4610
d77613be
APB
4611static void
4612check_abstract_method_definitions (do_interface, class_decl, type)
4613 int do_interface;
4614 tree class_decl, type;
4615{
4616 tree class = TREE_TYPE (class_decl);
4617 tree method, end_type;
4618
4619 end_type = (do_interface ? object_type_node : type);
4620 for (method = TYPE_METHODS (type); method; method = TREE_CHAIN (method))
4621 {
4622 tree other_super, other_method, method_sig, method_name;
4623 int found = 0;
4624
4625 if (!METHOD_ABSTRACT (method) || METHOD_FINAL (method))
4626 continue;
4627
4628 /* Now verify that somewhere in between TYPE and CLASS,
4629 abstract method METHOD gets a non abstract definition
4630 that is inherited by CLASS. */
4631
4632 method_sig = build_java_signature (TREE_TYPE (method));
4633 method_name = DECL_NAME (method);
4634 if (TREE_CODE (method_name) == EXPR_WITH_FILE_LOCATION)
4635 method_name = EXPR_WFL_NODE (method_name);
4636
4637 for (other_super = class; other_super != end_type;
4638 other_super = CLASSTYPE_SUPER (other_super))
4639 {
4640 for (other_method = TYPE_METHODS (other_super); other_method;
4641 other_method = TREE_CHAIN (other_method))
4642 {
4643 tree s = build_java_signature (TREE_TYPE (other_method));
4644 tree other_name = DECL_NAME (other_method);
4645
4646 if (TREE_CODE (other_name) == EXPR_WITH_FILE_LOCATION)
4647 other_name = EXPR_WFL_NODE (other_name);
4648 if (!IS_CLINIT (other_method)
4649 && !DECL_CONSTRUCTOR_P (other_method)
4650 && method_name == other_name && method_sig == s)
4651 {
4652 found = 1;
4653 break;
4654 }
4655 }
4656 }
4657
4658 /* Report that abstract METHOD didn't find an implementation
4659 that CLASS can use. */
4660 if (!found)
4661 {
c2e3db92 4662 char *t = xstrdup (lang_printable_name
d77613be
APB
4663 (TREE_TYPE (TREE_TYPE (method)), 0));
4664 tree ccn = DECL_NAME (TYPE_NAME (DECL_CONTEXT (method)));
4665 tree saved_wfl = NULL_TREE;
4666
4667 if (TREE_CODE (DECL_NAME (method)) == EXPR_WITH_FILE_LOCATION)
4668 {
4669 saved_wfl = DECL_NAME (method);
4670 DECL_NAME (method) = EXPR_WFL_NODE (DECL_NAME (method));
4671 }
4672
4673 parse_error_context
4674 (lookup_cl (class_decl),
4675 "Class `%s' doesn't define the abstract method `%s %s' from "
4676 "%s `%s'. This method must be defined or %s `%s' must be "
4677 "declared abstract",
4678 IDENTIFIER_POINTER (DECL_NAME (class_decl)),
4679 t, lang_printable_name (method, 0),
4680 (CLASS_INTERFACE (TYPE_NAME (DECL_CONTEXT (method))) ?
4681 "interface" : "class"),
4682 IDENTIFIER_POINTER (ccn),
4683 (CLASS_INTERFACE (class_decl) ? "interface" : "class"),
4684 IDENTIFIER_POINTER (DECL_NAME (class_decl)));
4685
4686 free (t);
4687
4688 if (saved_wfl)
4689 DECL_NAME (method) = saved_wfl;
4690 }
4691 }
4692}
4693
4694/* Check that CLASS_DECL somehoow implements all inherited abstract
4695 methods. */
4696
4697static void
4698java_check_abstract_method_definitions (class_decl)
4699 tree class_decl;
4700{
4701 tree class = TREE_TYPE (class_decl);
4702 tree super, vector;
4703 int i;
4704
4705 if (CLASS_ABSTRACT (class_decl))
4706 return;
4707
4708 /* Check for inherited types */
4709 for (super = CLASSTYPE_SUPER (class); super != object_type_node;
4710 super = CLASSTYPE_SUPER (super))
4711 {
4712 if (!CLASS_ABSTRACT (TYPE_NAME (super)))
4713 continue;
4714
4715 check_abstract_method_definitions (0, class_decl, super);
4716 }
4717
4718 /* Check for implemented interfaces. */
4719 vector = TYPE_BINFO_BASETYPES (class);
4720 for (i = 1; i < TREE_VEC_LENGTH (vector); i++)
4721 {
4722 super = BINFO_TYPE (TREE_VEC_ELT (vector, i));
4723 check_abstract_method_definitions (1, class_decl, super);
4724 }
4725}
4726
4727/* Check all the methods of CLASS_DECL. Methods are first completed
4728 then checked according to regular method existance rules. If no
4729 constructor for CLASS_DECL were encountered, then build its
4730 declaration. */
e04a16fb
AG
4731
4732static void
4733java_check_regular_methods (class_decl)
4734 tree class_decl;
4735{
5e942c50 4736 int saw_constructor = 0;
e04a16fb
AG
4737 tree method;
4738 tree class = CLASS_TO_HANDLE_TYPE (TREE_TYPE (class_decl));
4739 tree super_class = CLASSTYPE_SUPER (class);
5e942c50 4740 tree saved_found_wfl = NULL_TREE, found = NULL_TREE;
c877974e
APB
4741 tree mthrows;
4742
4743 /* It is not necessary to check methods defined in java.lang.Object */
4744 if (class == object_type_node)
4745 return;
e04a16fb 4746
23a79c61
APB
4747 if (!TYPE_NVIRTUALS (class))
4748 TYPE_METHODS (class) = nreverse (TYPE_METHODS (class));
e04a16fb
AG
4749
4750 /* Should take interfaces into account. FIXME */
4751 for (method = TYPE_METHODS (class); method; method = TREE_CHAIN (method))
4752 {
5e942c50 4753 tree sig;
e04a16fb
AG
4754 tree method_wfl = DECL_NAME (method);
4755 int aflags;
4756
5e942c50
APB
4757 /* If we previously found something and its name was saved,
4758 reinstall it now */
4759 if (found && saved_found_wfl)
ba179f9f
APB
4760 {
4761 DECL_NAME (found) = saved_found_wfl;
4762 saved_found_wfl = NULL_TREE;
4763 }
5e942c50 4764
e04a16fb
AG
4765 /* Check for redefinitions */
4766 if (check_method_redefinition (class, method))
4767 continue;
4768
22eed1e6
APB
4769 /* If we see one constructor a mark so we don't generate the
4770 default one. Also skip other verifications: constructors
4771 can't be inherited hence hiden or overriden */
4772 if (DECL_CONSTRUCTOR_P (method))
4773 {
4774 saw_constructor = 1;
4775 continue;
4776 }
4777
c877974e
APB
4778 /* We verify things thrown by the method. They must inherits from
4779 java.lang.Throwable */
4780 for (mthrows = DECL_FUNCTION_THROWS (method);
4781 mthrows; mthrows = TREE_CHAIN (mthrows))
4782 {
4783 if (!inherits_from_p (TREE_VALUE (mthrows), throwable_type_node))
4784 parse_error_context
4785 (TREE_PURPOSE (mthrows), "Class `%s' in `throws' clause must be "
4786 "a subclass of class `java.lang.Throwable'",
4787 IDENTIFIER_POINTER
4788 (DECL_NAME (TYPE_NAME (TREE_VALUE (mthrows)))));
4789 }
4790
e04a16fb 4791 sig = build_java_argument_signature (TREE_TYPE (method));
e04a16fb 4792 found = lookup_argument_method (super_class, DECL_NAME (method), sig);
b9f7e36c 4793
5e942c50 4794 /* Nothing overrides or it's a private method. */
aabd7048 4795 if (!found)
5e942c50 4796 continue;
aabd7048
PB
4797 if (METHOD_PRIVATE (found))
4798 {
4799 found = NULL_TREE;
4800 continue;
4801 }
5e942c50
APB
4802
4803 /* If found wasn't verified, it's DECL_NAME won't be set properly.
4804 We set it temporarily for the sake of the error report. */
4805 saved_found_wfl = DECL_NAME (found);
4806 reset_method_name (found);
4807
e04a16fb
AG
4808 /* Can't override a method with the same name and different return
4809 types. */
4810 if (TREE_TYPE (TREE_TYPE (found)) != TREE_TYPE (TREE_TYPE (method)))
b9f7e36c 4811 {
c2e3db92 4812 char *t = xstrdup (lang_printable_name (TREE_TYPE (TREE_TYPE (found)),
0a2138e2 4813 0));
b9f7e36c 4814 parse_error_context
7f10c2e2 4815 (method_wfl,
b9f7e36c 4816 "Method `%s' was defined with return type `%s' in class `%s'",
0a2138e2 4817 lang_printable_name (found, 0), t,
b9f7e36c
APB
4818 IDENTIFIER_POINTER
4819 (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
4820 free (t);
4821 }
e04a16fb 4822
7f10c2e2
APB
4823 aflags = get_access_flags_from_decl (found);
4824 /* If the method has default, access in an other package, then
4825 issue a warning that the current method doesn't override the
4826 one that was found elsewhere. Do not issue this warning when
4827 the match was found in java.lang.Object. */
4828 if (DECL_CONTEXT (found) != object_type_node
4829 && ((aflags & 0x7) == 0)
4830 && !class_in_current_package (DECL_CONTEXT (found))
1fb89a4d 4831 && DECL_NAME (found) != clinit_identifier_node
7f10c2e2
APB
4832 && flag_not_overriding)
4833 {
4834 parse_warning_context
4835 (method_wfl, "Method `%s' in class `%s' does not "
4836 "override the corresponding method in class `%s', which is "
4837 "private to a different package",
4838 lang_printable_name (found, 0),
4839 IDENTIFIER_POINTER (DECL_NAME (class_decl)),
4840 IDENTIFIER_POINTER (DECL_NAME
4841 (TYPE_NAME (DECL_CONTEXT (found)))));
4842 continue;
4843 }
4844
e04a16fb
AG
4845 /* Can't override final. Can't override static. */
4846 if (METHOD_FINAL (found) || METHOD_STATIC (found))
4847 {
4848 /* Static *can* override static */
4849 if (METHOD_STATIC (found) && METHOD_STATIC (method))
4850 continue;
4851 parse_error_context
4852 (method_wfl,
4853 "%s methods can't be overriden. Method `%s' is %s in class `%s'",
4854 (METHOD_FINAL (found) ? "Final" : "Static"),
0a2138e2 4855 lang_printable_name (found, 0),
e04a16fb
AG
4856 (METHOD_FINAL (found) ? "final" : "static"),
4857 IDENTIFIER_POINTER
4858 (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
4859 continue;
4860 }
7f10c2e2 4861
e04a16fb
AG
4862 /* Static method can't override instance method. */
4863 if (METHOD_STATIC (method))
4864 {
4865 parse_error_context
4866 (method_wfl,
4867 "Instance methods can't be overriden by a static method. Method "
4868 "`%s' is an instance method in class `%s'",
0a2138e2 4869 lang_printable_name (found, 0),
e04a16fb
AG
4870 IDENTIFIER_POINTER
4871 (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
4872 continue;
4873 }
5e942c50 4874
5e942c50
APB
4875 /* - Overriding/hiding public must be public
4876 - Overriding/hiding protected must be protected or public
4877 - If the overriden or hidden method has default (package)
4878 access, then the overriding or hiding method must not be
4879 private; otherwise, a compile-time error occurs */
4880 if ((METHOD_PUBLIC (found) && !METHOD_PUBLIC (method))
4881 || (METHOD_PROTECTED (found)
4882 && !(METHOD_PUBLIC (method) || METHOD_PROTECTED (method)))
4883 || (!(aflags & (ACC_PUBLIC | ACC_PRIVATE | ACC_STATIC))
4884 && METHOD_PRIVATE (method)))
e04a16fb
AG
4885 {
4886 parse_error_context
4887 (method_wfl,
4888 "Methods can't be overridden to be more private. Method `%s' is "
5e942c50
APB
4889 "not %s in class `%s'", lang_printable_name (method, 0),
4890 (METHOD_PUBLIC (method) ? "public" :
4891 (METHOD_PRIVATE (method) ? "private" : "protected")),
4892 IDENTIFIER_POINTER (DECL_NAME
4893 (TYPE_NAME (DECL_CONTEXT (found)))));
e04a16fb
AG
4894 continue;
4895 }
4896
b9f7e36c
APB
4897 /* Overriding methods must have compatible `throws' clauses on checked
4898 exceptions, if any */
4899 check_throws_clauses (method, method_wfl, found);
4900
e04a16fb
AG
4901 /* Inheriting multiple methods with the same signature. FIXME */
4902 }
4903
5e942c50
APB
4904 /* Don't forget eventual pending found and saved_found_wfl. Take
4905 into account that we might have exited because we saw an
d77613be 4906 artificial method as the last entry. */
5e942c50
APB
4907
4908 if (found && !DECL_ARTIFICIAL (found) && saved_found_wfl)
4909 DECL_NAME (found) = saved_found_wfl;
4910
23a79c61
APB
4911 if (!TYPE_NVIRTUALS (class))
4912 TYPE_METHODS (class) = nreverse (TYPE_METHODS (class));
e04a16fb 4913
d77613be
APB
4914 /* Search for inherited abstract method not yet implemented in this
4915 class. */
4916 java_check_abstract_method_definitions (class_decl);
4917
22eed1e6 4918 if (!saw_constructor)
e04a16fb 4919 {
23a79c61
APB
4920 /* No constructor seen, we craft one, at line 0. Since this
4921 operation takes place after we laid methods out
4922 (layout_class_methods), we prepare the its DECL
4923 appropriately. */
22eed1e6
APB
4924 int flags;
4925 tree decl;
4926
4927 /* If the class is declared PUBLIC, the default constructor is
4928 PUBLIC otherwise it has default access implied by no access
4929 modifiers. */
4930 flags = (get_access_flags_from_decl (class_decl) & ACC_PUBLIC ?
4931 ACC_PUBLIC : 0);
4932 decl = create_artificial_method (class, flags, void_type_node,
de4c7b02 4933 init_identifier_node, end_params_node);
e04a16fb 4934 DECL_CONSTRUCTOR_P (decl) = 1;
23a79c61 4935 layout_class_method (TREE_TYPE (class_decl), NULL_TREE, decl, NULL_TREE);
e04a16fb
AG
4936 }
4937}
4938
b9f7e36c
APB
4939/* Return a non zero value if the `throws' clause of METHOD (if any)
4940 is incompatible with the `throws' clause of FOUND (if any). */
4941
4942static void
4943check_throws_clauses (method, method_wfl, found)
4944 tree method, method_wfl, found;
4945{
4946 tree mthrows, fthrows;
4947
c877974e
APB
4948 /* Can't check these things with class loaded from bytecode. FIXME */
4949 if (!CLASS_FROM_SOURCE_P (DECL_CONTEXT (found)))
4950 return;
4951
b9f7e36c
APB
4952 for (mthrows = DECL_FUNCTION_THROWS (method);
4953 mthrows; mthrows = TREE_CHAIN (mthrows))
4954 {
4955 /* We don't verify unchecked expressions */
c877974e 4956 if (IS_UNCHECKED_EXCEPTION_P (TREE_VALUE (mthrows)))
b9f7e36c
APB
4957 continue;
4958 /* Checked expression must be compatible */
4959 for (fthrows = DECL_FUNCTION_THROWS (found);
4960 fthrows; fthrows = TREE_CHAIN (fthrows))
4961 if (inherits_from_p (TREE_VALUE (mthrows), TREE_VALUE (fthrows)))
4962 break;
4963 if (!fthrows)
4964 {
4965 parse_error_context
4966 (method_wfl, "Invalid checked exception class `%s' in "
4967 "`throws' clause. The exception must be a subclass of an "
4968 "exception thrown by `%s' from class `%s'",
4969 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (TREE_VALUE (mthrows)))),
0a2138e2 4970 lang_printable_name (found, 0),
b9f7e36c
APB
4971 IDENTIFIER_POINTER
4972 (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
4973 }
4974 }
4975}
4976
e04a16fb
AG
4977/* Check abstract method of interface INTERFACE */
4978
4979static void
5e942c50
APB
4980java_check_abstract_methods (interface_decl)
4981 tree interface_decl;
e04a16fb
AG
4982{
4983 int i, n;
4984 tree method, basetype_vec, found;
5e942c50 4985 tree interface = TREE_TYPE (interface_decl);
e04a16fb
AG
4986
4987 for (method = TYPE_METHODS (interface); method; method = TREE_CHAIN (method))
4988 {
b9f7e36c 4989 tree method_wfl = DECL_NAME (method);
e04a16fb
AG
4990
4991 /* 2- Check for double definition inside the defining interface */
4992 if (check_method_redefinition (interface, method))
4993 continue;
4994
4995 /* 3- Overriding is OK as far as we preserve the return type and
b9f7e36c 4996 the thrown exceptions (FIXME) */
e04a16fb
AG
4997 found = lookup_java_interface_method2 (interface, method);
4998 if (found)
4999 {
5e942c50
APB
5000 char *t;
5001 tree saved_found_wfl = DECL_NAME (found);
5002 reset_method_name (found);
c2e3db92 5003 t = xstrdup (lang_printable_name (TREE_TYPE (TREE_TYPE (found)), 0));
e04a16fb 5004 parse_error_context
b9f7e36c 5005 (method_wfl,
5e942c50 5006 "Method `%s' was defined with return type `%s' in class `%s'",
0a2138e2 5007 lang_printable_name (found, 0), t,
b9f7e36c
APB
5008 IDENTIFIER_POINTER
5009 (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
5010 free (t);
e04a16fb 5011 continue;
5e942c50
APB
5012
5013 DECL_NAME (found) = saved_found_wfl;
e04a16fb
AG
5014 }
5015 }
5016
5017 /* 4- Inherited methods can't differ by their returned types */
5018 if (!(basetype_vec = TYPE_BINFO_BASETYPES (interface)))
5019 return;
5020 n = TREE_VEC_LENGTH (basetype_vec);
5021 for (i = 0; i < n; i++)
5022 {
5023 tree sub_interface_method, sub_interface;
5024 tree vec_elt = TREE_VEC_ELT (basetype_vec, i);
5025 if (!vec_elt)
5026 continue;
5027 sub_interface = BINFO_TYPE (vec_elt);
5028 for (sub_interface_method = TYPE_METHODS (sub_interface);
5029 sub_interface_method;
5030 sub_interface_method = TREE_CHAIN (sub_interface_method))
5031 {
5032 found = lookup_java_interface_method2 (interface,
5033 sub_interface_method);
5034 if (found && (found != sub_interface_method))
5e942c50
APB
5035 {
5036 tree saved_found_wfl = DECL_NAME (found);
5037 reset_method_name (found);
5038 parse_error_context
5039 (lookup_cl (sub_interface_method),
5040 "Interface `%s' inherits method `%s' from interface `%s'. "
5041 "This method is redefined with a different return type in "
5042 "interface `%s'",
5043 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (interface))),
5044 lang_printable_name (found, 0),
5045 IDENTIFIER_POINTER
5046 (DECL_NAME (TYPE_NAME
5047 (DECL_CONTEXT (sub_interface_method)))),
5048 IDENTIFIER_POINTER
5049 (DECL_NAME (TYPE_NAME (DECL_CONTEXT (found)))));
5050 DECL_NAME (found) = saved_found_wfl;
5051 }
e04a16fb
AG
5052 }
5053 }
5054}
5055
e04a16fb
AG
5056/* Lookup methods in interfaces using their name and partial
5057 signature. Return a matching method only if their types differ. */
5058
5059static tree
5060lookup_java_interface_method2 (class, method_decl)
5061 tree class, method_decl;
5062{
5063 int i, n;
5064 tree basetype_vec = TYPE_BINFO_BASETYPES (class), to_return;
5065
5066 if (!basetype_vec)
5067 return NULL_TREE;
5068
5069 n = TREE_VEC_LENGTH (basetype_vec);
5070 for (i = 0; i < n; i++)
5071 {
5072 tree vec_elt = TREE_VEC_ELT (basetype_vec, i), to_return;
5073 if ((BINFO_TYPE (vec_elt) != object_type_node)
5074 && (to_return =
5075 lookup_java_method2 (BINFO_TYPE (vec_elt), method_decl, 1)))
5076 return to_return;
5077 }
5078 for (i = 0; i < n; i++)
5079 {
5080 to_return = lookup_java_interface_method2
5081 (BINFO_TYPE (TREE_VEC_ELT (basetype_vec, i)), method_decl);
5082 if (to_return)
5083 return to_return;
5084 }
5085
5086 return NULL_TREE;
5087}
5088
5089/* Lookup method using their name and partial signature. Return a
5090 matching method only if their types differ. */
5091
5092static tree
5093lookup_java_method2 (clas, method_decl, do_interface)
5094 tree clas, method_decl;
5095 int do_interface;
5096{
5e942c50
APB
5097 tree method, method_signature, method_name, method_type, name;
5098
e04a16fb 5099 method_signature = build_java_argument_signature (TREE_TYPE (method_decl));
5e942c50
APB
5100 name = DECL_NAME (method_decl);
5101 method_name = (TREE_CODE (name) == EXPR_WITH_FILE_LOCATION ?
5102 EXPR_WFL_NODE (name) : name);
e04a16fb
AG
5103 method_type = TREE_TYPE (TREE_TYPE (method_decl));
5104
5105 while (clas != NULL_TREE)
5106 {
5107 for (method = TYPE_METHODS (clas);
5108 method != NULL_TREE; method = TREE_CHAIN (method))
5109 {
5110 tree method_sig = build_java_argument_signature (TREE_TYPE (method));
5e942c50
APB
5111 tree name = DECL_NAME (method);
5112 if ((TREE_CODE (name) == EXPR_WITH_FILE_LOCATION ?
5113 EXPR_WFL_NODE (name) : name) == method_name
e04a16fb
AG
5114 && method_sig == method_signature
5115 && TREE_TYPE (TREE_TYPE (method)) != method_type)
5e942c50 5116 return method;
e04a16fb
AG
5117 }
5118 clas = (do_interface ? NULL_TREE : CLASSTYPE_SUPER (clas));
5119 }
5120 return NULL_TREE;
5121}
5122
f441f671
APB
5123/* Return the line that matches DECL line number, and try its best to
5124 position the column number. Used during error reports. */
e04a16fb
AG
5125
5126static tree
5127lookup_cl (decl)
5128 tree decl;
5129{
5130 static tree cl = NULL_TREE;
f441f671 5131 char *line, *found;
e04a16fb
AG
5132
5133 if (!decl)
5134 return NULL_TREE;
5135
5136 if (cl == NULL_TREE)
5137 cl = build_expr_wfl (NULL_TREE, NULL, 0, 0);
5138
5139 EXPR_WFL_FILENAME_NODE (cl) = get_identifier (DECL_SOURCE_FILE (decl));
5140 EXPR_WFL_SET_LINECOL (cl, DECL_SOURCE_LINE_FIRST (decl), -1);
5141
f441f671
APB
5142 line = java_get_line_col (IDENTIFIER_POINTER (EXPR_WFL_FILENAME_NODE (cl)),
5143 EXPR_WFL_LINENO (cl), EXPR_WFL_COLNO (cl));
5144
5145 found = strstr ((const char *)line,
5146 (const char *)IDENTIFIER_POINTER (DECL_NAME (decl)));
5147 if (found)
5148 EXPR_WFL_SET_LINECOL (cl, EXPR_WFL_LINENO (cl), found - line);
5149
e04a16fb
AG
5150 return cl;
5151}
5152
5153/* Look for a simple name in the single-type import list */
5154
5155static tree
5156find_name_in_single_imports (name)
5157 tree name;
5158{
5159 tree node;
5160
5161 for (node = ctxp->import_list; node; node = TREE_CHAIN (node))
5162 if (TREE_VALUE (node) == name)
5163 return (EXPR_WFL_NODE (TREE_PURPOSE (node)));
5164
5165 return NULL_TREE;
5166}
5167
5168/* Process all single-type import. */
5169
5170static int
5171process_imports ()
5172{
5173 tree import;
5174 int error_found;
5175
5176 for (import = ctxp->import_list; import; import = TREE_CHAIN (import))
5177 {
5178 tree to_be_found = EXPR_WFL_NODE (TREE_PURPOSE (import));
5179
5180 /* Don't load twice something already defined. */
5181 if (IDENTIFIER_CLASS_VALUE (to_be_found))
5182 continue;
5183 QUALIFIED_P (to_be_found) = 1;
5184 load_class (to_be_found, 0);
5185 error_found =
5186 check_pkg_class_access (to_be_found, TREE_PURPOSE (import));
5187 if (!IDENTIFIER_CLASS_VALUE (to_be_found))
5188 {
5189 parse_error_context (TREE_PURPOSE (import),
5190 "Class or interface `%s' not found in import",
5191 IDENTIFIER_POINTER (to_be_found));
5192 return 1;
5193 }
5194 if (error_found)
5195 return 1;
5196 }
5197 return 0;
5198}
5199
5200/* Possibly find a class imported by a single-type import statement. Return
5201 1 if an error occured, 0 otherwise. */
5202
5203static int
5204find_in_imports (class_type)
5205 tree class_type;
5206{
5207 tree import;
5208
5209 for (import = ctxp->import_list; import; import = TREE_CHAIN (import))
5210 if (TREE_VALUE (import) == TYPE_NAME (class_type))
5211 {
5212 TYPE_NAME (class_type) = EXPR_WFL_NODE (TREE_PURPOSE (import));
5213 QUALIFIED_P (TYPE_NAME (class_type)) = 1;
e04a16fb
AG
5214 }
5215 return 0;
5216}
5217
e04a16fb 5218static int
63a212ed 5219note_possible_classname (name, len)
49f48c71 5220 const char *name;
63a212ed 5221 int len;
e04a16fb 5222{
63a212ed
PB
5223 tree node;
5224 if (len > 5 && strncmp (&name [len-5], ".java", 5) == 0)
5225 len = len - 5;
5226 else if (len > 6 && strncmp (&name [len-6], ".class", 6) == 0)
5227 len = len - 6;
e04a16fb 5228 else
63a212ed
PB
5229 return 0;
5230 node = ident_subst (name, len, "", '/', '.', "");
5231 IS_A_CLASSFILE_NAME (node) = 1; /* Or soon to be */
fe0e4d76 5232 QUALIFIED_P (node) = strchr (name, '/') ? 1 : 0;
63a212ed 5233 return 1;
e04a16fb
AG
5234}
5235
5236/* Read a import directory, gathering potential match for further type
5237 references. Indifferently reads a filesystem or a ZIP archive
5238 directory. */
5239
5240static void
5241read_import_dir (wfl)
5242 tree wfl;
5243{
63a212ed 5244 tree package_id = EXPR_WFL_NODE (wfl);
49f48c71 5245 const char *package_name = IDENTIFIER_POINTER (package_id);
63a212ed 5246 int package_length = IDENTIFIER_LENGTH (package_id);
e04a16fb 5247 DIR *dirp = NULL;
d8fccff5 5248 JCF *saved_jcf = current_jcf;
e04a16fb 5249
63a212ed
PB
5250 int found = 0;
5251 int k;
5252 void *entry;
5253 struct buffer filename[1];
5254
5255
5256 if (IS_AN_IMPORT_ON_DEMAND_P (package_id))
5257 return;
5258 IS_AN_IMPORT_ON_DEMAND_P (package_id) = 1;
5259
5260 BUFFER_INIT (filename);
5261 buffer_grow (filename, package_length + 100);
5262
5263 for (entry = jcf_path_start (); entry != NULL; entry = jcf_path_next (entry))
5264 {
49f48c71 5265 const char *entry_name = jcf_path_name (entry);
63a212ed
PB
5266 int entry_length = strlen (entry_name);
5267 if (jcf_path_is_zipfile (entry))
5268 {
5269 ZipFile *zipf;
5270 buffer_grow (filename, entry_length);
5271 memcpy (filename->data, entry_name, entry_length - 1);
5272 filename->data[entry_length-1] = '\0';
5273 zipf = opendir_in_zip (filename->data, jcf_path_is_system (entry));
5274 if (zipf == NULL)
5275 error ("malformed .zip archive in CLASSPATH: %s", entry_name);
5276 else
5277 {
5278 ZipDirectory *zipd = (ZipDirectory *) zipf->central_directory;
5279 BUFFER_RESET (filename);
5280 for (k = 0; k < package_length; k++)
5281 {
5282 char ch = package_name[k];
5283 *filename->ptr++ = ch == '.' ? '/' : ch;
5284 }
5285 *filename->ptr++ = '/';
5286
345137c7 5287 for (k = 0; k < zipf->count; k++, zipd = ZIPDIR_NEXT (zipd))
63a212ed 5288 {
49f48c71 5289 const char *current_entry = ZIPDIR_FILENAME (zipd);
63a212ed
PB
5290 int current_entry_len = zipd->filename_length;
5291
345137c7
TT
5292 if (current_entry_len >= BUFFER_LENGTH (filename)
5293 && strncmp (filename->data, current_entry,
5294 BUFFER_LENGTH (filename)) != 0)
63a212ed 5295 continue;
345137c7 5296 found |= note_possible_classname (current_entry,
63a212ed
PB
5297 current_entry_len);
5298 }
5299 }
5300 }
5301 else
5302 {
5303 BUFFER_RESET (filename);
5304 buffer_grow (filename, entry_length + package_length + 4);
5305 strcpy (filename->data, entry_name);
5306 filename->ptr = filename->data + entry_length;
5307 for (k = 0; k < package_length; k++)
5308 {
5309 char ch = package_name[k];
5310 *filename->ptr++ = ch == '.' ? '/' : ch;
5311 }
5312 *filename->ptr = '\0';
5313
5314 dirp = opendir (filename->data);
5315 if (dirp == NULL)
5316 continue;
5317 *filename->ptr++ = '/';
5318 for (;;)
5319 {
63a212ed 5320 int len;
49f48c71 5321 const char *d_name;
63a212ed
PB
5322 struct dirent *direntp = readdir (dirp);
5323 if (!direntp)
5324 break;
5325 d_name = direntp->d_name;
5326 len = strlen (direntp->d_name);
5327 buffer_grow (filename, len+1);
5328 strcpy (filename->ptr, d_name);
345137c7 5329 found |= note_possible_classname (filename->data + entry_length,
63a212ed
PB
5330 package_length+len+1);
5331 }
5332 if (dirp)
5333 closedir (dirp);
5334 }
5335 }
e04a16fb 5336
63a212ed 5337 free (filename->data);
e04a16fb 5338
63a212ed
PB
5339 /* Here we should have a unified way of retrieving an entry, to be
5340 indexed. */
5341 if (!found)
e04a16fb
AG
5342 {
5343 static int first = 1;
5344 if (first)
5345 {
1ebadc60
KG
5346 error ("Can't find default package `%s'. Check "
5347 "the CLASSPATH environment variable and the access to the "
5348 "archives.", package_name);
e04a16fb
AG
5349 java_error_count++;
5350 first = 0;
5351 }
5352 else
63a212ed
PB
5353 parse_error_context (wfl, "Package `%s' not found in import",
5354 package_name);
e04a16fb
AG
5355 current_jcf = saved_jcf;
5356 return;
5357 }
e04a16fb
AG
5358 current_jcf = saved_jcf;
5359}
5360
5361/* Possibly find a type in the import on demands specified
5362 types. Returns 1 if an error occured, 0 otherwise. Run throught the
5363 entire list, to detected potential double definitions. */
5364
5365static int
5366find_in_imports_on_demand (class_type)
5367 tree class_type;
5368{
ab3a6dd6 5369 tree node, import, node_to_use = NULL_TREE;
e04a16fb 5370 int seen_once = -1;
ab3a6dd6 5371 tree cl = NULL_TREE;
e04a16fb
AG
5372
5373 for (import = ctxp->import_demand_list; import; import = TREE_CHAIN (import))
5374 {
49f48c71 5375 const char *id_name;
e04a16fb
AG
5376 obstack_grow (&temporary_obstack,
5377 IDENTIFIER_POINTER (EXPR_WFL_NODE (TREE_PURPOSE (import))),
5378 IDENTIFIER_LENGTH (EXPR_WFL_NODE (TREE_PURPOSE (import))));
63a212ed 5379 obstack_1grow (&temporary_obstack, '.');
e04a16fb
AG
5380 obstack_grow0 (&temporary_obstack,
5381 IDENTIFIER_POINTER (TYPE_NAME (class_type)),
5382 IDENTIFIER_LENGTH (TYPE_NAME (class_type)));
5383 id_name = obstack_finish (&temporary_obstack);
5384
5385 node = maybe_get_identifier (id_name);
5386 if (node && IS_A_CLASSFILE_NAME (node))
5387 {
5388 if (seen_once < 0)
5389 {
5390 cl = TREE_PURPOSE (import);
5391 seen_once = 1;
5392 node_to_use = node;
5393 }
5394 else
5395 {
5396 seen_once++;
5397 parse_error_context
5398 (import, "Type `%s' also potentially defined in package `%s'",
5399 IDENTIFIER_POINTER (TYPE_NAME (class_type)),
5400 IDENTIFIER_POINTER (EXPR_WFL_NODE (TREE_PURPOSE (import))));
5401 }
5402 }
5403 }
5404
5405 if (seen_once == 1)
5406 {
5407 /* Setup lineno so that it refers to the line of the import (in
5408 case we parse a class file and encounter errors */
5409 tree decl;
5410 int saved_lineno = lineno;
5411 lineno = EXPR_WFL_LINENO (cl);
63a212ed 5412 TYPE_NAME (class_type) = node_to_use;
e04a16fb
AG
5413 QUALIFIED_P (TYPE_NAME (class_type)) = 1;
5414 decl = IDENTIFIER_CLASS_VALUE (TYPE_NAME (class_type));
5415 /* If there is no DECL set for the class or if the class isn't
5416 loaded and not seen in source yet, the load */
5417 if (!decl || (!CLASS_LOADED_P (TREE_TYPE (decl))
5418 && !CLASS_FROM_SOURCE_P (TREE_TYPE (decl))))
5419 load_class (node_to_use, 0);
5420 lineno = saved_lineno;
5421 return check_pkg_class_access (TYPE_NAME (class_type), cl);
5422 }
5423 else
5424 return (seen_once < 0 ? 0 : seen_once); /* It's ok not to have found */
5425}
5426
5e942c50
APB
5427static tree
5428resolve_package (pkg, next)
5429 tree pkg, *next;
5430{
2c56429a 5431 tree current;
5e942c50 5432 tree type_name = NULL_TREE;
49f48c71 5433 const char *name = IDENTIFIER_POINTER (EXPR_WFL_NODE (pkg));
5e942c50
APB
5434
5435 /* The trick is to determine when the package name stops and were
5436 the name of something contained in the package starts. Then we
5437 return a fully qualified name of what we want to get. */
5438
5439 /* Do a quick search on well known package names */
5440 if (!strncmp (name, "java.lang.reflect", 17))
5441 {
5442 *next =
5443 TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (EXPR_WFL_QUALIFICATION (pkg))));
5444 type_name = lookup_package_type (name, 17);
5445 }
5446 else if (!strncmp (name, "java.lang", 9))
5447 {
5448 *next = TREE_CHAIN (TREE_CHAIN (EXPR_WFL_QUALIFICATION (pkg)));
5449 type_name = lookup_package_type (name, 9);
5450 }
5e942c50 5451
2c56429a
APB
5452 /* If we found something here, return */
5453 if (type_name)
5454 return type_name;
5455
5456 *next = EXPR_WFL_QUALIFICATION (pkg);
5457
5458 /* Try the current package. */
5459 if (ctxp->package && !strncmp (name, IDENTIFIER_POINTER (ctxp->package),
5460 IDENTIFIER_LENGTH (ctxp->package)))
5461 {
5462 type_name =
5463 lookup_package_type_and_set_next (name,
5464 IDENTIFIER_LENGTH (ctxp->package),
5465 next );
5466 if (type_name)
5467 return type_name;
5468 }
5469
5470 /* Search in imported package */
5471 for (current = ctxp->import_list; current; current = TREE_CHAIN (current))
5472 {
5473 tree current_pkg_name = EXPR_WFL_NODE (TREE_PURPOSE (current));
5474 int len = IDENTIFIER_LENGTH (current_pkg_name);
5475 if (!strncmp (name, IDENTIFIER_POINTER (current_pkg_name), len))
5476 {
5477 tree left, dummy;
5478
5479 breakdown_qualified (&left, &dummy, current_pkg_name);
5480 len = IDENTIFIER_LENGTH (left);
5481 type_name = lookup_package_type_and_set_next (name, len, next);
5482 if (type_name)
5483 break;
5484 }
5485 }
5486
5487 return type_name;
5488}
5489
5490static tree
5491lookup_package_type_and_set_next (name, len, next)
49f48c71 5492 const char *name;
2c56429a
APB
5493 int len;
5494 tree *next;
5495{
49f48c71 5496 const char *ptr;
2c56429a
APB
5497 tree type_name = lookup_package_type (name, len);
5498
5499 if (!type_name)
5500 return NULL;
5501
5502 ptr = IDENTIFIER_POINTER (type_name);
5503 while (ptr && (ptr = strchr (ptr, '.')))
5504 {
5505 *next = TREE_CHAIN (*next);
5506 ptr++;
5507 }
5e942c50
APB
5508 return type_name;
5509}
5510
5511static tree
5512lookup_package_type (name, from)
49f48c71 5513 const char *name;
5e942c50
APB
5514 int from;
5515{
5516 char subname [128];
49f48c71 5517 const char *sub = &name[from+1];
5e942c50
APB
5518 while (*sub != '.' && *sub)
5519 sub++;
5520 strncpy (subname, name, sub-name);
5521 subname [sub-name] = '\0';
5522 return get_identifier (subname);
5523}
5524
e04a16fb
AG
5525/* Check that CLASS_NAME refers to a PUBLIC class. Return 0 if no
5526 access violations were found, 1 otherwise. */
5527
5528static int
5529check_pkg_class_access (class_name, cl)
5530 tree class_name;
5531 tree cl;
5532{
5533 tree type;
e04a16fb
AG
5534
5535 if (!QUALIFIED_P (class_name) || !IDENTIFIER_CLASS_VALUE (class_name))
5536 return 0;
5537
5538 if (!(type = TREE_TYPE (IDENTIFIER_CLASS_VALUE (class_name))))
5539 return 0;
5540
5541 if (!CLASS_PUBLIC (TYPE_NAME (type)))
5542 {
e28cd97b
APB
5543 /* Access to a private class within the same package is
5544 allowed. */
5545 tree l, r;
5546 breakdown_qualified (&l, &r, class_name);
5547 if (l == ctxp->package)
5548 return 0;
5549
e04a16fb
AG
5550 parse_error_context
5551 (cl, "Can't access %s `%s'. Only public classes and interfaces in "
5552 "other packages can be accessed",
5553 (CLASS_INTERFACE (TYPE_NAME (type)) ? "interface" : "class"),
5554 IDENTIFIER_POINTER (class_name));
5555 return 1;
5556 }
5557 return 0;
5558}
5559
5560/* Local variable declaration. */
5561
5562static void
5563declare_local_variables (modifier, type, vlist)
5564 int modifier;
5565 tree type;
5566 tree vlist;
5567{
c583dd46
APB
5568 tree decl, current, saved_type;
5569 tree type_wfl = NULL_TREE;
e04a16fb
AG
5570 int must_chain = 0;
5571
2aa11e97 5572 /* Push a new block if statements were seen between the last time we
e04a16fb 5573 pushed a block and now. Keep a cound of block to close */
f099f336 5574 if (BLOCK_EXPR_BODY (GET_CURRENT_BLOCK (current_function_decl)))
e04a16fb 5575 {
f099f336 5576 tree body = GET_CURRENT_BLOCK (current_function_decl);
e04a16fb 5577 tree b = enter_block ();
f099f336 5578 BLOCK_EXPR_ORIGIN (b) = body;
e04a16fb
AG
5579 }
5580
5581 if (modifier)
5582 {
5583 int i;
5584 for (i = 0; i <= 10; i++) if (1 << i & modifier) break;
c877974e
APB
5585 if (modifier == ACC_FINAL)
5586 {
5587 if (flag_static_local_jdk1_1)
5588 parse_warning_context (ctxp->modifier_ctx [i],
5589 "Unsupported JDK1.1 `final' local variable "
5590 "(treated as non final)");
5591 }
5592 else
5593 {
5594 parse_error_context
5595 (ctxp->modifier_ctx [i],
5596 "Only `final' is allowed as a local variables modifier");
5597 return;
5598 }
e04a16fb
AG
5599 }
5600
c583dd46
APB
5601 /* Obtain an incomplete type if TYPE is not complete. TYPE_WFL will
5602 hold the TYPE value if a new incomplete has to be created (as
5603 opposed to being found already existing and reused). */
5604 SET_TYPE_FOR_RESOLUTION (type, type_wfl, must_chain);
5605
5606 /* If TYPE is fully resolved and we don't have a reference, make one */
1886c9d8 5607 PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
c583dd46
APB
5608
5609 /* Go through all the declared variables */
5610 for (current = vlist, saved_type = type; current;
5611 current = TREE_CHAIN (current), type = saved_type)
e04a16fb 5612 {
c877974e 5613 tree other, real_type;
e04a16fb
AG
5614 tree wfl = TREE_PURPOSE (current);
5615 tree name = EXPR_WFL_NODE (wfl);
5616 tree init = TREE_VALUE (current);
e04a16fb 5617
c583dd46
APB
5618 /* Process NAME, as it may specify extra dimension(s) for it */
5619 type = build_array_from_name (type, type_wfl, name, &name);
5620
5621 /* Variable redefinition check */
5622 if ((other = lookup_name_in_blocks (name)))
5623 {
5624 variable_redefinition_error (wfl, name, TREE_TYPE (other),
5625 DECL_SOURCE_LINE (other));
5626 continue;
5627 }
5628
5629 /* Type adjustment. We may have just readjusted TYPE because
5630 the variable specified more dimensions. Make sure we have
5631 a reference if we can and don't have one already. */
1886c9d8 5632 PROMOTE_RECORD_IF_COMPLETE (type, must_chain);
c877974e
APB
5633
5634 real_type = GET_REAL_TYPE (type);
c583dd46
APB
5635 /* Never layout this decl. This will be done when its scope
5636 will be entered */
c877974e 5637 decl = build_decl (VAR_DECL, name, real_type);
c583dd46
APB
5638 BLOCK_CHAIN_DECL (decl);
5639
d4370213
APB
5640 /* If doing xreferencing, replace the line number with the WFL
5641 compound value */
5642 if (flag_emit_xref)
5643 DECL_SOURCE_LINE (decl) = EXPR_WFL_LINECOL (wfl);
5644
e04a16fb
AG
5645 /* Don't try to use an INIT statement when an error was found */
5646 if (init && java_error_count)
5647 init = NULL_TREE;
c583dd46
APB
5648
5649 /* Add the initialization function to the current function's code */
5650 if (init)
e04a16fb 5651 {
c583dd46
APB
5652 /* Name might have been readjusted */
5653 EXPR_WFL_NODE (TREE_OPERAND (init, 0)) = name;
5654 MODIFY_EXPR_FROM_INITIALIZATION_P (init) = 1;
5655 java_method_add_stmt (current_function_decl,
5656 build_debugable_stmt (EXPR_WFL_LINECOL (init),
5657 init));
5658 }
5659
5660 /* Setup dependency the type of the decl */
5661 if (must_chain)
5662 {
5663 jdep *dep;
5664 register_incomplete_type (JDEP_VARIABLE, type_wfl, decl, type);
5665 dep = CLASSD_LAST (ctxp->classd_list);
5666 JDEP_GET_PATCH (dep) = &TREE_TYPE (decl);
e04a16fb
AG
5667 }
5668 }
5669 SOURCE_FRONTEND_DEBUG (("Defined locals"));
5670}
5671
5672/* Called during parsing. Build decls from argument list. */
5673
5674static void
5675source_start_java_method (fndecl)
5676 tree fndecl;
5677{
5678 tree tem;
5679 tree parm_decl;
5680 int i;
5681
79d13333
APB
5682 if (!fndecl)
5683 return;
5684
e04a16fb
AG
5685 current_function_decl = fndecl;
5686
5687 /* New scope for the function */
5688 enter_block ();
5689 for (tem = TYPE_ARG_TYPES (TREE_TYPE (fndecl)), i = 0;
de4c7b02 5690 tem != end_params_node; tem = TREE_CHAIN (tem), i++)
e04a16fb
AG
5691 {
5692 tree type = TREE_VALUE (tem);
5693 tree name = TREE_PURPOSE (tem);
5694
23a79c61
APB
5695 /* If type is incomplete. Create an incomplete decl and ask for
5696 the decl to be patched later */
e04a16fb
AG
5697 if (INCOMPLETE_TYPE_P (type))
5698 {
5699 jdep *jdep;
c877974e
APB
5700 tree real_type = GET_REAL_TYPE (type);
5701 parm_decl = build_decl (PARM_DECL, name, real_type);
23a79c61 5702 type = obtain_incomplete_type (type);
e04a16fb
AG
5703 register_incomplete_type (JDEP_PARM, NULL_TREE, NULL_TREE, type);
5704 jdep = CLASSD_LAST (ctxp->classd_list);
5705 JDEP_MISC (jdep) = name;
5706 JDEP_GET_PATCH (jdep) = &TREE_TYPE (parm_decl);
5707 }
5708 else
5709 parm_decl = build_decl (PARM_DECL, name, type);
5710
5711 BLOCK_CHAIN_DECL (parm_decl);
5712 }
5713 tem = BLOCK_EXPR_DECLS (DECL_FUNCTION_BODY (current_function_decl));
5714 BLOCK_EXPR_DECLS (DECL_FUNCTION_BODY (current_function_decl)) =
5715 nreverse (tem);
5716 DECL_ARG_SLOT_COUNT (current_function_decl) = i;
5717}
5718
22eed1e6
APB
5719/* Called during parsing. Creates an artificial method declaration. */
5720
5721static tree
5722create_artificial_method (class, flags, type, name, args)
5723 tree class;
5724 int flags;
5725 tree type, name, args;
5726{
5727 int saved_lineno = lineno;
5728 tree mdecl;
5729
5730 lineno = 0;
5731 mdecl = make_node (FUNCTION_TYPE);
5732 TREE_TYPE (mdecl) = type;
5733 TYPE_ARG_TYPES (mdecl) = args;
5734 mdecl = add_method (class, flags, name, build_java_signature (mdecl));
5735 lineno = saved_lineno;
5736 DECL_ARTIFICIAL (mdecl) = 1;
5737 return mdecl;
5738}
5739
5740/* Starts the body if an artifical method. */
5741
5742static void
5743start_artificial_method_body (mdecl)
5744 tree mdecl;
5745{
5746 DECL_SOURCE_LINE (mdecl) = 1;
5747 DECL_SOURCE_LINE_MERGE (mdecl, 1);
5748 source_start_java_method (mdecl);
5749 enter_block ();
5750}
5751
5752static void
5753end_artificial_method_body (mdecl)
5754 tree mdecl;
5755{
5756 BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (mdecl)) = exit_block ();
5757 exit_block ();
5758}
5759
e04a16fb
AG
5760/* Called during expansion. Push decls formerly built from argument
5761 list so they're usable during expansion. */
5762
5763static void
5764expand_start_java_method (fndecl)
5765 tree fndecl;
5766{
5767 tree tem, *ptr;
e04a16fb 5768
e04a16fb
AG
5769 current_function_decl = fndecl;
5770
5771 announce_function (fndecl);
5772 pushlevel (1); /* Push parameters */
5773 ptr = &DECL_ARGUMENTS (fndecl);
5774 tem = BLOCK_EXPR_DECLS (DECL_FUNCTION_BODY (current_function_decl));
5775 while (tem)
5776 {
5777 tree next = TREE_CHAIN (tem);
b67d701b 5778 tree type = TREE_TYPE (tem);
e438e1b7
JJ
5779 if (PROMOTE_PROTOTYPES
5780 && TYPE_PRECISION (type) < TYPE_PRECISION (integer_type_node)
b67d701b
PB
5781 && INTEGRAL_TYPE_P (type))
5782 type = integer_type_node;
b67d701b 5783 DECL_ARG_TYPE (tem) = type;
e04a16fb
AG
5784 layout_decl (tem, 0);
5785 pushdecl (tem);
e04a16fb
AG
5786 *ptr = tem;
5787 ptr = &TREE_CHAIN (tem);
5788 tem = next;
5789 }
5790 *ptr = NULL_TREE;
5791 pushdecl_force_head (DECL_ARGUMENTS (fndecl));
5792 lineno = DECL_SOURCE_LINE_FIRST (fndecl);
e04a16fb
AG
5793}
5794
5795/* Terminate a function and expand its body. */
5796
5797static void
5798source_end_java_method ()
5799{
5800 tree fndecl = current_function_decl;
138657ec 5801 int flag_asynchronous_exceptions = asynchronous_exceptions;
e04a16fb 5802
79d13333
APB
5803 if (!fndecl)
5804 return;
5805
e04a16fb
AG
5806 java_parser_context_save_global ();
5807 lineno = ctxp->last_ccb_indent1;
5808
b67d701b
PB
5809 /* Set EH language codes */
5810 java_set_exception_lang_code ();
5811
5423609c
APB
5812 /* Turn function bodies with only a NOP expr null, so they don't get
5813 generated at all and we won't get warnings when using the -W
5814 -Wall flags. */
5815 if (BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (fndecl)) == empty_stmt_node)
5816 BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (fndecl)) = NULL_TREE;
5817
e04a16fb
AG
5818 /* Generate function's code */
5819 if (BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (fndecl))
e8fc7396
APB
5820 && ! flag_emit_class_files
5821 && ! flag_emit_xref)
e04a16fb
AG
5822 expand_expr_stmt (BLOCK_EXPR_BODY (DECL_FUNCTION_BODY (fndecl)));
5823
5824 /* pop out of its parameters */
5825 pushdecl_force_head (DECL_ARGUMENTS (fndecl));
5826 poplevel (1, 0, 1);
5827 BLOCK_SUPERCONTEXT (DECL_INITIAL (fndecl)) = fndecl;
5828
5829 /* Generate rtl for function exit. */
e8fc7396 5830 if (! flag_emit_class_files && ! flag_emit_xref)
e04a16fb
AG
5831 {
5832 lineno = DECL_SOURCE_LINE_LAST (fndecl);
b67d701b
PB
5833 /* Emit catch-finally clauses */
5834 emit_handlers ();
e04a16fb
AG
5835 expand_function_end (input_filename, lineno, 0);
5836
138657ec
AH
5837 /* FIXME: If the current method contains any exception handlers,
5838 force asynchronous_exceptions: this is necessary because signal
5839 handlers in libjava may throw exceptions. This is far from being
5840 a perfect solution, but it's better than doing nothing at all.*/
5841 if (catch_clauses)
5842 asynchronous_exceptions = 1;
5843
e04a16fb
AG
5844 /* Run the optimizers and output assembler code for this function. */
5845 rest_of_compilation (fndecl);
5846 }
5847
5848 current_function_decl = NULL_TREE;
8226320b 5849 permanent_allocation (1);
e04a16fb 5850 java_parser_context_restore_global ();
138657ec 5851 asynchronous_exceptions = flag_asynchronous_exceptions;
e04a16fb
AG
5852}
5853
5854/* Record EXPR in the current function block. Complements compound
5855 expression second operand if necessary. */
5856
5857tree
5858java_method_add_stmt (fndecl, expr)
5859 tree fndecl, expr;
5860{
b771925e
APB
5861 if (!GET_CURRENT_BLOCK (fndecl))
5862 return NULL_TREE;
f099f336 5863 return add_stmt_to_block (GET_CURRENT_BLOCK (fndecl), NULL_TREE, expr);
b67d701b 5864}
e04a16fb 5865
b67d701b
PB
5866static tree
5867add_stmt_to_block (b, type, stmt)
5868 tree b, type, stmt;
5869{
5870 tree body = BLOCK_EXPR_BODY (b), c;
5871
e04a16fb
AG
5872 if (java_error_count)
5873 return body;
b67d701b
PB
5874
5875 if ((c = add_stmt_to_compound (body, type, stmt)) == body)
e04a16fb
AG
5876 return body;
5877
b67d701b
PB
5878 BLOCK_EXPR_BODY (b) = c;
5879 TREE_SIDE_EFFECTS (c) = 1;
5880 return c;
e04a16fb
AG
5881}
5882
5883/* Add STMT to EXISTING if possible, otherwise create a new
5884 COMPOUND_EXPR and add STMT to it. */
5885
5886static tree
5887add_stmt_to_compound (existing, type, stmt)
5888 tree existing, type, stmt;
5889{
15fdcfe9
PB
5890 if (existing)
5891 return build (COMPOUND_EXPR, type, existing, stmt);
e04a16fb 5892 else
15fdcfe9 5893 return stmt;
e04a16fb
AG
5894}
5895
5896/* Hold THIS for the scope of the current public method decl. */
5897static tree current_this;
5898
1886c9d8
APB
5899void java_layout_seen_class_methods ()
5900{
5901 tree previous_list = all_class_list;
5902 tree end = NULL_TREE;
5903 tree current;
5904
5905 while (1)
5906 {
5907 for (current = previous_list;
5908 current != end; current = TREE_CHAIN (current))
5909 layout_class_methods (TREE_TYPE (TREE_VALUE (current)));
5910
5911 if (previous_list != all_class_list)
5912 {
5913 end = previous_list;
5914 previous_list = all_class_list;
5915 }
5916 else
5917 break;
5918 }
5919}
5920
23a79c61
APB
5921/* Layout the methods of all classes loaded in one way on an
5922 other. Check methods of source parsed classes. Then reorder the
5923 fields and layout the classes or the type of all source parsed
5924 classes */
e04a16fb
AG
5925
5926void
5927java_layout_classes ()
5928{
5929 tree current;
bc3ca41b 5930 int save_error_count = java_error_count;
5e942c50 5931
23a79c61 5932 /* Layout the methods of all classes seen so far */
1886c9d8 5933 java_layout_seen_class_methods ();
23a79c61
APB
5934 java_parse_abort_on_error ();
5935 all_class_list = NULL_TREE;
5936
5937 /* Then check the methods of all parsed classes */
5938 for (current = ctxp->gclass_list; current; current = TREE_CHAIN (current))
5939 if (CLASS_FROM_SOURCE_P (TREE_TYPE (TREE_VALUE (current))))
5940 CHECK_METHODS (TREE_VALUE (current));
5941 java_parse_abort_on_error ();
5942
5e942c50 5943 for (current = ctxp->gclass_list; current; current = TREE_CHAIN (current))
e04a16fb 5944 {
5e942c50 5945 current_class = TREE_TYPE (TREE_VALUE (current));
22eed1e6 5946
c877974e
APB
5947 /* Reverse the fields, but leave the dummy field in front.
5948 Fields are already ordered for Object and Class */
5949 if (TYPE_FIELDS (current_class) && current_class != object_type_node
5950 && current_class != class_type_node)
5951 {
23a79c61
APB
5952 /* If the dummy field is there, reverse the right fields and
5953 just layout the type for proper fields offset */
c877974e
APB
5954 if (!DECL_NAME (TYPE_FIELDS (current_class)))
5955 {
5956 tree fields = TYPE_FIELDS (current_class);
5957 TREE_CHAIN (fields) = nreverse (TREE_CHAIN (fields));
5958 TYPE_SIZE (current_class) = NULL_TREE;
5959 layout_type (current_class);
5960 }
23a79c61
APB
5961 /* We don't have a dummy field, we need to layout the class,
5962 after having reversed the fields */
c877974e
APB
5963 else
5964 {
5965 TYPE_FIELDS (current_class) =
5966 nreverse (TYPE_FIELDS (current_class));
5967 TYPE_SIZE (current_class) = NULL_TREE;
5968 layout_class (current_class);
5969 }
5970 }
23a79c61
APB
5971 else
5972 layout_class (current_class);
5e942c50 5973
c877974e
APB
5974 /* From now on, the class is considered completely loaded */
5975 CLASS_LOADED_P (current_class) = 1;
5976
5e942c50
APB
5977 /* Error reported by the caller */
5978 if (java_error_count)
5979 return;
e04a16fb 5980 }
23a79c61
APB
5981
5982 /* We might have reloaded classes durign the process of laying out
5983 classes for code generation. We must layout the methods of those
5984 late additions, as constructor checks might use them */
1886c9d8 5985 java_layout_seen_class_methods ();
23a79c61 5986 java_parse_abort_on_error ();
e04a16fb
AG
5987}
5988
5989/* Expand all methods in all registered classes. */
5990
49f48c71 5991static void
e04a16fb
AG
5992java_complete_expand_methods ()
5993{
5994 tree current;
ce6e9147
APB
5995
5996 do_not_fold = flag_emit_xref;
e04a16fb
AG
5997
5998 for (current = ctxp->class_list; current; current = TREE_CHAIN (current))
5999 {
7f1d4866 6000 int is_interface;
e04a16fb
AG
6001 tree class_type = CLASS_TO_HANDLE_TYPE (TREE_TYPE (current));
6002 tree decl;
e04a16fb
AG
6003
6004 current_class = TREE_TYPE (current);
7f1d4866 6005 is_interface = CLASS_INTERFACE (TYPE_NAME (current_class));
e04a16fb
AG
6006
6007 /* Initialize a new constant pool */
6008 init_outgoing_cpool ();
6009
7525cc04
APB
6010 /* We want <clinit> (if any) to be processed first. */
6011 decl = tree_last (TYPE_METHODS (class_type));
7f1d4866 6012 if (IS_CLINIT (decl))
7525cc04 6013 {
cd9643f7
PB
6014 tree fbody = DECL_FUNCTION_BODY (decl);
6015 tree list;
6016 if (fbody != NULL_TREE)
6017 {
6018 /* First check if we can ignore empty <clinit> */
6019 tree block_body = BLOCK_EXPR_BODY (fbody);
6020
6021 current_this = NULL_TREE;
6022 current_function_decl = decl;
6023 if (block_body != NULL_TREE)
6024 {
6025 /* Prevent the use of `this' inside <clinit> */
6026 ctxp->explicit_constructor_p = 1;
6027
6028 block_body = java_complete_tree (block_body);
6029 ctxp->explicit_constructor_p = 0;
6030 BLOCK_EXPR_BODY (fbody) = block_body;
6031 if (block_body != NULL_TREE
6032 && TREE_CODE (block_body) == BLOCK
6033 && BLOCK_EXPR_BODY (block_body) == empty_stmt_node)
6034 decl = NULL_TREE;
6035 }
6036 }
6037 list = nreverse (TREE_CHAIN (nreverse (TYPE_METHODS (class_type))));
6038 if (decl != NULL_TREE)
6039 {
6040 TREE_CHAIN (decl) = list;
6041 TYPE_METHODS (class_type) = decl;
6042 }
6043 else
6044 TYPE_METHODS (class_type) = list;
7525cc04 6045 }
7f1d4866
APB
6046
6047 for (decl = TYPE_METHODS (class_type); decl; decl = TREE_CHAIN (decl))
6048 {
7f1d4866
APB
6049 current_function_decl = decl;
6050 /* Don't generate debug info on line zero when expanding a
6051 generated constructor. */
6052 if (DECL_CONSTRUCTOR_P (decl) && !DECL_FUNCTION_BODY (decl))
6053 {
6054 /* If we found errors, it's too dangerous to try to
6055 generate and expand a constructor */
6056 if (!java_error_count)
6057 {
6058 restore_line_number_status (1);
6059 java_complete_expand_method (decl);
6060 restore_line_number_status (0);
e04a16fb 6061 }
7f1d4866
APB
6062 }
6063 else if (METHOD_ABSTRACT (decl) || METHOD_NATIVE (decl))
6064 continue;
6065 else
6066 java_complete_expand_method (decl);
6067 }
e04a16fb 6068
22eed1e6
APB
6069 /* Now verify constructor circularity (stop after the first one
6070 we find) */
7f1d4866 6071 if (!is_interface)
22eed1e6
APB
6072 for (decl = TYPE_METHODS (class_type); decl; decl = TREE_CHAIN (decl))
6073 if (DECL_CONSTRUCTOR_P (decl) &&
6074 verify_constructor_circularity (decl, decl))
6075 break;
6076
e04a16fb
AG
6077 /* Make the class data, register it and run the rest of decl
6078 compilation on it */
63a212ed
PB
6079 if (!java_error_count)
6080 {
6081 if (flag_emit_class_files)
6082 write_classfile (current_class);
f099f336
APB
6083 if (flag_emit_xref)
6084 expand_xref (current_class);
aabd7048 6085 else if (! flag_syntax_only)
d593dd8c 6086 finish_class ();
63a212ed 6087 }
e04a16fb
AG
6088 }
6089}
6090
b9f7e36c
APB
6091/* Hold a list of catch clauses list. The first element of this list is
6092 the list of the catch clauses of the currently analysed try block. */
6093static tree currently_caught_type_list;
6094
e04a16fb
AG
6095/* Complete and expand a method. */
6096
6097static void
6098java_complete_expand_method (mdecl)
6099 tree mdecl;
6100{
22eed1e6
APB
6101 /* Fix constructors before expanding them */
6102 if (DECL_CONSTRUCTOR_P (mdecl))
6103 fix_constructors (mdecl);
e04a16fb 6104
22eed1e6 6105 /* Expand functions that have a body */
e04a16fb
AG
6106 if (DECL_FUNCTION_BODY (mdecl))
6107 {
9bbc7d9f
PB
6108 tree fbody = DECL_FUNCTION_BODY (mdecl);
6109 tree block_body = BLOCK_EXPR_BODY (fbody);
cd531a2e 6110 tree exception_copy = NULL_TREE;
e04a16fb 6111 expand_start_java_method (mdecl);
939d7216 6112 build_result_decl (mdecl);
e04a16fb
AG
6113
6114 current_this
6115 = (!METHOD_STATIC (mdecl) ?
6116 BLOCK_EXPR_DECLS (DECL_FUNCTION_BODY (mdecl)) : NULL_TREE);
6117
ce6e9147
APB
6118 /* Purge the `throws' list of unchecked exceptions. If we're
6119 doing xref, save a copy of the list and re-install it
6120 later. */
6121 if (flag_emit_xref)
6122 exception_copy = copy_list (DECL_FUNCTION_THROWS (mdecl));
6123
b9f7e36c
APB
6124 purge_unchecked_exceptions (mdecl);
6125
6126 /* Install exceptions thrown with `throws' */
6127 PUSH_EXCEPTIONS (DECL_FUNCTION_THROWS (mdecl));
6128
9bbc7d9f 6129 if (block_body != NULL_TREE)
bc3ca41b
PB
6130 {
6131 block_body = java_complete_tree (block_body);
ce6e9147
APB
6132 if (!flag_emit_xref)
6133 check_for_initialization (block_body);
f099f336 6134 ctxp->explicit_constructor_p = 0;
bc3ca41b 6135 }
9bbc7d9f 6136 BLOCK_EXPR_BODY (fbody) = block_body;
5e942c50 6137
9bbc7d9f 6138 if ((block_body == NULL_TREE || CAN_COMPLETE_NORMALLY (block_body))
ce6e9147
APB
6139 && TREE_CODE (TREE_TYPE (TREE_TYPE (mdecl))) != VOID_TYPE
6140 && !flag_emit_xref)
82371d41 6141 missing_return_error (current_function_decl);
7525cc04 6142
939d7216
PB
6143 complete_start_java_method (mdecl);
6144
e04a16fb
AG
6145 /* Don't go any further if we've found error(s) during the
6146 expansion */
6147 if (!java_error_count)
6148 source_end_java_method ();
22eed1e6
APB
6149 else
6150 {
6151 pushdecl_force_head (DECL_ARGUMENTS (mdecl));
6152 poplevel (1, 0, 1);
6153 }
b9f7e36c
APB
6154
6155 /* Pop the exceptions and sanity check */
6156 POP_EXCEPTIONS();
6157 if (currently_caught_type_list)
6158 fatal ("Exception list non empty - java_complete_expand_method");
ce6e9147
APB
6159
6160 if (flag_emit_xref)
6161 DECL_FUNCTION_THROWS (mdecl) = exception_copy;
e04a16fb
AG
6162 }
6163}
6164
22eed1e6
APB
6165/* Craft a body for default constructor. Patch existing constructor
6166 bodies with call to super() and field initialization statements if
6167 necessary. */
6168
6169static void
6170fix_constructors (mdecl)
6171 tree mdecl;
6172{
6173 tree body = DECL_FUNCTION_BODY (mdecl);
22eed1e6 6174
22eed1e6
APB
6175 if (!body)
6176 {
89e09b9a
PB
6177 /* The constructor body must be crafted by hand. It's the
6178 constructor we defined when we realize we didn't have the
6179 CLASSNAME() constructor */
6180
22eed1e6
APB
6181 tree compound;
6182
6183 /* It is an error for the compiler to generate a default
6184 constructor if the superclass doesn't have a constructor that
6185 takes no argument */
6186 if (verify_constructor_super ())
6187 {
6188 tree sclass_decl = TYPE_NAME (CLASSTYPE_SUPER (current_class));
49f48c71 6189 const char *n = IDENTIFIER_POINTER (DECL_NAME (sclass_decl));
22eed1e6
APB
6190 parse_error_context (lookup_cl (TYPE_NAME (current_class)),
6191 "No constructor matching `%s()' found in "
6192 "class `%s'", n, n);
6193 }
6194
6195 start_artificial_method_body (mdecl);
6196
6197 /* We don't generate a super constructor invocation if we're
6198 compiling java.lang.Object. build_super_invocation takes care
6199 of that. */
6200 compound = java_method_add_stmt (mdecl, build_super_invocation ());
22eed1e6
APB
6201
6202 end_artificial_method_body (mdecl);
6203 }
6204 /* Search for an explicit constructor invocation */
6205 else
6206 {
6207 int found = 0;
6208 tree main_block = BLOCK_EXPR_BODY (body);
6209 tree compound = NULL_TREE;
6210
6211 while (body)
6212 switch (TREE_CODE (body))
6213 {
6214 case CALL_EXPR:
6215 found = CALL_EXPLICIT_CONSTRUCTOR_P (body);
6216 body = NULL_TREE;
6217 break;
6218 case COMPOUND_EXPR:
6219 case EXPR_WITH_FILE_LOCATION:
6220 body = TREE_OPERAND (body, 0);
6221 break;
6222 case BLOCK:
6223 body = BLOCK_EXPR_BODY (body);
6224 break;
6225 default:
6226 found = 0;
6227 body = NULL_TREE;
6228 }
6229 /* The constructor is missing an invocation of super() */
6230 if (!found)
6231 compound = add_stmt_to_compound (compound, NULL_TREE,
6232 build_super_invocation ());
6233
22eed1e6
APB
6234 /* Fix the constructor main block if we're adding extra stmts */
6235 if (compound)
6236 {
6237 compound = add_stmt_to_compound (compound, NULL_TREE,
6238 BLOCK_EXPR_BODY (main_block));
6239 BLOCK_EXPR_BODY (main_block) = compound;
6240 }
6241 }
6242}
6243
6244/* Browse constructors in the super class, searching for a constructor
6245 that doesn't take any argument. Return 0 if one is found, 1
6246 otherwise. */
6247
6248static int
6249verify_constructor_super ()
6250{
6251 tree class = CLASSTYPE_SUPER (current_class);
6252 if (!class)
6253 return 0;
6254
6255 if (class)
6256 {
6257 tree mdecl;
6258 for (mdecl = TYPE_METHODS (class); mdecl; mdecl = TREE_CHAIN (mdecl))
6259 {
6260 if (DECL_CONSTRUCTOR_P (mdecl)
d77613be
APB
6261 && TREE_CHAIN (TYPE_ARG_TYPES (TREE_TYPE (mdecl)))
6262 == end_params_node)
22eed1e6
APB
6263 return 0;
6264 }
6265 }
6266 return 1;
6267}
6268
e04a16fb
AG
6269/* Expand finals. */
6270
49f48c71 6271static void
e04a16fb
AG
6272java_expand_finals ()
6273{
6274}
6275
22eed1e6 6276/* Generate code for all context remembered for code generation. */
b351b287
APB
6277
6278void
6279java_expand_classes ()
6280{
5423609c 6281 int save_error_count = 0;
23a79c61
APB
6282 java_parse_abort_on_error ();
6283 if (!(ctxp = ctxp_for_generation))
5e942c50
APB
6284 return;
6285 java_layout_classes ();
6286 java_parse_abort_on_error ();
6287
b351b287
APB
6288 for (; ctxp_for_generation; ctxp_for_generation = ctxp_for_generation->next)
6289 {
6290 ctxp = ctxp_for_generation;
6291 lang_init_source (2); /* Error msgs have method prototypes */
6292 java_complete_expand_methods (); /* Complete and expand method bodies */
6293 java_parse_abort_on_error ();
6294 java_expand_finals (); /* Expand and check the finals */
6295 java_parse_abort_on_error ();
6296 java_check_final (); /* Check unitialized final */
6297 java_parse_abort_on_error ();
6298 }
b351b287
APB
6299}
6300
e04a16fb
AG
6301/* Wrap non WFL PRIMARY around a WFL and set EXPR_WFL_QUALIFICATION to
6302 a tree list node containing RIGHT. Fore coming RIGHTs will be
6303 chained to this hook. LOCATION contains the location of the
6304 separating `.' operator. */
6305
6306static tree
6307make_qualified_primary (primary, right, location)
6308 tree primary, right;
6309 int location;
6310{
6311 tree wfl;
6312
6313 /* We want to process THIS . xxx symbolicaly, to keep it consistent
6314 with the way we're processing SUPER. A THIS from a primary as a
6315 different form than a SUPER. Turn THIS into something symbolic */
b67d701b 6316 if (TREE_CODE (primary) == THIS_EXPR)
e04a16fb 6317 {
9ee9b555 6318 wfl = build_wfl_node (this_identifier_node);
e04a16fb
AG
6319 EXPR_WFL_LINECOL (wfl) = EXPR_WFL_LINECOL (primary);
6320 wfl = make_qualified_name (wfl, right, location);
6321 PRIMARY_P (wfl) = 1;
6322 return wfl;
6323 }
6324 /* Other non WFL node are wrapped around a WFL */
6325 else if (TREE_CODE (primary) != EXPR_WITH_FILE_LOCATION)
6326 {
6327 wfl = build_expr_wfl (NULL_TREE, ctxp->filename, 0, 0);
6328 EXPR_WFL_LINECOL (wfl) = EXPR_WFL_LINECOL (primary);
6329 EXPR_WFL_QUALIFICATION (wfl) = build_tree_list (primary, NULL_TREE);
6330 }
6331 else
6332 {
6333 wfl = primary;
6334 if (!EXPR_WFL_QUALIFICATION (primary))
6335 EXPR_WFL_QUALIFICATION (primary) =
6336 build_tree_list (primary, NULL_TREE);
6337 }
6338
6339 EXPR_WFL_LINECOL (right) = location;
6340 chainon (EXPR_WFL_QUALIFICATION (wfl), build_tree_list (right, NULL_TREE));
6341 PRIMARY_P (wfl) = 1;
6342 return wfl;
6343}
6344
6345/* Simple merge of two name separated by a `.' */
6346
6347static tree
6348merge_qualified_name (left, right)
6349 tree left, right;
6350{
6351 tree node;
6352 obstack_grow (&temporary_obstack, IDENTIFIER_POINTER (left),
6353 IDENTIFIER_LENGTH (left));
6354 obstack_1grow (&temporary_obstack, '.');
6355 obstack_grow0 (&temporary_obstack, IDENTIFIER_POINTER (right),
6356 IDENTIFIER_LENGTH (right));
6357 node = get_identifier (obstack_base (&temporary_obstack));
6358 obstack_free (&temporary_obstack, obstack_base (&temporary_obstack));
6359 QUALIFIED_P (node) = 1;
6360 return node;
6361}
6362
6363/* Merge the two parts of a qualified name into LEFT. Set the
6364 location information of the resulting node to LOCATION, usually
6365 inherited from the location information of the `.' operator. */
6366
6367static tree
6368make_qualified_name (left, right, location)
6369 tree left, right;
6370 int location;
6371{
bc3ca41b
PB
6372#ifdef USE_COMPONENT_REF
6373 tree node = build (COMPONENT_REF, NULL_TREE, left, right);
6374 EXPR_WFL_LINECOL (node) = location;
6375 return node;
6376#else
e04a16fb
AG
6377 tree left_id = EXPR_WFL_NODE (left);
6378 tree right_id = EXPR_WFL_NODE (right);
6379 tree wfl, merge;
6380
6381 merge = merge_qualified_name (left_id, right_id);
6382
6383 /* Left wasn't qualified and is now qualified */
6384 if (!QUALIFIED_P (left_id))
6385 {
6386 tree wfl = build_expr_wfl (left_id, ctxp->filename, 0, 0);
6387 EXPR_WFL_LINECOL (wfl) = EXPR_WFL_LINECOL (left);
6388 EXPR_WFL_QUALIFICATION (left) = build_tree_list (wfl, NULL_TREE);
6389 }
6390
6391 wfl = build_expr_wfl (right_id, ctxp->filename, 0, 0);
6392 EXPR_WFL_LINECOL (wfl) = location;
6393 chainon (EXPR_WFL_QUALIFICATION (left), build_tree_list (wfl, NULL_TREE));
6394
6395 EXPR_WFL_NODE (left) = merge;
6396 return left;
bc3ca41b 6397#endif
e04a16fb
AG
6398}
6399
6400/* Extract the last identifier component of the qualified in WFL. The
6401 last identifier is removed from the linked list */
6402
6403static tree
6404cut_identifier_in_qualified (wfl)
6405 tree wfl;
6406{
6407 tree q;
6408 tree previous = NULL_TREE;
6409 for (q = EXPR_WFL_QUALIFICATION (wfl); ; previous = q, q = TREE_CHAIN (q))
6410 if (!TREE_CHAIN (q))
6411 {
6412 if (!previous)
6413 fatal ("Operating on a non qualified qualified WFL - "
6414 "cut_identifier_in_qualified");
6415 TREE_CHAIN (previous) = NULL_TREE;
6416 return TREE_PURPOSE (q);
6417 }
6418}
6419
6420/* Resolve the expression name NAME. Return its decl. */
6421
6422static tree
5e942c50 6423resolve_expression_name (id, orig)
e04a16fb 6424 tree id;
5e942c50 6425 tree *orig;
e04a16fb
AG
6426{
6427 tree name = EXPR_WFL_NODE (id);
6428 tree decl;
6429
6430 /* 6.5.5.1: Simple expression names */
6431 if (!PRIMARY_P (id) && !QUALIFIED_P (name))
6432 {
6433 /* 15.13.1: NAME can appear within the scope of a local variable
6434 declaration */
6435 if ((decl = IDENTIFIER_LOCAL_VALUE (name)))
6436 return decl;
6437
6438 /* 15.13.1: NAME can appear within a class declaration */
6439 else
6440 {
6441 decl = lookup_field_wrapper (current_class, name);
6442 if (decl)
6443 {
6444 int fs = FIELD_STATIC (decl);
6445 /* Instance variable (8.3.1.1) can't appear within
6446 static method, static initializer or initializer for
6447 a static variable. */
6448 if (!fs && METHOD_STATIC (current_function_decl))
6449 {
7f10c2e2 6450 static_ref_err (id, name, current_class);
e04a16fb
AG
6451 return error_mark_node;
6452 }
22eed1e6
APB
6453 /* Instance variables can't appear as an argument of
6454 an explicit constructor invocation */
6455 if (!fs && ctxp->explicit_constructor_p)
6456 {
6457 parse_error_context
6458 (id, "Can't reference `%s' before the superclass "
6459 "constructor has been called", IDENTIFIER_POINTER (name));
6460 return error_mark_node;
6461 }
5e942c50
APB
6462
6463 /* Otherwise build what it takes to access the field */
e04a16fb 6464 decl = build_field_ref ((fs ? NULL_TREE : current_this),
7f1d4866 6465 DECL_CONTEXT (decl), name);
e8fc7396 6466 if (fs && !flag_emit_class_files && !flag_emit_xref)
7f1d4866 6467 decl = build_class_init (DECL_CONTEXT (decl), decl);
5e942c50
APB
6468 /* We may be asked to save the real field access node */
6469 if (orig)
6470 *orig = decl;
6471 /* And we return what we got */
5b09b33e 6472 return decl;
e04a16fb
AG
6473 }
6474 /* Fall down to error report on undefined variable */
6475 }
6476 }
6477 /* 6.5.5.2 Qualified Expression Names */
6478 else
6479 {
5e942c50
APB
6480 if (orig)
6481 *orig = NULL_TREE;
e04a16fb
AG
6482 qualify_ambiguous_name (id);
6483 /* 15.10.1 Field Access Using a Primary and/or Expression Name */
6484 /* 15.10.2: Accessing Superclass Members using super */
6485 return resolve_field_access (id, NULL, NULL);
6486 }
6487
6488 /* We've got an error here */
6489 parse_error_context (id, "Undefined variable `%s'",
6490 IDENTIFIER_POINTER (name));
6491
6492 return error_mark_node;
6493}
6494
7f10c2e2
APB
6495static void
6496static_ref_err (wfl, field_id, class_type)
6497 tree wfl, field_id, class_type;
6498{
6499 parse_error_context
6500 (wfl,
6501 "Can't make a static reference to nonstatic variable `%s' in class `%s'",
6502 IDENTIFIER_POINTER (field_id),
6503 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (class_type))));
6504}
6505
e04a16fb
AG
6506/* 15.10.1 Field Acess Using a Primary and/or Expression Name.
6507 We return something suitable to generate the field access. We also
6508 return the field decl in FIELD_DECL and its type in FIELD_TYPE. If
6509 recipient's address can be null. */
6510
6511static tree
6512resolve_field_access (qual_wfl, field_decl, field_type)
6513 tree qual_wfl;
6514 tree *field_decl, *field_type;
6515{
6516 int is_static = 0;
6517 tree field_ref;
6518 tree decl, where_found, type_found;
6519
6520 if (resolve_qualified_expression_name (qual_wfl, &decl,
6521 &where_found, &type_found))
6522 return error_mark_node;
6523
6524 /* Resolve the LENGTH field of an array here */
6525 if (DECL_NAME (decl) == length_identifier_node && TYPE_ARRAY_P (type_found)
e8fc7396 6526 && ! flag_emit_class_files && ! flag_emit_xref)
e04a16fb
AG
6527 {
6528 tree length = build_java_array_length_access (where_found);
6529 field_ref =
6530 build_java_arraynull_check (type_found, length, int_type_node);
6531 }
6532 /* We might have been trying to resolve field.method(). In which
6533 case, the resolution is over and decl is the answer */
34f4db93 6534 else if (JDECL_P (decl) && IDENTIFIER_LOCAL_VALUE (DECL_NAME (decl)) == decl)
e04a16fb 6535 field_ref = decl;
34f4db93 6536 else if (JDECL_P (decl))
e04a16fb 6537 {
5e942c50
APB
6538 int static_final_found = 0;
6539 if (!type_found)
6540 type_found = DECL_CONTEXT (decl);
34f4db93 6541 is_static = JDECL_P (decl) && FIELD_STATIC (decl);
5e942c50
APB
6542 if (FIELD_FINAL (decl)
6543 && JPRIMITIVE_TYPE_P (TREE_TYPE (decl))
6544 && DECL_LANG_SPECIFIC (decl)
7525cc04 6545 && DECL_INITIAL (decl))
5e942c50 6546 {
7525cc04 6547 field_ref = DECL_INITIAL (decl);
5e942c50
APB
6548 static_final_found = 1;
6549 }
6550 else
7f10c2e2
APB
6551 field_ref = build_field_ref ((is_static && !flag_emit_xref?
6552 NULL_TREE : where_found),
5e942c50 6553 type_found, DECL_NAME (decl));
e04a16fb
AG
6554 if (field_ref == error_mark_node)
6555 return error_mark_node;
e8fc7396
APB
6556 if (is_static && !static_final_found
6557 && !flag_emit_class_files && !flag_emit_xref)
e04a16fb
AG
6558 {
6559 field_ref = build_class_init (type_found, field_ref);
6560 /* If the static field was identified by an expression that
6561 needs to be generated, make the field access a compound
7f10c2e2 6562 expression whose first part is the evaluation of the
e04a16fb 6563 field selector part. */
c877974e
APB
6564 if (where_found && TREE_CODE (where_found) != TYPE_DECL
6565 && TREE_CODE (where_found) != RECORD_TYPE)
e04a16fb
AG
6566 {
6567 tree type = QUAL_DECL_TYPE (field_ref);
8576f094
APB
6568 if (TREE_CODE (type) == RECORD_TYPE)
6569 type = build_pointer_type (type);
e04a16fb
AG
6570 field_ref = build (COMPOUND_EXPR, type, where_found, field_ref);
6571 }
6572 }
6573 }
6574 else
6575 field_ref = decl;
6576
6577 if (field_decl)
6578 *field_decl = decl;
6579 if (field_type)
c877974e
APB
6580 *field_type = (QUAL_DECL_TYPE (decl) ?
6581 QUAL_DECL_TYPE (decl) : TREE_TYPE (decl));
e04a16fb
AG
6582 return field_ref;
6583}
6584
e28cd97b
APB
6585/* If NODE is an access to f static field, strip out the class
6586 initialization part and return the field decl, otherwise, return
6587 NODE. */
6588
6589static tree
6590strip_out_static_field_access_decl (node)
6591 tree node;
6592{
6593 if (TREE_CODE (node) == COMPOUND_EXPR)
6594 {
6595 tree op1 = TREE_OPERAND (node, 1);
6596 if (TREE_CODE (op1) == COMPOUND_EXPR)
6597 {
6598 tree call = TREE_OPERAND (op1, 0);
6599 if (TREE_CODE (call) == CALL_EXPR
6600 && TREE_CODE (TREE_OPERAND (call, 0)) == ADDR_EXPR
6601 && TREE_OPERAND (TREE_OPERAND (call, 0), 0)
6602 == soft_initclass_node)
6603 return TREE_OPERAND (op1, 1);
6604 }
2f11d407
TT
6605 else if (JDECL_P (op1))
6606 return op1;
e28cd97b
APB
6607 }
6608 return node;
6609}
6610
e04a16fb
AG
6611/* 6.5.5.2: Qualified Expression Names */
6612
6613static int
6614resolve_qualified_expression_name (wfl, found_decl, where_found, type_found)
6615 tree wfl;
6616 tree *found_decl, *type_found, *where_found;
6617{
6618 int from_type = 0; /* Field search initiated from a type */
6619 int from_super = 0, from_cast = 0;
6620 int previous_call_static = 0;
6621 int is_static;
6622 tree decl = NULL_TREE, type = NULL_TREE, q;
c877974e 6623 *type_found = *where_found = NULL_TREE;
e04a16fb
AG
6624
6625 for (q = EXPR_WFL_QUALIFICATION (wfl); q; q = TREE_CHAIN (q))
6626 {
6627 tree qual_wfl = QUAL_WFL (q);
7705e9db
APB
6628 tree ret_decl; /* for EH checking */
6629 int location; /* for EH checking */
e04a16fb
AG
6630
6631 /* 15.10.1 Field Access Using a Primary */
e04a16fb
AG
6632 switch (TREE_CODE (qual_wfl))
6633 {
6634 case CALL_EXPR:
b67d701b 6635 case NEW_CLASS_EXPR:
e04a16fb
AG
6636 /* If the access to the function call is a non static field,
6637 build the code to access it. */
34f4db93 6638 if (JDECL_P (decl) && !FIELD_STATIC (decl))
e04a16fb 6639 {
ac825856
APB
6640 decl = maybe_access_field (decl, *where_found,
6641 DECL_CONTEXT (decl));
e04a16fb
AG
6642 if (decl == error_mark_node)
6643 return 1;
6644 }
6645 /* And code for the function call */
6646 if (complete_function_arguments (qual_wfl))
6647 return 1;
7705e9db 6648
89e09b9a
PB
6649 if (from_super && TREE_CODE (qual_wfl) == CALL_EXPR)
6650 CALL_USING_SUPER (qual_wfl) = 1;
7705e9db
APB
6651 location = (TREE_CODE (qual_wfl) == CALL_EXPR ?
6652 EXPR_WFL_LINECOL (TREE_OPERAND (qual_wfl, 0)) : 0);
6653 *where_found = patch_method_invocation (qual_wfl, decl, type,
6654 &is_static, &ret_decl);
e04a16fb
AG
6655 if (*where_found == error_mark_node)
6656 return 1;
6657 *type_found = type = QUAL_DECL_TYPE (*where_found);
6658
7705e9db
APB
6659 /* EH check */
6660 if (location)
6661 check_thrown_exceptions (location, ret_decl);
6662
e04a16fb
AG
6663 /* If the previous call was static and this one is too,
6664 build a compound expression to hold the two (because in
6665 that case, previous function calls aren't transported as
6666 forcoming function's argument. */
6667 if (previous_call_static && is_static)
6668 {
6669 decl = build (COMPOUND_EXPR, type, decl, *where_found);
6670 TREE_SIDE_EFFECTS (decl) = 1;
6671 }
6672 else
6673 {
6674 previous_call_static = is_static;
6675 decl = *where_found;
6676 }
6677 continue;
6678
d8fccff5
APB
6679 case NEW_ARRAY_EXPR:
6680 *where_found = decl = java_complete_tree (qual_wfl);
6681 if (decl == error_mark_node)
6682 return 1;
6683 *type_found = type = QUAL_DECL_TYPE (decl);
6684 CLASS_LOADED_P (type) = 1;
6685 continue;
6686
e04a16fb
AG
6687 case CONVERT_EXPR:
6688 *where_found = decl = java_complete_tree (qual_wfl);
6689 if (decl == error_mark_node)
6690 return 1;
6691 *type_found = type = QUAL_DECL_TYPE (decl);
6692 from_cast = 1;
6693 continue;
6694
22eed1e6 6695 case CONDITIONAL_EXPR:
5e942c50 6696 case STRING_CST:
ac22f9cb 6697 case MODIFY_EXPR:
22eed1e6
APB
6698 *where_found = decl = java_complete_tree (qual_wfl);
6699 if (decl == error_mark_node)
6700 return 1;
6701 *type_found = type = QUAL_DECL_TYPE (decl);
6702 continue;
6703
e04a16fb
AG
6704 case ARRAY_REF:
6705 /* If the access to the function call is a non static field,
6706 build the code to access it. */
34f4db93 6707 if (JDECL_P (decl) && !FIELD_STATIC (decl))
e04a16fb
AG
6708 {
6709 decl = maybe_access_field (decl, *where_found, type);
6710 if (decl == error_mark_node)
6711 return 1;
6712 }
6713 /* And code for the array reference expression */
6714 decl = java_complete_tree (qual_wfl);
6715 if (decl == error_mark_node)
6716 return 1;
6717 type = QUAL_DECL_TYPE (decl);
6718 continue;
0a2138e2 6719
37feda7d
APB
6720 case PLUS_EXPR:
6721 if ((decl = java_complete_tree (qual_wfl)) == error_mark_node)
6722 return 1;
6723 if ((type = patch_string (decl)))
6724 decl = type;
6725 *where_found = QUAL_RESOLUTION (q) = decl;
6726 *type_found = type = TREE_TYPE (decl);
6727 break;
6728
0a2138e2
APB
6729 default:
6730 /* Fix for -Wall Just go to the next statement. Don't
6731 continue */
a3f406ce 6732 break;
e04a16fb
AG
6733 }
6734
6735 /* If we fall here, we weren't processing a (static) function call. */
6736 previous_call_static = 0;
6737
6738 /* It can be the keyword THIS */
6739 if (EXPR_WFL_NODE (qual_wfl) == this_identifier_node)
6740 {
6741 if (!current_this)
6742 {
6743 parse_error_context
6744 (wfl, "Keyword `this' used outside allowed context");
6745 return 1;
6746 }
f63991a8
APB
6747 if (ctxp->explicit_constructor_p)
6748 {
6749 parse_error_context (wfl, "Can't reference `this' before the "
6750 "superclass constructor has been called");
6751 return 1;
6752 }
e04a16fb
AG
6753 /* We have to generate code for intermediate acess */
6754 *where_found = decl = current_this;
5e942c50 6755 *type_found = type = QUAL_DECL_TYPE (decl);
e04a16fb
AG
6756 continue;
6757 }
6758
6759 /* 15.10.2 Accessing Superclass Members using SUPER */
6760 if (EXPR_WFL_NODE (qual_wfl) == super_identifier_node)
6761 {
6762 tree node;
6763 /* Check on the restricted use of SUPER */
6764 if (METHOD_STATIC (current_function_decl)
6765 || current_class == object_type_node)
6766 {
6767 parse_error_context
6768 (wfl, "Keyword `super' used outside allowed context");
6769 return 1;
6770 }
6771 /* Otherwise, treat SUPER as (SUPER_CLASS)THIS */
6772 node = build_cast (EXPR_WFL_LINECOL (qual_wfl),
6773 CLASSTYPE_SUPER (current_class),
6774 build_this (EXPR_WFL_LINECOL (qual_wfl)));
6775 *where_found = decl = java_complete_tree (node);
22eed1e6
APB
6776 if (decl == error_mark_node)
6777 return 1;
e04a16fb
AG
6778 *type_found = type = QUAL_DECL_TYPE (decl);
6779 from_super = from_type = 1;
6780 continue;
6781 }
6782
6783 /* 15.13.1: Can't search for field name in packages, so we
6784 assume a variable/class name was meant. */
6785 if (RESOLVE_PACKAGE_NAME_P (qual_wfl))
6786 {
5e942c50
APB
6787 tree name = resolve_package (wfl, &q);
6788 if (name)
6789 {
6790 *where_found = decl = resolve_no_layout (name, qual_wfl);
6791 /* We wan't to be absolutely that the class is laid
6792 out. We're going to search something inside it. */
6793 *type_found = type = TREE_TYPE (decl);
6794 layout_class (type);
6795 from_type = 1;
6796 /* Should be a list, really. FIXME */
6797 RESOLVE_EXPRESSION_NAME_P (QUAL_WFL (TREE_CHAIN (q))) = 1;
6798 RESOLVE_PACKAGE_NAME_P (QUAL_WFL (TREE_CHAIN (q))) = 0;
6799 }
e04a16fb 6800 else
5e942c50
APB
6801 {
6802 if (from_super || from_cast)
6803 parse_error_context
6804 ((from_cast ? qual_wfl : wfl),
6805 "No variable `%s' defined in class `%s'",
6806 IDENTIFIER_POINTER (EXPR_WFL_NODE (qual_wfl)),
6807 lang_printable_name (type, 0));
6808 else
6809 parse_error_context
6810 (qual_wfl, "Undefined variable or class name: `%s'",
6811 IDENTIFIER_POINTER (EXPR_WFL_NODE (qual_wfl)));
6812 return 1;
6813 }
e04a16fb
AG
6814 }
6815
6816 /* We have a type name. It's been already resolved when the
6817 expression was qualified. */
6818 else if (RESOLVE_TYPE_NAME_P (qual_wfl))
6819 {
6820 if (!(decl = QUAL_RESOLUTION (q)))
6821 return 1; /* Error reported already */
6822
6823 if (not_accessible_p (TREE_TYPE (decl), decl, 0))
6824 {
6825 parse_error_context
6826 (qual_wfl, "Can't access %s field `%s.%s' from `%s'",
6827 java_accstring_lookup (get_access_flags_from_decl (decl)),
2aa11e97 6828 GET_TYPE_NAME (type),
e04a16fb
AG
6829 IDENTIFIER_POINTER (DECL_NAME (decl)),
6830 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (current_class))));
6831 return 1;
6832 }
5e942c50 6833 check_deprecation (qual_wfl, decl);
e04a16fb
AG
6834
6835 type = TREE_TYPE (decl);
6836 from_type = 1;
6837 }
6838 /* We resolve and expression name */
6839 else
6840 {
cd531a2e 6841 tree field_decl = NULL_TREE;
e04a16fb
AG
6842
6843 /* If there exists an early resolution, use it. That occurs
6844 only once and we know that there are more things to
6845 come. Don't do that when processing something after SUPER
6846 (we need more thing to be put in place below */
6847 if (!from_super && QUAL_RESOLUTION (q))
b67d701b
PB
6848 {
6849 decl = QUAL_RESOLUTION (q);
c877974e 6850 if (!type)
5e942c50 6851 {
7f10c2e2
APB
6852 if (TREE_CODE (decl) == FIELD_DECL && !FIELD_STATIC (decl))
6853 {
6854 if (current_this)
6855 *where_found = current_this;
6856 else
6857 {
6858 static_ref_err (qual_wfl, DECL_NAME (decl),
6859 current_class);
6860 return 1;
6861 }
6862 }
c877974e
APB
6863 else
6864 {
6865 *where_found = TREE_TYPE (decl);
6866 if (TREE_CODE (*where_found) == POINTER_TYPE)
6867 *where_found = TREE_TYPE (*where_found);
6868 }
5e942c50 6869 }
b67d701b 6870 }
e04a16fb
AG
6871
6872 /* We have to search for a field, knowing the type of its
6873 container. The flag FROM_TYPE indicates that we resolved
6874 the last member of the expression as a type name, which
5e942c50
APB
6875 means that for the resolution of this field, we'll look
6876 for other errors than if it was resolved as a member of
6877 an other field. */
e04a16fb
AG
6878 else
6879 {
6880 int is_static;
5e942c50
APB
6881 tree field_decl_type; /* For layout */
6882
e04a16fb
AG
6883 if (!from_type && !JREFERENCE_TYPE_P (type))
6884 {
6885 parse_error_context
6886 (qual_wfl, "Attempt to reference field `%s' in `%s %s'",
6887 IDENTIFIER_POINTER (EXPR_WFL_NODE (qual_wfl)),
0a2138e2 6888 lang_printable_name (type, 0),
e04a16fb
AG
6889 IDENTIFIER_POINTER (DECL_NAME (field_decl)));
6890 return 1;
6891 }
6892
dc0b3eff
PB
6893 field_decl = lookup_field_wrapper (type,
6894 EXPR_WFL_NODE (qual_wfl));
6895 if (field_decl == NULL_TREE)
e04a16fb
AG
6896 {
6897 parse_error_context
2aa11e97 6898 (qual_wfl, "No variable `%s' defined in type `%s'",
e04a16fb 6899 IDENTIFIER_POINTER (EXPR_WFL_NODE (qual_wfl)),
2aa11e97 6900 GET_TYPE_NAME (type));
e04a16fb
AG
6901 return 1;
6902 }
dc0b3eff
PB
6903 if (field_decl == error_mark_node)
6904 return 1;
5e942c50
APB
6905
6906 /* Layout the type of field_decl, since we may need
c877974e
APB
6907 it. Don't do primitive types or loaded classes. The
6908 situation of non primitive arrays may not handled
6909 properly here. FIXME */
5e942c50
APB
6910 if (TREE_CODE (TREE_TYPE (field_decl)) == POINTER_TYPE)
6911 field_decl_type = TREE_TYPE (TREE_TYPE (field_decl));
6912 else
6913 field_decl_type = TREE_TYPE (field_decl);
6914 if (!JPRIMITIVE_TYPE_P (field_decl_type)
c877974e
APB
6915 && !CLASS_LOADED_P (field_decl_type)
6916 && !TYPE_ARRAY_P (field_decl_type))
6917 resolve_and_layout (field_decl_type, NULL_TREE);
6918 if (TYPE_ARRAY_P (field_decl_type))
6919 CLASS_LOADED_P (field_decl_type) = 1;
e04a16fb
AG
6920
6921 /* Check on accessibility here */
6922 if (not_accessible_p (type, field_decl, from_super))
6923 {
6924 parse_error_context
6925 (qual_wfl,
6926 "Can't access %s field `%s.%s' from `%s'",
6927 java_accstring_lookup
6928 (get_access_flags_from_decl (field_decl)),
2aa11e97 6929 GET_TYPE_NAME (type),
e04a16fb
AG
6930 IDENTIFIER_POINTER (DECL_NAME (field_decl)),
6931 IDENTIFIER_POINTER
6932 (DECL_NAME (TYPE_NAME (current_class))));
6933 return 1;
6934 }
5e942c50 6935 check_deprecation (qual_wfl, field_decl);
e04a16fb
AG
6936
6937 /* There are things to check when fields are accessed
6938 from type. There are no restrictions on a static
6939 declaration of the field when it is accessed from an
6940 interface */
6941 is_static = FIELD_STATIC (field_decl);
6942 if (!from_super && from_type
6943 && !TYPE_INTERFACE_P (type) && !is_static)
6944 {
7f10c2e2 6945 static_ref_err (qual_wfl, EXPR_WFL_NODE (qual_wfl), type);
e04a16fb
AG
6946 return 1;
6947 }
6948 from_cast = from_super = 0;
6949
5e942c50
APB
6950 /* If we need to generate something to get a proper
6951 handle on what this field is accessed from, do it
6952 now. */
e04a16fb
AG
6953 if (!is_static)
6954 {
c583dd46 6955 decl = maybe_access_field (decl, *where_found, *type_found);
e04a16fb
AG
6956 if (decl == error_mark_node)
6957 return 1;
6958 }
6959
6960 /* We want to keep the location were found it, and the type
6961 we found. */
6962 *where_found = decl;
6963 *type_found = type;
6964
6965 /* This is the decl found and eventually the next one to
6966 search from */
6967 decl = field_decl;
6968 }
e04a16fb
AG
6969 from_type = 0;
6970 type = QUAL_DECL_TYPE (decl);
6971 }
6972 }
6973 *found_decl = decl;
6974 return 0;
6975}
6976
6977/* 6.6 Qualified name and access control. Returns 1 if MEMBER (a decl)
6978 can't be accessed from REFERENCE (a record type). */
6979
be245ac0
KG
6980static int
6981not_accessible_p (reference, member, from_super)
e04a16fb
AG
6982 tree reference, member;
6983 int from_super;
6984{
6985 int access_flag = get_access_flags_from_decl (member);
6986
6987 /* Access always granted for members declared public */
6988 if (access_flag & ACC_PUBLIC)
6989 return 0;
6990
6991 /* Check access on protected members */
6992 if (access_flag & ACC_PROTECTED)
6993 {
6994 /* Access granted if it occurs from within the package
6995 containing the class in which the protected member is
6996 declared */
6997 if (class_in_current_package (DECL_CONTEXT (member)))
6998 return 0;
6999
9bbc7d9f
PB
7000 /* If accessed with the form `super.member', then access is granted */
7001 if (from_super)
7002 return 0;
e04a16fb 7003
9bbc7d9f
PB
7004 /* Otherwise, access is granted if occuring from the class where
7005 member is declared or a subclass of it */
7006 if (inherits_from_p (reference, current_class))
7007 return 0;
e04a16fb
AG
7008 return 1;
7009 }
7010
7011 /* Check access on private members. Access is granted only if it
c877974e 7012 occurs from within the class in witch it is declared */
e04a16fb
AG
7013 if (access_flag & ACC_PRIVATE)
7014 return (current_class == DECL_CONTEXT (member) ? 0 : 1);
7015
7016 /* Default access are permitted only when occuring within the
7017 package in which the type (REFERENCE) is declared. In other words,
7018 REFERENCE is defined in the current package */
7019 if (ctxp->package)
7020 return !class_in_current_package (reference);
7021
7022 /* Otherwise, access is granted */
7023 return 0;
7024}
7025
5e942c50
APB
7026/* Test deprecated decl access. */
7027static void
7028check_deprecation (wfl, decl)
7029 tree wfl, decl;
7030{
49f48c71 7031 const char *file = DECL_SOURCE_FILE (decl);
5e942c50
APB
7032 /* Complain if the field is deprecated and the file it was defined
7033 in isn't compiled at the same time the file which contains its
7034 use is */
7035 if (DECL_DEPRECATED (decl)
7036 && !IS_A_COMMAND_LINE_FILENAME_P (get_identifier (file)))
7037 {
7038 char the [20];
7039 switch (TREE_CODE (decl))
7040 {
7041 case FUNCTION_DECL:
7042 strcpy (the, "method");
7043 break;
7044 case FIELD_DECL:
7045 strcpy (the, "field");
7046 break;
7047 case TYPE_DECL:
7048 strcpy (the, "class");
7049 break;
15fdcfe9
PB
7050 default:
7051 fatal ("unexpected DECL code - check_deprecation");
5e942c50
APB
7052 }
7053 parse_warning_context
7054 (wfl, "The %s `%s' in class `%s' has been deprecated",
7055 the, lang_printable_name (decl, 0),
7056 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (DECL_CONTEXT (decl)))));
7057 }
7058}
7059
e04a16fb
AG
7060/* Returns 1 if class was declared in the current package, 0 otherwise */
7061
7062static int
7063class_in_current_package (class)
7064 tree class;
7065{
7066 static tree cache = NULL_TREE;
7067 int qualified_flag;
7068 tree left;
7069
7070 if (cache == class)
7071 return 1;
7072
7073 qualified_flag = QUALIFIED_P (DECL_NAME (TYPE_NAME (class)));
7074
7075 /* If the current package is empty and the name of CLASS is
7076 qualified, class isn't in the current package. If there is a
7077 current package and the name of the CLASS is not qualified, class
7078 isn't in the current package */
0a2138e2 7079 if ((!ctxp->package && qualified_flag) || (ctxp->package && !qualified_flag))
e04a16fb
AG
7080 return 0;
7081
7082 /* If there is not package and the name of CLASS isn't qualified,
7083 they belong to the same unnamed package */
7084 if (!ctxp->package && !qualified_flag)
7085 return 1;
7086
7087 /* Compare the left part of the name of CLASS with the package name */
7088 breakdown_qualified (&left, NULL, DECL_NAME (TYPE_NAME (class)));
7089 if (ctxp->package == left)
7090 {
7091 cache = class;
7092 return 1;
7093 }
7094 return 0;
7095}
7096
7097/* This function may generate code to access DECL from WHERE. This is
7098 done only if certain conditions meet. */
7099
7100static tree
7101maybe_access_field (decl, where, type)
7102 tree decl, where, type;
7103{
5e942c50
APB
7104 if (TREE_CODE (decl) == FIELD_DECL && decl != current_this
7105 && !FIELD_STATIC (decl))
e04a16fb 7106 decl = build_field_ref (where ? where : current_this,
c583dd46
APB
7107 (type ? type : DECL_CONTEXT (decl)),
7108 DECL_NAME (decl));
e04a16fb
AG
7109 return decl;
7110}
7111
15fdcfe9 7112/* Build a method invocation, by patching PATCH. If non NULL
e04a16fb
AG
7113 and according to the situation, PRIMARY and WHERE may be
7114 used. IS_STATIC is set to 1 if the invoked function is static. */
7115
7116static tree
89e09b9a 7117patch_method_invocation (patch, primary, where, is_static, ret_decl)
e04a16fb
AG
7118 tree patch, primary, where;
7119 int *is_static;
b9f7e36c 7120 tree *ret_decl;
e04a16fb
AG
7121{
7122 tree wfl = TREE_OPERAND (patch, 0);
7123 tree args = TREE_OPERAND (patch, 1);
7124 tree name = EXPR_WFL_NODE (wfl);
5e942c50 7125 tree list;
22eed1e6 7126 int is_static_flag = 0;
89e09b9a 7127 int is_super_init = 0;
bccaf73a 7128 tree this_arg = NULL_TREE;
e04a16fb
AG
7129
7130 /* Should be overriden if everything goes well. Otherwise, if
7131 something fails, it should keep this value. It stop the
7132 evaluation of a bogus assignment. See java_complete_tree,
7133 MODIFY_EXPR: for the reasons why we sometimes want to keep on
7134 evaluating an assignment */
7135 TREE_TYPE (patch) = error_mark_node;
7136
7137 /* Since lookup functions are messing with line numbers, save the
7138 context now. */
7139 java_parser_context_save_global ();
7140
7141 /* 15.11.1: Compile-Time Step 1: Determine Class or Interface to Search */
7142
7143 /* Resolution of qualified name, excluding constructors */
7144 if (QUALIFIED_P (name) && !CALL_CONSTRUCTOR_P (patch))
7145 {
7146 tree class_decl, identifier, identifier_wfl;
7147 /* Extract the last IDENTIFIER of the qualified
7148 expression. This is a wfl and we will use it's location
7149 data during error report. */
7150 identifier_wfl = cut_identifier_in_qualified (wfl);
7151 identifier = EXPR_WFL_NODE (identifier_wfl);
7152
7153 /* Given the context, IDENTIFIER is syntactically qualified
7154 as a MethodName. We need to qualify what's before */
7155 qualify_ambiguous_name (wfl);
7156
2c56429a 7157 /* Package resolution */
e04a16fb
AG
7158 if (RESOLVE_PACKAGE_NAME_P (wfl))
7159 {
2c56429a
APB
7160 tree next, decl, name = resolve_package (wfl, &next);
7161
7162 if (!name)
7163 {
7164 tree remainder;
7165 breakdown_qualified (&remainder, NULL, EXPR_WFL_NODE (wfl));
7166 parse_error_context (wfl, "Can't search method `%s' in package "
7167 "`%s'",IDENTIFIER_POINTER (identifier),
7168 IDENTIFIER_POINTER (remainder));
7169 PATCH_METHOD_RETURN_ERROR ();
7170 }
7171 RESOLVE_PACKAGE_NAME_P (wfl) = 0;
7172 if ((decl = resolve_no_layout (name, QUAL_WFL (next))))
7173 {
7174 QUAL_RESOLUTION (EXPR_WFL_QUALIFICATION (wfl)) = decl;
7175 RESOLVE_EXPRESSION_NAME_P (wfl) = 0;
7176 RESOLVE_TYPE_NAME_P (wfl) = 1;
7177 }
7178 else
7179 {
7180 RESOLVE_EXPRESSION_NAME_P (wfl) = 1;
7181 RESOLVE_TYPE_NAME_P (wfl) = 0;
7182 }
e04a16fb 7183 }
2c56429a 7184
e04a16fb 7185 /* We're resolving a call from a type */
2c56429a 7186 if (RESOLVE_TYPE_NAME_P (wfl))
e04a16fb
AG
7187 {
7188 tree decl = QUAL_RESOLUTION (EXPR_WFL_QUALIFICATION (wfl));
7189 tree name = DECL_NAME (decl);
7190 tree type;
7191
7192 class_decl = resolve_and_layout (name, wfl);
7193 if (CLASS_INTERFACE (decl))
7194 {
7195 parse_error_context
7196 (identifier_wfl, "Can't make static reference to method "
7197 "`%s' in interface `%s'", IDENTIFIER_POINTER (identifier),
7198 IDENTIFIER_POINTER (name));
b9f7e36c 7199 PATCH_METHOD_RETURN_ERROR ();
e04a16fb
AG
7200 }
7201 /* Look the method up in the type selector. The method ought
7202 to be static. */
7203 type = TREE_TYPE (class_decl);
7204 list = lookup_method_invoke (0, wfl, type, identifier, args);
7205 if (list && !METHOD_STATIC (list))
7206 {
c2e3db92 7207 char *fct_name = xstrdup (lang_printable_name (list, 0));
e04a16fb
AG
7208 parse_error_context
7209 (identifier_wfl,
7210 "Can't make static reference to method `%s %s' in class `%s'",
0a2138e2
APB
7211 lang_printable_name (TREE_TYPE (TREE_TYPE (list)), 0),
7212 fct_name, IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (type))));
e04a16fb 7213 free (fct_name);
b9f7e36c 7214 PATCH_METHOD_RETURN_ERROR ();
e04a16fb 7215 }
5e942c50 7216 args = nreverse (args);
e04a16fb
AG
7217 }
7218 /* We're resolving an expression name */
7219 else
7220 {
7221 tree field, type;
7222
7223 /* 1- Find the field to which the call applies */
7224 field = resolve_field_access (wfl, NULL, &type);
7225 if (field == error_mark_node)
b9f7e36c 7226 PATCH_METHOD_RETURN_ERROR ();
c3f2a476
APB
7227 /* field is used in lieu of a primary. It alows us not to
7228 report errors on erroneous use of `this' in
7229 constructors. */
7230 primary = field;
e04a16fb
AG
7231
7232 /* 2- Do the layout of the class where the last field
7233 was found, so we can search it. */
c877974e 7234 class_decl = resolve_and_layout (type, NULL_TREE);
3e78f871 7235 if (class_decl != NULL_TREE)
c877974e
APB
7236 type = TREE_TYPE (class_decl);
7237
e04a16fb
AG
7238 /* 3- Retrieve a filtered list of method matches, Refine
7239 if necessary. In any cases, point out errors. */
7240 list = lookup_method_invoke (0, identifier_wfl, type,
7241 identifier, args);
7242
7243 /* 4- Add the field as an argument */
bccaf73a
PB
7244 args = nreverse (args);
7245 this_arg = field;
e04a16fb
AG
7246 }
7247
5e942c50 7248 /* IDENTIFIER_WFL will be used to report any problem further */
e04a16fb
AG
7249 wfl = identifier_wfl;
7250 }
7251 /* Resolution of simple names, names generated after a primary: or
7252 constructors */
7253 else
7254 {
cd531a2e 7255 tree class_to_search = NULL_TREE;
e04a16fb
AG
7256 int lc; /* Looking for Constructor */
7257
7258 /* We search constructor in their target class */
7259 if (CALL_CONSTRUCTOR_P (patch))
7260 {
22eed1e6
APB
7261 if (TREE_CODE (patch) == NEW_CLASS_EXPR)
7262 class_to_search = EXPR_WFL_NODE (wfl);
7263 else if (EXPR_WFL_NODE (TREE_OPERAND (patch, 0)) ==
7264 this_identifier_node)
7265 class_to_search = NULL_TREE;
7266 else if (EXPR_WFL_NODE (TREE_OPERAND (patch, 0)) ==
7267 super_identifier_node)
e04a16fb 7268 {
89e09b9a 7269 is_super_init = 1;
22eed1e6
APB
7270 if (CLASSTYPE_SUPER (current_class))
7271 class_to_search =
7272 DECL_NAME (TYPE_NAME (CLASSTYPE_SUPER (current_class)));
7273 else
7274 {
7275 parse_error_context (wfl, "Can't invoke super constructor "
7276 "on java.lang.Object");
7277 PATCH_METHOD_RETURN_ERROR ();
7278 }
e04a16fb 7279 }
22eed1e6
APB
7280
7281 /* Class to search is NULL if we're searching the current one */
7282 if (class_to_search)
e04a16fb 7283 {
23a79c61
APB
7284 class_to_search = resolve_and_layout (class_to_search,
7285 NULL_TREE);
22eed1e6
APB
7286 if (!class_to_search)
7287 {
7288 parse_error_context
7289 (wfl, "Class `%s' not found in type declaration",
7290 IDENTIFIER_POINTER (EXPR_WFL_NODE (wfl)));
7291 PATCH_METHOD_RETURN_ERROR ();
7292 }
7293
5e942c50
APB
7294 /* Can't instantiate an abstract class, but we can
7295 invoke it's constructor. It's use within the `new'
7296 context is denied here. */
7297 if (CLASS_ABSTRACT (class_to_search)
7298 && TREE_CODE (patch) == NEW_CLASS_EXPR)
22eed1e6
APB
7299 {
7300 parse_error_context
7301 (wfl, "Class `%s' is an abstract class. It can't be "
7302 "instantiated", IDENTIFIER_POINTER (EXPR_WFL_NODE (wfl)));
7303 PATCH_METHOD_RETURN_ERROR ();
7304 }
7305 class_to_search = TREE_TYPE (class_to_search);
e04a16fb 7306 }
22eed1e6
APB
7307 else
7308 class_to_search = current_class;
e04a16fb
AG
7309 lc = 1;
7310 }
7311 /* This is a regular search in the local class, unless an
7312 alternate class is specified. */
7313 else
7314 {
7315 class_to_search = (where ? where : current_class);
7316 lc = 0;
7317 }
7318
7319 /* NAME is a simple identifier or comes from a primary. Search
7320 in the class whose declaration contain the method being
7321 invoked. */
c877974e 7322 resolve_and_layout (class_to_search, NULL_TREE);
e04a16fb
AG
7323 list = lookup_method_invoke (lc, wfl, class_to_search, name, args);
7324
7325 /* Don't continue if no method were found, as the next statement
7326 can't be executed then. */
b9f7e36c
APB
7327 if (!list)
7328 PATCH_METHOD_RETURN_ERROR ();
e04a16fb
AG
7329
7330 /* Check for static reference if non static methods */
7331 if (check_for_static_method_reference (wfl, patch, list,
7332 class_to_search, primary))
b9f7e36c 7333 PATCH_METHOD_RETURN_ERROR ();
e04a16fb 7334
22eed1e6
APB
7335 /* Non static methods are called with the current object extra
7336 argument. If patch a `new TYPE()', the argument is the value
7337 returned by the object allocator. If method is resolved as a
7338 primary, use the primary otherwise use the current THIS. */
b9f7e36c 7339 args = nreverse (args);
bccaf73a
PB
7340 if (TREE_CODE (patch) != NEW_CLASS_EXPR)
7341 this_arg = primary ? primary : current_this;
e04a16fb 7342 }
b67d701b 7343
e04a16fb
AG
7344 /* Merge point of all resolution schemes. If we have nothing, this
7345 is an error, already signaled */
b9f7e36c
APB
7346 if (!list)
7347 PATCH_METHOD_RETURN_ERROR ();
b67d701b 7348
e04a16fb
AG
7349 /* Check accessibility, position the is_static flag, build and
7350 return the call */
9bbc7d9f 7351 if (not_accessible_p (DECL_CONTEXT (current_function_decl), list, 0))
e04a16fb 7352 {
c2e3db92 7353 char *fct_name = xstrdup (lang_printable_name (list, 0));
e04a16fb
AG
7354 parse_error_context
7355 (wfl, "Can't access %s method `%s %s.%s' from `%s'",
7356 java_accstring_lookup (get_access_flags_from_decl (list)),
0a2138e2 7357 lang_printable_name (TREE_TYPE (TREE_TYPE (list)), 0),
5e942c50
APB
7358 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (DECL_CONTEXT (list)))),
7359 fct_name, IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (current_class))));
e04a16fb 7360 free (fct_name);
b9f7e36c 7361 PATCH_METHOD_RETURN_ERROR ();
e04a16fb 7362 }
5e942c50 7363 check_deprecation (wfl, list);
22eed1e6
APB
7364
7365 is_static_flag = METHOD_STATIC (list);
bccaf73a
PB
7366 if (! METHOD_STATIC (list) && this_arg != NULL_TREE)
7367 args = tree_cons (NULL_TREE, this_arg, args);
22eed1e6 7368
c3f2a476
APB
7369 /* In the context of an explicit constructor invocation, we can't
7370 invoke any method relying on `this'. Exceptions are: we're
7371 invoking a static function, primary exists and is not the current
7372 this, we're creating a new object. */
22eed1e6 7373 if (ctxp->explicit_constructor_p
c3f2a476
APB
7374 && !is_static_flag
7375 && (!primary || primary == current_this)
7376 && (TREE_CODE (patch) != NEW_CLASS_EXPR))
22eed1e6
APB
7377 {
7378 parse_error_context
7379 (wfl, "Can't reference `this' before the superclass constructor has "
7380 "been called");
7381 PATCH_METHOD_RETURN_ERROR ();
7382 }
e04a16fb 7383 java_parser_context_restore_global ();
22eed1e6
APB
7384 if (is_static)
7385 *is_static = is_static_flag;
b9f7e36c
APB
7386 /* Sometimes, we want the decl of the selected method. Such as for
7387 EH checking */
7388 if (ret_decl)
7389 *ret_decl = list;
89e09b9a
PB
7390 patch = patch_invoke (patch, list, args);
7391 if (is_super_init && CLASS_HAS_FINIT_P (current_class))
7392 {
7393 /* Generate the code used to initialize fields declared with an
7394 initialization statement. For now, it returns a call the the
7395 artificial function $finit$, if required. */
7396
7397 tree finit_call =
7398 build_method_invocation (build_expr_wfl (finit_identifier_node,
7399 input_filename, 0, 0),
7400 NULL_TREE);
7401 patch = build (COMPOUND_EXPR, void_type_node, patch,
7402 java_complete_tree (finit_call));
7403 CAN_COMPLETE_NORMALLY (patch) = 1;
7404 }
7405 return patch;
e04a16fb
AG
7406}
7407
7408/* Check that we're not trying to do a static reference to a method in
7409 non static method. Return 1 if it's the case, 0 otherwise. */
7410
7411static int
7412check_for_static_method_reference (wfl, node, method, where, primary)
7413 tree wfl, node, method, where, primary;
7414{
7415 if (METHOD_STATIC (current_function_decl)
7416 && !METHOD_STATIC (method) && !primary && !CALL_CONSTRUCTOR_P (node))
7417 {
c2e3db92 7418 char *fct_name = xstrdup (lang_printable_name (method, 0));
e04a16fb
AG
7419 parse_error_context
7420 (wfl, "Can't make static reference to method `%s %s' in class `%s'",
0a2138e2 7421 lang_printable_name (TREE_TYPE (TREE_TYPE (method)), 0), fct_name,
e04a16fb
AG
7422 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (where))));
7423 free (fct_name);
7424 return 1;
7425 }
7426 return 0;
7427}
7428
7429/* Patch an invoke expression METHOD and ARGS, based on its invocation
7430 mode. */
7431
7432static tree
89e09b9a 7433patch_invoke (patch, method, args)
e04a16fb 7434 tree patch, method, args;
e04a16fb
AG
7435{
7436 tree dtable, func;
0a2138e2 7437 tree original_call, t, ta;
e04a16fb 7438
5e942c50
APB
7439 /* Last step for args: convert build-in types. If we're dealing with
7440 a new TYPE() type call, the first argument to the constructor
7441 isn't found in the incomming argument list, but delivered by
7442 `new' */
7443 t = TYPE_ARG_TYPES (TREE_TYPE (method));
7444 if (TREE_CODE (patch) == NEW_CLASS_EXPR)
7445 t = TREE_CHAIN (t);
ac825856
APB
7446 for (ta = args; t != end_params_node && ta;
7447 t = TREE_CHAIN (t), ta = TREE_CHAIN (ta))
b9f7e36c
APB
7448 if (JPRIMITIVE_TYPE_P (TREE_TYPE (TREE_VALUE (ta))) &&
7449 TREE_TYPE (TREE_VALUE (ta)) != TREE_VALUE (t))
7450 TREE_VALUE (ta) = convert (TREE_VALUE (t), TREE_VALUE (ta));
1a6d4fb7
APB
7451
7452 /* Resolve unresolved returned type isses */
7453 t = TREE_TYPE (TREE_TYPE (method));
7454 if (TREE_CODE (t) == POINTER_TYPE && !CLASS_LOADED_P (TREE_TYPE (t)))
7455 resolve_and_layout (TREE_TYPE (t), NULL);
22eed1e6 7456
e8fc7396 7457 if (flag_emit_class_files || flag_emit_xref)
15fdcfe9
PB
7458 func = method;
7459 else
e04a16fb 7460 {
15fdcfe9 7461 tree signature = build_java_signature (TREE_TYPE (method));
89e09b9a 7462 switch (invocation_mode (method, CALL_USING_SUPER (patch)))
15fdcfe9
PB
7463 {
7464 case INVOKE_VIRTUAL:
7465 dtable = invoke_build_dtable (0, args);
7466 func = build_invokevirtual (dtable, method);
7467 break;
b9f7e36c 7468
15fdcfe9
PB
7469 case INVOKE_SUPER:
7470 case INVOKE_STATIC:
7471 func = build_known_method_ref (method, TREE_TYPE (method),
7472 DECL_CONTEXT (method),
7473 signature, args);
7474 break;
e04a16fb 7475
15fdcfe9
PB
7476 case INVOKE_INTERFACE:
7477 dtable = invoke_build_dtable (1, args);
7478 func = build_invokeinterface (dtable, DECL_NAME (method), signature);
7479 break;
5e942c50 7480
15fdcfe9 7481 default:
89e09b9a 7482 fatal ("internal error - unknown invocation_mode result");
15fdcfe9
PB
7483 }
7484
7485 /* Ensure self_type is initialized, (invokestatic). FIXME */
7486 func = build1 (NOP_EXPR, build_pointer_type (TREE_TYPE (method)), func);
e04a16fb
AG
7487 }
7488
e04a16fb
AG
7489 TREE_TYPE (patch) = TREE_TYPE (TREE_TYPE (method));
7490 TREE_OPERAND (patch, 0) = func;
7491 TREE_OPERAND (patch, 1) = args;
7492 original_call = patch;
7493
22eed1e6
APB
7494 /* We're processing a `new TYPE ()' form. New is called an its
7495 returned value is the first argument to the constructor. We build
7496 a COMPOUND_EXPR and use saved expression so that the overall NEW
7497 expression value is a pointer to a newly created and initialized
7498 class. */
7499 if (TREE_CODE (original_call) == NEW_CLASS_EXPR)
e04a16fb
AG
7500 {
7501 tree class = DECL_CONTEXT (method);
7502 tree c1, saved_new, size, new;
e8fc7396 7503 if (flag_emit_class_files || flag_emit_xref)
15fdcfe9
PB
7504 {
7505 TREE_TYPE (patch) = build_pointer_type (class);
7506 return patch;
7507 }
e04a16fb
AG
7508 if (!TYPE_SIZE (class))
7509 safe_layout_class (class);
7510 size = size_in_bytes (class);
7511 new = build (CALL_EXPR, promote_type (class),
7512 build_address_of (alloc_object_node),
7513 tree_cons (NULL_TREE, build_class_ref (class),
7514 build_tree_list (NULL_TREE,
7515 size_in_bytes (class))),
7516 NULL_TREE);
7517 saved_new = save_expr (new);
7518 c1 = build_tree_list (NULL_TREE, saved_new);
7519 TREE_CHAIN (c1) = TREE_OPERAND (original_call, 1);
7520 TREE_OPERAND (original_call, 1) = c1;
7521 TREE_SET_CODE (original_call, CALL_EXPR);
7522 patch = build (COMPOUND_EXPR, TREE_TYPE (new), patch, saved_new);
7523 }
7524 return patch;
7525}
7526
7527static int
7528invocation_mode (method, super)
7529 tree method;
7530 int super;
7531{
7532 int access = get_access_flags_from_decl (method);
7533
22eed1e6
APB
7534 if (super)
7535 return INVOKE_SUPER;
7536
82371d41 7537 if (access & ACC_STATIC || access & ACC_FINAL || access & ACC_PRIVATE)
e04a16fb
AG
7538 return INVOKE_STATIC;
7539
7540 if (CLASS_FINAL (TYPE_NAME (DECL_CONTEXT (method))))
7541 return INVOKE_STATIC;
7542
e04a16fb
AG
7543 if (CLASS_INTERFACE (TYPE_NAME (DECL_CONTEXT (method))))
7544 return INVOKE_INTERFACE;
7545
7546 if (DECL_CONSTRUCTOR_P (method))
7547 return INVOKE_STATIC;
22eed1e6 7548
e04a16fb
AG
7549 return INVOKE_VIRTUAL;
7550}
7551
b67d701b
PB
7552/* Retrieve a refined list of matching methods. It covers the step
7553 15.11.2 (Compile-Time Step 2) */
e04a16fb
AG
7554
7555static tree
7556lookup_method_invoke (lc, cl, class, name, arg_list)
7557 int lc;
7558 tree cl;
7559 tree class, name, arg_list;
7560{
de4c7b02 7561 tree atl = end_params_node; /* Arg Type List */
c877974e 7562 tree method, signature, list, node;
49f48c71 7563 const char *candidates; /* Used for error report */
b5b8a0e7 7564 char *dup;
e04a16fb 7565
5e942c50 7566 /* Fix the arguments */
e04a16fb
AG
7567 for (node = arg_list; node; node = TREE_CHAIN (node))
7568 {
e3884b71 7569 tree current_arg = TREE_TYPE (TREE_VALUE (node));
c877974e 7570 /* Non primitive type may have to be resolved */
e3884b71 7571 if (!JPRIMITIVE_TYPE_P (current_arg))
c877974e
APB
7572 resolve_and_layout (current_arg, NULL_TREE);
7573 /* And promoted */
b67d701b 7574 if (TREE_CODE (current_arg) == RECORD_TYPE)
c877974e 7575 current_arg = promote_type (current_arg);
5e942c50 7576 atl = tree_cons (NULL_TREE, current_arg, atl);
e04a16fb 7577 }
e04a16fb 7578
5e942c50
APB
7579 /* Find all candidates and then refine the list, searching for the
7580 most specific method. */
7581 list = find_applicable_accessible_methods_list (lc, class, name, atl);
7582 list = find_most_specific_methods_list (list);
b67d701b
PB
7583 if (list && !TREE_CHAIN (list))
7584 return TREE_VALUE (list);
e04a16fb 7585
b67d701b
PB
7586 /* Issue an error. List candidates if any. Candidates are listed
7587 only if accessible (non accessible methods may end-up here for
7588 the sake of a better error report). */
7589 candidates = NULL;
7590 if (list)
e04a16fb 7591 {
e04a16fb 7592 tree current;
b67d701b 7593 obstack_grow (&temporary_obstack, ". Candidates are:\n", 18);
e04a16fb
AG
7594 for (current = list; current; current = TREE_CHAIN (current))
7595 {
b67d701b
PB
7596 tree cm = TREE_VALUE (current);
7597 char string [4096];
7598 if (!cm || not_accessible_p (class, cm, 0))
7599 continue;
b67d701b 7600 sprintf
22eed1e6
APB
7601 (string, " `%s' in `%s'%s",
7602 get_printable_method_name (cm),
b67d701b
PB
7603 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (DECL_CONTEXT (cm)))),
7604 (TREE_CHAIN (current) ? "\n" : ""));
7605 obstack_grow (&temporary_obstack, string, strlen (string));
7606 }
7607 obstack_1grow (&temporary_obstack, '\0');
7608 candidates = obstack_finish (&temporary_obstack);
7609 }
7610 /* Issue the error message */
c877974e
APB
7611 method = make_node (FUNCTION_TYPE);
7612 TYPE_ARG_TYPES (method) = atl;
b67d701b 7613 signature = build_java_argument_signature (method);
b5b8a0e7
APB
7614 dup = strdup (lang_printable_name (class, 0));
7615 parse_error_context (cl, "Can't find %s `%s(%s)' in type `%s'%s",
22eed1e6 7616 (lc ? "constructor" : "method"),
b5b8a0e7
APB
7617 (lc ? dup : IDENTIFIER_POINTER (name)),
7618 IDENTIFIER_POINTER (signature), dup,
b67d701b 7619 (candidates ? candidates : ""));
b5b8a0e7 7620 free (dup);
b67d701b
PB
7621 return NULL_TREE;
7622}
7623
5e942c50
APB
7624/* 15.11.2.1: Find Methods that are Applicable and Accessible. LC is 1
7625 when we're looking for a constructor. */
b67d701b
PB
7626
7627static tree
5e942c50
APB
7628find_applicable_accessible_methods_list (lc, class, name, arglist)
7629 int lc;
b67d701b
PB
7630 tree class, name, arglist;
7631{
b67d701b
PB
7632 tree list = NULL_TREE, all_list = NULL_TREE;
7633
1982388a 7634 /* Search interfaces */
f4e16489
APB
7635 if (CLASS_INTERFACE (TYPE_NAME (class))
7636 || CLASS_ABSTRACT (TYPE_NAME (class)))
b67d701b 7637 {
de0b553f
APB
7638 static tree searched_interfaces = NULL_TREE;
7639 static int search_not_done = 0;
1982388a
APB
7640 int i, n;
7641 tree basetype_vec = TYPE_BINFO_BASETYPES (class);
7642
de0b553f
APB
7643 /* Have we searched this interface already? */
7644 if (searched_interfaces)
7645 {
7646 tree current;
7647 for (current = searched_interfaces;
7648 current; current = TREE_CHAIN (current))
7649 if (TREE_VALUE (current) == class)
7650 return NULL;
7651 }
7652 searched_interfaces = tree_cons (NULL_TREE, class, searched_interfaces);
7653
1982388a
APB
7654 search_applicable_methods_list
7655 (lc, TYPE_METHODS (class), name, arglist, &list, &all_list);
7656
7657 n = TREE_VEC_LENGTH (basetype_vec);
7658 for (i = 0; i < n; i++)
b67d701b 7659 {
de0b553f
APB
7660 tree t = BINFO_TYPE (TREE_VEC_ELT (basetype_vec, i));
7661 tree rlist;
7662
7663 /* Skip java.lang.Object (we'll search it once later.) */
7664 if (t == object_type_node)
7665 continue;
7666
7667 search_not_done++;
7668 rlist = find_applicable_accessible_methods_list (lc, t, name,
7669 arglist);
1982388a 7670 all_list = chainon (rlist, (list ? list : all_list));
de0b553f
APB
7671 search_not_done--;
7672 }
7673
7674 /* We're done. Reset the searched interfaces list and finally search
7675 java.lang.Object */
7676 if (!search_not_done)
7677 {
7678 searched_interfaces = NULL_TREE;
7679 search_applicable_methods_list (lc, TYPE_METHODS (object_type_node),
7680 name, arglist, &list, &all_list);
e04a16fb 7681 }
e04a16fb 7682 }
1982388a
APB
7683 /* Search classes */
7684 else
7685 while (class != NULL_TREE)
7686 {
7687 search_applicable_methods_list
7688 (lc, TYPE_METHODS (class), name, arglist, &list, &all_list);
7689 class = (lc ? NULL_TREE : CLASSTYPE_SUPER (class));
7690 }
7691
b67d701b
PB
7692 /* Either return the list obtained or all selected (but
7693 inaccessible) methods for better error report. */
7694 return (!list ? all_list : list);
7695}
e04a16fb 7696
1982388a
APB
7697/* Effectively search for the approriate method in method */
7698
7699static void
7700search_applicable_methods_list(lc, method, name, arglist, list, all_list)
7701 int lc;
7702 tree method, name, arglist;
7703 tree *list, *all_list;
7704{
7705 for (; method; method = TREE_CHAIN (method))
7706 {
7707 /* When dealing with constructor, stop here, otherwise search
7708 other classes */
7709 if (lc && !DECL_CONSTRUCTOR_P (method))
7710 continue;
7711 else if (!lc && (DECL_CONSTRUCTOR_P (method)
7712 || (GET_METHOD_NAME (method) != name)))
7713 continue;
7714
7715 if (argument_types_convertible (method, arglist))
7716 {
7717 /* Retain accessible methods only */
7718 if (!not_accessible_p (DECL_CONTEXT (current_function_decl),
7719 method, 0))
7720 *list = tree_cons (NULL_TREE, method, *list);
7721 else
7722 /* Also retain all selected method here */
7723 *all_list = tree_cons (NULL_TREE, method, *list);
7724 }
7725 }
7726}
7727
b67d701b
PB
7728/* 15.11.2.2 Choose the Most Specific Method */
7729
7730static tree
7731find_most_specific_methods_list (list)
7732 tree list;
7733{
7734 int max = 0;
7735 tree current, new_list = NULL_TREE;
7736 for (current = list; current; current = TREE_CHAIN (current))
e04a16fb 7737 {
b67d701b
PB
7738 tree method;
7739 DECL_SPECIFIC_COUNT (TREE_VALUE (current)) = 0;
7740
7741 for (method = list; method; method = TREE_CHAIN (method))
7742 {
7743 /* Don't test a method against itself */
7744 if (method == current)
7745 continue;
7746
7747 /* Compare arguments and location where method where declared */
7748 if (argument_types_convertible (TREE_VALUE (method),
7749 TREE_VALUE (current))
7750 && valid_method_invocation_conversion_p
7751 (DECL_CONTEXT (TREE_VALUE (method)),
7752 DECL_CONTEXT (TREE_VALUE (current))))
7753 {
7754 int v = ++DECL_SPECIFIC_COUNT (TREE_VALUE (current));
7755 max = (v > max ? v : max);
7756 }
7757 }
e04a16fb
AG
7758 }
7759
b67d701b
PB
7760 /* Review the list and select the maximally specific methods */
7761 for (current = list; current; current = TREE_CHAIN (current))
7762 if (DECL_SPECIFIC_COUNT (TREE_VALUE (current)) == max)
7763 new_list = tree_cons (NULL_TREE, TREE_VALUE (current), new_list);
7764
7765 /* If we can't find one, lower expectations and try to gather multiple
7766 maximally specific methods */
7767 while (!new_list)
7768 {
7769 while (--max > 0)
7770 {
7771 if (DECL_SPECIFIC_COUNT (TREE_VALUE (current)) == max)
7772 new_list = tree_cons (NULL_TREE, TREE_VALUE (current), new_list);
7773 }
7774 return new_list;
7775 }
7776
7777 return new_list;
e04a16fb
AG
7778}
7779
b67d701b
PB
7780/* Make sure that the type of each M2_OR_ARGLIST arguments can be
7781 converted by method invocation conversion (5.3) to the type of the
7782 corresponding parameter of M1. Implementation expects M2_OR_ARGLIST
7783 to change less often than M1. */
e04a16fb 7784
b67d701b
PB
7785static int
7786argument_types_convertible (m1, m2_or_arglist)
7787 tree m1, m2_or_arglist;
e04a16fb 7788{
b67d701b
PB
7789 static tree m2_arg_value = NULL_TREE;
7790 static tree m2_arg_cache = NULL_TREE;
e04a16fb 7791
b67d701b 7792 register tree m1_arg, m2_arg;
e04a16fb 7793
b67d701b
PB
7794 m1_arg = TYPE_ARG_TYPES (TREE_TYPE (m1));
7795 if (!METHOD_STATIC (m1))
7796 m1_arg = TREE_CHAIN (m1_arg);
e04a16fb 7797
b67d701b
PB
7798 if (m2_arg_value == m2_or_arglist)
7799 m2_arg = m2_arg_cache;
7800 else
7801 {
7802 /* M2_OR_ARGLIST can be a function DECL or a raw list of
7803 argument types */
7804 if (m2_or_arglist && TREE_CODE (m2_or_arglist) == FUNCTION_DECL)
7805 {
7806 m2_arg = TYPE_ARG_TYPES (TREE_TYPE (m2_or_arglist));
7807 if (!METHOD_STATIC (m2_or_arglist))
7808 m2_arg = TREE_CHAIN (m2_arg);
7809 }
7810 else
7811 m2_arg = m2_or_arglist;
e04a16fb 7812
b67d701b
PB
7813 m2_arg_value = m2_or_arglist;
7814 m2_arg_cache = m2_arg;
7815 }
e04a16fb 7816
de4c7b02 7817 while (m1_arg != end_params_node && m2_arg != end_params_node)
b67d701b 7818 {
c877974e 7819 resolve_and_layout (TREE_VALUE (m1_arg), NULL_TREE);
b67d701b
PB
7820 if (!valid_method_invocation_conversion_p (TREE_VALUE (m1_arg),
7821 TREE_VALUE (m2_arg)))
7822 break;
7823 m1_arg = TREE_CHAIN (m1_arg);
7824 m2_arg = TREE_CHAIN (m2_arg);
e04a16fb 7825 }
de4c7b02 7826 return m1_arg == end_params_node && m2_arg == end_params_node;
e04a16fb
AG
7827}
7828
7829/* Qualification routines */
7830
7831static void
7832qualify_ambiguous_name (id)
7833 tree id;
7834{
cd531a2e
KG
7835 tree qual, qual_wfl, name = NULL_TREE, decl, ptr_type = NULL_TREE,
7836 saved_current_class;
d8fccff5 7837 int again, super_found = 0, this_found = 0, new_array_found = 0;
8576f094 7838 int code;
e04a16fb
AG
7839
7840 /* We first qualify the first element, then derive qualification of
7841 others based on the first one. If the first element is qualified
7842 by a resolution (field or type), this resolution is stored in the
7843 QUAL_RESOLUTION of the qual element being examined. We need to
7844 save the current_class since the use of SUPER might change the
7845 its value. */
7846 saved_current_class = current_class;
7847 qual = EXPR_WFL_QUALIFICATION (id);
7848 do {
7849
7850 /* Simple qualified expression feature a qual_wfl that is a
7851 WFL. Expression derived from a primary feature more complicated
7852 things like a CALL_EXPR. Expression from primary need to be
7853 worked out to extract the part on which the qualification will
7854 take place. */
7855 qual_wfl = QUAL_WFL (qual);
7856 switch (TREE_CODE (qual_wfl))
7857 {
7858 case CALL_EXPR:
7859 qual_wfl = TREE_OPERAND (qual_wfl, 0);
7860 if (TREE_CODE (qual_wfl) != EXPR_WITH_FILE_LOCATION)
7861 {
7862 qual = EXPR_WFL_QUALIFICATION (qual_wfl);
7863 qual_wfl = QUAL_WFL (qual);
7864 }
7865 break;
d8fccff5
APB
7866 case NEW_ARRAY_EXPR:
7867 qual = TREE_CHAIN (qual);
1a6d4fb7 7868 again = new_array_found = 1;
d8fccff5 7869 continue;
b67d701b 7870 case NEW_CLASS_EXPR:
e04a16fb 7871 case CONVERT_EXPR:
e04a16fb
AG
7872 qual_wfl = TREE_OPERAND (qual_wfl, 0);
7873 break;
c583dd46
APB
7874 case ARRAY_REF:
7875 while (TREE_CODE (qual_wfl) == ARRAY_REF)
7876 qual_wfl = TREE_OPERAND (qual_wfl, 0);
7877 break;
8576f094
APB
7878 case STRING_CST:
7879 qual = TREE_CHAIN (qual);
7880 qual_wfl = QUAL_WFL (qual);
7881 break;
0a2138e2
APB
7882 default:
7883 /* Fix for -Wall. Just break doing nothing */
7884 break;
e04a16fb 7885 }
8576f094 7886
e04a16fb
AG
7887 ptr_type = current_class;
7888 again = 0;
8576f094
APB
7889 code = TREE_CODE (qual_wfl);
7890
7891 /* Pos evaluation: non WFL leading expression nodes */
7892 if (code == CONVERT_EXPR
7893 && TREE_CODE (TREE_TYPE (qual_wfl)) == EXPR_WITH_FILE_LOCATION)
7894 name = EXPR_WFL_NODE (TREE_TYPE (qual_wfl));
7895
ac22f9cb 7896 else if ((code == ARRAY_REF || code == CALL_EXPR || code == MODIFY_EXPR) &&
8576f094
APB
7897 TREE_CODE (TREE_OPERAND (qual_wfl, 0)) == EXPR_WITH_FILE_LOCATION)
7898 name = EXPR_WFL_NODE (TREE_OPERAND (qual_wfl, 0));
7899
37feda7d
APB
7900 else if (code == STRING_CST || code == CONDITIONAL_EXPR
7901 || code == PLUS_EXPR)
8576f094
APB
7902 {
7903 qual = TREE_CHAIN (qual);
7904 qual_wfl = QUAL_WFL (qual);
7905 again = 1;
7906 }
7907 else
f441f671
APB
7908 {
7909 name = EXPR_WFL_NODE (qual_wfl);
7910 if (!name)
7911 {
7912 qual = EXPR_WFL_QUALIFICATION (qual_wfl);
7913 again = 1;
7914 }
7915 }
7916
e04a16fb
AG
7917 /* If we have a THIS (from a primary), we set the context accordingly */
7918 if (name == this_identifier_node)
7919 {
7920 qual = TREE_CHAIN (qual);
7921 qual_wfl = QUAL_WFL (qual);
22eed1e6
APB
7922 if (TREE_CODE (qual_wfl) == CALL_EXPR)
7923 again = 1;
7924 else
7925 name = EXPR_WFL_NODE (qual_wfl);
e04a16fb
AG
7926 this_found = 1;
7927 }
7928 /* If we have a SUPER, we set the context accordingly */
7929 if (name == super_identifier_node)
7930 {
7931 current_class = CLASSTYPE_SUPER (ptr_type);
7932 /* Check that there is such a thing as a super class. If not,
7933 return. The error will be caught later on, during the
7934 resolution */
7935 if (!current_class)
7936 {
7937 current_class = saved_current_class;
7938 return;
7939 }
7940 qual = TREE_CHAIN (qual);
7941 /* Do one more interation to set things up */
7942 super_found = again = 1;
7943 }
7944 } while (again);
7945
7946 /* If name appears within the scope of a location variable
7947 declaration or parameter declaration, then it is an expression
7948 name. We don't carry this test out if we're in the context of the
7949 use of SUPER or THIS */
1a6d4fb7
APB
7950 if (!this_found && !super_found &&
7951 TREE_CODE (name) != STRING_CST && (decl = IDENTIFIER_LOCAL_VALUE (name)))
e04a16fb
AG
7952 {
7953 RESOLVE_EXPRESSION_NAME_P (qual_wfl) = 1;
7954 QUAL_RESOLUTION (qual) = decl;
7955 }
7956
7957 /* If within the class/interface NAME was found to be used there
7958 exists a (possibly inherited) field named NAME, then this is an
d8fccff5
APB
7959 expression name. If we saw a NEW_ARRAY_EXPR before and want to
7960 address length, it is OK. */
7961 else if ((decl = lookup_field_wrapper (ptr_type, name))
7962 || (new_array_found && name == length_identifier_node))
e04a16fb
AG
7963 {
7964 RESOLVE_EXPRESSION_NAME_P (qual_wfl) = 1;
d8fccff5 7965 QUAL_RESOLUTION (qual) = (new_array_found ? NULL_TREE : decl);
e04a16fb
AG
7966 }
7967
1a6d4fb7 7968 /* We reclassify NAME as yielding to a type name resolution if:
e04a16fb
AG
7969 - NAME is a class/interface declared within the compilation
7970 unit containing NAME,
7971 - NAME is imported via a single-type-import declaration,
7972 - NAME is declared in an another compilation unit of the package
7973 of the compilation unit containing NAME,
7974 - NAME is declared by exactly on type-import-on-demand declaration
1a6d4fb7
APB
7975 of the compilation unit containing NAME.
7976 - NAME is actually a STRING_CST. */
7977 else if (TREE_CODE (name) == STRING_CST ||
7978 (decl = resolve_and_layout (name, NULL_TREE)))
e04a16fb
AG
7979 {
7980 RESOLVE_TYPE_NAME_P (qual_wfl) = 1;
7981 QUAL_RESOLUTION (qual) = decl;
7982 }
7983
7984 /* Method call are expression name */
9bbc7d9f 7985 else if (TREE_CODE (QUAL_WFL (qual)) == CALL_EXPR
8576f094
APB
7986 || TREE_CODE (QUAL_WFL (qual)) == ARRAY_REF
7987 || TREE_CODE (QUAL_WFL (qual)) == CONVERT_EXPR)
e04a16fb
AG
7988 RESOLVE_EXPRESSION_NAME_P (qual_wfl) = 1;
7989
7990 /* Check here that NAME isn't declared by more than one
7991 type-import-on-demand declaration of the compilation unit
7992 containing NAME. FIXME */
7993
7994 /* Otherwise, NAME is reclassified as a package name */
7995 else
7996 RESOLVE_PACKAGE_NAME_P (qual_wfl) = 1;
7997
7998 /* Propagate the qualification accross other components of the
7999 qualified name */
8000 for (qual = TREE_CHAIN (qual); qual;
8001 qual_wfl = QUAL_WFL (qual), qual = TREE_CHAIN (qual))
8002 {
8003 if (RESOLVE_PACKAGE_NAME_P (qual_wfl))
8004 RESOLVE_PACKAGE_NAME_P (QUAL_WFL (qual)) = 1;
8005 else
8006 RESOLVE_EXPRESSION_NAME_P (QUAL_WFL (qual)) = 1;
8007 }
8008
8009 /* Store the global qualification for the ambiguous part of ID back
8010 into ID fields */
8011 if (RESOLVE_EXPRESSION_NAME_P (qual_wfl))
8012 RESOLVE_EXPRESSION_NAME_P (id) = 1;
8013 else if (RESOLVE_TYPE_NAME_P (qual_wfl))
8014 RESOLVE_TYPE_NAME_P (id) = 1;
8015 else if (RESOLVE_PACKAGE_NAME_P (qual_wfl))
8016 RESOLVE_PACKAGE_NAME_P (id) = 1;
8017
8018 /* Restore the current class */
8019 current_class = saved_current_class;
8020}
8021
8022static int
8023breakdown_qualified (left, right, source)
8024 tree *left, *right, source;
8025{
8026 char *p = IDENTIFIER_POINTER (source), *base;
8027 int l = IDENTIFIER_LENGTH (source);
8028
8029 /* Breakdown NAME into REMAINDER . IDENTIFIER */
8030 base = p;
8031 p += (l-1);
8032 while (*p != '.' && p != base)
8033 p--;
8034
8035 /* We didn't find a '.'. Return an error */
8036 if (p == base)
8037 return 1;
8038
8039 *p = '\0';
8040 if (right)
8041 *right = get_identifier (p+1);
8042 *left = get_identifier (IDENTIFIER_POINTER (source));
8043 *p = '.';
8044
8045 return 0;
8046}
8047
e04a16fb 8048/* Patch tree nodes in a function body. When a BLOCK is found, push
5b09b33e
PB
8049 local variable decls if present.
8050 Same as java_complete_lhs, but does resolve static finals to values. */
e04a16fb
AG
8051
8052static tree
8053java_complete_tree (node)
8054 tree node;
5b09b33e
PB
8055{
8056 node = java_complete_lhs (node);
8057 if (TREE_CODE (node) == VAR_DECL && FIELD_STATIC (node)
7f10c2e2
APB
8058 && FIELD_FINAL (node) && DECL_INITIAL (node) != NULL_TREE
8059 && !flag_emit_xref)
5b09b33e
PB
8060 {
8061 tree value = DECL_INITIAL (node);
8062 DECL_INITIAL (node) = NULL_TREE;
100f7cd8 8063 push_obstacks (&permanent_obstack, &permanent_obstack);
5b09b33e 8064 value = fold_constant_for_init (value, node);
100f7cd8 8065 pop_obstacks ();
5b09b33e
PB
8066 DECL_INITIAL (node) = value;
8067 if (value != NULL_TREE)
8068 return value;
8069 }
8070 return node;
8071}
8072
2aa11e97
APB
8073static tree
8074java_stabilize_reference (node)
8075 tree node;
8076{
8077 if (TREE_CODE (node) == COMPOUND_EXPR)
8078 {
8079 tree op0 = TREE_OPERAND (node, 0);
8080 tree op1 = TREE_OPERAND (node, 1);
642f15d1 8081 TREE_OPERAND (node, 0) = save_expr (op0);
2aa11e97
APB
8082 TREE_OPERAND (node, 1) = java_stabilize_reference (op1);
8083 return node;
8084 }
5cbdba64 8085 return stabilize_reference (node);
2aa11e97
APB
8086}
8087
5b09b33e
PB
8088/* Patch tree nodes in a function body. When a BLOCK is found, push
8089 local variable decls if present.
8090 Same as java_complete_tree, but does not resolve static finals to values. */
8091
8092static tree
8093java_complete_lhs (node)
8094 tree node;
e04a16fb 8095{
22eed1e6 8096 tree nn, cn, wfl_op1, wfl_op2, wfl_op3;
b67d701b 8097 int flag;
e04a16fb
AG
8098
8099 /* CONVERT_EXPR always has its type set, even though it needs to be
b67d701b 8100 worked out. */
e04a16fb
AG
8101 if (TREE_TYPE (node) && TREE_CODE (node) != CONVERT_EXPR)
8102 return node;
8103
8104 /* The switch block implements cases processing container nodes
8105 first. Contained nodes are always written back. Leaves come
8106 next and return a value. */
8107 switch (TREE_CODE (node))
8108 {
8109 case BLOCK:
8110
8111 /* 1- Block section.
8112 Set the local values on decl names so we can identify them
8113 faster when they're referenced. At that stage, identifiers
8114 are legal so we don't check for declaration errors. */
8115 for (cn = BLOCK_EXPR_DECLS (node); cn; cn = TREE_CHAIN (cn))
8116 {
8117 DECL_CONTEXT (cn) = current_function_decl;
8118 IDENTIFIER_LOCAL_VALUE (DECL_NAME (cn)) = cn;
e04a16fb 8119 }
15fdcfe9
PB
8120 if (BLOCK_EXPR_BODY (node) == NULL_TREE)
8121 CAN_COMPLETE_NORMALLY (node) = 1;
8122 else
e04a16fb 8123 {
15fdcfe9
PB
8124 tree stmt = BLOCK_EXPR_BODY (node);
8125 tree *ptr;
8126 int error_seen = 0;
8127 if (TREE_CODE (stmt) == COMPOUND_EXPR)
8128 {
c877974e
APB
8129 /* Re-order from (((A; B); C); ...; Z) to
8130 (A; (B; (C ; (...; Z)))).
15fdcfe9
PB
8131 This makes it easier to scan the statements left-to-right
8132 without using recursion (which might overflow the stack
8133 if the block has many statements. */
8134 for (;;)
8135 {
8136 tree left = TREE_OPERAND (stmt, 0);
8137 if (TREE_CODE (left) != COMPOUND_EXPR)
8138 break;
8139 TREE_OPERAND (stmt, 0) = TREE_OPERAND (left, 1);
8140 TREE_OPERAND (left, 1) = stmt;
8141 stmt = left;
8142 }
8143 BLOCK_EXPR_BODY (node) = stmt;
8144 }
8145
c877974e
APB
8146 /* Now do the actual complete, without deep recursion for
8147 long blocks. */
15fdcfe9 8148 ptr = &BLOCK_EXPR_BODY (node);
dc0b3eff
PB
8149 while (TREE_CODE (*ptr) == COMPOUND_EXPR
8150 && TREE_OPERAND (*ptr, 1) != empty_stmt_node)
15fdcfe9
PB
8151 {
8152 tree cur = java_complete_tree (TREE_OPERAND (*ptr, 0));
8153 tree *next = &TREE_OPERAND (*ptr, 1);
8154 TREE_OPERAND (*ptr, 0) = cur;
cd9643f7
PB
8155 if (cur == empty_stmt_node)
8156 {
8157 /* Optimization; makes it easier to detect empty bodies.
8158 Most useful for <clinit> with all-constant initializer. */
8159 *ptr = *next;
8160 continue;
8161 }
15fdcfe9
PB
8162 if (TREE_CODE (cur) == ERROR_MARK)
8163 error_seen++;
8164 else if (! CAN_COMPLETE_NORMALLY (cur))
8165 {
8166 wfl_op2 = *next;
8167 for (;;)
8168 {
8169 if (TREE_CODE (wfl_op2) == BLOCK)
8170 wfl_op2 = BLOCK_EXPR_BODY (wfl_op2);
8171 else if (TREE_CODE (wfl_op2) == COMPOUND_EXPR)
8172 wfl_op2 = TREE_OPERAND (wfl_op2, 0);
8173 else
8174 break;
8175 }
8176 if (TREE_CODE (wfl_op2) != CASE_EXPR
dc0b3eff 8177 && TREE_CODE (wfl_op2) != DEFAULT_EXPR)
82371d41 8178 unreachable_stmt_error (*ptr);
15fdcfe9
PB
8179 }
8180 ptr = next;
8181 }
8182 *ptr = java_complete_tree (*ptr);
8183
8184 if (TREE_CODE (*ptr) == ERROR_MARK || error_seen > 0)
e04a16fb 8185 return error_mark_node;
15fdcfe9 8186 CAN_COMPLETE_NORMALLY (node) = CAN_COMPLETE_NORMALLY (*ptr);
e04a16fb
AG
8187 }
8188 /* Turn local bindings to null */
8189 for (cn = BLOCK_EXPR_DECLS (node); cn; cn = TREE_CHAIN (cn))
8190 IDENTIFIER_LOCAL_VALUE (DECL_NAME (cn)) = NULL_TREE;
8191
8192 TREE_TYPE (node) = void_type_node;
8193 break;
8194
8195 /* 2- They are expressions but ultimately deal with statements */
b67d701b 8196
b9f7e36c
APB
8197 case THROW_EXPR:
8198 wfl_op1 = TREE_OPERAND (node, 0);
8199 COMPLETE_CHECK_OP_0 (node);
15fdcfe9 8200 /* CAN_COMPLETE_NORMALLY (node) = 0; */
b9f7e36c
APB
8201 return patch_throw_statement (node, wfl_op1);
8202
8203 case SYNCHRONIZED_EXPR:
8204 wfl_op1 = TREE_OPERAND (node, 0);
b9f7e36c
APB
8205 return patch_synchronized_statement (node, wfl_op1);
8206
b67d701b
PB
8207 case TRY_EXPR:
8208 return patch_try_statement (node);
8209
a7d8d81f
PB
8210 case TRY_FINALLY_EXPR:
8211 COMPLETE_CHECK_OP_0 (node);
8212 COMPLETE_CHECK_OP_1 (node);
8213 CAN_COMPLETE_NORMALLY (node)
8214 = (CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 0))
8215 && CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 1)));
8216 TREE_TYPE (node) = TREE_TYPE (TREE_OPERAND (node, 0));
8217 return node;
8218
5a005d9e
PB
8219 case CLEANUP_POINT_EXPR:
8220 COMPLETE_CHECK_OP_0 (node);
8221 TREE_TYPE (node) = void_type_node;
2aa11e97
APB
8222 CAN_COMPLETE_NORMALLY (node) =
8223 CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 0));
5a005d9e
PB
8224 return node;
8225
8226 case WITH_CLEANUP_EXPR:
8227 COMPLETE_CHECK_OP_0 (node);
8228 COMPLETE_CHECK_OP_2 (node);
2aa11e97
APB
8229 CAN_COMPLETE_NORMALLY (node) =
8230 CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 0));
5a005d9e
PB
8231 TREE_TYPE (node) = void_type_node;
8232 return node;
8233
e04a16fb
AG
8234 case LABELED_BLOCK_EXPR:
8235 PUSH_LABELED_BLOCK (node);
8236 if (LABELED_BLOCK_BODY (node))
8237 COMPLETE_CHECK_OP_1 (node);
8238 TREE_TYPE (node) = void_type_node;
8239 POP_LABELED_BLOCK ();
1fb89a4d
APB
8240
8241 if (LABELED_BLOCK_BODY (node) == empty_stmt_node)
9dd939b2
APB
8242 {
8243 LABELED_BLOCK_BODY (node) = NULL_TREE;
8244 CAN_COMPLETE_NORMALLY (node) = 1;
8245 }
1fb89a4d 8246 else if (CAN_COMPLETE_NORMALLY (LABELED_BLOCK_BODY (node)))
15fdcfe9 8247 CAN_COMPLETE_NORMALLY (node) = 1;
e04a16fb
AG
8248 return node;
8249
8250 case EXIT_BLOCK_EXPR:
8251 /* We don't complete operand 1, because it's the return value of
8252 the EXIT_BLOCK_EXPR which doesn't exist it Java */
8253 return patch_bc_statement (node);
8254
15fdcfe9
PB
8255 case CASE_EXPR:
8256 cn = java_complete_tree (TREE_OPERAND (node, 0));
8257 if (cn == error_mark_node)
8258 return cn;
8259
8576f094
APB
8260 /* First, the case expression must be constant. Values of final
8261 fields are accepted. */
15fdcfe9 8262 cn = fold (cn);
8576f094
APB
8263 if ((TREE_CODE (cn) == COMPOUND_EXPR || TREE_CODE (cn) == COMPONENT_REF)
8264 && JDECL_P (TREE_OPERAND (cn, 1))
8265 && FIELD_FINAL (TREE_OPERAND (cn, 1))
8266 && DECL_INITIAL (TREE_OPERAND (cn, 1)))
100f7cd8
APB
8267 {
8268 push_obstacks (&permanent_obstack, &permanent_obstack);
8269 cn = fold_constant_for_init (DECL_INITIAL (TREE_OPERAND (cn, 1)),
8270 TREE_OPERAND (cn, 1));
8271 pop_obstacks ();
8272 }
15fdcfe9 8273
ce6e9147 8274 if (!TREE_CONSTANT (cn) && !flag_emit_xref)
15fdcfe9
PB
8275 {
8276 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
8277 parse_error_context (node, "Constant expression required");
8278 return error_mark_node;
8279 }
8280
8281 nn = ctxp->current_loop;
8282
8283 /* It must be assignable to the type of the switch expression. */
c877974e
APB
8284 if (!try_builtin_assignconv (NULL_TREE,
8285 TREE_TYPE (TREE_OPERAND (nn, 0)), cn))
15fdcfe9
PB
8286 {
8287 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
8288 parse_error_context
8289 (wfl_operator,
8290 "Incompatible type for case. Can't convert `%s' to `int'",
8291 lang_printable_name (TREE_TYPE (cn), 0));
8292 return error_mark_node;
8293 }
8294
8295 cn = fold (convert (int_type_node, cn));
8296
8297 /* Multiple instance of a case label bearing the same
8298 value is checked during code generation. The case
8299 expression is allright so far. */
8300 TREE_OPERAND (node, 0) = cn;
9bbc7d9f 8301 TREE_TYPE (node) = void_type_node;
15fdcfe9 8302 CAN_COMPLETE_NORMALLY (node) = 1;
10100cc7 8303 TREE_SIDE_EFFECTS (node) = 1;
15fdcfe9
PB
8304 break;
8305
8306 case DEFAULT_EXPR:
8307 nn = ctxp->current_loop;
8308 /* Only one default label is allowed per switch statement */
8309 if (SWITCH_HAS_DEFAULT (nn))
8310 {
8311 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
8312 parse_error_context (wfl_operator,
8313 "Duplicate case label: `default'");
8314 return error_mark_node;
8315 }
8316 else
8317 SWITCH_HAS_DEFAULT (nn) = 1;
9bbc7d9f 8318 TREE_TYPE (node) = void_type_node;
10100cc7 8319 TREE_SIDE_EFFECTS (node) = 1;
15fdcfe9
PB
8320 CAN_COMPLETE_NORMALLY (node) = 1;
8321 break;
8322
b67d701b 8323 case SWITCH_EXPR:
e04a16fb
AG
8324 case LOOP_EXPR:
8325 PUSH_LOOP (node);
8326 /* Check whether the loop was enclosed in a labeled
8327 statement. If not, create one, insert the loop in it and
8328 return the node */
8329 nn = patch_loop_statement (node);
b67d701b 8330
e04a16fb 8331 /* Anyways, walk the body of the loop */
b67d701b
PB
8332 if (TREE_CODE (node) == LOOP_EXPR)
8333 TREE_OPERAND (node, 0) = java_complete_tree (TREE_OPERAND (node, 0));
8334 /* Switch statement: walk the switch expression and the cases */
8335 else
8336 node = patch_switch_statement (node);
8337
e04a16fb 8338 if (TREE_OPERAND (node, 0) == error_mark_node)
b635eb2f
PB
8339 nn = error_mark_node;
8340 else
15fdcfe9 8341 {
b635eb2f
PB
8342 TREE_TYPE (nn) = TREE_TYPE (node) = void_type_node;
8343 /* If we returned something different, that's because we
8344 inserted a label. Pop the label too. */
8345 if (nn != node)
8346 {
8347 if (CAN_COMPLETE_NORMALLY (node))
8348 CAN_COMPLETE_NORMALLY (nn) = 1;
8349 POP_LABELED_BLOCK ();
8350 }
15fdcfe9 8351 }
e04a16fb
AG
8352 POP_LOOP ();
8353 return nn;
8354
8355 case EXIT_EXPR:
8356 TREE_OPERAND (node, 0) = java_complete_tree (TREE_OPERAND (node, 0));
8357 return patch_exit_expr (node);
8358
8359 case COND_EXPR:
8360 /* Condition */
8361 TREE_OPERAND (node, 0) = java_complete_tree (TREE_OPERAND (node, 0));
8362 if (TREE_OPERAND (node, 0) == error_mark_node)
8363 return error_mark_node;
8364 /* then-else branches */
8365 TREE_OPERAND (node, 1) = java_complete_tree (TREE_OPERAND (node, 1));
8366 if (TREE_OPERAND (node, 1) == error_mark_node)
8367 return error_mark_node;
8368 TREE_OPERAND (node, 2) = java_complete_tree (TREE_OPERAND (node, 2));
8369 if (TREE_OPERAND (node, 2) == error_mark_node)
8370 return error_mark_node;
8371 return patch_if_else_statement (node);
8372 break;
8373
22eed1e6
APB
8374 case CONDITIONAL_EXPR:
8375 /* Condition */
8376 wfl_op1 = TREE_OPERAND (node, 0);
8377 COMPLETE_CHECK_OP_0 (node);
8378 wfl_op2 = TREE_OPERAND (node, 1);
8379 COMPLETE_CHECK_OP_1 (node);
8380 wfl_op3 = TREE_OPERAND (node, 2);
8381 COMPLETE_CHECK_OP_2 (node);
8382 return patch_conditional_expr (node, wfl_op1, wfl_op2);
8383
e04a16fb
AG
8384 /* 3- Expression section */
8385 case COMPOUND_EXPR:
15fdcfe9 8386 wfl_op2 = TREE_OPERAND (node, 1);
ac825856
APB
8387 TREE_OPERAND (node, 0) = nn =
8388 java_complete_tree (TREE_OPERAND (node, 0));
dc0b3eff
PB
8389 if (wfl_op2 == empty_stmt_node)
8390 CAN_COMPLETE_NORMALLY (node) = CAN_COMPLETE_NORMALLY (nn);
8391 else
15fdcfe9 8392 {
dc0b3eff 8393 if (! CAN_COMPLETE_NORMALLY (nn) && TREE_CODE (nn) != ERROR_MARK)
bccaf73a 8394 {
dc0b3eff
PB
8395 /* An unreachable condition in a do-while statement
8396 is *not* (technically) an unreachable statement. */
8397 nn = wfl_op2;
8398 if (TREE_CODE (nn) == EXPR_WITH_FILE_LOCATION)
8399 nn = EXPR_WFL_NODE (nn);
8400 if (TREE_CODE (nn) != EXIT_EXPR)
8401 {
8402 SET_WFL_OPERATOR (wfl_operator, node, wfl_op2);
8403 parse_error_context (wfl_operator, "Unreachable statement");
8404 }
bccaf73a 8405 }
dc0b3eff
PB
8406 TREE_OPERAND (node, 1) = java_complete_tree (TREE_OPERAND (node, 1));
8407 if (TREE_OPERAND (node, 1) == error_mark_node)
8408 return error_mark_node;
8409 CAN_COMPLETE_NORMALLY (node)
8410 = CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 1));
15fdcfe9 8411 }
e04a16fb
AG
8412 TREE_TYPE (node) = TREE_TYPE (TREE_OPERAND (node, 1));
8413 break;
8414
8415 case RETURN_EXPR:
15fdcfe9 8416 /* CAN_COMPLETE_NORMALLY (node) = 0; */
e04a16fb
AG
8417 return patch_return (node);
8418
8419 case EXPR_WITH_FILE_LOCATION:
8420 if (!EXPR_WFL_NODE (node) /* Or a PRIMARY flag ? */
8421 || TREE_CODE (EXPR_WFL_NODE (node)) == IDENTIFIER_NODE)
15fdcfe9 8422 {
5423609c 8423 tree wfl = node;
15fdcfe9 8424 node = resolve_expression_name (node, NULL);
dc0b3eff
PB
8425 if (node == error_mark_node)
8426 return node;
5423609c
APB
8427 /* Keep line number information somewhere were it doesn't
8428 disrupt the completion process. */
2c56429a 8429 if (flag_emit_xref && TREE_CODE (node) != CALL_EXPR)
5423609c
APB
8430 {
8431 EXPR_WFL_NODE (wfl) = TREE_OPERAND (node, 1);
8432 TREE_OPERAND (node, 1) = wfl;
8433 }
15fdcfe9
PB
8434 CAN_COMPLETE_NORMALLY (node) = 1;
8435 }
e04a16fb
AG
8436 else
8437 {
5b09b33e
PB
8438 tree body;
8439 int save_lineno = lineno;
8440 lineno = EXPR_WFL_LINENO (node);
8441 body = java_complete_tree (EXPR_WFL_NODE (node));
8442 lineno = save_lineno;
15fdcfe9 8443 EXPR_WFL_NODE (node) = body;
dc0b3eff 8444 TREE_SIDE_EFFECTS (node) = TREE_SIDE_EFFECTS (body);
15fdcfe9 8445 CAN_COMPLETE_NORMALLY (node) = CAN_COMPLETE_NORMALLY (body);
cd9643f7
PB
8446 if (body == empty_stmt_node)
8447 {
8448 /* Optimization; makes it easier to detect empty bodies. */
8449 return body;
8450 }
dc0b3eff 8451 if (body == error_mark_node)
e04a16fb
AG
8452 {
8453 /* Its important for the evaluation of assignment that
8454 this mark on the TREE_TYPE is propagated. */
8455 TREE_TYPE (node) = error_mark_node;
8456 return error_mark_node;
8457 }
8458 else
8459 TREE_TYPE (node) = TREE_TYPE (EXPR_WFL_NODE (node));
15fdcfe9 8460
e04a16fb
AG
8461 }
8462 break;
8463
b67d701b 8464 case NEW_ARRAY_EXPR:
e04a16fb
AG
8465 /* Patch all the dimensions */
8466 flag = 0;
8467 for (cn = TREE_OPERAND (node, 1); cn; cn = TREE_CHAIN (cn))
8468 {
8469 int location = EXPR_WFL_LINECOL (TREE_VALUE (cn));
8470 tree dim = java_complete_tree (TREE_VALUE (cn));
8471 if (dim == error_mark_node)
8472 {
8473 flag = 1;
8474 continue;
8475 }
8476 else
8477 {
b9f7e36c 8478 TREE_VALUE (cn) = dim;
e04a16fb
AG
8479 /* Setup the location of the current dimension, for
8480 later error report. */
8481 TREE_PURPOSE (cn) =
8482 build_expr_wfl (NULL_TREE, input_filename, 0, 0);
8483 EXPR_WFL_LINECOL (TREE_PURPOSE (cn)) = location;
8484 }
8485 }
8486 /* They complete the array creation expression, if no errors
8487 were found. */
15fdcfe9 8488 CAN_COMPLETE_NORMALLY (node) = 1;
aee48ef8
PB
8489 return (flag ? error_mark_node
8490 : force_evaluation_order (patch_newarray (node)));
e04a16fb 8491
b67d701b 8492 case NEW_CLASS_EXPR:
e04a16fb 8493 case CALL_EXPR:
b67d701b 8494 /* Complete function's argument(s) first */
e04a16fb
AG
8495 if (complete_function_arguments (node))
8496 return error_mark_node;
8497 else
b9f7e36c 8498 {
22eed1e6
APB
8499 tree decl, wfl = TREE_OPERAND (node, 0);
8500 int in_this = CALL_THIS_CONSTRUCTOR_P (node);
8501
c877974e 8502 node = patch_method_invocation (node, NULL_TREE,
89e09b9a 8503 NULL_TREE, 0, &decl);
c877974e
APB
8504 if (node == error_mark_node)
8505 return error_mark_node;
8506
8507 check_thrown_exceptions (EXPR_WFL_LINECOL (node), decl);
8508 /* If we call this(...), register signature and positions */
8509 if (in_this)
8510 DECL_CONSTRUCTOR_CALLS (current_function_decl) =
8511 tree_cons (wfl, decl,
8512 DECL_CONSTRUCTOR_CALLS (current_function_decl));
de4c7b02 8513 CAN_COMPLETE_NORMALLY (node) = 1;
dc0b3eff 8514 return force_evaluation_order (node);
b9f7e36c 8515 }
e04a16fb
AG
8516
8517 case MODIFY_EXPR:
8518 /* Save potential wfls */
8519 wfl_op1 = TREE_OPERAND (node, 0);
cd9643f7
PB
8520 TREE_OPERAND (node, 0) = nn = java_complete_lhs (wfl_op1);
8521 if (MODIFY_EXPR_FROM_INITIALIZATION_P (node)
8522 && TREE_CODE (nn) == VAR_DECL && TREE_STATIC (nn)
8523 && DECL_INITIAL (nn) != NULL_TREE)
8524 {
100f7cd8
APB
8525 tree value;
8526
8527 push_obstacks (&permanent_obstack, &permanent_obstack);
8528 value = fold_constant_for_init (nn, nn);
8529 pop_obstacks ();
cd9643f7
PB
8530 if (value != NULL_TREE)
8531 {
8532 tree type = TREE_TYPE (value);
8533 if (JPRIMITIVE_TYPE_P (type) || type == string_ptr_type_node)
8534 return empty_stmt_node;
8535 }
8536 DECL_INITIAL (nn) = NULL_TREE;
8537 }
e04a16fb 8538 wfl_op2 = TREE_OPERAND (node, 1);
cd9643f7 8539
e04a16fb
AG
8540 if (TREE_OPERAND (node, 0) == error_mark_node)
8541 return error_mark_node;
8542
5cbdba64
APB
8543 flag = COMPOUND_ASSIGN_P (wfl_op2);
8544 if (flag)
e04a16fb 8545 {
2aa11e97 8546 tree lvalue = java_stabilize_reference (TREE_OPERAND (node, 0));
e04a16fb
AG
8547
8548 /* Hand stablize the lhs on both places */
e04a16fb 8549 TREE_OPERAND (node, 0) = lvalue;
5cbdba64
APB
8550 TREE_OPERAND (TREE_OPERAND (node, 1), 0) =
8551 (flag_emit_class_files ? lvalue : save_expr (lvalue));
2aa11e97 8552
5cbdba64 8553 /* 15.25.2.a: Left hand is not an array access. FIXME */
2aa11e97
APB
8554 /* Now complete the RHS. We write it back later on. */
8555 nn = java_complete_tree (TREE_OPERAND (node, 1));
8556
642f15d1
APB
8557 if ((cn = patch_string (nn)))
8558 nn = cn;
8559
2aa11e97
APB
8560 /* The last part of the rewrite for E1 op= E2 is to have
8561 E1 = (T)(E1 op E2), with T being the type of E1. */
642f15d1
APB
8562 nn = java_complete_tree (build_cast (EXPR_WFL_LINECOL (wfl_op2),
8563 TREE_TYPE (lvalue), nn));
5cbdba64
APB
8564
8565 /* 15.25.2.b: Left hand is an array access. FIXME */
e04a16fb
AG
8566 }
8567
f8976021
APB
8568 /* If we're about to patch a NEW_ARRAY_INIT, we call a special
8569 function to complete this RHS */
2aa11e97 8570 else if (TREE_CODE (wfl_op2) == NEW_ARRAY_INIT)
fdec99c6 8571 nn = patch_new_array_init (TREE_TYPE (TREE_OPERAND (node, 0)),
f8976021 8572 TREE_OPERAND (node, 1));
2aa11e97 8573 /* Otherwise we simply complete the RHS */
f8976021
APB
8574 else
8575 nn = java_complete_tree (TREE_OPERAND (node, 1));
8576
e04a16fb 8577 if (nn == error_mark_node)
c0d87ff6 8578 return error_mark_node;
2aa11e97
APB
8579
8580 /* Write back the RHS as we evaluated it. */
e04a16fb 8581 TREE_OPERAND (node, 1) = nn;
b67d701b
PB
8582
8583 /* In case we're handling = with a String as a RHS, we need to
8584 produce a String out of the RHS (it might still be a
8585 STRING_CST or a StringBuffer at this stage */
8586 if ((nn = patch_string (TREE_OPERAND (node, 1))))
8587 TREE_OPERAND (node, 1) = nn;
15fdcfe9 8588 node = patch_assignment (node, wfl_op1, wfl_op2);
5cbdba64
APB
8589 /* Reorganize the tree if necessary. */
8590 if (flag && (!JREFERENCE_TYPE_P (TREE_TYPE (node))
8591 || JSTRING_P (TREE_TYPE (node))))
8592 node = java_refold (node);
15fdcfe9
PB
8593 CAN_COMPLETE_NORMALLY (node) = 1;
8594 return node;
e04a16fb
AG
8595
8596 case MULT_EXPR:
8597 case PLUS_EXPR:
8598 case MINUS_EXPR:
8599 case LSHIFT_EXPR:
8600 case RSHIFT_EXPR:
8601 case URSHIFT_EXPR:
8602 case BIT_AND_EXPR:
8603 case BIT_XOR_EXPR:
8604 case BIT_IOR_EXPR:
8605 case TRUNC_MOD_EXPR:
8606 case RDIV_EXPR:
8607 case TRUTH_ANDIF_EXPR:
8608 case TRUTH_ORIF_EXPR:
8609 case EQ_EXPR:
8610 case NE_EXPR:
8611 case GT_EXPR:
8612 case GE_EXPR:
8613 case LT_EXPR:
8614 case LE_EXPR:
8615 /* Operands 0 and 1 are WFL in certain cases only. patch_binop
8616 knows how to handle those cases. */
8617 wfl_op1 = TREE_OPERAND (node, 0);
8618 wfl_op2 = TREE_OPERAND (node, 1);
b67d701b 8619
15fdcfe9 8620 CAN_COMPLETE_NORMALLY (node) = 1;
b67d701b
PB
8621 /* Don't complete string nodes if dealing with the PLUS operand. */
8622 if (TREE_CODE (node) != PLUS_EXPR || !JSTRING_P (wfl_op1))
2aa11e97
APB
8623 {
8624 nn = java_complete_tree (wfl_op1);
8625 if (nn == error_mark_node)
8626 return error_mark_node;
8627 if ((cn = patch_string (nn)))
8628 nn = cn;
8629 TREE_OPERAND (node, 0) = nn;
8630 }
b67d701b 8631 if (TREE_CODE (node) != PLUS_EXPR || !JSTRING_P (wfl_op2))
2aa11e97
APB
8632 {
8633 nn = java_complete_tree (wfl_op2);
8634 if (nn == error_mark_node)
8635 return error_mark_node;
8636 if ((cn = patch_string (nn)))
8637 nn = cn;
8638 TREE_OPERAND (node, 1) = nn;
8639 }
dc0b3eff 8640 return force_evaluation_order (patch_binop (node, wfl_op1, wfl_op2));
e04a16fb 8641
5e942c50
APB
8642 case INSTANCEOF_EXPR:
8643 wfl_op1 = TREE_OPERAND (node, 0);
8644 COMPLETE_CHECK_OP_0 (node);
ce6e9147
APB
8645 if (flag_emit_xref)
8646 {
8647 TREE_TYPE (node) = boolean_type_node;
8648 return node;
8649 }
5e942c50
APB
8650 return patch_binop (node, wfl_op1, TREE_OPERAND (node, 1));
8651
b67d701b 8652 case UNARY_PLUS_EXPR:
e04a16fb
AG
8653 case NEGATE_EXPR:
8654 case TRUTH_NOT_EXPR:
8655 case BIT_NOT_EXPR:
8656 case PREDECREMENT_EXPR:
8657 case PREINCREMENT_EXPR:
8658 case POSTDECREMENT_EXPR:
8659 case POSTINCREMENT_EXPR:
8660 case CONVERT_EXPR:
8661 /* There are cases were wfl_op1 is a WFL. patch_unaryop knows
8662 how to handle those cases. */
8663 wfl_op1 = TREE_OPERAND (node, 0);
15fdcfe9 8664 CAN_COMPLETE_NORMALLY (node) = 1;
e04a16fb
AG
8665 TREE_OPERAND (node, 0) = java_complete_tree (wfl_op1);
8666 if (TREE_OPERAND (node, 0) == error_mark_node)
8667 return error_mark_node;
4a5f66c3
APB
8668 node = patch_unaryop (node, wfl_op1);
8669 CAN_COMPLETE_NORMALLY (node) = 1;
8670 break;
e04a16fb
AG
8671
8672 case ARRAY_REF:
8673 /* There are cases were wfl_op1 is a WFL. patch_array_ref knows
8674 how to handle those cases. */
8675 wfl_op1 = TREE_OPERAND (node, 0);
8676 TREE_OPERAND (node, 0) = java_complete_tree (wfl_op1);
8677 if (TREE_OPERAND (node, 0) == error_mark_node)
8678 return error_mark_node;
7f1d4866 8679 if (!flag_emit_class_files && !flag_emit_xref)
b67d701b 8680 TREE_OPERAND (node, 0) = save_expr (TREE_OPERAND (node, 0));
e04a16fb
AG
8681 /* The same applies to wfl_op2 */
8682 wfl_op2 = TREE_OPERAND (node, 1);
8683 TREE_OPERAND (node, 1) = java_complete_tree (wfl_op2);
8684 if (TREE_OPERAND (node, 1) == error_mark_node)
8685 return error_mark_node;
7f1d4866 8686 if (!flag_emit_class_files && !flag_emit_xref)
22eed1e6 8687 TREE_OPERAND (node, 1) = save_expr (TREE_OPERAND (node, 1));
939d7216 8688 return patch_array_ref (node);
e04a16fb 8689
63a212ed
PB
8690 case RECORD_TYPE:
8691 return node;;
8692
8693 case COMPONENT_REF:
8694 /* The first step in the re-write of qualified name handling. FIXME.
8695 So far, this is only to support PRIMTYPE.class -> PRIMCLASS.TYPE. */
9bbc7d9f 8696 TREE_OPERAND (node, 0) = java_complete_tree (TREE_OPERAND (node, 0));
63a212ed
PB
8697 if (TREE_CODE (TREE_OPERAND (node, 0)) == RECORD_TYPE)
8698 {
8699 tree name = TREE_OPERAND (node, 1);
8700 tree field = lookup_field_wrapper (TREE_OPERAND (node, 0), name);
8701 if (field == NULL_TREE)
8702 {
8703 error ("missing static field `%s'", IDENTIFIER_POINTER (name));
8704 return error_mark_node;
8705 }
8706 if (! FIELD_STATIC (field))
8707 {
8708 error ("not a static field `%s'", IDENTIFIER_POINTER (name));
8709 return error_mark_node;
8710 }
8711 return field;
8712 }
8713 else
8714 fatal ("unimplemented java_complete_tree for COMPONENT_REF");
9bbc7d9f 8715 break;
9bbc7d9f 8716
b67d701b 8717 case THIS_EXPR:
e04a16fb
AG
8718 /* Can't use THIS in a static environment */
8719 if (!current_this)
8720 {
8721 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
8722 parse_error_context (wfl_operator, "Keyword `this' used outside "
8723 "allowed context");
8724 TREE_TYPE (node) = error_mark_node;
8725 return error_mark_node;
8726 }
22eed1e6
APB
8727 if (ctxp->explicit_constructor_p)
8728 {
8729 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
8730 parse_error_context
8731 (wfl_operator, "Can't reference `this' or `super' before the "
8732 "superclass constructor has been called");
8733 TREE_TYPE (node) = error_mark_node;
8734 return error_mark_node;
8735 }
e04a16fb
AG
8736 return current_this;
8737
e04a16fb 8738 default:
15fdcfe9 8739 CAN_COMPLETE_NORMALLY (node) = 1;
b67d701b
PB
8740 /* Ok: may be we have a STRING_CST or a crafted `StringBuffer'
8741 and it's time to turn it into the appropriate String object
8742 */
8743 if ((node = patch_string (node)))
8744 return node;
e04a16fb
AG
8745 fatal ("No case for tree code `%s' - java_complete_tree\n",
8746 tree_code_name [TREE_CODE (node)]);
8747 }
8748 return node;
8749}
8750
8751/* Complete function call's argument. Return a non zero value is an
8752 error was found. */
8753
8754static int
8755complete_function_arguments (node)
8756 tree node;
8757{
8758 int flag = 0;
8759 tree cn;
8760
f63991a8 8761 ctxp->explicit_constructor_p += (CALL_EXPLICIT_CONSTRUCTOR_P (node) ? 1 : 0);
e04a16fb
AG
8762 for (cn = TREE_OPERAND (node, 1); cn; cn = TREE_CHAIN (cn))
8763 {
b67d701b 8764 tree wfl = TREE_VALUE (cn), parm, temp;
e04a16fb
AG
8765 parm = java_complete_tree (wfl);
8766 if (parm == error_mark_node)
8767 {
8768 flag = 1;
8769 continue;
8770 }
b67d701b
PB
8771 /* If have a string literal that we haven't transformed yet or a
8772 crafted string buffer, as a result of use of the the String
8773 `+' operator. Build `parm.toString()' and expand it. */
8774 if ((temp = patch_string (parm)))
b9f7e36c 8775 parm = temp;
5e942c50
APB
8776 /* Inline PRIMTYPE.TYPE read access */
8777 parm = maybe_build_primttype_type_ref (parm, wfl);
b9f7e36c 8778
5e942c50 8779 TREE_VALUE (cn) = parm;
e04a16fb 8780 }
f63991a8 8781 ctxp->explicit_constructor_p -= (CALL_EXPLICIT_CONSTRUCTOR_P (node) ? 1 : 0);
e04a16fb
AG
8782 return flag;
8783}
8784
8785/* Sometimes (for loops and variable initialized during their
8786 declaration), we want to wrap a statement around a WFL and turn it
8787 debugable. */
8788
8789static tree
8790build_debugable_stmt (location, stmt)
8791 int location;
8792 tree stmt;
8793{
8794 if (TREE_CODE (stmt) != EXPR_WITH_FILE_LOCATION)
8795 {
8796 stmt = build_expr_wfl (stmt, input_filename, 0, 0);
8797 EXPR_WFL_LINECOL (stmt) = location;
8798 }
8799 JAVA_MAYBE_GENERATE_DEBUG_INFO (stmt);
8800 return stmt;
8801}
8802
8803static tree
8804build_expr_block (body, decls)
8805 tree body, decls;
8806{
8807 tree node = make_node (BLOCK);
8808 BLOCK_EXPR_DECLS (node) = decls;
b67d701b 8809 BLOCK_EXPR_BODY (node) = body;
e04a16fb
AG
8810 if (body)
8811 TREE_TYPE (node) = TREE_TYPE (body);
8812 TREE_SIDE_EFFECTS (node) = 1;
8813 return node;
8814}
8815
b67d701b
PB
8816/* Create a new function block and link it approriately to current
8817 function block chain */
e04a16fb
AG
8818
8819static tree
8820enter_block ()
8821{
b67d701b
PB
8822 return (enter_a_block (build_expr_block (NULL_TREE, NULL_TREE)));
8823}
8824
8825/* Link block B supercontext to the previous block. The current
8826 function DECL is used as supercontext when enter_a_block is called
8827 for the first time for a given function. The current function body
8828 (DECL_FUNCTION_BODY) is set to be block B. */
8829
8830static tree
8831enter_a_block (b)
8832 tree b;
8833{
e04a16fb
AG
8834 tree fndecl = current_function_decl;
8835
f099f336
APB
8836 if (!fndecl) {
8837 BLOCK_SUPERCONTEXT (b) = current_static_block;
8838 current_static_block = b;
8839 }
8840
8841 else if (!DECL_FUNCTION_BODY (fndecl))
e04a16fb
AG
8842 {
8843 BLOCK_SUPERCONTEXT (b) = fndecl;
8844 DECL_FUNCTION_BODY (fndecl) = b;
8845 }
8846 else
8847 {
8848 BLOCK_SUPERCONTEXT (b) = DECL_FUNCTION_BODY (fndecl);
8849 DECL_FUNCTION_BODY (fndecl) = b;
8850 }
8851 return b;
8852}
8853
8854/* Exit a block by changing the current function body
8855 (DECL_FUNCTION_BODY) to the current block super context, only if
8856 the block being exited isn't the method's top level one. */
8857
8858static tree
8859exit_block ()
8860{
f099f336
APB
8861 tree b;
8862 if (current_function_decl)
8863 {
8864 b = DECL_FUNCTION_BODY (current_function_decl);
8865 if (BLOCK_SUPERCONTEXT (b) != current_function_decl)
8866 DECL_FUNCTION_BODY (current_function_decl) = BLOCK_SUPERCONTEXT (b);
8867 }
8868 else
8869 {
8870 b = current_static_block;
e04a16fb 8871
f099f336
APB
8872 if (BLOCK_SUPERCONTEXT (b))
8873 current_static_block = BLOCK_SUPERCONTEXT (b);
8874 }
e04a16fb
AG
8875 return b;
8876}
8877
8878/* Lookup for NAME in the nested function's blocks, all the way up to
8879 the current toplevel one. It complies with Java's local variable
8880 scoping rules. */
8881
8882static tree
8883lookup_name_in_blocks (name)
8884 tree name;
8885{
f099f336 8886 tree b = GET_CURRENT_BLOCK (current_function_decl);
e04a16fb
AG
8887
8888 while (b != current_function_decl)
8889 {
8890 tree current;
8891
8892 /* Paranoid sanity check. To be removed */
8893 if (TREE_CODE (b) != BLOCK)
8894 fatal ("non block expr function body - lookup_name_in_blocks");
8895
8896 for (current = BLOCK_EXPR_DECLS (b); current;
8897 current = TREE_CHAIN (current))
8898 if (DECL_NAME (current) == name)
8899 return current;
8900 b = BLOCK_SUPERCONTEXT (b);
8901 }
8902 return NULL_TREE;
8903}
8904
8905static void
8906maybe_absorb_scoping_blocks ()
8907{
f099f336 8908 while (BLOCK_EXPR_ORIGIN (GET_CURRENT_BLOCK (current_function_decl)))
e04a16fb
AG
8909 {
8910 tree b = exit_block ();
8911 java_method_add_stmt (current_function_decl, b);
8912 SOURCE_FRONTEND_DEBUG (("Absorbing scoping block at line %d", lineno));
8913 }
8914}
8915
8916\f
8917/* This section of the source is reserved to build_* functions that
8918 are building incomplete tree nodes and the patch_* functions that
8919 are completing them. */
8920
9bbc7d9f 8921/* Build a super() constructor invocation. Returns empty_stmt_node if
22eed1e6
APB
8922 we're currently dealing with the class java.lang.Object. */
8923
8924static tree
8925build_super_invocation ()
8926{
8927 if (current_class == object_type_node)
9bbc7d9f 8928 return empty_stmt_node;
22eed1e6
APB
8929 else
8930 {
9ee9b555 8931 tree super_wfl = build_wfl_node (super_identifier_node);
22eed1e6
APB
8932 return build_method_invocation (super_wfl, NULL_TREE);
8933 }
8934}
8935
8936/* Build a SUPER/THIS qualified method invocation. */
8937
8938static tree
8939build_this_super_qualified_invocation (use_this, name, args, lloc, rloc)
8940 int use_this;
8941 tree name, args;
8942 int lloc, rloc;
8943
8944{
8945 tree invok;
8946 tree wfl =
9ee9b555 8947 build_wfl_node (use_this ? this_identifier_node : super_identifier_node);
22eed1e6
APB
8948 EXPR_WFL_LINECOL (wfl) = lloc;
8949 invok = build_method_invocation (name, args);
8950 return make_qualified_primary (wfl, invok, rloc);
8951}
8952
b67d701b 8953/* Build an incomplete CALL_EXPR node. */
e04a16fb
AG
8954
8955static tree
8956build_method_invocation (name, args)
8957 tree name;
8958 tree args;
8959{
8960 tree call = build (CALL_EXPR, NULL_TREE, name, args, NULL_TREE);
8961 TREE_SIDE_EFFECTS (call) = 1;
b67d701b
PB
8962 EXPR_WFL_LINECOL (call) = EXPR_WFL_LINECOL (name);
8963 return call;
8964}
8965
8966/* Build an incomplete new xxx(...) node. */
8967
8968static tree
8969build_new_invocation (name, args)
8970 tree name, args;
8971{
8972 tree call = build (NEW_CLASS_EXPR, NULL_TREE, name, args, NULL_TREE);
8973 TREE_SIDE_EFFECTS (call) = 1;
e04a16fb
AG
8974 EXPR_WFL_LINECOL (call) = EXPR_WFL_LINECOL (name);
8975 return call;
8976}
8977
8978/* Build an incomplete assignment expression. */
8979
8980static tree
8981build_assignment (op, op_location, lhs, rhs)
8982 int op, op_location;
8983 tree lhs, rhs;
8984{
8985 tree assignment;
8986 /* Build the corresponding binop if we deal with a Compound
8987 Assignment operator. Mark the binop sub-tree as part of a
8988 Compound Assignment expression */
8989 if (op != ASSIGN_TK)
8990 {
8991 rhs = build_binop (BINOP_LOOKUP (op), op_location, lhs, rhs);
8992 COMPOUND_ASSIGN_P (rhs) = 1;
8993 }
8994 assignment = build (MODIFY_EXPR, NULL_TREE, lhs, rhs);
8995 TREE_SIDE_EFFECTS (assignment) = 1;
8996 EXPR_WFL_LINECOL (assignment) = op_location;
8997 return assignment;
8998}
8999
9000/* Print an INTEGER_CST node in a static buffer, and return the buffer. */
9001
15fdcfe9 9002char *
e04a16fb
AG
9003print_int_node (node)
9004 tree node;
9005{
9006 static char buffer [80];
9007 if (TREE_CONSTANT_OVERFLOW (node))
9008 sprintf (buffer, "<overflow>");
9009
9010 if (TREE_INT_CST_HIGH (node) == 0)
9011 sprintf (buffer, HOST_WIDE_INT_PRINT_UNSIGNED,
9012 TREE_INT_CST_LOW (node));
9013 else if (TREE_INT_CST_HIGH (node) == -1
9014 && TREE_INT_CST_LOW (node) != 0)
9015 {
9016 buffer [0] = '-';
9017 sprintf (&buffer [1], HOST_WIDE_INT_PRINT_UNSIGNED,
9018 -TREE_INT_CST_LOW (node));
9019 }
9020 else
9021 sprintf (buffer, HOST_WIDE_INT_PRINT_DOUBLE_HEX,
9022 TREE_INT_CST_HIGH (node), TREE_INT_CST_LOW (node));
9023
9024 return buffer;
9025}
9026
7f1d4866
APB
9027/* Return 1 if an assignment to a FINAL is attempted in a non suitable
9028 context. */
5e942c50
APB
9029
9030static int
9031check_final_assignment (lvalue, wfl)
9032 tree lvalue, wfl;
9033{
7f1d4866
APB
9034 if (JDECL_P (lvalue)
9035 && FIELD_FINAL (lvalue) && !IS_CLINIT (current_function_decl))
5e942c50
APB
9036 {
9037 parse_error_context
9038 (wfl, "Can't assign a value to the final variable `%s'",
9039 IDENTIFIER_POINTER (EXPR_WFL_NODE (wfl)));
9040 return 1;
9041 }
9042 return 0;
9043}
9044
9045/* Inline references to java.lang.PRIMTYPE.TYPE when accessed in
9046 read. This is needed to avoid circularities in the implementation
9047 of these fields in libjava. */
9048
9049static tree
9050maybe_build_primttype_type_ref (rhs, wfl)
9051 tree rhs, wfl;
9052{
9053 tree to_return = NULL_TREE;
9054 tree rhs_type = TREE_TYPE (rhs);
9055 if (TREE_CODE (rhs) == COMPOUND_EXPR)
9056 {
9057 tree n = TREE_OPERAND (rhs, 1);
9058 if (TREE_CODE (n) == VAR_DECL
9059 && DECL_NAME (n) == TYPE_identifier_node
9060 && rhs_type == class_ptr_type)
9061 {
49f48c71 9062 const char *self_name = IDENTIFIER_POINTER (EXPR_WFL_NODE (wfl));
5e942c50
APB
9063 if (!strncmp (self_name, "java.lang.", 10))
9064 to_return = build_primtype_type_ref (self_name);
9065 }
9066 }
9067 return (to_return ? to_return : rhs );
9068}
9069
e04a16fb
AG
9070/* 15.25 Assignment operators. */
9071
9072static tree
9073patch_assignment (node, wfl_op1, wfl_op2)
9074 tree node;
9075 tree wfl_op1;
9076 tree wfl_op2;
9077{
0a2138e2 9078 tree rhs = TREE_OPERAND (node, 1);
5e942c50 9079 tree lvalue = TREE_OPERAND (node, 0), llvalue;
cd531a2e 9080 tree lhs_type = NULL_TREE, rhs_type, new_rhs = NULL_TREE;
e04a16fb
AG
9081 int error_found = 0;
9082 int lvalue_from_array = 0;
9083
9084 /* Can't assign to a final. */
5e942c50
APB
9085 if (check_final_assignment (lvalue, wfl_op1))
9086 error_found = 1;
e04a16fb
AG
9087
9088 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
9089
9090 /* Lhs can be a named variable */
34f4db93 9091 if (JDECL_P (lvalue))
e04a16fb 9092 {
e04a16fb
AG
9093 lhs_type = TREE_TYPE (lvalue);
9094 }
9095 /* Or Lhs can be a array acccess. Should that be lvalue ? FIXME +
9096 comment on reason why */
9097 else if (TREE_CODE (wfl_op1) == ARRAY_REF)
9098 {
9099 lhs_type = TREE_TYPE (lvalue);
9100 lvalue_from_array = 1;
9101 }
9102 /* Or a field access */
9103 else if (TREE_CODE (lvalue) == COMPONENT_REF)
9104 lhs_type = TREE_TYPE (lvalue);
9105 /* Or a function return slot */
9106 else if (TREE_CODE (lvalue) == RESULT_DECL)
9107 lhs_type = TREE_TYPE (lvalue);
5e942c50
APB
9108 /* Otherwise, we might want to try to write into an optimized static
9109 final, this is an of a different nature, reported further on. */
9110 else if (TREE_CODE (wfl_op1) == EXPR_WITH_FILE_LOCATION
1504b2b4 9111 && resolve_expression_name (wfl_op1, &llvalue))
5e942c50 9112 {
1504b2b4
APB
9113 if (check_final_assignment (llvalue, wfl_op1))
9114 {
9115 /* What we should do instead is resetting the all the flags
9116 previously set, exchange lvalue for llvalue and continue. */
9117 error_found = 1;
9118 return error_mark_node;
9119 }
9120 else
9121 lhs_type = TREE_TYPE (lvalue);
5e942c50
APB
9122 }
9123 else
e04a16fb
AG
9124 {
9125 parse_error_context (wfl_op1, "Invalid left hand side of assignment");
9126 error_found = 1;
9127 }
9128
9129 rhs_type = TREE_TYPE (rhs);
b67d701b 9130 /* 5.1 Try the assignment conversion for builtin type. */
0a2138e2 9131 new_rhs = try_builtin_assignconv (wfl_op1, lhs_type, rhs);
e04a16fb 9132
b67d701b 9133 /* 5.2 If it failed, try a reference conversion */
0a2138e2 9134 if (!new_rhs && (new_rhs = try_reference_assignconv (lhs_type, rhs)))
b67d701b 9135 lhs_type = promote_type (rhs_type);
e04a16fb
AG
9136
9137 /* 15.25.2 If we have a compound assignment, convert RHS into the
9138 type of the LHS */
9139 else if (COMPOUND_ASSIGN_P (TREE_OPERAND (node, 1)))
9140 new_rhs = convert (lhs_type, rhs);
9141
9142 /* Explicit cast required. This is an error */
9143 if (!new_rhs)
9144 {
c2e3db92
KG
9145 char *t1 = xstrdup (lang_printable_name (TREE_TYPE (rhs), 0));
9146 char *t2 = xstrdup (lang_printable_name (lhs_type, 0));
e04a16fb
AG
9147 tree wfl;
9148 char operation [32]; /* Max size known */
9149
9150 /* If the assignment is part of a declaration, we use the WFL of
9151 the declared variable to point out the error and call it a
9152 declaration problem. If the assignment is a genuine =
9153 operator, we call is a operator `=' problem, otherwise we
9154 call it an assignment problem. In both of these last cases,
9155 we use the WFL of the operator to indicate the error. */
9156
9157 if (MODIFY_EXPR_FROM_INITIALIZATION_P (node))
9158 {
9159 wfl = wfl_op1;
9160 strcpy (operation, "declaration");
9161 }
9162 else
9163 {
9164 wfl = wfl_operator;
9165 if (COMPOUND_ASSIGN_P (TREE_OPERAND (node, 1)))
9166 strcpy (operation, "assignment");
9167 else if (TREE_CODE (TREE_OPERAND (node, 0)) == RESULT_DECL)
9168 strcpy (operation, "`return'");
9169 else
9170 strcpy (operation, "`='");
9171 }
9172
1ebadc60
KG
9173 if (!valid_cast_to_p (rhs_type, lhs_type))
9174 parse_error_context (wfl, "Incompatible type for %s. "
9175 "Can't convert `%s' to `%s'",
9176 operation, t1, t2);
9177 else
9178 parse_error_context (wfl, "Incompatible type for %s. "
9179 "Explicit cast needed to convert `%s' to `%s'",
9180 operation, t1, t2);
e04a16fb
AG
9181 free (t1); free (t2);
9182 error_found = 1;
9183 }
9184
c877974e
APB
9185 /* Inline read access to java.lang.PRIMTYPE.TYPE */
9186 if (new_rhs)
9187 new_rhs = maybe_build_primttype_type_ref (new_rhs, wfl_op2);
5e942c50 9188
e04a16fb
AG
9189 if (error_found)
9190 return error_mark_node;
9191
2622b947
APB
9192 /* 10.10: Array Store Exception runtime check */
9193 if (!flag_emit_class_files
e8fc7396 9194 && !flag_emit_xref
2622b947 9195 && lvalue_from_array
afc390b1 9196 && JREFERENCE_TYPE_P (TYPE_ARRAY_ELEMENT (lhs_type)))
2622b947
APB
9197 {
9198 tree check;
9199 tree base = lvalue;
9200
9201 /* We need to retrieve the right argument for _Jv_CheckArrayStore */
9202 if (TREE_CODE (lvalue) == COMPOUND_EXPR)
9203 base = TREE_OPERAND (lvalue, 0);
9204 else
9205 {
9206 if (flag_bounds_check)
9207 base = TREE_OPERAND (TREE_OPERAND (TREE_OPERAND (base, 0), 1), 0);
9208 else
9209 base = TREE_OPERAND (TREE_OPERAND (base, 0), 0);
9210 }
9211
9212 /* Build the invocation of _Jv_CheckArrayStore */
dc4e6ccf 9213 new_rhs = save_expr (new_rhs);
2622b947
APB
9214 check = build (CALL_EXPR, void_type_node,
9215 build_address_of (soft_checkarraystore_node),
9216 tree_cons (NULL_TREE, base,
9217 build_tree_list (NULL_TREE, new_rhs)),
9218 NULL_TREE);
9219 TREE_SIDE_EFFECTS (check) = 1;
9220
9221 /* We have to decide on an insertion point */
9222 if (TREE_CODE (lvalue) == COMPOUND_EXPR)
9223 {
9224 tree t;
9225 if (flag_bounds_check)
9226 {
9227 t = TREE_OPERAND (TREE_OPERAND (TREE_OPERAND (lvalue, 1), 0), 0);
9228 TREE_OPERAND (TREE_OPERAND (TREE_OPERAND (lvalue, 1), 0), 0) =
9229 build (COMPOUND_EXPR, void_type_node, t, check);
9230 }
9231 else
9232 TREE_OPERAND (lvalue, 1) = build (COMPOUND_EXPR, lhs_type,
9233 check, TREE_OPERAND (lvalue, 1));
9234 }
9235 else
9236 {
9237 /* Make sure the bound check will happen before the store check */
9238 if (flag_bounds_check)
9239 TREE_OPERAND (TREE_OPERAND (lvalue, 0), 0) =
9240 build (COMPOUND_EXPR, void_type_node,
9241 TREE_OPERAND (TREE_OPERAND (lvalue, 0), 0), check);
9242 else
9243 lvalue = build (COMPOUND_EXPR, lhs_type, check, lvalue);
9244 }
9245 }
22eed1e6 9246
e04a16fb
AG
9247 TREE_OPERAND (node, 0) = lvalue;
9248 TREE_OPERAND (node, 1) = new_rhs;
9249 TREE_TYPE (node) = lhs_type;
9250 return node;
9251}
9252
b67d701b
PB
9253/* Check that type SOURCE can be cast into type DEST. If the cast
9254 can't occur at all, return 0 otherwise 1. This function is used to
9255 produce accurate error messages on the reasons why an assignment
9256 failed. */
e04a16fb 9257
b67d701b
PB
9258static tree
9259try_reference_assignconv (lhs_type, rhs)
9260 tree lhs_type, rhs;
e04a16fb 9261{
b67d701b
PB
9262 tree new_rhs = NULL_TREE;
9263 tree rhs_type = TREE_TYPE (rhs);
e04a16fb 9264
b67d701b
PB
9265 if (!JPRIMITIVE_TYPE_P (rhs_type) && JREFERENCE_TYPE_P (lhs_type))
9266 {
9267 /* `null' may be assigned to any reference type */
9268 if (rhs == null_pointer_node)
9269 new_rhs = null_pointer_node;
9270 /* Try the reference assignment conversion */
9271 else if (valid_ref_assignconv_cast_p (rhs_type, lhs_type, 0))
9272 new_rhs = rhs;
9273 /* This is a magic assignment that we process differently */
9274 else if (rhs == soft_exceptioninfo_call_node)
9275 new_rhs = rhs;
9276 }
9277 return new_rhs;
9278}
9279
9280/* Check that RHS can be converted into LHS_TYPE by the assignment
9281 conversion (5.2), for the cases of RHS being a builtin type. Return
9282 NULL_TREE if the conversion fails or if because RHS isn't of a
9283 builtin type. Return a converted RHS if the conversion is possible. */
9284
9285static tree
9286try_builtin_assignconv (wfl_op1, lhs_type, rhs)
9287 tree wfl_op1, lhs_type, rhs;
9288{
9289 tree new_rhs = NULL_TREE;
9290 tree rhs_type = TREE_TYPE (rhs);
9291
5e942c50
APB
9292 /* Zero accepted everywhere */
9293 if (TREE_CODE (rhs) == INTEGER_CST
9294 && TREE_INT_CST_HIGH (rhs) == 0 && TREE_INT_CST_LOW (rhs) == 0
9295 && JPRIMITIVE_TYPE_P (rhs_type))
9296 new_rhs = convert (lhs_type, rhs);
9297
b67d701b
PB
9298 /* 5.1.1 Try Identity Conversion,
9299 5.1.2 Try Widening Primitive Conversion */
5e942c50 9300 else if (valid_builtin_assignconv_identity_widening_p (lhs_type, rhs_type))
b67d701b
PB
9301 new_rhs = convert (lhs_type, rhs);
9302
9303 /* Try a narrowing primitive conversion (5.1.3):
9304 - expression is a constant expression of type int AND
9305 - variable is byte, short or char AND
9306 - The value of the expression is representable in the type of the
9307 variable */
9308 else if (rhs_type == int_type_node && TREE_CONSTANT (rhs)
9309 && (lhs_type == byte_type_node || lhs_type == char_type_node
9310 || lhs_type == short_type_node))
9311 {
9312 if (int_fits_type_p (rhs, lhs_type))
9313 new_rhs = convert (lhs_type, rhs);
9314 else if (wfl_op1) /* Might be called with a NULL */
9315 parse_warning_context
9316 (wfl_op1, "Constant expression `%s' to wide for narrowing "
9317 "primitive conversion to `%s'",
0a2138e2 9318 print_int_node (rhs), lang_printable_name (lhs_type, 0));
b67d701b
PB
9319 /* Reported a warning that will turn into an error further
9320 down, so we don't return */
9321 }
9322
9323 return new_rhs;
9324}
9325
9326/* Return 1 if RHS_TYPE can be converted to LHS_TYPE by identity
9327 conversion (5.1.1) or widening primitve conversion (5.1.2). Return
9328 0 is the conversion test fails. This implements parts the method
9329 invocation convertion (5.3). */
9330
9331static int
9332valid_builtin_assignconv_identity_widening_p (lhs_type, rhs_type)
9333 tree lhs_type, rhs_type;
9334{
acd663ee 9335 /* 5.1.1: This is the identity conversion part. */
5e942c50
APB
9336 if (lhs_type == rhs_type)
9337 return 1;
9338
acd663ee
APB
9339 /* Reject non primitive types */
9340 if (!JPRIMITIVE_TYPE_P (lhs_type) || !JPRIMITIVE_TYPE_P (rhs_type))
b67d701b
PB
9341 return 0;
9342
acd663ee
APB
9343 /* 5.1.2: widening primitive conversion. byte, even if it's smaller
9344 than a char can't be converted into a char. Short can't too, but
9345 the < test below takes care of that */
b67d701b
PB
9346 if (lhs_type == char_type_node && rhs_type == byte_type_node)
9347 return 0;
9348
5e942c50
APB
9349 /* Accept all promoted type here. Note, we can't use <= in the test
9350 below, because we still need to bounce out assignments of short
9351 to char and the likes */
9352 if (lhs_type == int_type_node
9353 && (rhs_type == promoted_byte_type_node
9354 || rhs_type == promoted_short_type_node
9355 || rhs_type == promoted_char_type_node
9356 || rhs_type == promoted_boolean_type_node))
9357 return 1;
9358
acd663ee
APB
9359 /* From here, an integral is widened if its precision is smaller
9360 than the precision of the LHS or if the LHS is a floating point
9361 type, or the RHS is a float and the RHS a double. */
9362 if ((JINTEGRAL_TYPE_P (rhs_type) && JINTEGRAL_TYPE_P (lhs_type)
9363 && (TYPE_PRECISION (rhs_type) < TYPE_PRECISION (lhs_type)))
9364 || (JINTEGRAL_TYPE_P (rhs_type) && JFLOAT_TYPE_P (lhs_type))
9365 || (rhs_type == float_type_node && lhs_type == double_type_node))
b67d701b
PB
9366 return 1;
9367
9368 return 0;
e04a16fb
AG
9369}
9370
9371/* Check that something of SOURCE type can be assigned or cast to
9372 something of DEST type at runtime. Return 1 if the operation is
9373 valid, 0 otherwise. If CAST is set to 1, we're treating the case
9374 were SOURCE is cast into DEST, which borrows a lot of the
9375 assignment check. */
9376
9377static int
9378valid_ref_assignconv_cast_p (source, dest, cast)
9379 tree source;
9380 tree dest;
9381 int cast;
9382{
09ed0f70
APB
9383 /* SOURCE or DEST might be null if not from a declared entity. */
9384 if (!source || !dest)
9385 return 0;
5e942c50
APB
9386 if (JNULLP_TYPE_P (source))
9387 return 1;
e04a16fb
AG
9388 if (TREE_CODE (source) == POINTER_TYPE)
9389 source = TREE_TYPE (source);
9390 if (TREE_CODE (dest) == POINTER_TYPE)
9391 dest = TREE_TYPE (dest);
9392 /* Case where SOURCE is a class type */
9393 if (TYPE_CLASS_P (source))
9394 {
9395 if (TYPE_CLASS_P (dest))
9396 return source == dest || inherits_from_p (source, dest)
0a2138e2 9397 || (cast && inherits_from_p (dest, source));
e04a16fb
AG
9398 if (TYPE_INTERFACE_P (dest))
9399 {
9400 /* If doing a cast and SOURCE is final, the operation is
9401 always correct a compile time (because even if SOURCE
9402 does not implement DEST, a subclass of SOURCE might). */
9403 if (cast && !CLASS_FINAL (TYPE_NAME (source)))
9404 return 1;
9405 /* Otherwise, SOURCE must implement DEST */
9406 return interface_of_p (dest, source);
9407 }
9408 /* DEST is an array, cast permited if SOURCE is of Object type */
9409 return (cast && source == object_type_node ? 1 : 0);
9410 }
9411 if (TYPE_INTERFACE_P (source))
9412 {
9413 if (TYPE_CLASS_P (dest))
9414 {
9415 /* If not casting, DEST must be the Object type */
9416 if (!cast)
9417 return dest == object_type_node;
9418 /* We're doing a cast. The cast is always valid is class
9419 DEST is not final, otherwise, DEST must implement SOURCE */
b67d701b 9420 else if (!CLASS_FINAL (TYPE_NAME (dest)))
e04a16fb
AG
9421 return 1;
9422 else
9423 return interface_of_p (source, dest);
9424 }
9425 if (TYPE_INTERFACE_P (dest))
9426 {
9427 /* If doing a cast, then if SOURCE and DEST contain method
9428 with the same signature but different return type, then
9429 this is a (compile time) error */
9430 if (cast)
9431 {
9432 tree method_source, method_dest;
9433 tree source_type;
0a2138e2 9434 tree source_sig;
e04a16fb
AG
9435 tree source_name;
9436 for (method_source = TYPE_METHODS (source); method_source;
9437 method_source = TREE_CHAIN (method_source))
9438 {
9439 source_sig =
9440 build_java_argument_signature (TREE_TYPE (method_source));
9441 source_type = TREE_TYPE (TREE_TYPE (method_source));
9442 source_name = DECL_NAME (method_source);
9443 for (method_dest = TYPE_METHODS (dest);
9444 method_dest; method_dest = TREE_CHAIN (method_dest))
9445 if (source_sig ==
9446 build_java_argument_signature (TREE_TYPE (method_dest))
9447 && source_name == DECL_NAME (method_dest)
9448 && source_type != TREE_TYPE (TREE_TYPE (method_dest)))
9449 return 0;
9450 }
9451 return 1;
9452 }
9453 else
9454 return source == dest || interface_of_p (dest, source);
9455 }
9456 else /* Array */
93024893
APB
9457 return (cast ?
9458 (DECL_NAME (TYPE_NAME (source)) == java_lang_cloneable) : 0);
e04a16fb
AG
9459 }
9460 if (TYPE_ARRAY_P (source))
9461 {
9462 if (TYPE_CLASS_P (dest))
9463 return dest == object_type_node;
09ed0f70
APB
9464 /* Can't cast an array to an interface unless the interface is
9465 java.lang.Cloneable */
e04a16fb 9466 if (TYPE_INTERFACE_P (dest))
09ed0f70 9467 return (DECL_NAME (TYPE_NAME (dest)) == java_lang_cloneable ? 1 : 0);
e04a16fb
AG
9468 else /* Arrays */
9469 {
9470 tree source_element_type = TYPE_ARRAY_ELEMENT (source);
9471 tree dest_element_type = TYPE_ARRAY_ELEMENT (dest);
9472
b9f7e36c
APB
9473 /* In case of severe errors, they turn out null */
9474 if (!dest_element_type || !source_element_type)
9475 return 0;
e04a16fb
AG
9476 if (source_element_type == dest_element_type)
9477 return 1;
9478 return valid_ref_assignconv_cast_p (source_element_type,
9479 dest_element_type, cast);
9480 }
9481 return 0;
9482 }
9483 return 0;
9484}
9485
b67d701b
PB
9486static int
9487valid_cast_to_p (source, dest)
9488 tree source;
9489 tree dest;
9490{
9491 if (TREE_CODE (source) == POINTER_TYPE)
9492 source = TREE_TYPE (source);
9493 if (TREE_CODE (dest) == POINTER_TYPE)
9494 dest = TREE_TYPE (dest);
9495
9496 if (TREE_CODE (source) == RECORD_TYPE && TREE_CODE (dest) == RECORD_TYPE)
9497 return valid_ref_assignconv_cast_p (source, dest, 1);
9498
9499 else if (JNUMERIC_TYPE_P (source) && JNUMERIC_TYPE_P (dest))
9500 return 1;
9501
9502 return 0;
9503}
9504
9505/* Method invocation conversion test. Return 1 if type SOURCE can be
9506 converted to type DEST through the methond invocation conversion
9507 process (5.3) */
9508
15fdcfe9
PB
9509static tree
9510do_unary_numeric_promotion (arg)
9511 tree arg;
9512{
9513 tree type = TREE_TYPE (arg);
9514 if (TREE_CODE (type) == INTEGER_TYPE ? TYPE_PRECISION (type) < 32
9515 : TREE_CODE (type) == CHAR_TYPE)
9516 arg = convert (int_type_node, arg);
9517 return arg;
9518}
9519
acd663ee
APB
9520/* Return a non zero value if SOURCE can be converted into DEST using
9521 the method invocation conversion rule (5.3). */
b67d701b
PB
9522static int
9523valid_method_invocation_conversion_p (dest, source)
9524 tree dest, source;
9525{
e3884b71 9526 return ((JPRIMITIVE_TYPE_P (source) && JPRIMITIVE_TYPE_P (dest)
acd663ee
APB
9527 && valid_builtin_assignconv_identity_widening_p (dest, source))
9528 || ((JREFERENCE_TYPE_P (source) || JNULLP_TYPE_P (source))
9529 && (JREFERENCE_TYPE_P (dest) || JNULLP_TYPE_P (dest))
9530 && valid_ref_assignconv_cast_p (source, dest, 0)));
b67d701b
PB
9531}
9532
e04a16fb
AG
9533/* Build an incomplete binop expression. */
9534
9535static tree
9536build_binop (op, op_location, op1, op2)
9537 enum tree_code op;
9538 int op_location;
9539 tree op1, op2;
9540{
5e942c50 9541 tree binop = build (op, NULL_TREE, op1, op2);
e04a16fb
AG
9542 TREE_SIDE_EFFECTS (binop) = 1;
9543 /* Store the location of the operator, for better error report. The
9544 string of the operator will be rebuild based on the OP value. */
9545 EXPR_WFL_LINECOL (binop) = op_location;
9546 return binop;
9547}
9548
9549/* Build the string of the operator retained by NODE. If NODE is part
9550 of a compound expression, add an '=' at the end of the string. This
9551 function is called when an error needs to be reported on an
9552 operator. The string is returned as a pointer to a static character
9553 buffer. */
9554
9555static char *
9556operator_string (node)
9557 tree node;
9558{
9559#define BUILD_OPERATOR_STRING(S) \
9560 { \
9561 sprintf (buffer, "%s%s", S, (COMPOUND_ASSIGN_P (node) ? "=" : "")); \
9562 return buffer; \
9563 }
9564
9565 static char buffer [10];
9566 switch (TREE_CODE (node))
9567 {
9568 case MULT_EXPR: BUILD_OPERATOR_STRING ("*");
9569 case RDIV_EXPR: BUILD_OPERATOR_STRING ("/");
9570 case TRUNC_MOD_EXPR: BUILD_OPERATOR_STRING ("%");
9571 case PLUS_EXPR: BUILD_OPERATOR_STRING ("+");
9572 case MINUS_EXPR: BUILD_OPERATOR_STRING ("-");
9573 case LSHIFT_EXPR: BUILD_OPERATOR_STRING ("<<");
9574 case RSHIFT_EXPR: BUILD_OPERATOR_STRING (">>");
9575 case URSHIFT_EXPR: BUILD_OPERATOR_STRING (">>>");
9576 case BIT_AND_EXPR: BUILD_OPERATOR_STRING ("&");
9577 case BIT_XOR_EXPR: BUILD_OPERATOR_STRING ("^");
9578 case BIT_IOR_EXPR: BUILD_OPERATOR_STRING ("|");
9579 case TRUTH_ANDIF_EXPR: BUILD_OPERATOR_STRING ("&&");
9580 case TRUTH_ORIF_EXPR: BUILD_OPERATOR_STRING ("||");
9581 case EQ_EXPR: BUILD_OPERATOR_STRING ("==");
9582 case NE_EXPR: BUILD_OPERATOR_STRING ("!=");
9583 case GT_EXPR: BUILD_OPERATOR_STRING (">");
9584 case GE_EXPR: BUILD_OPERATOR_STRING (">=");
9585 case LT_EXPR: BUILD_OPERATOR_STRING ("<");
9586 case LE_EXPR: BUILD_OPERATOR_STRING ("<=");
b67d701b 9587 case UNARY_PLUS_EXPR: BUILD_OPERATOR_STRING ("+");
e04a16fb
AG
9588 case NEGATE_EXPR: BUILD_OPERATOR_STRING ("-");
9589 case TRUTH_NOT_EXPR: BUILD_OPERATOR_STRING ("!");
9590 case BIT_NOT_EXPR: BUILD_OPERATOR_STRING ("~");
9591 case PREINCREMENT_EXPR: /* Fall through */
9592 case POSTINCREMENT_EXPR: BUILD_OPERATOR_STRING ("++");
9593 case PREDECREMENT_EXPR: /* Fall through */
9594 case POSTDECREMENT_EXPR: BUILD_OPERATOR_STRING ("--");
9595 default:
9596 fatal ("unregistered operator %s - operator_string",
9597 tree_code_name [TREE_CODE (node)]);
9598 }
9599 return NULL;
9600#undef BUILD_OPERATOR_STRING
9601}
9602
5cbdba64
APB
9603/* Return 1 if VAR_ACCESS1 is equivalent to VAR_ACCESS2. */
9604
9605static int
9606java_decl_equiv (var_acc1, var_acc2)
9607 tree var_acc1, var_acc2;
9608{
9609 if (JDECL_P (var_acc1))
9610 return (var_acc1 == var_acc2);
9611
9612 return (TREE_CODE (var_acc1) == COMPONENT_REF
9613 && TREE_CODE (var_acc2) == COMPONENT_REF
9614 && TREE_OPERAND (TREE_OPERAND (var_acc1, 0), 0)
9615 == TREE_OPERAND (TREE_OPERAND (var_acc2, 0), 0)
9616 && TREE_OPERAND (var_acc1, 1) == TREE_OPERAND (var_acc2, 1));
9617}
9618
9619/* Return a non zero value if CODE is one of the operators that can be
9620 used in conjunction with the `=' operator in a compound assignment. */
9621
9622static int
9623binop_compound_p (code)
9624 enum tree_code code;
9625{
9626 int i;
9627 for (i = 0; i < BINOP_COMPOUND_CANDIDATES; i++)
9628 if (binop_lookup [i] == code)
9629 break;
9630
9631 return i < BINOP_COMPOUND_CANDIDATES;
9632}
9633
9634/* Reorganize after a fold to get SAVE_EXPR to generate what we want. */
9635
9636static tree
9637java_refold (t)
9638 tree t;
9639{
9640 tree c, b, ns, decl;
9641
9642 if (TREE_CODE (t) != MODIFY_EXPR)
9643 return t;
9644
9645 c = TREE_OPERAND (t, 1);
9646 if (! (c && TREE_CODE (c) == COMPOUND_EXPR
9647 && TREE_CODE (TREE_OPERAND (c, 0)) == MODIFY_EXPR
9648 && binop_compound_p (TREE_CODE (TREE_OPERAND (c, 1)))))
9649 return t;
9650
9651 /* Now the left branch of the binary operator. */
9652 b = TREE_OPERAND (TREE_OPERAND (c, 1), 0);
9653 if (! (b && TREE_CODE (b) == NOP_EXPR
9654 && TREE_CODE (TREE_OPERAND (b, 0)) == SAVE_EXPR))
9655 return t;
9656
9657 ns = TREE_OPERAND (TREE_OPERAND (b, 0), 0);
9658 if (! (ns && TREE_CODE (ns) == NOP_EXPR
9659 && TREE_CODE (TREE_OPERAND (ns, 0)) == SAVE_EXPR))
9660 return t;
9661
9662 decl = TREE_OPERAND (TREE_OPERAND (ns, 0), 0);
9663 if ((JDECL_P (decl) || TREE_CODE (decl) == COMPONENT_REF)
9664 /* It's got to be the an equivalent decl */
9665 && java_decl_equiv (decl, TREE_OPERAND (TREE_OPERAND (c, 0), 0)))
9666 {
9667 /* Shorten the NOP_EXPR/SAVE_EXPR path. */
9668 TREE_OPERAND (TREE_OPERAND (c, 1), 0) = TREE_OPERAND (ns, 0);
9669 /* Substitute the COMPOUND_EXPR by the BINOP_EXPR */
9670 TREE_OPERAND (t, 1) = TREE_OPERAND (c, 1);
9671 /* Change the right part of the BINOP_EXPR */
9672 TREE_OPERAND (TREE_OPERAND (t, 1), 1) = TREE_OPERAND (c, 0);
9673 }
9674
9675 return t;
9676}
9677
e04a16fb
AG
9678/* Binary operators (15.16 up to 15.18). We return error_mark_node on
9679 errors but we modify NODE so that it contains the type computed
9680 according to the expression, when it's fixed. Otherwise, we write
9681 error_mark_node as the type. It allows us to further the analysis
9682 of remaining nodes and detects more errors in certain cases. */
9683
9684static tree
9685patch_binop (node, wfl_op1, wfl_op2)
9686 tree node;
9687 tree wfl_op1;
9688 tree wfl_op2;
9689{
9690 tree op1 = TREE_OPERAND (node, 0);
9691 tree op2 = TREE_OPERAND (node, 1);
9692 tree op1_type = TREE_TYPE (op1);
9693 tree op2_type = TREE_TYPE (op2);
ab3a6dd6 9694 tree prom_type = NULL_TREE;
e04a16fb 9695 int code = TREE_CODE (node);
b67d701b 9696
e04a16fb
AG
9697 /* If 1, tell the routine that we have to return error_mark_node
9698 after checking for the initialization of the RHS */
9699 int error_found = 0;
9700
e04a16fb
AG
9701 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
9702
e04a16fb
AG
9703 switch (code)
9704 {
9705 /* 15.16 Multiplicative operators */
9706 case MULT_EXPR: /* 15.16.1 Multiplication Operator * */
9707 case RDIV_EXPR: /* 15.16.2 Division Operator / */
9708 case TRUNC_MOD_EXPR: /* 15.16.3 Remainder operator % */
9709 if (!JPRIMITIVE_TYPE_P (op1_type) || !JPRIMITIVE_TYPE_P (op2_type))
9710 {
9711 if (!JPRIMITIVE_TYPE_P (op1_type))
9712 ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op1_type);
9713 if (!JPRIMITIVE_TYPE_P (op2_type) && (op1_type != op2_type))
9714 ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op2_type);
9715 TREE_TYPE (node) = error_mark_node;
9716 error_found = 1;
9717 break;
9718 }
9719 prom_type = binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
9720 /* Change the division operator if necessary */
9721 if (code == RDIV_EXPR && TREE_CODE (prom_type) == INTEGER_TYPE)
9722 TREE_SET_CODE (node, TRUNC_DIV_EXPR);
0b4d333e 9723
aa4759c1
AH
9724 if (TREE_CODE (prom_type) == INTEGER_TYPE
9725 && flag_use_divide_subroutine
9726 && ! flag_emit_class_files
9727 && (code == RDIV_EXPR || code == TRUNC_MOD_EXPR))
9728 return build_java_soft_divmod (TREE_CODE (node), prom_type, op1, op2);
9729
0b4d333e
APB
9730 /* This one is more complicated. FLOATs are processed by a
9731 function call to soft_fmod. Duplicate the value of the
9732 COMPOUND_ASSIGN_P flag. */
e04a16fb 9733 if (code == TRUNC_MOD_EXPR)
0b4d333e
APB
9734 {
9735 tree mod = build_java_binop (TRUNC_MOD_EXPR, prom_type, op1, op2);
9736 COMPOUND_ASSIGN_P (mod) = COMPOUND_ASSIGN_P (node);
dc0b3eff
PB
9737 TREE_SIDE_EFFECTS (mod)
9738 = TREE_SIDE_EFFECTS (op1) | TREE_SIDE_EFFECTS (op2);
0b4d333e
APB
9739 return mod;
9740 }
e04a16fb
AG
9741 break;
9742
9743 /* 15.17 Additive Operators */
9744 case PLUS_EXPR: /* 15.17.1 String Concatenation Operator + */
b67d701b
PB
9745
9746 /* Operation is valid if either one argument is a string
9747 constant, a String object or a StringBuffer crafted for the
9748 purpose of the a previous usage of the String concatenation
9749 operator */
9750
9751 if (TREE_CODE (op1) == STRING_CST
9752 || TREE_CODE (op2) == STRING_CST
9753 || JSTRING_TYPE_P (op1_type)
9754 || JSTRING_TYPE_P (op2_type)
9755 || IS_CRAFTED_STRING_BUFFER_P (op1)
9756 || IS_CRAFTED_STRING_BUFFER_P (op2))
9757 return build_string_concatenation (op1, op2);
9758
e04a16fb
AG
9759 case MINUS_EXPR: /* 15.17.2 Additive Operators (+ and -) for
9760 Numeric Types */
9761 if (!JPRIMITIVE_TYPE_P (op1_type) || !JPRIMITIVE_TYPE_P (op2_type))
9762 {
9763 if (!JPRIMITIVE_TYPE_P (op1_type))
9764 ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op1_type);
9765 if (!JPRIMITIVE_TYPE_P (op2_type) && (op1_type != op2_type))
9766 ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op2_type);
9767 TREE_TYPE (node) = error_mark_node;
9768 error_found = 1;
9769 break;
9770 }
9771 prom_type = binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
9772 break;
9773
9774 /* 15.18 Shift Operators */
9775 case LSHIFT_EXPR:
9776 case RSHIFT_EXPR:
9777 case URSHIFT_EXPR:
9778 if (!JINTEGRAL_TYPE_P (op1_type) || !JINTEGRAL_TYPE_P (op2_type))
9779 {
9780 if (!JINTEGRAL_TYPE_P (op1_type))
9781 ERROR_CAST_NEEDED_TO_INTEGRAL (wfl_operator, node, op1_type);
9782 else
1ebadc60
KG
9783 {
9784 if (JPRIMITIVE_TYPE_P (op2_type))
9785 parse_error_context (wfl_operator,
9786 "Incompatible type for `%s'. "
9787 "Explicit cast needed to convert "
9788 "shift distance from `%s' to integral",
9789 operator_string (node),
9790 lang_printable_name (op2_type, 0));
9791 else
9792 parse_error_context (wfl_operator, "Incompatible type for `%s'."
9793 " Can't convert shift distance from "
9794 "`%s' to integral",
9795 operator_string (node),
9796 lang_printable_name (op2_type, 0));
9797 }
e04a16fb
AG
9798 TREE_TYPE (node) = error_mark_node;
9799 error_found = 1;
9800 break;
9801 }
9802
9803 /* Unary numeric promotion (5.6.1) is performed on each operand
9804 separatly */
15fdcfe9
PB
9805 op1 = do_unary_numeric_promotion (op1);
9806 op2 = do_unary_numeric_promotion (op2);
e04a16fb
AG
9807
9808 /* The type of the shift expression is the type of the promoted
9809 type of the left-hand operand */
9810 prom_type = TREE_TYPE (op1);
9811
9812 /* Shift int only up to 0x1f and long up to 0x3f */
9813 if (prom_type == int_type_node)
9814 op2 = fold (build (BIT_AND_EXPR, int_type_node, op2,
9815 build_int_2 (0x1f, 0)));
9816 else
9817 op2 = fold (build (BIT_AND_EXPR, int_type_node, op2,
9818 build_int_2 (0x3f, 0)));
9819
9820 /* The >>> operator is a >> operating on unsigned quantities */
15fdcfe9 9821 if (code == URSHIFT_EXPR && ! flag_emit_class_files)
e04a16fb 9822 {
0b4d333e 9823 tree to_return;
73333a87
AH
9824 tree utype = unsigned_type (prom_type);
9825 op1 = convert (utype, op1);
e04a16fb 9826 TREE_SET_CODE (node, RSHIFT_EXPR);
73333a87
AH
9827 TREE_OPERAND (node, 0) = op1;
9828 TREE_OPERAND (node, 1) = op2;
9829 TREE_TYPE (node) = utype;
0b4d333e
APB
9830 to_return = convert (prom_type, node);
9831 /* Copy the original value of the COMPOUND_ASSIGN_P flag */
9832 COMPOUND_ASSIGN_P (to_return) = COMPOUND_ASSIGN_P (node);
dc0b3eff
PB
9833 TREE_SIDE_EFFECTS (to_return)
9834 = TREE_SIDE_EFFECTS (op1) | TREE_SIDE_EFFECTS (op2);
0b4d333e 9835 return to_return;
e04a16fb
AG
9836 }
9837 break;
5e942c50
APB
9838
9839 /* 15.19.1 Type Comparison Operator instaceof */
9840 case INSTANCEOF_EXPR:
9841
9842 TREE_TYPE (node) = boolean_type_node;
9843
9844 if (!(op2_type = resolve_type_during_patch (op2)))
9845 return error_mark_node;
9846
9847 /* The first operand must be a reference type or the null type */
9848 if (!JREFERENCE_TYPE_P (op1_type) && op1 != null_pointer_node)
9849 error_found = 1; /* Error reported further below */
9850
9851 /* The second operand must be a reference type */
9852 if (!JREFERENCE_TYPE_P (op2_type))
9853 {
9854 SET_WFL_OPERATOR (wfl_operator, node, wfl_op2);
9855 parse_error_context
9856 (wfl_operator, "Invalid argument `%s' for `instanceof'",
9857 lang_printable_name (op2_type, 0));
9858 error_found = 1;
9859 }
9860
9861 if (!error_found && valid_ref_assignconv_cast_p (op1_type, op2_type, 1))
9862 {
9863 /* If the first operand is null, the result is always false */
9864 if (op1 == null_pointer_node)
9865 return boolean_false_node;
15fdcfe9
PB
9866 else if (flag_emit_class_files)
9867 {
9868 TREE_OPERAND (node, 1) = op2_type;
dc0b3eff 9869 TREE_SIDE_EFFECTS (node) = TREE_SIDE_EFFECTS (op1);
15fdcfe9
PB
9870 return node;
9871 }
5e942c50
APB
9872 /* Otherwise we have to invoke instance of to figure it out */
9873 else
9874 {
9875 tree call =
9876 build (CALL_EXPR, boolean_type_node,
9877 build_address_of (soft_instanceof_node),
9878 tree_cons
9879 (NULL_TREE, op1,
9880 build_tree_list (NULL_TREE,
9881 build_class_ref (op2_type))),
9882 NULL_TREE);
dc0b3eff 9883 TREE_SIDE_EFFECTS (call) = TREE_SIDE_EFFECTS (op1);
5e942c50
APB
9884 return call;
9885 }
9886 }
9887 /* There is no way the expression operand can be an instance of
9888 the type operand. This is a compile time error. */
9889 else
9890 {
c2e3db92 9891 char *t1 = xstrdup (lang_printable_name (op1_type, 0));
5e942c50
APB
9892 SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
9893 parse_error_context
9894 (wfl_operator, "Impossible for `%s' to be instance of `%s'",
9895 t1, lang_printable_name (op2_type, 0));
9896 free (t1);
9897 error_found = 1;
9898 }
e04a16fb 9899
5e942c50 9900 break;
e04a16fb
AG
9901
9902 /* 15.21 Bitwise and Logical Operators */
9903 case BIT_AND_EXPR:
9904 case BIT_XOR_EXPR:
9905 case BIT_IOR_EXPR:
9906 if (JINTEGRAL_TYPE_P (op1_type) && JINTEGRAL_TYPE_P (op2_type))
9907 /* Binary numeric promotion is performed on both operand and the
9908 expression retain that type */
9909 prom_type = binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
9910
9911 else if (TREE_CODE (op1_type) == BOOLEAN_TYPE
9912 && TREE_CODE (op1_type) == BOOLEAN_TYPE)
9913 /* The type of the bitwise operator expression is BOOLEAN */
9914 prom_type = boolean_type_node;
9915 else
9916 {
9917 if (!JINTEGRAL_TYPE_P (op1_type))
9918 ERROR_CAST_NEEDED_TO_INTEGRAL (wfl_operator, node, op1_type);
9919 if (!JINTEGRAL_TYPE_P (op2_type) && (op1_type != op2_type))
9920 ERROR_CAST_NEEDED_TO_INTEGRAL (wfl_operator, node, op2_type);
9921 TREE_TYPE (node) = error_mark_node;
9922 error_found = 1;
9923 /* Insert a break here if adding thing before the switch's
9924 break for this case */
9925 }
9926 break;
9927
9928 /* 15.22 Conditional-And Operator */
9929 case TRUTH_ANDIF_EXPR:
9930 /* 15.23 Conditional-Or Operator */
9931 case TRUTH_ORIF_EXPR:
9932 /* Operands must be of BOOLEAN type */
9933 if (TREE_CODE (op1_type) != BOOLEAN_TYPE ||
9934 TREE_CODE (op2_type) != BOOLEAN_TYPE)
9935 {
9936 if (TREE_CODE (op1_type) != BOOLEAN_TYPE)
9937 ERROR_CANT_CONVERT_TO_BOOLEAN (wfl_operator, node, op1_type);
9938 if (TREE_CODE (op2_type) != BOOLEAN_TYPE && (op1_type != op2_type))
9939 ERROR_CANT_CONVERT_TO_BOOLEAN (wfl_operator, node, op2_type);
9940 TREE_TYPE (node) = boolean_type_node;
9941 error_found = 1;
9942 break;
9943 }
9944 /* The type of the conditional operators is BOOLEAN */
9945 prom_type = boolean_type_node;
9946 break;
9947
9948 /* 15.19.1 Numerical Comparison Operators <, <=, >, >= */
9949 case LT_EXPR:
9950 case GT_EXPR:
9951 case LE_EXPR:
9952 case GE_EXPR:
9953 /* The type of each of the operands must be a primitive numeric
9954 type */
9955 if (!JNUMERIC_TYPE_P (op1_type) || ! JNUMERIC_TYPE_P (op2_type))
9956 {
9957 if (!JNUMERIC_TYPE_P (op1_type))
9958 ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op1_type);
9959 if (!JNUMERIC_TYPE_P (op2_type) && (op1_type != op2_type))
9960 ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op2_type);
9961 TREE_TYPE (node) = boolean_type_node;
9962 error_found = 1;
9963 break;
9964 }
9965 /* Binary numeric promotion is performed on the operands */
9966 binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
9967 /* The type of the relation expression is always BOOLEAN */
9968 prom_type = boolean_type_node;
9969 break;
9970
9971 /* 15.20 Equality Operator */
9972 case EQ_EXPR:
9973 case NE_EXPR:
9974 /* 15.20.1 Numerical Equality Operators == and != */
9975 /* Binary numeric promotion is performed on the operands */
5e942c50 9976 if (JNUMERIC_TYPE_P (op1_type) && JNUMERIC_TYPE_P (op2_type))
e04a16fb
AG
9977 binary_numeric_promotion (op1_type, op2_type, &op1, &op2);
9978
9979 /* 15.20.2 Boolean Equality Operators == and != */
9980 else if (TREE_CODE (op1_type) == BOOLEAN_TYPE &&
9981 TREE_CODE (op2_type) == BOOLEAN_TYPE)
9982 ; /* Nothing to do here */
9983
9984 /* 15.20.3 Reference Equality Operators == and != */
5e942c50
APB
9985 /* Types have to be either references or the null type. If
9986 they're references, it must be possible to convert either
9987 type to the other by casting conversion. */
b9f7e36c
APB
9988 else if (op1 == null_pointer_node || op2 == null_pointer_node
9989 || (JREFERENCE_TYPE_P (op1_type) && JREFERENCE_TYPE_P (op2_type)
5e942c50
APB
9990 && (valid_ref_assignconv_cast_p (op1_type, op2_type, 1)
9991 || valid_ref_assignconv_cast_p (op2_type,
9992 op1_type, 1))))
e04a16fb
AG
9993 ; /* Nothing to do here */
9994
9995 /* Else we have an error figure what can't be converted into
9996 what and report the error */
9997 else
9998 {
9999 char *t1;
c2e3db92 10000 t1 = xstrdup (lang_printable_name (op1_type, 0));
e04a16fb
AG
10001 parse_error_context
10002 (wfl_operator, "Incompatible type for `%s'. Can't convert `%s' "
10003 "to `%s'", operator_string (node), t1,
0a2138e2 10004 lang_printable_name (op2_type, 0));
e04a16fb
AG
10005 free (t1);
10006 TREE_TYPE (node) = boolean_type_node;
10007 error_found = 1;
10008 break;
10009 }
10010 prom_type = boolean_type_node;
10011 break;
10012 }
10013
e04a16fb
AG
10014 if (error_found)
10015 return error_mark_node;
10016
10017 TREE_OPERAND (node, 0) = op1;
10018 TREE_OPERAND (node, 1) = op2;
10019 TREE_TYPE (node) = prom_type;
dc0b3eff
PB
10020 TREE_SIDE_EFFECTS (node) = TREE_SIDE_EFFECTS (op1) | TREE_SIDE_EFFECTS (op2);
10021
ce6e9147
APB
10022 if (flag_emit_xref)
10023 return node;
10024
d1472141
PB
10025 /* fold does not respect side-effect order as required for Java but not C.
10026 * Also, it sometimes create SAVE_EXPRs which are bad when emitting
10027 * bytecode.
10028 */
10029 if (flag_emit_class_files ? (TREE_CONSTANT (op1) && TREE_CONSTANT (op2))
10030 : ! TREE_SIDE_EFFECTS (node))
aee48ef8
PB
10031 node = fold (node);
10032 return node;
e04a16fb
AG
10033}
10034
b67d701b
PB
10035/* Concatenate the STRING_CST CSTE and STRING. When AFTER is a non
10036 zero value, the value of CSTE comes after the valude of STRING */
10037
10038static tree
10039do_merge_string_cste (cste, string, string_len, after)
10040 tree cste;
49f48c71 10041 const char *string;
b67d701b
PB
10042 int string_len, after;
10043{
10044 int len = TREE_STRING_LENGTH (cste) + string_len;
49f48c71 10045 const char *old = TREE_STRING_POINTER (cste);
b67d701b
PB
10046 TREE_STRING_LENGTH (cste) = len;
10047 TREE_STRING_POINTER (cste) = obstack_alloc (expression_obstack, len+1);
10048 if (after)
10049 {
10050 strcpy (TREE_STRING_POINTER (cste), string);
10051 strcat (TREE_STRING_POINTER (cste), old);
10052 }
10053 else
10054 {
10055 strcpy (TREE_STRING_POINTER (cste), old);
10056 strcat (TREE_STRING_POINTER (cste), string);
10057 }
10058 return cste;
10059}
10060
10061/* Tries to merge OP1 (a STRING_CST) and OP2 (if suitable). Return a
10062 new STRING_CST on success, NULL_TREE on failure */
10063
10064static tree
10065merge_string_cste (op1, op2, after)
10066 tree op1, op2;
10067 int after;
10068{
10069 /* Handle two string constants right away */
10070 if (TREE_CODE (op2) == STRING_CST)
10071 return do_merge_string_cste (op1, TREE_STRING_POINTER (op2),
10072 TREE_STRING_LENGTH (op2), after);
10073
10074 /* Reasonable integer constant can be treated right away */
10075 if (TREE_CODE (op2) == INTEGER_CST && !TREE_CONSTANT_OVERFLOW (op2))
10076 {
49f48c71
KG
10077 static const char *boolean_true = "true";
10078 static const char *boolean_false = "false";
10079 static const char *null_pointer = "null";
b67d701b 10080 char ch[3];
49f48c71 10081 const char *string;
b67d701b
PB
10082
10083 if (op2 == boolean_true_node)
10084 string = boolean_true;
10085 else if (op2 == boolean_false_node)
10086 string = boolean_false;
10087 else if (op2 == null_pointer_node)
10088 string = null_pointer;
10089 else if (TREE_TYPE (op2) == char_type_node)
10090 {
10091 ch[0] = (char )TREE_INT_CST_LOW (op2);
10092 ch[1] = '\0';
10093 string = ch;
10094 }
10095 else
10096 string = print_int_node (op2);
10097
10098 return do_merge_string_cste (op1, string, strlen (string), after);
10099 }
10100 return NULL_TREE;
10101}
10102
10103/* Tries to statically concatenate OP1 and OP2 if possible. Either one
10104 has to be a STRING_CST and the other part must be a STRING_CST or a
10105 INTEGRAL constant. Return a new STRING_CST if the operation
10106 succeed, NULL_TREE otherwise.
10107
10108 If the case we want to optimize for space, we might want to return
10109 NULL_TREE for each invocation of this routine. FIXME */
10110
10111static tree
10112string_constant_concatenation (op1, op2)
10113 tree op1, op2;
10114{
10115 if (TREE_CODE (op1) == STRING_CST || (TREE_CODE (op2) == STRING_CST))
10116 {
0a2138e2 10117 tree string, rest;
b67d701b
PB
10118 int invert;
10119
10120 string = (TREE_CODE (op1) == STRING_CST ? op1 : op2);
10121 rest = (string == op1 ? op2 : op1);
10122 invert = (string == op1 ? 0 : 1 );
10123
10124 /* Walk REST, only if it looks reasonable */
10125 if (TREE_CODE (rest) != STRING_CST
10126 && !IS_CRAFTED_STRING_BUFFER_P (rest)
10127 && !JSTRING_TYPE_P (TREE_TYPE (rest))
10128 && TREE_CODE (rest) == EXPR_WITH_FILE_LOCATION)
10129 {
10130 rest = java_complete_tree (rest);
10131 if (rest == error_mark_node)
10132 return error_mark_node;
10133 rest = fold (rest);
10134 }
10135 return merge_string_cste (string, rest, invert);
10136 }
10137 return NULL_TREE;
10138}
10139
10140/* Implement the `+' operator. Does static optimization if possible,
10141 otherwise create (if necessary) and append elements to a
10142 StringBuffer. The StringBuffer will be carried around until it is
10143 used for a function call or an assignment. Then toString() will be
10144 called on it to turn it into a String object. */
10145
10146static tree
10147build_string_concatenation (op1, op2)
10148 tree op1, op2;
10149{
10150 tree result;
dc0b3eff 10151 int side_effects = TREE_SIDE_EFFECTS (op1) | TREE_SIDE_EFFECTS (op2);
ce6e9147
APB
10152
10153 if (flag_emit_xref)
10154 return build (PLUS_EXPR, string_type_node, op1, op2);
b67d701b
PB
10155
10156 /* Try to do some static optimization */
10157 if ((result = string_constant_concatenation (op1, op2)))
10158 return result;
10159
c0d87ff6
PB
10160 /* Discard empty strings on either side of the expression */
10161 if (TREE_CODE (op1) == STRING_CST && TREE_STRING_LENGTH (op1) == 0)
acd663ee
APB
10162 {
10163 op1 = op2;
10164 op2 = NULL_TREE;
10165 }
c0d87ff6 10166 else if (TREE_CODE (op2) == STRING_CST && TREE_STRING_LENGTH (op2) == 0)
acd663ee 10167 op2 = NULL_TREE;
b67d701b 10168
acd663ee 10169 /* If operands are string constant, turn then into object references */
b67d701b
PB
10170 if (TREE_CODE (op1) == STRING_CST)
10171 op1 = patch_string_cst (op1);
acd663ee 10172 if (op2 && TREE_CODE (op2) == STRING_CST)
b67d701b
PB
10173 op2 = patch_string_cst (op2);
10174
acd663ee
APB
10175 /* If either one of the constant is null and the other non null
10176 operand is a String object, return it. */
10177 if (JSTRING_TYPE_P (TREE_TYPE (op1)) && !op2)
10178 return op1;
10179
b67d701b
PB
10180 /* If OP1 isn't already a StringBuffer, create and
10181 initialize a new one */
10182 if (!IS_CRAFTED_STRING_BUFFER_P (op1))
10183 {
10184 /* Two solutions here:
10185 1) OP1 is a string reference, we call new StringBuffer(OP1)
acd663ee 10186 2) OP1 is something else, we call new StringBuffer().append(OP1). */
b67d701b
PB
10187 if (JSTRING_TYPE_P (TREE_TYPE (op1)))
10188 op1 = BUILD_STRING_BUFFER (op1);
10189 else
10190 {
10191 tree aNew = BUILD_STRING_BUFFER (NULL_TREE);
10192 op1 = make_qualified_primary (aNew, BUILD_APPEND (op1), 0);
10193 }
10194 }
10195
acd663ee
APB
10196 if (op2)
10197 {
10198 /* OP1 is no longer the last node holding a crafted StringBuffer */
10199 IS_CRAFTED_STRING_BUFFER_P (op1) = 0;
10200 /* Create a node for `{new...,xxx}.append (op2)' */
10201 if (op2)
10202 op1 = make_qualified_primary (op1, BUILD_APPEND (op2), 0);
10203 }
10204
b67d701b
PB
10205 /* Mark the last node holding a crafted StringBuffer */
10206 IS_CRAFTED_STRING_BUFFER_P (op1) = 1;
dc0b3eff
PB
10207
10208 TREE_SIDE_EFFECTS (op1) = side_effects;
b67d701b
PB
10209 return op1;
10210}
10211
10212/* Patch the string node NODE. NODE can be a STRING_CST of a crafted
10213 StringBuffer. If no string were found to be patched, return
10214 NULL. */
10215
10216static tree
10217patch_string (node)
10218 tree node;
10219{
1179ebc2
APB
10220 if (node == error_mark_node)
10221 return error_mark_node;
b67d701b
PB
10222 if (TREE_CODE (node) == STRING_CST)
10223 return patch_string_cst (node);
10224 else if (IS_CRAFTED_STRING_BUFFER_P (node))
10225 {
c877974e 10226 int saved = ctxp->explicit_constructor_p;
b67d701b 10227 tree invoke = build_method_invocation (wfl_to_string, NULL_TREE);
c877974e
APB
10228 tree ret;
10229 /* Temporary disable forbid the use of `this'. */
10230 ctxp->explicit_constructor_p = 0;
10231 ret = java_complete_tree (make_qualified_primary (node, invoke, 0));
10232 /* Restore it at its previous value */
10233 ctxp->explicit_constructor_p = saved;
10234 return ret;
b67d701b
PB
10235 }
10236 return NULL_TREE;
10237}
10238
10239/* Build the internal representation of a string constant. */
10240
10241static tree
10242patch_string_cst (node)
10243 tree node;
10244{
10245 int location;
15fdcfe9
PB
10246 if (! flag_emit_class_files)
10247 {
10248 push_obstacks (&permanent_obstack, &permanent_obstack);
10249 node = get_identifier (TREE_STRING_POINTER (node));
10250 location = alloc_name_constant (CONSTANT_String, node);
10251 node = build_ref_from_constant_pool (location);
8226320b 10252 pop_obstacks ();
15fdcfe9 10253 }
cd9643f7 10254 TREE_TYPE (node) = string_ptr_type_node;
b67d701b
PB
10255 TREE_CONSTANT (node) = 1;
10256 return node;
10257}
10258
10259/* Build an incomplete unary operator expression. */
e04a16fb
AG
10260
10261static tree
10262build_unaryop (op_token, op_location, op1)
10263 int op_token, op_location;
10264 tree op1;
10265{
10266 enum tree_code op;
10267 tree unaryop;
10268 switch (op_token)
10269 {
b67d701b 10270 case PLUS_TK: op = UNARY_PLUS_EXPR; break;
e04a16fb
AG
10271 case MINUS_TK: op = NEGATE_EXPR; break;
10272 case NEG_TK: op = TRUTH_NOT_EXPR; break;
10273 case NOT_TK: op = BIT_NOT_EXPR; break;
10274 default: fatal ("Unknown token `%d' for unary operator - build_unaryop",
10275 op_token);
10276 }
10277
10278 unaryop = build1 (op, NULL_TREE, op1);
e04a16fb
AG
10279 TREE_SIDE_EFFECTS (unaryop) = 1;
10280 /* Store the location of the operator, for better error report. The
10281 string of the operator will be rebuild based on the OP value. */
10282 EXPR_WFL_LINECOL (unaryop) = op_location;
10283 return unaryop;
10284}
10285
10286/* Special case for the ++/-- operators, since they require an extra
10287 argument to build, which is set to NULL and patched
10288 later. IS_POST_P is 1 if the operator, 0 otherwise. */
10289
10290static tree
10291build_incdec (op_token, op_location, op1, is_post_p)
10292 int op_token, op_location;
10293 tree op1;
10294 int is_post_p;
10295{
10296 static enum tree_code lookup [2][2] =
10297 {
10298 { PREDECREMENT_EXPR, PREINCREMENT_EXPR, },
10299 { POSTDECREMENT_EXPR, POSTINCREMENT_EXPR, },
10300 };
10301 tree node = build (lookup [is_post_p][(op_token - DECR_TK)],
10302 NULL_TREE, op1, NULL_TREE);
10303 TREE_SIDE_EFFECTS (node) = 1;
10304 /* Store the location of the operator, for better error report. The
10305 string of the operator will be rebuild based on the OP value. */
10306 EXPR_WFL_LINECOL (node) = op_location;
10307 return node;
10308}
10309
10310/* Build an incomplete cast operator, based on the use of the
10311 CONVERT_EXPR. Note that TREE_TYPE of the constructed node is
10312 set. java_complete_tree is trained to walk a CONVERT_EXPR even
10313 though its type is already set. */
10314
10315static tree
10316build_cast (location, type, exp)
10317 int location;
10318 tree type, exp;
10319{
10320 tree node = build1 (CONVERT_EXPR, type, exp);
10321 EXPR_WFL_LINECOL (node) = location;
10322 return node;
10323}
10324
10325/* 15.14 Unary operators. We return error_mark_node in case of error,
10326 but preserve the type of NODE if the type is fixed. */
10327
10328static tree
10329patch_unaryop (node, wfl_op)
10330 tree node;
10331 tree wfl_op;
10332{
10333 tree op = TREE_OPERAND (node, 0);
10334 tree op_type = TREE_TYPE (op);
ab3a6dd6 10335 tree prom_type = NULL_TREE, value, decl;
e04a16fb
AG
10336 int code = TREE_CODE (node);
10337 int error_found = 0;
10338
10339 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
10340
10341 switch (code)
10342 {
10343 /* 15.13.2 Postfix Increment Operator ++ */
10344 case POSTINCREMENT_EXPR:
10345 /* 15.13.3 Postfix Increment Operator -- */
10346 case POSTDECREMENT_EXPR:
10347 /* 15.14.1 Prefix Increment Operator ++ */
10348 case PREINCREMENT_EXPR:
10349 /* 15.14.2 Prefix Decrement Operator -- */
10350 case PREDECREMENT_EXPR:
5cbdba64 10351 op = decl = strip_out_static_field_access_decl (op);
b3edebcf 10352 /* We really should have a JAVA_ARRAY_EXPR to avoid this */
e28cd97b 10353 if (!JDECL_P (decl)
b3edebcf
APB
10354 && TREE_CODE (decl) != COMPONENT_REF
10355 && !(flag_emit_class_files && TREE_CODE (decl) == ARRAY_REF)
10356 && TREE_CODE (decl) != INDIRECT_REF
10357 && !(TREE_CODE (decl) == COMPOUND_EXPR
10358 && TREE_OPERAND (decl, 1)
10359 && (TREE_CODE (TREE_OPERAND (decl, 1)) == INDIRECT_REF)))
e04a16fb 10360 {
5e942c50
APB
10361 tree lvalue;
10362 /* Before screaming, check that we're not in fact trying to
10363 increment a optimized static final access, in which case
10364 we issue an different error message. */
10365 if (!(TREE_CODE (wfl_op) == EXPR_WITH_FILE_LOCATION
10366 && resolve_expression_name (wfl_op, &lvalue)
10367 && check_final_assignment (lvalue, wfl_op)))
10368 parse_error_context (wfl_operator, "Invalid argument to `%s'",
10369 operator_string (node));
e04a16fb
AG
10370 TREE_TYPE (node) = error_mark_node;
10371 error_found = 1;
10372 }
5e942c50
APB
10373 else if (check_final_assignment (op, wfl_op))
10374 error_found = 1;
10375
e04a16fb
AG
10376 /* From now on, we know that op if a variable and that it has a
10377 valid wfl. We use wfl_op to locate errors related to the
10378 ++/-- operand. */
10379 else if (!JNUMERIC_TYPE_P (op_type))
10380 {
10381 parse_error_context
10382 (wfl_op, "Invalid argument type `%s' to `%s'",
0a2138e2 10383 lang_printable_name (op_type, 0), operator_string (node));
e04a16fb
AG
10384 TREE_TYPE (node) = error_mark_node;
10385 error_found = 1;
10386 }
10387 else
10388 {
4a5f66c3 10389 /* Before the addition, binary numeric promotion is performed on
5cbdba64
APB
10390 both operands, if really necessary */
10391 if (JINTEGRAL_TYPE_P (op_type))
10392 {
10393 value = build_int_2 (1, 0);
10394 TREE_TYPE (value) = TREE_TYPE (node) = op_type;
10395 }
10396 else
10397 {
10398 value = build_int_2 (1, 0);
10399 TREE_TYPE (node) =
10400 binary_numeric_promotion (op_type,
10401 TREE_TYPE (value), &op, &value);
10402 }
10403 /* And write back into the node. */
4a5f66c3 10404 TREE_OPERAND (node, 0) = op;
e04a16fb 10405 TREE_OPERAND (node, 1) = value;
5cbdba64
APB
10406 /* Convert the overall back into its original type, if
10407 necessary, and return */
10408 if (JINTEGRAL_TYPE_P (op_type))
10409 return fold (node);
10410 else
10411 return fold (convert (op_type, node));
e04a16fb
AG
10412 }
10413 break;
10414
10415 /* 15.14.3 Unary Plus Operator + */
b67d701b 10416 case UNARY_PLUS_EXPR:
e04a16fb
AG
10417 /* 15.14.4 Unary Minus Operator - */
10418 case NEGATE_EXPR:
10419 if (!JNUMERIC_TYPE_P (op_type))
10420 {
10421 ERROR_CANT_CONVERT_TO_NUMERIC (wfl_operator, node, op_type);
10422 TREE_TYPE (node) = error_mark_node;
10423 error_found = 1;
10424 }
10425 /* Unary numeric promotion is performed on operand */
10426 else
10427 {
15fdcfe9
PB
10428 op = do_unary_numeric_promotion (op);
10429 prom_type = TREE_TYPE (op);
b67d701b 10430 if (code == UNARY_PLUS_EXPR)
4a5f66c3 10431 return fold (op);
e04a16fb
AG
10432 }
10433 break;
10434
10435 /* 15.14.5 Bitwise Complement Operator ~ */
10436 case BIT_NOT_EXPR:
10437 if (!JINTEGRAL_TYPE_P (op_type))
10438 {
10439 ERROR_CAST_NEEDED_TO_INTEGRAL (wfl_operator, node, op_type);
10440 TREE_TYPE (node) = error_mark_node;
10441 error_found = 1;
10442 }
10443 else
10444 {
15fdcfe9
PB
10445 op = do_unary_numeric_promotion (op);
10446 prom_type = TREE_TYPE (op);
e04a16fb
AG
10447 }
10448 break;
10449
10450 /* 15.14.6 Logical Complement Operator ! */
10451 case TRUTH_NOT_EXPR:
10452 if (TREE_CODE (op_type) != BOOLEAN_TYPE)
10453 {
10454 ERROR_CANT_CONVERT_TO_BOOLEAN (wfl_operator, node, op_type);
c877974e
APB
10455 /* But the type is known. We will report an error if further
10456 attempt of a assignment is made with this rhs */
e04a16fb
AG
10457 TREE_TYPE (node) = boolean_type_node;
10458 error_found = 1;
10459 }
10460 else
10461 prom_type = boolean_type_node;
10462 break;
10463
10464 /* 15.15 Cast Expression */
10465 case CONVERT_EXPR:
0a2138e2 10466 value = patch_cast (node, wfl_operator);
e04a16fb 10467 if (value == error_mark_node)
c877974e
APB
10468 {
10469 /* If this cast is part of an assignment, we tell the code
10470 that deals with it not to complain about a mismatch,
10471 because things have been cast, anyways */
10472 TREE_TYPE (node) = error_mark_node;
10473 error_found = 1;
10474 }
10475 else
dc0b3eff
PB
10476 {
10477 value = fold (value);
10478 TREE_SIDE_EFFECTS (value) = TREE_SIDE_EFFECTS (op);
10479 return value;
10480 }
e04a16fb
AG
10481 break;
10482 }
10483
e04a16fb
AG
10484 if (error_found)
10485 return error_mark_node;
4a5f66c3
APB
10486
10487 /* There are cases where node has been replaced by something else
10488 and we don't end up returning here: UNARY_PLUS_EXPR,
10489 CONVERT_EXPR, {POST,PRE}{INCR,DECR}EMENT_EXPR. */
7525cc04 10490 TREE_OPERAND (node, 0) = fold (op);
4a5f66c3 10491 TREE_TYPE (node) = prom_type;
dc0b3eff 10492 TREE_SIDE_EFFECTS (node) = TREE_SIDE_EFFECTS (op);
e04a16fb
AG
10493 return fold (node);
10494}
10495
10496/* Generic type resolution that sometimes takes place during node
10497 patching. Returned the resolved type or generate an error
10498 message. Return the resolved type or NULL_TREE. */
10499
10500static tree
10501resolve_type_during_patch (type)
10502 tree type;
10503{
10504 if (unresolved_type_p (type, NULL))
10505 {
10506 tree type_decl = resolve_no_layout (EXPR_WFL_NODE (type), NULL_TREE);
10507 if (!type_decl)
10508 {
10509 parse_error_context (type,
10510 "Class `%s' not found in type declaration",
10511 IDENTIFIER_POINTER (EXPR_WFL_NODE (type)));
10512 return NULL_TREE;
10513 }
10514 else
5e942c50
APB
10515 {
10516 CLASS_LOADED_P (TREE_TYPE (type_decl)) = 1;
10517 return TREE_TYPE (type_decl);
10518 }
e04a16fb
AG
10519 }
10520 return type;
10521}
10522/* 5.5 Casting Conversion. error_mark_node is returned if an error is
10523 found. Otherwise NODE or something meant to replace it is returned. */
10524
10525static tree
0a2138e2 10526patch_cast (node, wfl_operator)
e04a16fb 10527 tree node;
e04a16fb
AG
10528 tree wfl_operator;
10529{
10530 tree op = TREE_OPERAND (node, 0);
10531 tree op_type = TREE_TYPE (op);
10532 tree cast_type = TREE_TYPE (node);
10533 char *t1;
10534
10535 /* First resolve OP_TYPE if unresolved */
10536 if (!(cast_type = resolve_type_during_patch (cast_type)))
10537 return error_mark_node;
10538
10539 /* Check on cast that are proven correct at compile time */
10540 if (JNUMERIC_TYPE_P (cast_type) && JNUMERIC_TYPE_P (op_type))
10541 {
e04a16fb
AG
10542 /* Same type */
10543 if (cast_type == op_type)
10544 return node;
10545
0b4d333e
APB
10546 /* float and double type are converted to the original type main
10547 variant and then to the target type. */
10548 if (JFLOAT_TYPE_P (op_type) && TREE_CODE (cast_type) == CHAR_TYPE)
10549 op = convert (integer_type_node, op);
10550
e04a16fb
AG
10551 /* Try widening/narowwing convertion. Potentially, things need
10552 to be worked out in gcc so we implement the extreme cases
10553 correctly. fold_convert() needs to be fixed. */
10554 return convert (cast_type, op);
10555 }
10556
0b4d333e
APB
10557 /* It's also valid to cast a boolean into a boolean */
10558 if (op_type == boolean_type_node && cast_type == boolean_type_node)
10559 return node;
10560
5e942c50
APB
10561 /* null can be casted to references */
10562 if (op == null_pointer_node && JREFERENCE_TYPE_P (cast_type))
10563 return build_null_of_type (cast_type);
10564
e04a16fb
AG
10565 /* The remaining legal casts involve conversion between reference
10566 types. Check for their compile time correctness. */
10567 if (JREFERENCE_TYPE_P (op_type) && JREFERENCE_TYPE_P (cast_type)
09ed0f70 10568 && valid_ref_assignconv_cast_p (op_type, cast_type, 1))
e04a16fb
AG
10569 {
10570 TREE_TYPE (node) = promote_type (cast_type);
10571 /* Now, the case can be determined correct at compile time if
10572 OP_TYPE can be converted into CAST_TYPE by assignment
10573 conversion (5.2) */
10574
10575 if (valid_ref_assignconv_cast_p (op_type, cast_type, 0))
15fdcfe9
PB
10576 {
10577 TREE_SET_CODE (node, NOP_EXPR);
10578 return node;
10579 }
10580
10581 if (flag_emit_class_files)
10582 {
10583 TREE_SET_CODE (node, CONVERT_EXPR);
10584 return node;
10585 }
e04a16fb
AG
10586
10587 /* The cast requires a run-time check */
10588 return build (CALL_EXPR, promote_type (cast_type),
10589 build_address_of (soft_checkcast_node),
10590 tree_cons (NULL_TREE, build_class_ref (cast_type),
10591 build_tree_list (NULL_TREE, op)),
10592 NULL_TREE);
10593 }
10594
10595 /* Any other casts are proven incorrect at compile time */
c2e3db92 10596 t1 = xstrdup (lang_printable_name (op_type, 0));
e04a16fb 10597 parse_error_context (wfl_operator, "Invalid cast from `%s' to `%s'",
0a2138e2 10598 t1, lang_printable_name (cast_type, 0));
e04a16fb
AG
10599 free (t1);
10600 return error_mark_node;
10601}
10602
5e942c50
APB
10603/* Build a null constant and give it the type TYPE. */
10604
10605static tree
10606build_null_of_type (type)
10607 tree type;
10608{
10609 tree node = build_int_2 (0, 0);
10610 TREE_TYPE (node) = promote_type (type);
10611 return node;
10612}
10613
e04a16fb
AG
10614/* Build an ARRAY_REF incomplete tree node. Note that operand 1 isn't
10615 a list of indices. */
10616static tree
10617build_array_ref (location, array, index)
10618 int location;
10619 tree array, index;
10620{
10621 tree node = build (ARRAY_REF, NULL_TREE, array, index);
10622 EXPR_WFL_LINECOL (node) = location;
10623 return node;
10624}
10625
10626/* 15.12 Array Access Expression */
10627
10628static tree
c877974e
APB
10629patch_array_ref (node)
10630 tree node;
e04a16fb
AG
10631{
10632 tree array = TREE_OPERAND (node, 0);
10633 tree array_type = TREE_TYPE (array);
10634 tree index = TREE_OPERAND (node, 1);
10635 tree index_type = TREE_TYPE (index);
e04a16fb
AG
10636 int error_found = 0;
10637
10638 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
10639
e04a16fb
AG
10640 if (TREE_CODE (array_type) == POINTER_TYPE)
10641 array_type = TREE_TYPE (array_type);
10642
10643 /* The array reference must be an array */
10644 if (!TYPE_ARRAY_P (array_type))
10645 {
10646 parse_error_context
10647 (wfl_operator, "`[]' can only be applied to arrays. It can't be "
0a2138e2 10648 "applied to `%s'", lang_printable_name (array_type, 0));
e04a16fb
AG
10649 TREE_TYPE (node) = error_mark_node;
10650 error_found = 1;
10651 }
10652
10653 /* The array index underdoes unary numeric promotion. The promoted
10654 type must be int */
15fdcfe9
PB
10655 index = do_unary_numeric_promotion (index);
10656 if (TREE_TYPE (index) != int_type_node)
e04a16fb 10657 {
1ebadc60
KG
10658 if (valid_cast_to_p (index_type, int_type_node))
10659 parse_error_context (wfl_operator, "Incompatible type for `[]'. "
10660 "Explicit cast needed to convert `%s' to `int'",
10661 lang_printable_name (index_type, 0));
10662 else
10663 parse_error_context (wfl_operator, "Incompatible type for `[]'. "
10664 "Can't convert `%s' to `int'",
10665 lang_printable_name (index_type, 0));
e04a16fb
AG
10666 TREE_TYPE (node) = error_mark_node;
10667 error_found = 1;
10668 }
10669
e04a16fb
AG
10670 if (error_found)
10671 return error_mark_node;
e04a16fb 10672
5e942c50 10673 array_type = TYPE_ARRAY_ELEMENT (array_type);
5e942c50 10674
7f1d4866 10675 if (flag_emit_class_files || flag_emit_xref)
e04a16fb 10676 {
15fdcfe9
PB
10677 TREE_OPERAND (node, 0) = array;
10678 TREE_OPERAND (node, 1) = index;
e04a16fb
AG
10679 }
10680 else
939d7216
PB
10681 {
10682 /* The save_expr is for correct evaluation order. It would be cleaner
10683 to use force_evaluation_order (see comment there), but that is
10684 difficult when we also have to deal with bounds checking. */
10685 if (TREE_SIDE_EFFECTS (index))
10686 array = save_expr (array);
10687 node = build_java_arrayaccess (array, array_type, index);
10688 if (TREE_SIDE_EFFECTS (index))
10689 node = build (COMPOUND_EXPR, array_type, array, node);
10690 }
e04a16fb
AG
10691 TREE_TYPE (node) = array_type;
10692 return node;
10693}
10694
10695/* 15.9 Array Creation Expressions */
10696
10697static tree
10698build_newarray_node (type, dims, extra_dims)
10699 tree type;
10700 tree dims;
10701 int extra_dims;
10702{
10703 tree node =
b67d701b 10704 build (NEW_ARRAY_EXPR, NULL_TREE, type, nreverse (dims),
e04a16fb 10705 build_int_2 (extra_dims, 0));
e04a16fb
AG
10706 return node;
10707}
10708
10709static tree
10710patch_newarray (node)
10711 tree node;
10712{
10713 tree type = TREE_OPERAND (node, 0);
10714 tree dims = TREE_OPERAND (node, 1);
10715 tree cdim, array_type;
10716 int error_found = 0;
10717 int ndims = 0;
10718 int xdims = TREE_INT_CST_LOW (TREE_OPERAND (node, 2));
e04a16fb
AG
10719
10720 /* Dimension types are verified. It's better for the types to be
10721 verified in order. */
10722 for (cdim = dims, ndims = 0; cdim; cdim = TREE_CHAIN (cdim), ndims++ )
10723 {
10724 int dim_error = 0;
10725 tree dim = TREE_VALUE (cdim);
10726
10727 /* Dim might have been saved during its evaluation */
10728 dim = (TREE_CODE (dim) == SAVE_EXPR ? dim = TREE_OPERAND (dim, 0) : dim);
10729
10730 /* The type of each specified dimension must be an integral type. */
10731 if (!JINTEGRAL_TYPE_P (TREE_TYPE (dim)))
10732 dim_error = 1;
10733
10734 /* Each expression undergoes an unary numeric promotion (5.6.1) and the
10735 promoted type must be int. */
10736 else
10737 {
15fdcfe9 10738 dim = do_unary_numeric_promotion (dim);
e04a16fb
AG
10739 if (TREE_TYPE (dim) != int_type_node)
10740 dim_error = 1;
10741 }
10742
10743 /* Report errors on types here */
10744 if (dim_error)
10745 {
10746 parse_error_context
10747 (TREE_PURPOSE (cdim),
10748 "Incompatible type for dimension in array creation expression. "
10749 "%s convert `%s' to `int'",
b67d701b 10750 (valid_cast_to_p (TREE_TYPE (dim), int_type_node) ?
e04a16fb 10751 "Explicit cast needed to" : "Can't"),
0a2138e2 10752 lang_printable_name (TREE_TYPE (dim), 0));
e04a16fb
AG
10753 error_found = 1;
10754 }
10755
e04a16fb
AG
10756 TREE_PURPOSE (cdim) = NULL_TREE;
10757 }
10758
10759 /* Resolve array base type if unresolved */
10760 if (!(type = resolve_type_during_patch (type)))
10761 error_found = 1;
10762
10763 if (error_found)
10764 {
10765 /* We don't want further evaluation of this bogus array creation
10766 operation */
10767 TREE_TYPE (node) = error_mark_node;
10768 return error_mark_node;
10769 }
10770
15fdcfe9
PB
10771 /* Set array_type to the actual (promoted) array type of the result. */
10772 if (TREE_CODE (type) == RECORD_TYPE)
10773 type = build_pointer_type (type);
10774 while (--xdims >= 0)
10775 {
10776 type = promote_type (build_java_array_type (type, -1));
10777 }
10778 dims = nreverse (dims);
10779 array_type = type;
10780 for (cdim = dims; cdim; cdim = TREE_CHAIN (cdim))
10781 {
10782 type = array_type;
10783 array_type = build_java_array_type (type,
10784 TREE_CODE (cdim) == INTEGER_CST ?
10785 TREE_INT_CST_LOW (cdim) : -1);
10786 array_type = promote_type (array_type);
10787 }
10788 dims = nreverse (dims);
10789
e04a16fb
AG
10790 /* The node is transformed into a function call. Things are done
10791 differently according to the number of dimensions. If the number
10792 of dimension is equal to 1, then the nature of the base type
10793 (primitive or not) matters. */
15fdcfe9 10794 if (ndims == 1)
fdec99c6 10795 return build_new_array (type, TREE_VALUE (dims));
e04a16fb 10796
e04a16fb
AG
10797 /* Can't reuse what's already written in expr.c because it uses the
10798 JVM stack representation. Provide a build_multianewarray. FIXME */
15fdcfe9 10799 return build (CALL_EXPR, array_type,
e04a16fb 10800 build_address_of (soft_multianewarray_node),
15fdcfe9 10801 tree_cons (NULL_TREE, build_class_ref (TREE_TYPE (array_type)),
e04a16fb 10802 tree_cons (NULL_TREE,
15fdcfe9 10803 build_int_2 (ndims, 0), dims )),
e04a16fb
AG
10804 NULL_TREE);
10805}
10806
f8976021
APB
10807/* 10.6 Array initializer. */
10808
10809/* Build a wfl for array element that don't have one, so we can
10810 pin-point errors. */
10811
10812static tree
10813maybe_build_array_element_wfl (node)
10814 tree node;
10815{
10816 if (TREE_CODE (node) != EXPR_WITH_FILE_LOCATION)
10817 return build_expr_wfl (NULL_TREE, ctxp->filename,
10818 ctxp->elc.line, ctxp->elc.prev_col);
10819 else
10820 return NULL_TREE;
10821}
10822
10823/* Build a NEW_ARRAY_INIT that features a CONSTRUCTOR node. This makes
10824 identification of initialized arrays easier to detect during walk
10825 and expansion. */
10826
10827static tree
10828build_new_array_init (location, values)
10829 int location;
10830 tree values;
10831{
10832 tree constructor = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, values);
10833 tree to_return = build1 (NEW_ARRAY_INIT, NULL_TREE, constructor);
5bba4807 10834 EXPR_WFL_LINECOL (to_return) = location;
f8976021
APB
10835 return to_return;
10836}
10837
10838/* Expand a NEW_ARRAY_INIT node. Return error_mark_node if an error
10839 occurred. Otherwise return NODE after having set its type
10840 appropriately. */
10841
10842static tree
10843patch_new_array_init (type, node)
10844 tree type, node;
f8976021
APB
10845{
10846 int error_seen = 0;
fdec99c6 10847 tree current, element_type;
f8976021 10848 HOST_WIDE_INT length;
fdec99c6
PB
10849 int all_constant = 1;
10850 tree init = TREE_OPERAND (node, 0);
f8976021 10851
fdec99c6
PB
10852 if (TREE_CODE (type) != POINTER_TYPE || ! TYPE_ARRAY_P (TREE_TYPE (type)))
10853 {
10854 parse_error_context (node,
10855 "Invalid array initializer for non-array type `%s'",
10856 lang_printable_name (type, 1));
10857 return error_mark_node;
10858 }
10859 type = TREE_TYPE (type);
10860 element_type = TYPE_ARRAY_ELEMENT (type);
f8976021 10861
fdec99c6
PB
10862 CONSTRUCTOR_ELTS (init) = nreverse (CONSTRUCTOR_ELTS (init));
10863
10864 for (length = 0, current = CONSTRUCTOR_ELTS (init);
10865 current; length++, current = TREE_CHAIN (current))
f8976021 10866 {
fdec99c6
PB
10867 tree elt = TREE_VALUE (current);
10868 if (elt == NULL_TREE || TREE_CODE (elt) != NEW_ARRAY_INIT)
f8976021 10869 {
fdec99c6 10870 error_seen |= array_constructor_check_entry (element_type, current);
5bba4807
PB
10871 elt = TREE_VALUE (current);
10872 /* When compiling to native code, STRING_CST is converted to
10873 INDIRECT_REF, but still with a TREE_CONSTANT flag. */
10874 if (! TREE_CONSTANT (elt) || TREE_CODE (elt) == INDIRECT_REF)
fdec99c6 10875 all_constant = 0;
f8976021 10876 }
fdec99c6
PB
10877 else
10878 {
10879 TREE_VALUE (current) = patch_new_array_init (element_type, elt);
10880 TREE_PURPOSE (current) = NULL_TREE;
10881 all_constant = 0;
10882 }
10883 if (elt && TREE_VALUE (elt) == error_mark_node)
10884 error_seen = 1;
f8976021
APB
10885 }
10886
10887 if (error_seen)
10888 return error_mark_node;
10889
10890 /* Create a new type. We can't reuse the one we have here by
10891 patching its dimension because it originally is of dimension -1
10892 hence reused by gcc. This would prevent triangular arrays. */
fdec99c6
PB
10893 type = build_java_array_type (element_type, length);
10894 TREE_TYPE (init) = TREE_TYPE (TREE_CHAIN (TREE_CHAIN (TYPE_FIELDS (type))));
10895 TREE_TYPE (node) = promote_type (type);
10896 TREE_CONSTANT (init) = all_constant;
bc3ca41b 10897 TREE_CONSTANT (node) = all_constant;
f8976021
APB
10898 return node;
10899}
10900
10901/* Verify that one entry of the initializer element list can be
10902 assigned to the array base type. Report 1 if an error occurred, 0
10903 otherwise. */
10904
10905static int
10906array_constructor_check_entry (type, entry)
10907 tree type, entry;
10908{
10909 char *array_type_string = NULL; /* For error reports */
10910 tree value, type_value, new_value, wfl_value, patched;
10911 int error_seen = 0;
10912
10913 new_value = NULL_TREE;
10914 wfl_value = TREE_VALUE (entry);
10915
100f7cd8 10916 push_obstacks (&permanent_obstack, &permanent_obstack);
f8976021 10917 value = java_complete_tree (TREE_VALUE (entry));
1179ebc2 10918 /* patch_string return error_mark_node if arg is error_mark_node */
f8976021
APB
10919 if ((patched = patch_string (value)))
10920 value = patched;
1179ebc2
APB
10921 if (value == error_mark_node)
10922 return 1;
f8976021 10923
f8976021
APB
10924 type_value = TREE_TYPE (value);
10925
1179ebc2 10926 /* At anytime, try_builtin_assignconv can report a warning on
f8976021
APB
10927 constant overflow during narrowing. */
10928 SET_WFL_OPERATOR (wfl_operator, TREE_PURPOSE (entry), wfl_value);
10929 new_value = try_builtin_assignconv (wfl_operator, type, value);
10930 if (!new_value && (new_value = try_reference_assignconv (type, value)))
10931 type_value = promote_type (type);
100f7cd8
APB
10932
10933 pop_obstacks ();
f8976021
APB
10934 /* Check and report errors */
10935 if (!new_value)
10936 {
49f48c71 10937 const char *msg = (!valid_cast_to_p (type_value, type) ?
f8976021
APB
10938 "Can't" : "Explicit cast needed to");
10939 if (!array_type_string)
c2e3db92 10940 array_type_string = xstrdup (lang_printable_name (type, 1));
f8976021
APB
10941 parse_error_context
10942 (wfl_operator, "Incompatible type for array. %s convert `%s' to `%s'",
10943 msg, lang_printable_name (type_value, 1), array_type_string);
10944 error_seen = 1;
10945 }
10946
10947 if (new_value)
10948 {
10949 new_value = maybe_build_primttype_type_ref (new_value, wfl_operator);
10950 TREE_VALUE (entry) = new_value;
10951 }
10952
10953 if (array_type_string)
10954 free (array_type_string);
10955
10956 TREE_PURPOSE (entry) = NULL_TREE;
10957 return error_seen;
10958}
10959
e04a16fb
AG
10960static tree
10961build_this (location)
10962 int location;
10963{
9ee9b555 10964 tree node = build_wfl_node (this_identifier_node);
b67d701b 10965 TREE_SET_CODE (node, THIS_EXPR);
e04a16fb
AG
10966 EXPR_WFL_LINECOL (node) = location;
10967 return node;
10968}
10969
10970/* 14.15 The return statement. It builds a modify expression that
10971 assigns the returned value to the RESULT_DECL that hold the value
10972 to be returned. */
10973
10974static tree
10975build_return (location, op)
10976 int location;
10977 tree op;
10978{
10979 tree node = build1 (RETURN_EXPR, NULL_TREE, op);
10980 EXPR_WFL_LINECOL (node) = location;
b67d701b 10981 node = build_debugable_stmt (location, node);
e04a16fb
AG
10982 return node;
10983}
10984
10985static tree
10986patch_return (node)
10987 tree node;
10988{
10989 tree return_exp = TREE_OPERAND (node, 0);
10990 tree meth = current_function_decl;
10991 tree mtype = TREE_TYPE (TREE_TYPE (current_function_decl));
e04a16fb
AG
10992 int error_found = 0;
10993
10994 TREE_TYPE (node) = error_mark_node;
10995 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
10996
10997 /* It's invalid to have a return value within a function that is
10998 declared with the keyword void or that is a constructor */
10999 if (return_exp && (mtype == void_type_node || DECL_CONSTRUCTOR_P (meth)))
11000 error_found = 1;
11001
f099f336 11002 /* It's invalid to use a return statement in a static block */
7f1d4866 11003 if (IS_CLINIT (current_function_decl))
f099f336
APB
11004 error_found = 1;
11005
e04a16fb
AG
11006 /* It's invalid to have a no return value within a function that
11007 isn't declared with the keyword `void' */
11008 if (!return_exp && (mtype != void_type_node && !DECL_CONSTRUCTOR_P (meth)))
11009 error_found = 2;
11010
11011 if (error_found)
11012 {
7f1d4866 11013 if (IS_CLINIT (current_function_decl))
f099f336
APB
11014 parse_error_context (wfl_operator,
11015 "`return' inside static initializer.");
11016
11017 else if (!DECL_CONSTRUCTOR_P (meth))
22eed1e6 11018 {
c2e3db92 11019 char *t = xstrdup (lang_printable_name (mtype, 0));
22eed1e6
APB
11020 parse_error_context (wfl_operator,
11021 "`return' with%s value from `%s %s'",
11022 (error_found == 1 ? "" : "out"),
11023 t, lang_printable_name (meth, 0));
11024 free (t);
11025 }
11026 else
11027 parse_error_context (wfl_operator,
11028 "`return' with value from constructor `%s'",
11029 lang_printable_name (meth, 0));
e04a16fb
AG
11030 return error_mark_node;
11031 }
11032
5e942c50
APB
11033 /* If we have a return_exp, build a modify expression and expand
11034 it. Note: at that point, the assignment is declared valid, but we
11035 may want to carry some more hacks */
e04a16fb
AG
11036 if (return_exp)
11037 {
5e942c50
APB
11038 tree exp = java_complete_tree (return_exp);
11039 tree modify, patched;
11040
11041 /* If the function returned value and EXP are booleans, EXP has
11042 to be converted into the type of DECL_RESULT, which is integer
11043 (see complete_start_java_method) */
11044 if (TREE_TYPE (exp) == boolean_type_node &&
11045 TREE_TYPE (TREE_TYPE (meth)) == boolean_type_node)
11046 exp = convert_to_integer (TREE_TYPE (DECL_RESULT (meth)), exp);
11047
11048 /* `null' can be assigned to a function returning a reference */
11049 if (JREFERENCE_TYPE_P (TREE_TYPE (TREE_TYPE (meth))) &&
11050 exp == null_pointer_node)
11051 exp = build_null_of_type (TREE_TYPE (TREE_TYPE (meth)));
11052
11053 if ((patched = patch_string (exp)))
11054 exp = patched;
11055
11056 modify = build (MODIFY_EXPR, NULL_TREE, DECL_RESULT (meth), exp);
e04a16fb
AG
11057 EXPR_WFL_LINECOL (modify) = EXPR_WFL_LINECOL (node);
11058 modify = java_complete_tree (modify);
5e942c50 11059
e04a16fb
AG
11060 if (modify != error_mark_node)
11061 {
11062 TREE_SIDE_EFFECTS (modify) = 1;
11063 TREE_OPERAND (node, 0) = modify;
11064 }
11065 else
11066 return error_mark_node;
11067 }
11068 TREE_TYPE (node) = void_type_node;
11069 TREE_SIDE_EFFECTS (node) = 1;
11070 return node;
11071}
11072
11073/* 14.8 The if Statement */
11074
11075static tree
11076build_if_else_statement (location, expression, if_body, else_body)
11077 int location;
11078 tree expression, if_body, else_body;
11079{
11080 tree node;
e04a16fb 11081 if (!else_body)
9bbc7d9f 11082 else_body = empty_stmt_node;
e04a16fb
AG
11083 node = build (COND_EXPR, NULL_TREE, expression, if_body, else_body);
11084 EXPR_WFL_LINECOL (node) = location;
b67d701b 11085 node = build_debugable_stmt (location, node);
e04a16fb
AG
11086 return node;
11087}
11088
11089static tree
11090patch_if_else_statement (node)
11091 tree node;
11092{
11093 tree expression = TREE_OPERAND (node, 0);
11094
11095 TREE_TYPE (node) = error_mark_node;
11096 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
11097
11098 /* The type of expression must be boolean */
b67d701b
PB
11099 if (TREE_TYPE (expression) != boolean_type_node
11100 && TREE_TYPE (expression) != promoted_boolean_type_node)
e04a16fb
AG
11101 {
11102 parse_error_context
11103 (wfl_operator,
11104 "Incompatible type for `if'. Can't convert `%s' to `boolean'",
0a2138e2 11105 lang_printable_name (TREE_TYPE (expression), 0));
e04a16fb
AG
11106 return error_mark_node;
11107 }
11108
11109 TREE_TYPE (node) = void_type_node;
11110 TREE_SIDE_EFFECTS (node) = 1;
15fdcfe9 11111 CAN_COMPLETE_NORMALLY (node)
9bbc7d9f
PB
11112 = CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 1))
11113 | CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 2));
e04a16fb
AG
11114 return node;
11115}
11116
11117/* 14.6 Labeled Statements */
11118
11119/* Action taken when a lableled statement is parsed. a new
11120 LABELED_BLOCK_EXPR is created. No statement is attached to the
b635eb2f 11121 label, yet. LABEL can be NULL_TREE for artificially-generated blocks. */
e04a16fb
AG
11122
11123static tree
0a2138e2 11124build_labeled_block (location, label)
e04a16fb 11125 int location;
0a2138e2 11126 tree label;
e04a16fb 11127{
b635eb2f 11128 tree label_name ;
e04a16fb 11129 tree label_decl, node;
b635eb2f
PB
11130 if (label == NULL_TREE || label == continue_identifier_node)
11131 label_name = label;
11132 else
e04a16fb 11133 {
b635eb2f
PB
11134 label_name = merge_qualified_name (label_id, label);
11135 /* Issue an error if we try to reuse a label that was previously
11136 declared */
11137 if (IDENTIFIER_LOCAL_VALUE (label_name))
11138 {
11139 EXPR_WFL_LINECOL (wfl_operator) = location;
11140 parse_error_context (wfl_operator, "Declaration of `%s' shadows "
11141 "a previous label declaration",
11142 IDENTIFIER_POINTER (label));
11143 EXPR_WFL_LINECOL (wfl_operator) =
11144 EXPR_WFL_LINECOL (IDENTIFIER_LOCAL_VALUE (label_name));
11145 parse_error_context (wfl_operator, "This is the location of the "
11146 "previous declaration of label `%s'",
11147 IDENTIFIER_POINTER (label));
11148 java_error_count--;
11149 }
e04a16fb
AG
11150 }
11151
11152 label_decl = create_label_decl (label_name);
11153 node = build (LABELED_BLOCK_EXPR, NULL_TREE, label_decl, NULL_TREE);
11154 EXPR_WFL_LINECOL (node) = location;
11155 TREE_SIDE_EFFECTS (node) = 1;
11156 return node;
11157}
11158
b67d701b 11159/* A labeled statement LBE is attached a statement. */
e04a16fb
AG
11160
11161static tree
b635eb2f 11162finish_labeled_statement (lbe, statement)
e04a16fb
AG
11163 tree lbe; /* Labeled block expr */
11164 tree statement;
11165{
11166 /* In anyways, tie the loop to its statement */
11167 LABELED_BLOCK_BODY (lbe) = statement;
b635eb2f
PB
11168 pop_labeled_block ();
11169 POP_LABELED_BLOCK ();
e04a16fb
AG
11170 return lbe;
11171}
11172
11173/* 14.10, 14.11, 14.12 Loop Statements */
11174
11175/* Create an empty LOOP_EXPR and make it the last in the nested loop
11176 list. */
11177
11178static tree
11179build_new_loop (loop_body)
11180 tree loop_body;
11181{
11182 tree loop = build (LOOP_EXPR, NULL_TREE, loop_body);
11183 TREE_SIDE_EFFECTS (loop) = 1;
11184 PUSH_LOOP (loop);
11185 return loop;
11186}
11187
11188/* Create a loop body according to the following structure:
11189 COMPOUND_EXPR
11190 COMPOUND_EXPR (loop main body)
11191 EXIT_EXPR (this order is for while/for loops.
11192 LABELED_BLOCK_EXPR the order is reversed for do loops)
34f4db93 11193 LABEL_DECL (a continue occuring here branches at the
e04a16fb
AG
11194 BODY end of this labeled block)
11195 INCREMENT (if any)
11196
11197 REVERSED, if non zero, tells that the loop condition expr comes
b67d701b
PB
11198 after the body, like in the do-while loop.
11199
11200 To obtain a loop, the loop body structure described above is
11201 encapsulated within a LOOP_EXPR surrounded by a LABELED_BLOCK_EXPR:
11202
11203 LABELED_BLOCK_EXPR
11204 LABEL_DECL (use this label to exit the loop)
11205 LOOP_EXPR
11206 <structure described above> */
e04a16fb
AG
11207
11208static tree
11209build_loop_body (location, condition, reversed)
11210 int location;
11211 tree condition;
11212 int reversed;
11213{
0a2138e2 11214 tree first, second, body;
e04a16fb
AG
11215
11216 condition = build (EXIT_EXPR, NULL_TREE, condition); /* Force walk */
11217 EXPR_WFL_LINECOL (condition) = location; /* For accurate error report */
11218 condition = build_debugable_stmt (location, condition);
11219 TREE_SIDE_EFFECTS (condition) = 1;
11220
b635eb2f 11221 body = build_labeled_block (0, continue_identifier_node);
e04a16fb
AG
11222 first = (reversed ? body : condition);
11223 second = (reversed ? condition : body);
11224 return
11225 build (COMPOUND_EXPR, NULL_TREE,
9bbc7d9f 11226 build (COMPOUND_EXPR, NULL_TREE, first, second), empty_stmt_node);
e04a16fb
AG
11227}
11228
11229/* Install CONDITION (if any) and loop BODY (using REVERSED to tell
11230 their order) on the current loop. Unlink the current loop from the
11231 loop list. */
11232
11233static tree
b635eb2f 11234finish_loop_body (location, condition, body, reversed)
e04a16fb
AG
11235 int location;
11236 tree condition, body;
11237 int reversed;
11238{
11239 tree to_return = ctxp->current_loop;
11240 tree loop_body = LOOP_EXPR_BODY (to_return);
11241 if (condition)
11242 {
11243 tree cnode = LOOP_EXPR_BODY_CONDITION_EXPR (loop_body, reversed);
11244 /* We wrapped the EXIT_EXPR around a WFL so we can debug it.
11245 The real EXIT_EXPR is one operand further. */
11246 EXPR_WFL_LINECOL (cnode) = location;
11247 /* This one is for accurate error reports */
11248 EXPR_WFL_LINECOL (TREE_OPERAND (cnode, 0)) = location;
11249 TREE_OPERAND (TREE_OPERAND (cnode, 0), 0) = condition;
11250 }
11251 LOOP_EXPR_BODY_BODY_EXPR (loop_body, reversed) = body;
11252 POP_LOOP ();
11253 return to_return;
11254}
11255
b635eb2f 11256/* Tailored version of finish_loop_body for FOR loops, when FOR
e04a16fb
AG
11257 loops feature the condition part */
11258
11259static tree
b635eb2f 11260finish_for_loop (location, condition, update, body)
e04a16fb
AG
11261 int location;
11262 tree condition, update, body;
11263{
11264 /* Put the condition and the loop body in place */
b635eb2f 11265 tree loop = finish_loop_body (location, condition, body, 0);
e04a16fb
AG
11266 /* LOOP is the current loop which has been now popped of the loop
11267 stack. Install the update block */
11268 LOOP_EXPR_BODY_UPDATE_BLOCK (LOOP_EXPR_BODY (loop)) = update;
11269 return loop;
11270}
11271
5cbdba64
APB
11272/* Try to find the loop a block might be related to. This comprises
11273 the case where the LOOP_EXPR is found as the second operand of a
11274 COMPOUND_EXPR, because the loop happens to have an initialization
11275 part, then expressed as the first operand of the COMPOUND_EXPR. If
11276 the search finds something, 1 is returned. Otherwise, 0 is
11277 returned. The search is assumed to start from a
11278 LABELED_BLOCK_EXPR's block. */
11279
11280static tree
11281search_loop (statement)
11282 tree statement;
11283{
11284 if (TREE_CODE (statement) == LOOP_EXPR)
11285 return statement;
11286
11287 if (TREE_CODE (statement) == BLOCK)
11288 statement = BLOCK_SUBBLOCKS (statement);
11289 else
11290 return NULL_TREE;
11291
11292 if (statement && TREE_CODE (statement) == COMPOUND_EXPR)
11293 while (statement && TREE_CODE (statement) == COMPOUND_EXPR)
11294 statement = TREE_OPERAND (statement, 1);
11295
11296 return (TREE_CODE (statement) == LOOP_EXPR
11297 && IS_FOR_LOOP_P (statement) ? statement : NULL_TREE);
11298}
11299
11300/* Return 1 if LOOP can be found in the labeled block BLOCK. 0 is
11301 returned otherwise. */
11302
11303static int
11304labeled_block_contains_loop_p (block, loop)
11305 tree block, loop;
11306{
11307 if (!block)
11308 return 0;
11309
11310 if (LABELED_BLOCK_BODY (block) == loop)
11311 return 1;
11312
11313 if (IS_FOR_LOOP_P (loop)
11314 && search_loop (LABELED_BLOCK_BODY (block)) == loop)
11315 return 1;
11316
11317 return 0;
11318}
11319
e04a16fb 11320/* If the loop isn't surrounded by a labeled statement, create one and
b635eb2f 11321 insert LOOP as its body. */
e04a16fb
AG
11322
11323static tree
11324patch_loop_statement (loop)
11325 tree loop;
11326{
cd9643f7 11327 tree loop_label;
5cbdba64 11328
cd9643f7 11329 TREE_TYPE (loop) = void_type_node;
5cbdba64
APB
11330 if (labeled_block_contains_loop_p (ctxp->current_labeled_block, loop))
11331 return loop;
11332
cd9643f7 11333 loop_label = build_labeled_block (0, NULL_TREE);
5cbdba64
APB
11334 /* LOOP is an EXPR node, so it should have a valid EXPR_WFL_LINECOL
11335 that LOOP_LABEL could enquire about, for a better accuracy. FIXME */
cd9643f7
PB
11336 LABELED_BLOCK_BODY (loop_label) = loop;
11337 PUSH_LABELED_BLOCK (loop_label);
5cbdba64 11338 return loop_label;
e04a16fb
AG
11339}
11340
11341/* 14.13, 14.14: break and continue Statements */
11342
11343/* Build a break or a continue statement. a null NAME indicates an
11344 unlabeled break/continue statement. */
11345
11346static tree
11347build_bc_statement (location, is_break, name)
11348 int location, is_break;
11349 tree name;
11350{
11351 tree break_continue, label_block_expr = NULL_TREE;
11352
11353 if (name)
11354 {
11355 if (!(label_block_expr = IDENTIFIER_LOCAL_VALUE
11356 (merge_qualified_name (label_id, EXPR_WFL_NODE (name)))))
11357 /* Null means that we don't have a target for this named
11358 break/continue. In this case, we make the target to be the
11359 label name, so that the error can be reported accuratly in
11360 patch_bc_statement. */
11361 label_block_expr = EXPR_WFL_NODE (name);
11362 }
11363 /* Unlabeled break/continue will be handled during the
11364 break/continue patch operation */
11365 break_continue
11366 = build (EXIT_BLOCK_EXPR, NULL_TREE, label_block_expr, NULL_TREE);
11367
11368 IS_BREAK_STMT_P (break_continue) = is_break;
11369 TREE_SIDE_EFFECTS (break_continue) = 1;
11370 EXPR_WFL_LINECOL (break_continue) = location;
b67d701b 11371 break_continue = build_debugable_stmt (location, break_continue);
e04a16fb
AG
11372 return break_continue;
11373}
11374
11375/* Verification of a break/continue statement. */
11376
11377static tree
11378patch_bc_statement (node)
11379 tree node;
11380{
11381 tree bc_label = EXIT_BLOCK_LABELED_BLOCK (node), target_stmt;
b635eb2f 11382 tree labeled_block = ctxp->current_labeled_block;
b67d701b 11383 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
e04a16fb 11384
e04a16fb 11385 /* Having an identifier here means that the target is unknown. */
b635eb2f 11386 if (bc_label != NULL_TREE && TREE_CODE (bc_label) == IDENTIFIER_NODE)
e04a16fb
AG
11387 {
11388 parse_error_context (wfl_operator, "No label definition found for `%s'",
11389 IDENTIFIER_POINTER (bc_label));
11390 return error_mark_node;
11391 }
b635eb2f 11392 if (! IS_BREAK_STMT_P (node))
e04a16fb 11393 {
b635eb2f
PB
11394 /* It's a continue statement. */
11395 for (;; labeled_block = TREE_CHAIN (labeled_block))
e04a16fb 11396 {
b635eb2f
PB
11397 if (labeled_block == NULL_TREE)
11398 {
11399 if (bc_label == NULL_TREE)
11400 parse_error_context (wfl_operator,
11401 "`continue' must be in loop");
11402 else
1504b2b4
APB
11403 parse_error_context
11404 (wfl_operator, "continue label `%s' does not name a loop",
11405 IDENTIFIER_POINTER (bc_label));
b635eb2f
PB
11406 return error_mark_node;
11407 }
11408 if ((DECL_NAME (LABELED_BLOCK_LABEL (labeled_block))
11409 == continue_identifier_node)
11410 && (bc_label == NULL_TREE
11411 || TREE_CHAIN (labeled_block) == bc_label))
11412 {
11413 bc_label = labeled_block;
11414 break;
11415 }
e04a16fb 11416 }
e04a16fb 11417 }
b635eb2f 11418 else if (!bc_label)
34f4db93 11419 {
b635eb2f 11420 for (;; labeled_block = TREE_CHAIN (labeled_block))
e04a16fb 11421 {
b635eb2f
PB
11422 if (labeled_block == NULL_TREE)
11423 {
11424 parse_error_context (wfl_operator,
11425 "`break' must be in loop or switch");
11426 return error_mark_node;
11427 }
11428 target_stmt = LABELED_BLOCK_BODY (labeled_block);
11429 if (TREE_CODE (target_stmt) == SWITCH_EXPR
5cbdba64 11430 || search_loop (target_stmt))
b635eb2f
PB
11431 {
11432 bc_label = labeled_block;
11433 break;
11434 }
e04a16fb 11435 }
e04a16fb
AG
11436 }
11437
b635eb2f 11438 EXIT_BLOCK_LABELED_BLOCK (node) = bc_label;
15fdcfe9
PB
11439 CAN_COMPLETE_NORMALLY (bc_label) = 1;
11440
e04a16fb
AG
11441 /* Our break/continue don't return values. */
11442 TREE_TYPE (node) = void_type_node;
11443 /* Encapsulate the break within a compound statement so that it's
5cbdba64 11444 expanded all the times by expand_expr (and not clobbered
e04a16fb
AG
11445 sometimes, like after a if statement) */
11446 node = add_stmt_to_compound (NULL_TREE, void_type_node, node);
11447 TREE_SIDE_EFFECTS (node) = 1;
11448 return node;
11449}
11450
11451/* Process the exit expression belonging to a loop. Its type must be
11452 boolean. */
11453
11454static tree
11455patch_exit_expr (node)
11456 tree node;
11457{
11458 tree expression = TREE_OPERAND (node, 0);
11459 TREE_TYPE (node) = error_mark_node;
11460 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
11461
11462 /* The type of expression must be boolean */
11463 if (TREE_TYPE (expression) != boolean_type_node)
11464 {
11465 parse_error_context
11466 (wfl_operator,
11467 "Incompatible type for loop conditional. Can't convert `%s' to "
11468 "`boolean'",
0a2138e2 11469 lang_printable_name (TREE_TYPE (expression), 0));
e04a16fb
AG
11470 return error_mark_node;
11471 }
11472 /* Now we know things are allright, invert the condition, fold and
11473 return */
11474 TREE_OPERAND (node, 0) =
11475 fold (build1 (TRUTH_NOT_EXPR, boolean_type_node, expression));
15fdcfe9
PB
11476
11477 if (! integer_zerop (TREE_OPERAND (node, 0))
11478 && ctxp->current_loop != NULL_TREE
11479 && TREE_CODE (ctxp->current_loop) == LOOP_EXPR)
11480 CAN_COMPLETE_NORMALLY (ctxp->current_loop) = 1;
11481 if (! integer_onep (TREE_OPERAND (node, 0)))
11482 CAN_COMPLETE_NORMALLY (node) = 1;
11483
11484
e04a16fb
AG
11485 TREE_TYPE (node) = void_type_node;
11486 return node;
11487}
b67d701b
PB
11488
11489/* 14.9 Switch statement */
11490
11491static tree
11492patch_switch_statement (node)
11493 tree node;
11494{
c877974e 11495 tree se = TREE_OPERAND (node, 0), se_type;
b67d701b
PB
11496
11497 /* Complete the switch expression */
11498 se = TREE_OPERAND (node, 0) = java_complete_tree (se);
11499 se_type = TREE_TYPE (se);
11500 /* The type of the switch expression must be char, byte, short or
11501 int */
11502 if (!JINTEGRAL_TYPE_P (se_type))
11503 {
11504 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (node);
11505 parse_error_context (wfl_operator, "Incompatible type for `switch'. "
11506 "Can't convert `%s' to `int'",
0a2138e2 11507 lang_printable_name (se_type, 0));
b67d701b
PB
11508 /* This is what java_complete_tree will check */
11509 TREE_OPERAND (node, 0) = error_mark_node;
11510 return error_mark_node;
11511 }
11512
15fdcfe9 11513 TREE_OPERAND (node, 1) = java_complete_tree (TREE_OPERAND (node, 1));
b67d701b
PB
11514
11515 /* Ready to return */
15fdcfe9 11516 if (TREE_CODE (TREE_OPERAND (node, 1)) == ERROR_MARK)
b67d701b
PB
11517 {
11518 TREE_TYPE (node) = error_mark_node;
11519 return error_mark_node;
11520 }
11521 TREE_TYPE (node) = void_type_node;
11522 TREE_SIDE_EFFECTS (node) = 1;
15fdcfe9 11523 CAN_COMPLETE_NORMALLY (node)
c877974e
APB
11524 = CAN_COMPLETE_NORMALLY (TREE_OPERAND (node, 1))
11525 || ! SWITCH_HAS_DEFAULT (node);
b67d701b
PB
11526 return node;
11527}
11528
b67d701b
PB
11529/* 14.18 The try statement */
11530
b67d701b 11531static tree
a7d8d81f 11532build_try_statement (location, try_block, catches)
b67d701b 11533 int location;
a7d8d81f
PB
11534 tree try_block, catches;
11535{
11536 tree node = build (TRY_EXPR, NULL_TREE, try_block, catches);
b67d701b 11537 EXPR_WFL_LINECOL (node) = location;
a7d8d81f 11538 return node;
b67d701b
PB
11539}
11540
a7d8d81f
PB
11541static tree
11542build_try_finally_statement (location, try_block, finally)
11543 int location;
11544 tree try_block, finally;
b67d701b 11545{
a7d8d81f
PB
11546 tree node = build (TRY_FINALLY_EXPR, NULL_TREE, try_block, finally);
11547 EXPR_WFL_LINECOL (node) = location;
11548 return node;
b67d701b
PB
11549}
11550
11551static tree
11552patch_try_statement (node)
11553 tree node;
11554{
11555 int error_found = 0;
11556 tree try = TREE_OPERAND (node, 0);
11557 /* Exception handlers are considered in left to right order */
11558 tree catch = nreverse (TREE_OPERAND (node, 1));
b9f7e36c 11559 tree current, caught_type_list = NULL_TREE;
b67d701b
PB
11560
11561 /* Check catch clauses, if any. Every time we find an error, we try
b9f7e36c
APB
11562 to process the next catch clause. We process the catch clause before
11563 the try block so that when processing the try block we can check thrown
11564 exceptions againts the caught type list. */
b67d701b
PB
11565 for (current = catch; current; current = TREE_CHAIN (current))
11566 {
11567 tree carg_decl, carg_type;
11568 tree sub_current, catch_block, catch_clause;
11569 int unreachable;
11570
b67d701b 11571 /* At this point, the structure of the catch clause is
b67d701b
PB
11572 CATCH_EXPR (catch node)
11573 BLOCK (with the decl of the parameter)
11574 COMPOUND_EXPR
7525cc04 11575 MODIFY_EXPR (assignment of the catch parameter)
b67d701b 11576 BLOCK (catch clause block)
a7d8d81f
PB
11577 */
11578 catch_clause = TREE_OPERAND (current, 0);
b67d701b
PB
11579 carg_decl = BLOCK_EXPR_DECLS (catch_clause);
11580 carg_type = TREE_TYPE (TREE_TYPE (carg_decl));
11581
11582 /* Catch clauses can't have more than one parameter declared,
11583 but it's already enforced by the grammar. Make sure that the
11584 only parameter of the clause statement in of class Throwable
11585 or a subclass of Throwable, but that was done earlier. The
11586 catch clause parameter type has also been resolved. */
11587
11588 /* Just make sure that the catch clause parameter type inherits
11589 from java.lang.Throwable */
11590 if (!inherits_from_p (carg_type, throwable_type_node))
11591 {
11592 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (current);
11593 parse_error_context (wfl_operator,
11594 "Can't catch class `%s'. Catch clause "
11595 "parameter type must be a subclass of "
11596 "class `java.lang.Throwable'",
0a2138e2 11597 lang_printable_name (carg_type, 0));
b67d701b
PB
11598 error_found = 1;
11599 continue;
11600 }
11601
11602 /* Partial check for unreachable catch statement: The catch
11603 clause is reachable iff is no earlier catch block A in
11604 the try statement such that the type of the catch
11605 clause's parameter is the same as or a subclass of the
11606 type of A's parameter */
11607 unreachable = 0;
11608 for (sub_current = catch;
11609 sub_current != current; sub_current = TREE_CHAIN (sub_current))
11610 {
11611 tree sub_catch_clause, decl;
a7d8d81f 11612 sub_catch_clause = TREE_OPERAND (sub_current, 0);
b67d701b
PB
11613 decl = BLOCK_EXPR_DECLS (sub_catch_clause);
11614
11615 if (inherits_from_p (carg_type, TREE_TYPE (TREE_TYPE (decl))))
11616 {
11617 EXPR_WFL_LINECOL (wfl_operator) = EXPR_WFL_LINECOL (current);
11618 parse_error_context
11619 (wfl_operator, "`catch' not reached because of the catch "
11620 "clause at line %d", EXPR_WFL_LINENO (sub_current));
11621 unreachable = error_found = 1;
11622 break;
11623 }
11624 }
b67d701b
PB
11625 /* Complete the catch clause block */
11626 catch_block = java_complete_tree (TREE_OPERAND (current, 0));
11627 if (catch_block == error_mark_node)
11628 {
11629 error_found = 1;
11630 continue;
11631 }
15fdcfe9
PB
11632 if (CAN_COMPLETE_NORMALLY (catch_block))
11633 CAN_COMPLETE_NORMALLY (node) = 1;
b67d701b 11634 TREE_OPERAND (current, 0) = catch_block;
15fdcfe9
PB
11635
11636 if (unreachable)
11637 continue;
11638
11639 /* Things to do here: the exception must be thrown */
11640
11641 /* Link this type to the caught type list */
11642 caught_type_list = tree_cons (NULL_TREE, carg_type, caught_type_list);
b67d701b
PB
11643 }
11644
b9f7e36c
APB
11645 PUSH_EXCEPTIONS (caught_type_list);
11646 if ((try = java_complete_tree (try)) == error_mark_node)
11647 error_found = 1;
15fdcfe9
PB
11648 if (CAN_COMPLETE_NORMALLY (try))
11649 CAN_COMPLETE_NORMALLY (node) = 1;
b9f7e36c
APB
11650 POP_EXCEPTIONS ();
11651
b67d701b
PB
11652 /* Verification ends here */
11653 if (error_found)
11654 return error_mark_node;
11655
11656 TREE_OPERAND (node, 0) = try;
11657 TREE_OPERAND (node, 1) = catch;
b67d701b
PB
11658 TREE_TYPE (node) = void_type_node;
11659 return node;
11660}
b9f7e36c
APB
11661
11662/* 14.17 The synchronized Statement */
11663
11664static tree
11665patch_synchronized_statement (node, wfl_op1)
11666 tree node, wfl_op1;
11667{
5a005d9e 11668 tree expr = java_complete_tree (TREE_OPERAND (node, 0));
b9f7e36c 11669 tree block = TREE_OPERAND (node, 1);
5a005d9e 11670
d8fccff5 11671 tree enter, exit, expr_decl, assignment;
5a005d9e
PB
11672
11673 if (expr == error_mark_node)
11674 {
11675 block = java_complete_tree (block);
11676 return expr;
11677 }
b9f7e36c
APB
11678
11679 /* The TYPE of expr must be a reference type */
5a005d9e 11680 if (!JREFERENCE_TYPE_P (TREE_TYPE (expr)))
b9f7e36c
APB
11681 {
11682 SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
11683 parse_error_context (wfl_operator, "Incompatible type for `synchronized'"
11684 ". Can't convert `%s' to `java.lang.Object'",
0a2138e2 11685 lang_printable_name (TREE_TYPE (expr), 0));
b9f7e36c
APB
11686 return error_mark_node;
11687 }
11688
ce6e9147
APB
11689 if (flag_emit_xref)
11690 {
11691 TREE_OPERAND (node, 0) = expr;
11692 TREE_OPERAND (node, 1) = java_complete_tree (block);
11693 CAN_COMPLETE_NORMALLY (node) = 1;
11694 return node;
11695 }
11696
b9f7e36c
APB
11697 /* Generate a try-finally for the synchronized statement, except
11698 that the handler that catches all throw exception calls
11699 _Jv_MonitorExit and then rethrow the exception.
11700 The synchronized statement is then implemented as:
11701 TRY
11702 {
11703 _Jv_MonitorEnter (expression)
11704 synchronized_block
11705 _Jv_MonitorExit (expression)
11706 }
11707 CATCH_ALL
11708 {
11709 e = _Jv_exception_info ();
11710 _Jv_MonitorExit (expression)
11711 Throw (e);
11712 } */
11713
5a005d9e
PB
11714 expr_decl = build_decl (VAR_DECL, generate_name (), TREE_TYPE (expr));
11715 BUILD_MONITOR_ENTER (enter, expr_decl);
11716 BUILD_MONITOR_EXIT (exit, expr_decl);
11717 CAN_COMPLETE_NORMALLY (enter) = 1;
11718 CAN_COMPLETE_NORMALLY (exit) = 1;
96847892
AH
11719 assignment = build (MODIFY_EXPR, NULL_TREE, expr_decl, expr);
11720 TREE_SIDE_EFFECTS (assignment) = 1;
5a005d9e
PB
11721 node = build1 (CLEANUP_POINT_EXPR, NULL_TREE,
11722 build (COMPOUND_EXPR, NULL_TREE,
11723 build (WITH_CLEANUP_EXPR, NULL_TREE,
11724 build (COMPOUND_EXPR, NULL_TREE,
96847892 11725 assignment, enter),
5a005d9e
PB
11726 NULL_TREE, exit),
11727 block));
11728 node = build_expr_block (node, expr_decl);
11729
11730 return java_complete_tree (node);
b9f7e36c
APB
11731}
11732
11733/* 14.16 The throw Statement */
11734
11735static tree
11736patch_throw_statement (node, wfl_op1)
11737 tree node, wfl_op1;
11738{
11739 tree expr = TREE_OPERAND (node, 0);
11740 tree type = TREE_TYPE (expr);
11741 int unchecked_ok = 0, tryblock_throws_ok = 0;
11742
11743 /* Thrown expression must be assignable to java.lang.Throwable */
11744 if (!try_reference_assignconv (throwable_type_node, expr))
11745 {
11746 SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
11747 parse_error_context (wfl_operator, "Can't throw `%s'; it must be a "
11748 "subclass of class `java.lang.Throwable'",
0a2138e2 11749 lang_printable_name (type, 0));
b9f7e36c
APB
11750 /* If the thrown expression was a reference, we further the
11751 compile-time check. */
11752 if (!JREFERENCE_TYPE_P (type))
11753 return error_mark_node;
11754 }
11755
11756 /* At least one of the following must be true */
11757
11758 /* The type of the throw expression is a not checked exception,
11759 i.e. is a unchecked expression. */
c877974e 11760 unchecked_ok = IS_UNCHECKED_EXCEPTION_P (TREE_TYPE (type));
b9f7e36c
APB
11761
11762 /* Throw is contained in a try statement and at least one catch
11763 clause can receive the thrown expression or the current method is
11764 declared to throw such an exception. Or, the throw statement is
11765 contained in a method or constructor declaration and the type of
11766 the Expression is assignable to at least one type listed in the
11767 throws clause the declaration. */
11768 SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
11769 if (!unchecked_ok)
f099f336 11770 tryblock_throws_ok = check_thrown_exceptions_do (TREE_TYPE (expr));
b9f7e36c
APB
11771 if (!(unchecked_ok || tryblock_throws_ok))
11772 {
11773 /* If there is a surrounding try block that has no matching
11774 clatch clause, report it first. A surrounding try block exits
11775 only if there is something after the list of checked
11776 exception thrown by the current function (if any). */
11777 if (IN_TRY_BLOCK_P ())
11778 parse_error_context (wfl_operator, "Checked exception `%s' can't be "
11779 "caught by any of the catch clause(s) "
11780 "of the surrounding `try' block",
0a2138e2 11781 lang_printable_name (type, 0));
b9f7e36c
APB
11782 /* If we have no surrounding try statement and the method doesn't have
11783 any throws, report it now. FIXME */
f099f336
APB
11784
11785 /* We report that the exception can't be throw from a try block
11786 in all circumstances but when the `throw' is inside a static
11787 block. */
b9f7e36c
APB
11788 else if (!EXCEPTIONS_P (currently_caught_type_list)
11789 && !tryblock_throws_ok)
f099f336 11790 {
7f1d4866 11791 if (IS_CLINIT (current_function_decl))
f099f336
APB
11792 parse_error_context (wfl_operator, "Checked exception `%s' can't "
11793 "be thrown in initializer",
11794 lang_printable_name (type, 0));
11795 else
11796 parse_error_context (wfl_operator, "Checked exception `%s' isn't "
11797 "thrown from a `try' block",
11798 lang_printable_name (type, 0));
11799 }
b9f7e36c
APB
11800 /* Otherwise, the current method doesn't have the appropriate
11801 throws declaration */
11802 else
11803 parse_error_context (wfl_operator, "Checked exception `%s' doesn't "
11804 "match any of current method's `throws' "
11805 "declaration(s)",
0a2138e2 11806 lang_printable_name (type, 0));
b9f7e36c
APB
11807 return error_mark_node;
11808 }
11809
ce6e9147 11810 if (! flag_emit_class_files && ! flag_emit_xref)
15fdcfe9 11811 BUILD_THROW (node, expr);
ce6e9147
APB
11812
11813 /* If doing xrefs, keep the location where the `throw' was seen. */
11814 if (flag_emit_xref)
11815 EXPR_WFL_LINECOL (node) = EXPR_WFL_LINECOL (wfl_op1);
b9f7e36c
APB
11816 return node;
11817}
11818
11819/* Check that exception said to be thrown by method DECL can be
11820 effectively caught from where DECL is invoked. */
11821
11822static void
11823check_thrown_exceptions (location, decl)
11824 int location;
11825 tree decl;
11826{
11827 tree throws;
11828 /* For all the unchecked exceptions thrown by DECL */
11829 for (throws = DECL_FUNCTION_THROWS (decl); throws;
11830 throws = TREE_CHAIN (throws))
0a2138e2 11831 if (!check_thrown_exceptions_do (TREE_VALUE (throws)))
b9f7e36c 11832 {
3e78f871
PB
11833#if 1
11834 /* Temporary hack to suppresses errors about cloning arrays. FIXME */
11835 if (DECL_NAME (decl) == get_identifier ("clone"))
11836 continue;
11837#endif
b9f7e36c 11838 EXPR_WFL_LINECOL (wfl_operator) = location;
7705e9db
APB
11839 if (DECL_NAME (current_function_decl) == finit_identifier_node)
11840 parse_error_context
11841 (wfl_operator, "Exception `%s' can't be thrown in initializer",
11842 lang_printable_name (TREE_VALUE (throws), 0));
11843 else
11844 {
11845 parse_error_context
11846 (wfl_operator, "Exception `%s' must be caught, or it must be "
11847 "declared in the `throws' clause of `%s'",
11848 lang_printable_name (TREE_VALUE (throws), 0),
11849 (DECL_NAME (current_function_decl) == init_identifier_node ?
11850 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (current_class))) :
11851 IDENTIFIER_POINTER (DECL_NAME (current_function_decl))));
11852 }
b9f7e36c
APB
11853 }
11854}
11855
c877974e 11856/* Return 1 if checked EXCEPTION is caught at the current nesting level of
b9f7e36c
APB
11857 try-catch blocks, OR is listed in the `throws' clause of the
11858 current method. */
11859
11860static int
0a2138e2 11861check_thrown_exceptions_do (exception)
b9f7e36c
APB
11862 tree exception;
11863{
11864 tree list = currently_caught_type_list;
c877974e 11865 resolve_and_layout (exception, NULL_TREE);
b9f7e36c
APB
11866 /* First, all the nested try-catch-finally at that stage. The
11867 last element contains `throws' clause exceptions, if any. */
c877974e
APB
11868 if (IS_UNCHECKED_EXCEPTION_P (exception))
11869 return 1;
b9f7e36c
APB
11870 while (list)
11871 {
11872 tree caught;
11873 for (caught = TREE_VALUE (list); caught; caught = TREE_CHAIN (caught))
11874 if (valid_ref_assignconv_cast_p (exception, TREE_VALUE (caught), 0))
11875 return 1;
11876 list = TREE_CHAIN (list);
11877 }
11878 return 0;
11879}
11880
11881static void
11882purge_unchecked_exceptions (mdecl)
11883 tree mdecl;
11884{
11885 tree throws = DECL_FUNCTION_THROWS (mdecl);
11886 tree new = NULL_TREE;
11887
11888 while (throws)
11889 {
11890 tree next = TREE_CHAIN (throws);
c877974e 11891 if (!IS_UNCHECKED_EXCEPTION_P (TREE_VALUE (throws)))
b9f7e36c
APB
11892 {
11893 TREE_CHAIN (throws) = new;
11894 new = throws;
11895 }
11896 throws = next;
11897 }
11898 /* List is inverted here, but it doesn't matter */
11899 DECL_FUNCTION_THROWS (mdecl) = new;
11900}
22eed1e6
APB
11901
11902/* 15.24 Conditional Operator ?: */
11903
11904static tree
11905patch_conditional_expr (node, wfl_cond, wfl_op1)
11906 tree node, wfl_cond, wfl_op1;
11907{
11908 tree cond = TREE_OPERAND (node, 0);
11909 tree op1 = TREE_OPERAND (node, 1);
11910 tree op2 = TREE_OPERAND (node, 2);
22eed1e6 11911 tree resulting_type = NULL_TREE;
ac825856 11912 tree t1, t2, patched;
22eed1e6
APB
11913 int error_found = 0;
11914
ac825856
APB
11915 /* Operands of ?: might be StringBuffers crafted as a result of a
11916 string concatenation. Obtain a descent operand here. */
11917 if ((patched = patch_string (op1)))
11918 TREE_OPERAND (node, 1) = op1 = patched;
11919 if ((patched = patch_string (op2)))
11920 TREE_OPERAND (node, 2) = op2 = patched;
11921
11922 t1 = TREE_TYPE (op1);
11923 t2 = TREE_TYPE (op2);
11924
22eed1e6
APB
11925 /* The first expression must be a boolean */
11926 if (TREE_TYPE (cond) != boolean_type_node)
11927 {
11928 SET_WFL_OPERATOR (wfl_operator, node, wfl_cond);
11929 parse_error_context (wfl_operator, "Incompatible type for `?:'. Can't "
11930 "convert `%s' to `boolean'",
11931 lang_printable_name (TREE_TYPE (cond), 0));
11932 error_found = 1;
11933 }
11934
11935 /* Second and third can be numeric, boolean (i.e. primitive),
11936 references or null. Anything else results in an error */
11937 if (!((JNUMERIC_TYPE_P (t1) && JNUMERIC_TYPE_P (t2))
11938 || ((JREFERENCE_TYPE_P (t1) || op1 == null_pointer_node)
11939 && (JREFERENCE_TYPE_P (t2) || op2 == null_pointer_node))
11940 || (t1 == boolean_type_node && t2 == boolean_type_node)))
11941 error_found = 1;
11942
11943 /* Determine the type of the conditional expression. Same types are
11944 easy to deal with */
11945 else if (t1 == t2)
11946 resulting_type = t1;
11947
11948 /* There are different rules for numeric types */
11949 else if (JNUMERIC_TYPE_P (t1))
11950 {
11951 /* if byte/short found, the resulting type is short */
11952 if ((t1 == byte_type_node && t2 == short_type_node)
11953 || (t1 == short_type_node && t2 == byte_type_node))
11954 resulting_type = short_type_node;
11955
11956 /* If t1 is a constant int and t2 is of type byte, short or char
11957 and t1's value fits in t2, then the resulting type is t2 */
11958 else if ((t1 == int_type_node && TREE_CONSTANT (TREE_OPERAND (node, 1)))
11959 && JBSC_TYPE_P (t2) && int_fits_type_p (TREE_OPERAND (node, 1), t2))
11960 resulting_type = t2;
11961
11962 /* If t2 is a constant int and t1 is of type byte, short or char
11963 and t2's value fits in t1, then the resulting type is t1 */
11964 else if ((t2 == int_type_node && TREE_CONSTANT (TREE_OPERAND (node, 2)))
11965 && JBSC_TYPE_P (t1) && int_fits_type_p (TREE_OPERAND (node, 2), t1))
11966 resulting_type = t1;
11967
11968 /* Otherwise, binary numeric promotion is applied and the
11969 resulting type is the promoted type of operand 1 and 2 */
11970 else
93024893 11971 resulting_type = binary_numeric_promotion (t1, t2,
22eed1e6
APB
11972 &TREE_OPERAND (node, 1),
11973 &TREE_OPERAND (node, 2));
11974 }
11975
11976 /* Cases of a reference and a null type */
11977 else if (JREFERENCE_TYPE_P (t1) && op2 == null_pointer_node)
11978 resulting_type = t1;
11979
11980 else if (JREFERENCE_TYPE_P (t2) && op1 == null_pointer_node)
11981 resulting_type = t2;
11982
11983 /* Last case: different reference types. If a type can be converted
11984 into the other one by assignment conversion, the latter
11985 determines the type of the expression */
11986 else if ((resulting_type = try_reference_assignconv (t1, op2)))
11987 resulting_type = promote_type (t1);
11988
11989 else if ((resulting_type = try_reference_assignconv (t2, op1)))
11990 resulting_type = promote_type (t2);
11991
11992 /* If we don't have any resulting type, we're in trouble */
11993 if (!resulting_type)
11994 {
c2e3db92 11995 char *t = xstrdup (lang_printable_name (t1, 0));
22eed1e6
APB
11996 SET_WFL_OPERATOR (wfl_operator, node, wfl_op1);
11997 parse_error_context (wfl_operator, "Incompatible type for `?:'. Can't "
11998 "convert `%s' to `%s'", t,
11999 lang_printable_name (t2, 0));
12000 free (t);
12001 error_found = 1;
12002 }
12003
12004 if (error_found)
12005 {
12006 TREE_TYPE (node) = error_mark_node;
12007 return error_mark_node;
12008 }
12009
12010 TREE_TYPE (node) = resulting_type;
12011 TREE_SET_CODE (node, COND_EXPR);
15fdcfe9 12012 CAN_COMPLETE_NORMALLY (node) = 1;
22eed1e6
APB
12013 return node;
12014}
ac825856 12015
5b09b33e
PB
12016/* Try to constant fold NODE.
12017 If NODE is not a constant expression, return NULL_EXPR.
12018 CONTEXT is a static final VAR_DECL whose initializer we are folding. */
12019
12020static tree
12021fold_constant_for_init (node, context)
12022 tree node;
12023 tree context;
12024{
12025 tree op0, op1, val;
12026 enum tree_code code = TREE_CODE (node);
12027
93024893 12028 if (code == STRING_CST)
5b09b33e 12029 return node;
93024893
APB
12030
12031 if (code == INTEGER_CST || code == REAL_CST)
12032 return convert (TREE_TYPE (context), node);
8576f094 12033 if (TREE_TYPE (node) != NULL_TREE && code != VAR_DECL && code != FIELD_DECL)
5b09b33e
PB
12034 return NULL_TREE;
12035
12036 switch (code)
12037 {
5b09b33e
PB
12038 case PLUS_EXPR:
12039 case MINUS_EXPR:
bc3ca41b
PB
12040 case MULT_EXPR:
12041 case TRUNC_MOD_EXPR:
12042 case RDIV_EXPR:
5b09b33e
PB
12043 case LSHIFT_EXPR:
12044 case RSHIFT_EXPR:
12045 case URSHIFT_EXPR:
12046 case BIT_AND_EXPR:
12047 case BIT_XOR_EXPR:
12048 case BIT_IOR_EXPR:
5b09b33e
PB
12049 case TRUTH_ANDIF_EXPR:
12050 case TRUTH_ORIF_EXPR:
12051 case EQ_EXPR:
12052 case NE_EXPR:
12053 case GT_EXPR:
12054 case GE_EXPR:
12055 case LT_EXPR:
12056 case LE_EXPR:
12057 op0 = TREE_OPERAND (node, 0);
12058 op1 = TREE_OPERAND (node, 1);
12059 val = fold_constant_for_init (op0, context);
12060 if (val == NULL_TREE || ! TREE_CONSTANT (val))
12061 return NULL_TREE;
12062 TREE_OPERAND (node, 0) = val;
12063 val = fold_constant_for_init (op1, context);
12064 if (val == NULL_TREE || ! TREE_CONSTANT (val))
12065 return NULL_TREE;
12066 TREE_OPERAND (node, 1) = val;
12067 return patch_binop (node, op0, op1);
12068
12069 case UNARY_PLUS_EXPR:
12070 case NEGATE_EXPR:
12071 case TRUTH_NOT_EXPR:
12072 case BIT_NOT_EXPR:
12073 case CONVERT_EXPR:
12074 op0 = TREE_OPERAND (node, 0);
12075 val = fold_constant_for_init (op0, context);
12076 if (val == NULL_TREE || ! TREE_CONSTANT (val))
12077 return NULL_TREE;
12078 TREE_OPERAND (node, 0) = val;
5a005d9e 12079 return patch_unaryop (node, op0);
5b09b33e
PB
12080 break;
12081
12082 case COND_EXPR:
12083 val = fold_constant_for_init (TREE_OPERAND (node, 0), context);
12084 if (val == NULL_TREE || ! TREE_CONSTANT (val))
12085 return NULL_TREE;
12086 TREE_OPERAND (node, 0) = val;
12087 val = fold_constant_for_init (TREE_OPERAND (node, 1), context);
12088 if (val == NULL_TREE || ! TREE_CONSTANT (val))
12089 return NULL_TREE;
12090 TREE_OPERAND (node, 1) = val;
12091 val = fold_constant_for_init (TREE_OPERAND (node, 2), context);
12092 if (val == NULL_TREE || ! TREE_CONSTANT (val))
12093 return NULL_TREE;
12094 TREE_OPERAND (node, 2) = val;
12095 return integer_zerop (TREE_OPERAND (node, 0)) ? TREE_OPERAND (node, 1)
12096 : TREE_OPERAND (node, 2);
12097
12098 case VAR_DECL:
8576f094
APB
12099 case FIELD_DECL:
12100 if (! FIELD_FINAL (node)
5b09b33e
PB
12101 || DECL_INITIAL (node) == NULL_TREE)
12102 return NULL_TREE;
12103 val = DECL_INITIAL (node);
12104 /* Guard against infinite recursion. */
12105 DECL_INITIAL (node) = NULL_TREE;
cd9643f7 12106 val = fold_constant_for_init (val, node);
5b09b33e
PB
12107 DECL_INITIAL (node) = val;
12108 return val;
12109
12110 case EXPR_WITH_FILE_LOCATION:
12111 /* Compare java_complete_tree and resolve_expression_name. */
12112 if (!EXPR_WFL_NODE (node) /* Or a PRIMARY flag ? */
12113 || TREE_CODE (EXPR_WFL_NODE (node)) == IDENTIFIER_NODE)
12114 {
12115 tree name = EXPR_WFL_NODE (node);
12116 tree decl;
12117 if (PRIMARY_P (node))
12118 return NULL_TREE;
12119 else if (! QUALIFIED_P (name))
12120 {
12121 decl = lookup_field_wrapper (DECL_CONTEXT (context), name);
8576f094
APB
12122 if (decl == NULL_TREE
12123 || (! FIELD_STATIC (decl) && ! FIELD_FINAL (decl)))
5b09b33e
PB
12124 return NULL_TREE;
12125 return fold_constant_for_init (decl, decl);
12126 }
12127 else
12128 {
5b09b33e
PB
12129 /* Wait until the USE_COMPONENT_REF re-write. FIXME. */
12130 qualify_ambiguous_name (node);
12131 if (resolve_field_access (node, &decl, NULL)
12132 && decl != NULL_TREE)
12133 return fold_constant_for_init (decl, decl);
5b09b33e
PB
12134 return NULL_TREE;
12135 }
12136 }
12137 else
12138 {
12139 op0 = TREE_OPERAND (node, 0);
12140 val = fold_constant_for_init (op0, context);
12141 if (val == NULL_TREE || ! TREE_CONSTANT (val))
12142 return NULL_TREE;
12143 TREE_OPERAND (node, 0) = val;
12144 return val;
12145 }
12146
bc3ca41b
PB
12147#ifdef USE_COMPONENT_REF
12148 case IDENTIFIER:
12149 case COMPONENT_REF:
12150 ?;
12151#endif
12152
5b09b33e
PB
12153 default:
12154 return NULL_TREE;
12155 }
12156}
bc3ca41b
PB
12157
12158#ifdef USE_COMPONENT_REF
12159/* Context is 'T' for TypeName, 'P' for PackageName,
12160 'M' for MethodName, 'E' for ExpressionName, and 'A' for AmbiguousName. */
12161
12162tree
12163resolve_simple_name (name, context)
12164 tree name;
12165 int context;
12166{
12167}
12168
12169tree
12170resolve_qualified_name (name, context)
12171 tree name;
12172 int context;
12173{
12174}
12175#endif
This page took 2.620611 seconds and 5 git commands to generate.