ParseInit.cpp revision 243830
1193326Sed//===--- ParseInit.cpp - Initializer Parsing ------------------------------===// 2193326Sed// 3193326Sed// The LLVM Compiler Infrastructure 4193326Sed// 5193326Sed// This file is distributed under the University of Illinois Open Source 6193326Sed// License. See LICENSE.TXT for details. 7193326Sed// 8193326Sed//===----------------------------------------------------------------------===// 9193326Sed// 10193326Sed// This file implements initializer parsing as specified by C99 6.7.8. 11193326Sed// 12193326Sed//===----------------------------------------------------------------------===// 13193326Sed 14193326Sed#include "clang/Parse/Parser.h" 15193326Sed#include "clang/Parse/ParseDiagnostic.h" 16218893Sdim#include "RAIIObjectsForParser.h" 17212904Sdim#include "clang/Sema/Designator.h" 18212904Sdim#include "clang/Sema/Scope.h" 19193326Sed#include "llvm/ADT/SmallString.h" 20198398Srdivacky#include "llvm/Support/raw_ostream.h" 21193326Sedusing namespace clang; 22193326Sed 23193326Sed 24234353Sdim/// MayBeDesignationStart - Return true if the current token might be the start 25234353Sdim/// of a designator. If we can tell it is impossible that it is a designator, 26234353Sdim/// return false. 27234353Sdimbool Parser::MayBeDesignationStart() { 28234353Sdim switch (Tok.getKind()) { 29234353Sdim default: 30234353Sdim return false; 31234353Sdim 32193326Sed case tok::period: // designator: '.' identifier 33234353Sdim return true; 34234353Sdim 35234353Sdim case tok::l_square: { // designator: array-designator 36234353Sdim if (!PP.getLangOpts().CPlusPlus0x) 37193326Sed return true; 38234353Sdim 39234353Sdim // C++11 lambda expressions and C99 designators can be ambiguous all the 40234353Sdim // way through the closing ']' and to the next character. Handle the easy 41234353Sdim // cases here, and fall back to tentative parsing if those fail. 42234353Sdim switch (PP.LookAhead(0).getKind()) { 43234353Sdim case tok::equal: 44234353Sdim case tok::r_square: 45234353Sdim // Definitely starts a lambda expression. 46234353Sdim return false; 47234353Sdim 48234353Sdim case tok::amp: 49234353Sdim case tok::kw_this: 50234353Sdim case tok::identifier: 51234353Sdim // We have to do additional analysis, because these could be the 52234353Sdim // start of a constant expression or a lambda capture list. 53234353Sdim break; 54234353Sdim 55234353Sdim default: 56234353Sdim // Anything not mentioned above cannot occur following a '[' in a 57234353Sdim // lambda expression. 58234353Sdim return true; 59234353Sdim } 60234353Sdim 61234353Sdim // Handle the complicated case below. 62234353Sdim break; 63234353Sdim } 64193326Sed case tok::identifier: // designation: identifier ':' 65193326Sed return PP.LookAhead(0).is(tok::colon); 66193326Sed } 67234353Sdim 68234353Sdim // Parse up to (at most) the token after the closing ']' to determine 69234353Sdim // whether this is a C99 designator or a lambda. 70234353Sdim TentativeParsingAction Tentative(*this); 71234353Sdim ConsumeBracket(); 72234353Sdim while (true) { 73234353Sdim switch (Tok.getKind()) { 74234353Sdim case tok::equal: 75234353Sdim case tok::amp: 76234353Sdim case tok::identifier: 77234353Sdim case tok::kw_this: 78234353Sdim // These tokens can occur in a capture list or a constant-expression. 79234353Sdim // Keep looking. 80234353Sdim ConsumeToken(); 81234353Sdim continue; 82234353Sdim 83234353Sdim case tok::comma: 84234353Sdim // Since a comma cannot occur in a constant-expression, this must 85234353Sdim // be a lambda. 86234353Sdim Tentative.Revert(); 87234353Sdim return false; 88234353Sdim 89234353Sdim case tok::r_square: { 90234353Sdim // Once we hit the closing square bracket, we look at the next 91234353Sdim // token. If it's an '=', this is a designator. Otherwise, it's a 92234353Sdim // lambda expression. This decision favors lambdas over the older 93234353Sdim // GNU designator syntax, which allows one to omit the '=', but is 94234353Sdim // consistent with GCC. 95234353Sdim ConsumeBracket(); 96234353Sdim tok::TokenKind Kind = Tok.getKind(); 97234353Sdim Tentative.Revert(); 98234353Sdim return Kind == tok::equal; 99234353Sdim } 100234353Sdim 101234353Sdim default: 102234353Sdim // Anything else cannot occur in a lambda capture list, so it 103234353Sdim // must be a designator. 104234353Sdim Tentative.Revert(); 105234353Sdim return true; 106234353Sdim } 107234353Sdim } 108234353Sdim 109234353Sdim return true; 110193326Sed} 111193326Sed 112207619Srdivackystatic void CheckArrayDesignatorSyntax(Parser &P, SourceLocation Loc, 113207619Srdivacky Designation &Desig) { 114207619Srdivacky // If we have exactly one array designator, this used the GNU 115207619Srdivacky // 'designation: array-designator' extension, otherwise there should be no 116207619Srdivacky // designators at all! 117207619Srdivacky if (Desig.getNumDesignators() == 1 && 118207619Srdivacky (Desig.getDesignator(0).isArrayDesignator() || 119207619Srdivacky Desig.getDesignator(0).isArrayRangeDesignator())) 120207619Srdivacky P.Diag(Loc, diag::ext_gnu_missing_equal_designator); 121207619Srdivacky else if (Desig.getNumDesignators() > 0) 122207619Srdivacky P.Diag(Loc, diag::err_expected_equal_designator); 123207619Srdivacky} 124207619Srdivacky 125193326Sed/// ParseInitializerWithPotentialDesignator - Parse the 'initializer' production 126193326Sed/// checking to see if the token stream starts with a designator. 127193326Sed/// 128193326Sed/// designation: 129193326Sed/// designator-list '=' 130193326Sed/// [GNU] array-designator 131193326Sed/// [GNU] identifier ':' 132193326Sed/// 133193326Sed/// designator-list: 134193326Sed/// designator 135193326Sed/// designator-list designator 136193326Sed/// 137193326Sed/// designator: 138193326Sed/// array-designator 139193326Sed/// '.' identifier 140193326Sed/// 141193326Sed/// array-designator: 142193326Sed/// '[' constant-expression ']' 143193326Sed/// [GNU] '[' constant-expression '...' constant-expression ']' 144193326Sed/// 145193326Sed/// NOTE: [OBC] allows '[ objc-receiver objc-message-args ]' as an 146193326Sed/// initializer (because it is an expression). We need to consider this case 147193326Sed/// when parsing array designators. 148193326Sed/// 149212904SdimExprResult Parser::ParseInitializerWithPotentialDesignator() { 150193326Sed 151193326Sed // If this is the old-style GNU extension: 152193326Sed // designation ::= identifier ':' 153193326Sed // Handle it as a field designator. Otherwise, this must be the start of a 154193326Sed // normal expression. 155193326Sed if (Tok.is(tok::identifier)) { 156193326Sed const IdentifierInfo *FieldName = Tok.getIdentifierInfo(); 157193326Sed 158234353Sdim SmallString<256> NewSyntax; 159198398Srdivacky llvm::raw_svector_ostream(NewSyntax) << '.' << FieldName->getName() 160198398Srdivacky << " = "; 161193326Sed 162193326Sed SourceLocation NameLoc = ConsumeToken(); // Eat the identifier. 163198092Srdivacky 164193326Sed assert(Tok.is(tok::colon) && "MayBeDesignationStart not working properly!"); 165193326Sed SourceLocation ColonLoc = ConsumeToken(); 166193326Sed 167226633Sdim Diag(NameLoc, diag::ext_gnu_old_style_field_designator) 168206084Srdivacky << FixItHint::CreateReplacement(SourceRange(NameLoc, ColonLoc), 169206084Srdivacky NewSyntax.str()); 170193326Sed 171193326Sed Designation D; 172193326Sed D.AddDesignator(Designator::getField(FieldName, SourceLocation(), NameLoc)); 173198092Srdivacky return Actions.ActOnDesignatedInitializer(D, ColonLoc, true, 174193326Sed ParseInitializer()); 175193326Sed } 176198092Srdivacky 177193326Sed // Desig - This is initialized when we see our first designator. We may have 178193326Sed // an objc message send with no designator, so we don't want to create this 179193326Sed // eagerly. 180193326Sed Designation Desig; 181198092Srdivacky 182193326Sed // Parse each designator in the designator list until we find an initializer. 183193326Sed while (Tok.is(tok::period) || Tok.is(tok::l_square)) { 184193326Sed if (Tok.is(tok::period)) { 185193326Sed // designator: '.' identifier 186193326Sed SourceLocation DotLoc = ConsumeToken(); 187198092Srdivacky 188193326Sed if (Tok.isNot(tok::identifier)) { 189193326Sed Diag(Tok.getLocation(), diag::err_expected_field_designator); 190193326Sed return ExprError(); 191193326Sed } 192198092Srdivacky 193193326Sed Desig.AddDesignator(Designator::getField(Tok.getIdentifierInfo(), DotLoc, 194193326Sed Tok.getLocation())); 195193326Sed ConsumeToken(); // Eat the identifier. 196193326Sed continue; 197193326Sed } 198198092Srdivacky 199193326Sed // We must have either an array designator now or an objc message send. 200193326Sed assert(Tok.is(tok::l_square) && "Unexpected token!"); 201198092Srdivacky 202193326Sed // Handle the two forms of array designator: 203193326Sed // array-designator: '[' constant-expression ']' 204193326Sed // array-designator: '[' constant-expression '...' constant-expression ']' 205193326Sed // 206193326Sed // Also, we have to handle the case where the expression after the 207193326Sed // designator an an objc message send: '[' objc-message-expr ']'. 208193326Sed // Interesting cases are: 209193326Sed // [foo bar] -> objc message send 210193326Sed // [foo] -> array designator 211193326Sed // [foo ... bar] -> array designator 212193326Sed // [4][foo bar] -> obsolete GNU designation with objc message send. 213193326Sed // 214234353Sdim // We do not need to check for an expression starting with [[ here. If it 215234353Sdim // contains an Objective-C message send, then it is not an ill-formed 216234353Sdim // attribute. If it is a lambda-expression within an array-designator, then 217234353Sdim // it will be rejected because a constant-expression cannot begin with a 218234353Sdim // lambda-expression. 219218893Sdim InMessageExpressionRAIIObject InMessage(*this, true); 220218893Sdim 221226633Sdim BalancedDelimiterTracker T(*this, tok::l_square); 222226633Sdim T.consumeOpen(); 223226633Sdim SourceLocation StartLoc = T.getOpenLocation(); 224226633Sdim 225212904Sdim ExprResult Idx; 226198092Srdivacky 227207619Srdivacky // If Objective-C is enabled and this is a typename (class message 228207619Srdivacky // send) or send to 'super', parse this as a message send 229207619Srdivacky // expression. We handle C++ and C separately, since C++ requires 230207619Srdivacky // much more complicated parsing. 231234353Sdim if (getLangOpts().ObjC1 && getLangOpts().CPlusPlus) { 232207619Srdivacky // Send to 'super'. 233207619Srdivacky if (Tok.is(tok::identifier) && Tok.getIdentifierInfo() == Ident_super && 234218893Sdim NextToken().isNot(tok::period) && 235218893Sdim getCurScope()->isInObjcMethodScope()) { 236207619Srdivacky CheckArrayDesignatorSyntax(*this, StartLoc, Desig); 237207619Srdivacky return ParseAssignmentExprWithObjCMessageExprStart(StartLoc, 238212904Sdim ConsumeToken(), 239212904Sdim ParsedType(), 240212904Sdim 0); 241207619Srdivacky } 242193326Sed 243207619Srdivacky // Parse the receiver, which is either a type or an expression. 244207619Srdivacky bool IsExpr; 245207619Srdivacky void *TypeOrExpr; 246207619Srdivacky if (ParseObjCXXMessageReceiver(IsExpr, TypeOrExpr)) { 247207619Srdivacky SkipUntil(tok::r_square); 248207619Srdivacky return ExprError(); 249207619Srdivacky } 250207619Srdivacky 251207619Srdivacky // If the receiver was a type, we have a class message; parse 252207619Srdivacky // the rest of it. 253207619Srdivacky if (!IsExpr) { 254207619Srdivacky CheckArrayDesignatorSyntax(*this, StartLoc, Desig); 255207619Srdivacky return ParseAssignmentExprWithObjCMessageExprStart(StartLoc, 256207619Srdivacky SourceLocation(), 257212904Sdim ParsedType::getFromOpaquePtr(TypeOrExpr), 258212904Sdim 0); 259207619Srdivacky } 260207619Srdivacky 261207619Srdivacky // If the receiver was an expression, we still don't know 262207619Srdivacky // whether we have a message send or an array designator; just 263207619Srdivacky // adopt the expression for further analysis below. 264207619Srdivacky // FIXME: potentially-potentially evaluated expression above? 265212904Sdim Idx = ExprResult(static_cast<Expr*>(TypeOrExpr)); 266234353Sdim } else if (getLangOpts().ObjC1 && Tok.is(tok::identifier)) { 267207619Srdivacky IdentifierInfo *II = Tok.getIdentifierInfo(); 268207619Srdivacky SourceLocation IILoc = Tok.getLocation(); 269212904Sdim ParsedType ReceiverType; 270207619Srdivacky // Three cases. This is a message send to a type: [type foo] 271207619Srdivacky // This is a message send to super: [super foo] 272207619Srdivacky // This is a message sent to an expr: [super.bar foo] 273212904Sdim switch (Sema::ObjCMessageKind Kind 274210299Sed = Actions.getObjCMessageKind(getCurScope(), II, IILoc, 275207619Srdivacky II == Ident_super, 276207619Srdivacky NextToken().is(tok::period), 277207619Srdivacky ReceiverType)) { 278212904Sdim case Sema::ObjCSuperMessage: 279212904Sdim case Sema::ObjCClassMessage: 280207619Srdivacky CheckArrayDesignatorSyntax(*this, StartLoc, Desig); 281212904Sdim if (Kind == Sema::ObjCSuperMessage) 282207619Srdivacky return ParseAssignmentExprWithObjCMessageExprStart(StartLoc, 283207619Srdivacky ConsumeToken(), 284212904Sdim ParsedType(), 285212904Sdim 0); 286207619Srdivacky ConsumeToken(); // the identifier 287207619Srdivacky if (!ReceiverType) { 288207619Srdivacky SkipUntil(tok::r_square); 289207619Srdivacky return ExprError(); 290207619Srdivacky } 291207619Srdivacky 292207619Srdivacky return ParseAssignmentExprWithObjCMessageExprStart(StartLoc, 293207619Srdivacky SourceLocation(), 294207619Srdivacky ReceiverType, 295212904Sdim 0); 296207619Srdivacky 297212904Sdim case Sema::ObjCInstanceMessage: 298207619Srdivacky // Fall through; we'll just parse the expression and 299207619Srdivacky // (possibly) treat this like an Objective-C message send 300207619Srdivacky // later. 301207619Srdivacky break; 302207619Srdivacky } 303193326Sed } 304193326Sed 305207619Srdivacky // Parse the index expression, if we haven't already gotten one 306207619Srdivacky // above (which can only happen in Objective-C++). 307193326Sed // Note that we parse this as an assignment expression, not a constant 308193326Sed // expression (allowing *=, =, etc) to handle the objc case. Sema needs 309193326Sed // to validate that the expression is a constant. 310207619Srdivacky // FIXME: We also need to tell Sema that we're in a 311207619Srdivacky // potentially-potentially evaluated context. 312207619Srdivacky if (!Idx.get()) { 313207619Srdivacky Idx = ParseAssignmentExpression(); 314207619Srdivacky if (Idx.isInvalid()) { 315207619Srdivacky SkipUntil(tok::r_square); 316243830Sdim return Idx; 317207619Srdivacky } 318193326Sed } 319198092Srdivacky 320193326Sed // Given an expression, we could either have a designator (if the next 321193326Sed // tokens are '...' or ']' or an objc message send. If this is an objc 322198092Srdivacky // message send, handle it now. An objc-message send is the start of 323193326Sed // an assignment-expression production. 324234353Sdim if (getLangOpts().ObjC1 && Tok.isNot(tok::ellipsis) && 325193326Sed Tok.isNot(tok::r_square)) { 326207619Srdivacky CheckArrayDesignatorSyntax(*this, Tok.getLocation(), Desig); 327193326Sed return ParseAssignmentExprWithObjCMessageExprStart(StartLoc, 328193326Sed SourceLocation(), 329212904Sdim ParsedType(), 330212904Sdim Idx.take()); 331193326Sed } 332193326Sed 333193326Sed // If this is a normal array designator, remember it. 334193326Sed if (Tok.isNot(tok::ellipsis)) { 335193326Sed Desig.AddDesignator(Designator::getArray(Idx.release(), StartLoc)); 336193326Sed } else { 337193326Sed // Handle the gnu array range extension. 338193326Sed Diag(Tok, diag::ext_gnu_array_range); 339193326Sed SourceLocation EllipsisLoc = ConsumeToken(); 340193326Sed 341212904Sdim ExprResult RHS(ParseConstantExpression()); 342193326Sed if (RHS.isInvalid()) { 343193326Sed SkipUntil(tok::r_square); 344243830Sdim return RHS; 345193326Sed } 346193326Sed Desig.AddDesignator(Designator::getArrayRange(Idx.release(), 347193326Sed RHS.release(), 348193326Sed StartLoc, EllipsisLoc)); 349193326Sed } 350193326Sed 351226633Sdim T.consumeClose(); 352226633Sdim Desig.getDesignator(Desig.getNumDesignators() - 1).setRBracketLoc( 353226633Sdim T.getCloseLocation()); 354193326Sed } 355193326Sed 356193326Sed // Okay, we're done with the designator sequence. We know that there must be 357193326Sed // at least one designator, because the only case we can get into this method 358193326Sed // without a designator is when we have an objc message send. That case is 359193326Sed // handled and returned from above. 360193326Sed assert(!Desig.empty() && "Designator is empty?"); 361193326Sed 362193326Sed // Handle a normal designator sequence end, which is an equal. 363193326Sed if (Tok.is(tok::equal)) { 364193326Sed SourceLocation EqualLoc = ConsumeToken(); 365193326Sed return Actions.ActOnDesignatedInitializer(Desig, EqualLoc, false, 366193326Sed ParseInitializer()); 367193326Sed } 368193326Sed 369193326Sed // We read some number of designators and found something that isn't an = or 370193326Sed // an initializer. If we have exactly one array designator, this 371193326Sed // is the GNU 'designation: array-designator' extension. Otherwise, it is a 372193326Sed // parse error. 373198092Srdivacky if (Desig.getNumDesignators() == 1 && 374193326Sed (Desig.getDesignator(0).isArrayDesignator() || 375193326Sed Desig.getDesignator(0).isArrayRangeDesignator())) { 376193326Sed Diag(Tok, diag::ext_gnu_missing_equal_designator) 377206084Srdivacky << FixItHint::CreateInsertion(Tok.getLocation(), "= "); 378193326Sed return Actions.ActOnDesignatedInitializer(Desig, Tok.getLocation(), 379193326Sed true, ParseInitializer()); 380193326Sed } 381193326Sed 382193326Sed Diag(Tok, diag::err_expected_equal_designator); 383193326Sed return ExprError(); 384193326Sed} 385193326Sed 386193326Sed 387193326Sed/// ParseBraceInitializer - Called when parsing an initializer that has a 388193326Sed/// leading open brace. 389193326Sed/// 390193326Sed/// initializer: [C99 6.7.8] 391193326Sed/// '{' initializer-list '}' 392193326Sed/// '{' initializer-list ',' '}' 393193326Sed/// [GNU] '{' '}' 394193326Sed/// 395193326Sed/// initializer-list: 396218893Sdim/// designation[opt] initializer ...[opt] 397218893Sdim/// initializer-list ',' designation[opt] initializer ...[opt] 398193326Sed/// 399212904SdimExprResult Parser::ParseBraceInitializer() { 400218893Sdim InMessageExpressionRAIIObject InMessage(*this, false); 401218893Sdim 402226633Sdim BalancedDelimiterTracker T(*this, tok::l_brace); 403226633Sdim T.consumeOpen(); 404226633Sdim SourceLocation LBraceLoc = T.getOpenLocation(); 405193326Sed 406193326Sed /// InitExprs - This is the actual list of expressions contained in the 407193326Sed /// initializer. 408243830Sdim ExprVector InitExprs; 409193326Sed 410193326Sed if (Tok.is(tok::r_brace)) { 411193326Sed // Empty initializers are a C++ feature and a GNU extension to C. 412234353Sdim if (!getLangOpts().CPlusPlus) 413193326Sed Diag(LBraceLoc, diag::ext_gnu_empty_initializer); 414193326Sed // Match the '}'. 415243830Sdim return Actions.ActOnInitList(LBraceLoc, MultiExprArg(), ConsumeBrace()); 416193326Sed } 417193326Sed 418193326Sed bool InitExprsOk = true; 419193326Sed 420193326Sed while (1) { 421234353Sdim // Handle Microsoft __if_exists/if_not_exists if necessary. 422234353Sdim if (getLangOpts().MicrosoftExt && (Tok.is(tok::kw___if_exists) || 423234353Sdim Tok.is(tok::kw___if_not_exists))) { 424234353Sdim if (ParseMicrosoftIfExistsBraceInitializer(InitExprs, InitExprsOk)) { 425234353Sdim if (Tok.isNot(tok::comma)) break; 426234353Sdim ConsumeToken(); 427234353Sdim } 428234353Sdim if (Tok.is(tok::r_brace)) break; 429234353Sdim continue; 430234353Sdim } 431234353Sdim 432193326Sed // Parse: designation[opt] initializer 433193326Sed 434193326Sed // If we know that this cannot be a designation, just parse the nested 435193326Sed // initializer directly. 436212904Sdim ExprResult SubElt; 437234353Sdim if (MayBeDesignationStart()) 438193326Sed SubElt = ParseInitializerWithPotentialDesignator(); 439193326Sed else 440193326Sed SubElt = ParseInitializer(); 441198092Srdivacky 442218893Sdim if (Tok.is(tok::ellipsis)) 443218893Sdim SubElt = Actions.ActOnPackExpansion(SubElt.get(), ConsumeToken()); 444218893Sdim 445193326Sed // If we couldn't parse the subelement, bail out. 446193326Sed if (!SubElt.isInvalid()) { 447193326Sed InitExprs.push_back(SubElt.release()); 448193326Sed } else { 449193326Sed InitExprsOk = false; 450198092Srdivacky 451193326Sed // We have two ways to try to recover from this error: if the code looks 452221345Sdim // grammatically ok (i.e. we have a comma coming up) try to continue 453193326Sed // parsing the rest of the initializer. This allows us to emit 454193326Sed // diagnostics for later elements that we find. If we don't see a comma, 455193326Sed // assume there is a parse error, and just skip to recover. 456193326Sed // FIXME: This comment doesn't sound right. If there is a r_brace 457193326Sed // immediately, it can't be an error, since there is no other way of 458193326Sed // leaving this loop except through this if. 459193326Sed if (Tok.isNot(tok::comma)) { 460193326Sed SkipUntil(tok::r_brace, false, true); 461193326Sed break; 462193326Sed } 463193326Sed } 464193326Sed 465193326Sed // If we don't have a comma continued list, we're done. 466193326Sed if (Tok.isNot(tok::comma)) break; 467193326Sed 468193326Sed // TODO: save comma locations if some client cares. 469193326Sed ConsumeToken(); 470193326Sed 471193326Sed // Handle trailing comma. 472193326Sed if (Tok.is(tok::r_brace)) break; 473193326Sed } 474226633Sdim 475226633Sdim bool closed = !T.consumeClose(); 476226633Sdim 477226633Sdim if (InitExprsOk && closed) 478243830Sdim return Actions.ActOnInitList(LBraceLoc, InitExprs, 479226633Sdim T.getCloseLocation()); 480193326Sed 481193326Sed return ExprError(); // an error occurred. 482193326Sed} 483193326Sed 484234353Sdim 485234353Sdim// Return true if a comma (or closing brace) is necessary after the 486234353Sdim// __if_exists/if_not_exists statement. 487234353Sdimbool Parser::ParseMicrosoftIfExistsBraceInitializer(ExprVector &InitExprs, 488234353Sdim bool &InitExprsOk) { 489234353Sdim bool trailingComma = false; 490234353Sdim IfExistsCondition Result; 491234353Sdim if (ParseMicrosoftIfExistsCondition(Result)) 492234353Sdim return false; 493234353Sdim 494234353Sdim BalancedDelimiterTracker Braces(*this, tok::l_brace); 495234353Sdim if (Braces.consumeOpen()) { 496234353Sdim Diag(Tok, diag::err_expected_lbrace); 497234353Sdim return false; 498234353Sdim } 499234353Sdim 500234353Sdim switch (Result.Behavior) { 501234353Sdim case IEB_Parse: 502234353Sdim // Parse the declarations below. 503234353Sdim break; 504234353Sdim 505234353Sdim case IEB_Dependent: 506234353Sdim Diag(Result.KeywordLoc, diag::warn_microsoft_dependent_exists) 507234353Sdim << Result.IsIfExists; 508234353Sdim // Fall through to skip. 509234353Sdim 510234353Sdim case IEB_Skip: 511234353Sdim Braces.skipToEnd(); 512234353Sdim return false; 513234353Sdim } 514234353Sdim 515234353Sdim while (Tok.isNot(tok::eof)) { 516234353Sdim trailingComma = false; 517234353Sdim // If we know that this cannot be a designation, just parse the nested 518234353Sdim // initializer directly. 519234353Sdim ExprResult SubElt; 520234353Sdim if (MayBeDesignationStart()) 521234353Sdim SubElt = ParseInitializerWithPotentialDesignator(); 522234353Sdim else 523234353Sdim SubElt = ParseInitializer(); 524234353Sdim 525234353Sdim if (Tok.is(tok::ellipsis)) 526234353Sdim SubElt = Actions.ActOnPackExpansion(SubElt.get(), ConsumeToken()); 527234353Sdim 528234353Sdim // If we couldn't parse the subelement, bail out. 529234353Sdim if (!SubElt.isInvalid()) 530234353Sdim InitExprs.push_back(SubElt.release()); 531234353Sdim else 532234353Sdim InitExprsOk = false; 533234353Sdim 534234353Sdim if (Tok.is(tok::comma)) { 535234353Sdim ConsumeToken(); 536234353Sdim trailingComma = true; 537234353Sdim } 538234353Sdim 539234353Sdim if (Tok.is(tok::r_brace)) 540234353Sdim break; 541234353Sdim } 542234353Sdim 543234353Sdim Braces.consumeClose(); 544234353Sdim 545234353Sdim return !trailingComma; 546234353Sdim} 547