aboutsummaryrefslogtreecommitdiff
path: root/gcc/builtins.c
diff options
context:
space:
mode:
authorRoger Sayle <roger@eyesopen.com>2003-06-03 11:27:23 +0000
committerRoger Sayle <sayle@gcc.gnu.org>2003-06-03 11:27:23 +0000
commit075ec276a051c77c1542992980d651f832e7140a (patch)
tree0ac72a6f0481c8c341e932108b5ac14e70debfbf /gcc/builtins.c
parentded9bf77e35ce9a22468a1f56595df0741e2f22a (diff)
downloadgcc-075ec276a051c77c1542992980d651f832e7140a.zip
gcc-075ec276a051c77c1542992980d651f832e7140a.tar.gz
gcc-075ec276a051c77c1542992980d651f832e7140a.tar.bz2
builtins.def (BUILT_IN_CABS, [...]): New builtins representing ISO C99's cabs, cabsf and cabsl.
* builtins.def (BUILT_IN_CABS, BUILT_IN_CABSF, BUILT_IN_CABSL): New builtins representing ISO C99's cabs, cabsf and cabsl. * builtins.c (expand_builtin_fabs): New function. (expand_builtin_cabs): New function. (expand_builtin): Expand BUILT_IN_FABS{,F,L} and BUILT_IN_CABS{,F,L} using expand_builtin_fabs and expand_builtin_cabs respectively. * doc/extend.texi: Document new cabs, cabsf and cabsl builtins. * gcc.dg/builtins-16.c: New test case. From-SVN: r67368
Diffstat (limited to 'gcc/builtins.c')
-rw-r--r--gcc/builtins.c73
1 files changed, 71 insertions, 2 deletions
diff --git a/gcc/builtins.c b/gcc/builtins.c
index 557e397..53a1744 100644
--- a/gcc/builtins.c
+++ b/gcc/builtins.c
@@ -169,6 +169,8 @@ static tree fold_builtin_nan PARAMS ((tree, tree, int));
static int validate_arglist PARAMS ((tree, ...));
static tree fold_trunc_transparent_mathfn PARAMS ((tree));
static bool readonly_data_expr PARAMS ((tree));
+static rtx expand_builtin_fabs PARAMS ((tree, rtx, rtx));
+static rtx expand_builtin_cabs PARAMS ((tree, rtx));
/* Return the alignment in bits of EXP, a pointer valued expression.
But don't return more than MAX_ALIGN no matter what.
@@ -4306,6 +4308,57 @@ expand_builtin_trap ()
emit_library_call (abort_libfunc, LCT_NORETURN, VOIDmode, 0);
emit_barrier ();
}
+
+/* Expand a call to fabs, fabsf or fabsl with arguments ARGLIST.
+ Return 0 if a normal call should be emitted rather than expanding
+ the function inline. If convenient, the result should be placed
+ in TARGET. SUBTARGET may be used as the target for computing
+ the operand. */
+
+static rtx
+expand_builtin_fabs (arglist, target, subtarget)
+ tree arglist;
+ rtx target, subtarget;
+{
+ enum machine_mode mode;
+ tree arg;
+ rtx op0;
+
+ if (!validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
+ return 0;
+
+ arg = TREE_VALUE (arglist);
+ mode = TYPE_MODE (TREE_TYPE (arg));
+ op0 = expand_expr (arg, subtarget, VOIDmode, 0);
+ return expand_abs (mode, op0, target, 0, safe_from_p (target, arg, 1));
+}
+
+/* Expand a call to cabs, cabsf or cabsl with arguments ARGLIST.
+ Return 0 if a normal call should be emitted rather than expanding
+ the function inline. If convenient, the result should be placed
+ in target. */
+
+static rtx
+expand_builtin_cabs (arglist, target)
+ tree arglist;
+ rtx target;
+{
+ enum machine_mode mode;
+ tree arg;
+ rtx op0;
+
+ if (arglist == 0 || TREE_CHAIN (arglist))
+ return 0;
+ arg = TREE_VALUE (arglist);
+ if (TREE_CODE (TREE_TYPE (arg)) != COMPLEX_TYPE
+ || TREE_CODE (TREE_TYPE (TREE_TYPE (arg))) != REAL_TYPE)
+ return 0;
+
+ mode = TYPE_MODE (TREE_TYPE (arg));
+ op0 = expand_expr (arg, NULL_RTX, VOIDmode, 0);
+ return expand_complex_abs (mode, op0, target, 0);
+}
+
/* Expand an expression EXP that calls a built-in function,
with result going to TARGET if that's convenient
@@ -4458,11 +4511,27 @@ expand_builtin (exp, target, subtarget, mode, ignore)
case BUILT_IN_LABS:
case BUILT_IN_LLABS:
case BUILT_IN_IMAXABS:
+ /* build_function_call changes these into ABS_EXPR. */
+ abort ();
+
case BUILT_IN_FABS:
case BUILT_IN_FABSF:
case BUILT_IN_FABSL:
- /* build_function_call changes these into ABS_EXPR. */
- abort ();
+ target = expand_builtin_fabs (arglist, target, subtarget);
+ if (target)
+ return target;
+ break;
+
+ case BUILT_IN_CABS:
+ case BUILT_IN_CABSF:
+ case BUILT_IN_CABSL:
+ if (flag_unsafe_math_optimizations)
+ {
+ target = expand_builtin_cabs (arglist, target);
+ if (target)
+ return target;
+ }
+ break;
case BUILT_IN_CONJ:
case BUILT_IN_CONJF: