]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
ifcvt.c (dead_or_predicable): Fail if there are any references to tablejump in merge_...
authorJakub Jelinek <jakub@redhat.com>
Wed, 19 Mar 2003 12:38:12 +0000 (13:38 +0100)
committerJakub Jelinek <jakub@gcc.gnu.org>
Wed, 19 Mar 2003 12:38:12 +0000 (13:38 +0100)
* ifcvt.c (dead_or_predicable): Fail if there are any references
to tablejump in merge_bb other than the final JUMP_INSN.

* gcc.dg/20030309-1.c: New test.

From-SVN: r64577

gcc/ChangeLog
gcc/ifcvt.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/20030309-1.c [new file with mode: 0644]

index 24a8e04f5fac6bd2ccd948865db05fd073da14dc..5e4f9c7af44023b915cc46412ffd15c302ac2860 100644 (file)
@@ -1,3 +1,8 @@
+2003-03-19  Jakub Jelinek  <jakub@redhat.com>
+
+       * ifcvt.c (dead_or_predicable): Fail if there are any references
+       to tablejump in merge_bb other than the final JUMP_INSN.
+
 2003-03-19  Alan Modra  <amodra@bigpond.net.au>
 
        PR target/10073
index 166c59c1307c65fe7b04264f86ee072d8ab1be15..a2b4cbd9512d1fda08d4488c4bb41ce39393ebb5 100644 (file)
@@ -2519,11 +2519,28 @@ dead_or_predicable (test_bb, merge_bb, other_bb, new_dest, reversep)
 
   if (GET_CODE (end) == JUMP_INSN)
     {
+      rtx tmp, insn, label;
+
       if (head == end)
        {
          head = end = NULL_RTX;
          goto no_body;
        }
+
+      /* If there is a jump table following merge_bb, fail
+        if there are any insn between head and PREV_INSN (end)
+        references it.  */
+      if ((label = JUMP_LABEL (end)) != NULL_RTX
+         && (tmp = NEXT_INSN (label)) != NULL_RTX
+         && GET_CODE (tmp) == JUMP_INSN
+         && (GET_CODE (PATTERN (tmp)) == ADDR_VEC
+             || GET_CODE (PATTERN (tmp)) == ADDR_DIFF_VEC))
+       {
+         for (insn = head; insn != PREV_INSN (end); insn = NEXT_INSN (insn))
+           if (find_reg_note (insn, REG_LABEL, label))
+             return FALSE;
+       }
+
       end = PREV_INSN (end);
     }
 
index b5e1ea2ab6767e7780e35a259dc0ca4a6bcfb84d..fc3c1abada9f26f26c66684594a66f5d81b1aa68 100644 (file)
@@ -1,3 +1,7 @@
+2003-03-19  Jakub Jelinek  <jakub@redhat.com>
+
+       * gcc.dg/20030309-1.c: New test.
+
 2003-03-16  Falk Hueffner  <falk.hueffner@student.uni-tuebingen.de>
 
         * gcc.c-torture/execute/20030316-1.c: New test case.
diff --git a/gcc/testsuite/gcc.dg/20030309-1.c b/gcc/testsuite/gcc.dg/20030309-1.c
new file mode 100644 (file)
index 0000000..2431bc1
--- /dev/null
@@ -0,0 +1,42 @@
+/* { dg-do link } */
+/* { dg-options "-O2" } */
+
+struct A0 { int x; };
+struct A1 { int x; int y[1]; };
+struct A2 { int x; int y[2]; };
+struct A3 { int x; int y[3]; };
+struct A4 { int x; int y[4]; };
+
+void *s;
+int u;
+
+int
+main (void)
+{
+  int x;
+  void *t = s;
+
+  switch (u)
+    {
+    case 0:
+      x = ((struct A0 *) t)->x;
+      break;
+    case 1:
+      x = ((struct A1 *) t)->x;
+      break;
+    case 2:
+      x = ((struct A2 *) t)->x;
+      break;
+    case 3:
+      x = ((struct A3 *) t)->x;
+      break;
+    case 4:
+      x = ((struct A4 *) t)->x;
+      break;
+    default:
+      x = 0;
+      break;
+    }
+
+  return x;
+}