26 #include "llvm/ADT/Optional.h" 27 #include "llvm/ADT/SmallSet.h" 28 #include "llvm/ADT/SmallString.h" 29 #include "llvm/ADT/StringSwitch.h" 31 using namespace clang;
47 DeclSpecContext DSC = getDeclSpecContextFromDeclaratorContext(Context);
48 if (DSC == DeclSpecContext::DSC_normal)
49 DSC = DeclSpecContext::DSC_type_specifier;
55 ParseSpecifierQualifierList(DS, AS, DSC);
61 ParseDeclarator(DeclaratorInfo);
73 if (Name.size() >= 4 && Name.startswith(
"__") && Name.endswith(
"__"))
74 return Name.drop_front(2).drop_back(2);
81 #define CLANG_ATTR_LATE_PARSED_LIST 83 #include "clang/Parse/AttrParserStringSwitches.inc" 85 #undef CLANG_ATTR_LATE_PARSED_LIST 98 bool AttrStartIsInMacro =
100 bool AttrEndIsInMacro =
102 return AttrStartIsInMacro && AttrEndIsInMacro;
148 LateParsedAttrList *LateAttrs,
150 assert(Tok.
is(tok::kw___attribute) &&
"Not a GNU attribute list!");
152 while (Tok.
is(tok::kw___attribute)) {
154 unsigned OldNumAttrs = attrs.
size();
155 unsigned OldNumLateAttrs = LateAttrs ? LateAttrs->size() : 0;
157 if (ExpectAndConsume(tok::l_paren, diag::err_expected_lparen_after,
162 if (ExpectAndConsume(tok::l_paren, diag::err_expected_lparen_after,
"(")) {
181 if (Tok.
isNot(tok::l_paren)) {
182 attrs.
addNew(AttrName, AttrNameLoc,
nullptr, AttrNameLoc,
nullptr, 0,
189 ParseGNUAttributeArgs(AttrName, AttrNameLoc, attrs, endLoc,
nullptr,
195 LateParsedAttribute *LA =
196 new LateParsedAttribute(
this, *AttrName, AttrNameLoc);
197 LateAttrs->push_back(LA);
201 if (!ClassStack.empty() && !LateAttrs->parseSoon())
202 getCurrentClass().LateParsedDeclarations.push_back(LA);
206 LA->Toks.push_back(Tok);
209 ConsumeAndStoreUntil(tok::r_paren, LA->Toks,
true);
214 LA->Toks.push_back(Eof);
215 }
while (Tok.
is(tok::comma));
217 if (ExpectAndConsume(tok::r_paren))
220 if (ExpectAndConsume(tok::r_paren))
231 StringRef FoundName =
235 for (
unsigned i = OldNumAttrs; i < attrs.
size(); ++i)
236 attrs[i].setMacroIdentifier(MacroII, ExpansionRange.
getBegin());
239 for (
unsigned i = OldNumLateAttrs; i < LateAttrs->size(); ++i)
240 (*LateAttrs)[i]->MacroII = MacroII;
248 #define CLANG_ATTR_IDENTIFIER_ARG_LIST 250 #include "clang/Parse/AttrParserStringSwitches.inc" 252 #undef CLANG_ATTR_IDENTIFIER_ARG_LIST 257 #define CLANG_ATTR_VARIADIC_IDENTIFIER_ARG_LIST 259 #include "clang/Parse/AttrParserStringSwitches.inc" 261 #undef CLANG_ATTR_VARIADIC_IDENTIFIER_ARG_LIST 266 #define CLANG_ATTR_THIS_ISA_IDENTIFIER_ARG_LIST 268 #include "clang/Parse/AttrParserStringSwitches.inc" 270 #undef CLANG_ATTR_THIS_ISA_IDENTIFIER_ARG_LIST 275 #define CLANG_ATTR_TYPE_ARG_LIST 277 #include "clang/Parse/AttrParserStringSwitches.inc" 279 #undef CLANG_ATTR_TYPE_ARG_LIST 285 #define CLANG_ATTR_ARG_CONTEXT_LIST 287 #include "clang/Parse/AttrParserStringSwitches.inc" 289 #undef CLANG_ATTR_ARG_CONTEXT_LIST 293 assert(Tok.
is(tok::identifier) &&
"expected an identifier");
312 if (Tok.
isNot(tok::r_paren))
324 ScopeName, ScopeLoc, T.
get(), Syntax);
327 ScopeName, ScopeLoc,
nullptr, 0, Syntax);
330 unsigned Parser::ParseAttributeArgsCommon(
341 if (ChangeKWThisToIdent && Tok.
is(tok::kw_this))
345 if (Tok.
is(tok::identifier)) {
357 IsIdentifierArg = Next.
isOneOf(tok::r_paren, tok::comma);
361 ArgExprs.push_back(ParseIdentifierLoc());
365 if (!ArgExprs.empty() ? Tok.
is(tok::comma) : Tok.
isNot(tok::r_paren)) {
367 if (!ArgExprs.empty())
373 if (ChangeKWThisToIdent && Tok.
is(tok::kw_this))
377 if (AttributeIsTypeArgAttr) {
384 TheParsedType = T.
get();
386 }
else if (Tok.
is(tok::identifier) &&
388 ArgExprs.push_back(ParseIdentifierLoc());
402 ArgExprs.push_back(ArgExpr.
get());
409 if (!ExpectAndConsume(tok::r_paren)) {
412 if (AttributeIsTypeArgAttr && !TheParsedType.
get().
isNull()) {
414 ScopeName, ScopeLoc, TheParsedType, Syntax);
417 ArgExprs.data(), ArgExprs.size(), Syntax);
424 return static_cast<unsigned>(ArgExprs.size() + !TheParsedType.
get().
isNull());
438 assert(Tok.
is(tok::l_paren) &&
"Attribute arg list not starting with '('");
443 if (AttrKind == ParsedAttr::AT_Availability) {
444 ParseAvailabilityAttribute(*AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName,
447 }
else if (AttrKind == ParsedAttr::AT_ExternalSourceSymbol) {
448 ParseExternalSourceSymbolAttribute(*AttrName, AttrNameLoc, Attrs, EndLoc,
449 ScopeName, ScopeLoc, Syntax);
451 }
else if (AttrKind == ParsedAttr::AT_ObjCBridgeRelated) {
452 ParseObjCBridgeRelatedAttribute(*AttrName, AttrNameLoc, Attrs, EndLoc,
453 ScopeName, ScopeLoc, Syntax);
455 }
else if (AttrKind == ParsedAttr::AT_TypeTagForDatatype) {
456 ParseTypeTagForDatatypeAttribute(*AttrName, AttrNameLoc, Attrs, EndLoc,
457 ScopeName, ScopeLoc, Syntax);
460 ParseAttributeWithTypeArg(*AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName,
474 for (
unsigned i = 0; i != FTI.
NumParams; ++i) {
480 ParseAttributeArgsCommon(AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName,
484 unsigned Parser::ParseClangAttributeArgs(
488 assert(Tok.
is(tok::l_paren) &&
"Attribute arg list not starting with '('");
495 return ParseAttributeArgsCommon(AttrName, AttrNameLoc, Attrs, EndLoc,
496 ScopeName, ScopeLoc, Syntax);
497 case ParsedAttr::AT_ExternalSourceSymbol:
498 ParseExternalSourceSymbolAttribute(*AttrName, AttrNameLoc, Attrs, EndLoc,
499 ScopeName, ScopeLoc, Syntax);
501 case ParsedAttr::AT_Availability:
502 ParseAvailabilityAttribute(*AttrName, AttrNameLoc, Attrs, EndLoc, ScopeName,
505 case ParsedAttr::AT_ObjCBridgeRelated:
506 ParseObjCBridgeRelatedAttribute(*AttrName, AttrNameLoc, Attrs, EndLoc,
507 ScopeName, ScopeLoc, Syntax);
509 case ParsedAttr::AT_TypeTagForDatatype:
510 ParseTypeTagForDatatypeAttribute(*AttrName, AttrNameLoc, Attrs, EndLoc,
511 ScopeName, ScopeLoc, Syntax);
514 return !Attrs.
empty() ? Attrs.
begin()->getNumArgs() : 0;
532 if (AttrName->
getName() ==
"property") {
547 bool HasInvalidAccessor =
false;
552 if (!Tok.
is(tok::identifier)) {
554 if (Tok.
is(tok::r_paren) && !HasInvalidAccessor &&
555 AccessorNames[AK_Put] ==
nullptr &&
556 AccessorNames[AK_Get] ==
nullptr) {
557 Diag(AttrNameLoc, diag::err_ms_property_no_getter_or_putter);
568 if (KindStr ==
"get") {
570 }
else if (KindStr ==
"put") {
574 }
else if (KindStr ==
"set") {
575 Diag(KindLoc, diag::err_ms_property_has_set_accessor)
582 Diag(KindLoc, diag::err_ms_property_missing_accessor_kind);
584 HasInvalidAccessor =
true;
585 goto next_property_accessor;
589 Diag(KindLoc, diag::err_ms_property_unknown_accessor);
590 HasInvalidAccessor =
true;
609 if (!Tok.
is(tok::identifier)) {
614 if (Kind == AK_Invalid) {
616 }
else if (AccessorNames[Kind] !=
nullptr) {
618 Diag(KindLoc, diag::err_ms_property_duplicate_accessor) << KindStr;
624 next_property_accessor:
630 if (Tok.
is(tok::r_paren))
633 Diag(Tok.
getLocation(), diag::err_ms_property_expected_comma_or_rparen);
638 if (!HasInvalidAccessor)
640 AccessorNames[AK_Get], AccessorNames[AK_Put],
643 return !HasInvalidAccessor;
647 ParseAttributeArgsCommon(AttrName, AttrNameLoc, Attrs,
nullptr,
nullptr,
652 if (!Attrs.
empty() && Attrs.
begin()->getMaxArgs() && !NumArgs) {
653 Diag(OpenParenLoc, diag::err_attribute_requires_arguments) << AttrName;
667 assert(
getLangOpts().DeclSpecKeyword &&
"__declspec keyword is not enabled");
668 assert(Tok.
is(tok::kw___declspec) &&
"Not a declspec!");
670 while (Tok.
is(tok::kw___declspec)) {
679 while (Tok.
isNot(tok::r_paren)) {
686 bool IsString = Tok.
getKind() == tok::string_literal;
687 if (!IsString && Tok.
getKind() != tok::identifier &&
688 Tok.
getKind() != tok::kw_restrict) {
689 Diag(Tok, diag::err_ms_declspec_type);
698 bool Invalid =
false;
699 StringRef Str = PP.
getSpelling(Tok, StrBuffer, &Invalid);
705 AttrNameLoc = ConsumeStringToken();
711 bool AttrHandled =
false;
714 if (Tok.
is(tok::l_paren))
715 AttrHandled = ParseMicrosoftDeclSpecArgs(AttrName, AttrNameLoc, Attrs);
716 else if (AttrName->
getName() ==
"property")
722 Attrs.
addNew(AttrName, AttrNameLoc,
nullptr, AttrNameLoc,
nullptr, 0,
735 case tok::kw___fastcall:
736 case tok::kw___stdcall:
737 case tok::kw___thiscall:
738 case tok::kw___regcall:
739 case tok::kw___cdecl:
740 case tok::kw___vectorcall:
741 case tok::kw___ptr64:
743 case tok::kw___ptr32:
745 case tok::kw___uptr: {
748 attrs.
addNew(AttrName, AttrNameLoc,
nullptr, AttrNameLoc,
nullptr, 0,
758 void Parser::DiagnoseAndSkipExtendedMicrosoftTypeAttributes() {
764 Diag(StartLoc, diag::warn_microsoft_qualifiers_ignored) << Range;
774 case tok::kw_volatile:
775 case tok::kw___fastcall:
776 case tok::kw___stdcall:
777 case tok::kw___thiscall:
778 case tok::kw___cdecl:
779 case tok::kw___vectorcall:
780 case tok::kw___ptr32:
781 case tok::kw___ptr64:
783 case tok::kw___unaligned:
796 while (Tok.
is(tok::kw___pascal)) {
799 attrs.
addNew(AttrName, AttrNameLoc,
nullptr, AttrNameLoc,
nullptr, 0,
806 while (Tok.
is(tok::kw___kernel)) {
809 attrs.
addNew(AttrName, AttrNameLoc,
nullptr, AttrNameLoc,
nullptr, 0,
817 Attrs.
addNew(AttrName, AttrNameLoc,
nullptr, AttrNameLoc,
nullptr, 0,
825 case tok::kw__Nonnull:
826 case tok::kw__Nullable:
827 case tok::kw__Null_unspecified: {
831 Diag(AttrNameLoc, diag::ext_nullability)
833 attrs.
addNew(AttrName, AttrNameLoc,
nullptr, AttrNameLoc,
nullptr, 0,
844 return (Separator ==
'.' || Separator ==
'_');
855 VersionTuple Parser::ParseVersionTuple(
SourceRange &Range) {
858 if (!Tok.
is(tok::numeric_constant)) {
859 Diag(Tok, diag::err_expected_version);
862 return VersionTuple();
871 const char *ThisTokBegin = &Buffer[0];
874 bool Invalid =
false;
875 unsigned ActualLength = PP.
getSpelling(Tok, ThisTokBegin, &Invalid);
877 return VersionTuple();
880 unsigned AfterMajor = 0;
882 while (AfterMajor < ActualLength &&
isDigit(ThisTokBegin[AfterMajor])) {
883 Major = Major * 10 + ThisTokBegin[AfterMajor] -
'0';
887 if (AfterMajor == 0) {
888 Diag(Tok, diag::err_expected_version);
891 return VersionTuple();
894 if (AfterMajor == ActualLength) {
899 Diag(Tok, diag::err_zero_version);
900 return VersionTuple();
903 return VersionTuple(Major);
906 const char AfterMajorSeparator = ThisTokBegin[AfterMajor];
908 || (AfterMajor + 1 == ActualLength)) {
909 Diag(Tok, diag::err_expected_version);
912 return VersionTuple();
916 unsigned AfterMinor = AfterMajor + 1;
918 while (AfterMinor < ActualLength &&
isDigit(ThisTokBegin[AfterMinor])) {
919 Minor = Minor * 10 + ThisTokBegin[AfterMinor] -
'0';
923 if (AfterMinor == ActualLength) {
927 if (Major == 0 && Minor == 0) {
928 Diag(Tok, diag::err_zero_version);
929 return VersionTuple();
932 return VersionTuple(Major, Minor);
935 const char AfterMinorSeparator = ThisTokBegin[AfterMinor];
938 Diag(Tok, diag::err_expected_version);
941 return VersionTuple();
945 if (AfterMajorSeparator != AfterMinorSeparator)
946 Diag(Tok, diag::warn_expected_consistent_version_separator);
949 unsigned AfterSubminor = AfterMinor + 1;
950 unsigned Subminor = 0;
951 while (AfterSubminor < ActualLength &&
isDigit(ThisTokBegin[AfterSubminor])) {
952 Subminor = Subminor * 10 + ThisTokBegin[AfterSubminor] -
'0';
956 if (AfterSubminor != ActualLength) {
957 Diag(Tok, diag::err_expected_version);
960 return VersionTuple();
963 return VersionTuple(Major, Minor, Subminor);
991 void Parser::ParseAvailabilityAttribute(
IdentifierInfo &Availability,
998 enum { Introduced, Deprecated, Obsoleted,
Unknown };
1005 Diag(Tok, diag::err_expected) << tok::l_paren;
1010 if (Tok.
isNot(tok::identifier)) {
1011 Diag(Tok, diag::err_availability_expected_platform);
1018 if (Ident->getName() ==
"macosx")
1022 else if (Ident->getName() ==
"macosx_app_extension")
1026 AvailabilityAttr::canonicalizePlatformName(Ident->getName()));
1030 if (ExpectAndConsume(tok::comma)) {
1037 if (!Ident_introduced) {
1051 if (Tok.
isNot(tok::identifier)) {
1052 Diag(Tok, diag::err_availability_expected_change);
1059 if (Keyword == Ident_strict) {
1061 Diag(KeywordLoc, diag::err_availability_redundant)
1064 StrictLoc = KeywordLoc;
1068 if (Keyword == Ident_unavailable) {
1069 if (UnavailableLoc.
isValid()) {
1070 Diag(KeywordLoc, diag::err_availability_redundant)
1073 UnavailableLoc = KeywordLoc;
1077 if (Keyword == Ident_deprecated && Platform->
Ident &&
1080 if (Changes[Deprecated].KeywordLoc.
isValid()) {
1081 Diag(KeywordLoc, diag::err_availability_redundant)
1088 Changes[Deprecated].
Version = VersionTuple(1);
1092 if (Tok.
isNot(tok::equal)) {
1093 Diag(Tok, diag::err_expected_after) << Keyword << tok::equal;
1098 if (Keyword == Ident_message || Keyword == Ident_replacement) {
1099 if (Tok.
isNot(tok::string_literal)) {
1100 Diag(Tok, diag::err_expected_string_literal)
1105 if (Keyword == Ident_message)
1106 MessageExpr = ParseStringLiteralExpression();
1108 ReplacementExpr = ParseStringLiteralExpression();
1111 cast_or_null<StringLiteral>(MessageExpr.
get())) {
1112 if (MessageStringLiteral->getCharByteWidth() != 1) {
1113 Diag(MessageStringLiteral->getSourceRange().getBegin(),
1114 diag::err_expected_string_literal)
1120 if (Keyword == Ident_message)
1128 if ((Keyword == Ident_introduced || Keyword == Ident_deprecated) &&
1129 Tok.
is(tok::identifier)) {
1133 if (Keyword == Ident_introduced)
1134 UnavailableLoc = KeywordLoc;
1140 VersionTuple Version = ParseVersionTuple(VersionRange);
1142 if (Version.empty()) {
1148 if (Keyword == Ident_introduced)
1150 else if (Keyword == Ident_deprecated)
1152 else if (Keyword == Ident_obsoleted)
1157 if (Index < Unknown) {
1158 if (!Changes[Index].KeywordLoc.
isInvalid()) {
1159 Diag(KeywordLoc, diag::err_availability_redundant)
1162 Changes[Index].VersionRange.
getEnd());
1166 Changes[Index].
Version = Version;
1169 Diag(KeywordLoc, diag::err_availability_unknown_change)
1170 << Keyword << VersionRange;
1184 if (UnavailableLoc.
isValid()) {
1185 bool Complained =
false;
1186 for (
unsigned Index = Introduced; Index !=
Unknown; ++Index) {
1187 if (Changes[Index].KeywordLoc.
isValid()) {
1189 Diag(UnavailableLoc, diag::warn_availability_and_unavailable)
1191 Changes[Index].VersionRange.getEnd());
1202 attrs.
addNew(&Availability,
1204 ScopeName, ScopeLoc,
1206 Changes[Introduced],
1207 Changes[Deprecated],
1209 UnavailableLoc, MessageExpr.
get(),
1210 Syntax, StrictLoc, ReplacementExpr.
get());
1226 void Parser::ParseExternalSourceSymbolAttribute(
1236 if (!Ident_language) {
1243 bool HasLanguage =
false;
1245 bool HasDefinedIn =
false;
1250 if (Tok.
isNot(tok::identifier)) {
1251 Diag(Tok, diag::err_external_source_symbol_expected_keyword);
1258 if (Keyword == Ident_generated_declaration) {
1259 if (GeneratedDeclaration) {
1260 Diag(Tok, diag::err_external_source_symbol_duplicate_clause) << Keyword;
1264 GeneratedDeclaration = ParseIdentifierLoc();
1268 if (Keyword != Ident_language && Keyword != Ident_defined_in) {
1269 Diag(Tok, diag::err_external_source_symbol_expected_keyword);
1275 if (ExpectAndConsume(tok::equal, diag::err_expected_after,
1281 bool HadLanguage = HasLanguage, HadDefinedIn = HasDefinedIn;
1282 if (Keyword == Ident_language)
1285 HasDefinedIn =
true;
1287 if (Tok.
isNot(tok::string_literal)) {
1288 Diag(Tok, diag::err_expected_string_literal)
1290 << (Keyword != Ident_language);
1294 if (Keyword == Ident_language) {
1296 Diag(KeywordLoc, diag::err_external_source_symbol_duplicate_clause)
1298 ParseStringLiteralExpression();
1301 Language = ParseStringLiteralExpression();
1303 assert(Keyword == Ident_defined_in &&
"Invalid clause keyword!");
1305 Diag(KeywordLoc, diag::err_external_source_symbol_duplicate_clause)
1307 ParseStringLiteralExpression();
1310 DefinedInExpr = ParseStringLiteralExpression();
1321 GeneratedDeclaration};
1323 ScopeName, ScopeLoc, Args, llvm::array_lengthof(Args), Syntax);
1337 void Parser::ParseObjCBridgeRelatedAttribute(
IdentifierInfo &ObjCBridgeRelated,
1347 Diag(Tok, diag::err_expected) << tok::l_paren;
1352 if (Tok.
isNot(tok::identifier)) {
1353 Diag(Tok, diag::err_objcbridge_related_expected_related_class);
1358 if (ExpectAndConsume(tok::comma)) {
1367 if (Tok.
is(tok::identifier)) {
1368 ClassMethod = ParseIdentifierLoc();
1370 Diag(Tok, diag::err_objcbridge_related_selector_name);
1376 if (Tok.
is(tok::colon))
1377 Diag(Tok, diag::err_objcbridge_related_selector_name);
1379 Diag(Tok, diag::err_expected) << tok::comma;
1387 if (Tok.
is(tok::identifier))
1388 InstanceMethod = ParseIdentifierLoc();
1389 else if (Tok.
isNot(tok::r_paren)) {
1390 Diag(Tok, diag::err_expected) << tok::r_paren;
1403 attrs.
addNew(&ObjCBridgeRelated,
1405 ScopeName, ScopeLoc,
1415 void Parser::LateParsedDeclaration::ParseLexedAttributes() {}
1417 void Parser::LateParsedClass::ParseLexedAttributes() {
1418 Self->ParseLexedAttributes(*Class);
1421 void Parser::LateParsedAttribute::ParseLexedAttributes() {
1422 Self->ParseLexedAttribute(*
this,
true,
false);
1427 void Parser::ParseLexedAttributes(ParsingClass &Class) {
1430 bool HasTemplateScope = !Class.TopLevelClass && Class.TemplateScope;
1433 if (HasTemplateScope)
1437 bool AlreadyHasClassScope = Class.TopLevelClass;
1439 ParseScope ClassScope(
this, ScopeFlags, !AlreadyHasClassScope);
1440 ParseScopeFlags ClassScopeFlags(
this, ScopeFlags, AlreadyHasClassScope);
1443 if (!AlreadyHasClassScope)
1445 Class.TagOrTemplate);
1446 if (!Class.LateParsedDeclarations.empty()) {
1447 for (
unsigned i = 0, ni = Class.LateParsedDeclarations.size(); i < ni; ++i){
1448 Class.LateParsedDeclarations[i]->ParseLexedAttributes();
1452 if (!AlreadyHasClassScope)
1454 Class.TagOrTemplate);
1458 void Parser::ParseLexedAttributeList(LateParsedAttrList &LAs,
Decl *D,
1460 assert(LAs.parseSoon() &&
1461 "Attribute list should be marked for immediate parsing.");
1462 for (
unsigned i = 0, ni = LAs.size(); i < ni; ++i) {
1465 ParseLexedAttribute(*LAs[i],
EnterScope, OnDefinition);
1476 void Parser::ParseLexedAttribute(LateParsedAttribute &LA,
1485 LA.Toks.push_back(AttrEnd);
1489 LA.Toks.push_back(Tok);
1490 PP.EnterTokenStream(LA.Toks,
true,
true);
1497 if (LA.Decls.size() > 0) {
1498 Decl *D = LA.Decls[0];
1506 if (LA.Decls.size() == 1) {
1510 if (HasTemplateScope)
1521 ParseGNUAttributeArgs(&LA.AttrName, LA.AttrNameLoc, Attrs, &endLoc,
1529 if (HasTemplateScope) {
1535 ParseGNUAttributeArgs(&LA.AttrName, LA.AttrNameLoc, Attrs, &endLoc,
1540 Diag(Tok, diag::warn_attribute_no_decl) << LA.AttrName.getName();
1543 if (OnDefinition && !Attrs.
empty() && !Attrs.
begin()->isCXX11Attribute() &&
1544 Attrs.
begin()->isKnownToGCC())
1545 Diag(Tok, diag::warn_attribute_on_function_definition)
1548 for (
unsigned i = 0, ni = LA.Decls.size(); i < ni; ++i)
1560 void Parser::ParseTypeTagForDatatypeAttribute(
IdentifierInfo &AttrName,
1567 assert(Tok.
is(tok::l_paren) &&
"Attribute arg list not starting with '('");
1572 if (Tok.
isNot(tok::identifier)) {
1573 Diag(Tok, diag::err_expected) << tok::identifier;
1579 if (ExpectAndConsume(tok::comma)) {
1591 bool LayoutCompatible =
false;
1592 bool MustBeNull =
false;
1594 if (Tok.
isNot(tok::identifier)) {
1595 Diag(Tok, diag::err_expected) << tok::identifier;
1600 if (Flag->
isStr(
"layout_compatible"))
1601 LayoutCompatible =
true;
1602 else if (Flag->
isStr(
"must_be_null"))
1605 Diag(Tok, diag::err_type_safety_unknown_flag) << Flag;
1612 if (!T.consumeClose()) {
1614 ArgumentKind, MatchingCType.
get(),
1615 LayoutCompatible, MustBeNull, Syntax);
1619 *EndLoc = T.getCloseLocation();
1630 bool Parser::DiagnoseProhibitedCXX11Attribute() {
1631 assert(Tok.
is(tok::l_square) &&
NextToken().
is(tok::l_square));
1633 switch (isCXX11AttributeSpecifier(
true)) {
1634 case CAK_NotAttributeSpecifier:
1638 case CAK_InvalidAttributeSpecifier:
1642 case CAK_AttributeSpecifier:
1647 assert(Tok.
is(tok::r_square) &&
"isCXX11AttributeSpecifier lied");
1649 Diag(BeginLoc, diag::err_attributes_not_allowed)
1653 llvm_unreachable(
"All cases handled above.");
1660 void Parser::DiagnoseMisplacedCXX11Attribute(ParsedAttributesWithRange &Attrs,
1662 assert((Tok.
is(tok::l_square) &&
NextToken().
is(tok::l_square)) ||
1663 Tok.
is(tok::kw_alignas));
1667 ParseCXX11Attributes(Attrs);
1670 Diag(Loc, diag::err_attributes_not_allowed)
1675 void Parser::DiagnoseProhibitedAttributes(
1677 if (CorrectLocation.
isValid()) {
1679 Diag(CorrectLocation, diag::err_attributes_misplaced)
1683 Diag(Range.
getBegin(), diag::err_attributes_not_allowed) << Range;
1686 void Parser::ProhibitCXX11Attributes(ParsedAttributesWithRange &Attrs,
1689 if (!AL.isCXX11Attribute() && !AL.isC2xAttribute())
1692 Diag(AL.getLoc(), diag::warn_unknown_attribute_ignored) << AL;
1694 Diag(AL.getLoc(), DiagID) << AL;
1707 void Parser::stripTypeAttributesOffDeclSpec(ParsedAttributesWithRange &Attrs,
1716 if ((AL.getKind() == ParsedAttr::AT_Aligned &&
1717 AL.isDeclspecAttribute()) ||
1718 AL.isMicrosoftAttribute())
1719 ToBeMoved.push_back(&AL);
1746 ParsedAttributesWithRange &attrs,
1753 Decl *SingleDecl =
nullptr;
1755 case tok::kw_template:
1756 case tok::kw_export:
1757 ProhibitAttributes(attrs);
1758 SingleDecl = ParseDeclarationStartingWithTemplate(Context, DeclEnd, attrs);
1760 case tok::kw_inline:
1763 ProhibitAttributes(attrs);
1765 return ParseNamespace(Context, DeclEnd, InlineLoc);
1767 return ParseSimpleDeclaration(Context, DeclEnd, attrs,
true,
nullptr,
1769 case tok::kw_namespace:
1770 ProhibitAttributes(attrs);
1771 return ParseNamespace(Context, DeclEnd);
1773 return ParseUsingDirectiveOrDeclaration(Context, ParsedTemplateInfo(),
1775 case tok::kw_static_assert:
1776 case tok::kw__Static_assert:
1777 ProhibitAttributes(attrs);
1778 SingleDecl = ParseStaticAssertDeclaration(DeclEnd);
1781 return ParseSimpleDeclaration(Context, DeclEnd, attrs,
true,
nullptr,
1813 ParsedAttributesWithRange &Attrs,
bool RequireSemi, ForRangeInit *FRI,
1818 DeclSpecContext DSContext = getDeclSpecContextFromDeclaratorContext(Context);
1819 ParseDeclarationSpecifiers(DS, ParsedTemplateInfo(),
AS_none, DSContext);
1824 DiagnoseMissingSemiAfterTagDefinition(DS,
AS_none, DSContext))
1829 if (Tok.
is(tok::semi)) {
1830 ProhibitAttributes(Attrs);
1838 Decl* decls[] = {AnonRecord, TheDecl};
1848 return ParseDeclGroup(DS, Context, &DeclEnd, FRI);
1855 case tok::annot_cxxscope:
1856 case tok::annot_template_id:
1858 case tok::code_completion:
1859 case tok::coloncolon:
1861 case tok::kw___attribute:
1862 case tok::kw_operator:
1879 case tok::identifier:
1881 case tok::code_completion:
1882 case tok::coloncolon:
1885 case tok::equalequal:
1886 case tok::kw_alignas:
1888 case tok::kw___attribute:
1907 case tok::identifier:
1930 if (Tok.
isOneOf(tok::comma, tok::l_brace, tok::kw_try)) {
1954 case tok::kw_inline:
1959 (!ParsingInObjCContainer || CurParsedObjCImpl))
1963 case tok::kw_namespace:
1968 (!ParsingInObjCContainer || CurParsedObjCImpl))
1975 ParsingInObjCContainer)
1987 case tok::annot_module_begin:
1988 case tok::annot_module_end:
1989 case tok::annot_module_include:
2006 ForRangeInit *FRI) {
2017 if (Tok.
is(tok::kw_requires))
2018 ParseTrailingRequiresClause(D);
2023 LateParsedAttrList LateParsedAttrs(
true);
2025 MaybeParseGNUAttributes(D, &LateParsedAttrs);
2030 if (Tok.
is(tok::kw__Noreturn)) {
2032 const char *PrevSpec;
2038 MaybeParseGNUAttributes(D, &LateParsedAttrs);
2039 Fixit &= Tok.
isOneOf(tok::semi, tok::l_brace, tok::kw_try);
2041 Diag(Loc, diag::err_c11_noreturn_misplaced)
2053 !isDeclarationAfterDeclarator()) {
2059 if (isStartOfFunctionDefinition(D)) {
2061 Diag(Tok, diag::err_function_declared_typedef);
2068 ParseFunctionDefinition(D, ParsedTemplateInfo(), &LateParsedAttrs);
2072 if (isDeclarationSpecifier()) {
2080 Diag(Tok, diag::err_expected_fn_body);
2085 if (Tok.
is(tok::l_brace)) {
2086 Diag(Tok, diag::err_function_definition_not_allowed);
2093 if (ParseAsmAttributesAfterDeclarator(D))
2102 if (FRI && (Tok.
is(tok::colon) || isTokIdentifier_in())) {
2103 bool IsForRangeLoop =
false;
2105 IsForRangeLoop =
true;
2108 if (Tok.
is(tok::l_brace))
2109 FRI->RangeExpr = ParseBraceInitializer();
2115 if (IsForRangeLoop) {
2119 if (
auto *VD = dyn_cast_or_null<VarDecl>(ThisDecl))
2120 VD->setObjCForDecl(
true);
2128 Decl *FirstDecl = ParseDeclarationAfterDeclaratorAndAttributes(
2129 D, ParsedTemplateInfo(), FRI);
2130 if (LateParsedAttrs.size() > 0)
2131 ParseLexedAttributeList(LateParsedAttrs, FirstDecl,
true,
false);
2134 DeclsInGroup.push_back(FirstDecl);
2142 if (Tok.
isAtStartOfLine() && ExpectSemi && !MightBeDeclarator(Context)) {
2146 Diag(CommaLoc, diag::err_expected_semi_declaration)
2163 MaybeParseGNUAttributes(D);
2167 DiagnoseAndSkipExtendedMicrosoftTypeAttributes();
2175 if (Tok.
is(tok::kw_requires))
2176 ParseTrailingRequiresClause(D);
2177 Decl *ThisDecl = ParseDeclarationAfterDeclarator(D);
2180 DeclsInGroup.push_back(ThisDecl);
2189 ? diag::err_invalid_token_after_toplevel_declarator
2190 : diag::err_expected_semi_declaration)) {
2194 if (!isDeclarationSpecifier()) {
2205 bool Parser::ParseAsmAttributesAfterDeclarator(
Declarator &D) {
2207 if (Tok.
is(tok::kw_asm)) {
2209 ExprResult AsmLabel(ParseSimpleAsm(
true, &Loc));
2219 MaybeParseGNUAttributes(D);
2245 Decl *Parser::ParseDeclarationAfterDeclarator(
2246 Declarator &D,
const ParsedTemplateInfo &TemplateInfo) {
2247 if (ParseAsmAttributesAfterDeclarator(D))
2250 return ParseDeclarationAfterDeclaratorAndAttributes(D, TemplateInfo);
2253 Decl *Parser::ParseDeclarationAfterDeclaratorAndAttributes(
2254 Declarator &D,
const ParsedTemplateInfo &TemplateInfo, ForRangeInit *FRI) {
2256 struct InitializerScopeRAII {
2262 :
P(P), D(D), ThisDecl(ThisDecl) {
2272 ~InitializerScopeRAII() { pop(); }
2287 Decl *ThisDecl =
nullptr;
2288 switch (TemplateInfo.Kind) {
2289 case ParsedTemplateInfo::NonTemplate:
2290 ThisDecl = Actions.ActOnDeclarator(
getCurScope(), D);
2293 case ParsedTemplateInfo::Template:
2294 case ParsedTemplateInfo::ExplicitSpecialization: {
2295 ThisDecl = Actions.ActOnTemplateDeclarator(
getCurScope(),
2296 *TemplateInfo.TemplateParams,
2298 if (
VarTemplateDecl *VT = dyn_cast_or_null<VarTemplateDecl>(ThisDecl))
2301 ThisDecl = VT->getTemplatedDecl();
2304 case ParsedTemplateInfo::ExplicitInstantiation: {
2305 if (Tok.
is(tok::semi)) {
2306 DeclResult ThisRes = Actions.ActOnExplicitInstantiation(
2307 getCurScope(), TemplateInfo.ExternLoc, TemplateInfo.TemplateLoc, D);
2312 ThisDecl = ThisRes.
get();
2320 Diag(Tok, diag::err_template_defn_explicit_instantiation)
2322 ThisDecl = Actions.ActOnDeclarator(
getCurScope(), D);
2325 PP.getLocForEndOfToken(TemplateInfo.TemplateLoc);
2327 diag::err_explicit_instantiation_with_definition)
2333 FakedParamLists.push_back(Actions.ActOnTemplateParameterList(
2335 LAngleLoc,
nullptr));
2338 Actions.ActOnTemplateDeclarator(
getCurScope(), FakedParamLists, D);
2347 if (isTokenEqualOrEqualTypo()) {
2350 if (Tok.
is(tok::kw_delete)) {
2356 }
else if (Tok.
is(tok::kw_default)) {
2364 InitializerScopeRAII InitScope(*
this, D, ThisDecl);
2366 if (Tok.
is(tok::code_completion)) {
2367 Actions.CodeCompleteInitializer(
getCurScope(), ThisDecl);
2368 Actions.FinalizeDeclaration(ThisDecl);
2373 PreferredType.enterVariableInit(Tok.getLocation(), ThisDecl);
2379 Diag(EqualLoc, diag::err_single_decl_assign_in_for_range)
2383 FRI->ColonLoc = EqualLoc;
2385 FRI->RangeExpr = Init;
2392 StopTokens.push_back(tok::comma);
2395 StopTokens.push_back(tok::r_paren);
2397 Actions.ActOnInitializerError(ThisDecl);
2399 Actions.AddInitializerToDecl(ThisDecl, Init.
get(),
2402 }
else if (Tok.
is(tok::l_paren)) {
2410 InitializerScopeRAII InitScope(*
this, D, ThisDecl);
2412 auto ThisVarDecl = dyn_cast_or_null<VarDecl>(ThisDecl);
2413 auto RunSignatureHelp = [&]() {
2414 QualType PreferredType = Actions.ProduceConstructorSignatureHelp(
2415 getCurScope(), ThisVarDecl->getType()->getCanonicalTypeInternal(),
2417 CalledSignatureHelp =
true;
2418 return PreferredType;
2420 auto SetPreferredType = [&] {
2421 PreferredType.enterFunctionArgument(Tok.getLocation(), RunSignatureHelp);
2424 llvm::function_ref<void()> ExpressionStarts;
2430 ExpressionStarts = SetPreferredType;
2432 if (ParseExpressionList(Exprs, CommaLocs, ExpressionStarts)) {
2433 if (ThisVarDecl && PP.isCodeCompletionReached() && !CalledSignatureHelp) {
2434 Actions.ProduceConstructorSignatureHelp(
2435 getCurScope(), ThisVarDecl->getType()->getCanonicalTypeInternal(),
2437 CalledSignatureHelp =
true;
2439 Actions.ActOnInitializerError(ThisDecl);
2445 assert(!Exprs.empty() && Exprs.size()-1 == CommaLocs.size() &&
2446 "Unexpected number of commas!");
2453 Actions.AddInitializerToDecl(ThisDecl, Initializer.
get(),
2456 }
else if (
getLangOpts().CPlusPlus11 && Tok.
is(tok::l_brace) &&
2459 Diag(Tok, diag::warn_cxx98_compat_generalized_initializer_lists);
2461 InitializerScopeRAII InitScope(*
this, D, ThisDecl);
2468 Actions.ActOnInitializerError(ThisDecl);
2470 Actions.AddInitializerToDecl(ThisDecl, Init.
get(),
true);
2473 Actions.ActOnUninitializedDecl(ThisDecl);
2476 Actions.FinalizeDeclaration(ThisDecl);
2488 DeclSpecContext DSC) {
2492 ParseDeclarationSpecifiers(DS, ParsedTemplateInfo(), AS, DSC);
2497 Diag(Tok, diag::err_expected_type);
2500 Diag(Tok, diag::err_typename_requires_specqual);
2511 diag::err_typename_invalid_storageclass);
2553 return T.
isOneOf(tok::l_square, tok::l_paren, tok::r_paren, tok::semi,
2554 tok::comma, tok::equal, tok::kw_asm, tok::l_brace,
2568 const ParsedTemplateInfo &TemplateInfo,
2570 ParsedAttributesWithRange &Attrs) {
2571 assert(Tok.
is(tok::identifier) &&
"should have identifier");
2593 if (!isTypeSpecifier(DSC) && !
getLangOpts().CPlusPlus &&
2611 AnnotateScopeToken(*SS,
false);
2620 if (
ParsedType T = Actions.ActOnMSVCUnknownTypeName(
2621 *Tok.getIdentifierInfo(), Tok.getLocation(),
2622 DSC == DeclSpecContext::DSC_template_type_arg)) {
2623 const char *PrevSpec;
2626 Actions.getASTContext().getPrintingPolicy());
2639 if (SS ==
nullptr) {
2640 const char *TagName =
nullptr, *FixitTagName =
nullptr;
2643 switch (Actions.isTagName(*Tok.getIdentifierInfo(),
getCurScope())) {
2646 TagName=
"enum" ; FixitTagName =
"enum " ; TagKind=tok::kw_enum ;
break;
2648 TagName=
"union" ; FixitTagName =
"union " ;TagKind=tok::kw_union ;
break;
2650 TagName=
"struct"; FixitTagName =
"struct ";TagKind=tok::kw_struct;
break;
2652 TagName=
"__interface"; FixitTagName =
"__interface ";
2653 TagKind=tok::kw___interface;
break;
2655 TagName=
"class" ; FixitTagName =
"class " ;TagKind=tok::kw_class ;
break;
2663 Diag(Loc, diag::err_use_of_tag_name_without_tag)
2664 << TokenName << TagName <<
getLangOpts().CPlusPlus
2667 if (Actions.LookupParsedName(R,
getCurScope(), SS)) {
2670 Diag((*I)->getLocation(), diag::note_decl_hiding_tag_type)
2671 << TokenName << TagName;
2675 if (TagKind == tok::kw_enum)
2676 ParseEnumSpecifier(Loc, DS, TemplateInfo, AS,
2677 DeclSpecContext::DSC_normal);
2679 ParseClassSpecifier(TagKind, Loc, DS, TemplateInfo, AS,
2681 DeclSpecContext::DSC_normal, Attrs);
2688 if (!isTypeSpecifier(DSC) && (!SS || DSC == DeclSpecContext::DSC_top_level ||
2689 DSC == DeclSpecContext::DSC_class)) {
2693 case tok::l_paren: {
2700 TentativeParsingAction PA(*
this);
2702 TPResult TPR = TryParseDeclarator(
false);
2705 if (TPR != TPResult::False) {
2713 if (DSC == DeclSpecContext::DSC_class ||
2714 (DSC == DeclSpecContext::DSC_top_level && SS)) {
2716 if (Actions.isCurrentClassNameTypo(II, SS)) {
2717 Diag(Loc, diag::err_constructor_bad_name)
2718 << Tok.getIdentifierInfo() << II
2720 Tok.setIdentifierInfo(II);
2738 AnnotateScopeToken(*SS,
false);
2754 Actions.DiagnoseUnknownTypeName(II, Loc,
getCurScope(), SS, T,
2760 const char *PrevSpec;
2763 Actions.getASTContext().getPrintingPolicy());
2768 }
else if (II != Tok.getIdentifierInfo()) {
2781 if (IsTemplateName) {
2783 TemplateArgList Args;
2784 ParseTemplateIdAfterTemplateName(
true, LAngle, Args, RAngle);
2798 Parser::DeclSpecContext
2801 return DeclSpecContext::DSC_class;
2803 return DeclSpecContext::DSC_top_level;
2805 return DeclSpecContext::DSC_template_param;
2808 return DeclSpecContext::DSC_template_type_arg;
2811 return DeclSpecContext::DSC_trailing;
2814 return DeclSpecContext::DSC_alias_declaration;
2815 return DeclSpecContext::DSC_normal;
2830 if (isTypeIdInParens()) {
2834 ER = Actions.ActOnUnaryExprOrTypeTraitExpr(TypeLoc,
UETT_AlignOf,
true,
2855 assert(Tok.
isOneOf(tok::kw_alignas, tok::kw__Alignas) &&
2856 "Not an alignment-specifier!");
2877 ArgExprs.push_back(ArgExpr.
get());
2878 Attrs.
addNew(KWName, KWLoc,
nullptr, KWLoc, ArgExprs.data(), 1,
2891 DeclSpecContext DSContext,
2892 LateParsedAttrList *LateAttrs) {
2895 bool EnteringContext = (DSContext == DeclSpecContext::DSC_class ||
2896 DSContext == DeclSpecContext::DSC_top_level);
2899 Tok.
isOneOf(tok::identifier, tok::coloncolon, tok::kw_decltype,
2900 tok::annot_template_id) &&
2906 bool HasScope = Tok.
is(tok::annot_cxxscope);
2912 bool MightBeDeclarator =
true;
2913 if (Tok.
isOneOf(tok::kw_typename, tok::annot_typename)) {
2915 MightBeDeclarator =
false;
2916 }
else if (AfterScope.
is(tok::annot_template_id)) {
2922 MightBeDeclarator =
false;
2923 }
else if (AfterScope.
is(tok::identifier)) {
2924 const Token &Next = HasScope ? GetLookAheadToken(2) :
NextToken();
2928 if (Next.
isOneOf(tok::star, tok::amp, tok::ampamp, tok::identifier,
2929 tok::annot_cxxscope, tok::coloncolon)) {
2931 MightBeDeclarator =
false;
2932 }
else if (HasScope) {
2937 Actions.RestoreNestedNameSpecifierAnnotation(
2938 Tok.getAnnotationValue(), Tok.getAnnotationRange(), SS);
2943 switch (Classification.
getKind()) {
2949 llvm_unreachable(
"typo correction is not possible here");
2956 MightBeDeclarator =
false;
2972 if (MightBeDeclarator)
2975 const PrintingPolicy &PPol = Actions.getASTContext().getPrintingPolicy();
2977 diag::err_expected_after)
2988 ParsedTemplateInfo NotATemplate;
2989 ParseDeclarationSpecifiers(DS, NotATemplate, AS, DSContext, LateAttrs);
2996 const char *&PrevSpec,
unsigned &DiagID,
2998 assert(!LangOpts.FixedPoint);
2999 DiagID = diag::err_fixed_point_not_enabled;
3031 void Parser::ParseDeclarationSpecifiers(
DeclSpec &DS,
3032 const ParsedTemplateInfo &TemplateInfo,
3034 DeclSpecContext DSContext,
3035 LateParsedAttrList *LateAttrs) {
3044 bool EnteringContext = (DSContext == DeclSpecContext::DSC_class ||
3045 DSContext == DeclSpecContext::DSC_top_level);
3046 bool AttrsLastTime =
false;
3047 ParsedAttributesWithRange attrs(AttrFactory);
3052 bool isStorageClass =
false;
3053 const char *PrevSpec =
nullptr;
3054 unsigned DiagID = 0;
3070 Tok.setKind(tok::identifier);
3074 switch (Tok.getKind()) {
3078 ProhibitAttributes(attrs);
3083 ProhibitCXX11Attributes(attrs, diag::err_attribute_not_type_attr);
3090 DS.
Finish(Actions, Policy);
3094 case tok::kw_alignas:
3095 if (!standardAttributesAllowed() || !isCXX11AttributeSpecifier())
3096 goto DoneWithDeclSpec;
3098 ProhibitAttributes(attrs);
3105 ParseCXX11Attributes(attrs);
3106 AttrsLastTime =
true;
3109 case tok::code_completion: {
3112 bool AllowNonIdentifiers
3118 bool AllowNestedNameSpecifiers
3119 = DSContext == DeclSpecContext::DSC_top_level ||
3123 AllowNonIdentifiers,
3124 AllowNestedNameSpecifiers);
3125 return cutOffParsing();
3130 else if (TemplateInfo.Kind != ParsedTemplateInfo::NonTemplate)
3133 else if (DSContext == DeclSpecContext::DSC_class)
3135 else if (CurParsedObjCImpl)
3138 Actions.CodeCompleteOrdinaryName(
getCurScope(), CCC);
3139 return cutOffParsing();
3142 case tok::coloncolon:
3147 goto DoneWithDeclSpec;
3149 if (Tok.
is(tok::coloncolon))
3150 goto DoneWithDeclSpec;
3153 case tok::annot_cxxscope: {
3155 goto DoneWithDeclSpec;
3158 Actions.RestoreNestedNameSpecifierAnnotation(Tok.getAnnotationValue(),
3159 Tok.getAnnotationRange(),
3164 if (Next.
is(tok::annot_template_id) &&
3177 if ((DSContext == DeclSpecContext::DSC_top_level ||
3178 DSContext == DeclSpecContext::DSC_class) &&
3181 isConstructorDeclarator(
false)) {
3186 goto DoneWithDeclSpec;
3190 ConsumeAnnotationToken();
3191 assert(Tok.
is(tok::annot_template_id) &&
3192 "ParseOptionalCXXScopeSpecifier not working");
3193 AnnotateTemplateIdTokenAsType(SS);
3197 if (Next.
is(tok::annot_template_id) &&
3200 GetLookAheadToken(2).isOneOf(tok::kw_auto, tok::kw_decltype)) {
3205 ConsumeAnnotationToken();
3209 if (Next.
is(tok::annot_typename)) {
3211 ConsumeAnnotationToken();
3212 if (Tok.getAnnotationValue()) {
3215 Tok.getAnnotationEndLoc(),
3216 PrevSpec, DiagID, T, Policy);
3223 ConsumeAnnotationToken();
3226 if (Next.
isNot(tok::identifier))
3227 goto DoneWithDeclSpec;
3232 if ((DSContext == DeclSpecContext::DSC_top_level ||
3233 DSContext == DeclSpecContext::DSC_class) &&
3236 isConstructorDeclarator(
false))
3237 goto DoneWithDeclSpec;
3244 isClassTemplateDeductionContext(DSContext));
3251 if (TryAnnotateTypeConstraint())
3252 goto DoneWithDeclSpec;
3253 if (isTypeConstraintAnnotation())
3256 ConsumeAnnotationToken();
3257 ParsedAttributesWithRange Attrs(AttrFactory);
3258 if (ParseImplicitInt(DS, &SS, TemplateInfo, AS, DSContext, Attrs)) {
3259 if (!Attrs.empty()) {
3260 AttrsLastTime =
true;
3261 attrs.takeAllFrom(Attrs);
3265 goto DoneWithDeclSpec;
3269 ConsumeAnnotationToken();
3272 DiagID, TypeRep, Policy);
3282 case tok::annot_typename: {
3286 goto DoneWithDeclSpec;
3288 if (Tok.getAnnotationValue()) {
3299 ConsumeAnnotationToken();
3304 case tok::kw___is_signed:
3315 TryKeywordIdentFallback(
true);
3318 goto DoneWithDeclSpec;
3321 case tok::kw___super:
3322 case tok::kw_decltype:
3323 case tok::identifier: {
3328 goto DoneWithDeclSpec;
3334 if (!
getLangOpts().DeclSpecKeyword && Tok.
is(tok::identifier) &&
3335 Tok.getIdentifierInfo()->getName().equals(
"__declspec")) {
3336 Diag(Loc, diag::err_ms_attributes_not_enabled);
3347 assert(
false &&
"Not a left paren?");
3360 goto DoneWithDeclSpec;
3362 if (!Tok.
is(tok::identifier))
3367 if (TryAltiVecToken(DS, Loc, PrevSpec, DiagID, isInvalid))
3373 goto DoneWithDeclSpec;
3375 if (DSContext == DeclSpecContext::DSC_objc_method_result &&
3376 isObjCInstancetype()) {
3377 ParsedType TypeRep = Actions.ActOnObjCInstanceType(Loc);
3380 DiagID, TypeRep, Policy);
3392 Actions.isCurrentClassName(*Tok.getIdentifierInfo(),
getCurScope()) &&
3393 isConstructorDeclarator(
true))
3394 goto DoneWithDeclSpec;
3397 *Tok.getIdentifierInfo(), Tok.getLocation(),
getCurScope(),
nullptr,
3398 false,
false,
nullptr,
false,
false,
3399 isClassTemplateDeductionContext(DSContext));
3404 if (TryAnnotateTypeConstraint())
3405 goto DoneWithDeclSpec;
3406 if (isTypeConstraintAnnotation())
3408 ParsedAttributesWithRange Attrs(AttrFactory);
3409 if (ParseImplicitInt(DS,
nullptr, TemplateInfo, AS, DSContext, Attrs)) {
3410 if (!Attrs.empty()) {
3411 AttrsLastTime =
true;
3412 attrs.takeAllFrom(Attrs);
3416 goto DoneWithDeclSpec;
3422 (DSContext == DeclSpecContext::DSC_class ||
3423 DSContext == DeclSpecContext::DSC_top_level) &&
3424 Actions.isDeductionGuideName(
getCurScope(), *Tok.getIdentifierInfo(),
3425 Tok.getLocation()) &&
3426 isConstructorDeclarator(
true,
3428 goto DoneWithDeclSpec;
3431 DiagID, TypeRep, Policy);
3443 TypeResult NewTypeRep = parseObjCTypeArgsAndProtocolQualifiers(
3458 case tok::annot_template_id: {
3462 Diag(Loc, diag::err_placeholder_expected_auto_or_decltype_auto)
3466 TemplateId, Policy);
3470 goto DoneWithDeclSpec;
3471 ConsumeAnnotationToken();
3477 Diag(Tok, diag::err_expected) << tok::l_paren;
3482 Diag(Tok, diag::err_placeholder_expected_auto_or_decltype_auto)
3490 ConsumedEnd = Tok.getLocation();
3494 DiagID, TemplateId, Policy);
3497 TemplateId, Policy);
3506 goto DoneWithDeclSpec;
3514 isConstructorDeclarator(
true))
3515 goto DoneWithDeclSpec;
3520 AnnotateTemplateIdTokenAsType(SS);
3525 case tok::kw___attribute:
3530 case tok::kw___declspec:
3535 case tok::kw___forceinline: {
3544 case tok::kw___unaligned:
3549 case tok::kw___sptr:
3550 case tok::kw___uptr:
3551 case tok::kw___ptr64:
3552 case tok::kw___ptr32:
3554 case tok::kw___cdecl:
3555 case tok::kw___stdcall:
3556 case tok::kw___fastcall:
3557 case tok::kw___thiscall:
3558 case tok::kw___regcall:
3559 case tok::kw___vectorcall:
3564 case tok::kw___pascal:
3569 case tok::kw___kernel:
3574 case tok::kw__Nonnull:
3575 case tok::kw__Nullable:
3576 case tok::kw__Null_unspecified:
3581 case tok::kw___kindof:
3588 case tok::kw_typedef:
3590 PrevSpec, DiagID, Policy);
3591 isStorageClass =
true;
3593 case tok::kw_extern:
3595 Diag(Tok, diag::ext_thread_before) <<
"extern";
3597 PrevSpec, DiagID, Policy);
3598 isStorageClass =
true;
3600 case tok::kw___private_extern__:
3602 Loc, PrevSpec, DiagID, Policy);
3603 isStorageClass =
true;
3605 case tok::kw_static:
3607 Diag(Tok, diag::ext_thread_before) <<
"static";
3609 PrevSpec, DiagID, Policy);
3610 isStorageClass =
true;
3614 if (isKnownToBeTypeSpecifier(GetLookAheadToken(1))) {
3616 PrevSpec, DiagID, Policy);
3618 Diag(Tok, diag::ext_auto_storage_class)
3625 PrevSpec, DiagID, Policy);
3626 isStorageClass =
true;
3628 case tok::kw___auto_type:
3629 Diag(Tok, diag::ext_auto_type);
3633 case tok::kw_register:
3635 PrevSpec, DiagID, Policy);
3636 isStorageClass =
true;
3638 case tok::kw_mutable:
3640 PrevSpec, DiagID, Policy);
3641 isStorageClass =
true;
3643 case tok::kw___thread:
3646 isStorageClass =
true;
3648 case tok::kw_thread_local:
3651 isStorageClass =
true;
3653 case tok::kw__Thread_local:
3655 Diag(Tok, diag::ext_c11_feature) << Tok.getName();
3657 Loc, PrevSpec, DiagID);
3658 isStorageClass =
true;
3662 case tok::kw_inline:
3665 case tok::kw_virtual:
3669 DiagID = diag::err_openclcxx_virtual_function;
3670 PrevSpec = Tok.getIdentifierInfo()->getNameStart();
3677 case tok::kw_explicit: {
3681 ConsumedEnd = ExplicitLoc;
3683 if (Tok.
is(tok::l_paren)) {
3684 if (
getLangOpts().CPlusPlus2a || isExplicitBool() == TPResult::True) {
3686 ? diag::warn_cxx17_compat_explicit_bool
3687 : diag::ext_explicit_bool);
3689 ExprResult ExplicitExpr(static_cast<Expr *>(
nullptr));
3693 ConsumedEnd = Tok.getLocation();
3694 if (ExplicitExpr.isUsable()) {
3695 CloseParenLoc = Tok.getLocation();
3698 Actions.ActOnExplicitBoolSpecifier(ExplicitExpr.get());
3702 Diag(Tok.getLocation(), diag::warn_cxx2a_compat_explicit_bool);
3706 ExplicitSpec, CloseParenLoc);
3709 case tok::kw__Noreturn:
3711 Diag(Tok, diag::ext_c11_feature) << Tok.getName();
3716 case tok::kw__Alignas:
3718 Diag(Tok, diag::ext_c11_feature) << Tok.getName();
3723 case tok::kw_friend:
3724 if (DSContext == DeclSpecContext::DSC_class)
3728 DiagID = diag::err_friend_invalid_in_context;
3734 case tok::kw___module_private__:
3739 case tok::kw_constexpr:
3742 case tok::kw_consteval:
3745 case tok::kw_constinit:
3762 case tok::kw___int64:
3766 case tok::kw_signed:
3770 case tok::kw_unsigned:
3774 case tok::kw__Complex:
3776 Diag(Tok, diag::ext_c99_feature) << Tok.getName();
3780 case tok::kw__Imaginary:
3782 Diag(Tok, diag::ext_c99_feature) << Tok.getName();
3798 case tok::kw___int128:
3810 case tok::kw_double:
3814 case tok::kw__Float16:
3818 case tok::kw__Accum:
3826 case tok::kw__Fract:
3841 case tok::kw___float128:
3845 case tok::kw_wchar_t:
3849 case tok::kw_char8_t:
3853 case tok::kw_char16_t:
3857 case tok::kw_char32_t:
3864 Diag(Tok, diag::ext_c99_feature) << Tok.getName();
3866 if (Tok.
is(tok::kw_bool) &&
3870 DiagID = diag::err_bool_redeclaration;
3872 Tok.setKind(tok::identifier);
3879 case tok::kw__Decimal32:
3883 case tok::kw__Decimal64:
3887 case tok::kw__Decimal128:
3891 case tok::kw___vector:
3894 case tok::kw___pixel:
3897 case tok::kw___bool:
3905 Tok.getIdentifierInfo()->revertTokenIDToIdentifier();
3906 goto DoneWithDeclSpec;
3908 isInvalid = DS.
SetTypePipe(
true, Loc, PrevSpec, DiagID, Policy);
3910 #define GENERIC_IMAGE_TYPE(ImgType, Id) \ 3911 case tok::kw_##ImgType##_t: \ 3912 isInvalid = DS.SetTypeSpecType(DeclSpec::TST_##ImgType##_t, Loc, PrevSpec, \ 3915 #include "clang/Basic/OpenCLImageTypes.def" 3916 case tok::kw___unknown_anytype:
3918 PrevSpec, DiagID, Policy);
3923 case tok::kw_struct:
3924 case tok::kw___interface:
3925 case tok::kw_union: {
3932 ParsedAttributesWithRange Attributes(AttrFactory);
3933 ParseClassSpecifier(Kind, Loc, DS, TemplateInfo, AS,
3934 EnteringContext, DSContext, Attributes);
3938 if (!Attributes.empty()) {
3939 AttrsLastTime =
true;
3940 attrs.takeAllFrom(Attributes);
3948 ParseEnumSpecifier(Loc, DS, TemplateInfo, AS, DSContext);
3956 case tok::kw_volatile:
3960 case tok::kw_restrict:
3966 case tok::kw_typename:
3969 goto DoneWithDeclSpec;
3971 if (!Tok.
is(tok::kw_typename))
3976 case tok::kw_typeof:
3977 ParseTypeofSpecifier(DS);
3980 case tok::annot_decltype:
3981 ParseDecltypeSpecifier(DS);
3984 case tok::annot_pragma_pack:
3988 case tok::annot_pragma_ms_pragma:
3989 HandlePragmaMSPragma();
3992 case tok::annot_pragma_ms_vtordisp:
3993 HandlePragmaMSVtorDisp();
3996 case tok::annot_pragma_ms_pointers_to_members:
3997 HandlePragmaMSPointersToMembers();
4000 case tok::kw___underlying_type:
4001 ParseUnderlyingTypeSpecifier(DS);
4004 case tok::kw__Atomic:
4010 Diag(Tok, diag::ext_c11_feature) << Tok.getName();
4013 ParseAtomicSpecifier(DS);
4021 case tok::kw___generic:
4024 if (Actions.getLangOpts().OpenCLVersion < 200 &&
4025 !Actions.getLangOpts().OpenCLCPlusPlus) {
4026 DiagID = diag::err_opencl_unknown_type_specifier;
4027 PrevSpec = Tok.getIdentifierInfo()->getNameStart();
4032 case tok::kw_private:
4036 goto DoneWithDeclSpec;
4038 case tok::kw___private:
4039 case tok::kw___global:
4040 case tok::kw___local:
4041 case tok::kw___constant:
4043 case tok::kw___read_only:
4044 case tok::kw___write_only:
4045 case tok::kw___read_write:
4054 goto DoneWithDeclSpec;
4061 PrevSpec, DiagID, Type.
get(),
4062 Actions.getASTContext().getPrintingPolicy()))
4063 Diag(StartLoc, DiagID) << PrevSpec;
4079 assert(PrevSpec &&
"Method did not return previous specifier!");
4082 if (DiagID == diag::ext_duplicate_declspec ||
4083 DiagID == diag::ext_warn_duplicate_declspec ||
4084 DiagID == diag::err_duplicate_declspec)
4085 Diag(Loc, DiagID) << PrevSpec
4088 else if (DiagID == diag::err_opencl_unknown_type_specifier) {
4091 << PrevSpec << isStorageClass;
4093 Diag(Loc, DiagID) << PrevSpec;
4096 if (DiagID != diag::err_bool_redeclaration && ConsumedEnd.
isInvalid())
4100 AttrsLastTime =
false;
4125 void Parser::ParseStructDeclaration(
4129 if (Tok.
is(tok::kw___extension__)) {
4133 return ParseStructDeclaration(DS, FieldsCallback);
4137 ParsedAttributesWithRange Attrs(AttrFactory);
4138 MaybeParseCXX11Attributes(Attrs);
4142 ParseSpecifierQualifierList(DS);
4146 if (Tok.
is(tok::semi)) {
4150 assert(!AnonRecord &&
"Did not expect anonymous struct or union here");
4156 bool FirstDeclarator =
true;
4163 if (!FirstDeclarator)
4164 MaybeParseGNUAttributes(DeclaratorInfo.
D);
4168 if (Tok.
isNot(tok::colon)) {
4171 ParseDeclarator(DeclaratorInfo.
D);
4184 MaybeParseGNUAttributes(DeclaratorInfo.
D);
4187 FieldsCallback(DeclaratorInfo);
4194 FirstDeclarator =
false;
4211 "parsing struct/union body");
4219 Actions.ActOnTagStartDefinition(
getCurScope(), TagDecl);
4224 while (!tryParseMisplacedModuleImport() && Tok.
isNot(tok::r_brace) &&
4229 if (Tok.
is(tok::semi)) {
4230 ConsumeExtraSemi(InsideStruct,
TagType);
4235 if (Tok.
is(tok::kw__Static_assert)) {
4237 ParseStaticAssertDeclaration(DeclEnd);
4241 if (Tok.
is(tok::annot_pragma_pack)) {
4246 if (Tok.
is(tok::annot_pragma_align)) {
4247 HandlePragmaAlign();
4251 if (Tok.
is(tok::annot_pragma_openmp)) {
4254 ParsedAttributesWithRange Attrs(AttrFactory);
4255 (void)ParseOpenMPDeclarativeDirectiveWithExtDecl(AS, Attrs);
4260 Diag(Tok.getLocation(), diag::err_pragma_misplaced_in_decl)
4262 TagType, Actions.getASTContext().getPrintingPolicy());
4263 ConsumeAnnotationToken();
4267 if (!Tok.
is(tok::at)) {
4273 FD.D, FD.BitfieldSize);
4274 FieldDecls.push_back(Field);
4280 ParseStructDeclaration(DS, CFieldCallback);
4284 Diag(Tok, diag::err_unexpected_at);
4289 ExpectAndConsume(tok::l_paren);
4290 if (!Tok.
is(tok::identifier)) {
4291 Diag(Tok, diag::err_expected) << tok::identifier;
4296 Actions.ActOnDefs(
getCurScope(), TagDecl, Tok.getLocation(),
4297 Tok.getIdentifierInfo(), Fields);
4298 FieldDecls.insert(FieldDecls.end(), Fields.begin(), Fields.end());
4300 ExpectAndConsume(tok::r_paren);
4306 if (Tok.
is(tok::r_brace)) {
4307 ExpectAndConsume(tok::semi, diag::ext_expected_semi_decl_list);
4311 ExpectAndConsume(tok::semi, diag::err_expected_semi_decl_list);
4322 MaybeParseGNUAttributes(attrs);
4324 Actions.ActOnFields(
getCurScope(), RecordLoc, TagDecl, FieldDecls,
4361 const ParsedTemplateInfo &TemplateInfo,
4364 if (Tok.
is(tok::code_completion)) {
4367 return cutOffParsing();
4371 ParsedAttributesWithRange attrs(AttrFactory);
4372 MaybeParseGNUAttributes(attrs);
4373 MaybeParseCXX11Attributes(attrs);
4374 MaybeParseMicrosoftDeclSpecs(attrs);
4377 bool IsScopedUsingClassTag =
false;
4380 if (Tok.
isOneOf(tok::kw_class, tok::kw_struct)) {
4382 : diag::ext_scoped_enum);
4383 IsScopedUsingClassTag = Tok.
is(tok::kw_class);
4388 ProhibitAttributes(attrs);
4391 MaybeParseGNUAttributes(attrs);
4392 MaybeParseCXX11Attributes(attrs);
4393 MaybeParseMicrosoftDeclSpecs(attrs);
4402 bool shouldDelayDiagsInTag =
4403 (TemplateInfo.Kind == ParsedTemplateInfo::ExplicitInstantiation ||
4404 TemplateInfo.Kind == ParsedTemplateInfo::ExplicitSpecialization);
4408 bool AllowDeclaration = DSC != DeclSpecContext::DSC_trailing;
4417 if (ParseOptionalCXXScopeSpecifier(Spec,
nullptr,
4421 if (Spec.
isSet() && Tok.
isNot(tok::identifier)) {
4422 Diag(Tok, diag::err_expected) << tok::identifier;
4423 if (Tok.
isNot(tok::l_brace)) {
4435 if (Tok.
isNot(tok::identifier) && Tok.
isNot(tok::l_brace) &&
4436 !(AllowDeclaration && Tok.
is(tok::colon))) {
4437 Diag(Tok, diag::err_expected_either) << tok::identifier << tok::l_brace;
4447 if (Tok.
is(tok::identifier)) {
4448 Name = Tok.getIdentifierInfo();
4452 if (!Name && ScopedEnumKWLoc.
isValid()) {
4455 Diag(Tok, diag::err_scoped_enum_missing_identifier);
4457 IsScopedUsingClassTag =
false;
4462 if (shouldDelayDiagsInTag)
4463 diagsFromTag.
done();
4469 if (AllowDeclaration && Tok.
is(tok::colon)) {
4470 bool PossibleBitfield =
false;
4471 if (CanBeBitfield) {
4484 if (TPR == TPResult::True)
4485 PossibleBitfield =
true;
4490 else if (TPR == TPResult::False &&
4491 GetLookAheadToken(2).
getKind() == tok::semi) {
4498 TentativeParsingAction TPA(*
this);
4510 isCXXDeclarationSpecifier(TPResult::True) != TPResult::True) ||
4513 PossibleBitfield =
true;
4525 if (!PossibleBitfield) {
4531 Diag(StartLoc, diag::warn_cxx98_compat_enum_fixed_underlying_type);
4533 Diag(StartLoc, diag::ext_cxx11_enum_fixed_underlying_type);
4535 Diag(StartLoc, diag::ext_ms_c_enum_fixed_underlying_type);
4537 Diag(StartLoc, diag::ext_clang_c_enum_fixed_underlying_type);
4553 if (!AllowDeclaration) {
4555 }
else if (Tok.
is(tok::l_brace)) {
4557 Diag(Tok.getLocation(), diag::err_friend_decl_defines_type)
4565 }
else if (!isTypeSpecifier(DSC) &&
4566 (Tok.
is(tok::semi) ||
4567 (Tok.isAtStartOfLine() &&
4568 !isValidAfterTypeSpecifier(CanBeBitfield)))) {
4570 if (Tok.
isNot(tok::semi)) {
4572 ExpectAndConsume(tok::semi, diag::err_expected_after,
"enum");
4573 PP.EnterToken(Tok,
true);
4574 Tok.setKind(tok::semi);
4587 if (TemplateInfo.Kind != ParsedTemplateInfo::NonTemplate &&
4591 Diag(Tok, diag::err_enum_template);
4596 if (TemplateInfo.Kind == ParsedTemplateInfo::ExplicitInstantiation) {
4599 Diag(StartLoc, diag::err_explicit_instantiation_enum);
4603 assert(TemplateInfo.TemplateParams &&
"no template parameters");
4605 TemplateInfo.TemplateParams->size());
4609 ProhibitAttributes(attrs);
4612 Diag(Tok, diag::err_enumerator_unnamed_no_def);
4619 stripTypeAttributesOffDeclSpec(attrs, DS, TUK);
4624 SkipBody = Actions.shouldSkipAnonEnumBody(
getCurScope(),
4629 bool IsDependent =
false;
4630 const char *PrevSpec =
nullptr;
4632 Decl *TagDecl = Actions.ActOnTag(
4635 ScopedEnumKWLoc, IsScopedUsingClassTag, BaseType,
4636 DSC == DeclSpecContext::DSC_type_specifier,
4637 DSC == DeclSpecContext::DSC_template_param ||
4638 DSC == DeclSpecContext::DSC_template_type_arg,
4649 NameLoc.
isValid() ? NameLoc : StartLoc,
4650 PrevSpec, DiagID, TagDecl, Owned,
4652 Diag(StartLoc, DiagID) << PrevSpec;
4661 Diag(Tok, diag::err_expected_type_name_after_typename);
4673 NameLoc.
isValid() ? NameLoc : StartLoc,
4674 PrevSpec, DiagID, Type.
get(),
4675 Actions.getASTContext().getPrintingPolicy()))
4676 Diag(StartLoc, DiagID) << PrevSpec;
4695 ParseEnumBody(StartLoc, D);
4697 !Actions.ActOnDuplicateDefinition(DS, TagDecl, SkipBody)) {
4704 NameLoc.
isValid() ? NameLoc : StartLoc,
4705 PrevSpec, DiagID, TagDecl, Owned,
4707 Diag(StartLoc, DiagID) << PrevSpec;
4723 Actions.ActOnTagStartDefinition(
getCurScope(), EnumDecl);
4730 Diag(Tok, diag::err_empty_enum);
4735 Decl *LastEnumConstDecl =
nullptr;
4738 while (Tok.
isNot(tok::r_brace)) {
4741 if (Tok.
isNot(tok::identifier)) {
4742 Diag(Tok.getLocation(), diag::err_expected) << tok::identifier;
4752 ParsedAttributesWithRange attrs(AttrFactory);
4753 MaybeParseGNUAttributes(attrs);
4754 ProhibitAttributes(attrs);
4755 if (standardAttributesAllowed() && isCXX11AttributeSpecifier()) {
4758 ? diag::warn_cxx14_compat_ns_enum_attribute
4759 : diag::ext_ns_enum_attribute)
4761 ParseCXX11Attributes(attrs);
4766 EnumAvailabilityDiags.emplace_back(*
this);
4777 Decl *EnumConstDecl = Actions.ActOnEnumConstant(
4778 getCurScope(), EnumDecl, LastEnumConstDecl, IdentLoc, Ident, attrs,
4779 EqualLoc, AssignedVal.
get());
4780 EnumAvailabilityDiags.back().done();
4782 EnumConstantDecls.push_back(EnumConstDecl);
4783 LastEnumConstDecl = EnumConstDecl;
4785 if (Tok.
is(tok::identifier)) {
4788 Diag(Loc, diag::err_enumerator_list_missing_comma)
4798 Diag(Tok.getLocation(), diag::err_expected_either) << tok::r_brace
4801 Diag(Tok.getLocation(), diag::err_expected_end_of_enumerator);
4811 if (Tok.
is(tok::r_brace) && CommaLoc.
isValid()) {
4814 diag::ext_enumerator_list_comma_cxx :
4815 diag::ext_enumerator_list_comma_c)
4818 Diag(CommaLoc, diag::warn_cxx98_compat_enumerator_list_comma)
4829 MaybeParseGNUAttributes(attrs);
4831 Actions.ActOnEnumBody(StartLoc, T.
getRange(), EnumDecl, EnumConstantDecls,
4835 assert(EnumConstantDecls.size() == EnumAvailabilityDiags.size());
4836 for (
size_t i = 0, e = EnumConstantDecls.size(); i != e; ++i) {
4838 EnumAvailabilityDiags[i].redelay();
4848 if (!isValidAfterTypeSpecifier(CanBeBitfield)) {
4849 ExpectAndConsume(tok::semi, diag::err_expected_after,
"enum");
4853 PP.EnterToken(Tok,
true);
4854 Tok.setKind(tok::semi);
4861 bool Parser::isKnownToBeTypeSpecifier(
const Token &Tok)
const {
4863 default:
return false;
4867 case tok::kw___int64:
4868 case tok::kw___int128:
4869 case tok::kw_signed:
4870 case tok::kw_unsigned:
4871 case tok::kw__Complex:
4872 case tok::kw__Imaginary:
4875 case tok::kw_wchar_t:
4876 case tok::kw_char8_t:
4877 case tok::kw_char16_t:
4878 case tok::kw_char32_t:
4882 case tok::kw_double:
4883 case tok::kw__Accum:
4884 case tok::kw__Fract:
4885 case tok::kw__Float16:
4886 case tok::kw___float128:
4889 case tok::kw__Decimal32:
4890 case tok::kw__Decimal64:
4891 case tok::kw__Decimal128:
4892 case tok::kw___vector:
4893 #define GENERIC_IMAGE_TYPE(ImgType, Id) case tok::kw_##ImgType##_t: 4894 #include "clang/Basic/OpenCLImageTypes.def" 4898 case tok::kw_struct:
4899 case tok::kw___interface:
4905 case tok::annot_typename:
4912 bool Parser::isTypeSpecifierQualifier() {
4914 default:
return false;
4916 case tok::identifier:
4917 if (TryAltiVecVectorToken())
4920 case tok::kw_typename:
4925 if (Tok.
is(tok::identifier))
4927 return isTypeSpecifierQualifier();
4929 case tok::coloncolon:
4936 return isTypeSpecifierQualifier();
4939 case tok::kw___attribute:
4941 case tok::kw_typeof:
4946 case tok::kw___int64:
4947 case tok::kw___int128:
4948 case tok::kw_signed:
4949 case tok::kw_unsigned:
4950 case tok::kw__Complex:
4951 case tok::kw__Imaginary:
4954 case tok::kw_wchar_t:
4955 case tok::kw_char8_t:
4956 case tok::kw_char16_t:
4957 case tok::kw_char32_t:
4961 case tok::kw_double:
4962 case tok::kw__Accum:
4963 case tok::kw__Fract:
4964 case tok::kw__Float16:
4965 case tok::kw___float128:
4968 case tok::kw__Decimal32:
4969 case tok::kw__Decimal64:
4970 case tok::kw__Decimal128:
4971 case tok::kw___vector:
4972 #define GENERIC_IMAGE_TYPE(ImgType, Id) case tok::kw_##ImgType##_t: 4973 #include "clang/Basic/OpenCLImageTypes.def" 4977 case tok::kw_struct:
4978 case tok::kw___interface:
4985 case tok::kw_volatile:
4986 case tok::kw_restrict:
4990 case tok::kw___unknown_anytype:
4993 case tok::annot_typename:
5000 case tok::kw___cdecl:
5001 case tok::kw___stdcall:
5002 case tok::kw___fastcall:
5003 case tok::kw___thiscall:
5004 case tok::kw___regcall:
5005 case tok::kw___vectorcall:
5007 case tok::kw___ptr64:
5008 case tok::kw___ptr32:
5009 case tok::kw___pascal:
5010 case tok::kw___unaligned:
5012 case tok::kw__Nonnull:
5013 case tok::kw__Nullable:
5014 case tok::kw__Null_unspecified:
5016 case tok::kw___kindof:
5018 case tok::kw___private:
5019 case tok::kw___local:
5020 case tok::kw___global:
5021 case tok::kw___constant:
5022 case tok::kw___generic:
5023 case tok::kw___read_only:
5024 case tok::kw___read_write:
5025 case tok::kw___write_only:
5028 case tok::kw_private:
5032 case tok::kw__Atomic:
5042 bool Parser::isDeclarationSpecifier(
bool DisambiguatingWithExpression) {
5044 default:
return false;
5050 case tok::identifier:
5054 if (TryAltiVecVectorToken())
5057 case tok::kw_decltype:
5058 case tok::kw_typename:
5063 if (TryAnnotateTypeConstraint())
5065 if (Tok.
is(tok::identifier))
5073 if (DisambiguatingWithExpression &&
5074 isStartOfObjCClassMessageMissingOpenBracket())
5077 return isDeclarationSpecifier();
5079 case tok::coloncolon:
5088 return isDeclarationSpecifier();
5091 case tok::kw_typedef:
5092 case tok::kw_extern:
5093 case tok::kw___private_extern__:
5094 case tok::kw_static:
5096 case tok::kw___auto_type:
5097 case tok::kw_register:
5098 case tok::kw___thread:
5099 case tok::kw_thread_local:
5100 case tok::kw__Thread_local:
5103 case tok::kw___module_private__:
5106 case tok::kw___unknown_anytype:
5111 case tok::kw___int64:
5112 case tok::kw___int128:
5113 case tok::kw_signed:
5114 case tok::kw_unsigned:
5115 case tok::kw__Complex:
5116 case tok::kw__Imaginary:
5119 case tok::kw_wchar_t:
5120 case tok::kw_char8_t:
5121 case tok::kw_char16_t:
5122 case tok::kw_char32_t:
5127 case tok::kw_double:
5128 case tok::kw__Accum:
5129 case tok::kw__Fract:
5130 case tok::kw__Float16:
5131 case tok::kw___float128:
5134 case tok::kw__Decimal32:
5135 case tok::kw__Decimal64:
5136 case tok::kw__Decimal128:
5137 case tok::kw___vector:
5141 case tok::kw_struct:
5143 case tok::kw___interface:
5149 case tok::kw_volatile:
5150 case tok::kw_restrict:
5154 case tok::kw_inline:
5155 case tok::kw_virtual:
5156 case tok::kw_explicit:
5157 case tok::kw__Noreturn:
5160 case tok::kw__Alignas:
5163 case tok::kw_friend:
5166 case tok::kw__Static_assert:
5169 case tok::kw_typeof:
5172 case tok::kw___attribute:
5175 case tok::annot_decltype:
5176 case tok::kw_constexpr:
5179 case tok::kw_consteval:
5180 case tok::kw_constinit:
5183 case tok::kw__Atomic:
5191 case tok::annot_typename:
5192 return !DisambiguatingWithExpression ||
5193 !isStartOfObjCClassMessageMissingOpenBracket();
5196 case tok::annot_template_id: {
5197 return isTypeConstraintAnnotation() &&
5200 case tok::annot_cxxscope:
5201 if (
NextToken().
is(tok::identifier) && TryAnnotateTypeConstraint())
5203 return isTypeConstraintAnnotation() &&
5204 GetLookAheadToken(2).isOneOf(tok::kw_auto, tok::kw_decltype);
5205 case tok::kw___declspec:
5206 case tok::kw___cdecl:
5207 case tok::kw___stdcall:
5208 case tok::kw___fastcall:
5209 case tok::kw___thiscall:
5210 case tok::kw___regcall:
5211 case tok::kw___vectorcall:
5213 case tok::kw___sptr:
5214 case tok::kw___uptr:
5215 case tok::kw___ptr64:
5216 case tok::kw___ptr32:
5217 case tok::kw___forceinline:
5218 case tok::kw___pascal:
5219 case tok::kw___unaligned:
5221 case tok::kw__Nonnull:
5222 case tok::kw__Nullable:
5223 case tok::kw__Null_unspecified:
5225 case tok::kw___kindof:
5227 case tok::kw___private:
5228 case tok::kw___local:
5229 case tok::kw___global:
5230 case tok::kw___constant:
5231 case tok::kw___generic:
5232 case tok::kw___read_only:
5233 case tok::kw___read_write:
5234 case tok::kw___write_only:
5235 #define GENERIC_IMAGE_TYPE(ImgType, Id) case tok::kw_##ImgType##_t: 5236 #include "clang/Basic/OpenCLImageTypes.def" 5240 case tok::kw_private:
5245 bool Parser::isConstructorDeclarator(
bool IsUnqualified,
bool DeductionGuide) {
5246 TentativeParsingAction TPA(*
this);
5250 if (ParseOptionalCXXScopeSpecifier(SS,
nullptr,
5257 if (Tok.
is(tok::identifier)) {
5261 }
else if (Tok.
is(tok::annot_template_id)) {
5262 ConsumeAnnotationToken();
5270 SkipCXX11Attributes();
5273 if (Tok.
isNot(tok::l_paren)) {
5281 if (Tok.
is(tok::r_paren) ||
5290 isCXX11AttributeSpecifier(
false,
5297 DeclaratorScopeObj DeclScopeObj(*
this, SS);
5299 DeclScopeObj.EnterDeclaratorScope();
5303 MaybeParseMicrosoftAttributes(Attrs);
5308 bool IsConstructor =
false;
5309 if (isDeclarationSpecifier())
5310 IsConstructor =
true;
5311 else if (Tok.
is(tok::identifier) ||
5312 (Tok.
is(tok::annot_cxxscope) &&
NextToken().
is(tok::identifier))) {
5317 if (Tok.
is(tok::annot_cxxscope))
5318 ConsumeAnnotationToken();
5330 case tok::coloncolon:
5343 SkipCXX11Attributes();
5345 if (DeductionGuide) {
5347 IsConstructor = Tok.
is(tok::arrow);
5350 if (Tok.
is(tok::colon) || Tok.
is(tok::kw_try)) {
5354 IsConstructor =
true;
5356 if (Tok.
is(tok::semi) || Tok.
is(tok::l_brace)) {
5369 IsConstructor = IsUnqualified;
5374 IsConstructor =
true;
5380 return IsConstructor;
5395 void Parser::ParseTypeQualifierListOpt(
5396 DeclSpec &DS,
unsigned AttrReqs,
bool AtomicAllowed,
5397 bool IdentifierRequired,
5399 if (standardAttributesAllowed() && (AttrReqs & AR_CXX11AttributesParsed) &&
5400 isCXX11AttributeSpecifier()) {
5401 ParsedAttributesWithRange attrs(AttrFactory);
5402 ParseCXX11Attributes(attrs);
5410 const char *PrevSpec =
nullptr;
5411 unsigned DiagID = 0;
5415 case tok::code_completion:
5417 (*CodeCompletionHandler)();
5419 Actions.CodeCompleteTypeQualifiers(DS);
5420 return cutOffParsing();
5426 case tok::kw_volatile:
5430 case tok::kw_restrict:
5434 case tok::kw__Atomic:
5436 goto DoneWithTypeQuals;
5438 Diag(Tok, diag::ext_c11_feature) << Tok.
getName();
5444 case tok::kw_private:
5446 goto DoneWithTypeQuals;
5448 case tok::kw___private:
5449 case tok::kw___global:
5450 case tok::kw___local:
5451 case tok::kw___constant:
5452 case tok::kw___generic:
5453 case tok::kw___read_only:
5454 case tok::kw___write_only:
5455 case tok::kw___read_write:
5459 case tok::kw___unaligned:
5463 case tok::kw___uptr:
5468 if (TryKeywordIdentFallback(
false))
5472 case tok::kw___sptr:
5474 case tok::kw___ptr64:
5475 case tok::kw___ptr32:
5476 case tok::kw___cdecl:
5477 case tok::kw___stdcall:
5478 case tok::kw___fastcall:
5479 case tok::kw___thiscall:
5480 case tok::kw___regcall:
5481 case tok::kw___vectorcall:
5482 if (AttrReqs & AR_DeclspecAttributesParsed) {
5486 goto DoneWithTypeQuals;
5487 case tok::kw___pascal:
5488 if (AttrReqs & AR_VendorAttributesParsed) {
5492 goto DoneWithTypeQuals;
5495 case tok::kw__Nonnull:
5496 case tok::kw__Nullable:
5497 case tok::kw__Null_unspecified:
5502 case tok::kw___kindof:
5508 case tok::kw___attribute:
5509 if (AttrReqs & AR_GNUAttributesParsedAndRejected)
5511 Diag(Tok, diag::err_attributes_not_allowed);
5515 if (AttrReqs & AR_GNUAttributesParsed ||
5516 AttrReqs & AR_GNUAttributesParsedAndRejected) {
5526 DS.
Finish(Actions, Actions.getASTContext().getPrintingPolicy());
5534 assert(PrevSpec &&
"Method did not return previous specifier!");
5535 Diag(Tok, DiagID) << PrevSpec;
5543 void Parser::ParseDeclarator(
Declarator &D) {
5546 ParseDeclaratorInternal(D, &Parser::ParseDirectDeclarator);
5551 if (Kind == tok::star || Kind == tok::caret)
5554 if (Kind == tok::kw_pipe &&
5555 ((Lang.OpenCL && Lang.OpenCLVersion >= 200) || Lang.OpenCLCPlusPlus))
5558 if (!Lang.CPlusPlus)
5561 if (Kind == tok::amp)
5569 if (Kind == tok::ampamp)
5570 return Lang.CPlusPlus11 ||
5581 for (
unsigned Idx = 0; Idx != NumTypes; ++Idx)
5613 void Parser::ParseDeclaratorInternal(
Declarator &D,
5614 DirectDeclParseFunction DirectDeclParser) {
5615 if (Diags.hasAllExtensionsSilenced())
5622 (Tok.
is(tok::coloncolon) || Tok.
is(tok::kw_decltype) ||
5623 (Tok.
is(tok::identifier) &&
5625 Tok.
is(tok::annot_cxxscope))) {
5626 bool EnteringContext =
5630 ParseOptionalCXXScopeSpecifier(SS,
nullptr, EnteringContext);
5633 if (Tok.
isNot(tok::star)) {
5638 AnnotateScopeToken(SS,
true);
5640 if (DirectDeclParser)
5641 (this->*DirectDeclParser)(D);
5648 ParseTypeQualifierListOpt(DS);
5652 ParseDeclaratorInternal(D, DirectDeclParser);
5668 ParseTypeQualifierListOpt(DS);
5677 if (DirectDeclParser)
5678 (this->*DirectDeclParser)(D);
5687 if (Kind == tok::star || Kind == tok::caret) {
5693 unsigned Reqs = AR_CXX11AttributesParsed | AR_DeclspecAttributesParsed |
5695 ? AR_GNUAttributesParsed
5696 : AR_GNUAttributesParsedAndRejected);
5701 ParseDeclaratorInternal(D, DirectDeclParser);
5702 if (Kind == tok::star)
5720 if (Kind == tok::ampamp)
5722 diag::warn_cxx98_compat_rvalue_reference :
5723 diag::ext_rvalue_reference);
5726 ParseTypeQualifierListOpt(DS);
5735 diag::err_invalid_reference_qualifier_application) <<
"const";
5738 diag::err_invalid_reference_qualifier_application) <<
"volatile";
5742 diag::err_invalid_reference_qualifier_application) <<
"_Atomic";
5746 ParseDeclaratorInternal(D, DirectDeclParser);
5753 Diag(InnerChunk.
Loc, diag::err_illegal_decl_reference_to_reference)
5756 Diag(InnerChunk.
Loc, diag::err_illegal_decl_reference_to_reference)
5831 void Parser::ParseDirectDeclarator(
Declarator &D) {
5838 return ParseDecompositionDeclarator(D);
5850 bool EnteringContext =
5858 if (Actions.ShouldEnterDeclaratorScope(
getCurScope(),
5862 DeclScopeObj.EnterDeclaratorScope();
5869 goto PastIdentifier;
5886 !Actions.containsUnexpandedParameterPacks(D) &&
5894 DiagnoseMisplacedEllipsisInDeclarator(EllipsisLoc, D);
5904 if (Tok.
isOneOf(tok::identifier, tok::kw_operator, tok::annot_template_id,
5908 bool AllowConstructorName;
5909 bool AllowDeductionGuide;
5911 AllowConstructorName =
false;
5912 AllowDeductionGuide =
false;
5914 AllowConstructorName =
5917 AllowDeductionGuide =
false;
5919 AllowConstructorName =
5921 AllowDeductionGuide =
5929 true, AllowConstructorName,
5930 AllowDeductionGuide,
nullptr,
nullptr,
5943 DeclScopeObj.EnterDeclaratorScope();
5950 goto PastIdentifier;
5956 diag::err_expected_unqualified_id)
5959 goto PastIdentifier;
5963 "There's a C++-specific check for tok::identifier above");
5968 goto PastIdentifier;
5973 bool DiagnoseIdentifier =
false;
5977 DiagnoseIdentifier =
true;
5980 DiagnoseIdentifier =
5988 !isCXX11VirtSpecifier(Tok))
5990 tok::comma, tok::semi, tok::equal, tok::l_brace, tok::kw_try);
5991 if (DiagnoseIdentifier) {
5996 goto PastIdentifier;
6000 if (Tok.
is(tok::l_paren)) {
6005 RevertingTentativeParsingAction PA(*
this);
6009 goto PastIdentifier;
6016 ParseParenDeclarator(D);
6029 DeclScopeObj.EnterDeclaratorScope();
6040 diag::ext_abstract_pack_declarator_parens);
6042 if (Tok.
getKind() == tok::annot_pragma_parser_crash)
6044 if (Tok.
is(tok::l_square))
6045 return ParseMisplacedBracketDeclarator(D);
6053 diag::err_expected_member_name_or_semi_objcxx_keyword)
6060 goto PastIdentifier;
6063 diag::err_expected_member_name_or_semi)
6067 if (Tok.
isOneOf(tok::period, tok::arrow))
6068 Diag(Tok, diag::err_invalid_operator_on_type) << Tok.
is(tok::arrow);
6072 Diag(PP.getLocForEndOfToken(Loc), diag::err_expected_unqualified_id)
6076 diag::err_expected_unqualified_id)
6081 diag::err_expected_either)
6082 << tok::identifier << tok::l_paren;
6090 "Haven't past the location of the identifier yet?");
6094 MaybeParseCXX11Attributes(D);
6097 if (Tok.
is(tok::l_paren)) {
6101 ParseScope PrototypeScope(
this,
6103 (IsFunctionDeclaration
6109 bool IsAmbiguous =
false;
6113 TentativelyDeclaredIdentifiers.push_back(D.
getIdentifier());
6114 bool IsFunctionDecl = isCXXFunctionDeclarator(&IsAmbiguous);
6115 TentativelyDeclaredIdentifiers.pop_back();
6116 if (!IsFunctionDecl)
6122 if (IsFunctionDeclaration)
6123 Actions.ActOnStartFunctionDeclarationDeclarator(D,
6124 TemplateParameterDepth);
6125 ParseFunctionDeclarator(D, attrs, T, IsAmbiguous);
6126 if (IsFunctionDeclaration)
6127 Actions.ActOnFinishFunctionDeclarationDeclarator(D);
6128 PrototypeScope.Exit();
6129 }
else if (Tok.
is(tok::l_square)) {
6130 ParseBracketDeclarator(D);
6139 Diag(Tok, diag::err_requires_clause_inside_parens);
6141 ExprResult TrailingRequiresClause = Actions.CorrectDelayedTyposInExpr(
6153 void Parser::ParseDecompositionDeclarator(
Declarator &D) {
6154 assert(Tok.
is(tok::l_square));
6160 if (!(
NextToken().is(tok::identifier) &&
6161 GetLookAheadToken(2).
isOneOf(tok::comma, tok::r_square)) &&
6163 GetLookAheadToken(2).isOneOf(tok::equal, tok::l_brace)))
6164 return ParseMisplacedBracketDeclarator(D);
6170 while (Tok.
isNot(tok::r_square)) {
6171 if (!Bindings.empty()) {
6172 if (Tok.
is(tok::comma))
6175 if (Tok.
is(tok::identifier)) {
6177 Diag(EndLoc, diag::err_expected)
6180 Diag(Tok, diag::err_expected_comma_or_rsquare);
6183 SkipUntil(tok::r_square, tok::comma, tok::identifier,
6185 if (Tok.
is(tok::comma))
6187 else if (Tok.
isNot(tok::identifier))
6192 if (Tok.
isNot(tok::identifier)) {
6193 Diag(Tok, diag::err_expected) << tok::identifier;
6201 if (Tok.
isNot(tok::r_square))
6207 if (Bindings.empty())
6230 void Parser::ParseParenDeclarator(
Declarator &D) {
6234 assert(!D.
isPastIdentifier() &&
"Should be called before passing identifier");
6247 bool RequiresArg =
false;
6248 if (Tok.
is(tok::kw___attribute)) {
6249 ParseGNUAttributes(attrs);
6257 ParseMicrosoftTypeAttributes(attrs);
6260 if (Tok.
is(tok::kw___pascal))
6261 ParseBorlandTypeAttributes(attrs);
6273 }
else if (Tok.
is(tok::r_paren) ||
6276 isDeclarationSpecifier() ||
6277 isCXX11AttributeSpecifier()) {
6295 ParseDeclaratorInternal(D, &Parser::ParseDirectDeclarator);
6306 DiagnoseMisplacedEllipsisInDeclarator(EllipsisLoc, D);
6319 ParseScope PrototypeScope(
this,
6323 ParseFunctionDeclarator(D, attrs, T,
false, RequiresArg);
6324 PrototypeScope.Exit();
6327 void Parser::InitCXXThisScopeForDeclaratorIfRelevant(
6337 bool IsCXX11MemberFunction =
getLangOpts().CPlusPlus11 &&
6343 Actions.CurContext->isRecord());
6344 if (!IsCXX11MemberFunction)
6357 LangAS ASIdx = attr.asOpenCLLangAS();
6364 ThisScope.emplace(Actions, dyn_cast<CXXRecordDecl>(Actions.CurContext), Q,
6365 IsCXX11MemberFunction);
6388 void Parser::ParseFunctionDeclarator(
Declarator &D,
6393 assert(
getCurScope()->isFunctionPrototypeScope() &&
6394 "Should call from a Function scope");
6400 bool HasProto =
false;
6407 bool RefQualifierIsLValueRef =
true;
6415 ParsedAttributesWithRange FnAttrs(AttrFactory);
6424 StartLoc = LParenLoc;
6426 if (isFunctionDeclaratorIdentifierList()) {
6428 Diag(Tok, diag::err_argument_required_after_attribute);
6430 ParseFunctionDeclaratorIdentifierList(D, ParamInfo);
6434 LocalEndLoc = RParenLoc;
6439 MaybeParseCXX11Attributes(FnAttrs);
6440 ProhibitAttributes(FnAttrs);
6442 if (Tok.
isNot(tok::r_paren))
6443 ParseParameterDeclarationClause(D.
getContext(), FirstArgAttrs, ParamInfo,
6445 else if (RequiresArg)
6446 Diag(Tok, diag::err_argument_required_after_attribute);
6448 HasProto = ParamInfo.size() ||
getLangOpts().CPlusPlus
6454 LocalEndLoc = RParenLoc;
6463 ParseTypeQualifierListOpt(DS, AR_NoAttributesParsed,
6466 llvm::function_ref<
void()>([&]() {
6467 Actions.CodeCompleteFunctionQualifiers(DS, D);
6474 if (ParseRefQualifier(RefQualifierIsLValueRef, RefQualifierLoc))
6475 EndLoc = RefQualifierLoc;
6478 InitCXXThisScopeForDeclaratorIfRelevant(D, DS, ThisScope);
6483 if (Delayed && Actions.isLibstdcxxEagerExceptionSpecHack(D) &&
6484 GetLookAheadToken(0).is(tok::kw_noexcept) &&
6485 GetLookAheadToken(1).is(tok::l_paren) &&
6486 GetLookAheadToken(2).is(tok::kw_noexcept) &&
6487 GetLookAheadToken(3).is(tok::l_paren) &&
6488 GetLookAheadToken(4).is(tok::identifier) &&
6489 GetLookAheadToken(4).getIdentifierInfo()->isStr(
"swap")) {
6500 ESpecType = tryParseExceptionSpecification(Delayed,
6503 DynamicExceptionRanges,
6505 ExceptionSpecTokens);
6507 EndLoc = ESpecRange.
getEnd();
6511 MaybeParseCXX11Attributes(FnAttrs);
6514 LocalEndLoc = EndLoc;
6516 Diag(Tok, diag::warn_cxx98_compat_trailing_return_type);
6521 TrailingReturnType =
6525 }
else if (standardAttributesAllowed()) {
6526 MaybeParseCXX11Attributes(FnAttrs);
6539 if (!ND || isa<ParmVarDecl>(ND))
6541 DeclsInPrototype.push_back(ND);
6547 HasProto, IsAmbiguous, LParenLoc, ParamInfo.data(),
6548 ParamInfo.size(), EllipsisLoc, RParenLoc,
6549 RefQualifierIsLValueRef, RefQualifierLoc,
6551 ESpecType, ESpecRange, DynamicExceptions.data(),
6552 DynamicExceptionRanges.data(), DynamicExceptions.size(),
6553 NoexceptExpr.
isUsable() ? NoexceptExpr.
get() :
nullptr,
6554 ExceptionSpecTokens, DeclsInPrototype, StartLoc,
6555 LocalEndLoc, D, TrailingReturnType, &DS),
6556 std::move(FnAttrs), EndLoc);
6561 bool Parser::ParseRefQualifier(
bool &RefQualifierIsLValueRef,
6563 if (Tok.
isOneOf(tok::amp, tok::ampamp)) {
6565 diag::warn_cxx98_compat_ref_qualifier :
6566 diag::ext_ref_qualifier);
6568 RefQualifierIsLValueRef = Tok.
is(tok::amp);
6580 bool Parser::isFunctionDeclaratorIdentifierList() {
6582 && Tok.
is(tok::identifier)
6583 && !TryAltiVecVectorToken()
6612 void Parser::ParseFunctionDeclaratorIdentifierList(
6620 Diag(Tok, diag::ext_ident_list_in_param);
6623 llvm::SmallSet<const IdentifierInfo*, 16> ParamsSoFar;
6627 if (Tok.
isNot(tok::identifier)) {
6628 Diag(Tok, diag::err_expected) << tok::identifier;
6639 Diag(Tok, diag::err_unexpected_typedef_ident) << ParmII;
6642 if (!ParamsSoFar.insert(ParmII).second) {
6643 Diag(Tok, diag::err_param_redefinition) << ParmII;
6688 void Parser::ParseParameterDeclarationClause(
6698 if (
getCurScope()->getFunctionPrototypeDepth() - 1 >
6731 ParseDeclarationSpecifiers(DS);
6743 ParseDeclarator(ParmDeclarator);
6746 MaybeParseGNUAttributes(ParmDeclarator);
6748 if (Tok.
is(tok::kw_requires)) {
6753 diag::err_requires_clause_on_declarator_not_declaring_a_function);
6755 Actions.CorrectDelayedTyposInExpr(
6764 std::unique_ptr<CachedTokens> DefArgToks;
6771 Diag(DSStart, diag::err_missing_param);
6778 if (Tok.
is(tok::ellipsis) &&
6781 !Actions.isUnexpandedParameterPackPermitted())) &&
6782 Actions.containsUnexpandedParameterPacks(ParmDeclarator))
6783 DiagnoseMisplacedEllipsisInDeclarator(
ConsumeToken(), ParmDeclarator);
6787 Decl *Param = Actions.ActOnParamDeclarator(
getCurScope(), ParmDeclarator);
6792 if (Tok.
is(tok::equal)) {
6803 if (!ConsumeAndStoreInitializer(*DefArgToks, CIK_DefaultArgument)) {
6805 Actions.ActOnParamDefaultArgumentError(Param, EqualLoc);
6807 Actions.ActOnParamUnparsedDefaultArgument(Param, EqualLoc,
6823 Diag(Tok, diag::warn_cxx98_compat_generalized_initializer_lists);
6824 DefArgResult = ParseBraceInitializer();
6827 DefArgResult = Actions.CorrectDelayedTyposInExpr(DefArgResult);
6829 Actions.ActOnParamDefaultArgumentError(Param, EqualLoc);
6833 Actions.ActOnParamDefaultArgument(Param, EqualLoc,
6834 DefArgResult.
get());
6841 Param, std::move(DefArgToks)));
6848 Diag(EllipsisLoc, diag::err_missing_comma_before_ellipsis)
6851 Actions.containsUnexpandedParameterPacks(ParmDeclarator)) {
6855 Diag(EllipsisLoc, diag::warn_misplaced_ellipsis_vararg)
6856 << ParmEllipsis.
isValid() << ParmEllipsis;
6859 diag::note_misplaced_ellipsis_vararg_existing_ellipsis);
6862 diag::note_misplaced_ellipsis_vararg_add_ellipsis)
6867 Diag(EllipsisLoc, diag::note_misplaced_ellipsis_vararg_add_comma)
6886 void Parser::ParseBracketDeclarator(
Declarator &D) {
6887 if (CheckProhibitedCXX11Attribute())
6895 if (Tok.
getKind() == tok::r_square) {
6898 MaybeParseCXX11Attributes(attrs);
6906 }
else if (Tok.
getKind() == tok::numeric_constant &&
6907 GetLookAheadToken(1).is(tok::r_square)) {
6914 MaybeParseCXX11Attributes(attrs);
6922 }
else if (Tok.
getKind() == tok::code_completion) {
6923 Actions.CodeCompleteBracketDeclarator(
getCurScope());
6924 return cutOffParsing();
6934 ParseTypeQualifierListOpt(DS, AR_CXX11AttributesParsed);
6942 bool isStar =
false;
6949 if (Tok.
is(tok::star) && GetLookAheadToken(1).is(tok::r_square)) {
6953 Diag(StaticLoc, diag::err_unspecified_vla_size_with_static);
6957 }
else if (Tok.
isNot(tok::r_square)) {
6975 Diag(StaticLoc, diag::err_unspecified_size_with_static);
7001 void Parser::ParseMisplacedBracketDeclarator(
Declarator &D) {
7002 assert(Tok.
is(tok::l_square) &&
"Missing opening bracket");
7008 while (Tok.
is(tok::l_square)) {
7009 ParseBracketDeclarator(TempDeclarator);
7015 if (Tok.
is(tok::semi))
7021 ParseDeclaratorInternal(D, &Parser::ParseDirectDeclarator);
7026 if (TempDeclarator.getNumTypeObjects() == 0)
7030 bool NeedParens =
false;
7055 for (
unsigned i = 0, e = TempDeclarator.getNumTypeObjects(); i < e; ++i) {
7068 SourceRange BracketRange(StartBracketLoc, EndBracketLoc);
7072 Diag(EndLoc, diag::err_brackets_go_after_unqualified_id)
7080 Diag(EndLoc, diag::err_brackets_go_after_unqualified_id)
7093 void Parser::ParseTypeofSpecifier(
DeclSpec &DS) {
7094 assert(Tok.
is(tok::kw_typeof) &&
"Not a typeof specifier");
7098 const bool hasParens = Tok.
is(tok::l_paren);
7107 ExprResult Operand = Actions.CorrectDelayedTyposInExpr(
7108 ParseExprAfterUnaryExprOrTypeTrait(OpTok, isCastExpr, CastTy, CastRange));
7124 const char *PrevSpec =
nullptr;
7129 Actions.getASTContext().getPrintingPolicy()))
7130 Diag(StartLoc, DiagID) << PrevSpec;
7141 Operand = Actions.HandleExprEvaluationContextForTypeof(Operand.
get());
7147 const char *PrevSpec =
nullptr;
7151 DiagID, Operand.
get(),
7152 Actions.getASTContext().getPrintingPolicy()))
7153 Diag(StartLoc, DiagID) << PrevSpec;
7159 void Parser::ParseAtomicSpecifier(
DeclSpec &DS) {
7160 assert(Tok.
is(tok::kw__Atomic) &&
NextToken().
is(tok::l_paren) &&
7161 "Not an atomic specifier");
7183 const char *PrevSpec =
nullptr;
7186 DiagID, Result.
get(),
7187 Actions.getASTContext().getPrintingPolicy()))
7188 Diag(StartLoc, DiagID) << PrevSpec;
7193 bool Parser::TryAltiVecVectorTokenOutOfLine() {
7196 default:
return false;
7199 case tok::kw_signed:
7200 case tok::kw_unsigned:
7205 case tok::kw_double:
7207 case tok::kw___bool:
7208 case tok::kw___pixel:
7209 Tok.
setKind(tok::kw___vector);
7211 case tok::identifier:
7213 Tok.
setKind(tok::kw___vector);
7217 Tok.
setKind(tok::kw___vector);
7225 const char *&PrevSpec,
unsigned &DiagID,
7227 const PrintingPolicy &Policy = Actions.getASTContext().getPrintingPolicy();
7233 case tok::kw_signed:
7234 case tok::kw_unsigned:
7239 case tok::kw_double:
7241 case tok::kw___bool:
7242 case tok::kw___pixel:
7245 case tok::identifier:
void ClearFunctionSpecs()
The name denotes a member of a dependent type that could not be resolved.
Defines the clang::ASTContext interface.
static bool isAttributeLateParsed(const IdentifierInfo &II)
isAttributeLateParsed - Return true if the attribute has arguments that require late parsing...
The name was classified as a variable template name.
static bool FindLocsWithCommonFileID(Preprocessor &PP, SourceLocation StartLoc, SourceLocation EndLoc)
Check if the a start and end source location expand to the same macro.
static Qualifiers fromCVRUMask(unsigned CVRU)
DeclaratorChunk::FunctionTypeInfo & getFunctionTypeInfo()
getFunctionTypeInfo - Retrieves the function type info object (looking through parentheses).
no exception specification
ExprResult ParseExpression(TypeCastState isTypeCast=NotTypeCast)
Simple precedence-based parser for binary/ternary operators.
A (possibly-)qualified type.
This is a scope that corresponds to the parameters within a function prototype.
SourceLocation getEndOfPreviousToken()
IdentifierInfo * getIdentifierInfo(StringRef Name) const
Return information about the specified preprocessor identifier token.
SourceRange getSourceRange() const LLVM_READONLY
Return the source range that covers this unqualified-id.
static const TSS TSS_unsigned
SourceLocation StartLocation
The location of the first token that describes this unqualified-id, which will be the location of the...
Code completion occurs within a class, struct, or union.
const DeclaratorChunk & getTypeObject(unsigned i) const
Return the specified TypeInfo from this declarator.
bool SetTypeQual(TQ T, SourceLocation Loc)
Ordinary name lookup, which finds ordinary names (functions, variables, typedefs, etc...
IdentifierInfo * Name
FIXME: Temporarily stores the name of a specialization.
static const TST TST_wchar
llvm::PointerUnion< Expr *, IdentifierLoc * > ArgsUnion
A union of the various pointer types that can be passed to an ParsedAttr as an argument.
The name was classified as an ADL-only function template name.
static bool attributeHasVariadicIdentifierArg(const IdentifierInfo &II)
Determine whether the given attribute has a variadic identifier argument.
bool is(tok::TokenKind K) const
is/isNot - Predicates to check if this token is a specific kind, as in "if (Tok.is(tok::l_brace)) {...
bool isEmpty() const
No scope specifier.
static const TST TST_typeofExpr
static const TST TST_char16
Decl - This represents one declaration (or definition), e.g.
Syntax
The style used to specify an attribute.
RAII object used to inform the actions that we're currently parsing a declaration.
Is the identifier known as a __declspec-style attribute?
A RAII object used to temporarily suppress access-like checking.
Defines the C++ template declaration subclasses.
The base class of the type hierarchy.
Classification failed; an error has been produced.
bool TryAnnotateCXXScopeToken(bool EnteringContext=false)
TryAnnotateScopeToken - Like TryAnnotateTypeOrScopeToken but only annotates C++ scope specifiers and ...
SourceLocation getCloseLocation() const
This indicates that the scope corresponds to a function, which means that labels are set here...
SourceLocation getBeginLoc() const LLVM_READONLY
One instance of this struct is used for each type in a declarator that is parsed. ...
Declaration of a variable template.
bool isFunctionDeclarator(unsigned &idx) const
isFunctionDeclarator - This method returns true if the declarator is a function declarator (looking t...
static FixItHint CreateInsertionFromRange(SourceLocation InsertionLoc, CharSourceRange FromRange, bool BeforePreviousInsertions=false)
Create a code modification hint that inserts the given code from FromRange at a specific location...
static const char * getSpecifierName(DeclSpec::TST T, const PrintingPolicy &Policy)
Turn a type-specifier-type into a string like "_Bool" or "union".
SourceLocation getEndLoc() const LLVM_READONLY
SourceLocation getEndLoc() const LLVM_READONLY
AccessSpecifier
A C++ access specifier (public, private, protected), plus the special value "none" which means differ...
TemplateNameKind Kind
The kind of template that Template refers to.
void ActOnExitFunctionContext()
Store information needed for an explicit specifier.
Parser - This implements a parser for the C family of languages.
bool SetTypeAltiVecBool(bool isAltiVecBool, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID, const PrintingPolicy &Policy)
bool hasExplicitSpecifier() const
TSCS getThreadStorageClassSpec() const
void SetIdentifier(IdentifierInfo *Id, SourceLocation IdLoc)
Set the name of this declarator to be the given identifier.
static IdentifierLoc * create(ASTContext &Ctx, SourceLocation Loc, IdentifierInfo *Ident)
SourceLocation getEndLoc() const
NameClassificationKind getKind() const
static bool isAtStartOfMacroExpansion(SourceLocation loc, const SourceManager &SM, const LangOptions &LangOpts, SourceLocation *MacroBegin=nullptr)
Returns true if the given MacroID location points at the first token of the macro expansion...
RAII object that enters a new expression evaluation context.
void ActOnStartDelayedMemberDeclarations(Scope *S, Decl *Record)
Information about one declarator, including the parsed type information and the identifier.
void setTypeofParensRange(SourceRange range)
unsigned getParsedSpecifiers() const
Return a bitmask of which flavors of specifiers this DeclSpec includes.
TypeSpecifierType
Specifies the kind of type.
LangAS
Defines the address space values used by the address space qualifier of QualType. ...
static const TST TST_interface
RAII object used to temporarily allow the C++ 'this' expression to be used, with the given qualifiers...
static const TST TST_char
bool hasTypeSpecifier() const
Return true if any type-specifier has been found.
Describes how types, statements, expressions, and declarations should be printed. ...
Code completion occurs within an Objective-C implementation or category implementation.
RAII object that makes sure paren/bracket/brace count is correct after declaration/statement parsing...
friend class ObjCDeclContextSwitch
bool isAnnotation() const
Return true if this is any of tok::annot_* kind tokens.
Represents a parameter to a function.
The name was classified as a non-type, and an expression representing that name has been formed...
ColonProtectionRAIIObject - This sets the Parser::ColonIsSacred bool and restores it when destroyed...
tok::TokenKind getKind() const
bool SetConstexprSpec(ConstexprSpecKind ConstexprKind, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
bool SkipUntil(tok::TokenKind T, SkipUntilFlags Flags=static_cast< SkipUntilFlags >(0))
SkipUntil - Read tokens until we get to the specified token, then consume it (unless StopBeforeMatch ...
void setTrailingRequiresClause(Expr *TRC)
Sets a trailing requires clause for this declarator.
bool mayOmitIdentifier() const
mayOmitIdentifier - Return true if the identifier is either optional or not allowed.
The collection of all-type qualifiers we support.
Information about a template-id annotation token.
Base wrapper for a particular "section" of type source info.
SourceLocation getFriendSpecLoc() const
Represents a struct/union/class.
const Token & NextToken()
NextToken - This peeks ahead one token and returns it without consuming it.
bool TryConsumeToken(tok::TokenKind Expected)
One of these records is kept for each identifier that is lexed.
SourceLocation getBegin() const
static const TST TST_decimal32
bool isStr(const char(&Str)[StrLen]) const
Return true if this is the identifier for the specified string.
static bool attributeHasIdentifierArg(const IdentifierInfo &II)
Determine whether the given attribute has an identifier argument.
static const TST TST_char8
Lookup for the name failed, but we're assuming it was a template name anyway.
SourceLocation getTypeSpecTypeLoc() const
static const TST TST_class
bool setFunctionSpecExplicit(SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID, ExplicitSpecifier ExplicitSpec, SourceLocation CloseParenLoc)
DeclGroupPtrTy ConvertDeclToDeclGroup(Decl *Ptr, Decl *OwnedType=nullptr)
static const TST TST_double
Code completion occurs following one or more template headers within a class.
bool setFunctionSpecVirtual(SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
The iterator over UnresolvedSets.
virtual SourceRange getSourceRange() const LLVM_READONLY
Source range that this declaration covers.
Token - This structure provides full information about a lexed token.
static const TST TST_enum
void setKind(tok::TokenKind K)
RAII class that helps handle the parsing of an open/close delimiter pair, such as braces { ...
void ActOnFinishDelayedAttribute(Scope *S, Decl *D, ParsedAttributes &Attrs)
ActOnFinishDelayedAttribute - Invoked when we have finished parsing an attribute for which parsing is...
bool hasTagDefinition() const
void ClearStorageClassSpecs()
static DeclaratorChunk getPointer(unsigned TypeQuals, SourceLocation Loc, SourceLocation ConstQualLoc, SourceLocation VolatileQualLoc, SourceLocation RestrictQualLoc, SourceLocation AtomicQualLoc, SourceLocation UnalignedQualLoc)
Return a DeclaratorChunk for a pointer.
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
const LangOptions & getLangOpts() const
void * getAsOpaquePtr() const
static const TST TST_accum
bool SetTypeAltiVecPixel(bool isAltiVecPixel, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID, const PrintingPolicy &Policy)
bool isInvalidType() const
The name was classified as a type.
Code completion occurs at top-level or namespace context.
The name was classified as a template whose specializations are types.
The controlling scope in a if/switch/while/for statement.
bool isObjCAtKeyword(tok::ObjCKeywordKind objcKey) const
Return true if we have an ObjC keyword identifier.
This is a scope that corresponds to a block/closure object.
bool isFunctionDeclaratorAFunctionDeclaration() const
Return true if a function declarator at this position would be a function declaration.
static ParsedType getTypeAnnotation(const Token &Tok)
getTypeAnnotation - Read a parsed type out of an annotation token.
Represents the results of name lookup.
void setExtension(bool Val=true)
void startOpenMPCXXRangeFor()
If the current region is a range loop-based region, mark the start of the loop construct.
This scope corresponds to an enum.
StringRef getSpelling(SourceLocation loc, SmallVectorImpl< char > &buffer, bool *invalid=nullptr) const
Return the 'spelling' of the token at the given location; does not go up to the spelling location or ...
tok::TokenKind getTokenID() const
If this is a source-language token (e.g.
static StringRef normalizeAttrName(StringRef Name)
Normalizes an attribute name by dropping prefixed and suffixed __.
void SetRangeBegin(SourceLocation Loc)
SetRangeBegin - Set the start of the source range to Loc, unless it's invalid.
Code completion occurs following one or more template headers.
bool isTypeSpecPipe() const
bool setFunctionSpecForceInline(SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
DeclGroupPtrTy BuildDeclaratorGroup(MutableArrayRef< Decl *> Group)
BuildDeclaratorGroup - convert a list of declarations into a declaration group, performing any necess...
ExprResult CorrectDelayedTyposInExpr(Expr *E, VarDecl *InitDecl=nullptr, llvm::function_ref< ExprResult(Expr *)> Filter=[](Expr *E) -> ExprResult { return E;})
Process any TypoExprs in the given Expr and its children, generating diagnostics as appropriate and r...
SourceRange getRange() const
unsigned getNumTypeObjects() const
Return the number of types applied to this declarator.
__ptr16, alignas(...), etc.
const clang::PrintingPolicy & getPrintingPolicy() const
The name has been typo-corrected to a keyword.
MutableArrayRef< TemplateParameterList * > MultiTemplateParamsArg
bool SetFriendSpec(SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
bool hasAttributes() const
Scope - A scope is a transient data structure that is used while parsing the program.
Represents information about a change in availability for an entity, which is part of the encoding of...
Represents a C++ nested-name-specifier or a global scope specifier.
int hasAttribute(AttrSyntax Syntax, const IdentifierInfo *Scope, const IdentifierInfo *Attr, const TargetInfo &Target, const LangOptions &LangOpts)
Return the version number associated with the attribute if we recognize and implement the attribute s...
bool SetTypePipe(bool isPipe, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID, const PrintingPolicy &Policy)
bool setFunctionSpecNoreturn(SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
SourceLocation getSpellingLoc(SourceLocation Loc) const
Given a SourceLocation object, return the spelling location referenced by the ID. ...
SourceLocation ConsumeAnyToken(bool ConsumeCodeCompletionTok=false)
ConsumeAnyToken - Dispatch to the right Consume* method based on the current token type...
SourceLocation getConstSpecLoc() const
const CXXScopeSpec & getCXXScopeSpec() const
getCXXScopeSpec - Return the C++ scope specifier (global scope or nested-name-specifier) that is part...
bool isCPlusPlusKeyword(const LangOptions &LangOpts) const
Return true if this token is a C++ keyword in the specified language.
void addAtEnd(ParsedAttr *newAttr)
static bool VersionNumberSeparator(const char Separator)
SourceRange getSourceRange() const LLVM_READONLY
const char * getName() const
The current context is "potentially evaluated" in C++11 terms, but the expression is evaluated at com...
VersionTuple getOpenCLVersionTuple() const
Return the OpenCL C or C++ version as a VersionTuple.
VersionTuple Version
The version number at which the change occurred.
IdentifierInfo * getIdentifier() const
static const TST TST_float
Language
The language for the input, used to select and validate the language standard and possible actions...
Code completion occurs within a sequence of declaration specifiers within a function, method, or block.
void ActOnCXXExitDeclInitializer(Scope *S, Decl *Dcl)
ActOnCXXExitDeclInitializer - Invoked after we are finished parsing an initializer for the declaratio...
unsigned getFlags() const
getFlags - Return the flags for this scope.
Provides definitions for the various language-specific address spaces.
static const TSW TSW_long
static DeclaratorChunk getFunction(bool HasProto, bool IsAmbiguous, SourceLocation LParenLoc, ParamInfo *Params, unsigned NumParams, SourceLocation EllipsisLoc, SourceLocation RParenLoc, bool RefQualifierIsLvalueRef, SourceLocation RefQualifierLoc, SourceLocation MutableLoc, ExceptionSpecificationType ESpecType, SourceRange ESpecRange, ParsedType *Exceptions, SourceRange *ExceptionRanges, unsigned NumExceptions, Expr *NoexceptExpr, CachedTokens *ExceptionSpecTokens, ArrayRef< NamedDecl *> DeclsInPrototype, SourceLocation LocalRangeBegin, SourceLocation LocalRangeEnd, Declarator &TheDeclarator, TypeResult TrailingReturnType=TypeResult(), DeclSpec *MethodQualifiers=nullptr)
DeclaratorChunk::getFunction - Return a DeclaratorChunk for a function.
SourceLocation getUnalignedSpecLoc() const
bool hasConstexprSpecifier() const
ParsedAttr * addNewTypeTagForDatatype(IdentifierInfo *attrName, SourceRange attrRange, IdentifierInfo *scopeName, SourceLocation scopeLoc, IdentifierLoc *argumentKind, ParsedType matchingCType, bool layoutCompatible, bool mustBeNull, ParsedAttr::Syntax syntax)
Add type_tag_for_datatype attribute.
void ClearConstexprSpec()
bool mayBeFollowedByCXXDirectInit() const
mayBeFollowedByCXXDirectInit - Return true if the declarator can be followed by a C++ direct initiali...
A class for parsing a declarator.
bool isPastIdentifier() const
isPastIdentifier - Return true if we have parsed beyond the point where the name would appear...
void SetRangeStart(SourceLocation Loc)
The name was classified as a function template name.
unsigned NumParams
NumParams - This is the number of formal parameters specified by the declarator.
void ActOnReenterCXXMethodParameter(Scope *S, ParmVarDecl *Param)
This is used to implement the constant expression evaluation part of the attribute enable_if extensio...
TST getTypeSpecType() const
static StringRef getSourceText(CharSourceRange Range, const SourceManager &SM, const LangOptions &LangOpts, bool *Invalid=nullptr)
Returns a string for the source that the range encompasses.
static bool isAtEndOfMacroExpansion(SourceLocation loc, const SourceManager &SM, const LangOptions &LangOpts, SourceLocation *MacroEnd=nullptr)
Returns true if the given MacroID location points at the last token of the macro expansion.
The current expression is potentially evaluated, but any declarations referenced inside that expressi...
ParsedAttr * addNewPropertyAttr(IdentifierInfo *attrName, SourceRange attrRange, IdentifierInfo *scopeName, SourceLocation scopeLoc, IdentifierInfo *getterId, IdentifierInfo *setterId, ParsedAttr::Syntax syntaxUsed)
Add microsoft __delspec(property) attribute.
Decl * ParsedFreeStandingDeclSpec(Scope *S, AccessSpecifier AS, DeclSpec &DS, RecordDecl *&AnonRecord)
ParsedFreeStandingDeclSpec - This method is invoked when a declspec with no declarator (e...
void setDecompositionBindings(SourceLocation LSquareLoc, ArrayRef< DecompositionDeclarator::Binding > Bindings, SourceLocation RSquareLoc)
Set the decomposition bindings for this declarator.
Represents a character-granular source range.
void SkipMalformedDecl()
SkipMalformedDecl - Read tokens until we get to some likely good stopping point for skipping past a s...
bool ParseUnqualifiedId(CXXScopeSpec &SS, bool EnteringContext, bool AllowDestructorName, bool AllowConstructorName, bool AllowDeductionGuide, ParsedType ObjectType, SourceLocation *TemplateKWLoc, UnqualifiedId &Result)
Parse a C++ unqualified-id (or a C identifier), which describes the name of an entity.
static DeclaratorChunk getPipe(unsigned TypeQuals, SourceLocation Loc)
Return a DeclaratorChunk for a block.
TypeResult ActOnTypeName(Scope *S, Declarator &D)
bool isTypeAltiVecVector() const
The name was classified as a specific non-type, non-template declaration.
void setEofData(const void *D)
The name refers to a concept.
static bool isPipeDeclerator(const Declarator &D)
SourceLocation getVolatileSpecLoc() const
SourceLocation getThreadStorageClassSpecLoc() const
static constexpr bool isOneOf()
SourceLocation getLocation() const
Return a source location identifier for the specified offset in the current file. ...
void setAsmLabel(Expr *E)
DeclContext * getDeclContext()
static const TST TST_decimal64
This is a compound statement scope.
SourceLocation getStorageClassSpecLoc() const
UnqualifiedIdKind getKind() const
Determine what kind of name we have.
The current expression and its subexpressions occur within an unevaluated operand (C++11 [expr]p7)...
void UpdateTypeRep(ParsedType Rep)
SourceLocation KeywordLoc
The location of the keyword indicating the kind of change.
A class for parsing a field declarator.
bool isValid() const
Determine whether this availability change is valid.
SourceLocation Loc
Loc - The place where this type was defined.
static SourceLocation getMissingDeclaratorIdLoc(Declarator &D, SourceLocation Loc)
void setEllipsisLoc(SourceLocation EL)
SourceLocation getEnd() const
bool SetTypeSpecSign(TSS S, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
SourceLocation getOpenLocation() const
static const TST TST_half
bool isFriendSpecified() const
Wraps an identifier and optional source location for the identifier.
void ActOnCXXEnterDeclInitializer(Scope *S, Decl *Dcl)
ActOnCXXEnterDeclInitializer - Invoked when we are about to parse an initializer for the declaration ...
The result type of a method or function.
SourceRange VersionRange
The source range covering the version number.
bool isNull() const
Return true if this QualType doesn't point to a type yet.
static const TSW TSW_short
PrettyDeclStackTraceEntry - If a crash occurs in the parser while parsing something related to a decl...
bool isFirstDeclarator() const
const LangOptions & getLangOpts() const
bool SetTypeSpecWidth(TSW W, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID, const PrintingPolicy &Policy)
These methods set the specified attribute of the DeclSpec, but return true and ignore the request if ...
This is a scope that corresponds to the parameters within a function prototype for a function declara...
bool hasGroupingParens() const
SourceManager & getSourceManager() const
ConstexprSpecKind getConstexprSpecifier() const
static const TST TST_char32
static const TST TST_fract
A class for parsing a DeclSpec.
bool isTemplateDecl() const
returns true if this declaration is a template
static DeclaratorChunk getParen(SourceLocation LParenLoc, SourceLocation RParenLoc)
Return a DeclaratorChunk for a paren.
Stop skipping at semicolon.
ActionResult - This structure is used while parsing/acting on expressions, stmts, etc...
static DeclaratorChunk getReference(unsigned TypeQuals, SourceLocation Loc, bool lvalue)
Return a DeclaratorChunk for a reference.
SCS getStorageClassSpec() const
static const TST TST_float16
bool hasName() const
hasName - Whether this declarator has a name, which might be an identifier (accessible via getIdentif...
Encodes a location in the source.
void ActOnFinishDelayedMemberDeclarations(Scope *S, Decl *Record)
bool isTypeSpecOwned() const
static const TST TST_auto_type
bool TryAnnotateTypeOrScopeToken()
TryAnnotateTypeOrScopeToken - If the current token position is on a typename (possibly qualified in C...
enum clang::DeclaratorChunk::@219 Kind
UnqualifiedId & getName()
Retrieve the name specified by this declarator.
void FinalizeDeclaration(Decl *D)
FinalizeDeclaration - called by ParseDeclarationAfterDeclarator to perform any semantic actions neces...
static void SetupFixedPointError(const LangOptions &LangOpts, const char *&PrevSpec, unsigned &DiagID, bool &isInvalid)
Represents the declaration of a struct/union/class/enum.
void ExitScope()
ExitScope - Pop a scope off the scope stack.
This is a scope that corresponds to the Objective-C @catch statement.
ASTContext & getASTContext() const LLVM_READONLY
SourceLocation getEndLoc() const LLVM_READONLY
static const TST TST_union
IdentifierInfo * getIdentifierInfo() const
ParsedAttr - Represents a syntactic attribute.
bool SetStorageClassSpec(Sema &S, SCS SC, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID, const PrintingPolicy &Policy)
These methods set the specified attribute of the DeclSpec and return false if there was no error...
bool hasTrailingRequiresClause() const
Determine whether a trailing requires clause was written in this declarator.
bool isWrittenInBuiltinFile(SourceLocation Loc) const
Returns whether Loc is located in a <built-in> file.
static const TSS TSS_signed
ExtensionRAIIObject - This saves the state of extension warnings when constructed and disables them...
void setGroupingParens(bool flag)
ParsedAttr * addNew(IdentifierInfo *attrName, SourceRange attrRange, IdentifierInfo *scopeName, SourceLocation scopeLoc, ArgsUnion *args, unsigned numArgs, ParsedAttr::Syntax syntax, SourceLocation ellipsisLoc=SourceLocation())
Add attribute with expression arguments.
void EnterScope(unsigned ScopeFlags)
EnterScope - Start a new scope.
const char * getNameStart() const
Return the beginning of the actual null-terminated string for this identifier.
This name is not a type or template in this context, but might be something else. ...
const void * getEofData() const
bool isAtStartOfLine() const
isAtStartOfLine - Return true if this token is at the start of a line.
static bool isPtrOperatorToken(tok::TokenKind Kind, const LangOptions &Lang, DeclaratorContext TheContext)
TokenKind
Provides a simple uniform namespace for tokens from all C languages.
void remove(ParsedAttr *ToBeRemoved)
Decl * getRepAsDecl() const
static const TST TST_typeofType
Used for C's _Alignof and C++'s alignof.
Scope * getCurScope() const
bool SetTypeAltiVecVector(bool isAltiVecVector, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID, const PrintingPolicy &Policy)
SourceLocation getInlineSpecLoc() const
static DeclaratorChunk getArray(unsigned TypeQuals, bool isStatic, bool isStar, Expr *NumElts, SourceLocation LBLoc, SourceLocation RBLoc)
Return a DeclaratorChunk for an array.
ExprResult ParseConstantExpressionInExprEvalContext(TypeCastState isTypeCast=NotTypeCast)
bool isInvalid() const
An error occurred during parsing of the scope specifier.
SourceLocation getModulePrivateSpecLoc() const
StringRef getName() const
Return the actual identifier string.
The scope of a struct/union/class definition.
SourceRange getSourceRange() const LLVM_READONLY
Get the source range that spans this declarator.
bool isNot(tok::TokenKind K) const
void ActOnReenterFunctionContext(Scope *S, Decl *D)
Push the parameters of D, which must be a function, into scope.
TSW getTypeSpecWidth() const
ParserCompletionContext
Describes the context in which code completion occurs.
bool setModulePrivateSpec(SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
static bool isInvalid(LocType Loc, bool *Invalid)
Dataflow Directional Tag Classes.
bool isValid() const
Return true if this is a valid SourceLocation object.
bool expectAndConsume(unsigned DiagID=diag::err_expected, const char *Msg="", tok::TokenKind SkipToTok=tok::unknown)
static const TST TST_auto
static const TST TST_void
bool isFunctionOrFunctionTemplate() const
Whether this declaration is a function or function template.
static const TST TST_int128
static FixItHint CreateRemoval(CharSourceRange RemoveRange)
Create a code modification hint that removes the given source range.
SourceLocation getPipeLoc() const
This is a scope that corresponds to the template parameters of a C++ template.
bool isOneOf(tok::TokenKind K1, tok::TokenKind K2) const
The name refers to a template whose specialization produces a type.
static const TST TST_unspecified
unsigned getLength() const
bool isValid() const
A scope specifier is present, and it refers to a real scope.
LLVM_READONLY bool isDigit(unsigned char c)
Return true if this character is an ASCII digit: [0-9].
FileID getFileID(SourceLocation SpellingLoc) const
Return the FileID for a SourceLocation.
const TargetInfo & getTargetInfo() const
static const TST TST_decimal128
unsigned getTypeQualifiers() const
getTypeQualifiers - Return a set of TQs.
void takeAttributesFrom(ParsedAttributes &attrs)
DiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID)
static const TSCS TSCS___thread
SourceLocation getVirtualSpecLoc() const
bool SetStorageClassSpecThread(TSCS TSC, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
static const TST TST_typename
The name was classified as an ADL-only function name.
void SetRangeEnd(SourceLocation Loc)
SetRangeEnd - Set the end of the source range to Loc, unless it's invalid.
ExprResult ParseAssignmentExpression(TypeCastState isTypeCast=NotTypeCast)
Parse an expr that doesn't include (top-level) commas.
ExceptionSpecificationType
The various types of exception specifications that exist in C++11.
void ActOnCXXForRangeDecl(Decl *D)
static FixItHint CreateInsertion(SourceLocation InsertionLoc, StringRef Code, bool BeforePreviousInsertions=false)
Create a code modification hint that inserts the given code string at a specific location.
void AddTypeInfo(const DeclaratorChunk &TI, ParsedAttributes &&attrs, SourceLocation EndLoc)
AddTypeInfo - Add a chunk to this declarator.
CharSourceRange getExpansionRange(SourceLocation Loc) const
Given a SourceLocation object, return the range of tokens covered by the expansion in the ultimate fi...
CXXScopeSpec & getTypeSpecScope()
This is a scope that can contain a declaration.
bool SetTypeSpecType(TST T, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID, const PrintingPolicy &Policy)
SourceLocation getIdentifierLoc() const
bool isSet() const
Deprecated.
The name was classified as a concept name.
X
Add a minimal nested name specifier fixit hint to allow lookup of a tag name from an outer enclosing ...
ParsedAttr * addNewTypeAttr(IdentifierInfo *attrName, SourceRange attrRange, IdentifierInfo *scopeName, SourceLocation scopeLoc, ParsedType typeArg, ParsedAttr::Syntax syntaxUsed)
Add an attribute with a single type argument.
void setInvalidType(bool Val=true)
ExprResult ParseConstantExpression(TypeCastState isTypeCast=NotTypeCast)
static constexpr unsigned getMaxFunctionScopeDepth()
static DeclaratorChunk getBlockPointer(unsigned TypeQuals, SourceLocation Loc)
Return a DeclaratorChunk for a block.
static bool attributeParsedArgsUnevaluated(const IdentifierInfo &II)
Determine whether the given attribute requires parsing its arguments in an unevaluated context or not...
Captures information about "declaration specifiers".
SourceLocation getRestrictSpecLoc() const
static bool isValidAfterIdentifierInDeclarator(const Token &T)
isValidAfterIdentifierInDeclaratorAfterDeclSpec - Return true if the specified token is valid after t...
DeclGroupPtrTy FinalizeDeclaratorGroup(Scope *S, const DeclSpec &DS, ArrayRef< Decl *> Group)
SourceLocation ConsumeToken()
ConsumeToken - Consume the current 'peek token' and lex the next one.
static const TSCS TSCS_thread_local
SourceLocation getEllipsisLoc() const
bool SetTypeSpecSat(SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
bool isPragmaAnnotation(TokenKind K)
Return true if this is an annotation token representing a pragma.
bool mayHaveIdentifier() const
mayHaveIdentifier - Return true if the identifier is either optional or required. ...
bool isNotEmpty() const
A scope specifier is present, but may be valid or invalid.
static const TST TST_float128
const DeclSpec & getDeclSpec() const
getDeclSpec - Return the declaration-specifier that this declarator was declared with.
static const TST TST_bool
bool isVirtualSpecified() const
Decl * getObjCDeclContext() const
static FixItHint CreateReplacement(CharSourceRange RemoveRange, StringRef Code)
Create a code modification hint that replaces the given source range with the given code string...
A template-id, e.g., f<int>.
void Finish(Sema &S, const PrintingPolicy &Policy)
Finish - This does final analysis of the declspec, issuing diagnostics for things like "_Imaginary" (...
StringLiteral - This represents a string literal expression, e.g.
Defines the clang::TargetInfo interface.
bool isInlineSpecified() const
void ExtendWithDeclSpec(const DeclSpec &DS)
ExtendWithDeclSpec - Extend the declarator source range to include the given declspec, unless its location is invalid.
SourceLocation getAtomicSpecLoc() const
static const TSW TSW_longlong
static Decl::Kind getKind(const Decl *D)
SourceLocation getExplicitSpecLoc() const
SourceLocation getConstexprSpecLoc() const
static bool attributeIsTypeArgAttr(const IdentifierInfo &II)
Determine whether the given attribute parses a type argument.
static const TST TST_atomic
static bool attributeTreatsKeywordThisAsIdentifier(const IdentifierInfo &II)
Determine whether the given attribute treats kw_this as an identifier.
bool isEmpty() const
isEmpty - Return true if this declaration specifier is completely empty: no tokens were parsed in the...
void addAddressSpace(LangAS space)
static const TST TST_struct
Annotates a diagnostic with some code that should be inserted, removed, or replaced to fix the proble...
ParamInfo - An array of paraminfo objects is allocated whenever a function declarator is parsed...
DeclaratorContext getContext() const
Kind getParsedKind() const
void setLocation(SourceLocation L)
A trivial tuple used to represent a source range.
bool SetTypeSpecComplex(TSC C, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
This represents a decl that may have a name.
SourceLocation EndLocation
The location of the last token that describes this unqualified-id.
static const TSCS TSCS__Thread_local
Callback handler that receives notifications when performing code completion within the preprocessor...
void * getAnnotationValue() const
bool isFirstDeclarationOfMember()
Returns true if this declares a real member and not a friend.
void SetRangeEnd(SourceLocation Loc)
void addAttributes(ParsedAttributesView &AL)
Concatenates two attribute lists.
SourceLocation getBegin() const
ParsedAttributes - A collection of parsed attributes.
void setCommaLoc(SourceLocation CL)
This class handles loading and caching of source files into memory.
ExprResult ParseConstraintLogicalOrExpression(bool IsTrailingRequiresClause)
Parse a constraint-logical-or-expression.
ParamInfo * Params
Params - This is a pointer to a new[]'d array of ParamInfo objects that describe the parameters speci...
TypeResult ParseTypeName(SourceRange *Range=nullptr, DeclaratorContext Context=DeclaratorContext::TypeNameContext, AccessSpecifier AS=AS_none, Decl **OwnedType=nullptr, ParsedAttributes *Attrs=nullptr)
ParseTypeName type-name: [C99 6.7.6] specifier-qualifier-list abstract-declarator[opt].
ParsedAttributes & getAttributes()
SourceLocation getLocation() const
void startToken()
Reset all flags to cleared.
Decl * ActOnDeclarator(Scope *S, Declarator &D)
Engages in a tight little dance with the lexer to efficiently preprocess tokens.
bool isCXXInstanceMember() const
Determine whether the given declaration is an instance member of a C++ class.
static DeclaratorChunk getMemberPointer(const CXXScopeSpec &SS, unsigned TypeQuals, SourceLocation Loc)
bool setFunctionSpecInline(SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID)
Stop skipping at specified token, but don't skip the token itself.
unsigned ActOnReenterTemplateScope(Scope *S, Decl *Template)
SourceLocation getEndLoc() const