Implement proper parameter pack matching for non-type template
parameters and template template parameters.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@122875 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Sema/SemaTemplate.cpp b/lib/Sema/SemaTemplate.cpp
index a0c89f0..8e7e1ee 100644
--- a/lib/Sema/SemaTemplate.cpp
+++ b/lib/Sema/SemaTemplate.cpp
@@ -3687,6 +3687,27 @@
NonTypeTemplateParmDecl *NewNTTP
= cast<NonTypeTemplateParmDecl>(*NewParm);
+ if (OldNTTP->isParameterPack() != NewNTTP->isParameterPack()) {
+ // FIXME: Implement the rules in C++0x [temp.arg.template]p5 that
+ // allow one to match a template parameter pack in the template
+ // parameter list of a template template parameter to one or more
+ // template parameters in the template parameter list of the
+ // corresponding template template argument.
+ if (Complain) {
+ unsigned NextDiag = diag::err_template_parameter_pack_non_pack;
+ if (TemplateArgLoc.isValid()) {
+ Diag(TemplateArgLoc,
+ diag::err_template_arg_template_params_mismatch);
+ NextDiag = diag::note_template_parameter_pack_non_pack;
+ }
+ Diag(NewNTTP->getLocation(), NextDiag)
+ << 1 << NewNTTP->isParameterPack();
+ Diag(OldNTTP->getLocation(), diag::note_template_parameter_pack_here)
+ << 1 << OldNTTP->isParameterPack();
+ }
+ return false;
+ }
+
// If we are matching a template template argument to a template
// template parameter and one of the non-type template parameter types
// is dependent, then we must wait until template instantiation time
@@ -3723,6 +3744,28 @@
= cast<TemplateTemplateParmDecl>(*OldParm);
TemplateTemplateParmDecl *NewTTP
= cast<TemplateTemplateParmDecl>(*NewParm);
+
+ if (OldTTP->isParameterPack() != NewTTP->isParameterPack()) {
+ // FIXME: Implement the rules in C++0x [temp.arg.template]p5 that
+ // allow one to match a template parameter pack in the template
+ // parameter list of a template template parameter to one or more
+ // template parameters in the template parameter list of the
+ // corresponding template template argument.
+ if (Complain) {
+ unsigned NextDiag = diag::err_template_parameter_pack_non_pack;
+ if (TemplateArgLoc.isValid()) {
+ Diag(TemplateArgLoc,
+ diag::err_template_arg_template_params_mismatch);
+ NextDiag = diag::note_template_parameter_pack_non_pack;
+ }
+ Diag(NewTTP->getLocation(), NextDiag)
+ << 2 << NewTTP->isParameterPack();
+ Diag(OldTTP->getLocation(), diag::note_template_parameter_pack_here)
+ << 2 << OldTTP->isParameterPack();
+ }
+ return false;
+ }
+
if (!TemplateParameterListsAreEqual(NewTTP->getTemplateParameters(),
OldTTP->getTemplateParameters(),
Complain,