diff options
author | Richard Smith <richard-llvm@metafoo.co.uk> | 2014-04-13 04:31:48 +0000 |
---|---|---|
committer | Richard Smith <richard-llvm@metafoo.co.uk> | 2014-04-13 04:31:48 +0000 |
commit | 9e2f0a4f628b2cefb9a234c3c66f820bdbc966fc (patch) | |
tree | 243b31598db83cc659cf606531530741e4836db4 /clang/lib/Parse/ParseInit.cpp | |
parent | 0563ca1be808a14863d87f3c878c30555328b0bf (diff) | |
download | bcm5719-llvm-9e2f0a4f628b2cefb9a234c3c66f820bdbc966fc.tar.gz bcm5719-llvm-9e2f0a4f628b2cefb9a234c3c66f820bdbc966fc.zip |
PR19339: Disambiguate lambdas with init-captures from designated initializers
properly.
llvm-svn: 206128
Diffstat (limited to 'clang/lib/Parse/ParseInit.cpp')
-rw-r--r-- | clang/lib/Parse/ParseInit.cpp | 58 |
1 files changed, 21 insertions, 37 deletions
diff --git a/clang/lib/Parse/ParseInit.cpp b/clang/lib/Parse/ParseInit.cpp index 44053f193bd..bdd45131676 100644 --- a/clang/lib/Parse/ParseInit.cpp +++ b/clang/lib/Parse/ParseInit.cpp @@ -66,45 +66,29 @@ bool Parser::MayBeDesignationStart() { } // Parse up to (at most) the token after the closing ']' to determine - // whether this is a C99 designator or a lambda. + // whether this is a C99 designator or a lambda. TentativeParsingAction Tentative(*this); - ConsumeBracket(); - while (true) { - switch (Tok.getKind()) { - case tok::equal: - case tok::amp: - case tok::identifier: - case tok::kw_this: - // These tokens can occur in a capture list or a constant-expression. - // Keep looking. - ConsumeToken(); - continue; - - case tok::comma: - // Since a comma cannot occur in a constant-expression, this must - // be a lambda. - Tentative.Revert(); - return false; - - case tok::r_square: { - // Once we hit the closing square bracket, we look at the next - // token. If it's an '=', this is a designator. Otherwise, it's a - // lambda expression. This decision favors lambdas over the older - // GNU designator syntax, which allows one to omit the '=', but is - // consistent with GCC. - ConsumeBracket(); - tok::TokenKind Kind = Tok.getKind(); - Tentative.Revert(); - return Kind == tok::equal; - } - - default: - // Anything else cannot occur in a lambda capture list, so it - // must be a designator. - Tentative.Revert(); - return true; - } + + LambdaIntroducer Intro; + bool SkippedInits = false; + Optional<unsigned> DiagID(ParseLambdaIntroducer(Intro, &SkippedInits)); + + if (DiagID) { + // If this can't be a lambda capture list, it's a designator. + Tentative.Revert(); + return true; } + + // Once we hit the closing square bracket, we look at the next + // token. If it's an '=', this is a designator. Otherwise, it's a + // lambda expression. This decision favors lambdas over the older + // GNU designator syntax, which allows one to omit the '=', but is + // consistent with GCC. + tok::TokenKind Kind = Tok.getKind(); + // FIXME: If we didn't skip any inits, parse the lambda from here + // rather than throwing away then reparsing the LambdaIntroducer. + Tentative.Revert(); + return Kind == tok::equal; } static void CheckArrayDesignatorSyntax(Parser &P, SourceLocation Loc, |