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]

[PATCH, tree-optimization]: Fix PR tree-optimization/33920, [4.3 Regression] Segfault in combine_blocks/tree-if-conv.c


Hello!

When SSA diamond degenerates into:

   11
   | \
   |  \
   |   12
   |  /
   | /
   13

then bb 11 is not required to have a condition predicate set in its bb->aux field.

At the point of ICE, we look into bb->aux fields of both incoming source bbs to find the bb predicate in order to choose one that is not TRUTH_NOT_EXPR. However, if aux field of the source bb of the first incoming edge is NULL, it is not possible to get TREE_CODE of a NULL_TREE...

AFAICS, this situation happens only in the situation above, where bb 12 is dominated by bb 11 (otherwise both incoming blocks would have their predicate set), and we generate ifcvt condition from the predicate of bb 12.

Attached patch simply checks aux field of the first incoming bb for NULL, before checking TREE_CODE of the predicate. For the attached testcase, generated -O2 and -O3 asm code is equivalent.

The patch was bootstrapped and regression tested on x86_64-pc-linux-gnu {,-m32}.

OK for mainline/branches?

2007-10-27 Uros Bizjak <ubizjak@gmail.com>

       PR tree-optimization/33920
       * tree-if-conversion (find_phi_replacement_condition): Do not check
       NULL tmp_cond for TRUTH_NOT_EXPR.

testsuite/ChangeLog:

2007-10-27  Martin Michlmayr  <tbm@cyrius.com>
           Uros Bizjak  <ubizjak@gmail.com>

       PR tree-optimization/33920
       * gcc.dg/tree-ssa/pr33290.c: New test.

Uros.
Index: testsuite/gcc.dg/tree-ssa/pr33920.c
===================================================================
--- testsuite/gcc.dg/tree-ssa/pr33920.c	(revision 0)
+++ testsuite/gcc.dg/tree-ssa/pr33920.c	(revision 0)
@@ -0,0 +1,51 @@
+/* Testcase by Martin Michlmayr <tbm@cyrius.com> */
+/* { dg-do compile } */
+/* { dg-options "-O3" } */
+
+typedef union lispunion *object;
+struct character
+{
+  long e;
+};
+extern struct symbol Cnil_body;
+extern struct symbol Ct_body;
+struct vector
+{
+  object *v_self;
+};
+union lispunion
+{
+  struct vector v;
+};
+void init_code ()
+{
+  object V659;
+  object _x, _y;
+  object V643;
+  long V648;
+  unsigned char V653;
+  object V651;
+  object V654;
+  object V658;
+
+T1240:
+  if (V648 >= (long)V651)
+    goto T1243;
+  V653 = ((char *) V654->v.v_self)[V648];
+  V659 = (object) V654 + V653;
+T1261:
+  V658 =
+    (object)
+     V659 ? (object) & Ct_body : (object) & Cnil_body;
+  if (V658 == (object) & Cnil_body)
+    goto T1249;
+  goto T1224;
+T1249:
+ V648 = (long) V648 + 1;
+  goto T1240;
+T1243:
+  V643 = (object) & Cnil_body;
+T1224:
+  _y = V643;
+  number_plus (_x, _y);
+}
Index: tree-if-conv.c
===================================================================
--- tree-if-conv.c	(revision 129683)
+++ tree-if-conv.c	(working copy)
@@ -724,7 +724,8 @@ find_phi_replacement_condition (struct l
 
   /* Select condition that is not TRUTH_NOT_EXPR.  */
   tmp_cond = (first_edge->src)->aux;
-  if (TREE_CODE (tmp_cond) == TRUTH_NOT_EXPR)
+  if (tmp_cond != NULL_TREE
+      && TREE_CODE (tmp_cond) == TRUTH_NOT_EXPR)
     {
       edge tmp_edge;
 

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