1//===--- ParseDecl.cpp - Declaration Parsing --------------------*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file implements the Declaration portions of the Parser interfaces.
10//
11//===----------------------------------------------------------------------===//
12
13#include "clang/AST/ASTContext.h"
14#include "clang/AST/DeclTemplate.h"
15#include "clang/AST/PrettyDeclStackTrace.h"
16#include "clang/Basic/AddressSpaces.h"
17#include "clang/Basic/AttributeCommonInfo.h"
18#include "clang/Basic/Attributes.h"
19#include "clang/Basic/CharInfo.h"
20#include "clang/Basic/DiagnosticParse.h"
21#include "clang/Basic/TargetInfo.h"
22#include "clang/Basic/TokenKinds.h"
23#include "clang/Parse/Parser.h"
24#include "clang/Parse/RAIIObjectsForParser.h"
25#include "clang/Sema/EnterExpressionEvaluationContext.h"
26#include "clang/Sema/Lookup.h"
27#include "clang/Sema/ParsedAttr.h"
28#include "clang/Sema/ParsedTemplate.h"
29#include "clang/Sema/Scope.h"
30#include "clang/Sema/SemaCUDA.h"
31#include "clang/Sema/SemaCodeCompletion.h"
32#include "clang/Sema/SemaObjC.h"
33#include "clang/Sema/SemaOpenMP.h"
34#include "llvm/ADT/ScopeExit.h"
35#include "llvm/ADT/SmallSet.h"
36#include "llvm/ADT/StringSwitch.h"
37#include <optional>
38
39using namespace clang;
40
41//===----------------------------------------------------------------------===//
42// C99 6.7: Declarations.
43//===----------------------------------------------------------------------===//
44
45TypeResult Parser::ParseTypeName(SourceRange *Range, DeclaratorContext Context,
46 AccessSpecifier AS, Decl **OwnedType,
47 ParsedAttributes *Attrs) {
48 DeclSpecContext DSC = getDeclSpecContextFromDeclaratorContext(Context);
49 if (DSC == DeclSpecContext::DSC_normal)
50 DSC = DeclSpecContext::DSC_type_specifier;
51
52 // Parse the common declaration-specifiers piece.
53 DeclSpec DS(AttrFactory);
54 if (Attrs)
55 DS.addAttributes(AL: *Attrs);
56 ParseSpecifierQualifierList(DS, AS, DSC);
57 if (OwnedType)
58 *OwnedType = DS.isTypeSpecOwned() ? DS.getRepAsDecl() : nullptr;
59
60 // Move declspec attributes to ParsedAttributes
61 if (Attrs) {
62 llvm::SmallVector<ParsedAttr *, 1> ToBeMoved;
63 for (ParsedAttr &AL : DS.getAttributes()) {
64 if (AL.isDeclspecAttribute())
65 ToBeMoved.push_back(Elt: &AL);
66 }
67
68 for (ParsedAttr *AL : ToBeMoved)
69 Attrs->takeOneFrom(Other&: DS.getAttributes(), PA: AL);
70 }
71
72 // Parse the abstract-declarator, if present.
73 Declarator DeclaratorInfo(DS, ParsedAttributesView::none(), Context);
74 ParseDeclarator(D&: DeclaratorInfo);
75 if (Range)
76 *Range = DeclaratorInfo.getSourceRange();
77
78 if (DeclaratorInfo.isInvalidType())
79 return true;
80
81 return Actions.ActOnTypeName(D&: DeclaratorInfo);
82}
83
84/// Normalizes an attribute name by dropping prefixed and suffixed __.
85static StringRef normalizeAttrName(StringRef Name) {
86 if (Name.size() >= 4 && Name.starts_with(Prefix: "__") && Name.ends_with(Suffix: "__"))
87 return Name.drop_front(N: 2).drop_back(N: 2);
88 return Name;
89}
90
91/// returns true iff attribute is annotated with `LateAttrParseExperimentalExt`
92/// in `Attr.td`.
93static bool IsAttributeLateParsedExperimentalExt(const IdentifierInfo &II) {
94#define CLANG_ATTR_LATE_PARSED_EXPERIMENTAL_EXT_LIST
95 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
96#include "clang/Parse/AttrParserStringSwitches.inc"
97 .Default(Value: false);
98#undef CLANG_ATTR_LATE_PARSED_EXPERIMENTAL_EXT_LIST
99}
100
101/// returns true iff attribute is annotated with `LateAttrParseStandard` in
102/// `Attr.td`.
103static bool IsAttributeLateParsedStandard(const IdentifierInfo &II) {
104#define CLANG_ATTR_LATE_PARSED_LIST
105 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
106#include "clang/Parse/AttrParserStringSwitches.inc"
107 .Default(Value: false);
108#undef CLANG_ATTR_LATE_PARSED_LIST
109}
110
111/// Such attributes need their arguments parsed inside a function prototype
112/// scope so the arguments can reference the function's parameters.
113static bool IsAttributeArgsParsedInFunctionScope(const IdentifierInfo &II) {
114#define CLANG_ATTR_PARSE_ARGS_IN_FUNCTION_SCOPE_LIST
115 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
116#include "clang/Parse/AttrParserStringSwitches.inc"
117 .Default(Value: false);
118#undef CLANG_ATTR_PARSE_ARGS_IN_FUNCTION_SCOPE_LIST
119}
120
121/// Check if the a start and end source location expand to the same macro.
122static bool FindLocsWithCommonFileID(Preprocessor &PP, SourceLocation StartLoc,
123 SourceLocation EndLoc) {
124 if (!StartLoc.isMacroID() || !EndLoc.isMacroID())
125 return false;
126
127 SourceManager &SM = PP.getSourceManager();
128 if (SM.getFileID(SpellingLoc: StartLoc) != SM.getFileID(SpellingLoc: EndLoc))
129 return false;
130
131 bool AttrStartIsInMacro =
132 Lexer::isAtStartOfMacroExpansion(loc: StartLoc, SM, LangOpts: PP.getLangOpts());
133 bool AttrEndIsInMacro =
134 Lexer::isAtEndOfMacroExpansion(loc: EndLoc, SM, LangOpts: PP.getLangOpts());
135 return AttrStartIsInMacro && AttrEndIsInMacro;
136}
137
138void Parser::ParseAttributes(unsigned WhichAttrKinds, ParsedAttributes &Attrs,
139 LateParsedAttrList *LateAttrs) {
140 bool MoreToParse;
141 do {
142 // Assume there's nothing left to parse, but if any attributes are in fact
143 // parsed, loop to ensure all specified attribute combinations are parsed.
144 MoreToParse = false;
145 if (WhichAttrKinds & PAKM_CXX11)
146 MoreToParse |= MaybeParseCXX11Attributes(Attrs);
147 if (WhichAttrKinds & PAKM_GNU)
148 MoreToParse |= MaybeParseGNUAttributes(Attrs, LateAttrs);
149 if (WhichAttrKinds & PAKM_Declspec)
150 MoreToParse |= MaybeParseMicrosoftDeclSpecs(Attrs);
151 } while (MoreToParse);
152}
153
154bool Parser::ParseSingleGNUAttribute(ParsedAttributes &Attrs,
155 SourceLocation &EndLoc,
156 LateParsedAttrList *LateAttrs,
157 Declarator *D) {
158 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
159 if (!AttrName)
160 return true;
161
162 SourceLocation AttrNameLoc = ConsumeToken();
163
164 if (Tok.isNot(K: tok::l_paren)) {
165 Attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
166 form: ParsedAttr::Form::GNU());
167 return false;
168 }
169
170 bool LateParse = false;
171 if (!LateAttrs)
172 LateParse = false;
173 else if (LateAttrs->lateAttrParseExperimentalExtOnly()) {
174 // The caller requested that this attribute **only** be late
175 // parsed for `LateAttrParseExperimentalExt` attributes. This will
176 // only be late parsed if the experimental language option is enabled.
177 LateParse = getLangOpts().ExperimentalLateParseAttributes &&
178 IsAttributeLateParsedExperimentalExt(II: *AttrName);
179 } else {
180 // The caller did not restrict late parsing to only
181 // `LateAttrParseExperimentalExt` attributes so late parse
182 // both `LateAttrParseStandard` and `LateAttrParseExperimentalExt`
183 // attributes.
184 LateParse = IsAttributeLateParsedExperimentalExt(II: *AttrName) ||
185 IsAttributeLateParsedStandard(II: *AttrName);
186 }
187
188 // Handle "parameterized" attributes
189 if (!LateParse) {
190 ParseGNUAttributeArgs(AttrName, AttrNameLoc, Attrs, EndLoc: &EndLoc, ScopeName: nullptr,
191 ScopeLoc: SourceLocation(), Form: ParsedAttr::Form::GNU(), D);
192 return false;
193 }
194
195 // Handle attributes with arguments that require late parsing.
196 LateParsedAttribute *LA =
197 new LateParsedAttribute(this, *AttrName, AttrNameLoc);
198
199 // Keep the innermost prototype's parameters available for a late-parsed
200 // attribute that is parsed in that prototype's scope, such as one describing
201 // a call through a function pointer (unlike guarded_by, which describes the
202 // pointer itself). A function keeps its own parameters in scope, so skip it;
203 // a parameter of function type is adjusted to a pointer, so keep it.
204 if (D && IsAttributeArgsParsedInFunctionScope(II: *AttrName) &&
205 (!D->isFunctionDeclarator() || D->isPrototypeContext())) {
206 for (unsigned I = 0, E = D->getNumTypeObjects(); I != E; ++I) {
207 const DeclaratorChunk &Chunk = D->getTypeObject(i: I);
208 if (Chunk.Kind != DeclaratorChunk::Function)
209 continue;
210 const DeclaratorChunk::FunctionTypeInfo &FTI = Chunk.Fun;
211 for (unsigned P = 0, NumParams = FTI.NumParams; P != NumParams; ++P)
212 if (auto *Param = dyn_cast_or_null<ParmVarDecl>(Val: FTI.Params[P].Param);
213 Param && Param->getIdentifier())
214 LA->ProtoParams.push_back(Elt: Param);
215 break;
216 }
217 }
218
219 LateAttrs->push_back(Elt: LA);
220
221 // Attributes in a class are parsed at the end of the class, along
222 // with other late-parsed declarations.
223 if (!ClassStack.empty() && !LateAttrs->parseSoon())
224 getCurrentClass().LateParsedDeclarations.push_back(Elt: LA);
225
226 // Be sure ConsumeAndStoreUntil doesn't see the start l_paren, since it
227 // recursively consumes balanced parens.
228 LA->Toks.push_back(Elt: Tok);
229 ConsumeParen();
230 // Consume everything up to and including the matching right parens.
231 ConsumeAndStoreUntil(T1: tok::r_paren, Toks&: LA->Toks, /*StopAtSemi=*/true);
232
233 Token Eof;
234 Eof.startToken();
235 Eof.setLocation(Tok.getLocation());
236 LA->Toks.push_back(Elt: Eof);
237
238 return false;
239}
240
241void Parser::ParseGNUAttributes(ParsedAttributes &Attrs,
242 LateParsedAttrList *LateAttrs, Declarator *D) {
243 assert(Tok.is(tok::kw___attribute) && "Not a GNU attribute list!");
244
245 SourceLocation StartLoc = Tok.getLocation();
246 SourceLocation EndLoc = StartLoc;
247
248 while (Tok.is(K: tok::kw___attribute)) {
249 SourceLocation AttrTokLoc = ConsumeToken();
250 unsigned OldNumAttrs = Attrs.size();
251 unsigned OldNumLateAttrs = LateAttrs ? LateAttrs->size() : 0;
252
253 if (ExpectAndConsume(ExpectedTok: tok::l_paren, Diag: diag::err_expected_lparen_after,
254 DiagMsg: "attribute")) {
255 SkipUntil(T: tok::r_paren, Flags: StopAtSemi); // skip until ) or ;
256 return;
257 }
258 if (ExpectAndConsume(ExpectedTok: tok::l_paren, Diag: diag::err_expected_lparen_after, DiagMsg: "(")) {
259 SkipUntil(T: tok::r_paren, Flags: StopAtSemi); // skip until ) or ;
260 return;
261 }
262 // Parse the attribute-list. e.g. __attribute__(( weak, alias("__f") ))
263 do {
264 // Eat preceeding commas to allow __attribute__((,,,foo))
265 while (TryConsumeToken(Expected: tok::comma))
266 ;
267
268 // Expect an identifier or declaration specifier (const, int, etc.)
269 if (Tok.isAnnotation())
270 break;
271 if (Tok.is(K: tok::code_completion)) {
272 cutOffParsing();
273 Actions.CodeCompletion().CodeCompleteAttribute(
274 Syntax: AttributeCommonInfo::Syntax::AS_GNU);
275 break;
276 }
277
278 if (ParseSingleGNUAttribute(Attrs, EndLoc, LateAttrs, D))
279 break;
280 } while (Tok.is(K: tok::comma));
281
282 if (ExpectAndConsume(ExpectedTok: tok::r_paren))
283 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
284 SourceLocation Loc = Tok.getLocation();
285 if (ExpectAndConsume(ExpectedTok: tok::r_paren))
286 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
287 EndLoc = Loc;
288
289 // If this was declared in a macro, attach the macro IdentifierInfo to the
290 // parsed attribute.
291 auto &SM = PP.getSourceManager();
292 if (!SM.isWrittenInBuiltinFile(Loc: SM.getSpellingLoc(Loc: AttrTokLoc)) &&
293 FindLocsWithCommonFileID(PP, StartLoc: AttrTokLoc, EndLoc: Loc)) {
294 CharSourceRange ExpansionRange = SM.getExpansionRange(Loc: AttrTokLoc);
295 StringRef FoundName =
296 Lexer::getSourceText(Range: ExpansionRange, SM, LangOpts: PP.getLangOpts());
297 IdentifierInfo *MacroII = PP.getIdentifierInfo(Name: FoundName);
298
299 for (unsigned i = OldNumAttrs; i < Attrs.size(); ++i)
300 Attrs[i].setMacroIdentifier(MacroName: MacroII, Loc: ExpansionRange.getBegin());
301
302 if (LateAttrs) {
303 for (unsigned i = OldNumLateAttrs; i < LateAttrs->size(); ++i)
304 (*LateAttrs)[i]->MacroII = MacroII;
305 }
306 }
307 }
308
309 Attrs.Range = SourceRange(StartLoc, EndLoc);
310}
311
312/// Determine whether the given attribute has an identifier argument.
313static bool attributeHasIdentifierArg(const llvm::Triple &T,
314 const IdentifierInfo &II,
315 ParsedAttr::Syntax Syntax,
316 IdentifierInfo *ScopeName) {
317#define CLANG_ATTR_IDENTIFIER_ARG_LIST
318 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
319#include "clang/Parse/AttrParserStringSwitches.inc"
320 .Default(Value: false);
321#undef CLANG_ATTR_IDENTIFIER_ARG_LIST
322}
323
324/// Determine whether the given attribute has string arguments.
325static ParsedAttributeArgumentsProperties
326attributeStringLiteralListArg(const llvm::Triple &T, const IdentifierInfo &II,
327 ParsedAttr::Syntax Syntax,
328 IdentifierInfo *ScopeName) {
329#define CLANG_ATTR_STRING_LITERAL_ARG_LIST
330 return llvm::StringSwitch<uint32_t>(normalizeAttrName(Name: II.getName()))
331#include "clang/Parse/AttrParserStringSwitches.inc"
332 .Default(Value: 0);
333#undef CLANG_ATTR_STRING_LITERAL_ARG_LIST
334}
335
336/// Determine whether the given attribute has a variadic identifier argument.
337static bool attributeHasVariadicIdentifierArg(const IdentifierInfo &II,
338 ParsedAttr::Syntax Syntax,
339 IdentifierInfo *ScopeName) {
340#define CLANG_ATTR_VARIADIC_IDENTIFIER_ARG_LIST
341 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
342#include "clang/Parse/AttrParserStringSwitches.inc"
343 .Default(Value: false);
344#undef CLANG_ATTR_VARIADIC_IDENTIFIER_ARG_LIST
345}
346
347/// Determine whether the given attribute treats kw_this as an identifier.
348static bool attributeTreatsKeywordThisAsIdentifier(const IdentifierInfo &II,
349 ParsedAttr::Syntax Syntax,
350 IdentifierInfo *ScopeName) {
351#define CLANG_ATTR_THIS_ISA_IDENTIFIER_ARG_LIST
352 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
353#include "clang/Parse/AttrParserStringSwitches.inc"
354 .Default(Value: false);
355#undef CLANG_ATTR_THIS_ISA_IDENTIFIER_ARG_LIST
356}
357
358/// Determine if an attribute accepts parameter packs.
359static bool attributeAcceptsExprPack(const IdentifierInfo &II,
360 ParsedAttr::Syntax Syntax,
361 IdentifierInfo *ScopeName) {
362#define CLANG_ATTR_ACCEPTS_EXPR_PACK
363 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
364#include "clang/Parse/AttrParserStringSwitches.inc"
365 .Default(Value: false);
366#undef CLANG_ATTR_ACCEPTS_EXPR_PACK
367}
368
369/// Determine whether the given attribute parses a type argument.
370static bool attributeIsTypeArgAttr(const IdentifierInfo &II,
371 ParsedAttr::Syntax Syntax,
372 IdentifierInfo *ScopeName) {
373#define CLANG_ATTR_TYPE_ARG_LIST
374 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
375#include "clang/Parse/AttrParserStringSwitches.inc"
376 .Default(Value: false);
377#undef CLANG_ATTR_TYPE_ARG_LIST
378}
379
380/// Determine whether the given attribute takes a strict identifier argument.
381static bool attributeHasStrictIdentifierArgs(const IdentifierInfo &II,
382 ParsedAttr::Syntax Syntax,
383 IdentifierInfo *ScopeName) {
384#define CLANG_ATTR_STRICT_IDENTIFIER_ARG_LIST
385 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
386#include "clang/Parse/AttrParserStringSwitches.inc"
387 .Default(Value: false);
388#undef CLANG_ATTR_STRICT_IDENTIFIER_ARG_LIST
389}
390
391/// Determine whether the given attribute requires parsing its arguments
392/// in an unevaluated context or not.
393static bool attributeParsedArgsUnevaluated(const IdentifierInfo &II,
394 ParsedAttr::Syntax Syntax,
395 IdentifierInfo *ScopeName) {
396#define CLANG_ATTR_ARG_CONTEXT_LIST
397 return llvm::StringSwitch<bool>(normalizeAttrName(Name: II.getName()))
398#include "clang/Parse/AttrParserStringSwitches.inc"
399 .Default(Value: false);
400#undef CLANG_ATTR_ARG_CONTEXT_LIST
401}
402
403IdentifierLoc *Parser::ParseIdentifierLoc() {
404 assert(Tok.is(tok::identifier) && "expected an identifier");
405 IdentifierLoc *IL = new (Actions.Context)
406 IdentifierLoc(Tok.getLocation(), Tok.getIdentifierInfo());
407 ConsumeToken();
408 return IL;
409}
410
411void Parser::ParseAttributeWithTypeArg(IdentifierInfo &AttrName,
412 SourceLocation AttrNameLoc,
413 ParsedAttributes &Attrs,
414 IdentifierInfo *ScopeName,
415 SourceLocation ScopeLoc,
416 ParsedAttr::Form Form) {
417 BalancedDelimiterTracker Parens(*this, tok::l_paren);
418 Parens.consumeOpen();
419
420 TypeResult T;
421 if (Tok.isNot(K: tok::r_paren))
422 T = ParseTypeName();
423
424 if (Parens.consumeClose())
425 return;
426
427 if (T.isInvalid())
428 return;
429
430 if (T.isUsable())
431 Attrs.addNewTypeAttr(
432 attrName: &AttrName, attrRange: SourceRange(AttrNameLoc, Parens.getCloseLocation()),
433 scope: AttributeScopeInfo(ScopeName, ScopeLoc), typeArg: T.get(), formUsed: Form);
434 else
435 Attrs.addNew(attrName: &AttrName, attrRange: SourceRange(AttrNameLoc, Parens.getCloseLocation()),
436 scope: AttributeScopeInfo(ScopeName, ScopeLoc), args: nullptr, numArgs: 0, form: Form);
437}
438
439ExprResult
440Parser::ParseUnevaluatedStringInAttribute(const IdentifierInfo &AttrName) {
441 if (Tok.is(K: tok::l_paren)) {
442 BalancedDelimiterTracker Paren(*this, tok::l_paren);
443 Paren.consumeOpen();
444 ExprResult Res = ParseUnevaluatedStringInAttribute(AttrName);
445 Paren.consumeClose();
446 return Res;
447 }
448 if (!isTokenStringLiteral()) {
449 Diag(Loc: Tok.getLocation(), DiagID: diag::err_expected_string_literal)
450 << /*in attribute...*/ 4 << AttrName.getName();
451 return ExprError();
452 }
453 return ParseUnevaluatedStringLiteralExpression();
454}
455
456bool Parser::ParseAttributeArgumentList(
457 const IdentifierInfo &AttrName, SmallVectorImpl<Expr *> &Exprs,
458 ParsedAttributeArgumentsProperties ArgsProperties, unsigned Arg) {
459 bool SawError = false;
460 while (true) {
461 ExprResult Expr;
462 if (ArgsProperties.isStringLiteralArg(I: Arg)) {
463 Expr = ParseUnevaluatedStringInAttribute(AttrName);
464 } else if (getLangOpts().CPlusPlus11 && Tok.is(K: tok::l_brace)) {
465 Diag(Tok, DiagID: diag::compat_cxx11_generalized_initializer_lists);
466 Expr = ParseBraceInitializer();
467 } else {
468 Expr = ParseAssignmentExpression();
469 }
470
471 if (Tok.is(K: tok::ellipsis))
472 Expr = Actions.ActOnPackExpansion(Pattern: Expr.get(), EllipsisLoc: ConsumeToken());
473 else if (Tok.is(K: tok::code_completion)) {
474 // There's nothing to suggest in here as we parsed a full expression.
475 // Instead fail and propagate the error since caller might have something
476 // the suggest, e.g. signature help in function call. Note that this is
477 // performed before pushing the \p Expr, so that signature help can report
478 // current argument correctly.
479 SawError = true;
480 cutOffParsing();
481 break;
482 }
483
484 if (Expr.isInvalid()) {
485 SawError = true;
486 break;
487 }
488
489 if (Actions.DiagnoseUnexpandedParameterPack(E: Expr.get())) {
490 SawError = true;
491 break;
492 }
493
494 Exprs.push_back(Elt: Expr.get());
495
496 if (Tok.isNot(K: tok::comma))
497 break;
498 // Move to the next argument, remember where the comma was.
499 Token Comma = Tok;
500 ConsumeToken();
501 checkPotentialAngleBracketDelimiter(OpToken: Comma);
502 Arg++;
503 }
504
505 return SawError;
506}
507
508unsigned Parser::ParseAttributeArgsCommon(
509 IdentifierInfo *AttrName, SourceLocation AttrNameLoc,
510 ParsedAttributes &Attrs, SourceLocation *EndLoc, IdentifierInfo *ScopeName,
511 SourceLocation ScopeLoc, ParsedAttr::Form Form) {
512 // Ignore the left paren location for now.
513 ConsumeParen();
514
515 bool ChangeKWThisToIdent = attributeTreatsKeywordThisAsIdentifier(
516 II: *AttrName, Syntax: Form.getSyntax(), ScopeName);
517 bool AttributeIsTypeArgAttr =
518 attributeIsTypeArgAttr(II: *AttrName, Syntax: Form.getSyntax(), ScopeName);
519 bool AttributeHasVariadicIdentifierArg =
520 attributeHasVariadicIdentifierArg(II: *AttrName, Syntax: Form.getSyntax(), ScopeName);
521
522 // Interpret "kw_this" as an identifier if the attributed requests it.
523 if (ChangeKWThisToIdent && Tok.is(K: tok::kw_this))
524 Tok.setKind(tok::identifier);
525
526 ArgsVector ArgExprs;
527 if (Tok.is(K: tok::identifier)) {
528 // If this attribute wants an 'identifier' argument, make it so.
529 bool IsIdentifierArg =
530 AttributeHasVariadicIdentifierArg ||
531 attributeHasIdentifierArg(T: getTargetInfo().getTriple(), II: *AttrName,
532 Syntax: Form.getSyntax(), ScopeName);
533 ParsedAttr::Kind AttrKind =
534 ParsedAttr::getParsedKind(Name: AttrName, Scope: ScopeName, SyntaxUsed: Form.getSyntax());
535
536 // If we don't know how to parse this attribute, but this is the only
537 // token in this argument, assume it's meant to be an identifier.
538 if (AttrKind == ParsedAttr::UnknownAttribute ||
539 AttrKind == ParsedAttr::IgnoredAttribute) {
540 const Token &Next = NextToken();
541 IsIdentifierArg = Next.isOneOf(Ks: tok::r_paren, Ks: tok::comma);
542 }
543
544 if (IsIdentifierArg)
545 ArgExprs.push_back(Elt: ParseIdentifierLoc());
546 }
547
548 ParsedType TheParsedType;
549 if (!ArgExprs.empty() ? Tok.is(K: tok::comma) : Tok.isNot(K: tok::r_paren)) {
550 // Eat the comma.
551 if (!ArgExprs.empty())
552 ConsumeToken();
553
554 if (AttributeIsTypeArgAttr) {
555 // FIXME: Multiple type arguments are not implemented.
556 TypeResult T = ParseTypeName();
557 if (T.isInvalid()) {
558 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
559 return 0;
560 }
561 if (T.isUsable())
562 TheParsedType = T.get();
563 } else if (AttributeHasVariadicIdentifierArg ||
564 attributeHasStrictIdentifierArgs(II: *AttrName, Syntax: Form.getSyntax(),
565 ScopeName)) {
566 // Parse variadic identifier arg. This can either consume identifiers or
567 // expressions. Variadic identifier args do not support parameter packs
568 // because those are typically used for attributes with enumeration
569 // arguments, and those enumerations are not something the user could
570 // express via a pack.
571 do {
572 // Interpret "kw_this" as an identifier if the attributed requests it.
573 if (ChangeKWThisToIdent && Tok.is(K: tok::kw_this))
574 Tok.setKind(tok::identifier);
575
576 ExprResult ArgExpr;
577 if (Tok.is(K: tok::identifier)) {
578 ArgExprs.push_back(Elt: ParseIdentifierLoc());
579 } else {
580 bool Uneval = attributeParsedArgsUnevaluated(
581 II: *AttrName, Syntax: Form.getSyntax(), ScopeName);
582 EnterExpressionEvaluationContext Unevaluated(
583 Actions,
584 Uneval ? Sema::ExpressionEvaluationContext::Unevaluated
585 : Sema::ExpressionEvaluationContext::ConstantEvaluated,
586 nullptr,
587 Sema::ExpressionEvaluationContextRecord::EK_AttrArgument);
588
589 ExprResult ArgExpr = ParseAssignmentExpression();
590 if (ArgExpr.isInvalid()) {
591 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
592 return 0;
593 }
594 ArgExprs.push_back(Elt: ArgExpr.get());
595 }
596 // Eat the comma, move to the next argument
597 } while (TryConsumeToken(Expected: tok::comma));
598 } else {
599 // General case. Parse all available expressions.
600 bool Uneval = attributeParsedArgsUnevaluated(II: *AttrName, Syntax: Form.getSyntax(),
601 ScopeName);
602 EnterExpressionEvaluationContext Unevaluated(
603 Actions,
604 Uneval ? Sema::ExpressionEvaluationContext::Unevaluated
605 : Sema::ExpressionEvaluationContext::ConstantEvaluated,
606 nullptr,
607 Sema::ExpressionEvaluationContextRecord::ExpressionKind::
608 EK_AttrArgument);
609
610 ExprVector ParsedExprs;
611 ParsedAttributeArgumentsProperties ArgProperties =
612 attributeStringLiteralListArg(T: getTargetInfo().getTriple(), II: *AttrName,
613 Syntax: Form.getSyntax(), ScopeName);
614 if (ParseAttributeArgumentList(AttrName: *AttrName, Exprs&: ParsedExprs, ArgsProperties: ArgProperties,
615 Arg: ArgExprs.size())) {
616 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
617 return 0;
618 }
619
620 // Pack expansion must currently be explicitly supported by an attribute.
621 for (size_t I = 0; I < ParsedExprs.size(); ++I) {
622 if (!isa<PackExpansionExpr>(Val: ParsedExprs[I]))
623 continue;
624
625 if (!attributeAcceptsExprPack(II: *AttrName, Syntax: Form.getSyntax(), ScopeName)) {
626 Diag(Loc: Tok.getLocation(),
627 DiagID: diag::err_attribute_argument_parm_pack_not_supported)
628 << AttrName;
629 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
630 return 0;
631 }
632 }
633
634 llvm::append_range(C&: ArgExprs, R&: ParsedExprs);
635 }
636 }
637
638 SourceLocation RParen = Tok.getLocation();
639 if (!ExpectAndConsume(ExpectedTok: tok::r_paren)) {
640 SourceLocation AttrLoc = ScopeLoc.isValid() ? ScopeLoc : AttrNameLoc;
641
642 if (AttributeIsTypeArgAttr && !TheParsedType.get().isNull()) {
643 Attrs.addNewTypeAttr(attrName: AttrName, attrRange: SourceRange(AttrNameLoc, RParen),
644 scope: AttributeScopeInfo(ScopeName, ScopeLoc),
645 typeArg: TheParsedType, formUsed: Form);
646 } else {
647 Attrs.addNew(attrName: AttrName, attrRange: SourceRange(AttrLoc, RParen),
648 scope: AttributeScopeInfo(ScopeName, ScopeLoc), args: ArgExprs.data(),
649 numArgs: ArgExprs.size(), form: Form);
650 }
651 }
652
653 if (EndLoc)
654 *EndLoc = RParen;
655
656 return static_cast<unsigned>(ArgExprs.size() + !TheParsedType.get().isNull());
657}
658
659void Parser::ParseGNUAttributeArgs(
660 IdentifierInfo *AttrName, SourceLocation AttrNameLoc,
661 ParsedAttributes &Attrs, SourceLocation *EndLoc, IdentifierInfo *ScopeName,
662 SourceLocation ScopeLoc, ParsedAttr::Form Form, Declarator *D) {
663
664 assert(Tok.is(tok::l_paren) && "Attribute arg list not starting with '('");
665
666 ParsedAttr::Kind AttrKind =
667 ParsedAttr::getParsedKind(Name: AttrName, Scope: ScopeName, SyntaxUsed: Form.getSyntax());
668
669 if (AttrKind == ParsedAttr::AT_Availability) {
670 ParseAvailabilityAttribute(Availability&: *AttrName, AvailabilityLoc: AttrNameLoc, attrs&: Attrs, endLoc: EndLoc, ScopeName,
671 ScopeLoc, Form);
672 return;
673 } else if (AttrKind == ParsedAttr::AT_ExternalSourceSymbol) {
674 ParseExternalSourceSymbolAttribute(ExternalSourceSymbol&: *AttrName, Loc: AttrNameLoc, Attrs, EndLoc,
675 ScopeName, ScopeLoc, Form);
676 return;
677 } else if (AttrKind == ParsedAttr::AT_ObjCBridgeRelated) {
678 ParseObjCBridgeRelatedAttribute(ObjCBridgeRelated&: *AttrName, ObjCBridgeRelatedLoc: AttrNameLoc, Attrs, EndLoc,
679 ScopeName, ScopeLoc, Form);
680 return;
681 } else if (AttrKind == ParsedAttr::AT_SwiftNewType) {
682 ParseSwiftNewTypeAttribute(AttrName&: *AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName,
683 ScopeLoc, Form);
684 return;
685 } else if (AttrKind == ParsedAttr::AT_TypeTagForDatatype) {
686 ParseTypeTagForDatatypeAttribute(AttrName&: *AttrName, AttrNameLoc, Attrs, EndLoc,
687 ScopeName, ScopeLoc, Form);
688 return;
689 } else if (attributeIsTypeArgAttr(II: *AttrName, Syntax: Form.getSyntax(), ScopeName)) {
690 ParseAttributeWithTypeArg(AttrName&: *AttrName, AttrNameLoc, Attrs, ScopeName,
691 ScopeLoc, Form);
692 return;
693 } else if (AttrKind == ParsedAttr::AT_CountedBy ||
694 AttrKind == ParsedAttr::AT_CountedByOrNull ||
695 AttrKind == ParsedAttr::AT_SizedBy ||
696 AttrKind == ParsedAttr::AT_SizedByOrNull) {
697 ParseBoundsAttribute(AttrName&: *AttrName, AttrNameLoc, Attrs, ScopeName, ScopeLoc,
698 Form);
699 return;
700 } else if (AttrKind == ParsedAttr::AT_CXXAssume) {
701 ParseCXXAssumeAttributeArg(Attrs, AttrName, AttrNameLoc, ScopeName,
702 ScopeLoc, EndLoc, Form);
703 return;
704 }
705
706 // These may refer to the function arguments, but need to be parsed early to
707 // participate in determining whether it's a redeclaration.
708 std::optional<ParseScope> PrototypeScope;
709 if (D && IsAttributeArgsParsedInFunctionScope(II: *AttrName)) {
710 // Find the innermost function chunk to make its parameters available for
711 // attribute argument parsing. This is necessary for attributes like thread
712 // safety annotations on function pointers which reference their parameters.
713 const DeclaratorChunk::FunctionTypeInfo *FTI = nullptr;
714 for (unsigned i = 0; i < D->getNumTypeObjects(); ++i) {
715 if (D->getTypeObject(i).Kind == DeclaratorChunk::Function) {
716 FTI = &D->getTypeObject(i).Fun;
717 break;
718 }
719 }
720
721 if (FTI) {
722 // Inherit the class scope flag from the current context. This is safe
723 // because it only preserves existing struct/class visibility, which is
724 // required for attributes to resolve sibling members in C structs.
725 PrototypeScope.emplace(
726 args: this, args: Scope::FunctionPrototypeScope |
727 Scope::FunctionDeclarationScope | Scope::DeclScope |
728 (getCurScope()->getFlags() & Scope::ClassScope));
729 for (unsigned i = 0; i < FTI->NumParams; ++i)
730 Actions.ActOnReenterCXXMethodParameter(
731 S: getCurScope(), Param: dyn_cast_or_null<ParmVarDecl>(Val: FTI->Params[i].Param));
732 }
733 }
734
735 ParseAttributeArgsCommon(AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName,
736 ScopeLoc, Form);
737}
738
739unsigned Parser::ParseClangAttributeArgs(
740 IdentifierInfo *AttrName, SourceLocation AttrNameLoc,
741 ParsedAttributes &Attrs, SourceLocation *EndLoc, IdentifierInfo *ScopeName,
742 SourceLocation ScopeLoc, ParsedAttr::Form Form) {
743 assert(Tok.is(tok::l_paren) && "Attribute arg list not starting with '('");
744
745 ParsedAttr::Kind AttrKind =
746 ParsedAttr::getParsedKind(Name: AttrName, Scope: ScopeName, SyntaxUsed: Form.getSyntax());
747
748 switch (AttrKind) {
749 default:
750 return ParseAttributeArgsCommon(AttrName, AttrNameLoc, Attrs, EndLoc,
751 ScopeName, ScopeLoc, Form);
752 case ParsedAttr::AT_ExternalSourceSymbol:
753 ParseExternalSourceSymbolAttribute(ExternalSourceSymbol&: *AttrName, Loc: AttrNameLoc, Attrs, EndLoc,
754 ScopeName, ScopeLoc, Form);
755 break;
756 case ParsedAttr::AT_Availability:
757 ParseAvailabilityAttribute(Availability&: *AttrName, AvailabilityLoc: AttrNameLoc, attrs&: Attrs, endLoc: EndLoc, ScopeName,
758 ScopeLoc, Form);
759 break;
760 case ParsedAttr::AT_ObjCBridgeRelated:
761 ParseObjCBridgeRelatedAttribute(ObjCBridgeRelated&: *AttrName, ObjCBridgeRelatedLoc: AttrNameLoc, Attrs, EndLoc,
762 ScopeName, ScopeLoc, Form);
763 break;
764 case ParsedAttr::AT_SwiftNewType:
765 ParseSwiftNewTypeAttribute(AttrName&: *AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName,
766 ScopeLoc, Form);
767 break;
768 case ParsedAttr::AT_TypeTagForDatatype:
769 ParseTypeTagForDatatypeAttribute(AttrName&: *AttrName, AttrNameLoc, Attrs, EndLoc,
770 ScopeName, ScopeLoc, Form);
771 break;
772
773 case ParsedAttr::AT_CXXAssume:
774 ParseCXXAssumeAttributeArg(Attrs, AttrName, AttrNameLoc, ScopeName,
775 ScopeLoc, EndLoc, Form);
776 break;
777 }
778 return !Attrs.empty() ? Attrs.begin()->getNumArgs() : 0;
779}
780
781bool Parser::ParseMicrosoftDeclSpecArgs(IdentifierInfo *AttrName,
782 SourceLocation AttrNameLoc,
783 ParsedAttributes &Attrs) {
784 unsigned ExistingAttrs = Attrs.size();
785
786 // If the attribute isn't known, we will not attempt to parse any
787 // arguments.
788 if (!hasAttribute(Syntax: AttributeCommonInfo::Syntax::AS_Declspec, Scope: nullptr, Attr: AttrName,
789 Target: getTargetInfo(), LangOpts: getLangOpts())) {
790 // Eat the left paren, then skip to the ending right paren.
791 ConsumeParen();
792 SkipUntil(T: tok::r_paren);
793 return false;
794 }
795
796 SourceLocation OpenParenLoc = Tok.getLocation();
797
798 if (AttrName->getName() == "property") {
799 // The property declspec is more complex in that it can take one or two
800 // assignment expressions as a parameter, but the lhs of the assignment
801 // must be named get or put.
802
803 BalancedDelimiterTracker T(*this, tok::l_paren);
804 T.expectAndConsume(DiagID: diag::err_expected_lparen_after,
805 Msg: AttrName->getNameStart(), SkipToTok: tok::r_paren);
806
807 enum AccessorKind {
808 AK_Invalid = -1,
809 AK_Put = 0,
810 AK_Get = 1 // indices into AccessorNames
811 };
812 IdentifierInfo *AccessorNames[] = {nullptr, nullptr};
813 bool HasInvalidAccessor = false;
814
815 // Parse the accessor specifications.
816 while (true) {
817 // Stop if this doesn't look like an accessor spec.
818 if (!Tok.is(K: tok::identifier)) {
819 // If the user wrote a completely empty list, use a special diagnostic.
820 if (Tok.is(K: tok::r_paren) && !HasInvalidAccessor &&
821 AccessorNames[AK_Put] == nullptr &&
822 AccessorNames[AK_Get] == nullptr) {
823 Diag(Loc: AttrNameLoc, DiagID: diag::err_ms_property_no_getter_or_putter);
824 break;
825 }
826
827 Diag(Loc: Tok.getLocation(), DiagID: diag::err_ms_property_unknown_accessor);
828 break;
829 }
830
831 AccessorKind Kind;
832 SourceLocation KindLoc = Tok.getLocation();
833 StringRef KindStr = Tok.getIdentifierInfo()->getName();
834 if (KindStr == "get") {
835 Kind = AK_Get;
836 } else if (KindStr == "put") {
837 Kind = AK_Put;
838
839 // Recover from the common mistake of using 'set' instead of 'put'.
840 } else if (KindStr == "set") {
841 Diag(Loc: KindLoc, DiagID: diag::err_ms_property_has_set_accessor)
842 << FixItHint::CreateReplacement(RemoveRange: KindLoc, Code: "put");
843 Kind = AK_Put;
844
845 // Handle the mistake of forgetting the accessor kind by skipping
846 // this accessor.
847 } else if (NextToken().is(K: tok::comma) || NextToken().is(K: tok::r_paren)) {
848 Diag(Loc: KindLoc, DiagID: diag::err_ms_property_missing_accessor_kind);
849 ConsumeToken();
850 HasInvalidAccessor = true;
851 goto next_property_accessor;
852
853 // Otherwise, complain about the unknown accessor kind.
854 } else {
855 Diag(Loc: KindLoc, DiagID: diag::err_ms_property_unknown_accessor);
856 HasInvalidAccessor = true;
857 Kind = AK_Invalid;
858
859 // Try to keep parsing unless it doesn't look like an accessor spec.
860 if (!NextToken().is(K: tok::equal))
861 break;
862 }
863
864 // Consume the identifier.
865 ConsumeToken();
866
867 // Consume the '='.
868 if (!TryConsumeToken(Expected: tok::equal)) {
869 Diag(Loc: Tok.getLocation(), DiagID: diag::err_ms_property_expected_equal)
870 << KindStr;
871 break;
872 }
873
874 // Expect the method name.
875 if (!Tok.is(K: tok::identifier)) {
876 Diag(Loc: Tok.getLocation(), DiagID: diag::err_ms_property_expected_accessor_name);
877 break;
878 }
879
880 if (Kind == AK_Invalid) {
881 // Just drop invalid accessors.
882 } else if (AccessorNames[Kind] != nullptr) {
883 // Complain about the repeated accessor, ignore it, and keep parsing.
884 Diag(Loc: KindLoc, DiagID: diag::err_ms_property_duplicate_accessor) << KindStr;
885 } else {
886 AccessorNames[Kind] = Tok.getIdentifierInfo();
887 }
888 ConsumeToken();
889
890 next_property_accessor:
891 // Keep processing accessors until we run out.
892 if (TryConsumeToken(Expected: tok::comma))
893 continue;
894
895 // If we run into the ')', stop without consuming it.
896 if (Tok.is(K: tok::r_paren))
897 break;
898
899 Diag(Loc: Tok.getLocation(), DiagID: diag::err_ms_property_expected_comma_or_rparen);
900 break;
901 }
902
903 // Only add the property attribute if it was well-formed.
904 if (!HasInvalidAccessor)
905 Attrs.addNewPropertyAttr(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(),
906 getterId: AccessorNames[AK_Get], setterId: AccessorNames[AK_Put],
907 formUsed: ParsedAttr::Form::Declspec());
908 T.skipToEnd();
909 return !HasInvalidAccessor;
910 }
911
912 unsigned NumArgs =
913 ParseAttributeArgsCommon(AttrName, AttrNameLoc, Attrs, EndLoc: nullptr, ScopeName: nullptr,
914 ScopeLoc: SourceLocation(), Form: ParsedAttr::Form::Declspec());
915
916 // If this attribute's args were parsed, and it was expected to have
917 // arguments but none were provided, emit a diagnostic.
918 if (ExistingAttrs < Attrs.size() && Attrs.back().getMaxArgs() && !NumArgs) {
919 Diag(Loc: OpenParenLoc, DiagID: diag::err_attribute_requires_arguments) << AttrName;
920 return false;
921 }
922 return true;
923}
924
925void Parser::ParseMicrosoftDeclSpecs(ParsedAttributes &Attrs) {
926 assert(getLangOpts().DeclSpecKeyword && "__declspec keyword is not enabled");
927 assert(Tok.is(tok::kw___declspec) && "Not a declspec!");
928
929 SourceLocation StartLoc = Tok.getLocation();
930 SourceLocation EndLoc = StartLoc;
931
932 while (Tok.is(K: tok::kw___declspec)) {
933 ConsumeToken();
934 BalancedDelimiterTracker T(*this, tok::l_paren);
935 if (T.expectAndConsume(DiagID: diag::err_expected_lparen_after, Msg: "__declspec",
936 SkipToTok: tok::r_paren))
937 return;
938
939 // An empty declspec is perfectly legal and should not warn. Additionally,
940 // you can specify multiple attributes per declspec.
941 while (Tok.isNot(K: tok::r_paren)) {
942 // Attribute not present.
943 if (TryConsumeToken(Expected: tok::comma))
944 continue;
945
946 if (Tok.is(K: tok::code_completion)) {
947 cutOffParsing();
948 Actions.CodeCompletion().CodeCompleteAttribute(
949 Syntax: AttributeCommonInfo::AS_Declspec);
950 return;
951 }
952
953 // We expect either a well-known identifier or a generic string. Anything
954 // else is a malformed declspec.
955 bool IsString = Tok.getKind() == tok::string_literal;
956 if (!IsString && Tok.getKind() != tok::identifier &&
957 Tok.getKind() != tok::kw_restrict) {
958 Diag(Tok, DiagID: diag::err_ms_declspec_type);
959 T.skipToEnd();
960 return;
961 }
962
963 IdentifierInfo *AttrName;
964 SourceLocation AttrNameLoc;
965 if (IsString) {
966 SmallString<8> StrBuffer;
967 bool Invalid = false;
968 StringRef Str = PP.getSpelling(Tok, Buffer&: StrBuffer, Invalid: &Invalid);
969 if (Invalid) {
970 T.skipToEnd();
971 return;
972 }
973 AttrName = PP.getIdentifierInfo(Name: Str);
974 AttrNameLoc = ConsumeStringToken();
975 } else {
976 AttrName = Tok.getIdentifierInfo();
977 AttrNameLoc = ConsumeToken();
978 }
979
980 bool AttrHandled = false;
981
982 // Parse attribute arguments.
983 if (Tok.is(K: tok::l_paren))
984 AttrHandled = ParseMicrosoftDeclSpecArgs(AttrName, AttrNameLoc, Attrs);
985 else if (AttrName->getName() == "property")
986 // The property attribute must have an argument list.
987 Diag(Loc: Tok.getLocation(), DiagID: diag::err_expected_lparen_after)
988 << AttrName->getName();
989
990 if (!AttrHandled)
991 Attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
992 form: ParsedAttr::Form::Declspec());
993 }
994 T.consumeClose();
995 EndLoc = T.getCloseLocation();
996 }
997
998 Attrs.Range = SourceRange(StartLoc, EndLoc);
999}
1000
1001void Parser::ParseMicrosoftTypeAttributes(ParsedAttributes &attrs) {
1002 // Treat these like attributes
1003 while (true) {
1004 auto Kind = Tok.getKind();
1005 switch (Kind) {
1006 case tok::kw___fastcall:
1007 case tok::kw___stdcall:
1008 case tok::kw___thiscall:
1009 case tok::kw___regcall:
1010 case tok::kw___cdecl:
1011 case tok::kw___vectorcall:
1012 case tok::kw___ptr64:
1013 case tok::kw___w64:
1014 case tok::kw___ptr32:
1015 case tok::kw___sptr:
1016 case tok::kw___uptr: {
1017 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
1018 SourceLocation AttrNameLoc = ConsumeToken();
1019 attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
1020 form: Kind);
1021 break;
1022 }
1023 default:
1024 return;
1025 }
1026 }
1027}
1028
1029void Parser::ParseWebAssemblyFuncrefTypeAttribute(ParsedAttributes &attrs) {
1030 assert(Tok.is(tok::kw___funcref));
1031 SourceLocation StartLoc = Tok.getLocation();
1032 if (!getTargetInfo().getTriple().isWasm()) {
1033 ConsumeToken();
1034 Diag(Loc: StartLoc, DiagID: diag::err_wasm_funcref_not_wasm);
1035 return;
1036 }
1037
1038 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
1039 SourceLocation AttrNameLoc = ConsumeToken();
1040 attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), /*Args=*/args: nullptr,
1041 /*numArgs=*/0, form: tok::kw___funcref);
1042}
1043
1044void Parser::DiagnoseAndSkipExtendedMicrosoftTypeAttributes() {
1045 SourceLocation StartLoc = Tok.getLocation();
1046 SourceLocation EndLoc = SkipExtendedMicrosoftTypeAttributes();
1047
1048 if (EndLoc.isValid()) {
1049 SourceRange Range(StartLoc, EndLoc);
1050 Diag(Loc: StartLoc, DiagID: diag::warn_microsoft_qualifiers_ignored) << Range;
1051 }
1052}
1053
1054SourceLocation Parser::SkipExtendedMicrosoftTypeAttributes() {
1055 SourceLocation EndLoc;
1056
1057 while (true) {
1058 switch (Tok.getKind()) {
1059 case tok::kw_const:
1060 case tok::kw_volatile:
1061 case tok::kw___fastcall:
1062 case tok::kw___stdcall:
1063 case tok::kw___thiscall:
1064 case tok::kw___cdecl:
1065 case tok::kw___vectorcall:
1066 case tok::kw___ptr32:
1067 case tok::kw___ptr64:
1068 case tok::kw___w64:
1069 case tok::kw___unaligned:
1070 case tok::kw___sptr:
1071 case tok::kw___uptr:
1072 EndLoc = ConsumeToken();
1073 break;
1074 default:
1075 return EndLoc;
1076 }
1077 }
1078}
1079
1080void Parser::ParseBorlandTypeAttributes(ParsedAttributes &attrs) {
1081 // Treat these like attributes
1082 while (Tok.is(K: tok::kw___pascal)) {
1083 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
1084 SourceLocation AttrNameLoc = ConsumeToken();
1085 attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
1086 form: tok::kw___pascal);
1087 }
1088}
1089
1090void Parser::ParseOpenCLKernelAttributes(ParsedAttributes &attrs) {
1091 // Treat these like attributes
1092 while (Tok.is(K: tok::kw___kernel)) {
1093 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
1094 SourceLocation AttrNameLoc = ConsumeToken();
1095 attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
1096 form: tok::kw___kernel);
1097 }
1098}
1099
1100void Parser::ParseCUDAFunctionAttributes(ParsedAttributes &attrs) {
1101 while (Tok.is(K: tok::kw___noinline__)) {
1102 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
1103 SourceLocation AttrNameLoc = ConsumeToken();
1104 attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
1105 form: tok::kw___noinline__);
1106 }
1107}
1108
1109void Parser::ParseOpenCLQualifiers(ParsedAttributes &Attrs) {
1110 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
1111 SourceLocation AttrNameLoc = Tok.getLocation();
1112 Attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
1113 form: Tok.getKind());
1114}
1115
1116void Parser::ParseHLSLQualifiers(ParsedAttributes &Attrs) {
1117 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
1118 auto Kind = Tok.getKind();
1119 SourceLocation AttrNameLoc = ConsumeToken();
1120 Attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), args: nullptr, numArgs: 0, form: Kind);
1121}
1122
1123void Parser::ParseNullabilityTypeSpecifiers(ParsedAttributes &attrs) {
1124 // Treat these like attributes, even though they're type specifiers.
1125 while (true) {
1126 auto Kind = Tok.getKind();
1127 switch (Kind) {
1128 case tok::kw__Nonnull:
1129 case tok::kw__Nullable:
1130 case tok::kw__Nullable_result:
1131 case tok::kw__Null_unspecified: {
1132 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
1133 SourceLocation AttrNameLoc = ConsumeToken();
1134 if (!getLangOpts().ObjC)
1135 Diag(Loc: AttrNameLoc, DiagID: diag::ext_nullability)
1136 << AttrName;
1137 attrs.addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
1138 form: Kind);
1139 break;
1140 }
1141 default:
1142 return;
1143 }
1144 }
1145}
1146
1147static bool VersionNumberSeparator(const char Separator) {
1148 return (Separator == '.' || Separator == '_');
1149}
1150
1151VersionTuple Parser::ParseVersionTuple(SourceRange &Range) {
1152 Range = SourceRange(Tok.getLocation(), Tok.getEndLoc());
1153
1154 if (!Tok.is(K: tok::numeric_constant)) {
1155 Diag(Tok, DiagID: diag::err_expected_version);
1156 SkipUntil(T1: tok::comma, T2: tok::r_paren,
1157 Flags: StopAtSemi | StopBeforeMatch | StopAtCodeCompletion);
1158 return VersionTuple();
1159 }
1160
1161 // Parse the major (and possibly minor and subminor) versions, which
1162 // are stored in the numeric constant. We utilize a quirk of the
1163 // lexer, which is that it handles something like 1.2.3 as a single
1164 // numeric constant, rather than two separate tokens.
1165 SmallString<512> Buffer;
1166 Buffer.resize(N: Tok.getLength()+1);
1167 const char *ThisTokBegin = &Buffer[0];
1168
1169 // Get the spelling of the token, which eliminates trigraphs, etc.
1170 bool Invalid = false;
1171 unsigned ActualLength = PP.getSpelling(Tok, Buffer&: ThisTokBegin, Invalid: &Invalid);
1172 if (Invalid)
1173 return VersionTuple();
1174
1175 // Parse the major version.
1176 unsigned AfterMajor = 0;
1177 unsigned Major = 0;
1178 while (AfterMajor < ActualLength && isDigit(c: ThisTokBegin[AfterMajor])) {
1179 Major = Major * 10 + ThisTokBegin[AfterMajor] - '0';
1180 ++AfterMajor;
1181 }
1182
1183 if (AfterMajor == 0) {
1184 Diag(Tok, DiagID: diag::err_expected_version);
1185 SkipUntil(T1: tok::comma, T2: tok::r_paren,
1186 Flags: StopAtSemi | StopBeforeMatch | StopAtCodeCompletion);
1187 return VersionTuple();
1188 }
1189
1190 if (AfterMajor == ActualLength) {
1191 ConsumeToken();
1192
1193 // We only had a single version component.
1194 if (Major == 0) {
1195 Diag(Tok, DiagID: diag::err_zero_version);
1196 return VersionTuple();
1197 }
1198
1199 return VersionTuple(Major);
1200 }
1201
1202 const char AfterMajorSeparator = ThisTokBegin[AfterMajor];
1203 if (!VersionNumberSeparator(Separator: AfterMajorSeparator)
1204 || (AfterMajor + 1 == ActualLength)) {
1205 Diag(Tok, DiagID: diag::err_expected_version);
1206 SkipUntil(T1: tok::comma, T2: tok::r_paren,
1207 Flags: StopAtSemi | StopBeforeMatch | StopAtCodeCompletion);
1208 return VersionTuple();
1209 }
1210
1211 // Parse the minor version.
1212 unsigned AfterMinor = AfterMajor + 1;
1213 unsigned Minor = 0;
1214 while (AfterMinor < ActualLength && isDigit(c: ThisTokBegin[AfterMinor])) {
1215 Minor = Minor * 10 + ThisTokBegin[AfterMinor] - '0';
1216 ++AfterMinor;
1217 }
1218
1219 if (AfterMinor == ActualLength) {
1220 ConsumeToken();
1221
1222 // We had major.minor.
1223 if (Major == 0 && Minor == 0) {
1224 Diag(Tok, DiagID: diag::err_zero_version);
1225 return VersionTuple();
1226 }
1227
1228 return VersionTuple(Major, Minor);
1229 }
1230
1231 const char AfterMinorSeparator = ThisTokBegin[AfterMinor];
1232 // If what follows is not a '.' or '_', we have a problem.
1233 if (!VersionNumberSeparator(Separator: AfterMinorSeparator)) {
1234 Diag(Tok, DiagID: diag::err_expected_version);
1235 SkipUntil(T1: tok::comma, T2: tok::r_paren,
1236 Flags: StopAtSemi | StopBeforeMatch | StopAtCodeCompletion);
1237 return VersionTuple();
1238 }
1239
1240 // Warn if separators, be it '.' or '_', do not match.
1241 if (AfterMajorSeparator != AfterMinorSeparator)
1242 Diag(Tok, DiagID: diag::warn_expected_consistent_version_separator);
1243
1244 // Parse the subminor version.
1245 unsigned AfterSubminor = AfterMinor + 1;
1246 unsigned Subminor = 0;
1247 while (AfterSubminor < ActualLength && isDigit(c: ThisTokBegin[AfterSubminor])) {
1248 Subminor = Subminor * 10 + ThisTokBegin[AfterSubminor] - '0';
1249 ++AfterSubminor;
1250 }
1251
1252 if (AfterSubminor != ActualLength) {
1253 Diag(Tok, DiagID: diag::err_expected_version);
1254 SkipUntil(T1: tok::comma, T2: tok::r_paren,
1255 Flags: StopAtSemi | StopBeforeMatch | StopAtCodeCompletion);
1256 return VersionTuple();
1257 }
1258 ConsumeToken();
1259 return VersionTuple(Major, Minor, Subminor);
1260}
1261
1262void Parser::ParseAvailabilityAttribute(
1263 IdentifierInfo &Availability, SourceLocation AvailabilityLoc,
1264 ParsedAttributes &attrs, SourceLocation *endLoc, IdentifierInfo *ScopeName,
1265 SourceLocation ScopeLoc, ParsedAttr::Form Form) {
1266 enum { Introduced, Deprecated, Obsoleted, Unknown };
1267 AvailabilityChange Changes[Unknown];
1268 ExprResult MessageExpr, ReplacementExpr;
1269 IdentifierLoc *EnvironmentLoc = nullptr;
1270
1271 // Opening '('.
1272 BalancedDelimiterTracker T(*this, tok::l_paren);
1273 if (T.consumeOpen()) {
1274 Diag(Tok, DiagID: diag::err_expected) << tok::l_paren;
1275 return;
1276 }
1277
1278 // Parse the platform name.
1279 if (Tok.isNot(K: tok::identifier)) {
1280 Diag(Tok, DiagID: diag::err_availability_expected_platform);
1281 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1282 return;
1283 }
1284 IdentifierLoc *Platform = ParseIdentifierLoc();
1285 if (const IdentifierInfo *const Ident = Platform->getIdentifierInfo()) {
1286 // Disallow xrOS for availability attributes.
1287 if (Ident->getName().contains(Other: "xrOS") || Ident->getName().contains(Other: "xros"))
1288 Diag(Loc: Platform->getLoc(), DiagID: diag::warn_availability_unknown_platform)
1289 << Ident;
1290 // Canonicalize platform name from "macosx" to "macos".
1291 else if (Ident->getName() == "macosx")
1292 Platform->setIdentifierInfo(PP.getIdentifierInfo(Name: "macos"));
1293 // Canonicalize platform name from "macosx_app_extension" to
1294 // "macos_app_extension".
1295 else if (Ident->getName() == "macosx_app_extension")
1296 Platform->setIdentifierInfo(PP.getIdentifierInfo(Name: "macos_app_extension"));
1297 else
1298 Platform->setIdentifierInfo(PP.getIdentifierInfo(
1299 Name: AvailabilityAttr::canonicalizePlatformName(Platform: Ident->getName())));
1300 }
1301
1302 // Parse the ',' following the platform name.
1303 if (ExpectAndConsume(ExpectedTok: tok::comma)) {
1304 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1305 return;
1306 }
1307
1308 // If we haven't grabbed the pointers for the identifiers
1309 // "introduced", "deprecated", and "obsoleted", do so now.
1310 if (!Ident_introduced) {
1311 Ident_introduced = PP.getIdentifierInfo(Name: "introduced");
1312 Ident_deprecated = PP.getIdentifierInfo(Name: "deprecated");
1313 Ident_obsoleted = PP.getIdentifierInfo(Name: "obsoleted");
1314 Ident_unavailable = PP.getIdentifierInfo(Name: "unavailable");
1315 Ident_message = PP.getIdentifierInfo(Name: "message");
1316 Ident_strict = PP.getIdentifierInfo(Name: "strict");
1317 Ident_replacement = PP.getIdentifierInfo(Name: "replacement");
1318 Ident_environment = PP.getIdentifierInfo(Name: "environment");
1319 }
1320
1321 // Parse the optional "strict", the optional "replacement" and the set of
1322 // introductions/deprecations/removals.
1323 SourceLocation UnavailableLoc, StrictLoc;
1324 do {
1325 if (Tok.isNot(K: tok::identifier)) {
1326 Diag(Tok, DiagID: diag::err_availability_expected_change);
1327 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1328 return;
1329 }
1330 IdentifierInfo *Keyword = Tok.getIdentifierInfo();
1331 SourceLocation KeywordLoc = ConsumeToken();
1332
1333 if (Keyword == Ident_strict) {
1334 if (StrictLoc.isValid()) {
1335 Diag(Loc: KeywordLoc, DiagID: diag::err_availability_redundant)
1336 << Keyword << SourceRange(StrictLoc);
1337 }
1338 StrictLoc = KeywordLoc;
1339 continue;
1340 }
1341
1342 if (Keyword == Ident_unavailable) {
1343 if (UnavailableLoc.isValid()) {
1344 Diag(Loc: KeywordLoc, DiagID: diag::err_availability_redundant)
1345 << Keyword << SourceRange(UnavailableLoc);
1346 }
1347 UnavailableLoc = KeywordLoc;
1348 continue;
1349 }
1350
1351 if (Keyword == Ident_deprecated && Platform->getIdentifierInfo() &&
1352 Platform->getIdentifierInfo()->isStr(Str: "swift")) {
1353 // For swift, we deprecate for all versions.
1354 if (Changes[Deprecated].KeywordLoc.isValid()) {
1355 Diag(Loc: KeywordLoc, DiagID: diag::err_availability_redundant)
1356 << Keyword
1357 << SourceRange(Changes[Deprecated].KeywordLoc);
1358 }
1359
1360 Changes[Deprecated].KeywordLoc = KeywordLoc;
1361 // Use a fake version here.
1362 Changes[Deprecated].Version = VersionTuple(1);
1363 continue;
1364 }
1365
1366 if (Keyword == Ident_environment) {
1367 if (EnvironmentLoc != nullptr) {
1368 Diag(Loc: KeywordLoc, DiagID: diag::err_availability_redundant)
1369 << Keyword << SourceRange(EnvironmentLoc->getLoc());
1370 }
1371 }
1372
1373 if (Tok.isNot(K: tok::equal)) {
1374 Diag(Tok, DiagID: diag::err_expected_after) << Keyword << tok::equal;
1375 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1376 return;
1377 }
1378 ConsumeToken();
1379 if (Keyword == Ident_message || Keyword == Ident_replacement) {
1380 if (!isTokenStringLiteral()) {
1381 Diag(Tok, DiagID: diag::err_expected_string_literal)
1382 << /*Source='availability attribute'*/2;
1383 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1384 return;
1385 }
1386 if (Keyword == Ident_message) {
1387 MessageExpr = ParseUnevaluatedStringLiteralExpression();
1388 break;
1389 } else {
1390 ReplacementExpr = ParseUnevaluatedStringLiteralExpression();
1391 continue;
1392 }
1393 }
1394 if (Keyword == Ident_environment) {
1395 if (Tok.isNot(K: tok::identifier)) {
1396 Diag(Tok, DiagID: diag::err_availability_expected_environment);
1397 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1398 return;
1399 }
1400 EnvironmentLoc = ParseIdentifierLoc();
1401 continue;
1402 }
1403
1404 // Special handling of 'NA' only when applied to introduced or
1405 // deprecated.
1406 if ((Keyword == Ident_introduced || Keyword == Ident_deprecated) &&
1407 Tok.is(K: tok::identifier)) {
1408 IdentifierInfo *NA = Tok.getIdentifierInfo();
1409 if (NA->getName() == "NA") {
1410 ConsumeToken();
1411 if (Keyword == Ident_introduced)
1412 UnavailableLoc = KeywordLoc;
1413 continue;
1414 }
1415 }
1416
1417 SourceRange VersionRange;
1418 VersionTuple Version = ParseVersionTuple(Range&: VersionRange);
1419
1420 if (Version.empty()) {
1421 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1422 return;
1423 }
1424
1425 unsigned Index;
1426 if (Keyword == Ident_introduced)
1427 Index = Introduced;
1428 else if (Keyword == Ident_deprecated)
1429 Index = Deprecated;
1430 else if (Keyword == Ident_obsoleted)
1431 Index = Obsoleted;
1432 else
1433 Index = Unknown;
1434
1435 if (Index < Unknown) {
1436 if (!Changes[Index].KeywordLoc.isInvalid()) {
1437 Diag(Loc: KeywordLoc, DiagID: diag::err_availability_redundant)
1438 << Keyword
1439 << SourceRange(Changes[Index].KeywordLoc,
1440 Changes[Index].VersionRange.getEnd());
1441 }
1442
1443 Changes[Index].KeywordLoc = KeywordLoc;
1444 Changes[Index].Version = Version;
1445 Changes[Index].VersionRange = VersionRange;
1446 } else {
1447 Diag(Loc: KeywordLoc, DiagID: diag::err_availability_unknown_change)
1448 << Keyword << VersionRange;
1449 }
1450
1451 } while (TryConsumeToken(Expected: tok::comma));
1452
1453 // Closing ')'.
1454 if (T.consumeClose())
1455 return;
1456
1457 if (endLoc)
1458 *endLoc = T.getCloseLocation();
1459
1460 // The 'unavailable' availability cannot be combined with any other
1461 // availability changes. Make sure that hasn't happened.
1462 if (UnavailableLoc.isValid()) {
1463 bool Complained = false;
1464 for (unsigned Index = Introduced; Index != Unknown; ++Index) {
1465 if (Changes[Index].KeywordLoc.isValid()) {
1466 if (!Complained) {
1467 Diag(Loc: UnavailableLoc, DiagID: diag::warn_availability_and_unavailable)
1468 << SourceRange(Changes[Index].KeywordLoc,
1469 Changes[Index].VersionRange.getEnd());
1470 Complained = true;
1471 }
1472
1473 // Clear out the availability.
1474 Changes[Index] = AvailabilityChange();
1475 }
1476 }
1477 }
1478
1479 // Record this attribute
1480 attrs.addNew(attrName: &Availability,
1481 attrRange: SourceRange(AvailabilityLoc, T.getCloseLocation()),
1482 scope: AttributeScopeInfo(ScopeName, ScopeLoc), Param: Platform,
1483 introduced: Changes[Introduced], deprecated: Changes[Deprecated], obsoleted: Changes[Obsoleted],
1484 unavailable: UnavailableLoc, MessageExpr: MessageExpr.get(), form: Form, strict: StrictLoc,
1485 ReplacementExpr: ReplacementExpr.get(), EnvironmentLoc);
1486}
1487
1488void Parser::ParseExternalSourceSymbolAttribute(
1489 IdentifierInfo &ExternalSourceSymbol, SourceLocation Loc,
1490 ParsedAttributes &Attrs, SourceLocation *EndLoc, IdentifierInfo *ScopeName,
1491 SourceLocation ScopeLoc, ParsedAttr::Form Form) {
1492 // Opening '('.
1493 BalancedDelimiterTracker T(*this, tok::l_paren);
1494 if (T.expectAndConsume())
1495 return;
1496
1497 // Initialize the pointers for the keyword identifiers when required.
1498 if (!Ident_language) {
1499 Ident_language = PP.getIdentifierInfo(Name: "language");
1500 Ident_defined_in = PP.getIdentifierInfo(Name: "defined_in");
1501 Ident_generated_declaration = PP.getIdentifierInfo(Name: "generated_declaration");
1502 Ident_USR = PP.getIdentifierInfo(Name: "USR");
1503 }
1504
1505 ExprResult Language;
1506 bool HasLanguage = false;
1507 ExprResult DefinedInExpr;
1508 bool HasDefinedIn = false;
1509 IdentifierLoc *GeneratedDeclaration = nullptr;
1510 ExprResult USR;
1511 bool HasUSR = false;
1512
1513 // Parse the language/defined_in/generated_declaration keywords
1514 do {
1515 if (Tok.isNot(K: tok::identifier)) {
1516 Diag(Tok, DiagID: diag::err_external_source_symbol_expected_keyword);
1517 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1518 return;
1519 }
1520
1521 SourceLocation KeywordLoc = Tok.getLocation();
1522 IdentifierInfo *Keyword = Tok.getIdentifierInfo();
1523 if (Keyword == Ident_generated_declaration) {
1524 if (GeneratedDeclaration) {
1525 Diag(Tok, DiagID: diag::err_external_source_symbol_duplicate_clause) << Keyword;
1526 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1527 return;
1528 }
1529 GeneratedDeclaration = ParseIdentifierLoc();
1530 continue;
1531 }
1532
1533 if (Keyword != Ident_language && Keyword != Ident_defined_in &&
1534 Keyword != Ident_USR) {
1535 Diag(Tok, DiagID: diag::err_external_source_symbol_expected_keyword);
1536 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1537 return;
1538 }
1539
1540 ConsumeToken();
1541 if (ExpectAndConsume(ExpectedTok: tok::equal, Diag: diag::err_expected_after,
1542 DiagMsg: Keyword->getName())) {
1543 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1544 return;
1545 }
1546
1547 bool HadLanguage = HasLanguage, HadDefinedIn = HasDefinedIn,
1548 HadUSR = HasUSR;
1549 if (Keyword == Ident_language)
1550 HasLanguage = true;
1551 else if (Keyword == Ident_USR)
1552 HasUSR = true;
1553 else
1554 HasDefinedIn = true;
1555
1556 if (!isTokenStringLiteral()) {
1557 Diag(Tok, DiagID: diag::err_expected_string_literal)
1558 << /*Source='external_source_symbol attribute'*/ 3
1559 << /*language | source container | USR*/ (
1560 Keyword == Ident_language
1561 ? 0
1562 : (Keyword == Ident_defined_in ? 1 : 2));
1563 SkipUntil(T1: tok::comma, T2: tok::r_paren, Flags: StopAtSemi | StopBeforeMatch);
1564 continue;
1565 }
1566 if (Keyword == Ident_language) {
1567 if (HadLanguage) {
1568 Diag(Loc: KeywordLoc, DiagID: diag::err_external_source_symbol_duplicate_clause)
1569 << Keyword;
1570 ParseUnevaluatedStringLiteralExpression();
1571 continue;
1572 }
1573 Language = ParseUnevaluatedStringLiteralExpression();
1574 } else if (Keyword == Ident_USR) {
1575 if (HadUSR) {
1576 Diag(Loc: KeywordLoc, DiagID: diag::err_external_source_symbol_duplicate_clause)
1577 << Keyword;
1578 ParseUnevaluatedStringLiteralExpression();
1579 continue;
1580 }
1581 USR = ParseUnevaluatedStringLiteralExpression();
1582 } else {
1583 assert(Keyword == Ident_defined_in && "Invalid clause keyword!");
1584 if (HadDefinedIn) {
1585 Diag(Loc: KeywordLoc, DiagID: diag::err_external_source_symbol_duplicate_clause)
1586 << Keyword;
1587 ParseUnevaluatedStringLiteralExpression();
1588 continue;
1589 }
1590 DefinedInExpr = ParseUnevaluatedStringLiteralExpression();
1591 }
1592 } while (TryConsumeToken(Expected: tok::comma));
1593
1594 // Closing ')'.
1595 if (T.consumeClose())
1596 return;
1597 if (EndLoc)
1598 *EndLoc = T.getCloseLocation();
1599
1600 ArgsUnion Args[] = {Language.get(), DefinedInExpr.get(), GeneratedDeclaration,
1601 USR.get()};
1602 Attrs.addNew(attrName: &ExternalSourceSymbol, attrRange: SourceRange(Loc, T.getCloseLocation()),
1603 scope: AttributeScopeInfo(ScopeName, ScopeLoc), args: Args, numArgs: std::size(Args),
1604 form: Form);
1605}
1606
1607void Parser::ParseObjCBridgeRelatedAttribute(
1608 IdentifierInfo &ObjCBridgeRelated, SourceLocation ObjCBridgeRelatedLoc,
1609 ParsedAttributes &Attrs, SourceLocation *EndLoc, IdentifierInfo *ScopeName,
1610 SourceLocation ScopeLoc, ParsedAttr::Form Form) {
1611 // Opening '('.
1612 BalancedDelimiterTracker T(*this, tok::l_paren);
1613 if (T.consumeOpen()) {
1614 Diag(Tok, DiagID: diag::err_expected) << tok::l_paren;
1615 return;
1616 }
1617
1618 // Parse the related class name.
1619 if (Tok.isNot(K: tok::identifier)) {
1620 Diag(Tok, DiagID: diag::err_objcbridge_related_expected_related_class);
1621 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1622 return;
1623 }
1624 IdentifierLoc *RelatedClass = ParseIdentifierLoc();
1625 if (ExpectAndConsume(ExpectedTok: tok::comma)) {
1626 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1627 return;
1628 }
1629
1630 // Parse class method name. It's non-optional in the sense that a trailing
1631 // comma is required, but it can be the empty string, and then we record a
1632 // nullptr.
1633 IdentifierLoc *ClassMethod = nullptr;
1634 if (Tok.is(K: tok::identifier)) {
1635 ClassMethod = ParseIdentifierLoc();
1636 if (!TryConsumeToken(Expected: tok::colon)) {
1637 Diag(Tok, DiagID: diag::err_objcbridge_related_selector_name);
1638 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1639 return;
1640 }
1641 }
1642 if (!TryConsumeToken(Expected: tok::comma)) {
1643 if (Tok.is(K: tok::colon))
1644 Diag(Tok, DiagID: diag::err_objcbridge_related_selector_name);
1645 else
1646 Diag(Tok, DiagID: diag::err_expected) << tok::comma;
1647 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1648 return;
1649 }
1650
1651 // Parse instance method name. Also non-optional but empty string is
1652 // permitted.
1653 IdentifierLoc *InstanceMethod = nullptr;
1654 if (Tok.is(K: tok::identifier))
1655 InstanceMethod = ParseIdentifierLoc();
1656 else if (Tok.isNot(K: tok::r_paren)) {
1657 Diag(Tok, DiagID: diag::err_expected) << tok::r_paren;
1658 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
1659 return;
1660 }
1661
1662 // Closing ')'.
1663 if (T.consumeClose())
1664 return;
1665
1666 if (EndLoc)
1667 *EndLoc = T.getCloseLocation();
1668
1669 // Record this attribute
1670 Attrs.addNew(attrName: &ObjCBridgeRelated,
1671 attrRange: SourceRange(ObjCBridgeRelatedLoc, T.getCloseLocation()),
1672 scope: AttributeScopeInfo(ScopeName, ScopeLoc), Param1: RelatedClass,
1673 Param2: ClassMethod, Param3: InstanceMethod, form: Form);
1674}
1675
1676void Parser::ParseSwiftNewTypeAttribute(
1677 IdentifierInfo &AttrName, SourceLocation AttrNameLoc,
1678 ParsedAttributes &Attrs, SourceLocation *EndLoc, IdentifierInfo *ScopeName,
1679 SourceLocation ScopeLoc, ParsedAttr::Form Form) {
1680 BalancedDelimiterTracker T(*this, tok::l_paren);
1681
1682 // Opening '('
1683 if (T.consumeOpen()) {
1684 Diag(Tok, DiagID: diag::err_expected) << tok::l_paren;
1685 return;
1686 }
1687
1688 if (Tok.is(K: tok::r_paren)) {
1689 Diag(Loc: Tok.getLocation(), DiagID: diag::err_argument_required_after_attribute);
1690 T.consumeClose();
1691 return;
1692 }
1693 if (Tok.isNot(K: tok::kw_struct) && Tok.isNot(K: tok::kw_enum)) {
1694 Diag(Tok, DiagID: diag::warn_attribute_type_not_supported)
1695 << &AttrName << Tok.getIdentifierInfo();
1696 if (!isTokenSpecial())
1697 ConsumeToken();
1698 T.consumeClose();
1699 return;
1700 }
1701
1702 auto *SwiftType = new (Actions.Context)
1703 IdentifierLoc(Tok.getLocation(), Tok.getIdentifierInfo());
1704 ConsumeToken();
1705
1706 // Closing ')'
1707 if (T.consumeClose())
1708 return;
1709 if (EndLoc)
1710 *EndLoc = T.getCloseLocation();
1711
1712 ArgsUnion Args[] = {SwiftType};
1713 Attrs.addNew(attrName: &AttrName, attrRange: SourceRange(AttrNameLoc, T.getCloseLocation()),
1714 scope: AttributeScopeInfo(ScopeName, ScopeLoc), args: Args, numArgs: std::size(Args),
1715 form: Form);
1716}
1717
1718void Parser::ParseTypeTagForDatatypeAttribute(
1719 IdentifierInfo &AttrName, SourceLocation AttrNameLoc,
1720 ParsedAttributes &Attrs, SourceLocation *EndLoc, IdentifierInfo *ScopeName,
1721 SourceLocation ScopeLoc, ParsedAttr::Form Form) {
1722 assert(Tok.is(tok::l_paren) && "Attribute arg list not starting with '('");
1723
1724 BalancedDelimiterTracker T(*this, tok::l_paren);
1725 T.consumeOpen();
1726
1727 if (Tok.isNot(K: tok::identifier)) {
1728 Diag(Tok, DiagID: diag::err_expected) << tok::identifier;
1729 T.skipToEnd();
1730 return;
1731 }
1732 IdentifierLoc *ArgumentKind = ParseIdentifierLoc();
1733
1734 if (ExpectAndConsume(ExpectedTok: tok::comma)) {
1735 T.skipToEnd();
1736 return;
1737 }
1738
1739 SourceRange MatchingCTypeRange;
1740 TypeResult MatchingCType = ParseTypeName(Range: &MatchingCTypeRange);
1741 if (MatchingCType.isInvalid()) {
1742 T.skipToEnd();
1743 return;
1744 }
1745
1746 bool LayoutCompatible = false;
1747 bool MustBeNull = false;
1748 while (TryConsumeToken(Expected: tok::comma)) {
1749 if (Tok.isNot(K: tok::identifier)) {
1750 Diag(Tok, DiagID: diag::err_expected) << tok::identifier;
1751 T.skipToEnd();
1752 return;
1753 }
1754 IdentifierInfo *Flag = Tok.getIdentifierInfo();
1755 if (Flag->isStr(Str: "layout_compatible"))
1756 LayoutCompatible = true;
1757 else if (Flag->isStr(Str: "must_be_null"))
1758 MustBeNull = true;
1759 else {
1760 Diag(Tok, DiagID: diag::err_type_safety_unknown_flag) << Flag;
1761 T.skipToEnd();
1762 return;
1763 }
1764 ConsumeToken(); // consume flag
1765 }
1766
1767 if (!T.consumeClose()) {
1768 Attrs.addNewTypeTagForDatatype(
1769 attrName: &AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(ScopeName, ScopeLoc),
1770 argumentKind: ArgumentKind, matchingCType: MatchingCType.get(), layoutCompatible: LayoutCompatible, mustBeNull: MustBeNull, form: Form);
1771 }
1772
1773 if (EndLoc)
1774 *EndLoc = T.getCloseLocation();
1775}
1776
1777bool Parser::DiagnoseProhibitedCXX11Attribute() {
1778 assert(Tok.is(tok::l_square) && NextToken().is(tok::l_square));
1779
1780 switch (isCXX11AttributeSpecifier(/*Disambiguate*/true)) {
1781 case CXX11AttributeKind::NotAttributeSpecifier:
1782 // No diagnostic: we're in Obj-C++11 and this is not actually an attribute.
1783 return false;
1784
1785 case CXX11AttributeKind::InvalidAttributeSpecifier:
1786 Diag(Loc: Tok.getLocation(), DiagID: diag::err_l_square_l_square_not_attribute);
1787 return false;
1788
1789 case CXX11AttributeKind::AttributeSpecifier:
1790 // Parse and discard the attributes.
1791 SourceLocation BeginLoc = ConsumeBracket();
1792 ConsumeBracket();
1793 SkipUntil(T: tok::r_square);
1794 assert(Tok.is(tok::r_square) && "isCXX11AttributeSpecifier lied");
1795 SourceLocation EndLoc = ConsumeBracket();
1796 Diag(Loc: BeginLoc, DiagID: diag::err_attributes_not_allowed)
1797 << SourceRange(BeginLoc, EndLoc);
1798 return true;
1799 }
1800 llvm_unreachable("All cases handled above.");
1801}
1802
1803void Parser::DiagnoseMisplacedCXX11Attribute(ParsedAttributes &Attrs,
1804 SourceLocation CorrectLocation) {
1805 assert((Tok.is(tok::l_square) && NextToken().is(tok::l_square)) ||
1806 Tok.is(tok::kw_alignas) || Tok.isRegularKeywordAttribute());
1807
1808 // Consume the attributes.
1809 auto Keyword =
1810 Tok.isRegularKeywordAttribute() ? Tok.getIdentifierInfo() : nullptr;
1811 SourceLocation Loc = Tok.getLocation();
1812 ParseCXX11Attributes(attrs&: Attrs);
1813 CharSourceRange AttrRange(SourceRange(Loc, Attrs.Range.getEnd()), true);
1814 // FIXME: use err_attributes_misplaced
1815 (Keyword ? Diag(Loc, DiagID: diag::err_keyword_not_allowed) << Keyword
1816 : Diag(Loc, DiagID: diag::err_attributes_not_allowed))
1817 << FixItHint::CreateInsertionFromRange(InsertionLoc: CorrectLocation, FromRange: AttrRange)
1818 << FixItHint::CreateRemoval(RemoveRange: AttrRange);
1819}
1820
1821void Parser::DiagnoseProhibitedAttributes(
1822 const ParsedAttributesView &Attrs, const SourceLocation CorrectLocation) {
1823 auto *FirstAttr = Attrs.empty() ? nullptr : &Attrs.front();
1824 if (CorrectLocation.isValid()) {
1825 CharSourceRange AttrRange(Attrs.Range, true);
1826 (FirstAttr && FirstAttr->isRegularKeywordAttribute()
1827 ? Diag(Loc: CorrectLocation, DiagID: diag::err_keyword_misplaced) << FirstAttr
1828 : Diag(Loc: CorrectLocation, DiagID: diag::err_attributes_misplaced))
1829 << FixItHint::CreateInsertionFromRange(InsertionLoc: CorrectLocation, FromRange: AttrRange)
1830 << FixItHint::CreateRemoval(RemoveRange: AttrRange);
1831 } else {
1832 const SourceRange &Range = Attrs.Range;
1833 (FirstAttr && FirstAttr->isRegularKeywordAttribute()
1834 ? Diag(Loc: Range.getBegin(), DiagID: diag::err_keyword_not_allowed) << FirstAttr
1835 : Diag(Loc: Range.getBegin(), DiagID: diag::err_attributes_not_allowed))
1836 << Range;
1837 }
1838}
1839
1840void Parser::ProhibitCXX11Attributes(ParsedAttributes &Attrs,
1841 unsigned AttrDiagID,
1842 unsigned KeywordDiagID,
1843 bool DiagnoseEmptyAttrs,
1844 bool WarnOnUnknownAttrs) {
1845
1846 if (DiagnoseEmptyAttrs && Attrs.empty() && Attrs.Range.isValid()) {
1847 // An attribute list has been parsed, but it was empty.
1848 // This is the case for [[]].
1849 const auto &LangOpts = getLangOpts();
1850 auto &SM = PP.getSourceManager();
1851 Token FirstLSquare;
1852 Lexer::getRawToken(Loc: Attrs.Range.getBegin(), Result&: FirstLSquare, SM, LangOpts);
1853
1854 if (FirstLSquare.is(K: tok::l_square)) {
1855 std::optional<Token> SecondLSquare =
1856 Lexer::findNextToken(Loc: FirstLSquare.getLocation(), SM, LangOpts);
1857
1858 if (SecondLSquare && SecondLSquare->is(K: tok::l_square)) {
1859 // The attribute range starts with [[, but is empty. So this must
1860 // be [[]], which we are supposed to diagnose because
1861 // DiagnoseEmptyAttrs is true.
1862 Diag(Loc: Attrs.Range.getBegin(), DiagID: AttrDiagID) << Attrs.Range;
1863 return;
1864 }
1865 }
1866 }
1867
1868 for (const ParsedAttr &AL : Attrs) {
1869 if (AL.isRegularKeywordAttribute()) {
1870 Diag(Loc: AL.getLoc(), DiagID: KeywordDiagID) << AL;
1871 AL.setInvalid();
1872 continue;
1873 }
1874 if (!AL.isStandardAttributeSyntax())
1875 continue;
1876 if (AL.getKind() == ParsedAttr::UnknownAttribute) {
1877 if (WarnOnUnknownAttrs) {
1878 Actions.DiagnoseUnknownAttribute(AL);
1879 AL.setInvalid();
1880 }
1881 } else {
1882 Diag(Loc: AL.getLoc(), DiagID: AttrDiagID) << AL;
1883 AL.setInvalid();
1884 }
1885 }
1886}
1887
1888void Parser::DiagnoseCXX11AttributeExtension(ParsedAttributes &Attrs) {
1889 for (const ParsedAttr &PA : Attrs) {
1890 if (PA.isStandardAttributeSyntax() || PA.isRegularKeywordAttribute())
1891 Diag(Loc: PA.getLoc(), DiagID: diag::ext_cxx11_attr_placement)
1892 << PA << PA.isRegularKeywordAttribute() << PA.getRange();
1893 }
1894}
1895
1896void Parser::stripTypeAttributesOffDeclSpec(ParsedAttributes &Attrs,
1897 DeclSpec &DS, TagUseKind TUK) {
1898 if (TUK == TagUseKind::Reference)
1899 return;
1900
1901 llvm::SmallVector<ParsedAttr *, 1> ToBeMoved;
1902
1903 for (ParsedAttr &AL : DS.getAttributes()) {
1904 if ((AL.getKind() == ParsedAttr::AT_Aligned &&
1905 AL.isDeclspecAttribute()) ||
1906 AL.isMicrosoftAttribute())
1907 ToBeMoved.push_back(Elt: &AL);
1908 }
1909
1910 for (ParsedAttr *AL : ToBeMoved) {
1911 DS.getAttributes().remove(ToBeRemoved: AL);
1912 Attrs.addAtEnd(newAttr: AL);
1913 }
1914}
1915
1916Parser::DeclGroupPtrTy Parser::ParseDeclaration(DeclaratorContext Context,
1917 SourceLocation &DeclEnd,
1918 ParsedAttributes &DeclAttrs,
1919 ParsedAttributes &DeclSpecAttrs,
1920 SourceLocation *DeclSpecStart) {
1921 ParenBraceBracketBalancer BalancerRAIIObj(*this);
1922 // Must temporarily exit the objective-c container scope for
1923 // parsing c none objective-c decls.
1924 ObjCDeclContextSwitch ObjCDC(*this);
1925
1926 Decl *SingleDecl = nullptr;
1927 switch (Tok.getKind()) {
1928 case tok::kw_template:
1929 case tok::kw_export:
1930 ProhibitAttributes(Attrs&: DeclAttrs);
1931 ProhibitAttributes(Attrs&: DeclSpecAttrs);
1932 return ParseDeclarationStartingWithTemplate(Context, DeclEnd, AccessAttrs&: DeclAttrs);
1933 case tok::kw_inline:
1934 // Could be the start of an inline namespace. Allowed as an ext in C++03.
1935 if (getLangOpts().CPlusPlus && NextToken().is(K: tok::kw_namespace)) {
1936 ProhibitAttributes(Attrs&: DeclAttrs);
1937 ProhibitAttributes(Attrs&: DeclSpecAttrs);
1938 SourceLocation InlineLoc = ConsumeToken();
1939 return ParseNamespace(Context, DeclEnd, InlineLoc);
1940 }
1941 return ParseSimpleDeclaration(Context, DeclEnd, DeclAttrs, DeclSpecAttrs,
1942 RequireSemi: true, FRI: nullptr, DeclSpecStart);
1943
1944 case tok::kw_cbuffer:
1945 case tok::kw_tbuffer:
1946 SingleDecl = ParseHLSLBuffer(DeclEnd, Attrs&: DeclAttrs);
1947 break;
1948 case tok::kw_namespace:
1949 ProhibitAttributes(Attrs&: DeclAttrs);
1950 ProhibitAttributes(Attrs&: DeclSpecAttrs);
1951 return ParseNamespace(Context, DeclEnd);
1952 case tok::kw_using: {
1953 takeAndConcatenateAttrs(First&: DeclAttrs, Second: std::move(DeclSpecAttrs));
1954 return ParseUsingDirectiveOrDeclaration(Context, TemplateInfo: ParsedTemplateInfo(),
1955 DeclEnd, Attrs&: DeclAttrs);
1956 }
1957 case tok::kw_static_assert:
1958 case tok::kw__Static_assert:
1959 ProhibitAttributes(Attrs&: DeclAttrs);
1960 ProhibitAttributes(Attrs&: DeclSpecAttrs);
1961 SingleDecl = ParseStaticAssertDeclaration(DeclEnd);
1962 break;
1963 default:
1964 return ParseSimpleDeclaration(Context, DeclEnd, DeclAttrs, DeclSpecAttrs,
1965 RequireSemi: true, FRI: nullptr, DeclSpecStart);
1966 }
1967
1968 // This routine returns a DeclGroup, if the thing we parsed only contains a
1969 // single decl, convert it now.
1970 return Actions.ConvertDeclToDeclGroup(Ptr: SingleDecl);
1971}
1972
1973Parser::DeclGroupPtrTy Parser::ParseSimpleDeclaration(
1974 DeclaratorContext Context, SourceLocation &DeclEnd,
1975 ParsedAttributes &DeclAttrs, ParsedAttributes &DeclSpecAttrs,
1976 bool RequireSemi, ForRangeInit *FRI, SourceLocation *DeclSpecStart) {
1977 // Need to retain these for diagnostics before we add them to the DeclSepc.
1978 ParsedAttributesView OriginalDeclSpecAttrs;
1979 OriginalDeclSpecAttrs.prepend(B: DeclSpecAttrs.begin(), E: DeclSpecAttrs.end());
1980 OriginalDeclSpecAttrs.Range = DeclSpecAttrs.Range;
1981
1982 // Parse the common declaration-specifiers piece.
1983 ParsingDeclSpec DS(*this);
1984 DS.takeAttributesAppendingingFrom(attrs&: DeclSpecAttrs);
1985
1986 ParsedTemplateInfo TemplateInfo;
1987 DeclSpecContext DSContext = getDeclSpecContextFromDeclaratorContext(Context);
1988 ParseDeclarationSpecifiers(DS, TemplateInfo, AS: AS_none, DSC: DSContext);
1989
1990 // If we had a free-standing type definition with a missing semicolon, we
1991 // may get this far before the problem becomes obvious.
1992 if (DS.hasTagDefinition() &&
1993 DiagnoseMissingSemiAfterTagDefinition(DS, AS: AS_none, DSContext))
1994 return nullptr;
1995
1996 // C99 6.7.2.3p6: Handle "struct-or-union identifier;", "enum { X };"
1997 // declaration-specifiers init-declarator-list[opt] ';'
1998 if (Tok.is(K: tok::semi)) {
1999 ProhibitAttributes(Attrs&: DeclAttrs);
2000 DeclEnd = Tok.getLocation();
2001 if (RequireSemi) ConsumeToken();
2002 RecordDecl *AnonRecord = nullptr;
2003 Decl *TheDecl = Actions.ParsedFreeStandingDeclSpec(
2004 S: getCurScope(), AS: AS_none, DS, DeclAttrs: ParsedAttributesView::none(), AnonRecord);
2005 Actions.ActOnDefinedDeclarationSpecifier(D: TheDecl);
2006 DS.complete(D: TheDecl);
2007 if (AnonRecord) {
2008 Decl* decls[] = {AnonRecord, TheDecl};
2009 return Actions.BuildDeclaratorGroup(Group: decls);
2010 }
2011 return Actions.ConvertDeclToDeclGroup(Ptr: TheDecl);
2012 }
2013
2014 if (DS.hasTagDefinition())
2015 Actions.ActOnDefinedDeclarationSpecifier(D: DS.getRepAsDecl());
2016
2017 if (DeclSpecStart)
2018 DS.SetRangeStart(*DeclSpecStart);
2019
2020 return ParseDeclGroup(DS, Context, Attrs&: DeclAttrs, TemplateInfo, DeclEnd: &DeclEnd, FRI);
2021}
2022
2023bool Parser::MightBeDeclarator(DeclaratorContext Context) {
2024 switch (Tok.getKind()) {
2025 case tok::annot_cxxscope:
2026 case tok::annot_template_id:
2027 case tok::caret:
2028 case tok::code_completion:
2029 case tok::coloncolon:
2030 case tok::ellipsis:
2031 case tok::kw___attribute:
2032 case tok::kw_operator:
2033 case tok::l_paren:
2034 case tok::star:
2035 return true;
2036
2037 case tok::amp:
2038 case tok::ampamp:
2039 return getLangOpts().CPlusPlus;
2040
2041 case tok::l_square: // Might be an attribute on an unnamed bit-field.
2042 return Context == DeclaratorContext::Member && getLangOpts().CPlusPlus11 &&
2043 NextToken().is(K: tok::l_square);
2044
2045 case tok::colon: // Might be a typo for '::' or an unnamed bit-field.
2046 return Context == DeclaratorContext::Member || getLangOpts().CPlusPlus;
2047
2048 case tok::identifier:
2049 switch (NextToken().getKind()) {
2050 case tok::code_completion:
2051 case tok::coloncolon:
2052 case tok::comma:
2053 case tok::equal:
2054 case tok::equalequal: // Might be a typo for '='.
2055 case tok::kw_alignas:
2056 case tok::kw_asm:
2057 case tok::kw___attribute:
2058 case tok::l_brace:
2059 case tok::l_paren:
2060 case tok::l_square:
2061 case tok::less:
2062 case tok::r_brace:
2063 case tok::r_paren:
2064 case tok::r_square:
2065 case tok::semi:
2066 return true;
2067
2068 case tok::colon:
2069 // At namespace scope, 'identifier:' is probably a typo for 'identifier::'
2070 // and in block scope it's probably a label. Inside a class definition,
2071 // this is a bit-field.
2072 return Context == DeclaratorContext::Member ||
2073 (getLangOpts().CPlusPlus && Context == DeclaratorContext::File);
2074
2075 case tok::identifier: // Possible virt-specifier.
2076 return getLangOpts().CPlusPlus11 && isCXX11VirtSpecifier(Tok: NextToken());
2077
2078 default:
2079 return Tok.isRegularKeywordAttribute();
2080 }
2081
2082 default:
2083 return Tok.isRegularKeywordAttribute();
2084 }
2085}
2086
2087void Parser::SkipMalformedDecl() {
2088 while (true) {
2089 switch (Tok.getKind()) {
2090 case tok::l_brace:
2091 // Skip until matching }, then stop. We've probably skipped over
2092 // a malformed class or function definition or similar.
2093 ConsumeBrace();
2094 SkipUntil(T: tok::r_brace);
2095 if (Tok.isOneOf(Ks: tok::comma, Ks: tok::l_brace, Ks: tok::kw_try)) {
2096 // This declaration isn't over yet. Keep skipping.
2097 continue;
2098 }
2099 TryConsumeToken(Expected: tok::semi);
2100 return;
2101
2102 case tok::l_square:
2103 ConsumeBracket();
2104 SkipUntil(T: tok::r_square);
2105 continue;
2106
2107 case tok::l_paren:
2108 ConsumeParen();
2109 SkipUntil(T: tok::r_paren);
2110 continue;
2111
2112 case tok::r_brace:
2113 return;
2114
2115 case tok::semi:
2116 ConsumeToken();
2117 return;
2118
2119 case tok::kw_inline:
2120 // 'inline namespace' at the start of a line is almost certainly
2121 // a good place to pick back up parsing, except in an Objective-C
2122 // @interface context.
2123 if (Tok.isAtStartOfLine() && NextToken().is(K: tok::kw_namespace) &&
2124 (!ParsingInObjCContainer || CurParsedObjCImpl))
2125 return;
2126 break;
2127
2128 case tok::kw_extern:
2129 // 'extern' at the start of a line is almost certainly a good
2130 // place to pick back up parsing
2131 case tok::kw_namespace:
2132 // 'namespace' at the start of a line is almost certainly a good
2133 // place to pick back up parsing, except in an Objective-C
2134 // @interface context.
2135 if (Tok.isAtStartOfLine() &&
2136 (!ParsingInObjCContainer || CurParsedObjCImpl))
2137 return;
2138 break;
2139
2140 case tok::at:
2141 // @end is very much like } in Objective-C contexts.
2142 if (NextToken().isObjCAtKeyword(objcKey: tok::objc_end) &&
2143 ParsingInObjCContainer)
2144 return;
2145 break;
2146
2147 case tok::minus:
2148 case tok::plus:
2149 // - and + probably start new method declarations in Objective-C contexts.
2150 if (Tok.isAtStartOfLine() && ParsingInObjCContainer)
2151 return;
2152 break;
2153
2154 case tok::eof:
2155 case tok::annot_module_begin:
2156 case tok::annot_module_end:
2157 case tok::annot_module_include:
2158 return;
2159
2160 default:
2161 break;
2162 }
2163
2164 ConsumeAnyToken();
2165 }
2166}
2167
2168Parser::DeclGroupPtrTy Parser::ParseDeclGroup(ParsingDeclSpec &DS,
2169 DeclaratorContext Context,
2170 ParsedAttributes &Attrs,
2171 ParsedTemplateInfo &TemplateInfo,
2172 SourceLocation *DeclEnd,
2173 ForRangeInit *FRI) {
2174 // Parse the first declarator.
2175 // Consume all of the attributes from `Attrs` by moving them to our own local
2176 // list. This ensures that we will not attempt to interpret them as statement
2177 // attributes higher up the callchain.
2178 ParsedAttributes LocalAttrs(AttrFactory);
2179 LocalAttrs.takeAllPrependingFrom(Other&: Attrs);
2180 ParsingDeclarator D(*this, DS, LocalAttrs, Context);
2181 if (TemplateInfo.TemplateParams)
2182 D.setTemplateParameterLists(*TemplateInfo.TemplateParams);
2183
2184 bool IsTemplateSpecOrInst =
2185 (TemplateInfo.Kind == ParsedTemplateKind::ExplicitInstantiation ||
2186 TemplateInfo.Kind == ParsedTemplateKind::ExplicitSpecialization);
2187 SuppressAccessChecks SAC(*this, IsTemplateSpecOrInst);
2188
2189 ParseDeclarator(D);
2190
2191 if (IsTemplateSpecOrInst)
2192 SAC.done();
2193
2194 // Bail out if the first declarator didn't seem well-formed.
2195 if (!D.hasName() && !D.mayOmitIdentifier()) {
2196 SkipMalformedDecl();
2197 return nullptr;
2198 }
2199
2200 if (getLangOpts().HLSL)
2201 while (MaybeParseHLSLAnnotations(D))
2202 ;
2203
2204 if (Tok.is(K: tok::kw_requires)) {
2205 TemplateParameterDepthRAII CurTemplateDepthTracker(TemplateParameterDepth);
2206 // With abbreviated function templates - we need to explicitly add depth to
2207 // account for the implicit template parameter list induced by the template.
2208 if (!TemplateInfo.TemplateParams && D.getInventedTemplateParameterList())
2209 ++CurTemplateDepthTracker;
2210 ParseTrailingRequiresClauseWithScope(D);
2211 }
2212
2213 // Save late-parsed attributes for now; they need to be parsed in the
2214 // appropriate function scope after the function Decl has been constructed.
2215 // These will be parsed in ParseFunctionDefinition or ParseLexedAttrList.
2216 LateParsedAttrList LateParsedAttrs(true);
2217 if (D.isFunctionDeclarator()) {
2218 MaybeParseGNUAttributes(D, LateAttrs: &LateParsedAttrs);
2219
2220 // The _Noreturn keyword can't appear here, unlike the GNU noreturn
2221 // attribute. If we find the keyword here, tell the user to put it
2222 // at the start instead.
2223 if (Tok.is(K: tok::kw__Noreturn)) {
2224 SourceLocation Loc = ConsumeToken();
2225 const char *PrevSpec;
2226 unsigned DiagID;
2227
2228 // We can offer a fixit if it's valid to mark this function as _Noreturn
2229 // and we don't have any other declarators in this declaration.
2230 bool Fixit = !DS.setFunctionSpecNoreturn(Loc, PrevSpec, DiagID);
2231 MaybeParseGNUAttributes(D, LateAttrs: &LateParsedAttrs);
2232 Fixit &= Tok.isOneOf(Ks: tok::semi, Ks: tok::l_brace, Ks: tok::kw_try);
2233
2234 Diag(Loc, DiagID: diag::err_c11_noreturn_misplaced)
2235 << (Fixit ? FixItHint::CreateRemoval(RemoveRange: Loc) : FixItHint())
2236 << (Fixit ? FixItHint::CreateInsertion(InsertionLoc: D.getBeginLoc(), Code: "_Noreturn ")
2237 : FixItHint());
2238 }
2239
2240 // Check to see if we have a function *definition* which must have a body.
2241 if (Tok.is(K: tok::equal) && NextToken().is(K: tok::code_completion)) {
2242 cutOffParsing();
2243 Actions.CodeCompletion().CodeCompleteAfterFunctionEquals(D);
2244 return nullptr;
2245 }
2246 // We're at the point where the parsing of function declarator is finished.
2247 //
2248 // A common error is that users accidently add a virtual specifier
2249 // (e.g. override) in an out-line method definition.
2250 // We attempt to recover by stripping all these specifiers coming after
2251 // the declarator.
2252 while (auto Specifier = isCXX11VirtSpecifier()) {
2253 Diag(Tok, DiagID: diag::err_virt_specifier_outside_class)
2254 << VirtSpecifiers::getSpecifierName(VS: Specifier)
2255 << FixItHint::CreateRemoval(RemoveRange: Tok.getLocation());
2256 ConsumeToken();
2257 }
2258 // Look at the next token to make sure that this isn't a function
2259 // declaration. We have to check this because __attribute__ might be the
2260 // start of a function definition in GCC-extended K&R C.
2261 if (!isDeclarationAfterDeclarator()) {
2262
2263 // Function definitions are only allowed at file scope and in C++ classes.
2264 // The C++ inline method definition case is handled elsewhere, so we only
2265 // need to handle the file scope definition case.
2266 if (Context == DeclaratorContext::File) {
2267 if (isStartOfFunctionDefinition(Declarator: D)) {
2268 // C++23 [dcl.typedef] p1:
2269 // The typedef specifier shall not be [...], and it shall not be
2270 // used in the decl-specifier-seq of a parameter-declaration nor in
2271 // the decl-specifier-seq of a function-definition.
2272 if (DS.getStorageClassSpec() == DeclSpec::SCS_typedef) {
2273 // If the user intended to write 'typename', we should have already
2274 // suggested adding it elsewhere. In any case, recover by ignoring
2275 // 'typedef' and suggest removing it.
2276 Diag(Loc: DS.getStorageClassSpecLoc(),
2277 DiagID: diag::err_function_declared_typedef)
2278 << FixItHint::CreateRemoval(RemoveRange: DS.getStorageClassSpecLoc());
2279 DS.ClearStorageClassSpecs();
2280 }
2281 Decl *TheDecl = nullptr;
2282
2283 if (TemplateInfo.Kind == ParsedTemplateKind::ExplicitInstantiation) {
2284 if (D.getName().getKind() != UnqualifiedIdKind::IK_TemplateId) {
2285 // If the declarator-id is not a template-id, issue a diagnostic
2286 // and recover by ignoring the 'template' keyword.
2287 Diag(Tok, DiagID: diag::err_template_defn_explicit_instantiation) << 0;
2288 TheDecl = ParseFunctionDefinition(D, TemplateInfo: ParsedTemplateInfo(),
2289 LateParsedAttrs: &LateParsedAttrs);
2290 } else {
2291 SourceLocation LAngleLoc =
2292 PP.getLocForEndOfToken(Loc: TemplateInfo.TemplateLoc);
2293 Diag(Loc: D.getIdentifierLoc(),
2294 DiagID: diag::err_explicit_instantiation_with_definition)
2295 << SourceRange(TemplateInfo.TemplateLoc)
2296 << FixItHint::CreateInsertion(InsertionLoc: LAngleLoc, Code: "<>");
2297
2298 // Recover as if it were an explicit specialization.
2299 TemplateParameterLists FakedParamLists;
2300 FakedParamLists.push_back(Elt: Actions.ActOnTemplateParameterList(
2301 Depth: 0, ExportLoc: SourceLocation(), TemplateLoc: TemplateInfo.TemplateLoc, LAngleLoc, Params: {},
2302 RAngleLoc: LAngleLoc, RequiresClause: nullptr));
2303
2304 TheDecl = ParseFunctionDefinition(
2305 D,
2306 TemplateInfo: ParsedTemplateInfo(&FakedParamLists,
2307 /*isSpecialization=*/true,
2308 /*lastParameterListWasEmpty=*/true),
2309 LateParsedAttrs: &LateParsedAttrs);
2310 }
2311 } else {
2312 TheDecl =
2313 ParseFunctionDefinition(D, TemplateInfo, LateParsedAttrs: &LateParsedAttrs);
2314 }
2315
2316 return Actions.ConvertDeclToDeclGroup(Ptr: TheDecl);
2317 }
2318
2319 if (isDeclarationSpecifier(AllowImplicitTypename: ImplicitTypenameContext::No) ||
2320 Tok.is(K: tok::kw_namespace)) {
2321 // If there is an invalid declaration specifier or a namespace
2322 // definition right after the function prototype, then we must be in a
2323 // missing semicolon case where this isn't actually a body. Just fall
2324 // through into the code that handles it as a prototype, and let the
2325 // top-level code handle the erroneous declspec where it would
2326 // otherwise expect a comma or semicolon. Note that
2327 // isDeclarationSpecifier already covers 'inline namespace', since
2328 // 'inline' can be a declaration specifier.
2329 } else {
2330 Diag(Tok, DiagID: diag::err_expected_fn_body);
2331 SkipUntil(T: tok::semi);
2332 return nullptr;
2333 }
2334 } else {
2335 if (Tok.is(K: tok::l_brace)) {
2336 Diag(Tok, DiagID: diag::err_function_definition_not_allowed);
2337 SkipMalformedDecl();
2338 return nullptr;
2339 }
2340 }
2341 }
2342 }
2343
2344 if (ParseAsmAttributesAfterDeclarator(D))
2345 return nullptr;
2346
2347 // C++0x [stmt.iter]p1: Check if we have a for-range-declarator. If so, we
2348 // must parse and analyze the for-range-initializer before the declaration is
2349 // analyzed.
2350 //
2351 // Handle the Objective-C for-in loop variable similarly, although we
2352 // don't need to parse the container in advance.
2353 if (FRI && (Tok.is(K: tok::colon) || isTokIdentifier_in())) {
2354 // If we're parsing an expansion statement, enter its context to ensure
2355 // the declaration ends up in a dependent context. We previously left the
2356 // context of the expansion statement because init-statements should *not*
2357 // be in a dependent context, and only once we get here do we know that this
2358 // is not an init-statement but rather a for-range-declaration.
2359 //
2360 // Note that this is *not* the case if we get here via ParseCXXCondition()
2361 // since if that is called when we parse an expansion statement, we know for
2362 // sure that it has to be the for-range-declaration.
2363 //
2364 // We can't use ContextRAII here since that pushes a new delayed diagnostics
2365 // pool, which causes issues during declaration parsing.
2366 bool EnterContext = FRI->ExpansionStmt &&
2367 Actions.CurContext == FRI->ExpansionStmt->getParent();
2368 if (EnterContext)
2369 Actions.PushDeclContext(S: nullptr, DC: FRI->ExpansionStmt);
2370 llvm::scope_exit RestoreDeclContext{[&] {
2371 if (EnterContext)
2372 Actions.PopDeclContext();
2373 }};
2374
2375 bool IsForRangeLoopOrExpansionStmt = false;
2376 if (TryConsumeToken(Expected: tok::colon, Loc&: FRI->ColonLoc)) {
2377 IsForRangeLoopOrExpansionStmt = true;
2378 if (getLangOpts().OpenMP && !FRI->ExpansionStmt)
2379 Actions.OpenMP().startOpenMPCXXRangeFor();
2380
2381 ParseForRangeInitializerAfterColon(FRI&: *FRI, VarDeclSpec: &DS);
2382 }
2383
2384 Decl *ThisDecl = Actions.ActOnDeclarator(S: getCurScope(), D);
2385 if (IsForRangeLoopOrExpansionStmt) {
2386 Actions.ActOnCXXForRangeDecl(D: ThisDecl, InExpansionStmt: FRI->ExpansionStmt);
2387 } else {
2388 // Obj-C for loop
2389 if (auto *VD = dyn_cast_or_null<VarDecl>(Val: ThisDecl))
2390 VD->setObjCForDecl(true);
2391 }
2392 Actions.FinalizeDeclaration(D: ThisDecl);
2393 D.complete(D: ThisDecl);
2394 return Actions.FinalizeDeclaratorGroup(S: getCurScope(), DS, Group: ThisDecl);
2395 }
2396
2397 SmallVector<Decl *, 8> DeclsInGroup;
2398 Decl *FirstDecl =
2399 ParseDeclarationAfterDeclaratorAndAttributes(D, TemplateInfo, FRI);
2400 if (LateParsedAttrs.size() > 0)
2401 ParseLexedAttributeList(LAs&: LateParsedAttrs, D: FirstDecl, EnterScope: true, OnDefinition: false);
2402 D.complete(D: FirstDecl);
2403 if (FirstDecl)
2404 DeclsInGroup.push_back(Elt: FirstDecl);
2405
2406 bool ExpectSemi = Context != DeclaratorContext::ForInit;
2407
2408 // If we don't have a comma, it is either the end of the list (a ';') or an
2409 // error, bail out.
2410 SourceLocation CommaLoc;
2411 while (TryConsumeToken(Expected: tok::comma, Loc&: CommaLoc)) {
2412 if (Tok.isAtStartOfLine() && ExpectSemi && !MightBeDeclarator(Context)) {
2413 // This comma was followed by a line-break and something which can't be
2414 // the start of a declarator. The comma was probably a typo for a
2415 // semicolon.
2416 Diag(Loc: CommaLoc, DiagID: diag::err_expected_semi_declaration)
2417 << FixItHint::CreateReplacement(RemoveRange: CommaLoc, Code: ";");
2418 ExpectSemi = false;
2419 break;
2420 }
2421
2422 // C++23 [temp.pre]p5:
2423 // In a template-declaration, explicit specialization, or explicit
2424 // instantiation the init-declarator-list in the declaration shall
2425 // contain at most one declarator.
2426 if (TemplateInfo.Kind != ParsedTemplateKind::NonTemplate &&
2427 D.isFirstDeclarator()) {
2428 Diag(Loc: CommaLoc, DiagID: diag::err_multiple_template_declarators)
2429 << TemplateInfo.Kind;
2430 }
2431
2432 // Parse the next declarator.
2433 D.clear();
2434 D.setCommaLoc(CommaLoc);
2435
2436 // Accept attributes in an init-declarator. In the first declarator in a
2437 // declaration, these would be part of the declspec. In subsequent
2438 // declarators, they become part of the declarator itself, so that they
2439 // don't apply to declarators after *this* one. Examples:
2440 // short __attribute__((common)) var; -> declspec
2441 // short var __attribute__((common)); -> declarator
2442 // short x, __attribute__((common)) var; -> declarator
2443 MaybeParseGNUAttributes(D);
2444
2445 // MSVC parses but ignores qualifiers after the comma as an extension.
2446 if (getLangOpts().MicrosoftExt)
2447 DiagnoseAndSkipExtendedMicrosoftTypeAttributes();
2448
2449 ParseDeclarator(D);
2450
2451 if (getLangOpts().HLSL)
2452 MaybeParseHLSLAnnotations(D);
2453
2454 if (!D.isInvalidType()) {
2455 // C++2a [dcl.decl]p1
2456 // init-declarator:
2457 // declarator initializer[opt]
2458 // declarator requires-clause
2459 if (Tok.is(K: tok::kw_requires))
2460 ParseTrailingRequiresClauseWithScope(D);
2461 Decl *ThisDecl = ParseDeclarationAfterDeclarator(D, TemplateInfo);
2462 D.complete(D: ThisDecl);
2463 if (ThisDecl)
2464 DeclsInGroup.push_back(Elt: ThisDecl);
2465 }
2466 }
2467
2468 if (DeclEnd)
2469 *DeclEnd = Tok.getLocation();
2470
2471 if (ExpectSemi && ExpectAndConsumeSemi(
2472 DiagID: Context == DeclaratorContext::File
2473 ? diag::err_invalid_token_after_toplevel_declarator
2474 : diag::err_expected_semi_declaration)) {
2475 // Okay, there was no semicolon and one was expected. If we see a
2476 // declaration specifier, just assume it was missing and continue parsing.
2477 // Otherwise things are very confused and we skip to recover.
2478 if (!isDeclarationSpecifier(AllowImplicitTypename: ImplicitTypenameContext::No))
2479 SkipMalformedDecl();
2480 }
2481
2482 return Actions.FinalizeDeclaratorGroup(S: getCurScope(), DS, Group: DeclsInGroup);
2483}
2484
2485bool Parser::ParseAsmAttributesAfterDeclarator(Declarator &D) {
2486 // If a simple-asm-expr is present, parse it.
2487 if (Tok.is(K: tok::kw_asm)) {
2488 SourceLocation Loc;
2489 ExprResult AsmLabel(ParseSimpleAsm(/*ForAsmLabel*/ true, EndLoc: &Loc));
2490 if (AsmLabel.isInvalid()) {
2491 SkipUntil(T: tok::semi, Flags: StopBeforeMatch);
2492 return true;
2493 }
2494
2495 D.setAsmLabel(AsmLabel.get());
2496 D.SetRangeEnd(Loc);
2497 }
2498
2499 MaybeParseGNUAttributes(D);
2500 return false;
2501}
2502
2503Decl *Parser::ParseDeclarationAfterDeclarator(
2504 Declarator &D, const ParsedTemplateInfo &TemplateInfo) {
2505 if (ParseAsmAttributesAfterDeclarator(D))
2506 return nullptr;
2507
2508 return ParseDeclarationAfterDeclaratorAndAttributes(D, TemplateInfo);
2509}
2510
2511Decl *Parser::ParseDeclarationAfterDeclaratorAndAttributes(
2512 Declarator &D, const ParsedTemplateInfo &TemplateInfo, ForRangeInit *FRI) {
2513 // RAII type used to track whether we're inside an initializer.
2514 struct InitializerScopeRAII {
2515 Parser &P;
2516 Declarator &D;
2517 Decl *ThisDecl;
2518 bool Entered;
2519
2520 InitializerScopeRAII(Parser &P, Declarator &D, Decl *ThisDecl)
2521 : P(P), D(D), ThisDecl(ThisDecl), Entered(false) {
2522 if (ThisDecl && P.getLangOpts().CPlusPlus) {
2523 Scope *S = nullptr;
2524 if (D.getCXXScopeSpec().isSet()) {
2525 P.EnterScope(ScopeFlags: 0);
2526 S = P.getCurScope();
2527 }
2528 if (ThisDecl && !ThisDecl->isInvalidDecl()) {
2529 P.Actions.ActOnCXXEnterDeclInitializer(S, Dcl: ThisDecl);
2530 Entered = true;
2531 }
2532 }
2533 }
2534 ~InitializerScopeRAII() {
2535 if (ThisDecl && P.getLangOpts().CPlusPlus) {
2536 Scope *S = nullptr;
2537 if (D.getCXXScopeSpec().isSet())
2538 S = P.getCurScope();
2539
2540 if (Entered)
2541 P.Actions.ActOnCXXExitDeclInitializer(S, Dcl: ThisDecl);
2542 if (S)
2543 P.ExitScope();
2544 }
2545 ThisDecl = nullptr;
2546 }
2547 };
2548
2549 enum class InitKind { Uninitialized, Equal, CXXDirect, CXXBraced };
2550 InitKind TheInitKind;
2551 // If a '==' or '+=' is found, suggest a fixit to '='.
2552 if (isTokenEqualOrEqualTypo())
2553 TheInitKind = InitKind::Equal;
2554 else if (getLangOpts().CPlusPlus && Tok.is(K: tok::l_paren))
2555 TheInitKind = InitKind::CXXDirect;
2556 else if (getLangOpts().CPlusPlus11 && Tok.is(K: tok::l_brace) &&
2557 (!CurParsedObjCImpl || !D.isFunctionDeclarator()))
2558 TheInitKind = InitKind::CXXBraced;
2559 else
2560 TheInitKind = InitKind::Uninitialized;
2561 if (TheInitKind != InitKind::Uninitialized)
2562 D.setHasInitializer();
2563
2564 // Inform Sema that we just parsed this declarator.
2565 Decl *ThisDecl = nullptr;
2566 Decl *OuterDecl = nullptr;
2567 switch (TemplateInfo.Kind) {
2568 case ParsedTemplateKind::NonTemplate:
2569 ThisDecl = Actions.ActOnDeclarator(S: getCurScope(), D);
2570 break;
2571
2572 case ParsedTemplateKind::Template:
2573 case ParsedTemplateKind::ExplicitSpecialization: {
2574 ThisDecl = Actions.ActOnTemplateDeclarator(S: getCurScope(),
2575 TemplateParameterLists: *TemplateInfo.TemplateParams,
2576 D);
2577 if (VarTemplateDecl *VT = dyn_cast_or_null<VarTemplateDecl>(Val: ThisDecl)) {
2578 // Re-direct this decl to refer to the templated decl so that we can
2579 // initialize it.
2580 ThisDecl = VT->getTemplatedDecl();
2581 OuterDecl = VT;
2582 }
2583 break;
2584 }
2585 case ParsedTemplateKind::ExplicitInstantiation: {
2586 if (Tok.is(K: tok::semi)) {
2587 DeclResult ThisRes = Actions.ActOnExplicitInstantiation(
2588 S: getCurScope(), ExternLoc: TemplateInfo.ExternLoc, TemplateLoc: TemplateInfo.TemplateLoc, D);
2589 if (ThisRes.isInvalid()) {
2590 SkipUntil(T: tok::semi, Flags: StopBeforeMatch);
2591 return nullptr;
2592 }
2593 ThisDecl = ThisRes.get();
2594 } else {
2595 // FIXME: This check should be for a variable template instantiation only.
2596
2597 // Check that this is a valid instantiation
2598 if (D.getName().getKind() != UnqualifiedIdKind::IK_TemplateId) {
2599 // If the declarator-id is not a template-id, issue a diagnostic and
2600 // recover by ignoring the 'template' keyword.
2601 Diag(Tok, DiagID: diag::err_template_defn_explicit_instantiation)
2602 << 2 << FixItHint::CreateRemoval(RemoveRange: TemplateInfo.TemplateLoc);
2603 ThisDecl = Actions.ActOnDeclarator(S: getCurScope(), D);
2604 } else {
2605 SourceLocation LAngleLoc =
2606 PP.getLocForEndOfToken(Loc: TemplateInfo.TemplateLoc);
2607 Diag(Loc: D.getIdentifierLoc(),
2608 DiagID: diag::err_explicit_instantiation_with_definition)
2609 << SourceRange(TemplateInfo.TemplateLoc)
2610 << FixItHint::CreateInsertion(InsertionLoc: LAngleLoc, Code: "<>");
2611
2612 // Recover as if it were an explicit specialization.
2613 TemplateParameterLists FakedParamLists;
2614 FakedParamLists.push_back(Elt: Actions.ActOnTemplateParameterList(
2615 Depth: 0, ExportLoc: SourceLocation(), TemplateLoc: TemplateInfo.TemplateLoc, LAngleLoc, Params: {},
2616 RAngleLoc: LAngleLoc, RequiresClause: nullptr));
2617
2618 ThisDecl =
2619 Actions.ActOnTemplateDeclarator(S: getCurScope(), TemplateParameterLists: FakedParamLists, D);
2620 }
2621 }
2622 break;
2623 }
2624 }
2625
2626 SemaCUDA::CUDATargetContextRAII X(Actions.CUDA(),
2627 SemaCUDA::CTCK_InitGlobalVar, ThisDecl);
2628 switch (TheInitKind) {
2629 // Parse declarator '=' initializer.
2630 case InitKind::Equal: {
2631 SourceLocation EqualLoc = ConsumeToken();
2632
2633 if (Tok.is(K: tok::kw_delete)) {
2634 if (D.isFunctionDeclarator())
2635 Diag(Loc: ConsumeToken(), DiagID: diag::err_default_delete_in_multiple_declaration)
2636 << 1 /* delete */;
2637 else
2638 Diag(Loc: ConsumeToken(), DiagID: diag::err_deleted_non_function);
2639 SkipDeletedFunctionBody();
2640 } else if (Tok.is(K: tok::kw_default)) {
2641 if (D.isFunctionDeclarator())
2642 Diag(Loc: ConsumeToken(), DiagID: diag::err_default_delete_in_multiple_declaration)
2643 << 0 /* default */;
2644 else
2645 Diag(Loc: ConsumeToken(), DiagID: diag::err_default_special_members)
2646 << getLangOpts().CPlusPlus20;
2647 } else {
2648 InitializerScopeRAII InitScope(*this, D, ThisDecl);
2649
2650 if (Tok.is(K: tok::code_completion)) {
2651 cutOffParsing();
2652 Actions.CodeCompletion().CodeCompleteInitializer(S: getCurScope(),
2653 D: ThisDecl);
2654 Actions.FinalizeDeclaration(D: ThisDecl);
2655 return nullptr;
2656 }
2657
2658 PreferredType.enterVariableInit(Tok: Tok.getLocation(), D: ThisDecl);
2659 ExprResult Init = ParseInitializer(DeclForInitializer: ThisDecl);
2660
2661 // If this is the only decl in (possibly) range based for statement,
2662 // our best guess is that the user meant ':' instead of '='.
2663 if (Tok.is(K: tok::r_paren) && FRI && D.isFirstDeclarator()) {
2664 Diag(Loc: EqualLoc, DiagID: diag::err_single_decl_assign_in_for_range)
2665 << FixItHint::CreateReplacement(RemoveRange: EqualLoc, Code: ":");
2666 // We are trying to stop parser from looking for ';' in this for
2667 // statement, therefore preventing spurious errors to be issued.
2668 FRI->ColonLoc = EqualLoc;
2669 Init = ExprError();
2670 FRI->RangeExpr = Init;
2671 }
2672
2673 if (Init.isInvalid()) {
2674 SmallVector<tok::TokenKind, 2> StopTokens;
2675 StopTokens.push_back(Elt: tok::comma);
2676 if (D.getContext() == DeclaratorContext::ForInit ||
2677 D.getContext() == DeclaratorContext::SelectionInit)
2678 StopTokens.push_back(Elt: tok::r_paren);
2679 SkipUntil(Toks: StopTokens, Flags: StopAtSemi | StopBeforeMatch);
2680 Actions.ActOnInitializerError(Dcl: ThisDecl);
2681 } else
2682 Actions.AddInitializerToDecl(dcl: ThisDecl, init: Init.get(),
2683 /*DirectInit=*/false);
2684 }
2685 break;
2686 }
2687 case InitKind::CXXDirect: {
2688 // Parse C++ direct initializer: '(' expression-list ')'
2689 BalancedDelimiterTracker T(*this, tok::l_paren);
2690 T.consumeOpen();
2691
2692 ExprVector Exprs;
2693
2694 InitializerScopeRAII InitScope(*this, D, ThisDecl);
2695
2696 auto ThisVarDecl = dyn_cast_or_null<VarDecl>(Val: ThisDecl);
2697 auto RunSignatureHelp = [&]() {
2698 QualType PreferredType =
2699 Actions.CodeCompletion().ProduceConstructorSignatureHelp(
2700 Type: ThisVarDecl->getType()->getCanonicalTypeInternal(),
2701 Loc: ThisDecl->getLocation(), Args: Exprs, OpenParLoc: T.getOpenLocation(),
2702 /*Braced=*/false);
2703 CalledSignatureHelp = true;
2704 return PreferredType;
2705 };
2706 auto SetPreferredType = [&] {
2707 PreferredType.enterFunctionArgument(Tok: Tok.getLocation(), ComputeType: RunSignatureHelp);
2708 };
2709
2710 llvm::function_ref<void()> ExpressionStarts;
2711 if (ThisVarDecl) {
2712 // ParseExpressionList can sometimes succeed even when ThisDecl is not
2713 // VarDecl. This is an error and it is reported in a call to
2714 // Actions.ActOnInitializerError(). However, we call
2715 // ProduceConstructorSignatureHelp only on VarDecls.
2716 ExpressionStarts = SetPreferredType;
2717 }
2718
2719 bool SawError = ParseExpressionList(Exprs, ExpressionStarts);
2720
2721 if (SawError) {
2722 if (ThisVarDecl && PP.isCodeCompletionReached() && !CalledSignatureHelp) {
2723 Actions.CodeCompletion().ProduceConstructorSignatureHelp(
2724 Type: ThisVarDecl->getType()->getCanonicalTypeInternal(),
2725 Loc: ThisDecl->getLocation(), Args: Exprs, OpenParLoc: T.getOpenLocation(),
2726 /*Braced=*/false);
2727 CalledSignatureHelp = true;
2728 }
2729 Actions.ActOnInitializerError(Dcl: ThisDecl);
2730 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
2731 } else {
2732 // Match the ')'.
2733 T.consumeClose();
2734
2735 ExprResult Initializer = Actions.ActOnParenListExpr(L: T.getOpenLocation(),
2736 R: T.getCloseLocation(),
2737 Val: Exprs);
2738 Actions.AddInitializerToDecl(dcl: ThisDecl, init: Initializer.get(),
2739 /*DirectInit=*/true);
2740 }
2741 break;
2742 }
2743 case InitKind::CXXBraced: {
2744 // Parse C++0x braced-init-list.
2745 Diag(Tok, DiagID: diag::compat_cxx11_generalized_initializer_lists);
2746
2747 InitializerScopeRAII InitScope(*this, D, ThisDecl);
2748
2749 PreferredType.enterVariableInit(Tok: Tok.getLocation(), D: ThisDecl);
2750 ExprResult Init(ParseBraceInitializer());
2751
2752 if (Init.isInvalid()) {
2753 Actions.ActOnInitializerError(Dcl: ThisDecl);
2754 } else
2755 Actions.AddInitializerToDecl(dcl: ThisDecl, init: Init.get(), /*DirectInit=*/true);
2756 break;
2757 }
2758 case InitKind::Uninitialized: {
2759 InitializerScopeRAII InitScope(*this, D, ThisDecl);
2760 Actions.ActOnUninitializedDecl(dcl: ThisDecl);
2761 break;
2762 }
2763 }
2764
2765 Actions.FinalizeDeclaration(D: ThisDecl);
2766 return OuterDecl ? OuterDecl : ThisDecl;
2767}
2768
2769void Parser::ParseSpecifierQualifierList(
2770 DeclSpec &DS, ImplicitTypenameContext AllowImplicitTypename,
2771 AccessSpecifier AS, DeclSpecContext DSC) {
2772 ParsedTemplateInfo TemplateInfo;
2773 /// specifier-qualifier-list is a subset of declaration-specifiers. Just
2774 /// parse declaration-specifiers and complain about extra stuff.
2775 /// TODO: diagnose attribute-specifiers and alignment-specifiers.
2776 ParseDeclarationSpecifiers(DS, TemplateInfo, AS, DSC, LateAttrs: nullptr,
2777 AllowImplicitTypename);
2778
2779 // Validate declspec for type-name.
2780 unsigned Specs = DS.getParsedSpecifiers();
2781 if (isTypeSpecifier(DSC) && !DS.hasTypeSpecifier()) {
2782 Diag(Tok, DiagID: diag::err_expected_type);
2783 DS.SetTypeSpecError();
2784 } else if (Specs == DeclSpec::PQ_None && !DS.hasAttributes()) {
2785 Diag(Tok, DiagID: diag::err_typename_requires_specqual);
2786 if (!DS.hasTypeSpecifier())
2787 DS.SetTypeSpecError();
2788 }
2789
2790 // Issue diagnostic and remove storage class if present.
2791 if (Specs & DeclSpec::PQ_StorageClassSpecifier) {
2792 if (DS.getStorageClassSpecLoc().isValid())
2793 Diag(Loc: DS.getStorageClassSpecLoc(),DiagID: diag::err_typename_invalid_storageclass);
2794 else
2795 Diag(Loc: DS.getThreadStorageClassSpecLoc(),
2796 DiagID: diag::err_typename_invalid_storageclass);
2797 DS.ClearStorageClassSpecs();
2798 }
2799
2800 // Issue diagnostic and remove function specifier if present.
2801 if (Specs & DeclSpec::PQ_FunctionSpecifier) {
2802 if (DS.isInlineSpecified())
2803 Diag(Loc: DS.getInlineSpecLoc(), DiagID: diag::err_typename_invalid_functionspec);
2804 if (DS.isVirtualSpecified())
2805 Diag(Loc: DS.getVirtualSpecLoc(), DiagID: diag::err_typename_invalid_functionspec);
2806 if (DS.hasExplicitSpecifier())
2807 Diag(Loc: DS.getExplicitSpecLoc(), DiagID: diag::err_typename_invalid_functionspec);
2808 if (DS.isNoreturnSpecified())
2809 Diag(Loc: DS.getNoreturnSpecLoc(), DiagID: diag::err_typename_invalid_functionspec);
2810 DS.ClearFunctionSpecs();
2811 }
2812
2813 // Issue diagnostic and remove constexpr specifier if present.
2814 if (DS.hasConstexprSpecifier() && DSC != DeclSpecContext::DSC_condition) {
2815 Diag(Loc: DS.getConstexprSpecLoc(), DiagID: diag::err_typename_invalid_constexpr)
2816 << static_cast<int>(DS.getConstexprSpecifier());
2817 DS.ClearConstexprSpec();
2818 }
2819}
2820
2821/// isValidAfterIdentifierInDeclaratorAfterDeclSpec - Return true if the
2822/// specified token is valid after the identifier in a declarator which
2823/// immediately follows the declspec. For example, these things are valid:
2824///
2825/// int x [ 4]; // direct-declarator
2826/// int x ( int y); // direct-declarator
2827/// int(int x ) // direct-declarator
2828/// int x ; // simple-declaration
2829/// int x = 17; // init-declarator-list
2830/// int x , y; // init-declarator-list
2831/// int x __asm__ ("foo"); // init-declarator-list
2832/// int x : 4; // struct-declarator
2833/// int x { 5}; // C++'0x unified initializers
2834///
2835/// This is not, because 'x' does not immediately follow the declspec (though
2836/// ')' happens to be valid anyway).
2837/// int (x)
2838///
2839static bool isValidAfterIdentifierInDeclarator(const Token &T) {
2840 return T.isOneOf(Ks: tok::l_square, Ks: tok::l_paren, Ks: tok::r_paren, Ks: tok::semi,
2841 Ks: tok::comma, Ks: tok::equal, Ks: tok::kw_asm, Ks: tok::l_brace,
2842 Ks: tok::colon);
2843}
2844
2845bool Parser::ParseImplicitInt(DeclSpec &DS, CXXScopeSpec *SS,
2846 ParsedTemplateInfo &TemplateInfo,
2847 AccessSpecifier AS, DeclSpecContext DSC,
2848 ParsedAttributes &Attrs) {
2849 assert(Tok.is(tok::identifier) && "should have identifier");
2850
2851 SourceLocation Loc = Tok.getLocation();
2852 // If we see an identifier that is not a type name, we normally would
2853 // parse it as the identifier being declared. However, when a typename
2854 // is typo'd or the definition is not included, this will incorrectly
2855 // parse the typename as the identifier name and fall over misparsing
2856 // later parts of the diagnostic.
2857 //
2858 // As such, we try to do some look-ahead in cases where this would
2859 // otherwise be an "implicit-int" case to see if this is invalid. For
2860 // example: "static foo_t x = 4;" In this case, if we parsed foo_t as
2861 // an identifier with implicit int, we'd get a parse error because the
2862 // next token is obviously invalid for a type. Parse these as a case
2863 // with an invalid type specifier.
2864 assert(!DS.hasTypeSpecifier() && "Type specifier checked above");
2865
2866 // Since we know that this either implicit int (which is rare) or an
2867 // error, do lookahead to try to do better recovery. This never applies
2868 // within a type specifier. Outside of C++, we allow this even if the
2869 // language doesn't "officially" support implicit int -- we support
2870 // implicit int as an extension in some language modes.
2871 if (!isTypeSpecifier(DSC) && getLangOpts().isImplicitIntAllowed() &&
2872 isValidAfterIdentifierInDeclarator(T: NextToken())) {
2873 // If this token is valid for implicit int, e.g. "static x = 4", then
2874 // we just avoid eating the identifier, so it will be parsed as the
2875 // identifier in the declarator.
2876 return false;
2877 }
2878
2879 // Early exit as Sema has a dedicated missing_actual_pipe_type diagnostic
2880 // for incomplete declarations such as `pipe p`.
2881 if (getLangOpts().OpenCLCPlusPlus && DS.isTypeSpecPipe())
2882 return false;
2883
2884 if (getLangOpts().CPlusPlus &&
2885 DS.getStorageClassSpec() == DeclSpec::SCS_auto) {
2886 // Don't require a type specifier if we have the 'auto' storage class
2887 // specifier in C++98 -- we'll promote it to a type specifier.
2888 if (SS)
2889 AnnotateScopeToken(SS&: *SS, /*IsNewAnnotation*/false);
2890 return false;
2891 }
2892
2893 if (getLangOpts().CPlusPlus && (!SS || SS->isEmpty()) &&
2894 getLangOpts().MSVCCompat) {
2895 // Lookup of an unqualified type name has failed in MSVC compatibility mode.
2896 // Give Sema a chance to recover if we are in a template with dependent base
2897 // classes.
2898 if (ParsedType T = Actions.ActOnMSVCUnknownTypeName(
2899 II: *Tok.getIdentifierInfo(), NameLoc: Tok.getLocation(),
2900 IsTemplateTypeArg: DSC == DeclSpecContext::DSC_template_type_arg)) {
2901 const char *PrevSpec;
2902 unsigned DiagID;
2903 DS.SetTypeSpecType(T: DeclSpec::TST_typename, Loc, PrevSpec, DiagID, Rep: T,
2904 Policy: Actions.getASTContext().getPrintingPolicy());
2905 DS.SetRangeEnd(Tok.getLocation());
2906 ConsumeToken();
2907 return false;
2908 }
2909 }
2910
2911 // Otherwise, if we don't consume this token, we are going to emit an
2912 // error anyway. Try to recover from various common problems. Check
2913 // to see if this was a reference to a tag name without a tag specified.
2914 // This is a common problem in C (saying 'foo' instead of 'struct foo').
2915 //
2916 // C++ doesn't need this, and isTagName doesn't take SS.
2917 if (SS == nullptr) {
2918 const char *TagName = nullptr, *FixitTagName = nullptr;
2919 tok::TokenKind TagKind = tok::unknown;
2920
2921 switch (Actions.isTagName(II&: *Tok.getIdentifierInfo(), S: getCurScope())) {
2922 default: break;
2923 case DeclSpec::TST_enum:
2924 TagName="enum" ; FixitTagName = "enum " ; TagKind=tok::kw_enum ;break;
2925 case DeclSpec::TST_union:
2926 TagName="union" ; FixitTagName = "union " ;TagKind=tok::kw_union ;break;
2927 case DeclSpec::TST_struct:
2928 TagName="struct"; FixitTagName = "struct ";TagKind=tok::kw_struct;break;
2929 case DeclSpec::TST_interface:
2930 TagName="__interface"; FixitTagName = "__interface ";
2931 TagKind=tok::kw___interface;break;
2932 case DeclSpec::TST_class:
2933 TagName="class" ; FixitTagName = "class " ;TagKind=tok::kw_class ;break;
2934 }
2935
2936 if (TagName) {
2937 IdentifierInfo *TokenName = Tok.getIdentifierInfo();
2938 LookupResult R(Actions, TokenName, SourceLocation(),
2939 Sema::LookupOrdinaryName);
2940
2941 Diag(Loc, DiagID: diag::err_use_of_tag_name_without_tag)
2942 << TokenName << TagName << getLangOpts().CPlusPlus
2943 << FixItHint::CreateInsertion(InsertionLoc: Tok.getLocation(), Code: FixitTagName);
2944
2945 if (Actions.LookupName(R, S: getCurScope())) {
2946 for (LookupResult::iterator I = R.begin(), IEnd = R.end();
2947 I != IEnd; ++I)
2948 Diag(Loc: (*I)->getLocation(), DiagID: diag::note_decl_hiding_tag_type)
2949 << TokenName << TagName;
2950 }
2951
2952 // Parse this as a tag as if the missing tag were present.
2953 if (TagKind == tok::kw_enum)
2954 ParseEnumSpecifier(TagLoc: Loc, DS, TemplateInfo, AS,
2955 DSC: DeclSpecContext::DSC_normal);
2956 else
2957 ParseClassSpecifier(TagTokKind: TagKind, TagLoc: Loc, DS, TemplateInfo, AS,
2958 /*EnteringContext*/ false,
2959 DSC: DeclSpecContext::DSC_normal, Attributes&: Attrs);
2960 return true;
2961 }
2962 }
2963
2964 // Determine whether this identifier could plausibly be the name of something
2965 // being declared (with a missing type).
2966 if (!isTypeSpecifier(DSC) && (!SS || DSC == DeclSpecContext::DSC_top_level ||
2967 DSC == DeclSpecContext::DSC_class)) {
2968 // Look ahead to the next token to try to figure out what this declaration
2969 // was supposed to be.
2970 switch (NextToken().getKind()) {
2971 case tok::l_paren: {
2972 // static x(4); // 'x' is not a type
2973 // x(int n); // 'x' is not a type
2974 // x (*p)[]; // 'x' is a type
2975 //
2976 // Since we're in an error case, we can afford to perform a tentative
2977 // parse to determine which case we're in.
2978 TentativeParsingAction PA(*this);
2979 ConsumeToken();
2980 TPResult TPR = TryParseDeclarator(/*mayBeAbstract*/false);
2981 PA.Revert();
2982
2983 if (TPR != TPResult::False) {
2984 // The identifier is followed by a parenthesized declarator.
2985 // It's supposed to be a type.
2986 break;
2987 }
2988
2989 // If we're in a context where we could be declaring a constructor,
2990 // check whether this is a constructor declaration with a bogus name.
2991 if (DSC == DeclSpecContext::DSC_class ||
2992 (DSC == DeclSpecContext::DSC_top_level && SS)) {
2993 IdentifierInfo *II = Tok.getIdentifierInfo();
2994 if (Actions.isCurrentClassNameTypo(II, SS)) {
2995 Diag(Loc, DiagID: diag::err_constructor_bad_name)
2996 << Tok.getIdentifierInfo() << II
2997 << FixItHint::CreateReplacement(RemoveRange: Tok.getLocation(), Code: II->getName());
2998 Tok.setIdentifierInfo(II);
2999 }
3000 }
3001 // Fall through.
3002 [[fallthrough]];
3003 }
3004 case tok::comma:
3005 case tok::equal:
3006 case tok::kw_asm:
3007 case tok::l_brace:
3008 case tok::l_square:
3009 case tok::semi:
3010 // This looks like a variable or function declaration. The type is
3011 // probably missing. We're done parsing decl-specifiers.
3012 // But only if we are not in a function prototype scope.
3013 if (getCurScope()->isFunctionPrototypeScope())
3014 break;
3015 if (SS)
3016 AnnotateScopeToken(SS&: *SS, /*IsNewAnnotation*/false);
3017 return false;
3018
3019 default:
3020 // This is probably supposed to be a type. This includes cases like:
3021 // int f(itn);
3022 // struct S { unsigned : 4; };
3023 break;
3024 }
3025 }
3026
3027 // This is almost certainly an invalid type name. Let Sema emit a diagnostic
3028 // and attempt to recover.
3029 ParsedType T;
3030 IdentifierInfo *II = Tok.getIdentifierInfo();
3031 bool IsTemplateName = getLangOpts().CPlusPlus && NextToken().is(K: tok::less);
3032 Actions.DiagnoseUnknownTypeName(II, IILoc: Loc, S: getCurScope(), SS, SuggestedType&: T,
3033 IsTemplateName);
3034 if (T) {
3035 // The action has suggested that the type T could be used. Set that as
3036 // the type in the declaration specifiers, consume the would-be type
3037 // name token, and we're done.
3038 const char *PrevSpec;
3039 unsigned DiagID;
3040 DS.SetTypeSpecType(T: DeclSpec::TST_typename, Loc, PrevSpec, DiagID, Rep: T,
3041 Policy: Actions.getASTContext().getPrintingPolicy());
3042 DS.SetRangeEnd(Tok.getLocation());
3043 ConsumeToken();
3044 // There may be other declaration specifiers after this.
3045 return true;
3046 } else if (II != Tok.getIdentifierInfo()) {
3047 // If no type was suggested, the correction is to a keyword
3048 Tok.setKind(II->getTokenID());
3049 // There may be other declaration specifiers after this.
3050 return true;
3051 }
3052
3053 // Otherwise, the action had no suggestion for us. Mark this as an error.
3054 DS.SetTypeSpecError();
3055 DS.SetRangeEnd(Tok.getLocation());
3056 ConsumeToken();
3057
3058 // Eat any following template arguments.
3059 if (IsTemplateName) {
3060 SourceLocation LAngle, RAngle;
3061 TemplateArgList Args;
3062 ParseTemplateIdAfterTemplateName(ConsumeLastToken: true, LAngleLoc&: LAngle, TemplateArgs&: Args, RAngleLoc&: RAngle);
3063 }
3064
3065 // TODO: Could inject an invalid typedef decl in an enclosing scope to
3066 // avoid rippling error messages on subsequent uses of the same type,
3067 // could be useful if #include was forgotten.
3068 return true;
3069}
3070
3071Parser::DeclSpecContext
3072Parser::getDeclSpecContextFromDeclaratorContext(DeclaratorContext Context) {
3073 switch (Context) {
3074 case DeclaratorContext::Member:
3075 return DeclSpecContext::DSC_class;
3076 case DeclaratorContext::File:
3077 return DeclSpecContext::DSC_top_level;
3078 case DeclaratorContext::TemplateParam:
3079 return DeclSpecContext::DSC_template_param;
3080 case DeclaratorContext::TemplateArg:
3081 return DeclSpecContext::DSC_template_arg;
3082 case DeclaratorContext::TemplateTypeArg:
3083 return DeclSpecContext::DSC_template_type_arg;
3084 case DeclaratorContext::TrailingReturn:
3085 case DeclaratorContext::TrailingReturnVar:
3086 return DeclSpecContext::DSC_trailing;
3087 case DeclaratorContext::AliasDecl:
3088 case DeclaratorContext::AliasTemplate:
3089 return DeclSpecContext::DSC_alias_declaration;
3090 case DeclaratorContext::Association:
3091 return DeclSpecContext::DSC_association;
3092 case DeclaratorContext::TypeName:
3093 return DeclSpecContext::DSC_type_specifier;
3094 case DeclaratorContext::Condition:
3095 return DeclSpecContext::DSC_condition;
3096 case DeclaratorContext::ConversionId:
3097 return DeclSpecContext::DSC_conv_operator;
3098 case DeclaratorContext::CXXNew:
3099 return DeclSpecContext::DSC_new;
3100 case DeclaratorContext::Prototype:
3101 case DeclaratorContext::ObjCResult:
3102 case DeclaratorContext::ObjCParameter:
3103 case DeclaratorContext::KNRTypeList:
3104 case DeclaratorContext::FunctionalCast:
3105 case DeclaratorContext::Block:
3106 case DeclaratorContext::ForInit:
3107 case DeclaratorContext::SelectionInit:
3108 case DeclaratorContext::CXXCatch:
3109 case DeclaratorContext::ObjCCatch:
3110 case DeclaratorContext::BlockLiteral:
3111 case DeclaratorContext::LambdaExpr:
3112 case DeclaratorContext::LambdaExprParameter:
3113 case DeclaratorContext::RequiresExpr:
3114 return DeclSpecContext::DSC_normal;
3115 }
3116
3117 llvm_unreachable("Missing DeclaratorContext case");
3118}
3119
3120ExprResult Parser::ParseAlignArgument(StringRef KWName, SourceLocation Start,
3121 SourceLocation &EllipsisLoc, bool &IsType,
3122 ParsedType &TypeResult) {
3123 ExprResult ER;
3124 if (isTypeIdInParens()) {
3125 SourceLocation TypeLoc = Tok.getLocation();
3126 ParsedType Ty = ParseTypeName().get();
3127 SourceRange TypeRange(Start, Tok.getLocation());
3128 if (Actions.ActOnAlignasTypeArgument(KWName, Ty, OpLoc: TypeLoc, R: TypeRange))
3129 return ExprError();
3130 TypeResult = Ty;
3131 IsType = true;
3132 } else {
3133 ER = ParseConstantExpression();
3134 IsType = false;
3135 }
3136
3137 if (getLangOpts().CPlusPlus11)
3138 TryConsumeToken(Expected: tok::ellipsis, Loc&: EllipsisLoc);
3139
3140 return ER;
3141}
3142
3143void Parser::ParseAlignmentSpecifier(ParsedAttributes &Attrs,
3144 SourceLocation *EndLoc) {
3145 assert(Tok.isOneOf(tok::kw_alignas, tok::kw__Alignas) &&
3146 "Not an alignment-specifier!");
3147 Token KWTok = Tok;
3148 IdentifierInfo *KWName = KWTok.getIdentifierInfo();
3149 auto Kind = KWTok.getKind();
3150 SourceLocation KWLoc = ConsumeToken();
3151
3152 BalancedDelimiterTracker T(*this, tok::l_paren);
3153 if (T.expectAndConsume())
3154 return;
3155
3156 bool IsType;
3157 ParsedType TypeResult;
3158 SourceLocation EllipsisLoc;
3159 ExprResult ArgExpr =
3160 ParseAlignArgument(KWName: PP.getSpelling(Tok: KWTok), Start: T.getOpenLocation(),
3161 EllipsisLoc, IsType, TypeResult);
3162 if (ArgExpr.isInvalid()) {
3163 T.skipToEnd();
3164 return;
3165 }
3166
3167 T.consumeClose();
3168 if (EndLoc)
3169 *EndLoc = T.getCloseLocation();
3170
3171 if (IsType) {
3172 Attrs.addNewTypeAttr(attrName: KWName, attrRange: KWLoc, scope: AttributeScopeInfo(), typeArg: TypeResult, formUsed: Kind,
3173 ellipsisLoc: EllipsisLoc);
3174 } else {
3175 ArgsVector ArgExprs;
3176 ArgExprs.push_back(Elt: ArgExpr.get());
3177 Attrs.addNew(attrName: KWName, attrRange: KWLoc, scope: AttributeScopeInfo(), args: ArgExprs.data(), numArgs: 1, form: Kind,
3178 ellipsisLoc: EllipsisLoc);
3179 }
3180}
3181
3182void Parser::DistributeCLateParsedAttrs(Decl *Dcl,
3183 LateParsedAttrList *LateAttrs) {
3184 if (!LateAttrs)
3185 return;
3186
3187 if (Dcl) {
3188 for (auto *LateAttr : *LateAttrs) {
3189 if (LateAttr->Decls.empty())
3190 LateAttr->addDecl(D: Dcl);
3191 }
3192 }
3193}
3194
3195void Parser::ParsePtrauthQualifier(ParsedAttributes &Attrs) {
3196 assert(Tok.is(tok::kw___ptrauth));
3197
3198 IdentifierInfo *KwName = Tok.getIdentifierInfo();
3199 SourceLocation KwLoc = ConsumeToken();
3200
3201 BalancedDelimiterTracker T(*this, tok::l_paren);
3202 if (T.expectAndConsume())
3203 return;
3204
3205 ArgsVector ArgExprs;
3206 do {
3207 ExprResult ER = ParseAssignmentExpression();
3208 if (ER.isInvalid()) {
3209 T.skipToEnd();
3210 return;
3211 }
3212 ArgExprs.push_back(Elt: ER.get());
3213 } while (TryConsumeToken(Expected: tok::comma));
3214
3215 T.consumeClose();
3216 SourceLocation EndLoc = T.getCloseLocation();
3217
3218 if (ArgExprs.empty() || ArgExprs.size() > 3) {
3219 Diag(Loc: KwLoc, DiagID: diag::err_ptrauth_qualifier_bad_arg_count);
3220 return;
3221 }
3222
3223 Attrs.addNew(attrName: KwName, attrRange: SourceRange(KwLoc, EndLoc), scope: AttributeScopeInfo(),
3224 args: ArgExprs.data(), numArgs: ArgExprs.size(),
3225 form: ParsedAttr::Form::Keyword(/*IsAlignAs=*/IsAlignas: false,
3226 /*IsRegularKeywordAttribute=*/false));
3227}
3228
3229void Parser::ParseBoundsAttribute(IdentifierInfo &AttrName,
3230 SourceLocation AttrNameLoc,
3231 ParsedAttributes &Attrs,
3232 IdentifierInfo *ScopeName,
3233 SourceLocation ScopeLoc,
3234 ParsedAttr::Form Form) {
3235 assert(Tok.is(tok::l_paren) && "Attribute arg list not starting with '('");
3236
3237 BalancedDelimiterTracker Parens(*this, tok::l_paren);
3238 Parens.consumeOpen();
3239
3240 if (Tok.is(K: tok::r_paren)) {
3241 Diag(Loc: Tok.getLocation(), DiagID: diag::err_argument_required_after_attribute);
3242 Parens.consumeClose();
3243 return;
3244 }
3245
3246 ArgsVector ArgExprs;
3247 // Don't evaluate argument when the attribute is ignored.
3248 using ExpressionKind =
3249 Sema::ExpressionEvaluationContextRecord::ExpressionKind;
3250 EnterExpressionEvaluationContext EC(
3251 Actions, Sema::ExpressionEvaluationContext::PotentiallyEvaluated, nullptr,
3252 ExpressionKind::EK_AttrArgument);
3253
3254 ExprResult ArgExpr = ParseAssignmentExpression();
3255 if (ArgExpr.isInvalid()) {
3256 Parens.skipToEnd();
3257 return;
3258 }
3259
3260 ArgExprs.push_back(Elt: ArgExpr.get());
3261 Parens.consumeClose();
3262
3263 ASTContext &Ctx = Actions.getASTContext();
3264
3265 ArgExprs.push_back(Elt: IntegerLiteral::Create(
3266 C: Ctx, V: llvm::APInt(Ctx.getTypeSize(T: Ctx.getSizeType()), 0),
3267 type: Ctx.getSizeType(), l: SourceLocation()));
3268
3269 Attrs.addNew(attrName: &AttrName, attrRange: SourceRange(AttrNameLoc, Parens.getCloseLocation()),
3270 scope: AttributeScopeInfo(), args: ArgExprs.data(), numArgs: ArgExprs.size(), form: Form);
3271}
3272
3273ExprResult Parser::ParseExtIntegerArgument() {
3274 assert(Tok.isOneOf(tok::kw__ExtInt, tok::kw__BitInt) &&
3275 "Not an extended int type");
3276 ConsumeToken();
3277
3278 BalancedDelimiterTracker T(*this, tok::l_paren);
3279 if (T.expectAndConsume())
3280 return ExprError();
3281
3282 ExprResult ER = ParseConstantExpression();
3283 if (ER.isInvalid()) {
3284 T.skipToEnd();
3285 return ExprError();
3286 }
3287
3288 if(T.consumeClose())
3289 return ExprError();
3290 return ER;
3291}
3292
3293bool
3294Parser::DiagnoseMissingSemiAfterTagDefinition(DeclSpec &DS, AccessSpecifier AS,
3295 DeclSpecContext DSContext,
3296 LateParsedAttrList *LateAttrs) {
3297 assert(DS.hasTagDefinition() && "shouldn't call this");
3298
3299 bool EnteringContext = (DSContext == DeclSpecContext::DSC_class ||
3300 DSContext == DeclSpecContext::DSC_top_level);
3301
3302 if (getLangOpts().CPlusPlus &&
3303 (Tok.isOneOf(Ks: tok::identifier, Ks: tok::coloncolon, Ks: tok::kw_decltype) ||
3304 (Tok.is(K: tok::annot_template_id) && NextToken().is(K: tok::coloncolon))) &&
3305 TryAnnotateCXXScopeToken(EnteringContext)) {
3306 SkipMalformedDecl();
3307 return true;
3308 }
3309
3310 bool HasScope = Tok.is(K: tok::annot_cxxscope);
3311 // Make a copy in case GetLookAheadToken invalidates the result of NextToken.
3312 Token AfterScope = HasScope ? NextToken() : Tok;
3313
3314 // Determine whether the following tokens could possibly be a
3315 // declarator.
3316 bool MightBeDeclarator = true;
3317 if (Tok.isOneOf(Ks: tok::kw_typename, Ks: tok::annot_typename)) {
3318 // A declarator-id can't start with 'typename'.
3319 MightBeDeclarator = false;
3320 } else if (AfterScope.is(K: tok::annot_template_id)) {
3321 // If we have a type expressed as a template-id, this cannot be a
3322 // declarator-id (such a type cannot be redeclared in a simple-declaration).
3323 TemplateIdAnnotation *Annot =
3324 static_cast<TemplateIdAnnotation *>(AfterScope.getAnnotationValue());
3325 if (Annot->Kind == TNK_Type_template)
3326 MightBeDeclarator = false;
3327 } else if (AfterScope.is(K: tok::identifier)) {
3328 const Token &Next = HasScope ? GetLookAheadToken(N: 2) : NextToken();
3329
3330 // These tokens cannot come after the declarator-id in a
3331 // simple-declaration, and are likely to come after a type-specifier.
3332 if (Next.isOneOf(Ks: tok::star, Ks: tok::amp, Ks: tok::ampamp, Ks: tok::identifier,
3333 Ks: tok::annot_cxxscope, Ks: tok::coloncolon)) {
3334 // Missing a semicolon.
3335 MightBeDeclarator = false;
3336 } else if (HasScope) {
3337 // If the declarator-id has a scope specifier, it must redeclare a
3338 // previously-declared entity. If that's a type (and this is not a
3339 // typedef), that's an error.
3340 CXXScopeSpec SS;
3341 Actions.RestoreNestedNameSpecifierAnnotation(
3342 Annotation: Tok.getAnnotationValue(), AnnotationRange: Tok.getAnnotationRange(), SS);
3343 IdentifierInfo *Name = AfterScope.getIdentifierInfo();
3344 Sema::NameClassification Classification = Actions.ClassifyName(
3345 S: getCurScope(), SS, Name, NameLoc: AfterScope.getLocation(), NextToken: Next,
3346 /*CCC=*/nullptr);
3347 switch (Classification.getKind()) {
3348 case NameClassificationKind::Error:
3349 SkipMalformedDecl();
3350 return true;
3351
3352 case NameClassificationKind::Keyword:
3353 llvm_unreachable("typo correction is not possible here");
3354
3355 case NameClassificationKind::Type:
3356 case NameClassificationKind::TypeTemplate:
3357 case NameClassificationKind::UndeclaredNonType:
3358 case NameClassificationKind::UndeclaredTemplate:
3359 case NameClassificationKind::Concept:
3360 // Not a previously-declared non-type entity.
3361 MightBeDeclarator = false;
3362 break;
3363
3364 case NameClassificationKind::Unknown:
3365 case NameClassificationKind::NonType:
3366 case NameClassificationKind::DependentNonType:
3367 case NameClassificationKind::OverloadSet:
3368 case NameClassificationKind::VarTemplate:
3369 case NameClassificationKind::FunctionTemplate:
3370 // Might be a redeclaration of a prior entity.
3371 break;
3372 }
3373 }
3374 }
3375
3376 if (MightBeDeclarator)
3377 return false;
3378
3379 const PrintingPolicy &PPol = Actions.getASTContext().getPrintingPolicy();
3380 Diag(Loc: PP.getLocForEndOfToken(Loc: DS.getRepAsDecl()->getEndLoc()),
3381 DiagID: diag::err_expected_after)
3382 << DeclSpec::getSpecifierName(T: DS.getTypeSpecType(), Policy: PPol) << tok::semi;
3383
3384 // Try to recover from the typo, by dropping the tag definition and parsing
3385 // the problematic tokens as a type.
3386 //
3387 // FIXME: Split the DeclSpec into pieces for the standalone
3388 // declaration and pieces for the following declaration, instead
3389 // of assuming that all the other pieces attach to new declaration,
3390 // and call ParsedFreeStandingDeclSpec as appropriate.
3391 DS.ClearTypeSpecType();
3392 ParsedTemplateInfo NotATemplate;
3393 ParseDeclarationSpecifiers(DS, TemplateInfo&: NotATemplate, AS, DSC: DSContext, LateAttrs);
3394 return false;
3395}
3396
3397void Parser::ParseDeclarationSpecifiers(
3398 DeclSpec &DS, ParsedTemplateInfo &TemplateInfo, AccessSpecifier AS,
3399 DeclSpecContext DSContext, LateParsedAttrList *LateAttrs,
3400 ImplicitTypenameContext AllowImplicitTypename) {
3401 if (DS.getSourceRange().isInvalid()) {
3402 // Start the range at the current token but make the end of the range
3403 // invalid. This will make the entire range invalid unless we successfully
3404 // consume a token.
3405 DS.SetRangeStart(Tok.getLocation());
3406 DS.SetRangeEnd(SourceLocation());
3407 }
3408
3409 // If we are in a operator context, convert it back into a type specifier
3410 // context for better error handling later on.
3411 if (DSContext == DeclSpecContext::DSC_conv_operator)
3412 DSContext = DeclSpecContext::DSC_type_specifier;
3413
3414 bool EnteringContext = (DSContext == DeclSpecContext::DSC_class ||
3415 DSContext == DeclSpecContext::DSC_top_level);
3416 bool AttrsLastTime = false;
3417 ParsedAttributes attrs(AttrFactory);
3418 // We use Sema's policy to get bool macros right.
3419 PrintingPolicy Policy = Actions.getPrintingPolicy();
3420 while (true) {
3421 bool isInvalid = false;
3422 bool isStorageClass = false;
3423 const char *PrevSpec = nullptr;
3424 unsigned DiagID = 0;
3425
3426 // This value needs to be set to the location of the last token if the last
3427 // token of the specifier is already consumed.
3428 SourceLocation ConsumedEnd;
3429
3430 // HACK: MSVC doesn't consider _Atomic to be a keyword and its STL
3431 // implementation for VS2013 uses _Atomic as an identifier for one of the
3432 // classes in <atomic>.
3433 //
3434 // A typedef declaration containing _Atomic<...> is among the places where
3435 // the class is used. If we are currently parsing such a declaration, treat
3436 // the token as an identifier.
3437 if (getLangOpts().MSVCCompat && Tok.is(K: tok::kw__Atomic) &&
3438 DS.getStorageClassSpec() == clang::DeclSpec::SCS_typedef &&
3439 !DS.hasTypeSpecifier() && GetLookAheadToken(N: 1).is(K: tok::less))
3440 Tok.setKind(tok::identifier);
3441
3442 SourceLocation Loc = Tok.getLocation();
3443
3444 // Helper for image types in OpenCL.
3445 auto handleOpenCLImageKW = [&] (StringRef Ext, TypeSpecifierType ImageTypeSpec) {
3446 // Check if the image type is supported and otherwise turn the keyword into an identifier
3447 // because image types from extensions are not reserved identifiers.
3448 if (!StringRef(Ext).empty() && !getActions().getOpenCLOptions().isSupported(Ext, LO: getLangOpts())) {
3449 Tok.getIdentifierInfo()->revertTokenIDToIdentifier();
3450 Tok.setKind(tok::identifier);
3451 return false;
3452 }
3453 isInvalid = DS.SetTypeSpecType(T: ImageTypeSpec, Loc, PrevSpec, DiagID, Policy);
3454 return true;
3455 };
3456
3457 // Turn off usual access checking for template specializations and
3458 // instantiations.
3459 bool IsTemplateSpecOrInst =
3460 (TemplateInfo.Kind == ParsedTemplateKind::ExplicitInstantiation ||
3461 TemplateInfo.Kind == ParsedTemplateKind::ExplicitSpecialization);
3462
3463 switch (Tok.getKind()) {
3464 default:
3465 if (Tok.isRegularKeywordAttribute())
3466 goto Attribute;
3467
3468 DoneWithDeclSpec:
3469 if (!AttrsLastTime)
3470 ProhibitAttributes(Attrs&: attrs);
3471 else {
3472 // Reject C++11 / C23 attributes that aren't type attributes.
3473 for (const ParsedAttr &PA : attrs) {
3474 if (!PA.isCXX11Attribute() && !PA.isC23Attribute() &&
3475 !PA.isRegularKeywordAttribute())
3476 continue;
3477 if (PA.getKind() == ParsedAttr::UnknownAttribute)
3478 // We will warn about the unknown attribute elsewhere (in
3479 // SemaDeclAttr.cpp)
3480 continue;
3481 // GCC ignores this attribute when placed on the DeclSpec in [[]]
3482 // syntax, so we do the same.
3483 if (PA.getKind() == ParsedAttr::AT_VectorSize) {
3484 Diag(Loc: PA.getLoc(), DiagID: diag::warn_attribute_ignored) << PA;
3485 PA.setInvalid();
3486 continue;
3487 }
3488 // We reject AT_LifetimeBound and AT_AnyX86NoCfCheck, even though they
3489 // are type attributes, because we historically haven't allowed these
3490 // to be used as type attributes in C++11 / C23 syntax.
3491 if (PA.isTypeAttr() && PA.getKind() != ParsedAttr::AT_LifetimeBound &&
3492 PA.getKind() != ParsedAttr::AT_AnyX86NoCfCheck)
3493 continue;
3494
3495 if (PA.getKind() == ParsedAttr::AT_LifetimeBound)
3496 Diag(Loc: PA.getLoc(), DiagID: diag::err_attribute_wrong_decl_type)
3497 << PA << PA.isRegularKeywordAttribute()
3498 << ExpectedParameterOrImplicitObjectParameter;
3499 else
3500 Diag(Loc: PA.getLoc(), DiagID: diag::err_attribute_not_type_attr)
3501 << PA << PA.isRegularKeywordAttribute();
3502 PA.setInvalid();
3503 }
3504
3505 DS.takeAttributesAppendingingFrom(attrs);
3506 }
3507
3508 // If this is not a declaration specifier token, we're done reading decl
3509 // specifiers. First verify that DeclSpec's are consistent.
3510 DS.Finish(S&: Actions, Policy);
3511 return;
3512
3513 // alignment-specifier
3514 case tok::kw__Alignas:
3515 diagnoseUseOfC11Keyword(Tok);
3516 [[fallthrough]];
3517 case tok::kw_alignas:
3518 // _Alignas and alignas (C23, not C++) should parse the same way. The C++
3519 // parsing for alignas happens through the usual attribute parsing. This
3520 // ensures that an alignas specifier can appear in a type position in C
3521 // despite that not being valid in C++.
3522 if (getLangOpts().C23 || Tok.getKind() == tok::kw__Alignas) {
3523 if (Tok.getKind() == tok::kw_alignas)
3524 Diag(Tok, DiagID: diag::warn_c23_compat_keyword) << Tok.getName();
3525 ParseAlignmentSpecifier(Attrs&: DS.getAttributes());
3526 continue;
3527 }
3528 [[fallthrough]];
3529 case tok::l_square:
3530 if (!isAllowedCXX11AttributeSpecifier())
3531 goto DoneWithDeclSpec;
3532
3533 Attribute:
3534 ProhibitAttributes(Attrs&: attrs);
3535 // FIXME: It would be good to recover by accepting the attributes,
3536 // but attempting to do that now would cause serious
3537 // madness in terms of diagnostics.
3538 attrs.clear();
3539 attrs.Range = SourceRange();
3540
3541 ParseCXX11Attributes(attrs);
3542 AttrsLastTime = true;
3543 continue;
3544
3545 case tok::code_completion: {
3546 SemaCodeCompletion::ParserCompletionContext CCC =
3547 SemaCodeCompletion::PCC_Namespace;
3548 if (DS.hasTypeSpecifier()) {
3549 bool AllowNonIdentifiers
3550 = (getCurScope()->getFlags() & (Scope::ControlScope |
3551 Scope::BlockScope |
3552 Scope::TemplateParamScope |
3553 Scope::FunctionPrototypeScope |
3554 Scope::AtCatchScope)) == 0;
3555 bool AllowNestedNameSpecifiers
3556 = DSContext == DeclSpecContext::DSC_top_level ||
3557 (DSContext == DeclSpecContext::DSC_class && DS.isFriendSpecified());
3558
3559 cutOffParsing();
3560 Actions.CodeCompletion().CodeCompleteDeclSpec(
3561 S: getCurScope(), DS, AllowNonIdentifiers, AllowNestedNameSpecifiers);
3562 return;
3563 }
3564
3565 // Class context can appear inside a function/block, so prioritise that.
3566 if (TemplateInfo.Kind != ParsedTemplateKind::NonTemplate)
3567 CCC = DSContext == DeclSpecContext::DSC_class
3568 ? SemaCodeCompletion::PCC_MemberTemplate
3569 : SemaCodeCompletion::PCC_Template;
3570 else if (DSContext == DeclSpecContext::DSC_class)
3571 CCC = SemaCodeCompletion::PCC_Class;
3572 else if (getCurScope()->getFnParent() || getCurScope()->getBlockParent())
3573 CCC = SemaCodeCompletion::PCC_LocalDeclarationSpecifiers;
3574 else if (CurParsedObjCImpl)
3575 CCC = SemaCodeCompletion::PCC_ObjCImplementation;
3576
3577 cutOffParsing();
3578 Actions.CodeCompletion().CodeCompleteOrdinaryName(S: getCurScope(), CompletionContext: CCC);
3579 return;
3580 }
3581
3582 case tok::coloncolon: // ::foo::bar
3583 // C++ scope specifier. Annotate and loop, or bail out on error.
3584 if (getLangOpts().CPlusPlus &&
3585 TryAnnotateCXXScopeToken(EnteringContext)) {
3586 if (!DS.hasTypeSpecifier())
3587 DS.SetTypeSpecError();
3588 goto DoneWithDeclSpec;
3589 }
3590 if (Tok.is(K: tok::coloncolon)) // ::new or ::delete
3591 goto DoneWithDeclSpec;
3592 continue;
3593
3594 case tok::annot_cxxscope: {
3595 if (DS.hasTypeSpecifier() || DS.isTypeAltiVecVector())
3596 goto DoneWithDeclSpec;
3597
3598 CXXScopeSpec SS;
3599 if (TemplateInfo.TemplateParams)
3600 SS.setTemplateParamLists(*TemplateInfo.TemplateParams);
3601 Actions.RestoreNestedNameSpecifierAnnotation(Annotation: Tok.getAnnotationValue(),
3602 AnnotationRange: Tok.getAnnotationRange(),
3603 SS);
3604
3605 // We are looking for a qualified typename.
3606 Token Next = NextToken();
3607
3608 TemplateIdAnnotation *TemplateId = Next.is(K: tok::annot_template_id)
3609 ? takeTemplateIdAnnotation(tok: Next)
3610 : nullptr;
3611 if (TemplateId && TemplateId->hasInvalidName()) {
3612 // We found something like 'T::U<Args> x', but U is not a template.
3613 // Assume it was supposed to be a type.
3614 DS.SetTypeSpecError();
3615 ConsumeAnnotationToken();
3616 break;
3617 }
3618
3619 if (TemplateId && TemplateId->Kind == TNK_Type_template) {
3620 // We have a qualified template-id, e.g., N::A<int>
3621
3622 // If this would be a valid constructor declaration with template
3623 // arguments, we will reject the attempt to form an invalid type-id
3624 // referring to the injected-class-name when we annotate the token,
3625 // per C++ [class.qual]p2.
3626 //
3627 // To improve diagnostics for this case, parse the declaration as a
3628 // constructor (and reject the extra template arguments later).
3629 if ((DSContext == DeclSpecContext::DSC_top_level ||
3630 DSContext == DeclSpecContext::DSC_class) &&
3631 TemplateId->Name &&
3632 Actions.isCurrentClassName(II: *TemplateId->Name, S: getCurScope(), SS: &SS) &&
3633 isConstructorDeclarator(/*Unqualified=*/false,
3634 /*DeductionGuide=*/false,
3635 IsFriend: DS.isFriendSpecified())) {
3636 // The user meant this to be an out-of-line constructor
3637 // definition, but template arguments are not allowed
3638 // there. Just allow this as a constructor; we'll
3639 // complain about it later.
3640 goto DoneWithDeclSpec;
3641 }
3642
3643 DS.getTypeSpecScope() = SS;
3644 ConsumeAnnotationToken(); // The C++ scope.
3645 assert(Tok.is(tok::annot_template_id) &&
3646 "ParseOptionalCXXScopeSpecifier not working");
3647 AnnotateTemplateIdTokenAsType(SS, AllowImplicitTypename);
3648 continue;
3649 }
3650
3651 if (TemplateId && TemplateId->Kind == TNK_Concept_template) {
3652 DS.getTypeSpecScope() = SS;
3653 // This is probably a qualified placeholder-specifier, e.g., ::C<int>
3654 // auto ... Consume the scope annotation and continue to consume the
3655 // template-id as a placeholder-specifier. Let the next iteration
3656 // diagnose a missing auto.
3657 ConsumeAnnotationToken();
3658 continue;
3659 }
3660
3661 if (Next.is(K: tok::annot_typename)) {
3662 DS.getTypeSpecScope() = SS;
3663 ConsumeAnnotationToken(); // The C++ scope.
3664 TypeResult T = getTypeAnnotation(Tok);
3665 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_typename,
3666 Loc: Tok.getAnnotationEndLoc(),
3667 PrevSpec, DiagID, Rep: T, Policy);
3668 if (isInvalid)
3669 break;
3670 DS.SetRangeEnd(Tok.getAnnotationEndLoc());
3671 ConsumeAnnotationToken(); // The typename
3672 }
3673
3674 if (AllowImplicitTypename == ImplicitTypenameContext::Yes &&
3675 Next.is(K: tok::annot_template_id) &&
3676 static_cast<TemplateIdAnnotation *>(Next.getAnnotationValue())
3677 ->Kind == TNK_Dependent_template_name) {
3678 DS.getTypeSpecScope() = SS;
3679 ConsumeAnnotationToken(); // The C++ scope.
3680 AnnotateTemplateIdTokenAsType(SS, AllowImplicitTypename);
3681 continue;
3682 }
3683
3684 if (Next.isNot(K: tok::identifier))
3685 goto DoneWithDeclSpec;
3686
3687 // Check whether this is a constructor declaration. If we're in a
3688 // context where the identifier could be a class name, and it has the
3689 // shape of a constructor declaration, process it as one.
3690 if ((DSContext == DeclSpecContext::DSC_top_level ||
3691 DSContext == DeclSpecContext::DSC_class) &&
3692 Actions.isCurrentClassName(II: *Next.getIdentifierInfo(), S: getCurScope(),
3693 SS: &SS) &&
3694 isConstructorDeclarator(/*Unqualified=*/false,
3695 /*DeductionGuide=*/false,
3696 IsFriend: DS.isFriendSpecified(),
3697 TemplateInfo: &TemplateInfo))
3698 goto DoneWithDeclSpec;
3699
3700 // C++20 [temp.spec] 13.9/6.
3701 // This disables the access checking rules for function template explicit
3702 // instantiation and explicit specialization:
3703 // - `return type`.
3704 SuppressAccessChecks SAC(*this, IsTemplateSpecOrInst);
3705
3706 ParsedType TypeRep = Actions.getTypeName(
3707 II: *Next.getIdentifierInfo(), NameLoc: Next.getLocation(), S: getCurScope(), SS: &SS,
3708 isClassName: false, HasTrailingDot: false, ObjectType: nullptr,
3709 /*IsCtorOrDtorName=*/false,
3710 /*WantNontrivialTypeSourceInfo=*/true,
3711 IsClassTemplateDeductionContext: isClassTemplateDeductionContext(DSC: DSContext), AllowImplicitTypename);
3712
3713 if (IsTemplateSpecOrInst)
3714 SAC.done();
3715
3716 // If the referenced identifier is not a type, then this declspec is
3717 // erroneous: We already checked about that it has no type specifier, and
3718 // C++ doesn't have implicit int. Diagnose it as a typo w.r.t. to the
3719 // typename.
3720 if (!TypeRep) {
3721 if (TryAnnotateTypeConstraint())
3722 goto DoneWithDeclSpec;
3723 if (Tok.isNot(K: tok::annot_cxxscope) ||
3724 NextToken().isNot(K: tok::identifier))
3725 continue;
3726 // Eat the scope spec so the identifier is current.
3727 ConsumeAnnotationToken();
3728 ParsedAttributes Attrs(AttrFactory);
3729 if (ParseImplicitInt(DS, SS: &SS, TemplateInfo, AS, DSC: DSContext, Attrs)) {
3730 if (!Attrs.empty()) {
3731 AttrsLastTime = true;
3732 attrs.takeAllAppendingFrom(Other&: Attrs);
3733 }
3734 continue;
3735 }
3736 goto DoneWithDeclSpec;
3737 }
3738
3739 DS.getTypeSpecScope() = SS;
3740 ConsumeAnnotationToken(); // The C++ scope.
3741
3742 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_typename, Loc, PrevSpec,
3743 DiagID, Rep: TypeRep, Policy);
3744 if (isInvalid)
3745 break;
3746
3747 DS.SetRangeEnd(Tok.getLocation());
3748 ConsumeToken(); // The typename.
3749
3750 continue;
3751 }
3752
3753 case tok::annot_typename: {
3754 // If we've previously seen a tag definition, we were almost surely
3755 // missing a semicolon after it.
3756 if (DS.hasTypeSpecifier() && DS.hasTagDefinition())
3757 goto DoneWithDeclSpec;
3758
3759 TypeResult T = getTypeAnnotation(Tok);
3760 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_typename, Loc, PrevSpec,
3761 DiagID, Rep: T, Policy);
3762 if (isInvalid)
3763 break;
3764
3765 DS.SetRangeEnd(Tok.getAnnotationEndLoc());
3766 ConsumeAnnotationToken(); // The typename
3767
3768 continue;
3769 }
3770
3771 case tok::kw___is_signed:
3772 // HACK: before 2022-12, libstdc++ uses __is_signed as an identifier,
3773 // but Clang typically treats it as a trait.
3774 // If we see __is_signed as it appears in libstdc++, e.g.,
3775 //
3776 // static const bool __is_signed;
3777 //
3778 // then treat __is_signed as an identifier rather than as a keyword.
3779 // This was fixed by libstdc++ in December 2022.
3780 if (DS.getTypeSpecType() == TST_bool &&
3781 DS.getTypeQualifiers() == DeclSpec::TQ_const &&
3782 DS.getStorageClassSpec() == DeclSpec::SCS_static)
3783 TryKeywordIdentFallback(DisableKeyword: true);
3784
3785 // We're done with the declaration-specifiers.
3786 goto DoneWithDeclSpec;
3787
3788 // typedef-name
3789 case tok::kw___super:
3790 case tok::kw_decltype:
3791 case tok::identifier:
3792 ParseIdentifier: {
3793 // This identifier can only be a typedef name if we haven't already seen
3794 // a type-specifier. Without this check we misparse:
3795 // typedef int X; struct Y { short X; }; as 'short int'.
3796 if (DS.hasTypeSpecifier())
3797 goto DoneWithDeclSpec;
3798
3799 // If the token is an identifier named "__declspec" and Microsoft
3800 // extensions are not enabled, it is likely that there will be cascading
3801 // parse errors if this really is a __declspec attribute. Attempt to
3802 // recognize that scenario and recover gracefully.
3803 if (!getLangOpts().DeclSpecKeyword && Tok.is(K: tok::identifier) &&
3804 Tok.getIdentifierInfo()->getName() == "__declspec") {
3805 Diag(Loc, DiagID: diag::err_ms_attributes_not_enabled);
3806
3807 // The next token should be an open paren. If it is, eat the entire
3808 // attribute declaration and continue.
3809 if (NextToken().is(K: tok::l_paren)) {
3810 // Consume the __declspec identifier.
3811 ConsumeToken();
3812
3813 // Eat the parens and everything between them.
3814 BalancedDelimiterTracker T(*this, tok::l_paren);
3815 if (T.consumeOpen()) {
3816 assert(false && "Not a left paren?");
3817 return;
3818 }
3819 T.skipToEnd();
3820 continue;
3821 }
3822 }
3823
3824 // In C++, check to see if this is a scope specifier like foo::bar::, if
3825 // so handle it as such. This is important for ctor parsing.
3826 if (getLangOpts().CPlusPlus) {
3827 // C++20 [temp.spec] 13.9/6.
3828 // This disables the access checking rules for function template
3829 // explicit instantiation and explicit specialization:
3830 // - `return type`.
3831 SuppressAccessChecks SAC(*this, IsTemplateSpecOrInst);
3832
3833 const bool Success = TryAnnotateCXXScopeToken(EnteringContext);
3834
3835 if (IsTemplateSpecOrInst)
3836 SAC.done();
3837
3838 if (Success) {
3839 if (IsTemplateSpecOrInst)
3840 SAC.redelay();
3841 DS.SetTypeSpecError();
3842 goto DoneWithDeclSpec;
3843 }
3844
3845 if (!Tok.is(K: tok::identifier))
3846 continue;
3847 }
3848
3849 // Check for need to substitute AltiVec keyword tokens.
3850 if (TryAltiVecToken(DS, Loc, PrevSpec, DiagID, isInvalid))
3851 break;
3852
3853 // [AltiVec] 2.2: [If the 'vector' specifier is used] The syntax does not
3854 // allow the use of a typedef name as a type specifier.
3855 if (DS.isTypeAltiVecVector())
3856 goto DoneWithDeclSpec;
3857
3858 if (DSContext == DeclSpecContext::DSC_objc_method_result &&
3859 isObjCInstancetype()) {
3860 ParsedType TypeRep = Actions.ObjC().ActOnObjCInstanceType(Loc);
3861 assert(TypeRep);
3862 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_typename, Loc, PrevSpec,
3863 DiagID, Rep: TypeRep, Policy);
3864 if (isInvalid)
3865 break;
3866
3867 DS.SetRangeEnd(Loc);
3868 ConsumeToken();
3869 continue;
3870 }
3871
3872 // If we're in a context where the identifier could be a class name,
3873 // check whether this is a constructor declaration.
3874 if (getLangOpts().CPlusPlus && DSContext == DeclSpecContext::DSC_class &&
3875 Actions.isCurrentClassName(II: *Tok.getIdentifierInfo(), S: getCurScope()) &&
3876 isConstructorDeclarator(/*Unqualified=*/true,
3877 /*DeductionGuide=*/false,
3878 IsFriend: DS.isFriendSpecified()))
3879 goto DoneWithDeclSpec;
3880
3881 ParsedType TypeRep = Actions.getTypeName(
3882 II: *Tok.getIdentifierInfo(), NameLoc: Tok.getLocation(), S: getCurScope(), SS: nullptr,
3883 isClassName: false, HasTrailingDot: false, ObjectType: nullptr, IsCtorOrDtorName: false, WantNontrivialTypeSourceInfo: false,
3884 IsClassTemplateDeductionContext: isClassTemplateDeductionContext(DSC: DSContext));
3885
3886 // If this is not a typedef name, don't parse it as part of the declspec,
3887 // it must be an implicit int or an error.
3888 if (!TypeRep) {
3889 if (TryAnnotateTypeConstraint())
3890 goto DoneWithDeclSpec;
3891 if (Tok.isNot(K: tok::identifier))
3892 continue;
3893 ParsedAttributes Attrs(AttrFactory);
3894 if (ParseImplicitInt(DS, SS: nullptr, TemplateInfo, AS, DSC: DSContext, Attrs)) {
3895 if (!Attrs.empty()) {
3896 AttrsLastTime = true;
3897 attrs.takeAllAppendingFrom(Other&: Attrs);
3898 }
3899 continue;
3900 }
3901 goto DoneWithDeclSpec;
3902 }
3903
3904 // Likewise, if this is a context where the identifier could be a template
3905 // name, check whether this is a deduction guide declaration.
3906 CXXScopeSpec SS;
3907 if (getLangOpts().CPlusPlus17 &&
3908 (DSContext == DeclSpecContext::DSC_class ||
3909 DSContext == DeclSpecContext::DSC_top_level) &&
3910 Actions.isDeductionGuideName(S: getCurScope(), Name: *Tok.getIdentifierInfo(),
3911 NameLoc: Tok.getLocation(), SS) &&
3912 isConstructorDeclarator(/*Unqualified*/ true,
3913 /*DeductionGuide*/ true))
3914 goto DoneWithDeclSpec;
3915
3916 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_typename, Loc, PrevSpec,
3917 DiagID, Rep: TypeRep, Policy);
3918 if (isInvalid)
3919 break;
3920
3921 DS.SetRangeEnd(Tok.getLocation());
3922 ConsumeToken(); // The identifier
3923
3924 // Objective-C supports type arguments and protocol references
3925 // following an Objective-C object or object pointer
3926 // type. Handle either one of them.
3927 if (Tok.is(K: tok::less) && getLangOpts().ObjC) {
3928 SourceLocation NewEndLoc;
3929 TypeResult NewTypeRep = parseObjCTypeArgsAndProtocolQualifiers(
3930 loc: Loc, type: TypeRep, /*consumeLastToken=*/true,
3931 endLoc&: NewEndLoc);
3932 if (NewTypeRep.isUsable()) {
3933 DS.UpdateTypeRep(Rep: NewTypeRep.get());
3934 DS.SetRangeEnd(NewEndLoc);
3935 }
3936 }
3937
3938 // Need to support trailing type qualifiers (e.g. "id<p> const").
3939 // If a type specifier follows, it will be diagnosed elsewhere.
3940 continue;
3941 }
3942
3943 // type-name or placeholder-specifier
3944 case tok::annot_template_id: {
3945 TemplateIdAnnotation *TemplateId = takeTemplateIdAnnotation(tok: Tok);
3946
3947 if (TemplateId->hasInvalidName()) {
3948 DS.SetTypeSpecError();
3949 break;
3950 }
3951
3952 if (TemplateId->Kind == TNK_Concept_template) {
3953 // If we've already diagnosed that this type-constraint has invalid
3954 // arguments, drop it and just form 'auto' or 'decltype(auto)'.
3955 if (TemplateId->hasInvalidArgs())
3956 TemplateId = nullptr;
3957
3958 // Any of the following tokens are likely the start of the user
3959 // forgetting 'auto' or 'decltype(auto)', so diagnose.
3960 // Note: if updating this list, please make sure we update
3961 // isCXXDeclarationSpecifier's check for IsPlaceholderSpecifier to have
3962 // a matching list.
3963 if (NextToken().isOneOf(Ks: tok::identifier, Ks: tok::kw_const,
3964 Ks: tok::kw_volatile, Ks: tok::kw_restrict, Ks: tok::amp,
3965 Ks: tok::ampamp)) {
3966 Diag(Loc, DiagID: diag::err_placeholder_expected_auto_or_decltype_auto)
3967 << FixItHint::CreateInsertion(InsertionLoc: NextToken().getLocation(), Code: "auto");
3968 // Attempt to continue as if 'auto' was placed here.
3969 isInvalid = DS.SetTypeSpecType(T: TST_auto, Loc, PrevSpec, DiagID,
3970 Rep: TemplateId, Policy);
3971 break;
3972 }
3973 if (!NextToken().isOneOf(Ks: tok::kw_auto, Ks: tok::kw_decltype))
3974 goto DoneWithDeclSpec;
3975
3976 if (TemplateId && !isInvalid && Actions.CheckTypeConstraint(TypeConstraint: TemplateId))
3977 TemplateId = nullptr;
3978
3979 ConsumeAnnotationToken();
3980 SourceLocation AutoLoc = Tok.getLocation();
3981 if (TryConsumeToken(Expected: tok::kw_decltype)) {
3982 BalancedDelimiterTracker Tracker(*this, tok::l_paren);
3983 if (Tracker.consumeOpen()) {
3984 // Something like `void foo(Iterator decltype i)`
3985 Diag(Tok, DiagID: diag::err_expected) << tok::l_paren;
3986 } else {
3987 if (!TryConsumeToken(Expected: tok::kw_auto)) {
3988 // Something like `void foo(Iterator decltype(int) i)`
3989 Tracker.skipToEnd();
3990 Diag(Tok, DiagID: diag::err_placeholder_expected_auto_or_decltype_auto)
3991 << FixItHint::CreateReplacement(RemoveRange: SourceRange(AutoLoc,
3992 Tok.getLocation()),
3993 Code: "auto");
3994 } else {
3995 Tracker.consumeClose();
3996 }
3997 }
3998 ConsumedEnd = Tok.getLocation();
3999 DS.setTypeArgumentRange(Tracker.getRange());
4000 // Even if something went wrong above, continue as if we've seen
4001 // `decltype(auto)`.
4002 isInvalid = DS.SetTypeSpecType(T: TST_decltype_auto, Loc, PrevSpec,
4003 DiagID, Rep: TemplateId, Policy);
4004 } else {
4005 isInvalid = DS.SetTypeSpecType(T: TST_auto, Loc: AutoLoc, PrevSpec, DiagID,
4006 Rep: TemplateId, Policy);
4007 }
4008 break;
4009 }
4010
4011 if (TemplateId->Kind != TNK_Type_template &&
4012 TemplateId->Kind != TNK_Undeclared_template) {
4013 // This template-id does not refer to a type name, so we're
4014 // done with the type-specifiers.
4015 goto DoneWithDeclSpec;
4016 }
4017
4018 // If we're in a context where the template-id could be a
4019 // constructor name or specialization, check whether this is a
4020 // constructor declaration.
4021 if (getLangOpts().CPlusPlus && DSContext == DeclSpecContext::DSC_class &&
4022 Actions.isCurrentClassName(II: *TemplateId->Name, S: getCurScope()) &&
4023 isConstructorDeclarator(/*Unqualified=*/true,
4024 /*DeductionGuide=*/false,
4025 IsFriend: DS.isFriendSpecified()))
4026 goto DoneWithDeclSpec;
4027
4028 // Turn the template-id annotation token into a type annotation
4029 // token, then try again to parse it as a type-specifier.
4030 CXXScopeSpec SS;
4031 AnnotateTemplateIdTokenAsType(SS, AllowImplicitTypename);
4032 continue;
4033 }
4034
4035 // Attributes support.
4036 case tok::kw___attribute:
4037 case tok::kw___declspec:
4038 ParseAttributes(WhichAttrKinds: PAKM_GNU | PAKM_Declspec, Attrs&: DS.getAttributes(), LateAttrs);
4039 continue;
4040
4041 // Microsoft single token adornments.
4042 case tok::kw___forceinline: {
4043 isInvalid = DS.setFunctionSpecForceInline(Loc, PrevSpec, DiagID);
4044 IdentifierInfo *AttrName = Tok.getIdentifierInfo();
4045 SourceLocation AttrNameLoc = Tok.getLocation();
4046 DS.getAttributes().addNew(attrName: AttrName, attrRange: AttrNameLoc, scope: AttributeScopeInfo(),
4047 args: nullptr, numArgs: 0, form: tok::kw___forceinline);
4048 break;
4049 }
4050
4051 case tok::kw___unaligned:
4052 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_unaligned, Loc, PrevSpec, DiagID,
4053 Lang: getLangOpts());
4054 break;
4055
4056 // __ptrauth qualifier.
4057 case tok::kw___ptrauth:
4058 ParsePtrauthQualifier(Attrs&: DS.getAttributes());
4059 continue;
4060
4061 case tok::kw___sptr:
4062 case tok::kw___uptr:
4063 case tok::kw___ptr64:
4064 case tok::kw___ptr32:
4065 case tok::kw___w64:
4066 case tok::kw___cdecl:
4067 case tok::kw___stdcall:
4068 case tok::kw___fastcall:
4069 case tok::kw___thiscall:
4070 case tok::kw___regcall:
4071 case tok::kw___vectorcall:
4072 ParseMicrosoftTypeAttributes(attrs&: DS.getAttributes());
4073 continue;
4074
4075 case tok::kw___funcref:
4076 ParseWebAssemblyFuncrefTypeAttribute(attrs&: DS.getAttributes());
4077 continue;
4078
4079 // Borland single token adornments.
4080 case tok::kw___pascal:
4081 ParseBorlandTypeAttributes(attrs&: DS.getAttributes());
4082 continue;
4083
4084 // OpenCL single token adornments.
4085 case tok::kw___kernel:
4086 ParseOpenCLKernelAttributes(attrs&: DS.getAttributes());
4087 continue;
4088
4089 // CUDA/HIP single token adornments.
4090 case tok::kw___noinline__:
4091 ParseCUDAFunctionAttributes(attrs&: DS.getAttributes());
4092 continue;
4093
4094 // Nullability type specifiers.
4095 case tok::kw__Nonnull:
4096 case tok::kw__Nullable:
4097 case tok::kw__Nullable_result:
4098 case tok::kw__Null_unspecified:
4099 ParseNullabilityTypeSpecifiers(attrs&: DS.getAttributes());
4100 continue;
4101
4102 // Objective-C 'kindof' types.
4103 case tok::kw___kindof:
4104 DS.getAttributes().addNew(attrName: Tok.getIdentifierInfo(), attrRange: Loc,
4105 scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
4106 form: tok::kw___kindof);
4107 (void)ConsumeToken();
4108 continue;
4109
4110 // storage-class-specifier
4111 case tok::kw_typedef:
4112 isInvalid = DS.SetStorageClassSpec(S&: Actions, SC: DeclSpec::SCS_typedef, Loc,
4113 PrevSpec, DiagID, Policy);
4114 isStorageClass = true;
4115 break;
4116 case tok::kw_extern:
4117 if (DS.getThreadStorageClassSpec() == DeclSpec::TSCS___thread)
4118 Diag(Tok, DiagID: diag::ext_thread_before) << "extern";
4119 isInvalid = DS.SetStorageClassSpec(S&: Actions, SC: DeclSpec::SCS_extern, Loc,
4120 PrevSpec, DiagID, Policy);
4121 isStorageClass = true;
4122 break;
4123 case tok::kw___private_extern__:
4124 isInvalid = DS.SetStorageClassSpec(S&: Actions, SC: DeclSpec::SCS_private_extern,
4125 Loc, PrevSpec, DiagID, Policy);
4126 isStorageClass = true;
4127 break;
4128 case tok::kw_static:
4129 if (DS.getThreadStorageClassSpec() == DeclSpec::TSCS___thread)
4130 Diag(Tok, DiagID: diag::ext_thread_before) << "static";
4131 isInvalid = DS.SetStorageClassSpec(S&: Actions, SC: DeclSpec::SCS_static, Loc,
4132 PrevSpec, DiagID, Policy);
4133 isStorageClass = true;
4134 break;
4135 case tok::kw_auto:
4136 if (getLangOpts().CPlusPlus11 || getLangOpts().C23) {
4137 auto IsTypedefName = [&](const Token &T) {
4138 if (!T.is(K: tok::identifier))
4139 return false;
4140 IdentifierInfo *II = T.getIdentifierInfo();
4141 if (!II)
4142 return false;
4143 // Suppress diagnostics; the real parse will emit them later.
4144 LookupResult R(Actions, II, T.getLocation(),
4145 Sema::LookupOrdinaryName);
4146 Actions.LookupName(R, S: getCurScope(),
4147 /*AllowBuiltinCreation=*/false);
4148 R.suppressDiagnostics();
4149 return R.isSingleResult() && isa<TypeDecl>(Val: R.getFoundDecl());
4150 };
4151 auto MayBeTypeSpecifier = [&]() {
4152 // In pre-C23 C, auto can be used as a storage-class specifier.
4153 // C23 removes auto from the storage-class specifiers and repurposes
4154 // it for type inference (6.7.10).
4155 if (getLangOpts().C23 && DS.hasTypeSpecifier() &&
4156 DS.getTypeSpecType() != DeclSpec::TST_auto)
4157 return true;
4158
4159 unsigned I = 1;
4160 while (true) {
4161 const Token &T = GetLookAheadToken(N: I);
4162 if (isKnownToBeTypeSpecifier(Tok: T))
4163 return true;
4164
4165 // C23: a bare identifier that names a typedef is a type
4166 // specifier here, so `auto typedefName varName;` should be
4167 // parsed with `auto` as the storage-class specifier — not as
4168 // type inference. Without this check the parser would consume
4169 // `auto` as type-inference and then error on the missing
4170 // initializer for what it thinks is `typedefName`.
4171 if (getLangOpts().C23 && IsTypedefName(T))
4172 return true;
4173
4174 if (getLangOpts().C23 && isTypeSpecifierQualifier(Tok: T))
4175 ++I;
4176 else
4177 return false;
4178 }
4179 };
4180
4181 if (MayBeTypeSpecifier()) {
4182 isInvalid = DS.SetStorageClassSpec(S&: Actions, SC: DeclSpec::SCS_auto, Loc,
4183 PrevSpec, DiagID, Policy);
4184 if (!isInvalid && !getLangOpts().C23)
4185 Diag(Tok, DiagID: diag::ext_auto_storage_class)
4186 << FixItHint::CreateRemoval(RemoveRange: DS.getStorageClassSpecLoc());
4187 } else
4188 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_auto, Loc, PrevSpec,
4189 DiagID, Policy);
4190 } else
4191 isInvalid = DS.SetStorageClassSpec(S&: Actions, SC: DeclSpec::SCS_auto, Loc,
4192 PrevSpec, DiagID, Policy);
4193 isStorageClass = true;
4194 break;
4195 case tok::kw___auto_type:
4196 Diag(Tok, DiagID: diag::ext_auto_type);
4197 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_auto_type, Loc, PrevSpec,
4198 DiagID, Policy);
4199 break;
4200 case tok::kw_register:
4201 isInvalid = DS.SetStorageClassSpec(S&: Actions, SC: DeclSpec::SCS_register, Loc,
4202 PrevSpec, DiagID, Policy);
4203 isStorageClass = true;
4204 break;
4205 case tok::kw_mutable:
4206 isInvalid = DS.SetStorageClassSpec(S&: Actions, SC: DeclSpec::SCS_mutable, Loc,
4207 PrevSpec, DiagID, Policy);
4208 isStorageClass = true;
4209 break;
4210 case tok::kw___thread:
4211 isInvalid = DS.SetStorageClassSpecThread(TSC: DeclSpec::TSCS___thread, Loc,
4212 PrevSpec, DiagID);
4213 isStorageClass = true;
4214 break;
4215 case tok::kw_thread_local:
4216 if (getLangOpts().C23)
4217 Diag(Tok, DiagID: diag::warn_c23_compat_keyword) << Tok.getName();
4218 // We map thread_local to _Thread_local in C23 mode so it retains the C
4219 // semantics rather than getting the C++ semantics.
4220 // FIXME: diagnostics will show _Thread_local when the user wrote
4221 // thread_local in source in C23 mode; we need some general way to
4222 // identify which way the user spelled the keyword in source.
4223 isInvalid = DS.SetStorageClassSpecThread(
4224 TSC: getLangOpts().C23 ? DeclSpec::TSCS__Thread_local
4225 : DeclSpec::TSCS_thread_local,
4226 Loc, PrevSpec, DiagID);
4227 isStorageClass = true;
4228 break;
4229 case tok::kw__Thread_local:
4230 diagnoseUseOfC11Keyword(Tok);
4231 isInvalid = DS.SetStorageClassSpecThread(TSC: DeclSpec::TSCS__Thread_local,
4232 Loc, PrevSpec, DiagID);
4233 isStorageClass = true;
4234 break;
4235
4236 // function-specifier
4237 case tok::kw_inline:
4238 isInvalid = DS.setFunctionSpecInline(Loc, PrevSpec, DiagID);
4239 break;
4240 case tok::kw_virtual:
4241 // C++ for OpenCL does not allow virtual function qualifier, to avoid
4242 // function pointers restricted in OpenCL v2.0 s6.9.a.
4243 if (getLangOpts().OpenCLCPlusPlus &&
4244 !getActions().getOpenCLOptions().isAvailableOption(
4245 Ext: "__cl_clang_function_pointers", LO: getLangOpts())) {
4246 DiagID = diag::err_openclcxx_virtual_function;
4247 PrevSpec = Tok.getIdentifierInfo()->getNameStart();
4248 isInvalid = true;
4249 } else if (getLangOpts().HLSL) {
4250 DiagID = diag::err_hlsl_virtual_function;
4251 PrevSpec = Tok.getIdentifierInfo()->getNameStart();
4252 isInvalid = true;
4253 } else {
4254 isInvalid = DS.setFunctionSpecVirtual(Loc, PrevSpec, DiagID);
4255 }
4256 break;
4257 case tok::kw_explicit: {
4258 SourceLocation ExplicitLoc = Loc;
4259 SourceLocation CloseParenLoc;
4260 ExplicitSpecifier ExplicitSpec(nullptr, ExplicitSpecKind::ResolvedTrue);
4261 ConsumedEnd = ExplicitLoc;
4262 ConsumeToken(); // kw_explicit
4263 if (Tok.is(K: tok::l_paren)) {
4264 if (getLangOpts().CPlusPlus20 || isExplicitBool() == TPResult::True) {
4265 DiagCompat(Loc: Tok.getLocation(), CompatDiagId: diag_compat::explicit_bool);
4266
4267 ExprResult ExplicitExpr(static_cast<Expr *>(nullptr));
4268 BalancedDelimiterTracker Tracker(*this, tok::l_paren);
4269 Tracker.consumeOpen();
4270
4271 EnterExpressionEvaluationContext ConstantEvaluated(
4272 Actions, Sema::ExpressionEvaluationContext::ConstantEvaluated);
4273
4274 ExplicitExpr = ParseConstantExpressionInExprEvalContext();
4275 ConsumedEnd = Tok.getLocation();
4276 if (ExplicitExpr.isUsable()) {
4277 CloseParenLoc = Tok.getLocation();
4278 Tracker.consumeClose();
4279 ExplicitSpec =
4280 Actions.ActOnExplicitBoolSpecifier(E: ExplicitExpr.get());
4281 } else
4282 Tracker.skipToEnd();
4283 } else {
4284 Diag(Loc: Tok.getLocation(), DiagID: diag::warn_cxx20_compat_explicit_bool);
4285 }
4286 }
4287 isInvalid = DS.setFunctionSpecExplicit(Loc: ExplicitLoc, PrevSpec, DiagID,
4288 ExplicitSpec, CloseParenLoc);
4289 break;
4290 }
4291 case tok::kw__Noreturn:
4292 diagnoseUseOfC11Keyword(Tok);
4293 isInvalid = DS.setFunctionSpecNoreturn(Loc, PrevSpec, DiagID);
4294 break;
4295
4296 // friend
4297 case tok::kw_friend:
4298 if (DSContext == DeclSpecContext::DSC_class) {
4299 isInvalid = DS.SetFriendSpec(Loc, PrevSpec, DiagID);
4300 Scope *CurS = getCurScope();
4301 if (!isInvalid && CurS)
4302 CurS->setFlags(CurS->getFlags() | Scope::FriendScope);
4303 } else {
4304 PrevSpec = ""; // not actually used by the diagnostic
4305 DiagID = diag::err_friend_invalid_in_context;
4306 isInvalid = true;
4307 }
4308 break;
4309
4310 // Modules
4311 case tok::kw___module_private__:
4312 isInvalid = DS.setModulePrivateSpec(Loc, PrevSpec, DiagID);
4313 break;
4314
4315 // constexpr, consteval, constinit specifiers
4316 case tok::kw_constexpr:
4317 if (getLangOpts().C23)
4318 Diag(Tok, DiagID: diag::warn_c23_compat_keyword) << Tok.getName();
4319 isInvalid = DS.SetConstexprSpec(ConstexprKind: ConstexprSpecKind::Constexpr, Loc,
4320 PrevSpec, DiagID);
4321 break;
4322 case tok::kw_consteval:
4323 isInvalid = DS.SetConstexprSpec(ConstexprKind: ConstexprSpecKind::Consteval, Loc,
4324 PrevSpec, DiagID);
4325 break;
4326 case tok::kw_constinit:
4327 isInvalid = DS.SetConstexprSpec(ConstexprKind: ConstexprSpecKind::Constinit, Loc,
4328 PrevSpec, DiagID);
4329 break;
4330
4331 // type-specifier
4332 case tok::kw_short:
4333 if (!getLangOpts().NativeInt16Type) {
4334 Diag(Tok, DiagID: diag::err_unknown_typename) << Tok.getName();
4335 DS.SetTypeSpecError();
4336 DS.SetRangeEnd(Tok.getLocation());
4337 ConsumeToken();
4338 goto DoneWithDeclSpec;
4339 }
4340 isInvalid = DS.SetTypeSpecWidth(W: TypeSpecifierWidth::Short, Loc, PrevSpec,
4341 DiagID, Policy);
4342 break;
4343 case tok::kw_long:
4344 if (DS.getTypeSpecWidth() != TypeSpecifierWidth::Long)
4345 isInvalid = DS.SetTypeSpecWidth(W: TypeSpecifierWidth::Long, Loc, PrevSpec,
4346 DiagID, Policy);
4347 else
4348 isInvalid = DS.SetTypeSpecWidth(W: TypeSpecifierWidth::LongLong, Loc,
4349 PrevSpec, DiagID, Policy);
4350 break;
4351 case tok::kw___int64:
4352 isInvalid = DS.SetTypeSpecWidth(W: TypeSpecifierWidth::LongLong, Loc,
4353 PrevSpec, DiagID, Policy);
4354 break;
4355 case tok::kw_signed:
4356 isInvalid =
4357 DS.SetTypeSpecSign(S: TypeSpecifierSign::Signed, Loc, PrevSpec, DiagID);
4358 break;
4359 case tok::kw_unsigned:
4360 isInvalid = DS.SetTypeSpecSign(S: TypeSpecifierSign::Unsigned, Loc, PrevSpec,
4361 DiagID);
4362 break;
4363 case tok::kw__Complex:
4364 if (!getLangOpts().C99)
4365 Diag(Tok, DiagID: diag::ext_c99_feature) << Tok.getName();
4366 isInvalid = DS.SetTypeSpecComplex(C: DeclSpec::TSC_complex, Loc, PrevSpec,
4367 DiagID);
4368 break;
4369 case tok::kw__Imaginary:
4370 if (!getLangOpts().C99)
4371 Diag(Tok, DiagID: diag::ext_c99_feature) << Tok.getName();
4372 isInvalid = DS.SetTypeSpecComplex(C: DeclSpec::TSC_imaginary, Loc, PrevSpec,
4373 DiagID);
4374 break;
4375 case tok::kw_void:
4376 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_void, Loc, PrevSpec,
4377 DiagID, Policy);
4378 break;
4379 case tok::kw_char:
4380 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_char, Loc, PrevSpec,
4381 DiagID, Policy);
4382 break;
4383 case tok::kw_int:
4384 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_int, Loc, PrevSpec,
4385 DiagID, Policy);
4386 break;
4387 case tok::kw__ExtInt:
4388 case tok::kw__BitInt: {
4389 DiagnoseBitIntUse(Tok);
4390 ExprResult ER = ParseExtIntegerArgument();
4391 if (ER.isInvalid())
4392 continue;
4393 isInvalid = DS.SetBitIntType(KWLoc: Loc, BitWidth: ER.get(), PrevSpec, DiagID, Policy);
4394 ConsumedEnd = PrevTokLocation;
4395 break;
4396 }
4397 case tok::kw___int128:
4398 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_int128, Loc, PrevSpec,
4399 DiagID, Policy);
4400 break;
4401 case tok::kw_half:
4402 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_half, Loc, PrevSpec,
4403 DiagID, Policy);
4404 break;
4405 case tok::kw___bf16:
4406 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_BFloat16, Loc, PrevSpec,
4407 DiagID, Policy);
4408 break;
4409 case tok::kw_float:
4410 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_float, Loc, PrevSpec,
4411 DiagID, Policy);
4412 break;
4413 case tok::kw_double:
4414 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_double, Loc, PrevSpec,
4415 DiagID, Policy);
4416 break;
4417 case tok::kw__Float16:
4418 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_float16, Loc, PrevSpec,
4419 DiagID, Policy);
4420 break;
4421 case tok::kw__Accum:
4422 assert(getLangOpts().FixedPoint &&
4423 "This keyword is only used when fixed point types are enabled "
4424 "with `-ffixed-point`");
4425 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_accum, Loc, PrevSpec, DiagID,
4426 Policy);
4427 break;
4428 case tok::kw__Fract:
4429 assert(getLangOpts().FixedPoint &&
4430 "This keyword is only used when fixed point types are enabled "
4431 "with `-ffixed-point`");
4432 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_fract, Loc, PrevSpec, DiagID,
4433 Policy);
4434 break;
4435 case tok::kw__Sat:
4436 assert(getLangOpts().FixedPoint &&
4437 "This keyword is only used when fixed point types are enabled "
4438 "with `-ffixed-point`");
4439 isInvalid = DS.SetTypeSpecSat(Loc, PrevSpec, DiagID);
4440 break;
4441 case tok::kw___float128:
4442 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_float128, Loc, PrevSpec,
4443 DiagID, Policy);
4444 break;
4445 case tok::kw___ibm128:
4446 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_ibm128, Loc, PrevSpec,
4447 DiagID, Policy);
4448 break;
4449 case tok::kw_wchar_t:
4450 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_wchar, Loc, PrevSpec,
4451 DiagID, Policy);
4452 break;
4453 case tok::kw_char8_t:
4454 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_char8, Loc, PrevSpec,
4455 DiagID, Policy);
4456 break;
4457 case tok::kw_char16_t:
4458 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_char16, Loc, PrevSpec,
4459 DiagID, Policy);
4460 break;
4461 case tok::kw_char32_t:
4462 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_char32, Loc, PrevSpec,
4463 DiagID, Policy);
4464 break;
4465 case tok::kw_bool:
4466 if (getLangOpts().C23)
4467 Diag(Tok, DiagID: diag::warn_c23_compat_keyword) << Tok.getName();
4468 [[fallthrough]];
4469 case tok::kw__Bool:
4470 if (Tok.is(K: tok::kw__Bool) && !getLangOpts().C99)
4471 Diag(Tok, DiagID: diag::ext_c99_feature) << Tok.getName();
4472
4473 if (Tok.is(K: tok::kw_bool) &&
4474 DS.getTypeSpecType() != DeclSpec::TST_unspecified &&
4475 DS.getStorageClassSpec() == DeclSpec::SCS_typedef) {
4476 PrevSpec = ""; // Not used by the diagnostic.
4477 DiagID = diag::err_bool_redeclaration;
4478 // For better error recovery.
4479 Tok.setKind(tok::identifier);
4480 isInvalid = true;
4481 } else {
4482 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_bool, Loc, PrevSpec,
4483 DiagID, Policy);
4484 }
4485 break;
4486 case tok::kw__Decimal32:
4487 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_decimal32, Loc, PrevSpec,
4488 DiagID, Policy);
4489 break;
4490 case tok::kw__Decimal64:
4491 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_decimal64, Loc, PrevSpec,
4492 DiagID, Policy);
4493 break;
4494 case tok::kw__Decimal128:
4495 isInvalid = DS.SetTypeSpecType(T: DeclSpec::TST_decimal128, Loc, PrevSpec,
4496 DiagID, Policy);
4497 break;
4498 case tok::kw___vector:
4499 isInvalid = DS.SetTypeAltiVecVector(isAltiVecVector: true, Loc, PrevSpec, DiagID, Policy);
4500 break;
4501 case tok::kw___pixel:
4502 isInvalid = DS.SetTypeAltiVecPixel(isAltiVecPixel: true, Loc, PrevSpec, DiagID, Policy);
4503 break;
4504 case tok::kw___bool:
4505 isInvalid = DS.SetTypeAltiVecBool(isAltiVecBool: true, Loc, PrevSpec, DiagID, Policy);
4506 break;
4507 case tok::kw_pipe:
4508 if (!getLangOpts().OpenCL ||
4509 getLangOpts().getOpenCLCompatibleVersion() < 200) {
4510 // OpenCL 2.0 and later define this keyword. OpenCL 1.2 and earlier
4511 // should support the "pipe" word as identifier.
4512 Tok.getIdentifierInfo()->revertTokenIDToIdentifier();
4513 Tok.setKind(tok::identifier);
4514 goto DoneWithDeclSpec;
4515 } else if (!getLangOpts().OpenCLPipes) {
4516 DiagID = diag::err_opencl_unknown_type_specifier;
4517 PrevSpec = Tok.getIdentifierInfo()->getNameStart();
4518 isInvalid = true;
4519 } else
4520 isInvalid = DS.SetTypePipe(isPipe: true, Loc, PrevSpec, DiagID, Policy);
4521 break;
4522// We only need to enumerate each image type once.
4523#define IMAGE_READ_WRITE_TYPE(Type, Id, Ext)
4524#define IMAGE_WRITE_TYPE(Type, Id, Ext)
4525#define IMAGE_READ_TYPE(ImgType, Id, Ext) \
4526 case tok::kw_##ImgType##_t: \
4527 if (!handleOpenCLImageKW(Ext, DeclSpec::TST_##ImgType##_t)) \
4528 goto DoneWithDeclSpec; \
4529 break;
4530#include "clang/Basic/OpenCLImageTypes.def"
4531 case tok::kw___unknown_anytype:
4532 isInvalid = DS.SetTypeSpecType(T: TST_unknown_anytype, Loc,
4533 PrevSpec, DiagID, Policy);
4534 break;
4535
4536 // class-specifier:
4537 case tok::kw_class:
4538 case tok::kw_struct:
4539 case tok::kw___interface:
4540 case tok::kw_union: {
4541 tok::TokenKind Kind = Tok.getKind();
4542 ConsumeToken();
4543
4544 // These are attributes following class specifiers.
4545 // To produce better diagnostic, we parse them when
4546 // parsing class specifier.
4547 ParsedAttributes Attributes(AttrFactory);
4548 ParseClassSpecifier(TagTokKind: Kind, TagLoc: Loc, DS, TemplateInfo, AS,
4549 EnteringContext, DSC: DSContext, Attributes);
4550
4551 // If there are attributes following class specifier,
4552 // take them over and handle them here.
4553 if (!Attributes.empty()) {
4554 AttrsLastTime = true;
4555 attrs.takeAllAppendingFrom(Other&: Attributes);
4556 }
4557 continue;
4558 }
4559
4560 // enum-specifier:
4561 case tok::kw_enum:
4562 ConsumeToken();
4563 ParseEnumSpecifier(TagLoc: Loc, DS, TemplateInfo, AS, DSC: DSContext);
4564 continue;
4565
4566 // cv-qualifier:
4567 case tok::kw_const:
4568 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_const, Loc, PrevSpec, DiagID,
4569 Lang: getLangOpts());
4570 break;
4571 case tok::kw_volatile:
4572 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_volatile, Loc, PrevSpec, DiagID,
4573 Lang: getLangOpts());
4574 break;
4575 case tok::kw_restrict:
4576 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_restrict, Loc, PrevSpec, DiagID,
4577 Lang: getLangOpts());
4578 break;
4579 case tok::kw___ob_wrap:
4580 if (!getLangOpts().OverflowBehaviorTypes) {
4581 Diag(Loc, DiagID: diag::warn_overflow_behavior_keyword_disabled)
4582 << tok::getKeywordSpelling(Kind: Tok.getKind());
4583 break;
4584 }
4585 isInvalid = DS.SetOverflowBehavior(
4586 Kind: OverflowBehaviorType::OverflowBehaviorKind::Wrap, Loc, PrevSpec,
4587 DiagID);
4588 break;
4589 case tok::kw___ob_trap:
4590 if (!getLangOpts().OverflowBehaviorTypes) {
4591 Diag(Loc, DiagID: diag::warn_overflow_behavior_keyword_disabled)
4592 << tok::getKeywordSpelling(Kind: Tok.getKind());
4593 break;
4594 }
4595 isInvalid = DS.SetOverflowBehavior(
4596 Kind: OverflowBehaviorType::OverflowBehaviorKind::Trap, Loc, PrevSpec,
4597 DiagID);
4598 break;
4599
4600 // C++ typename-specifier:
4601 case tok::kw_typename:
4602 if (TryAnnotateTypeOrScopeToken()) {
4603 DS.SetTypeSpecError();
4604 goto DoneWithDeclSpec;
4605 }
4606 if (!Tok.is(K: tok::kw_typename))
4607 continue;
4608 break;
4609
4610 // C23/GNU typeof support.
4611 case tok::kw_typeof:
4612 case tok::kw_typeof_unqual:
4613 ParseTypeofSpecifier(DS);
4614 continue;
4615
4616 case tok::annot_decltype:
4617 ParseDecltypeSpecifier(DS);
4618 continue;
4619
4620 case tok::annot_pack_indexing_type:
4621 ParsePackIndexingType(DS);
4622 continue;
4623
4624 case tok::annot_pragma_pack:
4625 HandlePragmaPack();
4626 continue;
4627
4628 case tok::annot_pragma_ms_pragma:
4629 HandlePragmaMSPragma();
4630 continue;
4631
4632 case tok::annot_pragma_ms_vtordisp:
4633 HandlePragmaMSVtorDisp();
4634 continue;
4635
4636 case tok::annot_pragma_ms_pointers_to_members:
4637 HandlePragmaMSPointersToMembers();
4638 continue;
4639
4640 case tok::annot_pragma_export:
4641 HandlePragmaExport();
4642 continue;
4643
4644#define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) case tok::kw___##Trait:
4645#include "clang/Basic/BuiltinTraits.inc"
4646 // HACK: libstdc++ already uses '__remove_cv' as an alias template so we
4647 // work around this by expecting all transform type traits to be suffixed
4648 // with '('. They're an identifier otherwise.
4649 if (!MaybeParseTypeTransformTypeSpecifier(DS))
4650 goto ParseIdentifier;
4651 continue;
4652
4653 case tok::kw__Atomic:
4654 // C11 6.7.2.4/4:
4655 // If the _Atomic keyword is immediately followed by a left parenthesis,
4656 // it is interpreted as a type specifier (with a type name), not as a
4657 // type qualifier.
4658 diagnoseUseOfC11Keyword(Tok);
4659 if (NextToken().is(K: tok::l_paren)) {
4660 ParseAtomicSpecifier(DS);
4661 continue;
4662 }
4663 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_atomic, Loc, PrevSpec, DiagID,
4664 Lang: getLangOpts());
4665 break;
4666
4667 // OpenCL address space qualifiers:
4668 case tok::kw___generic:
4669 // generic address space is introduced only in OpenCL v2.0
4670 // see OpenCL C Spec v2.0 s6.5.5
4671 // OpenCL v3.0 introduces __opencl_c_generic_address_space
4672 // feature macro to indicate if generic address space is supported
4673 if (!Actions.getLangOpts().OpenCLGenericAddressSpace) {
4674 DiagID = diag::err_opencl_unknown_type_specifier;
4675 PrevSpec = Tok.getIdentifierInfo()->getNameStart();
4676 isInvalid = true;
4677 break;
4678 }
4679 [[fallthrough]];
4680 case tok::kw_private:
4681 // It's fine (but redundant) to check this for __generic on the
4682 // fallthrough path; we only form the __generic token in OpenCL mode.
4683 if (!getLangOpts().OpenCL)
4684 goto DoneWithDeclSpec;
4685 [[fallthrough]];
4686 case tok::kw___private:
4687 case tok::kw___global:
4688 case tok::kw___local:
4689 case tok::kw___constant:
4690 // OpenCL access qualifiers:
4691 case tok::kw___read_only:
4692 case tok::kw___write_only:
4693 case tok::kw___read_write:
4694 ParseOpenCLQualifiers(Attrs&: DS.getAttributes());
4695 break;
4696 case tok::kw_row_major:
4697 case tok::kw_column_major:
4698 case tok::kw_nointerpolation:
4699 case tok::kw_linear:
4700 case tok::kw_centroid:
4701 case tok::kw_noperspective:
4702 case tok::kw_sample:
4703 case tok::kw_center:
4704 case tok::kw_groupshared:
4705 case tok::kw_in:
4706 case tok::kw_inout:
4707 case tok::kw_out:
4708 // NOTE: ParseHLSLQualifiers will consume the qualifier token.
4709 ParseHLSLQualifiers(Attrs&: DS.getAttributes());
4710 continue;
4711
4712#define HLSL_INTANGIBLE_TYPE(Name, Id, SingletonId) \
4713 case tok::kw_##Name: \
4714 isInvalid = DS.SetTypeSpecType(DeclSpec::TST_##Name, Loc, PrevSpec, \
4715 DiagID, Policy); \
4716 break;
4717#include "clang/Basic/HLSLIntangibleTypes.def"
4718
4719#define HLSL_PACKED_TYPE(Name, Id, SingletonId) \
4720 case tok::kw_##Name: \
4721 isInvalid = DS.SetTypeSpecType(DeclSpec::TST_##Name, Loc, PrevSpec, \
4722 DiagID, Policy); \
4723 break;
4724#include "clang/Basic/HLSLPackedTypes.def"
4725
4726 case tok::less:
4727 // GCC ObjC supports types like "<SomeProtocol>" as a synonym for
4728 // "id<SomeProtocol>". This is hopelessly old fashioned and dangerous,
4729 // but we support it.
4730 if (DS.hasTypeSpecifier() || !getLangOpts().ObjC)
4731 goto DoneWithDeclSpec;
4732
4733 SourceLocation StartLoc = Tok.getLocation();
4734 SourceLocation EndLoc;
4735 TypeResult Type = parseObjCProtocolQualifierType(rAngleLoc&: EndLoc);
4736 if (Type.isUsable()) {
4737 if (DS.SetTypeSpecType(T: DeclSpec::TST_typename, TagKwLoc: StartLoc, TagNameLoc: StartLoc,
4738 PrevSpec, DiagID, Rep: Type.get(),
4739 Policy: Actions.getASTContext().getPrintingPolicy()))
4740 Diag(Loc: StartLoc, DiagID) << PrevSpec;
4741
4742 DS.SetRangeEnd(EndLoc);
4743 } else {
4744 DS.SetTypeSpecError();
4745 }
4746
4747 // Need to support trailing type qualifiers (e.g. "id<p> const").
4748 // If a type specifier follows, it will be diagnosed elsewhere.
4749 continue;
4750 }
4751
4752 DS.SetRangeEnd(ConsumedEnd.isValid() ? ConsumedEnd : Tok.getLocation());
4753
4754 // If the specifier wasn't legal, issue a diagnostic.
4755 if (isInvalid) {
4756 assert(PrevSpec && "Method did not return previous specifier!");
4757 assert(DiagID);
4758
4759 if (DiagID == diag::ext_duplicate_declspec ||
4760 DiagID == diag::ext_warn_duplicate_declspec ||
4761 DiagID == diag::err_duplicate_declspec)
4762 Diag(Loc, DiagID) << PrevSpec
4763 << FixItHint::CreateRemoval(
4764 RemoveRange: SourceRange(Loc, DS.getEndLoc()));
4765 else if (DiagID == diag::err_opencl_unknown_type_specifier) {
4766 Diag(Loc, DiagID) << getLangOpts().getOpenCLVersionString() << PrevSpec
4767 << isStorageClass;
4768 } else
4769 Diag(Loc, DiagID) << PrevSpec;
4770 }
4771
4772 if (DiagID != diag::err_bool_redeclaration && ConsumedEnd.isInvalid())
4773 // After an error the next token can be an annotation token.
4774 ConsumeAnyToken();
4775
4776 AttrsLastTime = false;
4777 }
4778}
4779
4780static void DiagnoseCountAttributedTypeInUnnamedAnon(ParsingDeclSpec &DS,
4781 Parser &P) {
4782
4783 if (DS.getTypeSpecType() != DeclSpec::TST_struct)
4784 return;
4785
4786 auto *RD = dyn_cast<RecordDecl>(Val: DS.getRepAsDecl());
4787 // We're only interested in unnamed, non-anonymous struct
4788 if (!RD || !RD->getName().empty() || RD->isAnonymousStructOrUnion())
4789 return;
4790
4791 for (auto *I : RD->decls()) {
4792 auto *VD = dyn_cast<ValueDecl>(Val: I);
4793 if (!VD)
4794 continue;
4795
4796 auto *CAT = VD->getType()->getAs<CountAttributedType>();
4797 if (!CAT)
4798 continue;
4799
4800 for (const auto &DD : CAT->dependent_decls()) {
4801 if (!RD->containsDecl(D: DD.getDecl())) {
4802 P.Diag(Loc: VD->getBeginLoc(), DiagID: diag::err_count_attr_param_not_in_same_struct)
4803 << DD.getDecl() << CAT->getKind() << CAT->isArrayType();
4804 P.Diag(Loc: DD.getDecl()->getBeginLoc(),
4805 DiagID: diag::note_flexible_array_counted_by_attr_field)
4806 << DD.getDecl();
4807 }
4808 }
4809 }
4810}
4811
4812void Parser::ParseStructDeclaration(
4813 ParsingDeclSpec &DS,
4814 llvm::function_ref<Decl *(ParsingFieldDeclarator &)> FieldsCallback,
4815 LateParsedAttrList *LateFieldAttrs) {
4816
4817 if (Tok.is(K: tok::kw___extension__)) {
4818 // __extension__ silences extension warnings in the subexpression.
4819 ExtensionRAIIObject O(Diags); // Use RAII to do this.
4820 ConsumeToken();
4821 return ParseStructDeclaration(DS, FieldsCallback, LateFieldAttrs);
4822 }
4823
4824 // Parse leading attributes.
4825 ParsedAttributes Attrs(AttrFactory);
4826 MaybeParseCXX11Attributes(Attrs);
4827
4828 // Parse the common specifier-qualifiers-list piece.
4829 ParseSpecifierQualifierList(DS);
4830
4831 // If there are no declarators, this is a free-standing declaration
4832 // specifier. Let the actions module cope with it.
4833 if (Tok.is(K: tok::semi)) {
4834 // C23 6.7.2.1p9 : "The optional attribute specifier sequence in a
4835 // member declaration appertains to each of the members declared by the
4836 // member declarator list; it shall not appear if the optional member
4837 // declarator list is omitted."
4838 ProhibitAttributes(Attrs);
4839 RecordDecl *AnonRecord = nullptr;
4840 Decl *TheDecl = Actions.ParsedFreeStandingDeclSpec(
4841 S: getCurScope(), AS: AS_none, DS, DeclAttrs: ParsedAttributesView::none(), AnonRecord);
4842 assert(!AnonRecord && "Did not expect anonymous struct or union here");
4843 DS.complete(D: TheDecl);
4844 return;
4845 }
4846
4847 // Read struct-declarators until we find the semicolon.
4848 bool FirstDeclarator = true;
4849 SourceLocation CommaLoc;
4850 while (true) {
4851 ParsingFieldDeclarator DeclaratorInfo(*this, DS, Attrs);
4852 DeclaratorInfo.D.setCommaLoc(CommaLoc);
4853
4854 // Attributes are only allowed here on successive declarators.
4855 if (!FirstDeclarator) {
4856 // However, this does not apply for [[]] attributes (which could show up
4857 // before or after the __attribute__ attributes).
4858 DiagnoseAndSkipCXX11Attributes();
4859 MaybeParseGNUAttributes(D&: DeclaratorInfo.D);
4860 DiagnoseAndSkipCXX11Attributes();
4861 }
4862
4863 /// struct-declarator: declarator
4864 /// struct-declarator: declarator[opt] ':' constant-expression
4865 if (Tok.isNot(K: tok::colon)) {
4866 // Don't parse FOO:BAR as if it were a typo for FOO::BAR.
4867 ColonProtectionRAIIObject X(*this);
4868 ParseDeclarator(D&: DeclaratorInfo.D);
4869 } else
4870 DeclaratorInfo.D.SetIdentifier(Id: nullptr, IdLoc: Tok.getLocation());
4871
4872 // Here, we now know that the unnamed struct is not an anonymous struct.
4873 // Report an error if a counted_by attribute refers to a field in a
4874 // different named struct.
4875 DiagnoseCountAttributedTypeInUnnamedAnon(DS, P&: *this);
4876
4877 if (TryConsumeToken(Expected: tok::colon)) {
4878 ExprResult Res(ParseConstantExpression());
4879 if (Res.isInvalid())
4880 SkipUntil(T: tok::semi, Flags: StopBeforeMatch);
4881 else
4882 DeclaratorInfo.BitfieldSize = Res.get();
4883 }
4884
4885 // If attributes exist after the declarator, parse them.
4886 MaybeParseGNUAttributes(D&: DeclaratorInfo.D, LateAttrs: LateFieldAttrs);
4887
4888 // We're done with this declarator; invoke the callback.
4889 Decl *Field = FieldsCallback(DeclaratorInfo);
4890 if (Field)
4891 DistributeCLateParsedAttrs(Dcl: Field, LateAttrs: LateFieldAttrs);
4892
4893 // If we don't have a comma, it is either the end of the list (a ';')
4894 // or an error, bail out.
4895 if (!TryConsumeToken(Expected: tok::comma, Loc&: CommaLoc))
4896 return;
4897
4898 FirstDeclarator = false;
4899 }
4900}
4901
4902ParsedAttributes Parser::ParseLexedAttributeTokens(LateParsedAttribute &LPA) {
4903 // Create a fake EOF so that attribute parsing won't go off the end of the
4904 // attribute.
4905 Token AttrEnd = Token::createEof(Loc: Tok.getLocation(), Data: LPA.Toks.data());
4906 LPA.Toks.push_back(Elt: AttrEnd);
4907
4908 // Append the current token at the end of the new token stream so that it
4909 // doesn't get lost.
4910 LPA.Toks.push_back(Elt: Tok);
4911 PP.EnterTokenStream(Toks: LPA.Toks, /*DisableMacroExpansion=*/true,
4912 /*IsReinject=*/true);
4913
4914 // Drop the current token and bring the first cached one. It's the same token
4915 // as when we entered this function.
4916 ConsumeAnyToken(/*ConsumeCodeCompletionTok=*/true);
4917
4918 ParsedAttributes Attrs(AttrFactory);
4919
4920 ParseGNUAttributeArgs(AttrName: &LPA.AttrName, AttrNameLoc: LPA.AttrNameLoc, Attrs,
4921 /*EndLoc=*/nullptr, /*ScopeName=*/nullptr,
4922 ScopeLoc: SourceLocation(), Form: ParsedAttr::Form::GNU(),
4923 /*D=*/nullptr);
4924
4925 // Due to a parsing error, we either went over the cached tokens or
4926 // there are still cached tokens left, so we skip the leftover tokens.
4927 while (Tok.isNot(K: tok::eof))
4928 ConsumeAnyToken();
4929
4930 // Consume the fake EOF token if it's there
4931 if (Tok.is(K: tok::eof) && Tok.getEofData() == AttrEnd.getEofData())
4932 ConsumeAnyToken();
4933
4934 return Attrs;
4935}
4936
4937void Parser::ParseLexedTypeAttribute(LateParsedTypeAttribute &LA,
4938 ParsedAttributes &OutAttrs) {
4939 assert(LA.Decls.size() <= 1 &&
4940 "late field attribute expects to have at most one declaration.");
4941
4942 ParsedAttributes Attrs = ParseLexedAttributeTokens(LPA&: LA);
4943 OutAttrs.takeAllAppendingFrom(Other&: Attrs);
4944}
4945
4946void Parser::CompleteLateParsedTypeAttributes(
4947 SmallVectorImpl<LateParsedTypeAttribute *> &LateTypeAttrs) {
4948 for (LateParsedTypeAttribute *RawLTA : LateTypeAttrs) {
4949 std::unique_ptr<LateParsedTypeAttribute> LTA(RawLTA);
4950
4951 BoundsAttributedType *BATy = LTA->TypeToComplete;
4952 if (!BATy || Actions.isLateParsedBoundsTypeRejected(BATy))
4953 continue;
4954
4955 ArrayRef<Decl *> Fields = LTA->Decls;
4956
4957 AttributeFactory AF;
4958 ParsedAttributes Attrs(AF);
4959 ParseLexedTypeAttribute(LA&: *LTA, OutAttrs&: Attrs);
4960
4961 // An unparseable argument leaves no attribute behind; already diagnosed.
4962 if (Attrs.empty())
4963 continue;
4964 assert(Attrs.size() == 1);
4965
4966 Expr *Arg = Attrs[0].getArgAsExpr(Arg: 0);
4967 assert(Arg);
4968
4969 bool Valid = true;
4970 assert(!Fields.empty());
4971 for (Decl *FD : Fields)
4972 Valid &= Actions.ActOnLateParsedTypeAttrArgument(
4973 BATy, FD: cast<FieldDecl>(Val: FD), Arg);
4974
4975 if (Valid)
4976 Attrs[0].setUsedAsTypeAttr();
4977 else
4978 Attrs[0].setInvalid();
4979 }
4980 LateTypeAttrs.clear();
4981}
4982
4983void LateParsedTypeAttribute::ParseInto(ParsedAttributes &OutAttrs) {
4984 // Delegate to the Parser that created this attribute
4985 Self->ParseLexedTypeAttribute(LA&: *this, OutAttrs);
4986}
4987
4988void Parser::TakeTypeAttrsAppendingFrom(LateParsedAttrList &To,
4989 LateParsedAttrList &From) {
4990 LateParsedAttrList::iterator It =
4991 llvm::remove_if(Range&: From, P: [&](LateParsedAttribute *LA) {
4992 if (isa<LateParsedTypeAttribute>(Val: LA)) {
4993 To.push_back(Elt: LA);
4994 return true;
4995 }
4996 return false;
4997 });
4998 From.erase(CS: It, CE: From.end());
4999}
5000
5001void Parser::ParseStructUnionBody(SourceLocation RecordLoc,
5002 DeclSpec::TST TagType, RecordDecl *TagDecl) {
5003 PrettyDeclStackTraceEntry CrashInfo(Actions.Context, TagDecl, RecordLoc,
5004 "parsing struct/union body");
5005 assert(!getLangOpts().CPlusPlus && "C++ declarations not supported");
5006
5007 BalancedDelimiterTracker T(*this, tok::l_brace);
5008 if (T.consumeOpen())
5009 return;
5010
5011 ParseScope StructScope(this, Scope::ClassScope|Scope::DeclScope);
5012 Actions.ActOnTagStartDefinition(S: getCurScope(), TagDecl);
5013
5014 // `LateAttrParseExperimentalExtOnly=true` requests that only attributes
5015 // marked with `LateAttrParseExperimentalExt` are late parsed.
5016 LateParsedAttrList LateFieldAttrs(/*PSoon=*/true,
5017 /*LateAttrParseExperimentalExtOnly=*/true);
5018
5019 // While we still have something to read, read the declarations in the struct.
5020 while (!tryParseMisplacedModuleImport() && Tok.isNot(K: tok::r_brace) &&
5021 Tok.isNot(K: tok::eof)) {
5022 // Each iteration of this loop reads one struct-declaration.
5023
5024 // Check for extraneous top-level semicolon.
5025 if (Tok.is(K: tok::semi)) {
5026 ConsumeExtraSemi(Kind: ExtraSemiKind::InsideStruct, T: TagType);
5027 continue;
5028 }
5029
5030 // Parse _Static_assert declaration.
5031 if (Tok.isOneOf(Ks: tok::kw__Static_assert, Ks: tok::kw_static_assert)) {
5032 SourceLocation DeclEnd;
5033 ParseStaticAssertDeclaration(DeclEnd);
5034 continue;
5035 }
5036
5037 if (Tok.is(K: tok::annot_pragma_pack)) {
5038 HandlePragmaPack();
5039 continue;
5040 }
5041
5042 if (Tok.is(K: tok::annot_pragma_align)) {
5043 HandlePragmaAlign();
5044 continue;
5045 }
5046
5047 if (Tok.isOneOf(Ks: tok::annot_pragma_openmp, Ks: tok::annot_attr_openmp)) {
5048 // Result can be ignored, because it must be always empty.
5049 AccessSpecifier AS = AS_none;
5050 ParsedAttributes Attrs(AttrFactory);
5051 (void)ParseOpenMPDeclarativeDirectiveWithExtDecl(AS, Attrs);
5052 continue;
5053 }
5054
5055 if (Tok.is(K: tok::annot_pragma_openacc)) {
5056 AccessSpecifier AS = AS_none;
5057 ParsedAttributes Attrs(AttrFactory);
5058 ParseOpenACCDirectiveDecl(AS, Attrs, TagType, TagDecl);
5059 continue;
5060 }
5061
5062 if (tok::isPragmaAnnotation(K: Tok.getKind())) {
5063 Diag(Loc: Tok.getLocation(), DiagID: diag::err_pragma_misplaced_in_decl)
5064 << DeclSpec::getSpecifierName(
5065 T: TagType, Policy: Actions.getASTContext().getPrintingPolicy());
5066 ConsumeAnnotationToken();
5067 continue;
5068 }
5069
5070 if (!Tok.is(K: tok::at)) {
5071 auto CFieldCallback = [&](ParsingFieldDeclarator &FD) -> Decl * {
5072 // Install the declarator into the current TagDecl.
5073 Decl *Field =
5074 Actions.ActOnField(S: getCurScope(), TagD: TagDecl,
5075 DeclStart: FD.D.getDeclSpec().getSourceRange().getBegin(),
5076 D&: FD.D, BitfieldWidth: FD.BitfieldSize);
5077 FD.complete(D: Field);
5078 return Field;
5079 };
5080
5081 // Parse all the comma separated declarators.
5082 ParsingDeclSpec DS(*this);
5083 ParseStructDeclaration(DS, FieldsCallback: CFieldCallback, LateFieldAttrs: &LateFieldAttrs);
5084 } else { // Handle @defs
5085 ConsumeToken();
5086 if (!Tok.isObjCAtKeyword(objcKey: tok::objc_defs)) {
5087 Diag(Tok, DiagID: diag::err_unexpected_at);
5088 SkipUntil(T: tok::semi);
5089 continue;
5090 }
5091 ConsumeToken();
5092 ExpectAndConsume(ExpectedTok: tok::l_paren);
5093 if (!Tok.is(K: tok::identifier)) {
5094 Diag(Tok, DiagID: diag::err_expected) << tok::identifier;
5095 SkipUntil(T: tok::semi);
5096 continue;
5097 }
5098 SmallVector<Decl *, 16> Fields;
5099 Actions.ObjC().ActOnDefs(S: getCurScope(), TagD: TagDecl, DeclStart: Tok.getLocation(),
5100 ClassName: Tok.getIdentifierInfo(), Decls&: Fields);
5101 ConsumeToken();
5102 ExpectAndConsume(ExpectedTok: tok::r_paren);
5103 }
5104
5105 if (TryConsumeToken(Expected: tok::semi))
5106 continue;
5107
5108 if (Tok.is(K: tok::r_brace)) {
5109 ExpectAndConsume(ExpectedTok: tok::semi, Diag: diag::ext_expected_semi_decl_list);
5110 break;
5111 }
5112
5113 ExpectAndConsume(ExpectedTok: tok::semi, Diag: diag::err_expected_semi_decl_list);
5114 // Skip to end of block or statement to avoid ext-warning on extra ';'.
5115 SkipUntil(T: tok::r_brace, Flags: StopAtSemi | StopBeforeMatch);
5116 // If we stopped at a ';', eat it.
5117 TryConsumeToken(Expected: tok::semi);
5118 }
5119
5120 T.consumeClose();
5121
5122 ParsedAttributes attrs(AttrFactory);
5123 // If attributes exist after struct contents, parse them.
5124 MaybeParseGNUAttributes(Attrs&: attrs, LateAttrs: &LateFieldAttrs);
5125
5126 SmallVector<Decl *, 32> FieldDecls(TagDecl->fields());
5127
5128 Actions.ActOnFields(S: getCurScope(), RecLoc: RecordLoc, TagDecl, Fields: FieldDecls,
5129 LBrac: T.getOpenLocation(), RBrac: T.getCloseLocation(), AttrList: attrs);
5130
5131 // Late parse field attributes if necessary.
5132 ParseLexedAttributeList(LAs&: LateFieldAttrs, /*D=*/nullptr, /*EnterScope=*/false,
5133 /*OnDefinition=*/false);
5134 StructScope.Exit();
5135 Actions.ActOnTagFinishDefinition(S: getCurScope(), TagDecl, BraceRange: T.getRange());
5136}
5137
5138void Parser::ParseEnumSpecifier(SourceLocation StartLoc, DeclSpec &DS,
5139 const ParsedTemplateInfo &TemplateInfo,
5140 AccessSpecifier AS, DeclSpecContext DSC) {
5141 // Parse the tag portion of this.
5142 if (Tok.is(K: tok::code_completion)) {
5143 // Code completion for an enum name.
5144 cutOffParsing();
5145 Actions.CodeCompletion().CodeCompleteTag(S: getCurScope(), TagSpec: DeclSpec::TST_enum);
5146 DS.SetTypeSpecError(); // Needed by ActOnUsingDeclaration.
5147 return;
5148 }
5149
5150 // If attributes exist after tag, parse them.
5151 ParsedAttributes attrs(AttrFactory);
5152 MaybeParseAttributes(WhichAttrKinds: PAKM_GNU | PAKM_Declspec | PAKM_CXX11, Attrs&: attrs);
5153
5154 SourceLocation ScopedEnumKWLoc;
5155 bool IsScopedUsingClassTag = false;
5156
5157 // In C++11, recognize 'enum class' and 'enum struct'.
5158 if (Tok.isOneOf(Ks: tok::kw_class, Ks: tok::kw_struct) && getLangOpts().CPlusPlus) {
5159 DiagCompat(Tok, CompatDiagId: diag_compat::scoped_enum);
5160 IsScopedUsingClassTag = Tok.is(K: tok::kw_class);
5161 ScopedEnumKWLoc = ConsumeToken();
5162
5163 // Attributes are not allowed between these keywords. Diagnose,
5164 // but then just treat them like they appeared in the right place.
5165 ProhibitAttributes(Attrs&: attrs);
5166
5167 // They are allowed afterwards, though.
5168 MaybeParseAttributes(WhichAttrKinds: PAKM_GNU | PAKM_Declspec | PAKM_CXX11, Attrs&: attrs);
5169 }
5170
5171 // C++11 [temp.explicit]p12:
5172 // The usual access controls do not apply to names used to specify
5173 // explicit instantiations.
5174 // We extend this to also cover explicit specializations. Note that
5175 // we don't suppress if this turns out to be an elaborated type
5176 // specifier.
5177 bool shouldDelayDiagsInTag =
5178 (TemplateInfo.Kind == ParsedTemplateKind::ExplicitInstantiation ||
5179 TemplateInfo.Kind == ParsedTemplateKind::ExplicitSpecialization);
5180 SuppressAccessChecks diagsFromTag(*this, shouldDelayDiagsInTag);
5181
5182 // Determine whether this declaration is permitted to have an enum-base.
5183 AllowDefiningTypeSpec AllowEnumSpecifier =
5184 isDefiningTypeSpecifierContext(DSC, IsCPlusPlus: getLangOpts().CPlusPlus);
5185 bool CanBeOpaqueEnumDeclaration =
5186 DS.isEmpty() && isOpaqueEnumDeclarationContext(DSC);
5187 bool CanHaveEnumBase = (getLangOpts().CPlusPlus11 || getLangOpts().ObjC ||
5188 getLangOpts().MicrosoftExt) &&
5189 (AllowEnumSpecifier == AllowDefiningTypeSpec::Yes ||
5190 CanBeOpaqueEnumDeclaration);
5191
5192 // We use a temporary scope when parsing the name specifier for a
5193 // declaration with additional invalid type specifiers.
5194 CXXScopeSpec InvalidDeclScope;
5195 CXXScopeSpec &SS =
5196 DS.hasTypeSpecifier() ? InvalidDeclScope : DS.getTypeSpecScope();
5197 if (getLangOpts().CPlusPlus) {
5198 // "enum foo : bar;" is not a potential typo for "enum foo::bar;".
5199 ColonProtectionRAIIObject X(*this);
5200
5201 CXXScopeSpec Spec;
5202 if (ParseOptionalCXXScopeSpecifier(SS&: Spec, /*ObjectType=*/nullptr,
5203 /*ObjectHasErrors=*/false,
5204 /*EnteringContext=*/true))
5205 return;
5206
5207 if (Spec.isSet() && Tok.isNot(K: tok::identifier)) {
5208 Diag(Tok, DiagID: diag::err_expected) << tok::identifier;
5209 DS.SetTypeSpecError();
5210 if (Tok.isNot(K: tok::l_brace)) {
5211 // Has no name and is not a definition.
5212 // Skip the rest of this declarator, up until the comma or semicolon.
5213 SkipUntil(T: tok::comma, Flags: StopAtSemi);
5214 return;
5215 }
5216 }
5217
5218 SS = std::move(Spec);
5219 }
5220
5221 // Must have either 'enum name' or 'enum {...}' or (rarely) 'enum : T { ... }'.
5222 if (Tok.isNot(K: tok::identifier) && Tok.isNot(K: tok::l_brace) &&
5223 Tok.isNot(K: tok::colon)) {
5224 Diag(Tok, DiagID: diag::err_expected_either) << tok::identifier << tok::l_brace;
5225
5226 DS.SetTypeSpecError();
5227 // Skip the rest of this declarator, up until the comma or semicolon.
5228 SkipUntil(T: tok::comma, Flags: StopAtSemi);
5229 return;
5230 }
5231
5232 // If an identifier is present, consume and remember it.
5233 IdentifierInfo *Name = nullptr;
5234 SourceLocation NameLoc;
5235 if (Tok.is(K: tok::identifier)) {
5236 Name = Tok.getIdentifierInfo();
5237 NameLoc = ConsumeToken();
5238 }
5239
5240 if (!Name && ScopedEnumKWLoc.isValid()) {
5241 // C++0x 7.2p2: The optional identifier shall not be omitted in the
5242 // declaration of a scoped enumeration.
5243 Diag(Tok, DiagID: diag::err_scoped_enum_missing_identifier);
5244 ScopedEnumKWLoc = SourceLocation();
5245 IsScopedUsingClassTag = false;
5246 }
5247
5248 // Okay, end the suppression area. We'll decide whether to emit the
5249 // diagnostics in a second.
5250 if (shouldDelayDiagsInTag)
5251 diagsFromTag.done();
5252
5253 TypeResult BaseType;
5254 SourceRange BaseRange;
5255
5256 bool CanBeBitfield =
5257 getCurScope()->isClassScope() && ScopedEnumKWLoc.isInvalid() && Name;
5258
5259 auto IsCXXTypeAhead = [this]() {
5260 RevertingTentativeParsingAction PA(*this);
5261 ConsumeToken();
5262 return Parser::isCXXTypeId(Context: TentativeCXXTypeIdContext::Unambiguous);
5263 };
5264
5265 // Parse the fixed underlying type.
5266 if (Tok.is(K: tok::colon) &&
5267 (!ParsingGenericAssociationType || IsCXXTypeAhead())) {
5268 // This might be an enum-base or part of some unrelated enclosing context.
5269 //
5270 // 'enum E : base' is permitted in two circumstances:
5271 //
5272 // 1) As a defining-type-specifier, when followed by '{'.
5273 // 2) As the sole constituent of a complete declaration -- when DS is empty
5274 // and the next token is ';'.
5275 //
5276 // The restriction to defining-type-specifiers is important to allow parsing
5277 // a ? new enum E : int{}
5278 // _Generic(a, enum E : int{})
5279 // properly.
5280 //
5281 // One additional consideration applies:
5282 //
5283 // C++ [dcl.enum]p1:
5284 // A ':' following "enum nested-name-specifier[opt] identifier" within
5285 // the decl-specifier-seq of a member-declaration is parsed as part of
5286 // an enum-base.
5287 //
5288 // Other language modes supporting enumerations with fixed underlying types
5289 // do not have clear rules on this, so we disambiguate to determine whether
5290 // the tokens form a bit-field width or an enum-base.
5291
5292 if (CanBeBitfield && !isEnumBase(AllowSemi: CanBeOpaqueEnumDeclaration)) {
5293 // Outside C++11, do not interpret the tokens as an enum-base if they do
5294 // not make sense as one. In C++11, it's an error if this happens.
5295 if (getLangOpts().CPlusPlus11)
5296 Diag(Loc: Tok.getLocation(), DiagID: diag::err_anonymous_enum_bitfield);
5297 } else if (CanHaveEnumBase || !ColonIsSacred) {
5298 SourceLocation ColonLoc = ConsumeToken();
5299
5300 // Parse a type-specifier-seq as a type. We can't just ParseTypeName here,
5301 // because under -fms-extensions,
5302 // enum E : int *p;
5303 // declares 'enum E : int; E *p;' not 'enum E : int*; E p;'.
5304 DeclSpec DS(AttrFactory);
5305 // enum-base is not assumed to be a type and therefore requires the
5306 // typename keyword [p0634r3].
5307 ParseSpecifierQualifierList(DS, AllowImplicitTypename: ImplicitTypenameContext::No, AS,
5308 DSC: DeclSpecContext::DSC_type_specifier);
5309 Declarator DeclaratorInfo(DS, ParsedAttributesView::none(),
5310 DeclaratorContext::TypeName);
5311 BaseType = Actions.ActOnTypeName(D&: DeclaratorInfo);
5312
5313 BaseRange = SourceRange(ColonLoc, DeclaratorInfo.getSourceRange().getEnd());
5314
5315 if (!getLangOpts().ObjC) {
5316 if (getLangOpts().CPlusPlus)
5317 DiagCompat(Loc: ColonLoc, CompatDiagId: diag_compat::cxx_enum_fixed_underlying_type)
5318 << BaseRange;
5319 else if (getLangOpts().MicrosoftExt && !getLangOpts().C23)
5320 Diag(Loc: ColonLoc, DiagID: diag::ext_ms_c_enum_fixed_underlying_type)
5321 << BaseRange;
5322 else
5323 DiagCompat(Loc: ColonLoc, CompatDiagId: diag_compat::c_enum_fixed_underlying_type)
5324 << BaseRange;
5325 }
5326 }
5327 }
5328
5329 // There are four options here. If we have 'friend enum foo;' then this is a
5330 // friend declaration, and cannot have an accompanying definition. If we have
5331 // 'enum foo;', then this is a forward declaration. If we have
5332 // 'enum foo {...' then this is a definition. Otherwise we have something
5333 // like 'enum foo xyz', a reference.
5334 //
5335 // This is needed to handle stuff like this right (C99 6.7.2.3p11):
5336 // enum foo {..}; void bar() { enum foo; } <- new foo in bar.
5337 // enum foo {..}; void bar() { enum foo x; } <- use of old foo.
5338 //
5339 TagUseKind TUK;
5340 if (AllowEnumSpecifier == AllowDefiningTypeSpec::No)
5341 TUK = TagUseKind::Reference;
5342 else if (Tok.is(K: tok::l_brace)) {
5343 if (DS.isFriendSpecified()) {
5344 Diag(Loc: Tok.getLocation(), DiagID: diag::err_friend_decl_defines_type)
5345 << SourceRange(DS.getFriendSpecLoc());
5346 ConsumeBrace();
5347 SkipUntil(T: tok::r_brace, Flags: StopAtSemi);
5348 // Discard any other definition-only pieces.
5349 attrs.clear();
5350 ScopedEnumKWLoc = SourceLocation();
5351 IsScopedUsingClassTag = false;
5352 BaseType = TypeResult();
5353 TUK = TagUseKind::Friend;
5354 } else {
5355 TUK = TagUseKind::Definition;
5356 }
5357 } else if (!isTypeSpecifier(DSC) &&
5358 (Tok.is(K: tok::semi) ||
5359 (Tok.isAtStartOfLine() &&
5360 !isValidAfterTypeSpecifier(CouldBeBitfield: CanBeBitfield)))) {
5361 // An opaque-enum-declaration is required to be standalone (no preceding or
5362 // following tokens in the declaration). Sema enforces this separately by
5363 // diagnosing anything else in the DeclSpec.
5364 TUK = DS.isFriendSpecified() ? TagUseKind::Friend : TagUseKind::Declaration;
5365 if (Tok.isNot(K: tok::semi)) {
5366 // A semicolon was missing after this declaration. Diagnose and recover.
5367 ExpectAndConsume(ExpectedTok: tok::semi, Diag: diag::err_expected_after, DiagMsg: "enum");
5368 PP.EnterToken(Tok, /*IsReinject=*/true);
5369 Tok.setKind(tok::semi);
5370 }
5371 } else {
5372 TUK = TagUseKind::Reference;
5373 }
5374
5375 bool IsElaboratedTypeSpecifier =
5376 TUK == TagUseKind::Reference || TUK == TagUseKind::Friend;
5377
5378 // If this is an elaborated type specifier nested in a larger declaration,
5379 // and we delayed diagnostics before, just merge them into the current pool.
5380 if (TUK == TagUseKind::Reference && shouldDelayDiagsInTag) {
5381 diagsFromTag.redelay();
5382 }
5383
5384 MultiTemplateParamsArg TParams;
5385 if (TemplateInfo.Kind != ParsedTemplateKind::NonTemplate &&
5386 TUK != TagUseKind::Reference) {
5387 if (!getLangOpts().CPlusPlus11 || !SS.isSet()) {
5388 // Skip the rest of this declarator, up until the comma or semicolon.
5389 Diag(Tok, DiagID: diag::err_enum_template);
5390 SkipUntil(T: tok::comma, Flags: StopAtSemi);
5391 return;
5392 }
5393
5394 if (TemplateInfo.Kind == ParsedTemplateKind::ExplicitInstantiation) {
5395 // Enumerations can't be explicitly instantiated.
5396 DS.SetTypeSpecError();
5397 Diag(Loc: StartLoc, DiagID: diag::err_explicit_instantiation_enum);
5398 return;
5399 }
5400
5401 assert(TemplateInfo.TemplateParams && "no template parameters");
5402 TParams = MultiTemplateParamsArg(TemplateInfo.TemplateParams->data(),
5403 TemplateInfo.TemplateParams->size());
5404 SS.setTemplateParamLists(TParams);
5405 }
5406
5407 if (!Name && TUK != TagUseKind::Definition) {
5408 Diag(Tok, DiagID: diag::err_enumerator_unnamed_no_def);
5409
5410 DS.SetTypeSpecError();
5411 // Skip the rest of this declarator, up until the comma or semicolon.
5412 SkipUntil(T: tok::comma, Flags: StopAtSemi);
5413 return;
5414 }
5415
5416 // An elaborated-type-specifier has a much more constrained grammar:
5417 //
5418 // 'enum' nested-name-specifier[opt] identifier
5419 //
5420 // If we parsed any other bits, reject them now.
5421 //
5422 // MSVC and (for now at least) Objective-C permit a full enum-specifier
5423 // or opaque-enum-declaration anywhere.
5424 if (IsElaboratedTypeSpecifier && !getLangOpts().MicrosoftExt &&
5425 !getLangOpts().ObjC) {
5426 ProhibitCXX11Attributes(Attrs&: attrs, AttrDiagID: diag::err_attributes_not_allowed,
5427 KeywordDiagID: diag::err_keyword_not_allowed,
5428 /*DiagnoseEmptyAttrs=*/true);
5429 if (BaseType.isUsable())
5430 Diag(Loc: BaseRange.getBegin(), DiagID: diag::ext_enum_base_in_type_specifier)
5431 << (AllowEnumSpecifier == AllowDefiningTypeSpec::Yes) << BaseRange;
5432 else if (ScopedEnumKWLoc.isValid())
5433 Diag(Loc: ScopedEnumKWLoc, DiagID: diag::ext_elaborated_enum_class)
5434 << FixItHint::CreateRemoval(RemoveRange: ScopedEnumKWLoc) << IsScopedUsingClassTag;
5435 }
5436
5437 stripTypeAttributesOffDeclSpec(Attrs&: attrs, DS, TUK);
5438
5439 SkipBodyInfo SkipBody;
5440 if (!Name && TUK == TagUseKind::Definition && Tok.is(K: tok::l_brace) &&
5441 NextToken().is(K: tok::identifier))
5442 SkipBody = Actions.shouldSkipAnonEnumBody(S: getCurScope(),
5443 II: NextToken().getIdentifierInfo(),
5444 IILoc: NextToken().getLocation());
5445
5446 bool Owned = false;
5447 bool IsDependent = false;
5448 const char *PrevSpec = nullptr;
5449 unsigned DiagID;
5450 Decl *TagDecl =
5451 Actions.ActOnTag(S: getCurScope(), TagSpec: DeclSpec::TST_enum, TUK, KWLoc: StartLoc, SS,
5452 Name, NameLoc, Attr: attrs, AS, ModulePrivateLoc: DS.getModulePrivateSpecLoc(),
5453 TemplateParameterLists: TParams, OwnedDecl&: Owned, IsDependent, ScopedEnumKWLoc,
5454 ScopedEnumUsesClassTag: IsScopedUsingClassTag,
5455 UnderlyingType: BaseType, IsTypeSpecifier: DSC == DeclSpecContext::DSC_type_specifier,
5456 IsTemplateParamOrArg: DSC == DeclSpecContext::DSC_template_param ||
5457 DSC == DeclSpecContext::DSC_template_type_arg,
5458 OOK: OffsetOfState, SkipBody: &SkipBody).get();
5459
5460 if (SkipBody.ShouldSkip) {
5461 assert(TUK == TagUseKind::Definition && "can only skip a definition");
5462
5463 BalancedDelimiterTracker T(*this, tok::l_brace);
5464 T.consumeOpen();
5465 T.skipToEnd();
5466
5467 if (DS.SetTypeSpecType(T: DeclSpec::TST_enum, TagKwLoc: StartLoc,
5468 TagNameLoc: NameLoc.isValid() ? NameLoc : StartLoc,
5469 PrevSpec, DiagID, Rep: TagDecl, Owned,
5470 Policy: Actions.getASTContext().getPrintingPolicy()))
5471 Diag(Loc: StartLoc, DiagID) << PrevSpec;
5472 return;
5473 }
5474
5475 if (IsDependent) {
5476 // This enum has a dependent nested-name-specifier. Handle it as a
5477 // dependent tag.
5478 if (!Name) {
5479 DS.SetTypeSpecError();
5480 Diag(Tok, DiagID: diag::err_expected_type_name_after_typename);
5481 return;
5482 }
5483
5484 TypeResult Type = Actions.ActOnDependentTag(
5485 S: getCurScope(), TagSpec: DeclSpec::TST_enum, TUK, SS, Name, TagLoc: StartLoc, NameLoc);
5486 if (Type.isInvalid()) {
5487 DS.SetTypeSpecError();
5488 return;
5489 }
5490
5491 if (DS.SetTypeSpecType(T: DeclSpec::TST_typename, TagKwLoc: StartLoc,
5492 TagNameLoc: NameLoc.isValid() ? NameLoc : StartLoc,
5493 PrevSpec, DiagID, Rep: Type.get(),
5494 Policy: Actions.getASTContext().getPrintingPolicy()))
5495 Diag(Loc: StartLoc, DiagID) << PrevSpec;
5496
5497 return;
5498 }
5499
5500 if (!TagDecl) {
5501 // The action failed to produce an enumeration tag. If this is a
5502 // definition, consume the entire definition.
5503 if (Tok.is(K: tok::l_brace) && TUK != TagUseKind::Reference) {
5504 ConsumeBrace();
5505 SkipUntil(T: tok::r_brace, Flags: StopAtSemi);
5506 }
5507
5508 DS.SetTypeSpecError();
5509 return;
5510 }
5511
5512 if (Tok.is(K: tok::l_brace) && TUK == TagUseKind::Definition) {
5513 Decl *D = SkipBody.CheckSameAsPrevious ? SkipBody.New : TagDecl;
5514 ParseEnumBody(StartLoc, TagDecl: D, SkipBody: &SkipBody);
5515 if (SkipBody.CheckSameAsPrevious &&
5516 !Actions.ActOnDuplicateDefinition(S: getCurScope(), Prev: TagDecl, SkipBody)) {
5517 DS.SetTypeSpecError();
5518 return;
5519 }
5520 }
5521
5522 if (DS.SetTypeSpecType(T: DeclSpec::TST_enum, TagKwLoc: StartLoc,
5523 TagNameLoc: NameLoc.isValid() ? NameLoc : StartLoc,
5524 PrevSpec, DiagID, Rep: TagDecl, Owned,
5525 Policy: Actions.getASTContext().getPrintingPolicy()))
5526 Diag(Loc: StartLoc, DiagID) << PrevSpec;
5527}
5528
5529void Parser::ParseEnumBody(SourceLocation StartLoc, Decl *EnumDecl,
5530 SkipBodyInfo *SkipBody) {
5531 // Enter the scope of the enum body and start the definition.
5532 ParseScope EnumScope(this, Scope::DeclScope | Scope::EnumScope);
5533 Actions.ActOnTagStartDefinition(S: getCurScope(), TagDecl: EnumDecl);
5534
5535 BalancedDelimiterTracker T(*this, tok::l_brace);
5536 T.consumeOpen();
5537
5538 // C does not allow an empty enumerator-list, C++ does [dcl.enum].
5539 if (Tok.is(K: tok::r_brace) && !getLangOpts().CPlusPlus) {
5540 if (getLangOpts().MicrosoftExt)
5541 Diag(Loc: T.getOpenLocation(), DiagID: diag::ext_ms_c_empty_enum_type)
5542 << SourceRange(T.getOpenLocation(), Tok.getLocation());
5543 else
5544 Diag(Tok, DiagID: diag::err_empty_enum);
5545 }
5546
5547 SmallVector<Decl *, 32> EnumConstantDecls;
5548 SmallVector<SuppressAccessChecks, 32> EnumAvailabilityDiags;
5549
5550 Decl *LastEnumConstDecl = nullptr;
5551
5552 // Parse the enumerator-list.
5553 while (Tok.isNot(K: tok::r_brace)) {
5554 // Parse enumerator. If failed, try skipping till the start of the next
5555 // enumerator definition.
5556 if (Tok.isNot(K: tok::identifier)) {
5557 Diag(Loc: Tok.getLocation(), DiagID: diag::err_expected) << tok::identifier;
5558 if (SkipUntil(T1: tok::comma, T2: tok::r_brace, Flags: StopBeforeMatch) &&
5559 TryConsumeToken(Expected: tok::comma))
5560 continue;
5561 break;
5562 }
5563 IdentifierInfo *Ident = Tok.getIdentifierInfo();
5564 SourceLocation IdentLoc = ConsumeToken();
5565
5566 // If attributes exist after the enumerator, parse them.
5567 ParsedAttributes attrs(AttrFactory);
5568 MaybeParseGNUAttributes(Attrs&: attrs);
5569 if (isAllowedCXX11AttributeSpecifier()) {
5570 if (getLangOpts().CPlusPlus)
5571 DiagCompat(Loc: Tok.getLocation(), CompatDiagId: diag_compat::ns_enum_attribute)
5572 << 1 /*enumerator*/;
5573 ParseCXX11Attributes(attrs);
5574 }
5575
5576 SourceLocation EqualLoc;
5577 ExprResult AssignedVal;
5578 EnumAvailabilityDiags.emplace_back(Args&: *this);
5579
5580 EnterExpressionEvaluationContext ConstantEvaluated(
5581 Actions, Sema::ExpressionEvaluationContext::ConstantEvaluated);
5582 if (TryConsumeToken(Expected: tok::equal, Loc&: EqualLoc)) {
5583 AssignedVal = ParseConstantExpressionInExprEvalContext();
5584 if (AssignedVal.isInvalid())
5585 SkipUntil(T1: tok::comma, T2: tok::r_brace, Flags: StopBeforeMatch);
5586 }
5587
5588 // Install the enumerator constant into EnumDecl.
5589 Decl *EnumConstDecl = Actions.ActOnEnumConstant(
5590 S: getCurScope(), EnumDecl, LastEnumConstant: LastEnumConstDecl, IdLoc: IdentLoc, Id: Ident, Attrs: attrs,
5591 EqualLoc, Val: AssignedVal.get(), SkipBody);
5592 EnumAvailabilityDiags.back().done();
5593
5594 EnumConstantDecls.push_back(Elt: EnumConstDecl);
5595 LastEnumConstDecl = EnumConstDecl;
5596
5597 if (Tok.is(K: tok::identifier)) {
5598 // We're missing a comma between enumerators.
5599 SourceLocation Loc = getEndOfPreviousToken();
5600 Diag(Loc, DiagID: diag::err_enumerator_list_missing_comma)
5601 << FixItHint::CreateInsertion(InsertionLoc: Loc, Code: ", ");
5602 continue;
5603 }
5604
5605 // Emumerator definition must be finished, only comma or r_brace are
5606 // allowed here.
5607 SourceLocation CommaLoc;
5608 if (Tok.isNot(K: tok::r_brace) && !TryConsumeToken(Expected: tok::comma, Loc&: CommaLoc)) {
5609 if (EqualLoc.isValid())
5610 Diag(Loc: Tok.getLocation(), DiagID: diag::err_expected_either) << tok::r_brace
5611 << tok::comma;
5612 else
5613 Diag(Loc: Tok.getLocation(), DiagID: diag::err_expected_end_of_enumerator);
5614 if (SkipUntil(T1: tok::comma, T2: tok::r_brace, Flags: StopBeforeMatch)) {
5615 if (TryConsumeToken(Expected: tok::comma, Loc&: CommaLoc))
5616 continue;
5617 } else {
5618 break;
5619 }
5620 }
5621
5622 // If comma is followed by r_brace, emit appropriate warning.
5623 if (Tok.is(K: tok::r_brace) && CommaLoc.isValid()) {
5624 if (getLangOpts().CPlusPlus)
5625 DiagCompat(Loc: CommaLoc, CompatDiagId: diag_compat::cxx_enumerator_list_comma)
5626 << FixItHint::CreateRemoval(RemoveRange: CommaLoc);
5627 else if (!getLangOpts().C99)
5628 Diag(Loc: CommaLoc, DiagID: diag::ext_enumerator_list_comma_c)
5629 << FixItHint::CreateRemoval(RemoveRange: CommaLoc);
5630 break;
5631 }
5632 }
5633
5634 // Eat the }.
5635 T.consumeClose();
5636
5637 // If attributes exist after the identifier list, parse them.
5638 ParsedAttributes attrs(AttrFactory);
5639 MaybeParseGNUAttributes(Attrs&: attrs);
5640
5641 Actions.ActOnEnumBody(EnumLoc: StartLoc, BraceRange: T.getRange(), EnumDecl, Elements: EnumConstantDecls,
5642 S: getCurScope(), Attr: attrs);
5643
5644 // Now handle enum constant availability diagnostics.
5645 assert(EnumConstantDecls.size() == EnumAvailabilityDiags.size());
5646 for (size_t i = 0, e = EnumConstantDecls.size(); i != e; ++i) {
5647 ParsingDeclRAIIObject PD(*this, ParsingDeclRAIIObject::NoParent);
5648 EnumAvailabilityDiags[i].redelay();
5649 PD.complete(D: EnumConstantDecls[i]);
5650 }
5651
5652 EnumScope.Exit();
5653 Actions.ActOnTagFinishDefinition(S: getCurScope(), TagDecl: EnumDecl, BraceRange: T.getRange());
5654
5655 // The next token must be valid after an enum definition. If not, a ';'
5656 // was probably forgotten.
5657 bool CanBeBitfield = getCurScope()->isClassScope();
5658 if (!isValidAfterTypeSpecifier(CouldBeBitfield: CanBeBitfield)) {
5659 ExpectAndConsume(ExpectedTok: tok::semi, Diag: diag::err_expected_after, DiagMsg: "enum");
5660 // Push this token back into the preprocessor and change our current token
5661 // to ';' so that the rest of the code recovers as though there were an
5662 // ';' after the definition.
5663 PP.EnterToken(Tok, /*IsReinject=*/true);
5664 Tok.setKind(tok::semi);
5665 }
5666}
5667
5668bool Parser::isKnownToBeTypeSpecifier(const Token &Tok) const {
5669 switch (Tok.getKind()) {
5670 default: return false;
5671 // type-specifiers
5672 case tok::kw_short:
5673 case tok::kw_long:
5674 case tok::kw___int64:
5675 case tok::kw___int128:
5676 case tok::kw_signed:
5677 case tok::kw_unsigned:
5678 case tok::kw__Complex:
5679 case tok::kw__Imaginary:
5680 case tok::kw_void:
5681 case tok::kw_char:
5682 case tok::kw_wchar_t:
5683 case tok::kw_char8_t:
5684 case tok::kw_char16_t:
5685 case tok::kw_char32_t:
5686 case tok::kw_int:
5687 case tok::kw__ExtInt:
5688 case tok::kw__BitInt:
5689 case tok::kw___bf16:
5690 case tok::kw_half:
5691 case tok::kw_float:
5692 case tok::kw_double:
5693 case tok::kw__Accum:
5694 case tok::kw__Fract:
5695 case tok::kw__Float16:
5696 case tok::kw___float128:
5697 case tok::kw___ibm128:
5698 case tok::kw_bool:
5699 case tok::kw__Bool:
5700 case tok::kw__Decimal32:
5701 case tok::kw__Decimal64:
5702 case tok::kw__Decimal128:
5703 case tok::kw___vector:
5704#define GENERIC_IMAGE_TYPE(ImgType, Id) case tok::kw_##ImgType##_t:
5705#include "clang/Basic/OpenCLImageTypes.def"
5706#define HLSL_INTANGIBLE_TYPE(Name, Id, SingletonId) case tok::kw_##Name:
5707#include "clang/Basic/HLSLIntangibleTypes.def"
5708#define HLSL_PACKED_TYPE(Name, Id, SingletonId) case tok::kw_##Name:
5709#include "clang/Basic/HLSLPackedTypes.def"
5710
5711 // struct-or-union-specifier (C99) or class-specifier (C++)
5712 case tok::kw_class:
5713 case tok::kw_struct:
5714 case tok::kw___interface:
5715 case tok::kw_union:
5716 // enum-specifier
5717 case tok::kw_enum:
5718
5719 case tok::kw_typeof:
5720 case tok::kw_typeof_unqual:
5721
5722 // C11 _Atomic
5723 case tok::kw__Atomic:
5724
5725 // typedef-name
5726 case tok::annot_typename:
5727 return true;
5728 }
5729}
5730
5731bool Parser::isTypeSpecifierQualifier(const Token &Tok) {
5732 switch (Tok.getKind()) {
5733 default: return false;
5734
5735 case tok::identifier: // foo::bar
5736 if (TryAltiVecVectorToken())
5737 return true;
5738 [[fallthrough]];
5739 case tok::kw_typename: // typename T::type
5740 // Annotate typenames and C++ scope specifiers. If we get one, just
5741 // recurse to handle whatever we get.
5742 if (TryAnnotateTypeOrScopeToken())
5743 return true;
5744 if (getCurToken().is(K: tok::identifier))
5745 return false;
5746 return isTypeSpecifierQualifier(Tok: getCurToken());
5747
5748 case tok::coloncolon: // ::foo::bar
5749 if (NextToken().is(K: tok::kw_new) || // ::new
5750 NextToken().is(K: tok::kw_delete)) // ::delete
5751 return false;
5752
5753 if (TryAnnotateTypeOrScopeToken())
5754 return true;
5755 return isTypeSpecifierQualifier(Tok: getCurToken());
5756
5757 // GNU attributes support.
5758 case tok::kw___attribute:
5759 // C23/GNU typeof support.
5760 case tok::kw_typeof:
5761 case tok::kw_typeof_unqual:
5762
5763 // type-specifiers
5764 case tok::kw_short:
5765 case tok::kw_long:
5766 case tok::kw___int64:
5767 case tok::kw___int128:
5768 case tok::kw_signed:
5769 case tok::kw_unsigned:
5770 case tok::kw__Complex:
5771 case tok::kw__Imaginary:
5772 case tok::kw_void:
5773 case tok::kw_char:
5774 case tok::kw_wchar_t:
5775 case tok::kw_char8_t:
5776 case tok::kw_char16_t:
5777 case tok::kw_char32_t:
5778 case tok::kw_int:
5779 case tok::kw__ExtInt:
5780 case tok::kw__BitInt:
5781 case tok::kw_half:
5782 case tok::kw___bf16:
5783 case tok::kw_float:
5784 case tok::kw_double:
5785 case tok::kw__Accum:
5786 case tok::kw__Fract:
5787 case tok::kw__Float16:
5788 case tok::kw___float128:
5789 case tok::kw___ibm128:
5790 case tok::kw_bool:
5791 case tok::kw__Bool:
5792 case tok::kw__Decimal32:
5793 case tok::kw__Decimal64:
5794 case tok::kw__Decimal128:
5795 case tok::kw___vector:
5796#define GENERIC_IMAGE_TYPE(ImgType, Id) case tok::kw_##ImgType##_t:
5797#include "clang/Basic/OpenCLImageTypes.def"
5798#define HLSL_INTANGIBLE_TYPE(Name, Id, SingletonId) case tok::kw_##Name:
5799#include "clang/Basic/HLSLIntangibleTypes.def"
5800#define HLSL_PACKED_TYPE(Name, Id, SingletonId) case tok::kw_##Name:
5801#include "clang/Basic/HLSLPackedTypes.def"
5802
5803 // struct-or-union-specifier (C99) or class-specifier (C++)
5804 case tok::kw_class:
5805 case tok::kw_struct:
5806 case tok::kw___interface:
5807 case tok::kw_union:
5808 // enum-specifier
5809 case tok::kw_enum:
5810
5811 // type-qualifier
5812 case tok::kw_const:
5813 case tok::kw_volatile:
5814 case tok::kw_restrict:
5815 case tok::kw___ob_wrap:
5816 case tok::kw___ob_trap:
5817 case tok::kw__Sat:
5818
5819 // Debugger support.
5820 case tok::kw___unknown_anytype:
5821
5822 // typedef-name
5823 case tok::annot_typename:
5824 return true;
5825
5826 // GNU ObjC bizarre protocol extension: <proto1,proto2> with implicit 'id'.
5827 case tok::less:
5828 return getLangOpts().ObjC;
5829
5830 case tok::kw___cdecl:
5831 case tok::kw___stdcall:
5832 case tok::kw___fastcall:
5833 case tok::kw___thiscall:
5834 case tok::kw___regcall:
5835 case tok::kw___vectorcall:
5836 case tok::kw___w64:
5837 case tok::kw___ptr64:
5838 case tok::kw___ptr32:
5839 case tok::kw___pascal:
5840 case tok::kw___unaligned:
5841 case tok::kw___ptrauth:
5842
5843 case tok::kw__Nonnull:
5844 case tok::kw__Nullable:
5845 case tok::kw__Nullable_result:
5846 case tok::kw__Null_unspecified:
5847
5848 case tok::kw___kindof:
5849
5850 case tok::kw___private:
5851 case tok::kw___local:
5852 case tok::kw___global:
5853 case tok::kw___constant:
5854 case tok::kw___generic:
5855 case tok::kw___read_only:
5856 case tok::kw___read_write:
5857 case tok::kw___write_only:
5858 case tok::kw___funcref:
5859 return true;
5860
5861 case tok::kw_private:
5862 return getLangOpts().OpenCL;
5863
5864 // C11 _Atomic
5865 case tok::kw__Atomic:
5866 return true;
5867
5868 // HLSL type qualifiers
5869 case tok::kw_nointerpolation:
5870 case tok::kw_linear:
5871 case tok::kw_centroid:
5872 case tok::kw_noperspective:
5873 case tok::kw_sample:
5874 case tok::kw_center:
5875 case tok::kw_groupshared:
5876 case tok::kw_in:
5877 case tok::kw_inout:
5878 case tok::kw_out:
5879 case tok::kw_row_major:
5880 case tok::kw_column_major:
5881 return getLangOpts().HLSL;
5882 }
5883}
5884
5885Parser::DeclGroupPtrTy Parser::ParseTopLevelStmtDecl() {
5886 assert(PP.isIncrementalProcessingEnabled() && "Not in incremental mode");
5887
5888 // Parse a top-level-stmt.
5889 Parser::StmtVector Stmts;
5890 ParsedStmtContext SubStmtCtx = ParsedStmtContext();
5891 ParseScope FnScope(this, Scope::FnScope | Scope::DeclScope |
5892 Scope::CompoundStmtScope);
5893 TopLevelStmtDecl *TLSD = Actions.ActOnStartTopLevelStmtDecl(S: getCurScope());
5894 StmtResult R = ParseStatementOrDeclaration(Stmts, StmtCtx: SubStmtCtx);
5895 Actions.ActOnFinishTopLevelStmtDecl(D: TLSD, Statement: R.get());
5896 if (!R.isUsable()) {
5897 R = Actions.ActOnNullStmt(SemiLoc: Tok.getLocation());
5898 TLSD->setStmt(R.get());
5899 }
5900
5901 if (Tok.is(K: tok::eof) && Tok.getEofData()) {
5902 ConsumeToken();
5903 TLSD->setSemiMissing();
5904 }
5905
5906 SmallVector<Decl *, 2> DeclsInGroup;
5907 DeclsInGroup.push_back(Elt: TLSD);
5908
5909 // Currently happens for things like -fms-extensions and use `__if_exists`.
5910 for (Stmt *S : Stmts) {
5911 // Here we should be safe as `__if_exists` and friends are not introducing
5912 // new variables which need to live outside file scope.
5913 TopLevelStmtDecl *D = Actions.ActOnStartTopLevelStmtDecl(S: getCurScope());
5914 Actions.ActOnFinishTopLevelStmtDecl(D, Statement: S);
5915 DeclsInGroup.push_back(Elt: D);
5916 }
5917
5918 return Actions.BuildDeclaratorGroup(Group: DeclsInGroup);
5919}
5920
5921bool Parser::isDeclarationSpecifier(
5922 ImplicitTypenameContext AllowImplicitTypename,
5923 bool DisambiguatingWithExpression) {
5924 switch (Tok.getKind()) {
5925 default: return false;
5926
5927 // OpenCL 2.0 and later define this keyword.
5928 case tok::kw_pipe:
5929 return getLangOpts().OpenCL &&
5930 getLangOpts().getOpenCLCompatibleVersion() >= 200;
5931
5932 case tok::identifier: // foo::bar
5933 // Unfortunate hack to support "Class.factoryMethod" notation.
5934 if (getLangOpts().ObjC && NextToken().is(K: tok::period))
5935 return false;
5936 if (TryAltiVecVectorToken())
5937 return true;
5938 [[fallthrough]];
5939 case tok::kw_decltype: // decltype(T())::type
5940 case tok::kw_typename: // typename T::type
5941 // Annotate typenames and C++ scope specifiers. If we get one, just
5942 // recurse to handle whatever we get.
5943 if (TryAnnotateTypeOrScopeToken(AllowImplicitTypename))
5944 return true;
5945 if (TryAnnotateTypeConstraint())
5946 return true;
5947 if (Tok.is(K: tok::identifier))
5948 return false;
5949
5950 // If we're in Objective-C and we have an Objective-C class type followed
5951 // by an identifier and then either ':' or ']', in a place where an
5952 // expression is permitted, then this is probably a class message send
5953 // missing the initial '['. In this case, we won't consider this to be
5954 // the start of a declaration.
5955 if (DisambiguatingWithExpression &&
5956 isStartOfObjCClassMessageMissingOpenBracket())
5957 return false;
5958
5959 return isDeclarationSpecifier(AllowImplicitTypename);
5960
5961 case tok::coloncolon: // ::foo::bar
5962 if (!getLangOpts().CPlusPlus)
5963 return false;
5964 if (NextToken().is(K: tok::kw_new) || // ::new
5965 NextToken().is(K: tok::kw_delete)) // ::delete
5966 return false;
5967
5968 // Annotate typenames and C++ scope specifiers. If we get one, just
5969 // recurse to handle whatever we get.
5970 if (TryAnnotateTypeOrScopeToken())
5971 return true;
5972 return isDeclarationSpecifier(AllowImplicitTypename: ImplicitTypenameContext::No);
5973
5974 // storage-class-specifier
5975 case tok::kw_typedef:
5976 case tok::kw_extern:
5977 case tok::kw___private_extern__:
5978 case tok::kw_static:
5979 case tok::kw_auto:
5980 case tok::kw___auto_type:
5981 case tok::kw_register:
5982 case tok::kw___thread:
5983 case tok::kw_thread_local:
5984 case tok::kw__Thread_local:
5985
5986 // Modules
5987 case tok::kw___module_private__:
5988
5989 // Debugger support
5990 case tok::kw___unknown_anytype:
5991
5992 // type-specifiers
5993 case tok::kw_short:
5994 case tok::kw_long:
5995 case tok::kw___int64:
5996 case tok::kw___int128:
5997 case tok::kw_signed:
5998 case tok::kw_unsigned:
5999 case tok::kw__Complex:
6000 case tok::kw__Imaginary:
6001 case tok::kw_void:
6002 case tok::kw_char:
6003 case tok::kw_wchar_t:
6004 case tok::kw_char8_t:
6005 case tok::kw_char16_t:
6006 case tok::kw_char32_t:
6007
6008 case tok::kw_int:
6009 case tok::kw__ExtInt:
6010 case tok::kw__BitInt:
6011 case tok::kw_half:
6012 case tok::kw___bf16:
6013 case tok::kw_float:
6014 case tok::kw_double:
6015 case tok::kw__Accum:
6016 case tok::kw__Fract:
6017 case tok::kw__Float16:
6018 case tok::kw___float128:
6019 case tok::kw___ibm128:
6020 case tok::kw_bool:
6021 case tok::kw__Bool:
6022 case tok::kw__Decimal32:
6023 case tok::kw__Decimal64:
6024 case tok::kw__Decimal128:
6025 case tok::kw___vector:
6026
6027 // struct-or-union-specifier (C99) or class-specifier (C++)
6028 case tok::kw_class:
6029 case tok::kw_struct:
6030 case tok::kw_union:
6031 case tok::kw___interface:
6032 // enum-specifier
6033 case tok::kw_enum:
6034
6035 // type-qualifier
6036 case tok::kw_const:
6037 case tok::kw_volatile:
6038 case tok::kw_restrict:
6039 case tok::kw___ob_wrap:
6040 case tok::kw___ob_trap:
6041 case tok::kw__Sat:
6042
6043 // function-specifier
6044 case tok::kw_inline:
6045 case tok::kw_virtual:
6046 case tok::kw_explicit:
6047 case tok::kw__Noreturn:
6048
6049 // alignment-specifier
6050 case tok::kw__Alignas:
6051
6052 // friend keyword.
6053 case tok::kw_friend:
6054
6055 // static_assert-declaration
6056 case tok::kw_static_assert:
6057 case tok::kw__Static_assert:
6058
6059 // C23/GNU typeof support.
6060 case tok::kw_typeof:
6061 case tok::kw_typeof_unqual:
6062
6063 // GNU attributes.
6064 case tok::kw___attribute:
6065
6066 // C++11 decltype and constexpr.
6067 case tok::annot_decltype:
6068 case tok::annot_pack_indexing_type:
6069 case tok::kw_constexpr:
6070
6071 // C++20 consteval and constinit.
6072 case tok::kw_consteval:
6073 case tok::kw_constinit:
6074
6075 // C11 _Atomic
6076 case tok::kw__Atomic:
6077 return true;
6078
6079 case tok::kw_alignas:
6080 // alignas is a type-specifier-qualifier in C23, which is a kind of
6081 // declaration-specifier. Outside of C23 mode (including in C++), it is not.
6082 return getLangOpts().C23;
6083
6084 // GNU ObjC bizarre protocol extension: <proto1,proto2> with implicit 'id'.
6085 case tok::less:
6086 return getLangOpts().ObjC;
6087
6088 // typedef-name
6089 case tok::annot_typename:
6090 return !DisambiguatingWithExpression ||
6091 !isStartOfObjCClassMessageMissingOpenBracket();
6092
6093 // placeholder-type-specifier
6094 case tok::annot_template_id: {
6095 TemplateIdAnnotation *TemplateId = takeTemplateIdAnnotation(tok: Tok);
6096 if (TemplateId->hasInvalidName())
6097 return true;
6098 // FIXME: What about type templates that have only been annotated as
6099 // annot_template_id, not as annot_typename?
6100 return isTypeConstraintAnnotation() &&
6101 (NextToken().is(K: tok::kw_auto) || NextToken().is(K: tok::kw_decltype));
6102 }
6103
6104 case tok::annot_cxxscope: {
6105 TemplateIdAnnotation *TemplateId =
6106 NextToken().is(K: tok::annot_template_id)
6107 ? takeTemplateIdAnnotation(tok: NextToken())
6108 : nullptr;
6109 if (TemplateId && TemplateId->hasInvalidName())
6110 return true;
6111 // FIXME: What about type templates that have only been annotated as
6112 // annot_template_id, not as annot_typename?
6113 if (NextToken().is(K: tok::identifier) && TryAnnotateTypeConstraint())
6114 return true;
6115 return isTypeConstraintAnnotation() &&
6116 GetLookAheadToken(N: 2).isOneOf(Ks: tok::kw_auto, Ks: tok::kw_decltype);
6117 }
6118
6119 case tok::kw___declspec:
6120 case tok::kw___cdecl:
6121 case tok::kw___stdcall:
6122 case tok::kw___fastcall:
6123 case tok::kw___thiscall:
6124 case tok::kw___regcall:
6125 case tok::kw___vectorcall:
6126 case tok::kw___w64:
6127 case tok::kw___sptr:
6128 case tok::kw___uptr:
6129 case tok::kw___ptr64:
6130 case tok::kw___ptr32:
6131 case tok::kw___forceinline:
6132 case tok::kw___pascal:
6133 case tok::kw___unaligned:
6134 case tok::kw___ptrauth:
6135
6136 case tok::kw__Nonnull:
6137 case tok::kw__Nullable:
6138 case tok::kw__Nullable_result:
6139 case tok::kw__Null_unspecified:
6140
6141 case tok::kw___kindof:
6142
6143 case tok::kw___private:
6144 case tok::kw___local:
6145 case tok::kw___global:
6146 case tok::kw___constant:
6147 case tok::kw___generic:
6148 case tok::kw___read_only:
6149 case tok::kw___read_write:
6150 case tok::kw___write_only:
6151#define GENERIC_IMAGE_TYPE(ImgType, Id) case tok::kw_##ImgType##_t:
6152#include "clang/Basic/OpenCLImageTypes.def"
6153#define HLSL_INTANGIBLE_TYPE(Name, Id, SingletonId) case tok::kw_##Name:
6154#include "clang/Basic/HLSLIntangibleTypes.def"
6155#define HLSL_PACKED_TYPE(Name, Id, SingletonId) case tok::kw_##Name:
6156#include "clang/Basic/HLSLPackedTypes.def"
6157
6158 case tok::kw___funcref:
6159 case tok::kw_groupshared:
6160 return true;
6161
6162 case tok::kw_nointerpolation:
6163 case tok::kw_linear:
6164 case tok::kw_centroid:
6165 case tok::kw_noperspective:
6166 case tok::kw_sample:
6167 case tok::kw_center:
6168 case tok::kw_row_major:
6169 case tok::kw_column_major:
6170 return getLangOpts().HLSL;
6171
6172 case tok::kw_private:
6173 return getLangOpts().OpenCL;
6174 }
6175}
6176
6177bool Parser::isConstructorDeclarator(bool IsUnqualified, bool DeductionGuide,
6178 DeclSpec::FriendSpecified IsFriend,
6179 const ParsedTemplateInfo *TemplateInfo) {
6180 RevertingTentativeParsingAction TPA(*this);
6181 // Parse the C++ scope specifier.
6182 CXXScopeSpec SS;
6183 if (TemplateInfo && TemplateInfo->TemplateParams)
6184 SS.setTemplateParamLists(*TemplateInfo->TemplateParams);
6185
6186 if (ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/nullptr,
6187 /*ObjectHasErrors=*/false,
6188 /*EnteringContext=*/true)) {
6189 return false;
6190 }
6191
6192 // Parse the constructor name.
6193 if (Tok.is(K: tok::identifier)) {
6194 // We already know that we have a constructor name; just consume
6195 // the token.
6196 ConsumeToken();
6197 } else if (Tok.is(K: tok::annot_template_id)) {
6198 ConsumeAnnotationToken();
6199 } else {
6200 return false;
6201 }
6202
6203 // There may be attributes here, appertaining to the constructor name or type
6204 // we just stepped past.
6205 SkipCXX11Attributes();
6206
6207 // Current class name must be followed by a left parenthesis.
6208 if (Tok.isNot(K: tok::l_paren)) {
6209 return false;
6210 }
6211 ConsumeParen();
6212
6213 // A right parenthesis, or ellipsis followed by a right parenthesis signals
6214 // that we have a constructor.
6215 if (Tok.is(K: tok::r_paren) ||
6216 (Tok.is(K: tok::ellipsis) && NextToken().is(K: tok::r_paren))) {
6217 return true;
6218 }
6219
6220 // A C++11 attribute here signals that we have a constructor, and is an
6221 // attribute on the first constructor parameter.
6222 if (isCXX11AttributeSpecifier(/*Disambiguate=*/false,
6223 /*OuterMightBeMessageSend=*/true) !=
6224 CXX11AttributeKind::NotAttributeSpecifier) {
6225 return true;
6226 }
6227
6228 // If we need to, enter the specified scope.
6229 DeclaratorScopeObj DeclScopeObj(*this, SS);
6230 if (SS.isSet() && Actions.ShouldEnterDeclaratorScope(S: getCurScope(), SS))
6231 DeclScopeObj.EnterDeclaratorScope();
6232
6233 // Optionally skip Microsoft attributes.
6234 ParsedAttributes Attrs(AttrFactory);
6235 MaybeParseMicrosoftAttributes(Attrs);
6236
6237 // Check whether the next token(s) are part of a declaration
6238 // specifier, in which case we have the start of a parameter and,
6239 // therefore, we know that this is a constructor.
6240 // Due to an ambiguity with implicit typename, the above is not enough.
6241 // Additionally, check to see if we are a friend.
6242 // If we parsed a scope specifier as well as friend,
6243 // we might be parsing a friend constructor.
6244 bool IsConstructor = false;
6245 ImplicitTypenameContext ITC = IsFriend && !SS.isSet()
6246 ? ImplicitTypenameContext::No
6247 : ImplicitTypenameContext::Yes;
6248 // Constructors cannot have this parameters, but we support that scenario here
6249 // to improve diagnostic.
6250 if (Tok.is(K: tok::kw_this)) {
6251 ConsumeToken();
6252 return isDeclarationSpecifier(AllowImplicitTypename: ITC);
6253 }
6254
6255 if (isDeclarationSpecifier(AllowImplicitTypename: ITC))
6256 IsConstructor = true;
6257 else if (Tok.is(K: tok::identifier) ||
6258 (Tok.is(K: tok::annot_cxxscope) && NextToken().is(K: tok::identifier))) {
6259 // We've seen "C ( X" or "C ( X::Y", but "X" / "X::Y" is not a type.
6260 // This might be a parenthesized member name, but is more likely to
6261 // be a constructor declaration with an invalid argument type. Keep
6262 // looking.
6263 if (Tok.is(K: tok::annot_cxxscope))
6264 ConsumeAnnotationToken();
6265 ConsumeToken();
6266
6267 // If this is not a constructor, we must be parsing a declarator,
6268 // which must have one of the following syntactic forms (see the
6269 // grammar extract at the start of ParseDirectDeclarator):
6270 switch (Tok.getKind()) {
6271 case tok::l_paren:
6272 // C(X ( int));
6273 case tok::l_square:
6274 // C(X [ 5]);
6275 // C(X [ [attribute]]);
6276 case tok::coloncolon:
6277 // C(X :: Y);
6278 // C(X :: *p);
6279 // Assume this isn't a constructor, rather than assuming it's a
6280 // constructor with an unnamed parameter of an ill-formed type.
6281 break;
6282
6283 case tok::r_paren:
6284 // C(X )
6285
6286 // Skip past the right-paren and any following attributes to get to
6287 // the function body or trailing-return-type.
6288 ConsumeParen();
6289 SkipCXX11Attributes();
6290
6291 if (DeductionGuide) {
6292 // C(X) -> ... is a deduction guide.
6293 IsConstructor = Tok.is(K: tok::arrow);
6294 break;
6295 }
6296 if (Tok.is(K: tok::colon) || Tok.is(K: tok::kw_try)) {
6297 // Assume these were meant to be constructors:
6298 // C(X) : (the name of a bit-field cannot be parenthesized).
6299 // C(X) try (this is otherwise ill-formed).
6300 IsConstructor = true;
6301 }
6302 if (Tok.is(K: tok::semi) || Tok.is(K: tok::l_brace)) {
6303 // If we have a constructor name within the class definition,
6304 // assume these were meant to be constructors:
6305 // C(X) {
6306 // C(X) ;
6307 // ... because otherwise we would be declaring a non-static data
6308 // member that is ill-formed because it's of the same type as its
6309 // surrounding class.
6310 //
6311 // FIXME: We can actually do this whether or not the name is qualified,
6312 // because if it is qualified in this context it must be being used as
6313 // a constructor name.
6314 // currently, so we're somewhat conservative here.
6315 IsConstructor = IsUnqualified;
6316 }
6317 break;
6318
6319 default:
6320 IsConstructor = true;
6321 break;
6322 }
6323 }
6324 return IsConstructor;
6325}
6326
6327void Parser::ParseTypeQualifierListOpt(
6328 DeclSpec &DS, unsigned AttrReqs, bool AtomicOrPtrauthAllowed,
6329 bool IdentifierRequired, llvm::function_ref<void()> CodeCompletionHandler) {
6330 if ((AttrReqs & AR_CXX11AttributesParsed) &&
6331 isAllowedCXX11AttributeSpecifier()) {
6332 ParsedAttributes Attrs(AttrFactory);
6333 ParseCXX11Attributes(attrs&: Attrs);
6334 DS.takeAttributesAppendingingFrom(attrs&: Attrs);
6335 }
6336
6337 SourceLocation EndLoc;
6338
6339 while (true) {
6340 bool isInvalid = false;
6341 const char *PrevSpec = nullptr;
6342 unsigned DiagID = 0;
6343 SourceLocation Loc = Tok.getLocation();
6344
6345 switch (Tok.getKind()) {
6346 case tok::code_completion:
6347 cutOffParsing();
6348 if (CodeCompletionHandler)
6349 CodeCompletionHandler();
6350 else
6351 Actions.CodeCompletion().CodeCompleteTypeQualifiers(DS);
6352 return;
6353
6354 case tok::kw_const:
6355 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_const , Loc, PrevSpec, DiagID,
6356 Lang: getLangOpts());
6357 break;
6358 case tok::kw_volatile:
6359 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_volatile, Loc, PrevSpec, DiagID,
6360 Lang: getLangOpts());
6361 break;
6362 case tok::kw_restrict:
6363 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_restrict, Loc, PrevSpec, DiagID,
6364 Lang: getLangOpts());
6365 break;
6366 case tok::kw___ob_wrap:
6367 if (!getLangOpts().OverflowBehaviorTypes) {
6368 Diag(Loc, DiagID: diag::warn_overflow_behavior_keyword_disabled)
6369 << tok::getKeywordSpelling(Kind: Tok.getKind());
6370 break;
6371 }
6372 isInvalid = DS.SetOverflowBehavior(
6373 Kind: OverflowBehaviorType::OverflowBehaviorKind::Wrap, Loc, PrevSpec,
6374 DiagID);
6375 break;
6376 case tok::kw___ob_trap:
6377 if (!getLangOpts().OverflowBehaviorTypes) {
6378 Diag(Loc, DiagID: diag::warn_overflow_behavior_keyword_disabled)
6379 << tok::getKeywordSpelling(Kind: Tok.getKind());
6380 break;
6381 }
6382 isInvalid = DS.SetOverflowBehavior(
6383 Kind: OverflowBehaviorType::OverflowBehaviorKind::Trap, Loc, PrevSpec,
6384 DiagID);
6385 break;
6386 case tok::kw__Atomic:
6387 if (!AtomicOrPtrauthAllowed)
6388 goto DoneWithTypeQuals;
6389 diagnoseUseOfC11Keyword(Tok);
6390 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_atomic, Loc, PrevSpec, DiagID,
6391 Lang: getLangOpts());
6392 break;
6393
6394 // OpenCL qualifiers:
6395 case tok::kw_private:
6396 if (!getLangOpts().OpenCL)
6397 goto DoneWithTypeQuals;
6398 [[fallthrough]];
6399 case tok::kw___private:
6400 case tok::kw___global:
6401 case tok::kw___local:
6402 case tok::kw___constant:
6403 case tok::kw___generic:
6404 case tok::kw___read_only:
6405 case tok::kw___write_only:
6406 case tok::kw___read_write:
6407 ParseOpenCLQualifiers(Attrs&: DS.getAttributes());
6408 break;
6409
6410 case tok::kw_groupshared:
6411 case tok::kw_in:
6412 case tok::kw_inout:
6413 case tok::kw_out:
6414 case tok::kw_nointerpolation:
6415 case tok::kw_linear:
6416 case tok::kw_centroid:
6417 case tok::kw_noperspective:
6418 case tok::kw_sample:
6419 case tok::kw_center:
6420 // NOTE: ParseHLSLQualifiers will consume the qualifier token.
6421 ParseHLSLQualifiers(Attrs&: DS.getAttributes());
6422 continue;
6423
6424 // __ptrauth qualifier.
6425 case tok::kw___ptrauth:
6426 if (!AtomicOrPtrauthAllowed)
6427 goto DoneWithTypeQuals;
6428 ParsePtrauthQualifier(Attrs&: DS.getAttributes());
6429 EndLoc = PrevTokLocation;
6430 continue;
6431
6432 case tok::kw___unaligned:
6433 isInvalid = DS.SetTypeQual(T: DeclSpec::TQ_unaligned, Loc, PrevSpec, DiagID,
6434 Lang: getLangOpts());
6435 break;
6436 case tok::kw___uptr:
6437 // GNU libc headers in C mode use '__uptr' as an identifier which conflicts
6438 // with the MS modifier keyword.
6439 if ((AttrReqs & AR_DeclspecAttributesParsed) && !getLangOpts().CPlusPlus &&
6440 IdentifierRequired && DS.isEmpty() && NextToken().is(K: tok::semi)) {
6441 if (TryKeywordIdentFallback(DisableKeyword: false))
6442 continue;
6443 }
6444 [[fallthrough]];
6445 case tok::kw___sptr:
6446 case tok::kw___w64:
6447 case tok::kw___ptr64:
6448 case tok::kw___ptr32:
6449 case tok::kw___cdecl:
6450 case tok::kw___stdcall:
6451 case tok::kw___fastcall:
6452 case tok::kw___thiscall:
6453 case tok::kw___regcall:
6454 case tok::kw___vectorcall:
6455 if (AttrReqs & AR_DeclspecAttributesParsed) {
6456 ParseMicrosoftTypeAttributes(attrs&: DS.getAttributes());
6457 continue;
6458 }
6459 goto DoneWithTypeQuals;
6460
6461 case tok::kw___funcref:
6462 ParseWebAssemblyFuncrefTypeAttribute(attrs&: DS.getAttributes());
6463 continue;
6464
6465 case tok::kw___pascal:
6466 if (AttrReqs & AR_VendorAttributesParsed) {
6467 ParseBorlandTypeAttributes(attrs&: DS.getAttributes());
6468 continue;
6469 }
6470 goto DoneWithTypeQuals;
6471
6472 // Nullability type specifiers.
6473 case tok::kw__Nonnull:
6474 case tok::kw__Nullable:
6475 case tok::kw__Nullable_result:
6476 case tok::kw__Null_unspecified:
6477 ParseNullabilityTypeSpecifiers(attrs&: DS.getAttributes());
6478 continue;
6479
6480 // Objective-C 'kindof' types.
6481 case tok::kw___kindof:
6482 DS.getAttributes().addNew(attrName: Tok.getIdentifierInfo(), attrRange: Loc,
6483 scope: AttributeScopeInfo(), args: nullptr, numArgs: 0,
6484 form: tok::kw___kindof);
6485 (void)ConsumeToken();
6486 continue;
6487
6488 case tok::kw___attribute:
6489 if (AttrReqs & AR_GNUAttributesParsedAndRejected)
6490 // When GNU attributes are expressly forbidden, diagnose their usage.
6491 Diag(Tok, DiagID: diag::err_attributes_not_allowed);
6492
6493 // Parse the attributes even if they are rejected to ensure that error
6494 // recovery is graceful.
6495 if (AttrReqs & AR_GNUAttributesParsed ||
6496 AttrReqs & AR_GNUAttributesParsedAndRejected) {
6497 ParseGNUAttributes(Attrs&: DS.getAttributes());
6498 continue; // do *not* consume the next token!
6499 }
6500 // otherwise, FALL THROUGH!
6501 [[fallthrough]];
6502 default:
6503 DoneWithTypeQuals:
6504 // If this is not a type-qualifier token, we're done reading type
6505 // qualifiers. First verify that DeclSpec's are consistent.
6506 DS.Finish(S&: Actions, Policy: Actions.getASTContext().getPrintingPolicy());
6507 if (EndLoc.isValid())
6508 DS.SetRangeEnd(EndLoc);
6509 return;
6510 }
6511
6512 // If the specifier combination wasn't legal, issue a diagnostic.
6513 if (isInvalid) {
6514 assert(PrevSpec && "Method did not return previous specifier!");
6515 Diag(Tok, DiagID) << PrevSpec;
6516 }
6517 EndLoc = ConsumeToken();
6518 }
6519}
6520
6521void Parser::ParseDeclarator(Declarator &D) {
6522 /// This implements the 'declarator' production in the C grammar, then checks
6523 /// for well-formedness and issues diagnostics.
6524 Actions.runWithSufficientStackSpace(Loc: D.getBeginLoc(), Fn: [&] {
6525 ParseDeclaratorInternal(D, DirectDeclParser: &Parser::ParseDirectDeclarator);
6526 });
6527}
6528
6529static bool isPtrOperatorToken(tok::TokenKind Kind, const LangOptions &Lang,
6530 DeclaratorContext TheContext) {
6531 if (Kind == tok::star || Kind == tok::caret)
6532 return true;
6533
6534 // OpenCL 2.0 and later define this keyword.
6535 if (Kind == tok::kw_pipe && Lang.OpenCL &&
6536 Lang.getOpenCLCompatibleVersion() >= 200)
6537 return true;
6538
6539 if (!Lang.CPlusPlus)
6540 return false;
6541
6542 if (Kind == tok::amp)
6543 return true;
6544
6545 // We parse rvalue refs in C++03, because otherwise the errors are scary.
6546 // But we must not parse them in conversion-type-ids and new-type-ids, since
6547 // those can be legitimately followed by a && operator.
6548 // (The same thing can in theory happen after a trailing-return-type, but
6549 // since those are a C++11 feature, there is no rejects-valid issue there.)
6550 if (Kind == tok::ampamp)
6551 return Lang.CPlusPlus11 || (TheContext != DeclaratorContext::ConversionId &&
6552 TheContext != DeclaratorContext::CXXNew);
6553
6554 return false;
6555}
6556
6557// Indicates whether the given declarator is a pipe declarator.
6558static bool isPipeDeclarator(const Declarator &D) {
6559 const unsigned NumTypes = D.getNumTypeObjects();
6560
6561 for (unsigned Idx = 0; Idx != NumTypes; ++Idx)
6562 if (DeclaratorChunk::Pipe == D.getTypeObject(i: Idx).Kind)
6563 return true;
6564
6565 return false;
6566}
6567
6568void Parser::ParseDeclaratorInternal(Declarator &D,
6569 DirectDeclParseFunction DirectDeclParser) {
6570 if (Diags.hasAllExtensionsSilenced())
6571 D.setExtension();
6572
6573 // C++ member pointers start with a '::' or a nested-name.
6574 // Member pointers get special handling, since there's no place for the
6575 // scope spec in the generic path below.
6576 // A 'decltype' can only begin a nested-name-specifier if it is followed by
6577 // '('; otherwise it is not a decltype-specifier at all and must not be
6578 // parsed as one.
6579 if (getLangOpts().CPlusPlus &&
6580 (Tok.is(K: tok::coloncolon) ||
6581 (Tok.is(K: tok::kw_decltype) && NextToken().is(K: tok::l_paren)) ||
6582 (Tok.is(K: tok::identifier) &&
6583 (NextToken().is(K: tok::coloncolon) || NextToken().is(K: tok::less))) ||
6584 Tok.is(K: tok::annot_cxxscope))) {
6585 TentativeParsingAction TPA(*this, /*Unannotated=*/true);
6586 bool EnteringContext = D.getContext() == DeclaratorContext::File ||
6587 D.getContext() == DeclaratorContext::Member;
6588 CXXScopeSpec SS;
6589 SS.setTemplateParamLists(D.getTemplateParameterLists());
6590
6591 if (ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/nullptr,
6592 /*ObjectHasErrors=*/false,
6593 /*EnteringContext=*/false,
6594 /*MayBePseudoDestructor=*/nullptr,
6595 /*IsTypename=*/false, /*LastII=*/nullptr,
6596 /*OnlyNamespace=*/false,
6597 /*InUsingDeclaration=*/false,
6598 /*Disambiguation=*/EnteringContext,
6599 /*IsAddressOfOperand=*/false,
6600 /*IsInDeclarationContext=*/true) ||
6601
6602 SS.isEmpty() || SS.isInvalid() || !EnteringContext ||
6603 Tok.is(K: tok::star)) {
6604 TPA.Commit();
6605 if (SS.isNotEmpty() && Tok.is(K: tok::star)) {
6606 if (SS.isValid()) {
6607 checkCompoundToken(FirstTokLoc: SS.getEndLoc(), FirstTokKind: tok::coloncolon,
6608 Op: CompoundToken::MemberPtr);
6609 }
6610
6611 SourceLocation StarLoc = ConsumeToken();
6612 D.SetRangeEnd(StarLoc);
6613 DeclSpec DS(AttrFactory);
6614 ParseTypeQualifierListOpt(DS);
6615 D.ExtendWithDeclSpec(DS);
6616
6617 // Recurse to parse whatever is left.
6618 Actions.runWithSufficientStackSpace(Loc: D.getBeginLoc(), Fn: [&] {
6619 ParseDeclaratorInternal(D, DirectDeclParser);
6620 });
6621
6622 // Sema will have to catch (syntactically invalid) pointers into global
6623 // scope. It has to catch pointers into namespace scope anyway.
6624 D.AddTypeInfo(TI: DeclaratorChunk::getMemberPointer(
6625 SS, TypeQuals: DS.getTypeQualifiers(), StarLoc, EndLoc: DS.getEndLoc()),
6626 attrs: std::move(DS.getAttributes()),
6627 /*EndLoc=*/SourceLocation());
6628 return;
6629 }
6630 } else {
6631 TPA.Revert();
6632 SS.clear();
6633 ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/nullptr,
6634 /*ObjectHasErrors=*/false,
6635 /*EnteringContext=*/true);
6636 }
6637
6638 if (SS.isNotEmpty()) {
6639 // The scope spec really belongs to the direct-declarator.
6640 if (D.mayHaveIdentifier())
6641 D.getCXXScopeSpec() = std::move(SS);
6642 else
6643 AnnotateScopeToken(SS, IsNewAnnotation: true);
6644
6645 if (DirectDeclParser)
6646 (this->*DirectDeclParser)(D);
6647 return;
6648 }
6649 }
6650
6651 tok::TokenKind Kind = Tok.getKind();
6652
6653 if (D.getDeclSpec().isTypeSpecPipe() && !isPipeDeclarator(D)) {
6654 DeclSpec DS(AttrFactory);
6655 ParseTypeQualifierListOpt(DS);
6656
6657 D.AddTypeInfo(
6658 TI: DeclaratorChunk::getPipe(TypeQuals: DS.getTypeQualifiers(), Loc: DS.getPipeLoc()),
6659 attrs: std::move(DS.getAttributes()), EndLoc: SourceLocation());
6660 }
6661
6662 // Not a pointer, C++ reference, or block.
6663 if (!isPtrOperatorToken(Kind, Lang: getLangOpts(), TheContext: D.getContext())) {
6664 if (DirectDeclParser)
6665 (this->*DirectDeclParser)(D);
6666 return;
6667 }
6668
6669 // Otherwise, '*' -> pointer, '^' -> block, '&' -> lvalue reference,
6670 // '&&' -> rvalue reference
6671 SourceLocation Loc = ConsumeToken(); // Eat the *, ^, & or &&.
6672 D.SetRangeEnd(Loc);
6673
6674 if (Kind == tok::star || Kind == tok::caret) {
6675 // Is a pointer.
6676 DeclSpec DS(AttrFactory);
6677
6678 // GNU attributes are not allowed here in a new-type-id, but Declspec and
6679 // C++11 attributes are allowed.
6680 unsigned Reqs = AR_CXX11AttributesParsed | AR_DeclspecAttributesParsed |
6681 ((D.getContext() != DeclaratorContext::CXXNew)
6682 ? AR_GNUAttributesParsed
6683 : AR_GNUAttributesParsedAndRejected);
6684 ParseTypeQualifierListOpt(DS, AttrReqs: Reqs, /*AtomicOrPtrauthAllowed=*/true,
6685 IdentifierRequired: !D.mayOmitIdentifier());
6686 D.ExtendWithDeclSpec(DS);
6687
6688 // Recursively parse the declarator.
6689 Actions.runWithSufficientStackSpace(
6690 Loc: D.getBeginLoc(), Fn: [&] { ParseDeclaratorInternal(D, DirectDeclParser); });
6691 if (Kind == tok::star)
6692 // Remember that we parsed a pointer type, and remember the type-quals.
6693 D.AddTypeInfo(TI: DeclaratorChunk::getPointer(
6694 TypeQuals: DS.getTypeQualifiers(), Loc, ConstQualLoc: DS.getConstSpecLoc(),
6695 VolatileQualLoc: DS.getVolatileSpecLoc(), RestrictQualLoc: DS.getRestrictSpecLoc(),
6696 AtomicQualLoc: DS.getAtomicSpecLoc(), UnalignedQualLoc: DS.getUnalignedSpecLoc(),
6697 OverflowBehaviorLoc: DS.getOverflowBehaviorLoc(), OverflowBehaviorIsWrap: DS.isWrapSpecified()),
6698 attrs: std::move(DS.getAttributes()), EndLoc: SourceLocation());
6699 else
6700 // Remember that we parsed a Block type, and remember the type-quals.
6701 D.AddTypeInfo(
6702 TI: DeclaratorChunk::getBlockPointer(TypeQuals: DS.getTypeQualifiers(), Loc),
6703 attrs: std::move(DS.getAttributes()), EndLoc: SourceLocation());
6704 } else {
6705 // Is a reference
6706 DeclSpec DS(AttrFactory);
6707
6708 // Complain about rvalue references in C++03, but then go on and build
6709 // the declarator.
6710 if (Kind == tok::ampamp)
6711 DiagCompat(Loc, CompatDiagId: diag_compat::rvalue_reference);
6712
6713 // GNU-style and C++11 attributes are allowed here, as is restrict.
6714 ParseTypeQualifierListOpt(DS);
6715 D.ExtendWithDeclSpec(DS);
6716
6717 // C++ 8.3.2p1: cv-qualified references are ill-formed except when the
6718 // cv-qualifiers are introduced through the use of a typedef or of a
6719 // template type argument, in which case the cv-qualifiers are ignored.
6720 if (DS.getTypeQualifiers() != DeclSpec::TQ_unspecified) {
6721 if (DS.getTypeQualifiers() & DeclSpec::TQ_const)
6722 Diag(Loc: DS.getConstSpecLoc(),
6723 DiagID: diag::err_invalid_reference_qualifier_application) << "const";
6724 if (DS.getTypeQualifiers() & DeclSpec::TQ_volatile)
6725 Diag(Loc: DS.getVolatileSpecLoc(),
6726 DiagID: diag::err_invalid_reference_qualifier_application) << "volatile";
6727 // 'restrict' is permitted as an extension.
6728 if (DS.getTypeQualifiers() & DeclSpec::TQ_atomic)
6729 Diag(Loc: DS.getAtomicSpecLoc(),
6730 DiagID: diag::err_invalid_reference_qualifier_application) << "_Atomic";
6731 }
6732
6733 // Recursively parse the declarator.
6734 Actions.runWithSufficientStackSpace(
6735 Loc: D.getBeginLoc(), Fn: [&] { ParseDeclaratorInternal(D, DirectDeclParser); });
6736
6737 if (D.getNumTypeObjects() > 0) {
6738 // C++ [dcl.ref]p4: There shall be no references to references.
6739 DeclaratorChunk& InnerChunk = D.getTypeObject(i: D.getNumTypeObjects() - 1);
6740 if (InnerChunk.Kind == DeclaratorChunk::Reference) {
6741 if (const IdentifierInfo *II = D.getIdentifier())
6742 Diag(Loc: InnerChunk.Loc, DiagID: diag::err_illegal_decl_reference_to_reference)
6743 << II;
6744 else
6745 Diag(Loc: InnerChunk.Loc, DiagID: diag::err_illegal_decl_reference_to_reference)
6746 << "type name";
6747
6748 // Once we've complained about the reference-to-reference, we
6749 // can go ahead and build the (technically ill-formed)
6750 // declarator: reference collapsing will take care of it.
6751 }
6752 }
6753
6754 // Remember that we parsed a reference type.
6755 D.AddTypeInfo(TI: DeclaratorChunk::getReference(TypeQuals: DS.getTypeQualifiers(), Loc,
6756 lvalue: Kind == tok::amp),
6757 attrs: std::move(DS.getAttributes()), EndLoc: SourceLocation());
6758 }
6759}
6760
6761// When correcting from misplaced brackets before the identifier, the location
6762// is saved inside the declarator so that other diagnostic messages can use
6763// them. This extracts and returns that location, or returns the provided
6764// location if a stored location does not exist.
6765static SourceLocation getMissingDeclaratorIdLoc(Declarator &D,
6766 SourceLocation Loc) {
6767 if (D.getName().StartLocation.isInvalid() &&
6768 D.getName().EndLocation.isValid())
6769 return D.getName().EndLocation;
6770
6771 return Loc;
6772}
6773
6774void Parser::ParseDirectDeclarator(Declarator &D) {
6775 DeclaratorScopeObj DeclScopeObj(*this, D.getCXXScopeSpec());
6776
6777 if (getLangOpts().CPlusPlus && D.mayHaveIdentifier()) {
6778 // This might be a C++17 structured binding.
6779 if (Tok.is(K: tok::l_square) && !D.mayOmitIdentifier() &&
6780 D.getCXXScopeSpec().isEmpty())
6781 return ParseDecompositionDeclarator(D);
6782
6783 // Don't parse FOO:BAR as if it were a typo for FOO::BAR inside a class, in
6784 // this context it is a bitfield. Also in range-based for statement colon
6785 // may delimit for-range-declaration.
6786 ColonProtectionRAIIObject X(
6787 *this, D.getContext() == DeclaratorContext::Member ||
6788 (D.getContext() == DeclaratorContext::ForInit &&
6789 getLangOpts().CPlusPlus11));
6790
6791 // ParseDeclaratorInternal might already have parsed the scope.
6792 if (D.getCXXScopeSpec().isEmpty()) {
6793 bool EnteringContext = D.getContext() == DeclaratorContext::File ||
6794 D.getContext() == DeclaratorContext::Member;
6795 ParseOptionalCXXScopeSpecifier(
6796 SS&: D.getCXXScopeSpec(), /*ObjectType=*/nullptr,
6797 /*ObjectHasErrors=*/false, EnteringContext);
6798 }
6799
6800 // C++23 [basic.scope.namespace]p1:
6801 // For each non-friend redeclaration or specialization whose target scope
6802 // is or is contained by the scope, the portion after the declarator-id,
6803 // class-head-name, or enum-head-name is also included in the scope.
6804 // C++23 [basic.scope.class]p1:
6805 // For each non-friend redeclaration or specialization whose target scope
6806 // is or is contained by the scope, the portion after the declarator-id,
6807 // class-head-name, or enum-head-name is also included in the scope.
6808 //
6809 // FIXME: We should not be doing this for friend declarations; they have
6810 // their own special lookup semantics specified by [basic.lookup.unqual]p6.
6811 if (D.getCXXScopeSpec().isValid()) {
6812 if (Actions.ShouldEnterDeclaratorScope(S: getCurScope(),
6813 SS: D.getCXXScopeSpec()))
6814 // Change the declaration context for name lookup, until this function
6815 // is exited (and the declarator has been parsed).
6816 DeclScopeObj.EnterDeclaratorScope();
6817 else if (getObjCDeclContext()) {
6818 // Ensure that we don't interpret the next token as an identifier when
6819 // dealing with declarations in an Objective-C container.
6820 D.SetIdentifier(Id: nullptr, IdLoc: Tok.getLocation());
6821 D.setInvalidType(true);
6822 ConsumeToken();
6823 goto PastIdentifier;
6824 }
6825 }
6826
6827 // C++0x [dcl.fct]p14:
6828 // There is a syntactic ambiguity when an ellipsis occurs at the end of a
6829 // parameter-declaration-clause without a preceding comma. In this case,
6830 // the ellipsis is parsed as part of the abstract-declarator if the type
6831 // of the parameter either names a template parameter pack that has not
6832 // been expanded or contains auto; otherwise, it is parsed as part of the
6833 // parameter-declaration-clause.
6834 if (Tok.is(K: tok::ellipsis) && D.getCXXScopeSpec().isEmpty() &&
6835 !((D.getContext() == DeclaratorContext::Prototype ||
6836 D.getContext() == DeclaratorContext::LambdaExprParameter ||
6837 D.getContext() == DeclaratorContext::BlockLiteral) &&
6838 NextToken().is(K: tok::r_paren) && !D.hasGroupingParens() &&
6839 !Actions.containsUnexpandedParameterPacks(D) &&
6840 D.getDeclSpec().getTypeSpecType() != TST_auto)) {
6841 SourceLocation EllipsisLoc = ConsumeToken();
6842 if (isPtrOperatorToken(Kind: Tok.getKind(), Lang: getLangOpts(), TheContext: D.getContext())) {
6843 // The ellipsis was put in the wrong place. Recover, and explain to
6844 // the user what they should have done.
6845 ParseDeclarator(D);
6846 if (EllipsisLoc.isValid())
6847 DiagnoseMisplacedEllipsisInDeclarator(EllipsisLoc, D);
6848 return;
6849 } else
6850 D.setEllipsisLoc(EllipsisLoc);
6851
6852 // The ellipsis can't be followed by a parenthesized declarator. We
6853 // check for that in ParseParenDeclarator, after we have disambiguated
6854 // the l_paren token.
6855 }
6856
6857 if (Tok.isOneOf(Ks: tok::identifier, Ks: tok::kw_operator, Ks: tok::annot_template_id,
6858 Ks: tok::tilde)) {
6859 // We found something that indicates the start of an unqualified-id.
6860 // Parse that unqualified-id.
6861 bool AllowConstructorName;
6862 bool AllowDeductionGuide;
6863 if (D.getDeclSpec().hasTypeSpecifier()) {
6864 AllowConstructorName = false;
6865 AllowDeductionGuide = false;
6866 } else if (D.getCXXScopeSpec().isSet()) {
6867 AllowConstructorName = (D.getContext() == DeclaratorContext::File ||
6868 D.getContext() == DeclaratorContext::Member);
6869 AllowDeductionGuide = false;
6870 } else {
6871 AllowConstructorName = (D.getContext() == DeclaratorContext::Member);
6872 AllowDeductionGuide = (D.getContext() == DeclaratorContext::File ||
6873 D.getContext() == DeclaratorContext::Member);
6874 }
6875
6876 bool HadScope = D.getCXXScopeSpec().isValid();
6877 SourceLocation TemplateKWLoc;
6878 if (ParseUnqualifiedId(SS&: D.getCXXScopeSpec(),
6879 /*ObjectType=*/nullptr,
6880 /*ObjectHadErrors=*/false,
6881 /*EnteringContext=*/true,
6882 /*AllowDestructorName=*/true, AllowConstructorName,
6883 AllowDeductionGuide, TemplateKWLoc: &TemplateKWLoc,
6884 Result&: D.getName()) ||
6885 // Once we're past the identifier, if the scope was bad, mark the
6886 // whole declarator bad.
6887 D.getCXXScopeSpec().isInvalid()) {
6888 D.SetIdentifier(Id: nullptr, IdLoc: Tok.getLocation());
6889 D.setInvalidType(true);
6890 } else {
6891 // ParseUnqualifiedId might have parsed a scope specifier during error
6892 // recovery. If it did so, enter that scope.
6893 if (!HadScope && D.getCXXScopeSpec().isValid() &&
6894 Actions.ShouldEnterDeclaratorScope(S: getCurScope(),
6895 SS: D.getCXXScopeSpec()))
6896 DeclScopeObj.EnterDeclaratorScope();
6897
6898 // Parsed the unqualified-id; update range information and move along.
6899 if (D.getSourceRange().getBegin().isInvalid())
6900 D.SetRangeBegin(D.getName().getSourceRange().getBegin());
6901 D.SetRangeEnd(D.getName().getSourceRange().getEnd());
6902 }
6903 goto PastIdentifier;
6904 }
6905
6906 if (D.getCXXScopeSpec().isNotEmpty()) {
6907 // We have a scope specifier but no following unqualified-id.
6908 Diag(Loc: PP.getLocForEndOfToken(Loc: D.getCXXScopeSpec().getEndLoc()),
6909 DiagID: diag::err_expected_unqualified_id)
6910 << /*C++*/1;
6911 D.SetIdentifier(Id: nullptr, IdLoc: Tok.getLocation());
6912 goto PastIdentifier;
6913 }
6914 } else if (Tok.is(K: tok::identifier) && D.mayHaveIdentifier()) {
6915 assert(!getLangOpts().CPlusPlus &&
6916 "There's a C++-specific check for tok::identifier above");
6917 assert(Tok.getIdentifierInfo() && "Not an identifier?");
6918 D.SetIdentifier(Id: Tok.getIdentifierInfo(), IdLoc: Tok.getLocation());
6919 D.SetRangeEnd(Tok.getLocation());
6920 ConsumeToken();
6921 goto PastIdentifier;
6922 } else if (Tok.is(K: tok::identifier) && !D.mayHaveIdentifier()) {
6923 // We're not allowed an identifier here, but we got one. Try to figure out
6924 // if the user was trying to attach a name to the type, or whether the name
6925 // is some unrelated trailing syntax.
6926 bool DiagnoseIdentifier = false;
6927 if (D.hasGroupingParens())
6928 // An identifier within parens is unlikely to be intended to be anything
6929 // other than a name being "declared".
6930 DiagnoseIdentifier = true;
6931 else if (D.getContext() == DeclaratorContext::TemplateArg)
6932 // T<int N> is an accidental identifier; T<int N indicates a missing '>'.
6933 DiagnoseIdentifier =
6934 NextToken().isOneOf(Ks: tok::comma, Ks: tok::greater, Ks: tok::greatergreater);
6935 else if (D.getContext() == DeclaratorContext::AliasDecl ||
6936 D.getContext() == DeclaratorContext::AliasTemplate)
6937 // The most likely error is that the ';' was forgotten.
6938 DiagnoseIdentifier = NextToken().isOneOf(Ks: tok::comma, Ks: tok::semi);
6939 else if ((D.getContext() == DeclaratorContext::TrailingReturn ||
6940 D.getContext() == DeclaratorContext::TrailingReturnVar) &&
6941 !isCXX11VirtSpecifier(Tok))
6942 DiagnoseIdentifier = NextToken().isOneOf(
6943 Ks: tok::comma, Ks: tok::semi, Ks: tok::equal, Ks: tok::l_brace, Ks: tok::kw_try);
6944 if (DiagnoseIdentifier) {
6945 Diag(Loc: Tok.getLocation(), DiagID: diag::err_unexpected_unqualified_id)
6946 << FixItHint::CreateRemoval(RemoveRange: Tok.getLocation());
6947 D.SetIdentifier(Id: nullptr, IdLoc: Tok.getLocation());
6948 ConsumeToken();
6949 goto PastIdentifier;
6950 }
6951 }
6952
6953 if (Tok.is(K: tok::l_paren)) {
6954 // If this might be an abstract-declarator followed by a direct-initializer,
6955 // check whether this is a valid declarator chunk. If it can't be, assume
6956 // that it's an initializer instead.
6957 if (D.mayOmitIdentifier() && D.mayBeFollowedByCXXDirectInit()) {
6958 RevertingTentativeParsingAction PA(*this);
6959 if (TryParseDeclarator(mayBeAbstract: true, mayHaveIdentifier: D.mayHaveIdentifier(), mayHaveDirectInit: true,
6960 mayHaveTrailingReturnType: D.getDeclSpec().getTypeSpecType() == TST_auto) ==
6961 TPResult::False) {
6962 D.SetIdentifier(Id: nullptr, IdLoc: Tok.getLocation());
6963 goto PastIdentifier;
6964 }
6965 }
6966
6967 // direct-declarator: '(' declarator ')'
6968 // direct-declarator: '(' attributes declarator ')'
6969 // Example: 'char (*X)' or 'int (*XX)(void)'
6970 ParseParenDeclarator(D);
6971
6972 // As noted above, a structured binding declarator cannot be followed by any
6973 // declarator chunks.
6974 if (D.isDecompositionDeclarator())
6975 return;
6976
6977 // If the declarator was parenthesized, we entered the declarator
6978 // scope when parsing the parenthesized declarator, then exited
6979 // the scope already. Re-enter the scope, if we need to.
6980 if (D.getCXXScopeSpec().isSet()) {
6981 // If there was an error parsing parenthesized declarator, declarator
6982 // scope may have been entered before. Don't do it again.
6983 if (!D.isInvalidType() &&
6984 Actions.ShouldEnterDeclaratorScope(S: getCurScope(),
6985 SS: D.getCXXScopeSpec()))
6986 // Change the declaration context for name lookup, until this function
6987 // is exited (and the declarator has been parsed).
6988 DeclScopeObj.EnterDeclaratorScope();
6989 }
6990 } else if (D.mayOmitIdentifier()) {
6991 // This could be something simple like "int" (in which case the declarator
6992 // portion is empty), if an abstract-declarator is allowed.
6993 D.SetIdentifier(Id: nullptr, IdLoc: Tok.getLocation());
6994
6995 // The grammar for abstract-pack-declarator does not allow grouping parens.
6996 // FIXME: Revisit this once core issue 1488 is resolved.
6997 if (D.hasEllipsis() && D.hasGroupingParens())
6998 Diag(Loc: PP.getLocForEndOfToken(Loc: D.getEllipsisLoc()),
6999 DiagID: diag::ext_abstract_pack_declarator_parens);
7000 } else {
7001 if (Tok.getKind() == tok::annot_pragma_parser_crash)
7002 LLVM_BUILTIN_TRAP;
7003 if (Tok.is(K: tok::l_square))
7004 return ParseMisplacedBracketDeclarator(D);
7005 if (D.getContext() == DeclaratorContext::Member) {
7006 // Objective-C++: Detect C++ keywords and try to prevent further errors by
7007 // treating these keyword as valid member names.
7008 if (getLangOpts().ObjC && getLangOpts().CPlusPlus &&
7009 !Tok.isAnnotation() && Tok.getIdentifierInfo() &&
7010 Tok.getIdentifierInfo()->isCPlusPlusKeyword(LangOpts: getLangOpts())) {
7011 Diag(Loc: getMissingDeclaratorIdLoc(D, Loc: Tok.getLocation()),
7012 DiagID: diag::err_expected_member_name_or_semi_objcxx_keyword)
7013 << Tok.getIdentifierInfo()
7014 << (D.getDeclSpec().isEmpty() ? SourceRange()
7015 : D.getDeclSpec().getSourceRange());
7016 D.SetIdentifier(Id: Tok.getIdentifierInfo(), IdLoc: Tok.getLocation());
7017 D.SetRangeEnd(Tok.getLocation());
7018 ConsumeToken();
7019 goto PastIdentifier;
7020 }
7021 Diag(Loc: getMissingDeclaratorIdLoc(D, Loc: Tok.getLocation()),
7022 DiagID: diag::err_expected_member_name_or_semi)
7023 << (D.getDeclSpec().isEmpty() ? SourceRange()
7024 : D.getDeclSpec().getSourceRange());
7025 } else {
7026 if (Tok.getKind() == tok::TokenKind::kw_while) {
7027 Diag(Tok, DiagID: diag::err_while_loop_outside_of_a_function);
7028 } else if (getLangOpts().CPlusPlus) {
7029 if (Tok.isOneOf(Ks: tok::period, Ks: tok::arrow))
7030 Diag(Tok, DiagID: diag::err_invalid_operator_on_type) << Tok.is(K: tok::arrow);
7031 else {
7032 SourceLocation Loc = D.getCXXScopeSpec().getEndLoc();
7033 if (Tok.isAtStartOfLine() && Loc.isValid())
7034 Diag(Loc: PP.getLocForEndOfToken(Loc), DiagID: diag::err_expected_unqualified_id)
7035 << getLangOpts().CPlusPlus;
7036 else
7037 Diag(Loc: getMissingDeclaratorIdLoc(D, Loc: Tok.getLocation()),
7038 DiagID: diag::err_expected_unqualified_id)
7039 << getLangOpts().CPlusPlus;
7040 }
7041 } else {
7042 Diag(Loc: getMissingDeclaratorIdLoc(D, Loc: Tok.getLocation()),
7043 DiagID: diag::err_expected_either)
7044 << tok::identifier << tok::l_paren;
7045 }
7046 }
7047 D.SetIdentifier(Id: nullptr, IdLoc: Tok.getLocation());
7048 D.setInvalidType(true);
7049 }
7050
7051 PastIdentifier:
7052 assert(D.isPastIdentifier() &&
7053 "Haven't past the location of the identifier yet?");
7054
7055 // Don't parse attributes unless we have parsed an unparenthesized name.
7056 if (D.hasName() && !D.getNumTypeObjects())
7057 MaybeParseCXX11Attributes(D);
7058
7059 while (true) {
7060 if (Tok.is(K: tok::l_paren)) {
7061 bool IsFunctionDeclaration = D.isFunctionDeclaratorAFunctionDeclaration();
7062 // Enter function-declaration scope, limiting any declarators to the
7063 // function prototype scope, including parameter declarators.
7064 ParseScope PrototypeScope(
7065 this, Scope::FunctionPrototypeScope | Scope::DeclScope |
7066 (IsFunctionDeclaration ? Scope::FunctionDeclarationScope
7067 : Scope::NoScope));
7068
7069 // The paren may be part of a C++ direct initializer, eg. "int x(1);".
7070 // In such a case, check if we actually have a function declarator; if it
7071 // is not, the declarator has been fully parsed.
7072 bool IsAmbiguous = false;
7073 if (getLangOpts().CPlusPlus && D.mayBeFollowedByCXXDirectInit()) {
7074 // C++2a [temp.res]p5
7075 // A qualified-id is assumed to name a type if
7076 // - [...]
7077 // - it is a decl-specifier of the decl-specifier-seq of a
7078 // - [...]
7079 // - parameter-declaration in a member-declaration [...]
7080 // - parameter-declaration in a declarator of a function or function
7081 // template declaration whose declarator-id is qualified [...]
7082 auto AllowImplicitTypename = ImplicitTypenameContext::No;
7083 if (D.getCXXScopeSpec().isSet())
7084 AllowImplicitTypename =
7085 (ImplicitTypenameContext)Actions.isDeclaratorFunctionLike(D);
7086 else if (D.getContext() == DeclaratorContext::Member) {
7087 AllowImplicitTypename = ImplicitTypenameContext::Yes;
7088 }
7089
7090 // The name of the declarator, if any, is tentatively declared within
7091 // a possible direct initializer.
7092 TentativelyDeclaredIdentifiers.push_back(Elt: D.getIdentifier());
7093 bool IsFunctionDecl =
7094 isCXXFunctionDeclarator(IsAmbiguous: &IsAmbiguous, AllowImplicitTypename);
7095 TentativelyDeclaredIdentifiers.pop_back();
7096 if (!IsFunctionDecl)
7097 break;
7098 }
7099 ParsedAttributes attrs(AttrFactory);
7100 BalancedDelimiterTracker T(*this, tok::l_paren);
7101 T.consumeOpen();
7102 if (IsFunctionDeclaration)
7103 Actions.ActOnStartFunctionDeclarationDeclarator(D,
7104 TemplateParameterDepth);
7105 ParseFunctionDeclarator(D, FirstArgAttrs&: attrs, Tracker&: T, IsAmbiguous);
7106 if (IsFunctionDeclaration)
7107 Actions.ActOnFinishFunctionDeclarationDeclarator(D);
7108 PrototypeScope.Exit();
7109 } else if (Tok.is(K: tok::l_square)) {
7110 ParseBracketDeclarator(D);
7111 } else if (Tok.isRegularKeywordAttribute()) {
7112 // For consistency with attribute parsing.
7113 Diag(Tok, DiagID: diag::err_keyword_not_allowed) << Tok.getIdentifierInfo();
7114 bool TakesArgs = doesKeywordAttributeTakeArgs(Kind: Tok.getKind());
7115 ConsumeToken();
7116 if (TakesArgs) {
7117 BalancedDelimiterTracker T(*this, tok::l_paren);
7118 if (!T.consumeOpen())
7119 T.skipToEnd();
7120 }
7121 } else if (Tok.is(K: tok::kw_requires) && D.hasGroupingParens()) {
7122 // This declarator is declaring a function, but the requires clause is
7123 // in the wrong place:
7124 // void (f() requires true);
7125 // instead of
7126 // void f() requires true;
7127 // or
7128 // void (f()) requires true;
7129 Diag(Tok, DiagID: diag::err_requires_clause_inside_parens);
7130 ConsumeToken();
7131 ExprResult TrailingRequiresClause =
7132 ParseConstraintLogicalOrExpression(/*IsTrailingRequiresClause=*/true);
7133 if (TrailingRequiresClause.isUsable() && D.isFunctionDeclarator() &&
7134 !D.hasTrailingRequiresClause())
7135 // We're already ill-formed if we got here but we'll accept it anyway.
7136 D.setTrailingRequiresClause(TrailingRequiresClause.get());
7137 } else {
7138 break;
7139 }
7140 }
7141}
7142
7143void Parser::ParseDecompositionDeclarator(Declarator &D) {
7144 assert(Tok.is(tok::l_square));
7145
7146 TentativeParsingAction PA(*this);
7147 BalancedDelimiterTracker T(*this, tok::l_square);
7148 T.consumeOpen();
7149
7150 if (isCXX11AttributeSpecifier() != CXX11AttributeKind::NotAttributeSpecifier)
7151 DiagnoseAndSkipCXX11Attributes();
7152
7153 // If this doesn't look like a structured binding, maybe it's a misplaced
7154 // array declarator.
7155 if (!(Tok.isOneOf(Ks: tok::identifier, Ks: tok::ellipsis) &&
7156 NextToken().isOneOf(Ks: tok::comma, Ks: tok::r_square, Ks: tok::kw_alignas,
7157 Ks: tok::identifier, Ks: tok::l_square, Ks: tok::ellipsis)) &&
7158 !(Tok.is(K: tok::r_square) &&
7159 NextToken().isOneOf(Ks: tok::equal, Ks: tok::l_brace))) {
7160 PA.Revert();
7161 return ParseMisplacedBracketDeclarator(D);
7162 }
7163
7164 SourceLocation PrevEllipsisLoc;
7165 SmallVector<DecompositionDeclarator::Binding, 32> Bindings;
7166 while (Tok.isNot(K: tok::r_square)) {
7167 if (!Bindings.empty()) {
7168 if (Tok.is(K: tok::comma))
7169 ConsumeToken();
7170 else {
7171 if (Tok.is(K: tok::identifier)) {
7172 SourceLocation EndLoc = getEndOfPreviousToken();
7173 Diag(Loc: EndLoc, DiagID: diag::err_expected)
7174 << tok::comma << FixItHint::CreateInsertion(InsertionLoc: EndLoc, Code: ",");
7175 } else {
7176 Diag(Tok, DiagID: diag::err_expected_comma_or_rsquare);
7177 }
7178
7179 SkipUntil(Toks: {tok::r_square, tok::comma, tok::identifier, tok::ellipsis},
7180 Flags: StopAtSemi | StopBeforeMatch);
7181 if (Tok.is(K: tok::comma))
7182 ConsumeToken();
7183 else if (Tok.is(K: tok::r_square))
7184 break;
7185 }
7186 }
7187
7188 if (isCXX11AttributeSpecifier() !=
7189 CXX11AttributeKind::NotAttributeSpecifier)
7190 DiagnoseAndSkipCXX11Attributes();
7191
7192 SourceLocation EllipsisLoc;
7193
7194 if (Tok.is(K: tok::ellipsis)) {
7195 DiagCompat(Tok, CompatDiagId: diag_compat::binding_pack);
7196 if (PrevEllipsisLoc.isValid()) {
7197 Diag(Tok, DiagID: diag::err_binding_multiple_ellipses);
7198 Diag(Loc: PrevEllipsisLoc, DiagID: diag::note_previous_ellipsis);
7199 break;
7200 }
7201 EllipsisLoc = Tok.getLocation();
7202 PrevEllipsisLoc = EllipsisLoc;
7203 ConsumeToken();
7204 }
7205
7206 if (Tok.isNot(K: tok::identifier)) {
7207 Diag(Tok, DiagID: diag::err_expected) << tok::identifier;
7208 break;
7209 }
7210
7211 IdentifierInfo *II = Tok.getIdentifierInfo();
7212 SourceLocation Loc = Tok.getLocation();
7213 ConsumeToken();
7214
7215 if (Tok.is(K: tok::ellipsis) && !PrevEllipsisLoc.isValid()) {
7216 DiagnoseMisplacedEllipsis(EllipsisLoc: Tok.getLocation(), CorrectLoc: Loc, AlreadyHasEllipsis: EllipsisLoc.isValid(),
7217 IdentifierHasName: true);
7218 EllipsisLoc = Tok.getLocation();
7219 ConsumeToken();
7220 }
7221
7222 ParsedAttributes Attrs(AttrFactory);
7223 if (isCXX11AttributeSpecifier() !=
7224 CXX11AttributeKind::NotAttributeSpecifier) {
7225 DiagCompat(Tok, CompatDiagId: diag_compat::attrs_on_binding);
7226 MaybeParseCXX11Attributes(Attrs);
7227 }
7228
7229 Bindings.push_back(Elt: {.Name: II, .NameLoc: Loc, .Attrs: std::move(Attrs), .EllipsisLoc: EllipsisLoc});
7230 }
7231
7232 if (Tok.isNot(K: tok::r_square))
7233 // We've already diagnosed a problem here.
7234 T.skipToEnd();
7235 else {
7236 // C++17 does not allow the identifier-list in a structured binding
7237 // to be empty.
7238 if (Bindings.empty())
7239 Diag(Loc: Tok.getLocation(), DiagID: diag::ext_decomp_decl_empty);
7240
7241 T.consumeClose();
7242 }
7243
7244 PA.Commit();
7245
7246 return D.setDecompositionBindings(LSquareLoc: T.getOpenLocation(), Bindings,
7247 RSquareLoc: T.getCloseLocation());
7248}
7249
7250void Parser::ParseParenDeclarator(Declarator &D) {
7251 BalancedDelimiterTracker T(*this, tok::l_paren);
7252 T.consumeOpen();
7253
7254 assert(!D.isPastIdentifier() && "Should be called before passing identifier");
7255
7256 // Eat any attributes before we look at whether this is a grouping or function
7257 // declarator paren. If this is a grouping paren, the attribute applies to
7258 // the type being built up, for example:
7259 // int (__attribute__(()) *x)(long y)
7260 // If this ends up not being a grouping paren, the attribute applies to the
7261 // first argument, for example:
7262 // int (__attribute__(()) int x)
7263 // In either case, we need to eat any attributes to be able to determine what
7264 // sort of paren this is.
7265 //
7266 ParsedAttributes attrs(AttrFactory);
7267 bool RequiresArg = false;
7268 if (Tok.is(K: tok::kw___attribute)) {
7269 ParseGNUAttributes(Attrs&: attrs);
7270
7271 // We require that the argument list (if this is a non-grouping paren) be
7272 // present even if the attribute list was empty.
7273 RequiresArg = true;
7274 }
7275
7276 // Eat any Microsoft extensions.
7277 ParseMicrosoftTypeAttributes(attrs);
7278
7279 // Eat any Borland extensions.
7280 if (Tok.is(K: tok::kw___pascal))
7281 ParseBorlandTypeAttributes(attrs);
7282
7283 // If we haven't past the identifier yet (or where the identifier would be
7284 // stored, if this is an abstract declarator), then this is probably just
7285 // grouping parens. However, if this could be an abstract-declarator, then
7286 // this could also be the start of function arguments (consider 'void()').
7287 bool isGrouping;
7288
7289 if (!D.mayOmitIdentifier()) {
7290 // If this can't be an abstract-declarator, this *must* be a grouping
7291 // paren, because we haven't seen the identifier yet.
7292 isGrouping = true;
7293 } else if (Tok.is(K: tok::r_paren) || // 'int()' is a function.
7294 ((getLangOpts().CPlusPlus || getLangOpts().C23) &&
7295 Tok.is(K: tok::ellipsis) &&
7296 NextToken().is(K: tok::r_paren)) || // C++ int(...)
7297 isDeclarationSpecifier(
7298 AllowImplicitTypename: ImplicitTypenameContext::No) || // 'int(int)' is a function.
7299 isCXX11AttributeSpecifier() !=
7300 CXX11AttributeKind::NotAttributeSpecifier) { // 'int([[]]int)'
7301 // is a function.
7302 // This handles C99 6.7.5.3p11: in "typedef int X; void foo(X)", X is
7303 // considered to be a type, not a K&R identifier-list.
7304 isGrouping = false;
7305 } else {
7306 // Otherwise, this is a grouping paren, e.g. 'int (*X)' or 'int(X)'.
7307 isGrouping = true;
7308 }
7309
7310 // If this is a grouping paren, handle:
7311 // direct-declarator: '(' declarator ')'
7312 // direct-declarator: '(' attributes declarator ')'
7313 if (isGrouping) {
7314 SourceLocation EllipsisLoc = D.getEllipsisLoc();
7315 D.setEllipsisLoc(SourceLocation());
7316
7317 bool hadGroupingParens = D.hasGroupingParens();
7318 D.setGroupingParens(true);
7319 ParseDeclaratorInternal(D, DirectDeclParser: &Parser::ParseDirectDeclarator);
7320 // Match the ')'.
7321 T.consumeClose();
7322 D.AddTypeInfo(
7323 TI: DeclaratorChunk::getParen(LParenLoc: T.getOpenLocation(), RParenLoc: T.getCloseLocation()),
7324 attrs: std::move(attrs), EndLoc: T.getCloseLocation());
7325
7326 D.setGroupingParens(hadGroupingParens);
7327
7328 // An ellipsis cannot be placed outside parentheses.
7329 if (EllipsisLoc.isValid())
7330 DiagnoseMisplacedEllipsisInDeclarator(EllipsisLoc, D);
7331
7332 return;
7333 }
7334
7335 // Okay, if this wasn't a grouping paren, it must be the start of a function
7336 // argument list. Recognize that this declarator will never have an
7337 // identifier (and remember where it would have been), then call into
7338 // ParseFunctionDeclarator to handle of argument list.
7339 D.SetIdentifier(Id: nullptr, IdLoc: Tok.getLocation());
7340
7341 // Enter function-declaration scope, limiting any declarators to the
7342 // function prototype scope, including parameter declarators.
7343 ParseScope PrototypeScope(this,
7344 Scope::FunctionPrototypeScope | Scope::DeclScope |
7345 (D.isFunctionDeclaratorAFunctionDeclaration()
7346 ? Scope::FunctionDeclarationScope
7347 : Scope::NoScope));
7348 ParseFunctionDeclarator(D, FirstArgAttrs&: attrs, Tracker&: T, IsAmbiguous: false, RequiresArg);
7349 PrototypeScope.Exit();
7350}
7351
7352void Parser::InitCXXThisScopeForDeclaratorIfRelevant(
7353 const Declarator &D, const DeclSpec &DS,
7354 std::optional<Sema::CXXThisScopeRAII> &ThisScope) {
7355 // C++11 [expr.prim.general]p3:
7356 // If a declaration declares a member function or member function
7357 // template of a class X, the expression this is a prvalue of type
7358 // "pointer to cv-qualifier-seq X" between the optional cv-qualifer-seq
7359 // and the end of the function-definition, member-declarator, or
7360 // declarator.
7361 // FIXME: currently, "static" case isn't handled correctly.
7362 bool IsCXX11MemberFunction =
7363 getLangOpts().CPlusPlus11 &&
7364 D.getDeclSpec().getStorageClassSpec() != DeclSpec::SCS_typedef &&
7365 (D.getContext() == DeclaratorContext::Member
7366 ? !D.getDeclSpec().isFriendSpecified()
7367 : D.getContext() == DeclaratorContext::File &&
7368 D.getCXXScopeSpec().isValid() &&
7369 Actions.CurContext->isRecord());
7370 if (!IsCXX11MemberFunction)
7371 return;
7372
7373 Qualifiers Q = Qualifiers::fromCVRUMask(CVRU: DS.getTypeQualifiers());
7374 if (D.getDeclSpec().hasConstexprSpecifier() && !getLangOpts().CPlusPlus14)
7375 Q.addConst();
7376 // FIXME: Collect C++ address spaces.
7377 // If there are multiple different address spaces, the source is invalid.
7378 // Carry on using the first addr space for the qualifiers of 'this'.
7379 // The diagnostic will be given later while creating the function
7380 // prototype for the method.
7381 if (getLangOpts().OpenCLCPlusPlus) {
7382 for (ParsedAttr &attr : DS.getAttributes()) {
7383 LangAS ASIdx = attr.asOpenCLLangAS();
7384 if (ASIdx != LangAS::Default) {
7385 Q.addAddressSpace(space: ASIdx);
7386 break;
7387 }
7388 }
7389 }
7390 ThisScope.emplace(args&: Actions, args: dyn_cast<CXXRecordDecl>(Val: Actions.CurContext), args&: Q,
7391 args&: IsCXX11MemberFunction);
7392}
7393
7394void Parser::ParseFunctionDeclarator(Declarator &D,
7395 ParsedAttributes &FirstArgAttrs,
7396 BalancedDelimiterTracker &Tracker,
7397 bool IsAmbiguous,
7398 bool RequiresArg) {
7399 assert(getCurScope()->isFunctionPrototypeScope() &&
7400 "Should call from a Function scope");
7401 // lparen is already consumed!
7402 assert(D.isPastIdentifier() && "Should not call before identifier!");
7403
7404 // This should be true when the function has typed arguments.
7405 // Otherwise, it is treated as a K&R-style function.
7406 bool HasProto = false;
7407 // Build up an array of information about the parsed arguments.
7408 SmallVector<DeclaratorChunk::ParamInfo, 16> ParamInfo;
7409 // Remember where we see an ellipsis, if any.
7410 SourceLocation EllipsisLoc;
7411
7412 DeclSpec DS(AttrFactory);
7413 bool RefQualifierIsLValueRef = true;
7414 SourceLocation RefQualifierLoc;
7415 ExceptionSpecificationType ESpecType = EST_None;
7416 SourceRange ESpecRange;
7417 SmallVector<ParsedType, 2> DynamicExceptions;
7418 SmallVector<SourceRange, 2> DynamicExceptionRanges;
7419 ExprResult NoexceptExpr;
7420 CachedTokens *ExceptionSpecTokens = nullptr;
7421 ParsedAttributes FnAttrs(AttrFactory);
7422 TypeResult TrailingReturnType;
7423 SourceLocation TrailingReturnTypeLoc;
7424
7425 /* LocalEndLoc is the end location for the local FunctionTypeLoc.
7426 EndLoc is the end location for the function declarator.
7427 They differ for trailing return types. */
7428 SourceLocation StartLoc, LocalEndLoc, EndLoc;
7429 SourceLocation LParenLoc, RParenLoc;
7430 LParenLoc = Tracker.getOpenLocation();
7431 StartLoc = LParenLoc;
7432
7433 if (isFunctionDeclaratorIdentifierList()) {
7434 if (RequiresArg)
7435 Diag(Tok, DiagID: diag::err_argument_required_after_attribute);
7436
7437 ParseFunctionDeclaratorIdentifierList(D, ParamInfo);
7438
7439 Tracker.consumeClose();
7440 RParenLoc = Tracker.getCloseLocation();
7441 LocalEndLoc = RParenLoc;
7442 EndLoc = RParenLoc;
7443
7444 // If there are attributes following the identifier list, parse them and
7445 // prohibit them.
7446 MaybeParseCXX11Attributes(Attrs&: FnAttrs);
7447 ProhibitAttributes(Attrs&: FnAttrs);
7448 } else {
7449 if (Tok.isNot(K: tok::r_paren))
7450 ParseParameterDeclarationClause(D, attrs&: FirstArgAttrs, ParamInfo, EllipsisLoc);
7451 else if (RequiresArg)
7452 Diag(Tok, DiagID: diag::err_argument_required_after_attribute);
7453
7454 // OpenCL disallows functions without a prototype, but it doesn't enforce
7455 // strict prototypes as in C23 because it allows a function definition to
7456 // have an identifier list. See OpenCL 3.0 6.11/g for more details.
7457 HasProto = ParamInfo.size() || getLangOpts().requiresStrictPrototypes() ||
7458 getLangOpts().OpenCL;
7459
7460 // If we have the closing ')', eat it.
7461 Tracker.consumeClose();
7462 RParenLoc = Tracker.getCloseLocation();
7463 LocalEndLoc = RParenLoc;
7464 EndLoc = RParenLoc;
7465
7466 if (getLangOpts().CPlusPlus) {
7467 // FIXME: Accept these components in any order, and produce fixits to
7468 // correct the order if the user gets it wrong. Ideally we should deal
7469 // with the pure-specifier in the same way.
7470
7471 // Parse cv-qualifier-seq[opt].
7472 ParseTypeQualifierListOpt(
7473 DS, AttrReqs: AR_NoAttributesParsed,
7474 /*AtomicOrPtrauthAllowed=*/false,
7475 /*IdentifierRequired=*/false, CodeCompletionHandler: [&]() {
7476 Actions.CodeCompletion().CodeCompleteFunctionQualifiers(DS, D);
7477 });
7478 if (!DS.getSourceRange().getEnd().isInvalid()) {
7479 EndLoc = DS.getSourceRange().getEnd();
7480 }
7481
7482 // Parse ref-qualifier[opt].
7483 if (ParseRefQualifier(RefQualifierIsLValueRef, RefQualifierLoc))
7484 EndLoc = RefQualifierLoc;
7485
7486 std::optional<Sema::CXXThisScopeRAII> ThisScope;
7487 InitCXXThisScopeForDeclaratorIfRelevant(D, DS, ThisScope);
7488
7489 // C++ [class.mem.general]p8:
7490 // A complete-class context of a class (template) is a
7491 // - function body,
7492 // - default argument,
7493 // - default template argument,
7494 // - noexcept-specifier, or
7495 // - default member initializer
7496 // within the member-specification of the class or class template.
7497 //
7498 // Parse exception-specification[opt]. If we are in the
7499 // member-specification of a class or class template, this is a
7500 // complete-class context and parsing of the noexcept-specifier should be
7501 // delayed (even if this is a friend declaration).
7502 bool Delayed = D.getContext() == DeclaratorContext::Member &&
7503 D.isFunctionDeclaratorAFunctionDeclaration();
7504 if (Delayed && Actions.isLibstdcxxEagerExceptionSpecHack(D) &&
7505 GetLookAheadToken(N: 0).is(K: tok::kw_noexcept) &&
7506 GetLookAheadToken(N: 1).is(K: tok::l_paren) &&
7507 GetLookAheadToken(N: 2).is(K: tok::kw_noexcept) &&
7508 GetLookAheadToken(N: 3).is(K: tok::l_paren) &&
7509 GetLookAheadToken(N: 4).is(K: tok::identifier) &&
7510 GetLookAheadToken(N: 4).getIdentifierInfo()->isStr(Str: "swap")) {
7511 // HACK: We've got an exception-specification
7512 // noexcept(noexcept(swap(...)))
7513 // or
7514 // noexcept(noexcept(swap(...)) && noexcept(swap(...)))
7515 // on a 'swap' member function. This is a libstdc++ bug; the lookup
7516 // for 'swap' will only find the function we're currently declaring,
7517 // whereas it expects to find a non-member swap through ADL. Turn off
7518 // delayed parsing to give it a chance to find what it expects.
7519 Delayed = false;
7520 }
7521 ESpecType = tryParseExceptionSpecification(Delayed,
7522 SpecificationRange&: ESpecRange,
7523 DynamicExceptions,
7524 DynamicExceptionRanges,
7525 NoexceptExpr,
7526 ExceptionSpecTokens);
7527 if (ESpecType != EST_None)
7528 EndLoc = ESpecRange.getEnd();
7529
7530 // Parse attribute-specifier-seq[opt]. Per DR 979 and DR 1297, this goes
7531 // after the exception-specification.
7532 MaybeParseCXX11Attributes(Attrs&: FnAttrs);
7533
7534 // Parse trailing-return-type[opt].
7535 LocalEndLoc = EndLoc;
7536 if (getLangOpts().CPlusPlus11 && Tok.is(K: tok::arrow)) {
7537 Diag(Tok, DiagID: diag::warn_cxx98_compat_trailing_return_type);
7538 if (D.getDeclSpec().getTypeSpecType() == TST_auto)
7539 StartLoc = D.getDeclSpec().getTypeSpecTypeLoc();
7540 LocalEndLoc = Tok.getLocation();
7541 SourceRange Range;
7542 TrailingReturnType =
7543 ParseTrailingReturnType(Range, MayBeFollowedByDirectInit: D.mayBeFollowedByCXXDirectInit());
7544 TrailingReturnTypeLoc = Range.getBegin();
7545 EndLoc = Range.getEnd();
7546 }
7547 } else {
7548 MaybeParseCXX11Attributes(Attrs&: FnAttrs);
7549 }
7550 }
7551
7552 // Collect non-parameter declarations from the prototype if this is a function
7553 // declaration. They will be moved into the scope of the function. Only do
7554 // this in C and not C++, where the decls will continue to live in the
7555 // surrounding context.
7556 SmallVector<NamedDecl *, 0> DeclsInPrototype;
7557 if (getCurScope()->isFunctionDeclarationScope() && !getLangOpts().CPlusPlus) {
7558 for (Decl *D : getCurScope()->decls()) {
7559 NamedDecl *ND = dyn_cast<NamedDecl>(Val: D);
7560 if (!ND || isa<ParmVarDecl>(Val: ND))
7561 continue;
7562 DeclsInPrototype.push_back(Elt: ND);
7563 }
7564 // Sort DeclsInPrototype based on raw encoding of the source location.
7565 // Scope::decls() is iterating over a SmallPtrSet so sort the Decls before
7566 // moving to DeclContext. This provides a stable ordering for traversing
7567 // Decls in DeclContext, which is important for tasks like ASTWriter for
7568 // deterministic output.
7569 llvm::sort(C&: DeclsInPrototype, Comp: [](Decl *D1, Decl *D2) {
7570 return D1->getLocation().getRawEncoding() <
7571 D2->getLocation().getRawEncoding();
7572 });
7573 }
7574
7575 // Remember that we parsed a function type, and remember the attributes.
7576 D.AddTypeInfo(TI: DeclaratorChunk::getFunction(
7577 HasProto, IsAmbiguous, LParenLoc, Params: ParamInfo.data(),
7578 NumParams: ParamInfo.size(), EllipsisLoc, RParenLoc,
7579 RefQualifierIsLvalueRef: RefQualifierIsLValueRef, RefQualifierLoc,
7580 /*MutableLoc=*/SourceLocation(),
7581 ESpecType, ESpecRange, Exceptions: DynamicExceptions.data(),
7582 ExceptionRanges: DynamicExceptionRanges.data(), NumExceptions: DynamicExceptions.size(),
7583 NoexceptExpr: NoexceptExpr.isUsable() ? NoexceptExpr.get() : nullptr,
7584 ExceptionSpecTokens, DeclsInPrototype, LocalRangeBegin: StartLoc,
7585 LocalRangeEnd: LocalEndLoc, TheDeclarator&: D, TrailingReturnType, TrailingReturnTypeLoc,
7586 MethodQualifiers: &DS),
7587 attrs: std::move(FnAttrs), EndLoc);
7588}
7589
7590bool Parser::ParseRefQualifier(bool &RefQualifierIsLValueRef,
7591 SourceLocation &RefQualifierLoc) {
7592 if (Tok.isOneOf(Ks: tok::amp, Ks: tok::ampamp)) {
7593 DiagCompat(Tok, CompatDiagId: diag_compat::ref_qualifier);
7594 RefQualifierIsLValueRef = Tok.is(K: tok::amp);
7595 RefQualifierLoc = ConsumeToken();
7596 return true;
7597 }
7598 return false;
7599}
7600
7601bool Parser::isFunctionDeclaratorIdentifierList() {
7602 return !getLangOpts().requiresStrictPrototypes()
7603 && Tok.is(K: tok::identifier)
7604 && !TryAltiVecVectorToken()
7605 // K&R identifier lists can't have typedefs as identifiers, per C99
7606 // 6.7.5.3p11.
7607 && (TryAnnotateTypeOrScopeToken() || !Tok.is(K: tok::annot_typename))
7608 // Identifier lists follow a really simple grammar: the identifiers can
7609 // be followed *only* by a ", identifier" or ")". However, K&R
7610 // identifier lists are really rare in the brave new modern world, and
7611 // it is very common for someone to typo a type in a non-K&R style
7612 // list. If we are presented with something like: "void foo(intptr x,
7613 // float y)", we don't want to start parsing the function declarator as
7614 // though it is a K&R style declarator just because intptr is an
7615 // invalid type.
7616 //
7617 // To handle this, we check to see if the token after the first
7618 // identifier is a "," or ")". Only then do we parse it as an
7619 // identifier list.
7620 && (!Tok.is(K: tok::eof) &&
7621 (NextToken().is(K: tok::comma) || NextToken().is(K: tok::r_paren)));
7622}
7623
7624void Parser::ParseFunctionDeclaratorIdentifierList(
7625 Declarator &D,
7626 SmallVectorImpl<DeclaratorChunk::ParamInfo> &ParamInfo) {
7627 // We should never reach this point in C23 or C++.
7628 assert(!getLangOpts().requiresStrictPrototypes() &&
7629 "Cannot parse an identifier list in C23 or C++");
7630
7631 // If there was no identifier specified for the declarator, either we are in
7632 // an abstract-declarator, or we are in a parameter declarator which was found
7633 // to be abstract. In abstract-declarators, identifier lists are not valid:
7634 // diagnose this.
7635 if (!D.getIdentifier())
7636 Diag(Tok, DiagID: diag::ext_ident_list_in_param);
7637
7638 // Maintain an efficient lookup of params we have seen so far.
7639 llvm::SmallPtrSet<const IdentifierInfo *, 16> ParamsSoFar;
7640
7641 do {
7642 // If this isn't an identifier, report the error and skip until ')'.
7643 if (Tok.isNot(K: tok::identifier)) {
7644 Diag(Tok, DiagID: diag::err_expected) << tok::identifier;
7645 SkipUntil(T: tok::r_paren, Flags: StopAtSemi | StopBeforeMatch);
7646 // Forget we parsed anything.
7647 ParamInfo.clear();
7648 return;
7649 }
7650
7651 IdentifierInfo *ParmII = Tok.getIdentifierInfo();
7652
7653 // Reject 'typedef int y; int test(x, y)', but continue parsing.
7654 if (Actions.getTypeName(II: *ParmII, NameLoc: Tok.getLocation(), S: getCurScope()))
7655 Diag(Tok, DiagID: diag::err_unexpected_typedef_ident) << ParmII;
7656
7657 // Verify that the argument identifier has not already been mentioned.
7658 if (!ParamsSoFar.insert(Ptr: ParmII).second) {
7659 Diag(Tok, DiagID: diag::err_param_redefinition) << ParmII;
7660 } else {
7661 // Remember this identifier in ParamInfo.
7662 ParamInfo.push_back(Elt: DeclaratorChunk::ParamInfo(ParmII,
7663 Tok.getLocation(),
7664 nullptr));
7665 }
7666
7667 // Eat the identifier.
7668 ConsumeToken();
7669 // The list continues if we see a comma.
7670 } while (TryConsumeToken(Expected: tok::comma));
7671}
7672
7673void Parser::ParseParameterDeclarationClause(
7674 DeclaratorContext DeclaratorCtx, ParsedAttributes &FirstArgAttrs,
7675 SmallVectorImpl<DeclaratorChunk::ParamInfo> &ParamInfo,
7676 SourceLocation &EllipsisLoc, bool IsACXXFunctionDeclaration) {
7677
7678 // Avoid exceeding the maximum function scope depth.
7679 // See https://bugs.llvm.org/show_bug.cgi?id=19607
7680 // Note Sema::ActOnParamDeclarator calls ParmVarDecl::setScopeInfo with
7681 // getFunctionPrototypeDepth() - 1.
7682 if (getCurScope()->getFunctionPrototypeDepth() - 1 >
7683 ParmVarDecl::getMaxFunctionScopeDepth()) {
7684 Diag(Loc: Tok.getLocation(), DiagID: diag::err_function_scope_depth_exceeded)
7685 << ParmVarDecl::getMaxFunctionScopeDepth();
7686 cutOffParsing();
7687 return;
7688 }
7689
7690 // C++2a [temp.res]p5
7691 // A qualified-id is assumed to name a type if
7692 // - [...]
7693 // - it is a decl-specifier of the decl-specifier-seq of a
7694 // - [...]
7695 // - parameter-declaration in a member-declaration [...]
7696 // - parameter-declaration in a declarator of a function or function
7697 // template declaration whose declarator-id is qualified [...]
7698 // - parameter-declaration in a lambda-declarator [...]
7699 auto AllowImplicitTypename = ImplicitTypenameContext::No;
7700 if (DeclaratorCtx == DeclaratorContext::Member ||
7701 DeclaratorCtx == DeclaratorContext::LambdaExpr ||
7702 DeclaratorCtx == DeclaratorContext::RequiresExpr ||
7703 IsACXXFunctionDeclaration) {
7704 AllowImplicitTypename = ImplicitTypenameContext::Yes;
7705 }
7706
7707 // An attribute on a parameter may name another parameter of the same
7708 // prototype that is declared later, such as a callback parameter whose
7709 // attribute names a lock passed after it. Defer those to the end of the
7710 // clause, where every parameter is declared and the prototype scope is still
7711 // open, so no scope need be re-entered.
7712 LateParsedAttrList LateParamAttrs(/*PSoon=*/true,
7713 /*LateAttrParseExperimentalExtOnly=*/true);
7714
7715 do {
7716 // FIXME: Issue a diagnostic if we parsed an attribute-specifier-seq
7717 // before deciding this was a parameter-declaration-clause.
7718 if (TryConsumeToken(Expected: tok::ellipsis, Loc&: EllipsisLoc))
7719 break;
7720
7721 // Parse the declaration-specifiers.
7722 // Just use the ParsingDeclaration "scope" of the declarator.
7723 DeclSpec DS(AttrFactory);
7724
7725 ParsedAttributes ArgDeclAttrs(AttrFactory);
7726 ParsedAttributes ArgDeclSpecAttrs(AttrFactory);
7727
7728 if (FirstArgAttrs.Range.isValid()) {
7729 // If the caller parsed attributes for the first argument, add them now.
7730 // Take them so that we only apply the attributes to the first parameter.
7731 // We have already started parsing the decl-specifier sequence, so don't
7732 // parse any parameter-declaration pieces that precede it.
7733 ArgDeclSpecAttrs.takeAllPrependingFrom(Other&: FirstArgAttrs);
7734 } else {
7735 // Parse any C++11 attributes.
7736 MaybeParseCXX11Attributes(Attrs&: ArgDeclAttrs);
7737
7738 // Skip any Microsoft attributes before a param.
7739 MaybeParseMicrosoftAttributes(Attrs&: ArgDeclSpecAttrs);
7740 }
7741
7742 SourceLocation DSStart = Tok.getLocation();
7743
7744 // Parse a C++23 Explicit Object Parameter
7745 // We do that in all language modes to produce a better diagnostic.
7746 SourceLocation ThisLoc;
7747 if (getLangOpts().CPlusPlus && Tok.is(K: tok::kw_this))
7748 ThisLoc = ConsumeToken();
7749
7750 ParsedTemplateInfo TemplateInfo;
7751 ParseDeclarationSpecifiers(DS, TemplateInfo, AS: AS_none,
7752 DSContext: DeclSpecContext::DSC_normal,
7753 /*LateAttrs=*/nullptr, AllowImplicitTypename);
7754
7755 DS.takeAttributesAppendingingFrom(attrs&: ArgDeclSpecAttrs);
7756
7757 // Parse the declarator. This is "PrototypeContext" or
7758 // "LambdaExprParameterContext", because we must accept either
7759 // 'declarator' or 'abstract-declarator' here.
7760 Declarator ParmDeclarator(DS, ArgDeclAttrs,
7761 DeclaratorCtx == DeclaratorContext::RequiresExpr
7762 ? DeclaratorContext::RequiresExpr
7763 : DeclaratorCtx == DeclaratorContext::LambdaExpr
7764 ? DeclaratorContext::LambdaExprParameter
7765 : DeclaratorContext::Prototype);
7766 ParseDeclarator(D&: ParmDeclarator);
7767
7768 if (ThisLoc.isValid())
7769 ParmDeclarator.SetRangeBegin(ThisLoc);
7770
7771 // Parse GNU attributes, if present.
7772 MaybeParseGNUAttributes(D&: ParmDeclarator, LateAttrs: &LateParamAttrs);
7773 if (getLangOpts().HLSL)
7774 MaybeParseHLSLAnnotations(Attrs&: DS.getAttributes());
7775
7776 if (Tok.is(K: tok::kw_requires)) {
7777 // User tried to define a requires clause in a parameter declaration,
7778 // which is surely not a function declaration.
7779 // void f(int (*g)(int, int) requires true);
7780 Diag(Tok,
7781 DiagID: diag::err_requires_clause_on_declarator_not_declaring_a_function);
7782 ConsumeToken();
7783 ParseConstraintLogicalOrExpression(/*IsTrailingRequiresClause=*/true);
7784 }
7785
7786 // Remember this parsed parameter in ParamInfo.
7787 const IdentifierInfo *ParmII = ParmDeclarator.getIdentifier();
7788
7789 // DefArgToks is used when the parsing of default arguments needs
7790 // to be delayed.
7791 std::unique_ptr<CachedTokens> DefArgToks;
7792
7793 // If no parameter was specified, verify that *something* was specified,
7794 // otherwise we have a missing type and identifier.
7795 if (DS.isEmpty() && ParmDeclarator.getIdentifier() == nullptr &&
7796 ParmDeclarator.getNumTypeObjects() == 0) {
7797 // Completely missing, emit error.
7798 Diag(Loc: DSStart, DiagID: diag::err_missing_param);
7799 } else {
7800 // Otherwise, we have something. Add it and let semantic analysis try
7801 // to grok it and add the result to the ParamInfo we are building.
7802
7803 // Last chance to recover from a misplaced ellipsis in an attempted
7804 // parameter pack declaration.
7805 if (Tok.is(K: tok::ellipsis) &&
7806 (NextToken().isNot(K: tok::r_paren) ||
7807 (!ParmDeclarator.getEllipsisLoc().isValid() &&
7808 !Actions.isUnexpandedParameterPackPermitted())) &&
7809 Actions.containsUnexpandedParameterPacks(D&: ParmDeclarator))
7810 DiagnoseMisplacedEllipsisInDeclarator(EllipsisLoc: ConsumeToken(), D&: ParmDeclarator);
7811
7812 // Now we are at the point where declarator parsing is finished.
7813 //
7814 // Try to catch keywords in place of the identifier in a declarator, and
7815 // in particular the common case where:
7816 // 1 identifier comes at the end of the declarator
7817 // 2 if the identifier is dropped, the declarator is valid but anonymous
7818 // (no identifier)
7819 // 3 declarator parsing succeeds, and then we have a trailing keyword,
7820 // which is never valid in a param list (e.g. missing a ',')
7821 // And we can't handle this in ParseDeclarator because in general keywords
7822 // may be allowed to follow the declarator. (And in some cases there'd be
7823 // better recovery like inserting punctuation). ParseDeclarator is just
7824 // treating this as an anonymous parameter, and fortunately at this point
7825 // we've already almost done that.
7826 //
7827 // We care about case 1) where the declarator type should be known, and
7828 // the identifier should be null.
7829 if (!ParmDeclarator.isInvalidType() && !ParmDeclarator.hasName() &&
7830 Tok.isNot(K: tok::raw_identifier) && !Tok.isAnnotation() &&
7831 Tok.getIdentifierInfo() &&
7832 Tok.getIdentifierInfo()->isKeyword(LangOpts: getLangOpts())) {
7833 Diag(Tok, DiagID: diag::err_keyword_as_parameter) << PP.getSpelling(Tok);
7834 // Consume the keyword.
7835 ConsumeToken();
7836 }
7837
7838 // We can only store so many parameters
7839 // Skip until the the end of the parameter list, ignoring
7840 // parameters that would overflow.
7841 if (ParamInfo.size() == Type::FunctionTypeNumParamsLimit) {
7842 Diag(Loc: ParmDeclarator.getBeginLoc(),
7843 DiagID: diag::err_function_parameter_limit_exceeded);
7844 SkipUntil(T: tok::r_paren, Flags: SkipUntilFlags::StopBeforeMatch);
7845 break;
7846 }
7847
7848 // Inform the actions module about the parameter declarator, so it gets
7849 // added to the current scope.
7850 Decl *Param =
7851 Actions.ActOnParamDeclarator(S: getCurScope(), D&: ParmDeclarator, ExplicitThisLoc: ThisLoc);
7852 // Claim deferred attributes now, before the next parameter can.
7853 DistributeCLateParsedAttrs(Dcl: Param, LateAttrs: &LateParamAttrs);
7854 // Parse the default argument, if any. We parse the default
7855 // arguments in all dialects; the semantic analysis in
7856 // ActOnParamDefaultArgument will reject the default argument in
7857 // C.
7858 if (Tok.is(K: tok::equal)) {
7859 SourceLocation EqualLoc = Tok.getLocation();
7860
7861 // Parse the default argument
7862 if (DeclaratorCtx == DeclaratorContext::Member) {
7863 // If we're inside a class definition, cache the tokens
7864 // corresponding to the default argument. We'll actually parse
7865 // them when we see the end of the class definition.
7866 DefArgToks.reset(p: new CachedTokens);
7867
7868 SourceLocation ArgStartLoc = NextToken().getLocation();
7869 ConsumeAndStoreInitializer(Toks&: *DefArgToks,
7870 CIK: CachedInitKind::DefaultArgument);
7871 Actions.ActOnParamUnparsedDefaultArgument(param: Param, EqualLoc,
7872 ArgLoc: ArgStartLoc);
7873 } else {
7874 // Consume the '='.
7875 ConsumeToken();
7876
7877 // The default argument may contain a lambda whose body triggers
7878 // MaybeDestroyTemplateIds at the end of the inner statements; avoid
7879 // destroying parsed template-ids that may still be referenced by
7880 // the enclosing declarator (e.g. a template-id in the function
7881 // name or other parameters).
7882 DelayTemplateIdDestructionRAII DontDestructTemplateIds(
7883 *this, /*DelayTemplateIdDestruction=*/true);
7884
7885 // The argument isn't actually potentially evaluated unless it is
7886 // used.
7887 EnterExpressionEvaluationContext Eval(
7888 Actions,
7889 Sema::ExpressionEvaluationContext::PotentiallyEvaluatedIfUsed,
7890 Param);
7891
7892 ExprResult DefArgResult;
7893 if (getLangOpts().CPlusPlus11 && Tok.is(K: tok::l_brace)) {
7894 Diag(Tok, DiagID: diag::compat_cxx11_generalized_initializer_lists);
7895 DefArgResult = ParseBraceInitializer();
7896 } else {
7897 if (Tok.is(K: tok::l_paren) && NextToken().is(K: tok::l_brace)) {
7898 Diag(Tok, DiagID: diag::err_stmt_expr_in_default_arg) << 0;
7899 Actions.ActOnParamDefaultArgumentError(param: Param, EqualLoc,
7900 /*DefaultArg=*/nullptr);
7901 // Skip the statement expression and continue parsing
7902 SkipUntil(T: tok::comma, Flags: StopBeforeMatch);
7903 DefArgResult = ExprError();
7904 } else {
7905 DefArgResult = ParseAssignmentExpression();
7906 }
7907 }
7908 if (DefArgResult.isInvalid()) {
7909 Actions.ActOnParamDefaultArgumentError(param: Param, EqualLoc,
7910 /*DefaultArg=*/nullptr);
7911 SkipUntil(T1: tok::comma, T2: tok::r_paren, Flags: StopAtSemi | StopBeforeMatch);
7912 } else {
7913 // Inform the actions module about the default argument
7914 Actions.ActOnParamDefaultArgument(param: Param, EqualLoc,
7915 defarg: DefArgResult.get());
7916 }
7917 }
7918 }
7919
7920 ParamInfo.push_back(Elt: DeclaratorChunk::ParamInfo(ParmII,
7921 ParmDeclarator.getIdentifierLoc(),
7922 Param, std::move(DefArgToks)));
7923 }
7924
7925 if (TryConsumeToken(Expected: tok::ellipsis, Loc&: EllipsisLoc)) {
7926 if (getLangOpts().CPlusPlus26) {
7927 // C++26 [dcl.dcl.fct]p3:
7928 // A parameter-declaration-clause of the form
7929 // parameter-list '...' is deprecated.
7930 Diag(Loc: EllipsisLoc, DiagID: diag::warn_deprecated_missing_comma_before_ellipsis)
7931 << FixItHint::CreateInsertion(InsertionLoc: EllipsisLoc, Code: ", ");
7932 }
7933
7934 if (!getLangOpts().CPlusPlus) {
7935 // We have ellipsis without a preceding ',', which is ill-formed
7936 // in C. Complain and provide the fix.
7937 Diag(Loc: EllipsisLoc, DiagID: diag::err_missing_comma_before_ellipsis)
7938 << FixItHint::CreateInsertion(InsertionLoc: EllipsisLoc, Code: ", ");
7939 } else if (ParmDeclarator.getEllipsisLoc().isValid() ||
7940 Actions.containsUnexpandedParameterPacks(D&: ParmDeclarator)) {
7941 // It looks like this was supposed to be a parameter pack. Warn and
7942 // point out where the ellipsis should have gone.
7943 SourceLocation ParmEllipsis = ParmDeclarator.getEllipsisLoc();
7944 Diag(Loc: EllipsisLoc, DiagID: diag::warn_misplaced_ellipsis_vararg)
7945 << ParmEllipsis.isValid() << ParmEllipsis;
7946 if (ParmEllipsis.isValid()) {
7947 Diag(Loc: ParmEllipsis,
7948 DiagID: diag::note_misplaced_ellipsis_vararg_existing_ellipsis);
7949 } else {
7950 Diag(Loc: ParmDeclarator.getIdentifierLoc(),
7951 DiagID: diag::note_misplaced_ellipsis_vararg_add_ellipsis)
7952 << FixItHint::CreateInsertion(InsertionLoc: ParmDeclarator.getIdentifierLoc(),
7953 Code: "...")
7954 << !ParmDeclarator.hasName();
7955 }
7956 Diag(Loc: EllipsisLoc, DiagID: diag::note_misplaced_ellipsis_vararg_add_comma)
7957 << FixItHint::CreateInsertion(InsertionLoc: EllipsisLoc, Code: ", ");
7958 }
7959
7960 // We can't have any more parameters after an ellipsis.
7961 break;
7962 }
7963
7964 // If the next token is a comma, consume it and keep reading arguments.
7965 } while (TryConsumeToken(Expected: tok::comma));
7966
7967 // Every parameter is declared and still in scope, so a deferred attribute can
7968 // name any of them.
7969 if (!LateParamAttrs.empty())
7970 ParseLexedAttributeList(LAs&: LateParamAttrs, /*D=*/nullptr, /*EnterScope=*/false,
7971 /*OnDefinition=*/false);
7972}
7973
7974void Parser::ParseBracketDeclarator(Declarator &D) {
7975 if (CheckProhibitedCXX11Attribute())
7976 return;
7977
7978 BalancedDelimiterTracker T(*this, tok::l_square);
7979 T.consumeOpen();
7980
7981 // C array syntax has many features, but by-far the most common is [] and [4].
7982 // This code does a fast path to handle some of the most obvious cases.
7983 if (Tok.getKind() == tok::r_square) {
7984 T.consumeClose();
7985 ParsedAttributes attrs(AttrFactory);
7986 MaybeParseCXX11Attributes(Attrs&: attrs);
7987
7988 // Remember that we parsed the empty array type.
7989 D.AddTypeInfo(TI: DeclaratorChunk::getArray(TypeQuals: 0, isStatic: false, isStar: false, NumElts: nullptr,
7990 LBLoc: T.getOpenLocation(),
7991 RBLoc: T.getCloseLocation()),
7992 attrs: std::move(attrs), EndLoc: T.getCloseLocation());
7993 return;
7994 } else if (Tok.getKind() == tok::numeric_constant &&
7995 GetLookAheadToken(N: 1).is(K: tok::r_square)) {
7996 // [4] is very common. Parse the numeric constant expression.
7997 ExprResult ExprRes(Actions.ActOnNumericConstant(Tok, UDLScope: getCurScope()));
7998 ConsumeToken();
7999
8000 T.consumeClose();
8001 ParsedAttributes attrs(AttrFactory);
8002 MaybeParseCXX11Attributes(Attrs&: attrs);
8003
8004 // Remember that we parsed a array type, and remember its features.
8005 D.AddTypeInfo(TI: DeclaratorChunk::getArray(TypeQuals: 0, isStatic: false, isStar: false, NumElts: ExprRes.get(),
8006 LBLoc: T.getOpenLocation(),
8007 RBLoc: T.getCloseLocation()),
8008 attrs: std::move(attrs), EndLoc: T.getCloseLocation());
8009 return;
8010 } else if (Tok.getKind() == tok::code_completion) {
8011 cutOffParsing();
8012 Actions.CodeCompletion().CodeCompleteBracketDeclarator(S: getCurScope());
8013 return;
8014 }
8015
8016 // If valid, this location is the position where we read the 'static' keyword.
8017 SourceLocation StaticLoc;
8018 TryConsumeToken(Expected: tok::kw_static, Loc&: StaticLoc);
8019
8020 // If there is a type-qualifier-list, read it now.
8021 // Type qualifiers in an array subscript are a C99 feature.
8022 DeclSpec DS(AttrFactory);
8023 ParseTypeQualifierListOpt(DS, AttrReqs: AR_CXX11AttributesParsed);
8024
8025 // If we haven't already read 'static', check to see if there is one after the
8026 // type-qualifier-list.
8027 if (!StaticLoc.isValid())
8028 TryConsumeToken(Expected: tok::kw_static, Loc&: StaticLoc);
8029
8030 // Handle "direct-declarator [ type-qual-list[opt] * ]".
8031 bool isStar = false;
8032 ExprResult NumElements;
8033
8034 // Handle the case where we have '[*]' as the array size. However, a leading
8035 // star could be the start of an expression, for example 'X[*p + 4]'. Verify
8036 // the token after the star is a ']'. Since stars in arrays are
8037 // infrequent, use of lookahead is not costly here.
8038 if (Tok.is(K: tok::star) && GetLookAheadToken(N: 1).is(K: tok::r_square)) {
8039 ConsumeToken(); // Eat the '*'.
8040
8041 if (StaticLoc.isValid()) {
8042 Diag(Loc: StaticLoc, DiagID: diag::err_unspecified_vla_size_with_static);
8043 StaticLoc = SourceLocation(); // Drop the static.
8044 }
8045 isStar = true;
8046 } else if (Tok.isNot(K: tok::r_square)) {
8047 // Note, in C89, this production uses the constant-expr production instead
8048 // of assignment-expr. The only difference is that assignment-expr allows
8049 // things like '=' and '*='. Sema rejects these in C89 mode because they
8050 // are not i-c-e's, so we don't need to distinguish between the two here.
8051
8052 // Parse the constant-expression or assignment-expression now (depending
8053 // on dialect).
8054 if (getLangOpts().CPlusPlus) {
8055 NumElements = ParseArrayBoundExpression();
8056 } else {
8057 EnterExpressionEvaluationContext Unevaluated(
8058 Actions, Sema::ExpressionEvaluationContext::ConstantEvaluated);
8059 NumElements = ParseAssignmentExpression();
8060 }
8061 } else {
8062 if (StaticLoc.isValid()) {
8063 Diag(Loc: StaticLoc, DiagID: diag::err_unspecified_size_with_static);
8064 StaticLoc = SourceLocation(); // Drop the static.
8065 }
8066 }
8067
8068 // If there was an error parsing the assignment-expression, recover.
8069 if (NumElements.isInvalid()) {
8070 D.setInvalidType(true);
8071 // If the expression was invalid, skip it.
8072 SkipUntil(T: tok::r_square, Flags: StopAtSemi);
8073 return;
8074 }
8075
8076 T.consumeClose();
8077
8078 MaybeParseCXX11Attributes(Attrs&: DS.getAttributes());
8079
8080 // Remember that we parsed a array type, and remember its features.
8081 D.AddTypeInfo(
8082 TI: DeclaratorChunk::getArray(TypeQuals: DS.getTypeQualifiers(), isStatic: StaticLoc.isValid(),
8083 isStar, NumElts: NumElements.get(), LBLoc: T.getOpenLocation(),
8084 RBLoc: T.getCloseLocation()),
8085 attrs: std::move(DS.getAttributes()), EndLoc: T.getCloseLocation());
8086}
8087
8088void Parser::ParseMisplacedBracketDeclarator(Declarator &D) {
8089 assert(Tok.is(tok::l_square) && "Missing opening bracket");
8090 assert(!D.mayOmitIdentifier() && "Declarator cannot omit identifier");
8091
8092 SourceLocation StartBracketLoc = Tok.getLocation();
8093 Declarator TempDeclarator(D.getDeclSpec(), ParsedAttributesView::none(),
8094 D.getContext());
8095
8096 while (Tok.is(K: tok::l_square)) {
8097 ParseBracketDeclarator(D&: TempDeclarator);
8098 }
8099
8100 // Stuff the location of the start of the brackets into the Declarator.
8101 // The diagnostics from ParseDirectDeclarator will make more sense if
8102 // they use this location instead.
8103 if (Tok.is(K: tok::semi))
8104 D.getName().EndLocation = StartBracketLoc;
8105
8106 SourceLocation SuggestParenLoc = Tok.getLocation();
8107
8108 // Now that the brackets are removed, try parsing the declarator again.
8109 ParseDeclaratorInternal(D, DirectDeclParser: &Parser::ParseDirectDeclarator);
8110
8111 // Something went wrong parsing the brackets, in which case,
8112 // ParseBracketDeclarator has emitted an error, and we don't need to emit
8113 // one here.
8114 if (TempDeclarator.getNumTypeObjects() == 0)
8115 return;
8116
8117 // Determine if parens will need to be suggested in the diagnostic.
8118 bool NeedParens = false;
8119 if (D.getNumTypeObjects() != 0) {
8120 switch (D.getTypeObject(i: D.getNumTypeObjects() - 1).Kind) {
8121 case DeclaratorChunk::Pointer:
8122 case DeclaratorChunk::Reference:
8123 case DeclaratorChunk::BlockPointer:
8124 case DeclaratorChunk::MemberPointer:
8125 case DeclaratorChunk::Pipe:
8126 NeedParens = true;
8127 break;
8128 case DeclaratorChunk::Array:
8129 case DeclaratorChunk::Function:
8130 case DeclaratorChunk::Paren:
8131 break;
8132 }
8133 }
8134
8135 if (NeedParens) {
8136 // Create a DeclaratorChunk for the inserted parens.
8137 SourceLocation EndLoc = PP.getLocForEndOfToken(Loc: D.getEndLoc());
8138 D.AddTypeInfo(TI: DeclaratorChunk::getParen(LParenLoc: SuggestParenLoc, RParenLoc: EndLoc),
8139 EndLoc: SourceLocation());
8140 }
8141
8142 // Adding back the bracket info to the end of the Declarator.
8143 for (unsigned i = 0, e = TempDeclarator.getNumTypeObjects(); i < e; ++i) {
8144 const DeclaratorChunk &Chunk = TempDeclarator.getTypeObject(i);
8145 D.AddTypeInfo(TI: Chunk, OtherPool&: TempDeclarator.getAttributePool(), EndLoc: SourceLocation());
8146 }
8147
8148 // The missing name would have been diagnosed in ParseDirectDeclarator.
8149 // If parentheses are required, always suggest them.
8150 if (!D.hasName() && !NeedParens)
8151 return;
8152
8153 SourceLocation EndBracketLoc = TempDeclarator.getEndLoc();
8154
8155 // Generate the move bracket error message.
8156 SourceRange BracketRange(StartBracketLoc, EndBracketLoc);
8157 SourceLocation EndLoc = PP.getLocForEndOfToken(Loc: D.getEndLoc());
8158
8159 if (NeedParens) {
8160 Diag(Loc: EndLoc, DiagID: diag::err_brackets_go_after_unqualified_id)
8161 << getLangOpts().CPlusPlus
8162 << FixItHint::CreateInsertion(InsertionLoc: SuggestParenLoc, Code: "(")
8163 << FixItHint::CreateInsertion(InsertionLoc: EndLoc, Code: ")")
8164 << FixItHint::CreateInsertionFromRange(
8165 InsertionLoc: EndLoc, FromRange: CharSourceRange(BracketRange, true))
8166 << FixItHint::CreateRemoval(RemoveRange: BracketRange);
8167 } else {
8168 Diag(Loc: EndLoc, DiagID: diag::err_brackets_go_after_unqualified_id)
8169 << getLangOpts().CPlusPlus
8170 << FixItHint::CreateInsertionFromRange(
8171 InsertionLoc: EndLoc, FromRange: CharSourceRange(BracketRange, true))
8172 << FixItHint::CreateRemoval(RemoveRange: BracketRange);
8173 }
8174}
8175
8176void Parser::ParseTypeofSpecifier(DeclSpec &DS) {
8177 assert(Tok.isOneOf(tok::kw_typeof, tok::kw_typeof_unqual) &&
8178 "Not a typeof specifier");
8179
8180 bool IsUnqual = Tok.is(K: tok::kw_typeof_unqual);
8181 const IdentifierInfo *II = Tok.getIdentifierInfo();
8182 if (getLangOpts().C23 && !II->getName().starts_with(Prefix: "__"))
8183 Diag(Loc: Tok.getLocation(), DiagID: diag::warn_c23_compat_keyword) << Tok.getName();
8184
8185 Token OpTok = Tok;
8186 SourceLocation StartLoc = ConsumeToken();
8187 bool HasParens = Tok.is(K: tok::l_paren);
8188
8189 EnterExpressionEvaluationContext Unevaluated(
8190 Actions, Sema::ExpressionEvaluationContext::Unevaluated,
8191 Sema::ReuseLambdaContextDecl);
8192
8193 bool isCastExpr;
8194 ParsedType CastTy;
8195 SourceRange CastRange;
8196 ExprResult Operand =
8197 ParseExprAfterUnaryExprOrTypeTrait(OpTok, isCastExpr, CastTy, CastRange);
8198 if (HasParens)
8199 DS.setTypeArgumentRange(CastRange);
8200
8201 if (CastRange.getEnd().isInvalid())
8202 // FIXME: Not accurate, the range gets one token more than it should.
8203 DS.SetRangeEnd(Tok.getLocation());
8204 else
8205 DS.SetRangeEnd(CastRange.getEnd());
8206
8207 if (isCastExpr) {
8208 if (!CastTy) {
8209 DS.SetTypeSpecError();
8210 return;
8211 }
8212
8213 const char *PrevSpec = nullptr;
8214 unsigned DiagID;
8215 // Check for duplicate type specifiers (e.g. "int typeof(int)").
8216 if (DS.SetTypeSpecType(T: IsUnqual ? DeclSpec::TST_typeof_unqualType
8217 : DeclSpec::TST_typeofType,
8218 Loc: StartLoc, PrevSpec,
8219 DiagID, Rep: CastTy,
8220 Policy: Actions.getASTContext().getPrintingPolicy()))
8221 Diag(Loc: StartLoc, DiagID) << PrevSpec;
8222 return;
8223 }
8224
8225 // If we get here, the operand to the typeof was an expression.
8226 if (Operand.isInvalid()) {
8227 DS.SetTypeSpecError();
8228 return;
8229 }
8230
8231 // We might need to transform the operand if it is potentially evaluated.
8232 Operand = Actions.HandleExprEvaluationContextForTypeof(E: Operand.get());
8233 if (Operand.isInvalid()) {
8234 DS.SetTypeSpecError();
8235 return;
8236 }
8237
8238 const char *PrevSpec = nullptr;
8239 unsigned DiagID;
8240 // Check for duplicate type specifiers (e.g. "int typeof(int)").
8241 if (DS.SetTypeSpecType(T: IsUnqual ? DeclSpec::TST_typeof_unqualExpr
8242 : DeclSpec::TST_typeofExpr,
8243 Loc: StartLoc, PrevSpec,
8244 DiagID, Rep: Operand.get(),
8245 policy: Actions.getASTContext().getPrintingPolicy()))
8246 Diag(Loc: StartLoc, DiagID) << PrevSpec;
8247}
8248
8249void Parser::ParseAtomicSpecifier(DeclSpec &DS) {
8250 assert(Tok.is(tok::kw__Atomic) && NextToken().is(tok::l_paren) &&
8251 "Not an atomic specifier");
8252
8253 SourceLocation StartLoc = ConsumeToken();
8254 BalancedDelimiterTracker T(*this, tok::l_paren);
8255 if (T.consumeOpen())
8256 return;
8257
8258 TypeResult Result = ParseTypeName();
8259 if (Result.isInvalid()) {
8260 SkipUntil(T: tok::r_paren, Flags: StopAtSemi);
8261 return;
8262 }
8263
8264 // Match the ')'
8265 T.consumeClose();
8266
8267 if (T.getCloseLocation().isInvalid())
8268 return;
8269
8270 DS.setTypeArgumentRange(T.getRange());
8271 DS.SetRangeEnd(T.getCloseLocation());
8272
8273 const char *PrevSpec = nullptr;
8274 unsigned DiagID;
8275 if (DS.SetTypeSpecType(T: DeclSpec::TST_atomic, Loc: StartLoc, PrevSpec,
8276 DiagID, Rep: Result.get(),
8277 Policy: Actions.getASTContext().getPrintingPolicy()))
8278 Diag(Loc: StartLoc, DiagID) << PrevSpec;
8279}
8280
8281bool Parser::TryAltiVecVectorTokenOutOfLine() {
8282 Token Next = NextToken();
8283 switch (Next.getKind()) {
8284 default: return false;
8285 case tok::kw_short:
8286 case tok::kw_long:
8287 case tok::kw_signed:
8288 case tok::kw_unsigned:
8289 case tok::kw_void:
8290 case tok::kw_char:
8291 case tok::kw_int:
8292 case tok::kw_float:
8293 case tok::kw_double:
8294 case tok::kw_bool:
8295 case tok::kw__Bool:
8296 case tok::kw___bool:
8297 case tok::kw___pixel:
8298 Tok.setKind(tok::kw___vector);
8299 return true;
8300 case tok::identifier:
8301 if (Next.getIdentifierInfo() == Ident_pixel) {
8302 Tok.setKind(tok::kw___vector);
8303 return true;
8304 }
8305 if (Next.getIdentifierInfo() == Ident_bool ||
8306 Next.getIdentifierInfo() == Ident_Bool) {
8307 Tok.setKind(tok::kw___vector);
8308 return true;
8309 }
8310 return false;
8311 }
8312}
8313
8314bool Parser::TryAltiVecTokenOutOfLine(DeclSpec &DS, SourceLocation Loc,
8315 const char *&PrevSpec, unsigned &DiagID,
8316 bool &isInvalid) {
8317 const PrintingPolicy &Policy = Actions.getASTContext().getPrintingPolicy();
8318 if (Tok.getIdentifierInfo() == Ident_vector) {
8319 Token Next = NextToken();
8320 switch (Next.getKind()) {
8321 case tok::kw_short:
8322 case tok::kw_long:
8323 case tok::kw_signed:
8324 case tok::kw_unsigned:
8325 case tok::kw_void:
8326 case tok::kw_char:
8327 case tok::kw_int:
8328 case tok::kw_float:
8329 case tok::kw_double:
8330 case tok::kw_bool:
8331 case tok::kw__Bool:
8332 case tok::kw___bool:
8333 case tok::kw___pixel:
8334 isInvalid = DS.SetTypeAltiVecVector(isAltiVecVector: true, Loc, PrevSpec, DiagID, Policy);
8335 return true;
8336 case tok::identifier:
8337 if (Next.getIdentifierInfo() == Ident_pixel) {
8338 isInvalid = DS.SetTypeAltiVecVector(isAltiVecVector: true, Loc, PrevSpec, DiagID,Policy);
8339 return true;
8340 }
8341 if (Next.getIdentifierInfo() == Ident_bool ||
8342 Next.getIdentifierInfo() == Ident_Bool) {
8343 isInvalid =
8344 DS.SetTypeAltiVecVector(isAltiVecVector: true, Loc, PrevSpec, DiagID, Policy);
8345 return true;
8346 }
8347 break;
8348 default:
8349 break;
8350 }
8351 } else if ((Tok.getIdentifierInfo() == Ident_pixel) &&
8352 DS.isTypeAltiVecVector()) {
8353 isInvalid = DS.SetTypeAltiVecPixel(isAltiVecPixel: true, Loc, PrevSpec, DiagID, Policy);
8354 return true;
8355 } else if ((Tok.getIdentifierInfo() == Ident_bool) &&
8356 DS.isTypeAltiVecVector()) {
8357 isInvalid = DS.SetTypeAltiVecBool(isAltiVecBool: true, Loc, PrevSpec, DiagID, Policy);
8358 return true;
8359 }
8360 return false;
8361}
8362
8363TypeResult Parser::ParseTypeFromString(StringRef TypeStr, StringRef Context,
8364 SourceLocation IncludeLoc) {
8365 // Consume (unexpanded) tokens up to the end-of-directive.
8366 SmallVector<Token, 4> Tokens;
8367 {
8368 // Create a new buffer from which we will parse the type.
8369 auto &SourceMgr = PP.getSourceManager();
8370 FileID FID = SourceMgr.createFileID(
8371 Buffer: llvm::MemoryBuffer::getMemBufferCopy(InputData: TypeStr, BufferName: Context), FileCharacter: SrcMgr::C_User,
8372 LoadedID: 0, LoadedOffset: 0, IncludeLoc);
8373
8374 // Form a new lexer that references the buffer.
8375 Lexer L(FID, SourceMgr.getBufferOrFake(FID), PP);
8376 L.setParsingPreprocessorDirective(true);
8377
8378 // Lex the tokens from that buffer.
8379 Token Tok;
8380 do {
8381 L.Lex(Result&: Tok);
8382 Tokens.push_back(Elt: Tok);
8383 } while (Tok.isNot(K: tok::eod));
8384 }
8385
8386 // Replace the "eod" token with an "eof" token identifying the end of
8387 // the provided string.
8388 Token &EndToken = Tokens.back();
8389 EndToken = Token::createEof(Loc: Tok.getLocation(), Data: TypeStr.data());
8390
8391 // Add the current token back.
8392 Tokens.push_back(Elt: Tok);
8393
8394 // Enter the tokens into the token stream.
8395 PP.EnterTokenStream(Toks: Tokens, /*DisableMacroExpansion=*/false,
8396 /*IsReinject=*/false);
8397
8398 // Consume the current token so that we'll start parsing the tokens we
8399 // added to the stream.
8400 ConsumeAnyToken();
8401
8402 // Enter a new scope.
8403 ParseScope LocalScope(this, 0);
8404
8405 // Parse the type.
8406 TypeResult Result = ParseTypeName(Range: nullptr);
8407
8408 // Check if we parsed the whole thing.
8409 if (Result.isUsable() &&
8410 (Tok.isNot(K: tok::eof) || Tok.getEofData() != TypeStr.data())) {
8411 Diag(Loc: Tok.getLocation(), DiagID: diag::err_type_unparsed);
8412 }
8413
8414 // There could be leftover tokens (e.g. because of an error).
8415 // Skip through until we reach the 'end of directive' token.
8416 while (Tok.isNot(K: tok::eof))
8417 ConsumeAnyToken();
8418
8419 // Consume the end token.
8420 if (Tok.is(K: tok::eof) && Tok.getEofData() == TypeStr.data())
8421 ConsumeAnyToken();
8422 return Result;
8423}
8424
8425void Parser::DiagnoseBitIntUse(const Token &Tok) {
8426 // If the token is for _ExtInt, diagnose it as being deprecated. Otherwise,
8427 // the token is about _BitInt and gets (potentially) diagnosed as use of an
8428 // extension.
8429 assert(Tok.isOneOf(tok::kw__ExtInt, tok::kw__BitInt) &&
8430 "expected either an _ExtInt or _BitInt token!");
8431
8432 SourceLocation Loc = Tok.getLocation();
8433 if (Tok.is(K: tok::kw__ExtInt)) {
8434 Diag(Loc, DiagID: diag::warn_ext_int_deprecated)
8435 << FixItHint::CreateReplacement(RemoveRange: Loc, Code: "_BitInt");
8436 } else {
8437 // In C23 mode, diagnose that the use is not compatible with pre-C23 modes.
8438 // Otherwise, diagnose that the use is a Clang extension.
8439 if (getLangOpts().C23)
8440 Diag(Loc, DiagID: diag::warn_c23_compat_keyword) << Tok.getName();
8441 else
8442 Diag(Loc, DiagID: diag::ext_bit_int) << getLangOpts().CPlusPlus;
8443 }
8444}
8445