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]

Re: Fix combine EH related failure


On Tue, Feb 17, 2004 at 11:38:56AM +1030, Alan Modra wrote:
> I really don't like combine moving instructions
> around for no purpose as shown in PR 14119

Actually, I think this is quite easy to fix.  There's no need for calls
to rtx_equal_p;  If added_sets_2 is true and we're not combining three
instructions, then we know that one of the sets is the original i2 (or
the SET part of i2 which is a parallel containing exactly one non-dead
SET and some CLOBBERs or USEs).  ie. added_sets_2 && i1 == 0 means we
are effectively getting i2 back again.

Note that the comment "We *must* test.." is referring to the case where
three instructions are being combined.

	* combine.c (try_combine): When attemting to fix unrecognized insns,
	don't split a PARALLEL that contains the original i2.

I also noticed some other places in combine.c that were checking for
REG_UNUSED notes without looking for REG_EH_REGION.  A followup patch
will address them..

Index: gcc/combine.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/combine.c,v
retrieving revision 1.410
diff -u -p -r1.410 combine.c
--- gcc/combine.c	17 Feb 2004 22:21:00 -0000	1.410
+++ gcc/combine.c	17 Feb 2004 23:11:36 -0000
@@ -2022,11 +2022,21 @@ try_combine (rtx i3, rtx i2, rtx i1, int
      we just need the first SET.   This can occur when simplifying a divmod
      insn.  We *must* test for this case here because the code below that
      splits two independent SETs doesn't handle this case correctly when it
-     updates the register status.  Also check the case where the first
-     SET's destination is unused.  That would not cause incorrect code, but
-     does cause an unneeded insn to remain.  */
+     updates the register status.
 
-  if (insn_code_number < 0 && GET_CODE (newpat) == PARALLEL
+     It's pointless doing this if we originally had two sets, one from
+     i3, and one from i2.  Combining then splitting the parallel results
+     in the original i2 again plus an invalid insn (which we delete).
+     The net effect is only to move instructions around, which makes
+     debug info less accurate.
+
+     Also check the case where the first SET's destination is unused.
+     That would not cause incorrect code, but does cause an unneeded
+     insn to remain.  */
+
+  if (insn_code_number < 0
+      && !(added_sets_2 && i1 == 0)
+      && GET_CODE (newpat) == PARALLEL
       && XVECLEN (newpat, 0) == 2
       && GET_CODE (XVECEXP (newpat, 0, 0)) == SET
       && GET_CODE (XVECEXP (newpat, 0, 1)) == SET

-- 
Alan Modra
IBM OzLabs - Linux Technology Centre


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