public inbox for gcc-cvs@sourceware.org
help / color / mirror / Atom feed
* [gcc r12-8645] openmp: Fix up handling of non-rectangular simd loops with pointer type iterators [PR106449]
@ 2022-07-30  9:34 Jakub Jelinek
  0 siblings, 0 replies; only message in thread
From: Jakub Jelinek @ 2022-07-30  9:34 UTC (permalink / raw)
  To: gcc-cvs

https://gcc.gnu.org/g:681c73db9bd156f9b65a73ccc6c4a0a697fe70d6

commit r12-8645-g681c73db9bd156f9b65a73ccc6c4a0a697fe70d6
Author: Jakub Jelinek <jakub@redhat.com>
Date:   Fri Jul 29 09:49:11 2022 +0200

    openmp: Fix up handling of non-rectangular simd loops with pointer type iterators [PR106449]
    
    There were 2 issues visible on this new testcase, one that we didn't have
    special POINTER_TYPE_P handling in a few spots of expand_omp_simd - for
    pointers we need to use POINTER_PLUS_EXPR and need to have the non-pointer
    part in sizetype, for non-rectangular loop on the other side we can rely on
    multiplication factor 1, pointers can't be multiplied, without those changes
    we'd ICE.  The other issue was that we put n2 expression directly into a
    comparison in a condition and regimplified that, for the &a[512] case that
    and with gimplification being destructed that unfortunately meant modification
    of original fd->loops[?].n2.  Fixed by unsharing the expression.  This was
    causing a runtime failure on the testcase.
    
    2022-07-29  Jakub Jelinek  <jakub@redhat.com>
    
            PR middle-end/106449
            * omp-expand.cc (expand_omp_simd): Fix up handling of pointer
            iterators in non-rectangular simd loops.  Unshare fd->loops[i].n2
            or n2 before regimplifying it inside of a condition.
    
            * testsuite/libgomp.c-c++-common/pr106449.c: New test.
    
    (cherry picked from commit 97d32048c04e9787fccadc4bae1c042754503e34)

Diff:
---
 gcc/omp-expand.cc                                 | 57 ++++++++++++++-------
 libgomp/testsuite/libgomp.c-c++-common/pr106449.c | 62 +++++++++++++++++++++++
 2 files changed, 101 insertions(+), 18 deletions(-)

diff --git a/gcc/omp-expand.cc b/gcc/omp-expand.cc
index ee708314793..19d04a0d959 100644
--- a/gcc/omp-expand.cc
+++ b/gcc/omp-expand.cc
@@ -6718,7 +6718,7 @@ expand_omp_simd (struct omp_region *region, struct omp_for_data *fd)
       if (fd->loops[i].m2)
 	t = n2v = create_tmp_var (itype);
       else
-	t = fold_convert (itype, fd->loops[i].n2);
+	t = fold_convert (itype, unshare_expr (fd->loops[i].n2));
       t = force_gimple_operand_gsi (&gsi, t, true, NULL_TREE,
 				    false, GSI_CONTINUE_LINKING);
       tree v = fd->loops[i].v;
@@ -6732,7 +6732,7 @@ expand_omp_simd (struct omp_region *region, struct omp_for_data *fd)
       if (fd->collapse > 1 && !broken_loop)
 	t = n2var;
       else
-	t = fold_convert (type, n2);
+	t = fold_convert (type, unshare_expr (n2));
       t = force_gimple_operand_gsi (&gsi, t, true, NULL_TREE,
 				    false, GSI_CONTINUE_LINKING);
       tree v = fd->loop.v;
@@ -6844,7 +6844,7 @@ expand_omp_simd (struct omp_region *region, struct omp_for_data *fd)
 	  if (fd->loops[i].m2)
 	    t = nextn2v = create_tmp_var (itype);
 	  else
-	    t = fold_convert (itype, fd->loops[i].n2);
+	    t = fold_convert (itype, unshare_expr (fd->loops[i].n2));
 	  t = force_gimple_operand_gsi (&gsi, t, true, NULL_TREE,
 					false, GSI_CONTINUE_LINKING);
 	  tree v = fd->loops[i].v;
@@ -6874,17 +6874,25 @@ expand_omp_simd (struct omp_region *region, struct omp_for_data *fd)
 	  ne->probability = e->probability.invert ();
 
 	  gsi = gsi_after_labels (init_bb);
-	  t = fold_convert (TREE_TYPE (fd->loops[i + 1].v),
-			    fd->loops[i + 1].n1);
 	  if (fd->loops[i + 1].m1)
 	    {
-	      tree t2 = fold_convert (TREE_TYPE (t),
+	      tree t2 = fold_convert (TREE_TYPE (fd->loops[i + 1].v),
 				      fd->loops[i + 1
 						- fd->loops[i + 1].outer].v);
-	      tree t3 = fold_convert (TREE_TYPE (t), fd->loops[i + 1].m1);
-	      t2 = fold_build2 (MULT_EXPR, TREE_TYPE (t), t2, t3);
-	      t = fold_build2 (PLUS_EXPR, TREE_TYPE (t), t, t2);
+	      if (POINTER_TYPE_P (TREE_TYPE (t2)))
+		t = fold_build_pointer_plus (t2, fd->loops[i + 1].n1);
+	      else
+		{
+		  t = fold_convert (TREE_TYPE (fd->loops[i + 1].v),
+				    fd->loops[i + 1].n1);
+		  tree t3 = fold_convert (TREE_TYPE (t), fd->loops[i + 1].m1);
+		  t2 = fold_build2 (MULT_EXPR, TREE_TYPE (t), t2, t3);
+		  t = fold_build2 (PLUS_EXPR, TREE_TYPE (t), t, t2);
+		}
 	    }
+	  else
+	    t = fold_convert (TREE_TYPE (fd->loops[i + 1].v),
+			      fd->loops[i + 1].n1);
 	  expand_omp_build_assign (&gsi, fd->loops[i + 1].v, t);
 	  if (fd->loops[i + 1].m2)
 	    {
@@ -6893,14 +6901,19 @@ expand_omp_simd (struct omp_region *region, struct omp_for_data *fd)
 		  gcc_assert (n2v == NULL_TREE);
 		  n2v = create_tmp_var (TREE_TYPE (fd->loops[i + 1].v));
 		}
-	      t = fold_convert (TREE_TYPE (fd->loops[i + 1].v),
-				fd->loops[i + 1].n2);
-	      tree t2 = fold_convert (TREE_TYPE (t),
+	      tree t2 = fold_convert (TREE_TYPE (fd->loops[i + 1].v),
 				      fd->loops[i + 1
 						- fd->loops[i + 1].outer].v);
-	      tree t3 = fold_convert (TREE_TYPE (t), fd->loops[i + 1].m2);
-	      t2 = fold_build2 (MULT_EXPR, TREE_TYPE (t), t2, t3);
-	      t = fold_build2 (PLUS_EXPR, TREE_TYPE (t), t, t2);
+	      if (POINTER_TYPE_P (TREE_TYPE (t2)))
+		t = fold_build_pointer_plus (t2, fd->loops[i + 1].n2);
+	      else
+		{
+		  t = fold_convert (TREE_TYPE (fd->loops[i + 1].v),
+				    fd->loops[i + 1].n2);
+		  tree t3 = fold_convert (TREE_TYPE (t), fd->loops[i + 1].m2);
+		  t2 = fold_build2 (MULT_EXPR, TREE_TYPE (t), t2, t3);
+		  t = fold_build2 (PLUS_EXPR, TREE_TYPE (t), t, t2);
+		}
 	      expand_omp_build_assign (&gsi, n2v, t);
 	    }
 	  if (i + 2 == fd->collapse && n2var)
@@ -6916,17 +6929,25 @@ expand_omp_simd (struct omp_region *region, struct omp_for_data *fd)
 	      tree t2 = fold_build2 (MINUS_EXPR, type, n2, fd->loop.v);
 	      if (fd->loops[i + 1].m1 || fd->loops[i + 1].m2)
 		{
+		  tree itype = TREE_TYPE (fd->loops[i].v);
+		  if (POINTER_TYPE_P (itype))
+		    itype = signed_type_for (itype);
 		  t = build_int_cst (itype, (fd->loops[i + 1].cond_code
 					     == LT_EXPR ? -1 : 1));
 		  t = fold_build2 (PLUS_EXPR, itype,
 				   fold_convert (itype,
 						 fd->loops[i + 1].step), t);
-		  if (fd->loops[i + 1].m2)
-		    t = fold_build2 (PLUS_EXPR, itype, t, n2v);
-		  else
+		  if (fd->loops[i + 1].m2 == NULL_TREE)
 		    t = fold_build2 (PLUS_EXPR, itype, t,
 				     fold_convert (itype,
 						   fd->loops[i + 1].n2));
+		  else if (POINTER_TYPE_P (TREE_TYPE (n2v)))
+		    {
+		      t = fold_build_pointer_plus (n2v, t);
+		      t = fold_convert (itype, t);
+		    }
+		  else
+		    t = fold_build2 (PLUS_EXPR, itype, t, n2v);
 		  t = fold_build2 (MINUS_EXPR, itype, t,
 				   fold_convert (itype, fd->loops[i + 1].v));
 		  tree step = fold_convert (itype, fd->loops[i + 1].step);
diff --git a/libgomp/testsuite/libgomp.c-c++-common/pr106449.c b/libgomp/testsuite/libgomp.c-c++-common/pr106449.c
new file mode 100644
index 00000000000..ea3cd827cee
--- /dev/null
+++ b/libgomp/testsuite/libgomp.c-c++-common/pr106449.c
@@ -0,0 +1,62 @@
+/* PR middle-end/106449 */
+/* { dg-do run } */
+
+void
+foo (void)
+{
+  int a[1024], *b[65536];
+  int *p, *q, **r = &b[0], i;
+  #pragma omp simd collapse(2) linear(r : 2)
+  for (p = &a[0]; p < &a[512]; p++)
+    for (q = p + 64; q < p + 128; q++)
+      {
+        *r++ = p;
+        *r++ = q;
+      }
+  for (i = 0; i < 32768; i++)
+    if (b[2 * i] != &a[i / 64] || b[2 * i + 1] != &a[(i / 64) + 64 + (i % 64)])
+      __builtin_abort ();
+}
+
+void
+bar (int n, int m)
+{
+  int a[1024], *b[65536];
+  int *p, *q, **r = &b[0], i;
+  #pragma omp parallel for simd collapse(2) linear(r : 2)
+  for (p = &a[0]; p < &a[512]; p++)
+    for (q = p + n; q < p + m; q++)
+      {
+        *r++ = p;
+        *r++ = q;
+      }
+  for (i = 0; i < 32768; i++)
+    if (b[2 * i] != &a[i / 64] || b[2 * i + 1] != &a[(i / 64) + 64 + (i % 64)])
+      __builtin_abort ();
+}
+
+void
+baz (int n, int m)
+{
+  int a[1024], *b[8192];
+  int *p, *q, **r = &b[0], i;
+  #pragma omp parallel for simd collapse(2) linear(r : 2)
+  for (p = &a[0]; p < &a[512]; p += 4)
+    for (q = p + n; q < p + m; q += 2)
+      {
+        *r++ = p;
+        *r++ = q;
+      }
+  for (i = 0; i < 4096; i++)
+    if (b[2 * i] != &a[(i / 32) * 4] || b[2 * i + 1] != &a[(i / 32) * 4 + 64 + (i % 32) * 2])
+      __builtin_abort ();
+}
+
+int
+main ()
+{
+  foo ();
+  bar (64, 128);
+  baz (64, 128);
+  return 0;
+}


^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2022-07-30  9:34 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-07-30  9:34 [gcc r12-8645] openmp: Fix up handling of non-rectangular simd loops with pointer type iterators [PR106449] Jakub Jelinek

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).