diff options
author | Alexandre Petit-Bianco <apbianco@cygnus.com> | 1999-04-09 16:26:33 +0000 |
---|---|---|
committer | Alexandre Petit-Bianco <apbianco@gcc.gnu.org> | 1999-04-09 09:26:33 -0700 |
commit | 2622b9478575059f41687a2f6a820cdc40e40868 (patch) | |
tree | 2f6407a4c763f83e183d2eb262b97017b40994a5 /gcc/java/parse.c | |
parent | 11249cf0df9d2a868a09a49d12586c3c08823392 (diff) | |
download | gcc-2622b9478575059f41687a2f6a820cdc40e40868.zip gcc-2622b9478575059f41687a2f6a820cdc40e40868.tar.gz gcc-2622b9478575059f41687a2f6a820cdc40e40868.tar.bz2 |
parse.y (patch_assignment): Added ArrayStoreException runtime check.
Tue Apr 6 15:15:51 1999 Alexandre Petit-Bianco <apbianco@cygnus.com>
* parse.y (patch_assignment): Added ArrayStoreException runtime
check.
From-SVN: r26318
Diffstat (limited to 'gcc/java/parse.c')
-rw-r--r-- | gcc/java/parse.c | 57 |
1 files changed, 53 insertions, 4 deletions
diff --git a/gcc/java/parse.c b/gcc/java/parse.c index 69f1861..ed25b16 100644 --- a/gcc/java/parse.c +++ b/gcc/java/parse.c @@ -11252,10 +11252,59 @@ patch_assignment (node, wfl_op1, wfl_op2) if (error_found) return error_mark_node; - /* If we built a compound expression as the result of a reference - assignment into an array element, return it here. */ - if (TREE_CODE (node) == COMPOUND_EXPR) - return node; + /* 10.10: Array Store Exception runtime check */ + if (!flag_emit_class_files + && lvalue_from_array + && JREFERENCE_TYPE_P (TYPE_ARRAY_ELEMENT (lhs_type)) + && !CLASS_FINAL (TYPE_NAME (GET_SKIP_TYPE (rhs_type)))) + { + tree check; + tree base = lvalue; + + /* We need to retrieve the right argument for _Jv_CheckArrayStore */ + if (TREE_CODE (lvalue) == COMPOUND_EXPR) + base = TREE_OPERAND (lvalue, 0); + else + { + if (flag_bounds_check) + base = TREE_OPERAND (TREE_OPERAND (TREE_OPERAND (base, 0), 1), 0); + else + base = TREE_OPERAND (TREE_OPERAND (base, 0), 0); + } + + /* Build the invocation of _Jv_CheckArrayStore */ + check = build (CALL_EXPR, void_type_node, + build_address_of (soft_checkarraystore_node), + tree_cons (NULL_TREE, base, + build_tree_list (NULL_TREE, new_rhs)), + NULL_TREE); + TREE_SIDE_EFFECTS (check) = 1; + + /* We have to decide on an insertion point */ + if (TREE_CODE (lvalue) == COMPOUND_EXPR) + { + tree t; + if (flag_bounds_check) + { + t = TREE_OPERAND (TREE_OPERAND (TREE_OPERAND (lvalue, 1), 0), 0); + TREE_OPERAND (TREE_OPERAND (TREE_OPERAND (lvalue, 1), 0), 0) = + build (COMPOUND_EXPR, void_type_node, t, check); + } + else + TREE_OPERAND (lvalue, 1) = build (COMPOUND_EXPR, lhs_type, + check, TREE_OPERAND (lvalue, 1)); + } + else + { + /* Make sure the bound check will happen before the store check */ + if (flag_bounds_check) + TREE_OPERAND (TREE_OPERAND (lvalue, 0), 0) = + build (COMPOUND_EXPR, void_type_node, + TREE_OPERAND (TREE_OPERAND (lvalue, 0), 0), check); + else + lvalue = build (COMPOUND_EXPR, lhs_type, check, lvalue); + } + } TREE_OPERAND (node, 0) = lvalue; TREE_OPERAND (node, 1) = new_rhs; |