aboutsummaryrefslogtreecommitdiff
path: root/lib/Parse/ParseInit.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/Parse/ParseInit.cpp')
-rw-r--r--lib/Parse/ParseInit.cpp27
1 files changed, 27 insertions, 0 deletions
diff --git a/lib/Parse/ParseInit.cpp b/lib/Parse/ParseInit.cpp
index 7a455484b902..5ab055130dc2 100644
--- a/lib/Parse/ParseInit.cpp
+++ b/lib/Parse/ParseInit.cpp
@@ -39,12 +39,14 @@ bool Parser::MayBeDesignationStart() {
// cases here, and fall back to tentative parsing if those fail.
switch (PP.LookAhead(0).getKind()) {
case tok::equal:
+ case tok::ellipsis:
case tok::r_square:
// Definitely starts a lambda expression.
return false;
case tok::amp:
case tok::kw_this:
+ case tok::star:
case tok::identifier:
// We have to do additional analysis, because these could be the
// start of a constant expression or a lambda capture list.
@@ -114,6 +116,8 @@ static void CheckArrayDesignatorSyntax(Parser &P, SourceLocation Loc,
/// ParseInitializerWithPotentialDesignator - Parse the 'initializer' production
/// checking to see if the token stream starts with a designator.
///
+/// C99:
+///
/// designation:
/// designator-list '='
/// [GNU] array-designator
@@ -131,6 +135,21 @@ static void CheckArrayDesignatorSyntax(Parser &P, SourceLocation Loc,
/// '[' constant-expression ']'
/// [GNU] '[' constant-expression '...' constant-expression ']'
///
+/// C++20:
+///
+/// designated-initializer-list:
+/// designated-initializer-clause
+/// designated-initializer-list ',' designated-initializer-clause
+///
+/// designated-initializer-clause:
+/// designator brace-or-equal-initializer
+///
+/// designator:
+/// '.' identifier
+///
+/// We allow the C99 syntax extensions in C++20, but do not allow the C++20
+/// extension (a braced-init-list after the designator with no '=') in C99.
+///
/// NOTE: [OBC] allows '[ objc-receiver objc-message-args ]' as an
/// initializer (because it is an expression). We need to consider this case
/// when parsing array designators.
@@ -363,6 +382,14 @@ ExprResult Parser::ParseInitializerWithPotentialDesignator() {
ParseInitializer());
}
+ // Handle a C++20 braced designated initialization, which results in
+ // direct-list-initialization of the aggregate element. We allow this as an
+ // extension from C++11 onwards (when direct-list-initialization was added).
+ if (Tok.is(tok::l_brace) && getLangOpts().CPlusPlus11) {
+ return Actions.ActOnDesignatedInitializer(Desig, SourceLocation(), false,
+ ParseBraceInitializer());
+ }
+
// We read some number of designators and found something that isn't an = or
// an initializer. If we have exactly one array designator, this
// is the GNU 'designation: array-designator' extension. Otherwise, it is a