diff options
author | Douglas Gregor <dgregor@apple.com> | 2011-01-14 17:04:44 +0000 |
---|---|---|
committer | Douglas Gregor <dgregor@apple.com> | 2011-01-14 17:04:44 +0000 |
commit | cded4f649cd4b7ba7d461c25c6482ef52b8d3a2a (patch) | |
tree | 886197b026701bb900caeca77c4135297c4b276a /lib/Sema/SemaTemplateInstantiateDecl.cpp | |
parent | 5576d9b0a389f6f1f89bdcd37194f4e992b1fbcb (diff) |
Keep track of the number of expansions to be produced from a type pack
expansion, when it is known due to the substitution of an out
parameter pack. This allows us to properly handle substitution into
pack expansions that involve multiple parameter packs at different
template parameter levels, even when this substitution happens one
level at a time (as with partial specializations of member class
templates and the signatures of member function templates).
Note that the diagnostic we provide when there is an arity mismatch
between an outer parameter pack and an inner parameter pack in this
case isn't as clear as the normal diagnostic for an arity
mismatch. However, this doesn't matter because these cases are very,
very rare and (even then) only typically occur in a SFINAE context.
The other kinds of pack expansions (expression, template, etc.) still
need to support optional tracking of the number of expansions, and we
need the moral equivalent of SubstTemplateTypeParmPackType for
substituted argument packs of template template and non-type template
parameters.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@123448 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/SemaTemplateInstantiateDecl.cpp')
-rw-r--r-- | lib/Sema/SemaTemplateInstantiateDecl.cpp | 13 |
1 files changed, 8 insertions, 5 deletions
diff --git a/lib/Sema/SemaTemplateInstantiateDecl.cpp b/lib/Sema/SemaTemplateInstantiateDecl.cpp index a18bfbafc0..6b5713a2fa 100644 --- a/lib/Sema/SemaTemplateInstantiateDecl.cpp +++ b/lib/Sema/SemaTemplateInstantiateDecl.cpp @@ -1977,7 +1977,8 @@ TemplateDeclInstantiator::InitFunctionInstantiation(FunctionDecl *New, bool Expand = false; bool RetainExpansion = false; - unsigned NumExpansions = 0; + llvm::Optional<unsigned> NumExpansions + = PackExpansion->getNumExpansions(); if (SemaRef.CheckParameterPacksForExpansion(New->getLocation(), SourceRange(), Unexpanded.data(), @@ -1990,7 +1991,8 @@ TemplateDeclInstantiator::InitFunctionInstantiation(FunctionDecl *New, if (!Expand) { // We can't expand this pack expansion into separate arguments yet; - // just substitute into the argument pack. + // just substitute into the pattern and create a new pack expansion + // type. Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(SemaRef, -1); QualType T = SemaRef.SubstType(PackExpansion->getPattern(), TemplateArgs, @@ -1998,13 +2000,14 @@ TemplateDeclInstantiator::InitFunctionInstantiation(FunctionDecl *New, if (T.isNull()) break; + T = SemaRef.Context.getPackExpansionType(T, NumExpansions); Exceptions.push_back(T); continue; } // Substitute into the pack expansion pattern for each template bool Invalid = false; - for (unsigned ArgIdx = 0; ArgIdx != NumExpansions; ++ArgIdx) { + for (unsigned ArgIdx = 0; ArgIdx != *NumExpansions; ++ArgIdx) { Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(SemaRef, ArgIdx); QualType T = SemaRef.SubstType(PackExpansion->getPattern(), @@ -2384,7 +2387,7 @@ Sema::InstantiateMemInitializers(CXXConstructorDecl *New, collectUnexpandedParameterPacks(BaseTL, Unexpanded); bool ShouldExpand = false; bool RetainExpansion = false; - unsigned NumExpansions = 0; + llvm::Optional<unsigned> NumExpansions; if (CheckParameterPacksForExpansion(Init->getEllipsisLoc(), BaseTL.getSourceRange(), Unexpanded.data(), @@ -2399,7 +2402,7 @@ Sema::InstantiateMemInitializers(CXXConstructorDecl *New, assert(ShouldExpand && "Partial instantiation of base initializer?"); // Loop over all of the arguments in the argument pack(s), - for (unsigned I = 0; I != NumExpansions; ++I) { + for (unsigned I = 0; I != *NumExpansions; ++I) { Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(*this, I); // Instantiate the initializer. |