I've seen a number of execution failures with the soon-to-be submitted
ARCompact port in the context of gcc 4.8, which where down to an
rtlanal.c:dead_or_set_p problem, e.g.:
gcc.c-torture/execute/builtin-bitops-1.c -O1

As the comment at the top of dead_or_set_p states, this function should
return true if a register is dies in INSN or is entirely set.

A COND_EXEC does not set at all if the condition is not true; for the
purposes of dead_or_set_p, it should be treated like a partial set or
a REG_INC, i.e. the COND_EXEC and its contents should be disregarded.

Yet dead_or_set_regno_p, a helper function of dead_or_set_p, instead
processes a COND_EXEC as if it always took place.  I see this was
introduced in the 2000-04-07 mega-patch that introduced COND_EXEC.
Certainly in lots of other places the right thing is to look inside
the COND_EXEC, but not here.

Fixed with the attached patch.

Bootstrapped on ia64-unknown-linux-gnu.
2011-11-27  Joern Rennecke  <joern.renne...@embecosm.com>

        * rtlanal.c (dead_or_set_regno_p): Fix COND_EXEC handling.

Index: rtlanal.c
===================================================================
--- rtlanal.c   (revision 191467)
+++ rtlanal.c   (working copy)
@@ -1701,8 +1701,9 @@
 
   pattern = PATTERN (insn);
 
+  /* If a COND_EXEC is not executed, the value survives.  */
   if (GET_CODE (pattern) == COND_EXEC)
-    pattern = COND_EXEC_CODE (pattern);
+    return 0;
 
   if (GET_CODE (pattern) == SET)
     return covers_regno_p (SET_DEST (pattern), test_regno);

Reply via email to