clang 22.0.0git
ParseExpr.cpp
Go to the documentation of this file.
1//===--- ParseExpr.cpp - Expression Parsing -------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8///
9/// \file
10/// Provides the Expression parsing implementation.
11///
12/// Expressions in C99 basically consist of a bunch of binary operators with
13/// unary operators and other random stuff at the leaves.
14///
15/// In the C99 grammar, these unary operators bind tightest and are represented
16/// as the 'cast-expression' production. Everything else is either a binary
17/// operator (e.g. '/') or a ternary operator ("?:"). The unary leaves are
18/// handled by ParseCastExpression, the higher level pieces are handled by
19/// ParseBinaryExpression.
20///
21//===----------------------------------------------------------------------===//
22
25#include "clang/AST/ExprCXX.h"
29#include "clang/Parse/Parser.h"
31#include "clang/Sema/DeclSpec.h"
34#include "clang/Sema/Scope.h"
35#include "clang/Sema/SemaCUDA.h"
37#include "clang/Sema/SemaObjC.h"
40#include "clang/Sema/SemaSYCL.h"
42#include "llvm/ADT/SmallVector.h"
43#include <optional>
44using namespace clang;
45
48 ExprResult LHS(ParseAssignmentExpression(CorrectionBehavior));
49 return ParseRHSOfBinaryExpression(LHS, prec::Comma);
50}
51
53Parser::ParseExpressionWithLeadingAt(SourceLocation AtLoc) {
54 ExprResult LHS(ParseObjCAtExpression(AtLoc));
55 return ParseRHSOfBinaryExpression(LHS, prec::Comma);
56}
57
59Parser::ParseExpressionWithLeadingExtension(SourceLocation ExtLoc) {
60 ExprResult LHS(true);
61 {
62 // Silence extension warnings in the sub-expression
63 ExtensionRAIIObject O(Diags);
64
65 LHS = ParseCastExpression(CastParseKind::AnyCastExpr);
66 }
67
68 if (!LHS.isInvalid())
69 LHS = Actions.ActOnUnaryOp(getCurScope(), ExtLoc, tok::kw___extension__,
70 LHS.get());
71
72 return ParseRHSOfBinaryExpression(LHS, prec::Comma);
73}
74
76 TypoCorrectionTypeBehavior CorrectionBehavior) {
77 if (Tok.is(tok::code_completion)) {
78 cutOffParsing();
80 getCurScope(), PreferredType.get(Tok.getLocation()));
81 return ExprError();
82 }
83
84 if (Tok.is(tok::kw_throw))
85 return ParseThrowExpression();
86 if (Tok.is(tok::kw_co_yield))
87 return ParseCoyieldExpression();
88
89 ExprResult LHS =
90 ParseCastExpression(CastParseKind::AnyCastExpr,
91 /*isAddressOfOperand=*/false, CorrectionBehavior);
92 return ParseRHSOfBinaryExpression(LHS, prec::Assignment);
93}
94
96 if (Tok.is(tok::code_completion)) {
97 cutOffParsing();
99 getCurScope(), PreferredType.get(Tok.getLocation()));
100 return ExprError();
101 }
102
103 ExprResult LHS = ParseCastExpression(
105 /*isAddressOfOperand=*/false, TypoCorrectionTypeBehavior::AllowNonTypes);
106 return ParseRHSOfBinaryExpression(LHS, prec::Conditional);
107}
108
110Parser::ParseAssignmentExprWithObjCMessageExprStart(SourceLocation LBracLoc,
111 SourceLocation SuperLoc,
112 ParsedType ReceiverType,
113 Expr *ReceiverExpr) {
114 ExprResult R
115 = ParseObjCMessageExpressionBody(LBracLoc, SuperLoc,
116 ReceiverType, ReceiverExpr);
117 R = ParsePostfixExpressionSuffix(R);
118 return ParseRHSOfBinaryExpression(R, prec::Assignment);
119}
120
122 TypoCorrectionTypeBehavior CorrectionBehavior) {
123 assert(Actions.ExprEvalContexts.back().Context ==
125 "Call this function only if your ExpressionEvaluationContext is "
126 "already ConstantEvaluated");
127 ExprResult LHS(ParseCastExpression(CastParseKind::AnyCastExpr, false,
128 CorrectionBehavior));
129 ExprResult Res(ParseRHSOfBinaryExpression(LHS, prec::Conditional));
130 return Actions.ActOnConstantExpression(Res);
131}
132
134 // C++03 [basic.def.odr]p2:
135 // An expression is potentially evaluated unless it appears where an
136 // integral constant expression is required (see 5.19) [...].
137 // C++98 and C++11 have no such rule, but this is only a defect in C++98.
138 EnterExpressionEvaluationContext ConstantEvaluated(
142}
143
145 EnterExpressionEvaluationContext ConstantEvaluated(
147 // If we parse the bound of a VLA... we parse a non-constant
148 // constant-expression!
149 Actions.ExprEvalContexts.back().InConditionallyConstantEvaluateContext = true;
150 // For a VLA type inside an unevaluated operator like:
151 //
152 // sizeof(typeof(*(int (*)[N])array))
153 //
154 // N and array are supposed to be ODR-used.
155 // Initially when encountering `array`, it is deemed unevaluated and non-ODR
156 // used because that occurs before parsing the type cast. Therefore we use
157 // Sema::TransformToPotentiallyEvaluated() to rebuild the expression to ensure
158 // it's actually ODR-used.
159 //
160 // However, in other unevaluated contexts as in constraint substitution, it
161 // would end up rebuilding the type twice which is unnecessary. So we push up
162 // a flag to help distinguish these cases.
163 for (auto Iter = Actions.ExprEvalContexts.rbegin() + 1;
164 Iter != Actions.ExprEvalContexts.rend(); ++Iter) {
165 if (!Iter->isUnevaluated())
166 break;
167 Iter->InConditionallyConstantEvaluateContext = true;
168 }
171}
172
174 EnterExpressionEvaluationContext ConstantEvaluated(
176 Actions.currentEvaluationContext().IsCaseExpr = true;
177
178 ExprResult LHS(
179 ParseCastExpression(CastParseKind::AnyCastExpr, false,
181 ExprResult Res(ParseRHSOfBinaryExpression(LHS, prec::Conditional));
182 return Actions.ActOnCaseExpr(CaseLoc, Res);
183}
184
186 EnterExpressionEvaluationContext ConstantEvaluated(
188 ExprResult LHS(ParseCastExpression(CastParseKind::AnyCastExpr));
189 ExprResult Res(ParseRHSOfBinaryExpression(LHS, prec::LogicalOr));
190 if (Res.isUsable() && !Actions.CheckConstraintExpression(Res.get())) {
191 return ExprError();
192 }
193 return Res;
194}
195
197Parser::ParseConstraintLogicalAndExpression(bool IsTrailingRequiresClause) {
198 EnterExpressionEvaluationContext ConstantEvaluated(
200 bool NotPrimaryExpression = false;
201 auto ParsePrimary = [&]() {
202 ExprResult E = ParseCastExpression(
204 /*isAddressOfOperand=*/false, TypoCorrectionTypeBehavior::AllowNonTypes,
205 /*isVectorLiteral=*/false, &NotPrimaryExpression);
206 if (E.isInvalid())
207 return ExprError();
208 auto RecoverFromNonPrimary = [&] (ExprResult E, bool Note) {
209 E = ParsePostfixExpressionSuffix(E);
210 // Use InclusiveOr, the precedence just after '&&' to not parse the
211 // next arguments to the logical and.
212 E = ParseRHSOfBinaryExpression(E, prec::InclusiveOr);
213 if (!E.isInvalid())
214 Diag(E.get()->getExprLoc(),
215 Note
216 ? diag::note_unparenthesized_non_primary_expr_in_requires_clause
217 : diag::err_unparenthesized_non_primary_expr_in_requires_clause)
220 PP.getLocForEndOfToken(E.get()->getEndLoc()), ")")
221 << E.get()->getSourceRange();
222 return E;
223 };
224
225 if (NotPrimaryExpression ||
226 // Check if the following tokens must be a part of a non-primary
227 // expression
228 getBinOpPrecedence(Tok.getKind(), GreaterThanIsOperator,
229 /*CPlusPlus11=*/true) > prec::LogicalAnd ||
230 // Postfix operators other than '(' (which will be checked for in
231 // CheckConstraintExpression).
232 Tok.isOneOf(tok::period, tok::plusplus, tok::minusminus) ||
233 (Tok.is(tok::l_square) && !NextToken().is(tok::l_square))) {
234 E = RecoverFromNonPrimary(E, /*Note=*/false);
235 if (E.isInvalid())
236 return ExprError();
237 NotPrimaryExpression = false;
238 }
239 bool PossibleNonPrimary;
240 bool IsConstraintExpr =
241 Actions.CheckConstraintExpression(E.get(), Tok, &PossibleNonPrimary,
242 IsTrailingRequiresClause);
243 if (!IsConstraintExpr || PossibleNonPrimary) {
244 // Atomic constraint might be an unparenthesized non-primary expression
245 // (such as a binary operator), in which case we might get here (e.g. in
246 // 'requires 0 + 1 && true' we would now be at '+', and parse and ignore
247 // the rest of the addition expression). Try to parse the rest of it here.
248 if (PossibleNonPrimary)
249 E = RecoverFromNonPrimary(E, /*Note=*/!IsConstraintExpr);
250 return ExprError();
251 }
252 return E;
253 };
254 ExprResult LHS = ParsePrimary();
255 if (LHS.isInvalid())
256 return ExprError();
257 while (Tok.is(tok::ampamp)) {
258 SourceLocation LogicalAndLoc = ConsumeToken();
259 ExprResult RHS = ParsePrimary();
260 if (RHS.isInvalid()) {
261 return ExprError();
262 }
263 ExprResult Op = Actions.ActOnBinOp(getCurScope(), LogicalAndLoc,
264 tok::ampamp, LHS.get(), RHS.get());
265 if (!Op.isUsable()) {
266 return ExprError();
267 }
268 LHS = Op;
269 }
270 return LHS;
271}
272
274Parser::ParseConstraintLogicalOrExpression(bool IsTrailingRequiresClause) {
275 ExprResult LHS(ParseConstraintLogicalAndExpression(IsTrailingRequiresClause));
276 if (!LHS.isUsable())
277 return ExprError();
278 while (Tok.is(tok::pipepipe)) {
279 SourceLocation LogicalOrLoc = ConsumeToken();
280 ExprResult RHS =
281 ParseConstraintLogicalAndExpression(IsTrailingRequiresClause);
282 if (!RHS.isUsable()) {
283 return ExprError();
284 }
285 ExprResult Op = Actions.ActOnBinOp(getCurScope(), LogicalOrLoc,
286 tok::pipepipe, LHS.get(), RHS.get());
287 if (!Op.isUsable()) {
288 return ExprError();
289 }
290 LHS = Op;
291 }
292 return LHS;
293}
294
295bool Parser::isNotExpressionStart() {
296 tok::TokenKind K = Tok.getKind();
297 if (K == tok::l_brace || K == tok::r_brace ||
298 K == tok::kw_for || K == tok::kw_while ||
299 K == tok::kw_if || K == tok::kw_else ||
300 K == tok::kw_goto || K == tok::kw_try)
301 return true;
302 // If this is a decl-specifier, we can't be at the start of an expression.
303 return isKnownToBeDeclarationSpecifier();
304}
305
306bool Parser::isFoldOperator(prec::Level Level) const {
307 return Level > prec::Unknown && Level != prec::Conditional &&
308 Level != prec::Spaceship;
309}
310
311bool Parser::isFoldOperator(tok::TokenKind Kind) const {
312 return isFoldOperator(getBinOpPrecedence(Kind, GreaterThanIsOperator, true));
313}
314
316Parser::ParseRHSOfBinaryExpression(ExprResult LHS, prec::Level MinPrec) {
317 prec::Level NextTokPrec = getBinOpPrecedence(Tok.getKind(),
318 GreaterThanIsOperator,
320 SourceLocation ColonLoc;
321
322 auto SavedType = PreferredType;
323 while (true) {
324 // Every iteration may rely on a preferred type for the whole expression.
325 PreferredType = SavedType;
326 // If this token has a lower precedence than we are allowed to parse (e.g.
327 // because we are called recursively, or because the token is not a binop),
328 // then we are done!
329 if (NextTokPrec < MinPrec)
330 return LHS;
331
332 // Consume the operator, saving the operator token for error reporting.
333 Token OpToken = Tok;
334 ConsumeToken();
335
336 // If we're potentially in a template-id, we may now be able to determine
337 // whether we're actually in one or not.
338 if (OpToken.isOneOf(tok::comma, tok::greater, tok::greatergreater,
339 tok::greatergreatergreater) &&
340 checkPotentialAngleBracketDelimiter(OpToken))
341 return ExprError();
342
343 // Bail out when encountering a comma followed by a token which can't
344 // possibly be the start of an expression. For instance:
345 // int f() { return 1, }
346 // We can't do this before consuming the comma, because
347 // isNotExpressionStart() looks at the token stream.
348 if (OpToken.is(tok::comma) && isNotExpressionStart()) {
349 PP.EnterToken(Tok, /*IsReinject*/true);
350 Tok = OpToken;
351 return LHS;
352 }
353
354 // If the next token is an ellipsis, then this is a fold-expression. Leave
355 // it alone so we can handle it in the paren expression.
356 if (isFoldOperator(NextTokPrec) && Tok.is(tok::ellipsis)) {
357 // FIXME: We can't check this via lookahead before we consume the token
358 // because that tickles a lexer bug.
359 PP.EnterToken(Tok, /*IsReinject*/true);
360 Tok = OpToken;
361 return LHS;
362 }
363
364 // In Objective-C++, alternative operator tokens can be used as keyword args
365 // in message expressions. Unconsume the token so that it can reinterpreted
366 // as an identifier in ParseObjCMessageExpressionBody. i.e., we support:
367 // [foo meth:0 and:0];
368 // [foo not_eq];
370 Tok.isOneOf(tok::colon, tok::r_square) &&
371 OpToken.getIdentifierInfo() != nullptr) {
372 PP.EnterToken(Tok, /*IsReinject*/true);
373 Tok = OpToken;
374 return LHS;
375 }
376
377 // Special case handling for the ternary operator.
378 ExprResult TernaryMiddle(true);
379 if (NextTokPrec == prec::Conditional) {
380 if (getLangOpts().CPlusPlus11 && Tok.is(tok::l_brace)) {
381 // Parse a braced-init-list here for error recovery purposes.
382 SourceLocation BraceLoc = Tok.getLocation();
383 TernaryMiddle = ParseBraceInitializer();
384 if (!TernaryMiddle.isInvalid()) {
385 Diag(BraceLoc, diag::err_init_list_bin_op)
386 << /*RHS*/ 1 << PP.getSpelling(OpToken)
387 << Actions.getExprRange(TernaryMiddle.get());
388 TernaryMiddle = ExprError();
389 }
390 } else if (Tok.isNot(tok::colon)) {
391 // Don't parse FOO:BAR as if it were a typo for FOO::BAR.
393
394 // Handle this production specially:
395 // logical-OR-expression '?' expression ':' conditional-expression
396 // In particular, the RHS of the '?' is 'expression', not
397 // 'logical-OR-expression' as we might expect.
398 TernaryMiddle = ParseExpression();
399 } else {
400 // Special case handling of "X ? Y : Z" where Y is empty:
401 // logical-OR-expression '?' ':' conditional-expression [GNU]
402 TernaryMiddle = nullptr;
403 Diag(Tok, diag::ext_gnu_conditional_expr);
404 }
405
406 if (TernaryMiddle.isInvalid()) {
407 LHS = ExprError();
408 TernaryMiddle = nullptr;
409 }
410
411 if (!TryConsumeToken(tok::colon, ColonLoc)) {
412 // Otherwise, we're missing a ':'. Assume that this was a typo that
413 // the user forgot. If we're not in a macro expansion, we can suggest
414 // a fixit hint. If there were two spaces before the current token,
415 // suggest inserting the colon in between them, otherwise insert ": ".
416 SourceLocation FILoc = Tok.getLocation();
417 const char *FIText = ": ";
418 const SourceManager &SM = PP.getSourceManager();
419 if (FILoc.isFileID() || PP.isAtStartOfMacroExpansion(FILoc, &FILoc)) {
420 assert(FILoc.isFileID());
421 bool IsInvalid = false;
422 const char *SourcePtr =
423 SM.getCharacterData(FILoc.getLocWithOffset(-1), &IsInvalid);
424 if (!IsInvalid && *SourcePtr == ' ') {
425 SourcePtr =
426 SM.getCharacterData(FILoc.getLocWithOffset(-2), &IsInvalid);
427 if (!IsInvalid && *SourcePtr == ' ') {
428 FILoc = FILoc.getLocWithOffset(-1);
429 FIText = ":";
430 }
431 }
432 }
433
434 Diag(Tok, diag::err_expected)
435 << tok::colon << FixItHint::CreateInsertion(FILoc, FIText);
436 Diag(OpToken, diag::note_matching) << tok::question;
437 ColonLoc = Tok.getLocation();
438 }
439 }
440
441 PreferredType.enterBinary(Actions, Tok.getLocation(), LHS.get(),
442 OpToken.getKind());
443 // Parse another leaf here for the RHS of the operator.
444 // ParseCastExpression works here because all RHS expressions in C have it
445 // as a prefix, at least. However, in C++, an assignment-expression could
446 // be a throw-expression, which is not a valid cast-expression.
447 // Therefore we need some special-casing here.
448 // Also note that the third operand of the conditional operator is
449 // an assignment-expression in C++, and in C++11, we can have a
450 // braced-init-list on the RHS of an assignment. For better diagnostics,
451 // parse as if we were allowed braced-init-lists everywhere, and check that
452 // they only appear on the RHS of assignments later.
453 ExprResult RHS;
454 bool RHSIsInitList = false;
455 if (getLangOpts().CPlusPlus11 && Tok.is(tok::l_brace)) {
456 RHS = ParseBraceInitializer();
457 RHSIsInitList = true;
458 } else if (getLangOpts().CPlusPlus && NextTokPrec <= prec::Conditional)
460 else
461 RHS = ParseCastExpression(CastParseKind::AnyCastExpr);
462
463 if (RHS.isInvalid()) {
464 LHS = ExprError();
465 }
466
467 // Remember the precedence of this operator and get the precedence of the
468 // operator immediately to the right of the RHS.
469 prec::Level ThisPrec = NextTokPrec;
470 NextTokPrec = getBinOpPrecedence(Tok.getKind(), GreaterThanIsOperator,
472
473 // Assignment and conditional expressions are right-associative.
474 bool isRightAssoc = ThisPrec == prec::Conditional ||
475 ThisPrec == prec::Assignment;
476
477 // Get the precedence of the operator to the right of the RHS. If it binds
478 // more tightly with RHS than we do, evaluate it completely first.
479 if (ThisPrec < NextTokPrec ||
480 (ThisPrec == NextTokPrec && isRightAssoc)) {
481 if (!RHS.isInvalid() && RHSIsInitList) {
482 Diag(Tok, diag::err_init_list_bin_op)
483 << /*LHS*/0 << PP.getSpelling(Tok) << Actions.getExprRange(RHS.get());
484 RHS = ExprError();
485 }
486 // If this is left-associative, only parse things on the RHS that bind
487 // more tightly than the current operator. If it is right-associative, it
488 // is okay, to bind exactly as tightly. For example, compile A=B=C=D as
489 // A=(B=(C=D)), where each paren is a level of recursion here.
490 // The function takes ownership of the RHS.
491 RHS = ParseRHSOfBinaryExpression(RHS,
492 static_cast<prec::Level>(ThisPrec + !isRightAssoc));
493 RHSIsInitList = false;
494
495 if (RHS.isInvalid()) {
496 LHS = ExprError();
497 }
498
499 NextTokPrec = getBinOpPrecedence(Tok.getKind(), GreaterThanIsOperator,
501 }
502
503 if (!RHS.isInvalid() && RHSIsInitList) {
504 if (ThisPrec == prec::Assignment) {
505 Diag(OpToken, diag::warn_cxx98_compat_generalized_initializer_lists)
506 << Actions.getExprRange(RHS.get());
507 } else if (ColonLoc.isValid()) {
508 Diag(ColonLoc, diag::err_init_list_bin_op)
509 << /*RHS*/1 << ":"
510 << Actions.getExprRange(RHS.get());
511 LHS = ExprError();
512 } else {
513 Diag(OpToken, diag::err_init_list_bin_op)
514 << /*RHS*/1 << PP.getSpelling(OpToken)
515 << Actions.getExprRange(RHS.get());
516 LHS = ExprError();
517 }
518 }
519
520 if (!LHS.isInvalid()) {
521 // Combine the LHS and RHS into the LHS (e.g. build AST).
522 if (TernaryMiddle.isInvalid()) {
523 // If we're using '>>' as an operator within a template
524 // argument list (in C++98), suggest the addition of
525 // parentheses so that the code remains well-formed in C++0x.
526 if (!GreaterThanIsOperator && OpToken.is(tok::greatergreater))
527 SuggestParentheses(OpToken.getLocation(),
528 diag::warn_cxx11_right_shift_in_template_arg,
529 SourceRange(Actions.getExprRange(LHS.get()).getBegin(),
530 Actions.getExprRange(RHS.get()).getEnd()));
531
532 ExprResult BinOp =
533 Actions.ActOnBinOp(getCurScope(), OpToken.getLocation(),
534 OpToken.getKind(), LHS.get(), RHS.get());
535 if (BinOp.isInvalid())
536 BinOp = Actions.CreateRecoveryExpr(LHS.get()->getBeginLoc(),
537 RHS.get()->getEndLoc(),
538 {LHS.get(), RHS.get()});
539
540 LHS = BinOp;
541 } else {
542 ExprResult CondOp = Actions.ActOnConditionalOp(
543 OpToken.getLocation(), ColonLoc, LHS.get(), TernaryMiddle.get(),
544 RHS.get());
545 if (CondOp.isInvalid()) {
546 std::vector<clang::Expr *> Args;
547 // TernaryMiddle can be null for the GNU conditional expr extension.
548 if (TernaryMiddle.get())
549 Args = {LHS.get(), TernaryMiddle.get(), RHS.get()};
550 else
551 Args = {LHS.get(), RHS.get()};
552 CondOp = Actions.CreateRecoveryExpr(LHS.get()->getBeginLoc(),
553 RHS.get()->getEndLoc(), Args);
554 }
555
556 LHS = CondOp;
557 }
558 }
559 }
560}
561
563Parser::ParseCastExpression(CastParseKind ParseKind, bool isAddressOfOperand,
564 TypoCorrectionTypeBehavior CorrectionBehavior,
565 bool isVectorLiteral, bool *NotPrimaryExpression) {
566 bool NotCastExpr;
567 ExprResult Res = ParseCastExpression(ParseKind, isAddressOfOperand,
568 NotCastExpr, CorrectionBehavior,
569 isVectorLiteral, NotPrimaryExpression);
570 if (NotCastExpr)
571 Diag(Tok, diag::err_expected_expression);
572 return Res;
573}
574
575namespace {
576class CastExpressionIdValidator final : public CorrectionCandidateCallback {
577public:
578 CastExpressionIdValidator(Token Next,
579 TypoCorrectionTypeBehavior CorrectionBehavior)
580 : NextToken(Next) {
581 WantTypeSpecifiers = WantFunctionLikeCasts =
582 (CorrectionBehavior != TypoCorrectionTypeBehavior::AllowNonTypes);
584 (CorrectionBehavior != TypoCorrectionTypeBehavior::AllowTypes);
585 }
586
587 bool ValidateCandidate(const TypoCorrection &candidate) override {
588 NamedDecl *ND = candidate.getCorrectionDecl();
589 if (!ND)
590 return candidate.isKeyword();
591
592 if (isa<TypeDecl>(ND))
593 return WantTypeSpecifiers;
594
596 return false;
597
598 if (!NextToken.isOneOf(tok::equal, tok::arrow, tok::period))
599 return true;
600
601 for (auto *C : candidate) {
602 NamedDecl *ND = C->getUnderlyingDecl();
603 if (isa<ValueDecl>(ND) && !isa<FunctionDecl>(ND))
604 return true;
605 }
606 return false;
607 }
608
609 std::unique_ptr<CorrectionCandidateCallback> clone() override {
610 return std::make_unique<CastExpressionIdValidator>(*this);
611 }
612
613 private:
614 Token NextToken;
615 bool AllowNonTypes;
616};
617}
618
619bool Parser::isRevertibleTypeTrait(const IdentifierInfo *II,
620 tok::TokenKind *Kind) {
621 if (RevertibleTypeTraits.empty()) {
622// Revertible type trait is a feature for backwards compatibility with older
623// standard libraries that declare their own structs with the same name as
624// the builtins listed below. New builtins should NOT be added to this list.
625#define RTT_JOIN(X, Y) X##Y
626#define REVERTIBLE_TYPE_TRAIT(Name) \
627 RevertibleTypeTraits[PP.getIdentifierInfo(#Name)] = RTT_JOIN(tok::kw_, Name)
628
629 REVERTIBLE_TYPE_TRAIT(__is_abstract);
630 REVERTIBLE_TYPE_TRAIT(__is_aggregate);
631 REVERTIBLE_TYPE_TRAIT(__is_arithmetic);
632 REVERTIBLE_TYPE_TRAIT(__is_array);
633 REVERTIBLE_TYPE_TRAIT(__is_assignable);
634 REVERTIBLE_TYPE_TRAIT(__is_base_of);
635 REVERTIBLE_TYPE_TRAIT(__is_bounded_array);
636 REVERTIBLE_TYPE_TRAIT(__is_class);
637 REVERTIBLE_TYPE_TRAIT(__is_complete_type);
638 REVERTIBLE_TYPE_TRAIT(__is_compound);
639 REVERTIBLE_TYPE_TRAIT(__is_const);
640 REVERTIBLE_TYPE_TRAIT(__is_constructible);
641 REVERTIBLE_TYPE_TRAIT(__is_convertible);
642 REVERTIBLE_TYPE_TRAIT(__is_convertible_to);
643 REVERTIBLE_TYPE_TRAIT(__is_destructible);
644 REVERTIBLE_TYPE_TRAIT(__is_empty);
645 REVERTIBLE_TYPE_TRAIT(__is_enum);
646 REVERTIBLE_TYPE_TRAIT(__is_floating_point);
647 REVERTIBLE_TYPE_TRAIT(__is_final);
648 REVERTIBLE_TYPE_TRAIT(__is_function);
649 REVERTIBLE_TYPE_TRAIT(__is_fundamental);
650 REVERTIBLE_TYPE_TRAIT(__is_integral);
651 REVERTIBLE_TYPE_TRAIT(__is_interface_class);
652 REVERTIBLE_TYPE_TRAIT(__is_literal);
653 REVERTIBLE_TYPE_TRAIT(__is_lvalue_expr);
654 REVERTIBLE_TYPE_TRAIT(__is_lvalue_reference);
655 REVERTIBLE_TYPE_TRAIT(__is_member_function_pointer);
656 REVERTIBLE_TYPE_TRAIT(__is_member_object_pointer);
657 REVERTIBLE_TYPE_TRAIT(__is_member_pointer);
658 REVERTIBLE_TYPE_TRAIT(__is_nothrow_assignable);
659 REVERTIBLE_TYPE_TRAIT(__is_nothrow_constructible);
660 REVERTIBLE_TYPE_TRAIT(__is_nothrow_destructible);
661 REVERTIBLE_TYPE_TRAIT(__is_object);
662 REVERTIBLE_TYPE_TRAIT(__is_pod);
663 REVERTIBLE_TYPE_TRAIT(__is_pointer);
664 REVERTIBLE_TYPE_TRAIT(__is_polymorphic);
665 REVERTIBLE_TYPE_TRAIT(__is_reference);
666 REVERTIBLE_TYPE_TRAIT(__is_rvalue_expr);
667 REVERTIBLE_TYPE_TRAIT(__is_rvalue_reference);
668 REVERTIBLE_TYPE_TRAIT(__is_same);
669 REVERTIBLE_TYPE_TRAIT(__is_scalar);
670 REVERTIBLE_TYPE_TRAIT(__is_scoped_enum);
671 REVERTIBLE_TYPE_TRAIT(__is_sealed);
672 REVERTIBLE_TYPE_TRAIT(__is_signed);
673 REVERTIBLE_TYPE_TRAIT(__is_standard_layout);
674 REVERTIBLE_TYPE_TRAIT(__is_trivial);
675 REVERTIBLE_TYPE_TRAIT(__is_trivially_assignable);
676 REVERTIBLE_TYPE_TRAIT(__is_trivially_constructible);
677 REVERTIBLE_TYPE_TRAIT(__is_trivially_copyable);
678 REVERTIBLE_TYPE_TRAIT(__is_unbounded_array);
679 REVERTIBLE_TYPE_TRAIT(__is_union);
680 REVERTIBLE_TYPE_TRAIT(__is_unsigned);
681 REVERTIBLE_TYPE_TRAIT(__is_void);
682 REVERTIBLE_TYPE_TRAIT(__is_volatile);
683 REVERTIBLE_TYPE_TRAIT(__reference_binds_to_temporary);
684#define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) \
685 REVERTIBLE_TYPE_TRAIT(RTT_JOIN(__, Trait));
686#include "clang/Basic/TransformTypeTraits.def"
687#undef REVERTIBLE_TYPE_TRAIT
688#undef RTT_JOIN
689 }
690 llvm::SmallDenseMap<IdentifierInfo *, tok::TokenKind>::iterator Known =
691 RevertibleTypeTraits.find(II);
692 if (Known != RevertibleTypeTraits.end()) {
693 if (Kind)
694 *Kind = Known->second;
695 return true;
696 }
697 return false;
698}
699
700ExprResult Parser::ParseBuiltinPtrauthTypeDiscriminator() {
702
703 BalancedDelimiterTracker T(*this, tok::l_paren);
704 if (T.expectAndConsume())
705 return ExprError();
706
708 if (Ty.isInvalid()) {
709 SkipUntil(tok::r_paren, StopAtSemi);
710 return ExprError();
711 }
712
713 SourceLocation EndLoc = Tok.getLocation();
714 T.consumeClose();
715 return Actions.ActOnUnaryExprOrTypeTraitExpr(
716 Loc, UETT_PtrAuthTypeDiscriminator,
717 /*isType=*/true, Ty.get().getAsOpaquePtr(), SourceRange(Loc, EndLoc));
718}
719
721Parser::ParseCastExpression(CastParseKind ParseKind, bool isAddressOfOperand,
722 bool &NotCastExpr,
723 TypoCorrectionTypeBehavior CorrectionBehavior,
724 bool isVectorLiteral, bool *NotPrimaryExpression) {
725 ExprResult Res;
726 tok::TokenKind SavedKind = Tok.getKind();
727 auto SavedType = PreferredType;
728 NotCastExpr = false;
729
730 // Are postfix-expression suffix operators permitted after this
731 // cast-expression? If not, and we find some, we'll parse them anyway and
732 // diagnose them.
733 bool AllowSuffix = true;
734
735 // This handles all of cast-expression, unary-expression, postfix-expression,
736 // and primary-expression. We handle them together like this for efficiency
737 // and to simplify handling of an expression starting with a '(' token: which
738 // may be one of a parenthesized expression, cast-expression, compound literal
739 // expression, or statement expression.
740 //
741 // If the parsed tokens consist of a primary-expression, the cases below
742 // break out of the switch; at the end we call ParsePostfixExpressionSuffix
743 // to handle the postfix expression suffixes. Cases that cannot be followed
744 // by postfix exprs should set AllowSuffix to false.
745 switch (SavedKind) {
746 case tok::l_paren: {
747 // If this expression is limited to being a unary-expression, the paren can
748 // not start a cast expression.
749 ParenParseOption ParenExprType;
750 switch (ParseKind) {
752 assert(getLangOpts().CPlusPlus && "not possible to get here in C");
753 [[fallthrough]];
755 ParenExprType = ParenParseOption::CastExpr;
756 break;
758 ParenExprType = ParenParseOption::FoldExpr;
759 break;
760 }
761 ParsedType CastTy;
762 SourceLocation RParenLoc;
763 Res = ParseParenExpression(ParenExprType, /*StopIfCastExr=*/false,
764 ParenExprKind::Unknown, CorrectionBehavior,
765 CastTy, RParenLoc);
766
767 // FIXME: What should we do if a vector literal is followed by a
768 // postfix-expression suffix? Usually postfix operators are permitted on
769 // literals.
770 if (isVectorLiteral)
771 return Res;
772
773 switch (ParenExprType) {
775 break; // Nothing else to do.
777 break; // Nothing else to do.
779 // We parsed '(' type-name ')' '{' ... '}'. If any suffixes of
780 // postfix-expression exist, parse them now.
781 break;
783 // We have parsed the cast-expression and no postfix-expr pieces are
784 // following.
785 return Res;
787 // We only parsed a fold-expression. There might be postfix-expr pieces
788 // afterwards; parse them now.
789 break;
790 }
791
792 break;
793 }
794
795 // primary-expression
796 case tok::numeric_constant:
797 case tok::binary_data:
798 // constant: integer-constant
799 // constant: floating-constant
800
801 Res = Actions.ActOnNumericConstant(Tok, /*UDLScope*/getCurScope());
802 ConsumeToken();
803 break;
804
805 case tok::kw_true:
806 case tok::kw_false:
807 Res = ParseCXXBoolLiteral();
808 break;
809
810 case tok::kw___objc_yes:
811 case tok::kw___objc_no:
812 Res = ParseObjCBoolLiteral();
813 break;
814
815 case tok::kw_nullptr:
817 Diag(Tok, diag::warn_cxx98_compat_nullptr);
818 else
819 Diag(Tok, getLangOpts().C23 ? diag::warn_c23_compat_keyword
820 : diag::ext_c_nullptr) << Tok.getName();
821
822 Res = Actions.ActOnCXXNullPtrLiteral(ConsumeToken());
823 break;
824
825 case tok::annot_primary_expr:
826 case tok::annot_overload_set:
827 Res = getExprAnnotation(Tok);
828 if (!Res.isInvalid() && Tok.getKind() == tok::annot_overload_set)
829 Res = Actions.ActOnNameClassifiedAsOverloadSet(getCurScope(), Res.get());
830 ConsumeAnnotationToken();
831 if (!Res.isInvalid() && Tok.is(tok::less))
832 checkPotentialAngleBracket(Res);
833 break;
834
835 case tok::annot_non_type:
836 case tok::annot_non_type_dependent:
837 case tok::annot_non_type_undeclared: {
838 CXXScopeSpec SS;
839 Token Replacement;
840 Res = tryParseCXXIdExpression(SS, isAddressOfOperand, Replacement);
841 assert(!Res.isUnset() &&
842 "should not perform typo correction on annotation token");
843 break;
844 }
845
846 case tok::annot_embed: {
847 injectEmbedTokens();
848 return ParseCastExpression(ParseKind, isAddressOfOperand,
849 CorrectionBehavior, isVectorLiteral,
850 NotPrimaryExpression);
851 }
852
853 case tok::kw___super:
854 case tok::kw_decltype:
855 // Annotate the token and tail recurse.
857 return ExprError();
858 assert(Tok.isNot(tok::kw_decltype) && Tok.isNot(tok::kw___super));
859 return ParseCastExpression(ParseKind, isAddressOfOperand,
860 CorrectionBehavior, isVectorLiteral,
861 NotPrimaryExpression);
862
863 case tok::identifier:
864 ParseIdentifier: { // primary-expression: identifier
865 // unqualified-id: identifier
866 // constant: enumeration-constant
867 // Turn a potentially qualified name into a annot_typename or
868 // annot_cxxscope if it would be valid. This handles things like x::y, etc.
869 if (getLangOpts().CPlusPlus) {
870 // Avoid the unnecessary parse-time lookup in the common case
871 // where the syntax forbids a type.
872 Token Next = NextToken();
873
874 if (Next.is(tok::ellipsis) && Tok.is(tok::identifier) &&
875 GetLookAheadToken(2).is(tok::l_square)) {
876 // Annotate the token and tail recurse.
877 // If the token is not annotated, then it might be an expression pack
878 // indexing
880 Tok.isOneOf(tok::annot_pack_indexing_type, tok::annot_cxxscope))
881 return ParseCastExpression(ParseKind, isAddressOfOperand,
882 CorrectionBehavior, isVectorLiteral,
883 NotPrimaryExpression);
884 }
885
886 // If this identifier was reverted from a token ID, and the next token
887 // is a parenthesis, this is likely to be a use of a type trait. Check
888 // those tokens.
889 else if (Next.is(tok::l_paren) && Tok.is(tok::identifier) &&
893 if (isRevertibleTypeTrait(II, &Kind)) {
894 Tok.setKind(Kind);
895 return ParseCastExpression(ParseKind, isAddressOfOperand, NotCastExpr,
896 CorrectionBehavior, isVectorLiteral,
897 NotPrimaryExpression);
898 }
899 }
900
901 else if ((!ColonIsSacred && Next.is(tok::colon)) ||
902 Next.isOneOf(tok::coloncolon, tok::less, tok::l_paren,
903 tok::l_brace)) {
904 // If TryAnnotateTypeOrScopeToken annotates the token, tail recurse.
906 return ExprError();
907 if (!Tok.is(tok::identifier))
908 return ParseCastExpression(ParseKind, isAddressOfOperand, NotCastExpr,
909 CorrectionBehavior, isVectorLiteral,
910 NotPrimaryExpression);
911 }
912 }
913
914 // Consume the identifier so that we can see if it is followed by a '(' or
915 // '.'.
918
919 // Support 'Class.property' and 'super.property' notation.
920 if (getLangOpts().ObjC && Tok.is(tok::period) &&
921 (Actions.getTypeName(II, ILoc, getCurScope()) ||
922 // Allow the base to be 'super' if in an objc-method.
923 (&II == Ident_super && getCurScope()->isInObjcMethodScope()))) {
924 ConsumeToken();
925
926 if (Tok.is(tok::code_completion) && &II != Ident_super) {
927 cutOffParsing();
929 getCurScope(), II, ILoc, ExprStatementTokLoc == ILoc);
930 return ExprError();
931 }
932 // Allow either an identifier or the keyword 'class' (in C++).
933 if (Tok.isNot(tok::identifier) &&
934 !(getLangOpts().CPlusPlus && Tok.is(tok::kw_class))) {
935 Diag(Tok, diag::err_expected_property_name);
936 return ExprError();
937 }
938 IdentifierInfo &PropertyName = *Tok.getIdentifierInfo();
939 SourceLocation PropertyLoc = ConsumeToken();
940
941 Res = Actions.ObjC().ActOnClassPropertyRefExpr(II, PropertyName, ILoc,
942 PropertyLoc);
943 break;
944 }
945
946 // In an Objective-C method, if we have "super" followed by an identifier,
947 // the token sequence is ill-formed. However, if there's a ':' or ']' after
948 // that identifier, this is probably a message send with a missing open
949 // bracket. Treat it as such.
950 if (getLangOpts().ObjC && &II == Ident_super && !InMessageExpression &&
951 getCurScope()->isInObjcMethodScope() &&
952 ((Tok.is(tok::identifier) &&
953 (NextToken().is(tok::colon) || NextToken().is(tok::r_square))) ||
954 Tok.is(tok::code_completion))) {
955 Res = ParseObjCMessageExpressionBody(SourceLocation(), ILoc, nullptr,
956 nullptr);
957 break;
958 }
959
960 // If we have an Objective-C class name followed by an identifier
961 // and either ':' or ']', this is an Objective-C class message
962 // send that's missing the opening '['. Recovery
963 // appropriately. Also take this path if we're performing code
964 // completion after an Objective-C class name.
965 if (getLangOpts().ObjC &&
966 ((Tok.is(tok::identifier) && !InMessageExpression) ||
967 Tok.is(tok::code_completion))) {
968 const Token& Next = NextToken();
969 if (Tok.is(tok::code_completion) ||
970 Next.is(tok::colon) || Next.is(tok::r_square))
971 if (ParsedType Typ = Actions.getTypeName(II, ILoc, getCurScope()))
972 if (Typ.get()->isObjCObjectOrInterfaceType()) {
973 // Fake up a Declarator to use with ActOnTypeName.
974 DeclSpec DS(AttrFactory);
975 DS.SetRangeStart(ILoc);
976 DS.SetRangeEnd(ILoc);
977 const char *PrevSpec = nullptr;
978 unsigned DiagID;
979 DS.SetTypeSpecType(TST_typename, ILoc, PrevSpec, DiagID, Typ,
980 Actions.getASTContext().getPrintingPolicy());
981
982 Declarator DeclaratorInfo(DS, ParsedAttributesView::none(),
984 TypeResult Ty = Actions.ActOnTypeName(DeclaratorInfo);
985 if (Ty.isInvalid())
986 break;
987
988 Res = ParseObjCMessageExpressionBody(SourceLocation(),
990 Ty.get(), nullptr);
991 break;
992 }
993 }
994
995 // Make sure to pass down the right value for isAddressOfOperand.
996 if (isAddressOfOperand && isPostfixExpressionSuffixStart())
997 isAddressOfOperand = false;
998
999 // Function designators are allowed to be undeclared (C99 6.5.1p2), so we
1000 // need to know whether or not this identifier is a function designator or
1001 // not.
1002 UnqualifiedId Name;
1003 CXXScopeSpec ScopeSpec;
1004 SourceLocation TemplateKWLoc;
1005 Token Replacement;
1006 CastExpressionIdValidator Validator(Tok, CorrectionBehavior);
1007 Validator.IsAddressOfOperand = isAddressOfOperand;
1008 if (Tok.isOneOf(tok::periodstar, tok::arrowstar)) {
1009 Validator.WantExpressionKeywords = false;
1010 Validator.WantRemainingKeywords = false;
1011 } else {
1012 Validator.WantRemainingKeywords = Tok.isNot(tok::r_paren);
1013 }
1014 Name.setIdentifier(&II, ILoc);
1015 Res = Actions.ActOnIdExpression(
1016 getCurScope(), ScopeSpec, TemplateKWLoc, Name, Tok.is(tok::l_paren),
1017 isAddressOfOperand, &Validator,
1018 /*IsInlineAsmIdentifier=*/false,
1019 Tok.is(tok::r_paren) ? nullptr : &Replacement);
1020 if (!Res.isInvalid() && Res.isUnset()) {
1021 UnconsumeToken(Replacement);
1022 return ParseCastExpression(
1023 ParseKind, isAddressOfOperand, NotCastExpr, CorrectionBehavior,
1024 /*isVectorLiteral=*/false, NotPrimaryExpression);
1025 }
1026 Res = tryParseCXXPackIndexingExpression(Res);
1027 if (!Res.isInvalid() && Tok.is(tok::less))
1028 checkPotentialAngleBracket(Res);
1029 break;
1030 }
1031 case tok::char_constant: // constant: character-constant
1032 case tok::wide_char_constant:
1033 case tok::utf8_char_constant:
1034 case tok::utf16_char_constant:
1035 case tok::utf32_char_constant:
1036 Res = Actions.ActOnCharacterConstant(Tok, /*UDLScope*/getCurScope());
1037 ConsumeToken();
1038 break;
1039 case tok::kw___func__: // primary-expression: __func__ [C99 6.4.2.2]
1040 case tok::kw___FUNCTION__: // primary-expression: __FUNCTION__ [GNU]
1041 case tok::kw___FUNCDNAME__: // primary-expression: __FUNCDNAME__ [MS]
1042 case tok::kw___FUNCSIG__: // primary-expression: __FUNCSIG__ [MS]
1043 case tok::kw_L__FUNCTION__: // primary-expression: L__FUNCTION__ [MS]
1044 case tok::kw_L__FUNCSIG__: // primary-expression: L__FUNCSIG__ [MS]
1045 case tok::kw___PRETTY_FUNCTION__: // primary-expression: __P..Y_F..N__ [GNU]
1046 // Function local predefined macros are represented by PredefinedExpr except
1047 // when Microsoft extensions are enabled and one of these macros is adjacent
1048 // to a string literal or another one of these macros.
1049 if (!(getLangOpts().MicrosoftExt &&
1052 Res = Actions.ActOnPredefinedExpr(Tok.getLocation(), SavedKind);
1053 ConsumeToken();
1054 break;
1055 }
1056 [[fallthrough]]; // treat MS function local macros as concatenable strings
1057 case tok::string_literal: // primary-expression: string-literal
1058 case tok::wide_string_literal:
1059 case tok::utf8_string_literal:
1060 case tok::utf16_string_literal:
1061 case tok::utf32_string_literal:
1062 Res = ParseStringLiteralExpression(true);
1063 break;
1064 case tok::kw__Generic: // primary-expression: generic-selection [C11 6.5.1]
1065 Res = ParseGenericSelectionExpression();
1066 break;
1067 case tok::kw___builtin_available:
1068 Res = ParseAvailabilityCheckExpr(Tok.getLocation());
1069 break;
1070 case tok::kw___builtin_va_arg:
1071 case tok::kw___builtin_offsetof:
1072 case tok::kw___builtin_choose_expr:
1073 case tok::kw___builtin_astype: // primary-expression: [OCL] as_type()
1074 case tok::kw___builtin_convertvector:
1075 case tok::kw___builtin_COLUMN:
1076 case tok::kw___builtin_FILE:
1077 case tok::kw___builtin_FILE_NAME:
1078 case tok::kw___builtin_FUNCTION:
1079 case tok::kw___builtin_FUNCSIG:
1080 case tok::kw___builtin_LINE:
1081 case tok::kw___builtin_source_location:
1082 if (NotPrimaryExpression)
1083 *NotPrimaryExpression = true;
1084 // This parses the complete suffix; we can return early.
1085 return ParseBuiltinPrimaryExpression();
1086 case tok::kw___null:
1087 Res = Actions.ActOnGNUNullExpr(ConsumeToken());
1088 break;
1089
1090 case tok::plusplus: // unary-expression: '++' unary-expression [C99]
1091 case tok::minusminus: { // unary-expression: '--' unary-expression [C99]
1092 if (NotPrimaryExpression)
1093 *NotPrimaryExpression = true;
1094 // C++ [expr.unary] has:
1095 // unary-expression:
1096 // ++ cast-expression
1097 // -- cast-expression
1098 Token SavedTok = Tok;
1099 ConsumeToken();
1100
1101 PreferredType.enterUnary(Actions, Tok.getLocation(), SavedTok.getKind(),
1102 SavedTok.getLocation());
1103 // One special case is implicitly handled here: if the preceding tokens are
1104 // an ambiguous cast expression, such as "(T())++", then we recurse to
1105 // determine whether the '++' is prefix or postfix.
1106 Res = ParseCastExpression(getLangOpts().CPlusPlus
1109 /*isAddressOfOperand*/ false, NotCastExpr,
1111 if (NotCastExpr) {
1112 // If we return with NotCastExpr = true, we must not consume any tokens,
1113 // so put the token back where we found it.
1114 assert(Res.isInvalid());
1115 UnconsumeToken(SavedTok);
1116 return ExprError();
1117 }
1118 if (!Res.isInvalid()) {
1119 Expr *Arg = Res.get();
1120 Res = Actions.ActOnUnaryOp(getCurScope(), SavedTok.getLocation(),
1121 SavedKind, Arg);
1122 if (Res.isInvalid())
1123 Res = Actions.CreateRecoveryExpr(SavedTok.getLocation(),
1124 Arg->getEndLoc(), Arg);
1125 }
1126 return Res;
1127 }
1128 case tok::amp: { // unary-expression: '&' cast-expression
1129 if (NotPrimaryExpression)
1130 *NotPrimaryExpression = true;
1131 // Special treatment because of member pointers
1132 SourceLocation SavedLoc = ConsumeToken();
1133 PreferredType.enterUnary(Actions, Tok.getLocation(), tok::amp, SavedLoc);
1134
1135 Res = ParseCastExpression(CastParseKind::AnyCastExpr,
1136 /*isAddressOfOperand=*/true);
1137 if (!Res.isInvalid()) {
1138 Expr *Arg = Res.get();
1139 Res = Actions.ActOnUnaryOp(getCurScope(), SavedLoc, SavedKind, Arg);
1140 if (Res.isInvalid())
1141 Res = Actions.CreateRecoveryExpr(Tok.getLocation(), Arg->getEndLoc(),
1142 Arg);
1143 }
1144 return Res;
1145 }
1146
1147 case tok::star: // unary-expression: '*' cast-expression
1148 case tok::plus: // unary-expression: '+' cast-expression
1149 case tok::minus: // unary-expression: '-' cast-expression
1150 case tok::tilde: // unary-expression: '~' cast-expression
1151 case tok::exclaim: // unary-expression: '!' cast-expression
1152 case tok::kw___real: // unary-expression: '__real' cast-expression [GNU]
1153 case tok::kw___imag: { // unary-expression: '__imag' cast-expression [GNU]
1154 if (NotPrimaryExpression)
1155 *NotPrimaryExpression = true;
1156 SourceLocation SavedLoc = ConsumeToken();
1157 PreferredType.enterUnary(Actions, Tok.getLocation(), SavedKind, SavedLoc);
1158 Res = ParseCastExpression(CastParseKind::AnyCastExpr);
1159 if (!Res.isInvalid()) {
1160 Expr *Arg = Res.get();
1161 Res = Actions.ActOnUnaryOp(getCurScope(), SavedLoc, SavedKind, Arg,
1162 isAddressOfOperand);
1163 if (Res.isInvalid())
1164 Res = Actions.CreateRecoveryExpr(SavedLoc, Arg->getEndLoc(), Arg);
1165 }
1166 return Res;
1167 }
1168
1169 case tok::kw_co_await: { // unary-expression: 'co_await' cast-expression
1170 if (NotPrimaryExpression)
1171 *NotPrimaryExpression = true;
1172 SourceLocation CoawaitLoc = ConsumeToken();
1173 Res = ParseCastExpression(CastParseKind::AnyCastExpr);
1174 if (!Res.isInvalid())
1175 Res = Actions.ActOnCoawaitExpr(getCurScope(), CoawaitLoc, Res.get());
1176 return Res;
1177 }
1178
1179 case tok::kw___extension__:{//unary-expression:'__extension__' cast-expr [GNU]
1180 // __extension__ silences extension warnings in the subexpression.
1181 if (NotPrimaryExpression)
1182 *NotPrimaryExpression = true;
1183 ExtensionRAIIObject O(Diags); // Use RAII to do this.
1184 SourceLocation SavedLoc = ConsumeToken();
1185 Res = ParseCastExpression(CastParseKind::AnyCastExpr);
1186 if (!Res.isInvalid())
1187 Res = Actions.ActOnUnaryOp(getCurScope(), SavedLoc, SavedKind, Res.get());
1188 return Res;
1189 }
1190 case tok::kw__Alignof: // unary-expression: '_Alignof' '(' type-name ')'
1191 diagnoseUseOfC11Keyword(Tok);
1192 [[fallthrough]];
1193 case tok::kw_alignof: // unary-expression: 'alignof' '(' type-id ')'
1194 case tok::kw___alignof: // unary-expression: '__alignof' unary-expression
1195 // unary-expression: '__alignof' '(' type-name ')'
1196 case tok::kw_sizeof: // unary-expression: 'sizeof' unary-expression
1197 // unary-expression: 'sizeof' '(' type-name ')'
1198 // unary-expression: '__datasizeof' unary-expression
1199 // unary-expression: '__datasizeof' '(' type-name ')'
1200 case tok::kw___datasizeof:
1201 case tok::kw_vec_step: // unary-expression: OpenCL 'vec_step' expression
1202 // unary-expression: '__builtin_omp_required_simd_align' '(' type-name ')'
1203 case tok::kw___builtin_omp_required_simd_align:
1204 case tok::kw___builtin_vectorelements:
1205 case tok::kw__Countof:
1206 if (NotPrimaryExpression)
1207 *NotPrimaryExpression = true;
1208 AllowSuffix = false;
1209 Res = ParseUnaryExprOrTypeTraitExpression();
1210 break;
1211 case tok::ampamp: { // unary-expression: '&&' identifier
1212 if (NotPrimaryExpression)
1213 *NotPrimaryExpression = true;
1214 SourceLocation AmpAmpLoc = ConsumeToken();
1215 if (Tok.isNot(tok::identifier))
1216 return ExprError(Diag(Tok, diag::err_expected) << tok::identifier);
1217
1218 if (getCurScope()->getFnParent() == nullptr)
1219 return ExprError(Diag(Tok, diag::err_address_of_label_outside_fn));
1220
1221 Diag(AmpAmpLoc, diag::ext_gnu_address_of_label);
1223 Tok.getLocation());
1224 Res = Actions.ActOnAddrLabel(AmpAmpLoc, Tok.getLocation(), LD);
1225 ConsumeToken();
1226 AllowSuffix = false;
1227 break;
1228 }
1229 case tok::kw_const_cast:
1230 case tok::kw_dynamic_cast:
1231 case tok::kw_reinterpret_cast:
1232 case tok::kw_static_cast:
1233 case tok::kw_addrspace_cast:
1234 if (NotPrimaryExpression)
1235 *NotPrimaryExpression = true;
1236 Res = ParseCXXCasts();
1237 break;
1238 case tok::kw___builtin_bit_cast:
1239 if (NotPrimaryExpression)
1240 *NotPrimaryExpression = true;
1241 Res = ParseBuiltinBitCast();
1242 break;
1243 case tok::kw_typeid:
1244 if (NotPrimaryExpression)
1245 *NotPrimaryExpression = true;
1246 Res = ParseCXXTypeid();
1247 break;
1248 case tok::kw___uuidof:
1249 if (NotPrimaryExpression)
1250 *NotPrimaryExpression = true;
1251 Res = ParseCXXUuidof();
1252 break;
1253 case tok::kw_this:
1254 Res = ParseCXXThis();
1255 break;
1256 case tok::kw___builtin_sycl_unique_stable_name:
1257 Res = ParseSYCLUniqueStableNameExpression();
1258 break;
1259
1260 case tok::annot_typename:
1261 if (isStartOfObjCClassMessageMissingOpenBracket()) {
1263
1264 // Fake up a Declarator to use with ActOnTypeName.
1265 DeclSpec DS(AttrFactory);
1266 DS.SetRangeStart(Tok.getLocation());
1267 DS.SetRangeEnd(Tok.getLastLoc());
1268
1269 const char *PrevSpec = nullptr;
1270 unsigned DiagID;
1271 DS.SetTypeSpecType(TST_typename, Tok.getAnnotationEndLoc(),
1272 PrevSpec, DiagID, Type,
1273 Actions.getASTContext().getPrintingPolicy());
1274
1275 Declarator DeclaratorInfo(DS, ParsedAttributesView::none(),
1277 TypeResult Ty = Actions.ActOnTypeName(DeclaratorInfo);
1278 if (Ty.isInvalid())
1279 break;
1280
1281 ConsumeAnnotationToken();
1282 Res = ParseObjCMessageExpressionBody(SourceLocation(), SourceLocation(),
1283 Ty.get(), nullptr);
1284 break;
1285 }
1286 [[fallthrough]];
1287
1288 case tok::annot_decltype:
1289 case tok::annot_pack_indexing_type:
1290 case tok::kw_char:
1291 case tok::kw_wchar_t:
1292 case tok::kw_char8_t:
1293 case tok::kw_char16_t:
1294 case tok::kw_char32_t:
1295 case tok::kw_bool:
1296 case tok::kw_short:
1297 case tok::kw_int:
1298 case tok::kw_long:
1299 case tok::kw___int64:
1300 case tok::kw___int128:
1301 case tok::kw__ExtInt:
1302 case tok::kw__BitInt:
1303 case tok::kw_signed:
1304 case tok::kw_unsigned:
1305 case tok::kw_half:
1306 case tok::kw_float:
1307 case tok::kw_double:
1308 case tok::kw___bf16:
1309 case tok::kw__Float16:
1310 case tok::kw___float128:
1311 case tok::kw___ibm128:
1312 case tok::kw_void:
1313 case tok::kw_auto:
1314 case tok::kw_typename:
1315 case tok::kw_typeof:
1316 case tok::kw___vector:
1317 case tok::kw__Accum:
1318 case tok::kw__Fract:
1319 case tok::kw__Sat:
1320#define GENERIC_IMAGE_TYPE(ImgType, Id) case tok::kw_##ImgType##_t:
1321#include "clang/Basic/OpenCLImageTypes.def"
1322#define HLSL_INTANGIBLE_TYPE(Name, Id, SingletonId) case tok::kw_##Name:
1323#include "clang/Basic/HLSLIntangibleTypes.def"
1324 {
1325 if (!getLangOpts().CPlusPlus) {
1326 Diag(Tok, diag::err_expected_expression);
1327 return ExprError();
1328 }
1329
1330 // Everything henceforth is a postfix-expression.
1331 if (NotPrimaryExpression)
1332 *NotPrimaryExpression = true;
1333
1334 if (SavedKind == tok::kw_typename) {
1335 // postfix-expression: typename-specifier '(' expression-list[opt] ')'
1336 // typename-specifier braced-init-list
1338 return ExprError();
1339
1341 // We are trying to parse a simple-type-specifier but might not get such
1342 // a token after error recovery.
1343 return ExprError();
1344 }
1345
1346 // postfix-expression: simple-type-specifier '(' expression-list[opt] ')'
1347 // simple-type-specifier braced-init-list
1348 //
1349 DeclSpec DS(AttrFactory);
1350
1351 ParseCXXSimpleTypeSpecifier(DS);
1352 if (Tok.isNot(tok::l_paren) &&
1353 (!getLangOpts().CPlusPlus11 || Tok.isNot(tok::l_brace)))
1354 return ExprError(Diag(Tok, diag::err_expected_lparen_after_type)
1355 << DS.getSourceRange());
1356
1357 if (Tok.is(tok::l_brace))
1358 Diag(Tok, diag::warn_cxx98_compat_generalized_initializer_lists);
1359
1360 Res = ParseCXXTypeConstructExpression(DS);
1361 break;
1362 }
1363
1364 case tok::annot_cxxscope: { // [C++] id-expression: qualified-id
1365 // If TryAnnotateTypeOrScopeToken annotates the token, tail recurse.
1366 // (We can end up in this situation after tentative parsing.)
1368 return ExprError();
1369 if (!Tok.is(tok::annot_cxxscope))
1370 return ParseCastExpression(ParseKind, isAddressOfOperand, NotCastExpr,
1371 CorrectionBehavior, isVectorLiteral,
1372 NotPrimaryExpression);
1373
1374 Token Next = NextToken();
1375 if (Next.is(tok::annot_template_id)) {
1376 TemplateIdAnnotation *TemplateId = takeTemplateIdAnnotation(Next);
1377 if (TemplateId->Kind == TNK_Type_template) {
1378 // We have a qualified template-id that we know refers to a
1379 // type, translate it into a type and continue parsing as a
1380 // cast expression.
1381 CXXScopeSpec SS;
1382 ParseOptionalCXXScopeSpecifier(SS, /*ObjectType=*/nullptr,
1383 /*ObjectHasErrors=*/false,
1384 /*EnteringContext=*/false);
1385 AnnotateTemplateIdTokenAsType(SS, ImplicitTypenameContext::Yes);
1386 return ParseCastExpression(ParseKind, isAddressOfOperand, NotCastExpr,
1387 CorrectionBehavior, isVectorLiteral,
1388 NotPrimaryExpression);
1389 }
1390 }
1391
1392 // Parse as an id-expression.
1393 Res = ParseCXXIdExpression(isAddressOfOperand);
1394 break;
1395 }
1396
1397 case tok::annot_template_id: { // [C++] template-id
1398 TemplateIdAnnotation *TemplateId = takeTemplateIdAnnotation(Tok);
1399 if (TemplateId->Kind == TNK_Type_template) {
1400 // We have a template-id that we know refers to a type,
1401 // translate it into a type and continue parsing as a cast
1402 // expression.
1403 CXXScopeSpec SS;
1404 AnnotateTemplateIdTokenAsType(SS, ImplicitTypenameContext::Yes);
1405 return ParseCastExpression(ParseKind, isAddressOfOperand, NotCastExpr,
1406 CorrectionBehavior, isVectorLiteral,
1407 NotPrimaryExpression);
1408 }
1409
1410 // Fall through to treat the template-id as an id-expression.
1411 [[fallthrough]];
1412 }
1413
1414 case tok::kw_operator: // [C++] id-expression: operator/conversion-function-id
1415 Res = ParseCXXIdExpression(isAddressOfOperand);
1416 break;
1417
1418 case tok::coloncolon: {
1419 // ::foo::bar -> global qualified name etc. If TryAnnotateTypeOrScopeToken
1420 // annotates the token, tail recurse.
1422 return ExprError();
1423 if (!Tok.is(tok::coloncolon))
1424 return ParseCastExpression(ParseKind, isAddressOfOperand,
1425 CorrectionBehavior, isVectorLiteral,
1426 NotPrimaryExpression);
1427
1428 // ::new -> [C++] new-expression
1429 // ::delete -> [C++] delete-expression
1430 SourceLocation CCLoc = ConsumeToken();
1431 if (Tok.is(tok::kw_new)) {
1432 if (NotPrimaryExpression)
1433 *NotPrimaryExpression = true;
1434 Res = ParseCXXNewExpression(true, CCLoc);
1435 AllowSuffix = false;
1436 break;
1437 }
1438 if (Tok.is(tok::kw_delete)) {
1439 if (NotPrimaryExpression)
1440 *NotPrimaryExpression = true;
1441 Res = ParseCXXDeleteExpression(true, CCLoc);
1442 AllowSuffix = false;
1443 break;
1444 }
1445
1446 // This is not a type name or scope specifier, it is an invalid expression.
1447 Diag(CCLoc, diag::err_expected_expression);
1448 return ExprError();
1449 }
1450
1451 case tok::kw_new: // [C++] new-expression
1452 if (NotPrimaryExpression)
1453 *NotPrimaryExpression = true;
1454 Res = ParseCXXNewExpression(false, Tok.getLocation());
1455 AllowSuffix = false;
1456 break;
1457
1458 case tok::kw_delete: // [C++] delete-expression
1459 if (NotPrimaryExpression)
1460 *NotPrimaryExpression = true;
1461 Res = ParseCXXDeleteExpression(false, Tok.getLocation());
1462 AllowSuffix = false;
1463 break;
1464
1465 case tok::kw_requires: // [C++2a] requires-expression
1466 Res = ParseRequiresExpression();
1467 AllowSuffix = false;
1468 break;
1469
1470 case tok::kw_noexcept: { // [C++0x] 'noexcept' '(' expression ')'
1471 if (NotPrimaryExpression)
1472 *NotPrimaryExpression = true;
1473 Diag(Tok, diag::warn_cxx98_compat_noexcept_expr);
1474 SourceLocation KeyLoc = ConsumeToken();
1475 BalancedDelimiterTracker T(*this, tok::l_paren);
1476
1477 if (T.expectAndConsume(diag::err_expected_lparen_after, "noexcept"))
1478 return ExprError();
1479 // C++11 [expr.unary.noexcept]p1:
1480 // The noexcept operator determines whether the evaluation of its operand,
1481 // which is an unevaluated operand, can throw an exception.
1484 Res = ParseExpression();
1485
1486 T.consumeClose();
1487
1488 if (!Res.isInvalid())
1489 Res = Actions.ActOnNoexceptExpr(KeyLoc, T.getOpenLocation(), Res.get(),
1490 T.getCloseLocation());
1491 AllowSuffix = false;
1492 break;
1493 }
1494
1495#define TYPE_TRAIT(N,Spelling,K) \
1496 case tok::kw_##Spelling:
1497#include "clang/Basic/TokenKinds.def"
1498 Res = ParseTypeTrait();
1499 break;
1500
1501 case tok::kw___array_rank:
1502 case tok::kw___array_extent:
1503 if (NotPrimaryExpression)
1504 *NotPrimaryExpression = true;
1505 Res = ParseArrayTypeTrait();
1506 break;
1507
1508 case tok::kw___builtin_ptrauth_type_discriminator:
1509 return ParseBuiltinPtrauthTypeDiscriminator();
1510
1511 case tok::kw___is_lvalue_expr:
1512 case tok::kw___is_rvalue_expr:
1513 if (NotPrimaryExpression)
1514 *NotPrimaryExpression = true;
1515 Res = ParseExpressionTrait();
1516 break;
1517
1518 case tok::at: {
1519 if (NotPrimaryExpression)
1520 *NotPrimaryExpression = true;
1521 SourceLocation AtLoc = ConsumeToken();
1522 return ParseObjCAtExpression(AtLoc);
1523 }
1524 case tok::caret:
1525 Res = ParseBlockLiteralExpression();
1526 break;
1527 case tok::code_completion: {
1528 cutOffParsing();
1530 getCurScope(), PreferredType.get(Tok.getLocation()));
1531 return ExprError();
1532 }
1533#define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) case tok::kw___##Trait:
1534#include "clang/Basic/TransformTypeTraits.def"
1535 // HACK: libstdc++ uses some of the transform-type-traits as alias
1536 // templates, so we need to work around this.
1537 if (!NextToken().is(tok::l_paren)) {
1538 Tok.setKind(tok::identifier);
1539 Diag(Tok, diag::ext_keyword_as_ident)
1540 << Tok.getIdentifierInfo()->getName() << 0;
1541 goto ParseIdentifier;
1542 }
1543 goto ExpectedExpression;
1544 case tok::l_square:
1545 if (getLangOpts().CPlusPlus) {
1546 if (getLangOpts().ObjC) {
1547 // C++11 lambda expressions and Objective-C message sends both start with a
1548 // square bracket. There are three possibilities here:
1549 // we have a valid lambda expression, we have an invalid lambda
1550 // expression, or we have something that doesn't appear to be a lambda.
1551 // If we're in the last case, we fall back to ParseObjCMessageExpression.
1552 Res = TryParseLambdaExpression();
1553 if (!Res.isInvalid() && !Res.get()) {
1554 // We assume Objective-C++ message expressions are not
1555 // primary-expressions.
1556 if (NotPrimaryExpression)
1557 *NotPrimaryExpression = true;
1558 Res = ParseObjCMessageExpression();
1559 }
1560 break;
1561 }
1562 Res = ParseLambdaExpression();
1563 break;
1564 }
1565 if (getLangOpts().ObjC) {
1566 Res = ParseObjCMessageExpression();
1567 break;
1568 }
1569 [[fallthrough]];
1570 default:
1571 ExpectedExpression:
1572 NotCastExpr = true;
1573 return ExprError();
1574 }
1575
1576 // Check to see whether Res is a function designator only. If it is and we
1577 // are compiling for OpenCL, we need to return an error as this implies
1578 // that the address of the function is being taken, which is illegal in CL.
1579
1580 if (ParseKind == CastParseKind::PrimaryExprOnly)
1581 // This is strictly a primary-expression - no postfix-expr pieces should be
1582 // parsed.
1583 return Res;
1584
1585 if (!AllowSuffix) {
1586 // FIXME: Don't parse a primary-expression suffix if we encountered a parse
1587 // error already.
1588 if (Res.isInvalid())
1589 return Res;
1590
1591 switch (Tok.getKind()) {
1592 case tok::l_square:
1593 case tok::l_paren:
1594 case tok::plusplus:
1595 case tok::minusminus:
1596 // "expected ';'" or similar is probably the right diagnostic here. Let
1597 // the caller decide what to do.
1598 if (Tok.isAtStartOfLine())
1599 return Res;
1600
1601 [[fallthrough]];
1602 case tok::period:
1603 case tok::arrow:
1604 break;
1605
1606 default:
1607 return Res;
1608 }
1609
1610 // This was a unary-expression for which a postfix-expression suffix is
1611 // not permitted by the grammar (eg, a sizeof expression or
1612 // new-expression or similar). Diagnose but parse the suffix anyway.
1613 Diag(Tok.getLocation(), diag::err_postfix_after_unary_requires_parens)
1614 << Tok.getKind() << Res.get()->getSourceRange()
1616 << FixItHint::CreateInsertion(PP.getLocForEndOfToken(PrevTokLocation),
1617 ")");
1618 }
1619
1620 // These can be followed by postfix-expr pieces.
1621 PreferredType = SavedType;
1622 Res = ParsePostfixExpressionSuffix(Res);
1623 if (getLangOpts().OpenCL &&
1624 !getActions().getOpenCLOptions().isAvailableOption(
1625 "__cl_clang_function_pointers", getLangOpts()))
1626 if (Expr *PostfixExpr = Res.get()) {
1627 QualType Ty = PostfixExpr->getType();
1628 if (!Ty.isNull() && Ty->isFunctionType()) {
1629 Diag(PostfixExpr->getExprLoc(),
1630 diag::err_opencl_taking_function_address_parser);
1631 return ExprError();
1632 }
1633 }
1634
1635 return Res;
1636}
1637
1639Parser::ParsePostfixExpressionSuffix(ExprResult LHS) {
1640 // Now that the primary-expression piece of the postfix-expression has been
1641 // parsed, see if there are any postfix-expression pieces here.
1643 auto SavedType = PreferredType;
1644 while (true) {
1645 // Each iteration relies on preferred type for the whole expression.
1646 PreferredType = SavedType;
1647 switch (Tok.getKind()) {
1648 case tok::code_completion:
1649 if (InMessageExpression)
1650 return LHS;
1651
1652 cutOffParsing();
1654 getCurScope(), LHS, PreferredType.get(Tok.getLocation()));
1655 return ExprError();
1656
1657 case tok::identifier:
1658 // If we see identifier: after an expression, and we're not already in a
1659 // message send, then this is probably a message send with a missing
1660 // opening bracket '['.
1661 if (getLangOpts().ObjC && !InMessageExpression &&
1662 (NextToken().is(tok::colon) || NextToken().is(tok::r_square))) {
1663 LHS = ParseObjCMessageExpressionBody(SourceLocation(), SourceLocation(),
1664 nullptr, LHS.get());
1665 break;
1666 }
1667 // Fall through; this isn't a message send.
1668 [[fallthrough]];
1669
1670 default: // Not a postfix-expression suffix.
1671 return LHS;
1672 case tok::l_square: { // postfix-expression: p-e '[' expression ']'
1673 // If we have a array postfix expression that starts on a new line and
1674 // Objective-C is enabled, it is highly likely that the user forgot a
1675 // semicolon after the base expression and that the array postfix-expr is
1676 // actually another message send. In this case, do some look-ahead to see
1677 // if the contents of the square brackets are obviously not a valid
1678 // expression and recover by pretending there is no suffix.
1679 if (getLangOpts().ObjC && Tok.isAtStartOfLine() &&
1680 isSimpleObjCMessageExpression())
1681 return LHS;
1682
1683 // Reject array indices starting with a lambda-expression. '[[' is
1684 // reserved for attributes.
1685 if (CheckProhibitedCXX11Attribute()) {
1686 return ExprError();
1687 }
1688 BalancedDelimiterTracker T(*this, tok::l_square);
1689 T.consumeOpen();
1690 Loc = T.getOpenLocation();
1691 ExprResult Length, Stride;
1692 SourceLocation ColonLocFirst, ColonLocSecond;
1693 ExprVector ArgExprs;
1694 bool HasError = false;
1695 PreferredType.enterSubscript(Actions, Tok.getLocation(), LHS.get());
1696
1697 // We try to parse a list of indexes in all language mode first
1698 // and, in we find 0 or one index, we try to parse an OpenMP/OpenACC array
1699 // section. This allow us to support C++23 multi dimensional subscript and
1700 // OpenMP/OpenACC sections in the same language mode.
1701 if ((!getLangOpts().OpenMP && !AllowOpenACCArraySections) ||
1702 Tok.isNot(tok::colon)) {
1703 if (!getLangOpts().CPlusPlus23) {
1704 ExprResult Idx;
1705 if (getLangOpts().CPlusPlus11 && Tok.is(tok::l_brace)) {
1706 Diag(Tok, diag::warn_cxx98_compat_generalized_initializer_lists);
1707 Idx = ParseBraceInitializer();
1708 } else {
1709 Idx = ParseExpression(); // May be a comma expression
1710 }
1711 if (Idx.isInvalid()) {
1712 HasError = true;
1713 } else {
1714 ArgExprs.push_back(Idx.get());
1715 }
1716 } else if (Tok.isNot(tok::r_square)) {
1717 if (ParseExpressionList(ArgExprs)) {
1718 HasError = true;
1719 }
1720 }
1721 }
1722
1723 // Handle OpenACC first, since 'AllowOpenACCArraySections' is only enabled
1724 // when actively parsing a 'var' in a 'var-list' during clause/'cache'
1725 // parsing, so it is the most specific, and best allows us to handle
1726 // OpenACC and OpenMP at the same time.
1727 if (ArgExprs.size() <= 1 && AllowOpenACCArraySections) {
1728 ColonProtectionRAIIObject RAII(*this);
1729 if (Tok.is(tok::colon)) {
1730 // Consume ':'
1731 ColonLocFirst = ConsumeToken();
1732 if (Tok.isNot(tok::r_square))
1733 Length = ParseExpression();
1734 }
1735 } else if (ArgExprs.size() <= 1 && getLangOpts().OpenMP) {
1736 ColonProtectionRAIIObject RAII(*this);
1737 if (Tok.is(tok::colon)) {
1738 // Consume ':'
1739 ColonLocFirst = ConsumeToken();
1740 if (Tok.isNot(tok::r_square) &&
1741 (getLangOpts().OpenMP < 50 ||
1742 ((Tok.isNot(tok::colon) && getLangOpts().OpenMP >= 50)))) {
1743 Length = ParseExpression();
1744 }
1745 }
1746 if (getLangOpts().OpenMP >= 50 &&
1747 (OMPClauseKind == llvm::omp::Clause::OMPC_to ||
1748 OMPClauseKind == llvm::omp::Clause::OMPC_from) &&
1749 Tok.is(tok::colon)) {
1750 // Consume ':'
1751 ColonLocSecond = ConsumeToken();
1752 if (Tok.isNot(tok::r_square)) {
1753 Stride = ParseExpression();
1754 }
1755 }
1756 }
1757
1758 SourceLocation RLoc = Tok.getLocation();
1759 if (!LHS.isInvalid() && !HasError && !Length.isInvalid() &&
1760 !Stride.isInvalid() && Tok.is(tok::r_square)) {
1761 if (ColonLocFirst.isValid() || ColonLocSecond.isValid()) {
1762 // Like above, AllowOpenACCArraySections is 'more specific' and only
1763 // enabled when actively parsing a 'var' in a 'var-list' during
1764 // clause/'cache' construct parsing, so it is more specific. So we
1765 // should do it first, so that the correct node gets created.
1766 if (AllowOpenACCArraySections) {
1767 assert(!Stride.isUsable() && !ColonLocSecond.isValid() &&
1768 "Stride/second colon not allowed for OpenACC");
1769 LHS = Actions.OpenACC().ActOnArraySectionExpr(
1770 LHS.get(), Loc, ArgExprs.empty() ? nullptr : ArgExprs[0],
1771 ColonLocFirst, Length.get(), RLoc);
1772 } else {
1773 LHS = Actions.OpenMP().ActOnOMPArraySectionExpr(
1774 LHS.get(), Loc, ArgExprs.empty() ? nullptr : ArgExprs[0],
1775 ColonLocFirst, ColonLocSecond, Length.get(), Stride.get(),
1776 RLoc);
1777 }
1778 } else {
1779 LHS = Actions.ActOnArraySubscriptExpr(getCurScope(), LHS.get(), Loc,
1780 ArgExprs, RLoc);
1781 }
1782 } else {
1783 LHS = ExprError();
1784 }
1785
1786 // Match the ']'.
1787 T.consumeClose();
1788 break;
1789 }
1790
1791 case tok::l_paren: // p-e: p-e '(' argument-expression-list[opt] ')'
1792 case tok::lesslessless: { // p-e: p-e '<<<' argument-expression-list '>>>'
1793 // '(' argument-expression-list[opt] ')'
1794 tok::TokenKind OpKind = Tok.getKind();
1795 InMessageExpressionRAIIObject InMessage(*this, false);
1796
1797 Expr *ExecConfig = nullptr;
1798
1799 BalancedDelimiterTracker PT(*this, tok::l_paren);
1800
1801 if (OpKind == tok::lesslessless) {
1802 ExprVector ExecConfigExprs;
1803 SourceLocation OpenLoc = ConsumeToken();
1804
1805 if (ParseSimpleExpressionList(ExecConfigExprs)) {
1806 LHS = ExprError();
1807 }
1808
1809 SourceLocation CloseLoc;
1810 if (TryConsumeToken(tok::greatergreatergreater, CloseLoc)) {
1811 } else if (LHS.isInvalid()) {
1812 SkipUntil(tok::greatergreatergreater, StopAtSemi);
1813 } else {
1814 // There was an error closing the brackets
1815 Diag(Tok, diag::err_expected) << tok::greatergreatergreater;
1816 Diag(OpenLoc, diag::note_matching) << tok::lesslessless;
1817 SkipUntil(tok::greatergreatergreater, StopAtSemi);
1818 LHS = ExprError();
1819 }
1820
1821 if (!LHS.isInvalid()) {
1822 if (ExpectAndConsume(tok::l_paren))
1823 LHS = ExprError();
1824 else
1825 Loc = PrevTokLocation;
1826 }
1827
1828 if (!LHS.isInvalid()) {
1829 ExprResult ECResult = Actions.CUDA().ActOnExecConfigExpr(
1830 getCurScope(), OpenLoc, ExecConfigExprs, CloseLoc);
1831 if (ECResult.isInvalid())
1832 LHS = ExprError();
1833 else
1834 ExecConfig = ECResult.get();
1835 }
1836 } else {
1837 PT.consumeOpen();
1838 Loc = PT.getOpenLocation();
1839 }
1840
1841 ExprVector ArgExprs;
1842 auto RunSignatureHelp = [&]() -> QualType {
1843 QualType PreferredType =
1845 LHS.get(), ArgExprs, PT.getOpenLocation());
1846 CalledSignatureHelp = true;
1847 return PreferredType;
1848 };
1849 bool ExpressionListIsInvalid = false;
1850 if (OpKind == tok::l_paren || !LHS.isInvalid()) {
1851 if (Tok.isNot(tok::r_paren)) {
1852 if ((ExpressionListIsInvalid = ParseExpressionList(ArgExprs, [&] {
1853 PreferredType.enterFunctionArgument(Tok.getLocation(),
1854 RunSignatureHelp);
1855 }))) {
1856 // If we got an error when parsing expression list, we don't call
1857 // the CodeCompleteCall handler inside the parser. So call it here
1858 // to make sure we get overload suggestions even when we are in the
1859 // middle of a parameter.
1860 if (PP.isCodeCompletionReached() && !CalledSignatureHelp)
1861 RunSignatureHelp();
1862 }
1863 }
1864 }
1865
1866 // Match the ')'.
1867 if (LHS.isInvalid()) {
1868 SkipUntil(tok::r_paren, StopAtSemi);
1869 } else if (ExpressionListIsInvalid) {
1870 Expr *Fn = LHS.get();
1871 ArgExprs.insert(ArgExprs.begin(), Fn);
1872 LHS = Actions.CreateRecoveryExpr(Fn->getBeginLoc(), Tok.getLocation(),
1873 ArgExprs);
1874 SkipUntil(tok::r_paren, StopAtSemi);
1875 } else if (Tok.isNot(tok::r_paren)) {
1876 bool HadErrors = false;
1877 if (LHS.get()->containsErrors())
1878 HadErrors = true;
1879 for (auto &E : ArgExprs)
1880 if (E->containsErrors())
1881 HadErrors = true;
1882 // If there were errors in the LHS or ArgExprs, call SkipUntil instead
1883 // of PT.consumeClose() to avoid emitting extra diagnostics for the
1884 // unmatched l_paren.
1885 if (HadErrors)
1886 SkipUntil(tok::r_paren, StopAtSemi);
1887 else
1888 PT.consumeClose();
1889 LHS = ExprError();
1890 } else {
1891 Expr *Fn = LHS.get();
1892 SourceLocation RParLoc = Tok.getLocation();
1893 LHS = Actions.ActOnCallExpr(getCurScope(), Fn, Loc, ArgExprs, RParLoc,
1894 ExecConfig);
1895 if (LHS.isInvalid()) {
1896 ArgExprs.insert(ArgExprs.begin(), Fn);
1897 LHS =
1898 Actions.CreateRecoveryExpr(Fn->getBeginLoc(), RParLoc, ArgExprs);
1899 }
1900 PT.consumeClose();
1901 }
1902
1903 break;
1904 }
1905 case tok::arrow:
1906 case tok::period: {
1907 // postfix-expression: p-e '->' template[opt] id-expression
1908 // postfix-expression: p-e '.' template[opt] id-expression
1909 tok::TokenKind OpKind = Tok.getKind();
1910 SourceLocation OpLoc = ConsumeToken(); // Eat the "." or "->" token.
1911
1912 CXXScopeSpec SS;
1913 ParsedType ObjectType;
1914 bool MayBePseudoDestructor = false;
1915 Expr* OrigLHS = !LHS.isInvalid() ? LHS.get() : nullptr;
1916
1917 PreferredType.enterMemAccess(Actions, Tok.getLocation(), OrigLHS);
1918
1919 if (getLangOpts().CPlusPlus && !LHS.isInvalid()) {
1920 Expr *Base = OrigLHS;
1921 const Type* BaseType = Base->getType().getTypePtrOrNull();
1922 if (BaseType && Tok.is(tok::l_paren) &&
1923 (BaseType->isFunctionType() ||
1924 BaseType->isSpecificPlaceholderType(BuiltinType::BoundMember))) {
1925 Diag(OpLoc, diag::err_function_is_not_record)
1926 << OpKind << Base->getSourceRange()
1927 << FixItHint::CreateRemoval(OpLoc);
1928 return ParsePostfixExpressionSuffix(Base);
1929 }
1930
1931 LHS = Actions.ActOnStartCXXMemberReference(getCurScope(), Base, OpLoc,
1932 OpKind, ObjectType,
1933 MayBePseudoDestructor);
1934 if (LHS.isInvalid()) {
1935 // Clang will try to perform expression based completion as a
1936 // fallback, which is confusing in case of member references. So we
1937 // stop here without any completions.
1938 if (Tok.is(tok::code_completion)) {
1939 cutOffParsing();
1940 return ExprError();
1941 }
1942 break;
1943 }
1944 ParseOptionalCXXScopeSpecifier(
1945 SS, ObjectType, LHS.get() && LHS.get()->containsErrors(),
1946 /*EnteringContext=*/false, &MayBePseudoDestructor);
1947 if (SS.isNotEmpty())
1948 ObjectType = nullptr;
1949 }
1950
1951 if (Tok.is(tok::code_completion)) {
1952 tok::TokenKind CorrectedOpKind =
1953 OpKind == tok::arrow ? tok::period : tok::arrow;
1954 ExprResult CorrectedLHS(/*Invalid=*/true);
1955 if (getLangOpts().CPlusPlus && OrigLHS) {
1956 // FIXME: Creating a TentativeAnalysisScope from outside Sema is a
1957 // hack.
1958 Sema::TentativeAnalysisScope Trap(Actions);
1959 CorrectedLHS = Actions.ActOnStartCXXMemberReference(
1960 getCurScope(), OrigLHS, OpLoc, CorrectedOpKind, ObjectType,
1961 MayBePseudoDestructor);
1962 }
1963
1964 Expr *Base = LHS.get();
1965 Expr *CorrectedBase = CorrectedLHS.get();
1966 if (!CorrectedBase && !getLangOpts().CPlusPlus)
1967 CorrectedBase = Base;
1968
1969 // Code completion for a member access expression.
1970 cutOffParsing();
1972 getCurScope(), Base, CorrectedBase, OpLoc, OpKind == tok::arrow,
1973 Base && ExprStatementTokLoc == Base->getBeginLoc(),
1974 PreferredType.get(Tok.getLocation()));
1975
1976 return ExprError();
1977 }
1978
1979 if (MayBePseudoDestructor && !LHS.isInvalid()) {
1980 LHS = ParseCXXPseudoDestructor(LHS.get(), OpLoc, OpKind, SS,
1981 ObjectType);
1982 break;
1983 }
1984
1985 // Either the action has told us that this cannot be a
1986 // pseudo-destructor expression (based on the type of base
1987 // expression), or we didn't see a '~' in the right place. We
1988 // can still parse a destructor name here, but in that case it
1989 // names a real destructor.
1990 // Allow explicit constructor calls in Microsoft mode.
1991 // FIXME: Add support for explicit call of template constructor.
1992 SourceLocation TemplateKWLoc;
1993 UnqualifiedId Name;
1994 if (getLangOpts().ObjC && OpKind == tok::period &&
1995 Tok.is(tok::kw_class)) {
1996 // Objective-C++:
1997 // After a '.' in a member access expression, treat the keyword
1998 // 'class' as if it were an identifier.
1999 //
2000 // This hack allows property access to the 'class' method because it is
2001 // such a common method name. For other C++ keywords that are
2002 // Objective-C method names, one must use the message send syntax.
2005 Name.setIdentifier(Id, Loc);
2006 } else if (ParseUnqualifiedId(
2007 SS, ObjectType, LHS.get() && LHS.get()->containsErrors(),
2008 /*EnteringContext=*/false,
2009 /*AllowDestructorName=*/true,
2010 /*AllowConstructorName=*/
2011 getLangOpts().MicrosoftExt && SS.isNotEmpty(),
2012 /*AllowDeductionGuide=*/false, &TemplateKWLoc, Name)) {
2013 LHS = ExprError();
2014 }
2015
2016 if (!LHS.isInvalid())
2017 LHS = Actions.ActOnMemberAccessExpr(getCurScope(), LHS.get(), OpLoc,
2018 OpKind, SS, TemplateKWLoc, Name,
2019 CurParsedObjCImpl ? CurParsedObjCImpl->Dcl
2020 : nullptr);
2021 if (!LHS.isInvalid()) {
2022 if (Tok.is(tok::less))
2023 checkPotentialAngleBracket(LHS);
2024 } else if (OrigLHS && Name.isValid()) {
2025 // Preserve the LHS if the RHS is an invalid member.
2026 LHS = Actions.CreateRecoveryExpr(OrigLHS->getBeginLoc(),
2027 Name.getEndLoc(), {OrigLHS});
2028 }
2029 break;
2030 }
2031 case tok::plusplus: // postfix-expression: postfix-expression '++'
2032 case tok::minusminus: // postfix-expression: postfix-expression '--'
2033 if (!LHS.isInvalid()) {
2034 Expr *Arg = LHS.get();
2035 LHS = Actions.ActOnPostfixUnaryOp(getCurScope(), Tok.getLocation(),
2036 Tok.getKind(), Arg);
2037 if (LHS.isInvalid())
2038 LHS = Actions.CreateRecoveryExpr(Arg->getBeginLoc(),
2039 Tok.getLocation(), Arg);
2040 }
2041 ConsumeToken();
2042 break;
2043 }
2044 }
2045}
2046
2048Parser::ParseExprAfterUnaryExprOrTypeTrait(const Token &OpTok,
2049 bool &isCastExpr,
2050 ParsedType &CastTy,
2051 SourceRange &CastRange) {
2052
2053 assert(OpTok.isOneOf(tok::kw_typeof, tok::kw_typeof_unqual, tok::kw_sizeof,
2054 tok::kw___datasizeof, tok::kw___alignof, tok::kw_alignof,
2055 tok::kw__Alignof, tok::kw_vec_step,
2056 tok::kw___builtin_omp_required_simd_align,
2057 tok::kw___builtin_vectorelements, tok::kw__Countof) &&
2058 "Not a typeof/sizeof/alignof/vec_step expression!");
2059
2061
2062 // If the operand doesn't start with an '(', it must be an expression.
2063 if (Tok.isNot(tok::l_paren)) {
2064 // If construct allows a form without parenthesis, user may forget to put
2065 // pathenthesis around type name.
2066 if (OpTok.isOneOf(tok::kw_sizeof, tok::kw___datasizeof, tok::kw___alignof,
2067 tok::kw_alignof, tok::kw__Alignof)) {
2068 if (isTypeIdUnambiguously()) {
2069 DeclSpec DS(AttrFactory);
2070 ParseSpecifierQualifierList(DS);
2071 Declarator DeclaratorInfo(DS, ParsedAttributesView::none(),
2073 ParseDeclarator(DeclaratorInfo);
2074
2075 SourceLocation LParenLoc = PP.getLocForEndOfToken(OpTok.getLocation());
2076 SourceLocation RParenLoc = PP.getLocForEndOfToken(PrevTokLocation);
2077 if (LParenLoc.isInvalid() || RParenLoc.isInvalid()) {
2078 Diag(OpTok.getLocation(),
2079 diag::err_expected_parentheses_around_typename)
2080 << OpTok.getName();
2081 } else {
2082 Diag(LParenLoc, diag::err_expected_parentheses_around_typename)
2083 << OpTok.getName() << FixItHint::CreateInsertion(LParenLoc, "(")
2084 << FixItHint::CreateInsertion(RParenLoc, ")");
2085 }
2086 isCastExpr = true;
2087 return ExprEmpty();
2088 }
2089 }
2090
2091 isCastExpr = false;
2092 if (OpTok.isOneOf(tok::kw_typeof, tok::kw_typeof_unqual) &&
2094 Diag(Tok, diag::err_expected_after) << OpTok.getIdentifierInfo()
2095 << tok::l_paren;
2096 return ExprError();
2097 }
2098
2099 // If we're parsing a chain that consists of keywords that could be
2100 // followed by a non-parenthesized expression, BalancedDelimiterTracker
2101 // is not going to help when the nesting is too deep. In this corner case
2102 // we continue to parse with sufficient stack space to avoid crashing.
2103 if (OpTok.isOneOf(tok::kw_sizeof, tok::kw___datasizeof, tok::kw___alignof,
2104 tok::kw_alignof, tok::kw__Alignof, tok::kw__Countof) &&
2105 Tok.isOneOf(tok::kw_sizeof, tok::kw___datasizeof, tok::kw___alignof,
2106 tok::kw_alignof, tok::kw__Alignof, tok::kw__Countof))
2107 Actions.runWithSufficientStackSpace(Tok.getLocation(), [&] {
2108 Operand = ParseCastExpression(CastParseKind::UnaryExprOnly);
2109 });
2110 else
2111 Operand = ParseCastExpression(CastParseKind::UnaryExprOnly);
2112 } else {
2113 // If it starts with a '(', we know that it is either a parenthesized
2114 // type-name, or it is a unary-expression that starts with a compound
2115 // literal, or starts with a primary-expression that is a parenthesized
2116 // expression. Most unary operators have an expression form without parens
2117 // as part of the grammar for the operator, and a type form with the parens
2118 // as part of the grammar for the operator. However, typeof and
2119 // typeof_unqual require parens for both forms. This means that we *know*
2120 // that the open and close parens cannot be part of a cast expression,
2121 // which means we definitely are not parsing a compound literal expression.
2122 // This disambiguates a case like enum E : typeof(int) { }; where we've
2123 // parsed typeof and need to handle the (int){} tokens properly despite
2124 // them looking like a compound literal, as in sizeof (int){}; where the
2125 // parens could be part of a parenthesized type name or for a cast
2126 // expression of some kind.
2127 bool ParenKnownToBeNonCast =
2128 OpTok.isOneOf(tok::kw_typeof, tok::kw_typeof_unqual);
2130 SourceLocation LParenLoc = Tok.getLocation(), RParenLoc;
2131
2132 Operand = ParseParenExpression(
2133 ExprType, /*StopIfCastExr=*/true,
2134 ParenKnownToBeNonCast ? ParenExprKind::PartOfOperator
2136 TypoCorrectionTypeBehavior::AllowBoth, CastTy, RParenLoc);
2137 CastRange = SourceRange(LParenLoc, RParenLoc);
2138
2139 // If ParseParenExpression parsed a '(typename)' sequence only, then this is
2140 // a type.
2141 if (ExprType == ParenParseOption::CastExpr) {
2142 isCastExpr = true;
2143 return ExprEmpty();
2144 }
2145
2146 if (getLangOpts().CPlusPlus ||
2147 !OpTok.isOneOf(tok::kw_typeof, tok::kw_typeof_unqual)) {
2148 // GNU typeof in C requires the expression to be parenthesized. Not so for
2149 // sizeof/alignof or in C++. Therefore, the parenthesized expression is
2150 // the start of a unary-expression, but doesn't include any postfix
2151 // pieces. Parse these now if present.
2152 if (!Operand.isInvalid())
2153 Operand = ParsePostfixExpressionSuffix(Operand.get());
2154 }
2155 }
2156
2157 // If we get here, the operand to the typeof/sizeof/alignof was an expression.
2158 isCastExpr = false;
2159 return Operand;
2160}
2161
2162ExprResult Parser::ParseSYCLUniqueStableNameExpression() {
2163 assert(Tok.is(tok::kw___builtin_sycl_unique_stable_name) &&
2164 "Not __builtin_sycl_unique_stable_name");
2165
2166 SourceLocation OpLoc = ConsumeToken();
2167 BalancedDelimiterTracker T(*this, tok::l_paren);
2168
2169 // __builtin_sycl_unique_stable_name expressions are always parenthesized.
2170 if (T.expectAndConsume(diag::err_expected_lparen_after,
2171 "__builtin_sycl_unique_stable_name"))
2172 return ExprError();
2173
2175
2176 if (Ty.isInvalid()) {
2177 T.skipToEnd();
2178 return ExprError();
2179 }
2180
2181 if (T.consumeClose())
2182 return ExprError();
2183
2184 return Actions.SYCL().ActOnUniqueStableNameExpr(
2185 OpLoc, T.getOpenLocation(), T.getCloseLocation(), Ty.get());
2186}
2187
2188ExprResult Parser::ParseUnaryExprOrTypeTraitExpression() {
2189 assert(Tok.isOneOf(tok::kw_sizeof, tok::kw___datasizeof, tok::kw___alignof,
2190 tok::kw_alignof, tok::kw__Alignof, tok::kw_vec_step,
2191 tok::kw___builtin_omp_required_simd_align,
2192 tok::kw___builtin_vectorelements, tok::kw__Countof) &&
2193 "Not a sizeof/alignof/vec_step expression!");
2194 Token OpTok = Tok;
2195 ConsumeToken();
2196
2197 // [C++11] 'sizeof' '...' '(' identifier ')'
2198 if (Tok.is(tok::ellipsis) && OpTok.is(tok::kw_sizeof)) {
2199 SourceLocation EllipsisLoc = ConsumeToken();
2200 SourceLocation LParenLoc, RParenLoc;
2201 IdentifierInfo *Name = nullptr;
2202 SourceLocation NameLoc;
2203 if (Tok.is(tok::l_paren)) {
2204 BalancedDelimiterTracker T(*this, tok::l_paren);
2205 T.consumeOpen();
2206 LParenLoc = T.getOpenLocation();
2207 if (Tok.is(tok::identifier)) {
2208 Name = Tok.getIdentifierInfo();
2209 NameLoc = ConsumeToken();
2210 T.consumeClose();
2211 RParenLoc = T.getCloseLocation();
2212 if (RParenLoc.isInvalid())
2213 RParenLoc = PP.getLocForEndOfToken(NameLoc);
2214 } else {
2215 Diag(Tok, diag::err_expected_parameter_pack);
2216 SkipUntil(tok::r_paren, StopAtSemi);
2217 }
2218 } else if (Tok.is(tok::identifier)) {
2219 Name = Tok.getIdentifierInfo();
2220 NameLoc = ConsumeToken();
2221 LParenLoc = PP.getLocForEndOfToken(EllipsisLoc);
2222 RParenLoc = PP.getLocForEndOfToken(NameLoc);
2223 Diag(LParenLoc, diag::err_paren_sizeof_parameter_pack)
2224 << Name
2225 << FixItHint::CreateInsertion(LParenLoc, "(")
2226 << FixItHint::CreateInsertion(RParenLoc, ")");
2227 } else {
2228 Diag(Tok, diag::err_sizeof_parameter_pack);
2229 }
2230
2231 if (!Name)
2232 return ExprError();
2233
2237
2239 OpTok.getLocation(),
2240 *Name, NameLoc,
2241 RParenLoc);
2242 }
2243
2244 if (getLangOpts().CPlusPlus &&
2245 OpTok.isOneOf(tok::kw_alignof, tok::kw__Alignof))
2246 Diag(OpTok, diag::warn_cxx98_compat_alignof);
2247 else if (getLangOpts().C23 && OpTok.is(tok::kw_alignof))
2248 Diag(OpTok, diag::warn_c23_compat_keyword) << OpTok.getName();
2249 else if (getLangOpts().C2y && OpTok.is(tok::kw__Countof))
2250 Diag(OpTok, diag::warn_c2y_compat_keyword) << OpTok.getName();
2251
2255
2256 bool isCastExpr;
2257 ParsedType CastTy;
2258 SourceRange CastRange;
2259 ExprResult Operand = ParseExprAfterUnaryExprOrTypeTrait(OpTok,
2260 isCastExpr,
2261 CastTy,
2262 CastRange);
2263
2264 UnaryExprOrTypeTrait ExprKind = UETT_SizeOf;
2265 switch (OpTok.getKind()) {
2266 case tok::kw_alignof:
2267 case tok::kw__Alignof:
2268 ExprKind = UETT_AlignOf;
2269 break;
2270 case tok::kw___alignof:
2271 ExprKind = UETT_PreferredAlignOf;
2272 break;
2273 case tok::kw_vec_step:
2274 ExprKind = UETT_VecStep;
2275 break;
2276 case tok::kw___builtin_omp_required_simd_align:
2277 ExprKind = UETT_OpenMPRequiredSimdAlign;
2278 break;
2279 case tok::kw___datasizeof:
2280 ExprKind = UETT_DataSizeOf;
2281 break;
2282 case tok::kw___builtin_vectorelements:
2283 ExprKind = UETT_VectorElements;
2284 break;
2285 case tok::kw__Countof:
2286 ExprKind = UETT_CountOf;
2287 assert(!getLangOpts().CPlusPlus && "_Countof in C++ mode?");
2288 if (!getLangOpts().C2y)
2289 Diag(OpTok, diag::ext_c2y_feature) << OpTok.getName();
2290 break;
2291 default:
2292 break;
2293 }
2294
2295 if (isCastExpr)
2296 return Actions.ActOnUnaryExprOrTypeTraitExpr(OpTok.getLocation(),
2297 ExprKind,
2298 /*IsType=*/true,
2299 CastTy.getAsOpaquePtr(),
2300 CastRange);
2301
2302 if (OpTok.isOneOf(tok::kw_alignof, tok::kw__Alignof))
2303 Diag(OpTok, diag::ext_alignof_expr) << OpTok.getIdentifierInfo();
2304
2305 // If we get here, the operand to the sizeof/alignof was an expression.
2306 if (!Operand.isInvalid())
2308 ExprKind,
2309 /*IsType=*/false,
2310 Operand.get(),
2311 CastRange);
2312 return Operand;
2313}
2314
2315ExprResult Parser::ParseBuiltinPrimaryExpression() {
2316 ExprResult Res;
2317 const IdentifierInfo *BuiltinII = Tok.getIdentifierInfo();
2318
2319 tok::TokenKind T = Tok.getKind();
2320 SourceLocation StartLoc = ConsumeToken(); // Eat the builtin identifier.
2321
2322 // All of these start with an open paren.
2323 if (Tok.isNot(tok::l_paren))
2324 return ExprError(Diag(Tok, diag::err_expected_after) << BuiltinII
2325 << tok::l_paren);
2326
2327 BalancedDelimiterTracker PT(*this, tok::l_paren);
2328 PT.consumeOpen();
2329
2330 // TODO: Build AST.
2331
2332 switch (T) {
2333 default: llvm_unreachable("Not a builtin primary expression!");
2334 case tok::kw___builtin_va_arg: {
2336
2337 if (ExpectAndConsume(tok::comma)) {
2338 SkipUntil(tok::r_paren, StopAtSemi);
2339 Expr = ExprError();
2340 }
2341
2343
2344 if (Tok.isNot(tok::r_paren)) {
2345 Diag(Tok, diag::err_expected) << tok::r_paren;
2346 Expr = ExprError();
2347 }
2348
2349 if (Expr.isInvalid() || Ty.isInvalid())
2350 Res = ExprError();
2351 else
2352 Res = Actions.ActOnVAArg(StartLoc, Expr.get(), Ty.get(), ConsumeParen());
2353 break;
2354 }
2355 case tok::kw___builtin_offsetof: {
2357 auto OOK = OffsetOfKind::Builtin;
2358 if (Tok.getLocation().isMacroID()) {
2359 StringRef MacroName = Lexer::getImmediateMacroNameForDiagnostics(
2361 if (MacroName == "offsetof")
2362 OOK = OffsetOfKind::Macro;
2363 }
2364 TypeResult Ty;
2365 {
2366 OffsetOfStateRAIIObject InOffsetof(*this, OOK);
2367 Ty = ParseTypeName();
2368 if (Ty.isInvalid()) {
2369 SkipUntil(tok::r_paren, StopAtSemi);
2370 return ExprError();
2371 }
2372 }
2373
2374 if (ExpectAndConsume(tok::comma)) {
2375 SkipUntil(tok::r_paren, StopAtSemi);
2376 return ExprError();
2377 }
2378
2379 // We must have at least one identifier here.
2380 if (Tok.isNot(tok::identifier)) {
2381 Diag(Tok, diag::err_expected) << tok::identifier;
2382 SkipUntil(tok::r_paren, StopAtSemi);
2383 return ExprError();
2384 }
2385
2386 // Keep track of the various subcomponents we see.
2388
2389 Comps.push_back(Sema::OffsetOfComponent());
2390 Comps.back().isBrackets = false;
2391 Comps.back().U.IdentInfo = Tok.getIdentifierInfo();
2392 Comps.back().LocStart = Comps.back().LocEnd = ConsumeToken();
2393
2394 // FIXME: This loop leaks the index expressions on error.
2395 while (true) {
2396 if (Tok.is(tok::period)) {
2397 // offsetof-member-designator: offsetof-member-designator '.' identifier
2398 Comps.push_back(Sema::OffsetOfComponent());
2399 Comps.back().isBrackets = false;
2400 Comps.back().LocStart = ConsumeToken();
2401
2402 if (Tok.isNot(tok::identifier)) {
2403 Diag(Tok, diag::err_expected) << tok::identifier;
2404 SkipUntil(tok::r_paren, StopAtSemi);
2405 return ExprError();
2406 }
2407 Comps.back().U.IdentInfo = Tok.getIdentifierInfo();
2408 Comps.back().LocEnd = ConsumeToken();
2409 } else if (Tok.is(tok::l_square)) {
2410 if (CheckProhibitedCXX11Attribute())
2411 return ExprError();
2412
2413 // offsetof-member-designator: offsetof-member-design '[' expression ']'
2414 Comps.push_back(Sema::OffsetOfComponent());
2415 Comps.back().isBrackets = true;
2416 BalancedDelimiterTracker ST(*this, tok::l_square);
2417 ST.consumeOpen();
2418 Comps.back().LocStart = ST.getOpenLocation();
2419 Res = ParseExpression();
2420 if (Res.isInvalid()) {
2421 SkipUntil(tok::r_paren, StopAtSemi);
2422 return Res;
2423 }
2424 Comps.back().U.E = Res.get();
2425
2426 ST.consumeClose();
2427 Comps.back().LocEnd = ST.getCloseLocation();
2428 } else {
2429 if (Tok.isNot(tok::r_paren)) {
2430 PT.consumeClose();
2431 Res = ExprError();
2432 } else if (Ty.isInvalid()) {
2433 Res = ExprError();
2434 } else {
2435 PT.consumeClose();
2436 Res = Actions.ActOnBuiltinOffsetOf(getCurScope(), StartLoc, TypeLoc,
2437 Ty.get(), Comps,
2438 PT.getCloseLocation());
2439 }
2440 break;
2441 }
2442 }
2443 break;
2444 }
2445 case tok::kw___builtin_choose_expr: {
2447 if (Cond.isInvalid()) {
2448 SkipUntil(tok::r_paren, StopAtSemi);
2449 return Cond;
2450 }
2451 if (ExpectAndConsume(tok::comma)) {
2452 SkipUntil(tok::r_paren, StopAtSemi);
2453 return ExprError();
2454 }
2455
2457 if (Expr1.isInvalid()) {
2458 SkipUntil(tok::r_paren, StopAtSemi);
2459 return Expr1;
2460 }
2461 if (ExpectAndConsume(tok::comma)) {
2462 SkipUntil(tok::r_paren, StopAtSemi);
2463 return ExprError();
2464 }
2465
2467 if (Expr2.isInvalid()) {
2468 SkipUntil(tok::r_paren, StopAtSemi);
2469 return Expr2;
2470 }
2471 if (Tok.isNot(tok::r_paren)) {
2472 Diag(Tok, diag::err_expected) << tok::r_paren;
2473 return ExprError();
2474 }
2475 Res = Actions.ActOnChooseExpr(StartLoc, Cond.get(), Expr1.get(),
2476 Expr2.get(), ConsumeParen());
2477 break;
2478 }
2479 case tok::kw___builtin_astype: {
2480 // The first argument is an expression to be converted, followed by a comma.
2482 if (Expr.isInvalid()) {
2483 SkipUntil(tok::r_paren, StopAtSemi);
2484 return ExprError();
2485 }
2486
2487 if (ExpectAndConsume(tok::comma)) {
2488 SkipUntil(tok::r_paren, StopAtSemi);
2489 return ExprError();
2490 }
2491
2492 // Second argument is the type to bitcast to.
2493 TypeResult DestTy = ParseTypeName();
2494 if (DestTy.isInvalid())
2495 return ExprError();
2496
2497 // Attempt to consume the r-paren.
2498 if (Tok.isNot(tok::r_paren)) {
2499 Diag(Tok, diag::err_expected) << tok::r_paren;
2500 SkipUntil(tok::r_paren, StopAtSemi);
2501 return ExprError();
2502 }
2503
2504 Res = Actions.ActOnAsTypeExpr(Expr.get(), DestTy.get(), StartLoc,
2505 ConsumeParen());
2506 break;
2507 }
2508 case tok::kw___builtin_convertvector: {
2509 // The first argument is an expression to be converted, followed by a comma.
2511 if (Expr.isInvalid()) {
2512 SkipUntil(tok::r_paren, StopAtSemi);
2513 return ExprError();
2514 }
2515
2516 if (ExpectAndConsume(tok::comma)) {
2517 SkipUntil(tok::r_paren, StopAtSemi);
2518 return ExprError();
2519 }
2520
2521 // Second argument is the type to bitcast to.
2522 TypeResult DestTy = ParseTypeName();
2523 if (DestTy.isInvalid())
2524 return ExprError();
2525
2526 // Attempt to consume the r-paren.
2527 if (Tok.isNot(tok::r_paren)) {
2528 Diag(Tok, diag::err_expected) << tok::r_paren;
2529 SkipUntil(tok::r_paren, StopAtSemi);
2530 return ExprError();
2531 }
2532
2533 Res = Actions.ActOnConvertVectorExpr(Expr.get(), DestTy.get(), StartLoc,
2534 ConsumeParen());
2535 break;
2536 }
2537 case tok::kw___builtin_COLUMN:
2538 case tok::kw___builtin_FILE:
2539 case tok::kw___builtin_FILE_NAME:
2540 case tok::kw___builtin_FUNCTION:
2541 case tok::kw___builtin_FUNCSIG:
2542 case tok::kw___builtin_LINE:
2543 case tok::kw___builtin_source_location: {
2544 // Attempt to consume the r-paren.
2545 if (Tok.isNot(tok::r_paren)) {
2546 Diag(Tok, diag::err_expected) << tok::r_paren;
2547 SkipUntil(tok::r_paren, StopAtSemi);
2548 return ExprError();
2549 }
2550 SourceLocIdentKind Kind = [&] {
2551 switch (T) {
2552 case tok::kw___builtin_FILE:
2554 case tok::kw___builtin_FILE_NAME:
2556 case tok::kw___builtin_FUNCTION:
2558 case tok::kw___builtin_FUNCSIG:
2560 case tok::kw___builtin_LINE:
2562 case tok::kw___builtin_COLUMN:
2564 case tok::kw___builtin_source_location:
2566 default:
2567 llvm_unreachable("invalid keyword");
2568 }
2569 }();
2570 Res = Actions.ActOnSourceLocExpr(Kind, StartLoc, ConsumeParen());
2571 break;
2572 }
2573 }
2574
2575 if (Res.isInvalid())
2576 return ExprError();
2577
2578 // These can be followed by postfix-expr pieces because they are
2579 // primary-expressions.
2580 return ParsePostfixExpressionSuffix(Res.get());
2581}
2582
2583bool Parser::tryParseOpenMPArrayShapingCastPart() {
2584 assert(Tok.is(tok::l_square) && "Expected open bracket");
2585 bool ErrorFound = true;
2586 TentativeParsingAction TPA(*this);
2587 do {
2588 if (Tok.isNot(tok::l_square))
2589 break;
2590 // Consume '['
2591 ConsumeBracket();
2592 // Skip inner expression.
2593 while (!SkipUntil(tok::r_square, tok::annot_pragma_openmp_end,
2595 ;
2596 if (Tok.isNot(tok::r_square))
2597 break;
2598 // Consume ']'
2599 ConsumeBracket();
2600 // Found ')' - done.
2601 if (Tok.is(tok::r_paren)) {
2602 ErrorFound = false;
2603 break;
2604 }
2605 } while (Tok.isNot(tok::annot_pragma_openmp_end));
2606 TPA.Revert();
2607 return !ErrorFound;
2608}
2609
2611Parser::ParseParenExpression(ParenParseOption &ExprType, bool StopIfCastExpr,
2612 ParenExprKind ParenBehavior,
2613 TypoCorrectionTypeBehavior CorrectionBehavior,
2614 ParsedType &CastTy, SourceLocation &RParenLoc) {
2615 assert(Tok.is(tok::l_paren) && "Not a paren expr!");
2616 ColonProtectionRAIIObject ColonProtection(*this, false);
2617 BalancedDelimiterTracker T(*this, tok::l_paren);
2618 if (T.consumeOpen())
2619 return ExprError();
2620 SourceLocation OpenLoc = T.getOpenLocation();
2621
2622 PreferredType.enterParenExpr(Tok.getLocation(), OpenLoc);
2623
2624 ExprResult Result(true);
2625 bool isAmbiguousTypeId;
2626 CastTy = nullptr;
2627
2628 if (Tok.is(tok::code_completion)) {
2629 cutOffParsing();
2631 getCurScope(), PreferredType.get(Tok.getLocation()),
2632 /*IsParenthesized=*/ExprType >= ParenParseOption::CompoundLiteral);
2633 return ExprError();
2634 }
2635
2636 // Diagnose use of bridge casts in non-arc mode.
2637 bool BridgeCast = (getLangOpts().ObjC &&
2638 Tok.isOneOf(tok::kw___bridge,
2639 tok::kw___bridge_transfer,
2640 tok::kw___bridge_retained,
2641 tok::kw___bridge_retain));
2642 if (BridgeCast && !getLangOpts().ObjCAutoRefCount) {
2643 if (!TryConsumeToken(tok::kw___bridge)) {
2644 StringRef BridgeCastName = Tok.getName();
2645 SourceLocation BridgeKeywordLoc = ConsumeToken();
2646 if (!PP.getSourceManager().isInSystemHeader(BridgeKeywordLoc))
2647 Diag(BridgeKeywordLoc, diag::warn_arc_bridge_cast_nonarc)
2648 << BridgeCastName
2649 << FixItHint::CreateReplacement(BridgeKeywordLoc, "");
2650 }
2651 BridgeCast = false;
2652 }
2653
2654 // None of these cases should fall through with an invalid Result
2655 // unless they've already reported an error.
2656 if (ExprType >= ParenParseOption::CompoundStmt && Tok.is(tok::l_brace)) {
2657 Diag(Tok, OpenLoc.isMacroID() ? diag::ext_gnu_statement_expr_macro
2658 : diag::ext_gnu_statement_expr);
2659
2660 checkCompoundToken(OpenLoc, tok::l_paren, CompoundToken::StmtExprBegin);
2661
2662 if (!getCurScope()->getFnParent() && !getCurScope()->getBlockParent()) {
2663 Result = ExprError(Diag(OpenLoc, diag::err_stmtexpr_file_scope));
2664 } else {
2665 // Find the nearest non-record decl context. Variables declared in a
2666 // statement expression behave as if they were declared in the enclosing
2667 // function, block, or other code construct.
2668 DeclContext *CodeDC = Actions.CurContext;
2669 while (CodeDC->isRecord() || isa<EnumDecl>(CodeDC)) {
2670 CodeDC = CodeDC->getParent();
2671 assert(CodeDC && !CodeDC->isFileContext() &&
2672 "statement expr not in code context");
2673 }
2674 Sema::ContextRAII SavedContext(Actions, CodeDC, /*NewThisContext=*/false);
2675
2676 Actions.ActOnStartStmtExpr();
2677
2678 StmtResult Stmt(ParseCompoundStatement(true));
2680
2681 // If the substmt parsed correctly, build the AST node.
2682 if (!Stmt.isInvalid()) {
2683 Result = Actions.ActOnStmtExpr(getCurScope(), OpenLoc, Stmt.get(),
2684 Tok.getLocation());
2685 } else {
2686 Actions.ActOnStmtExprError();
2687 }
2688 }
2689 } else if (ExprType >= ParenParseOption::CompoundLiteral && BridgeCast) {
2690 tok::TokenKind tokenKind = Tok.getKind();
2691 SourceLocation BridgeKeywordLoc = ConsumeToken();
2692
2693 // Parse an Objective-C ARC ownership cast expression.
2695 if (tokenKind == tok::kw___bridge)
2696 Kind = OBC_Bridge;
2697 else if (tokenKind == tok::kw___bridge_transfer)
2699 else if (tokenKind == tok::kw___bridge_retained)
2701 else {
2702 // As a hopefully temporary workaround, allow __bridge_retain as
2703 // a synonym for __bridge_retained, but only in system headers.
2704 assert(tokenKind == tok::kw___bridge_retain);
2706 if (!PP.getSourceManager().isInSystemHeader(BridgeKeywordLoc))
2707 Diag(BridgeKeywordLoc, diag::err_arc_bridge_retain)
2708 << FixItHint::CreateReplacement(BridgeKeywordLoc,
2709 "__bridge_retained");
2710 }
2711
2713 T.consumeClose();
2714 ColonProtection.restore();
2715 RParenLoc = T.getCloseLocation();
2716
2717 PreferredType.enterTypeCast(Tok.getLocation(), Ty.get().get());
2718 ExprResult SubExpr = ParseCastExpression(CastParseKind::AnyCastExpr);
2719
2720 if (Ty.isInvalid() || SubExpr.isInvalid())
2721 return ExprError();
2722
2723 return Actions.ObjC().ActOnObjCBridgedCast(getCurScope(), OpenLoc, Kind,
2724 BridgeKeywordLoc, Ty.get(),
2725 RParenLoc, SubExpr.get());
2726 } else if (ExprType >= ParenParseOption::CompoundLiteral &&
2727 isTypeIdInParens(isAmbiguousTypeId)) {
2728
2729 // Otherwise, this is a compound literal expression or cast expression.
2730
2731 // In C++, if the type-id is ambiguous we disambiguate based on context.
2732 // If stopIfCastExpr is true the context is a typeof/sizeof/alignof
2733 // in which case we should treat it as type-id.
2734 // if stopIfCastExpr is false, we need to determine the context past the
2735 // parens, so we defer to ParseCXXAmbiguousParenExpression for that.
2736 if (isAmbiguousTypeId && !StopIfCastExpr) {
2737 ExprResult res = ParseCXXAmbiguousParenExpression(ExprType, CastTy, T,
2738 ColonProtection);
2739 RParenLoc = T.getCloseLocation();
2740 return res;
2741 }
2742
2743 // Parse the type declarator.
2744 DeclSpec DS(AttrFactory);
2745 ParseSpecifierQualifierList(DS);
2746 Declarator DeclaratorInfo(DS, ParsedAttributesView::none(),
2748 ParseDeclarator(DeclaratorInfo);
2749
2750 // If our type is followed by an identifier and either ':' or ']', then
2751 // this is probably an Objective-C message send where the leading '[' is
2752 // missing. Recover as if that were the case.
2753 if (!DeclaratorInfo.isInvalidType() && Tok.is(tok::identifier) &&
2754 !InMessageExpression && getLangOpts().ObjC &&
2755 (NextToken().is(tok::colon) || NextToken().is(tok::r_square))) {
2756 TypeResult Ty;
2757 {
2758 InMessageExpressionRAIIObject InMessage(*this, false);
2759 Ty = Actions.ActOnTypeName(DeclaratorInfo);
2760 }
2761 Result = ParseObjCMessageExpressionBody(SourceLocation(),
2763 Ty.get(), nullptr);
2764 } else {
2765 // Match the ')'.
2766 T.consumeClose();
2767 ColonProtection.restore();
2768 RParenLoc = T.getCloseLocation();
2769 if (ParenBehavior == ParenExprKind::Unknown && Tok.is(tok::l_brace)) {
2771 TypeResult Ty;
2772 {
2773 InMessageExpressionRAIIObject InMessage(*this, false);
2774 Ty = Actions.ActOnTypeName(DeclaratorInfo);
2775 }
2776 return ParseCompoundLiteralExpression(Ty.get(), OpenLoc, RParenLoc);
2777 }
2778
2779 if (ParenBehavior == ParenExprKind::Unknown && Tok.is(tok::l_paren)) {
2780 // This could be OpenCL vector Literals
2781 if (getLangOpts().OpenCL)
2782 {
2783 TypeResult Ty;
2784 {
2785 InMessageExpressionRAIIObject InMessage(*this, false);
2786 Ty = Actions.ActOnTypeName(DeclaratorInfo);
2787 }
2788 if(Ty.isInvalid())
2789 {
2790 return ExprError();
2791 }
2792 QualType QT = Ty.get().get().getCanonicalType();
2793 if (QT->isVectorType())
2794 {
2795 // We parsed '(' vector-type-name ')' followed by '('
2796
2797 // Parse the cast-expression that follows it next.
2798 // isVectorLiteral = true will make sure we don't parse any
2799 // Postfix expression yet
2800 Result = ParseCastExpression(
2801 /*isUnaryExpression=*/CastParseKind::AnyCastExpr,
2802 /*isAddressOfOperand=*/false,
2804 /*isVectorLiteral=*/true);
2805
2806 if (!Result.isInvalid()) {
2807 Result = Actions.ActOnCastExpr(getCurScope(), OpenLoc,
2808 DeclaratorInfo, CastTy,
2809 RParenLoc, Result.get());
2810 }
2811
2812 // After we performed the cast we can check for postfix-expr pieces.
2813 if (!Result.isInvalid()) {
2814 Result = ParsePostfixExpressionSuffix(Result);
2815 }
2816
2817 return Result;
2818 }
2819 }
2820 }
2821
2822 if (ExprType == ParenParseOption::CastExpr) {
2823 // We parsed '(' type-name ')' and the thing after it wasn't a '{'.
2824
2825 if (DeclaratorInfo.isInvalidType())
2826 return ExprError();
2827
2828 // Note that this doesn't parse the subsequent cast-expression, it just
2829 // returns the parsed type to the callee.
2830 if (StopIfCastExpr) {
2831 TypeResult Ty;
2832 {
2833 InMessageExpressionRAIIObject InMessage(*this, false);
2834 Ty = Actions.ActOnTypeName(DeclaratorInfo);
2835 }
2836 CastTy = Ty.get();
2837 return ExprResult();
2838 }
2839
2840 // Reject the cast of super idiom in ObjC.
2841 if (Tok.is(tok::identifier) && getLangOpts().ObjC &&
2842 Tok.getIdentifierInfo() == Ident_super &&
2843 getCurScope()->isInObjcMethodScope() &&
2844 GetLookAheadToken(1).isNot(tok::period)) {
2845 Diag(Tok.getLocation(), diag::err_illegal_super_cast)
2846 << SourceRange(OpenLoc, RParenLoc);
2847 return ExprError();
2848 }
2849
2850 PreferredType.enterTypeCast(Tok.getLocation(), CastTy.get());
2851 // Parse the cast-expression that follows it next.
2852 // TODO: For cast expression with CastTy.
2853 Result = ParseCastExpression(
2854 /*isUnaryExpression=*/CastParseKind::AnyCastExpr,
2855 /*isAddressOfOperand=*/false,
2857 if (!Result.isInvalid()) {
2858 Result = Actions.ActOnCastExpr(getCurScope(), OpenLoc,
2859 DeclaratorInfo, CastTy,
2860 RParenLoc, Result.get());
2861 }
2862 return Result;
2863 }
2864
2865 Diag(Tok, diag::err_expected_lbrace_in_compound_literal);
2866 return ExprError();
2867 }
2868 } else if (ExprType >= ParenParseOption::FoldExpr && Tok.is(tok::ellipsis) &&
2869 isFoldOperator(NextToken().getKind())) {
2870 ExprType = ParenParseOption::FoldExpr;
2871 return ParseFoldExpression(ExprResult(), T);
2872 } else if (CorrectionBehavior == TypoCorrectionTypeBehavior::AllowTypes) {
2873 // FIXME: This should not be predicated on typo correction behavior.
2874 // Parse the expression-list.
2875 InMessageExpressionRAIIObject InMessage(*this, false);
2876 ExprVector ArgExprs;
2877
2878 if (!ParseSimpleExpressionList(ArgExprs)) {
2879 // FIXME: If we ever support comma expressions as operands to
2880 // fold-expressions, we'll need to allow multiple ArgExprs here.
2881 if (ExprType >= ParenParseOption::FoldExpr && ArgExprs.size() == 1 &&
2882 isFoldOperator(Tok.getKind()) && NextToken().is(tok::ellipsis)) {
2883 ExprType = ParenParseOption::FoldExpr;
2884 return ParseFoldExpression(ArgExprs[0], T);
2885 }
2886
2888 Result = Actions.ActOnParenListExpr(OpenLoc, Tok.getLocation(),
2889 ArgExprs);
2890 }
2891 } else if (getLangOpts().OpenMP >= 50 && OpenMPDirectiveParsing &&
2892 ExprType == ParenParseOption::CastExpr && Tok.is(tok::l_square) &&
2893 tryParseOpenMPArrayShapingCastPart()) {
2894 bool ErrorFound = false;
2895 SmallVector<Expr *, 4> OMPDimensions;
2896 SmallVector<SourceRange, 4> OMPBracketsRanges;
2897 do {
2898 BalancedDelimiterTracker TS(*this, tok::l_square);
2899 TS.consumeOpen();
2900 ExprResult NumElements = ParseExpression();
2901 if (!NumElements.isUsable()) {
2902 ErrorFound = true;
2903 while (!SkipUntil(tok::r_square, tok::r_paren,
2905 ;
2906 }
2907 TS.consumeClose();
2908 OMPDimensions.push_back(NumElements.get());
2909 OMPBracketsRanges.push_back(TS.getRange());
2910 } while (Tok.isNot(tok::r_paren));
2911 // Match the ')'.
2912 T.consumeClose();
2913 RParenLoc = T.getCloseLocation();
2915 if (ErrorFound) {
2916 Result = ExprError();
2917 } else if (!Result.isInvalid()) {
2919 Result.get(), OpenLoc, RParenLoc, OMPDimensions, OMPBracketsRanges);
2920 }
2921 return Result;
2922 } else {
2923 InMessageExpressionRAIIObject InMessage(*this, false);
2924
2926 if (ExprType >= ParenParseOption::FoldExpr &&
2927 isFoldOperator(Tok.getKind()) && NextToken().is(tok::ellipsis)) {
2928 ExprType = ParenParseOption::FoldExpr;
2929 return ParseFoldExpression(Result, T);
2930 }
2932
2933 // Don't build a paren expression unless we actually match a ')'.
2934 if (!Result.isInvalid() && Tok.is(tok::r_paren))
2935 Result =
2936 Actions.ActOnParenExpr(OpenLoc, Tok.getLocation(), Result.get());
2937 }
2938
2939 // Match the ')'.
2940 if (Result.isInvalid()) {
2941 SkipUntil(tok::r_paren, StopAtSemi);
2942 return ExprError();
2943 }
2944
2945 T.consumeClose();
2946 RParenLoc = T.getCloseLocation();
2947 return Result;
2948}
2949
2951Parser::ParseCompoundLiteralExpression(ParsedType Ty,
2952 SourceLocation LParenLoc,
2953 SourceLocation RParenLoc) {
2954 assert(Tok.is(tok::l_brace) && "Not a compound literal!");
2955 if (!getLangOpts().C99) // Compound literals don't exist in C90.
2956 Diag(LParenLoc, diag::ext_c99_compound_literal);
2957 PreferredType.enterTypeCast(Tok.getLocation(), Ty.get());
2958 ExprResult Result = ParseInitializer();
2959 if (!Result.isInvalid() && Ty)
2960 return Actions.ActOnCompoundLiteral(LParenLoc, Ty, RParenLoc, Result.get());
2961 return Result;
2962}
2963
2965 return ParseStringLiteralExpression(AllowUserDefinedLiteral,
2966 /*Unevaluated=*/false);
2967}
2968
2970 return ParseStringLiteralExpression(/*AllowUserDefinedLiteral=*/false,
2971 /*Unevaluated=*/true);
2972}
2973
2974ExprResult Parser::ParseStringLiteralExpression(bool AllowUserDefinedLiteral,
2975 bool Unevaluated) {
2976 assert(tokenIsLikeStringLiteral(Tok, getLangOpts()) &&
2977 "Not a string-literal-like token!");
2978
2979 // String concatenation.
2980 // Note: some keywords like __FUNCTION__ are not considered to be strings
2981 // for concatenation purposes, unless Microsoft extensions are enabled.
2982 SmallVector<Token, 4> StringToks;
2983
2984 do {
2985 StringToks.push_back(Tok);
2987 } while (tokenIsLikeStringLiteral(Tok, getLangOpts()));
2988
2989 if (Unevaluated) {
2990 assert(!AllowUserDefinedLiteral && "UDL are always evaluated");
2991 return Actions.ActOnUnevaluatedStringLiteral(StringToks);
2992 }
2993
2994 // Pass the set of string tokens, ready for concatenation, to the actions.
2995 return Actions.ActOnStringLiteral(StringToks,
2996 AllowUserDefinedLiteral ? getCurScope()
2997 : nullptr);
2998}
2999
3000ExprResult Parser::ParseGenericSelectionExpression() {
3001 assert(Tok.is(tok::kw__Generic) && "_Generic keyword expected");
3002
3003 diagnoseUseOfC11Keyword(Tok);
3004
3005 SourceLocation KeyLoc = ConsumeToken();
3006 BalancedDelimiterTracker T(*this, tok::l_paren);
3007 if (T.expectAndConsume())
3008 return ExprError();
3009
3010 // We either have a controlling expression or we have a controlling type, and
3011 // we need to figure out which it is.
3012 TypeResult ControllingType;
3013 ExprResult ControllingExpr;
3014 if (isTypeIdForGenericSelection()) {
3015 ControllingType = ParseTypeName();
3016 if (ControllingType.isInvalid()) {
3017 SkipUntil(tok::r_paren, StopAtSemi);
3018 return ExprError();
3019 }
3020 const auto *LIT = cast<LocInfoType>(ControllingType.get().get());
3021 SourceLocation Loc = LIT->getTypeSourceInfo()->getTypeLoc().getBeginLoc();
3022 Diag(Loc, getLangOpts().C2y ? diag::warn_c2y_compat_generic_with_type_arg
3023 : diag::ext_c2y_generic_with_type_arg);
3024 } else {
3025 // C11 6.5.1.1p3 "The controlling expression of a generic selection is
3026 // not evaluated."
3029 ControllingExpr = ParseAssignmentExpression();
3030 if (ControllingExpr.isInvalid()) {
3031 SkipUntil(tok::r_paren, StopAtSemi);
3032 return ExprError();
3033 }
3034 }
3035
3036 if (ExpectAndConsume(tok::comma)) {
3037 SkipUntil(tok::r_paren, StopAtSemi);
3038 return ExprError();
3039 }
3040
3041 SourceLocation DefaultLoc;
3043 ExprVector Exprs;
3044 do {
3045 ParsedType Ty;
3046 if (Tok.is(tok::kw_default)) {
3047 // C11 6.5.1.1p2 "A generic selection shall have no more than one default
3048 // generic association."
3049 if (!DefaultLoc.isInvalid()) {
3050 Diag(Tok, diag::err_duplicate_default_assoc);
3051 Diag(DefaultLoc, diag::note_previous_default_assoc);
3052 SkipUntil(tok::r_paren, StopAtSemi);
3053 return ExprError();
3054 }
3055 DefaultLoc = ConsumeToken();
3056 Ty = nullptr;
3057 } else {
3060 if (TR.isInvalid()) {
3061 SkipUntil(tok::r_paren, StopAtSemi);
3062 return ExprError();
3063 }
3064 Ty = TR.get();
3065 }
3066 Types.push_back(Ty);
3067
3068 if (ExpectAndConsume(tok::colon)) {
3069 SkipUntil(tok::r_paren, StopAtSemi);
3070 return ExprError();
3071 }
3072
3073 // FIXME: These expressions should be parsed in a potentially potentially
3074 // evaluated context.
3076 if (ER.isInvalid()) {
3077 SkipUntil(tok::r_paren, StopAtSemi);
3078 return ExprError();
3079 }
3080 Exprs.push_back(ER.get());
3081 } while (TryConsumeToken(tok::comma));
3082
3083 T.consumeClose();
3084 if (T.getCloseLocation().isInvalid())
3085 return ExprError();
3086
3087 void *ExprOrTy = ControllingExpr.isUsable()
3088 ? ControllingExpr.get()
3089 : ControllingType.get().getAsOpaquePtr();
3090
3091 return Actions.ActOnGenericSelectionExpr(
3092 KeyLoc, DefaultLoc, T.getCloseLocation(), ControllingExpr.isUsable(),
3093 ExprOrTy, Types, Exprs);
3094}
3095
3096ExprResult Parser::ParseFoldExpression(ExprResult LHS,
3098 if (LHS.isInvalid()) {
3099 T.skipToEnd();
3100 return true;
3101 }
3102
3103 tok::TokenKind Kind = tok::unknown;
3104 SourceLocation FirstOpLoc;
3105 if (LHS.isUsable()) {
3106 Kind = Tok.getKind();
3107 assert(isFoldOperator(Kind) && "missing fold-operator");
3108 FirstOpLoc = ConsumeToken();
3109 }
3110
3111 assert(Tok.is(tok::ellipsis) && "not a fold-expression");
3112 SourceLocation EllipsisLoc = ConsumeToken();
3113
3114 ExprResult RHS;
3115 if (Tok.isNot(tok::r_paren)) {
3116 if (!isFoldOperator(Tok.getKind()))
3117 return Diag(Tok.getLocation(), diag::err_expected_fold_operator);
3118
3119 if (Kind != tok::unknown && Tok.getKind() != Kind)
3120 Diag(Tok.getLocation(), diag::err_fold_operator_mismatch)
3121 << SourceRange(FirstOpLoc);
3122 Kind = Tok.getKind();
3123 ConsumeToken();
3124
3125 RHS = ParseExpression();
3126 if (RHS.isInvalid()) {
3127 T.skipToEnd();
3128 return true;
3129 }
3130 }
3131
3132 Diag(EllipsisLoc, getLangOpts().CPlusPlus17
3133 ? diag::warn_cxx14_compat_fold_expression
3134 : diag::ext_fold_expression);
3135
3136 T.consumeClose();
3137 return Actions.ActOnCXXFoldExpr(getCurScope(), T.getOpenLocation(), LHS.get(),
3138 Kind, EllipsisLoc, RHS.get(),
3139 T.getCloseLocation());
3140}
3141
3142void Parser::injectEmbedTokens() {
3144 reinterpret_cast<EmbedAnnotationData *>(Tok.getAnnotationValue());
3146 Data->BinaryData.size() * 2 - 1),
3147 Data->BinaryData.size() * 2 - 1);
3148 unsigned I = 0;
3149 for (auto &Byte : Data->BinaryData) {
3150 Toks[I].startToken();
3151 Toks[I].setKind(tok::binary_data);
3152 Toks[I].setLocation(Tok.getLocation());
3153 Toks[I].setLength(1);
3154 Toks[I].setLiteralData(&Byte);
3155 if (I != ((Data->BinaryData.size() - 1) * 2)) {
3156 Toks[I + 1].startToken();
3157 Toks[I + 1].setKind(tok::comma);
3158 Toks[I + 1].setLocation(Tok.getLocation());
3159 }
3160 I += 2;
3161 }
3162 PP.EnterTokenStream(std::move(Toks), /*DisableMacroExpansion=*/true,
3163 /*IsReinject=*/true);
3164 ConsumeAnyToken(/*ConsumeCodeCompletionTok=*/true);
3165}
3166
3167bool Parser::ParseExpressionList(SmallVectorImpl<Expr *> &Exprs,
3168 llvm::function_ref<void()> ExpressionStarts,
3169 bool FailImmediatelyOnInvalidExpr) {
3170 bool SawError = false;
3171 while (true) {
3172 if (ExpressionStarts)
3173 ExpressionStarts();
3174
3176 if (getLangOpts().CPlusPlus11 && Tok.is(tok::l_brace)) {
3177 Diag(Tok, diag::warn_cxx98_compat_generalized_initializer_lists);
3178 Expr = ParseBraceInitializer();
3179 } else
3181
3182 if (Tok.is(tok::ellipsis))
3183 Expr = Actions.ActOnPackExpansion(Expr.get(), ConsumeToken());
3184 else if (Tok.is(tok::code_completion)) {
3185 // There's nothing to suggest in here as we parsed a full expression.
3186 // Instead fail and propagate the error since caller might have something
3187 // the suggest, e.g. signature help in function call. Note that this is
3188 // performed before pushing the \p Expr, so that signature help can report
3189 // current argument correctly.
3190 SawError = true;
3191 cutOffParsing();
3192 break;
3193 }
3194 if (Expr.isInvalid()) {
3195 SawError = true;
3196 if (FailImmediatelyOnInvalidExpr)
3197 break;
3198 SkipUntil(tok::comma, tok::r_paren, StopAtSemi | StopBeforeMatch);
3199 } else {
3200 Exprs.push_back(Expr.get());
3201 }
3202
3203 if (Tok.isNot(tok::comma))
3204 break;
3205 // Move to the next argument, remember where the comma was.
3206 Token Comma = Tok;
3207 ConsumeToken();
3208 checkPotentialAngleBracketDelimiter(Comma);
3209 }
3210 return SawError;
3211}
3212
3213bool Parser::ParseSimpleExpressionList(SmallVectorImpl<Expr *> &Exprs) {
3214 while (true) {
3216 if (Expr.isInvalid())
3217 return true;
3218
3219 Exprs.push_back(Expr.get());
3220
3221 // We might be parsing the LHS of a fold-expression. If we reached the fold
3222 // operator, stop.
3223 if (Tok.isNot(tok::comma) || NextToken().is(tok::ellipsis))
3224 return false;
3225
3226 // Move to the next argument, remember where the comma was.
3227 Token Comma = Tok;
3228 ConsumeToken();
3229 checkPotentialAngleBracketDelimiter(Comma);
3230 }
3231}
3232
3233void Parser::ParseBlockId(SourceLocation CaretLoc) {
3234 if (Tok.is(tok::code_completion)) {
3235 cutOffParsing();
3238 return;
3239 }
3240
3241 // Parse the specifier-qualifier-list piece.
3242 DeclSpec DS(AttrFactory);
3243 ParseSpecifierQualifierList(DS);
3244
3245 // Parse the block-declarator.
3246 Declarator DeclaratorInfo(DS, ParsedAttributesView::none(),
3248 DeclaratorInfo.setFunctionDefinitionKind(FunctionDefinitionKind::Definition);
3249 ParseDeclarator(DeclaratorInfo);
3250
3251 MaybeParseGNUAttributes(DeclaratorInfo);
3252
3253 // Inform sema that we are starting a block.
3254 Actions.ActOnBlockArguments(CaretLoc, DeclaratorInfo, getCurScope());
3255}
3256
3257ExprResult Parser::ParseBlockLiteralExpression() {
3258 assert(Tok.is(tok::caret) && "block literal starts with ^");
3259 SourceLocation CaretLoc = ConsumeToken();
3260
3261 PrettyStackTraceLoc CrashInfo(PP.getSourceManager(), CaretLoc,
3262 "block literal parsing");
3263
3264 // Enter a scope to hold everything within the block. This includes the
3265 // argument decls, decls within the compound expression, etc. This also
3266 // allows determining whether a variable reference inside the block is
3267 // within or outside of the block.
3268 ParseScope BlockScope(this, Scope::BlockScope | Scope::FnScope |
3270
3271 // Inform sema that we are starting a block.
3272 Actions.ActOnBlockStart(CaretLoc, getCurScope());
3273
3274 // Parse the return type if present.
3275 DeclSpec DS(AttrFactory);
3276 Declarator ParamInfo(DS, ParsedAttributesView::none(),
3278 ParamInfo.setFunctionDefinitionKind(FunctionDefinitionKind::Definition);
3279 // FIXME: Since the return type isn't actually parsed, it can't be used to
3280 // fill ParamInfo with an initial valid range, so do it manually.
3281 ParamInfo.SetSourceRange(SourceRange(Tok.getLocation(), Tok.getLocation()));
3282
3283 // If this block has arguments, parse them. There is no ambiguity here with
3284 // the expression case, because the expression case requires a parameter list.
3285 if (Tok.is(tok::l_paren)) {
3286 ParseParenDeclarator(ParamInfo);
3287 // Parse the pieces after the identifier as if we had "int(...)".
3288 // SetIdentifier sets the source range end, but in this case we're past
3289 // that location.
3290 SourceLocation Tmp = ParamInfo.getSourceRange().getEnd();
3291 ParamInfo.SetIdentifier(nullptr, CaretLoc);
3292 ParamInfo.SetRangeEnd(Tmp);
3293 if (ParamInfo.isInvalidType()) {
3294 // If there was an error parsing the arguments, they may have
3295 // tried to use ^(x+y) which requires an argument list. Just
3296 // skip the whole block literal.
3297 Actions.ActOnBlockError(CaretLoc, getCurScope());
3298 return ExprError();
3299 }
3300
3301 MaybeParseGNUAttributes(ParamInfo);
3302
3303 // Inform sema that we are starting a block.
3304 Actions.ActOnBlockArguments(CaretLoc, ParamInfo, getCurScope());
3305 } else if (!Tok.is(tok::l_brace)) {
3306 ParseBlockId(CaretLoc);
3307 } else {
3308 // Otherwise, pretend we saw (void).
3309 SourceLocation NoLoc;
3310 ParamInfo.AddTypeInfo(
3311 DeclaratorChunk::getFunction(/*HasProto=*/true,
3312 /*IsAmbiguous=*/false,
3313 /*RParenLoc=*/NoLoc,
3314 /*ArgInfo=*/nullptr,
3315 /*NumParams=*/0,
3316 /*EllipsisLoc=*/NoLoc,
3317 /*RParenLoc=*/NoLoc,
3318 /*RefQualifierIsLvalueRef=*/true,
3319 /*RefQualifierLoc=*/NoLoc,
3320 /*MutableLoc=*/NoLoc, EST_None,
3321 /*ESpecRange=*/SourceRange(),
3322 /*Exceptions=*/nullptr,
3323 /*ExceptionRanges=*/nullptr,
3324 /*NumExceptions=*/0,
3325 /*NoexceptExpr=*/nullptr,
3326 /*ExceptionSpecTokens=*/nullptr,
3327 /*DeclsInPrototype=*/{}, CaretLoc,
3328 CaretLoc, ParamInfo),
3329 CaretLoc);
3330
3331 MaybeParseGNUAttributes(ParamInfo);
3332
3333 // Inform sema that we are starting a block.
3334 Actions.ActOnBlockArguments(CaretLoc, ParamInfo, getCurScope());
3335 }
3336
3337
3338 ExprResult Result(true);
3339 if (!Tok.is(tok::l_brace)) {
3340 // Saw something like: ^expr
3341 Diag(Tok, diag::err_expected_expression);
3342 Actions.ActOnBlockError(CaretLoc, getCurScope());
3343 return ExprError();
3344 }
3347 StmtResult Stmt(ParseCompoundStatementBody());
3348 BlockScope.Exit();
3349 if (!Stmt.isInvalid())
3350 Result = Actions.ActOnBlockStmtExpr(CaretLoc, Stmt.get(), getCurScope());
3351 else
3352 Actions.ActOnBlockError(CaretLoc, getCurScope());
3353 return Result;
3354}
3355
3356ExprResult Parser::ParseObjCBoolLiteral() {
3357 tok::TokenKind Kind = Tok.getKind();
3358 return Actions.ObjC().ActOnObjCBoolLiteral(ConsumeToken(), Kind);
3359}
3360
3361/// Validate availability spec list, emitting diagnostics if necessary. Returns
3362/// true if invalid.
3364 ArrayRef<AvailabilitySpec> AvailSpecs) {
3365 llvm::SmallSet<StringRef, 4> Platforms;
3366 bool HasOtherPlatformSpec = false;
3367 bool Valid = true;
3368 for (const auto &Spec : AvailSpecs) {
3369 if (Spec.isOtherPlatformSpec()) {
3370 if (HasOtherPlatformSpec) {
3371 P.Diag(Spec.getBeginLoc(), diag::err_availability_query_repeated_star);
3372 Valid = false;
3373 }
3374
3375 HasOtherPlatformSpec = true;
3376 continue;
3377 }
3378
3379 bool Inserted = Platforms.insert(Spec.getPlatform()).second;
3380 if (!Inserted) {
3381 // Rule out multiple version specs referring to the same platform.
3382 // For example, we emit an error for:
3383 // @available(macos 10.10, macos 10.11, *)
3384 StringRef Platform = Spec.getPlatform();
3385 P.Diag(Spec.getBeginLoc(), diag::err_availability_query_repeated_platform)
3386 << Spec.getEndLoc() << Platform;
3387 Valid = false;
3388 }
3389 }
3390
3391 if (!HasOtherPlatformSpec) {
3392 SourceLocation InsertWildcardLoc = AvailSpecs.back().getEndLoc();
3393 P.Diag(InsertWildcardLoc, diag::err_availability_query_wildcard_required)
3394 << FixItHint::CreateInsertion(InsertWildcardLoc, ", *");
3395 return true;
3396 }
3397
3398 return !Valid;
3399}
3400
3401std::optional<AvailabilitySpec> Parser::ParseAvailabilitySpec() {
3402 if (Tok.is(tok::star)) {
3404 } else {
3405 // Parse the platform name.
3406 if (Tok.is(tok::code_completion)) {
3407 cutOffParsing();
3409 return std::nullopt;
3410 }
3411 if (Tok.isNot(tok::identifier)) {
3412 Diag(Tok, diag::err_avail_query_expected_platform_name);
3413 return std::nullopt;
3414 }
3415
3416 IdentifierLoc *PlatformIdentifier = ParseIdentifierLoc();
3417 SourceRange VersionRange;
3418 VersionTuple Version = ParseVersionTuple(VersionRange);
3419
3420 if (Version.empty())
3421 return std::nullopt;
3422
3423 StringRef GivenPlatform =
3424 PlatformIdentifier->getIdentifierInfo()->getName();
3425 StringRef Platform =
3426 AvailabilityAttr::canonicalizePlatformName(GivenPlatform);
3427
3428 if (AvailabilityAttr::getPrettyPlatformName(Platform).empty() ||
3429 (GivenPlatform.contains("xros") || GivenPlatform.contains("xrOS"))) {
3430 Diag(PlatformIdentifier->getLoc(),
3431 diag::err_avail_query_unrecognized_platform_name)
3432 << GivenPlatform;
3433 return std::nullopt;
3434 }
3435
3436 return AvailabilitySpec(Version, Platform, PlatformIdentifier->getLoc(),
3437 VersionRange.getEnd());
3438 }
3439}
3440
3441ExprResult Parser::ParseAvailabilityCheckExpr(SourceLocation BeginLoc) {
3442 assert(Tok.is(tok::kw___builtin_available) ||
3443 Tok.isObjCAtKeyword(tok::objc_available));
3444
3445 // Eat the available or __builtin_available.
3446 ConsumeToken();
3447
3448 BalancedDelimiterTracker Parens(*this, tok::l_paren);
3449 if (Parens.expectAndConsume())
3450 return ExprError();
3451
3453 bool HasError = false;
3454 while (true) {
3455 std::optional<AvailabilitySpec> Spec = ParseAvailabilitySpec();
3456 if (!Spec)
3457 HasError = true;
3458 else
3459 AvailSpecs.push_back(*Spec);
3460
3461 if (!TryConsumeToken(tok::comma))
3462 break;
3463 }
3464
3465 if (HasError) {
3466 SkipUntil(tok::r_paren, StopAtSemi);
3467 return ExprError();
3468 }
3469
3470 CheckAvailabilitySpecList(*this, AvailSpecs);
3471
3472 if (Parens.consumeClose())
3473 return ExprError();
3474
3475 return Actions.ObjC().ActOnObjCAvailabilityCheckExpr(
3476 AvailSpecs, BeginLoc, Parens.getCloseLocation());
3477}
Defines the clang::ASTContext interface.
StringRef P
Expr * E
static Decl::Kind getKind(const Decl *D)
Definition: DeclBase.cpp:1192
Defines the clang::Expr interface and subclasses for C++ expressions.
unsigned Iter
Definition: HTMLLogger.cpp:153
#define X(type, name)
Definition: Value.h:145
#define SM(sm)
Definition: OffloadArch.cpp:16
static bool CheckAvailabilitySpecList(Parser &P, ArrayRef< AvailabilitySpec > AvailSpecs)
Validate availability spec list, emitting diagnostics if necessary.
Definition: ParseExpr.cpp:3363
#define REVERTIBLE_TYPE_TRAIT(Name)
Defines the PrettyStackTraceEntry class, which is used to make crashes give more contextual informati...
uint32_t Id
Definition: SemaARM.cpp:1179
This file declares semantic analysis for CUDA constructs.
This file declares facilities that support code completion.
SourceLocation Loc
Definition: SemaObjC.cpp:754
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
Definition: ASTContext.h:793
bool isUnset() const
Definition: Ownership.h:168
PtrTy get() const
Definition: Ownership.h:171
bool isInvalid() const
Definition: Ownership.h:167
bool isUsable() const
Definition: Ownership.h:169
One specifier in an @available expression.
Definition: Availability.h:31
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.
Definition: DeclSpec.h:73
bool isNotEmpty() const
A scope specifier is present, but may be valid or invalid.
Definition: DeclSpec.h:180
ColonProtectionRAIIObject - This sets the Parser::ColonIsSacred bool and restores it when destroyed.
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...
Definition: DeclBase.h:1449
DeclContext * getParent()
getParent - Returns the containing DeclContext.
Definition: DeclBase.h:2109
bool isFileContext() const
Definition: DeclBase.h:2180
bool isRecord() const
Definition: DeclBase.h:2189
Captures information about "declaration specifiers".
Definition: DeclSpec.h:217
Information about one declarator, including the parsed type information and the identifier.
Definition: DeclSpec.h:1874
RAII object that enters a new function expression evaluation context.
RAII object that enters a new expression evaluation context.
This represents one expression.
Definition: Expr.h:112
bool containsErrors() const
Whether this expression contains subexpressions which had errors.
Definition: Expr.h:246
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
Definition: Expr.cpp:273
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.
Definition: Diagnostic.h:139
static FixItHint CreateRemoval(CharSourceRange RemoveRange)
Create a code modification hint that removes the given source range.
Definition: Diagnostic.h:128
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.
Definition: Diagnostic.h:102
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.
A simple pair of identifier info and location.
SourceLocation getLoc() const
IdentifierInfo * getIdentifierInfo() const
Represents the declaration of a label.
Definition: Decl.h:523
static StringRef getImmediateMacroNameForDiagnostics(SourceLocation Loc, const SourceManager &SM, const LangOptions &LangOpts)
Retrieve the name of the immediate macro expansion.
Definition: Lexer.cpp:1103
This represents a decl that may have a name.
Definition: Decl.h:273
void * getAsOpaquePtr() const
Definition: Ownership.h:91
PtrTy get() const
Definition: Ownership.h:81
static const ParsedAttributesView & none()
Definition: ParsedAttr.h:817
Parser - This implements a parser for the C family of languages.
Definition: Parser.h:171
TypeResult ParseTypeName(SourceRange *Range=nullptr, DeclaratorContext Context=DeclaratorContext::TypeName, AccessSpecifier AS=AS_none, Decl **OwnedType=nullptr, ParsedAttributes *Attrs=nullptr)
ParseTypeName.
Definition: ParseDecl.cpp:44
DiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID)
Definition: Parser.cpp:85
ExprResult ParseStringLiteralExpression(bool AllowUserDefinedLiteral=false)
ParseStringLiteralExpression - This handles the various token types that form string literals,...
Definition: ParseExpr.cpp:2964
SourceLocation ConsumeToken()
ConsumeToken - Consume the current 'peek token' and lex the next one.
Definition: Parser.h:262
Sema & getActions() const
Definition: Parser.h:207
static TypeResult getTypeAnnotation(const Token &Tok)
getTypeAnnotation - Read a parsed type out of an annotation token.
Definition: Parser.h:327
ExprResult ParseCaseExpression(SourceLocation CaseLoc)
Definition: ParseExpr.cpp:173
ExprResult ParseConstraintLogicalOrExpression(bool IsTrailingRequiresClause)
Parse a constraint-logical-or-expression.
Definition: ParseExpr.cpp:274
ExprResult ParseConstantExpressionInExprEvalContext(TypoCorrectionTypeBehavior CorrectionBehavior=TypoCorrectionTypeBehavior::AllowNonTypes)
Definition: ParseExpr.cpp:121
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.
Definition: Parser.h:290
const Token & GetLookAheadToken(unsigned N)
GetLookAheadToken - This peeks ahead N tokens and returns that token without consuming any tokens.
Definition: Parser.h:316
ExprResult ParseConstantExpression()
Definition: ParseExpr.cpp:133
ExprResult ParseConditionalExpression()
Definition: ParseExpr.cpp:95
bool TryConsumeToken(tok::TokenKind Expected)
Definition: Parser.h:270
Scope * getCurScope() const
Definition: Parser.h:211
ExprResult ParseArrayBoundExpression()
Definition: ParseExpr.cpp:144
ExprResult ParseConstraintLogicalAndExpression(bool IsTrailingRequiresClause)
Parse a constraint-logical-and-expression.
Definition: ParseExpr.cpp:197
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 ...
Definition: Parser.h:495
const LangOptions & getLangOpts() const
Definition: Parser.h:204
ExprResult ParseExpression(TypoCorrectionTypeBehavior CorrectionBehavior=TypoCorrectionTypeBehavior::AllowNonTypes)
Simple precedence-based parser for binary/ternary operators.
Definition: ParseExpr.cpp:47
@ StopBeforeMatch
Stop skipping at specified token, but don't skip the token itself.
Definition: Parser.h:476
@ StopAtSemi
Stop skipping at semicolon.
Definition: Parser.h:474
bool TryAnnotateTypeOrScopeToken(ImplicitTypenameContext AllowImplicitTypename=ImplicitTypenameContext::No)
TryAnnotateTypeOrScopeToken - If the current token position is on a typename (possibly qualified in C...
Definition: Parser.cpp:1894
ExprResult ParseUnevaluatedStringLiteralExpression()
Definition: ParseExpr.cpp:2969
const Token & NextToken()
NextToken - This peeks ahead one token and returns it without consuming it.
Definition: Parser.h:324
ExprResult ParseAssignmentExpression(TypoCorrectionTypeBehavior CorrectionBehavior=TypoCorrectionTypeBehavior::AllowNonTypes)
Parse an expr that doesn't include (top-level) commas.
Definition: ParseExpr.cpp:75
ExprResult ParseConstraintExpression()
Parse a constraint-expression.
Definition: ParseExpr.cpp:185
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.
Definition: Sema.h:327
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.
Definition: TypeBase.h:937
bool isNull() const
Return true if this QualType doesn't point to a type yet.
Definition: TypeBase.h:1004
@ BlockScope
This is a scope that corresponds to a block/closure object.
Definition: Scope.h:75
@ CompoundStmtScope
This is a compound statement scope.
Definition: Scope.h:134
@ FnScope
This indicates that the scope corresponds to a function, which means that labels are set here.
Definition: Scope.h:51
@ DeclScope
This is a scope that can contain a declaration.
Definition: Scope.h:63
ExprResult ActOnExecConfigExpr(Scope *S, SourceLocation LLLLoc, MultiExprArg ExecConfig, SourceLocation GGGLoc)
Definition: SemaCUDA.cpp:52
@ 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 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)
Definition: SemaSYCL.cpp:151
A RAII object to temporarily push a declaration context.
Definition: Sema.h:3468
RAII class used to indicate that we are performing provisional semantic analysis to determine the val...
Definition: Sema.h:12401
ExprResult ActOnUnaryOp(Scope *S, SourceLocation OpLoc, tok::TokenKind Op, Expr *Input, bool IsAfterAmp=false)
Unary Operators. 'Tok' is the token for the operator.
Definition: SemaExpr.cpp:16082
ExprResult ActOnConstantExpression(ExprResult Res)
Definition: SemaExpr.cpp:19987
ExprResult ActOnNoexceptExpr(SourceLocation KeyLoc, SourceLocation LParen, Expr *Operand, SourceLocation RParen)
ExprResult ActOnCompoundLiteral(SourceLocation LParenLoc, ParsedType Ty, SourceLocation RParenLoc, Expr *InitExpr)
Definition: SemaExpr.cpp:7112
SemaOpenMP & OpenMP()
Definition: Sema.h:1498
void ActOnStartStmtExpr()
Definition: SemaExpr.cpp:16101
void ActOnStmtExprError()
Definition: SemaExpr.cpp:16107
SemaCUDA & CUDA()
Definition: Sema.h:1438
ExprResult ActOnIdExpression(Scope *S, CXXScopeSpec &SS, SourceLocation TemplateKWLoc, UnqualifiedId &Id, bool HasTrailingLParen, bool IsAddressOfOperand, CorrectionCandidateCallback *CCC=nullptr, bool IsInlineAsmIdentifier=false, Token *KeywordReplacement=nullptr)
Definition: SemaExpr.cpp:2720
const ExpressionEvaluationContextRecord & currentEvaluationContext() const
Definition: Sema.h:6882
ExprResult ActOnCharacterConstant(const Token &Tok, Scope *UDLScope=nullptr)
Definition: SemaExpr.cpp:3575
ExprResult ActOnStartCXXMemberReference(Scope *S, Expr *Base, SourceLocation OpLoc, tok::TokenKind OpKind, ParsedType &ObjectType, bool &MayBePseudoDestructor)
ExprResult ActOnCaseExpr(SourceLocation CaseLoc, ExprResult Val)
Definition: SemaStmt.cpp:485
SemaSYCL & SYCL()
Definition: Sema.h:1523
ExprResult ActOnCXXNullPtrLiteral(SourceLocation Loc)
ActOnCXXNullPtrLiteral - Parse 'nullptr'.
SemaObjC & ObjC()
Definition: Sema.h:1483
bool CheckConstraintExpression(const Expr *CE, Token NextToken=Token(), bool *PossibleNonPrimary=nullptr, bool IsTrailingRequiresClause=false)
Check whether the given expression is a valid constraint expression.
Definition: SemaConcept.cpp:90
ASTContext & getASTContext() const
Definition: Sema.h:918
ExprResult ActOnAddrLabel(SourceLocation OpLoc, SourceLocation LabLoc, LabelDecl *TheDecl)
ActOnAddrLabel - Parse the GNU address of label extension: "&&foo".
Definition: SemaExpr.cpp:16088
ExprResult ActOnParenListExpr(SourceLocation L, SourceLocation R, MultiExprArg Val)
Definition: SemaExpr.cpp:8030
ExprResult ActOnChooseExpr(SourceLocation BuiltinLoc, Expr *CondExpr, Expr *LHSExpr, Expr *RHSExpr, SourceLocation RPLoc)
Definition: SemaExpr.cpp:16375
ExprResult ActOnUnevaluatedStringLiteral(ArrayRef< Token > StringToks)
Definition: SemaExpr.cpp:2065
SourceRange getExprRange(Expr *E) const
Definition: SemaExpr.cpp:500
SemaCodeCompletion & CodeCompletion()
Definition: Sema.h:1433
SemaOpenACC & OpenACC()
Definition: Sema.h:1488
@ ReuseLambdaContextDecl
Definition: Sema.h:6970
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 *.
Definition: SemaExpr.cpp:1727
void ActOnBlockError(SourceLocation CaretLoc, Scope *CurScope)
ActOnBlockError - If there is an error parsing a block, this callback is invoked to pop the informati...
Definition: SemaExpr.cpp:16551
DeclContext * CurContext
CurContext - This is the current declaration context of parsing.
Definition: Sema.h:1411
ExprResult ActOnGNUNullExpr(SourceLocation TokenLoc)
Definition: SemaExpr.cpp:16926
ExprResult ActOnParenExpr(SourceLocation L, SourceLocation R, Expr *E)
Definition: SemaExpr.cpp:4154
ExprResult ActOnSourceLocExpr(SourceLocIdentKind Kind, SourceLocation BuiltinLoc, SourceLocation RPLoc)
Definition: SemaExpr.cpp:17011
ExprResult ActOnConditionalOp(SourceLocation QuestionLoc, SourceLocation ColonLoc, Expr *CondExpr, Expr *LHSExpr, Expr *RHSExpr)
ActOnConditionalOp - Parse a ?: operation.
Definition: SemaExpr.cpp:8916
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)
Definition: SemaType.cpp:6402
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....
Definition: SemaExpr.cpp:2144
ExprResult ActOnBinOp(Scope *S, SourceLocation TokLoc, tok::TokenKind Kind, Expr *LHSExpr, Expr *RHSExpr)
Binary Operators. 'Tok' is the token for the operator.
Definition: SemaExpr.cpp:15539
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.
Definition: SemaDecl.cpp:270
ExprResult ActOnPredefinedExpr(SourceLocation Loc, tok::TokenKind Kind)
Definition: SemaExpr.cpp:3571
@ ConstantEvaluated
The current context is "potentially evaluated" in C++11 terms, but the expression is evaluated at com...
@ PotentiallyEvaluated
The current expression is potentially evaluated at run time, which means that code may be generated t...
@ 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.
Definition: SemaExpr.cpp:6809
ExprResult ActOnVAArg(SourceLocation BuiltinLoc, Expr *E, ParsedType Ty, SourceLocation RPLoc)
Definition: SemaExpr.cpp:16756
ExprResult ActOnCastExpr(Scope *S, SourceLocation LParenLoc, Declarator &D, ParsedType &Ty, SourceLocation RParenLoc, Expr *CastExpr)
Definition: SemaExpr.cpp:7862
SmallVector< ExpressionEvaluationContextRecord, 8 > ExprEvalContexts
A stack of expression evaluation contexts.
Definition: Sema.h:8262
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)
Definition: SemaExpr.cpp:16115
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...
Definition: SemaExpr.cpp:16561
void runWithSufficientStackSpace(SourceLocation Loc, llvm::function_ref< void()> Fn)
Run some code with "sufficient" stack space.
Definition: Sema.cpp:627
ExprResult ActOnPostfixUnaryOp(Scope *S, SourceLocation OpLoc, tok::TokenKind Kind, Expr *Input)
Definition: SemaExpr.cpp:4832
ExprResult CreateRecoveryExpr(SourceLocation Begin, SourceLocation End, ArrayRef< Expr * > SubExprs, QualType T=QualType())
Attempts to produce a RecoveryExpr after some AST node cannot be created.
Definition: SemaExpr.cpp:21528
ExprResult ActOnNumericConstant(const Token &Tok, Scope *UDLScope=nullptr)
Definition: SemaExpr.cpp:3709
void ActOnBlockStart(SourceLocation CaretLoc, Scope *CurScope)
ActOnBlockStart - This callback is invoked when a block literal is started.
Definition: SemaExpr.cpp:16413
ExprResult ActOnArraySubscriptExpr(Scope *S, Expr *Base, SourceLocation LLoc, MultiExprArg ArgExprs, SourceLocation RLoc)
Definition: SemaExpr.cpp:4905
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.
Definition: SemaExpr.cpp:6520
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...
Definition: SemaExpr.cpp:4762
void ActOnBlockArguments(SourceLocation CaretLoc, Declarator &ParamInfo, Scope *CurScope)
ActOnBlockArguments - This callback allows processing of block arguments.
Definition: SemaExpr.cpp:16442
ExprResult ActOnConvertVectorExpr(Expr *E, ParsedType ParsedDestTy, SourceLocation BuiltinLoc, SourceLocation RParenLoc)
ActOnConvertVectorExpr - create a new convert-vector expression from the provided arguments.
Definition: SemaExpr.cpp:6830
ExprResult ActOnBuiltinOffsetOf(Scope *S, SourceLocation BuiltinLoc, SourceLocation TypeLoc, ParsedType ParsedArgTy, ArrayRef< OffsetOfComponent > Components, SourceLocation RParenLoc)
Definition: SemaExpr.cpp:16356
ExprResult ActOnNameClassifiedAsOverloadSet(Scope *S, Expr *OverloadSet)
Act on the result of classifying a name as an overload set.
Definition: SemaDecl.cpp:1322
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.
Definition: Stmt.h:85
SourceLocation getEndLoc() const LLVM_READONLY
Definition: Stmt.cpp:358
SourceRange getSourceRange() const LLVM_READONLY
SourceLocation tokens are not useful in isolation - they are low level value objects created/interpre...
Definition: Stmt.cpp:334
SourceLocation getBeginLoc() const LLVM_READONLY
Definition: Stmt.cpp:346
Token - This structure provides full information about a lexed token.
Definition: Token.h:36
IdentifierInfo * getIdentifierInfo() const
Definition: Token.h:189
SourceLocation getLocation() const
Return a source location identifier for the specified offset in the current file.
Definition: Token.h:134
const char * getName() const
Definition: Token.h:176
void setKind(tok::TokenKind K)
Definition: Token.h:98
SourceLocation getAnnotationEndLoc() const
Definition: Token.h:148
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)) {....
Definition: Token.h:102
void * getAnnotationValue() const
Definition: Token.h:236
tok::TokenKind getKind() const
Definition: Token.h:97
bool isAtStartOfLine() const
isAtStartOfLine - Return true if this token is at the start of a line.
Definition: Token.h:278
bool isOneOf(Ts... Ks) const
Definition: Token.h:104
bool isNot(tok::TokenKind K) const
Definition: Token.h:103
bool isObjCAtKeyword(tok::ObjCKeywordKind objcKey) const
Return true if we have an ObjC keyword identifier.
Definition: Lexer.cpp:60
bool isSimpleTypeSpecifier(const LangOptions &LangOpts) const
Determine whether the token kind starts a simple-type-specifier.
Definition: Lexer.cpp:77
SourceLocation getLastLoc() const
Definition: Token.h:157
Base wrapper for a particular "section" of type source info.
Definition: TypeLoc.h:59
The base class of the type hierarchy.
Definition: TypeBase.h:1833
bool isSpecificPlaceholderType(unsigned K) const
Test for a specific placeholder type.
Definition: TypeBase.h:8925
bool isFunctionType() const
Definition: TypeBase.h:8576
bool isVectorType() const
Definition: TypeBase.h:8719
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.
Definition: DeclSpec.h:998
TokenKind
Provides a simple uniform namespace for tokens from all C languages.
Definition: TokenKinds.h:25
The JSON file list parser is used to communicate input to InstallAPI.
@ TST_typename
Definition: Specifiers.h:84
@ OpenCL
Definition: LangStandard.h:65
@ CPlusPlus23
Definition: LangStandard.h:60
@ CPlusPlus
Definition: LangStandard.h:55
@ CPlusPlus11
Definition: LangStandard.h:56
@ CPlusPlus17
Definition: LangStandard.h:58
TypoCorrectionTypeBehavior
If a typo should be encountered, should typo correction suggest type names, non type names,...
Definition: Parser.h:106
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.
Definition: TypeTraits.h:51
ExprResult ExprEmpty()
Definition: Ownership.h:272
@ 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
Definition: Ownership.h:249
ExprResult ExprError()
Definition: Ownership.h:265
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.
Definition: TemplateKinds.h:30
const FunctionProtoType * T
ParenExprKind
In a call to ParseParenExpression, are the initial parentheses part of an operator that requires the ...
Definition: Parser.h:128
CastParseKind
Control what ParseCastExpression will parse.
Definition: Parser.h:113
SourceLocIdentKind
Definition: Expr.h:4940
ParenParseOption
ParenParseOption - Control what ParseParenExpression will parse.
Definition: Parser.h:116
@ 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.
Definition: DeclSpec.cpp:132
Helper class to shuttle information about #embed directives from the preprocessor to the parser throu...
bool IsCaseExpr
Whether evaluating an expression for a switch case label.
Definition: Sema.h:6807
Information about a template-id annotation token.
TemplateNameKind Kind
The kind of template that Template refers to.