41 #include "llvm/ADT/ArrayRef.h"
42 #include "llvm/ADT/DenseMap.h"
43 #include "llvm/ADT/STLExtras.h"
44 #include "llvm/ADT/STLForwardCompat.h"
45 #include "llvm/ADT/SmallPtrSet.h"
46 #include "llvm/ADT/SmallString.h"
47 #include "llvm/ADT/SmallVector.h"
48 #include "llvm/ADT/StringExtras.h"
50 using namespace clang;
71 DiscardCleanupsInEvaluationContext();
76 bool HasLeadingEmptyMacro) {
77 return new (Context)
NullStmt(SemiLoc, HasLeadingEmptyMacro);
87 return new (Context)
DeclStmt(DG, StartLoc, EndLoc);
105 Diag(
decl->getLocation(), diag::err_non_variable_decl_in_for);
106 decl->setInvalidDecl();
112 var->setInit(
nullptr);
117 if (getLangOpts().ObjCAutoRefCount) {
125 var->setType(
type.withConst());
126 var->setARCPseudoStrong(
true);
142 if (!Op->isComparisonOp())
145 if (Op->getOpcode() == BO_EQ)
147 else if (Op->getOpcode() == BO_NE)
149 else if (Op->getOpcode() == BO_Cmp)
152 assert(Op->isRelationalOp());
155 Loc = Op->getOperatorLoc();
156 CanAssign = Op->getLHS()->IgnoreParenImpCasts()->isLValue();
158 switch (Op->getOperator()) {
162 case OO_ExclaimEqual:
167 case OO_GreaterEqual:
178 Loc = Op->getOperatorLoc();
179 CanAssign = Op->getArg(0)->IgnoreParenImpCasts()->isLValue();
190 S.
Diag(
Loc, diag::warn_unused_comparison)
196 if (
Kind == Inequality)
197 S.
Diag(
Loc, diag::note_inequality_comparison_to_or_assign)
200 S.
Diag(
Loc, diag::note_equality_comparison_to_assign)
212 StringRef Msg = A->getMessage();
216 return S.
Diag(
Loc, diag::warn_unused_constructor) << A << R1 << R2;
217 return S.
Diag(
Loc, diag::warn_unused_result) << A << R1 << R2;
221 return S.
Diag(
Loc, diag::warn_unused_constructor_msg) << A << Msg << R1
223 return S.
Diag(
Loc, diag::warn_unused_result_msg) << A << Msg << R1 << R2;
228 return DiagnoseUnusedExprResult(
Label->getSubStmt(), DiagID);
230 const Expr *E = dyn_cast_or_null<Expr>(S);
236 if (isUnevaluatedContext())
245 bool ShouldSuppress =
246 SourceMgr.isMacroBodyExpansion(ExprLoc) ||
247 SourceMgr.isInSystemMacro(ExprLoc);
249 const Expr *WarnExpr;
267 if (findMacroSpelling(SpellLoc,
"UNREFERENCED_PARAMETER"))
274 if (
const FullExpr *Temps = dyn_cast<FullExpr>(E))
275 E = Temps->getSubExpr();
277 E = TempExpr->getSubExpr();
283 if (
const auto *
Cast = dyn_cast<CastExpr>(E))
284 if (
Cast->getCastKind() == CK_NoOp ||
285 Cast->getCastKind() == CK_ConstructorConversion)
286 E =
Cast->getSubExpr()->IgnoreImpCasts();
288 if (
const CallExpr *CE = dyn_cast<CallExpr>(E)) {
293 CE->getUnusedResultAttr(Context)),
301 if (
const Decl *FD = CE->getCalleeDecl()) {
304 if (FD->hasAttr<PureAttr>()) {
305 Diag(
Loc, diag::warn_unused_call) << R1 << R2 <<
"pure";
308 if (FD->hasAttr<ConstAttr>()) {
309 Diag(
Loc, diag::warn_unused_call) << R1 << R2 <<
"const";
313 }
else if (
const auto *CE = dyn_cast<CXXConstructExpr>(E)) {
315 const auto *A = Ctor->getAttr<WarnUnusedResultAttr>();
316 A = A ? A : Ctor->getParent()->getAttr<WarnUnusedResultAttr>();
320 }
else if (
const auto *ILE = dyn_cast<InitListExpr>(E)) {
321 if (
const TagDecl *TD = ILE->getType()->getAsTagDecl()) {
327 }
else if (ShouldSuppress)
332 if (getLangOpts().ObjCAutoRefCount && ME->isDelegateInitCall()) {
333 Diag(
Loc, diag::err_arc_unused_init_message) << R1;
343 const Expr *Source = POE->getSyntacticForm();
345 if (LangOpts.OpenMP && isa<CallExpr>(Source) &&
346 POE->getNumSemanticExprs() == 1 &&
347 isa<CallExpr>(POE->getSemanticExpr(0)))
348 return DiagnoseUnusedExprResult(POE->getSemanticExpr(0), DiagID);
349 if (isa<ObjCSubscriptRefExpr>(Source))
350 DiagID = diag::warn_unused_container_subscript_expr;
351 else if (isa<ObjCPropertyRefExpr>(Source))
352 DiagID = diag::warn_unused_property_expr;
354 = dyn_cast<CXXFunctionalCastExpr>(E)) {
355 const Expr *E = FC->getSubExpr();
357 E = TE->getSubExpr();
358 if (isa<CXXTemporaryObjectExpr>(E))
361 if (
const CXXRecordDecl *RD = CE->getType()->getAsCXXRecordDecl())
362 if (!RD->getAttr<WarnUnusedAttr>())
366 else if (
const CStyleCastExpr *CE = dyn_cast<CStyleCastExpr>(E)) {
374 Diag(
Loc, diag::warn_unused_voidptr)
384 Diag(
Loc, diag::warn_unused_volatile) << R1 << R2;
391 if (DiagID != diag::warn_unused_comma_left_operand || !isSFINAEContext())
393 PDiag(DiagID) << R1 << R2);
397 PushCompoundScope(IsStmtExpr);
401 if (getCurFPFeatures().isFPConstrained()) {
413 return getCurFunction()->CompoundScopes.back();
418 const unsigned NumElts = Elts.size();
423 const unsigned MixedDeclsCodeID = getLangOpts().C99
424 ? diag::warn_mixed_decls_code
425 : diag::ext_mixed_decls_code;
426 if (!getLangOpts().
CPlusPlus && !Diags.isIgnored(MixedDeclsCodeID, L)) {
430 for (; i != NumElts && isa<DeclStmt>(Elts[i]); ++i)
434 for (; i != NumElts && !isa<DeclStmt>(Elts[i]); ++i)
438 Decl *D = *cast<DeclStmt>(Elts[i])->decl_begin();
446 if (NumElts != 0 && !CurrentInstantiationScope &&
447 getCurCompoundScope().HasEmptyLoopBodies) {
448 for (
unsigned i = 0; i != NumElts - 1; ++i)
449 DiagnoseEmptyLoopBody(Elts[i], Elts[i + 1]);
456 FPOptions FPO = (getCurFunction()->CompoundScopes.size() == 1)
458 : getCurCompoundScope().InitialFPFeatures;
469 if (DiagnoseUnexpandedParameterPack(Val.
get()))
474 if (getCurFunction()->SwitchStack.empty())
479 getCurFunction()->SwitchStack.back().getPointer()->getCond();
484 auto CheckAndFinish = [&](
Expr *E) {
488 if (getLangOpts().CPlusPlus11) {
497 if (!E->isValueDependent())
498 ER = VerifyIntegerConstantExpression(E, AllowFold);
500 ER = DefaultLvalueConversion(ER.
get());
502 ER = ImpCastExprToType(ER.
get(), CondType, CK_IntegralCast);
508 ExprResult Converted = CorrectDelayedTyposInExpr(
511 if (Converted.
get() == Val.
get())
512 Converted = CheckAndFinish(Val.
get());
520 assert((LHSVal.
isInvalid() || LHSVal.
get()) &&
"missing LHS value");
523 "missing RHS value");
525 if (getCurFunction()->SwitchStack.empty()) {
526 Diag(CaseLoc, diag::err_case_not_in_switch);
531 getCurFunction()->SwitchStack.back().setInt(
true);
535 if (LangOpts.OpenACC &&
537 Diag(CaseLoc, diag::err_acc_branch_in_out_compute_construct)
543 CaseLoc, DotDotDotLoc, ColonLoc);
544 getCurFunction()->SwitchStack.back().getPointer()->addSwitchCase(CS);
550 cast<CaseStmt>(S)->setSubStmt(SubStmt);
556 if (getCurFunction()->SwitchStack.empty()) {
557 Diag(DefaultLoc, diag::err_default_not_in_switch);
561 if (LangOpts.OpenACC &&
563 Diag(DefaultLoc, diag::err_acc_branch_in_out_compute_construct)
569 getCurFunction()->SwitchStack.back().getPointer()->addSwitchCase(DS);
578 Diag(IdentLoc, diag::err_redefinition_of_label) << TheDecl->
getDeclName();
586 Diag(IdentLoc, diag::warn_reserved_extern_symbol)
587 << TheDecl << static_cast<int>(Status);
591 if (getCurScope()->isInOpenACCComputeConstructScope())
592 setFunctionHasBranchProtectedScope();
613 for (
const auto *A : Attrs) {
614 if (A->getKind() == attr::MustTail) {
615 if (!checkAndRewriteMustTailAttr(SubStmt, *A)) {
618 setFunctionHasMustTail();
628 ProcessStmtAttributes(SubStmt, Attrs, SemanticAttrs);
629 if (!SemanticAttrs.empty())
630 return BuildAttributedStmt(Attrs.
Range.
getBegin(), SemanticAttrs, SubStmt);
645 if (!checkMustTailAttr(St, MTA))
651 auto IgnoreImplicitAsWritten = [](
Expr *E) ->
Expr * {
662 bool Sema::checkMustTailAttr(
const Stmt *St,
const Attr &MTA) {
663 assert(!CurContext->isDependentContext() &&
664 "musttail cannot be checked from a dependent context");
667 auto IgnoreParenImplicitAsWritten = [](
const Expr *E) ->
const Expr * {
673 const Expr *E = cast<ReturnStmt>(St)->getRetValue();
674 const auto *CE = dyn_cast_or_null<CallExpr>(IgnoreParenImplicitAsWritten(E));
681 if (
const auto *EWC = dyn_cast<ExprWithCleanups>(E)) {
682 if (EWC->cleanupsHaveSideEffects()) {
683 Diag(St->
getBeginLoc(), diag::err_musttail_needs_trivial_args) << &MTA;
694 ft_non_static_member,
695 ft_pointer_to_member,
696 } MemberType = ft_non_member;
701 } CallerType, CalleeType;
704 bool IsCallee) ->
bool {
705 if (isa<CXXConstructorDecl, CXXDestructorDecl>(CMD)) {
707 << IsCallee << isa<CXXDestructorDecl>(CMD);
709 Diag(CMD->getBeginLoc(), diag::note_musttail_structors_forbidden)
710 << isa<CXXDestructorDecl>(CMD);
715 Type.MemberType = FuncType::ft_static_member;
717 Type.This = CMD->getFunctionObjectParameterType();
718 Type.MemberType = FuncType::ft_non_static_member;
724 const auto *CallerDecl = dyn_cast<FunctionDecl>(CurContext);
729 if (isa<BlockDecl>(CurContext))
731 else if (isa<ObjCMethodDecl>(CurContext))
735 Diag(St->
getBeginLoc(), diag::err_musttail_forbidden_from_this_context)
738 }
else if (
const auto *CMD = dyn_cast<CXXMethodDecl>(CurContext)) {
740 if (!GetMethodType(CMD, CallerType,
false))
748 const auto *CalleeBinOp = dyn_cast<BinaryOperator>(CalleeExpr);
750 ? CE->getCalleeDecl()->getBeginLoc()
755 dyn_cast_or_null<CXXMethodDecl>(CE->getCalleeDecl())) {
757 if (!GetMethodType(CMD, CalleeType,
true))
759 }
else if (CalleeBinOp && CalleeBinOp->isPtrMemOp()) {
763 CalleeType.This =
QualType(MPT->getClass(), 0);
765 CalleeType.MemberType = FuncType::ft_pointer_to_member;
766 }
else if (isa<CXXPseudoDestructorExpr>(CalleeExpr)) {
778 if (!CalleeType.Func || !CallerType.Func) {
780 if (!CalleeType.Func && CE->getDirectCallee()) {
781 Diag(CE->getDirectCallee()->getBeginLoc(),
782 diag::note_musttail_fix_non_prototype);
784 if (!CallerType.Func)
785 Diag(CallerDecl->getBeginLoc(), diag::note_musttail_fix_non_prototype);
796 if (CallerType.Func->getCallConv() != CalleeType.Func->getCallConv()) {
797 if (
const auto *ND = dyn_cast_or_null<NamedDecl>(CE->getCalleeDecl()))
799 <<
true << ND->getDeclName();
801 Diag(St->
getBeginLoc(), diag::err_musttail_callconv_mismatch) <<
false;
802 Diag(CalleeLoc, diag::note_musttail_callconv_mismatch)
809 if (CalleeType.Func->isVariadic() || CallerType.Func->isVariadic()) {
814 const auto *CalleeDecl = CE->getCalleeDecl();
815 if (CalleeDecl && CalleeDecl->hasAttr<CXX11NoReturnAttr>()) {
821 if (CallerType.This.isNull() != CalleeType.This.isNull()) {
822 if (
const auto *ND = dyn_cast_or_null<NamedDecl>(CE->getCalleeDecl())) {
824 << CallerType.MemberType << CalleeType.MemberType <<
true
825 << ND->getDeclName();
826 Diag(CalleeLoc, diag::note_musttail_callee_defined_here)
827 << ND->getDeclName();
830 << CallerType.MemberType << CalleeType.MemberType <<
false;
835 auto CheckTypesMatch = [
this](FuncType CallerType, FuncType CalleeType,
845 unsigned Select) ->
bool {
853 if (!CallerType.This.isNull() &&
857 if (!DoTypesMatch(CallerType.Func->getReturnType(),
861 if (CallerType.Func->getNumParams() != CalleeType.Func->getNumParams()) {
863 << CalleeType.Func->getNumParams();
869 size_t N = CallerType.Func->getNumParams();
870 for (
size_t I = 0; I < N; I++) {
871 if (!DoTypesMatch(CalleeParams[I], CallerParams[I],
873 PD << static_cast<int>(I) + 1;
882 if (!CheckTypesMatch(CallerType, CalleeType, PD)) {
883 if (
const auto *ND = dyn_cast_or_null<NamedDecl>(CE->getCalleeDecl()))
885 <<
true << ND->getDeclName();
901 CommaVisitor(
Sema &SemaRef) : Inherited(SemaRef.Context), SemaRef(SemaRef) {}
919 bool ConstevalOrNegatedConsteval =
923 Expr *CondExpr = Cond.
get().second;
924 assert((CondExpr || ConstevalOrNegatedConsteval) &&
925 "If statement: missing condition");
927 if (CondExpr && (getLangOpts().
C99 || getLangOpts().
CPlusPlus) &&
928 !Diags.isIgnored(diag::warn_comma_operator, CondExpr->
getExprLoc()))
929 CommaVisitor(*this).Visit(CondExpr);
931 if (!ConstevalOrNegatedConsteval && !elseStmt)
932 DiagnoseEmptyStmtBody(RParenLoc, thenStmt, diag::warn_empty_if_body);
934 if (ConstevalOrNegatedConsteval ||
936 auto DiagnoseLikelihood = [&](
const Stmt *S) {
938 Diags.Report(A->getLocation(),
939 diag::warn_attribute_has_no_effect_on_compile_time_if)
940 << A << ConstevalOrNegatedConsteval << A->getRange();
942 diag::note_attribute_has_no_effect_on_compile_time_if_here)
943 << ConstevalOrNegatedConsteval
950 DiagnoseLikelihood(thenStmt);
951 DiagnoseLikelihood(elseStmt);
953 std::tuple<bool, const Attr *, const Attr *> LHC =
955 if (std::get<0>(LHC)) {
956 const Attr *ThenAttr = std::get<1>(LHC);
957 const Attr *ElseAttr = std::get<2>(LHC);
959 diag::warn_attributes_likelihood_ifstmt_conflict)
960 << ThenAttr << ThenAttr->
getRange();
961 Diags.Report(ElseAttr->
getLocation(), diag::note_conflicting_attribute)
962 << ElseAttr << ElseAttr->
getRange();
966 if (ConstevalOrNegatedConsteval) {
967 bool Immediate = ExprEvalContexts.back().Context ==
968 ExpressionEvaluationContext::ImmediateFunctionContext;
969 if (CurContext->isFunctionOrMethod()) {
972 if (FD && FD->isImmediateFunction())
975 if (isUnevaluatedContext() || Immediate)
976 Diags.Report(IfLoc, diag::warn_consteval_if_always_true) << Immediate;
979 return BuildIfStmt(IfLoc, StatementKind, LParenLoc, InitStmt, Cond, RParenLoc,
980 thenStmt, ElseLoc, elseStmt);
993 isa<ObjCAvailabilityCheckExpr>(Cond.
get().second))
994 setFunctionHasBranchProtectedScope();
997 Cond.
get().first, Cond.
get().second, LParenLoc,
998 RParenLoc, thenStmt, ElseLoc, elseStmt);
1002 struct CaseCompareFunctor {
1003 bool operator()(
const std::pair<llvm::APSInt, CaseStmt*> &LHS,
1005 return LHS.first < RHS;
1007 bool operator()(
const std::pair<llvm::APSInt, CaseStmt*> &LHS,
1008 const std::pair<llvm::APSInt, CaseStmt*> &RHS) {
1009 return LHS.first < RHS.first;
1012 const std::pair<llvm::APSInt, CaseStmt*> &RHS) {
1013 return LHS < RHS.first;
1020 static bool CmpCaseVals(
const std::pair<llvm::APSInt, CaseStmt*>& lhs,
1021 const std::pair<llvm::APSInt, CaseStmt*>& rhs) {
1022 if (lhs.first < rhs.first)
1025 if (lhs.first == rhs.first &&
1026 lhs.second->getCaseLoc() < rhs.second->getCaseLoc())
1033 static bool CmpEnumVals(
const std::pair<llvm::APSInt, EnumConstantDecl*>& lhs,
1034 const std::pair<llvm::APSInt, EnumConstantDecl*>& rhs)
1036 return lhs.first < rhs.first;
1041 static bool EqEnumVals(
const std::pair<llvm::APSInt, EnumConstantDecl*>& lhs,
1042 const std::pair<llvm::APSInt, EnumConstantDecl*>& rhs)
1044 return lhs.first == rhs.first;
1050 if (
const auto *FE = dyn_cast<FullExpr>(E))
1051 E = FE->getSubExpr();
1052 while (
const auto *ImpCast = dyn_cast<ImplicitCastExpr>(E)) {
1053 if (ImpCast->getCastKind() != CK_IntegralCast)
break;
1054 E = ImpCast->getSubExpr();
1064 SwitchConvertDiagnoser(
Expr *Cond)
1070 return S.
Diag(
Loc, diag::err_typecheck_statement_requires_integer) <<
T;
1075 return S.
Diag(
Loc, diag::err_switch_incomplete_class_type)
1081 return S.
Diag(
Loc, diag::err_switch_explicit_conversion) <<
T << ConvTy;
1092 return S.
Diag(
Loc, diag::err_switch_multiple_conversions) <<
T;
1103 llvm_unreachable(
"conversion functions are permitted");
1105 } SwitchDiagnoser(Cond);
1108 PerformContextualImplicitConversion(SwitchLoc, Cond, SwitchDiagnoser);
1114 Cond = CondResult.
get();
1120 return UsualUnaryConversions(Cond);
1127 Expr *CondExpr = Cond.
get().second;
1128 assert((Cond.
isInvalid() || CondExpr) &&
"switch with no condition");
1141 Diag(SwitchLoc, diag::warn_bool_switch_condition)
1146 setFunctionHasBranchIntoScope();
1149 LParenLoc, RParenLoc);
1150 getCurFunction()->SwitchStack.push_back(
1156 Val = Val.extOrTrunc(BitWidth);
1157 Val.setIsSigned(IsSigned);
1163 unsigned UnpromotedWidth,
bool UnpromotedSign) {
1171 if (UnpromotedWidth < Val.getBitWidth()) {
1173 AdjustAPSInt(ConvVal, UnpromotedWidth, UnpromotedSign);
1174 AdjustAPSInt(ConvVal, Val.getBitWidth(), Val.isSigned());
1190 const Expr *CaseExpr,
1191 EnumValsTy::iterator &EI,
1192 EnumValsTy::iterator &EIEnd,
1199 if (
const VarDecl *VD = dyn_cast<VarDecl>(DRE->getDecl())) {
1208 if (ED->
hasAttr<FlagEnumAttr>())
1211 while (EI != EIEnd && EI->first < Val)
1214 if (EI != EIEnd && EI->first == Val)
1227 if (!CondEnumType || !CaseEnumType)
1234 if (!CaseEnumType->getDecl()->getIdentifier() &&
1235 !CaseEnumType->getDecl()->getTypedefNameForAnonDecl())
1241 S.
Diag(Case->
getExprLoc(), diag::warn_comparison_of_mixed_enum_types_switch)
1250 bool CaseListIsIncomplete = getCurFunction()->SwitchStack.back().getInt();
1251 assert(SS == getCurFunction()->SwitchStack.back().getPointer() &&
1252 "switch stack missing push/pop!");
1254 getCurFunction()->SwitchStack.pop_back();
1257 SS->
setBody(BodyStmt, SwitchLoc);
1271 const Expr *CondExprBeforePromotion = CondExpr;
1277 bool HasDependentValue
1279 unsigned CondWidth = HasDependentValue ? 0 : Context.
getIntWidth(CondType);
1286 unsigned CondWidthBeforePromotion
1287 = HasDependentValue ? 0 : Context.
getIntWidth(CondTypeBeforePromotion);
1288 bool CondIsSignedBeforePromotion
1295 CaseValsTy CaseVals;
1298 typedef std::vector<std::pair<llvm::APSInt, CaseStmt*> > CaseRangesTy;
1299 CaseRangesTy CaseRanges;
1303 bool CaseListIsErroneous =
false;
1311 if (
DefaultStmt *DS = dyn_cast<DefaultStmt>(SC)) {
1312 if (TheDefaultStmt) {
1313 Diag(DS->getDefaultLoc(), diag::err_multiple_default_labels_defined);
1320 CaseListIsErroneous =
true;
1322 TheDefaultStmt = DS;
1330 HasDependentValue =
true;
1336 const Expr *LoBeforePromotion = Lo;
1343 CondIsSignedBeforePromotion);
1355 HasDependentValue =
true;
1358 CaseRanges.push_back(std::make_pair(LoVal, CS));
1360 CaseVals.push_back(std::make_pair(LoVal, CS));
1364 if (!HasDependentValue) {
1368 bool HasConstantCond =
false;
1369 if (!TheDefaultStmt) {
1373 if (Result.Val.isInt())
1374 ConstantCondValue = Result.Val.getInt();
1375 assert(!HasConstantCond ||
1376 (ConstantCondValue.getBitWidth() == CondWidth &&
1377 ConstantCondValue.isSigned() == CondIsSigned));
1378 Diag(SwitchLoc, diag::warn_switch_default);
1380 bool ShouldCheckConstantCond = HasConstantCond;
1385 if (!CaseVals.empty()) {
1386 for (
unsigned i = 0, e = CaseVals.size(); i != e; ++i) {
1387 if (ShouldCheckConstantCond &&
1388 CaseVals[i].first == ConstantCondValue)
1389 ShouldCheckConstantCond =
false;
1391 if (i != 0 && CaseVals[i].first == CaseVals[i-1].first) {
1394 StringRef PrevString, CurrString;
1397 if (
DeclRefExpr *DeclRef = dyn_cast<DeclRefExpr>(PrevCase)) {
1398 PrevString = DeclRef->getDecl()->getName();
1400 if (
DeclRefExpr *DeclRef = dyn_cast<DeclRefExpr>(CurrCase)) {
1401 CurrString = DeclRef->getDecl()->getName();
1404 CaseVals[i-1].first.toString(CaseValStr);
1406 if (PrevString == CurrString)
1407 Diag(CaseVals[i].second->getLHS()->getBeginLoc(),
1408 diag::err_duplicate_case)
1409 << (PrevString.empty() ? CaseValStr.str() : PrevString);
1411 Diag(CaseVals[i].second->getLHS()->getBeginLoc(),
1412 diag::err_duplicate_case_differing_expr)
1413 << (PrevString.empty() ? CaseValStr.str() : PrevString)
1414 << (CurrString.empty() ? CaseValStr.str() : CurrString)
1417 Diag(CaseVals[i - 1].second->getLHS()->getBeginLoc(),
1418 diag::note_duplicate_case_prev);
1421 CaseListIsErroneous =
true;
1428 if (!CaseRanges.empty()) {
1431 llvm::stable_sort(CaseRanges);
1434 std::vector<llvm::APSInt> HiVals;
1435 for (
unsigned i = 0, e = CaseRanges.size(); i != e; ++i) {
1437 CaseStmt *CR = CaseRanges[i].second;
1440 const Expr *HiBeforePromotion = Hi;
1447 CondWidthBeforePromotion, CondIsSignedBeforePromotion);
1453 if (LoVal > HiVal) {
1456 CaseRanges.erase(CaseRanges.begin()+i);
1462 if (ShouldCheckConstantCond &&
1463 LoVal <= ConstantCondValue &&
1464 ConstantCondValue <= HiVal)
1465 ShouldCheckConstantCond =
false;
1467 HiVals.push_back(HiVal);
1473 for (
unsigned i = 0, e = CaseRanges.size(); i != e; ++i) {
1476 CaseStmt *CR = CaseRanges[i].second;
1485 CaseValsTy::iterator I =
1486 llvm::lower_bound(CaseVals, CRLo, CaseCompareFunctor());
1487 if (I != CaseVals.end() && I->first < CRHi) {
1488 OverlapVal = I->first;
1489 OverlapStmt = I->second;
1493 I = std::upper_bound(I, CaseVals.end(), CRHi, CaseCompareFunctor());
1494 if (I != CaseVals.begin() && (I-1)->first >= CRLo) {
1495 OverlapVal = (I-1)->first;
1496 OverlapStmt = (I-1)->second;
1501 if (i && CRLo <= HiVals[i-1]) {
1502 OverlapVal = HiVals[i-1];
1503 OverlapStmt = CaseRanges[i-1].second;
1511 diag::note_duplicate_case_prev);
1514 CaseListIsErroneous =
true;
1520 if (!CaseListIsErroneous && !CaseListIsIncomplete &&
1521 ShouldCheckConstantCond) {
1524 Diag(CondExpr->
getExprLoc(), diag::warn_missing_case_for_condition)
1537 if (!CaseListIsErroneous && !CaseListIsIncomplete && !HasConstantCond &&
1548 EnumVals.push_back(std::make_pair(Val, EDI));
1551 auto EI = EnumVals.begin(), EIEnd =
1552 std::unique(EnumVals.begin(), EnumVals.end(),
EqEnumVals);
1555 for (CaseValsTy::const_iterator CI = CaseVals.begin();
1556 CI != CaseVals.end(); CI++) {
1557 Expr *CaseExpr = CI->second->getLHS();
1561 << CondTypeBeforePromotion;
1565 EI = EnumVals.begin();
1566 for (CaseRangesTy::const_iterator RI = CaseRanges.begin();
1567 RI != CaseRanges.end(); RI++) {
1568 Expr *CaseExpr = RI->second->getLHS();
1572 << CondTypeBeforePromotion;
1575 RI->second->getRHS()->EvaluateKnownConstInt(Context);
1578 CaseExpr = RI->second->getRHS();
1582 << CondTypeBeforePromotion;
1586 auto CI = CaseVals.begin();
1587 auto RI = CaseRanges.begin();
1588 bool hasCasesNotInSwitch =
false;
1592 for (EI = EnumVals.begin(); EI != EIEnd; EI++) {
1594 switch (EI->second->getAvailability()) {
1607 if (EI->second->hasAttr<UnusedAttr>())
1611 while (CI != CaseVals.end() && CI->first < EI->first)
1614 if (CI != CaseVals.end() && CI->first == EI->first)
1618 for (; RI != CaseRanges.end(); RI++) {
1620 RI->second->getRHS()->EvaluateKnownConstInt(Context);
1622 if (EI->first <= Hi)
1626 if (RI == CaseRanges.end() || EI->first < RI->first) {
1627 hasCasesNotInSwitch =
true;
1628 UnhandledNames.push_back(EI->second->getDeclName());
1632 if (TheDefaultStmt && UnhandledNames.empty() && ED->
isClosedNonFlag())
1636 if (!UnhandledNames.empty()) {
1638 ? diag::warn_def_missing_case
1639 : diag::warn_missing_case)
1642 for (
size_t I = 0, E =
std::min(UnhandledNames.size(), (
size_t)3);
1644 DB << UnhandledNames[I];
1647 if (!hasCasesNotInSwitch)
1653 DiagnoseEmptyStmtBody(CondExpr->
getEndLoc(), BodyStmt,
1654 diag::warn_empty_switch_body);
1658 if (CaseListIsErroneous)
1667 if (Diags.isIgnored(diag::warn_not_in_enum_assignment, SrcExpr->
getExprLoc()))
1681 const EnumDecl *ED = ET->getDecl();
1686 if (ED->
hasAttr<FlagEnumAttr>()) {
1687 if (!IsValueInFlagEnum(ED, RhsVal,
true))
1700 EnumVals.push_back(std::make_pair(Val, EDI));
1702 if (EnumVals.empty())
1705 EnumValsTy::iterator EIend =
1706 std::unique(EnumVals.begin(), EnumVals.end(),
EqEnumVals);
1709 EnumValsTy::const_iterator EI = EnumVals.begin();
1710 while (EI != EIend && EI->first < RhsVal)
1712 if (EI == EIend || EI->first != RhsVal) {
1727 auto CondVal = Cond.
get();
1728 CheckBreakContinueBinding(CondVal.second);
1730 if (CondVal.second &&
1731 !Diags.isIgnored(diag::warn_comma_operator, CondVal.second->getExprLoc()))
1732 CommaVisitor(*this).Visit(CondVal.second);
1734 if (isa<NullStmt>(Body))
1735 getCurCompoundScope().setHasEmptyLoopBodies();
1738 WhileLoc, LParenLoc, RParenLoc);
1745 assert(Cond &&
"ActOnDoStmt(): missing expression");
1747 CheckBreakContinueBinding(Cond);
1748 ExprResult CondResult = CheckBooleanCondition(DoLoc, Cond);
1751 Cond = CondResult.
get();
1753 CondResult = ActOnFinishFullExpr(Cond, DoLoc,
false);
1756 Cond = CondResult.
get();
1759 if (Cond && !getLangOpts().
C99 && !getLangOpts().
CPlusPlus &&
1760 !Diags.isIgnored(diag::warn_comma_operator, Cond->
getExprLoc()))
1761 CommaVisitor(*this).Visit(Cond);
1763 return new (Context)
DoStmt(Body, Cond, DoLoc, WhileLoc, CondRParen);
1774 DeclSetVector &Decls;
1780 DeclExtractor(
Sema &S, DeclSetVector &Decls,
1782 Inherited(S.Context),
1787 bool isSimple() {
return Simple; }
1796 void VisitStmt(
Stmt *S) { Simple =
false; }
1855 DeclSetVector &Decls;
1861 DeclMatcher(
Sema &S, DeclSetVector &Decls,
Stmt *Statement) :
1862 Inherited(S.Context), Decls(Decls), FoundDecl(
false) {
1863 if (!Statement)
return;
1887 void CheckLValueToRValueCast(
Expr *E) {
1890 if (isa<DeclRefExpr>(E)) {
1895 Visit(CO->getCond());
1896 CheckLValueToRValueCast(CO->getTrueExpr());
1897 CheckLValueToRValueCast(CO->getFalseExpr());
1902 dyn_cast<BinaryConditionalOperator>(E)) {
1903 CheckLValueToRValueCast(BCO->getOpaqueValue()->getSourceExpr());
1904 CheckLValueToRValueCast(BCO->getFalseExpr());
1913 if (Decls.count(VD))
1921 if (
auto *OVE = dyn_cast<OpaqueValueExpr>(S))
1923 Visit(OVE->getSourceExpr());
1929 bool FoundDeclInUse() {
return FoundDecl; }
1933 void CheckForLoopConditionalStatement(
Sema &S,
Expr *Second,
1936 if (!Second)
return;
1943 DeclSetVector Decls;
1945 DeclExtractor DE(S, Decls, Ranges);
1949 if (!DE.isSimple())
return;
1952 if (Decls.size() == 0)
return;
1955 for (
auto *VD : Decls)
1959 if (DeclMatcher(S, Decls, Second).FoundDeclInUse() ||
1960 DeclMatcher(S, Decls, Third).FoundDeclInUse() ||
1961 DeclMatcher(S, Decls, Body).FoundDeclInUse())
1965 if (Decls.size() > 4) {
1969 for (
auto *VD : Decls)
1973 for (
auto Range : Ranges)
1976 S.
Diag(Ranges.begin()->getBegin(), PDiag);
1981 bool ProcessIterationStmt(
Sema &S,
Stmt* Statement,
bool &Increment,
1983 if (
auto Cleanups = dyn_cast<ExprWithCleanups>(Statement))
1984 if (!Cleanups->cleanupsHaveSideEffects())
1987 if (
UnaryOperator *UO = dyn_cast<UnaryOperator>(Statement)) {
1988 switch (UO->getOpcode()) {
1989 default:
return false;
1999 DRE = dyn_cast<DeclRefExpr>(UO->getSubExpr());
2007 default:
return false;
2015 DRE = dyn_cast<DeclRefExpr>(
Call->getArg(0));
2027 bool InSwitch =
false;
2030 BreakContinueFinder(
Sema &S,
const Stmt* Body) :
2031 Inherited(S.Context) {
2041 void VisitBreakStmt(
const BreakStmt* E) {
2047 if (
const Stmt *Init = S->getInit())
2049 if (
const Stmt *CondVar = S->getConditionVariableDeclStmt())
2051 if (
const Stmt *Cond = S->getCond())
2056 if (
const Stmt *Body = S->getBody())
2061 void VisitForStmt(
const ForStmt *S) {
2064 if (
const Stmt *Init = S->getInit())
2068 void VisitWhileStmt(
const WhileStmt *) {
2073 void VisitDoStmt(
const DoStmt *) {
2081 if (
const Stmt *Init = S->getInit())
2083 if (
const Stmt *Range = S->getRangeStmt())
2085 if (
const Stmt *
Begin = S->getBeginStmt())
2087 if (
const Stmt *
End = S->getEndStmt())
2094 if (
const Stmt *Element = S->getElement())
2096 if (
const Stmt *Collection = S->getCollection())
2100 bool ContinueFound() {
return ContinueLoc.
isValid(); }
2101 bool BreakFound() {
return BreakLoc.
isValid(); }
2112 void CheckForRedundantIteration(
Sema &S,
Expr *Third,
Stmt *Body) {
2114 if (!Body || !Third)
return;
2124 if (!LastStmt)
return;
2126 bool LoopIncrement, LastIncrement;
2129 if (!ProcessIterationStmt(S, Third, LoopIncrement, LoopDRE))
return;
2130 if (!ProcessIterationStmt(S, LastStmt, LastIncrement, LastDRE))
return;
2134 if (LoopIncrement != LastIncrement ||
2137 if (BreakContinueFinder(S, Body).ContinueFound())
return;
2140 << LastDRE->
getDecl() << LastIncrement;
2148 void Sema::CheckBreakContinueBinding(
Expr *E) {
2151 BreakContinueFinder BCFinder(*
this, E);
2153 if (BCFinder.BreakFound() && BreakParent) {
2155 Diag(BCFinder.GetBreakLoc(), diag::warn_break_binds_to_switch);
2157 Diag(BCFinder.GetBreakLoc(), diag::warn_loop_ctrl_binds_to_inner)
2160 }
else if (BCFinder.ContinueFound() && CurScope->getContinueParent()) {
2161 Diag(BCFinder.GetContinueLoc(), diag::warn_loop_ctrl_binds_to_inner)
2178 const Decl *NonVarSeen =
nullptr;
2179 bool VarDeclSeen =
false;
2180 for (
auto *DI : DS->decls()) {
2181 if (
VarDecl *VD = dyn_cast<VarDecl>(DI)) {
2184 Diag(DI->getLocation(), diag::err_non_local_variable_decl_in_for);
2185 DI->setInvalidDecl();
2187 }
else if (!NonVarSeen) {
2197 if (NonVarSeen && !VarDeclSeen)
2202 CheckBreakContinueBinding(Second.
get().second);
2203 CheckBreakContinueBinding(third.
get());
2205 if (!Second.
get().first)
2206 CheckForLoopConditionalStatement(*
this, Second.
get().second, third.
get(),
2208 CheckForRedundantIteration(*
this, third.
get(), Body);
2210 if (Second.
get().second &&
2211 !Diags.isIgnored(diag::warn_comma_operator,
2212 Second.
get().second->getExprLoc()))
2213 CommaVisitor(*this).Visit(Second.
get().second);
2216 if (isa<NullStmt>(Body))
2217 getCurCompoundScope().setHasEmptyLoopBodies();
2219 return new (Context)
2221 Body, ForLoc, LParenLoc, RParenLoc);
2245 if (
Decl->getType()->isUndeducedType()) {
2257 if (!isa<InitListExpr>(Init) && Init->getType()->isVoidType()) {
2258 SemaRef.
Diag(
Loc, DiagID) << Init->getType();
2262 Decl->getTypeSourceInfo()->getTypeLoc(), Init, InitType, Info);
2265 SemaRef.
Diag(
Loc, DiagID) << Init->getType();
2272 Decl->setType(InitType);
2290 enum BeginEndFunction {
2299 void NoteForRangeBeginEndFunction(
Sema &SemaRef,
Expr *E,
2300 BeginEndFunction BEF) {
2301 CallExpr *CE = dyn_cast<CallExpr>(E);
2309 std::string Description;
2310 bool IsTemplate =
false;
2317 SemaRef.
Diag(
Loc, diag::note_for_range_begin_end)
2318 << BEF << IsTemplate << Description << E->
getType();
2370 return Diag(InitStmt->
getBeginLoc(), diag::err_objc_for_range_init_stmt)
2372 return ObjC().ActOnObjCForCollectionStmt(ForLoc,
First,
Range, RParenLoc);
2376 assert(DS &&
"first part of for range not a decl stmt");
2387 DiagnoseUnexpandedParameterPack(
Range, UPPC_Expression)) {
2388 ActOnInitializerError(LoopVar);
2395 if (!ActOnCoroutineBodyStart(S, CoawaitLoc,
"co_await")) {
2396 ActOnInitializerError(LoopVar);
2403 const auto DepthStr = std::to_string(S->getDepth() / 2);
2405 VarDecl *RangeVar = BuildForRangeVarDecl(*
this, RangeLoc,
2407 std::string(
"__range") + DepthStr);
2409 diag::err_for_range_deduction_failure)) {
2410 ActOnInitializerError(LoopVar);
2417 StmtResult RangeDecl = ActOnDeclStmt(RangeGroup, RangeLoc, RangeLoc);
2419 ActOnInitializerError(LoopVar);
2424 ForLoc, CoawaitLoc, InitStmt, ColonLoc, RangeDecl.
get(),
2426 nullptr,
nullptr, DS, RParenLoc,
Kind,
2427 LifetimeExtendTemps);
2429 ActOnInitializerError(LoopVar);
2450 ExprResult *EndExpr, BeginEndFunction *BEF) {
2460 auto BuildBegin = [&] {
2464 BeginMemberLookup, CandidateSet,
2465 BeginRange, BeginExpr);
2470 << ColonLoc << BEF_begin << BeginRange->
getType();
2483 diag::err_for_range_iter_deduction_failure)) {
2484 NoteForRangeBeginEndFunction(SemaRef, BeginExpr->
get(), *BEF);
2490 auto BuildEnd = [&] {
2494 EndMemberLookup, CandidateSet,
2499 << ColonLoc << BEF_end << EndRange->
getType();
2503 diag::err_for_range_iter_deduction_failure)) {
2504 NoteForRangeBeginEndFunction(SemaRef, EndExpr->
get(), *BEF);
2524 if (BeginMemberLookup.
empty() != EndMemberLookup.
empty()) {
2529 auto BuildNonmember = [&](
2539 switch (BuildFound()) {
2546 SemaRef.
PDiag(diag::err_for_range_invalid)
2547 << BeginRange->
getType() << BEFFound),
2554 diag::note_for_range_member_begin_end_ignored)
2555 << BeginRange->
getType() << BEFFound;
2559 llvm_unreachable(
"unexpected ForRangeStatus");
2561 if (BeginMemberLookup.
empty())
2562 return BuildNonmember(BEF_end, EndMemberLookup, BuildEnd, BuildBegin);
2563 return BuildNonmember(BEF_begin, BeginMemberLookup, BuildBegin, BuildEnd);
2600 S, ForLoc, CoawaitLoc, InitStmt, LoopVarDecl, ColonLoc,
2609 SemaRef.
Diag(RangeLoc, diag::err_for_range_dereference)
2612 S, ForLoc, CoawaitLoc, InitStmt, LoopVarDecl, ColonLoc,
2632 Scope *S = getCurScope();
2634 DeclStmt *RangeDS = cast<DeclStmt>(RangeDecl);
2638 DeclStmt *LoopVarDS = cast<DeclStmt>(LoopVarDecl);
2652 if (
auto *DD = dyn_cast<DecompositionDecl>(LoopVar))
2653 for (
auto *Binding : DD->bindings())
2657 }
else if (!BeginDeclStmt.
get()) {
2662 ExprResult BeginRangeRef = BuildDeclRefExpr(RangeVar, RangeVarNonRefType,
2667 ExprResult EndRangeRef = BuildDeclRefExpr(RangeVar, RangeVarNonRefType,
2678 if (RequireCompleteType(RangeLoc, RangeType,
2679 diag::err_for_range_incomplete_type))
2683 if (getLangOpts().
CPlusPlus23 && !LifetimeExtendTemps.empty()) {
2686 for (
auto *MTE : LifetimeExtendTemps)
2692 const auto DepthStr = std::to_string(S->getDepth() / 2);
2694 std::string(
"__begin") + DepthStr);
2696 std::string(
"__end") + DepthStr);
2707 BeginExpr = BeginRangeRef;
2709 BeginExpr = ActOnCoawaitExpr(S, ColonLoc, BeginExpr.
get());
2714 diag::err_for_range_iter_deduction_failure)) {
2715 NoteForRangeBeginEndFunction(*
this, BeginExpr.
get(), BEF_begin);
2725 dyn_cast<VariableArrayType>(UnqAT)) {
2748 ExprResult SizeOfVLAExprR = ActOnUnaryExprOrTypeTraitExpr(
2752 VAT->desugar(), RangeLoc))
2758 ExprResult SizeOfEachElementExprR = ActOnUnaryExprOrTypeTraitExpr(
2761 CreateParsedType(VAT->desugar(),
2763 VAT->getElementType(), RangeLoc))
2771 SizeOfVLAExprR.
get(), SizeOfEachElementExprR.
get());
2778 llvm_unreachable(
"Unexpected array type in for-range");
2782 EndExpr = ActOnBinOp(S, ColonLoc, tok::plus, EndRangeRef.
get(),
2787 diag::err_for_range_iter_deduction_failure)) {
2788 NoteForRangeBeginEndFunction(*
this, EndExpr.
get(), BEF_end);
2794 BeginEndFunction BEFFailure;
2796 *
this, BeginRangeRef.
get(), EndRangeRef.
get(), RangeType, BeginVar,
2797 EndVar, ColonLoc, CoawaitLoc, &CandidateSet, &BeginExpr, &EndExpr,
2800 if (
Kind == BFRK_Build && RangeStatus == FRS_NoViableFunction &&
2801 BEFFailure == BEF_begin) {
2806 QualType ArrayTy = PVD->getOriginalType();
2807 QualType PointerTy = PVD->getType();
2809 Diag(
Range->getBeginLoc(), diag::err_range_on_array_parameter)
2810 << RangeLoc << PVD << ArrayTy << PointerTy;
2811 Diag(PVD->getLocation(), diag::note_declared_at);
2820 CoawaitLoc, InitStmt,
2821 LoopVarDecl, ColonLoc,
2829 if (RangeStatus == FRS_NoViableFunction) {
2833 PDiag(diag::err_for_range_invalid)
2834 << RangeLoc <<
Range->getType()
2839 if (RangeStatus != FRS_Success)
2844 "invalid range expression in for loop");
2851 ? diag::warn_for_range_begin_end_types_differ
2852 : diag::ext_for_range_begin_end_types_differ)
2853 << BeginType << EndType;
2854 NoteForRangeBeginEndFunction(*
this, BeginExpr.
get(), BEF_begin);
2855 NoteForRangeBeginEndFunction(*
this, EndExpr.
get(), BEF_end);
2859 ActOnDeclStmt(ConvertDeclToDeclGroup(BeginVar), ColonLoc, ColonLoc);
2861 ActOnDeclStmt(ConvertDeclToDeclGroup(EndVar), ColonLoc, ColonLoc);
2864 ExprResult BeginRef = BuildDeclRefExpr(BeginVar, BeginRefNonRefType,
2869 ExprResult EndRef = BuildDeclRefExpr(EndVar, EndType.getNonReferenceType(),
2875 NotEqExpr = ActOnBinOp(S, ColonLoc, tok::exclaimequal,
2876 BeginRef.
get(), EndRef.
get());
2878 NotEqExpr = CheckBooleanCondition(ColonLoc, NotEqExpr.
get());
2881 ActOnFinishFullExpr(NotEqExpr.
get(),
false);
2883 Diag(RangeLoc, diag::note_for_range_invalid_iterator)
2884 << RangeLoc << 0 << BeginRangeRef.
get()->
getType();
2885 NoteForRangeBeginEndFunction(*
this, BeginExpr.
get(), BEF_begin);
2887 NoteForRangeBeginEndFunction(*
this, EndExpr.
get(), BEF_end);
2892 BeginRef = BuildDeclRefExpr(BeginVar, BeginRefNonRefType,
2897 IncrExpr = ActOnUnaryOp(S, ColonLoc, tok::plusplus, BeginRef.
get());
2898 if (!IncrExpr.isInvalid() && CoawaitLoc.
isValid())
2902 IncrExpr = ActOnCoawaitExpr(S, CoawaitLoc, IncrExpr.get());
2903 if (!IncrExpr.isInvalid())
2904 IncrExpr = ActOnFinishFullExpr(IncrExpr.get(),
false);
2905 if (IncrExpr.isInvalid()) {
2906 Diag(RangeLoc, diag::note_for_range_invalid_iterator)
2907 << RangeLoc << 2 << BeginRangeRef.
get()->
getType() ;
2908 NoteForRangeBeginEndFunction(*
this, BeginExpr.
get(), BEF_begin);
2913 BeginRef = BuildDeclRefExpr(BeginVar, BeginRefNonRefType,
2918 ExprResult DerefExpr = ActOnUnaryOp(S, ColonLoc, tok::star, BeginRef.
get());
2920 Diag(RangeLoc, diag::note_for_range_invalid_iterator)
2921 << RangeLoc << 1 << BeginRangeRef.
get()->
getType();
2922 NoteForRangeBeginEndFunction(*
this, BeginExpr.
get(), BEF_begin);
2929 AddInitializerToDecl(LoopVar, DerefExpr.
get(),
false);
2932 NoteForRangeBeginEndFunction(*
this, BeginExpr.
get(), BEF_begin);
2938 if (
Kind == BFRK_Check)
2943 if (getLangOpts().OpenMP >= 50 && BeginDeclStmt.
isUsable())
2944 OpenMP().ActOnOpenMPLoopInitialization(ForLoc, BeginDeclStmt.
get());
2947 InitStmt, RangeDS, cast_or_null<DeclStmt>(BeginDeclStmt.
get()),
2948 cast_or_null<DeclStmt>(EndDeclStmt.
get()), NotEqExpr.
get(),
2949 IncrExpr.get(), LoopVarDS,
nullptr, ForLoc, CoawaitLoc,
2950 ColonLoc, RParenLoc);
2969 if (
auto Cleanups = dyn_cast<ExprWithCleanups>(InitExpr))
2970 if (!Cleanups->cleanupsHaveSideEffects())
2971 InitExpr = Cleanups->getSubExpr();
2974 dyn_cast<MaterializeTemporaryExpr>(InitExpr);
2984 while (!isa<CXXOperatorCallExpr>(E) && !isa<UnaryOperator>(E)) {
2988 const MemberExpr *ME = cast<MemberExpr>(Call->getCallee());
2998 if (isa<UnaryOperator>(E)) {
3005 ReferenceReturnType = ReturnType;
3008 if (!ReferenceReturnType.
isNull()) {
3013 diag::warn_for_range_const_ref_binds_temp_built_from_ref)
3014 << VD << VariableType << ReferenceReturnType;
3027 SemaRef.
Diag(VD->
getLocation(), diag::warn_for_range_ref_binds_ret_temp)
3028 << VD << RangeInitType;
3041 return RD->hasAttr<TrivialABIAttr>();
3058 if (!CE->getConstructor()->isCopyConstructor())
3060 }
else if (
const CastExpr *CE = dyn_cast<CastExpr>(InitExpr)) {
3061 if (CE->getCastKind() != CK_LValueToRValue)
3079 << VD << VariableType;
3100 diag::warn_for_range_const_ref_binds_temp_built_from_ref,
3127 ForStmt->getRangeInit()->getType());
3141 if (isa<ObjCForCollectionStmt>(S))
3142 return ObjC().FinishObjCForCollectionStmt(S, B);
3148 diag::warn_empty_range_based_for_body);
3158 setFunctionHasBranchIntoScope();
3162 if (getCurScope()->isInOpenACCComputeConstructScope())
3163 setFunctionHasBranchProtectedScope();
3166 return new (Context)
GotoStmt(TheDecl, GotoLoc, LabelLoc);
3178 CheckSingleAssignmentConstraints(DestTy, ExprRes);
3182 if (DiagnoseAssignmentResult(ConvTy, StarLoc, DestTy, ETy, E, AA_Passing))
3186 ExprResult ExprRes = ActOnFinishFullExpr(E,
false);
3191 setFunctionHasIndirectGoto();
3195 if (getCurScope()->isInOpenACCComputeConstructScope())
3196 setFunctionHasBranchProtectedScope();
3202 const Scope &DestScope) {
3205 S.
Diag(
Loc, diag::warn_jump_out_of_seh_finally);
3214 return StmtError(
Diag(ContinueLoc, diag::err_continue_not_in_loop));
3216 if (S->isConditionVarScope()) {
3220 return StmtError(
Diag(ContinueLoc, diag::err_continue_from_cond_var_init));
3226 if (S->isOpenACCComputeConstructScope())
3228 Diag(ContinueLoc, diag::err_acc_branch_in_out_compute_construct)
3241 return StmtError(
Diag(BreakLoc, diag::err_break_not_in_loop_or_switch));
3243 if (S->isOpenMPLoopScope())
3244 return StmtError(
Diag(BreakLoc, diag::err_omp_loop_cannot_use_stmt)
3254 if (S->isOpenACCComputeConstructScope() ||
3255 (S->isLoopScope() && S->getParent() &&
3256 S->getParent()->isOpenACCComputeConstructScope()))
3258 Diag(BreakLoc, diag::err_acc_branch_in_out_compute_construct)
3263 return new (Context)
BreakStmt(BreakLoc);
3286 const auto *DR = dyn_cast<DeclRefExpr>(E->
IgnoreParens());
3287 if (!DR || DR->refersToEnclosingVariableOrCapture())
3289 const auto *VD = dyn_cast<VarDecl>(DR->getDecl());
3296 (Mode == SimplerImplicitMoveMode::ForceOn ||
3297 (Mode != SimplerImplicitMoveMode::ForceOff &&
3315 NamedReturnInfo Info{VD, NamedReturnInfo::MoveEligibleAndCopyElidable};
3320 if (VD->
getKind() == Decl::ParmVar)
3321 Info.S = NamedReturnInfo::MoveEligible;
3322 else if (VD->
getKind() != Decl::Var)
3327 Info.S = NamedReturnInfo::MoveEligible;
3335 if (VD->
hasAttr<BlocksAttr>())
3352 Info.S = NamedReturnInfo::MoveEligible;
3361 Info.S = NamedReturnInfo::MoveEligible;
3380 auto invalidNRVO = [&] {
3389 if ((ReturnType->
getTypeClass() == Type::TypeClass::Auto &&
3392 return invalidNRVO();
3398 return invalidNRVO();
3405 Info.
S = NamedReturnInfo::MoveEligible;
3418 const auto *Step = llvm::find_if(
Seq.steps(), [](
const auto &Step) {
3419 return Step.Kind == InitializationSequence::SK_ConstructorInitialization ||
3420 Step.Kind == InitializationSequence::SK_UserConversion;
3422 if (Step !=
Seq.step_end()) {
3423 const auto *FD = Step->Function.Function;
3424 if (isa<CXXConstructorDecl>(FD)
3426 : cast<CXXMethodDecl>(FD)->getRefQualifier() ==
RQ_None)
3440 bool SupressSimplerImplicitMoves) {
3442 (!getLangOpts().
CPlusPlus23 || SupressSimplerImplicitMoves) &&
3446 Expr *InitExpr = &AsRvalue;
3448 Value->getBeginLoc());
3450 auto Res =
Seq.getFailedOverloadResult();
3484 bool SupressSimplerImplicitMoves) {
3492 bool HasDeducedReturnType =
3495 if (ExprEvalContexts.back().isDiscardedStatementContext() &&
3499 ActOnFinishFullExpr(RetValExp, ReturnLoc,
false);
3502 RetValExp = ER.
get();
3508 if (HasDeducedReturnType) {
3521 assert(AT &&
"lost auto type from lambda return type");
3522 if (DeduceFunctionTypeFromReturnExpr(FD, ReturnLoc, RetValExp, AT)) {
3533 if (RetValExp && !isa<InitListExpr>(RetValExp)) {
3534 ExprResult Result = DefaultFunctionArrayLvalueConversion(RetValExp);
3535 if (Result.isInvalid())
3537 RetValExp = Result.get();
3543 if (!CurContext->isDependentContext())
3552 Diag(ReturnLoc, diag::err_lambda_return_init_list)
3556 FnRetType = Context.
VoidTy;
3564 const VarDecl *NRVOCandidate = getCopyElisionCandidate(NRInfo, FnRetType);
3566 if (
auto *CurBlock = dyn_cast<BlockScopeInfo>(CurCap)) {
3568 Diag(ReturnLoc, diag::err_noreturn_block_has_return_expr);
3571 }
else if (
auto *CurRegion = dyn_cast<CapturedRegionScopeInfo>(CurCap)) {
3572 Diag(ReturnLoc, diag::err_return_in_captured_stmt) << CurRegion->getRegionName();
3575 assert(CurLambda &&
"unknown kind of captured scope");
3579 Diag(ReturnLoc, diag::err_noreturn_lambda_has_return_expr);
3591 if (RetValExp && !isa<InitListExpr>(RetValExp) &&
3597 Diag(ReturnLoc, diag::ext_return_has_void_expr) <<
"literal" << 2;
3599 Diag(ReturnLoc, diag::err_return_block_has_expr);
3600 RetValExp =
nullptr;
3603 }
else if (!RetValExp) {
3604 return StmtError(
Diag(ReturnLoc, diag::err_block_return_missing_expr));
3616 ExprResult Res = PerformMoveOrCopyInitialization(
3617 Entity, NRInfo, RetValExp, SupressSimplerImplicitMoves);
3622 RetValExp = Res.
get();
3623 CheckReturnValExpr(RetValExp, FnRetType, ReturnLoc);
3628 ActOnFinishFullExpr(RetValExp, ReturnLoc,
false);
3631 RetValExp = ER.
get();
3640 FunctionScopes.back()->Returns.push_back(Result);
3642 if (FunctionScopes.back()->FirstReturnLoc.isInvalid())
3643 FunctionScopes.back()->FirstReturnLoc = ReturnLoc;
3645 if (
auto *CurBlock = dyn_cast<BlockScopeInfo>(CurCap);
3648 CurBlock->TheDecl->setInvalidDecl();
3666 class LocalTypedefNameReferencer
3669 LocalTypedefNameReferencer(
Sema &S) : S(S) {}
3674 bool LocalTypedefNameReferencer::VisitRecordType(
const RecordType *RT) {
3675 auto *R = dyn_cast<CXXRecordDecl>(RT->
getDecl());
3676 if (!R || !R->isLocalClass() || !R->isLocalClass()->isExternallyVisible() ||
3677 R->isDependentType())
3679 for (
auto *TmpD : R->decls())
3680 if (
auto *
T = dyn_cast<TypedefNameDecl>(TmpD))
3681 if (
T->getAccess() !=
AS_private || R->hasFriends())
3705 if (RetExpr && isa<InitListExpr>(RetExpr)) {
3709 getCurLambda() ? diag::err_lambda_return_init_list
3710 : diag::err_auto_fn_return_init_list)
3720 assert(AT->
isDeduced() &&
"should have deduced to dependent type");
3724 TypeLoc OrigResultType = getReturnTypeLoc(FD);
3734 Diag(ReturnLoc, diag::err_auto_fn_return_void_but_not_auto)
3750 if (FindResult.Expression)
3751 TemplateSpecLoc = FindResult.Expression->getNameLoc();
3755 OrigResultType, RetExpr, Deduced, Info,
false,
3771 Diag(ReturnLoc, diag::err_typecheck_missing_return_type_incompatible)
3774 Diag(ReturnLoc, diag::err_auto_fn_different_deductions)
3789 LocalTypedefNameReferencer(*this).TraverseType(RetExpr->
getType());
3792 if (getLangOpts().
CUDA && FD->
hasAttr<CUDAGlobalAttr>() &&
3811 ExprResult RetVal = CorrectDelayedTyposInExpr(
3812 RetValExp,
nullptr,
true);
3816 if (getCurScope()->isInOpenACCComputeConstructScope())
3818 Diag(ReturnLoc, diag::err_acc_branch_in_out_compute_construct)
3822 BuildReturnStmt(ReturnLoc, RetVal.
get(),
true);
3823 if (R.
isInvalid() || ExprEvalContexts.back().isDiscardedStatementContext())
3827 const_cast<VarDecl *
>(cast<ReturnStmt>(R.
get())->getNRVOCandidate());
3851 bool AllowRecovery) {
3853 if (RetValExp && DiagnoseUnexpandedParameterPack(RetValExp))
3859 bool SupressSimplerImplicitMoves =
3862 RetValExp, SupressSimplerImplicitMoves ? SimplerImplicitMoveMode::ForceOff
3863 : SimplerImplicitMoveMode::Normal);
3865 if (isa<CapturingScopeInfo>(getCurFunction()))
3866 return ActOnCapScopeReturnStmt(ReturnLoc, RetValExp, NRInfo,
3867 SupressSimplerImplicitMoves);
3871 const AttrVec *Attrs =
nullptr;
3872 bool isObjCMethod =
false;
3879 Diag(ReturnLoc, diag::warn_noreturn_function_has_return_expr) << FD;
3880 if (FD->
isMain() && RetValExp)
3881 if (isa<CXXBoolLiteralExpr>(RetValExp))
3882 Diag(ReturnLoc, diag::warn_main_returns_bool_literal)
3884 if (FD->
hasAttr<CmseNSEntryAttr>() && RetValExp) {
3891 FnRetType = MD->getReturnType();
3892 isObjCMethod =
true;
3894 Attrs = &MD->getAttrs();
3895 if (MD->hasRelatedResultType() && MD->getClassInterface()) {
3906 const auto *ATy = dyn_cast<ArrayType>(RetValExp->
getType());
3907 if (ATy && ATy->getElementType().isWebAssemblyReferenceType()) {
3908 Diag(ReturnLoc, diag::err_wasm_table_art) << 1;
3915 if (ExprEvalContexts.back().isDiscardedStatementContext() &&
3919 ActOnFinishFullExpr(RetValExp, ReturnLoc,
false);
3922 RetValExp = ER.
get();
3938 DeduceFunctionTypeFromReturnExpr(FD, ReturnLoc, RetValExp, AT)) {
3946 auto Recovery = CreateRecoveryExpr(
3948 AT->isDeduced() ? FnRetType :
QualType());
3949 if (Recovery.isInvalid())
3951 RetValExp = Recovery.get();
3960 const VarDecl *NRVOCandidate = getCopyElisionCandidate(NRInfo, FnRetType);
3967 if (
auto *ILE = dyn_cast<InitListExpr>(RetValExp)) {
3971 NamedDecl *CurDecl = getCurFunctionOrMethodDecl();
3972 int FunctionKind = 0;
3973 if (isa<ObjCMethodDecl>(CurDecl))
3975 else if (isa<CXXConstructorDecl>(CurDecl))
3977 else if (isa<CXXDestructorDecl>(CurDecl))
3980 Diag(ReturnLoc, diag::err_return_init_list)
3984 RetValExp = AllowRecovery
3985 ? CreateRecoveryExpr(ILE->getLBraceLoc(),
3986 ILE->getRBraceLoc(), ILE->inits())
3991 unsigned D = diag::ext_return_has_expr;
3993 NamedDecl *CurDecl = getCurFunctionOrMethodDecl();
3994 if (isa<CXXConstructorDecl>(CurDecl) ||
3995 isa<CXXDestructorDecl>(CurDecl))
3996 D = diag::err_ctor_dtor_returns_void;
3998 D = diag::ext_return_has_void_expr;
4002 Result = IgnoredValueConversions(Result.get());
4003 if (Result.isInvalid())
4005 RetValExp = Result.get();
4006 RetValExp = ImpCastExprToType(RetValExp,
4007 Context.
VoidTy, CK_ToVoid).get();
4010 if (D == diag::err_ctor_dtor_returns_void) {
4011 NamedDecl *CurDecl = getCurFunctionOrMethodDecl();
4012 Diag(ReturnLoc, D) << CurDecl << isa<CXXDestructorDecl>(CurDecl)
4016 else if (D != diag::ext_return_has_void_expr ||
4018 NamedDecl *CurDecl = getCurFunctionOrMethodDecl();
4020 int FunctionKind = 0;
4021 if (isa<ObjCMethodDecl>(CurDecl))
4023 else if (isa<CXXConstructorDecl>(CurDecl))
4025 else if (isa<CXXDestructorDecl>(CurDecl))
4035 ActOnFinishFullExpr(RetValExp, ReturnLoc,
false);
4038 RetValExp = ER.
get();
4044 }
else if (!RetValExp && !HasDependentReturnType) {
4051 Diag(ReturnLoc, diag::err_constexpr_return_missing_expr)
4057 unsigned DiagID = getLangOpts().C99 ? diag::ext_return_missing_expr
4058 : diag::warn_return_missing_expr;
4061 assert((getCurFunctionDecl() || getCurMethodDecl()) &&
4062 "Not in a FunctionDecl or ObjCMethodDecl?");
4063 bool IsMethod = FD ==
nullptr;
4065 IsMethod ? cast<NamedDecl>(getCurMethodDecl()) : cast<NamedDecl>(FD);
4066 Diag(ReturnLoc, DiagID) << ND << IsMethod;
4072 assert(RetValExp || HasDependentReturnType);
4073 QualType RetType = RelatedRetType.
isNull() ? FnRetType : RelatedRetType;
4085 ExprResult Res = PerformMoveOrCopyInitialization(
4086 Entity, NRInfo, RetValExp, SupressSimplerImplicitMoves);
4088 Res = CreateRecoveryExpr(RetValExp->
getBeginLoc(),
4089 RetValExp->
getEndLoc(), RetValExp, RetType);
4100 if (!RelatedRetType.
isNull()) {
4103 Res = PerformCopyInitialization(Entity, ReturnLoc, RetValExp);
4111 CheckReturnValExpr(RetValExp, FnRetType, ReturnLoc, isObjCMethod, Attrs,
4112 getCurFunctionDecl());
4117 ActOnFinishFullExpr(RetValExp, ReturnLoc,
false);
4120 RetValExp = ER.
get();
4127 if (Result->getNRVOCandidate())
4128 FunctionScopes.back()->Returns.push_back(Result);
4130 if (FunctionScopes.back()->FirstReturnLoc.isInvalid())
4131 FunctionScopes.back()->FirstReturnLoc = ReturnLoc;
4140 Stmt *HandlerBlock) {
4142 return new (Context)
4143 CXXCatchStmt(CatchLoc, cast_or_null<VarDecl>(ExDecl), HandlerBlock);
4147 class CatchHandlerType {
4149 LLVM_PREFERRED_TYPE(
bool)
4150 unsigned IsPointer : 1;
4154 friend struct llvm::DenseMapInfo<CatchHandlerType>;
4155 enum Unique { ForDenseMap };
4156 CatchHandlerType(
QualType QT, Unique) : QT(QT), IsPointer(
false) {}
4174 CatchHandlerType(
QualType QT,
bool IsPointer)
4175 : QT(QT), IsPointer(IsPointer) {}
4177 QualType underlying()
const {
return QT; }
4178 bool isPointer()
const {
return IsPointer; }
4180 friend bool operator==(
const CatchHandlerType &LHS,
4181 const CatchHandlerType &RHS) {
4183 if (LHS.IsPointer != RHS.IsPointer)
4186 return LHS.QT == RHS.QT;
4192 template <>
struct DenseMapInfo<CatchHandlerType> {
4194 return CatchHandlerType(DenseMapInfo<QualType>::getEmptyKey(),
4195 CatchHandlerType::ForDenseMap);
4199 return CatchHandlerType(DenseMapInfo<QualType>::getTombstoneKey(),
4200 CatchHandlerType::ForDenseMap);
4204 return DenseMapInfo<QualType>::getHashValue(
Base.underlying());
4208 const CatchHandlerType &RHS) {
4215 class CatchTypePublicBases {
4216 const llvm::DenseMap<QualType, CXXCatchStmt *> &TypesToCheck;
4223 CatchTypePublicBases(
const llvm::DenseMap<QualType, CXXCatchStmt *> &
T,
4225 : TypesToCheck(
T), FoundHandler(nullptr), TestAgainstType(QT) {}
4227 CXXCatchStmt *getFoundHandler()
const {
return FoundHandler; }
4228 QualType getFoundHandlerType()
const {
return FoundHandlerType; }
4232 QualType Check = S->getType().getCanonicalType();
4233 const auto &M = TypesToCheck;
4234 auto I = M.find(Check);
4246 if (I->second->getCaughtType()->isPointerType() ==
4248 FoundHandler = I->second;
4249 FoundHandlerType = Check;
4264 const bool IsOpenMPGPUTarget =
4265 getLangOpts().OpenMPIsTargetDevice && (
T.isNVPTX() ||
T.isAMDGCN());
4268 if (!IsOpenMPGPUTarget && !getLangOpts().CXXExceptions &&
4269 !getSourceManager().isInSystemHeader(TryLoc) && !getLangOpts().CUDA) {
4271 targetDiag(TryLoc, diag::err_exceptions_disabled) <<
"try";
4276 if (IsOpenMPGPUTarget)
4277 targetDiag(TryLoc, diag::warn_try_not_valid_on_target) <<
T.str();
4280 if (getLangOpts().
CUDA)
4281 CUDA().DiagIfDeviceCode(TryLoc, diag::err_cuda_device_exceptions)
4282 <<
"try" << llvm::to_underlying(
CUDA().CurrentTarget());
4285 if (getLangOpts().SYCLIsDevice)
4286 SYCL().DiagIfDeviceCode(TryLoc, diag::err_sycl_restrict)
4289 if (getCurScope() && getCurScope()->isOpenMPSimdDirectiveScope())
4290 Diag(TryLoc, diag::err_omp_simd_region_cannot_use_stmt) <<
"try";
4296 Diag(TryLoc, diag::err_mixing_cxx_try_seh_try) << 0;
4300 const unsigned NumHandlers = Handlers.size();
4301 assert(!Handlers.empty() &&
4302 "The parser shouldn't call this if there are no handlers.");
4304 llvm::DenseMap<QualType, CXXCatchStmt *> HandledBaseTypes;
4305 llvm::DenseMap<CatchHandlerType, CXXCatchStmt *> HandledTypes;
4306 for (
unsigned i = 0; i < NumHandlers; ++i) {
4313 if (i < NumHandlers - 1)
4327 QualType Underlying = HandlerCHT.underlying();
4329 if (!RD->hasDefinition())
4337 Paths.setOrigin(RD);
4338 CatchTypePublicBases CTPB(HandledBaseTypes,
4340 if (RD->lookupInBases(CTPB, Paths)) {
4342 if (!Paths.isAmbiguous(
4345 diag::warn_exception_caught_by_earlier_handler)
4348 diag::note_previous_exception_handler)
4360 auto R = HandledTypes.insert(
4365 diag::warn_exception_caught_by_earlier_handler)
4368 diag::note_previous_exception_handler)
4381 assert(TryBlock && Handler);
4387 if (!getLangOpts().Borland) {
4398 if (getLangOpts().SYCLIsDevice)
4399 SYCL().DiagIfDeviceCode(TryLoc, diag::err_sycl_restrict)
4413 Diag(TryLoc, diag::err_seh_try_outside_functions);
4417 if (getLangOpts().SYCLIsDevice)
4418 SYCL().DiagIfDeviceCode(TryLoc, diag::err_seh_try_unsupported);
4420 Diag(TryLoc, diag::err_seh_try_unsupported);
4428 assert(FilterExpr &&
Block);
4432 Diag(FilterExpr->
getExprLoc(), diag::err_filter_expression_integral)
4439 CurrentSEHFinally.push_back(CurScope);
4443 CurrentSEHFinally.pop_back();
4448 CurrentSEHFinally.pop_back();
4454 Scope *SEHTryParent = CurScope;
4456 SEHTryParent = SEHTryParent->
getParent();
4471 QualifierLoc, NameInfo,
4472 cast<CompoundStmt>(Nested));
4481 return BuildMSDependentExistsStmt(KeywordLoc, IsIfExists,
4483 GetNameFromUnqualifiedId(Name),
4489 unsigned NumParams) {
4507 assert(NumParams > 0 &&
"CapturedStmt requires context parameter");
4551 CaptureInits.push_back(Init.get());
4558 unsigned NumParams) {
4560 RecordDecl *RD = CreateCapturedStmtRecordDecl(CD,
Loc, NumParams);
4574 PushCapturedRegionScope(CurScope, CD, RD,
Kind);
4577 PushDeclContext(CurScope, CD);
4581 PushExpressionEvaluationContext(
4582 ExpressionEvaluationContext::PotentiallyEvaluated);
4583 ExprEvalContexts.back().InImmediateEscalatingFunctionContext =
false;
4589 unsigned OpenMPCaptureLevel) {
4591 RecordDecl *RD = CreateCapturedStmtRecordDecl(CD,
Loc, Params.size());
4595 bool ContextIsFound =
false;
4596 unsigned ParamNum = 0;
4599 I != E; ++I, ++ParamNum) {
4600 if (I->second.isNull()) {
4601 assert(!ContextIsFound &&
4602 "null type has been found already for '__context' parameter");
4612 ContextIsFound =
true;
4622 assert(ContextIsFound &&
"no null type for '__context' parameter");
4623 if (!ContextIsFound) {
4634 PushCapturedRegionScope(CurScope, CD, RD,
Kind, OpenMPCaptureLevel);
4637 PushDeclContext(CurScope, CD);
4641 PushExpressionEvaluationContext(
4642 ExpressionEvaluationContext::PotentiallyEvaluated);
4646 DiscardCleanupsInEvaluationContext();
4647 PopExpressionEvaluationContext();
4656 ActOnFields(
nullptr,
Record->getLocation(),
Record, Fields,
4663 DiscardCleanupsInEvaluationContext();
4664 PopExpressionEvaluationContext();
4679 Captures, CaptureInits, CD, RD);
Defines the clang::ASTContext interface.
This file provides some common utility functions for processing Lambda related AST Constructs.
Defines the clang::Expr interface and subclasses for C++ expressions.
static DiagnosticBuilder Diag(DiagnosticsEngine *Diags, const LangOptions &Features, FullSourceLoc TokLoc, const char *TokBegin, const char *TokRangeBegin, const char *TokRangeEnd, unsigned DiagID)
Produce a diagnostic highlighting some portion of a literal.
llvm::MachO::Record Record
Defines the clang::Preprocessor interface.
This file declares semantic analysis for CUDA constructs.
This file declares semantic analysis for Objective-C.
This file declares semantic analysis for OpenMP constructs and clauses.
static ExprResult CheckConvertedConstantExpression(Sema &S, Expr *From, QualType T, APValue &Value, Sema::CCEKind CCE, bool RequireInt, NamedDecl *Dest)
CheckConvertedConstantExpression - Check that the expression From is a converted constant expression ...
This file declares semantic analysis for SYCL constructs.
static bool CmpEnumVals(const std::pair< llvm::APSInt, EnumConstantDecl * > &lhs, const std::pair< llvm::APSInt, EnumConstantDecl * > &rhs)
CmpEnumVals - Comparison predicate for sorting enumeration values.
static bool FinishForRangeVarDecl(Sema &SemaRef, VarDecl *Decl, Expr *Init, SourceLocation Loc, int DiagID)
Finish building a variable declaration for a for-range statement.
static bool CmpCaseVals(const std::pair< llvm::APSInt, CaseStmt * > &lhs, const std::pair< llvm::APSInt, CaseStmt * > &rhs)
CmpCaseVals - Comparison predicate for sorting case values.
SmallVector< std::pair< llvm::APSInt, EnumConstantDecl * >, 64 > EnumValsTy
static bool ShouldDiagnoseSwitchCaseNotInEnum(const Sema &S, const EnumDecl *ED, const Expr *CaseExpr, EnumValsTy::iterator &EI, EnumValsTy::iterator &EIEnd, const llvm::APSInt &Val)
Returns true if we should emit a diagnostic about this case expression not being a part of the enum u...
static bool DiagnoseUnusedComparison(Sema &S, const Expr *E)
Diagnose unused comparisons, both builtin and overloaded operators.
static bool EqEnumVals(const std::pair< llvm::APSInt, EnumConstantDecl * > &lhs, const std::pair< llvm::APSInt, EnumConstantDecl * > &rhs)
EqEnumVals - Comparison preficate for uniqing enumeration values.
static bool hasDeducedReturnType(FunctionDecl *FD)
Determine whether the declared return type of the specified function contains 'auto'.
static bool ObjCEnumerationCollection(Expr *Collection)
static void DiagnoseForRangeConstVariableCopies(Sema &SemaRef, const VarDecl *VD)
static StmtResult RebuildForRangeWithDereference(Sema &SemaRef, Scope *S, SourceLocation ForLoc, SourceLocation CoawaitLoc, Stmt *InitStmt, Stmt *LoopVarDecl, SourceLocation ColonLoc, Expr *Range, SourceLocation RangeLoc, SourceLocation RParenLoc)
Speculatively attempt to dereference an invalid range expression.
static void checkEnumTypesInSwitchStmt(Sema &S, const Expr *Cond, const Expr *Case)
static void DiagnoseForRangeReferenceVariableCopies(Sema &SemaRef, const VarDecl *VD, QualType RangeInitType)
static void DiagnoseForRangeVariableCopies(Sema &SemaRef, const CXXForRangeStmt *ForStmt)
DiagnoseForRangeVariableCopies - Diagnose three cases and fixes for them.
static bool CheckSimplerImplicitMovesMSVCWorkaround(const Sema &S, const Expr *E)
static bool VerifyInitializationSequenceCXX98(const Sema &S, const InitializationSequence &Seq)
Verify that the initialization sequence that was picked for the first overload resolution is permissi...
static QualType GetTypeBeforeIntegralPromotion(const Expr *&E)
GetTypeBeforeIntegralPromotion - Returns the pre-promotion type of potentially integral-promoted expr...
static Sema::ForRangeStatus BuildNonArrayForRange(Sema &SemaRef, Expr *BeginRange, Expr *EndRange, QualType RangeType, VarDecl *BeginVar, VarDecl *EndVar, SourceLocation ColonLoc, SourceLocation CoawaitLoc, OverloadCandidateSet *CandidateSet, ExprResult *BeginExpr, ExprResult *EndExpr, BeginEndFunction *BEF)
Create the initialization, compare, and increment steps for the range-based for loop expression.
static bool DiagnoseNoDiscard(Sema &S, const WarnUnusedResultAttr *A, SourceLocation Loc, SourceRange R1, SourceRange R2, bool IsCtor)
static bool hasTrivialABIAttr(QualType VariableType)
Determines whether the VariableType's declaration is a record with the clang::trivial_abi attribute.
static void AdjustAPSInt(llvm::APSInt &Val, unsigned BitWidth, bool IsSigned)
static bool buildCapturedStmtCaptureList(Sema &S, CapturedRegionScopeInfo *RSI, SmallVectorImpl< CapturedStmt::Capture > &Captures, SmallVectorImpl< Expr * > &CaptureInits)
static void checkCaseValue(Sema &S, SourceLocation Loc, const llvm::APSInt &Val, unsigned UnpromotedWidth, bool UnpromotedSign)
Check the specified case value is in range for the given unpromoted switch type.
static void CheckJumpOutOfSEHFinally(Sema &S, SourceLocation Loc, const Scope &DestScope)
Defines the Objective-C statement AST node classes.
enum clang::format::@1273::AnnotatingParser::Context::@343 ContextType
Defines the clang::TypeLoc interface and its subclasses.
Allows QualTypes to be sorted and hence used in maps and sets.
__DEVICE__ int min(int __a, int __b)
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
CharUnits getTypeAlignInChars(QualType T) const
Return the ABI-specified alignment of a (complete) type T, in characters.
SourceManager & getSourceManager()
unsigned getIntWidth(QualType T) const
bool hasSimilarType(QualType T1, QualType T2)
Determine if two types are similar, according to the C++ rules.
QualType getObjCInterfaceType(const ObjCInterfaceDecl *Decl, ObjCInterfaceDecl *PrevDecl=nullptr) const
getObjCInterfaceType - Return the unique reference to the type for the specified ObjC interface decl.
QualType getAutoRRefDeductType() const
C++11 deduction pattern for 'auto &&' type.
QualType getTagDeclType(const TagDecl *Decl) const
Return the unique reference to the type for the specified TagDecl (struct/union/class/enum) decl.
bool hasSameType(QualType T1, QualType T2) const
Determine whether the given types T1 and T2 are equivalent.
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
QualType getLValueReferenceType(QualType T, bool SpelledAsLValue=true) const
Return the uniqued reference to the type for an lvalue reference to the specified type.
QualType getTypeDeclType(const TypeDecl *Decl, const TypeDecl *PrevDecl=nullptr) const
Return the unique reference to the type for the specified type declaration.
QualType getPointerDiffType() const
Return the unique type for "ptrdiff_t" (C99 7.17) defined in <stddef.h>.
TypeSourceInfo * getTrivialTypeSourceInfo(QualType T, SourceLocation Loc=SourceLocation()) const
Allocate a TypeSourceInfo where all locations have been initialized to a given location,...
QualType getObjCObjectPointerType(QualType OIT) const
Return a ObjCObjectPointerType type for the given ObjCObjectType.
CharUnits getDeclAlign(const Decl *D, bool ForAlignof=false) const
Return a conservative estimate of the alignment of the specified decl D.
bool hasSameUnqualifiedType(QualType T1, QualType T2) const
Determine whether the given types are equivalent after cvr-qualifiers have been removed.
uint64_t getTypeSize(QualType T) const
Return the size of the specified (complete) type T, in bits.
const TargetInfo & getTargetInfo() const
QualType getAutoDeductType() const
C++11 deduction pattern for 'auto' type.
void adjustDeducedFunctionResultType(FunctionDecl *FD, QualType ResultType)
Change the result type of a function type once it is deduced.
Represents an array type, per C99 6.7.5.2 - Array Declarators.
Attr - This represents one attribute.
SourceLocation getLocation() const
SourceRange getRange() const
static AttributedStmt * Create(const ASTContext &C, SourceLocation Loc, ArrayRef< const Attr * > Attrs, Stmt *SubStmt)
Represents a C++11 auto or C++14 decltype(auto) type, possibly constrained by a type-constraint.
bool isDecltypeAuto() const
BinaryConditionalOperator - The GNU extension to the conditional operator which allows the middle ope...
Expr * getFalseExpr() const
getFalseExpr - Return the subexpression which will be evaluated if the condnition evaluates to false;...
OpaqueValueExpr * getOpaqueValue() const
getOpaqueValue - Return the opaque value placeholder.
A builtin binary operation expression such as "x + y" or "x <= y".
SourceLocation getExprLoc() const
BreakStmt - This represents a break.
SourceLocation getBreakLoc() const
CStyleCastExpr - An explicit cast in C (C99 6.5.4) or a C-style cast in C++ (C++ [expr....
Represents a path from a specific derived class (which is not represented as part of the path) to a p...
BasePaths - Represents the set of paths from a derived class to one of its (direct or indirect) bases...
Represents a base class of a C++ class.
Represents binding an expression to a temporary.
A boolean literal, per ([C++ lex.bool] Boolean literals).
CXXCatchStmt - This represents a C++ catch block.
SourceLocation getBeginLoc() const LLVM_READONLY
VarDecl * getExceptionDecl() const
QualType getCaughtType() const
Represents a call to a C++ constructor.
Represents a C++ constructor within a class.
Represents a C++ conversion function within a class.
CXXForRangeStmt - This represents C++0x [stmt.ranged]'s ranged for statement, represented as 'for (ra...
Represents an explicit C++ type conversion that uses "functional" notation (C++ [expr....
Represents a call to a member function that may be written either with member call syntax (e....
Represents a static or instance method of a struct/union/class.
A call to an overloaded operator written using operator syntax.
Represents a C++ struct/union/class.
static CXXRecordDecl * Create(const ASTContext &C, TagKind TK, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, IdentifierInfo *Id, CXXRecordDecl *PrevDecl=nullptr, bool DelayTypeCreation=false)
An expression "T()" which creates a value-initialized rvalue of type T, which is a non-class type.
Represents a C++ nested-name-specifier or a global scope specifier.
NestedNameSpecifierLoc getWithLocInContext(ASTContext &Context) const
Retrieve a nested-name-specifier with location information, copied into the given AST context.
static CXXTryStmt * Create(const ASTContext &C, SourceLocation tryLoc, CompoundStmt *tryBlock, ArrayRef< Stmt * > handlers)
CallExpr - Represents a function call (C99 6.5.2.2, C++ [expr.call]).
static CanQual< Type > CreateUnsafe(QualType Other)
Builds a canonical type from a QualType.
QualType withConst() const
Retrieves a version of this type with const applied.
Represents the body of a CapturedStmt, and serves as its DeclContext.
void setContextParam(unsigned i, ImplicitParamDecl *P)
void setParam(unsigned i, ImplicitParamDecl *P)
static DeclContext * castToDeclContext(const CapturedDecl *D)
static CapturedDecl * Create(ASTContext &C, DeclContext *DC, unsigned NumParams)
Describes the capture of either a variable, or 'this', or variable-length array type.
This captures a statement into a function.
static CapturedStmt * Create(const ASTContext &Context, Stmt *S, CapturedRegionKind Kind, ArrayRef< Capture > Captures, ArrayRef< Expr * > CaptureInits, CapturedDecl *CD, RecordDecl *RD)
Stmt * getCapturedStmt()
Retrieve the statement being captured.
CaseStmt - Represent a case statement.
static CaseStmt * Create(const ASTContext &Ctx, Expr *lhs, Expr *rhs, SourceLocation caseLoc, SourceLocation ellipsisLoc, SourceLocation colonLoc)
Build a case statement.
CastExpr - Base class for type casts, including both implicit casts (ImplicitCastExpr) and explicit c...
CastKind getCastKind() const
CompoundStmt - This represents a group of statements like { stmt stmt }.
static CompoundStmt * Create(const ASTContext &C, ArrayRef< Stmt * > Stmts, FPOptionsOverride FPFeatures, SourceLocation LB, SourceLocation RB)
ConditionalOperator - The ?: ternary operator.
Expr * getCond() const
getCond - Return the expression representing the condition for the ?: operator.
Expr * getTrueExpr() const
getTrueExpr - Return the subexpression representing the value of the expression if the condition eval...
Expr * getFalseExpr() const
getFalseExpr - Return the subexpression representing the value of the expression if the condition eva...
ConstEvaluatedExprVisitor - This class visits 'const Expr *'s.
Represents the canonical version of C arrays with a specified constant size.
ContinueStmt - This represents a continue.
SourceLocation getContinueLoc() const
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
bool isFileContext() const
bool isDependentContext() const
Determines whether this context is dependent on a template parameter.
DeclContext * getParent()
getParent - Returns the containing DeclContext.
void addDecl(Decl *D)
Add the declaration D into this context.
bool isStdNamespace() const
bool isFunctionOrMethod() const
void addHiddenDecl(Decl *D)
Add the declaration D to this context without modifying any lookup tables.
bool isSingleDecl() const
A reference to a declared variable, function, enum, etc.
SourceLocation getLocation() const
DeclStmt - Adaptor class for mixing declarations with statements and expressions.
const Decl * getSingleDecl() const
bool isSingleDecl() const
isSingleDecl - This method returns true if this DeclStmt refers to a single Decl.
SourceLocation getBeginLoc() const LLVM_READONLY
Decl - This represents one declaration (or definition), e.g.
void setInvalidDecl(bool Invalid=true)
setInvalidDecl - Indicates the Decl had a semantic error.
void markUsed(ASTContext &C)
Mark the declaration used, in the sense of odr-use.
static Decl * castFromDeclContext(const DeclContext *)
bool isInvalidDecl() const
SourceLocation getLocation() const
void setImplicit(bool I=true)
void setLocation(SourceLocation L)
DeclContext * getDeclContext()
SourceLocation getTypeSpecEndLoc() const
SourceLocation getTypeSpecStartLoc() const
SourceLocation getBeginLoc() const LLVM_READONLY
TypeSourceInfo * getTypeSourceInfo() const
QualType getDeducedType() const
Get the type deduced for this placeholder type, or null if it has not been deduced.
SourceLocation getDefaultLoc() const
bool isIgnored(unsigned DiagID, SourceLocation Loc) const
Determine whether the diagnostic is known to be ignored.
DoStmt - This represents a 'do/while' stmt.
enumerator_range enumerators() const
bool isClosed() const
Returns true if this enum is either annotated with enum_extensibility(closed) or isn't annotated with...
bool isClosedNonFlag() const
Returns true if this enum is annotated with neither flag_enum nor enum_extensibility(open).
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of enums.
EnumDecl * getDecl() const
EvaluatedExprVisitor - This class visits 'Expr *'s.
This represents one expression.
bool EvaluateAsInt(EvalResult &Result, const ASTContext &Ctx, SideEffectsKind AllowSideEffects=SE_NoSideEffects, bool InConstantContext=false) const
EvaluateAsInt - Return true if this is a constant which we can fold and convert to an integer,...
@ SE_AllowSideEffects
Allow any unmodeled side effect.
Expr * IgnoreParenCasts() LLVM_READONLY
Skip past any parentheses and casts which might surround this expression until reaching a fixed point...
bool isUnusedResultAWarning(const Expr *&WarnExpr, SourceLocation &Loc, SourceRange &R1, SourceRange &R2, ASTContext &Ctx) const
isUnusedResultAWarning - Return true if this immediate expression should be warned about if the resul...
bool isValueDependent() const
Determines whether the value of this expression depends on.
bool isTypeDependent() const
Determines whether the type of this expression depends on.
llvm::APSInt EvaluateKnownConstInt(const ASTContext &Ctx, SmallVectorImpl< PartialDiagnosticAt > *Diag=nullptr) const
EvaluateKnownConstInt - Call EvaluateAsRValue and return the folded integer.
Expr * IgnoreParenImpCasts() LLVM_READONLY
Skip past any parentheses and implicit casts which might surround this expression until reaching a fi...
bool containsErrors() const
Whether this expression contains subexpressions which had errors, e.g.
Expr * IgnoreParens() LLVM_READONLY
Skip past any parentheses which might surround this expression until reaching a fixed point.
Decl * getReferencedDeclOfCallee()
bool isInstantiationDependent() const
Whether this expression is instantiation-dependent, meaning that it depends in some way on.
bool isIntegerConstantExpr(const ASTContext &Ctx, SourceLocation *Loc=nullptr) const
Expr * IgnoreImpCasts() LLVM_READONLY
Skip past any implicit casts which might surround this expression until reaching a fixed point.
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
bool isKnownToHaveBooleanValue(bool Semantic=true) const
isKnownToHaveBooleanValue - Return true if this is an integer expression that is known to return 0 or...
Represents difference between two FPOptions values.
Represents a member of a struct/union/class.
static FixItHint CreateReplacement(CharSourceRange RemoveRange, StringRef Code)
Create a code modification hint that replaces the given source range with the given code string.
static FixItHint CreateRemoval(CharSourceRange RemoveRange)
Create a code modification hint that removes the given source range.
static FixItHint CreateInsertion(SourceLocation InsertionLoc, StringRef Code, bool BeforePreviousInsertions=false)
Create a code modification hint that inserts the given code string at a specific location.
ForStmt - This represents a 'for (init;cond;inc)' stmt.
SourceLocation getRParenLoc() const
SourceLocation getBeginLoc() const
FullExpr - Represents a "full-expression" node.
Represents a function declaration or definition.
void setUsesSEHTry(bool UST)
bool isNoReturn() const
Determines whether this function is known to be 'noreturn', through an attribute on its declaration o...
QualType getReturnType() const
FunctionTemplateDecl * getPrimaryTemplate() const
Retrieve the primary template that this function template specialization either specializes or was in...
const TemplateArgumentList * getTemplateSpecializationArgs() const
Retrieve the template arguments used to produce this function template specialization from the primar...
bool isConstexpr() const
Whether this is a (C++11) constexpr function or constexpr constructor.
bool isMain() const
Determines whether this function is "main", which is the entry point into an executable program.
SourceRange getSourceRange() const override LLVM_READONLY
Source range that this declaration covers.
bool isOverloadedOperator() const
Whether this function declaration represents an C++ overloaded operator, e.g., "operator+".
OverloadedOperatorKind getOverloadedOperator() const
getOverloadedOperator - Which C++ overloaded operator this function represents, if any.
const ParmVarDecl * getParamDecl(unsigned i) const
Represents a prototype with parameter type info, e.g.
Declaration of a template function.
FunctionType - C99 6.7.5.3 - Function Declarators.
static StringRef getNameForCallConv(CallingConv CC)
bool getNoReturnAttr() const
Determine whether this function type includes the GNU noreturn attribute.
QualType getReturnType() const
GNUNullExpr - Implements the GNU __null extension, which is a name for a null pointer constant that h...
GotoStmt - This represents a direct goto.
One of these records is kept for each identifier that is lexed.
IdentifierInfo & get(StringRef Name)
Return the identifier token info for the specified named identifier.
static IfStmt * Create(const ASTContext &Ctx, SourceLocation IL, IfStatementKind Kind, Stmt *Init, VarDecl *Var, Expr *Cond, SourceLocation LPL, SourceLocation RPL, Stmt *Then, SourceLocation EL=SourceLocation(), Stmt *Else=nullptr)
Create an IfStmt.
ImaginaryLiteral - We support imaginary integer and floating point literals, like "1....
ImplicitCastExpr - Allows us to explicitly represent implicit type conversions, which have no direct ...
static ImplicitCastExpr * Create(const ASTContext &Context, QualType T, CastKind Kind, Expr *Operand, const CXXCastPath *BasePath, ExprValueKind Cat, FPOptionsOverride FPO)
static ImplicitParamDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation IdLoc, IdentifierInfo *Id, QualType T, ImplicitParamKind ParamKind)
Create implicit parameter.
IndirectGotoStmt - This represents an indirect goto.
static InitializationKind CreateCopy(SourceLocation InitLoc, SourceLocation EqualLoc, bool AllowExplicitConvs=false)
Create a copy initialization.
Describes the sequence of initializations required to initialize a given object or reference with a s...
Describes an entity that is being initialized.
static InitializedEntity InitializeResult(SourceLocation ReturnLoc, QualType Type)
Create the initialization entity for the result of a function.
static InitializedEntity InitializeRelatedResult(ObjCMethodDecl *MD, QualType Type)
Create the initialization entity for a related result.
unsigned allocateManglingNumber() const
static InitializedEntity InitializeVariable(VarDecl *Var)
Create the initialization entity for a variable.
static IntegerLiteral * Create(const ASTContext &C, const llvm::APInt &V, QualType type, SourceLocation l)
Returns a new integer literal with value 'V' and type 'type'.
Represents the declaration of a label.
void setLocStart(SourceLocation L)
LabelStmt * getStmt() const
void setStmt(LabelStmt *T)
bool isMSAsmLabel() const
LabelStmt - Represents a label, which has a substatement.
Represents the results of name lookup.
bool empty() const
Return true if no decls were found.
Representation of a Microsoft __if_exists or __if_not_exists statement with a dependent name.
Represents a prvalue temporary that is written into memory so that a reference can bind to it.
Expr * getSubExpr() const
Retrieve the temporary-generating subexpression whose value will be materialized into a glvalue.
MemberExpr - [C99 6.5.2.3] Structure and Union Members.
A pointer to member type per C++ 8.3.3 - Pointers to members.
This represents a decl that may have a name.
DeclarationName getDeclName() const
Get the actual, stored name of the declaration, which may be a special name.
IdentifierInfo * getIdentifier() const
Get the identifier that names this declaration, if there is one.
ReservedIdentifierStatus isReserved(const LangOptions &LangOpts) const
Determine if the declaration obeys the reserved identifier rules of the given language.
A C++ nested-name-specifier augmented with source location information.
NullStmt - This is the null statement ";": C99 6.8.3p3.
Represents Objective-C's collection statement.
An expression that sends a message to the given Objective-C object or class.
ObjCMethodDecl - Represents an instance or class method declaration.
Represents a pointer to an Objective C object.
Wrapper for void* pointer.
Expr * getSourceExpr() const
The source expression of an opaque value expression is the expression which originally generated the ...
OverloadCandidateSet - A set of overload candidates, used in C++ overload resolution (C++ 13....
@ CSK_Normal
Normal lookup.
void NoteCandidates(PartialDiagnosticAt PA, Sema &S, OverloadCandidateDisplayKind OCD, ArrayRef< Expr * > Args, StringRef Opc="", SourceLocation Loc=SourceLocation(), llvm::function_ref< bool(OverloadCandidate &)> Filter=[](OverloadCandidate &) { return true;})
When overload resolution fails, prints diagnostic messages containing the candidates in the candidate...
static FindResult find(Expr *E)
Finds the overloaded expression in the given expression E of OverloadTy.
ParenExpr - This represents a parethesized expression, e.g.
const Expr * getSubExpr() const
Represents a parameter to a function.
ParsedAttributes - A collection of parsed attributes.
Wrapper for source info for pointers.
SourceLocation getStarLoc() const
IdentifierTable & getIdentifierTable()
PseudoObjectExpr - An expression which accesses a pseudo-object l-value.
ArrayRef< Expr * > semantics()
A (possibly-)qualified type.
bool isVolatileQualified() const
Determine whether this type is volatile-qualified.
QualType withRestrict() const
QualType withConst() const
bool isTriviallyCopyConstructibleType(const ASTContext &Context) const
Return true if this is a trivially copyable type.
bool isNull() const
Return true if this QualType doesn't point to a type yet.
QualType getNonReferenceType() const
If Type is a reference type (e.g., const int&), returns the type that the reference refers to ("const...
QualType getCanonicalType() const
QualType getUnqualifiedType() const
Retrieve the unqualified variant of the given type, removing as little sugar as possible.
bool isConstQualified() const
Determine whether this type is const-qualified.
@ OCL_Strong
Assigning into this object requires the old value to be released and the new value to be retained.
Represents a struct/union/class.
static RecordDecl * Create(const ASTContext &C, TagKind TK, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, IdentifierInfo *Id, RecordDecl *PrevDecl=nullptr)
bool isOrContainsUnion() const
Returns whether this record is a union, or contains (at any nesting level) a union member.
virtual void completeDefinition()
Note that the definition of this type is now complete.
void setCapturedRecord()
Mark the record as a record for captured variables in CapturedStmt construct.
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of structs/unions/cl...
RecordDecl * getDecl() const
A class that does preorder or postorder depth-first traversal on the entire Clang AST and visits each...
ReturnStmt - This represents a return, optionally of an expression: return; return 4;.
void setRetValue(Expr *E)
static ReturnStmt * Create(const ASTContext &Ctx, SourceLocation RL, Expr *E, const VarDecl *NRVOCandidate)
Create a return statement.
static SEHExceptStmt * Create(const ASTContext &C, SourceLocation ExceptLoc, Expr *FilterExpr, Stmt *Block)
static SEHFinallyStmt * Create(const ASTContext &C, SourceLocation FinallyLoc, Stmt *Block)
Represents a __leave statement.
static SEHTryStmt * Create(const ASTContext &C, bool isCXXTry, SourceLocation TryLoc, Stmt *TryBlock, Stmt *Handler)
Scope - A scope is a transient data structure that is used while parsing the program.
bool Contains(const Scope &rhs) const
Returns if rhs has a higher scope depth than this.
unsigned getFlags() const
getFlags - Return the flags for this scope.
const Scope * getFnParent() const
getFnParent - Return the closest scope that is a function body.
Scope * getContinueParent()
getContinueParent - Return the closest scope that a continue statement would be affected by.
bool isSEHTryScope() const
Determine whether this scope is a SEH '__try' block.
Scope * getBreakParent()
getBreakParent - Return the closest scope that a break statement would be affected by.
const Scope * getParent() const
getParent - Return the scope that this is nested in.
void updateNRVOCandidate(VarDecl *VD)
@ SwitchScope
This is a scope that corresponds to a switch statement.
A generic diagnostic builder for errors which may or may not be deferred.
SemaDiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID, bool DeferHint=false)
Emit a diagnostic.
bool inferObjCARCLifetime(ValueDecl *decl)
void setOpenMPCaptureKind(FieldDecl *FD, const ValueDecl *D, unsigned Level)
Sets OpenMP capture kind (OMPC_private, OMPC_firstprivate, OMPC_map etc.) for FD based on DSA for the...
std::pair< VarDecl *, Expr * > get() const
RAII class used to determine whether SFINAE has trapped any errors that occur during template argumen...
Sema - This implements semantic analysis and AST building for C.
SmallVector< Scope *, 2 > CurrentSEHFinally
Stack of active SEH __finally scopes. Can be empty.
StmtResult BuildMSDependentExistsStmt(SourceLocation KeywordLoc, bool IsIfExists, NestedNameSpecifierLoc QualifierLoc, DeclarationNameInfo NameInfo, Stmt *Nested)
@ LookupMemberName
Member name lookup, which finds the names of class/struct/union members.
StmtResult BuildAttributedStmt(SourceLocation AttrsLoc, ArrayRef< const Attr * > Attrs, Stmt *SubStmt)
StmtResult ActOnSEHLeaveStmt(SourceLocation Loc, Scope *CurScope)
StmtResult ActOnForEachLValueExpr(Expr *E)
In an Objective C collection iteration statement: for (x in y) x can be an arbitrary l-value expressi...
void ActOnForEachDeclStmt(DeclGroupPtrTy Decl)
bool checkAndRewriteMustTailAttr(Stmt *St, const Attr &MTA)
Check whether the given statement can have musttail applied to it, issuing a diagnostic and returning...
StmtResult ActOnGotoStmt(SourceLocation GotoLoc, SourceLocation LabelLoc, LabelDecl *TheDecl)
StmtResult ActOnReturnStmt(SourceLocation ReturnLoc, Expr *RetValExp, Scope *CurScope)
ExprResult ActOnCaseExpr(SourceLocation CaseLoc, ExprResult Val)
StmtResult ActOnExprStmt(ExprResult Arg, bool DiscardedValue=true)
FieldDecl * BuildCaptureField(RecordDecl *RD, const sema::Capture &Capture)
Build a FieldDecl suitable to hold the given capture.
StmtResult BuildIfStmt(SourceLocation IfLoc, IfStatementKind StatementKind, SourceLocation LParenLoc, Stmt *InitStmt, ConditionResult Cond, SourceLocation RParenLoc, Stmt *ThenVal, SourceLocation ElseLoc, Stmt *ElseVal)
void DiagnoseCommaOperator(const Expr *LHS, SourceLocation Loc)
ExprResult CheckSwitchCondition(SourceLocation SwitchLoc, Expr *Cond)
void FinalizeDeclaration(Decl *D)
FinalizeDeclaration - called by ParseDeclarationAfterDeclarator to perform any semantic actions neces...
void ActOnCapturedRegionError()
ExprResult BuildUnaryOp(Scope *S, SourceLocation OpLoc, UnaryOperatorKind Opc, Expr *Input, bool IsAfterAmp=false)
Scope * getCurScope() const
Retrieve the parser's current scope.
StmtResult ActOnSEHTryBlock(bool IsCXXTry, SourceLocation TryLoc, Stmt *TryBlock, Stmt *Handler)
ExprResult BuildCaptureInit(const sema::Capture &Capture, SourceLocation ImplicitCaptureLoc, bool IsOpenMPMapping=false)
Initialize the given capture with a suitable expression.
StmtResult ActOnFinishSwitchStmt(SourceLocation SwitchLoc, Stmt *Switch, Stmt *Body)
NamedReturnInfo getNamedReturnInfo(Expr *&E, SimplerImplicitMoveMode Mode=SimplerImplicitMoveMode::Normal)
Determine whether the given expression might be move-eligible or copy-elidable in either a (co_)retur...
std::unique_ptr< sema::FunctionScopeInfo, PoppedFunctionScopeDeleter > PoppedFunctionScopePtr
void DiagnoseUnusedExprResult(const Stmt *S, unsigned DiagID)
DiagnoseUnusedExprResult - If the statement passed in is an expression whose result is unused,...
StmtResult ActOnWhileStmt(SourceLocation WhileLoc, SourceLocation LParenLoc, ConditionResult Cond, SourceLocation RParenLoc, Stmt *Body)
const LangOptions & getLangOpts() const
void ActOnStartOfCompoundStmt(bool IsStmtExpr)
bool DeduceFunctionTypeFromReturnExpr(FunctionDecl *FD, SourceLocation ReturnLoc, Expr *RetExpr, const AutoType *AT)
Deduce the return type for a function from a returned expression, per C++1y [dcl.spec....
void MarkAnyDeclReferenced(SourceLocation Loc, Decl *D, bool MightBeOdrUse)
Perform marking for a reference to an arbitrary declaration.
TypeLoc getReturnTypeLoc(FunctionDecl *FD) const
StmtResult ActOnExprStmtError()
const VarDecl * getCopyElisionCandidate(NamedReturnInfo &Info, QualType ReturnType)
Updates given NamedReturnInfo's move-eligible and copy-elidable statuses, considering the function re...
StmtResult ActOnNullStmt(SourceLocation SemiLoc, bool HasLeadingEmptyMacro=false)
RecordDecl * CreateCapturedStmtRecordDecl(CapturedDecl *&CD, SourceLocation Loc, unsigned NumParams)
void ActOnCapturedRegionStart(SourceLocation Loc, Scope *CurScope, CapturedRegionKind Kind, unsigned NumParams)
void DiagnoseAssignmentEnum(QualType DstType, QualType SrcType, Expr *SrcExpr)
DiagnoseAssignmentEnum - Warn if assignment to enum is a constant integer not in the range of enum va...
ExprResult ActOnCoawaitExpr(Scope *S, SourceLocation KwLoc, Expr *E)
DeclContext * CurContext
CurContext - This is the current declaration context of parsing.
StmtResult ActOnCapScopeReturnStmt(SourceLocation ReturnLoc, Expr *RetValExp, NamedReturnInfo &NRInfo, bool SupressSimplerImplicitMoves)
ActOnCapScopeReturnStmt - Utility routine to type-check return statements for capturing scopes.
AssignConvertType
AssignConvertType - All of the 'assignment' semantic checks return this enum to indicate whether the ...
StmtResult ActOnCapturedRegionEnd(Stmt *S)
StmtResult ActOnForStmt(SourceLocation ForLoc, SourceLocation LParenLoc, Stmt *First, ConditionResult Second, FullExprArg Third, SourceLocation RParenLoc, Stmt *Body)
StmtResult ActOnIndirectGotoStmt(SourceLocation GotoLoc, SourceLocation StarLoc, Expr *DestExp)
bool inTemplateInstantiation() const
Determine whether we are currently performing template instantiation.
ExprResult PerformMoveOrCopyInitialization(const InitializedEntity &Entity, const NamedReturnInfo &NRInfo, Expr *Value, bool SupressSimplerImplicitMoves=false)
Perform the initialization of a potentially-movable value, which is the result of return value.
StmtResult ActOnCXXForRangeStmt(Scope *S, SourceLocation ForLoc, SourceLocation CoawaitLoc, Stmt *InitStmt, Stmt *LoopVar, SourceLocation ColonLoc, Expr *Collection, SourceLocation RParenLoc, BuildForRangeKind Kind, ArrayRef< MaterializeTemporaryExpr * > LifetimeExtendTemps={})
ActOnCXXForRangeStmt - Check and build a C++11 for-range statement.
StmtResult BuildReturnStmt(SourceLocation ReturnLoc, Expr *RetValExp, bool AllowRecovery=false)
StmtResult ActOnFinishSEHFinallyBlock(SourceLocation Loc, Stmt *Block)
StmtResult ActOnContinueStmt(SourceLocation ContinueLoc, Scope *CurScope)
StmtResult BuildCXXForRangeStmt(SourceLocation ForLoc, SourceLocation CoawaitLoc, Stmt *InitStmt, SourceLocation ColonLoc, Stmt *RangeDecl, Stmt *Begin, Stmt *End, Expr *Cond, Expr *Inc, Stmt *LoopVarDecl, SourceLocation RParenLoc, BuildForRangeKind Kind, ArrayRef< MaterializeTemporaryExpr * > LifetimeExtendTemps={})
BuildCXXForRangeStmt - Build or instantiate a C++11 for-range statement.
StmtResult ActOnDoStmt(SourceLocation DoLoc, Stmt *Body, SourceLocation WhileLoc, SourceLocation CondLParen, Expr *Cond, SourceLocation CondRParen)
StmtResult ActOnStartOfSwitchStmt(SourceLocation SwitchLoc, SourceLocation LParenLoc, Stmt *InitStmt, ConditionResult Cond, SourceLocation RParenLoc)
StmtResult ActOnMSDependentExistsStmt(SourceLocation KeywordLoc, bool IsIfExists, CXXScopeSpec &SS, UnqualifiedId &Name, Stmt *Nested)
StmtResult ActOnSEHExceptBlock(SourceLocation Loc, Expr *FilterExpr, Stmt *Block)
void ActOnAfterCompoundStatementLeadingPragmas()
StmtResult ActOnDeclStmt(DeclGroupPtrTy Decl, SourceLocation StartLoc, SourceLocation EndLoc)
PartialDiagnostic PDiag(unsigned DiagID=0)
Build a partial diagnostic.
bool LookupQualifiedName(LookupResult &R, DeclContext *LookupCtx, bool InUnqualifiedLookup=false)
Perform qualified name lookup into a given context.
StmtResult ActOnAttributedStmt(const ParsedAttributes &AttrList, Stmt *SubStmt)
SourceManager & SourceMgr
DiagnosticsEngine & Diags
StmtResult ActOnBreakStmt(SourceLocation BreakLoc, Scope *CurScope)
void ActOnStartSEHFinallyBlock()
void ActOnAbortSEHFinallyBlock()
@ BFRK_Check
Determining whether a for-range statement could be built.
@ BFRK_Rebuild
Instantiation or recovery rebuild of a for-range statement.
StmtResult ActOnCXXCatchBlock(SourceLocation CatchLoc, Decl *ExDecl, Stmt *HandlerBlock)
ActOnCXXCatchBlock - Takes an exception declaration and a handler block and creates a proper catch ha...
void ActOnCaseStmtBody(Stmt *CaseStmt, Stmt *SubStmt)
ActOnCaseStmtBody - This installs a statement as the body of a case.
void AddInitializerToDecl(Decl *dcl, Expr *init, bool DirectInit)
AddInitializerToDecl - Adds the initializer Init to the declaration dcl.
StmtResult ActOnIfStmt(SourceLocation IfLoc, IfStatementKind StatementKind, SourceLocation LParenLoc, Stmt *InitStmt, ConditionResult Cond, SourceLocation RParenLoc, Stmt *ThenVal, SourceLocation ElseLoc, Stmt *ElseVal)
std::string getTemplateArgumentBindingsText(const TemplateParameterList *Params, const TemplateArgumentList &Args)
Produces a formatted string that describes the binding of template parameters to template arguments.
ForRangeStatus BuildForRangeBeginEndCall(SourceLocation Loc, SourceLocation RangeLoc, const DeclarationNameInfo &NameInfo, LookupResult &MemberLookup, OverloadCandidateSet *CandidateSet, Expr *Range, ExprResult *CallExpr)
Build a call to 'begin' or 'end' for a C++11 for-range statement.
sema::CompoundScopeInfo & getCurCompoundScope() const
TemplateDeductionResult DeduceAutoType(TypeLoc AutoTypeLoc, Expr *Initializer, QualType &Result, sema::TemplateDeductionInfo &Info, bool DependentDeduction=false, bool IgnoreConstraints=false, TemplateSpecCandidateSet *FailedTSC=nullptr)
Deduce the type for an auto type-specifier (C++11 [dcl.spec.auto]p6)
void ActOnFinishOfCompoundStmt()
StmtResult ActOnCompoundStmt(SourceLocation L, SourceLocation R, ArrayRef< Stmt * > Elts, bool isStmtExpr)
bool IsValueInFlagEnum(const EnumDecl *ED, const llvm::APInt &Val, bool AllowMask) const
IsValueInFlagEnum - Determine if a value is allowed as part of a flag enum.
StmtResult ActOnLabelStmt(SourceLocation IdentLoc, LabelDecl *TheDecl, SourceLocation ColonLoc, Stmt *SubStmt)
StmtResult ActOnCXXTryBlock(SourceLocation TryLoc, Stmt *TryBlock, ArrayRef< Stmt * > Handlers)
ActOnCXXTryBlock - Takes a try compound-statement and a number of handlers and creates a try statemen...
StmtResult ActOnDefaultStmt(SourceLocation DefaultLoc, SourceLocation ColonLoc, Stmt *SubStmt, Scope *CurScope)
StmtResult ActOnCaseStmt(SourceLocation CaseLoc, ExprResult LHS, SourceLocation DotDotDotLoc, ExprResult RHS, SourceLocation ColonLoc)
StmtResult FinishCXXForRangeStmt(Stmt *ForRange, Stmt *Body)
FinishCXXForRangeStmt - Attach the body to a C++0x for-range statement.
ExprResult CorrectDelayedTyposInExpr(Expr *E, VarDecl *InitDecl=nullptr, bool RecoverUncorrectedTypos=false, llvm::function_ref< ExprResult(Expr *)> Filter=[](Expr *E) -> ExprResult { return E;})
Process any TypoExprs in the given Expr and its children, generating diagnostics as appropriate and r...
Encodes a location in the source.
bool isValid() const
Return true if this is a valid SourceLocation object.
SourceLocation getLocWithOffset(IntTy Offset) const
Return a source location with the specified offset from this SourceLocation.
bool isMacroBodyExpansion(SourceLocation Loc) const
Tests whether the given source location represents the expansion of a macro body.
bool isInSystemHeader(SourceLocation Loc) const
Returns if a SourceLocation is in a system header.
A trivial tuple used to represent a source range.
SourceLocation getBegin() const
Stmt - This represents one statement.
SourceLocation getEndLoc() const LLVM_READONLY
SourceRange getSourceRange() const LLVM_READONLY
SourceLocation tokens are not useful in isolation - they are low level value objects created/interpre...
static std::tuple< bool, const Attr *, const Attr * > determineLikelihoodConflict(const Stmt *Then, const Stmt *Else)
static const Attr * getLikelihoodAttr(const Stmt *S)
SourceLocation getBeginLoc() const LLVM_READONLY
const SwitchCase * getNextSwitchCase() const
SwitchStmt - This represents a 'switch' stmt.
static SwitchStmt * Create(const ASTContext &Ctx, Stmt *Init, VarDecl *Var, Expr *Cond, SourceLocation LParenLoc, SourceLocation RParenLoc)
Create a switch statement.
SwitchCase * getSwitchCaseList()
void setAllEnumCasesCovered()
Set a flag in the SwitchStmt indicating that if the 'switch (X)' is a switch over an enum value then ...
Represents the declaration of a struct/union/class/enum.
bool isCompleteDefinition() const
Return true if this decl has its body fully specified.
void startDefinition()
Starts the definition of this tag declaration.
TypedefNameDecl * getTypedefNameForAnonDecl() const
bool isSEHTrySupported() const
Whether the target supports SEH __try.
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
TemplateSpecCandidateSet - A set of generalized overload candidates, used in template specializations...
void NoteCandidates(Sema &S, SourceLocation Loc)
NoteCandidates - When no template specialization match is found, prints diagnostic messages containin...
Base wrapper for a particular "section" of type source info.
QualType getType() const
Get the type for which this source info wrapper provides information.
T castAs() const
Convert to the specified TypeLoc type, asserting that this TypeLoc is of the desired type.
T getAsAdjusted() const
Convert to the specified TypeLoc type, returning a null TypeLoc if this TypeLoc is not of the desired...
A container of type source information.
TypeLoc getTypeLoc() const
Return the TypeLoc wrapper for the type source info.
QualType getType() const
Return the type wrapped by this type source info.
The base class of the type hierarchy.
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
bool isSignedIntegerOrEnumerationType() const
Determines whether this is an integer type that is signed or an enumeration types whose underlying ty...
bool isRValueReferenceType() const
AutoType * getContainedAutoType() const
Get the AutoType whose type will be deduced for a variable with an initializer of this type.
bool isPointerType() const
bool isIntegerType() const
isIntegerType() does not include complex integers (a GCC extension).
const T * castAs() const
Member-template castAs<specific type>.
bool isReferenceType() const
bool isEnumeralType() const
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.
bool isIntegralOrEnumerationType() const
Determine whether this type is an integral or enumeration type.
bool isSpecificBuiltinType(unsigned K) const
Test for a particular builtin type.
bool isDependentType() const
Whether this type is a dependent type, meaning that its definition somehow depends on a template para...
bool containsErrors() const
Whether this type is an error type.
const ArrayType * getAsArrayTypeUnsafe() const
A variant of getAs<> for array types which silently discards qualifiers from the outermost type.
bool isUndeducedType() const
Determine whether this type is an undeduced type, meaning that it somehow involves a C++11 'auto' typ...
bool isObjectType() const
Determine whether this type is an object type.
bool isIncompleteType(NamedDecl **Def=nullptr) const
Types are partitioned into 3 broad categories (C99 6.2.5p1): object types, function types,...
TypeClass getTypeClass() const
bool isCanonicalUnqualified() const
Determines if this type would be canonical if it had no further qualification.
const T * getAs() const
Member-template getAs<specific type>'.
bool isRecordType() const
UnaryOperator - This represents the unary-expression's (except sizeof and alignof),...
Expr * getSubExpr() const
Represents a C++ unqualified-id that has been parsed.
void setType(QualType newType)
Represents a variable declaration or definition.
static VarDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, const IdentifierInfo *Id, QualType T, TypeSourceInfo *TInfo, StorageClass S)
SourceRange getSourceRange() const override LLVM_READONLY
Source range that this declaration covers.
bool hasGlobalStorage() const
Returns true for all variables that do not have local storage.
const Expr * getInit() const
bool isExceptionVariable() const
Determine whether this variable is the exception variable in a C++ catch statememt or an Objective-C ...
bool hasLocalStorage() const
Returns true if a variable with function scope is a non-static local variable.
bool isLocalVarDecl() const
Returns true for local variable declarations other than parameters.
bool hasDependentAlignment() const
Determines if this variable's alignment is dependent.
Represents a C array with a specified size that is not an integer-constant-expression.
WhileStmt - This represents a 'while' stmt.
static WhileStmt * Create(const ASTContext &Ctx, VarDecl *Var, Expr *Cond, Stmt *Body, SourceLocation WL, SourceLocation LParenLoc, SourceLocation RParenLoc)
Create a while statement.
bool isVariableCapture() const
SourceLocation getLocation() const
Retrieve the location at which this variable was captured.
bool isVLATypeCapture() const
bool isThisCapture() const
bool isReferenceCapture() const
ValueDecl * getVariable() const
Retains information about a captured region.
unsigned short OpenMPLevel
unsigned short CapRegionKind
The kind of captured region.
RecordDecl * TheRecordDecl
The captured record type.
CapturedDecl * TheCapturedDecl
The CapturedDecl for this statement.
QualType ReturnType
ReturnType - The target type of return statements in this context, or null if unknown.
SmallVector< Capture, 4 > Captures
Captures - The captures.
bool HasImplicitReturnType
Contains information about the compound statement currently being parsed.
Retains information about a function, method, or block that is currently being parsed.
llvm::PointerIntPair< SwitchStmt *, 1, bool > SwitchInfo
A SwitchStmt, along with a flag indicating if its list of case statements is incomplete (because we d...
SourceLocation FirstCXXOrObjCTryLoc
First C++ 'try' or ObjC @try statement in the current function.
enum clang::sema::FunctionScopeInfo::@243 FirstTryType
SourceLocation FirstSEHTryLoc
First SEH '__try' statement in the current function.
void setHasCXXTry(SourceLocation TryLoc)
void setHasSEHTry(SourceLocation TryLoc)
CXXMethodDecl * CallOperator
The lambda's compiler-generated operator().
Provides information about an attempted template argument deduction, whose success or failure was des...
TemplateArgument SecondArg
The second template argument to which the template argument deduction failure refers.
TemplateArgument FirstArg
The first template argument to which the template argument deduction failure refers.
Defines the clang::TargetInfo interface.
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
const internal::VariadicAllOfMatcher< Decl > decl
Matches declarations.
constexpr Variable var(Literal L)
Returns the variable of L.
bool Call(InterpState &S, CodePtr OpPC, const Function *Func, uint32_t VarArgSize)
bool This(InterpState &S, CodePtr OpPC)
bool Cast(InterpState &S, CodePtr OpPC)
std::string toString(const til::SExpr *E)
The JSON file list parser is used to communicate input to InstallAPI.
@ Seq
'seq' clause, allowed on 'loop' and 'routine' directives.
@ OR_Deleted
Succeeded, but refers to a deleted function.
@ OR_Success
Overload resolution succeeded.
bool isReservedInAllContexts(ReservedIdentifierStatus Status)
Determine whether an identifier is reserved in all contexts.
IfStatementKind
In an if statement, this denotes whether the statement is a constexpr or consteval if statement.
@ RQ_None
No ref-qualifier was provided.
Expr * IgnoreParensSingleStep(Expr *E)
@ OCD_AllCandidates
Requests that all candidates be shown.
Expr * IgnoreImplicitAsWrittenSingleStep(Expr *E)
bool operator==(const CallGraphNode::CallRecord &LHS, const CallGraphNode::CallRecord &RHS)
CapturedRegionKind
The different kinds of captured statement.
Expr * IgnoreElidableImplicitConstructorSingleStep(Expr *E)
ActionResult< Expr * > ExprResult
@ Struct
The "struct" keyword.
Expr * IgnoreExprNodes(Expr *E, FnTys &&... Fns)
Given an expression E and functions Fn_1,...,Fn_n : Expr * -> Expr *, Recursively apply each of the f...
bool isLambdaConversionOperator(CXXConversionDecl *C)
ActionResult< Stmt * > StmtResult
@ VK_XValue
An x-value expression is a reference to an object with independent storage but which can be "moved",...
@ VK_LValue
An l-value expression is a reference to an object with independent storage.
const FunctionProtoType * T
std::pair< SourceLocation, PartialDiagnostic > PartialDiagnosticAt
A partial diagnostic along with the source location where this diagnostic occurs.
TemplateDeductionResult
Describes the result of template argument deduction.
@ Success
Template argument deduction was successful.
@ Inconsistent
Template argument deduction produced inconsistent deduced values for the given template parameter.
@ AlreadyDiagnosed
Some error which was already diagnosed.
@ CapturedContext
Parameter for captured context.
Diagnostic wrappers for TextAPI types for error reporting.
DeclarationNameInfo - A collector data type for bundling together a DeclarationName and the correspon...
EvalResult is a struct with detailed info about an evaluated expression.
bool isMoveEligible() const
bool isCopyElidable() const
const VarDecl * Candidate
static CatchHandlerType getEmptyKey()
static CatchHandlerType getTombstoneKey()
static unsigned getHashValue(const CatchHandlerType &Base)
static bool isEqual(const CatchHandlerType &LHS, const CatchHandlerType &RHS)