Here is a follow-up patch to the C++ front end that handles ambiguous syntaxes implying colons in array sections with strides, including the scope and splice notations.
--
PA
From c628cdfbcea159549d0349bf07abb49fae458fd2 Mon Sep 17 00:00:00 2001
From: Paul-Antoine Arras <[email protected]>
Date: Thu, 6 Aug 2026 20:03:30 +0200
Subject: [PATCH] C++: Disambiguate colon syntaxes in array sections
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

The general syntax for array sections is: '[index:length:stride]'; any of the
three components may be omitted. Runs of adjacent colons in this syntax (e.g.
'[::', '[:::', '[::::', trailing '::]') can ambiguously refer to the splice
([:/:]) and scope (::) notations, as well as component separators of the array
section.

While awaiting clarification from the OpenMP committe, this patch adopts the
following stance: "In an intra-clause-specification, if a sequence of two or
more colons appears without separating whitespace, they are treated as follows:
the trailing :: is treated as nested-name-specifier or being part of a
nested-name-specifier – the other colons, if any, as separators according to the
OpenMP syntax."

gcc/cp/ChangeLog:

	* parser.cc (cp_parser_new): Rename omp_array_section_p to
	omp_array_section_kind.
	(cp_parser_statement_expr): Likewise.
	(cp_parser_postfix_expression): Likewise.
	(cp_parser_postfix_open_square_expression): Support scope (::) and
	splice ([:/:]) syntaxes in combination with strides in array sections.
	(cp_parser_parenthesized_expression_list): Rename
	omp_array_section_p to omp_array_section_kind.
	(cp_parser_cast_expression): Likewise.
	(cp_parser_lambda_expression): Likewise.
	(cp_parser_braced_list): Likewise.
	(cp_parser_skip_up_to_closing_square_bracket): Likewise.
	(cp_parser_omp_var_list_no_open): Pass
	OMP_ARRAY_SECTION_STRIDED for 'to'/'from' clauses and
	OMP_ARRAY_SECTION_UNSTRIDED for 'map' clauses, instead of a
	single boolean.
	* parser.h (omp_array_section_p): Replace bool with...
	(omp_array_section_kind): ...this unsigned char.
	(OMP_ARRAY_SECTION_NONE, OMP_ARRAY_SECTION_UNSTRIDED)
	(OMP_ARRAY_SECTION_STRIDED): New macros.

gcc/testsuite/ChangeLog:

	* g++.dg/gomp/array-section-7.C: New test.
	* g++.dg/gomp/array-section-8.C: New test.
---
 gcc/cp/parser.cc                            | 116 +++++++++++++-------
 gcc/cp/parser.h                             |   6 +-
 gcc/testsuite/g++.dg/gomp/array-section-7.C |  36 ++++++
 gcc/testsuite/g++.dg/gomp/array-section-8.C |  57 ++++++++++
 4 files changed, 173 insertions(+), 42 deletions(-)
 create mode 100644 gcc/testsuite/g++.dg/gomp/array-section-7.C
 create mode 100644 gcc/testsuite/g++.dg/gomp/array-section-8.C

diff --git a/gcc/cp/parser.cc b/gcc/cp/parser.cc
index 2d5b3c0ed3c..ab672aed649 100644
--- a/gcc/cp/parser.cc
+++ b/gcc/cp/parser.cc
@@ -4777,7 +4777,7 @@ cp_parser_new (cp_lexer *lexer)
   parser->oacc_routine = NULL;
 
   /* Disallow OpenMP array sections in expressions.  */
-  parser->omp_array_section_p = false;
+  parser->omp_array_section_kind = false;
 
   /* Disallow OpenMP array-shaping operator in expressions.  */
   parser->omp_array_shaping_op_p = false;
@@ -5815,7 +5815,7 @@ static cp_expr
 cp_parser_statement_expr (cp_parser *parser)
 {
   cp_token_position start = cp_parser_start_tentative_firewall (parser);
-  auto oas = make_temp_override (parser->omp_array_section_p, false);
+  auto oas = make_temp_override (parser->omp_array_section_kind, false);
   auto aso = make_temp_override (parser->omp_array_shaping_op_p, false);
 
   /* Consume the '('.  */
@@ -8926,9 +8926,9 @@ cp_parser_postfix_expression (cp_parser *parser, bool address_p, bool cast_p,
       switch (token->type)
 	{
 	case CPP_OPEN_SPLICE:
-	  if (!parser->omp_array_section_p)
+	  if (!parser->omp_array_section_kind)
 	    goto default_case;
-	  /* Parse '[: length]' array section.  */
+	  /* Parse '[: length :]' array section.  */
 	  postfix_expression
 	    = cp_parser_postfix_open_square_expression (parser,
 							postfix_expression,
@@ -9289,9 +9289,10 @@ cp_parser_parenthesized_expression_list_elt (cp_parser *parser, bool cast_p,
    changes how we deal with integer constant expressions.
 
    With parser->omp_array_section_p, it also handles OpenMP
-   array sections of the type [ index : length ] where both
-   index and length are optional. Note that an absent index
-   might be lexed as CPP_OPEN_SPLICE ('[:') since C++26.  */
+   array sections of the type [ index : length : stride ] where index,
+   length and stride are optional. Note that an absent index
+   might be lexed as CPP_OPEN_SPLICE ('[:') and an absent stride
+   might be lexed as CPP_CLOSE_SPLICE (':]') since C++26.  */
 
 static tree
 cp_parser_postfix_open_square_expression (cp_parser *parser,
@@ -9310,11 +9311,17 @@ cp_parser_postfix_open_square_expression (cp_parser *parser,
   /* Consume the `[' token - or with open_splice the '[:' token.  */
   cp_lexer_consume_token (parser->lexer);
 
+  bool double_scope = cp_lexer_next_token_is (parser->lexer, CPP_SCOPE)
+		      && cp_lexer_nth_token_is (parser->lexer, 2, CPP_SCOPE);
+  bool double_colon_only
+    = cp_lexer_next_token_is (parser->lexer, CPP_SCOPE)
+      && cp_lexer_nth_token_is (parser->lexer, 2, CPP_CLOSE_SQUARE);
+
   saved_greater_than_is_operator_p = parser->greater_than_is_operator_p;
   parser->greater_than_is_operator_p = true;
 
   saved_colon_corrects_to_scope_p = parser->colon_corrects_to_scope_p;
-  if (parser->omp_array_section_p)
+  if (parser->omp_array_section_kind)
     parser->colon_corrects_to_scope_p = false;
 
   if (open_splice)
@@ -9330,7 +9337,12 @@ cp_parser_postfix_open_square_expression (cp_parser *parser,
      constant expressions here.  */
   if (for_offsetof)
     index = cp_parser_constant_expression (parser);
-  else if (!parser->omp_array_section_p
+  else if (parser->omp_array_section_kind == OMP_ARRAY_SECTION_STRIDED
+	   && (double_scope || double_colon_only))
+    {
+      /* Handle '[::::' and '[::]' in post_colon_parsing.  */
+    }
+  else if (!parser->omp_array_section_kind
 	   || (cp_lexer_next_token_is_not (parser->lexer, CPP_COLON)
 	       && cp_lexer_next_token_is_not (parser->lexer, CPP_CLOSE_SPLICE)))
     {
@@ -9393,6 +9405,14 @@ cp_parser_postfix_open_square_expression (cp_parser *parser,
 	  maybe_warn_cpp0x (CPP0X_INITIALIZER_LISTS);
 	  index = cp_parser_braced_list (parser);
 	}
+      else if (cp_lexer_next_token_is (parser->lexer, CPP_SCOPE)
+	       && cp_lexer_nth_token_is (parser->lexer, 2, CPP_COLON))
+	{
+	  /* The lexer greedily tokenizes '[:::' as '[ :: :'.
+	     It should be '[ : ::'. Let's swap the last two.  */
+	  cp_lexer_peek_token (parser->lexer)->type = CPP_COLON;
+	  cp_lexer_peek_nth_token (parser->lexer, 2)->type = CPP_SCOPE;
+	}
       else
 	index = cp_parser_expression (parser, NULL, /*cast_p=*/false,
 				      /*decltype_p=*/false,
@@ -9402,8 +9422,7 @@ cp_parser_postfix_open_square_expression (cp_parser *parser,
 post_colon_parsing:
   parser->greater_than_is_operator_p = saved_greater_than_is_operator_p;
 
-  if (cxx_dialect >= cxx23
-      && parser->omp_array_section_p
+  if (cxx_dialect >= cxx23 && parser->omp_array_section_kind
       && expression_list.get () != NULL
       && vec_safe_length (expression_list) > 1)
     {
@@ -9412,15 +9431,16 @@ post_colon_parsing:
       index = error_mark_node;
     }
 
-  if (parser->omp_array_section_p
-      && (open_splice
-	  || cp_lexer_next_token_is (parser->lexer, CPP_COLON)
-	  || cp_lexer_next_token_is (parser->lexer, CPP_CLOSE_SPLICE)))
+  if (parser->omp_array_section_kind
+      && (open_splice || cp_lexer_next_token_is (parser->lexer, CPP_COLON)
+	  || cp_lexer_next_token_is (parser->lexer, CPP_CLOSE_SPLICE)
+	  || (parser->omp_array_section_kind == OMP_ARRAY_SECTION_STRIDED
+	      && (double_scope || double_colon_only))))
     {
       tree length = NULL_TREE, stride = NULL_TREE;
       bool close_splice = cp_lexer_next_token_is (parser->lexer,
 						  CPP_CLOSE_SPLICE);
-      if (!open_splice)
+      if (!open_splice && !double_scope)
 	cp_lexer_consume_token (parser->lexer);
       if (open_splice && close_splice)
 	{
@@ -9428,19 +9448,24 @@ post_colon_parsing:
 				    UNKNOWN_LOCATION);
 	  length = error_mark_node;
 	}
+      else if (open_splice && cp_lexer_next_token_is (parser->lexer, CPP_SCOPE)
+	       && cp_lexer_nth_token_is (parser->lexer, 2, CPP_COLON))
+	{
+	  /* The lexer greedily tokenizes '[::::' as '[: :: :'.
+	     It should be '[ : : ::'. Let's swap the last two.  */
+	  cp_lexer_peek_token (parser->lexer)->type = CPP_COLON;
+	  cp_lexer_peek_nth_token (parser->lexer, 2)->type = CPP_SCOPE;
+	}
       else if (cp_lexer_next_token_is_not (parser->lexer, CPP_CLOSE_SQUARE)
-	       && !close_splice)
+	       && !close_splice && !double_scope)
 	{
 	  if (cxx_dialect >= cxx23)
 	    {
-	      cp_expr expr
-		= cp_parser_parenthesized_expression_list_elt (parser,
-							       /*cast_p=*/
-							       false,
-							       /*allow_exp_p=*/
-							       true,
-							       /*non_cst_p=*/
-							       NULL);
+	      cp_expr expr = cp_parser_parenthesized_expression_list_elt (
+		parser,
+		/*cast_p=*/false,
+		/*allow_exp_p=*/true,
+		/*non_cst_p=*/NULL);
 
 	      if (expr == error_mark_node)
 		length = error_mark_node;
@@ -9450,7 +9475,7 @@ post_colon_parsing:
 	      if (cp_lexer_next_token_is (parser->lexer, CPP_COMMA))
 		{
 		  error_at (loc, "cannot use multidimensional subscript in "
-			    "OpenMP array section");
+				 "OpenMP array section");
 		  length = error_mark_node;
 		}
 	    }
@@ -9461,7 +9486,9 @@ post_colon_parsing:
 				      /*warn_comma_p=*/warn_comma_subscript);
 	}
 
-      if (cp_lexer_next_token_is (parser->lexer, CPP_COLON))
+      if (parser->omp_array_section_kind == OMP_ARRAY_SECTION_STRIDED
+	  && (cp_lexer_next_token_is (parser->lexer, CPP_COLON)
+	      || double_scope))
 	{
 	  cp_lexer_consume_token (parser->lexer);
 	  /* We could check for C++-23 multidimensional/comma-separated
@@ -9482,7 +9509,13 @@ post_colon_parsing:
 	  cp_parser_skip_to_closing_square_bracket (parser);
 	  return error_mark_node;
 	}
-      else if (!close_splice)
+      else if (parser->omp_array_section_kind == OMP_ARRAY_SECTION_STRIDED
+	       && cp_lexer_next_token_is (parser->lexer, CPP_CLOSE_SPLICE))
+	cp_lexer_consume_token (parser->lexer);
+      else if (!close_splice
+	       && (OMP_ARRAY_SECTION_UNSTRIDED
+		   || cp_lexer_next_token_is_not (parser->lexer,
+						  CPP_CLOSE_SPLICE)))
 	cp_parser_require (parser, CPP_CLOSE_SQUARE, RT_CLOSE_SQUARE);
 
       return grok_omp_array_section (input_location, postfix_expression, index,
@@ -9888,9 +9921,9 @@ cp_parser_parenthesized_expression_list (cp_parser* parser,
     = parser->greater_than_is_operator_p;
   parser->greater_than_is_operator_p = true;
 
-  saved_omp_array_section_p = parser->omp_array_section_p;
+  saved_omp_array_section_p = parser->omp_array_section_kind;
   saved_omp_array_shaping_op_p = parser->omp_array_shaping_op_p;
-  parser->omp_array_section_p = false;
+  parser->omp_array_section_kind = false;
   parser->omp_array_shaping_op_p = false;
 
   cp_expr expr (NULL_TREE);
@@ -9985,7 +10018,7 @@ cp_parser_parenthesized_expression_list (cp_parser* parser,
 	{
 	  parser->greater_than_is_operator_p
 	    = saved_greater_than_is_operator_p;
-	  parser->omp_array_section_p = saved_omp_array_section_p;
+	  parser->omp_array_section_kind = saved_omp_array_section_p;
 	  parser->omp_array_shaping_op_p = saved_omp_array_shaping_op_p;
 	  return NULL;
 	}
@@ -9993,7 +10026,7 @@ cp_parser_parenthesized_expression_list (cp_parser* parser,
 
   parser->greater_than_is_operator_p
     = saved_greater_than_is_operator_p;
-  parser->omp_array_section_p = saved_omp_array_section_p;
+  parser->omp_array_section_kind = saved_omp_array_section_p;
   parser->omp_array_shaping_op_p = saved_omp_array_shaping_op_p;
 
   return expression_list;
@@ -11542,7 +11575,7 @@ cp_parser_cast_expression (cp_parser *parser, bool address_p, bool cast_p,
       else if (parser->omp_array_shaping_op_p
 	       && cp_lexer_next_token_is (parser->lexer, CPP_OPEN_SQUARE))
 	{
-	  auto oas = make_temp_override (parser->omp_array_section_p, false);
+	  auto oas = make_temp_override (parser->omp_array_section_kind, false);
 	  auto aso = make_temp_override (parser->omp_array_shaping_op_p, false);
 
 	  while (cp_lexer_next_token_is (parser->lexer, CPP_OPEN_SQUARE))
@@ -12929,7 +12962,7 @@ cp_parser_lambda_expression (cp_parser* parser,
     cp_binding_level* implicit_template_scope = parser->implicit_template_scope;
     bool auto_is_implicit_function_template_parm_p
         = parser->auto_is_implicit_function_template_parm_p;
-    bool saved_omp_array_section_p = parser->omp_array_section_p;
+    bool saved_omp_array_section_p = parser->omp_array_section_kind;
     bool saved_omp_array_shaping_op_p = parser->omp_array_shaping_op_p;
     bool saved_in_targ = parser->in_template_argument_list_p;
     bool saved_in_declarator_p = parser->in_declarator_p;
@@ -12943,7 +12976,7 @@ cp_parser_lambda_expression (cp_parser* parser,
     parser->implicit_template_parms = 0;
     parser->implicit_template_scope = 0;
     parser->auto_is_implicit_function_template_parm_p = false;
-    parser->omp_array_section_p = false;
+    parser->omp_array_section_kind = false;
     parser->omp_array_shaping_op_p = false;
     parser->in_template_argument_list_p = false;
     parser->in_declarator_p = false;
@@ -13012,7 +13045,7 @@ cp_parser_lambda_expression (cp_parser* parser,
     parser->implicit_template_scope = implicit_template_scope;
     parser->auto_is_implicit_function_template_parm_p
 	= auto_is_implicit_function_template_parm_p;
-    parser->omp_array_section_p = saved_omp_array_section_p;
+    parser->omp_array_section_kind = saved_omp_array_section_p;
     parser->omp_array_shaping_op_p = saved_omp_array_shaping_op_p;
     parser->in_template_argument_list_p = saved_in_targ;
     parser->in_declarator_p = saved_in_declarator_p;
@@ -29194,7 +29227,7 @@ cp_parser_braced_list (cp_parser *parser, bool *non_constant_p /*=nullptr*/)
 {
   tree initializer;
   location_t start_loc = cp_lexer_peek_token (parser->lexer)->location;
-  auto oas = make_temp_override (parser->omp_array_section_p, false);
+  auto oas = make_temp_override (parser->omp_array_section_kind, false);
   auto aso = make_temp_override (parser->omp_array_shaping_op_p, false);
 
   /* Within a brace-enclosed initializer list, a `>' token is always the
@@ -29271,7 +29304,7 @@ cp_parser_skip_up_to_closing_square_bracket (cp_parser *parser)
 	  return false;
 
 	case CPP_OPEN_SPLICE:
-	  if (!parser->omp_array_section_p)
+	  if (!parser->omp_array_section_kind)
 	    break;
 	  /* FALLTHRU */
 
@@ -29280,7 +29313,7 @@ cp_parser_skip_up_to_closing_square_bracket (cp_parser *parser)
           break;
 
 	case CPP_CLOSE_SPLICE:
-	  if (!parser->omp_array_section_p)
+	  if (!parser->omp_array_section_kind)
 	    break;
 	  /* FALLTHRU */
         case CPP_CLOSE_SQUARE:
@@ -41680,7 +41713,10 @@ cp_parser_omp_var_list_no_open (cp_parser *parser, enum omp_clause_code kind,
 		   || kind == OMP_CLAUSE_TO
 		   || kind == OMP_CLAUSE_FROM))
 	{
-	  auto s = make_temp_override (parser->omp_array_section_p, true);
+	  auto s = make_temp_override (parser->omp_array_section_kind,
+				       kind == OMP_CLAUSE_MAP
+					 ? OMP_ARRAY_SECTION_UNSTRIDED
+					 : OMP_ARRAY_SECTION_STRIDED);
 	  auto o = make_temp_override (parser->omp_array_shaping_op_p,
 				       (kind == OMP_CLAUSE_TO
 					|| kind == OMP_CLAUSE_FROM));
diff --git a/gcc/cp/parser.h b/gcc/cp/parser.h
index 2f696502246..19dc0154372 100644
--- a/gcc/cp/parser.h
+++ b/gcc/cp/parser.h
@@ -425,8 +425,10 @@ struct GTY(()) cp_parser {
      appear.  */
   bool omp_attrs_forbidden_p;
 
-  /* TRUE if an OpenMP array section is allowed.  */
-  bool omp_array_section_p;
+#define OMP_ARRAY_SECTION_NONE 0
+#define OMP_ARRAY_SECTION_UNSTRIDED 1
+#define OMP_ARRAY_SECTION_STRIDED 2
+  unsigned char omp_array_section_kind;
 
   /* TRUE if an OpenMP array-shaping operator is allowed.  */
   bool omp_array_shaping_op_p;
diff --git a/gcc/testsuite/g++.dg/gomp/array-section-7.C b/gcc/testsuite/g++.dg/gomp/array-section-7.C
new file mode 100644
index 00000000000..622e100be29
--- /dev/null
+++ b/gcc/testsuite/g++.dg/gomp/array-section-7.C
@@ -0,0 +1,36 @@
+// { dg-do compile { target c++26 } }
+// { dg-additional-options "-freflection -fdump-tree-original" }
+
+// Check that the OpenMP stride array-section notation
+// '[ lower : length : stride ]' is not confused with C++26's splice specifier,
+// including when the latter is used to supply one of the section's components.
+
+constexpr int lb0 = 4;
+constexpr auto rlb = ^^lb0;
+constexpr int s0 = 2;
+constexpr auto rs = ^^s0;
+
+void f() {
+  int arr[128];
+  int lb = 4, len = 16, s = 2;
+
+  // baseline: all three components explicit, nothing splice-shaped.
+#pragma omp target update to(arr[lb:len:s])
+
+  // splice-expression supplying the lower bound.
+#pragma omp target update to(arr[[:rlb:]:len:s])
+
+  // splice-expression supplying the stride.
+#pragma omp target update to(arr[lb:len:[:rs:]])
+
+  // Stride left empty: the trailing ':' + ']' is lexed as a single
+  // CPP_CLOSE_SPLICE token.
+#pragma omp target update to(arr[lb:len:])
+#pragma omp target update to(arr[:len:])
+}
+
+// { dg-final { scan-tree-dump "map\\(to_grid:arr \\\[len: 4\\\]\\) map\\(grid_dim:SAVE_EXPR <lb> \\\[len: len\\\]\\) map\\(grid_stride:s\\)" "original" } }
+// { dg-final { scan-tree-dump "map\\(to_grid:arr \\\[len: 4\\\]\\) map\\(grid_dim:4 \\\[len: len\\\]\\) map\\(grid_stride:s\\)" "original" } }
+// { dg-final { scan-tree-dump "map\\(to_grid:arr \\\[len: 4\\\]\\) map\\(grid_dim:SAVE_EXPR <lb> \\\[len: len\\\]\\) map\\(grid_stride:2\\)" "original" } }
+// { dg-final { scan-tree-dump "to\\(arr\\\[SAVE_EXPR <lb>\\\] \\\[len: \\(sizetype\\) len \\* 4\\\]\\)" "original" } }
+// { dg-final { scan-tree-dump "to\\(arr\\\[0\\\] \\\[len: \\(sizetype\\) len \\* 4\\\]\\)" "original" } }
diff --git a/gcc/testsuite/g++.dg/gomp/array-section-8.C b/gcc/testsuite/g++.dg/gomp/array-section-8.C
new file mode 100644
index 00000000000..08f07e000de
--- /dev/null
+++ b/gcc/testsuite/g++.dg/gomp/array-section-8.C
@@ -0,0 +1,57 @@
+// { dg-do compile }
+// { dg-additional-options "-fdump-tree-original" }
+
+// Check parsing of double colon (::). In case of ambiguity between the scope
+// resolution operator and the array section syntax, spaces are required.
+
+int lb2 = 4;
+int len2 = 16;
+int s2 = 2;
+
+void g() {
+  int arr[128];
+  int lb = 4, len = 16, s = 2;
+
+#pragma omp target update to(arr[lb::s])
+// { dg-error "34: 'lb' is not a class" "" { target *-*-* } .-1 }
+// { dg-error "must contain at least one" "" { target *-*-* } .-2 }
+
+#pragma omp target update to(arr[::s])
+// { dg-error "36: '::s' has not been declared" "" { target *-*-* } .-1 }
+// { dg-error "must contain at least one" "" { target *-*-* } .-2 }
+
+#pragma omp target update to(arr[lb::])
+// { dg-error "34: 'lb' is not a class" "" { target *-*-* } .-1 }
+// { dg-error "38: expected unqualified-id before '\\\]' token" "" { target *-*-* } .-2 }
+// { dg-error "must contain at least one" "" { target *-*-* } .-3 }
+
+  // Valid: default values.
+#pragma omp target update to(arr[::])
+// { dg-final { scan-tree-dump "to\\(arr\\\[0\\\] \\\[len: 512\\\]\\)" "original" } }
+
+  // Valid: len2 is looked up in the global namespace and forms the length of the
+  // array section.
+#pragma omp target update to(arr[:::len2])
+#pragma omp target update to(arr[:::len2:])
+// { dg-final { scan-tree-dump-times "to\\(arr\\\[0\\\] \\\[len: \\(sizetype\\) len2 \\* 4\\\]\\)" 2 "original" } }
+
+  // Valid: s2 is looked up in the global namespace and forms the stride of the
+  // array section.
+#pragma omp target update to(arr[::::s2])
+// { dg-final { scan-tree-dump "map\\(to_grid:arr \\\[len: 4\\\]\\) map\\(grid_dim:0 \\\[len: 1\\\]\\) map\\(grid_stride:s2\\)" "original" } }
+
+  // Valid: lb2 is looked up in the global namespace and forms the lower bound
+  // of the array section.
+#pragma omp target update to(arr[::lb2:])
+// { dg-final { scan-tree-dump "to\\(arr\\\[SAVE_EXPR <lb2>\\\] \\\[len: \\(128 - \\(sizetype\\) SAVE_EXPR <lb2>\\) \\* 4\\\]\\)" "original" } }
+
+#pragma omp target update to(arr[::lb2::])
+// { dg-error "36: '::lb2' is not a class" "" { target *-*-* } .-1 }
+// { dg-error "41: expected unqualified-id before '\\\]' token" "" { target *-*-* } .-2 }
+// { dg-error "must contain at least one" "" { target *-*-* } .-3 }
+
+#pragma omp target update to(arr[::lb2::s2])
+// { dg-error "36: '::lb2' is not a class" "" { target *-*-* } .-1 }
+// { dg-error "must contain at least one" "" { target *-*-* } .-2 }
+
+}
-- 
2.53.0

Reply via email to