diff options
author | Anthony Green <green@cygnus.com> | 2000-02-26 05:12:27 +0000 |
---|---|---|
committer | Anthony Green <green@gcc.gnu.org> | 2000-02-26 05:12:27 +0000 |
commit | 3ff9925ce0be6f6e72f8da4d8ec96aad25e593f2 (patch) | |
tree | cfe8d050a2c658d4be3700810c5e25cbdfe9806d /gcc/java/expr.c | |
parent | 985dae7cdd18b543af8396c61c5332d685e47745 (diff) | |
download | gcc-3ff9925ce0be6f6e72f8da4d8ec96aad25e593f2.zip gcc-3ff9925ce0be6f6e72f8da4d8ec96aad25e593f2.tar.gz gcc-3ff9925ce0be6f6e72f8da4d8ec96aad25e593f2.tar.bz2 |
expr.c (build_class_init): Mark the decl to be ignored by check_init.
2000-02-25 Anthony Green <green@cygnus.com>
* expr.c (build_class_init): Mark the decl to be ignored by
check_init.
* java-tree.h (DECL_BIT_INDEX): Move definition from check-init.c
* check-init.c: Move DECL_BIT_INDEX to java-tree.h
* class.c (init_test_hash_newfunc): New function.
(decl_hash): New function.
(decl_compare): New function.
* decl.c (emit_init_test_initialization): New function.
(complete_start_java_method): Traverse the init test hashtable,
calling emit_init_test_initialization.
(always_initialize_class_p): Define.
* expr.c (build_class_init): Use initialization tests when
emitting class initialization code.
(always_initialize_class_p): Declare.
* jcf-parse.c (parse_class_file): Set always_initialize_class_p to
1.
* java-tree.h: Include hash.h.
(DECL_FUNCTION_INIT_TEST_TABLE): Define.
(struct lang_decl): Add init_test_table field.
(init_test_hash_entry): Define.
From-SVN: r32166
Diffstat (limited to 'gcc/java/expr.c')
-rw-r--r-- | gcc/java/expr.c | 50 |
1 files changed, 44 insertions, 6 deletions
diff --git a/gcc/java/expr.c b/gcc/java/expr.c index f25b194..41a1d3d 100644 --- a/gcc/java/expr.c +++ b/gcc/java/expr.c @@ -83,6 +83,10 @@ static tree case_identity PARAMS ((tree, tree)); static tree operand_type[59]; extern struct obstack permanent_obstack; +/* Set to non-zero value in order to emit class initilization code + before static field references. */ +int always_initialize_class_p; + void init_expr_processing() { @@ -1490,14 +1494,48 @@ tree build_class_init (clas, expr) tree clas, expr; { - tree init; + tree init, call; + struct init_test_hash_entry *ite; if (inherits_from_p (current_class, clas)) return expr; - init = build (CALL_EXPR, void_type_node, - build_address_of (soft_initclass_node), - build_tree_list (NULL_TREE, build_class_ref (clas)), - NULL_TREE); - TREE_SIDE_EFFECTS (init) = 1; + + if (always_initialize_class_p) + { + init = build (CALL_EXPR, void_type_node, + build_address_of (soft_initclass_node), + build_tree_list (NULL_TREE, build_class_ref (clas)), + NULL_TREE); + TREE_SIDE_EFFECTS (init) = 1; + } + else + { + ite = (struct init_test_hash_entry *) + hash_lookup (&DECL_FUNCTION_INIT_TEST_TABLE (current_function_decl), + (const hash_table_key) clas, + TRUE, NULL); + + if (ite->init_test_decl == 0) + ite->init_test_decl = build_decl (VAR_DECL, NULL_TREE, + boolean_type_node); + /* Tell the check-init code to ignore this decl. */ + DECL_BIT_INDEX(ite->init_test_decl) = -1; + + init = build (CALL_EXPR, void_type_node, + build_address_of (soft_initclass_node), + build_tree_list (NULL_TREE, build_class_ref (clas)), + NULL_TREE); + TREE_SIDE_EFFECTS (init) = 1; + call = build (COMPOUND_EXPR, TREE_TYPE (expr), init, + build (MODIFY_EXPR, boolean_type_node, + ite->init_test_decl, boolean_true_node)); + TREE_SIDE_EFFECTS (call) = 1; + init = build (COND_EXPR, void_type_node, + build (EQ_EXPR, boolean_type_node, + ite->init_test_decl, boolean_false_node), + call, integer_zero_node); + TREE_SIDE_EFFECTS (init) = 1; + } + if (expr != NULL_TREE) { expr = build (COMPOUND_EXPR, TREE_TYPE (expr), init, expr); |