The testcase shows both live lane extraction and (reduction) root
schedule verification errorneously allow the use/root stmt to be
the same as the placement point.  But as we insert vector defs
after the placement point we have to exclude it.

Bootstrapped and tested on x86_64-unknown-linux-gnu, pushed.

        PR tree-optimization/126936
        * tree-vect-slp.cc (vect_bb_slp_mark_live_stmts): Exclude
        use_stmt from dominance check.
        (vect_schedule_slp): Likewise for root.

        * gcc.dg/vect/bb-slp-pr126936.c: New testcase.
---
 gcc/testsuite/gcc.dg/vect/bb-slp-pr126936.c | 142 ++++++++++++++++++++
 gcc/tree-vect-slp.cc                        |  12 +-
 2 files changed, 151 insertions(+), 3 deletions(-)
 create mode 100644 gcc/testsuite/gcc.dg/vect/bb-slp-pr126936.c

diff --git a/gcc/testsuite/gcc.dg/vect/bb-slp-pr126936.c 
b/gcc/testsuite/gcc.dg/vect/bb-slp-pr126936.c
new file mode 100644
index 00000000000..a5683f0abf1
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/vect/bb-slp-pr126936.c
@@ -0,0 +1,142 @@
+/* { dg-do compile } */
+/* { dg-additional-options "-fgimple" } */
+
+void foo(int);
+
+int *c;
+char d;
+
+void __GIMPLE (ssa,guessed_local(63136016),startwith("slp"))
+fn1 ()
+{
+  int * _1;
+  int _2;
+  char _9;
+  int _12;
+  int _17;
+  int _32;
+  unsigned int _33;
+  int _35;
+  int _36;
+  unsigned int _37;
+  unsigned int _38;
+  int _39;
+  unsigned int _47;
+  int _48;
+  int * _49;
+  int * _54;
+  int _55;
+  unsigned int _56;
+  unsigned int _57;
+  int _58;
+  int _59;
+  int * _70;
+  int _71;
+  unsigned int _72;
+  unsigned int _73;
+  int _74;
+  int _75;
+  int * _86;
+  int _87;
+  unsigned int _88;
+  unsigned int _89;
+  int _90;
+  int _91;
+  int * _102;
+  int _103;
+  unsigned int _104;
+  unsigned int _105;
+  int _106;
+  int _107;
+  int * _118;
+  int _119;
+  unsigned int _120;
+  unsigned int _121;
+  int _122;
+  int _123;
+  unsigned int _136;
+  unsigned int _137;
+  int _138;
+  int _139;
+  unsigned int _152;
+  unsigned int _153;
+  int _154;
+  int _155;
+  int _171;
+  int _187;
+  int _203;
+  int _219;
+  int _235;
+  int _251;
+
+  __BB(2,guessed_local(63136016)):
+  _1 = c;
+  _2 = __MEM <int> (_1 + _Literal (int *) 56);
+  foo (_2);
+  _39 = __MEM <int> (_1);
+  _38 = (unsigned int) _39;
+  _37 = _38 % 3u;
+  _36 = (int) _37;
+  _35 = _36 & _39;
+  __MEM <int> (_1) = _35;
+  _49 = _1 + 8ul;
+  _48 = __MEM <int> (_49);
+  _47 = (unsigned int) _48;
+  _33 = _47 % 3u;
+  _32 = (int) _33;
+  _17 = _32 & _35;
+  __MEM <int> (_1) = _17;
+  _54 = _1 + 16ul;
+  _55 = __MEM <int> (_54);
+  _56 = (unsigned int) _55;
+  _57 = _56 % 3u;
+  _58 = (int) _57;
+  _59 = _17 & _58;
+  __MEM <int> (_1) = _59;
+  _70 = _1 + 24ul;
+  _71 = __MEM <int> (_70);
+  _72 = (unsigned int) _71;
+  _73 = _72 % 3u;
+  _74 = (int) _73;
+  _75 = _59 & _74;
+  __MEM <int> (_1) = _75;
+  _86 = _1 + 32ul;
+  _87 = __MEM <int> (_86);
+  _88 = (unsigned int) _87;
+  _89 = _88 % 3u;
+  _90 = (int) _89;
+  _91 = _75 & _90;
+  __MEM <int> (_1) = _91;
+  _102 = _1 + 40ul;
+  _103 = __MEM <int> (_102);
+  _104 = (unsigned int) _103;
+  _105 = _104 % 3u;
+  _106 = (int) _105;
+  _107 = _91 & _106;
+  __MEM <int> (_1) = _107;
+  _118 = _1 + 48ul;
+  _119 = __MEM <int> (_118);
+  _120 = (unsigned int) _119;
+  _121 = _120 % 3u;
+  _122 = (int) _121;
+  _123 = _107 & _122;
+  _136 = (unsigned int) _2;
+  _137 = _136 % 3u;
+  _138 = (int) _137;
+  _139 = _123 & _138;
+  _152 = (unsigned int) _139;
+  _153 = _152 % 3u;
+  _154 = (int) _153;
+  _155 = _139 & _154;
+  _171 = _32 & _155;
+  _187 = _58 & _171;
+  _203 = _74 & _187;
+  _219 = _90 & _203;
+  _235 = _106 & _219;
+  _251 = _122 & _235;
+  _12 = _138 & _251;
+  __MEM <int> (_1) = _12;
+  _9 = (char) _137;
+  d = _9;
+  return;
+}
diff --git a/gcc/tree-vect-slp.cc b/gcc/tree-vect-slp.cc
index d0692b088c1..e7aff6565bf 100644
--- a/gcc/tree-vect-slp.cc
+++ b/gcc/tree-vect-slp.cc
@@ -9400,7 +9400,10 @@ vect_bb_slp_mark_live_stmts (bb_vec_info bb_vinfo, 
slp_tree node,
                                       gimple_bb (last_stmt)))
                    can_insert = false;
                }
-             else if (!vect_stmt_dominates_stmt_p (last_stmt, use_stmt))
+             /* As we instert after last_stmt it may not be the use_stmt
+                itself.  */
+             else if (last_stmt == use_stmt
+                      || !vect_stmt_dominates_stmt_p (last_stmt, use_stmt))
                can_insert = false;
              if (!can_insert)
                {
@@ -12924,8 +12927,11 @@ vect_schedule_slp (vec_info *vinfo, vec<slp_instance> 
&slp_instances,
          if (place_only)
            {
              gimple *root_stmt = instance->root_stmts[0]->stmt;
-             res &= (!node->si || vect_stmt_dominates_stmt_p (node->si,
-                                                              root_stmt));
+             res &= (!node->si
+                     /* As we instert after node->si it may not be the
+                        root_stmt itself.  */
+                     || (node->si != root_stmt
+                         && vect_stmt_dominates_stmt_p (node->si, root_stmt)));
            }
          else
            vectorize_slp_instance_root_stmt (vinfo, node, instance);
-- 
2.51.0

Reply via email to