Revert "[OPENMP] Fix for parsing OpenMP directives with extra braces, brackets and parens"

These parser changes were redundant. The same or better recovery can be
achieved with a one-line fix to SkipUntil() due to land in the next commit.

This reverts commit r197553.

llvm-svn: 197597
This commit is contained in:
Alp Toker 2013-12-18 19:10:49 +00:00
parent 67e6d506d8
commit d751fa7868
6 changed files with 41 additions and 86 deletions

View File

@ -684,13 +684,9 @@ private:
/// If the input is malformed, this emits the specified diagnostic. Next, if
/// SkipToTok is specified, it calls SkipUntil(SkipToTok). Finally, true is
/// returned.
/// If NoCount is true, it ignores parens/brackets/braces as regular tokens
/// and does not count them. By default it recursively skips properly-nested
/// parens/brackets/braces.
bool ExpectAndConsume(tok::TokenKind ExpectedTok, unsigned Diag,
const char *DiagMsg = "",
tok::TokenKind SkipToTok = tok::unknown,
bool NoCount = false);
tok::TokenKind SkipToTok = tok::unknown);
/// \brief The parser expects a semicolon and, if present, will consume it.
///
@ -793,9 +789,7 @@ public:
StopAtSemi = 1 << 0, ///< Stop skipping at semicolon
/// \brief Stop skipping at specified token, but don't skip the token itself
StopBeforeMatch = 1 << 1,
StopAtCodeCompletion = 1 << 2, ///< Stop at code completion
NoBracketsCount = 1 << 3 /// \brief Don't count braces/brackets/parens
/// to skip balanced pairs
StopAtCodeCompletion = 1 << 2 ///< Stop at code completion
};
friend LLVM_CONSTEXPR SkipUntilFlags operator|(SkipUntilFlags L,

View File

@ -48,7 +48,7 @@ Parser::DeclGroupPtrTy Parser::ParseOpenMPDeclarativeDirective() {
if (Tok.isNot(tok::annot_pragma_openmp_end)) {
Diag(Tok, diag::warn_omp_extra_tokens_at_eol)
<< getOpenMPDirectiveName(OMPD_threadprivate);
SkipUntil(tok::annot_pragma_openmp_end, StopBeforeMatch | NoBracketsCount);
SkipUntil(tok::annot_pragma_openmp_end, StopBeforeMatch);
}
// Skip the last annot_pragma_openmp_end.
ConsumeToken();
@ -66,7 +66,7 @@ Parser::DeclGroupPtrTy Parser::ParseOpenMPDeclarativeDirective() {
<< getOpenMPDirectiveName(DKind);
break;
}
SkipUntil(tok::annot_pragma_openmp_end, NoBracketsCount);
SkipUntil(tok::annot_pragma_openmp_end);
return DeclGroupPtrTy();
}
@ -105,14 +105,14 @@ StmtResult Parser::ParseOpenMPDeclarativeOrExecutableDirective() {
if (Tok.isNot(tok::annot_pragma_openmp_end)) {
Diag(Tok, diag::warn_omp_extra_tokens_at_eol)
<< getOpenMPDirectiveName(OMPD_threadprivate);
SkipUntil(tok::annot_pragma_openmp_end, StopBeforeMatch | NoBracketsCount);
SkipUntil(tok::annot_pragma_openmp_end, StopBeforeMatch);
}
DeclGroupPtrTy Res =
Actions.ActOnOpenMPThreadprivateDirective(Loc,
Identifiers);
Directive = Actions.ActOnDeclStmt(Res, Loc, Tok.getLocation());
}
SkipUntil(tok::annot_pragma_openmp_end, NoBracketsCount);
SkipUntil(tok::annot_pragma_openmp_end);
break;
case OMPD_parallel: {
ConsumeToken();
@ -171,13 +171,13 @@ StmtResult Parser::ParseOpenMPDeclarativeOrExecutableDirective() {
break;
case OMPD_unknown:
Diag(Tok, diag::err_omp_unknown_directive);
SkipUntil(tok::annot_pragma_openmp_end, NoBracketsCount);
SkipUntil(tok::annot_pragma_openmp_end);
break;
case OMPD_task:
case NUM_OPENMP_DIRECTIVES:
Diag(Tok, diag::err_omp_unexpected_directive)
<< getOpenMPDirectiveName(DKind);
SkipUntil(tok::annot_pragma_openmp_end, NoBracketsCount);
SkipUntil(tok::annot_pragma_openmp_end);
break;
}
return Directive;
@ -194,8 +194,7 @@ bool Parser::ParseOpenMPSimpleVarList(OpenMPDirectiveKind Kind,
bool AllowScopeSpecifier) {
VarList.clear();
// Parse '('.
BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end,
true);
BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end);
if (T.expectAndConsume(diag::err_expected_lparen_after,
getOpenMPDirectiveName(Kind)))
return true;
@ -215,17 +214,17 @@ bool Parser::ParseOpenMPSimpleVarList(OpenMPDirectiveKind Kind,
ParseOptionalCXXScopeSpecifier(SS, ParsedType(), false)) {
IsCorrect = false;
SkipUntil(tok::comma, tok::r_paren, tok::annot_pragma_openmp_end,
StopBeforeMatch | NoBracketsCount);
StopBeforeMatch);
} else if (ParseUnqualifiedId(SS, false, false, false, ParsedType(),
TemplateKWLoc, Name)) {
IsCorrect = false;
SkipUntil(tok::comma, tok::r_paren, tok::annot_pragma_openmp_end,
StopBeforeMatch | NoBracketsCount);
StopBeforeMatch);
} else if (Tok.isNot(tok::comma) && Tok.isNot(tok::r_paren) &&
Tok.isNot(tok::annot_pragma_openmp_end)) {
IsCorrect = false;
SkipUntil(tok::comma, tok::r_paren, tok::annot_pragma_openmp_end,
StopBeforeMatch | NoBracketsCount);
StopBeforeMatch);
Diag(PrevTok.getLocation(), diag::err_expected_ident)
<< SourceRange(PrevTok.getLocation(), PrevTokLocation);
} else {
@ -288,13 +287,13 @@ OMPClause *Parser::ParseOpenMPClause(OpenMPDirectiveKind DKind,
case OMPC_unknown:
Diag(Tok, diag::warn_omp_extra_tokens_at_eol)
<< getOpenMPDirectiveName(DKind);
SkipUntil(tok::annot_pragma_openmp_end, StopBeforeMatch | NoBracketsCount);
SkipUntil(tok::annot_pragma_openmp_end, StopBeforeMatch);
break;
case OMPC_threadprivate:
case NUM_OPENMP_CLAUSES:
Diag(Tok, diag::err_omp_unexpected_clause)
<< getOpenMPClauseName(CKind) << getOpenMPDirectiveName(DKind);
SkipUntil(tok::comma, tok::annot_pragma_openmp_end, StopBeforeMatch | NoBracketsCount);
SkipUntil(tok::comma, tok::annot_pragma_openmp_end, StopBeforeMatch);
break;
}
return ErrorFound ? 0 : Clause;
@ -309,8 +308,7 @@ OMPClause *Parser::ParseOpenMPSimpleClause(OpenMPClauseKind Kind) {
SourceLocation Loc = Tok.getLocation();
SourceLocation LOpen = ConsumeToken();
// Parse '('.
BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end,
true);
BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end);
if (T.expectAndConsume(diag::err_expected_lparen_after,
getOpenMPClauseName(Kind)))
return 0;
@ -344,8 +342,7 @@ OMPClause *Parser::ParseOpenMPVarListClause(OpenMPClauseKind Kind) {
SourceLocation Loc = Tok.getLocation();
SourceLocation LOpen = ConsumeToken();
// Parse '('.
BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end,
true);
BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end);
if (T.expectAndConsume(diag::err_expected_lparen_after,
getOpenMPClauseName(Kind)))
return 0;
@ -360,7 +357,7 @@ OMPClause *Parser::ParseOpenMPVarListClause(OpenMPClauseKind Kind) {
Vars.push_back(VarExpr.take());
} else {
SkipUntil(tok::comma, tok::r_paren, tok::annot_pragma_openmp_end,
StopBeforeMatch | NoBracketsCount);
StopBeforeMatch);
}
// Skip ',' if any
IsComma = Tok.is(tok::comma);

View File

@ -159,8 +159,7 @@ static bool IsCommonTypo(tok::TokenKind ExpectedTok, const Token &Tok) {
/// SkipToTok is specified, it calls SkipUntil(SkipToTok). Finally, true is
/// returned.
bool Parser::ExpectAndConsume(tok::TokenKind ExpectedTok, unsigned DiagID,
const char *Msg, tok::TokenKind SkipToTok,
bool NoCount) {
const char *Msg, tok::TokenKind SkipToTok) {
if (Tok.is(ExpectedTok) || Tok.is(tok::code_completion)) {
ConsumeAnyToken();
return false;
@ -190,12 +189,8 @@ bool Parser::ExpectAndConsume(tok::TokenKind ExpectedTok, unsigned DiagID,
} else
Diag(Tok, DiagID) << Msg;
if (SkipToTok != tok::unknown) {
SkipUntilFlags Flags = StopAtSemi;
if (NoCount)
Flags = Flags | NoBracketsCount;
SkipUntil(SkipToTok, Flags);
}
if (SkipToTok != tok::unknown)
SkipUntil(SkipToTok, StopAtSemi);
return true;
}
@ -319,32 +314,26 @@ bool Parser::SkipUntil(ArrayRef<tok::TokenKind> Toks, SkipUntilFlags Flags) {
case tok::l_paren:
// Recursively skip properly-nested parens.
ConsumeParen();
if (!HasFlagsSet(Flags, NoBracketsCount)) {
if (HasFlagsSet(Flags, StopAtCodeCompletion))
SkipUntil(tok::r_paren, StopAtCodeCompletion);
else
SkipUntil(tok::r_paren);
}
if (HasFlagsSet(Flags, StopAtCodeCompletion))
SkipUntil(tok::r_paren, StopAtCodeCompletion);
else
SkipUntil(tok::r_paren);
break;
case tok::l_square:
// Recursively skip properly-nested square brackets.
ConsumeBracket();
if (!HasFlagsSet(Flags, NoBracketsCount)) {
if (HasFlagsSet(Flags, StopAtCodeCompletion))
SkipUntil(tok::r_square, StopAtCodeCompletion);
else
SkipUntil(tok::r_square);
}
if (HasFlagsSet(Flags, StopAtCodeCompletion))
SkipUntil(tok::r_square, StopAtCodeCompletion);
else
SkipUntil(tok::r_square);
break;
case tok::l_brace:
// Recursively skip properly-nested braces.
ConsumeBrace();
if (!HasFlagsSet(Flags, NoBracketsCount)) {
if (HasFlagsSet(Flags, StopAtCodeCompletion))
SkipUntil(tok::r_brace, StopAtCodeCompletion);
else
SkipUntil(tok::r_brace);
}
if (HasFlagsSet(Flags, StopAtCodeCompletion))
SkipUntil(tok::r_brace, StopAtCodeCompletion);
else
SkipUntil(tok::r_brace);
break;
// Okay, we found a ']' or '}' or ')', which we think should be balanced.
@ -353,17 +342,17 @@ bool Parser::SkipUntil(ArrayRef<tok::TokenKind> Toks, SkipUntilFlags Flags) {
// higher level, we will assume that this matches the unbalanced token
// and return it. Otherwise, this is a spurious RHS token, which we skip.
case tok::r_paren:
if (!HasFlagsSet(Flags, NoBracketsCount) && ParenCount && !isFirstTokenSkipped)
if (ParenCount && !isFirstTokenSkipped)
return false; // Matches something.
ConsumeParen();
break;
case tok::r_square:
if (!HasFlagsSet(Flags, NoBracketsCount) && BracketCount && !isFirstTokenSkipped)
if (BracketCount && !isFirstTokenSkipped)
return false; // Matches something.
ConsumeBracket();
break;
case tok::r_brace:
if (!HasFlagsSet(Flags, NoBracketsCount) && BraceCount && !isFirstTokenSkipped)
if (BraceCount && !isFirstTokenSkipped)
return false; // Matches something.
ConsumeBrace();
break;
@ -2042,7 +2031,7 @@ bool BalancedDelimiterTracker::expectAndConsume(unsigned DiagID,
const char *Msg,
tok::TokenKind SkipToToc ) {
LOpen = P.Tok.getLocation();
if (P.ExpectAndConsume(Kind, DiagID, Msg, SkipToToc, NoCount))
if (P.ExpectAndConsume(Kind, DiagID, Msg, SkipToToc))
return true;
if (getDepth() < MaxDepth)
@ -2067,21 +2056,16 @@ bool BalancedDelimiterTracker::diagnoseMissingClose() {
// If we're not already at some kind of closing bracket, skip to our closing
// token.
Parser::SkipUntilFlags Flags = Parser::StopAtSemi | Parser::StopBeforeMatch;
if (NoCount)
Flags = Flags | Parser::NoBracketsCount;
if (P.Tok.isNot(tok::r_paren) && P.Tok.isNot(tok::r_brace) &&
P.Tok.isNot(tok::r_square) &&
P.SkipUntil(Close, FinalToken, Flags) &&
P.SkipUntil(Close, FinalToken,
Parser::StopAtSemi | Parser::StopBeforeMatch) &&
P.Tok.is(Close))
LClose = P.ConsumeAnyToken();
return true;
}
void BalancedDelimiterTracker::skipToEnd() {
Parser::SkipUntilFlags Flags = Parser::StopBeforeMatch;
if (NoCount)
Flags = Flags | Parser::NoBracketsCount;
P.SkipUntil(Close, Flags);
P.SkipUntil(Close, Parser::StopBeforeMatch);
consumeClose();
}

View File

@ -361,7 +361,6 @@ namespace clang {
tok::TokenKind Kind, Close, FinalToken;
SourceLocation (Parser::*Consumer)();
SourceLocation LOpen, LClose;
bool NoCount;
unsigned short &getDepth() {
switch (Kind) {
@ -379,10 +378,9 @@ namespace clang {
public:
BalancedDelimiterTracker(Parser& p, tok::TokenKind k,
tok::TokenKind FinalToken = tok::semi,
bool NoCount = false)
tok::TokenKind FinalToken = tok::semi)
: GreaterThanIsOperatorScope(p.GreaterThanIsOperator, true),
P(p), Kind(k), FinalToken(FinalToken), NoCount(NoCount)
P(p), Kind(k), FinalToken(FinalToken)
{
switch (Kind) {
default: llvm_unreachable("Unexpected balanced token");

View File

@ -6,18 +6,6 @@ void foo() {
#pragma omp parallel // expected-error {{unexpected OpenMP directive '#pragma omp parallel'}}
int main(int argc, char **argv) {
#pragma omp parallel { // expected-warning {{extra tokens at the end of '#pragma omp parallel' are ignored}}
foo();
#pragma omp parallel ( // expected-warning {{extra tokens at the end of '#pragma omp parallel' are ignored}}
foo();
#pragma omp parallel [ // expected-warning {{extra tokens at the end of '#pragma omp parallel' are ignored}}
foo();
#pragma omp parallel ] // expected-warning {{extra tokens at the end of '#pragma omp parallel' are ignored}}
foo();
#pragma omp parallel ) // expected-warning {{extra tokens at the end of '#pragma omp parallel' are ignored}}
foo();
#pragma omp parallel } // expected-warning {{extra tokens at the end of '#pragma omp parallel' are ignored}}
foo();
#pragma omp parallel
#pragma omp parallel unknown() // expected-warning {{extra tokens at the end of '#pragma omp parallel' are ignored}}
foo();

View File

@ -24,12 +24,6 @@ int foo() { // expected-note {{declared here}}
return (a);
}
#pragma omp threadprivate (a) ( // expected-error {{'#pragma omp threadprivate' must precede all references to variable 'a'}} expected-warning {{extra tokens at the end of '#pragma omp threadprivate' are ignored}}
#pragma omp threadprivate (a) [ // expected-error {{'#pragma omp threadprivate' must precede all references to variable 'a'}} expected-warning {{extra tokens at the end of '#pragma omp threadprivate' are ignored}}
#pragma omp threadprivate (a) { // expected-error {{'#pragma omp threadprivate' must precede all references to variable 'a'}} expected-warning {{extra tokens at the end of '#pragma omp threadprivate' are ignored}}
#pragma omp threadprivate (a) ) // expected-error {{'#pragma omp threadprivate' must precede all references to variable 'a'}} expected-warning {{extra tokens at the end of '#pragma omp threadprivate' are ignored}}
#pragma omp threadprivate (a) ] // expected-error {{'#pragma omp threadprivate' must precede all references to variable 'a'}} expected-warning {{extra tokens at the end of '#pragma omp threadprivate' are ignored}}
#pragma omp threadprivate (a) } // expected-error {{'#pragma omp threadprivate' must precede all references to variable 'a'}} expected-warning {{extra tokens at the end of '#pragma omp threadprivate' are ignored}}
#pragma omp threadprivate a // expected-error {{expected '(' after 'threadprivate'}}
#pragma omp threadprivate(d // expected-error {{expected ')'}} expected-note {{to match this '('}} expected-error {{'#pragma omp threadprivate' must precede all references to variable 'd'}}
#pragma omp threadprivate(d)) // expected-error {{'#pragma omp threadprivate' must precede all references to variable 'd'}} expected-warning {{extra tokens at the end of '#pragma omp threadprivate' are ignored}}