gcse.c (store_killed_in_insn): Handle PARALLELs.
authorAlexandre Oliva <aoliva@redhat.com>
Sat, 21 Apr 2007 06:48:37 +0000 (06:48 +0000)
committerAlexandre Oliva <aoliva@gcc.gnu.org>
Sat, 21 Apr 2007 06:48:37 +0000 (06:48 +0000)
gcc/ChangeLog:
* gcse.c (store_killed_in_insn): Handle PARALLELs.
(store_killed_in_pat): New.
gcc/testsuite/ChangeLog:
* gcc.target/i386/movsi-sm-1.c: New.

From-SVN: r124015

gcc/ChangeLog
gcc/gcse.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.target/i386/movsi-sm-1.c [new file with mode: 0644]

index f60a91b..cc3d7ab 100644 (file)
@@ -1,3 +1,8 @@
+2007-04-21  Alexandre Oliva  <aoliva@redhat.com>
+
+       * gcse.c (store_killed_in_insn): Handle PARALLELs.
+       (store_killed_in_pat): New.
+
 2007-04-20  Richard Henderson  <rth@redhat.com>
 
        PR target/31628
index 36b2c8f..70c89ef 100644 (file)
@@ -5909,6 +5909,39 @@ find_loads (rtx x, rtx store_pattern, int after)
   return ret;
 }
 
+static inline bool
+store_killed_in_pat (rtx x, rtx pat, int after)
+{
+  if (GET_CODE (pat) == SET)
+    {
+      rtx dest = SET_DEST (pat);
+
+      if (GET_CODE (dest) == ZERO_EXTRACT)
+       dest = XEXP (dest, 0);
+
+      /* Check for memory stores to aliased objects.  */
+      if (MEM_P (dest)
+         && !expr_equiv_p (dest, x))
+       {
+         if (after)
+           {
+             if (output_dependence (dest, x))
+               return true;
+           }
+         else
+           {
+             if (output_dependence (x, dest))
+               return true;
+           }
+       }
+    }
+
+  if (find_loads (pat, x, after))
+    return true;
+
+  return false;
+}
+
 /* Check if INSN kills the store pattern X (is aliased with it).
    AFTER is true if we are checking the case when store X occurs
    after the insn.  Return true if it does.  */
@@ -5916,7 +5949,7 @@ find_loads (rtx x, rtx store_pattern, int after)
 static bool
 store_killed_in_insn (rtx x, rtx x_regs, rtx insn, int after)
 {
-  rtx reg, base, note;
+  rtx reg, base, note, pat;
 
   if (!INSN_P (insn))
     return false;
@@ -5943,32 +5976,20 @@ store_killed_in_insn (rtx x, rtx x_regs, rtx insn, int after)
       return false;
     }
 
-  if (GET_CODE (PATTERN (insn)) == SET)
+  pat = PATTERN (insn);
+  if (GET_CODE (pat) == SET)
     {
-      rtx pat = PATTERN (insn);
-      rtx dest = SET_DEST (pat);
-
-      if (GET_CODE (dest) == ZERO_EXTRACT)
-       dest = XEXP (dest, 0);
-
-      /* Check for memory stores to aliased objects.  */
-      if (MEM_P (dest)
-         && !expr_equiv_p (dest, x))
-       {
-         if (after)
-           {
-             if (output_dependence (dest, x))
-               return true;
-           }
-         else
-           {
-             if (output_dependence (x, dest))
-               return true;
-           }
-       }
-      if (find_loads (SET_SRC (pat), x, after))
+      if (store_killed_in_pat (x, pat, after))
        return true;
     }
+  else if (GET_CODE (pat) == PARALLEL)
+    {
+      int i;
+
+      for (i = 0; i < XVECLEN (pat, 0); i++)
+       if (store_killed_in_pat (x, XVECEXP (pat, 0, i), after))
+         return true;
+    }
   else if (find_loads (PATTERN (insn), x, after))
     return true;
 
index 5b43dc1..00af7d4 100644 (file)
@@ -1,3 +1,7 @@
+2007-04-21  Alexandre Oliva  <aoliva@redhat.com>
+
+       * gcc.target/i386/movsi-sm-1.c: New.
+
 2007-04-20  Richard Henderson  <rth@redhat.com>
 
        * gcc.dg/pr28796-2.c: Add -mieee for alpha.
diff --git a/gcc/testsuite/gcc.target/i386/movsi-sm-1.c b/gcc/testsuite/gcc.target/i386/movsi-sm-1.c
new file mode 100644 (file)
index 0000000..3594140
--- /dev/null
@@ -0,0 +1,31 @@
+/* { dg-do run } */
+/* { dg-options "-O2 -fgcse-sm -minline-all-stringops" } */
+
+/* Store motion used to fail to recognize killed expressions within
+   parallels such as those generated for memory copying.  */
+
+static const char s[1024] __attribute__ ((__aligned__ (32)))
+  = "This is what we should get!";
+
+int bug (int arg) {
+  char str[sizeof(s) > 4 ? sizeof(s) : 4] __attribute__ ((__aligned__ (32)));
+
+  __builtin_memcpy (str, "Bug", 4);
+
+  if (arg <= 2)
+    __builtin_memcpy (str, s, sizeof (s));
+
+  if (arg <= 1)
+    __builtin_memcpy (str, "Err", 4);
+
+  __builtin_puts (str);
+
+  return str[0] != s[0];
+}
+
+int main () {
+  if (bug (2))
+    __builtin_abort ();
+
+  return 0;
+}