aboutsummaryrefslogtreecommitdiff
path: root/gcc/java/expr.c
diff options
context:
space:
mode:
authorAndrew Haley <aph@cygnus.com>1999-07-21 14:28:33 +0000
committerAndrew Haley <aph@gcc.gnu.org>1999-07-21 14:28:33 +0000
commitaa4759c11cc78443455b69fca236c24ff89c91a1 (patch)
tree7a86e6410656ef434107be5353da306f7adf35c0 /gcc/java/expr.c
parent9c1ce4332e0bfc9289296fde205af0eb3a21e50b (diff)
downloadgcc-aa4759c11cc78443455b69fca236c24ff89c91a1.zip
gcc-aa4759c11cc78443455b69fca236c24ff89c91a1.tar.gz
gcc-aa4759c11cc78443455b69fca236c24ff89c91a1.tar.bz2
lang.c (flag_use_divide_subroutine): New variable.
1999-07-15 Andrew Haley <aph@cygnus.com> * lang.c (flag_use_divide_subroutine): New variable. * typeck.c: (convert_ieee_real_to_integer): Bounds check fp-to-integer conversion. (convert): Call convert_ieee_real_to_integer when flag_fast_math is not set. * expr.c (build_java_soft_divmod): New function. (build_java_binop): Call build_java_soft_divmod if flag_use_divide_subroutine is set. * decl.c: soft_idiv_node, soft_irem_node, soft_ldiv_node, tree soft_lrem_node: new builtin functions. (init_decl_processing) Initialize the new builtins. * java-tree.h soft_idiv_node, soft_irem_node, soft_ldiv_node, tree soft_lrem_node: new builtin functions. (build_java_soft_divmod): New function. * parse.y: Call build_java_soft_divmod if flag_use_divide_subroutine is set. From-SVN: r28208
Diffstat (limited to 'gcc/java/expr.c')
-rw-r--r--gcc/java/expr.c60
1 files changed, 57 insertions, 3 deletions
diff --git a/gcc/java/expr.c b/gcc/java/expr.c
index d47ed1a..dbf6db5 100644
--- a/gcc/java/expr.c
+++ b/gcc/java/expr.c
@@ -1052,6 +1052,53 @@ expand_iinc (local_var_index, ival, pc)
expand_assignment (local_var, res, 0, 0);
}
+
+tree
+build_java_soft_divmod (op, type, op1, op2)
+ enum tree_code op;
+ tree type, op1, op2;
+{
+ tree call = NULL;
+ tree arg1 = convert (type, op1);
+ tree arg2 = convert (type, op2);
+
+ if (type == int_type_node)
+ {
+ switch (op)
+ {
+ case TRUNC_DIV_EXPR:
+ call = soft_idiv_node;
+ break;
+ case TRUNC_MOD_EXPR:
+ call = soft_irem_node;
+ break;
+ }
+ }
+ else if (type == long_type_node)
+ {
+ switch (op)
+ {
+ case TRUNC_DIV_EXPR:
+ call = soft_ldiv_node;
+ break;
+ case TRUNC_MOD_EXPR:
+ call = soft_lrem_node;
+ break;
+ }
+ }
+
+ if (! call)
+ fatal ("Internal compiler error in build_java_soft_divmod");
+
+ call = build (CALL_EXPR, type,
+ build_address_of (call),
+ tree_cons (NULL_TREE, arg1,
+ build_tree_list (NULL_TREE, arg2)),
+ NULL_TREE);
+
+ return call;
+}
+
tree
build_java_binop (op, type, arg1, arg2)
enum tree_code op;
@@ -1100,10 +1147,11 @@ build_java_binop (op, type, arg1, arg2)
integer_zero_node));
return fold (build (COND_EXPR, int_type_node,
ifexp1, integer_negative_one_node, second_compare));
- }
-
+ }
+ case TRUNC_DIV_EXPR:
case TRUNC_MOD_EXPR:
- if (TREE_CODE (type) == REAL_TYPE)
+ if (TREE_CODE (type) == REAL_TYPE
+ && op == TRUNC_MOD_EXPR)
{
tree call;
if (type != double_type_node)
@@ -1120,6 +1168,12 @@ build_java_binop (op, type, arg1, arg2)
call = convert (type, call);
return call;
}
+
+ if (TREE_CODE (type) == INTEGER_TYPE
+ && flag_use_divide_subroutine
+ && ! flag_syntax_only)
+ return build_java_soft_divmod (op, type, arg1, arg2);
+
break;
default: ;
}