Hi! The following testcase endlessly diagnoses a syntax error. The problem is that the various C++ parser routines to skip tokens until something happily skip over CPP_PRAGMA that starts a pragma line, but always stop at CPP_PRAGMA_EOL, but the caller expect them to stop at something different.
The fix is similar to what the C FE already does, treat CPP_PRAGMA_EOL as CPP_EOF only if in_pragma flag is set. Otherwise we didn't really parse CPP_PRAGMA normally and should skip everything until we find whatever we are looking for. Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk? 2018-11-30 Jakub Jelinek <ja...@redhat.com> PR c++/88258 * parser.c (cp_parser_skip_to_closing_parenthesis_1, cp_parser_skip_to_end_of_statement, cp_parser_skip_to_end_of_block_or_statement, cp_parser_skip_to_closing_brace, cp_parser_skip_to_closing_square_bracket, cp_parser_skip_balanced_tokens): Don't treat CPP_PRAGMA_EOL specially if in_pragma is false. * g++.dg/gomp/pr88258.C: New test. --- gcc/cp/parser.c.jj 2018-11-29 08:41:30.804788606 +0100 +++ gcc/cp/parser.c 2018-11-30 14:18:51.928839749 +0100 @@ -3556,8 +3556,11 @@ cp_parser_skip_to_closing_parenthesis_1 switch (token->type) { - case CPP_EOF: case CPP_PRAGMA_EOL: + if (!parser->lexer->in_pragma) + break; + /* FALLTHRU */ + case CPP_EOF: /* If we've run out of tokens, then there is no closing `)'. */ return 0; @@ -3652,8 +3655,11 @@ cp_parser_skip_to_end_of_statement (cp_p switch (token->type) { - case CPP_EOF: case CPP_PRAGMA_EOL: + if (!parser->lexer->in_pragma) + break; + /* FALLTHRU */ + case CPP_EOF: /* If we've run out of tokens, stop. */ return; @@ -3742,8 +3748,11 @@ cp_parser_skip_to_end_of_block_or_statem switch (token->type) { - case CPP_EOF: case CPP_PRAGMA_EOL: + if (!parser->lexer->in_pragma) + break; + /* FALLTHRU */ + case CPP_EOF: /* If we've run out of tokens, stop. */ return; @@ -3792,8 +3801,11 @@ cp_parser_skip_to_closing_brace (cp_pars switch (token->type) { - case CPP_EOF: case CPP_PRAGMA_EOL: + if (!parser->lexer->in_pragma) + break; + /* FALLTHRU */ + case CPP_EOF: /* If we've run out of tokens, stop. */ return false; @@ -22498,8 +22510,11 @@ cp_parser_skip_to_closing_square_bracket switch (token->type) { - case CPP_EOF: case CPP_PRAGMA_EOL: + if (!parser->lexer->in_pragma) + break; + /* FALLTHRU */ + case CPP_EOF: /* If we've run out of tokens, then there is no closing `]'. */ return false; @@ -26008,8 +26023,11 @@ cp_parser_skip_balanced_tokens (cp_parse do switch (cp_lexer_peek_nth_token (parser->lexer, n++)->type) { - case CPP_EOF: case CPP_PRAGMA_EOL: + if (!parser->lexer->in_pragma) + break; + /* FALLTHRU */ + case CPP_EOF: /* Ran out of tokens. */ return orig_n; case CPP_OPEN_PAREN: --- gcc/testsuite/g++.dg/gomp/pr88258.C.jj 2018-11-30 14:26:00.806805739 +0100 +++ gcc/testsuite/g++.dg/gomp/pr88258.C 2018-11-30 14:25:33.614251741 +0100 @@ -0,0 +1,11 @@ +// PR c++/88258 +// { dg-do compile } +// { dg-options "-fopenmp" } + +void +foo (bar int p) // { dg-error "variable or field|was not declared in this scope" } +{ + int i, x; + #pragma omp atomic write + x = 6; +} Jakub