Hi! While working on error directive, I've noticed a few spots in OpenMP parsing where we consume and don't diagnose superfluous commas at the end (either of depend sink arguments or at the end of requires pragma).
Bootstrapped/regtested on x86_64-linux and i686-linux, committed to trunk. 2021-08-20 Jakub Jelinek <ja...@redhat.com> gcc/c/ * c-parser.c (c_parser_omp_clause_depend_sink): Reject spurious comma at the end of list. (c_parser_omp_requires): Likewise. gcc/cp/ * parser.c (cp_parser_omp_clause_depend_sink): Reject spurious comma at the end of list. Don't parse closing paren here... (cp_parser_omp_clause_depend): ... but here instead. gcc/testsuite/ * c-c++-common/gomp/sink-5.c: New test. * c-c++-common/gomp/requires-3.c: Add test for spurious comma at the end of pragma line. --- gcc/c/c-parser.c.jj 2021-08-19 12:53:44.692106632 +0200 +++ gcc/c/c-parser.c 2021-08-19 13:19:56.217288105 +0200 @@ -15481,7 +15481,9 @@ c_parser_omp_clause_depend_sink (c_parse OMP_CLAUSE_DEPEND_SINK_NEGATIVE (vec) = 1; } - if (c_parser_next_token_is_not (parser, CPP_COMMA)) + if (c_parser_next_token_is_not (parser, CPP_COMMA) + || c_parser_peek_2nd_token (parser)->type != CPP_NAME + || c_parser_peek_2nd_token (parser)->id_kind != C_ID_ID) break; c_parser_consume_token (parser); @@ -21663,7 +21665,9 @@ c_parser_omp_requires (c_parser *parser) location_t loc = c_parser_peek_token (parser)->location; while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL)) { - if (!first && c_parser_next_token_is (parser, CPP_COMMA)) + if (!first + && c_parser_next_token_is (parser, CPP_COMMA) + && c_parser_peek_2nd_token (parser)->type == CPP_NAME) c_parser_consume_token (parser); first = false; --- gcc/cp/parser.c.jj 2021-08-19 11:42:27.335422818 +0200 +++ gcc/cp/parser.c 2021-08-19 13:40:26.387178416 +0200 @@ -38465,13 +38465,14 @@ cp_parser_omp_clause_depend_sink (cp_par OMP_CLAUSE_DEPEND_SINK_NEGATIVE (vec) = 1; } - if (cp_lexer_next_token_is_not (parser->lexer, CPP_COMMA)) + if (cp_lexer_next_token_is_not (parser->lexer, CPP_COMMA) + || !cp_lexer_nth_token_is (parser->lexer, 2, CPP_NAME)) break; cp_lexer_consume_token (parser->lexer); } - if (cp_parser_require (parser, CPP_CLOSE_PAREN, RT_CLOSE_PAREN) && vec) + if (vec) { tree u = build_omp_clause (clause_loc, OMP_CLAUSE_DEPEND); OMP_CLAUSE_DEPEND_KIND (u) = OMP_CLAUSE_DEPEND_SINK; @@ -38791,7 +38792,13 @@ cp_parser_omp_clause_depend (cp_parser * goto resync_fail; if (kind == OMP_CLAUSE_DEPEND_SINK) - nlist = cp_parser_omp_clause_depend_sink (parser, loc, list); + { + nlist = cp_parser_omp_clause_depend_sink (parser, loc, list); + if (!parens.require_close (parser)) + cp_parser_skip_to_closing_parenthesis (parser, /*recovering=*/true, + /*or_comma=*/false, + /*consume_paren=*/true); + } else { nlist = cp_parser_omp_var_list_no_open (parser, OMP_CLAUSE_DEPEND, --- gcc/testsuite/c-c++-common/gomp/sink-5.c.jj 2021-08-19 13:04:38.934031130 +0200 +++ gcc/testsuite/c-c++-common/gomp/sink-5.c 2021-08-19 13:26:43.522623672 +0200 @@ -0,0 +1,16 @@ +/* { dg-do compile } */ + +void bar (int); + +void +foo () +{ + int i; +#pragma omp parallel for ordered(1) + for (i = 0; i < 100; ++i) + { +#pragma omp ordered depend(sink:i-1,) /* { dg-error "expected '\\\)' before ',' token" } */ + bar (i); +#pragma omp ordered depend(source) + } +} --- gcc/testsuite/c-c++-common/gomp/requires-3.c.jj 2021-08-19 11:42:27.393422011 +0200 +++ gcc/testsuite/c-c++-common/gomp/requires-3.c 2021-08-19 13:23:53.217992113 +0200 @@ -3,3 +3,4 @@ #pragma omp requires atomic_default_mem_order(foobar) /* { dg-error "expected 'seq_cst', 'relaxed' or 'acq_rel'" } */ #pragma omp requires atomic_default_mem_order ( /* { dg-error "expected 'seq_cst', 'relaxed' or 'acq_rel'" } */ /* { dg-error "expected '\\\)' before end of line" "" { target *-*-* } .-1 } */ +#pragma omp requires atomic_default_mem_order(seq_cst), /* { dg-error "expected end of line before ',' token" } */ Jakub