aboutsummaryrefslogtreecommitdiff
path: root/gcc/java/decl.c
diff options
context:
space:
mode:
authorPer Bothner <bothner@gcc.gnu.org>1999-02-21 07:42:27 -0800
committerPer Bothner <bothner@gcc.gnu.org>1999-02-21 07:42:27 -0800
commit939d7216dca76eac6675e54f10154ad5d2898cfa (patch)
treebc94f54b074dc8162b8ed7adee22a07f1784413d /gcc/java/decl.c
parent2d5a51939f53e104020ac07784f5f2087aa06275 (diff)
downloadgcc-939d7216dca76eac6675e54f10154ad5d2898cfa.zip
gcc-939d7216dca76eac6675e54f10154ad5d2898cfa.tar.gz
gcc-939d7216dca76eac6675e54f10154ad5d2898cfa.tar.bz2
decl.c (build_result_decl): New method.
d * decl.c (build_result_decl), java-tree.h: New method. (complete_start_java_method): Handle synchronized methods. Don't build DECL_RESULT here. (Ordering dependency problem.) (start_java_method): Call build_result_decl here instead ... * parse.y (java_complete_expand_method): ... and here. (expand_start_java_method): Don't call complete_start_java_method here. (java_complete_expand_method): Call it here instead. * parse.h (BUILD_MONITOR_ENTER, BUILD_MONITOR_EXIT): Moved to .. * java-tree.h: ... here. * expr.c (force_evaluation_order): Fix typo, don't handle ARRAY_REF. * parse.y (java_complete_lhs): Don't call force_evaluation_order for ARRAY_REF - it doesn't work when array bounds are checked. (patch_array_ref): Handle it here instead. From-SVN: r25346
Diffstat (limited to 'gcc/java/decl.c')
-rw-r--r--gcc/java/decl.c34
1 files changed, 29 insertions, 5 deletions
diff --git a/gcc/java/decl.c b/gcc/java/decl.c
index 5293ddc..14b8ece 100644
--- a/gcc/java/decl.c
+++ b/gcc/java/decl.c
@@ -1465,8 +1465,8 @@ give_name_to_locals (jcf)
}
}
-void
-complete_start_java_method (fndecl)
+tree
+build_result_decl (fndecl)
tree fndecl;
{
tree restype = TREE_TYPE (TREE_TYPE (fndecl));
@@ -1474,8 +1474,13 @@ complete_start_java_method (fndecl)
if (INTEGRAL_TYPE_P (restype)
&& TYPE_PRECISION (restype) < TYPE_PRECISION (integer_type_node))
restype = integer_type_node;
- DECL_RESULT (fndecl) = build_decl (RESULT_DECL, NULL_TREE, restype);
+ return (DECL_RESULT (fndecl) = build_decl (RESULT_DECL, NULL_TREE, restype));
+}
+void
+complete_start_java_method (fndecl)
+ tree fndecl;
+{
if (! flag_emit_class_files)
{
/* Initialize the RTL code for the function. */
@@ -1509,9 +1514,27 @@ complete_start_java_method (fndecl)
expand_expr_stmt (init);
}
- if (METHOD_SYNCHRONIZED (fndecl))
+ if (METHOD_SYNCHRONIZED (fndecl) && ! flag_emit_class_files
+ && DECL_FUNCTION_BODY (fndecl) != NULL_TREE)
{
- /* FIXME: surround the function body by a try/finally set. */
+ /* Warp function body with a monitorenter plus monitorexit cleanup. */
+ tree function_body = DECL_FUNCTION_BODY (fndecl);
+ tree body = BLOCK_EXPR_BODY (function_body);
+ tree enter, exit, lock;
+ if (METHOD_STATIC (fndecl))
+ lock = build_class_ref (DECL_CONTEXT (fndecl));
+ else
+ lock = DECL_ARGUMENTS (fndecl);
+ BUILD_MONITOR_ENTER (enter, lock);
+ BUILD_MONITOR_EXIT (exit, lock);
+ lock = build (WITH_CLEANUP_EXPR, void_type_node,
+ enter, NULL_TREE, exit);
+ TREE_SIDE_EFFECTS (lock) = 1;
+ lock = build (COMPOUND_EXPR, TREE_TYPE (body), lock, body);
+ TREE_SIDE_EFFECTS (lock) = 1;
+ lock = build1 (CLEANUP_POINT_EXPR, TREE_TYPE (body), lock);
+ TREE_SIDE_EFFECTS (lock) = 1;
+ BLOCK_EXPR_BODY (function_body) = lock;
}
/* Push local variables. Function compiled from source code are
@@ -1578,6 +1601,7 @@ start_java_method (fndecl)
while (i < DECL_MAX_LOCALS(fndecl))
type_map[i++] = NULL_TREE;
+ build_result_decl (fndecl);
complete_start_java_method (fndecl);
}