clang: lib/Parse/ParseExpr.cpp Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

42#include "llvm/ADT/SmallVector.h"

43#include

44using namespace clang;

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

121

122

123

124

125

126

127

128

129

130

131

132

133

136 return ParseRHSOfBinaryExpression(LHS, prec::Comma);

137}

138

139

140

141

142

143

145Parser::ParseExpressionWithLeadingAt(SourceLocation AtLoc) {

146 ExprResult LHS(ParseObjCAtExpression(AtLoc));

147 return ParseRHSOfBinaryExpression(LHS, prec::Comma);

148}

149

150

151

152

154Parser::ParseExpressionWithLeadingExtension(SourceLocation ExtLoc) {

156 {

157

159

160 LHS = ParseCastExpression(AnyCastExpr);

161 }

162

163 if (!LHS.isInvalid())

165 LHS.get());

166

167 return ParseRHSOfBinaryExpression(LHS, prec::Comma);

168}

169

170

172 if (Tok.is(tok::code_completion)) {

173 cutOffParsing();

177 }

178

179 if (Tok.is(tok::kw_throw))

180 return ParseThrowExpression();

181 if (Tok.is(tok::kw_co_yield))

182 return ParseCoyieldExpression();

183

184 ExprResult LHS = ParseCastExpression(AnyCastExpr,

185 false,

186 isTypeCast);

188}

189

191 if (Tok.is(tok::code_completion)) {

192 cutOffParsing();

196 }

197

198 ExprResult LHS = ParseCastExpression(

199 AnyCastExpr, false, NotTypeCast);

201}

202

203

204

205

206

207

208

209

210

211

213Parser::ParseAssignmentExprWithObjCMessageExprStart(SourceLocation LBracLoc,

216 Expr *ReceiverExpr) {

218 = ParseObjCMessageExpressionBody(LBracLoc, SuperLoc,

219 ReceiverType, ReceiverExpr);

220 R = ParsePostfixExpressionSuffix(R);

222}

223

228 "Call this function only if your ExpressionEvaluationContext is "

229 "already ConstantEvaluated");

230 ExprResult LHS(ParseCastExpression(AnyCastExpr, false, isTypeCast));

233}

234

236

237

238

239

243}

244

248

249

250 Actions.ExprEvalContexts.back().InConditionallyConstantEvaluateContext = true;

251

252

253

254

255

256

257

258

259

260

261

262

263

266 if (Iter->isUnevaluated())

267 break;

268 Iter->InConditionallyConstantEvaluateContext = true;

269 }

271}

272

279}

280

281

282

283

284

285

286

290 ExprResult LHS(ParseCastExpression(AnyCastExpr));

295 }

296 return Res;

297}

298

299

300

301

302

303

304

305

306

307

312 bool NotPrimaryExpression = false;

313 auto ParsePrimary = [&] () {

314 ExprResult E = ParseCastExpression(PrimaryExprOnly,

315 false,

317 false,

318 &NotPrimaryExpression);

319 if (E.isInvalid())

321 auto RecoverFromNonPrimary = [&] (ExprResult E, bool Note) {

322 E = ParsePostfixExpressionSuffix(E);

323

324

326 if (E.isInvalid())

329 ? diag::note_unparenthesized_non_primary_expr_in_requires_clause

330 : diag::err_unparenthesized_non_primary_expr_in_requires_clause)

335 return E;

336 };

337

338 if (NotPrimaryExpression ||

339

340

343

344

345 Tok.isOneOf(tok::period, tok::plusplus, tok::minusminus) ||

346 (Tok.is(tok::l_square) && NextToken().is(tok::l_square))) {

347 E = RecoverFromNonPrimary(E, false);

348 if (E.isInvalid())

350 NotPrimaryExpression = false;

351 }

352 bool PossibleNonPrimary;

353 bool IsConstraintExpr =

355 IsTrailingRequiresClause);

356 if (!IsConstraintExpr || PossibleNonPrimary) {

357

358

359

360

361 if (PossibleNonPrimary)

362 E = RecoverFromNonPrimary(E, !IsConstraintExpr);

365 }

366 return E;

367 };

371 while (Tok.is(tok::ampamp)) {

377 }

379 tok::ampamp, LHS.get(), RHS.get());

384 }

385 LHS = Op;

386 }

387 return LHS;

388}

389

390

391

392

393

394

395

396

397

398

399

405 while (Tok.is(tok::pipepipe)) {

412 }

414 tok::pipepipe, LHS.get(), RHS.get());

419 }

420 LHS = Op;

421 }

422 return LHS;

423}

424

425bool Parser::isNotExpressionStart() {

427 if (K == tok::l_brace || K == tok::r_brace ||

428 K == tok::kw_for || K == tok::kw_while ||

429 K == tok::kw_if || K == tok::kw_else ||

430 K == tok::kw_goto || K == tok::kw_try)

431 return true;

432

433 return isKnownToBeDeclarationSpecifier();

434}

435

436bool Parser::isFoldOperator(prec::Level Level) const {

439}

440

441bool Parser::isFoldOperator(tok::TokenKind Kind) const {

442 return isFoldOperator(getBinOpPrecedence(Kind, GreaterThanIsOperator, true));

443}

444

445

446

450 GreaterThanIsOperator,

453

454 auto SavedType = PreferredType;

455 while (true) {

456

457 PreferredType = SavedType;

458

459

460

461 if (NextTokPrec < MinPrec)

462 return LHS;

463

464

465 Token OpToken = Tok;

467

468

469

470 if (OpToken.isOneOf(tok::comma, tok::greater, tok::greatergreater,

471 tok::greatergreatergreater) &&

472 checkPotentialAngleBracketDelimiter(OpToken))

474

475

476

477

478

479

480 if (OpToken.is(tok::comma) && isNotExpressionStart()) {

481 PP.EnterToken(Tok, true);

482 Tok = OpToken;

483 return LHS;

484 }

485

486

487

488 if (isFoldOperator(NextTokPrec) && Tok.is(tok::ellipsis)) {

489

490

491 PP.EnterToken(Tok, true);

492 Tok = OpToken;

493 return LHS;

494 }

495

496

497

498

499

500

502 Tok.isOneOf(tok::colon, tok::r_square) &&

504 PP.EnterToken(Tok, true);

505 Tok = OpToken;

506 return LHS;

507 }

508

509

513

515 TernaryMiddle = ParseBraceInitializer();

516 if (!TernaryMiddle.isInvalid()) {

517 Diag(BraceLoc, diag::err_init_list_bin_op)

519 << Actions.getExprRange(TernaryMiddle.get());

521 }

522 } else if (Tok.isNot(tok::colon)) {

523

525

526

527

528

529

531 } else {

532

533

534 TernaryMiddle = nullptr;

535 Diag(Tok, diag::ext_gnu_conditional_expr);

536 }

537

538 if (TernaryMiddle.isInvalid()) {

541 TernaryMiddle = nullptr;

542 }

543

545

546

547

548

550 const char *FIText = ": ";

554 bool IsInvalid = false;

555 const char *SourcePtr =

557 if (!IsInvalid && *SourcePtr == ' ') {

558 SourcePtr =

560 if (!IsInvalid && *SourcePtr == ' ') {

562 FIText = ":";

563 }

564 }

565 }

566

567 Diag(Tok, diag::err_expected)

569 Diag(OpToken, diag::note_matching) << tok::question;

571 }

572 }

573

576

577

578

579

580

581

582

583

584

585

587 bool RHSIsInitList = false;

589 RHS = ParseBraceInitializer();

590 RHSIsInitList = true;

593 else

594 RHS = ParseCastExpression(AnyCastExpr);

595

597

598

600 if (TernaryMiddle.isUsable())

603 }

604

605

606

610

611

614

615

616

617 if (ThisPrec < NextTokPrec ||

618 (ThisPrec == NextTokPrec && isRightAssoc)) {

619 if (!RHS.isInvalid() && RHSIsInitList) {

620 Diag(Tok, diag::err_init_list_bin_op)

623 }

624

625

626

627

628

629 RHS = ParseRHSOfBinaryExpression(RHS,

630 static_cast<prec::Level>(ThisPrec + !isRightAssoc));

631 RHSIsInitList = false;

632

634

635

637 if (TernaryMiddle.isUsable())

640 }

641

644 }

645

646 if (!RHS.isInvalid() && RHSIsInitList) {

648 Diag(OpToken, diag::warn_cxx98_compat_generalized_initializer_lists)

650 } else if (ColonLoc.isValid()) {

651 Diag(ColonLoc, diag::err_init_list_bin_op)

652 << 1 << ":"

655 } else {

656 Diag(OpToken, diag::err_init_list_bin_op)

660 }

661 }

662

665

666 if (TernaryMiddle.isInvalid()) {

667

668

669

670 if (!GreaterThanIsOperator && OpToken.is(tok::greatergreater))

671 SuggestParentheses(OpToken.getLocation(),

672 diag::warn_cxx11_right_shift_in_template_arg,

675

682 {LHS.get(), RHS.get()});

683

684 LHS = BinOp;

685 } else {

687 OpToken.getLocation(), ColonLoc, LHS.get(), TernaryMiddle.get(),

688 RHS.get());

690 std::vector<clang::Expr *> Args;

691

692 if (TernaryMiddle.get())

693 Args = {LHS.get(), TernaryMiddle.get(), RHS.get()};

694 else

695 Args = {LHS.get(), RHS.get()};

698 }

699

700 LHS = CondOp;

701 }

702

703

705 continue;

706 }

707

708

713 }

714 }

715}

716

717

718

719

720

721

722

723ExprResult Parser::ParseCastExpression(CastParseKind ParseKind,

724 bool isAddressOfOperand,

725 TypeCastState isTypeCast,

726 bool isVectorLiteral,

727 bool *NotPrimaryExpression) {

728 bool NotCastExpr;

729 ExprResult Res = ParseCastExpression(ParseKind,

730 isAddressOfOperand,

731 NotCastExpr,

732 isTypeCast,

733 isVectorLiteral,

734 NotPrimaryExpression);

735 if (NotCastExpr)

736 Diag(Tok, diag::err_expected_expression);

737 return Res;

738}

739

740namespace {

742 public:

743 CastExpressionIdValidator(Token Next, bool AllowTypes, bool AllowNonTypes)

744 : NextToken(Next), AllowNonTypes(AllowNonTypes) {

745 WantTypeSpecifiers = WantFunctionLikeCasts = AllowTypes;

746 }

747

748 bool ValidateCandidate(const TypoCorrection &candidate) override {

750 if (!ND)

752

753 if (isa(ND))

754 return WantTypeSpecifiers;

755

757 return false;

758

759 if (!NextToken.isOneOf(tok::equal, tok::arrow, tok::period))

760 return true;

761

762 for (auto *C : candidate) {

763 NamedDecl *ND = C->getUnderlyingDecl();

764 if (isa(ND) && !isa(ND))

765 return true;

766 }

767 return false;

768 }

769

770 std::unique_ptr clone() override {

771 return std::make_unique(*this);

772 }

773

774 private:

776 bool AllowNonTypes;

777};

778}

779

780bool Parser::isRevertibleTypeTrait(const IdentifierInfo *II,

782 if (RevertibleTypeTraits.empty()) {

783

784

785

786#define RTT_JOIN(X, Y) X##Y

787#define REVERTIBLE_TYPE_TRAIT(Name) \

788 RevertibleTypeTraits[PP.getIdentifierInfo(#Name)] = RTT_JOIN(tok::kw_, Name)

789

846#define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) \

847 REVERTIBLE_TYPE_TRAIT(RTT_JOIN(__, Trait));

848#include "clang/Basic/TransformTypeTraits.def"

849#undef REVERTIBLE_TYPE_TRAIT

850#undef RTT_JOIN

851 }

852 llvm::SmallDenseMap<IdentifierInfo *, tok::TokenKind>::iterator Known =

853 RevertibleTypeTraits.find(II);

854 if (Known != RevertibleTypeTraits.end()) {

855 if (Kind)

856 *Kind = Known->second;

857 return true;

858 }

859 return false;

860}

861

862ExprResult Parser::ParseBuiltinPtrauthTypeDiscriminator() {

864

866 if (T.expectAndConsume())

868

873 }

874

876 T.consumeClose();

878 Loc, UETT_PtrAuthTypeDiscriminator,

879 true, Ty.get().getAsOpaquePtr(), SourceRange(Loc, EndLoc));

880}

881

882

883

884

885

886

887

888

889

890

891

892

893

894

895

896

897

898

899

900

901

902

903

904

905

906

907

908

909

910

911

912

913

914

915

916

917

918

919

920

921

922

923

924

925

926

927

928

929

930

931

932

933

934

935

936

937

938

939

940

941

942

943

944

945

946

947

948

949

950

951

952

953

954

955

956

957

958

959

960

961

962

963

964

965

966

967

968

969

970

971

972

973

974

975

976

977

978

979

980

981

982

983

984

985

986

987

988

989

990

991

992

993

994

995

996

997

998

999

1000

1001

1002

1003

1004

1005

1006

1007

1008

1009

1010

1011

1012

1013

1014

1015

1016

1017

1018

1019

1020

1021

1022

1023

1024

1025

1026

1027

1028

1029

1030

1031

1032

1033

1034

1035

1036

1037

1038

1039

1040

1041

1042

1043

1044

1045

1046

1047

1048

1049

1050

1051

1052

1053

1054

1055

1056

1057

1058

1059

1060

1061

1062

1063

1064

1065ExprResult Parser::ParseCastExpression(CastParseKind ParseKind,

1066 bool isAddressOfOperand,

1067 bool &NotCastExpr,

1068 TypeCastState isTypeCast,

1069 bool isVectorLiteral,

1070 bool *NotPrimaryExpression) {

1073 auto SavedType = PreferredType;

1074 NotCastExpr = false;

1075

1076

1077

1078

1079 bool AllowSuffix = true;

1080

1081

1082

1083

1084

1085

1086

1087

1088

1089

1090

1091 switch (SavedKind) {

1092 case tok::l_paren: {

1093

1094

1095 ParenParseOption ParenExprType;

1096 switch (ParseKind) {

1097 case CastParseKind::UnaryExprOnly:

1099 [[fallthrough]];

1100 case CastParseKind::AnyCastExpr:

1101 ParenExprType = ParenParseOption::CastExpr;

1102 break;

1103 case CastParseKind::PrimaryExprOnly:

1104 ParenExprType = FoldExpr;

1105 break;

1106 }

1109 Res = ParseParenExpression(ParenExprType, false,

1110 isTypeCast == IsTypeCast, CastTy, RParenLoc);

1111

1112

1113

1114

1115 if (isVectorLiteral)

1116 return Res;

1117

1118 switch (ParenExprType) {

1119 case SimpleExpr: break;

1120 case CompoundStmt: break;

1121 case CompoundLiteral:

1122

1123

1124 break;

1126

1127

1128 return Res;

1129 case FoldExpr:

1130

1131

1132 break;

1133 }

1134

1135 break;

1136 }

1137

1138

1139 case tok::numeric_constant:

1140 case tok::binary_data:

1141

1142

1143

1146 break;

1147

1148 case tok::kw_true:

1149 case tok::kw_false:

1150 Res = ParseCXXBoolLiteral();

1151 break;

1152

1153 case tok::kw___objc_yes:

1154 case tok::kw___objc_no:

1155 Res = ParseObjCBoolLiteral();

1156 break;

1157

1158 case tok::kw_nullptr:

1160 Diag(Tok, diag::warn_cxx98_compat_nullptr);

1161 else

1163 : diag::ext_c_nullptr) << Tok.getName();

1164

1166 break;

1167

1168 case tok::annot_primary_expr:

1169 case tok::annot_overload_set:

1170 Res = getExprAnnotation(Tok);

1171 if (!Res.isInvalid() && Tok.getKind() == tok::annot_overload_set)

1173 ConsumeAnnotationToken();

1174 if (!Res.isInvalid() && Tok.is(tok::less))

1175 checkPotentialAngleBracket(Res);

1176 break;

1177

1178 case tok::annot_non_type:

1179 case tok::annot_non_type_dependent:

1180 case tok::annot_non_type_undeclared: {

1182 Token Replacement;

1183 Res = tryParseCXXIdExpression(SS, isAddressOfOperand, Replacement);

1184 assert(!Res.isUnset() &&

1185 "should not perform typo correction on annotation token");

1186 break;

1187 }

1188

1189 case tok::annot_embed: {

1190 injectEmbedTokens();

1191 return ParseCastExpression(ParseKind, isAddressOfOperand, isTypeCast,

1192 isVectorLiteral, NotPrimaryExpression);

1193 }

1194

1195 case tok::kw___super:

1196 case tok::kw_decltype:

1197

1200 assert(Tok.isNot(tok::kw_decltype) && Tok.isNot(tok::kw___super));

1201 return ParseCastExpression(ParseKind, isAddressOfOperand, isTypeCast,

1202 isVectorLiteral, NotPrimaryExpression);

1203

1204 case tok::identifier:

1205 ParseIdentifier: {

1206

1207

1208

1209

1211

1212

1214

1215 if (Next.is(tok::ellipsis) && Tok.is(tok::identifier) &&

1216 GetLookAheadToken(2).is(tok::l_square)) {

1217

1218

1219

1221 Tok.isOneOf(tok::annot_pack_indexing_type, tok::annot_cxxscope))

1222 return ParseCastExpression(ParseKind, isAddressOfOperand, isTypeCast,

1223 isVectorLiteral, NotPrimaryExpression);

1224 }

1225

1226

1227

1228

1229 else if (Next.is(tok::l_paren) && Tok.is(tok::identifier) &&

1233 if (isRevertibleTypeTrait(II, &Kind)) {

1235 return ParseCastExpression(ParseKind, isAddressOfOperand,

1236 NotCastExpr, isTypeCast,

1237 isVectorLiteral, NotPrimaryExpression);

1238 }

1239 }

1240

1241 else if ((!ColonIsSacred && Next.is(tok::colon)) ||

1242 Next.isOneOf(tok::coloncolon, tok::less, tok::l_paren,

1243 tok::l_brace)) {

1244

1247 if (!Tok.is(tok::identifier))

1248 return ParseCastExpression(ParseKind, isAddressOfOperand,

1249 NotCastExpr, isTypeCast,

1250 isVectorLiteral,

1251 NotPrimaryExpression);

1252 }

1253 }

1254

1255

1256

1259

1260

1263

1264 (&II == Ident_super && getCurScope()->isInObjcMethodScope()))) {

1266

1267 if (Tok.is(tok::code_completion) && &II != Ident_super) {

1268 cutOffParsing();

1270 getCurScope(), II, ILoc, ExprStatementTokLoc == ILoc);

1272 }

1273

1274 if (Tok.isNot(tok::identifier) &&

1276 Diag(Tok, diag::err_expected_property_name);

1278 }

1281

1283 PropertyLoc);

1284 break;

1285 }

1286

1287

1288

1289

1290

1291 if (getLangOpts().ObjC && &II == Ident_super && !InMessageExpression &&

1293 ((Tok.is(tok::identifier) &&

1295 Tok.is(tok::code_completion))) {

1296 Res = ParseObjCMessageExpressionBody(SourceLocation(), ILoc, nullptr,

1297 nullptr);

1298 break;

1299 }

1300

1301

1302

1303

1304

1305

1307 ((Tok.is(tok::identifier) && !InMessageExpression) ||

1308 Tok.is(tok::code_completion))) {

1310 if (Tok.is(tok::code_completion) ||

1311 Next.is(tok::colon) || Next.is(tok::r_square))

1313 if (Typ.get()->isObjCObjectOrInterfaceType()) {

1314

1316 DS.SetRangeStart(ILoc);

1317 DS.SetRangeEnd(ILoc);

1318 const char *PrevSpec = nullptr;

1319 unsigned DiagID;

1320 DS.SetTypeSpecType(TST_typename, ILoc, PrevSpec, DiagID, Typ,

1322

1327 break;

1328

1329 Res = ParseObjCMessageExpressionBody(SourceLocation(),

1331 Ty.get(), nullptr);

1332 break;

1333 }

1334 }

1335

1336

1337 if (isAddressOfOperand && isPostfixExpressionSuffixStart())

1338 isAddressOfOperand = false;

1339

1340

1341

1342

1346 Token Replacement;

1347 CastExpressionIdValidator Validator(

1348 Tok,

1349 isTypeCast != NotTypeCast,

1350 isTypeCast != IsTypeCast);

1351 Validator.IsAddressOfOperand = isAddressOfOperand;

1352 if (Tok.isOneOf(tok::periodstar, tok::arrowstar)) {

1353 Validator.WantExpressionKeywords = false;

1354 Validator.WantRemainingKeywords = false;

1355 } else {

1356 Validator.WantRemainingKeywords = Tok.isNot(tok::r_paren);

1357 }

1358 Name.setIdentifier(&II, ILoc);

1360 getCurScope(), ScopeSpec, TemplateKWLoc, Name, Tok.is(tok::l_paren),

1361 isAddressOfOperand, &Validator,

1362 false,

1363 Tok.is(tok::r_paren) ? nullptr : &Replacement);

1365 UnconsumeToken(Replacement);

1366 return ParseCastExpression(ParseKind, isAddressOfOperand,

1367 NotCastExpr, isTypeCast,

1368 false,

1369 NotPrimaryExpression);

1370 }

1371 Res = tryParseCXXPackIndexingExpression(Res);

1372 if (!Res.isInvalid() && Tok.is(tok::less))

1373 checkPotentialAngleBracket(Res);

1374 break;

1375 }

1376 case tok::char_constant:

1377 case tok::wide_char_constant:

1378 case tok::utf8_char_constant:

1379 case tok::utf16_char_constant:

1380 case tok::utf32_char_constant:

1383 break;

1384 case tok::kw___func__:

1385 case tok::kw___FUNCTION__:

1386 case tok::kw___FUNCDNAME__:

1387 case tok::kw___FUNCSIG__:

1388 case tok::kw_L__FUNCTION__:

1389 case tok::kw_L__FUNCSIG__:

1390 case tok::kw___PRETTY_FUNCTION__:

1391

1392

1393

1399 break;

1400 }

1401 [[fallthrough]];

1402 case tok::string_literal:

1403 case tok::wide_string_literal:

1404 case tok::utf8_string_literal:

1405 case tok::utf16_string_literal:

1406 case tok::utf32_string_literal:

1408 break;

1409 case tok::kw__Generic:

1410 Res = ParseGenericSelectionExpression();

1411 break;

1412 case tok::kw___builtin_available:

1413 Res = ParseAvailabilityCheckExpr(Tok.getLocation());

1414 break;

1415 case tok::kw___builtin_va_arg:

1416 case tok::kw___builtin_offsetof:

1417 case tok::kw___builtin_choose_expr:

1418 case tok::kw___builtin_astype:

1419 case tok::kw___builtin_convertvector:

1420 case tok::kw___builtin_COLUMN:

1421 case tok::kw___builtin_FILE:

1422 case tok::kw___builtin_FILE_NAME:

1423 case tok::kw___builtin_FUNCTION:

1424 case tok::kw___builtin_FUNCSIG:

1425 case tok::kw___builtin_LINE:

1426 case tok::kw___builtin_source_location:

1427 if (NotPrimaryExpression)

1428 *NotPrimaryExpression = true;

1429

1430 return ParseBuiltinPrimaryExpression();

1431 case tok::kw___null:

1433 break;

1434

1435 case tok::plusplus:

1436 case tok::minusminus: {

1437 if (NotPrimaryExpression)

1438 *NotPrimaryExpression = true;

1439

1440

1441

1442

1443 Token SavedTok = Tok;

1445

1448

1449

1450

1452 UnaryExprOnly : AnyCastExpr,

1453 false, NotCastExpr,

1455 if (NotCastExpr) {

1456

1457

1459 UnconsumeToken(SavedTok);

1461 }

1465 SavedKind, Arg);

1469 }

1470 return Res;

1471 }

1472 case tok::amp: {

1473 if (NotPrimaryExpression)

1474 *NotPrimaryExpression = true;

1475

1478

1479 Res = ParseCastExpression(AnyCastExpr, true);

1485 Arg);

1486 }

1487 return Res;

1488 }

1489

1490 case tok:⭐

1491 case tok:➕

1492 case tok:➖

1493 case tok::tilde:

1494 case tok::exclaim:

1495 case tok::kw___real:

1496 case tok::kw___imag: {

1497 if (NotPrimaryExpression)

1498 *NotPrimaryExpression = true;

1501 Res = ParseCastExpression(AnyCastExpr);

1505 isAddressOfOperand);

1508 }

1509 return Res;

1510 }

1511

1512 case tok::kw_co_await: {

1513 if (NotPrimaryExpression)

1514 *NotPrimaryExpression = true;

1516 Res = ParseCastExpression(AnyCastExpr);

1519 return Res;

1520 }

1521

1522 case tok::kw___extension__:{

1523

1524 if (NotPrimaryExpression)

1525 *NotPrimaryExpression = true;

1528 Res = ParseCastExpression(AnyCastExpr);

1531 return Res;

1532 }

1533 case tok::kw__Alignof:

1534 diagnoseUseOfC11Keyword(Tok);

1535 [[fallthrough]];

1536 case tok::kw_alignof:

1537 case tok::kw___alignof:

1538

1539 case tok::kw_sizeof:

1540

1541

1542

1543 case tok::kw___datasizeof:

1544 case tok::kw_vec_step:

1545

1546 case tok::kw___builtin_omp_required_simd_align:

1547 case tok::kw___builtin_vectorelements:

1548 if (NotPrimaryExpression)

1549 *NotPrimaryExpression = true;

1550 AllowSuffix = false;

1551 Res = ParseUnaryExprOrTypeTraitExpression();

1552 break;

1553 case tok::ampamp: {

1554 if (NotPrimaryExpression)

1555 *NotPrimaryExpression = true;

1557 if (Tok.isNot(tok::identifier))

1558 return ExprError(Diag(Tok, diag::err_expected) << tok::identifier);

1559

1560 if (getCurScope()->getFnParent() == nullptr)

1561 return ExprError(Diag(Tok, diag::err_address_of_label_outside_fn));

1562

1563 Diag(AmpAmpLoc, diag::ext_gnu_address_of_label);

1568 AllowSuffix = false;

1569 break;

1570 }

1571 case tok::kw_const_cast:

1572 case tok::kw_dynamic_cast:

1573 case tok::kw_reinterpret_cast:

1574 case tok::kw_static_cast:

1575 case tok::kw_addrspace_cast:

1576 if (NotPrimaryExpression)

1577 *NotPrimaryExpression = true;

1578 Res = ParseCXXCasts();

1579 break;

1580 case tok::kw___builtin_bit_cast:

1581 if (NotPrimaryExpression)

1582 *NotPrimaryExpression = true;

1583 Res = ParseBuiltinBitCast();

1584 break;

1585 case tok::kw_typeid:

1586 if (NotPrimaryExpression)

1587 *NotPrimaryExpression = true;

1588 Res = ParseCXXTypeid();

1589 break;

1590 case tok::kw___uuidof:

1591 if (NotPrimaryExpression)

1592 *NotPrimaryExpression = true;

1593 Res = ParseCXXUuidof();

1594 break;

1595 case tok::kw_this:

1596 Res = ParseCXXThis();

1597 break;

1598 case tok::kw___builtin_sycl_unique_stable_name:

1599 Res = ParseSYCLUniqueStableNameExpression();

1600 break;

1601

1602 case tok::annot_typename:

1603 if (isStartOfObjCClassMessageMissingOpenBracket()) {

1605

1606

1610

1611 const char *PrevSpec = nullptr;

1612 unsigned DiagID;

1614 PrevSpec, DiagID, Type,

1616

1621 break;

1622

1623 ConsumeAnnotationToken();

1625 Ty.get(), nullptr);

1626 break;

1627 }

1628 [[fallthrough]];

1629

1630 case tok::annot_decltype:

1631 case tok::annot_pack_indexing_type:

1632 case tok::kw_char:

1633 case tok::kw_wchar_t:

1634 case tok::kw_char8_t:

1635 case tok::kw_char16_t:

1636 case tok::kw_char32_t:

1637 case tok::kw_bool:

1638 case tok::kw_short:

1639 case tok::kw_int:

1640 case tok::kw_long:

1641 case tok::kw___int64:

1642 case tok::kw___int128:

1643 case tok::kw__ExtInt:

1644 case tok::kw__BitInt:

1645 case tok::kw_signed:

1646 case tok::kw_unsigned:

1647 case tok::kw_half:

1648 case tok::kw_float:

1649 case tok::kw_double:

1650 case tok::kw___bf16:

1651 case tok::kw__Float16:

1652 case tok::kw___float128:

1653 case tok::kw___ibm128:

1654 case tok::kw_void:

1655 case tok::kw_auto:

1656 case tok::kw_typename:

1657 case tok::kw_typeof:

1658 case tok::kw___vector:

1659 case tok::kw__Accum:

1660 case tok::kw__Fract:

1661 case tok::kw__Sat:

1662#define GENERIC_IMAGE_TYPE(ImgType, Id) case tok::kw_##ImgType##_t:

1663#include "clang/Basic/OpenCLImageTypes.def"

1664#define HLSL_INTANGIBLE_TYPE(Name, Id, SingletonId) case tok::kw_##Name:

1665#include "clang/Basic/HLSLIntangibleTypes.def"

1666 {

1668 Diag(Tok, diag::err_expected_expression);

1670 }

1671

1672

1673 if (NotPrimaryExpression)

1674 *NotPrimaryExpression = true;

1675

1676 if (SavedKind == tok::kw_typename) {

1677

1678

1681

1683

1684

1686 }

1687

1688

1689

1690

1692

1693 ParseCXXSimpleTypeSpecifier(DS);

1694 if (Tok.isNot(tok::l_paren) &&

1696 return ExprError(Diag(Tok, diag::err_expected_lparen_after_type)

1697 << DS.getSourceRange());

1698

1699 if (Tok.is(tok::l_brace))

1700 Diag(Tok, diag::warn_cxx98_compat_generalized_initializer_lists);

1701

1702 Res = ParseCXXTypeConstructExpression(DS);

1703 break;

1704 }

1705

1706 case tok::annot_cxxscope: {

1707

1708

1711 if (!Tok.is(tok::annot_cxxscope))

1712 return ParseCastExpression(ParseKind, isAddressOfOperand, NotCastExpr,

1713 isTypeCast, isVectorLiteral,

1714 NotPrimaryExpression);

1715

1717 if (Next.is(tok::annot_template_id)) {

1720

1721

1722

1724 ParseOptionalCXXScopeSpecifier(SS, nullptr,

1725 false,

1726 false);

1728 return ParseCastExpression(ParseKind, isAddressOfOperand, NotCastExpr,

1729 isTypeCast, isVectorLiteral,

1730 NotPrimaryExpression);

1731 }

1732 }

1733

1734

1735 Res = ParseCXXIdExpression(isAddressOfOperand);

1736 break;

1737 }

1738

1739 case tok::annot_template_id: {

1742

1743

1744

1747 return ParseCastExpression(ParseKind, isAddressOfOperand,

1748 NotCastExpr, isTypeCast, isVectorLiteral,

1749 NotPrimaryExpression);

1750 }

1751

1752

1753 [[fallthrough]];

1754 }

1755

1756 case tok::kw_operator:

1757 Res = ParseCXXIdExpression(isAddressOfOperand);

1758 break;

1759

1760 case tok::coloncolon: {

1761

1762

1765 if (!Tok.is(tok::coloncolon))

1766 return ParseCastExpression(ParseKind, isAddressOfOperand, isTypeCast,

1767 isVectorLiteral, NotPrimaryExpression);

1768

1769

1770

1772 if (Tok.is(tok::kw_new)) {

1773 if (NotPrimaryExpression)

1774 *NotPrimaryExpression = true;

1775 Res = ParseCXXNewExpression(true, CCLoc);

1776 AllowSuffix = false;

1777 break;

1778 }

1779 if (Tok.is(tok::kw_delete)) {

1780 if (NotPrimaryExpression)

1781 *NotPrimaryExpression = true;

1782 Res = ParseCXXDeleteExpression(true, CCLoc);

1783 AllowSuffix = false;

1784 break;

1785 }

1786

1787

1788 Diag(CCLoc, diag::err_expected_expression);

1790 }

1791

1792 case tok::kw_new:

1793 if (NotPrimaryExpression)

1794 *NotPrimaryExpression = true;

1795 Res = ParseCXXNewExpression(false, Tok.getLocation());

1796 AllowSuffix = false;

1797 break;

1798

1799 case tok::kw_delete:

1800 if (NotPrimaryExpression)

1801 *NotPrimaryExpression = true;

1802 Res = ParseCXXDeleteExpression(false, Tok.getLocation());

1803 AllowSuffix = false;

1804 break;

1805

1806 case tok::kw_requires:

1807 Res = ParseRequiresExpression();

1808 AllowSuffix = false;

1809 break;

1810

1811 case tok::kw_noexcept: {

1812 if (NotPrimaryExpression)

1813 *NotPrimaryExpression = true;

1814 Diag(Tok, diag::warn_cxx98_compat_noexcept_expr);

1817

1818 if (T.expectAndConsume(diag::err_expected_lparen_after, "noexcept"))

1820

1821

1822

1826

1827 T.consumeClose();

1828

1831 T.getCloseLocation());

1832 AllowSuffix = false;

1833 break;

1834 }

1835

1836#define TYPE_TRAIT(N,Spelling,K) \

1837 case tok::kw_##Spelling:

1838#include "clang/Basic/TokenKinds.def"

1839 Res = ParseTypeTrait();

1840 break;

1841

1842 case tok::kw___array_rank:

1843 case tok::kw___array_extent:

1844 if (NotPrimaryExpression)

1845 *NotPrimaryExpression = true;

1846 Res = ParseArrayTypeTrait();

1847 break;

1848

1849 case tok::kw___builtin_ptrauth_type_discriminator:

1850 return ParseBuiltinPtrauthTypeDiscriminator();

1851

1852 case tok::kw___is_lvalue_expr:

1853 case tok::kw___is_rvalue_expr:

1854 if (NotPrimaryExpression)

1855 *NotPrimaryExpression = true;

1856 Res = ParseExpressionTrait();

1857 break;

1858

1859 case tok::at: {

1860 if (NotPrimaryExpression)

1861 *NotPrimaryExpression = true;

1863 return ParseObjCAtExpression(AtLoc);

1864 }

1865 case tok::caret:

1866 Res = ParseBlockLiteralExpression();

1867 break;

1868 case tok::code_completion: {

1869 cutOffParsing();

1873 }

1874#define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) case tok::kw___##Trait:

1875#include "clang/Basic/TransformTypeTraits.def"

1876

1877

1878 if (NextToken().is(tok::l_paren)) {

1879 Tok.setKind(tok::identifier);

1880 Diag(Tok, diag::ext_keyword_as_ident)

1882 goto ParseIdentifier;

1883 }

1884 goto ExpectedExpression;

1885 case tok::l_square:

1888

1889

1890

1891

1892

1893 Res = TryParseLambdaExpression();

1895

1896

1897 if (NotPrimaryExpression)

1898 *NotPrimaryExpression = true;

1899 Res = ParseObjCMessageExpression();

1900 }

1901 break;

1902 }

1903 Res = ParseLambdaExpression();

1904 break;

1905 }

1907 Res = ParseObjCMessageExpression();

1908 break;

1909 }

1910 [[fallthrough]];

1911 default:

1912 ExpectedExpression:

1913 NotCastExpr = true;

1915 }

1916

1917

1918

1919

1920

1921 if (ParseKind == PrimaryExprOnly)

1922

1923

1924 return Res;

1925

1926 if (!AllowSuffix) {

1927

1928

1930 return Res;

1931

1932 switch (Tok.getKind()) {

1933 case tok::l_square:

1934 case tok::l_paren:

1935 case tok::plusplus:

1936 case tok::minusminus:

1937

1938

1940 return Res;

1941

1942 [[fallthrough]];

1943 case tok::period:

1944 case tok::arrow:

1945 break;

1946

1947 default:

1948 return Res;

1949 }

1950

1951

1952

1953

1954 Diag(Tok.getLocation(), diag::err_postfix_after_unary_requires_parens)

1958 ")");

1959 }

1960

1961

1962 PreferredType = SavedType;

1963 Res = ParsePostfixExpressionSuffix(Res);

1965 getActions().getOpenCLOptions().isAvailableOption(

1966 "__cl_clang_function_pointers", getLangOpts()))

1967 if (Expr *PostfixExpr = Res.get()) {

1968 QualType Ty = PostfixExpr->getType();

1970 Diag(PostfixExpr->getExprLoc(),

1971 diag::err_opencl_taking_function_address_parser);

1973 }

1974 }

1975

1976 return Res;

1977}

1978

1979

1980

1981

1982

1983

1984

1985

1986

1987

1988

1989

1990

1991

1992

1993

1994

1995

1996

1997

1998

1999

2001Parser::ParsePostfixExpressionSuffix(ExprResult LHS) {

2002

2003

2005 auto SavedType = PreferredType;

2006 while (true) {

2007

2008 PreferredType = SavedType;

2009 switch (Tok.getKind()) {

2010 case tok::code_completion:

2011 if (InMessageExpression)

2012 return LHS;

2013

2014 cutOffParsing();

2018

2019 case tok::identifier:

2020

2021

2022

2026 nullptr, LHS.get());

2027 break;

2028 }

2029

2030 [[fallthrough]];

2031

2032 default:

2033 return LHS;

2034 case tok::l_square: {

2035

2036

2037

2038

2039

2040

2042 isSimpleObjCMessageExpression())

2043 return LHS;

2044

2045

2046

2047 if (CheckProhibitedCXX11Attribute()) {

2050 }

2052 T.consumeOpen();

2053 Loc = T.getOpenLocation();

2056 ExprVector ArgExprs;

2057 bool HasError = false;

2059

2060

2061

2062

2063

2064 if ((getLangOpts().OpenMP && !AllowOpenACCArraySections) ||

2065 Tok.isNot(tok::colon)) {

2069 Diag(Tok, diag::warn_cxx98_compat_generalized_initializer_lists);

2070 Idx = ParseBraceInitializer();

2071 } else {

2073 }

2077 HasError = true;

2078 } else {

2079 ArgExprs.push_back(Idx.get());

2080 }

2081 } else if (Tok.isNot(tok::r_square)) {

2082 if (ParseExpressionList(ArgExprs)) {

2084 HasError = true;

2085 }

2086 }

2087 }

2088

2089

2090

2091

2092

2093 if (ArgExprs.size() <= 1 && AllowOpenACCArraySections) {

2095 if (Tok.is(tok::colon)) {

2096

2098 if (Tok.isNot(tok::r_square))

2100 }

2101 } else if (ArgExprs.size() <= 1 && getLangOpts().OpenMP) {

2103 if (Tok.is(tok::colon)) {

2104

2106 if (Tok.isNot(tok::r_square) &&

2111 }

2112 }

2114 (OMPClauseKind == llvm::omp::Clause::OMPC_to ||

2115 OMPClauseKind == llvm::omp::Clause::OMPC_from) &&

2116 Tok.is(tok::colon)) {

2117

2119 if (Tok.isNot(tok::r_square)) {

2121 }

2122 }

2123 }

2124

2127

2128 if (!LHS.isInvalid() && !HasError && !Length.isInvalid() &&

2129 !Stride.isInvalid() && Tok.is(tok::r_square)) {

2130 if (ColonLocFirst.isValid() || ColonLocSecond.isValid()) {

2131

2132

2133

2134

2135 if (AllowOpenACCArraySections) {

2136 assert(!Stride.isUsable() && !ColonLocSecond.isValid() &&

2137 "Stride/second colon not allowed for OpenACC");

2139 LHS.get(), Loc, ArgExprs.empty() ? nullptr : ArgExprs[0],

2140 ColonLocFirst, Length.get(), RLoc);

2141 } else {

2143 LHS.get(), Loc, ArgExprs.empty() ? nullptr : ArgExprs[0],

2144 ColonLocFirst, ColonLocSecond, Length.get(), Stride.get(),

2145 RLoc);

2146 }

2147 } else {

2149 ArgExprs, RLoc);

2150 }

2151 } else {

2153 }

2154

2155

2156 T.consumeClose();

2157 break;

2158 }

2159

2160 case tok::l_paren:

2161 case tok::lesslessless: {

2162

2165

2166 Expr *ExecConfig = nullptr;

2167

2169

2170 if (OpKind == tok::lesslessless) {

2171 ExprVector ExecConfigExprs;

2173

2174 if (ParseSimpleExpressionList(ExecConfigExprs)) {

2177 }

2178

2180 if (TryConsumeToken(tok::greatergreatergreater, CloseLoc)) {

2183 } else {

2184

2185 Diag(Tok, diag::err_expected) << tok::greatergreatergreater;

2186 Diag(OpenLoc, diag::note_matching) << tok::lesslessless;

2189 }

2190

2192 if (ExpectAndConsume(tok::l_paren))

2194 else

2195 Loc = PrevTokLocation;

2196 }

2197

2200 getCurScope(), OpenLoc, ExecConfigExprs, CloseLoc);

2203 else

2204 ExecConfig = ECResult.get();

2205 }

2206 } else {

2207 PT.consumeOpen();

2208 Loc = PT.getOpenLocation();

2209 }

2210

2211 ExprVector ArgExprs;

2212 auto RunSignatureHelp = [&]() -> QualType {

2215 LHS.get(), ArgExprs, PT.getOpenLocation());

2216 CalledSignatureHelp = true;

2217 return PreferredType;

2218 };

2219 if (OpKind == tok::l_paren || !LHS.isInvalid()) {

2220 if (Tok.isNot(tok::r_paren)) {

2221 bool HasTrailingComma = false;

2222 bool HasError = ParseExpressionList(

2223 ArgExprs,

2224 [&] {

2225 PreferredType.enterFunctionArgument(Tok.getLocation(),

2226 RunSignatureHelp);

2227 },

2228 false,

2229 false, &HasTrailingComma);

2230

2231 if (HasError && !HasTrailingComma) {

2233

2234

2235

2236

2238 RunSignatureHelp();

2241 for (auto &E : ArgExprs)

2243 }

2244 }

2245 }

2246

2247

2250 } else if (Tok.isNot(tok::r_paren)) {

2251 bool HadDelayedTypo = false;

2253 HadDelayedTypo = true;

2254 for (auto &E : ArgExprs)

2256 HadDelayedTypo = true;

2257

2258

2259

2260 if (HadDelayedTypo)

2262 else

2263 PT.consumeClose();

2265 } else {

2269 ExecConfig);

2271 ArgExprs.insert(ArgExprs.begin(), Fn);

2272 LHS =

2274 }

2275 PT.consumeClose();

2276 }

2277

2278 break;

2279 }

2280 case tok::arrow:

2281 case tok::period: {

2282

2283

2286

2289 bool MayBePseudoDestructor = false;

2291

2292 PreferredType.enterMemAccess(Actions, Tok.getLocation(), OrigLHS);

2293

2296 const Type* BaseType = Base->getType().getTypePtrOrNull();

2297 if (BaseType && Tok.is(tok::l_paren) &&

2300 Diag(OpLoc, diag::err_function_is_not_record)

2301 << OpKind << Base->getSourceRange()

2303 return ParsePostfixExpressionSuffix(Base);

2304 }

2305

2307 OpKind, ObjectType,

2308 MayBePseudoDestructor);

2310

2311

2312

2313 if (Tok.is(tok::code_completion)) {

2314 cutOffParsing();

2316 }

2317 break;

2318 }

2319 ParseOptionalCXXScopeSpecifier(

2321 false, &MayBePseudoDestructor);

2323 ObjectType = nullptr;

2324 }

2325

2326 if (Tok.is(tok::code_completion)) {

2328 OpKind == tok::arrow ? tok::period : tok::arrow;

2329 ExprResult CorrectedLHS(true);

2331

2332

2335 getCurScope(), OrigLHS, OpLoc, CorrectedOpKind, ObjectType,

2336 MayBePseudoDestructor);

2337 }

2338

2340 Expr *CorrectedBase = CorrectedLHS.get();

2342 CorrectedBase = Base;

2343

2344

2345 cutOffParsing();

2347 getCurScope(), Base, CorrectedBase, OpLoc, OpKind == tok::arrow,

2348 Base && ExprStatementTokLoc == Base->getBeginLoc(),

2350

2352 }

2353

2354 if (MayBePseudoDestructor && !LHS.isInvalid()) {

2355 LHS = ParseCXXPseudoDestructor(LHS.get(), OpLoc, OpKind, SS,

2356 ObjectType);

2357 break;

2358 }

2359

2360

2361

2362

2363

2364

2365

2366

2370 Tok.is(tok::kw_class)) {

2371

2372

2373

2374

2375

2376

2377

2380 Name.setIdentifier(Id, Loc);

2383 false,

2384 true,

2385

2387 false, &TemplateKWLoc, Name)) {

2390 }

2391

2394 OpKind, SS, TemplateKWLoc, Name,

2395 CurParsedObjCImpl ? CurParsedObjCImpl->Dcl

2396 : nullptr);

2398 if (Tok.is(tok::less))

2399 checkPotentialAngleBracket(LHS);

2400 } else if (OrigLHS && Name.isValid()) {

2401

2403 Name.getEndLoc(), {OrigLHS});

2404 }

2405 break;

2406 }

2407 case tok::plusplus:

2408 case tok::minusminus:

2416 }

2418 break;

2419 }

2420 }

2421}

2422

2423

2424

2425

2426

2427

2428

2429

2430

2431

2432

2433

2434

2435

2436

2437

2438

2439

2440

2441

2442

2443

2444

2445

2446

2447

2448

2449

2450

2451

2452

2453

2454

2456Parser::ParseExprAfterUnaryExprOrTypeTrait(const Token &OpTok,

2457 bool &isCastExpr,

2460

2461 assert(OpTok.isOneOf(tok::kw_typeof, tok::kw_typeof_unqual, tok::kw_sizeof,

2462 tok::kw___datasizeof, tok::kw___alignof, tok::kw_alignof,

2463 tok::kw__Alignof, tok::kw_vec_step,

2464 tok::kw___builtin_omp_required_simd_align,

2465 tok::kw___builtin_vectorelements) &&

2466 "Not a typeof/sizeof/alignof/vec_step expression!");

2467

2469

2470

2471 if (Tok.isNot(tok::l_paren)) {

2472

2473

2474 if (OpTok.isOneOf(tok::kw_sizeof, tok::kw___datasizeof, tok::kw___alignof,

2475 tok::kw_alignof, tok::kw__Alignof)) {

2476 if (isTypeIdUnambiguously()) {

2478 ParseSpecifierQualifierList(DS);

2481 ParseDeclarator(DeclaratorInfo);

2482

2487 diag::err_expected_parentheses_around_typename)

2489 } else {

2490 Diag(LParenLoc, diag::err_expected_parentheses_around_typename)

2493 }

2494 isCastExpr = true;

2496 }

2497 }

2498

2499 isCastExpr = false;

2500 if (OpTok.isOneOf(tok::kw_typeof, tok::kw_typeof_unqual) &&

2503 << tok::l_paren;

2505 }

2506

2507

2508

2509

2510

2511 if (OpTok.isOneOf(tok::kw_sizeof, tok::kw___datasizeof, tok::kw___alignof,

2512 tok::kw_alignof, tok::kw__Alignof) &&

2513 Tok.isOneOf(tok::kw_sizeof, tok::kw___datasizeof, tok::kw___alignof,

2514 tok::kw_alignof, tok::kw__Alignof))

2516 Operand = ParseCastExpression(UnaryExprOnly);

2517 });

2518 else

2519 Operand = ParseCastExpression(UnaryExprOnly);

2520 } else {

2521

2522

2523

2524

2525 ParenParseOption ExprType = CastExpr;

2527

2528 Operand = ParseParenExpression(ExprType, true,

2529 false, CastTy, RParenLoc);

2530 CastRange = SourceRange(LParenLoc, RParenLoc);

2531

2532

2533

2535 isCastExpr = true;

2537 }

2538

2540 !OpTok.isOneOf(tok::kw_typeof, tok::kw_typeof_unqual)) {

2541

2542

2543

2544

2545 if (Operand.isInvalid())

2546 Operand = ParsePostfixExpressionSuffix(Operand.get());

2547 }

2548 }

2549

2550

2551 isCastExpr = false;

2553}

2554

2555

2556

2557ExprResult Parser::ParseSYCLUniqueStableNameExpression() {

2558 assert(Tok.is(tok::kw___builtin_sycl_unique_stable_name) &&

2559 "Not __builtin_sycl_unique_stable_name");

2560

2563

2564

2565 if (T.expectAndConsume(diag::err_expected_lparen_after,

2566 "__builtin_sycl_unique_stable_name"))

2568

2570

2572 T.skipToEnd();

2574 }

2575

2576 if (T.consumeClose())

2578

2580 OpLoc, T.getOpenLocation(), T.getCloseLocation(), Ty.get());

2581}

2582

2583

2584

2585

2586

2587

2588

2589

2590

2591

2592

2593

2594

2595

2596

2597ExprResult Parser::ParseUnaryExprOrTypeTraitExpression() {

2598 assert(Tok.isOneOf(tok::kw_sizeof, tok::kw___datasizeof, tok::kw___alignof,

2599 tok::kw_alignof, tok::kw__Alignof, tok::kw_vec_step,

2600 tok::kw___builtin_omp_required_simd_align,

2601 tok::kw___builtin_vectorelements) &&

2602 "Not a sizeof/alignof/vec_step expression!");

2603 Token OpTok = Tok;

2605

2606

2607 if (Tok.is(tok::ellipsis) && OpTok.is(tok::kw_sizeof)) {

2612 if (Tok.is(tok::l_paren)) {

2614 T.consumeOpen();

2615 LParenLoc = T.getOpenLocation();

2616 if (Tok.is(tok::identifier)) {

2619 T.consumeClose();

2620 RParenLoc = T.getCloseLocation();

2623 } else {

2624 Diag(Tok, diag::err_expected_parameter_pack);

2626 }

2627 } else if (Tok.is(tok::identifier)) {

2632 Diag(LParenLoc, diag::err_paren_sizeof_parameter_pack)

2633 << Name

2636 } else {

2637 Diag(Tok, diag::err_sizeof_parameter_pack);

2638 }

2639

2640 if (!Name)

2642

2646

2649 *Name, NameLoc,

2650 RParenLoc);

2651 }

2652

2654 OpTok.isOneOf(tok::kw_alignof, tok::kw__Alignof))

2655 Diag(OpTok, diag::warn_cxx98_compat_alignof);

2657 Diag(OpTok, diag::warn_c23_compat_keyword) << OpTok.getName();

2658

2662

2663 bool isCastExpr;

2667 isCastExpr,

2668 CastTy,

2669 CastRange);

2670

2672 switch (OpTok.getKind()) {

2673 case tok::kw_alignof:

2674 case tok::kw__Alignof:

2675 ExprKind = UETT_AlignOf;

2676 break;

2677 case tok::kw___alignof:

2678 ExprKind = UETT_PreferredAlignOf;

2679 break;

2680 case tok::kw_vec_step:

2681 ExprKind = UETT_VecStep;

2682 break;

2683 case tok::kw___builtin_omp_required_simd_align:

2684 ExprKind = UETT_OpenMPRequiredSimdAlign;

2685 break;

2686 case tok::kw___datasizeof:

2687 ExprKind = UETT_DataSizeOf;

2688 break;

2689 case tok::kw___builtin_vectorelements:

2690 ExprKind = UETT_VectorElements;

2691 break;

2692 default:

2693 break;

2694 }

2695

2696 if (isCastExpr)

2698 ExprKind,

2699 true,

2701 CastRange);

2702

2703 if (OpTok.isOneOf(tok::kw_alignof, tok::kw__Alignof))

2705

2706

2707 if (Operand.isInvalid())

2709 ExprKind,

2710 false,

2712 CastRange);

2714}

2715

2716

2717

2718

2719

2720

2721

2722

2723

2724

2725

2726

2727

2728

2729

2730

2731

2732

2733

2734

2735

2736

2737

2738

2739ExprResult Parser::ParseBuiltinPrimaryExpression() {

2742

2745

2746

2747 if (Tok.isNot(tok::l_paren))

2748 return ExprError(Diag(Tok, diag::err_expected_after) << BuiltinII

2749 << tok::l_paren);

2750

2752 PT.consumeOpen();

2753

2754

2755

2756 switch (T) {

2757 default: llvm_unreachable("Not a builtin primary expression!");

2758 case tok::kw___builtin_va_arg: {

2760

2761 if (ExpectAndConsume(tok::comma)) {

2764 }

2765

2767

2768 if (Tok.isNot(tok::r_paren)) {

2769 Diag(Tok, diag::err_expected) << tok::r_paren;

2771 }

2772

2775 else

2776 Res = Actions.ActOnVAArg(StartLoc, Expr.get(), Ty.get(), ConsumeParen());

2777 break;

2778 }

2779 case tok::kw___builtin_offsetof: {

2785 if (MacroName == "offsetof")

2787 }

2789 {

2795 }

2796 }

2797

2798 if (ExpectAndConsume(tok::comma)) {

2801 }

2802

2803

2804 if (Tok.isNot(tok::identifier)) {

2805 Diag(Tok, diag::err_expected) << tok::identifier;

2808 }

2809

2810

2812

2814 Comps.back().isBrackets = false;

2816 Comps.back().LocStart = Comps.back().LocEnd = ConsumeToken();

2817

2818

2819 while (true) {

2820 if (Tok.is(tok::period)) {

2821

2823 Comps.back().isBrackets = false;

2825

2826 if (Tok.isNot(tok::identifier)) {

2827 Diag(Tok, diag::err_expected) << tok::identifier;

2830 }

2833 } else if (Tok.is(tok::l_square)) {

2834 if (CheckProhibitedCXX11Attribute())

2836

2837

2839 Comps.back().isBrackets = true;

2841 ST.consumeOpen();

2842 Comps.back().LocStart = ST.getOpenLocation();

2846 return Res;

2847 }

2848 Comps.back().U.E = Res.get();

2849

2850 ST.consumeClose();

2851 Comps.back().LocEnd = ST.getCloseLocation();

2852 } else {

2853 if (Tok.isNot(tok::r_paren)) {

2854 PT.consumeClose();

2858 } else {

2859 PT.consumeClose();

2861 Ty.get(), Comps,

2862 PT.getCloseLocation());

2863 }

2864 break;

2865 }

2866 }

2867 break;

2868 }

2869 case tok::kw___builtin_choose_expr: {

2871 if (Cond.isInvalid()) {

2873 return Cond;

2874 }

2875 if (ExpectAndConsume(tok::comma)) {

2878 }

2879

2881 if (Expr1.isInvalid()) {

2883 return Expr1;

2884 }

2885 if (ExpectAndConsume(tok::comma)) {

2888 }

2889

2891 if (Expr2.isInvalid()) {

2893 return Expr2;

2894 }

2895 if (Tok.isNot(tok::r_paren)) {

2896 Diag(Tok, diag::err_expected) << tok::r_paren;

2898 }

2899 Res = Actions.ActOnChooseExpr(StartLoc, Cond.get(), Expr1.get(),

2900 Expr2.get(), ConsumeParen());

2901 break;

2902 }

2903 case tok::kw___builtin_astype: {

2904

2906 if (Expr.isInvalid()) {

2909 }

2910

2911 if (ExpectAndConsume(tok::comma)) {

2914 }

2915

2916

2920

2921

2922 if (Tok.isNot(tok::r_paren)) {

2923 Diag(Tok, diag::err_expected) << tok::r_paren;

2926 }

2927

2929 ConsumeParen());

2930 break;

2931 }

2932 case tok::kw___builtin_convertvector: {

2933

2935 if (Expr.isInvalid()) {

2938 }

2939

2940 if (ExpectAndConsume(tok::comma)) {

2943 }

2944

2945

2949

2950

2951 if (Tok.isNot(tok::r_paren)) {

2952 Diag(Tok, diag::err_expected) << tok::r_paren;

2955 }

2956

2958 ConsumeParen());

2959 break;

2960 }

2961 case tok::kw___builtin_COLUMN:

2962 case tok::kw___builtin_FILE:

2963 case tok::kw___builtin_FILE_NAME:

2964 case tok::kw___builtin_FUNCTION:

2965 case tok::kw___builtin_FUNCSIG:

2966 case tok::kw___builtin_LINE:

2967 case tok::kw___builtin_source_location: {

2968

2969 if (Tok.isNot(tok::r_paren)) {

2970 Diag(Tok, diag::err_expected) << tok::r_paren;

2973 }

2975 switch (T) {

2976 case tok::kw___builtin_FILE:

2978 case tok::kw___builtin_FILE_NAME:

2980 case tok::kw___builtin_FUNCTION:

2982 case tok::kw___builtin_FUNCSIG:

2984 case tok::kw___builtin_LINE:

2986 case tok::kw___builtin_COLUMN:

2988 case tok::kw___builtin_source_location:

2990 default:

2991 llvm_unreachable("invalid keyword");

2992 }

2993 }();

2995 break;

2996 }

2997 }

2998

3001

3002

3003

3004 return ParsePostfixExpressionSuffix(Res.get());

3005}

3006

3007bool Parser::tryParseOpenMPArrayShapingCastPart() {

3008 assert(Tok.is(tok::l_square) && "Expected open bracket");

3009 bool ErrorFound = true;

3010 TentativeParsingAction TPA(*this);

3011 do {

3012 if (Tok.isNot(tok::l_square))

3013 break;

3014

3015 ConsumeBracket();

3016

3017 while (SkipUntil(tok::r_square, tok::annot_pragma_openmp_end,

3019 ;

3020 if (Tok.isNot(tok::r_square))

3021 break;

3022

3023 ConsumeBracket();

3024

3025 if (Tok.is(tok::r_paren)) {

3026 ErrorFound = false;

3027 break;

3028 }

3029 } while (Tok.isNot(tok::annot_pragma_openmp_end));

3030 TPA.Revert();

3031 return !ErrorFound;

3032}

3033

3034

3035

3036

3037

3038

3039

3040

3041

3042

3043

3044

3045

3046

3047

3048

3049

3050

3051

3052

3053

3054

3055

3056

3057

3058

3059

3060

3062Parser::ParseParenExpression(ParenParseOption &ExprType, bool stopIfCastExpr,

3063 bool isTypeCast, ParsedType &CastTy,

3065 assert(Tok.is(tok::l_paren) && "Not a paren expr!");

3068 if (T.consumeOpen())

3071

3072 PreferredType.enterParenExpr(Tok.getLocation(), OpenLoc);

3073

3075 bool isAmbiguousTypeId;

3076 CastTy = nullptr;

3077

3078 if (Tok.is(tok::code_completion)) {

3079 cutOffParsing();

3082 ExprType >= CompoundLiteral);

3084 }

3085

3086

3087 bool BridgeCast = (getLangOpts().ObjC &&

3088 Tok.isOneOf(tok::kw___bridge,

3089 tok::kw___bridge_transfer,

3090 tok::kw___bridge_retained,

3091 tok::kw___bridge_retain));

3092 if (BridgeCast && getLangOpts().ObjCAutoRefCount) {

3094 StringRef BridgeCastName = Tok.getName();

3097 Diag(BridgeKeywordLoc, diag::warn_arc_bridge_cast_nonarc)

3098 << BridgeCastName

3100 }

3101 BridgeCast = false;

3102 }

3103

3104

3105

3106 if (ExprType >= CompoundStmt && Tok.is(tok::l_brace)) {

3107 Diag(Tok, OpenLoc.isMacroID() ? diag::ext_gnu_statement_expr_macro

3108 : diag::ext_gnu_statement_expr);

3109

3110 checkCompoundToken(OpenLoc, tok::l_paren, CompoundToken::StmtExprBegin);

3111

3114 } else {

3115

3116

3117

3119 while (CodeDC->isRecord() || isa(CodeDC)) {

3122 "statement expr not in code context");

3123 }

3124 Sema::ContextRAII SavedContext(Actions, CodeDC, false);

3125

3127

3130

3131

3132 if (Stmt.isInvalid()) {

3135 } else {

3137 }

3138 }

3139 } else if (ExprType >= CompoundLiteral && BridgeCast) {

3142

3143

3145 if (tokenKind == tok::kw___bridge)

3147 else if (tokenKind == tok::kw___bridge_transfer)

3149 else if (tokenKind == tok::kw___bridge_retained)

3151 else {

3152

3153

3154 assert(tokenKind == tok::kw___bridge_retain);

3157 Diag(BridgeKeywordLoc, diag::err_arc_bridge_retain)

3159 "__bridge_retained");

3160 }

3161

3163 T.consumeClose();

3164 ColonProtection.restore();

3165 RParenLoc = T.getCloseLocation();

3166

3167 PreferredType.enterTypeCast(Tok.getLocation(), Ty.get().get());

3168 ExprResult SubExpr = ParseCastExpression(AnyCastExpr);

3169

3172

3174 BridgeKeywordLoc, Ty.get(),

3175 RParenLoc, SubExpr.get());

3176 } else if (ExprType >= CompoundLiteral &&

3177 isTypeIdInParens(isAmbiguousTypeId)) {

3178

3179

3180

3181

3182

3183

3184

3185

3186 if (isAmbiguousTypeId && !stopIfCastExpr) {

3187 ExprResult res = ParseCXXAmbiguousParenExpression(ExprType, CastTy, T,

3188 ColonProtection);

3189 RParenLoc = T.getCloseLocation();

3190 return res;

3191 }

3192

3193

3195 ParseSpecifierQualifierList(DS);

3198 ParseDeclarator(DeclaratorInfo);

3199

3200

3201

3202

3203 if (!DeclaratorInfo.isInvalidType() && Tok.is(tok::identifier) &&

3207 {

3210 }

3213 Ty.get(), nullptr);

3214 } else {

3215

3216 T.consumeClose();

3217 ColonProtection.restore();

3218 RParenLoc = T.getCloseLocation();

3219 if (Tok.is(tok::l_brace)) {

3220 ExprType = CompoundLiteral;

3222 {

3225 }

3226 return ParseCompoundLiteralExpression(Ty.get(), OpenLoc, RParenLoc);

3227 }

3228

3229 if (Tok.is(tok::l_paren)) {

3230

3232 {

3234 {

3237 }

3239 {

3241 }

3242 QualType QT = Ty.get().get().getCanonicalType();

3244 {

3245

3246

3247

3248

3249

3250 Result = ParseCastExpression(AnyCastExpr,

3251 false,

3253 true);

3254

3255 if (Result.isInvalid()) {

3257 DeclaratorInfo, CastTy,

3258 RParenLoc, Result.get());

3259 }

3260

3261

3262 if (Result.isInvalid()) {

3263 Result = ParsePostfixExpressionSuffix(Result);

3264 }

3265

3267 }

3268 }

3269 }

3270

3272

3273

3274 if (DeclaratorInfo.isInvalidType())

3276

3277

3278

3279 if (stopIfCastExpr) {

3281 {

3284 }

3285 CastTy = Ty.get();

3287 }

3288

3289

3293 GetLookAheadToken(1).isNot(tok::period)) {

3297 }

3298

3299 PreferredType.enterTypeCast(Tok.getLocation(), CastTy.get());

3300

3301

3302 Result = ParseCastExpression(AnyCastExpr,

3303 false,

3305 if (Result.isInvalid()) {

3307 DeclaratorInfo, CastTy,

3308 RParenLoc, Result.get());

3309 }

3311 }

3312

3313 Diag(Tok, diag::err_expected_lbrace_in_compound_literal);

3315 }

3316 } else if (ExprType >= FoldExpr && Tok.is(tok::ellipsis) &&

3318 ExprType = FoldExpr;

3319 return ParseFoldExpression(ExprResult(), T);

3320 } else if (isTypeCast) {

3321

3323 ExprVector ArgExprs;

3324

3325 if (!ParseSimpleExpressionList(ArgExprs)) {

3326

3327

3328 if (ExprType >= FoldExpr && ArgExprs.size() == 1 &&

3329 isFoldOperator(Tok.getKind()) && NextToken().is(tok::ellipsis)) {

3330 ExprType = FoldExpr;

3331 return ParseFoldExpression(ArgExprs[0], T);

3332 }

3333

3334 ExprType = SimpleExpr;

3336 ArgExprs);

3337 }

3338 } else if (getLangOpts().OpenMP >= 50 && OpenMPDirectiveParsing &&

3339 ExprType == CastExpr && Tok.is(tok::l_square) &&

3340 tryParseOpenMPArrayShapingCastPart()) {

3341 bool ErrorFound = false;

3344 do {

3346 TS.consumeOpen();

3349 if (!NumElements.isUsable()) {

3350 ErrorFound = true;

3351 while (SkipUntil(tok::r_square, tok::r_paren,

3353 ;

3354 }

3355 TS.consumeClose();

3356 OMPDimensions.push_back(NumElements.get());

3357 OMPBracketsRanges.push_back(TS.getRange());

3358 } while (Tok.isNot(tok::r_paren));

3359

3360 T.consumeClose();

3361 RParenLoc = T.getCloseLocation();

3363 if (ErrorFound) {

3365 } else if (Result.isInvalid()) {

3367 Result.get(), OpenLoc, RParenLoc, OMPDimensions, OMPBracketsRanges);

3368 }

3370 } else {

3372

3375

3376

3378 }

3379

3380 if (ExprType >= FoldExpr && isFoldOperator(Tok.getKind()) &&

3381 NextToken().is(tok::ellipsis)) {

3382 ExprType = FoldExpr;

3383 return ParseFoldExpression(Result, T);

3384 }

3385 ExprType = SimpleExpr;

3386

3387

3388 if (Result.isInvalid() && Tok.is(tok::r_paren))

3391 }

3392

3393

3394 if (Result.isInvalid()) {

3397 }

3398

3399 T.consumeClose();

3400 RParenLoc = T.getCloseLocation();

3402}

3403

3404

3405

3406

3407

3408

3409

3410

3411

3413Parser::ParseCompoundLiteralExpression(ParsedType Ty,

3416 assert(Tok.is(tok::l_brace) && "Not a compound literal!");

3417 if (getLangOpts().C99)

3418 Diag(LParenLoc, diag::ext_c99_compound_literal);

3419 PreferredType.enterTypeCast(Tok.getLocation(), Ty.get());

3421 if (Result.isInvalid() && Ty)

3424}

3425

3426

3427

3428

3429

3430

3431

3432

3433

3436 false);

3437}

3438

3441 true);

3442}

3443

3447 "Not a string-literal-like token!");

3448

3449

3450

3451

3453

3454 do {

3455 StringToks.push_back(Tok);

3458

3460 assert(!AllowUserDefinedLiteral && "UDL are always evaluated");

3462 }

3463

3464

3467 : nullptr);

3468}

3469

3470

3471

3472

3473

3474

3475

3476

3477

3478

3479

3480

3481

3482

3483

3484

3485

3486

3487

3488

3489ExprResult Parser::ParseGenericSelectionExpression() {

3490 assert(Tok.is(tok::kw__Generic) && "_Generic keyword expected");

3491

3492 diagnoseUseOfC11Keyword(Tok);

3493

3496 if (T.expectAndConsume())

3498

3499

3500

3503 if (isTypeIdForGenericSelection()) {

3505 if (ControllingType.isInvalid()) {

3508 }

3509 const auto *LIT = cast(ControllingType.get().get());

3510 SourceLocation Loc = LIT->getTypeSourceInfo()->getTypeLoc().getBeginLoc();

3512 : diag::ext_c2y_generic_with_type_arg);

3513 } else {

3514

3515

3518 ControllingExpr =

3520 if (ControllingExpr.isInvalid()) {

3523 }

3524 }

3525

3526 if (ExpectAndConsume(tok::comma)) {

3529 }

3530

3533 ExprVector Exprs;

3534 do {

3536 if (Tok.is(tok::kw_default)) {

3537

3538

3540 Diag(Tok, diag::err_duplicate_default_assoc);

3541 Diag(DefaultLoc, diag::note_previous_default_assoc);

3544 }

3546 Ty = nullptr;

3547 } else {

3553 }

3554 Ty = TR.get();

3555 }

3556 Types.push_back(Ty);

3557

3558 if (ExpectAndConsume(tok::colon)) {

3561 }

3562

3563

3564

3567 if (ER.isInvalid()) {

3570 }

3571 Exprs.push_back(ER.get());

3573

3574 T.consumeClose();

3575 if (T.getCloseLocation().isInvalid())

3577

3578 void *ExprOrTy = ControllingExpr.isUsable()

3579 ? ControllingExpr.get()

3580 : ControllingType.get().getAsOpaquePtr();

3581

3583 KeyLoc, DefaultLoc, T.getCloseLocation(), ControllingExpr.isUsable(),

3584 ExprOrTy, Types, Exprs);

3585}

3586

3587

3588

3589

3590

3591

3592

3593

3594

3598 T.skipToEnd();

3599 return true;

3600 }

3601

3606 assert(isFoldOperator(Kind) && "missing fold-operator");

3608 }

3609

3610 assert(Tok.is(tok::ellipsis) && "not a fold-expression");

3612

3614 if (Tok.isNot(tok::r_paren)) {

3615 if (!isFoldOperator(Tok.getKind()))

3616 return Diag(Tok.getLocation(), diag::err_expected_fold_operator);

3617

3618 if (Kind != tok::unknown && Tok.getKind() != Kind)

3619 Diag(Tok.getLocation(), diag::err_fold_operator_mismatch)

3623

3626 T.skipToEnd();

3627 return true;

3628 }

3629 }

3630

3632 ? diag::warn_cxx14_compat_fold_expression

3633 : diag::ext_fold_expression);

3634

3635 T.consumeClose();

3637 Kind, EllipsisLoc, RHS.get(),

3638 T.getCloseLocation());

3639}

3640

3641void Parser::injectEmbedTokens() {

3645 Data->BinaryData.size() * 2 - 1),

3646 Data->BinaryData.size() * 2 - 1);

3647 unsigned I = 0;

3648 for (auto &Byte : Data->BinaryData) {

3649 Toks[I].startToken();

3650 Toks[I].setKind(tok::binary_data);

3652 Toks[I].setLength(1);

3653 Toks[I].setLiteralData(&Byte);

3654 if (I != ((Data->BinaryData.size() - 1) * 2)) {

3655 Toks[I + 1].startToken();

3656 Toks[I + 1].setKind(tok::comma);

3657 Toks[I + 1].setLocation(Tok.getLocation());

3658 }

3659 I += 2;

3660 }

3661 PP.EnterTokenStream(std::move(Toks), true,

3662 true);

3664}

3665

3666

3667

3668

3669

3670

3671

3672

3673

3674

3675

3676

3677

3678

3679

3680

3681

3682

3683

3684

3685

3686

3687

3689 llvm::function_ref<void()> ExpressionStarts,

3690 bool FailImmediatelyOnInvalidExpr,

3691 bool EarlyTypoCorrection,

3692 bool *HasTrailingComma) {

3693 bool SawError = false;

3694 while (true) {

3695 if (ExpressionStarts)

3696 ExpressionStarts();

3697

3700 Diag(Tok, diag::warn_cxx98_compat_generalized_initializer_lists);

3701 Expr = ParseBraceInitializer();

3702 } else

3704

3705 if (EarlyTypoCorrection)

3707

3708 if (Tok.is(tok::ellipsis))

3710 else if (Tok.is(tok::code_completion)) {

3711

3712

3713

3714

3715

3716 SawError = true;

3717 cutOffParsing();

3718 break;

3719 }

3720 if (Expr.isInvalid()) {

3721 SawError = true;

3722 if (FailImmediatelyOnInvalidExpr)

3723 break;

3725 } else {

3726 Exprs.push_back(Expr.get());

3727 }

3728

3729 if (Tok.isNot(tok::comma))

3730 break;

3731

3734 checkPotentialAngleBracketDelimiter(Comma);

3735

3736 if (Tok.is(tok::r_paren)) {

3737 if (HasTrailingComma)

3738 *HasTrailingComma = true;

3739 break;

3740 }

3741 }

3742 if (SawError) {

3743

3744

3745 for (auto &E : Exprs) {

3747 if (Expr.isUsable()) E = Expr.get();

3748 }

3749 }

3750 return SawError;

3751}

3752

3753

3754

3755

3756

3757

3758

3759

3760

3762 while (true) {

3764 if (Expr.isInvalid())

3765 return true;

3766

3767 Exprs.push_back(Expr.get());

3768

3769

3770

3771 if (Tok.isNot(tok::comma) || NextToken().is(tok::ellipsis))

3772 return false;

3773

3774

3777 checkPotentialAngleBracketDelimiter(Comma);

3778 }

3779}

3780

3781

3782

3783

3784

3785

3786

3788 if (Tok.is(tok::code_completion)) {

3789 cutOffParsing();

3792 return;

3793 }

3794

3795

3797 ParseSpecifierQualifierList(DS);

3798

3799

3803 ParseDeclarator(DeclaratorInfo);

3804

3805 MaybeParseGNUAttributes(DeclaratorInfo);

3806

3807

3809}

3810

3811

3812

3813

3814

3815

3816

3817

3818

3819

3820

3821ExprResult Parser::ParseBlockLiteralExpression() {

3822 assert(Tok.is(tok::caret) && "block literal starts with ^");

3824

3826 "block literal parsing");

3827

3828

3829

3830

3831

3834

3835

3837

3838

3843

3844

3846

3847

3848

3849 if (Tok.is(tok::l_paren)) {

3850 ParseParenDeclarator(ParamInfo);

3851

3852

3853

3854 SourceLocation Tmp = ParamInfo.getSourceRange().getEnd();

3855 ParamInfo.SetIdentifier(nullptr, CaretLoc);

3856 ParamInfo.SetRangeEnd(Tmp);

3857 if (ParamInfo.isInvalidType()) {

3858

3859

3860

3863 }

3864

3865 MaybeParseGNUAttributes(ParamInfo);

3866

3867

3869 } else if (!Tok.is(tok::l_brace)) {

3870 ParseBlockId(CaretLoc);

3871 } else {

3872

3874 ParamInfo.AddTypeInfo(

3876 false,

3877 NoLoc,

3878 nullptr,

3879 0,

3880 NoLoc,

3881 NoLoc,

3882 true,

3883 NoLoc,

3884 NoLoc, EST_None,

3886 nullptr,

3887 nullptr,

3888 0,

3889 nullptr,

3890 nullptr,

3891 {}, CaretLoc,

3892 CaretLoc, ParamInfo),

3893 CaretLoc);

3894

3895 MaybeParseGNUAttributes(ParamInfo);

3896

3897

3899 }

3900

3901

3903 if (!Tok.is(tok::l_brace)) {

3904

3905 Diag(Tok, diag::err_expected_expression);

3908 }

3909

3911 BlockScope.Exit();

3912 if (Stmt.isInvalid())

3914 else

3917}

3918

3919

3920

3921

3922

3923ExprResult Parser::ParseObjCBoolLiteral() {

3926}

3927

3928

3929

3932 llvm::SmallSet<StringRef, 4> Platforms;

3933 bool HasOtherPlatformSpec = false;

3934 bool Valid = true;

3935 for (const auto &Spec : AvailSpecs) {

3936 if (Spec.isOtherPlatformSpec()) {

3937 if (HasOtherPlatformSpec) {

3938 P.Diag(Spec.getBeginLoc(), diag::err_availability_query_repeated_star);

3939 Valid = false;

3940 }

3941

3942 HasOtherPlatformSpec = true;

3943 continue;

3944 }

3945

3946 bool Inserted = Platforms.insert(Spec.getPlatform()).second;

3947 if (!Inserted) {

3948

3949

3950

3951 StringRef Platform = Spec.getPlatform();

3952 P.Diag(Spec.getBeginLoc(), diag::err_availability_query_repeated_platform)

3953 << Spec.getEndLoc() << Platform;

3954 Valid = false;

3955 }

3956 }

3957

3958 if (!HasOtherPlatformSpec) {

3959 SourceLocation InsertWildcardLoc = AvailSpecs.back().getEndLoc();

3960 P.Diag(InsertWildcardLoc, diag::err_availability_query_wildcard_required)

3962 return true;

3963 }

3964

3965 return !Valid;

3966}

3967

3968

3969

3970

3971

3972

3973std::optional Parser::ParseAvailabilitySpec() {

3974 if (Tok.is(tok::star)) {

3976 } else {

3977

3978 if (Tok.is(tok::code_completion)) {

3979 cutOffParsing();

3981 return std::nullopt;

3982 }

3983 if (Tok.isNot(tok::identifier)) {

3984 Diag(Tok, diag::err_avail_query_expected_platform_name);

3985 return std::nullopt;

3986 }

3987

3988 IdentifierLoc *PlatformIdentifier = ParseIdentifierLoc();

3990 VersionTuple Version = ParseVersionTuple(VersionRange);

3991

3992 if (Version.empty())

3993 return std::nullopt;

3994

3995 StringRef GivenPlatform = PlatformIdentifier->Ident->getName();

3996 StringRef Platform =

3997 AvailabilityAttr::canonicalizePlatformName(GivenPlatform);

3998

3999 if (AvailabilityAttr::getPrettyPlatformName(Platform).empty() ||

4000 (GivenPlatform.contains("xros") || GivenPlatform.contains("xrOS"))) {

4001 Diag(PlatformIdentifier->Loc,

4002 diag::err_avail_query_unrecognized_platform_name)

4003 << GivenPlatform;

4004 return std::nullopt;

4005 }

4006

4008 VersionRange.getEnd());

4009 }

4010}

4011

4013 assert(Tok.is(tok::kw___builtin_available) ||

4015

4016

4018

4020 if (Parens.expectAndConsume())

4022

4024 bool HasError = false;

4025 while (true) {

4026 std::optional Spec = ParseAvailabilitySpec();

4027 if (!Spec)

4028 HasError = true;

4029 else

4030 AvailSpecs.push_back(*Spec);

4031

4033 break;

4034 }

4035

4036 if (HasError) {

4039 }

4040

4042

4043 if (Parens.consumeClose())

4045

4047 AvailSpecs, BeginLoc, Parens.getCloseLocation());

4048}

Defines the clang::ASTContext interface.

static Decl::Kind getKind(const Decl *D)

Defines the clang::Expr interface and subclasses for C++ expressions.

static bool CheckAvailabilitySpecList(Parser &P, ArrayRef< AvailabilitySpec > AvailSpecs)

Validate availability spec list, emitting diagnostics if necessary.

#define REVERTIBLE_TYPE_TRAIT(Name)

Defines the PrettyStackTraceEntry class, which is used to make crashes give more contextual informati...

This file declares semantic analysis for CUDA constructs.

This file declares facilities that support code completion.

This file declares semantic analysis for Objective-C.

This file declares semantic analysis for OpenACC constructs and clauses.

This file declares semantic analysis for OpenMP constructs and clauses.

This file declares semantic analysis for SYCL constructs.

const clang::PrintingPolicy & getPrintingPolicy() const

One specifier in an @available expression.

RAII class that helps handle the parsing of an open/close delimiter pair, such as braces { ....

Represents a C++ nested-name-specifier or a global scope specifier.

bool isNotEmpty() const

A scope specifier is present, but may be valid or invalid.

CastExpr - Base class for type casts, including both implicit casts (ImplicitCastExpr) and explicit c...

ColonProtectionRAIIObject - This sets the Parser::ColonIsSacred bool and restores it when destroyed.

CompoundStmt - This represents a group of statements like { stmt stmt }.

Base class for callback objects used by Sema::CorrectTypo to check the validity of a potential typo c...

virtual bool ValidateCandidate(const TypoCorrection &candidate)

Simple predicate used by the default RankCandidate to determine whether to return an edit distance of...

DeclContext - This is used only as base class of specific decl types that can act as declaration cont...

DeclContext * getParent()

getParent - Returns the containing DeclContext.

bool isFileContext() const

Captures information about "declaration specifiers".

Information about one declarator, including the parsed type information and the identifier.

RAII object that enters a new expression evaluation context.

This represents one expression.

bool containsErrors() const

Whether this expression contains subexpressions which had errors, e.g.

SourceLocation getExprLoc() const LLVM_READONLY

getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...

ExtensionRAIIObject - This saves the state of extension warnings when constructed and disables them.

static FixItHint CreateReplacement(CharSourceRange RemoveRange, StringRef Code)

Create a code modification hint that replaces the given source range with the given code string.

static FixItHint CreateRemoval(CharSourceRange RemoveRange)

Create a code modification hint that removes the given source range.

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.

One of these records is kept for each identifier that is lexed.

bool hasRevertedTokenIDToIdentifier() const

True if revertTokenIDToIdentifier() was called.

StringRef getName() const

Return the actual identifier string.

Represents the declaration of a label.

static StringRef getImmediateMacroNameForDiagnostics(SourceLocation Loc, const SourceManager &SM, const LangOptions &LangOpts)

Retrieve the name of the immediate macro expansion.

This represents a decl that may have a name.

void * getAsOpaquePtr() const

static const ParsedAttributesView & none()

Parser - This implements a parser for the C family of languages.

TypeResult ParseTypeName(SourceRange *Range=nullptr, DeclaratorContext Context=DeclaratorContext::TypeName, AccessSpecifier AS=AS_none, Decl **OwnedType=nullptr, ParsedAttributes *Attrs=nullptr)

ParseTypeName type-name: [C99 6.7.6] specifier-qualifier-list abstract-declarator[opt].

DiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID)

SourceLocation ConsumeToken()

ConsumeToken - Consume the current 'peek token' and lex the next one.

Sema & getActions() const

static TypeResult getTypeAnnotation(const Token &Tok)

getTypeAnnotation - Read a parsed type out of an annotation token.

ExprResult ParseCaseExpression(SourceLocation CaseLoc)

ExprResult ParseConstraintLogicalOrExpression(bool IsTrailingRequiresClause)

Parse a constraint-logical-or-expression.

bool ParseUnqualifiedId(CXXScopeSpec &SS, ParsedType ObjectType, bool ObjectHadErrors, bool EnteringContext, bool AllowDestructorName, bool AllowConstructorName, bool AllowDeductionGuide, SourceLocation *TemplateKWLoc, UnqualifiedId &Result)

Parse a C++ unqualified-id (or a C identifier), which describes the name of an entity.

SourceLocation ConsumeAnyToken(bool ConsumeCodeCompletionTok=false)

ConsumeAnyToken - Dispatch to the right Consume* method based on the current token type.

ExprResult ParseConstantExpression()

ExprResult ParseConditionalExpression()

bool TryConsumeToken(tok::TokenKind Expected)

Scope * getCurScope() const

ExprResult ParseArrayBoundExpression()

ExprResult ParseConstraintLogicalAndExpression(bool IsTrailingRequiresClause)

Parse a constraint-logical-and-expression.

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 ...

ExprResult ParseAssignmentExpression(TypeCastState isTypeCast=NotTypeCast)

Parse an expr that doesn't include (top-level) commas.

ExprResult ParseConstantExpressionInExprEvalContext(TypeCastState isTypeCast=NotTypeCast)

const LangOptions & getLangOpts() const

ExprResult ParseExpression(TypeCastState isTypeCast=NotTypeCast)

Simple precedence-based parser for binary/ternary operators.

@ StopBeforeMatch

Stop skipping at specified token, but don't skip the token itself.

@ StopAtSemi

Stop skipping at semicolon.

bool TryAnnotateTypeOrScopeToken(ImplicitTypenameContext AllowImplicitTypename=ImplicitTypenameContext::No)

TryAnnotateTypeOrScopeToken - If the current token position is on a typename (possibly qualified in C...

TypeCastState

TypeCastState - State whether an expression is or may be a type cast.

ExprResult ParseUnevaluatedStringLiteralExpression()

ExprResult ParseStringLiteralExpression(bool AllowUserDefinedLiteral=false)

const Token & NextToken()

NextToken - This peeks ahead one token and returns it without consuming it.

ExprResult ParseConstraintExpression()

Parse a constraint-expression.

void enterSubscript(Sema &S, SourceLocation Tok, Expr *LHS)

void enterUnary(Sema &S, SourceLocation Tok, tok::TokenKind OpKind, SourceLocation OpLoc)

void enterBinary(Sema &S, SourceLocation Tok, Expr *LHS, tok::TokenKind Op)

QualType get(SourceLocation Tok) const

Get the expected type associated with this location, if any.

void EnterToken(const Token &Tok, bool IsReinject)

Enters a token in the token stream to be lexed next.

SourceManager & getSourceManager() const

llvm::BumpPtrAllocator & getPreprocessorAllocator()

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 ...

bool isAtStartOfMacroExpansion(SourceLocation loc, SourceLocation *MacroBegin=nullptr) const

Returns true if the given MacroID location points at the first token of the macro expansion.

bool isCodeCompletionReached() const

Returns true if code-completion is enabled and we have hit the code-completion point.

SourceLocation getLocForEndOfToken(SourceLocation Loc, unsigned Offset=0)

Computes the source location just past the end of the token at this source location.

If a crash happens while one of these objects are live, the message is printed out along with the spe...

A (possibly-)qualified type.

bool isNull() const

Return true if this QualType doesn't point to a type yet.

@ BlockScope

This is a scope that corresponds to a block/closure object.

@ CompoundStmtScope

This is a compound statement scope.

@ FnScope

This indicates that the scope corresponds to a function, which means that labels are set here.

@ DeclScope

This is a scope that can contain a declaration.

ExprResult ActOnExecConfigExpr(Scope *S, SourceLocation LLLLoc, MultiExprArg ExecConfig, SourceLocation GGGLoc)

@ PCC_Type

Code completion occurs where only a type is permitted.

void CodeCompleteExpression(Scope *S, const CodeCompleteExpressionData &Data)

Perform code-completion in an expression context when we know what type we're looking for.

QualType ProduceCallSignatureHelp(Expr *Fn, ArrayRef< Expr * > Args, SourceLocation OpenParLoc)

Determines the preferred type of the current function argument, by examining the signatures of all po...

void CodeCompleteOrdinaryName(Scope *S, ParserCompletionContext CompletionContext)

void CodeCompleteObjCClassPropertyRefExpr(Scope *S, const IdentifierInfo &ClassName, SourceLocation ClassNameLoc, bool IsBaseExprStatement)

void CodeCompleteAvailabilityPlatformName()

void CodeCompleteMemberReferenceExpr(Scope *S, Expr *Base, Expr *OtherOpBase, SourceLocation OpLoc, bool IsArrow, bool IsBaseExprStatement, QualType PreferredType)

void CodeCompletePostfixExpression(Scope *S, ExprResult LHS, QualType PreferredType)

ExprResult ActOnObjCBridgedCast(Scope *S, SourceLocation LParenLoc, ObjCBridgeCastKind Kind, SourceLocation BridgeKeywordLoc, ParsedType Type, SourceLocation RParenLoc, Expr *SubExpr)

ExprResult ActOnClassPropertyRefExpr(const IdentifierInfo &receiverName, const IdentifierInfo &propertyName, SourceLocation receiverNameLoc, SourceLocation propertyNameLoc)

ExprResult ActOnObjCBoolLiteral(SourceLocation AtLoc, SourceLocation ValueLoc, bool Value)

ExprResult ActOnObjCAvailabilityCheckExpr(llvm::ArrayRef< AvailabilitySpec > AvailSpecs, SourceLocation AtLoc, SourceLocation RParen)

ExprResult ActOnArraySectionExpr(Expr *Base, SourceLocation LBLoc, Expr *LowerBound, SourceLocation ColonLocFirst, Expr *Length, SourceLocation RBLoc)

Checks and creates an Array Section used in an OpenACC construct/clause.

ExprResult ActOnOMPArraySectionExpr(Expr *Base, SourceLocation LBLoc, Expr *LowerBound, SourceLocation ColonLocFirst, SourceLocation ColonLocSecond, Expr *Length, Expr *Stride, SourceLocation RBLoc)

ExprResult ActOnOMPArrayShapingExpr(Expr *Base, SourceLocation LParenLoc, SourceLocation RParenLoc, ArrayRef< Expr * > Dims, ArrayRef< SourceRange > Brackets)

ExprResult ActOnUniqueStableNameExpr(SourceLocation OpLoc, SourceLocation LParen, SourceLocation RParen, ParsedType ParsedTy)

RAII class used to indicate that we are performing provisional semantic analysis to determine the val...

ExprResult ActOnUnaryOp(Scope *S, SourceLocation OpLoc, tok::TokenKind Op, Expr *Input, bool IsAfterAmp=false)

Unary Operators. 'Tok' is the token for the operator.

ExprResult ActOnConstantExpression(ExprResult Res)

ExprResult ActOnNoexceptExpr(SourceLocation KeyLoc, SourceLocation LParen, Expr *Operand, SourceLocation RParen)

ExprResult ActOnCompoundLiteral(SourceLocation LParenLoc, ParsedType Ty, SourceLocation RParenLoc, Expr *InitExpr)

void ActOnStartStmtExpr()

void ActOnStmtExprError()

ExprResult ActOnIdExpression(Scope *S, CXXScopeSpec &SS, SourceLocation TemplateKWLoc, UnqualifiedId &Id, bool HasTrailingLParen, bool IsAddressOfOperand, CorrectionCandidateCallback *CCC=nullptr, bool IsInlineAsmIdentifier=false, Token *KeywordReplacement=nullptr)

ExprResult ActOnCharacterConstant(const Token &Tok, Scope *UDLScope=nullptr)

ExprResult ActOnStartCXXMemberReference(Scope *S, Expr *Base, SourceLocation OpLoc, tok::TokenKind OpKind, ParsedType &ObjectType, bool &MayBePseudoDestructor)

ExprResult ActOnCaseExpr(SourceLocation CaseLoc, ExprResult Val)

ExprResult ActOnCXXNullPtrLiteral(SourceLocation Loc)

ActOnCXXNullPtrLiteral - Parse 'nullptr'.

bool CheckConstraintExpression(const Expr *CE, Token NextToken=Token(), bool *PossibleNonPrimary=nullptr, bool IsTrailingRequiresClause=false)

Check whether the given expression is a valid constraint expression.

ASTContext & getASTContext() const

ExprResult ActOnAddrLabel(SourceLocation OpLoc, SourceLocation LabLoc, LabelDecl *TheDecl)

ActOnAddrLabel - Parse the GNU address of label extension: "&&foo".

ExprResult ActOnParenListExpr(SourceLocation L, SourceLocation R, MultiExprArg Val)

ExprResult ActOnChooseExpr(SourceLocation BuiltinLoc, Expr *CondExpr, Expr *LHSExpr, Expr *RHSExpr, SourceLocation RPLoc)

ExprResult ActOnUnevaluatedStringLiteral(ArrayRef< Token > StringToks)

SourceRange getExprRange(Expr *E) const

SemaCodeCompletion & CodeCompletion()

ExprResult ActOnCoawaitExpr(Scope *S, SourceLocation KwLoc, Expr *E)

ExprResult ActOnMemberAccessExpr(Scope *S, Expr *Base, SourceLocation OpLoc, tok::TokenKind OpKind, CXXScopeSpec &SS, SourceLocation TemplateKWLoc, UnqualifiedId &Member, Decl *ObjCImpDecl)

The main callback when the parser finds something like expression .

ExprResult ActOnGenericSelectionExpr(SourceLocation KeyLoc, SourceLocation DefaultLoc, SourceLocation RParenLoc, bool PredicateIsExpr, void *ControllingExprOrType, ArrayRef< ParsedType > ArgTypes, ArrayRef< Expr * > ArgExprs)

ControllingExprOrType is either an opaque pointer coming out of a ParsedType or an Expr *.

void ActOnBlockError(SourceLocation CaretLoc, Scope *CurScope)

ActOnBlockError - If there is an error parsing a block, this callback is invoked to pop the informati...

DeclContext * CurContext

CurContext - This is the current declaration context of parsing.

ExprResult ActOnGNUNullExpr(SourceLocation TokenLoc)

ExprResult ActOnParenExpr(SourceLocation L, SourceLocation R, Expr *E)

ExprResult ActOnSourceLocExpr(SourceLocIdentKind Kind, SourceLocation BuiltinLoc, SourceLocation RPLoc)

ExprResult ActOnConditionalOp(SourceLocation QuestionLoc, SourceLocation ColonLoc, Expr *CondExpr, Expr *LHSExpr, Expr *RHSExpr)

ActOnConditionalOp - Parse a ?: operation.

LabelDecl * LookupOrCreateLabel(IdentifierInfo *II, SourceLocation IdentLoc, SourceLocation GnuLabelLoc=SourceLocation())

LookupOrCreateLabel - Do a name lookup of a label with the specified name.

TypeResult ActOnTypeName(Declarator &D)

ParsedTemplateArgument ActOnPackExpansion(const ParsedTemplateArgument &Arg, SourceLocation EllipsisLoc)

Invoked when parsing a template argument followed by an ellipsis, which creates a pack expansion.

ExprResult ActOnStringLiteral(ArrayRef< Token > StringToks, Scope *UDLScope=nullptr)

ActOnStringLiteral - The specified tokens were lexed as pasted string fragments (e....

ExprResult ActOnBinOp(Scope *S, SourceLocation TokLoc, tok::TokenKind Kind, Expr *LHSExpr, Expr *RHSExpr)

Binary Operators. 'Tok' is the token for the operator.

ParsedType getTypeName(const IdentifierInfo &II, SourceLocation NameLoc, Scope *S, CXXScopeSpec *SS=nullptr, bool isClassName=false, bool HasTrailingDot=false, ParsedType ObjectType=nullptr, bool IsCtorOrDtorName=false, bool WantNontrivialTypeSourceInfo=false, bool IsClassTemplateDeductionContext=true, ImplicitTypenameContext AllowImplicitTypename=ImplicitTypenameContext::No, IdentifierInfo **CorrectedII=nullptr)

If the identifier refers to a type name within this scope, return the declaration of that type.

ExprResult ActOnPredefinedExpr(SourceLocation Loc, tok::TokenKind Kind)

@ ConstantEvaluated

The current context is "potentially evaluated" in C++11 terms, but the expression is evaluated at com...

@ Unevaluated

The current expression and its subexpressions occur within an unevaluated operand (C++11 [expr]p7),...

ExprResult ActOnAsTypeExpr(Expr *E, ParsedType ParsedDestTy, SourceLocation BuiltinLoc, SourceLocation RParenLoc)

Parse a __builtin_astype expression.

ExprResult ActOnVAArg(SourceLocation BuiltinLoc, Expr *E, ParsedType Ty, SourceLocation RPLoc)

ExprResult ActOnCastExpr(Scope *S, SourceLocation LParenLoc, Declarator &D, ParsedType &Ty, SourceLocation RParenLoc, Expr *CastExpr)

SmallVector< ExpressionEvaluationContextRecord, 8 > ExprEvalContexts

A stack of expression evaluation contexts.

ExprResult ActOnSizeofParameterPackExpr(Scope *S, SourceLocation OpLoc, IdentifierInfo &Name, SourceLocation NameLoc, SourceLocation RParenLoc)

Called when an expression computing the size of a parameter pack is parsed.

ExprResult ActOnStmtExpr(Scope *S, SourceLocation LPLoc, Stmt *SubStmt, SourceLocation RPLoc)

ExprResult ActOnCXXFoldExpr(Scope *S, SourceLocation LParenLoc, Expr *LHS, tok::TokenKind Operator, SourceLocation EllipsisLoc, Expr *RHS, SourceLocation RParenLoc)

Handle a C++1z fold-expression: ( expr op ... op expr ).

ExprResult ActOnBlockStmtExpr(SourceLocation CaretLoc, Stmt *Body, Scope *CurScope)

ActOnBlockStmtExpr - This is called when the body of a block statement literal was successfully compl...

void runWithSufficientStackSpace(SourceLocation Loc, llvm::function_ref< void()> Fn)

Run some code with "sufficient" stack space.

ExprResult ActOnPostfixUnaryOp(Scope *S, SourceLocation OpLoc, tok::TokenKind Kind, Expr *Input)

ExprResult CreateRecoveryExpr(SourceLocation Begin, SourceLocation End, ArrayRef< Expr * > SubExprs, QualType T=QualType())

Attempts to produce a RecoveryExpr after some AST node cannot be created.

ExprResult ActOnNumericConstant(const Token &Tok, Scope *UDLScope=nullptr)

void ActOnBlockStart(SourceLocation CaretLoc, Scope *CurScope)

ActOnBlockStart - This callback is invoked when a block literal is started.

ExprResult ActOnArraySubscriptExpr(Scope *S, Expr *Base, SourceLocation LLoc, MultiExprArg ArgExprs, SourceLocation RLoc)

ExprResult ActOnCallExpr(Scope *S, Expr *Fn, SourceLocation LParenLoc, MultiExprArg ArgExprs, SourceLocation RParenLoc, Expr *ExecConfig=nullptr)

ActOnCallExpr - Handle a call to Fn with the specified array of arguments.

ExprResult ActOnUnaryExprOrTypeTraitExpr(SourceLocation OpLoc, UnaryExprOrTypeTrait ExprKind, bool IsType, void *TyOrEx, SourceRange ArgRange)

ActOnUnaryExprOrTypeTraitExpr - Handle sizeof(type) and sizeof expr and the same for alignof and __al...

void ActOnBlockArguments(SourceLocation CaretLoc, Declarator &ParamInfo, Scope *CurScope)

ActOnBlockArguments - This callback allows processing of block arguments.

ExprResult ActOnConvertVectorExpr(Expr *E, ParsedType ParsedDestTy, SourceLocation BuiltinLoc, SourceLocation RParenLoc)

ActOnConvertVectorExpr - create a new convert-vector expression from the provided arguments.

ExprResult ActOnBuiltinOffsetOf(Scope *S, SourceLocation BuiltinLoc, SourceLocation TypeLoc, ParsedType ParsedArgTy, ArrayRef< OffsetOfComponent > Components, SourceLocation RParenLoc)

ExprResult CorrectDelayedTyposInExpr(Expr *E, VarDecl *InitDecl=nullptr, bool RecoverUncorrectedTypos=false, 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...

ExprResult ActOnNameClassifiedAsOverloadSet(Scope *S, Expr *OverloadSet)

Act on the result of classifying a name as an overload set.

Encodes a location in the source.

bool isValid() const

Return true if this is a valid SourceLocation object.

SourceLocation getLocWithOffset(IntTy Offset) const

Return a source location with the specified offset from this SourceLocation.

This class handles loading and caching of source files into memory.

bool isInSystemHeader(SourceLocation Loc) const

Returns if a SourceLocation is in a system header.

A trivial tuple used to represent a source range.

SourceLocation getEnd() const

SourceLocation getBegin() const

Stmt - This represents one statement.

SourceLocation getEndLoc() const LLVM_READONLY

SourceRange getSourceRange() const LLVM_READONLY

SourceLocation tokens are not useful in isolation - they are low level value objects created/interpre...

SourceLocation getBeginLoc() const LLVM_READONLY

Token - This structure provides full information about a lexed token.

IdentifierInfo * getIdentifierInfo() const

SourceLocation getLocation() const

Return a source location identifier for the specified offset in the current file.

const char * getName() const

void setKind(tok::TokenKind K)

SourceLocation getAnnotationEndLoc() const

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)) {....

void * getAnnotationValue() const

tok::TokenKind getKind() const

bool isAtStartOfLine() const

isAtStartOfLine - Return true if this token is at the start of a line.

bool isOneOf(tok::TokenKind K1, tok::TokenKind K2) const

bool isNot(tok::TokenKind K) const

bool isObjCAtKeyword(tok::ObjCKeywordKind objcKey) const

Return true if we have an ObjC keyword identifier.

bool isSimpleTypeSpecifier(const LangOptions &LangOpts) const

Determine whether the token kind starts a simple-type-specifier.

SourceLocation getLastLoc() const

Base wrapper for a particular "section" of type source info.

The base class of the type hierarchy.

bool isSpecificPlaceholderType(unsigned K) const

Test for a specific placeholder type.

bool isFunctionType() const

bool isVectorType() const

Simple class containing the result of Sema::CorrectTypo.

NamedDecl * getCorrectionDecl() const

Gets the pointer to the declaration of the typo correction.

Represents a C++ unqualified-id that has been parsed.

TokenKind

Provides a simple uniform namespace for tokens from all C languages.

The JSON file list parser is used to communicate input to InstallAPI.

bool tokenIsLikeStringLiteral(const Token &Tok, const LangOptions &LO)

Return true if the token is a string literal, or a function local predefined macro,...

UnaryExprOrTypeTrait

Names for the "expression or type" traits.

@ Result

The result type of a method or function.

ObjCBridgeCastKind

The kind of bridging performed by the Objective-C bridge cast.

@ OBC_Bridge

Bridging via __bridge, which does nothing but reinterpret the bits.

@ OBC_BridgeTransfer

Bridging via __bridge_transfer, which transfers ownership of an Objective-C pointer into ARC.

@ OBC_BridgeRetained

Bridging via __bridge_retain, which makes an ARC object available as a +1 C pointer.

ActionResult< Expr * > ExprResult

prec::Level getBinOpPrecedence(tok::TokenKind Kind, bool GreaterThanIsOperator, bool CPlusPlus11)

Return the precedence of the specified binary operator token.

@ TNK_Type_template

The name refers to a template whose specialization produces a type.

const FunctionProtoType * T

@ Parens

New-expression has a C++98 paren-delimited initializer.

@ EST_None

no exception specification

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(), SourceLocation TrailingReturnTypeLoc=SourceLocation(), DeclSpec *MethodQualifiers=nullptr)

DeclaratorChunk::getFunction - Return a DeclaratorChunk for a function.

Helper class to shuttle information about #embed directives from the preprocessor to the parser throu...

Wraps an identifier and optional source location for the identifier.

Information about a template-id annotation token.

TemplateNameKind Kind

The kind of template that Template refers to.