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]

[gomp4.1] Doacross tweaks


Hi!

The latest spec proposals change the meaning of the ordered(n) clause
if collapse > 1 to count the number of source loops.
The ordered >= collapse requirement is something I'm pushing for even when
it is not in the spec (yet).
And, finally, another proposed change is that the + or - signs in the sink:
vector are significant (primarily for unsigned iterators).

Tested on x86_64-linux, committed to gomp-4_1-branch.

2015-09-25  Jakub Jelinek  <jakub@redhat.com>

	* tree.h (OMP_CLAUSE_DEPEND_SINK_NEGATIVE): Define.
	* omp-low.c (extract_omp_for_data, expand_omp_for_init_counts,
	expand_omp_ordered_source, expand_omp_ordered_sink,
	expand_omp_for_ordered_loops, expand_omp_for_generic): Adjust
	for fd->ordered being newly 0 when it used to be 0 before,
	but otherwise being equal to fd->collapse - 1 + old fd->ordered.
	expand_omp_ordered_source_sink): Likewise.  Warn for lexically
	later iteration sink, or for sink on iteration never in iteration
	space.  Use OMP_CLAUSE_DEPEND_SINK_NEGATIVE.
	(lower_depend_clauses): Assert not seeing sink/source depend kinds.
	* tree-pretty-print.c (dump_omp_clause): Use
	OMP_CLAUSE_DEPEND_SINK_NEGATIVE for the +/- sign of sink vector
	constants.
gcc/c/
	* c-parser.c (c_parser_omp_clause_depend_sink): Put - sign
	into OMP_CLAUSE_DEPEND_SINK_NEGATIVE instead of negating the number.
	(c_parser_omp_for_loop): Adjust for ordered clause counting
	source loops before collapsing instead of after it.  Require
	ordered clause parameter to be >= collapse parameter.
gcc/cp/
	* parser.c (cp_parser_omp_clause_depend_sink): Put - sign
	into OMP_CLAUSE_DEPEND_SINK_NEGATIVE instead of negating the number.
	(cp_parser_omp_for_loop): Adjust for ordered clause counting
	source loops before collapsing instead of after it.  Require
	ordered clause parameter to be >= collapse parameter.
	* pt.c (tsubst_omp_clause_decl): Copy
	OMP_CLAUSE_DEPEND_SINK_NEGATIVE flag.
gcc/testsuite/
	* c-c++-common/gomp/sink-1.c (foo): Adjust for new meaning of
	ordered clause on collapse > 1 loops.
	* gcc.dg/gomp/sink-fold-2.c (funk): Remove xfails and adjust
	for new diagnostics wording and only warnings, no errors.
libgomp/
	* testsuite/libgomp.c/doacross-1.c (main): Adjust for new meaning of
	ordered clause on collapse > 1 loops.

--- gcc/tree.h.jj	2015-09-03 16:36:19.000000000 +0200
+++ gcc/tree.h	2015-09-25 13:40:16.739807842 +0200
@@ -1446,6 +1446,9 @@ extern void protected_set_expr_location
 #define OMP_CLAUSE_DEPEND_KIND(NODE) \
   (OMP_CLAUSE_SUBCODE_CHECK (NODE, OMP_CLAUSE_DEPEND)->omp_clause.subcode.depend_kind)
 
+#define OMP_CLAUSE_DEPEND_SINK_NEGATIVE(NODE) \
+  TREE_PUBLIC (TREE_LIST_CHECK (NODE))
+
 #define OMP_CLAUSE_MAP_KIND(NODE) \
   ((enum gomp_map_kind) OMP_CLAUSE_SUBCODE_CHECK (NODE, OMP_CLAUSE_MAP)->omp_clause.subcode.map_kind)
 #define OMP_CLAUSE_SET_MAP_KIND(NODE, MAP_KIND) \
--- gcc/omp-low.c.jj	2015-09-24 20:20:32.000000000 +0200
+++ gcc/omp-low.c	2015-09-25 18:17:13.331812912 +0200
@@ -565,7 +565,7 @@ extract_omp_for_data (gomp_for *for_stmt
 			 ? integer_zero_node : integer_one_node;
     }
 
-  int cnt = fd->collapse + (fd->ordered > 0 ? fd->ordered - 1 : 0);
+  int cnt = fd->ordered ? fd->ordered : fd->collapse;
   for (i = 0; i < cnt; i++)
     {
       if (i == 0 && fd->collapse == 1 && (fd->ordered == 0 || loops == NULL))
@@ -6761,7 +6761,7 @@ expand_omp_for_init_counts (struct omp_f
       return;
     }
 
-  for (i = fd->collapse; i < fd->collapse + fd->ordered - 1; i++)
+  for (i = fd->collapse; i < fd->ordered; i++)
     {
       tree itype = TREE_TYPE (fd->loops[i].v);
       counts[i] = NULL_TREE;
@@ -6770,12 +6770,12 @@ expand_omp_for_init_counts (struct omp_f
 		       fold_convert (itype, fd->loops[i].n2));
       if (t && integer_zerop (t))
 	{
-	  for (i = fd->collapse; i < fd->collapse + fd->ordered - 1; i++)
+	  for (i = fd->collapse; i < fd->ordered; i++)
 	    counts[i] = build_int_cst (type, 0);
 	  break;
 	}
     }
-  for (i = 0; i < fd->collapse + (fd->ordered ? fd->ordered - 1 : 0); i++)
+  for (i = 0; i < (fd->ordered ? fd->ordered : fd->collapse); i++)
     {
       tree itype = TREE_TYPE (fd->loops[i].v);
 
@@ -7074,8 +7074,7 @@ expand_omp_ordered_source (gimple_stmt_i
   enum built_in_function source_ix = BUILT_IN_GOMP_DOACROSS_POST;
   gimple g
     = gimple_build_call (builtin_decl_explicit (source_ix), 1,
-			 build_fold_addr_expr (counts[fd->collapse
-						      + fd->ordered - 1]));
+			 build_fold_addr_expr (counts[fd->ordered]));
   gimple_set_location (g, loc);
   gsi_insert_before (gsi, g, GSI_SAME_STMT);
 }
@@ -7091,13 +7090,38 @@ expand_omp_ordered_sink (gimple_stmt_ite
   tree t, off, coff = NULL_TREE, deps = OMP_CLAUSE_DECL (c), cond = NULL_TREE;
   int i;
   gimple_stmt_iterator gsi2 = *gsi;
+  bool warned_step = false;
 
+  for (i = 0; i < fd->ordered; i++)
+    {
+      off = TREE_PURPOSE (deps);
+      if (!integer_zerop (off))
+	{
+	  gcc_assert (fd->loops[i].cond_code == LT_EXPR
+		      || fd->loops[i].cond_code == GT_EXPR);
+	  bool forward = fd->loops[i].cond_code == LT_EXPR;
+	  if (forward ^ OMP_CLAUSE_DEPEND_SINK_NEGATIVE (deps))
+	    warning_at (loc, 0, "%<depend(sink)%> clause waiting for "
+				"lexically later iteration");
+	  break;
+	}
+      deps = TREE_CHAIN (deps);
+    }
+  /* If all offsets corresponding to the collapsed loops are zero,
+     this depend clause can be ignored.  FIXME: but there is still a
+     flush needed.  We need to emit one __sync_synchronize () for it
+     though (perhaps conditionally)?  Solve this together with the
+     conservative dependence folding optimization.
+  if (i >= fd->collapse)
+    return;  */
+
+  deps = OMP_CLAUSE_DECL (c);
   gsi_prev (&gsi2);
   edge e1 = split_block (gsi_bb (gsi2), gsi_stmt (gsi2));
   edge e2 = split_block_after_labels (e1->dest);
 
   *gsi = gsi_after_labels (e1->dest);
-  for (i = 0; i < fd->collapse + fd->ordered - 1; i++)
+  for (i = 0; i < fd->ordered; i++)
     {
       tree itype = TREE_TYPE (fd->loops[i].v);
       if (POINTER_TYPE_P (itype))
@@ -7114,51 +7138,34 @@ expand_omp_ordered_sink (gimple_stmt_ite
 	  tree a;
 	  tree co = fold_convert_loc (loc, itype, off);
 	  if (POINTER_TYPE_P (TREE_TYPE (fd->loops[i].v)))
-	    a = fold_build2_loc (loc, POINTER_PLUS_EXPR,
-				 TREE_TYPE (fd->loops[i].v), fd->loops[i].v,
-				 co);
+	    {
+	      if (OMP_CLAUSE_DEPEND_SINK_NEGATIVE (deps))
+		co = fold_build1_loc (loc, NEGATE_EXPR, itype, co);
+	      a = fold_build2_loc (loc, POINTER_PLUS_EXPR,
+				   TREE_TYPE (fd->loops[i].v), fd->loops[i].v,
+				   co);
+	    }
+	  else if (OMP_CLAUSE_DEPEND_SINK_NEGATIVE (deps))
+	    a = fold_build2_loc (loc, MINUS_EXPR, TREE_TYPE (fd->loops[i].v),
+				 fd->loops[i].v, co);
 	  else
 	    a = fold_build2_loc (loc, PLUS_EXPR, TREE_TYPE (fd->loops[i].v),
 				 fd->loops[i].v, co);
-	  if (!TYPE_UNSIGNED (itype)
-	      || POINTER_TYPE_P (TREE_TYPE (fd->loops[i].v)))
+	  if (fd->loops[i].cond_code == LT_EXPR)
 	    {
-	      if (fd->loops[i].cond_code == LT_EXPR)
-		{
-		  if (wi::neg_p (co))
-		    t = fold_build2_loc (loc, GE_EXPR, boolean_type_node, a,
-					 fd->loops[i].n1);
-		  else
-		    t = fold_build2_loc (loc, LT_EXPR, boolean_type_node, a,
-					 fd->loops[i].n2);
-		}
-	      else if (wi::neg_p (co))
-		t = fold_build2_loc (loc, GT_EXPR, boolean_type_node, a,
-				     fd->loops[i].n2);
-	      else
-		t = fold_build2_loc (loc, LE_EXPR, boolean_type_node, a,
+	      if (OMP_CLAUSE_DEPEND_SINK_NEGATIVE (deps))
+		t = fold_build2_loc (loc, GE_EXPR, boolean_type_node, a,
 				     fd->loops[i].n1);
+	      else
+		t = fold_build2_loc (loc, LT_EXPR, boolean_type_node, a,
+				     fd->loops[i].n2);
 	    }
-	  else if (fd->loops[i].cond_code == LT_EXPR)
-	    {
-	      a = fold_build2_loc (loc, MINUS_EXPR, TREE_TYPE (fd->loops[i].v),
-				   a, fd->loops[i].n1);
-	      t = fold_build2_loc (loc, MINUS_EXPR, TREE_TYPE (fd->loops[i].v),
-				   fd->loops[i].n2, fd->loops[i].n1);
-	      t = fold_build2_loc (loc, LT_EXPR, boolean_type_node, a, t);
-	    }
+	  else if (OMP_CLAUSE_DEPEND_SINK_NEGATIVE (deps))
+	    t = fold_build2_loc (loc, GT_EXPR, boolean_type_node, a,
+				 fd->loops[i].n2);
 	  else
-	    {
-	      a = fold_build2_loc (loc, MINUS_EXPR, TREE_TYPE (fd->loops[i].v),
-				   a, fd->loops[i].n2);
-	      a = fold_build2_loc (loc, MINUS_EXPR, TREE_TYPE (fd->loops[i].v),
-				   a,
-				   build_int_cst (TREE_TYPE (fd->loops[i].v),
-						  1));
-	      t = fold_build2_loc (loc, MINUS_EXPR, TREE_TYPE (fd->loops[i].v),
-				   fd->loops[i].n1, fd->loops[i].n2);
-	      t = fold_build2_loc (loc, LT_EXPR, boolean_type_node, a, t);
-	    }
+	    t = fold_build2_loc (loc, LE_EXPR, boolean_type_node, a,
+				 fd->loops[i].n1);
 	}
       if (cond)
 	cond = fold_build2_loc (loc, BIT_AND_EXPR, boolean_type_node, cond, t);
@@ -7172,15 +7179,19 @@ expand_omp_ordered_sink (gimple_stmt_ite
 	  : !integer_minus_onep (fd->loops[i].step))
 	{
 	  if (TYPE_UNSIGNED (itype) && fd->loops[i].cond_code == GT_EXPR)
-	    t = fold_build2_loc (loc, TRUNC_MOD_EXPR, itype,
-				 fold_build1_loc (loc, NEGATE_EXPR, itype,
-						  off),
+	    t = fold_build2_loc (loc, TRUNC_MOD_EXPR, itype, off,
 				 fold_build1_loc (loc, NEGATE_EXPR, itype,
 						  s));
 	  else
 	    t = fold_build2_loc (loc, TRUNC_MOD_EXPR, itype, off, s);
 	  t = fold_build2_loc (loc, EQ_EXPR, boolean_type_node, t,
 			       build_int_cst (itype, 0));
+	  if (integer_zerop (t) && !warned_step)
+	    {
+	      warning_at (loc, 0, "%<depend(sink)%> refers to iteration never "
+				  "in the iteration space");
+	      warned_step = true;
+	    }
 	  cond = fold_build2_loc (loc, BIT_AND_EXPR, boolean_type_node,
 				  cond, t);
 	}
@@ -7196,13 +7207,13 @@ expand_omp_ordered_sink (gimple_stmt_ite
 	  t = fold_convert_loc (loc, fd->iter_type, t);
 	}
       if (TYPE_UNSIGNED (itype) && fd->loops[i].cond_code == GT_EXPR)
-	off = fold_build2_loc (loc, TRUNC_DIV_EXPR, itype,
-			       fold_build1_loc (loc, NEGATE_EXPR, itype,
-						off),
+	off = fold_build2_loc (loc, TRUNC_DIV_EXPR, itype, off,
 			       fold_build1_loc (loc, NEGATE_EXPR, itype,
 						s));
       else
 	off = fold_build2_loc (loc, TRUNC_DIV_EXPR, itype, off, s);
+      if (OMP_CLAUSE_DEPEND_SINK_NEGATIVE (deps))
+	off = fold_build1_loc (loc, NEGATE_EXPR, itype, off);
       off = fold_convert_loc (loc, fd->iter_type, off);
       if (i <= fd->collapse - 1 && fd->collapse > 1)
 	{
@@ -7251,7 +7262,7 @@ expand_omp_ordered_source_sink (struct o
 {
   struct omp_region *inner;
   int i;
-  for (i = fd->collapse - 1; i < fd->collapse + fd->ordered - 1; i++)
+  for (i = fd->collapse - 1; i < fd->ordered; i++)
     if (i == fd->collapse - 1 && fd->collapse > 1)
       counts[i] = NULL_TREE;
     else if (i >= fd->collapse && !cont_bb)
@@ -7261,9 +7272,10 @@ expand_omp_ordered_source_sink (struct o
       counts[i] = NULL_TREE;
     else
       counts[i] = create_tmp_var (fd->iter_type, ".orditer");
-  tree atype = build_array_type_nelts (fd->iter_type, fd->ordered);
-  counts[fd->collapse + fd->ordered - 1] = create_tmp_var (atype, ".orditera");
-  TREE_ADDRESSABLE (counts[fd->collapse + fd->ordered - 1]) = 1;
+  tree atype
+    = build_array_type_nelts (fd->iter_type, fd->ordered - fd->collapse + 1);
+  counts[fd->ordered] = create_tmp_var (atype, ".orditera");
+  TREE_ADDRESSABLE (counts[fd->ordered]) = 1;
 
   for (inner = region->inner; inner; inner = inner->next)
     if (inner->type == GIMPLE_OMP_ORDERED)
@@ -7286,25 +7298,25 @@ expand_omp_ordered_source_sink (struct o
       }
 }
 
-/* Wrap the body into fd->ordered - 1 loops that aren't collapsed.  */
+/* Wrap the body into fd->ordered - fd->collapse loops that aren't
+   collapsed.  */
 
 static basic_block
 expand_omp_for_ordered_loops (struct omp_for_data *fd, tree *counts,
 			      basic_block cont_bb, basic_block body_bb)
 {
-  if (fd->ordered <= 1)
+  if (fd->ordered == fd->collapse)
     return cont_bb;
 
   if (!cont_bb)
     {
       gimple_stmt_iterator gsi = gsi_after_labels (body_bb);
-      for (int i = fd->collapse; i < fd->collapse + fd->ordered - 1; i++)
+      for (int i = fd->collapse; i < fd->ordered; i++)
 	{
 	  tree type = TREE_TYPE (fd->loops[i].v);
 	  tree n1 = fold_convert (type, fd->loops[i].n1);
 	  expand_omp_build_assign (&gsi, fd->loops[i].v, n1);
-	  tree aref = build4 (ARRAY_REF, fd->iter_type,
-			      counts[fd->collapse + fd->ordered - 1],
+	  tree aref = build4 (ARRAY_REF, fd->iter_type, counts[fd->ordered],
 			      size_int (i - fd->collapse + 1),
 			      NULL_TREE, NULL_TREE);
 	  expand_omp_build_assign (&gsi, aref, build_zero_cst (fd->iter_type));
@@ -7312,7 +7324,7 @@ expand_omp_for_ordered_loops (struct omp
       return NULL;
     }
 
-  for (int i = fd->collapse + fd->ordered - 2; i >= fd->collapse; i--)
+  for (int i = fd->ordered - 1; i >= fd->collapse; i--)
     {
       tree t, type = TREE_TYPE (fd->loops[i].v);
       gimple_stmt_iterator gsi = gsi_after_labels (body_bb);
@@ -7321,8 +7333,7 @@ expand_omp_for_ordered_loops (struct omp
       if (counts[i])
 	expand_omp_build_assign (&gsi, counts[i],
 				 build_zero_cst (fd->iter_type));
-      tree aref = build4 (ARRAY_REF, fd->iter_type,
-			  counts[fd->collapse + fd->ordered - 1],
+      tree aref = build4 (ARRAY_REF, fd->iter_type, counts[fd->ordered],
 			  size_int (i - fd->collapse + 1),
 			  NULL_TREE, NULL_TREE);
       expand_omp_build_assign (&gsi, aref, build_zero_cst (fd->iter_type));
@@ -7358,8 +7369,7 @@ expand_omp_for_ordered_loops (struct omp
 	  t = force_gimple_operand_gsi (&gsi, t, true, NULL_TREE,
 					true, GSI_SAME_STMT);
 	}
-      aref = build4 (ARRAY_REF, fd->iter_type,
-		     counts[fd->collapse + fd->ordered - 1],
+      aref = build4 (ARRAY_REF, fd->iter_type, counts[fd->ordered],
 		     size_int (i - fd->collapse + 1), NULL_TREE, NULL_TREE);
       expand_omp_build_assign (&gsi, aref, t);
       gsi_prev (&gsi);
@@ -7535,8 +7545,7 @@ expand_omp_for_generic (struct omp_regio
       int first_zero_iter1 = -1, first_zero_iter2 = -1;
       basic_block zero_iter1_bb = NULL, zero_iter2_bb = NULL, l2_dom_bb = NULL;
 
-      counts = XALLOCAVEC (tree, fd->collapse
-				 + (fd->ordered ? fd->ordered - 1 + 1 : 0));
+      counts = XALLOCAVEC (tree, fd->ordered ? fd->ordered + 1 : fd->collapse);
       expand_omp_for_init_counts (fd, &gsi, entry_bb, counts,
 				  zero_iter1_bb, first_zero_iter1,
 				  zero_iter2_bb, first_zero_iter2, l2_dom_bb);
@@ -7547,7 +7556,7 @@ expand_omp_for_generic (struct omp_regio
 	     some loop has zero iterations.  But the body shouldn't
 	     be executed in that case, so just avoid uninit warnings.  */
 	  for (i = first_zero_iter1;
-	       i < fd->collapse + (fd->ordered ? fd->ordered - 1 : 0); i++)
+	       i < (fd->ordered ? fd->ordered : fd->collapse); i++)
 	    if (SSA_VAR_P (counts[i]))
 	      TREE_NO_WARNING (counts[i]) = 1;
 	  gsi_prev (&gsi);
@@ -7564,7 +7573,7 @@ expand_omp_for_generic (struct omp_regio
 	  /* Some counts[i] vars might be uninitialized if
 	     some loop has zero iterations.  But the body shouldn't
 	     be executed in that case, so just avoid uninit warnings.  */
-	  for (i = first_zero_iter2; i < fd->collapse + fd->ordered - 1; i++)
+	  for (i = first_zero_iter2; i < fd->ordered; i++)
 	    if (SSA_VAR_P (counts[i]))
 	      TREE_NO_WARNING (counts[i]) = 1;
 	  if (zero_iter1_bb)
@@ -7640,18 +7649,20 @@ expand_omp_for_generic (struct omp_regio
       t3 = build_fold_addr_expr (istart0);
       if (fd->ordered)
 	{
-	  t0 = build_int_cst (unsigned_type_node, fd->ordered);
+	  t0 = build_int_cst (unsigned_type_node,
+			      fd->ordered - fd->collapse + 1);
 	  arr = create_tmp_var (build_array_type_nelts (fd->iter_type,
-							fd->ordered),
+							fd->ordered
+							- fd->collapse + 1),
 				".omp_counts");
 	  DECL_NAMELESS (arr) = 1;
 	  TREE_ADDRESSABLE (arr) = 1;
 	  TREE_STATIC (arr) = 1;
 	  vec<constructor_elt, va_gc> *v;
-	  vec_alloc (v, fd->ordered);
+	  vec_alloc (v, fd->ordered - fd->collapse + 1);
 	  int idx;
 
-	  for (idx = 0; idx < fd->ordered; idx++)
+	  for (idx = 0; idx < fd->ordered - fd->collapse + 1; idx++)
 	    {
 	      tree c;
 	      if (idx == 0 && fd->collapse > 1)
@@ -7927,7 +7938,7 @@ expand_omp_for_generic (struct omp_regio
 	 those counts only for collapsed loops, and only for the 2nd
 	 till the last collapsed one.  Move those one element earlier,
 	 we'll use counts[fd->collapse - 1] for the first source/sink
-	 iteration counter and so on and counts[fd->collapse + fd->ordered - 1]
+	 iteration counter and so on and counts[fd->ordered]
 	 as the array holding the current counter values for
 	 depend(source).  */
       if (fd->collapse > 1)
@@ -7944,8 +7955,7 @@ expand_omp_for_generic (struct omp_regio
 	  t = fold_build2 (PLUS_EXPR, fd->iter_type, counts[fd->collapse - 1],
 			   build_int_cst (fd->iter_type, 1));
 	  expand_omp_build_assign (&gsi, counts[fd->collapse - 1], t);
-	  tree aref = build4 (ARRAY_REF, fd->iter_type,
-			      counts[fd->collapse + fd->ordered - 1],
+	  tree aref = build4 (ARRAY_REF, fd->iter_type, counts[fd->ordered],
 			      size_zero_node, NULL_TREE, NULL_TREE);
 	  expand_omp_build_assign (&gsi, aref, counts[fd->collapse - 1]);
 	  t = counts[fd->collapse - 1];
@@ -7959,8 +7969,7 @@ expand_omp_for_generic (struct omp_regio
 	  t = fold_convert (fd->iter_type, t);
 	}
       gsi = gsi_last_bb (l0_bb);
-      tree aref = build4 (ARRAY_REF, fd->iter_type,
-			  counts[fd->collapse + fd->ordered - 1],
+      tree aref = build4 (ARRAY_REF, fd->iter_type, counts[fd->ordered],
 			  size_zero_node, NULL_TREE, NULL_TREE);
       t = force_gimple_operand_gsi (&gsi, t, true, NULL_TREE,
 				    false, GSI_CONTINUE_LINKING);
@@ -8001,8 +8010,8 @@ expand_omp_for_generic (struct omp_regio
 		  t = fold_convert (fd->iter_type, t);
 		}
 	      tree aref = build4 (ARRAY_REF, fd->iter_type,
-				  counts[fd->collapse + fd->ordered - 1],
-				  size_zero_node, NULL_TREE, NULL_TREE);
+				  counts[fd->ordered], size_zero_node,
+				  NULL_TREE, NULL_TREE);
 	      t = force_gimple_operand_gsi (&gsi, t, true, NULL_TREE,
 					    true, GSI_SAME_STMT);
 	      expand_omp_build_assign (&gsi, aref, t);
@@ -8050,7 +8059,7 @@ expand_omp_for_generic (struct omp_regio
   gsi_insert_after (&gsi, call_stmt, GSI_SAME_STMT);
   if (fd->ordered)
     {
-      tree arr = counts[fd->collapse + fd->ordered - 1];
+      tree arr = counts[fd->ordered];
       tree clobber = build_constructor (TREE_TYPE (arr), NULL);
       TREE_THIS_VOLATILE (clobber) = 1;
       gsi_insert_after (&gsi, gimple_build_assign (arr, clobber),
@@ -13613,8 +13622,7 @@ lower_depend_clauses (tree *pclauses, gi
 	  break;
 	case OMP_CLAUSE_DEPEND_SOURCE:
 	case OMP_CLAUSE_DEPEND_SINK:
-	  /* FIXME:  */
-	  break;
+	  /* FALLTHRU */
 	default:
 	  gcc_unreachable ();
 	}
--- gcc/tree-pretty-print.c.jj	2015-09-03 16:35:58.000000000 +0200
+++ gcc/tree-pretty-print.c	2015-09-25 15:04:46.911844111 +0200
@@ -569,7 +569,9 @@ dump_omp_clause (pretty_printer *pp, tre
 		if (TREE_PURPOSE (t) != integer_zero_node)
 		  {
 		    tree p = TREE_PURPOSE (t);
-		    if (!wi::neg_p (p, TYPE_SIGN (TREE_TYPE (p))))
+		    if (OMP_CLAUSE_DEPEND_SINK_NEGATIVE (t))
+		      pp_minus (pp);
+		    else
 		      pp_plus (pp);
 		    dump_generic_node (pp, TREE_PURPOSE (t), spc, flags,
 				       false);
--- gcc/c/c-parser.c.jj	2015-09-10 10:45:20.000000000 +0200
+++ gcc/c/c-parser.c	2015-09-25 14:47:20.501151011 +0200
@@ -11913,14 +11913,13 @@ c_parser_omp_clause_depend_sink (c_parse
 
       c_parser_consume_token (parser);
 
-      bool neg;
+      bool neg = false;
       if (c_parser_next_token_is (parser, CPP_MINUS))
 	neg = true;
-      else if (c_parser_next_token_is (parser, CPP_PLUS))
-	neg = false;
-      else
+      else if (!c_parser_next_token_is (parser, CPP_PLUS))
 	{
 	  addend = integer_zero_node;
+	  neg = false;
 	  goto add_to_vector;
 	}
       c_parser_consume_token (parser);
@@ -11937,21 +11936,15 @@ c_parser_omp_clause_depend_sink (c_parse
 	  c_parser_error (parser, "expected integer");
 	  return list;
 	}
-      if (neg)
-	{
-	  bool overflow;
-	  wide_int offset = wi::neg (addend, &overflow);
-	  addend = wide_int_to_tree (TREE_TYPE (addend), offset);
-	  if (overflow)
-	    warning_at (c_parser_peek_token (parser)->location,
-			OPT_Woverflow,
-			"overflow in implicit constant conversion");
-	}
       c_parser_consume_token (parser);
 
     add_to_vector:
       if (t != error_mark_node)
-	vec = tree_cons (addend, t, vec);
+	{
+	  vec = tree_cons (addend, t, vec);
+	  if (neg)
+	    OMP_CLAUSE_DEPEND_SINK_NEGATIVE (vec) = 1;
+	}
 
       if (c_parser_next_token_is_not (parser, CPP_COMMA))
 	break;
@@ -13645,6 +13638,7 @@ c_parser_omp_for_loop (location_t loc, c
   tree decl, cond, incr, save_break, save_cont, body, init, stmt, cl;
   tree declv, condv, incrv, initv, ret = NULL_TREE;
   tree pre_body = NULL_TREE, this_pre_body;
+  tree ordered_cl = NULL_TREE;
   bool fail = false, open_brace_parsed = false;
   int i, collapse = 1, ordered = 0, count, nbraces = 0;
   location_t for_loc;
@@ -13655,10 +13649,22 @@ c_parser_omp_for_loop (location_t loc, c
       collapse = tree_to_shwi (OMP_CLAUSE_COLLAPSE_EXPR (cl));
     else if (OMP_CLAUSE_CODE (cl) == OMP_CLAUSE_ORDERED
 	     && OMP_CLAUSE_ORDERED_EXPR (cl))
-      ordered = tree_to_shwi (OMP_CLAUSE_ORDERED_EXPR (cl));
+      {
+	ordered_cl = cl;
+	ordered = tree_to_shwi (OMP_CLAUSE_ORDERED_EXPR (cl));
+      }
+
+  if (ordered && ordered < collapse)
+    {
+      error_at (OMP_CLAUSE_LOCATION (ordered_cl),
+		"%<ordered%> clause parameter is less than %<collapse%>");
+      OMP_CLAUSE_ORDERED_EXPR (ordered_cl)
+	= build_int_cst (NULL_TREE, collapse);
+      ordered = collapse;
+    }
 
   gcc_assert (collapse >= 1 && ordered >= 0);
-  count = collapse + (ordered > 0 ? ordered - 1 : 0);
+  count = ordered ? ordered : collapse;
 
   declv = make_tree_vec (count);
   initv = make_tree_vec (count);
--- gcc/cp/parser.c.jj	2015-09-10 12:03:29.000000000 +0200
+++ gcc/cp/parser.c	2015-09-25 14:47:29.098025038 +0200
@@ -30464,12 +30464,10 @@ cp_parser_omp_clause_depend_sink (cp_par
 					 id_loc);
 	}
 
-      bool neg;
+      bool neg = false;
       if (cp_lexer_next_token_is (parser->lexer, CPP_MINUS))
 	neg = true;
-      else if (cp_lexer_next_token_is (parser->lexer, CPP_PLUS))
-	neg = false;
-      else
+      else if (!cp_lexer_next_token_is (parser->lexer, CPP_PLUS))
 	{
 	  addend = integer_zero_node;
 	  goto add_to_vector;
@@ -30488,21 +30486,15 @@ cp_parser_omp_clause_depend_sink (cp_par
 	  cp_parser_error (parser, "expected integer");
 	  return list;
 	}
-      if (neg)
-	{
-	  bool overflow;
-	  wide_int offset = wi::neg (addend, &overflow);
-	  addend = wide_int_to_tree (TREE_TYPE (addend), offset);
-	  if (overflow)
-	    warning_at (cp_lexer_peek_token (parser->lexer)->location,
-			OPT_Woverflow,
-			"overflow in implicit constant conversion");
-	}
       cp_lexer_consume_token (parser->lexer);
 
     add_to_vector:
       if (t != error_mark_node)
-	vec = tree_cons (addend, t, vec);
+	{
+	  vec = tree_cons (addend, t, vec);
+	  if (neg)
+	    OMP_CLAUSE_DEPEND_SINK_NEGATIVE (vec) = 1;
+	}
 
       if (cp_lexer_next_token_is_not (parser->lexer, CPP_COMMA))
 	break;
@@ -32212,7 +32204,7 @@ cp_parser_omp_for_loop (cp_parser *parse
 {
   tree init, cond, incr, body, decl, pre_body = NULL_TREE, ret;
   tree real_decl, initv, condv, incrv, declv;
-  tree this_pre_body, cl;
+  tree this_pre_body, cl, ordered_cl = NULL_TREE;
   location_t loc_first;
   bool collapse_err = false;
   int i, collapse = 1, ordered = 0, count, nbraces = 0;
@@ -32223,10 +32215,22 @@ cp_parser_omp_for_loop (cp_parser *parse
       collapse = tree_to_shwi (OMP_CLAUSE_COLLAPSE_EXPR (cl));
     else if (OMP_CLAUSE_CODE (cl) == OMP_CLAUSE_ORDERED
 	     && OMP_CLAUSE_ORDERED_EXPR (cl))
-      ordered = tree_to_shwi (OMP_CLAUSE_ORDERED_EXPR (cl));
+      {
+	ordered_cl = cl;
+	ordered = tree_to_shwi (OMP_CLAUSE_ORDERED_EXPR (cl));
+      }
+
+  if (ordered && ordered < collapse)
+    {
+      error_at (OMP_CLAUSE_LOCATION (ordered_cl),
+		"%<ordered%> clause parameter is less than %<collapse%>");
+      OMP_CLAUSE_ORDERED_EXPR (ordered_cl)
+	= build_int_cst (NULL_TREE, collapse);
+      ordered = collapse;
+    }
 
   gcc_assert (collapse >= 1 && ordered >= 0);
-  count = collapse + (ordered > 0 ? ordered - 1 : 0);
+  count = ordered ? ordered : collapse;
 
   declv = make_tree_vec (count);
   initv = make_tree_vec (count);
--- gcc/cp/pt.c.jj	2015-09-10 10:45:41.000000000 +0200
+++ gcc/cp/pt.c	2015-09-25 14:53:22.986839372 +0200
@@ -14086,7 +14086,10 @@ tsubst_omp_clause_decl (tree decl, tree
 	  && TREE_VALUE (decl) == length
 	  && TREE_CHAIN (decl) == chain)
 	return decl;
-      return tree_cons (low_bound, length, chain);
+      tree ret = tree_cons (low_bound, length, chain);
+      OMP_CLAUSE_DEPEND_SINK_NEGATIVE (ret)
+	= OMP_CLAUSE_DEPEND_SINK_NEGATIVE (decl);
+      return ret;
     }
   tree ret = tsubst_expr (decl, args, complain, in_decl,
 			  /*integral_constant_expression_p=*/false);
--- gcc/testsuite/c-c++-common/gomp/sink-1.c.jj	2015-07-15 13:00:32.000000000 +0200
+++ gcc/testsuite/c-c++-common/gomp/sink-1.c	2015-09-25 16:47:40.294063449 +0200
@@ -68,7 +68,7 @@ void
 foo (int n, int m, int o)
 {
   int i, j, k;
-  #pragma omp for collapse(2) ordered(2)
+  #pragma omp for collapse(2) ordered(3)
   for (i = 0; i < m; i++)
     {
       for (j = 0; j < n; j++)
--- gcc/testsuite/gcc.dg/gomp/sink-fold-2.c.jj	2015-09-24 19:37:06.000000000 +0200
+++ gcc/testsuite/gcc.dg/gomp/sink-fold-2.c	2015-09-25 18:14:38.626071155 +0200
@@ -11,8 +11,8 @@ funk ()
   for (i=0; i < N; i += 3)
     for (j=0; j < N; ++j)
     {
-#pragma omp ordered depend(sink:i-8,j-1) /* { dg-warning "ignoring sink clause with offset that is not a multiple" "" { xfail *-*-* } } */
-#pragma omp ordered depend(sink:i+3,j-1) /* { dg-error "first offset must be in opposite direction" "" { xfail *-*-* } } */
+#pragma omp ordered depend(sink:i-8,j-1) /* { dg-warning "refers to iteration never in the iteration space" } */
+#pragma omp ordered depend(sink:i+3,j-1) /* { dg-warning "waiting for lexically later iteration" } */
         bar();
 #pragma omp ordered depend(source)
     }
--- libgomp/testsuite/libgomp.c/doacross-1.c.jj	2015-09-24 20:20:32.000000000 +0200
+++ libgomp/testsuite/libgomp.c/doacross-1.c	2015-09-25 16:54:47.118834681 +0200
@@ -79,7 +79,7 @@ main ()
 #define D(n) C(n##0) C(n##1) C(n##2) C(n##3)
     D(m)
 #undef A
-    #pragma omp for collapse (2) ordered(60) schedule(dynamic, 15)
+    #pragma omp for collapse (2) ordered(61) schedule(dynamic, 15)
     for (i = 0; i < N / 32; i++)
       for (j = 7; j > 1; j--)
 	for (k = 6; k >= 0; k -= 2)
@@ -119,7 +119,7 @@ main ()
 	      c[i][j][k] = 3;
 	    }
 
-    #pragma omp for collapse(2) ordered(3) lastprivate (i, j, k)
+    #pragma omp for collapse(2) ordered(4) lastprivate (i, j, k)
     for (i = 0; i < d + 1; i++)
       for (j = d + 1; j >= 0; j--)
 	for (k = 0; k < d; k++)
@@ -136,7 +136,7 @@ main ()
 	abort ();
       i = 8; j = 9; k = 10;
     }
-    #pragma omp for collapse(2) ordered(3) lastprivate (i, j, k, m)
+    #pragma omp for collapse(2) ordered(4) lastprivate (i, j, k, m)
     for (i = 0; i < d + 1; i++)
       for (j = d + 1; j >= 0; j--)
 	for (k = 0; k < d + 2; k++)
@@ -150,7 +150,7 @@ main ()
     #pragma omp single
     if (i != 1 || j != -1 || k != 2 || m != 0)
       abort ();
-    #pragma omp for collapse(2) ordered(3) nowait
+    #pragma omp for collapse(2) ordered(4) nowait
     for (i = 0; i < d + 1; i++)
       for (j = d; j > 0; j--)
 	for (k = 0; k < d + 2; k++)

	Jakub


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