38#include "llvm/ADT/SmallVectorExtras.h"
39#include "llvm/ADT/StringExtras.h"
40#include "llvm/Support/ErrorHandling.h"
41#include "llvm/Support/SaveAndRestore.h"
42#include "llvm/Support/TimeProfiler.h"
55 const Decl *NextDecl =
nullptr;
57 bool ClearRelativeToPrimary =
true;
58 static Response Done() {
63 static Response ChangeDecl(
const Decl *ND) {
68 static Response ChangeDecl(
const DeclContext *Ctx) {
74 static Response UseNextDecl(
const Decl *CurDecl) {
78 static Response DontClearRelativeToPrimaryNextDecl(
const Decl *CurDecl) {
79 Response R = Response::UseNextDecl(CurDecl);
80 R.ClearRelativeToPrimary =
false;
89getPrimaryTemplateOfGenericLambda(
const FunctionDecl *LambdaCallOperator) {
91 return LambdaCallOperator;
93 if (
auto *FTD = dyn_cast_if_present<FunctionTemplateDecl>(
95 FTD && FTD->getInstantiatedFromMemberTemplate()) {
97 FTD->getInstantiatedFromMemberTemplate()->getTemplatedDecl();
104 ->getInstantiatedFromMemberFunction())
105 LambdaCallOperator = Prev;
109 return LambdaCallOperator;
112struct EnclosingTypeAliasTemplateDetails {
122EnclosingTypeAliasTemplateDetails
123getEnclosingTypeAliasTemplateDecl(
Sema &SemaRef) {
126 TypeAliasTemplateInstantiation)
128 EnclosingTypeAliasTemplateDetails Result;
130 *
Next = TATD->getInstantiatedFromMemberTemplate();
134 CSC.template_arguments(),
137 Result.PrimaryTypeAliasDecl =
Next;
138 Next =
Next->getInstantiatedFromMemberTemplate();
151bool isLambdaEnclosedByTypeAliasDecl(
155 Visitor(
const FunctionDecl *CallOperator) : CallOperator(CallOperator) {}
156 bool VisitLambdaExpr(
LambdaExpr *LE)
override {
159 return getPrimaryTemplateOfGenericLambda(LE->getCallOperator()) !=
168 return !Visitor(getPrimaryTemplateOfGenericLambda(LambdaCallOperator))
169 .TraverseType(Underlying);
176 bool SkipForSpecialization) {
180 return Response::DontClearRelativeToPrimaryNextDecl(VarTemplSpec);
185 return Response::Done();
190 llvm::PointerUnion<VarTemplateDecl *, VarTemplatePartialSpecializationDecl *>
193 dyn_cast<VarTemplatePartialSpecializationDecl *>(Specialized)) {
194 if (!SkipForSpecialization)
195 Result.addOuterTemplateArguments(
198 if (Partial->isMemberSpecialization())
199 return Response::Done();
202 if (!SkipForSpecialization)
203 Result.addOuterTemplateArguments(
207 return Response::Done();
209 return Response::DontClearRelativeToPrimaryNextDecl(VarTemplSpec);
221 for (
unsigned I = 0, N = TTP->
getDepth() + 1; I != N; ++I)
222 Result.addOuterTemplateArguments(std::nullopt);
223 return Response::Done();
226Response HandlePartialClassTemplateSpec(
229 if (!SkipForSpecialization)
231 return Response::Done();
238 bool SkipForSpecialization) {
243 return Response::Done();
245 if (!SkipForSpecialization)
246 Result.addOuterTemplateArguments(
255 return Response::Done();
261 if (
auto *InstFromPartialTempl =
264 return Response::ChangeDecl(
265 InstFromPartialTempl->getLexicalDeclContext());
267 return Response::UseNextDecl(ClassTemplSpec);
273 bool ForConstraintInstantiation,
274 bool ForDefaultArgumentSubstitution) {
276 if (!RelativeToPrimary &&
277 Function->getTemplateSpecializationKindForInstantiation() ==
279 return Response::Done();
281 if (!RelativeToPrimary &&
286 return Response::UseNextDecl(Function);
288 Function->getTemplateSpecializationArgs()) {
290 Result.addOuterTemplateArguments(
const_cast<FunctionDecl *
>(Function),
291 TemplateArgs->asArray(),
294 if (RelativeToPrimary &&
295 (Function->getTemplateSpecializationKind() ==
297 (Function->getFriendObjectKind() &&
298 !Function->getPrimaryTemplate()->getFriendObjectKind())))
299 return Response::UseNextDecl(Function);
303 assert(Function->getPrimaryTemplate() &&
"No function template?");
304 if (!ForDefaultArgumentSubstitution &&
305 Function->getPrimaryTemplate()->isMemberSpecialization())
306 return Response::Done();
309 if (!ForConstraintInstantiation &&
311 return Response::Done();
313 }
else if (
auto *
Template = Function->getDescribedFunctionTemplate()) {
315 (ForConstraintInstantiation || Result.getNumSubstitutedLevels() == 0) &&
316 "Outer template not instantiated?");
317 if (ForConstraintInstantiation) {
325 Result.addOuterTemplateArguments(
Template, Inst.template_arguments(),
336 if ((Function->getFriendObjectKind() || Function->isLocalExternDecl()) &&
337 Function->getNonTransparentDeclContext()->isFileContext() &&
339 return Response::ChangeDecl(Function->getLexicalDeclContext());
342 if (ForConstraintInstantiation && Function->getFriendObjectKind())
343 return Response::ChangeDecl(Function->getLexicalDeclContext());
344 return Response::UseNextDecl(Function);
347Response HandleFunctionTemplateDecl(
Sema &SemaRef,
351 Result.addOuterTemplateArguments(
364 Ty = std::exchange(NextTy,
nullptr)) {
367 NextTy = P.getAsType();
368 const auto *TSTy = dyn_cast<TemplateSpecializationType>(Ty);
390 if (TSTy->isCurrentInstantiation()) {
391 auto *RD = TSTy->getCanonicalTypeInternal()->getAsCXXRecordDecl();
393 Arguments = CTD->getInjectedTemplateArgs(SemaRef.
Context);
395 dyn_cast<ClassTemplateSpecializationDecl>(RD))
396 Arguments =
Specialization->getTemplateInstantiationArgs().asArray();
398 Result.addOuterTemplateArguments(
399 TSTy->getTemplateName().getAsTemplateDecl(), Arguments,
410 bool ForConstraintInstantiation) {
413 (ForConstraintInstantiation || Result.getNumSubstitutedLevels() == 0) &&
414 "Outer template not instantiated?");
415 if (ClassTemplate->isMemberSpecialization())
416 return Response::Done();
417 if (ForConstraintInstantiation)
418 Result.addOuterTemplateArguments(
420 ClassTemplate->getInjectedTemplateArgs(SemaRef.
Context),
427 return Response::Done();
432 if (ForConstraintInstantiation && IsFriend &&
441 return Response::ChangeDecl(LCD);
445 if (
auto TypeAlias = getEnclosingTypeAliasTemplateDecl(SemaRef);
446 ForConstraintInstantiation &&
TypeAlias) {
449 Result.addOuterTemplateArguments(
TypeAlias.Template,
465 return Response::ChangeDecl(
TypeAlias.Template->getDeclContext());
470 return Response::UseNextDecl(Rec);
473Response HandleImplicitConceptSpecializationDecl(
476 Result.addOuterTemplateArguments(
480 return Response::UseNextDecl(CSD);
483Response HandleGenericDeclContext(
const Decl *CurDecl) {
484 return Response::UseNextDecl(CurDecl);
492 const FunctionDecl *Pattern,
bool ForConstraintInstantiation,
493 bool SkipForSpecialization,
bool ForDefaultArgumentSubstitution) {
494 assert((ND || DC) &&
"Can't find arguments for a decl if one isn't provided");
499 const Decl *CurDecl = ND;
502 Result.addOuterTemplateArguments(
const_cast<NamedDecl *
>(ND), *Innermost,
512 if (
const auto *TTP = dyn_cast<TemplateTemplateParmDecl>(CurDecl))
513 HandleDefaultTempArgIntoTempTempParam(TTP,
Result);
515 : Response::UseNextDecl(CurDecl).NextDecl;
521 if (
const auto *VarTemplSpec =
522 dyn_cast<VarTemplateSpecializationDecl>(CurDecl)) {
523 R = HandleVarTemplateSpec(VarTemplSpec,
Result, SkipForSpecialization);
524 }
else if (
const auto *PartialClassTemplSpec =
525 dyn_cast<ClassTemplatePartialSpecializationDecl>(CurDecl)) {
526 R = HandlePartialClassTemplateSpec(PartialClassTemplSpec,
Result,
527 SkipForSpecialization);
528 }
else if (
const auto *ClassTemplSpec =
529 dyn_cast<ClassTemplateSpecializationDecl>(CurDecl)) {
530 R = HandleClassTemplateSpec(ClassTemplSpec,
Result,
531 SkipForSpecialization);
532 }
else if (
const auto *
Function = dyn_cast<FunctionDecl>(CurDecl)) {
533 R = HandleFunction(*
this,
Function,
Result, Pattern, RelativeToPrimary,
534 ForConstraintInstantiation,
535 ForDefaultArgumentSubstitution);
536 }
else if (
const auto *Rec = dyn_cast<CXXRecordDecl>(CurDecl)) {
538 ForConstraintInstantiation);
539 }
else if (
const auto *CSD =
540 dyn_cast<ImplicitConceptSpecializationDecl>(CurDecl)) {
541 R = HandleImplicitConceptSpecializationDecl(CSD,
Result);
542 }
else if (
const auto *FTD = dyn_cast<FunctionTemplateDecl>(CurDecl)) {
543 R = HandleFunctionTemplateDecl(*
this, FTD,
Result);
544 }
else if (
const auto *CTD = dyn_cast<ClassTemplateDecl>(CurDecl)) {
545 R = Response::ChangeDecl(CTD->getLexicalDeclContext());
547 R = Response::DontClearRelativeToPrimaryNextDecl(CurDecl);
548 if (
const auto *TTP = dyn_cast<TemplateTemplateParmDecl>(CurDecl)) {
549 R = HandleDefaultTempArgIntoTempTempParam(TTP,
Result);
552 R = HandleGenericDeclContext(CurDecl);
557 if (R.ClearRelativeToPrimary)
558 RelativeToPrimary =
false;
560 CurDecl = R.NextDecl;
603 llvm_unreachable(
"Invalid SynthesisKind!");
614 if (
SemaRef.Diags.hasFatalErrorOccurred() &&
615 SemaRef.hasUncompilableErrorOccurred()) {
628 Inst.InConstraintSubstitution =
630 Inst.InParameterMappingSubstitution =
632 if (!
SemaRef.CodeSynthesisContexts.empty()) {
633 Inst.InConstraintSubstitution |=
634 SemaRef.CodeSynthesisContexts.back().InConstraintSubstitution;
635 Inst.InParameterMappingSubstitution |=
636 SemaRef.CodeSynthesisContexts.back().InParameterMappingSubstitution;
649 PointOfInstantiation, InstantiationRange, Entity) {}
656 PointOfInstantiation, InstantiationRange, Entity) {}
695 PointOfInstantiation, InstantiationRange, PartialSpec,
nullptr,
704 PointOfInstantiation, InstantiationRange, PartialSpec,
nullptr,
713 PointOfInstantiation, InstantiationRange, Param,
nullptr,
723 PointOfInstantiation, InstantiationRange, Param,
Template,
733 PointOfInstantiation, InstantiationRange, Param,
Template,
742 PointOfInstantiation, InstantiationRange, Entity,
751 PointOfInstantiation, InstantiationRange, Param,
Template,
759 PointOfInstantiation, InstantiationRange,
nullptr,
768 PointOfInstantiation, InstantiationRange,
nullptr,
776 PointOfInstantiation, InstantiationRange,
nullptr,
801 PointOfInstantiation, InstantiationRange,
Template) {}
809 PointOfInstantiation, InstantiationRange,
Template) {}
816 PointOfInstantiation, InstantiationRange, Entity) {}
822 ArgLoc, InstantiationRange, PArg) {}
828 assert(
SemaRef.NonInstantiationEntries <=
829 SemaRef.CodeSynthesisContexts.size());
830 if ((
SemaRef.CodeSynthesisContexts.size() -
831 SemaRef.NonInstantiationEntries) >
832 SemaRef.getLangOpts().InstantiationDepth) {
834 diag::err_template_recursion_depth_exceeded)
837 diag::note_template_recursion_depth)
838 <<
SemaRef.getLangOpts().InstantiationDepth;
853 if (!Active.isInstantiationRecord()) {
861 "forgot to remove a lookup module for a template instantiation");
881 SemaRef.CodeSynthesisContexts.back());
883 SemaRef.popCodeSynthesisContext();
891 llvm::raw_string_ostream
OS(Result);
892 llvm::ListSeparator Comma;
893 for (
const Expr *Arg : Args) {
895 Arg->IgnoreParens()->printPretty(
OS,
nullptr,
904 unsigned Limit =
Diags.getTemplateBacktraceLimit();
906 SkipStart = Limit / 2 + Limit % 2;
911 unsigned InstantiationIdx = 0;
916 ++Active, ++InstantiationIdx) {
918 if (InstantiationIdx >= SkipStart && InstantiationIdx < SkipEnd) {
919 if (InstantiationIdx == SkipStart) {
921 DiagFunc(Active->PointOfInstantiation,
922 PDiag(diag::note_instantiation_contexts_suppressed)
928 switch (Active->Kind) {
930 Decl *D = Active->Entity;
932 unsigned DiagID = diag::note_template_member_class_here;
934 DiagID = diag::note_template_class_instantiation_here;
935 DiagFunc(Active->PointOfInstantiation,
936 PDiag(DiagID) <<
Record << Active->InstantiationRange);
940 DiagID = diag::note_function_template_spec_here;
942 DiagID = diag::note_template_member_function_here;
943 DiagFunc(Active->PointOfInstantiation,
945 }
else if (
VarDecl *VD = dyn_cast<VarDecl>(D)) {
946 DiagFunc(Active->PointOfInstantiation,
947 PDiag(VD->isStaticDataMember()
948 ? diag::note_template_static_data_member_def_here
949 : diag::note_template_variable_def_here)
950 << VD << Active->InstantiationRange);
951 }
else if (
EnumDecl *ED = dyn_cast<EnumDecl>(D)) {
952 DiagFunc(Active->PointOfInstantiation,
953 PDiag(diag::note_template_enum_def_here)
954 << ED << Active->InstantiationRange);
955 }
else if (
FieldDecl *FD = dyn_cast<FieldDecl>(D)) {
956 DiagFunc(Active->PointOfInstantiation,
957 PDiag(diag::note_template_nsdmi_here)
958 << FD << Active->InstantiationRange);
960 DiagFunc(Active->PointOfInstantiation,
961 PDiag(diag::note_template_class_instantiation_here)
962 << CTD << Active->InstantiationRange);
970 llvm::raw_svector_ostream
OS(TemplateArgsStr);
972 printTemplateArgumentList(
OS, Active->template_arguments(),
974 DiagFunc(Active->PointOfInstantiation,
975 PDiag(diag::note_default_arg_instantiation_here)
976 <<
OS.str() << Active->InstantiationRange);
982 DiagFunc(Active->PointOfInstantiation,
983 PDiag(diag::note_explicit_template_arg_substitution_here)
987 Active->NumTemplateArgs)
988 << Active->InstantiationRange);
994 dyn_cast<FunctionTemplateDecl>(Active->Entity)) {
996 Active->PointOfInstantiation,
997 PDiag(diag::note_function_template_deduction_instantiation_here)
1000 FnTmpl->getTemplateParameters(), Active->TemplateArgs,
1001 Active->NumTemplateArgs)
1002 << Active->InstantiationRange);
1006 bool IsTemplate =
false;
1008 if (
auto *D = dyn_cast<TemplateDecl>(Active->Entity)) {
1010 Params = D->getTemplateParameters();
1011 }
else if (
auto *D = dyn_cast<ClassTemplatePartialSpecializationDecl>(
1013 Params = D->getTemplateParameters();
1014 }
else if (
auto *D = dyn_cast<VarTemplatePartialSpecializationDecl>(
1016 Params = D->getTemplateParameters();
1018 llvm_unreachable(
"unexpected template kind");
1021 DiagFunc(Active->PointOfInstantiation,
1022 PDiag(diag::note_deduced_template_arg_substitution_here)
1025 Active->TemplateArgs,
1026 Active->NumTemplateArgs)
1027 << Active->InstantiationRange);
1037 llvm::raw_svector_ostream
OS(TemplateArgsStr);
1039 printTemplateArgumentList(
OS, Active->template_arguments(),
1041 DiagFunc(Active->PointOfInstantiation,
1042 PDiag(diag::note_default_function_arg_instantiation_here)
1043 <<
OS.str() << Active->InstantiationRange);
1051 Name = std::string(
" '") + Parm->
getName().str() +
"'";
1055 TemplateParams =
Template->getTemplateParameters();
1059 ->getTemplateParameters();
1060 DiagFunc(Active->PointOfInstantiation,
1061 PDiag(diag::note_prior_template_arg_substitution)
1064 Active->TemplateArgs,
1065 Active->NumTemplateArgs)
1066 << Active->InstantiationRange);
1073 TemplateParams =
Template->getTemplateParameters();
1077 ->getTemplateParameters();
1079 DiagFunc(Active->PointOfInstantiation,
1080 PDiag(diag::note_template_default_arg_checking)
1082 Active->TemplateArgs,
1083 Active->NumTemplateArgs)
1084 << Active->InstantiationRange);
1089 DiagFunc(Active->PointOfInstantiation,
1090 PDiag(diag::note_evaluating_exception_spec_here)
1095 DiagFunc(Active->PointOfInstantiation,
1096 PDiag(diag::note_template_exception_spec_instantiation_here)
1098 << Active->InstantiationRange);
1102 DiagFunc(Active->PointOfInstantiation,
1103 PDiag(diag::note_template_requirement_instantiation_here)
1104 << Active->InstantiationRange);
1107 DiagFunc(Active->PointOfInstantiation,
1108 PDiag(diag::note_template_requirement_params_instantiation_here)
1109 << Active->InstantiationRange);
1113 DiagFunc(Active->PointOfInstantiation,
1114 PDiag(diag::note_nested_requirement_here)
1115 << Active->InstantiationRange);
1119 DiagFunc(Active->PointOfInstantiation,
1120 PDiag(diag::note_in_declaration_of_implicit_special_member)
1122 << Active->SpecialMember);
1127 Active->Entity->getLocation(),
1128 PDiag(diag::note_in_declaration_of_implicit_equality_comparison));
1134 auto *FD = dyn_cast<FunctionDecl>(Active->Entity);
1142 DiagFunc(Active->PointOfInstantiation,
1143 PDiag(diag::note_member_synthesized_at)
1145 <<
Context.getCanonicalTagType(MD->getParent()));
1147 QualType RecordType = FD->getParamDecl(0)
1149 .getNonReferenceType()
1150 .getUnqualifiedType();
1151 DiagFunc(Active->PointOfInstantiation,
1152 PDiag(diag::note_comparison_synthesized_at)
1159 DiagFunc(Active->Entity->getLocation(),
1160 PDiag(diag::note_rewriting_operator_as_spaceship));
1164 DiagFunc(Active->PointOfInstantiation,
1165 PDiag(diag::note_in_binding_decl_init)
1170 DiagFunc(Active->PointOfInstantiation,
1171 PDiag(diag::note_due_to_dllexported_class)
1177 DiagFunc(Active->PointOfInstantiation,
1178 PDiag(diag::note_building_builtin_dump_struct_call)
1181 Active->NumCallArgs)));
1188 DiagFunc(Active->PointOfInstantiation,
1189 PDiag(diag::note_lambda_substitution_here));
1192 unsigned DiagID = 0;
1193 if (!Active->Entity) {
1194 DiagFunc(Active->PointOfInstantiation,
1195 PDiag(diag::note_nested_requirement_here)
1196 << Active->InstantiationRange);
1200 DiagID = diag::note_concept_specialization_here;
1202 DiagID = diag::note_checking_constraints_for_template_id_here;
1204 DiagID = diag::note_checking_constraints_for_var_spec_id_here;
1206 DiagID = diag::note_checking_constraints_for_class_spec_id_here;
1209 DiagID = diag::note_checking_constraints_for_function_here;
1212 llvm::raw_svector_ostream
OS(TemplateArgsStr);
1215 printTemplateArgumentList(
OS, Active->template_arguments(),
1218 DiagFunc(Active->PointOfInstantiation,
1219 PDiag(DiagID) <<
OS.str() << Active->InstantiationRange);
1223 DiagFunc(Active->PointOfInstantiation,
1224 PDiag(diag::note_constraint_substitution_here)
1225 << Active->InstantiationRange);
1228 DiagFunc(Active->PointOfInstantiation,
1229 PDiag(diag::note_constraint_normalization_here)
1231 << Active->InstantiationRange);
1234 DiagFunc(Active->PointOfInstantiation,
1235 PDiag(diag::note_parameter_mapping_substitution_here)
1236 << Active->InstantiationRange);
1239 DiagFunc(Active->PointOfInstantiation,
1240 PDiag(diag::note_building_deduction_guide_here));
1247 if (Active->NumTemplateArgs == 0)
1249 DiagFunc(Active->PointOfInstantiation,
1250 PDiag(diag::note_template_type_alias_instantiation_here)
1252 << Active->InstantiationRange);
1255 DiagFunc(Active->PointOfInstantiation,
1256 PDiag(diag::note_template_arg_template_params_mismatch));
1259 DiagFunc(ParamLoc,
PDiag(diag::note_template_prev_declaration)
1261 << Active->InstantiationRange);
1272 class TemplateInstantiator :
public TreeTransform<TemplateInstantiator> {
1277 bool EvaluateConstraints =
true;
1280 bool IsIncomplete =
false;
1282 bool BailOutOnIncomplete;
1287 bool maybeInstantiateFunctionParameterToScope(
ParmVarDecl *OldParm);
1292 TemplateInstantiator(
Sema &SemaRef,
1295 bool BailOutOnIncomplete =
false)
1296 : inherited(SemaRef), TemplateArgs(TemplateArgs), Loc(Loc),
1297 Entity(Entity), BailOutOnIncomplete(BailOutOnIncomplete) {}
1299 void setEvaluateConstraints(
bool B) {
1300 EvaluateConstraints = B;
1302 bool getEvaluateConstraints() {
1303 return EvaluateConstraints;
1306 inline static struct ForParameterMappingSubstitution_t {
1307 } ForParameterMappingSubstitution;
1309 TemplateInstantiator(ForParameterMappingSubstitution_t, Sema &SemaRef,
1311 const MultiLevelTemplateArgumentList &TemplateArgs)
1312 : inherited(SemaRef), TemplateArgs(TemplateArgs), Loc(Loc),
1313 BailOutOnIncomplete(
false) {}
1320 bool AlreadyTransformed(QualType
T);
1323 SourceLocation getBaseLocation() {
return Loc; }
1326 DeclarationName getBaseEntity() {
return Entity; }
1329 bool getIsIncomplete()
const {
return IsIncomplete; }
1333 void setBase(SourceLocation Loc, DeclarationName Entity) {
1335 this->Entity = Entity;
1338 unsigned TransformTemplateDepth(
unsigned Depth) {
1342 bool TryExpandParameterPacks(SourceLocation EllipsisLoc,
1343 SourceRange PatternRange,
1344 ArrayRef<UnexpandedParameterPack> Unexpanded,
1345 bool FailOnPackProducingTemplates,
1346 bool &ShouldExpand,
bool &RetainExpansion,
1347 UnsignedOrNone &NumExpansions) {
1352 NamedDecl *VD = ParmPack.first.dyn_cast<NamedDecl *>();
1353 if (
auto *PVD = dyn_cast_if_present<ParmVarDecl>(VD);
1354 PVD && maybeInstantiateFunctionParameterToScope(PVD))
1359 return getSema().CheckParameterPacksForExpansion(
1360 EllipsisLoc, PatternRange, Unexpanded, TemplateArgs,
1361 FailOnPackProducingTemplates, ShouldExpand, RetainExpansion,
1365 void ExpandingFunctionParameterPack(ParmVarDecl *Pack) {
1369 TemplateArgument ForgetPartiallySubstitutedPack() {
1373 MultiLevelTemplateArgumentList &TemplateArgs =
1374 const_cast<MultiLevelTemplateArgumentList &
>(this->TemplateArgs);
1375 unsigned Depth, Index;
1378 Result = TemplateArgs(Depth, Index);
1379 TemplateArgs.
setArgument(Depth, Index, TemplateArgument());
1381 IsIncomplete =
true;
1382 if (BailOutOnIncomplete)
1383 return TemplateArgument();
1390 void RememberPartiallySubstitutedPack(TemplateArgument Arg) {
1396 MultiLevelTemplateArgumentList &TemplateArgs =
1397 const_cast<MultiLevelTemplateArgumentList &
>(this->TemplateArgs);
1398 unsigned Depth, Index;
1404 MultiLevelTemplateArgumentList ForgetSubstitution() {
1405 MultiLevelTemplateArgumentList
New;
1408 MultiLevelTemplateArgumentList Old =
1409 const_cast<MultiLevelTemplateArgumentList &
>(this->TemplateArgs);
1410 const_cast<MultiLevelTemplateArgumentList &
>(this->TemplateArgs) =
1415 void RememberSubstitution(MultiLevelTemplateArgumentList Old) {
1416 const_cast<MultiLevelTemplateArgumentList &
>(this->TemplateArgs) = Old;
1420 getTemplateArgumentPackPatternForRewrite(
const TemplateArgument &TA) {
1426 "unexpected pack arguments in template rewrite");
1435 Decl *TransformDecl(SourceLocation Loc, Decl *D);
1437 void transformAttrs(Decl *Old, Decl *
New) {
1441 void transformedLocalDecl(Decl *Old, ArrayRef<Decl *> NewDecls) {
1443 (NewDecls.size() != 1 || !NewDecls.front()->isParameterPack())) {
1445 for (
auto *
New : NewDecls)
1451 assert(NewDecls.size() == 1 &&
1452 "should only have multiple expansions for a pack");
1458 auto *NewMD = dyn_cast<CXXMethodDecl>(
New);
1460 auto *OldMD = dyn_cast<CXXMethodDecl>(Old);
1461 if (
auto *NewTD = NewMD->getDescribedFunctionTemplate())
1462 NewTD->setInstantiatedFromMemberTemplate(
1463 OldMD->getDescribedFunctionTemplate());
1465 NewMD->setInstantiationOfMemberFunction(OldMD,
1473 if (
auto *DC = dyn_cast<DeclContext>(Old);
1474 DC && DC->isDependentContext() && DC->isFunctionOrMethod())
1480 Decl *TransformDefinition(SourceLocation Loc, Decl *D);
1484 NamedDecl *TransformFirstQualifierInScope(NamedDecl *D, SourceLocation Loc);
1486 bool TransformExceptionSpec(SourceLocation Loc,
1487 FunctionProtoType::ExceptionSpecInfo &ESI,
1488 SmallVectorImpl<QualType> &Exceptions,
1493 VarDecl *RebuildExceptionDecl(VarDecl *ExceptionDecl,
1494 TypeSourceInfo *Declarator,
1495 SourceLocation StartLoc,
1496 SourceLocation NameLoc,
1497 IdentifierInfo *Name);
1501 VarDecl *RebuildObjCExceptionDecl(VarDecl *ExceptionDecl,
1502 TypeSourceInfo *TSInfo, QualType
T);
1505 TransformTemplateName(NestedNameSpecifierLoc &QualifierLoc,
1507 SourceLocation NameLoc,
1508 QualType ObjectType = QualType(),
1509 NamedDecl *FirstQualifierInScope =
nullptr,
1510 bool AllowInjectedClassName =
false);
1512 const AnnotateAttr *TransformAnnotateAttr(
const AnnotateAttr *AA);
1513 const CXXAssumeAttr *TransformCXXAssumeAttr(
const CXXAssumeAttr *AA);
1514 const LoopHintAttr *TransformLoopHintAttr(
const LoopHintAttr *LH);
1515 const NoInlineAttr *TransformStmtNoInlineAttr(
const Stmt *OrigS,
1517 const NoInlineAttr *A);
1518 const AlwaysInlineAttr *
1519 TransformStmtAlwaysInlineAttr(
const Stmt *OrigS,
const Stmt *InstS,
1520 const AlwaysInlineAttr *A);
1521 const CodeAlignAttr *TransformCodeAlignAttr(
const CodeAlignAttr *CA);
1522 const OpenACCRoutineDeclAttr *
1523 TransformOpenACCRoutineDeclAttr(
const OpenACCRoutineDeclAttr *A);
1524 ExprResult TransformPredefinedExpr(PredefinedExpr *E);
1525 ExprResult TransformDeclRefExpr(DeclRefExpr *E);
1526 ExprResult TransformCXXDefaultArgExpr(CXXDefaultArgExpr *E);
1528 ExprResult TransformTemplateParmRefExpr(DeclRefExpr *E,
1529 NonTypeTemplateParmDecl *D);
1532 ExprResult RebuildVarDeclRefExpr(ValueDecl *PD, SourceLocation Loc);
1535 ExprResult TransformFunctionParmPackRefExpr(DeclRefExpr *E, ValueDecl *PD);
1540 ExprResult TransformFunctionParmPackExpr(FunctionParmPackExpr *E);
1542 QualType TransformFunctionProtoType(TypeLocBuilder &TLB,
1543 FunctionProtoTypeLoc TL) {
1545 return inherited::TransformFunctionProtoType(TLB, TL);
1548 QualType TransformTagType(TypeLocBuilder &TLB, TagTypeLoc TL) {
1549 auto Type = inherited::TransformTagType(TLB, TL);
1555 if (
const auto *ICNT = dyn_cast<InjectedClassNameType>(TL.
getTypePtr());
1558 Type = inherited::TransformType(
1559 ICNT->getDecl()->getCanonicalTemplateSpecializationType(
1567 bool TransformTemplateArgument(
const TemplateArgumentLoc &Input,
1568 TemplateArgumentLoc &Output,
1569 bool Uneval =
false) {
1570 const TemplateArgument &Arg = Input.
getArgument();
1571 std::vector<TemplateArgument> TArgs;
1581 pack, QualType(), SourceLocation{});
1582 TemplateArgumentLoc Output;
1583 if (TransformTemplateArgument(Input, Output, Uneval))
1588 TemplateArgument(llvm::ArrayRef(TArgs).copy(SemaRef.
Context)),
1589 QualType(), SourceLocation{});
1594 return inherited::TransformTemplateArgument(Input, Output, Uneval);
1599 TransformTemplateSpecializationType(TypeLocBuilder &TLB,
1600 TemplateSpecializationTypeLoc TL) {
1602 if (!getSema().ArgPackSubstIndex || !
T->
isSugared() ||
1612 QualType R = TransformType(
T->
desugar());
1617 UnsignedOrNone ComputeSizeOfPackExprWithoutSubstitution(
1618 ArrayRef<TemplateArgument> PackArgs) {
1629 return std::nullopt;
1631 return inherited::ComputeSizeOfPackExprWithoutSubstitution(PackArgs);
1634 template<
typename Fn>
1635 QualType TransformFunctionProtoType(TypeLocBuilder &TLB,
1636 FunctionProtoTypeLoc TL,
1637 CXXRecordDecl *ThisContext,
1638 Qualifiers ThisTypeQuals,
1639 Fn TransformExceptionSpec);
1641 ParmVarDecl *TransformFunctionTypeParam(ParmVarDecl *OldParm,
1642 int indexAdjustment,
1643 UnsignedOrNone NumExpansions,
1644 bool ExpectParameterPack);
1646 using inherited::TransformTemplateTypeParmType;
1649 QualType TransformTemplateTypeParmType(TypeLocBuilder &TLB,
1650 TemplateTypeParmTypeLoc TL,
1651 bool SuppressObjCLifetime);
1653 QualType BuildSubstTemplateTypeParmType(
1654 TypeLocBuilder &TLB,
bool SuppressObjCLifetime,
bool Final,
1655 Decl *AssociatedDecl,
unsigned Index, UnsignedOrNone PackIndex,
1656 TemplateArgument Arg, SourceLocation NameLoc);
1661 using inherited::TransformSubstTemplateTypeParmPackType;
1663 TransformSubstTemplateTypeParmPackType(TypeLocBuilder &TLB,
1664 SubstTemplateTypeParmPackTypeLoc TL,
1665 bool SuppressObjCLifetime);
1667 TransformSubstBuiltinTemplatePackType(TypeLocBuilder &TLB,
1668 SubstBuiltinTemplatePackTypeLoc TL);
1671 ComputeLambdaDependency(LambdaScopeInfo *LSI) {
1673 TemplateInstArgsHelpers::getEnclosingTypeAliasTemplateDecl(
1675 TypeAlias && TemplateInstArgsHelpers::isLambdaEnclosedByTypeAliasDecl(
1677 unsigned TypeAliasDeclDepth =
TypeAlias.Template->getTemplateDepth();
1679 return CXXRecordDecl::LambdaDependencyKind::LDK_AlwaysDependent;
1680 for (
const TemplateArgument &TA :
TypeAlias.AssociatedTemplateArguments)
1682 return CXXRecordDecl::LambdaDependencyKind::LDK_AlwaysDependent;
1684 return inherited::ComputeLambdaDependency(LSI);
1692 LocalInstantiationScope Scope(SemaRef,
true,
1694 Sema::ConstraintEvalRAII<TemplateInstantiator> RAII(*
this);
1696 return inherited::TransformLambdaExpr(E);
1699 ExprResult TransformBlockExpr(BlockExpr *E) {
1700 LocalInstantiationScope Scope(SemaRef,
true,
1702 return inherited::TransformBlockExpr(E);
1705 ExprResult RebuildLambdaExpr(SourceLocation StartLoc, SourceLocation EndLoc,
1706 LambdaScopeInfo *LSI) {
1709 assert(PVD &&
"null in a parameter list");
1710 if (!PVD->hasDefaultArg())
1712 Expr *UninstExpr = PVD->getUninstantiatedDefaultArg();
1714 SourceLocation EqualLoc = UninstExpr->
getBeginLoc();
1723 PVD->setDefaultArg(ErrorResult.
get());
1726 return inherited::RebuildLambdaExpr(StartLoc, EndLoc, LSI);
1739 llvm::SaveAndRestore _(EvaluateConstraints,
true);
1740 return inherited::TransformLambdaBody(E, Body);
1744 LocalInstantiationScope Scope(SemaRef,
true);
1745 ExprResult TransReq = inherited::TransformRequiresExpr(E);
1748 assert(TransReq.
get() != E &&
1749 "Do not change value of isSatisfied for the existing expression. "
1750 "Create a new expression instead.");
1752 Sema::SFINAETrap Trap(SemaRef);
1757 if (Trap.hasErrorOccurred())
1763 bool TransformRequiresExprRequirements(
1764 ArrayRef<concepts::Requirement *> Reqs,
1765 SmallVectorImpl<concepts::Requirement *> &Transformed) {
1766 bool SatisfactionDetermined =
false;
1767 for (concepts::Requirement *Req : Reqs) {
1768 concepts::Requirement *TransReq =
nullptr;
1769 if (!SatisfactionDetermined) {
1770 if (
auto *TypeReq = dyn_cast<concepts::TypeRequirement>(Req))
1771 TransReq = TransformTypeRequirement(TypeReq);
1772 else if (
auto *ExprReq = dyn_cast<concepts::ExprRequirement>(Req))
1773 TransReq = TransformExprRequirement(ExprReq);
1775 TransReq = TransformNestedRequirement(
1785 SatisfactionDetermined =
true;
1788 Transformed.push_back(TransReq);
1793 TemplateParameterList *TransformTemplateParameterList(
1794 TemplateParameterList *OrigTPL) {
1795 if (!OrigTPL || !OrigTPL->
size())
return OrigTPL;
1798 TemplateDeclInstantiator DeclInstantiator(getSema(),
1799 Owner, TemplateArgs);
1800 DeclInstantiator.setEvaluateConstraints(EvaluateConstraints);
1801 return DeclInstantiator.SubstTemplateParams(OrigTPL);
1804 concepts::TypeRequirement *
1805 TransformTypeRequirement(concepts::TypeRequirement *Req);
1806 concepts::ExprRequirement *
1807 TransformExprRequirement(concepts::ExprRequirement *Req);
1808 concepts::NestedRequirement *
1809 TransformNestedRequirement(concepts::NestedRequirement *Req);
1811 SourceLocation KWLoc, SourceLocation RBraceLoc,
const RequiresExpr *RE,
1812 RequiresExprBodyDecl *Body, ArrayRef<ParmVarDecl *> Params,
1813 SmallVectorImpl<QualType> &PTypes,
1814 SmallVectorImpl<ParmVarDecl *> &TransParams,
1815 Sema::ExtParameterInfoBuilder &PInfos);
1819bool TemplateInstantiator::AlreadyTransformed(QualType
T) {
1827 getSema().MarkDeclarationsReferencedInType(Loc,
T);
1831Decl *TemplateInstantiator::TransformDecl(SourceLocation Loc, Decl *D) {
1835 if (TemplateTemplateParmDecl *TTP = dyn_cast<TemplateTemplateParmDecl>(D)) {
1842 TTP->getPosition())) {
1843 IsIncomplete =
true;
1844 return BailOutOnIncomplete ?
nullptr : D;
1847 TemplateArgument Arg = TemplateArgs(TTP->getDepth(), TTP->getPosition());
1849 if (TTP->isParameterPack()) {
1851 "Missing argument pack");
1852 Arg =
SemaRef.getPackSubstitutedTemplateArgument(Arg);
1857 "Wrong kind of template template argument");
1858 return Template.getAsTemplateDecl();
1865 if (ParmVarDecl *PVD = dyn_cast<ParmVarDecl>(D);
1866 PVD &&
SemaRef.CurrentInstantiationScope &&
1867 (
SemaRef.inConstraintSubstitution() ||
1868 SemaRef.inParameterMappingSubstitution()) &&
1869 maybeInstantiateFunctionParameterToScope(PVD))
1875bool TemplateInstantiator::maybeInstantiateFunctionParameterToScope(
1876 ParmVarDecl *OldParm) {
1877 if (
SemaRef.CurrentInstantiationScope->getInstantiationOfIfExists(OldParm))
1881 return !TransformFunctionTypeParam(OldParm, 0,
1885 SmallVector<UnexpandedParameterPack, 2> Unexpanded;
1889 PackExpansionTypeLoc ExpansionTL = TL.
castAs<PackExpansionTypeLoc>();
1891 SemaRef.collectUnexpandedParameterPacks(Pattern, Unexpanded);
1892 assert(!Unexpanded.empty() &&
"Pack expansion without parameter packs?");
1894 bool ShouldExpand =
false;
1895 bool RetainExpansion =
false;
1896 UnsignedOrNone OrigNumExpansions =
1897 ExpansionTL.
getTypePtr()->getNumExpansions();
1898 UnsignedOrNone NumExpansions = OrigNumExpansions;
1900 Pattern.getSourceRange(), Unexpanded,
1902 ShouldExpand, RetainExpansion, NumExpansions))
1905 assert(ShouldExpand && !RetainExpansion &&
1906 "Shouldn't preserve pack expansion when evaluating constraints");
1907 ExpandingFunctionParameterPack(OldParm);
1908 for (
unsigned I = 0; I != *NumExpansions; ++I) {
1909 Sema::ArgPackSubstIndexRAII SubstIndex(getSema(), I);
1910 if (!TransformFunctionTypeParam(OldParm, 0,
1918Decl *TemplateInstantiator::TransformDefinition(SourceLocation Loc, Decl *D) {
1919 Decl *Inst = getSema().SubstDecl(D, getSema().
CurContext, TemplateArgs);
1923 getSema().CurrentInstantiationScope->InstantiatedLocal(D, Inst);
1927bool TemplateInstantiator::TransformExceptionSpec(
1928 SourceLocation Loc, FunctionProtoType::ExceptionSpecInfo &ESI,
1929 SmallVectorImpl<QualType> &Exceptions,
bool &Changed) {
1934 return inherited::TransformExceptionSpec(Loc, ESI, Exceptions, Changed);
1938TemplateInstantiator::TransformFirstQualifierInScope(NamedDecl *D,
1939 SourceLocation Loc) {
1942 if (TemplateTypeParmDecl *TTPD = dyn_cast_or_null<TemplateTypeParmDecl>(D)) {
1943 const TemplateTypeParmType *TTP
1948 TemplateArgument Arg = TemplateArgs(TTP->getDepth(), TTP->getIndex());
1950 if (TTP->isParameterPack()) {
1952 "Missing argument pack");
1957 Arg =
SemaRef.getPackSubstitutedTemplateArgument(Arg);
1962 return cast_or_null<NamedDecl>(TransformDecl(Loc, D));
1964 if (
const TagType *Tag =
T->
getAs<TagType>())
1965 return Tag->getDecl();
1968 getSema().Diag(Loc, diag::err_nested_name_spec_non_tag) <<
T;
1973 return cast_or_null<NamedDecl>(TransformDecl(Loc, D));
1977TemplateInstantiator::RebuildExceptionDecl(VarDecl *ExceptionDecl,
1978 TypeSourceInfo *Declarator,
1979 SourceLocation StartLoc,
1980 SourceLocation NameLoc,
1981 IdentifierInfo *Name) {
1982 VarDecl *Var = inherited::RebuildExceptionDecl(ExceptionDecl, Declarator,
1983 StartLoc, NameLoc, Name);
1985 getSema().CurrentInstantiationScope->InstantiatedLocal(ExceptionDecl, Var);
1989VarDecl *TemplateInstantiator::RebuildObjCExceptionDecl(VarDecl *ExceptionDecl,
1990 TypeSourceInfo *TSInfo,
1992 VarDecl *Var = inherited::RebuildObjCExceptionDecl(ExceptionDecl, TSInfo,
T);
1994 getSema().CurrentInstantiationScope->InstantiatedLocal(ExceptionDecl, Var);
1998TemplateName TemplateInstantiator::TransformTemplateName(
1999 NestedNameSpecifierLoc &QualifierLoc, SourceLocation TemplateKWLoc,
2000 TemplateName Name, SourceLocation NameLoc, QualType ObjectType,
2001 NamedDecl *FirstQualifierInScope,
bool AllowInjectedClassName) {
2003 assert(!QualifierLoc &&
"Unexpected qualifier");
2006 TTP && TTP->getDepth() < TemplateArgs.
getNumLevels()) {
2012 TTP->getPosition())) {
2013 IsIncomplete =
true;
2017 TemplateArgument Arg = TemplateArgs(TTP->getDepth(), TTP->getPosition());
2022 Arg = getTemplateArgumentPackPatternForRewrite(Arg);
2024 "unexpected nontype template argument kind in template rewrite");
2028 auto [AssociatedDecl, Final] =
2030 UnsignedOrNone PackIndex = std::nullopt;
2031 if (TTP->isParameterPack()) {
2033 "Missing argument pack");
2039 return getSema().Context.getSubstTemplateTemplateParmPack(
2040 Arg, AssociatedDecl, TTP->getIndex(), Final);
2043 PackIndex =
SemaRef.getPackIndex(Arg);
2044 Arg =
SemaRef.getPackSubstitutedTemplateArgument(Arg);
2048 assert(!
Template.isNull() &&
"Null template template argument");
2049 return getSema().Context.getSubstTemplateTemplateParm(
2050 Template, AssociatedDecl, TTP->getIndex(), PackIndex, Final);
2054 if (SubstTemplateTemplateParmPackStorage *SubstPack
2059 TemplateArgument Pack = SubstPack->getArgumentPack();
2061 SemaRef.getPackSubstitutedTemplateArgument(Pack).getAsTemplate();
2062 return getSema().Context.getSubstTemplateTemplateParm(
2063 Template, SubstPack->getAssociatedDecl(), SubstPack->getIndex(),
2064 SemaRef.getPackIndex(Pack), SubstPack->getFinal());
2067 return inherited::TransformTemplateName(
2068 QualifierLoc, TemplateKWLoc, Name, NameLoc, ObjectType,
2069 FirstQualifierInScope, AllowInjectedClassName);
2073TemplateInstantiator::TransformPredefinedExpr(PredefinedExpr *E) {
2081TemplateInstantiator::TransformTemplateParmRefExpr(DeclRefExpr *E,
2082 NonTypeTemplateParmDecl *NTTP) {
2089 IsIncomplete =
true;
2090 return BailOutOnIncomplete ?
ExprError() : E;
2098 Arg = getTemplateArgumentPackPatternForRewrite(Arg);
2100 "unexpected nontype template argument kind in template rewrite");
2106 auto [AssociatedDecl, Final] =
2108 UnsignedOrNone PackIndex = std::nullopt;
2111 "Missing argument pack");
2117 QualType TargetType =
SemaRef.SubstType(NTTP->
getType(), TemplateArgs,
2126 return new (
SemaRef.Context) SubstNonTypeTemplateParmPackExpr(
2130 PackIndex =
SemaRef.getPackIndex(Arg);
2131 Arg =
SemaRef.getPackSubstitutedTemplateArgument(Arg);
2133 return SemaRef.BuildSubstNonTypeTemplateParmExpr(
2134 AssociatedDecl, NTTP, E->
getLocation(), Arg, PackIndex, Final);
2138TemplateInstantiator::TransformAnnotateAttr(
const AnnotateAttr *AA) {
2139 SmallVector<Expr *> Args;
2140 for (Expr *Arg : AA->args()) {
2141 ExprResult Res = getDerived().TransformExpr(Arg);
2143 Args.push_back(Res.
get());
2145 return AnnotateAttr::CreateImplicit(getSema().
Context, AA->getAnnotation(),
2146 Args.data(), Args.size(), AA->getRange());
2149const CXXAssumeAttr *
2150TemplateInstantiator::TransformCXXAssumeAttr(
const CXXAssumeAttr *AA) {
2151 ExprResult Res = getDerived().TransformExpr(AA->getAssumption());
2155 if (!(Res.
get()->
getDependence() & ExprDependence::TypeValueInstantiation)) {
2156 Res = getSema().BuildCXXAssumeExpr(Res.
get(), AA->getAttrName(),
2162 return CXXAssumeAttr::CreateImplicit(getSema().
Context, Res.
get(),
2167TemplateInstantiator::TransformLoopHintAttr(
const LoopHintAttr *LH) {
2168 Expr *TransformedExpr = getDerived().TransformExpr(LH->getValue()).get();
2170 if (TransformedExpr == LH->getValue())
2175 LH->getSemanticSpelling() ==
2176 LoopHintAttr::Pragma_unroll))
2179 LoopHintAttr::OptionType Option = LH->getOption();
2180 LoopHintAttr::LoopHintState State = LH->getState();
2187 if (Option == LoopHintAttr::UnrollCount &&
2189 llvm::APSInt ValueAPS =
2193 if (ValueAPS.isZero() || ValueAPS.isOne()) {
2194 Option = LoopHintAttr::Unroll;
2195 State = LoopHintAttr::Disable;
2201 return LoopHintAttr::CreateImplicit(getSema().
Context, Option, State,
2202 TransformedExpr, *LH);
2204const NoInlineAttr *TemplateInstantiator::TransformStmtNoInlineAttr(
2205 const Stmt *OrigS,
const Stmt *InstS,
const NoInlineAttr *A) {
2211const AlwaysInlineAttr *TemplateInstantiator::TransformStmtAlwaysInlineAttr(
2212 const Stmt *OrigS,
const Stmt *InstS,
const AlwaysInlineAttr *A) {
2219const CodeAlignAttr *
2220TemplateInstantiator::TransformCodeAlignAttr(
const CodeAlignAttr *CA) {
2221 Expr *TransformedExpr = getDerived().TransformExpr(CA->getAlignment()).get();
2222 return getSema().BuildCodeAlignAttr(*CA, TransformedExpr);
2224const OpenACCRoutineDeclAttr *
2225TemplateInstantiator::TransformOpenACCRoutineDeclAttr(
2226 const OpenACCRoutineDeclAttr *A) {
2227 llvm_unreachable(
"RoutineDecl should only be a declaration attribute, as it "
2228 "applies to a Function Decl (and a few places for VarDecl)");
2231ExprResult TemplateInstantiator::RebuildVarDeclRefExpr(ValueDecl *PD,
2232 SourceLocation Loc) {
2233 DeclarationNameInfo NameInfo(PD->
getDeclName(), Loc);
2234 return getSema().BuildDeclarationNameExpr(CXXScopeSpec(), NameInfo, PD);
2238TemplateInstantiator::TransformFunctionParmPackExpr(FunctionParmPackExpr *E) {
2242 ValueDecl *VD = cast_or_null<ValueDecl>(TransformDecl(E->
getExprLoc(), D));
2245 return RebuildVarDeclRefExpr(VD, E->
getExprLoc());
2248 QualType
T = TransformType(E->
getType());
2254 SmallVector<ValueDecl *, 8> Vars;
2258 ValueDecl *D = cast_or_null<ValueDecl>(TransformDecl(E->
getExprLoc(), *I));
2267 getSema().MarkFunctionParmPackReferenced(PackExpr);
2272TemplateInstantiator::TransformFunctionParmPackRefExpr(DeclRefExpr *E,
2275 llvm::PointerUnion<Decl *, DeclArgumentPack *> *
Found
2276 = getSema().CurrentInstantiationScope->findInstantiationOf(PD);
2277 assert(
Found &&
"no instantiation for parameter pack");
2279 Decl *TransformedDecl;
2280 if (DeclArgumentPack *Pack = dyn_cast<DeclArgumentPack *>(*
Found)) {
2284 QualType
T = TransformType(E->
getType());
2289 getSema().MarkFunctionParmPackReferenced(PackExpr);
2293 TransformedDecl = (*Pack)[*getSema().ArgPackSubstIndex];
2304TemplateInstantiator::TransformDeclRefExpr(DeclRefExpr *E) {
2309 if (NonTypeTemplateParmDecl *NTTP = dyn_cast<NonTypeTemplateParmDecl>(D)) {
2311 return TransformTemplateParmRefExpr(E, NTTP);
2318 if (VarDecl *PD = dyn_cast<VarDecl>(D))
2320 return TransformFunctionParmPackRefExpr(E, PD);
2322 return inherited::TransformDeclRefExpr(E);
2325ExprResult TemplateInstantiator::TransformCXXDefaultArgExpr(
2326 CXXDefaultArgExpr *E) {
2328 getDescribedFunctionTemplate() &&
2329 "Default arg expressions are never formed in dependent cases.");
2330 return SemaRef.BuildCXXDefaultArgExpr(
2335template<
typename Fn>
2336QualType TemplateInstantiator::TransformFunctionProtoType(TypeLocBuilder &TLB,
2337 FunctionProtoTypeLoc TL,
2338 CXXRecordDecl *ThisContext,
2339 Qualifiers ThisTypeQuals,
2340 Fn TransformExceptionSpec) {
2348 LocalInstantiationScope *Current = getSema().CurrentInstantiationScope;
2349 std::optional<LocalInstantiationScope> Scope;
2353 return inherited::TransformFunctionProtoType(
2354 TLB, TL, ThisContext, ThisTypeQuals, TransformExceptionSpec);
2357ParmVarDecl *TemplateInstantiator::TransformFunctionTypeParam(
2358 ParmVarDecl *OldParm,
int indexAdjustment, UnsignedOrNone NumExpansions,
2359 bool ExpectParameterPack) {
2360 auto NewParm =
SemaRef.SubstParmVarDecl(
2361 OldParm, TemplateArgs, indexAdjustment, NumExpansions,
2362 ExpectParameterPack, EvaluateConstraints);
2363 if (NewParm &&
SemaRef.getLangOpts().OpenCL)
2364 SemaRef.deduceOpenCLAddressSpace(NewParm);
2368QualType TemplateInstantiator::BuildSubstTemplateTypeParmType(
2369 TypeLocBuilder &TLB,
bool SuppressObjCLifetime,
bool Final,
2370 Decl *AssociatedDecl,
unsigned Index, UnsignedOrNone PackIndex,
2371 TemplateArgument Arg, SourceLocation NameLoc) {
2376 if (SuppressObjCLifetime) {
2378 RQs = Replacement.getQualifiers();
2381 SemaRef.Context.getQualifiedType(Replacement.getUnqualifiedType(), RQs);
2385 QualType
Result = getSema().Context.getSubstTemplateTypeParmType(
2386 Replacement, AssociatedDecl, Index, PackIndex, Final);
2387 SubstTemplateTypeParmTypeLoc NewTL =
2388 TLB.
push<SubstTemplateTypeParmTypeLoc>(
Result);
2394TemplateInstantiator::TransformTemplateTypeParmType(TypeLocBuilder &TLB,
2395 TemplateTypeParmTypeLoc TL,
2396 bool SuppressObjCLifetime) {
2407 IsIncomplete =
true;
2408 if (BailOutOnIncomplete)
2411 TemplateTypeParmTypeLoc NewTL
2412 = TLB.
push<TemplateTypeParmTypeLoc>(TL.
getType());
2417 TemplateArgument Arg = TemplateArgs(
T->getDepth(),
T->getIndex());
2422 Arg = getTemplateArgumentPackPatternForRewrite(Arg);
2424 "unexpected nontype template argument kind in template rewrite");
2430 auto [AssociatedDecl, Final] =
2432 UnsignedOrNone PackIndex = std::nullopt;
2433 if (
T->isParameterPack() ||
2440 (
T->getDecl() &&
T->getDecl()->isTemplateParameterPack())) {
2442 "Missing argument pack");
2448 QualType
Result = getSema().Context.getSubstTemplateTypeParmPackType(
2449 AssociatedDecl,
T->getIndex(), Final, Arg);
2450 SubstTemplateTypeParmPackTypeLoc NewTL
2451 = TLB.
push<SubstTemplateTypeParmPackTypeLoc>(
Result);
2457 PackIndex =
SemaRef.getPackIndex(Arg);
2458 Arg =
SemaRef.getPackSubstitutedTemplateArgument(Arg);
2462 "Template argument kind mismatch");
2464 return BuildSubstTemplateTypeParmType(TLB, SuppressObjCLifetime, Final,
2465 AssociatedDecl,
T->getIndex(),
2473 TemplateTypeParmDecl *NewTTPDecl =
nullptr;
2474 if (TemplateTypeParmDecl *OldTTPDecl =
T->getDecl())
2475 NewTTPDecl = cast_or_null<TemplateTypeParmDecl>(
2477 QualType
Result = getSema().Context.getTemplateTypeParmType(
2479 T->isParameterPack(), NewTTPDecl);
2480 TemplateTypeParmTypeLoc NewTL = TLB.
push<TemplateTypeParmTypeLoc>(
Result);
2485QualType TemplateInstantiator::TransformSubstTemplateTypeParmPackType(
2486 TypeLocBuilder &TLB, SubstTemplateTypeParmPackTypeLoc TL,
2487 bool SuppressObjCLifetime) {
2488 const SubstTemplateTypeParmPackType *
T = TL.
getTypePtr();
2490 Decl *NewReplaced = TransformDecl(TL.
getNameLoc(),
T->getAssociatedDecl());
2495 if (NewReplaced !=
T->getAssociatedDecl())
2496 Result = getSema().Context.getSubstTemplateTypeParmPackType(
2497 NewReplaced,
T->getIndex(),
T->getFinal(),
T->getArgumentPack());
2498 SubstTemplateTypeParmPackTypeLoc NewTL =
2499 TLB.
push<SubstTemplateTypeParmPackTypeLoc>(
Result);
2504 TemplateArgument Pack =
T->getArgumentPack();
2505 TemplateArgument Arg =
SemaRef.getPackSubstitutedTemplateArgument(Pack);
2506 return BuildSubstTemplateTypeParmType(
2507 TLB, SuppressObjCLifetime,
T->getFinal(), NewReplaced,
T->getIndex(),
2511QualType TemplateInstantiator::TransformSubstBuiltinTemplatePackType(
2512 TypeLocBuilder &TLB, SubstBuiltinTemplatePackTypeLoc TL) {
2514 return TreeTransform::TransformSubstBuiltinTemplatePackType(TLB, TL);
2515 TemplateArgument
Result =
SemaRef.getPackSubstitutedTemplateArgument(
2519 return Result.getAsType();
2522static concepts::Requirement::SubstitutionDiagnostic *
2532 ErrorLoc = PDA.first;
2537 llvm::raw_svector_ostream
OS(Entity);
2541 C.backupStr(Entity), ErrorLoc,
C.backupStr(Message)};
2544concepts::Requirement::SubstitutionDiagnostic *
2547 llvm::raw_svector_ostream
OS(Entity);
2551 C.backupStr(Entity),
2552 Location, StringRef()};
2555ExprResult TemplateInstantiator::TransformRequiresTypeParams(
2568 if (getDerived().TransformFunctionTypeParams(
2569 KWLoc, Params,
nullptr,
nullptr, PTypes,
2570 &TransParams, PInfos, &ErrorIdx) ||
2571 Trap.hasErrorOccurred()) {
2577 SemaRef, Info, [&](llvm::raw_ostream &
OS) {
OS << *FailedDecl; })));
2578 return getDerived().RebuildRequiresExpr(KWLoc, Body, RE->
getLParenLoc(),
2580 TransReqs, RBraceLoc);
2586concepts::TypeRequirement *
2587TemplateInstantiator::TransformTypeRequirement(concepts::TypeRequirement *Req) {
2591 if (AlwaysRebuild())
2592 return RebuildTypeRequirement(
2598 Sema::SFINAETrap Trap(
SemaRef, Info);
2599 Sema::InstantiatingTemplate TypeInst(
2602 if (TypeInst.isInvalid())
2604 TypeSourceInfo *TransType = TransformType(Req->
getType());
2605 if (!TransType || Trap.hasErrorOccurred())
2607 [&] (llvm::raw_ostream&
OS) {
2610 return RebuildTypeRequirement(TransType);
2613concepts::ExprRequirement *
2614TemplateInstantiator::TransformExprRequirement(concepts::ExprRequirement *Req) {
2618 llvm::PointerUnion<Expr *, concepts::Requirement::SubstitutionDiagnostic *>
2625 Sema::SFINAETrap Trap(
SemaRef, Info);
2628 if (ExprInst.isInvalid())
2631 if (!TransExprRes.
isInvalid() && !Trap.hasErrorOccurred() &&
2633 TransExprRes =
SemaRef.CheckPlaceholderExpr(TransExprRes.
get());
2634 if (TransExprRes.
isInvalid() || Trap.hasErrorOccurred())
2639 TransExpr = TransExprRes.
get();
2642 std::optional<concepts::ExprRequirement::ReturnTypeRequirement> TransRetReq;
2644 if (RetReq.isEmpty())
2645 TransRetReq.emplace();
2646 else if (RetReq.isSubstitutionFailure())
2647 TransRetReq.emplace(RetReq.getSubstitutionDiagnostic());
2648 else if (RetReq.isTypeConstraint()) {
2649 TemplateParameterList *OrigTPL =
2650 RetReq.getTypeConstraintTemplateParameterList();
2652 Sema::SFINAETrap Trap(
SemaRef, Info);
2655 if (TPLInst.isInvalid())
2657 TemplateParameterList *TPL = TransformTemplateParameterList(OrigTPL);
2658 if (!TPL || Trap.hasErrorOccurred())
2660 [&] (llvm::raw_ostream&
OS) {
2661 RetReq.getTypeConstraint()->getImmediatelyDeclaredConstraint()
2662 ->printPretty(
OS,
nullptr,
SemaRef.getPrintingPolicy());
2666 TransRetReq.emplace(TPL);
2669 assert(TransRetReq &&
"All code paths leading here must set TransRetReq");
2670 if (Expr *E = TransExpr.dyn_cast<Expr *>())
2672 std::move(*TransRetReq));
2673 return RebuildExprRequirement(
2678concepts::NestedRequirement *
2679TemplateInstantiator::TransformNestedRequirement(
2680 concepts::NestedRequirement *Req) {
2685 ConstraintSatisfaction Satisfaction;
2687 auto NestedReqWithDiag = [&
C,
this](Expr *E,
2688 ConstraintSatisfaction Satisfaction) {
2690 SmallString<128> Entity;
2691 llvm::raw_svector_ostream
OS(Entity);
2692 E->printPretty(
OS,
nullptr,
SemaRef.getPrintingPolicy());
2693 return new (
C) concepts::NestedRequirement(
2694 SemaRef.Context,
C.backupStr(Entity), std::move(Satisfaction));
2698 if (AlwaysRebuild())
2704 if (!getEvaluateConstraints()) {
2706 if (TransConstraint.
isInvalid() || !TransConstraint.
get())
2710 concepts::NestedRequirement(TransConstraint.
get());
2711 ConstraintSatisfaction Satisfaction;
2712 return new (
SemaRef.Context) concepts::NestedRequirement(
2713 SemaRef.Context, TransConstraint.
get(), Satisfaction);
2717 Expr *NewConstraint;
2721 Sema::InstantiatingTemplate ConstrInst(
2723 Sema::InstantiatingTemplate::ConstraintsCheck(),
2726 if (ConstrInst.isInvalid())
2730 Req, AssociatedConstraint(Constraint,
SemaRef.ArgPackSubstIndex),
2732 nullptr, &NewConstraint);
2736 return NestedReqWithDiag(Constraint, Satisfaction);
2740 if (!NewConstraint) {
2742 return NestedReqWithDiag(Constraint, Satisfaction);
2744 NewConstraint = Constraint;
2746 return new (
C) concepts::NestedRequirement(
C, NewConstraint, Satisfaction);
2753 bool AllowDeducedTST) {
2755 "Cannot perform an instantiation without some context on the "
2756 "instantiation stack");
2758 if (!
T->getType()->isInstantiationDependentType() &&
2759 !
T->getType()->isVariablyModifiedType())
2762 TemplateInstantiator Instantiator(*
this, Args, Loc, Entity);
2763 return AllowDeducedTST ? Instantiator.TransformTypeWithDeducedTST(
T)
2764 : Instantiator.TransformType(
T);
2772 "Cannot perform an instantiation without some context on the "
2773 "instantiation stack");
2787 TemplateInstantiator Instantiator(*
this, Args, Loc, Entity);
2801 bool *IsIncompleteSubstitution) {
2803 "Cannot perform an instantiation without some context on the "
2804 "instantiation stack");
2808 if (!
T->isInstantiationDependentType() && !
T->isVariablyModifiedType())
2811 TemplateInstantiator Instantiator(
2812 *
this, TemplateArgs, Loc, Entity,
2813 IsIncompleteSubstitution !=
nullptr);
2814 QualType QT = Instantiator.TransformType(
T);
2815 if (IsIncompleteSubstitution && Instantiator.getIsIncomplete())
2816 *IsIncompleteSubstitution =
true;
2821 if (
T->getType()->isInstantiationDependentType() ||
2822 T->getType()->isVariablyModifiedType())
2825 TypeLoc TL =
T->getTypeLoc().IgnoreParens();
2848 bool EvaluateConstraints) {
2850 "Cannot perform an instantiation without some context on the "
2851 "instantiation stack");
2856 TemplateInstantiator Instantiator(*
this, Args, Loc, Entity);
2857 Instantiator.setEvaluateConstraints(EvaluateConstraints);
2873 Result = Instantiator.TransformFunctionProtoType(
2874 TLB, Proto, ThisContext, ThisTypeQuals,
2876 bool &Changed) {
return false; });
2878 Result = Instantiator.TransformType(TLB, TL);
2892 bool Changed =
false;
2893 TemplateInstantiator Instantiator(*
this, Args, Loc,
DeclarationName());
2894 return Instantiator.TransformExceptionSpec(Loc, ESI, ExceptionStorage,
2905 ESI, ExceptionStorage, Args))
2914 struct GetContainedInventedTypeParmVisitor :
2915 public TypeVisitor<GetContainedInventedTypeParmVisitor,
2916 TemplateTypeParmDecl *> {
2917 using TypeVisitor<GetContainedInventedTypeParmVisitor,
2923 return Visit(
T.getTypePtr());
2927 const TemplateTypeParmType *
T) {
2928 if (!
T->getDecl() || !
T->getDecl()->isImplicit())
2930 return T->getDecl();
2936 TemplateTypeParmDecl *VisitPointerType(
const PointerType *
T) {
2940 TemplateTypeParmDecl *VisitBlockPointerType(
const BlockPointerType *
T) {
2944 TemplateTypeParmDecl *VisitReferenceType(
const ReferenceType *
T) {
2945 return Visit(
T->getPointeeTypeAsWritten());
2948 TemplateTypeParmDecl *VisitMemberPointerType(
const MemberPointerType *
T) {
2952 TemplateTypeParmDecl *VisitArrayType(
const ArrayType *
T) {
2953 return Visit(
T->getElementType());
2956 TemplateTypeParmDecl *VisitDependentSizedExtVectorType(
2957 const DependentSizedExtVectorType *
T) {
2958 return Visit(
T->getElementType());
2961 TemplateTypeParmDecl *VisitVectorType(
const VectorType *
T) {
2962 return Visit(
T->getElementType());
2965 TemplateTypeParmDecl *VisitFunctionProtoType(
const FunctionProtoType *
T) {
2966 return VisitFunctionType(
T);
2969 TemplateTypeParmDecl *VisitFunctionType(
const FunctionType *
T) {
2973 TemplateTypeParmDecl *VisitParenType(
const ParenType *
T) {
2974 return Visit(
T->getInnerType());
2977 TemplateTypeParmDecl *VisitAttributedType(
const AttributedType *
T) {
2978 return Visit(
T->getModifiedType());
2981 TemplateTypeParmDecl *VisitMacroQualifiedType(
const MacroQualifiedType *
T) {
2982 return Visit(
T->getUnderlyingType());
2985 TemplateTypeParmDecl *VisitAdjustedType(
const AdjustedType *
T) {
2986 return Visit(
T->getOriginalType());
2989 TemplateTypeParmDecl *VisitPackExpansionType(
const PackExpansionType *
T) {
2990 return Visit(
T->getPattern());
2999 bool EvaluateConstraints) {
3006 Index =
SemaRef.ArgPackSubstIndex;
3035 bool ExpectParameterPack,
bool EvaluateConstraint) {
3055 }
else if (ExpectParameterPack) {
3061 diag::err_function_parameter_pack_without_parameter_packs)
3085 GetContainedInventedTypeParmVisitor().Visit(OldTSI->
getType())) {
3087 auto *Inst = cast_or_null<TemplateTypeParmDecl>(
3092 if (Inst && !Inst->getTypeConstraint()) {
3159 "Cannot perform an instantiation without some context on the "
3160 "instantiation stack");
3162 TemplateInstantiator Instantiator(*
this, TemplateArgs, Loc,
3164 return Instantiator.TransformFunctionTypeParams(
3165 Loc, Params,
nullptr, ExtParamInfos, ParamTypes, OutParams, ParamInfos);
3174 Expr *PatternExpr = Param->getUninstantiatedDefaultArg();
3178 if (AlreadyInstantiating) {
3179 Param->setInvalidDecl();
3180 return Diag(Param->getBeginLoc(), diag::err_recursive_default_argument)
3198 std::optional<LocalInstantiationScope> LIS;
3209 if (addInstantiatedParametersToScope(FD, PatternFD, *LIS, TemplateArgs))
3226 Param->getLocation(),
3231 Result = InitSeq.Perform(*
this, Entity, Kind, ResultE);
3261 auto ComputeInfo = [&S, &TemplateArgs, BaseSourceRange, BaseEllipsisLoc](
3268 if (IsLateExpansionAttempt) {
3273 return P.first.dyn_cast<
const SubstBuiltinTemplatePackType *>();
3275 if (!SawPackTypes) {
3287 BaseEllipsisLoc, BaseSourceRange, Unexpanded, TemplateArgs,
3292 if (ComputeInfo(
Base.getTypeSourceInfo(),
false, Info))
3296 Out =
Base.getTypeSourceInfo();
3306 if (!Out->getType()->containsUnexpandedParameterPack())
3311 if (ComputeInfo(Out,
true, Info))
3324 for (
const auto &
Base : Pattern->
bases()) {
3325 if (!
Base.getType()->isDependentType()) {
3327 if (RD->isInvalidDecl())
3336 if (
Base.isPackExpansion()) {
3348 ArgsForSubst = &EmptyList;
3363 Instantiation,
Base.getSourceRange(),
Base.isVirtual(),
3364 Base.getAccessSpecifierAsWritten(), Expanded,
3366 InstantiatedBases.push_back(InstantiatedBase);
3375 EllipsisLoc =
Base.getEllipsisLoc();
3383 Base.getSourceRange().getBegin(),
3394 Base.getSourceRange(),
3396 Base.getAccessSpecifierAsWritten(),
3399 InstantiatedBases.push_back(InstantiatedBase);
3429 assert(!AlreadyInstantiating &&
"should have been caught by caller");
3432 return InstantiateClassImpl(PointOfInstantiation, Instantiation, Pattern,
3433 TemplateArgs, TSK, Complain);
3436bool Sema::InstantiateClassImpl(
3443 if (DiagnoseUninstantiableTemplate(PointOfInstantiation, Instantiation,
3445 Pattern, PatternDef, TSK, Complain))
3448 llvm::TimeTraceScope TimeScope(
"InstantiateClass", [&]() {
3449 llvm::TimeTraceMetadata M;
3450 llvm::raw_string_ostream OS(M.Detail);
3453 if (llvm::isTimeTraceVerbose()) {
3454 auto Loc = SourceMgr.getExpansionLoc(Instantiation->
getLocation());
3455 M.File = SourceMgr.getFilename(Loc);
3456 M.Line = SourceMgr.getExpansionLineNumber(Loc);
3461 Pattern = PatternDef;
3464 if (MemberSpecializationInfo *MSInfo
3466 MSInfo->setTemplateSpecializationKind(TSK);
3467 MSInfo->setPointOfInstantiation(PointOfInstantiation);
3468 }
else if (ClassTemplateSpecializationDecl *Spec
3469 = dyn_cast<ClassTemplateSpecializationDecl>(Instantiation)) {
3470 Spec->setTemplateSpecializationKind(TSK);
3471 Spec->setPointOfInstantiation(PointOfInstantiation);
3474 NonSFINAEContext _(*
this);
3475 InstantiatingTemplate Inst(*
this, PointOfInstantiation, Instantiation);
3476 if (Inst.isInvalid())
3478 PrettyDeclStackTraceEntry CrashInfo(Context, Instantiation, SourceLocation(),
3479 "instantiating class definition");
3483 ContextRAII SavedContext(*
this, Instantiation);
3484 EnterExpressionEvaluationContext EvalContext(
3485 *
this, Sema::ExpressionEvaluationContext::PotentiallyEvaluated);
3491 LocalInstantiationScope Scope(*
this, MergeWithParentScope);
3497 SavePendingParsedClassStateRAII SavedPendingParsedClassState(*
this);
3500 InstantiateAttrs(TemplateArgs, Pattern, Instantiation);
3510 Instantiation->
setTagKind(Pattern->getTagKind());
3513 if (SubstBaseSpecifiers(Instantiation, Pattern, TemplateArgs))
3516 TemplateDeclInstantiator Instantiator(*
this, Instantiation, TemplateArgs);
3517 Instantiator.setEvaluateConstraints(
false);
3518 SmallVector<Decl*, 4> Fields;
3520 LateInstantiatedAttrVec LateAttrs;
3521 Instantiator.enableLateAttributeInstantiation(&LateAttrs);
3523 bool MightHaveConstexprVirtualFunctions =
false;
3524 for (
auto *
Member : Pattern->decls()) {
3534 if (
Member->getDeclContext() != Pattern)
3545 if (
Member->isInvalidDecl()) {
3550 Decl *NewMember = Instantiator.Visit(
Member);
3552 if (FieldDecl *Field = dyn_cast<FieldDecl>(NewMember)) {
3553 Fields.push_back(Field);
3554 }
else if (EnumDecl *
Enum = dyn_cast<EnumDecl>(NewMember)) {
3560 Enum->isCompleteDefinition()) {
3561 MemberSpecializationInfo *MSInfo =
Enum->getMemberSpecializationInfo();
3562 assert(MSInfo &&
"no spec info for member enum specialization");
3566 }
else if (StaticAssertDecl *SA = dyn_cast<StaticAssertDecl>(NewMember)) {
3567 if (SA->isFailed()) {
3573 }
else if (CXXMethodDecl *MD = dyn_cast<CXXMethodDecl>(NewMember)) {
3576 MightHaveConstexprVirtualFunctions =
true;
3590 ActOnFields(
nullptr, Instantiation->
getLocation(), Instantiation, Fields,
3591 SourceLocation(), SourceLocation(), ParsedAttributesView());
3592 CheckCompletedCXXClass(
nullptr, Instantiation);
3597 if (ParsingClassDepth == 0)
3598 ActOnFinishCXXNonNestedClass();
3602 for (LateInstantiatedAttrVec::iterator I = LateAttrs.begin(),
3603 E = LateAttrs.end(); I != E; ++I) {
3604 assert(CurrentInstantiationScope == Instantiator.getStartingScope());
3605 CurrentInstantiationScope = I->Scope;
3609 auto *ThisContext = dyn_cast_or_null<CXXRecordDecl>(ND->getDeclContext());
3610 CXXThisScopeRAII ThisScope(*
this, ThisContext, Qualifiers(),
3611 ND->isCXXInstanceMember());
3616 I->NewDecl->addAttr(NewAttr);
3618 Instantiator.getStartingScope());
3620 Instantiator.disableLateAttributeInstantiation();
3623 ActOnFinishDelayedMemberInitializers(Instantiation);
3628 Instantiation->
setLocation(Pattern->getLocation());
3629 Instantiation->
setLocStart(Pattern->getInnerLocStart());
3635 if (Pattern->isDependentContext())
3636 PerformDependentDiagnostics(Pattern, TemplateArgs);
3641 P = Instantiator.delayed_partial_spec_begin(),
3642 PEnd = Instantiator.delayed_partial_spec_end();
3644 if (!Instantiator.InstantiateClassTemplatePartialSpecialization(
3645 P->first, P->second)) {
3654 P = Instantiator.delayed_var_partial_spec_begin(),
3655 PEnd = Instantiator.delayed_var_partial_spec_end();
3657 if (!Instantiator.InstantiateVarTemplatePartialSpecialization(
3658 P->first, P->second)) {
3674 MarkVTableUsed(PointOfInstantiation, Instantiation,
true);
3675 else if (MightHaveConstexprVirtualFunctions)
3676 MarkVirtualMembersReferenced(PointOfInstantiation, Instantiation,
3680 Consumer.HandleTagDeclDefinition(Instantiation);
3692 assert(!AlreadyInstantiating &&
"should have been caught by caller");
3698 Pattern, PatternDef, TSK,
true))
3700 Pattern = PatternDef;
3714 "instantiating enum definition");
3749 "pattern and instantiation disagree about init style");
3753 if (AlreadyInstantiating)
3755 return Diag(PointOfInstantiation,
3756 diag::err_default_member_initializer_cycle)
3765 Diag(PointOfInstantiation,
3766 diag::err_default_member_initializer_not_yet_parsed)
3767 << OutermostClass << Pattern;
3768 Diag(Pattern->getEndLoc(),
3769 diag::note_default_member_initializer_not_yet_parsed);
3779 "instantiating default member init");
3787 PointOfInstantiation, Instantiation,
CurContext};
3803 L->DefaultMemberInitializerInstantiated(Instantiation);
3812 struct PartialSpecMatchResult {
3838 !CTPSD->getMostRecentDecl()->isMemberSpecialization())
3858 std::optional<Sema::NonSFINAEContext> NSC(S);
3878 typedef PartialSpecMatchResult MatchResult;
3881 Template->getPartialSpecializations(PartialSpecs);
3894 if (
Template->getMostRecentDecl()->isMemberSpecialization() &&
3895 !Partial->getMostRecentDecl()->isMemberSpecialization())
3913 if (Matched.empty() && PrimaryStrictPackMatch)
3914 Matched = std::move(ExtraMatched);
3920 if (Matched.size() >= 1) {
3922 if (Matched.size() == 1) {
3935 PEnd = Matched.end();
3938 P->Partial, Best->Partial, PointOfInstantiation) ==
3947 PEnd = Matched.end();
3950 P->Partial, Best->Partial,
3951 PointOfInstantiation) != Best->Partial) {
3961 S.
Diag(PointOfInstantiation,
3962 diag::err_partial_spec_ordering_ambiguous)
3963 << ClassTemplateSpec;
3967 PEnd = Matched.end();
3969 S.
Diag(P->Partial->getLocation(), diag::note_partial_spec_match)
3971 P->Partial->getTemplateParameters(), *P->Args);
3986 if (
auto *PartialSpec =
3989 while (PartialSpec->getInstantiatedFromMember()) {
3992 if (PartialSpec->isMemberSpecialization())
3995 PartialSpec = PartialSpec->getInstantiatedFromMember();
3997 Pattern = PartialSpec;
4000 while (
Template->getInstantiatedFromMemberTemplate()) {
4003 if (
Template->isMemberSpecialization())
4008 Pattern =
Template->getTemplatedDecl();
4018 bool PrimaryStrictPackMatch) {
4027 if (AlreadyInstantiating)
4030 bool HadAvaibilityWarning =
4036 ClassTemplateSpec, TSK,
4037 PrimaryStrictPackMatch);
4042 bool Err = InstantiateClassImpl(
4043 PointOfInstantiation, ClassTemplateSpec, Pattern.
get(),
4050 if (!Err && !HadAvaibilityWarning) {
4070 "Unexpected template specialization kind!");
4071 for (
auto *D : Instantiation->
decls()) {
4072 bool SuppressNew =
false;
4073 if (
auto *
Function = dyn_cast<FunctionDecl>(D)) {
4075 Function->getInstantiatedFromMemberFunction()) {
4077 if (
Function->getTrailingRequiresClause()) {
4085 if (
Function->hasAttr<ExcludeFromExplicitInstantiationAttr>())
4089 Function->getTemplateSpecializationKind();
4094 PointOfInstantiation, TSK,
Function, PrevTSK,
4095 Function->getPointOfInstantiation(), SuppressNew) ||
4108 Function->setTemplateSpecializationKind(TSK, PointOfInstantiation);
4118 std::make_pair(
Function, PointOfInstantiation));
4121 }
else if (
auto *Var = dyn_cast<VarDecl>(D)) {
4126 if (Var->
hasAttr<ExcludeFromExplicitInstantiationAttr>())
4130 assert(MSInfo &&
"No member specialization information?");
4159 }
else if (
auto *
Record = dyn_cast<CXXRecordDecl>(D)) {
4160 if (
Record->hasAttr<ExcludeFromExplicitInstantiationAttr>())
4168 if (
Record->isInjectedClassName() ||
Record->getPreviousDecl() ||
4173 assert(MSInfo &&
"No member specialization information?");
4179 if (
Context.getTargetInfo().getTriple().isOSWindows() &&
4199 assert(Pattern &&
"Missing instantiated-from-template information");
4201 if (!
Record->getDefinition()) {
4222 Record->getTemplateSpecializationKind() ==
4224 Record->setTemplateSpecializationKind(TSK);
4229 Pattern = cast_or_null<CXXRecordDecl>(
Record->getDefinition());
4233 }
else if (
auto *
Enum = dyn_cast<EnumDecl>(D)) {
4235 assert(MSInfo &&
"No member specialization information?");
4242 PointOfInstantiation, TSK,
Enum,
4248 if (
Enum->getDefinition())
4251 EnumDecl *Pattern =
Enum->getTemplateInstantiationPattern();
4252 assert(Pattern &&
"Missing instantiated-from-template information");
4263 }
else if (
auto *Field = dyn_cast<FieldDecl>(D)) {
4274 ClassPattern->
lookup(Field->getDeclName());
4307 TemplateInstantiator Instantiator(*
this, TemplateArgs,
4310 return Instantiator.TransformStmt(S);
4318 TemplateInstantiator Instantiator(*
this, TemplateArgs, Loc, Entity);
4319 return Instantiator.TransformTemplateArgument(Input, Output);
4326 TemplateInstantiator Instantiator(*
this, TemplateArgs,
SourceLocation(),
4328 return Instantiator.TransformTemplateArguments(Args.begin(), Args.end(), Out);
4335 TemplateInstantiator Instantiator(
4336 TemplateInstantiator::ForParameterMappingSubstitution, *
this, BaseLoc,
4338 return Instantiator.TransformTemplateArguments(Args.begin(), Args.end(), Out);
4346 TemplateInstantiator Instantiator(*
this, TemplateArgs,
4349 return Instantiator.TransformExpr(E);
4358 TemplateInstantiator Instantiator(*
this, TemplateArgs,
SourceLocation(),
4360 return Instantiator.TransformAddressOfOperand(E);
4376 TemplateInstantiator Instantiator(*
this, TemplateArgs,
SourceLocation(),
4378 Instantiator.setEvaluateConstraints(
false);
4379 return Instantiator.TransformExpr(E);
4385 TemplateInstantiator Instantiator(*
this, MLTAL,
SourceLocation(),
4394 *
this, ArgsAsWritten->
arguments().front().getSourceRange().getBegin(),
4397 ArgsAsWritten->
arguments().front().getSourceRange());
4402 if (Instantiator.TransformConceptTemplateArguments(
4427 struct ConstraintExprTransformer :
TreeTransform<ConstraintExprTransformer> {
4439 case Stmt::BinaryOperatorClass:
4440 case Stmt::ConceptSpecializationExprClass:
4441 case Stmt::ParenExprClass:
4442 case Stmt::UnresolvedLookupExprClass:
4443 return Base::TransformExpr(E);
4454 if (!(E->
getOpcode() == BinaryOperatorKind::BO_LAnd ||
4455 E->
getOpcode() == BinaryOperatorKind::BO_LOr))
4472 bool Uneval =
false) {
4474 return Base::TransformTemplateArgument(Input, Output, Uneval);
4481 bool IsAddressOfOperand =
false) {
4482 if (E->isConceptReference()) {
4490 ConstraintExprTransformer Transformer(*
this, MLTALForConstraint);
4492 Transformer.TransformExpr(
const_cast<Expr *
>(ConstraintExpr));
4498 bool CXXDirectInit) {
4499 TemplateInstantiator Instantiator(*
this, TemplateArgs,
SourceLocation(),
4501 return Instantiator.TransformInitializer(
Init, CXXDirectInit);
4510 TemplateInstantiator Instantiator(*
this, TemplateArgs,
4513 return Instantiator.TransformExprs(Exprs.data(), Exprs.size(),
4523 TemplateInstantiator Instantiator(*
this, TemplateArgs, NNS.
getBeginLoc(),
4525 return Instantiator.TransformNestedNameSpecifierLoc(NNS);
4531 TemplateInstantiator Instantiator(*
this, TemplateArgs, NameInfo.
getLoc(),
4533 return Instantiator.TransformDeclarationNameInfo(NameInfo);
4541 TemplateInstantiator Instantiator(*
this, TemplateArgs, NameLoc,
4543 return Instantiator.TransformTemplateName(QualifierLoc, TemplateKWLoc, Name,
4552 if (
const ParmVarDecl *PV = dyn_cast<ParmVarDecl>(D)) {
4553 if (
const FunctionDecl *FD = dyn_cast<FunctionDecl>(PV->getDeclContext())) {
4554 unsigned i = PV->getFunctionScopeIndex();
4557 if (i < FD->getNumParams() && FD->getParamDecl(i) == PV)
4558 return FD->getCanonicalDecl()->getParamDecl(i);
4564llvm::PointerUnion<Decl *, LocalInstantiationScope::DeclArgumentPack *> *
4568 Current = Current->Outer) {
4571 const Decl *CheckD = D;
4573 LocalDeclsMap::iterator
Found = Current->LocalDecls.find(CheckD);
4574 if (
Found != Current->LocalDecls.end())
4575 return &
Found->second;
4579 if (
const TagDecl *Tag = dyn_cast<TagDecl>(CheckD))
4586 if (!Current->CombineWithOuterScope)
4593llvm::PointerUnion<Decl *, LocalInstantiationScope::DeclArgumentPack *> *
4606 if (RD->isLocalClass())
4623 assert(
isa<LabelDecl>(D) &&
"declaration not instantiated in this scope");
4629 llvm::PointerUnion<Decl *, DeclArgumentPack *> &Stored = LocalDecls[D];
4630 if (Stored.isNull()) {
4634 while (Current->CombineWithOuterScope && Current->Outer) {
4635 Current = Current->Outer;
4636 assert(!Current->LocalDecls.contains(D) &&
4637 "Instantiated local in inner and outer scopes");
4641 }
else if (
DeclArgumentPack *Pack = dyn_cast<DeclArgumentPack *>(Stored)) {
4644 assert(
cast<Decl *>(Stored) == Inst &&
"Already instantiated this local");
4652 Pack->push_back(Inst);
4659 Current && Current->CombineWithOuterScope; Current = Current->Outer)
4660 assert(!Current->LocalDecls.contains(D) &&
4661 "Creating local pack after instantiation of local");
4665 llvm::PointerUnion<Decl *, DeclArgumentPack *> &Stored = LocalDecls[D];
4668 ArgumentPacks.push_back(Pack);
4673 if (llvm::is_contained(*Pack, D))
4680 unsigned NumExplicitArgs) {
4681 assert((!PartiallySubstitutedPack || PartiallySubstitutedPack == Pack) &&
4682 "Already have a partially-substituted pack");
4683 assert((!PartiallySubstitutedPack
4684 || NumArgsInPartiallySubstitutedPack == NumExplicitArgs) &&
4685 "Wrong number of arguments in partially-substituted pack");
4686 PartiallySubstitutedPack = Pack;
4687 ArgsInPartiallySubstitutedPack = ExplicitArgs;
4688 NumArgsInPartiallySubstitutedPack = NumExplicitArgs;
4693 unsigned *NumExplicitArgs)
const {
4695 *ExplicitArgs =
nullptr;
4696 if (NumExplicitArgs)
4697 *NumExplicitArgs = 0;
4700 Current = Current->Outer) {
4701 if (Current->PartiallySubstitutedPack) {
4703 *ExplicitArgs = Current->ArgsInPartiallySubstitutedPack;
4704 if (NumExplicitArgs)
4705 *NumExplicitArgs = Current->NumArgsInPartiallySubstitutedPack;
4707 return Current->PartiallySubstitutedPack;
4710 if (!Current->CombineWithOuterScope)
This file provides AST data structures related to concepts.
Defines the clang::ASTContext interface.
This file provides some common utility functions for processing Lambda related AST Constructs.
This file defines the classes used to store parsed information about declaration-specifiers and decla...
Defines the C++ template declaration subclasses.
Defines Expressions and AST nodes for C++2a concepts.
Defines the clang::LangOptions interface.
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
static TemplateDeductionResult DeduceTemplateArguments(Sema &S, TemplateParameterList *TemplateParams, ArrayRef< TemplateArgument > Ps, ArrayRef< TemplateArgument > As, TemplateDeductionInfo &Info, SmallVectorImpl< DeducedTemplateArgument > &Deduced, bool NumberOfArgumentsMustMatch, bool PartialOrdering, PackFold PackFold, bool *HasDeducedAnyParam)
static bool PreparePackForExpansion(Sema &S, const CXXBaseSpecifier &Base, const MultiLevelTemplateArgumentList &TemplateArgs, TypeSourceInfo *&Out, UnexpandedInfo &Info)
static const Decl * getCanonicalParmVarDecl(const Decl *D)
static ActionResult< CXXRecordDecl * > getPatternForClassTemplateSpecialization(Sema &S, SourceLocation PointOfInstantiation, ClassTemplateSpecializationDecl *ClassTemplateSpec, TemplateSpecializationKind TSK, bool PrimaryStrictPackMatch)
Get the instantiation pattern to use to instantiate the definition of a given ClassTemplateSpecializa...
static bool NeedsInstantiationAsFunctionType(TypeSourceInfo *T)
static concepts::Requirement::SubstitutionDiagnostic * createSubstDiag(Sema &S, TemplateDeductionInfo &Info, Sema::EntityPrinter Printer)
static std::string convertCallArgsToString(Sema &S, llvm::ArrayRef< const Expr * > Args)
Defines the clang::TypeLoc interface and its subclasses.
C Language Family Type Representation.
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
const clang::PrintingPolicy & getPrintingPolicy() const
The result of parsing/analyzing an expression, statement etc.
Attr - This represents one attribute.
A builtin binary operation expression such as "x + y" or "x <= y".
SourceLocation getOperatorLoc() const
static BinaryOperator * Create(const ASTContext &C, Expr *lhs, Expr *rhs, Opcode opc, QualType ResTy, ExprValueKind VK, ExprObjectKind OK, SourceLocation opLoc, FPOptionsOverride FPFeatures)
Represents a base class of a C++ class.
SourceLocation getUsedLocation() const
Retrieve the location where this default argument was actually used.
const ParmVarDecl * getParam() const
Represents a C++ struct/union/class.
Decl * getLambdaContextDecl() const
Retrieve the declaration that provides additional context for a lambda, when the normal declaration c...
const FunctionDecl * isLocalClass() const
If the class is a local class [class.local], returns the enclosing function declaration.
CXXRecordDecl * getInstantiatedFromMemberClass() const
If this record is an instantiation of a member class, retrieves the member class from which it was in...
bool isLambda() const
Determine whether this class describes a lambda function object.
CXXRecordDecl * getDefinition() const
unsigned getNumBases() const
Retrieves the number of base classes of this class.
const CXXRecordDecl * getTemplateInstantiationPattern() const
Retrieve the record declaration from which this record could be instantiated.
TemplateSpecializationKind getTemplateSpecializationKind() const
Determine whether this particular class is a specialization or instantiation of a class template or m...
ClassTemplateDecl * getDescribedClassTemplate() const
Retrieves the class template that is described by this class declaration.
MemberSpecializationInfo * getMemberSpecializationInfo() const
If this class is an instantiation of a member class of a class template specialization,...
CXXMethodDecl * getLambdaCallOperator() const
Retrieve the lambda call operator of the closure type if this is a closure type.
CXXRecordDecl * getCanonicalDecl() override
Retrieves the "canonical" declaration of the given declaration.
Declaration of a class template.
ClassTemplateDecl * getMostRecentDecl()
llvm::FoldingSetVector< ClassTemplatePartialSpecializationDecl > & getPartialSpecializations() const
Retrieve the set of partial specializations of this class template.
Represents a class template specialization, which refers to a class template with a given set of temp...
TemplateSpecializationKind getSpecializationKind() const
Determine the kind of specialization that this declaration represents.
ClassTemplateDecl * getSpecializedTemplate() const
Retrieve the template that this specialization specializes.
bool isClassScopeExplicitSpecialization() const
Is this an explicit specialization at class scope (within the class that owns the primary template)?
llvm::PointerUnion< ClassTemplateDecl *, ClassTemplatePartialSpecializationDecl * > getSpecializedTemplateOrPartial() const
Retrieve the class template or class template partial specialization which was specialized by this.
const TemplateArgumentList & getTemplateArgs() const
Retrieve the template arguments of the class template specialization.
const TemplateArgumentList & getTemplateInstantiationArgs() const
Retrieve the set of template arguments that should be used to instantiate members of the class templa...
void setInstantiationOf(ClassTemplatePartialSpecializationDecl *PartialSpec, const TemplateArgumentList *TemplateArgs)
Note that this class template specialization is actually an instantiation of the given class template...
NamedDecl * getFoundDecl() const
Represents the specialization of a concept - evaluates to a prvalue of type bool.
const ASTTemplateArgumentListInfo * getTemplateArgsAsWritten() const
ConceptDecl * getNamedConcept() const
const TypeClass * getTypePtr() const
The result of a constraint satisfaction check, containing the necessary information to diagnose an un...
bool HasSubstitutionFailure()
static DeclAccessPair make(NamedDecl *D, AccessSpecifier AS)
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
bool isFileContext() const
DeclContextLookupResult lookup_result
bool isDependentContext() const
Determines whether this context is dependent on a template parameter.
lookup_result lookup(DeclarationName Name) const
lookup - Find the declarations (if any) with the given Name in this context.
RecordDecl * getOuterLexicalRecordContext()
Retrieve the outermost lexically enclosing record context.
decl_range decls() const
decls_begin/decls_end - Iterate over the declarations stored in this context.
SourceLocation getLocation() const
Decl - This represents one declaration (or definition), e.g.
Decl * getPreviousDecl()
Retrieve the previous declaration that declares the same entity as this declaration,...
TemplateDecl * getDescribedTemplate() const
If this is a declaration that describes some template, this method returns that template declaration.
FriendObjectKind getFriendObjectKind() const
Determines whether this declaration is the object of a friend declaration and, if so,...
bool isParameterPack() const
Whether this declaration is a parameter pack.
void setInvalidDecl(bool Invalid=true)
setInvalidDecl - Indicates the Decl had a semantic error.
bool isFileContextDecl() const
static Decl * castFromDeclContext(const DeclContext *)
unsigned getTemplateDepth() const
Determine the number of levels of template parameter surrounding this declaration.
DeclContext * getNonTransparentDeclContext()
Return the non transparent context.
bool isInvalidDecl() const
SourceLocation getLocation() const
void setLocation(SourceLocation L)
bool isDefinedOutsideFunctionOrMethod() const
isDefinedOutsideFunctionOrMethod - This predicate returns true if this scoped decl is defined outside...
DeclContext * getDeclContext()
void setDeclContext(DeclContext *DC)
setDeclContext - Set both the semantic and lexical DeclContext to DC.
DeclContext * getLexicalDeclContext()
getLexicalDeclContext - The declaration context where this Decl was lexically declared (LexicalDC).
void setVisibleDespiteOwningModule()
Set that this declaration is globally visible, even if it came from a module that is not visible.
The name of a declaration.
SourceLocation getInnerLocStart() const
Return start of source range ignoring outer template declarations.
NestedNameSpecifier getQualifier() const
Retrieve the nested-name-specifier that qualifies the name of this declaration, if it was present in ...
TypeSourceInfo * getTypeSourceInfo() const
RAII object that enters a new expression evaluation context.
MemberSpecializationInfo * getMemberSpecializationInfo() const
If this enumeration is an instantiation of a member enumeration of a class template specialization,...
EnumDecl * getInstantiatedFromMemberEnum() const
Returns the enumeration (declared within the template) from which this enumeration type was instantia...
EnumDecl * getDefinition() const
This represents one expression.
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) const
EvaluateKnownConstInt - Call EvaluateAsRValue and return the folded integer.
bool isInstantiationDependent() const
Whether this expression is instantiation-dependent, meaning that it depends in some way on.
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
bool hasPlaceholderType() const
Returns whether this expression has a placeholder type.
ExprDependence getDependence() const
Represents difference between two FPOptions values.
Represents a member of a struct/union/class.
Expr * getInClassInitializer() const
Get the C++11 default member initializer for this member, or null if one has not been set.
bool hasInClassInitializer() const
Determine whether this member has a C++11 default member initializer.
InClassInitStyle getInClassInitStyle() const
Get the kind of (C++11) default member initializer that this field has.
const RecordDecl * getParent() const
Returns the parent of this field declaration, which is the struct in which this field is defined.
Represents a function declaration or definition.
ArrayRef< ParmVarDecl * > parameters() const
FunctionDecl * getTemplateInstantiationPattern(bool ForDefinition=true) const
Retrieve the function declaration from which this function could be instantiated, if it is an instant...
FunctionTemplateDecl * getPrimaryTemplate() const
Retrieve the primary template that this function template specialization either specializes or was in...
bool isConstexpr() const
Whether this is a (C++11) constexpr function or constexpr constructor.
bool isVirtualAsWritten() const
Whether this function is marked as virtual explicitly.
static FunctionParmPackExpr * Create(const ASTContext &Context, QualType T, ValueDecl *ParamPack, SourceLocation NameLoc, ArrayRef< ValueDecl * > Params)
ValueDecl * getExpansion(unsigned I) const
Get an expansion of the parameter pack by index.
ValueDecl *const * iterator
Iterators over the parameters which the parameter pack expanded into.
ValueDecl * getParameterPack() const
Get the parameter pack which this expression refers to.
unsigned getNumExpansions() const
Get the number of parameters in this parameter pack.
SourceLocation getParameterPackLocation() const
Get the location of the parameter pack.
Represents a prototype with parameter type info, e.g.
ExtProtoInfo getExtProtoInfo() const
Declaration of a template function.
FunctionDecl * getTemplatedDecl() const
Get the underlying function declaration of the template.
ArrayRef< ParmVarDecl * > getParams() const
Interesting information about a specific parameter that can't simply be reflected in parameter's type...
QualType getReturnType() const
ArrayRef< TemplateArgument > getTemplateArguments() const
const TypeClass * getTypePtr() const
Describes the kind of initialization being performed, along with location information for tokens rela...
static InitializationKind CreateCopy(SourceLocation InitLoc, SourceLocation EqualLoc, bool AllowExplicitConvs=false)
Create a copy initialization.
Describes an entity that is being initialized.
static InitializedEntity InitializeParameter(ASTContext &Context, ParmVarDecl *Parm)
Create the initialization entity for a parameter.
A C++ lambda expression, which produces a function object (of unspecified type) that can be invoked l...
A stack-allocated class that identifies which local variable declaration instantiations are present i...
LocalInstantiationScope(Sema &SemaRef, bool CombineWithOuterScope=false, bool InstantiatingLambdaOrBlock=false)
void SetPartiallySubstitutedPack(NamedDecl *Pack, const TemplateArgument *ExplicitArgs, unsigned NumExplicitArgs)
Note that the given parameter pack has been partially substituted via explicit specification of templ...
NamedDecl * getPartiallySubstitutedPack(const TemplateArgument **ExplicitArgs=nullptr, unsigned *NumExplicitArgs=nullptr) const
Retrieve the partially-substitued template parameter pack.
bool isLocalPackExpansion(const Decl *D)
Determine whether D is a pack expansion created in this scope.
SmallVector< ValueDecl *, 4 > DeclArgumentPack
A set of declarations.
llvm::PointerUnion< Decl *, DeclArgumentPack * > * getInstantiationOfIfExists(const Decl *D)
Similar to findInstantiationOf(), but it wouldn't assert if the instantiation was not found within th...
static void deleteScopes(LocalInstantiationScope *Scope, LocalInstantiationScope *Outermost)
deletes the given scope, and all outer scopes, down to the given outermost scope.
void InstantiatedLocal(const Decl *D, Decl *Inst)
void InstantiatedLocalPackArg(const Decl *D, VarDecl *Inst)
bool isLambdaOrBlock() const
Determine whether this scope is for instantiating a lambda or block.
void MakeInstantiatedLocalArgPack(const Decl *D)
llvm::PointerUnion< Decl *, DeclArgumentPack * > * findInstantiationOf(const Decl *D)
Find the instantiation of the declaration D within the current instantiation scope.
Provides information a specialization of a member of a class template, which may be a member function...
void setTemplateSpecializationKind(TemplateSpecializationKind TSK)
Set the template specialization kind.
TemplateSpecializationKind getTemplateSpecializationKind() const
Determine what kind of template specialization this is.
SourceLocation getPointOfInstantiation() const
Retrieve the first point of instantiation of this member.
void setPointOfInstantiation(SourceLocation POI)
Set the first point of instantiation.
Describes a module or submodule.
Data structure that captures multiple levels of template argument lists for use in template instantia...
bool hasTemplateArgument(unsigned Depth, unsigned Index) const
Determine whether there is a non-NULL template argument at the given depth and index.
const ArgList & getInnermost() const
Retrieve the innermost template argument list.
std::pair< Decl *, bool > getAssociatedDecl(unsigned Depth) const
A template-like entity which owns the whole pattern being substituted.
unsigned getNumLevels() const
Determine the number of levels in this template argument list.
unsigned getNumSubstitutedLevels() const
Determine the number of substituted levels in this template argument list.
unsigned getNewDepth(unsigned OldDepth) const
Determine how many of the OldDepth outermost template parameter lists would be removed by substitutin...
void setArgument(unsigned Depth, unsigned Index, TemplateArgument Arg)
Clear out a specific template argument.
bool isRewrite() const
Determine whether we are rewriting template parameters rather than substituting for them.
This represents a decl that may have a name.
IdentifierInfo * getIdentifier() const
Get the identifier that names this declaration, if there is one.
StringRef getName() const
Get the name of identifier for this declaration as a StringRef.
DeclarationName getDeclName() const
Get the actual, stored name of the declaration, which may be a special name.
virtual void getNameForDiagnostic(raw_ostream &OS, const PrintingPolicy &Policy, bool Qualified) const
Appends a human-readable name for this declaration into the given stream.
virtual void printName(raw_ostream &OS, const PrintingPolicy &Policy) const
Pretty-print the unqualified name of this declaration.
A C++ nested-name-specifier augmented with source location information.
SourceLocation getBeginLoc() const
Retrieve the location of the beginning of this nested-name-specifier.
Represents a C++ nested name specifier, such as "\::std::vector<int>::".
const Type * getAsType() const
@ Type
A type, stored as a Type*.
NonTypeTemplateParmDecl - Declares a non-type template parameter, e.g., "Size" in.
unsigned getPosition() const
Get the position of the template parameter within its parameter list.
bool isParameterPack() const
Whether this parameter is a non-type template parameter pack.
unsigned getDepth() const
Get the nesting depth of the template parameter.
SourceLocation getEllipsisLoc() const
TypeLoc getPatternLoc() const
Represents a parameter to a function.
unsigned getFunctionScopeIndex() const
Returns the index of this parameter in its prototype or method scope.
SourceLocation getExplicitObjectParamThisLoc() const
void setUnparsedDefaultArg()
Specify that this parameter has an unparsed default argument.
bool hasUnparsedDefaultArg() const
Determines whether this parameter has a default argument that has not yet been parsed.
void setUninstantiatedDefaultArg(Expr *arg)
void setScopeInfo(unsigned scopeDepth, unsigned parameterIndex)
bool hasUninstantiatedDefaultArg() const
bool hasInheritedDefaultArg() const
void setExplicitObjectParameterLoc(SourceLocation Loc)
Expr * getUninstantiatedDefaultArg()
unsigned getFunctionScopeDepth() const
void setHasInheritedDefaultArg(bool I=true)
PredefinedIdentKind getIdentKind() const
SourceLocation getLocation() const
PrettyDeclStackTraceEntry - If a crash occurs in the parser while parsing something related to a decl...
A (possibly-)qualified type.
QualType getNonLValueExprType(const ASTContext &Context) const
Determine the type of a (typically non-lvalue) expression with the specified result type.
void addConst()
Add the const type qualifier to this QualType.
bool isNull() const
Return true if this QualType doesn't point to a type yet.
void print(raw_ostream &OS, const PrintingPolicy &Policy, const Twine &PlaceHolder=Twine(), unsigned Indentation=0) const
The collection of all-type qualifiers we support.
void removeObjCLifetime()
Represents a struct/union/class.
bool isMemberSpecialization() const
Determines whether this template was a specialization of a member template.
Represents the body of a requires-expression.
C++2a [expr.prim.req]: A requires-expression provides a concise way to express requirements on templa...
SourceLocation getLParenLoc() const
SourceLocation getRParenLoc() const
RequiresExprBodyDecl * getBody() const
Scope - A scope is a transient data structure that is used while parsing the program.
PartialDiagnostic PDiag(unsigned DiagID=0)
Build a partial diagnostic.
SemaDiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID)
Emit a diagnostic.
RAII object used to change the argument pack substitution index within a Sema object.
RAII object used to temporarily allow the C++ 'this' expression to be used, with the given qualifiers...
For a defaulted function, the kind of defaulted function that it is.
DefaultedComparisonKind asComparison() const
bool isSpecialMember() const
bool isComparison() const
CXXSpecialMemberKind asSpecialMember() const
A helper class for building up ExtParameterInfos.
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.
llvm::DenseSet< Module * > LookupModulesCache
Cache of additional modules that should be used for name lookup within the current template instantia...
bool SubstTypeConstraint(TemplateTypeParmDecl *Inst, const TypeConstraint *TC, const MultiLevelTemplateArgumentList &TemplateArgs, bool EvaluateConstraint)
SmallVector< CodeSynthesisContext, 16 > CodeSynthesisContexts
List of active code synthesis contexts.
LocalInstantiationScope * CurrentInstantiationScope
The current instantiation scope used to store local variables.
TemplateArgumentLoc getTrivialTemplateArgumentLoc(const TemplateArgument &Arg, QualType NTTPType, SourceLocation Loc, NamedDecl *TemplateParam=nullptr)
Allocate a TemplateArgumentLoc where all locations have been initialized to the given location.
DefaultedFunctionKind getDefaultedFunctionKind(const FunctionDecl *FD)
Determine the kind of defaulting that would be done for a given function.
ExprResult SubstConceptTemplateArguments(const ConceptSpecializationExpr *CSE, const Expr *ConstraintExpr, const MultiLevelTemplateArgumentList &MLTAL)
Substitute concept template arguments in the constraint expression of a concept-id.
NamedDecl * FindInstantiatedDecl(SourceLocation Loc, NamedDecl *D, const MultiLevelTemplateArgumentList &TemplateArgs, bool FindingInstantiatedContext=false)
Find the instantiation of the given declaration within the current instantiation.
llvm::function_ref< void(SourceLocation, PartialDiagnostic)> InstantiationContextDiagFuncRef
TemplateName SubstTemplateName(SourceLocation TemplateKWLoc, NestedNameSpecifierLoc &QualifierLoc, TemplateName Name, SourceLocation NameLoc, const MultiLevelTemplateArgumentList &TemplateArgs)
ParmVarDecl * SubstParmVarDecl(ParmVarDecl *D, const MultiLevelTemplateArgumentList &TemplateArgs, int indexAdjustment, UnsignedOrNone NumExpansions, bool ExpectParameterPack, bool EvaluateConstraints=true)
void InstantiateClassTemplateSpecializationMembers(SourceLocation PointOfInstantiation, ClassTemplateSpecializationDecl *ClassTemplateSpec, TemplateSpecializationKind TSK)
Instantiate the definitions of all of the members of the given class template specialization,...
ClassTemplatePartialSpecializationDecl * getMoreSpecializedPartialSpecialization(ClassTemplatePartialSpecializationDecl *PS1, ClassTemplatePartialSpecializationDecl *PS2, SourceLocation Loc)
Returns the more specialized class template partial specialization according to the rules of partial ...
ExprResult SubstInitializer(Expr *E, const MultiLevelTemplateArgumentList &TemplateArgs, bool CXXDirectInit)
llvm::function_ref< void(llvm::raw_ostream &)> EntityPrinter
void SubstExceptionSpec(FunctionDecl *New, const FunctionProtoType *Proto, const MultiLevelTemplateArgumentList &Args)
concepts::Requirement::SubstitutionDiagnostic * createSubstDiagAt(SourceLocation Location, EntityPrinter Printer)
create a Requirement::SubstitutionDiagnostic with only a SubstitutedEntity and DiagLoc using ASTConte...
bool SubstExprs(ArrayRef< Expr * > Exprs, bool IsCall, const MultiLevelTemplateArgumentList &TemplateArgs, SmallVectorImpl< Expr * > &Outputs)
Substitute the given template arguments into a list of expressions, expanding pack expansions if requ...
StmtResult SubstStmt(Stmt *S, const MultiLevelTemplateArgumentList &TemplateArgs)
bool InstantiateClassTemplateSpecialization(SourceLocation PointOfInstantiation, ClassTemplateSpecializationDecl *ClassTemplateSpec, TemplateSpecializationKind TSK, bool Complain, bool PrimaryStrictPackMatch)
ExprResult SubstExpr(Expr *E, const MultiLevelTemplateArgumentList &TemplateArgs)
DiagnosticsEngine & getDiagnostics() const
bool CheckParameterPacksForExpansion(SourceLocation EllipsisLoc, SourceRange PatternRange, ArrayRef< UnexpandedParameterPack > Unexpanded, const MultiLevelTemplateArgumentList &TemplateArgs, bool FailOnPackProducingTemplates, bool &ShouldExpand, bool &RetainExpansion, UnsignedOrNone &NumExpansions, bool Diagnose=true)
Determine whether we could expand a pack expansion with the given set of parameter packs into separat...
ExprResult SubstConstraintExprWithoutSatisfaction(Expr *E, const MultiLevelTemplateArgumentList &TemplateArgs)
void PrintInstantiationStack()
ASTContext & getASTContext() const
TypeSourceInfo * SubstType(TypeSourceInfo *T, const MultiLevelTemplateArgumentList &TemplateArgs, SourceLocation Loc, DeclarationName Entity, bool AllowDeducedTST=false)
Perform substitution on the type T with a given set of template arguments.
void InstantiateVariableDefinition(SourceLocation PointOfInstantiation, VarDecl *Var, bool Recursive=false, bool DefinitionRequired=false, bool AtEndOfTU=false)
Instantiate the definition of the given variable from its template.
void ActOnStartCXXInClassMemberInitializer()
Enter a new C++ default initializer scope.
PrintingPolicy getPrintingPolicy() const
Retrieve a suitable printing policy for diagnostics.
bool pushCodeSynthesisContext(CodeSynthesisContext Ctx)
bool SubstTemplateArguments(ArrayRef< TemplateArgumentLoc > Args, const MultiLevelTemplateArgumentList &TemplateArgs, TemplateArgumentListInfo &Outputs)
Sema(Preprocessor &pp, ASTContext &ctxt, ASTConsumer &consumer, TranslationUnitKind TUKind=TU_Complete, CodeCompleteConsumer *CompletionConsumer=nullptr)
void InstantiateAttrs(const MultiLevelTemplateArgumentList &TemplateArgs, const Decl *Pattern, Decl *Inst, LateInstantiatedAttrVec *LateAttrs=nullptr, LocalInstantiationScope *OuterMostScope=nullptr)
const LangOptions & getLangOpts() const
void collectUnexpandedParameterPacks(TemplateArgument Arg, SmallVectorImpl< UnexpandedParameterPack > &Unexpanded)
Collect the set of unexpanded parameter packs within the given template argument.
bool SubstTemplateArgumentsInParameterMapping(ArrayRef< TemplateArgumentLoc > Args, SourceLocation BaseLoc, const MultiLevelTemplateArgumentList &TemplateArgs, TemplateArgumentListInfo &Out)
void InstantiateClassMembers(SourceLocation PointOfInstantiation, CXXRecordDecl *Instantiation, const MultiLevelTemplateArgumentList &TemplateArgs, TemplateSpecializationKind TSK)
Instantiates the definitions of all of the member of the given class, which is an instantiation of a ...
DeclarationNameInfo SubstDeclarationNameInfo(const DeclarationNameInfo &NameInfo, const MultiLevelTemplateArgumentList &TemplateArgs)
Do template substitution on declaration name info.
void MarkVTableUsed(SourceLocation Loc, CXXRecordDecl *Class, bool DefinitionRequired=false)
Note that the vtable for the given class was used at the given location.
TemplateArgument getPackSubstitutedTemplateArgument(TemplateArgument Arg) const
void popCodeSynthesisContext()
bool usesPartialOrExplicitSpecialization(SourceLocation Loc, ClassTemplateSpecializationDecl *ClassTemplateSpec)
bool CheckLoopHintExpr(Expr *E, SourceLocation Loc, bool AllowZero)
CXXBaseSpecifier * CheckBaseSpecifier(CXXRecordDecl *Class, SourceRange SpecifierRange, bool Virtual, AccessSpecifier Access, TypeSourceInfo *TInfo, SourceLocation EllipsisLoc)
Check the validity of a C++ base class specifier.
UnparsedDefaultArgInstantiationsMap UnparsedDefaultArgInstantiations
A mapping from parameters with unparsed default arguments to the set of instantiations of each parame...
bool SubstParmTypes(SourceLocation Loc, ArrayRef< ParmVarDecl * > Params, const FunctionProtoType::ExtParameterInfo *ExtParamInfos, const MultiLevelTemplateArgumentList &TemplateArgs, SmallVectorImpl< QualType > &ParamTypes, SmallVectorImpl< ParmVarDecl * > *OutParams, ExtParameterInfoBuilder &ParamInfos)
Substitute the given template arguments into the given set of parameters, producing the set of parame...
DeclContext * CurContext
CurContext - This is the current declaration context of parsing.
MultiLevelTemplateArgumentList getTemplateInstantiationArgs(const NamedDecl *D, const DeclContext *DC=nullptr, bool Final=false, std::optional< ArrayRef< TemplateArgument > > Innermost=std::nullopt, bool RelativeToPrimary=false, const FunctionDecl *Pattern=nullptr, bool ForConstraintInstantiation=false, bool SkipForSpecialization=false, bool ForDefaultArgumentSubstitution=false)
Retrieve the template argument list(s) that should be used to instantiate the definition of the given...
std::deque< PendingImplicitInstantiation > PendingLocalImplicitInstantiations
The queue of implicit template instantiations that are required and must be performed within the curr...
ParmVarDecl * CheckParameter(DeclContext *DC, SourceLocation StartLoc, SourceLocation NameLoc, const IdentifierInfo *Name, QualType T, TypeSourceInfo *TSInfo, StorageClass SC)
bool CheckFunctionConstraints(const FunctionDecl *FD, ConstraintSatisfaction &Satisfaction, SourceLocation UsageLoc=SourceLocation(), bool ForOverloadResolution=false)
Check whether the given function decl's trailing requires clause is satisfied, if any.
bool CheckSpecializationInstantiationRedecl(SourceLocation NewLoc, TemplateSpecializationKind ActOnExplicitInstantiationNewTSK, NamedDecl *PrevDecl, TemplateSpecializationKind PrevTSK, SourceLocation PrevPtOfInstantiation, bool &SuppressNew)
Diagnose cases where we have an explicit template specialization before/after an explicit template in...
unsigned NonInstantiationEntries
The number of CodeSynthesisContexts that are not template instantiations and, therefore,...
bool CheckNoInlineAttr(const Stmt *OrigSt, const Stmt *CurSt, const AttributeCommonInfo &A)
void ActOnFinishCXXInClassMemberInitializer(Decl *VarDecl, SourceLocation EqualLoc, ExprResult Init)
This is invoked after parsing an in-class initializer for a non-static C++ class member,...
bool inConstraintSubstitution() const
Determine whether we are currently performing constraint substitution.
bool CheckAlwaysInlineAttr(const Stmt *OrigSt, const Stmt *CurSt, const AttributeCommonInfo &A)
void DiagnoseAvailabilityOfDecl(NamedDecl *D, ArrayRef< SourceLocation > Locs, const ObjCInterfaceDecl *UnknownObjCClass, bool ObjCPropertyAccess, bool AvoidPartialAvailabilityChecks, ObjCInterfaceDecl *ClassReceiver)
bool AttachTypeConstraint(NestedNameSpecifierLoc NS, DeclarationNameInfo NameInfo, TemplateDecl *NamedConcept, NamedDecl *FoundDecl, const TemplateArgumentListInfo *TemplateArgs, TemplateTypeParmDecl *ConstrainedParameter, SourceLocation EllipsisLoc)
Attach a type-constraint to a template parameter.
std::pair< AvailabilityResult, const NamedDecl * > ShouldDiagnoseAvailabilityOfDecl(const NamedDecl *D, std::string *Message, ObjCInterfaceDecl *ClassReceiver)
The diagnostic we should emit for D, and the declaration that originated it, or AR_Available.
bool InstantiateInClassInitializer(SourceLocation PointOfInstantiation, FieldDecl *Instantiation, FieldDecl *Pattern, const MultiLevelTemplateArgumentList &TemplateArgs)
Instantiate the definition of a field from the given pattern.
UnsignedOrNone ArgPackSubstIndex
The current index into pack expansion arguments that will be used for substitution of parameter packs...
bool InstantiateClass(SourceLocation PointOfInstantiation, CXXRecordDecl *Instantiation, CXXRecordDecl *Pattern, const MultiLevelTemplateArgumentList &TemplateArgs, TemplateSpecializationKind TSK, bool Complain=true)
Instantiate the definition of a class from a given pattern.
bool SubstTemplateArgument(const TemplateArgumentLoc &Input, const MultiLevelTemplateArgumentList &TemplateArgs, TemplateArgumentLoc &Output, SourceLocation Loc={}, const DeclarationName &Entity={})
void InstantiateFunctionDefinition(SourceLocation PointOfInstantiation, FunctionDecl *Function, bool Recursive=false, bool DefinitionRequired=false, bool AtEndOfTU=false)
Instantiate the definition of the given function from its template.
bool SubstDefaultArgument(SourceLocation Loc, ParmVarDecl *Param, const MultiLevelTemplateArgumentList &TemplateArgs, bool ForCallExpr=false)
Substitute the given template arguments into the default argument.
ExprResult SubstConstraintExpr(Expr *E, const MultiLevelTemplateArgumentList &TemplateArgs)
@ ConstantEvaluated
The current context is "potentially evaluated" in C++11 terms, but the expression is evaluated at com...
@ PotentiallyEvaluated
The current expression is potentially evaluated at run time, which means that code may be generated t...
unsigned LastEmittedCodeSynthesisContextDepth
The depth of the context stack at the point when the most recent error or warning was produced.
bool inParameterMappingSubstitution() const
NestedNameSpecifierLoc SubstNestedNameSpecifierLoc(NestedNameSpecifierLoc NNS, const MultiLevelTemplateArgumentList &TemplateArgs)
bool RebuildingImmediateInvocation
Whether the AST is currently being rebuilt to correct immediate invocations.
SmallVector< ExpressionEvaluationContextRecord, 8 > ExprEvalContexts
A stack of expression evaluation contexts.
bool DiagnoseUninstantiableTemplate(SourceLocation PointOfInstantiation, NamedDecl *Instantiation, bool InstantiatedFromMember, const NamedDecl *Pattern, const NamedDecl *PatternDef, TemplateSpecializationKind TSK, bool Complain=true, bool *Unreachable=nullptr)
Determine whether we would be unable to instantiate this template (because it either has no definitio...
DiagnosticsEngine & Diags
bool AttachBaseSpecifiers(CXXRecordDecl *Class, MutableArrayRef< CXXBaseSpecifier * > Bases)
Performs the actual work of attaching the given base class specifiers to a C++ class.
friend class InitializationSequence
SmallVector< Module *, 16 > CodeSynthesisContextLookupModules
Extra modules inspected when performing a lookup during a template instantiation.
ExprResult ConvertParamDefaultArgument(ParmVarDecl *Param, Expr *DefaultArg, SourceLocation EqualLoc)
TemplateDeductionResult DeduceTemplateArguments(ClassTemplatePartialSpecializationDecl *Partial, ArrayRef< TemplateArgument > TemplateArgs, sema::TemplateDeductionInfo &Info)
void runWithSufficientStackSpace(SourceLocation Loc, llvm::function_ref< void()> Fn)
Run some code with "sufficient" stack space.
ExprResult CreateRecoveryExpr(SourceLocation Begin, SourceLocation End, ArrayRef< Expr * > SubExprs, QualType T=QualType())
Attempts to produce a RecoveryExpr after some AST node cannot be created.
bool InstantiateEnum(SourceLocation PointOfInstantiation, EnumDecl *Instantiation, EnumDecl *Pattern, const MultiLevelTemplateArgumentList &TemplateArgs, TemplateSpecializationKind TSK)
Instantiate the definition of an enum from a given pattern.
void UpdateExceptionSpec(FunctionDecl *FD, const FunctionProtoType::ExceptionSpecInfo &ESI)
ExprResult SubstCXXIdExpr(Expr *E, const MultiLevelTemplateArgumentList &TemplateArgs)
Substitute an expression as if it is a address-of-operand, which makes it act like a CXXIdExpression ...
std::string getTemplateArgumentBindingsText(const TemplateParameterList *Params, const TemplateArgumentList &Args)
Produces a formatted string that describes the binding of template parameters to template arguments.
bool SubstBaseSpecifiers(CXXRecordDecl *Instantiation, CXXRecordDecl *Pattern, const MultiLevelTemplateArgumentList &TemplateArgs)
Perform substitution on the base class specifiers of the given class template specialization.
void PerformDependentDiagnostics(const DeclContext *Pattern, const MultiLevelTemplateArgumentList &TemplateArgs)
TypeSourceInfo * CheckPackExpansion(TypeSourceInfo *Pattern, SourceLocation EllipsisLoc, UnsignedOrNone NumExpansions)
Construct a pack expansion type from the pattern of the pack expansion.
ASTMutationListener * getASTMutationListener() const
ExprResult ActOnFinishFullExpr(Expr *Expr, bool DiscardedValue)
TypeSourceInfo * SubstFunctionDeclType(TypeSourceInfo *T, const MultiLevelTemplateArgumentList &TemplateArgs, SourceLocation Loc, DeclarationName Entity, CXXRecordDecl *ThisContext, Qualifiers ThisTypeQuals, bool EvaluateConstraints=true)
A form of SubstType intended specifically for instantiating the type of a FunctionDecl.
Encodes a location in the source.
bool isValid() const
Return true if this is a valid SourceLocation object.
A trivial tuple used to represent a source range.
SourceLocation getBegin() const
Stmt - This represents one statement.
SourceLocation getEndLoc() const LLVM_READONLY
void printPretty(raw_ostream &OS, PrinterHelper *Helper, const PrintingPolicy &Policy, unsigned Indentation=0, StringRef NewlineSymbol="\n", const ASTContext *Context=nullptr) const
StmtClass getStmtClass() const
SourceRange getSourceRange() const LLVM_READONLY
SourceLocation tokens are not useful in isolation - they are low level value objects created/interpre...
SourceLocation getBeginLoc() const LLVM_READONLY
Represents the declaration of a struct/union/class/enum.
void setTagKind(TagKind TK)
void startDefinition()
Starts the definition of this tag declaration.
void setBraceRange(SourceRange R)
SourceLocation getNameLoc() const
A convenient class for passing around template argument information.
void setLAngleLoc(SourceLocation Loc)
void setRAngleLoc(SourceLocation Loc)
ArrayRef< TemplateArgumentLoc > arguments() const
A template argument list.
ArrayRef< TemplateArgument > asArray() const
Produce this as an array ref.
Location wrapper for a TemplateArgument.
const TemplateArgument & getArgument() const
Represents a template argument.
ArrayRef< TemplateArgument > getPackAsArray() const
Return the array of arguments in this template argument pack.
Expr * getAsExpr() const
Retrieve the template argument as an expression.
bool isDependent() const
Whether this template argument is dependent on a template parameter such that its result can change f...
pack_iterator pack_begin() const
Iterator referencing the first argument of a template argument pack.
bool isConceptOrConceptTemplateParameter() const
QualType getAsType() const
Retrieve the type for a type template argument.
TemplateName getAsTemplate() const
Retrieve the template name for a template name argument.
TemplateArgument getPackExpansionPattern() const
When the template argument is a pack expansion, returns the pattern of the pack expansion.
bool isNull() const
Determine whether this template argument has no value.
unsigned pack_size() const
The number of template arguments in the given template argument pack.
@ Template
The template argument is a template name that was provided for a template template parameter.
@ Pack
The template argument is actually a parameter pack.
@ Type
The template argument is a type.
@ Expression
The template argument is an expression, and we've not resolved it to one of the other forms yet,...
ArgKind getKind() const
Return the kind of stored template argument.
bool isPackExpansion() const
Determine whether this template argument is a pack expansion.
SmallVectorImpl< std::pair< ClassTemplateDecl *, ClassTemplatePartialSpecializationDecl * > >::iterator delayed_partial_spec_iterator
void InstantiateEnumDefinition(EnumDecl *Enum, EnumDecl *Pattern)
SmallVectorImpl< std::pair< VarTemplateDecl *, VarTemplatePartialSpecializationDecl * > >::iterator delayed_var_partial_spec_iterator
The base class of all kinds of template declarations (e.g., class, function, etc.).
TemplateParameterList * getTemplateParameters() const
Get the list of template parameters.
Represents a C++ template name within the type system.
TemplateDecl * getAsTemplateDecl(bool IgnoreDeduced=false) const
Retrieve the underlying template declaration that this template name refers to, if known.
@ Template
A single template declaration.
SubstTemplateTemplateParmPackStorage * getAsSubstTemplateTemplateParmPack() const
Retrieve the substituted template template parameter pack, if known.
Stores a list of template parameters for a TemplateDecl and its derived classes.
NamedDecl * getParam(unsigned Idx)
SourceRange getSourceRange() const LLVM_READONLY
SourceLocation getTemplateLoc() const
TemplateSpecCandidateSet - A set of generalized overload candidates, used in template specializations...
SourceLocation getLocation() const
TemplateSpecCandidate & addCandidate()
Add a new candidate with NumConversions conversion sequence slots to the overload set.
TemplateTemplateParmDecl - Declares a template template parameter, e.g., "T" in.
unsigned getDepth() const
Get the nesting depth of the template parameter.
Declaration of a template type parameter.
void setTypeConstraint(ConceptReference *CR, Expr *ImmediatelyDeclaredConstraint, UnsignedOrNone ArgPackSubstIndex)
bool isParameterPack() const
Returns whether this is a parameter pack.
Declaration of an alias template.
TypeAliasDecl * getTemplatedDecl() const
Get the underlying function declaration of the template.
Models the abbreviated syntax to constrain a template type parameter: template <convertible_to<string...
const ASTTemplateArgumentListInfo * getTemplateArgsAsWritten() const
UnsignedOrNone getArgPackSubstIndex() const
Expr * getImmediatelyDeclaredConstraint() const
Get the immediately-declared constraint expression introduced by this type-constraint,...
const NestedNameSpecifierLoc & getNestedNameSpecifierLoc() const
TemplateDecl * getNamedConcept() const
const DeclarationNameInfo & getConceptNameInfo() const
ConceptReference * getConceptReference() const
void setLocStart(SourceLocation L)
TyLocType push(QualType T)
Pushes space for a new TypeLoc of the given type.
void pushFullCopy(TypeLoc L)
Pushes a copy of the given TypeLoc onto this builder.
void reserve(size_t Requested)
Ensures that this buffer has at least as much capacity as described.
TypeSourceInfo * getTypeSourceInfo(ASTContext &Context, QualType T)
Creates a TypeSourceInfo for the given type.
void pushTrivial(ASTContext &Context, QualType T, SourceLocation Loc)
Pushes 'T' with all locations pointing to 'Loc'.
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 getAs() const
Convert to the specified TypeLoc type, returning a null TypeLoc if this TypeLoc is not of the desired...
TypeLoc IgnoreParens() const
T castAs() const
Convert to the specified TypeLoc type, asserting that this TypeLoc is of the desired type.
SourceRange getSourceRange() const LLVM_READONLY
Get the full source range.
unsigned getFullDataSize() const
Returns the size of the type source info data block.
SourceLocation getBeginLoc() const
Get the begin source location.
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.
SourceLocation getNameLoc() const
void setNameLoc(SourceLocation Loc)
The base class of the type hierarchy.
bool isReferenceType() const
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.
bool isInstantiationDependentType() const
Determine whether this type is an instantiation-dependent type, meaning that the type involves a temp...
bool containsUnexpandedParameterPack() const
Whether this type is or contains an unexpanded parameter pack, used to support C++0x variadic templat...
bool isVariablyModifiedType() const
Whether this type is a variably-modified type (C99 6.7.5).
const T * getAs() const
Member-template getAs<specific type>'.
bool isRecordType() const
QualType getUnderlyingType() const
A reference to a name which we were able to look up during parsing but could not resolve to a specifi...
bool isParameterPack() const
Determine whether this value is actually a function parameter pack, init-capture pack,...
Represents a variable declaration or definition.
bool isStaticDataMember() const
Determines whether this is a static data member.
VarDecl * getDefinition(ASTContext &)
Get the real (not just tentative) definition for this declaration.
VarDecl * getInstantiatedFromStaticDataMember() const
If this variable is an instantiated static data member of a class template specialization,...
void setTemplateSpecializationKind(TemplateSpecializationKind TSK, SourceLocation PointOfInstantiation=SourceLocation())
For a static data member that was instantiated from a static data member of a class template,...
StorageClass getStorageClass() const
Returns the storage class as written in the source.
MemberSpecializationInfo * getMemberSpecializationInfo() const
If this variable is an instantiation of a static data member of a class template specialization,...
Declaration of a variable template.
Represents a variable template specialization, which refers to a variable template with a given set o...
const TemplateArgumentList & getTemplateInstantiationArgs() const
Retrieve the set of template arguments that should be used to instantiate the initializer of the vari...
bool isClassScopeExplicitSpecialization() const
llvm::PointerUnion< VarTemplateDecl *, VarTemplatePartialSpecializationDecl * > getSpecializedTemplateOrPartial() const
Retrieve the variable template or variable template partial specialization which was specialized by t...
TemplateSpecializationKind getSpecializationKind() const
Determine the kind of specialization that this declaration represents.
VarTemplateDecl * getSpecializedTemplate() const
Retrieve the template that this specialization specializes.
SubstitutionDiagnostic * getExprSubstitutionDiagnostic() const
bool isExprSubstitutionFailure() const
const ReturnTypeRequirement & getReturnTypeRequirement() const
SourceLocation getNoexceptLoc() const
A requires-expression requirement which is satisfied when a general constraint expression is satisfie...
const ASTConstraintSatisfaction & getConstraintSatisfaction() const
bool hasInvalidConstraint() const
Expr * getConstraintExpr() const
StringRef getInvalidConstraintEntity()
A static requirement that can be used in a requires-expression to check properties of types and expre...
bool isSubstitutionFailure() const
SubstitutionDiagnostic * getSubstitutionDiagnostic() const
TypeSourceInfo * getType() const
CXXMethodDecl * CallOperator
The lambda's compiler-generated operator().
Provides information about an attempted template argument deduction, whose success or failure was des...
TemplateArgumentList * takeCanonical()
SourceLocation getLocation() const
Returns the location at which template argument is occurring.
bool hasSFINAEDiagnostic() const
Is a SFINAE diagnostic available?
void takeSFINAEDiagnostic(PartialDiagnosticAt &PD)
Take ownership of the SFINAE diagnostic.
bool hasStrictPackMatch() const
Defines the clang::TargetInfo interface.
std::variant< struct RequiresDecl, struct HeaderDecl, struct UmbrellaDirDecl, struct ModuleDecl, struct ExcludeDecl, struct ExportDecl, struct ExportAsDecl, struct ExternModuleDecl, struct UseDecl, struct LinkDecl, struct ConfigMacrosDecl, struct ConflictDecl > Decl
All declarations that can appear in a module declaration.
Attr * instantiateTemplateAttribute(const Attr *At, ASTContext &C, Sema &S, const MultiLevelTemplateArgumentList &TemplateArgs)
Attr * instantiateTemplateAttributeForDecl(const Attr *At, ASTContext &C, Sema &S, const MultiLevelTemplateArgumentList &TemplateArgs)
The JSON file list parser is used to communicate input to InstallAPI.
void atTemplateEnd(TemplateInstantiationCallbackPtrs &Callbacks, const Sema &TheSema, const Sema::CodeSynthesisContext &Inst)
bool isa(CodeGen::Address addr)
void atTemplateBegin(TemplateInstantiationCallbackPtrs &Callbacks, const Sema &TheSema, const Sema::CodeSynthesisContext &Inst)
if(T->getSizeExpr()) TRY_TO(TraverseStmt(const_cast< Expr * >(T -> getSizeExpr())))
@ Specialization
We are substituting template parameters for template arguments in order to form a template specializa...
@ Ambiguous
Name lookup results in an ambiguity; use getAmbiguityKind to figure out what kind of ambiguity we hav...
@ TemplateName
The identifier is a template name. FIXME: Add an annotation for that.
NamedDecl * getAsNamedDecl(TemplateParameter P)
@ OK_Ordinary
An ordinary object is located at an address in memory.
std::pair< llvm::PointerUnion< const TemplateTypeParmType *, NamedDecl *, const TemplateSpecializationType *, const SubstBuiltinTemplatePackType * >, SourceLocation > UnexpandedParameterPack
bool isPackProducingBuiltinTemplateName(TemplateName N)
nullptr
This class represents a compute construct, representing a 'Kind' of ‘parallel’, 'serial',...
bool isGenericLambdaCallOperatorOrStaticInvokerSpecialization(const DeclContext *DC)
bool isLambdaCallOperator(const CXXMethodDecl *MD)
@ Result
The result type of a method or function.
std::pair< unsigned, unsigned > getDepthAndIndex(const NamedDecl *ND)
Retrieve the depth and index of a template parameter.
const FunctionProtoType * T
@ Template
We are parsing a template declaration.
DeductionFailureInfo MakeDeductionFailureInfo(ASTContext &Context, TemplateDeductionResult TDK, sema::TemplateDeductionInfo &Info)
Convert from Sema's representation of template deduction information to the form used in overload-can...
@ Type
The name was classified as a type.
std::pair< SourceLocation, PartialDiagnostic > PartialDiagnosticAt
A partial diagnostic along with the source location where this diagnostic occurs.
@ VK_PRValue
A pr-value expression (in the C++11 taxonomy) produces a temporary value.
@ VK_LValue
An l-value expression is a reference to an object with independent storage.
llvm::PointerUnion< TemplateTypeParmDecl *, NonTypeTemplateParmDecl *, TemplateTemplateParmDecl * > TemplateParameter
Stores a template parameter of any kind.
DynamicRecursiveASTVisitorBase< false > DynamicRecursiveASTVisitor
TemplateDeductionResult
Describes the result of template argument deduction.
@ Success
Template argument deduction was successful.
TemplateSpecializationKind
Describes the kind of template specialization that a particular template specialization declaration r...
@ TSK_ExplicitInstantiationDefinition
This template specialization was instantiated from a template due to an explicit instantiation defini...
@ TSK_ExplicitInstantiationDeclaration
This template specialization was instantiated from a template due to an explicit instantiation declar...
@ TSK_ExplicitSpecialization
This template specialization was declared or defined by an explicit specialization (C++ [temp....
@ TSK_ImplicitInstantiation
This template specialization was implicitly instantiated from a template.
@ TSK_Undeclared
This template specialization was formed from a template-id but has not yet been declared,...
U cast(CodeGen::Address addr)
@ Enum
The "enum" keyword introduces the elaborated-type-specifier.
ActionResult< Expr * > ExprResult
@ EST_Uninstantiated
not instantiated yet
@ EST_None
no exception specification
ActionResult< Stmt * > StmtResult
Represents an explicit template argument list in C++, e.g., the "<int>" in "sort<int>".
SourceLocation RAngleLoc
The source location of the right angle bracket ('>').
const TemplateArgumentLoc * getTemplateArgs() const
Retrieve the template arguments.
SourceLocation LAngleLoc
The source location of the left angle bracket ('<').
SourceLocation getLAngleLoc() const
ArrayRef< TemplateArgumentLoc > arguments() const
unsigned getNumTemplateArgs() const
SourceLocation getRAngleLoc() const
DeclarationNameInfo - A collector data type for bundling together a DeclarationName and the correspon...
SourceLocation getLoc() const
getLoc - Returns the main location of the declaration name.
DeclarationName getName() const
getName - Returns the embedded declaration name.
Holds information about the various types of exception specification.
ExceptionSpecificationType Type
The kind of exception specification this is.
ExceptionSpecInfo ExceptionSpec
A context in which code is being synthesized (where a source location alone is not sufficient to iden...
SourceRange InstantiationRange
The source range that covers the construct that cause the instantiation, e.g., the template-id that c...
enum clang::Sema::CodeSynthesisContext::SynthesisKind Kind
const TemplateArgument * TemplateArgs
The list of template arguments we are substituting, if they are not part of the entity.
SourceLocation PointOfInstantiation
The point of instantiation or synthesis within the source code.
SynthesisKind
The kind of template instantiation we are performing.
@ MarkingClassDllexported
We are marking a class as __dllexport.
@ RequirementParameterInstantiation
@ DefaultTemplateArgumentInstantiation
We are instantiating a default argument for a template parameter.
@ ExplicitTemplateArgumentSubstitution
We are substituting explicit template arguments provided for a function template.
@ DefaultTemplateArgumentChecking
We are checking the validity of a default template argument that has been used when naming a template...
@ InitializingStructuredBinding
We are initializing a structured binding.
@ ExceptionSpecInstantiation
We are instantiating the exception specification for a function template which was deferred until it ...
@ NestedRequirementConstraintsCheck
We are checking the satisfaction of a nested requirement of a requires expression.
@ BuildingBuiltinDumpStructCall
We are building an implied call from __builtin_dump_struct.
@ ParameterMappingSubstitution
@ DefiningSynthesizedFunction
We are defining a synthesized function (such as a defaulted special member).
@ Memoization
Added for Template instantiation observation.
@ ConstraintNormalization
@ LambdaExpressionSubstitution
We are substituting into a lambda expression.
@ TypeAliasTemplateInstantiation
We are instantiating a type alias template declaration.
@ BuildingDeductionGuides
We are building deduction guides for a class.
@ PartialOrderingTTP
We are performing partial ordering for template template parameters.
@ DeducedTemplateArgumentSubstitution
We are substituting template argument determined as part of template argument deduction for either a ...
@ PriorTemplateArgumentSubstitution
We are substituting prior template arguments into a new template parameter.
@ ExceptionSpecEvaluation
We are computing the exception specification for a defaulted special member function.
@ TemplateInstantiation
We are instantiating a template declaration.
@ DeclaringSpecialMember
We are declaring an implicit special member function.
@ DeclaringImplicitEqualityComparison
We are declaring an implicit 'operator==' for a defaulted 'operator<=>'.
@ DefaultFunctionArgumentInstantiation
We are instantiating a default argument for a function.
@ RewritingOperatorAsSpaceship
We are rewriting a comparison operator in terms of an operator<=>.
@ RequirementInstantiation
We are instantiating a requirement of a requires expression.
Decl * Entity
The entity that is being synthesized.
bool isInstantiationRecord() const
Determines whether this template is an actual instantiation that should be counted toward the maximum...
A stack object to be created when performing template instantiation.
bool isInvalid() const
Determines whether we have exceeded the maximum recursive template instantiations.
InstantiatingTemplate(Sema &SemaRef, SourceLocation PointOfInstantiation, Decl *Entity, SourceRange InstantiationRange=SourceRange())
Note that we are instantiating a class template, function template, variable template,...
void Clear()
Note that we have finished instantiating this template.
void set(DeclAccessPair Found, Decl *Spec, DeductionFailureInfo Info)
bool ExpandUnderForgetSubstitions
UnsignedOrNone NumExpansions