This is the mail archive of the
gcc@gcc.gnu.org
mailing list for the GCC project.
expand_binop misplacing results?
- From: DJ Delorie <dj at redhat dot com>
- To: gcc at gcc dot gnu dot org
- Date: Mon, 21 Mar 2005 20:47:44 -0500
- Subject: expand_binop misplacing results?
gcc.c-torture/execute/20000403-1.c tripped over this on an internal
(16 bit) port doing SImode subtract. The comments for expand_binop()
explicitly state that you can't rely on the target being set:
If TARGET is nonzero, the value
is generated there, if it is convenient to do so.
but we seem to have that expectation later:
/* Main add/subtract of the input operands. */
x = expand_binop (word_mode, binoptab,
op0_piece, op1_piece,
target_piece, unsignedp, next_methods);
The only place where target_piece is assigned is in the (i > 0) case:
if (i > 0)
{
. . .
emit_move_insn (target_piece, newx);
}
So it seems to me that in the (i == 0) case we need to see if
target_piece happened to receive the result, and if not, assign it.
It seems to me that this kind of bug should have been noticed already,
so... am I missing something?
2005-03-21 DJ Delorie <dj@redhat.com>
* optabs.c (expand_binop): Make sure the first subword's result
gets stored.
Index: optabs.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/optabs.c,v
retrieving revision 1.265
diff -p -U3 -r1.265 optabs.c
--- optabs.c 16 Mar 2005 18:29:23 -0000 1.265
+++ optabs.c 22 Mar 2005 01:25:35 -0000
@@ -1534,6 +1534,11 @@ expand_binop (enum machine_mode mode, op
}
emit_move_insn (target_piece, newx);
}
+ else
+ {
+ if (x != target_piece)
+ emit_move_insn (target_piece, x);
+ }
carry_in = carry_out;
}