This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
simplify_plus_minus busted in 4.3
- From: Bernd Schmidt <bernds_cb1 at t-online dot de>
- To: GCC Patches <gcc-patches at gcc dot gnu dot org>
- Cc: "Bergner, Peter" <bergner at vnet dot ibm dot com>, Paolo Bonzini <bonzini at gnu dot org>
- Date: Mon, 09 Feb 2009 15:48:01 +0100
- Subject: simplify_plus_minus busted in 4.3
While trying to teach the doloop code new tricks in our Blackfin tree
based on 4.3, I've noticed that simplify_plus_minus appears to be
busted. When called like this:
#0 simplify_plus_minus (code=MINUS, mode=SImode, op0=0xb7bad0fc,
op1=0xb7b90e10)
(gdb) p debug_rtx (op0)
(plus:SI (reg/v/f:SI 103 [ b ])
(reg:SI 112))
(gdb) p debug_rtx (op1)
(reg/v/f:SI 103 [ b ])
nothing ever sets the canonicalized flag, and we return without
simplifying anything.
Before Peter's revision 126852, this probably would have worked, since a
return value of 0 (for identical regs) from
simplify_plus_minus_op_data_cmp would have caused canonicalized to be
set. I don't know whether this would have been only working by accident
though.
Since I can't even figure out how this is supposed to work, I'm Cc'ing
the folks who seem to have last changed this function. Maybe we need an
additional step to compact the array by removing identical operands with
different signs before doing the full simplification loop (suggested
patch below)?
Bernd
--
This footer brought to you by insane German lawmakers.
Analog Devices GmbH Wilhelm-Wagenfeld-Str. 6 80807 Muenchen
Sitz der Gesellschaft Muenchen, Registergericht Muenchen HRB 40368
Geschaeftsfuehrer Thomas Wessel, William A. Martin, Margaret Seif
* simplify-rtx.c (simplify_plus_minus): Remove identical operands with
opposite signs from the array before further processing.
Index: gcc-4.3/gcc/simplify-rtx.c
===================================================================
--- gcc-4.3/gcc/simplify-rtx.c (revision 3121)
+++ gcc-4.3/gcc/simplify-rtx.c (working copy)
@@ -3555,6 +3583,29 @@ simplify_plus_minus (enum rtx_code code,
return simplify_const_binary_operation (code, mode, lhs, rhs);
}
+ for (i = 1; i < n_ops; i++)
+ {
+ for (j = 0; j < i; j++)
+ {
+ if (ops[i].neg != ops[j].neg && rtx_equal_p (ops[j].op, ops[i].op))
+ {
+ ops[i].op = ops[j].op = NULL_RTX;
+ canonicalized = 1;
+ break;
+ }
+ }
+ }
+ for (i = j = 0; i < n_ops; i++)
+ {
+ if (ops[i].op != NULL_RTX)
+ {
+ if (i != j)
+ ops[j] = ops[i];
+ j++;
+ }
+ }
+ n_ops = j;
+
/* Now simplify each pair of operands until nothing changes. */
do
{