From ef07b918a7ad4f64e0e1e3db21d861f2e79de92a Mon Sep 17 00:00:00 2001 From: Jakub Jelinek Date: Thu, 12 Aug 2021 09:18:23 +0200 Subject: [PATCH] openmp: Diagnose another case of mixing parameter and attribute syntax This patch diagnoses cases like: #pragma omp parallel [[omp::directive (declare simd)]] int foo (); or #pragma omp taskgroup int bar [[omp::directive (declare simd)]] (int); where the pragma is on the same declaration statement as the declare simd attribute. 2021-08-12 Jakub Jelinek * parser.c (cp_parser_lambda_body): Add temp overrides for parser->{omp_declare_simd,oacc_routine,omp_attrs_forbidden_p}. (cp_parser_statement): Restore parser->omp_attrs_forbidden_p for cp_parser_declaration_statement. (cp_parser_default_argument): Add temp override for parser->omp_attrs_forbidden_p. (cp_parser_late_parsing_omp_declare_simd): Diagnose declare simd or declare variant in attribute syntax on a declaration immediately following an OpenMP construct in pragma syntax. * g++.dg/gomp/attrs-11.C: Add new tests. --- gcc/cp/parser.c | 15 +++++++++++++++ gcc/testsuite/g++.dg/gomp/attrs-11.C | 12 ++++++++++++ 2 files changed, 27 insertions(+) diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index ec885d7..fbb8130 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -11628,6 +11628,9 @@ cp_parser_lambda_body (cp_parser* parser, tree lambda_expr) middle of an expression. */ ++function_depth; + auto odsd = make_temp_override (parser->omp_declare_simd, NULL); + auto ord = make_temp_override (parser->oacc_routine, NULL); + auto oafp = make_temp_override (parser->omp_attrs_forbidden_p, false); vec omp_privatization_save; save_omp_privatization_clauses (omp_privatization_save); /* Clear this in case we're in the middle of a default argument. */ @@ -12271,9 +12274,11 @@ cp_parser_statement (cp_parser* parser, tree in_statement_expr, so let's un-parse them. */ saved_tokens.rollback(); + parser->omp_attrs_forbidden_p = omp_attrs_forbidden_p; cp_parser_parse_tentatively (parser); /* Try to parse the declaration-statement. */ cp_parser_declaration_statement (parser); + parser->omp_attrs_forbidden_p = false; /* If that worked, we're done. */ if (cp_parser_parse_definitely (parser)) return; @@ -24768,6 +24773,8 @@ cp_parser_default_argument (cp_parser *parser, bool template_parm_p) parser->greater_than_is_operator_p = !template_parm_p; auto odsd = make_temp_override (parser->omp_declare_simd, NULL); auto ord = make_temp_override (parser->oacc_routine, NULL); + auto oafp = make_temp_override (parser->omp_attrs_forbidden_p, false); + /* Local variable names (and the `this' keyword) may not appear in a default argument. */ saved_local_variables_forbidden_p = parser->local_variables_forbidden_p; @@ -44503,6 +44510,14 @@ cp_parser_late_parsing_omp_declare_simd (cp_parser *parser, tree attrs) continue; } + if (parser->omp_attrs_forbidden_p) + { + error_at (first->location, + "mixing OpenMP directives with attribute and " + "pragma syntax on the same statement"); + parser->omp_attrs_forbidden_p = false; + } + if (!flag_openmp && strcmp (directive[1], "simd") != 0) continue; if (lexer == NULL) diff --git a/gcc/testsuite/g++.dg/gomp/attrs-11.C b/gcc/testsuite/g++.dg/gomp/attrs-11.C index 009bcb2..44e025e 100644 --- a/gcc/testsuite/g++.dg/gomp/attrs-11.C +++ b/gcc/testsuite/g++.dg/gomp/attrs-11.C @@ -72,3 +72,15 @@ int f28 [[omp::directive (declare simd), omp::directive (foobar)]] (int); // { d int f29 [[omp::directive (foobar), omp::directive (declare simd)]] (int); // { dg-error "unknown OpenMP directive name" } int f30 [[omp::directive (threadprivate (t7)), omp::directive (declare simd)]] (int); // { dg-error "OpenMP directive other than 'declare simd' or 'declare variant' appertains to a declaration" } int f31 [[omp::directive (declare simd), omp::directive (threadprivate (t8))]] (int); // { dg-error "OpenMP directive other than 'declare simd' or 'declare variant' appertains to a declaration" } + +void +baz () +{ + #pragma omp parallel + [[omp::directive (declare simd)]] extern int f32 (int); // { dg-error "mixing OpenMP directives with attribute and pragma syntax on the same statement" } + #pragma omp parallel + extern int f33 [[omp::directive (declare simd)]] (int); // { dg-error "mixing OpenMP directives with attribute and pragma syntax on the same statement" } + [[omp::directive (parallel)]] + #pragma omp declare simd // { dg-error "mixing OpenMP directives with attribute and pragma syntax on the same statement" } + extern int f34 (int); +} -- 2.7.4