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

Provided by KDAB

Privacy Policy
Improve your Profiling and Debugging skills
Find out more

source code of clang/lib/Parse/ParseExpr.cpp