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