This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: [PR middle-end/20491] combine generates bad subregs
- From: Alexandre Oliva <aoliva at redhat dot com>
- To: gcc-patches at gcc dot gnu dot org
- Cc: gcc-bugzilla at gcc dot gnu dot org
- Date: 24 Mar 2005 07:45:44 -0300
- Subject: Re: [PR middle-end/20491] combine generates bad subregs
- Organization: Red Hat Global Engineering Services Compiler Team
- References: <oreke5bdlf.fsf@livre.redhat.lsd.ic.unicamp.br>
On Mar 24, 2005, Alexandre Oliva <aoliva@redhat.com> wrote:
> Combine doesn't ensure the subregs it generates are valid. In most
> cases, insn recog will reject the invalid subregs, or reload will
> somehow make them fit, but if the constraint of the insn or the asm
> operand is "X", this won't work, so I think we're better off ensuring
> we don't ever introduce subregs of non-REGs.
> Does this look like a reasonable change to make?
Ugh. It failed building libgcc for stage 1, after simplifying
(subreg:QI (subreg:SI (reg:HI))) to (subreg:QI (reg:HI)), leaving
op0_mode set to SImode, causing an error in combine_simplify_rtx(),
when it called simplify_subreg with the wrong mode.
Index: gcc/ChangeLog
from Alexandre Oliva <aoliva@redhat.com>
PR middle-end/20491
* combine.c (subst): Make sure we don't create invalid subregs.
Index: gcc/combine.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/combine.c,v
retrieving revision 1.484
diff -u -p -r1.484 combine.c
--- gcc/combine.c 22 Mar 2005 03:48:44 -0000 1.484
+++ gcc/combine.c 24 Mar 2005 10:01:17 -0000
@@ -3689,15 +3689,24 @@ subst (rtx x, rtx from, rtx to, int in_d
if (GET_CODE (new) == CLOBBER && XEXP (new, 0) == const0_rtx)
return new;
- if (GET_CODE (x) == SUBREG
- && (GET_CODE (new) == CONST_INT
- || GET_CODE (new) == CONST_DOUBLE))
+ /* If we changed the reg of a subreg, make sure it's
+ still valid. For anything but a REG, require the
+ SUBREG to be simplified out. */
+
+ if (GET_CODE (x) == SUBREG && new != SUBREG_REG (x))
{
enum machine_mode mode = GET_MODE (x);
+ enum machine_mode submode = op0_mode;
+
+ if (GET_CODE (new) == REG)
+ x = simplify_gen_subreg (mode, new, submode,
+ SUBREG_BYTE (x));
+ else
+ x = simplify_subreg (mode, new, submode,
+ SUBREG_BYTE (x));
+
+ op0_mode = VOIDmode;
- x = simplify_subreg (GET_MODE (x), new,
- GET_MODE (SUBREG_REG (x)),
- SUBREG_BYTE (x));
if (! x)
x = gen_rtx_CLOBBER (mode, const0_rtx);
}
Index: gcc/testsuite/ChangeLog
from Alexandre Oliva <aoliva@redhat.com>
PR middle-end/20491
* gcc.dg/asm-subreg-1.c: New.
Index: gcc/testsuite/gcc.dg/asm-subreg-1.c
===================================================================
RCS file: gcc/testsuite/gcc.dg/asm-subreg-1.c
diff -N gcc/testsuite/gcc.dg/asm-subreg-1.c
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ gcc/testsuite/gcc.dg/asm-subreg-1.c 24 Mar 2005 09:10:14 -0000
@@ -0,0 +1,14 @@
+/* PR middle-end/20491 */
+
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+
+/* Combine used to introduce invalid subregs for the asm input. */
+
+volatile unsigned short _const_32 [4] = {1,2,3,4};
+void
+evas_common_convert_yuv_420p_601_rgba()
+{
+ __asm__ __volatile__ ("" : : "X" (*_const_32));
+}
+
--
Alexandre Oliva http://www.ic.unicamp.br/~oliva/
Red Hat Compiler Engineer aoliva@{redhat.com, gcc.gnu.org}
Free Software Evangelist oliva@{lsd.ic.unicamp.br, gnu.org}