This is the mail archive of the java-patches@gcc.gnu.org mailing list for the Java project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

revised PATCH: CALL_EXPR representation changes, part 7/9 (Java front end)


2007-02-14  Sandra Loosemore  <sandra@codesourcery.com>
	    Brooks Moses  <brooks.moses@codesourcery.com>
	    Lee Millward  <lee.millward@codesourcery.com>

	* java-tree.h (BUILD_MONITOR_ENTER): Use build_call_nary instead
	of build3.
	(BUILD_MONITOR_EXIT): Likewise.

	* java-gimplify.c (java_gimplify_component_ref): Use build_call_expr.
	(java_gimplify_modify_expr): Likewise.

	* class.c (cache_this_class_ref): Use build_call_expr.
	(build_static_field_ref): Likewise.
	(emit_indirect_register_classes): Likewise.
	(emit_register_classes): Likewise.

	* resource.c (write_resource_constructor): Use build_call_expr.

	* builtins.c (builtin_creator_function): Change interpretation of
	the second parameter to be the whole CALL_EXPR instead of the arglist.
	(max_builtin): Tweak parameter list.  Use new CALL_EXPR accessors.
	(min_builtin): Likewise.
	(abs_builtin): Likewise.
	(java_build_function_call_expr): Likewise.
	(convert_real): Likewise.
	(UNMARSHAL3): Likewise.
	(UNMARSHAL4): Likewise.
	(UNMARSHAL5): Likewise.
	(build_arglist_for_builtin): Delete.  Fix callers to use
	build_call_expr instead.
	(putObject_builtin): Tweak parameter list.  Use new CALL_EXPR
	accessors.
	(compareAndSwapInt_builtin): Likewise.
	(compareAndSwapLong_builtin): Likewise.
	(compareAndSwapObject_builtin): Likewise.
	(putVolatile_builtin): Likewise.
	(getVolatile_builtin): Likewise.
	(VMSupportsCS8_builtin): Likewise.
	(check_for_builtin): Pass entire CALL_EXPR to builtin expander
	instead of arglist.

	* expr.c (build_java_athrow): Use build_call_nary instead of build3.
	(build_java_throw_out_of_bounds_exception): Likewise.
	(java_check_reference): Likewise.
	(build_java_arraystore_check): Likewise.
	(build_newarray): Likewise.
	(build_anewarray): Likewise.
	(expand_java_multinewarray): Use build_call_list instead of build3.
	(build_java_monitor): Use build_call_nary instead of build3.
	(java_create_object): Likewise.
	(expand_java_NEW): Likewise.
	(build_instanceof): Likewise.
	(expand_java_CHECKCAST): Likewise.
	(build_java_soft_divmod): Likewise.
	(build_java_binop): Likewise.
	(build_field_ref): Likewise.
	(build_class_init): Likewise.
	(rewrite_arglist_getcaller): Use build_call_expr.
	(build_invokeinterface):  Use build_call_nary instead of build3.
	(expand_invoke): Use build_call_list instead of build3.
	(build_jni_stub): Use build_call_nary, build_call_list, or
	build_call_expr instead	of build3.
	(expand_java_field_op): Use build_call_expr instead of build3.
	(force_evaluation_order): Use new CALL_EXPR accessors.

	* lang.c (java_get_callee_fndecl): Use new CALL_EXPR accessors.

Index: gcc/java/java-tree.h
===================================================================
*** gcc/java/java-tree.h	(revision 121818)
--- gcc/java/java-tree.h	(working copy)
*************** extern tree *type_map;
*** 1626,1645 ****
  
  #define BUILD_MONITOR_ENTER(WHERE, ARG)					\
    {									\
!     (WHERE) = build3 (CALL_EXPR, int_type_node,				\
! 		      build_address_of (soft_monitorenter_node),	\
! 		      build_tree_list (NULL_TREE, (ARG)),	 	\
! 		      NULL_TREE);					\
      TREE_SIDE_EFFECTS (WHERE) = 1;					\
    }
  
! #define BUILD_MONITOR_EXIT(WHERE, ARG)				\
!   {								\
!     (WHERE) = build3 (CALL_EXPR, int_type_node,			\
! 		      build_address_of (soft_monitorexit_node),	\
! 		      build_tree_list (NULL_TREE, (ARG)),	\
! 		      NULL_TREE);				\
!     TREE_SIDE_EFFECTS (WHERE) = 1;				\
    }
  
  /* True when we can perform static class initialization optimization */
--- 1626,1643 ----
  
  #define BUILD_MONITOR_ENTER(WHERE, ARG)					\
    {									\
!     (WHERE) = build_call_nary (int_type_node,				\
! 			       build_address_of (soft_monitorenter_node), \
! 			       1, (ARG));				\
      TREE_SIDE_EFFECTS (WHERE) = 1;					\
    }
  
! #define BUILD_MONITOR_EXIT(WHERE, ARG)					\
!   {									\
!     (WHERE) = build_call_nary (int_type_node,				\
! 			       build_address_of (soft_monitorexit_node), \
! 			       1, (ARG));				\
!     TREE_SIDE_EFFECTS (WHERE) = 1;					\
    }
  
  /* True when we can perform static class initialization optimization */
Index: gcc/java/java-gimplify.c
===================================================================
*** gcc/java/java-gimplify.c	(revision 121818)
--- gcc/java/java-gimplify.c	(working copy)
*************** java_gimplify_component_ref (tree *expr_
*** 212,221 ****
      if (stat == GS_ERROR)
        return stat;
  
!     sync_expr 
!       = build3 (CALL_EXPR, void_type_node,
! 		build_address_of (built_in_decls[BUILT_IN_SYNCHRONIZE]),
! 		NULL_TREE, NULL_TREE);
      TREE_SIDE_EFFECTS (sync_expr) = 1;
      *expr_p = build2 (COMPOUND_EXPR, TREE_TYPE (*expr_p),
  		      sync_expr, *expr_p);
--- 212,218 ----
      if (stat == GS_ERROR)
        return stat;
  
!     sync_expr = build_call_expr (built_in_decls[BUILT_IN_SYNCHRONIZE], 0);
      TREE_SIDE_EFFECTS (sync_expr) = 1;
      *expr_p = build2 (COMPOUND_EXPR, TREE_TYPE (*expr_p),
  		      sync_expr, *expr_p);
*************** java_gimplify_modify_expr (tree *modify_
*** 255,264 ****
        */
    
        enum gimplify_status stat;
!       tree sync_expr 
! 	= build3 (CALL_EXPR, void_type_node,
! 		  build_address_of (built_in_decls[BUILT_IN_SYNCHRONIZE]),
! 		  NULL_TREE, NULL_TREE);
        TREE_SIDE_EFFECTS (sync_expr) = 1;
  
        stat = gimplify_expr (&rhs, pre_p, post_p,
--- 252,259 ----
        */
    
        enum gimplify_status stat;
!       tree sync_expr =
! 	build_call_expr (built_in_decls[BUILT_IN_SYNCHRONIZE], 0);
        TREE_SIDE_EFFECTS (sync_expr) = 1;
  
        stat = gimplify_expr (&rhs, pre_p, post_p,
Index: gcc/java/class.c
===================================================================
*** gcc/java/class.c	(revision 121818)
--- gcc/java/class.c	(working copy)
*************** cache_this_class_ref (tree fndecl)
*** 1039,1048 ****
        && ! DECL_CLINIT_P (fndecl)
        && ! CLASS_INTERFACE (TYPE_NAME (DECL_CONTEXT (fndecl))))
      {
!       tree init = build3 (CALL_EXPR, void_type_node,
! 			  build_address_of (soft_initclass_node),
! 			  build_tree_list (NULL_TREE, this_classdollar),
! 			  NULL_TREE);
        java_add_stmt (init);
      }
  }
--- 1039,1046 ----
        && ! DECL_CLINIT_P (fndecl)
        && ! CLASS_INTERFACE (TYPE_NAME (DECL_CONTEXT (fndecl))))
      {
!       tree init = build_call_expr (soft_initclass_node, 1,
! 				   this_classdollar);
        java_add_stmt (init);
      }
  }
*************** build_static_field_ref (tree fdecl)
*** 1177,1196 ****
  
        int cpool_index = alloc_constant_fieldref (output_class, fdecl);
        tree cache_entry = build_fieldref_cache_entry (cpool_index, fdecl);
!       tree test 
! 	= build3 (CALL_EXPR, boolean_type_node, 
! 		  build_address_of (built_in_decls[BUILT_IN_EXPECT]),
! 		  tree_cons (NULL_TREE, build2 (EQ_EXPR, boolean_type_node,
! 						cache_entry, null_pointer_node),
! 			     build_tree_list (NULL_TREE, boolean_false_node)),
! 		  NULL_TREE);
        tree cpool_index_cst = build_int_cst (NULL_TREE, cpool_index);
        tree init
! 	= build3 (CALL_EXPR, ptr_type_node,
! 		  build_address_of (soft_resolvepoolentry_node),
! 		  tree_cons (NULL_TREE, build_class_ref (output_class),
! 			     build_tree_list (NULL_TREE, cpool_index_cst)),
! 		  NULL_TREE);
        init = build2 (MODIFY_EXPR, ptr_type_node, cache_entry, init);
        init = build3 (COND_EXPR, ptr_type_node, test, init, cache_entry);
        init = fold_convert (build_pointer_type (TREE_TYPE (fdecl)), init);
--- 1175,1190 ----
  
        int cpool_index = alloc_constant_fieldref (output_class, fdecl);
        tree cache_entry = build_fieldref_cache_entry (cpool_index, fdecl);
!       tree test
!         = build_call_expr (built_in_decls[BUILT_IN_EXPECT], 2,
! 			   build2 (EQ_EXPR, boolean_type_node,
! 				   cache_entry, null_pointer_node),
! 			   boolean_false_node);
        tree cpool_index_cst = build_int_cst (NULL_TREE, cpool_index);
        tree init
! 	= build_call_expr (soft_resolvepoolentry_node, 2,
! 			   build_class_ref (output_class),
! 			   cpool_index_cst);
        init = build2 (MODIFY_EXPR, ptr_type_node, cache_entry, init);
        init = build3 (COND_EXPR, ptr_type_node, test, init, cache_entry);
        init = fold_convert (build_pointer_type (TREE_TYPE (fdecl)), init);
*************** emit_indirect_register_classes (tree *li
*** 2693,2700 ****
    TREE_PUBLIC (t) = 1;
    DECL_EXTERNAL (t) = 1;
    register_class_fn = t;
!   t = tree_cons (NULL, reg_class_list, NULL);
!   t = build_function_call_expr (register_class_fn, t);
    append_to_statement_list (t, list_p);
  }
  
--- 2687,2693 ----
    TREE_PUBLIC (t) = 1;
    DECL_EXTERNAL (t) = 1;
    register_class_fn = t;
!   t = build_call_expr (register_class_fn, 1, reg_class_list);
    append_to_statement_list (t, list_p);
  }
  
*************** emit_register_classes (tree *list_p)
*** 2759,2766 ****
        for (i = 0; VEC_iterate (tree, registered_class, i, klass); ++i)
  	{
  	  t = build_fold_addr_expr (klass);
! 	  t = tree_cons (NULL, t, NULL);
! 	  t = build_function_call_expr (register_class_fn, t);
  	  append_to_statement_list (t, list_p);
  	}
      }
--- 2752,2758 ----
        for (i = 0; VEC_iterate (tree, registered_class, i, klass); ++i)
  	{
  	  t = build_fold_addr_expr (klass);
! 	  t = build_call_expr (register_class_fn, 1, t);
  	  append_to_statement_list (t, list_p);
  	}
      }
Index: gcc/java/resource.c
===================================================================
*** gcc/java/resource.c	(revision 121818)
--- gcc/java/resource.c	(working copy)
*************** write_resource_constructor (tree *list_p
*** 116,123 ****
    for (iter = nreverse (resources); iter ; iter = TREE_CHAIN (iter))
      {
        t = build_fold_addr_expr (TREE_VALUE (iter));
!       t = tree_cons (NULL, t, NULL);
!       t = build_function_call_expr (register_resource_fn, t);
        append_to_statement_list (t, list_p);
      }
  }
--- 116,122 ----
    for (iter = nreverse (resources); iter ; iter = TREE_CHAIN (iter))
      {
        t = build_fold_addr_expr (TREE_VALUE (iter));
!       t = build_call_expr (register_resource_fn, 1, t);
        append_to_statement_list (t, list_p);
      }
  }
Index: gcc/java/builtins.c
===================================================================
*** gcc/java/builtins.c	(revision 121818)
--- gcc/java/builtins.c	(working copy)
*************** static tree VMSupportsCS8_builtin (tree,
*** 60,66 ****
  /* Functions of this type are used to inline a given call.  Such a
     function should either return an expression, if the call is to be
     inlined, or NULL_TREE if a real call should be emitted.  Arguments
!    are method return type and arguments to call.  */
  typedef tree builtin_creator_function (tree, tree);
  
  /* Hold a char*, before initialization, or a tree, after
--- 60,67 ----
  /* Functions of this type are used to inline a given call.  Such a
     function should either return an expression, if the call is to be
     inlined, or NULL_TREE if a real call should be emitted.  Arguments
!    are method return type and the original CALL_EXPR containing the
!    arguments to the call.  */
  typedef tree builtin_creator_function (tree, tree);
  
  /* Hold a char*, before initialization, or a tree, after
*************** static GTY(()) struct builtin_record jav
*** 130,179 ****
  /* Internal functions which implement various builtin conversions.  */
  
  static tree
! max_builtin (tree method_return_type, tree method_arguments)
  {
    /* MAX_EXPR does not handle -0.0 in the Java style.  */
    if (TREE_CODE (method_return_type) == REAL_TYPE)
      return NULL_TREE;
    return fold_build2 (MAX_EXPR, method_return_type,
! 		      TREE_VALUE (method_arguments),
! 		      TREE_VALUE (TREE_CHAIN (method_arguments)));
  }
  
  static tree
! min_builtin (tree method_return_type, tree method_arguments)
  {
    /* MIN_EXPR does not handle -0.0 in the Java style.  */
    if (TREE_CODE (method_return_type) == REAL_TYPE)
      return NULL_TREE;
    return fold_build2 (MIN_EXPR, method_return_type,
! 		      TREE_VALUE (method_arguments),
! 		      TREE_VALUE (TREE_CHAIN (method_arguments)));
  }
  
  static tree
! abs_builtin (tree method_return_type, tree method_arguments)
  {
    return fold_build1 (ABS_EXPR, method_return_type,
! 		      TREE_VALUE (method_arguments));
  }
  
! /* Mostly copied from ../builtins.c.  */
  static tree
! java_build_function_call_expr (tree fn, tree arglist)
  {
!   tree call_expr;
! 
!   call_expr = build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (fn)), fn);
!   return fold_build3 (CALL_EXPR, TREE_TYPE (TREE_TYPE (fn)),
! 		      call_expr, arglist, NULL_TREE);
  }
  
  static tree
! convert_real (tree method_return_type, tree method_arguments)
  {
    return build1 (VIEW_CONVERT_EXPR, method_return_type,
! 		 TREE_VALUE (method_arguments));
  }
  
  
--- 131,203 ----
  /* Internal functions which implement various builtin conversions.  */
  
  static tree
! max_builtin (tree method_return_type, tree orig_call)
  {
    /* MAX_EXPR does not handle -0.0 in the Java style.  */
    if (TREE_CODE (method_return_type) == REAL_TYPE)
      return NULL_TREE;
    return fold_build2 (MAX_EXPR, method_return_type,
! 		      CALL_EXPR_ARG (orig_call, 0),
! 		      CALL_EXPR_ARG (orig_call, 1));
  }
  
  static tree
! min_builtin (tree method_return_type, tree orig_call)
  {
    /* MIN_EXPR does not handle -0.0 in the Java style.  */
    if (TREE_CODE (method_return_type) == REAL_TYPE)
      return NULL_TREE;
    return fold_build2 (MIN_EXPR, method_return_type,
! 		      CALL_EXPR_ARG (orig_call, 0),
! 		      CALL_EXPR_ARG (orig_call, 1));
  }
  
  static tree
! abs_builtin (tree method_return_type, tree orig_call)
  {
    return fold_build1 (ABS_EXPR, method_return_type,
! 		      CALL_EXPR_ARG (orig_call, 0));
  }
  
! /* Construct a new call to FN using the arguments from ORIG_CALL.  */
! 
  static tree
! java_build_function_call_expr (tree fn, tree orig_call)
  {
!   int nargs = call_expr_nargs (orig_call);
!   switch (nargs)
!     {
!       /* Although we could handle the 0-3 argument cases using the general
! 	 logic in the default case, splitting them out permits folding to
! 	 be performed without constructing a temporary CALL_EXPR.  */
!     case 0:
!       return build_call_expr (fn, 0);
!     case 1:
!       return build_call_expr (fn, 1, CALL_EXPR_ARG (orig_call, 0));
!     case 2:
!       return build_call_expr (fn, 2,
! 			      CALL_EXPR_ARG (orig_call, 0),
! 			      CALL_EXPR_ARG (orig_call, 1));
!     case 3:
!       return build_call_expr (fn, 3,
! 			      CALL_EXPR_ARG (orig_call, 0),
! 			      CALL_EXPR_ARG (orig_call, 1),
! 			      CALL_EXPR_ARG (orig_call, 2));
!     default:
!       {
! 	tree fntype = TREE_TYPE (fn);
! 	fn = build1 (ADDR_EXPR, build_pointer_type (fntype), fn);
! 	return fold (build_call_array (TREE_TYPE (fntype),
! 				       fn, nargs, CALL_EXPR_ARGP (orig_call)));
!       }
!     }
  }
  
  static tree
! convert_real (tree method_return_type, tree orig_call)
  {
    return build1 (VIEW_CONVERT_EXPR, method_return_type,
! 		 CALL_EXPR_ARG (orig_call, 0));
  }
  
  
*************** convert_real (tree method_return_type, t
*** 191,266 ****
  */
  
  
! /* Macros to unmarshal arguments from a TREE_LIST into a few
     variables.  We also convert the offset arg from a long to an
     integer that is the same size as a pointer.  */
  
! #define UNMARSHAL3(METHOD_ARGUMENTS)					\
  tree this_arg, obj_arg, offset_arg;					\
  do									\
  {									\
!   tree chain = METHOD_ARGUMENTS;					\
!   this_arg = TREE_VALUE (chain);					\
!   chain = TREE_CHAIN (chain);						\
!   obj_arg = TREE_VALUE (chain);						\
!   chain = TREE_CHAIN (chain);						\
    offset_arg = fold_convert (java_type_for_size (POINTER_SIZE, 0),	\
! 			     TREE_VALUE (chain));			\
  }									\
  while (0)
  
! #define UNMARSHAL4(METHOD_ARGUMENTS)					\
  tree value_type, this_arg, obj_arg, offset_arg, value_arg;		\
  do									\
  {									\
!   tree chain = METHOD_ARGUMENTS;					\
!   this_arg = TREE_VALUE (chain);					\
!   chain = TREE_CHAIN (chain);						\
!   obj_arg = TREE_VALUE (chain);						\
!   chain = TREE_CHAIN (chain);						\
    offset_arg = fold_convert (java_type_for_size (POINTER_SIZE, 0),	\
! 			     TREE_VALUE (chain));			\
!   chain = TREE_CHAIN (chain);						\
!   value_arg = TREE_VALUE (chain);					\
    value_type = TREE_TYPE (value_arg);					\
  }									\
  while (0)
  
! #define UNMARSHAL5(METHOD_ARGUMENTS)					\
  tree value_type, this_arg, obj_arg, offset_arg, expected_arg, value_arg; \
  do									\
  {									\
!   tree chain = METHOD_ARGUMENTS;					\
!   this_arg = TREE_VALUE (chain);					\
!   chain = TREE_CHAIN (chain);						\
!   obj_arg = TREE_VALUE (chain);						\
!   chain = TREE_CHAIN (chain);						\
    offset_arg = fold_convert (java_type_for_size (POINTER_SIZE, 0),	\
! 			     TREE_VALUE (chain));			\
!   chain = TREE_CHAIN (chain);						\
!   expected_arg = TREE_VALUE (chain);					\
!   chain = TREE_CHAIN (chain);						\
!   value_arg = TREE_VALUE (chain);					\
    value_type = TREE_TYPE (value_arg);					\
  }									\
  while (0)
  
- /* Construct an arglist from a call.  */
- 
- static tree
- build_arglist_for_builtin (tree arg, ...)
- {
-   va_list ap;
-   tree nextarg;
-   tree newarglist = build_tree_list (NULL_TREE, arg);
- 
-   va_start(ap, arg);
-   while ((nextarg = va_arg(ap, tree)))
-     newarglist = tree_cons (NULL_TREE, nextarg, newarglist);
- 
-   return nreverse (newarglist);
- }
- 
  /* Add an address to an offset, forming a sum.  */
  
  static tree
--- 215,265 ----
  */
  
  
! /* Macros to unmarshal arguments from a CALL_EXPR into a few
     variables.  We also convert the offset arg from a long to an
     integer that is the same size as a pointer.  */
  
! #define UNMARSHAL3(METHOD_CALL)					\
  tree this_arg, obj_arg, offset_arg;					\
  do									\
  {									\
!   tree orig_method_call = METHOD_CALL;					\
!   this_arg = CALL_EXPR_ARG (orig_method_call, 0);			\
!   obj_arg = CALL_EXPR_ARG (orig_method_call, 1);			\
    offset_arg = fold_convert (java_type_for_size (POINTER_SIZE, 0),	\
! 			     CALL_EXPR_ARG (orig_method_call, 2));	\
  }									\
  while (0)
  
! #define UNMARSHAL4(METHOD_CALL)					\
  tree value_type, this_arg, obj_arg, offset_arg, value_arg;		\
  do									\
  {									\
!   tree orig_method_call = METHOD_CALL;					\
!   this_arg = CALL_EXPR_ARG (orig_method_call, 0);			\
!   obj_arg = CALL_EXPR_ARG (orig_method_call, 1);			\
    offset_arg = fold_convert (java_type_for_size (POINTER_SIZE, 0),	\
! 			     CALL_EXPR_ARG (orig_method_call, 2));	\
!   value_arg = CALL_EXPR_ARG (orig_method_call, 3);			\
    value_type = TREE_TYPE (value_arg);					\
  }									\
  while (0)
  
! #define UNMARSHAL5(METHOD_CALL)					\
  tree value_type, this_arg, obj_arg, offset_arg, expected_arg, value_arg; \
  do									\
  {									\
!   tree orig_method_call = METHOD_CALL;					\
!   this_arg = CALL_EXPR_ARG (orig_method_call, 0);			\
!   obj_arg = CALL_EXPR_ARG (orig_method_call, 1);			\
    offset_arg = fold_convert (java_type_for_size (POINTER_SIZE, 0),	\
! 			     CALL_EXPR_ARG (orig_method_call, 2));	\
!   expected_arg = CALL_EXPR_ARG (orig_method_call, 3);			\
!   value_arg = CALL_EXPR_ARG (orig_method_call, 4);			\
    value_type = TREE_TYPE (value_arg);					\
  }									\
  while (0)
  
  /* Add an address to an offset, forming a sum.  */
  
  static tree
*************** build_check_this (tree stmt, tree this_a
*** 286,295 ****
  
  static tree
  putObject_builtin (tree method_return_type ATTRIBUTE_UNUSED, 
! 		   tree method_arguments)
  {
    tree addr, stmt;
!   UNMARSHAL4 (method_arguments);
  
    addr = build_addr_sum (value_type, obj_arg, offset_arg);
    stmt = fold_build2 (MODIFY_EXPR, value_type,
--- 285,294 ----
  
  static tree
  putObject_builtin (tree method_return_type ATTRIBUTE_UNUSED, 
! 		   tree orig_call)
  {
    tree addr, stmt;
!   UNMARSHAL4 (orig_call);
  
    addr = build_addr_sum (value_type, obj_arg, offset_arg);
    stmt = fold_build2 (MODIFY_EXPR, value_type,
*************** putObject_builtin (tree method_return_ty
*** 302,323 ****
  
  static tree
  compareAndSwapInt_builtin (tree method_return_type ATTRIBUTE_UNUSED,
! 			   tree method_arguments)
  {
    enum machine_mode mode = TYPE_MODE (int_type_node);
    if (sync_compare_and_swap_cc[mode] != CODE_FOR_nothing 
        || sync_compare_and_swap[mode] != CODE_FOR_nothing)
      {
!       tree newarglist, addr, stmt;
!       UNMARSHAL5 (method_arguments);
  
        addr = build_addr_sum (int_type_node, obj_arg, offset_arg);
! 
!       newarglist 
! 	= build_arglist_for_builtin (addr, expected_arg, value_arg, NULL_TREE);
!       stmt = (build_function_call_expr
! 	      (built_in_decls[BUILT_IN_BOOL_COMPARE_AND_SWAP_4],
! 	       newarglist));
  
        return build_check_this (stmt, this_arg);
      }
--- 301,318 ----
  
  static tree
  compareAndSwapInt_builtin (tree method_return_type ATTRIBUTE_UNUSED,
! 			   tree orig_call)
  {
    enum machine_mode mode = TYPE_MODE (int_type_node);
    if (sync_compare_and_swap_cc[mode] != CODE_FOR_nothing 
        || sync_compare_and_swap[mode] != CODE_FOR_nothing)
      {
!       tree addr, stmt;
!       UNMARSHAL5 (orig_call);
  
        addr = build_addr_sum (int_type_node, obj_arg, offset_arg);
!       stmt = build_call_expr (built_in_decls[BUILT_IN_BOOL_COMPARE_AND_SWAP_4],
! 			      3, addr, expected_arg, value_arg);
  
        return build_check_this (stmt, this_arg);
      }
*************** compareAndSwapInt_builtin (tree method_r
*** 326,347 ****
  
  static tree
  compareAndSwapLong_builtin (tree method_return_type ATTRIBUTE_UNUSED,
! 			    tree method_arguments)
  {
    enum machine_mode mode = TYPE_MODE (long_type_node);
    if (sync_compare_and_swap_cc[mode] != CODE_FOR_nothing 
        || sync_compare_and_swap[mode] != CODE_FOR_nothing)
      {
!       tree newarglist, addr, stmt;
!       UNMARSHAL5 (method_arguments);
  
        addr = build_addr_sum (long_type_node, obj_arg, offset_arg);
! 
!       newarglist 
! 	= build_arglist_for_builtin (addr, expected_arg, value_arg, NULL_TREE);
!       stmt = (build_function_call_expr
! 	      (built_in_decls[BUILT_IN_BOOL_COMPARE_AND_SWAP_8],
! 	       newarglist));
  
        return build_check_this (stmt, this_arg);
      }
--- 321,338 ----
  
  static tree
  compareAndSwapLong_builtin (tree method_return_type ATTRIBUTE_UNUSED,
! 			    tree orig_call)
  {
    enum machine_mode mode = TYPE_MODE (long_type_node);
    if (sync_compare_and_swap_cc[mode] != CODE_FOR_nothing 
        || sync_compare_and_swap[mode] != CODE_FOR_nothing)
      {
!       tree addr, stmt;
!       UNMARSHAL5 (orig_call);
  
        addr = build_addr_sum (long_type_node, obj_arg, offset_arg);
!       stmt = build_call_expr (built_in_decls[BUILT_IN_BOOL_COMPARE_AND_SWAP_8],
! 			      3, addr, expected_arg, value_arg);
  
        return build_check_this (stmt, this_arg);
      }
*************** compareAndSwapLong_builtin (tree method_
*** 349,375 ****
  }
  static tree
  compareAndSwapObject_builtin (tree method_return_type ATTRIBUTE_UNUSED, 
! 			      tree method_arguments)
  {
    enum machine_mode mode = TYPE_MODE (ptr_type_node);
    if (sync_compare_and_swap_cc[mode] != CODE_FOR_nothing 
        || sync_compare_and_swap[mode] != CODE_FOR_nothing)
    {
!     tree newarglist, addr, stmt;
      int builtin;
  
!     UNMARSHAL5 (method_arguments);
      builtin = (POINTER_SIZE == 32 
  	       ? BUILT_IN_BOOL_COMPARE_AND_SWAP_4 
  	       : BUILT_IN_BOOL_COMPARE_AND_SWAP_8);
  
      addr = build_addr_sum (value_type, obj_arg, offset_arg);
! 
!     newarglist 
!       = build_arglist_for_builtin (addr, expected_arg, value_arg, NULL_TREE);
!     stmt = (build_function_call_expr
! 	    (built_in_decls[builtin],
! 	     newarglist));
  
      return build_check_this (stmt, this_arg);
    }
--- 340,362 ----
  }
  static tree
  compareAndSwapObject_builtin (tree method_return_type ATTRIBUTE_UNUSED, 
! 			      tree orig_call)
  {
    enum machine_mode mode = TYPE_MODE (ptr_type_node);
    if (sync_compare_and_swap_cc[mode] != CODE_FOR_nothing 
        || sync_compare_and_swap[mode] != CODE_FOR_nothing)
    {
!     tree addr, stmt;
      int builtin;
  
!     UNMARSHAL5 (orig_call);
      builtin = (POINTER_SIZE == 32 
  	       ? BUILT_IN_BOOL_COMPARE_AND_SWAP_4 
  	       : BUILT_IN_BOOL_COMPARE_AND_SWAP_8);
  
      addr = build_addr_sum (value_type, obj_arg, offset_arg);
!     stmt = build_call_expr (built_in_decls[builtin],
! 			    3, addr, expected_arg, value_arg);
  
      return build_check_this (stmt, this_arg);
    }
*************** compareAndSwapObject_builtin (tree metho
*** 378,397 ****
  
  static tree
  putVolatile_builtin (tree method_return_type ATTRIBUTE_UNUSED, 
! 		     tree method_arguments)
  {
!   tree newarglist, addr, stmt, modify_stmt;
!   UNMARSHAL4 (method_arguments);
    
    addr = build_addr_sum (value_type, obj_arg, offset_arg);
    addr 
      = fold_convert (build_pointer_type (build_type_variant (value_type, 0, 1)),
  		    addr);
    
!   newarglist = NULL_TREE;
!   stmt = (build_function_call_expr
! 	  (built_in_decls[BUILT_IN_SYNCHRONIZE],
! 	   newarglist));
    modify_stmt = fold_build2 (MODIFY_EXPR, value_type,
  			     build_java_indirect_ref (value_type, addr,
  						      flag_check_references),
--- 365,381 ----
  
  static tree
  putVolatile_builtin (tree method_return_type ATTRIBUTE_UNUSED, 
! 		     tree orig_call)
  {
!   tree addr, stmt, modify_stmt;
!   UNMARSHAL4 (orig_call);
    
    addr = build_addr_sum (value_type, obj_arg, offset_arg);
    addr 
      = fold_convert (build_pointer_type (build_type_variant (value_type, 0, 1)),
  		    addr);
    
!   stmt = build_call_expr (built_in_decls[BUILT_IN_SYNCHRONIZE], 0);
    modify_stmt = fold_build2 (MODIFY_EXPR, value_type,
  			     build_java_indirect_ref (value_type, addr,
  						      flag_check_references),
*************** putVolatile_builtin (tree method_return_
*** 404,423 ****
  
  static tree
  getVolatile_builtin (tree method_return_type ATTRIBUTE_UNUSED, 
! 		     tree method_arguments)
  {
!   tree newarglist, addr, stmt, modify_stmt, tmp;
!   UNMARSHAL3 (method_arguments);
    
    addr = build_addr_sum (method_return_type, obj_arg, offset_arg);
    addr 
      = fold_convert (build_pointer_type (build_type_variant 
  					(method_return_type, 0, 1)), addr);
    
!   newarglist = NULL_TREE;
!   stmt = (build_function_call_expr
! 	  (built_in_decls[BUILT_IN_SYNCHRONIZE],
! 	   newarglist));
    
    tmp = build_decl (VAR_DECL, NULL, method_return_type);
    DECL_IGNORED_P (tmp) = 1;
--- 388,404 ----
  
  static tree
  getVolatile_builtin (tree method_return_type ATTRIBUTE_UNUSED, 
! 		     tree orig_call)
  {
!   tree addr, stmt, modify_stmt, tmp;
!   UNMARSHAL3 (orig_call);
    
    addr = build_addr_sum (method_return_type, obj_arg, offset_arg);
    addr 
      = fold_convert (build_pointer_type (build_type_variant 
  					(method_return_type, 0, 1)), addr);
    
!   stmt = build_call_expr (built_in_decls[BUILT_IN_SYNCHRONIZE], 0);
    
    tmp = build_decl (VAR_DECL, NULL, method_return_type);
    DECL_IGNORED_P (tmp) = 1;
*************** getVolatile_builtin (tree method_return_
*** 437,443 ****
  
  static tree
  VMSupportsCS8_builtin (tree method_return_type, 
! 		       tree method_arguments ATTRIBUTE_UNUSED)
  {
    enum machine_mode mode = TYPE_MODE (long_type_node);
    gcc_assert (method_return_type == boolean_type_node);
--- 418,424 ----
  
  static tree
  VMSupportsCS8_builtin (tree method_return_type, 
! 		       tree orig_call ATTRIBUTE_UNUSED)
  {
    enum machine_mode mode = TYPE_MODE (long_type_node);
    gcc_assert (method_return_type == boolean_type_node);
*************** check_for_builtin (tree method, tree cal
*** 596,602 ****
    if (optimize && TREE_CODE (call) == CALL_EXPR)
      {
        int i;
-       tree method_arguments = TREE_OPERAND (call, 1);
        tree method_class = DECL_NAME (TYPE_NAME (DECL_CONTEXT (method)));
        tree method_name = DECL_NAME (method);
        tree method_return_type = TREE_TYPE (TREE_TYPE (method));
--- 577,582 ----
*************** check_for_builtin (tree method, tree cal
*** 611,618 ****
  	      if (java_builtins[i].creator != NULL)
  		{
  		  tree result
! 		    = (*java_builtins[i].creator) (method_return_type,
! 						   method_arguments);
  		  return result == NULL_TREE ? call : result;
  		}
  
--- 591,597 ----
  	      if (java_builtins[i].creator != NULL)
  		{
  		  tree result
! 		    = (*java_builtins[i].creator) (method_return_type, call);
  		  return result == NULL_TREE ? call : result;
  		}
  
*************** check_for_builtin (tree method, tree cal
*** 623,629 ****
  	      fn = built_in_decls[java_builtins[i].builtin_code];
  	      if (fn == NULL_TREE)
  		return call;
! 	      return java_build_function_call_expr (fn, method_arguments);
  	    }
  	}
      }
--- 602,608 ----
  	      fn = built_in_decls[java_builtins[i].builtin_code];
  	      if (fn == NULL_TREE)
  		return call;
! 	      return java_build_function_call_expr (fn, call);
  	    }
  	}
      }
Index: gcc/java/expr.c
===================================================================
*** gcc/java/expr.c	(revision 121818)
--- gcc/java/expr.c	(working copy)
*************** build_java_athrow (tree node)
*** 716,726 ****
  {
    tree call;
  
!   call = build3 (CALL_EXPR,
! 		 void_type_node,
! 		 build_address_of (throw_node),
! 		 build_tree_list (NULL_TREE, node),
! 		 NULL_TREE);
    TREE_SIDE_EFFECTS (call) = 1;
    java_add_stmt (call);
    java_stack_pop (stack_pointer);
--- 716,724 ----
  {
    tree call;
  
!   call = build_call_nary (void_type_node,
! 			  build_address_of (throw_node),
! 			  1, node);
    TREE_SIDE_EFFECTS (call) = 1;
    java_add_stmt (call);
    java_stack_pop (stack_pointer);
*************** encode_newarray_type (tree type)
*** 799,807 ****
  static tree
  build_java_throw_out_of_bounds_exception (tree index)
  {
!   tree node = build3 (CALL_EXPR, int_type_node,
! 		      build_address_of (soft_badarrayindex_node), 
! 		      build_tree_list (NULL_TREE, index), NULL_TREE);
    TREE_SIDE_EFFECTS (node) = 1;	/* Allows expansion within ANDIF */
    return (node);
  }
--- 797,805 ----
  static tree
  build_java_throw_out_of_bounds_exception (tree index)
  {
!   tree node = build_call_nary (int_type_node,
! 			       build_address_of (soft_badarrayindex_node),
! 			       1, index);
    TREE_SIDE_EFFECTS (node) = 1;	/* Allows expansion within ANDIF */
    return (node);
  }
*************** java_check_reference (tree expr, int che
*** 850,858 ****
        expr = build3 (COND_EXPR, TREE_TYPE (expr),
  		     build2 (EQ_EXPR, boolean_type_node,
  			     expr, null_pointer_node),
! 		     build3 (CALL_EXPR, void_type_node, 
! 			     build_address_of (soft_nullpointer_node),
! 			     NULL_TREE, NULL_TREE),
  		     expr);
      }
  
--- 848,856 ----
        expr = build3 (COND_EXPR, TREE_TYPE (expr),
  		     build2 (EQ_EXPR, boolean_type_node,
  			     expr, null_pointer_node),
! 		     build_call_nary (void_type_node, 
! 				      build_address_of (soft_nullpointer_node),
! 				      0),
  		     expr);
      }
  
*************** build_java_arraystore_check (tree array,
*** 1014,1024 ****
      }
  
    /* Build an invocation of _Jv_CheckArrayStore */
!   check = build3 (CALL_EXPR, void_type_node,
! 		  build_address_of (soft_checkarraystore_node),
! 		  tree_cons (NULL_TREE, array,
! 			     build_tree_list (NULL_TREE, object)),
! 		  NULL_TREE);
    TREE_SIDE_EFFECTS (check) = 1;
  
    return check;
--- 1012,1020 ----
      }
  
    /* Build an invocation of _Jv_CheckArrayStore */
!   check = build_call_nary (void_type_node,
! 			   build_address_of (soft_checkarraystore_node),
! 			   2, array, object);
    TREE_SIDE_EFFECTS (check) = 1;
  
    return check;
*************** build_newarray (int atype_value, tree le
*** 1060,1071 ****
       some work.  */
    type_arg = build_class_ref (prim_type);
  
!   return build3 (CALL_EXPR, promote_type (type),
! 		 build_address_of (soft_newarray_node),
! 		 tree_cons (NULL_TREE, 
! 			    type_arg,
! 			    build_tree_list (NULL_TREE, length)),
! 		 NULL_TREE);
  }
  
  /* Generates anewarray from a given CLASS_TYPE. Gets from the stack the size
--- 1056,1064 ----
       some work.  */
    type_arg = build_class_ref (prim_type);
  
!   return build_call_nary (promote_type (type),
! 			  build_address_of (soft_newarray_node),
! 			  2, type_arg, length);
  }
  
  /* Generates anewarray from a given CLASS_TYPE. Gets from the stack the size
*************** build_anewarray (tree class_type, tree l
*** 1079,1091 ****
  			     host_integerp (length, 0)
  			     ? tree_low_cst (length, 0) : -1);
  
!   return build3 (CALL_EXPR, promote_type (type),
! 		 build_address_of (soft_anewarray_node),
! 		 tree_cons (NULL_TREE, length,
! 			    tree_cons (NULL_TREE, build_class_ref (class_type),
! 				       build_tree_list (NULL_TREE,
! 							null_pointer_node))),
! 		 NULL_TREE);
  }
  
  /* Return a node the evaluates 'new TYPE[LENGTH]'. */
--- 1072,1083 ----
  			     host_integerp (length, 0)
  			     ? tree_low_cst (length, 0) : -1);
  
!   return build_call_nary (promote_type (type),
! 			  build_address_of (soft_anewarray_node),
! 			  3,
! 			  length,
! 			  build_class_ref (class_type),
! 			  null_pointer_node);
  }
  
  /* Return a node the evaluates 'new TYPE[LENGTH]'. */
*************** expand_java_multianewarray (tree class_t
*** 1112,1125 ****
    for( i = 0; i < ndim; i++ )
      args = tree_cons (NULL_TREE, pop_value (int_type_node), args);
  
!   push_value (build3 (CALL_EXPR,
! 		      promote_type (class_type),
! 		      build_address_of (soft_multianewarray_node),
! 		      tree_cons (NULL_TREE, build_class_ref (class_type),
! 				 tree_cons (NULL_TREE, 
! 					    build_int_cst (NULL_TREE, ndim),
! 					    args)),
! 		      NULL_TREE));
  }
  
  /*  ARRAY[INDEX] <- RHS. build_java_check_indexed_type makes sure that
--- 1104,1118 ----
    for( i = 0; i < ndim; i++ )
      args = tree_cons (NULL_TREE, pop_value (int_type_node), args);
  
!   args = tree_cons (NULL_TREE,
! 		    build_class_ref (class_type),
! 		    tree_cons (NULL_TREE, 
! 			       build_int_cst (NULL_TREE, ndim),
! 			       args));
! 
!   push_value (build_call_list (promote_type (class_type),
! 			       build_address_of (soft_multianewarray_node),
! 			       args));
  }
  
  /*  ARRAY[INDEX] <- RHS. build_java_check_indexed_type makes sure that
*************** expand_java_array_length (void)
*** 1246,1256 ****
  static tree
  build_java_monitor (tree call, tree object)
  {
!   return build3 (CALL_EXPR,
! 		 void_type_node,
! 		 build_address_of (call),
! 		 build_tree_list (NULL_TREE, object),
! 		 NULL_TREE);
  }
  
  /* Emit code for one of the PUSHC instructions. */
--- 1239,1247 ----
  static tree
  build_java_monitor (tree call, tree object)
  {
!   return build_call_nary (void_type_node,
! 			  build_address_of (call),
! 			  1, object);
  }
  
  /* Emit code for one of the PUSHC instructions. */
*************** java_create_object (tree type)
*** 1347,1356 ****
  		     ? alloc_object_node
  		     : alloc_no_finalizer_node);
    
!   return build3 (CALL_EXPR, promote_type (type),
! 		 build_address_of (alloc_node),
! 		 build_tree_list (NULL_TREE, build_class_ref (type)),
! 		 NULL_TREE);
  }
  
  static void
--- 1338,1346 ----
  		     ? alloc_object_node
  		     : alloc_no_finalizer_node);
    
!   return build_call_nary (promote_type (type),
! 			  build_address_of (alloc_node),
! 			  1, build_class_ref (type));
  }
  
  static void
*************** expand_java_NEW (tree type)
*** 1363,1372 ****
    if (! CLASS_LOADED_P (type))
      load_class (type, 1);
    safe_layout_class (type);
!   push_value (build3 (CALL_EXPR, promote_type (type),
! 		      build_address_of (alloc_node),
! 		      build_tree_list (NULL_TREE, build_class_ref (type)),
! 		      NULL_TREE));
  }
  
  /* This returns an expression which will extract the class of an
--- 1353,1361 ----
    if (! CLASS_LOADED_P (type))
      load_class (type, 1);
    safe_layout_class (type);
!   push_value (build_call_nary (promote_type (type),
! 			       build_address_of (alloc_node),
! 			       1, build_class_ref (type)));
  }
  
  /* This returns an expression which will extract the class of an
*************** build_instanceof (tree value, tree type)
*** 1445,1456 ****
      }
    else
      {
!       expr = build3 (CALL_EXPR, itype,
! 		     build_address_of (soft_instanceof_node),
! 		     tree_cons (NULL_TREE, value,
! 				build_tree_list (NULL_TREE,
! 						 build_class_ref (type))),
! 		     NULL_TREE);
      }
    TREE_SIDE_EFFECTS (expr) = TREE_SIDE_EFFECTS (value);
    return expr;
--- 1434,1442 ----
      }
    else
      {
!       expr = build_call_nary (itype,
! 			      build_address_of (soft_instanceof_node),
! 			      2, value, build_class_ref (type));
      }
    TREE_SIDE_EFFECTS (expr) = TREE_SIDE_EFFECTS (value);
    return expr;
*************** static void
*** 1468,1478 ****
  expand_java_CHECKCAST (tree type)
  {
    tree value = pop_value (ptr_type_node);
!   value = build3 (CALL_EXPR, promote_type (type),
! 		  build_address_of (soft_checkcast_node),
! 		  tree_cons (NULL_TREE, build_class_ref (type),
! 			     build_tree_list (NULL_TREE, value)),
! 		  NULL_TREE);
    push_value (value);
  }
  
--- 1454,1462 ----
  expand_java_CHECKCAST (tree type)
  {
    tree value = pop_value (ptr_type_node);
!   value = build_call_nary (promote_type (type),
! 			   build_address_of (soft_checkcast_node),
! 			   2, build_class_ref (type), value);
    push_value (value);
  }
  
*************** build_java_soft_divmod (enum tree_code o
*** 1527,1538 ****
      }
  
    gcc_assert (call);
!   call = build3 (CALL_EXPR, type,
! 		 build_address_of (call),
! 		 tree_cons (NULL_TREE, arg1,
! 			    build_tree_list (NULL_TREE, arg2)),
! 		 NULL_TREE);
! 	  
    return call;
  }
  
--- 1511,1517 ----
      }
  
    gcc_assert (call);
!   call = build_call_nary (type, build_address_of (call), 2, arg1, arg2);
    return call;
  }
  
*************** build_java_binop (enum tree_code op, tre
*** 1595,1605 ****
  	      arg1 = convert (double_type_node, arg1);
  	      arg2 = convert (double_type_node, arg2);
  	    }
! 	  call = build3 (CALL_EXPR, double_type_node,
! 			 build_address_of (soft_fmod_node),
! 			 tree_cons (NULL_TREE, arg1,
! 				    build_tree_list (NULL_TREE, arg2)),
! 			 NULL_TREE);
  	  if (type != double_type_node)
  	    call = convert (type, call);
  	  return call;
--- 1574,1582 ----
  	      arg1 = convert (double_type_node, arg1);
  	      arg2 = convert (double_type_node, arg2);
  	    }
! 	  call = build_call_nary (double_type_node,
! 				  build_address_of (soft_fmod_node),
! 				  2, arg1, arg2);
  	  if (type != double_type_node)
  	    call = convert (type, call);
  	  return call;
*************** build_field_ref (tree self_value, tree s
*** 1759,1768 ****
  	      = build3 (COND_EXPR, TREE_TYPE (field_offset),
  			build2 (EQ_EXPR, boolean_type_node,
  				field_offset, integer_zero_node),
! 			build3 (CALL_EXPR, void_type_node, 
! 				build_address_of (soft_nosuchfield_node),
! 				build_tree_list (NULL_TREE, otable_index), 
! 				NULL_TREE),
  			field_offset);
  	  
  	  field_offset = fold (convert (sizetype, field_offset));
--- 1736,1744 ----
  	      = build3 (COND_EXPR, TREE_TYPE (field_offset),
  			build2 (EQ_EXPR, boolean_type_node,
  				field_offset, integer_zero_node),
! 			build_call_nary (void_type_node, 
! 					 build_address_of (soft_nosuchfield_node),
! 					 1, otable_index),
  			field_offset);
  	  
  	  field_offset = fold (convert (sizetype, field_offset));
*************** build_class_init (tree clas, tree expr)
*** 1998,2007 ****
  
    if (always_initialize_class_p)
      {
!       init = build3 (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
--- 1974,1982 ----
  
    if (always_initialize_class_p)
      {
!       init = build_call_nary (void_type_node,
! 			      build_address_of (soft_initclass_node),
! 			      1, build_class_ref (clas));
        TREE_SIDE_EFFECTS (init) = 1;
      }
    else
*************** build_class_init (tree clas, tree expr)
*** 2031,2040 ****
  	  *init_test_decl = decl;
  	}
  
!       init = build3 (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;
        init = build3 (COND_EXPR, void_type_node,
  		     build2 (EQ_EXPR, boolean_type_node, 
--- 2006,2014 ----
  	  *init_test_decl = decl;
  	}
  
!       init = build_call_nary (void_type_node,
! 			      build_address_of (soft_initclass_node),
! 			      1, build_class_ref (clas));
        TREE_SIDE_EFFECTS (init) = 1;
        init = build3 (COND_EXPR, void_type_node,
  		     build2 (EQ_EXPR, boolean_type_node, 
*************** static tree 
*** 2084,2092 ****
  rewrite_arglist_getcaller (tree arglist)
  {
    tree retaddr 
!     = (build_function_call_expr 
!        (built_in_decls[BUILT_IN_RETURN_ADDRESS],
! 	build_tree_list (NULL_TREE, integer_zero_node)));
    
    DECL_INLINE (current_function_decl) = 0;
  
--- 2058,2065 ----
  rewrite_arglist_getcaller (tree arglist)
  {
    tree retaddr 
!     = build_call_expr (built_in_decls[BUILT_IN_RETURN_ADDRESS],
! 		       1, integer_zero_node);
    
    DECL_INLINE (current_function_decl) = 0;
  
*************** static GTY(()) tree class_ident;
*** 2356,2362 ****
  tree
  build_invokeinterface (tree dtable, tree method)
  {
-   tree lookup_arg;
    tree interface;
    tree idx;
  
--- 2329,2334 ----
*************** build_invokeinterface (tree dtable, tree
*** 2401,2413 ****
        interface = build_class_ref (interface);
      }
  				     			  
!   lookup_arg = tree_cons (NULL_TREE, dtable,
! 			  tree_cons (NULL_TREE, interface,
! 				     build_tree_list (NULL_TREE, idx)));
! 
!   return build3 (CALL_EXPR, ptr_type_node, 
! 		 build_address_of (soft_lookupinterfacemethod_node),
! 		 lookup_arg, NULL_TREE);
  }
    
  /* Expand one of the invoke_* opcodes.
--- 2373,2381 ----
        interface = build_class_ref (interface);
      }
  				     			  
!   return build_call_nary (ptr_type_node, 
! 			  build_address_of (soft_lookupinterfacemethod_node),
! 			  3, dtable, interface, idx);
  }
    
  /* Expand one of the invoke_* opcodes.
*************** expand_invoke (int opcode, int method_re
*** 2590,2597 ****
    else
      func = build1 (NOP_EXPR, build_pointer_type (method_type), func);
  
!   call = build3 (CALL_EXPR, TREE_TYPE (method_type),
! 		 func, arg_list, NULL_TREE);
    TREE_SIDE_EFFECTS (call) = 1;
    call = check_for_builtin (method, call);
  
--- 2558,2564 ----
    else
      func = build1 (NOP_EXPR, build_pointer_type (method_type), func);
  
!   call = build_call_list (TREE_TYPE (method_type), func, arg_list);
    TREE_SIDE_EFFECTS (call) = 1;
    call = check_for_builtin (method, call);
  
*************** expand_invoke (int opcode, int method_re
*** 2616,2622 ****
  tree
  build_jni_stub (tree method)
  {
!   tree jnifunc, call, args, body, lookup_arg, method_sig, arg_types;
    tree jni_func_type, tem;
    tree env_var, res_var = NULL_TREE, block;
    tree method_args, res_type;
--- 2583,2590 ----
  tree
  build_jni_stub (tree method)
  {
!   tree jnifunc, call, args, body, method_sig, arg_types;
!   tree jniarg0, jniarg1, jniarg2, jniarg3;
    tree jni_func_type, tem;
    tree env_var, res_var = NULL_TREE, block;
    tree method_args, res_type;
*************** build_jni_stub (tree method)
*** 2671,2680 ****
  
    /* Compute the local `env' by calling _Jv_GetJNIEnvNewFrame.  */
    body = build2 (MODIFY_EXPR, ptr_type_node, env_var,
! 		 build3 (CALL_EXPR, ptr_type_node,
! 			 build_address_of (soft_getjnienvnewframe_node),
! 			 build_tree_list (NULL_TREE, klass),
! 			 NULL_TREE));
    CAN_COMPLETE_NORMALLY (body) = 1;
  
    /* All the arguments to this method become arguments to the
--- 2639,2647 ----
  
    /* Compute the local `env' by calling _Jv_GetJNIEnvNewFrame.  */
    body = build2 (MODIFY_EXPR, ptr_type_node, env_var,
! 		 build_call_nary (ptr_type_node,
! 				  build_address_of (soft_getjnienvnewframe_node),
! 				  1, klass));
    CAN_COMPLETE_NORMALLY (body) = 1;
  
    /* All the arguments to this method become arguments to the
*************** build_jni_stub (tree method)
*** 2713,2730 ****
    /* We call _Jv_LookupJNIMethod to find the actual underlying
       function pointer.  _Jv_LookupJNIMethod will throw the appropriate
       exception if this function is not found at runtime.  */
-   tem = build_tree_list (NULL_TREE, build_int_cst (NULL_TREE, args_size));
    method_sig = build_java_signature (TREE_TYPE (method));
!   lookup_arg = tree_cons (NULL_TREE,
!                           build_utf8_ref (unmangle_classname
!                                           (IDENTIFIER_POINTER (method_sig),
!                                            IDENTIFIER_LENGTH (method_sig))), 
!                           tem);
!   tem = DECL_NAME (method);
!   lookup_arg
!     = tree_cons (NULL_TREE, klass,
! 		 tree_cons (NULL_TREE, build_utf8_ref (tem), lookup_arg));
!   
    tem = build_function_type (TREE_TYPE (TREE_TYPE (method)), arg_types);
  
  #ifdef MODIFY_JNI_METHOD_CALL
--- 2680,2693 ----
    /* We call _Jv_LookupJNIMethod to find the actual underlying
       function pointer.  _Jv_LookupJNIMethod will throw the appropriate
       exception if this function is not found at runtime.  */
    method_sig = build_java_signature (TREE_TYPE (method));
!   jniarg0 = klass;
!   jniarg1 = build_utf8_ref (DECL_NAME (method));
!   jniarg2 = build_utf8_ref (unmangle_classname
! 			    (IDENTIFIER_POINTER (method_sig),
! 			     IDENTIFIER_LENGTH (method_sig)));
!   jniarg3 = build_int_cst (NULL_TREE, args_size);
! 
    tem = build_function_type (TREE_TYPE (TREE_TYPE (method)), arg_types);
  
  #ifdef MODIFY_JNI_METHOD_CALL
*************** build_jni_stub (tree method)
*** 2736,2751 ****
    jnifunc = build3 (COND_EXPR, ptr_type_node,
  		    meth_var, meth_var,
  		    build2 (MODIFY_EXPR, ptr_type_node, meth_var,
! 			    build3 (CALL_EXPR, ptr_type_node,
! 				    build_address_of
! 				      (soft_lookupjnimethod_node),
! 				    lookup_arg, NULL_TREE)));
  
    /* Now we make the actual JNI call via the resulting function
       pointer.    */
!   call = build3 (CALL_EXPR, TREE_TYPE (TREE_TYPE (method)),
! 		 build1 (NOP_EXPR, jni_func_type, jnifunc),
! 		 args, NULL_TREE);
  
    /* If the JNI call returned a result, capture it here.  If we had to
       unwrap JNI object results, we would do that here.  */
--- 2699,2716 ----
    jnifunc = build3 (COND_EXPR, ptr_type_node,
  		    meth_var, meth_var,
  		    build2 (MODIFY_EXPR, ptr_type_node, meth_var,
! 			    build_call_nary (ptr_type_node,
! 					     build_address_of
! 					       (soft_lookupjnimethod_node),
! 					     4,
! 					     jniarg0, jniarg1,
! 					     jniarg2, jniarg3)));
  
    /* Now we make the actual JNI call via the resulting function
       pointer.    */
!   call = build_call_list (TREE_TYPE (TREE_TYPE (method)),
! 			  build1 (NOP_EXPR, jni_func_type, jnifunc),
! 			  args);
  
    /* If the JNI call returned a result, capture it here.  If we had to
       unwrap JNI object results, we would do that here.  */
*************** build_jni_stub (tree method)
*** 2754,2763 ****
        /* If the call returns an object, it may return a JNI weak
  	 reference, in which case we must unwrap it.  */
        if (! JPRIMITIVE_TYPE_P (TREE_TYPE (TREE_TYPE (method))))
! 	call = build3 (CALL_EXPR, TREE_TYPE (TREE_TYPE (method)),
! 		       build_address_of (soft_unwrapjni_node),
! 		       build_tree_list (NULL_TREE, call),
! 		       NULL_TREE);
        call = build2 (MODIFY_EXPR, TREE_TYPE (TREE_TYPE (method)),
  		     res_var, call);
      }
--- 2719,2727 ----
        /* If the call returns an object, it may return a JNI weak
  	 reference, in which case we must unwrap it.  */
        if (! JPRIMITIVE_TYPE_P (TREE_TYPE (TREE_TYPE (method))))
! 	call = build_call_nary (TREE_TYPE (TREE_TYPE (method)),
! 				build_address_of (soft_unwrapjni_node),
! 				1, call);
        call = build2 (MODIFY_EXPR, TREE_TYPE (TREE_TYPE (method)),
  		     res_var, call);
      }
*************** build_jni_stub (tree method)
*** 2769,2778 ****
    TREE_SIDE_EFFECTS (body) = 1;
  
    /* Now free the environment we allocated.  */
!   call = build3 (CALL_EXPR, ptr_type_node,
! 		 build_address_of (soft_jnipopsystemframe_node),
! 		 build_tree_list (NULL_TREE, env_var),
! 		 NULL_TREE);
    TREE_SIDE_EFFECTS (call) = 1;
    CAN_COMPLETE_NORMALLY (call) = 1;
    body = build2 (COMPOUND_EXPR, void_type_node, body, call);
--- 2733,2741 ----
    TREE_SIDE_EFFECTS (body) = 1;
  
    /* Now free the environment we allocated.  */
!   call = build_call_nary (ptr_type_node,
! 			  build_address_of (soft_jnipopsystemframe_node),
! 			  1, env_var);
    TREE_SIDE_EFFECTS (call) = 1;
    CAN_COMPLETE_NORMALLY (call) = 1;
    body = build2 (COMPOUND_EXPR, void_type_node, body, call);
*************** build_jni_stub (tree method)
*** 2805,2815 ****
        && (! METHOD_PRIVATE (method)
            || INNER_CLASS_P (DECL_CONTEXT (method))))
      {
!       tree init = build3 (CALL_EXPR, void_type_node,
! 			  build_address_of (soft_initclass_node),
! 			  build_tree_list (NULL_TREE, 
! 					   klass),
! 			  NULL_TREE);
        body = build2 (COMPOUND_EXPR, void_type_node, init, body);
        TREE_SIDE_EFFECTS (body) = 1;
      }
--- 2768,2775 ----
        && (! METHOD_PRIVATE (method)
            || INNER_CLASS_P (DECL_CONTEXT (method))))
      {
!       tree init = build_call_expr (soft_initclass_node, 1, 
! 				   klass);
        body = build2 (COMPOUND_EXPR, void_type_node, init, body);
        TREE_SIDE_EFFECTS (body) = 1;
      }
*************** expand_java_field_op (int is_static, int
*** 2943,2953 ****
  			    field_ref, new_value);
  
        if (TREE_THIS_VOLATILE (field_decl))
! 	java_add_stmt 
! 	  (build3 
! 	   (CALL_EXPR, void_type_node,
! 	    build_address_of (built_in_decls[BUILT_IN_SYNCHRONIZE]),
! 	    NULL_TREE, NULL_TREE));
        	  
        java_add_stmt (modify_expr);
      }
--- 2903,2910 ----
  			    field_ref, new_value);
  
        if (TREE_THIS_VOLATILE (field_decl))
! 	java_add_stmt
! 	  (build_call_expr (built_in_decls[BUILT_IN_SYNCHRONIZE], 0));
        	  
        java_add_stmt (modify_expr);
      }
*************** expand_java_field_op (int is_static, int
*** 2965,2974 ****
  
        if (TREE_THIS_VOLATILE (field_decl))
  	java_add_stmt 
! 	  (build3 
! 	   (CALL_EXPR, void_type_node,
! 	    build_address_of (built_in_decls[BUILT_IN_SYNCHRONIZE]),
! 	    NULL_TREE, NULL_TREE));
  
        push_value (temp);
      }      
--- 2922,2928 ----
  
        if (TREE_THIS_VOLATILE (field_decl))
  	java_add_stmt 
! 	  (build_call_expr (built_in_decls[BUILT_IN_SYNCHRONIZE], 0));
  
        push_value (temp);
      }      
*************** force_evaluation_order (tree node)
*** 3725,3764 ****
  	  && TREE_CODE (TREE_OPERAND (node, 0)) == CALL_EXPR
  	  && TREE_CODE (TREE_OPERAND (node, 1)) == SAVE_EXPR)) 
      {
!       tree arg, cmp;
  
!       arg = node;
!       
!       /* Position arg properly, account for wrapped around ctors. */
        if (TREE_CODE (node) == COMPOUND_EXPR)
!         arg = TREE_OPERAND (node, 0);
!       
!       arg = TREE_OPERAND (arg, 1);
!       
!       /* An empty argument list is ok, just ignore it.  */
!       if (!arg)
! 	return node;
  
!       /* Not having a list of arguments here is an error. */ 
!       gcc_assert (TREE_CODE (arg) == TREE_LIST);
  
        /* This reverses the evaluation order. This is a desired effect. */
!       for (cmp = NULL_TREE; arg; arg = TREE_CHAIN (arg))
  	{
  	  /* Promote types smaller than integer.  This is required by
  	     some ABIs.  */
! 	  tree type = TREE_TYPE (TREE_VALUE (arg));
  	  tree saved;
  	  if (targetm.calls.promote_prototypes (type)
  	      && INTEGRAL_TYPE_P (type)
  	      && INT_CST_LT_UNSIGNED (TYPE_SIZE (type),
  				      TYPE_SIZE (integer_type_node)))
! 	    TREE_VALUE (arg) = fold_convert (integer_type_node, TREE_VALUE (arg));
  
! 	  saved = save_expr (force_evaluation_order (TREE_VALUE (arg)));
  	  cmp = (cmp == NULL_TREE ? saved :
  		 build2 (COMPOUND_EXPR, void_type_node, cmp, saved));
! 	  TREE_VALUE (arg) = saved;
  	}
        
        if (cmp && TREE_CODE (cmp) == COMPOUND_EXPR)
--- 3679,3714 ----
  	  && TREE_CODE (TREE_OPERAND (node, 0)) == CALL_EXPR
  	  && TREE_CODE (TREE_OPERAND (node, 1)) == SAVE_EXPR)) 
      {
!       tree call, cmp;
!       int i, nargs;
  
!       /* Account for wrapped around ctors.  */
        if (TREE_CODE (node) == COMPOUND_EXPR)
!         call = TREE_OPERAND (node, 0);
!       else
! 	call = node;
  
!       nargs = call_expr_nargs (call);
  
        /* This reverses the evaluation order. This is a desired effect. */
!       for (i = 0, cmp = NULL_TREE; i < nargs; i++)
  	{
+ 	  tree arg = CALL_EXPR_ARG (call, i);
  	  /* Promote types smaller than integer.  This is required by
  	     some ABIs.  */
! 	  tree type = TREE_TYPE (arg);
  	  tree saved;
  	  if (targetm.calls.promote_prototypes (type)
  	      && INTEGRAL_TYPE_P (type)
  	      && INT_CST_LT_UNSIGNED (TYPE_SIZE (type),
  				      TYPE_SIZE (integer_type_node)))
! 	    arg = fold_convert (integer_type_node, arg);
  
! 	  saved = save_expr (force_evaluation_order (arg));
  	  cmp = (cmp == NULL_TREE ? saved :
  		 build2 (COMPOUND_EXPR, void_type_node, cmp, saved));
! 
! 	  CALL_EXPR_ARG (call, i) = saved;
  	}
        
        if (cmp && TREE_CODE (cmp) == COMPOUND_EXPR)
Index: gcc/java/lang.c
===================================================================
*** gcc/java/lang.c	(revision 121818)
--- gcc/java/lang.c	(working copy)
*************** java_get_callee_fndecl (tree call_expr)
*** 989,995 ****
  
    if (TREE_CODE (call_expr) != CALL_EXPR)
      return NULL;
!   method = TREE_OPERAND (call_expr, 0);
    STRIP_NOPS (method);
    if (TREE_CODE (method) != ARRAY_REF)
      return NULL;
--- 989,995 ----
  
    if (TREE_CODE (call_expr) != CALL_EXPR)
      return NULL;
!   method = CALL_EXPR_FN (call_expr);
    STRIP_NOPS (method);
    if (TREE_CODE (method) != ARRAY_REF)
      return NULL;

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]