This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Committed] Correct big-endian problem in emit_group_store


The following patch corrects an endianess bug in my recent change to
emit_group_store, diagnosed by Eric Botcazou.  The problem is a mistake
in the logic, where when calling subreg_low_part offset, the arguments
require the narrow mode to come before the wide mode, matching the
outer/inner modes of a SUBREG.  For this optimization of PARALLELs,
the sense of inner and outer is reversed.

The following correction has been tested on i686-pc-linux-gnu and
powerpc-linux-gnu with a full "make bootstrap", and regression
tested with a top-level "make -k check".  I've confirmed that
PR17959 is still resolved, but it looks like poor register allocation
(or a missing peephole2?) generates slightly worse code than before.
Before my original patch we required 4 insns, after my original patch
we required 2, with this correctness fix we now require 3.  I'll see
what I can do, but the initial RTL looks good.

Committed to mainline as 112887.



2006-04-11  Roger Sayle  <roger@eyesopen.com>

	* expr.c (emit_group_store): Correct operand order in call to
	subreg_lowpart_offset.  Always create paradoxical SUBREGs with
	a SUBREG_BYTE of zero.


Index: expr.c
===================================================================
*** expr.c	(revision 112817)
--- expr.c	(working copy)
*************** emit_group_store (rtx orig_dst, rtx src,
*** 1940,1950 ****
        if (start < finish)
  	{
  	  inner = GET_MODE (tmps[start]);
! 	  bytepos = subreg_lowpart_offset (outer, inner);
  	  if (INTVAL (XEXP (XVECEXP (src, 0, start), 1)) == bytepos)
  	    {
  	      temp = simplify_gen_subreg (outer, tmps[start],
! 					  inner, bytepos);
  	      if (temp)
  		{
  		  emit_move_insn (dst, temp);
--- 1940,1950 ----
        if (start < finish)
  	{
  	  inner = GET_MODE (tmps[start]);
! 	  bytepos = subreg_lowpart_offset (inner, outer);
  	  if (INTVAL (XEXP (XVECEXP (src, 0, start), 1)) == bytepos)
  	    {
  	      temp = simplify_gen_subreg (outer, tmps[start],
! 					  inner, 0);
  	      if (temp)
  		{
  		  emit_move_insn (dst, temp);
*************** emit_group_store (rtx orig_dst, rtx src,
*** 1959,1969 ****
  	  && start < finish - 1)
  	{
  	  inner = GET_MODE (tmps[finish - 1]);
! 	  bytepos = subreg_lowpart_offset (outer, inner);
  	  if (INTVAL (XEXP (XVECEXP (src, 0, finish - 1), 1)) == bytepos)
  	    {
  	      temp = simplify_gen_subreg (outer, tmps[finish - 1],
! 					  inner, bytepos);
  	      if (temp)
  		{
  		  emit_move_insn (dst, temp);
--- 1959,1969 ----
  	  && start < finish - 1)
  	{
  	  inner = GET_MODE (tmps[finish - 1]);
! 	  bytepos = subreg_lowpart_offset (inner, outer);
  	  if (INTVAL (XEXP (XVECEXP (src, 0, finish - 1), 1)) == bytepos)
  	    {
  	      temp = simplify_gen_subreg (outer, tmps[finish - 1],
! 					  inner, 0);
  	      if (temp)
  		{
  		  emit_move_insn (dst, temp);


Roger
--


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]