aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorRoger Sayle <roger@eyesopen.com>2004-08-09 22:36:39 +0000
committerRoger Sayle <sayle@gcc.gnu.org>2004-08-09 22:36:39 +0000
commitfdded40102ee40d7acbcb6bc2518e5ec14245688 (patch)
treef2d96387c14f84dfdf8d12ed5292bcb427a0fa5a /gcc
parentfeb21f0d146b949153c91d6a800f5707b0da516d (diff)
downloadgcc-fdded40102ee40d7acbcb6bc2518e5ec14245688.zip
gcc-fdded40102ee40d7acbcb6bc2518e5ec14245688.tar.gz
gcc-fdded40102ee40d7acbcb6bc2518e5ec14245688.tar.bz2
expmed.c (sdiv_pow2_cheap, [...]): Change type to bool.
* expmed.c (sdiv_pow2_cheap, smod_pow2_cheap): Change type to bool. (init_expmed): Fix potential overrun problem with "all.reg". (expand_sdiv2_pow2): Add an alternate implementation for signed division, if the target provides a suitable conditional move insn. From-SVN: r85728
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog7
-rw-r--r--gcc/expmed.c31
2 files changed, 35 insertions, 3 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index ee1cbd7..34ba341 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,10 @@
+2004-08-09 Roger Sayle <roger@eyesopen.com>
+
+ * expmed.c (sdiv_pow2_cheap, smod_pow2_cheap): Change type to bool.
+ (init_expmed): Fix potential overrun problem with "all.reg".
+ (expand_sdiv2_pow2): Add an alternate implementation for signed
+ division, if the target provides a suitable conditional move insn.
+
2004-08-09 Paul Brook <paul@codesourcery.com>
Richard Henderson <rth@redhat.com>
diff --git a/gcc/expmed.c b/gcc/expmed.c
index cdbbd17..735fe98 100644
--- a/gcc/expmed.c
+++ b/gcc/expmed.c
@@ -59,8 +59,8 @@ static rtx expand_sdiv_pow2 (enum machine_mode, rtx, HOST_WIDE_INT);
Usually, this will mean that the MD file will emit non-branch
sequences. */
-static int sdiv_pow2_cheap[NUM_MACHINE_MODES];
-static int smod_pow2_cheap[NUM_MACHINE_MODES];
+static bool sdiv_pow2_cheap[NUM_MACHINE_MODES];
+static bool smod_pow2_cheap[NUM_MACHINE_MODES];
#ifndef SLOW_UNALIGNED_ACCESS
#define SLOW_UNALIGNED_ACCESS(MODE, ALIGN) STRICT_ALIGNMENT
@@ -109,7 +109,7 @@ init_expmed (void)
{
struct
{
- struct rtx_def reg;
+ struct rtx_def reg; rtunion reg_fld[2];
struct rtx_def plus; rtunion plus_fld1;
struct rtx_def neg;
struct rtx_def udiv; rtunion udiv_fld1;
@@ -3194,6 +3194,31 @@ expand_sdiv_pow2 (enum machine_mode mode, rtx op0, HOST_WIDE_INT d)
return expand_shift (RSHIFT_EXPR, mode, temp, shift, NULL_RTX, 0);
}
+#ifdef HAVE_conditional_move
+ if (BRANCH_COST >= 2)
+ {
+ rtx temp2;
+
+ start_sequence ();
+ temp2 = copy_to_mode_reg (mode, op0);
+ temp = expand_binop (mode, add_optab, temp2, GEN_INT (d-1),
+ NULL_RTX, 0, OPTAB_LIB_WIDEN);
+ temp = force_reg (mode, temp);
+
+ /* Construct "temp2 = (temp2 < 0) ? temp : temp2". */
+ temp2 = emit_conditional_move (temp2, LT, temp2, const0_rtx,
+ mode, temp, temp2, mode, 0);
+ if (temp2)
+ {
+ rtx seq = get_insns ();
+ end_sequence ();
+ emit_insn (seq);
+ return expand_shift (RSHIFT_EXPR, mode, temp2, shift, NULL_RTX, 0);
+ }
+ end_sequence ();
+ }
+#endif
+
if (BRANCH_COST >= 2)
{
int ushift = GET_MODE_BITSIZE (mode) - logd;