aboutsummaryrefslogtreecommitdiff
path: root/gcc/expmed.c
diff options
context:
space:
mode:
authorRoger Sayle <roger@eyesopen.com>2003-08-04 23:42:48 +0000
committerRoger Sayle <sayle@gcc.gnu.org>2003-08-04 23:42:48 +0000
commitf2593a6649384b002184762c58b083eb5f8e939f (patch)
tree9617a20782252283684d9c8639c9ad8e7fbf7873 /gcc/expmed.c
parent29019803327d246f686bcc22d9d95b0e3cdc244d (diff)
downloadgcc-f2593a6649384b002184762c58b083eb5f8e939f.zip
gcc-f2593a6649384b002184762c58b083eb5f8e939f.tar.gz
gcc-f2593a6649384b002184762c58b083eb5f8e939f.tar.bz2
fold-const.c (fold <PLUS_EXPR>): Transform x+x into x*2.0.
* fold-const.c (fold <PLUS_EXPR>): Transform x+x into x*2.0. Optimize x*c+x and x+x*c into x*(c+1) and x*c1+x*c2 into x*(c1+c2) for floating point expressions with -ffast-math. (fold <MULT_EXPR>): Don't transform x*2.0 into x+x. * expmed.c (expand_mult): Wrap long line. Expand x*2.0 as x+x. * gcc.dg/20030804-1.c: New test case. From-SVN: r70158
Diffstat (limited to 'gcc/expmed.c')
-rw-r--r--gcc/expmed.c25
1 files changed, 24 insertions, 1 deletions
diff --git a/gcc/expmed.c b/gcc/expmed.c
index 68163e9..89ecd0c 100644
--- a/gcc/expmed.c
+++ b/gcc/expmed.c
@@ -2300,7 +2300,8 @@ synth_mult (struct algorithm *alg_out, unsigned HOST_WIDE_INT t,
you should swap the two operands if OP0 would be constant. */
rtx
-expand_mult (enum machine_mode mode, rtx op0, rtx op1, rtx target, int unsignedp)
+expand_mult (enum machine_mode mode, rtx op0, rtx op1, rtx target,
+ int unsignedp)
{
rtx const_op1 = op1;
@@ -2514,6 +2515,28 @@ expand_mult (enum machine_mode mode, rtx op0, rtx op1, rtx target, int unsignedp
}
}
+ if (GET_CODE (op0) == CONST_DOUBLE)
+ {
+ rtx temp = op0;
+ op0 = op1;
+ op1 = temp;
+ }
+
+ /* Expand x*2.0 as x+x. */
+ if (GET_CODE (op1) == CONST_DOUBLE
+ && GET_MODE_CLASS (mode) == MODE_FLOAT)
+ {
+ REAL_VALUE_TYPE d;
+ REAL_VALUE_FROM_CONST_DOUBLE (d, op1);
+
+ if (REAL_VALUES_EQUAL (d, dconst2))
+ {
+ op0 = force_reg (GET_MODE (op0), op0);
+ return expand_binop (mode, add_optab, op0, op0,
+ target, unsignedp, OPTAB_LIB_WIDEN);
+ }
+ }
+
/* This used to use umul_optab if unsigned, but for non-widening multiply
there is no difference between signed and unsigned. */
op0 = expand_binop (mode,