@@ -88,6 +88,23 @@ namespace {
88
88
return true ;
89
89
}
90
90
91
+ bool
92
+ VisitSubstTemplateTypeParmPackTypeLoc (SubstTemplateTypeParmPackTypeLoc TL) {
93
+ Unexpanded.push_back ({TL.getTypePtr (), TL.getNameLoc ()});
94
+ return true ;
95
+ }
96
+
97
+ bool VisitSubstTemplateTypeParmPackType (SubstTemplateTypeParmPackType *T) {
98
+ Unexpanded.push_back ({T, SourceLocation ()});
99
+ return true ;
100
+ }
101
+
102
+ bool
103
+ VisitSubstNonTypeTemplateParmPackExpr (SubstNonTypeTemplateParmPackExpr *E) {
104
+ Unexpanded.push_back ({E, E->getParameterPackLocation ()});
105
+ return true ;
106
+ }
107
+
91
108
// / Record occurrences of function and non-type template
92
109
// / parameter packs in an expression.
93
110
bool VisitDeclRefExpr (DeclRefExpr *E) {
@@ -306,7 +323,8 @@ Sema::DiagnoseUnexpandedParameterPacks(SourceLocation Loc,
306
323
auto *TTPD = dyn_cast<TemplateTypeParmDecl>(LocalPack);
307
324
return TTPD && TTPD->getTypeForDecl () == TTPT;
308
325
}
309
- return declaresSameEntity (Pack.first .get <NamedDecl *>(), LocalPack);
326
+ return declaresSameEntity (Pack.first .get <const NamedDecl *>(),
327
+ LocalPack);
310
328
};
311
329
if (llvm::any_of (LSI->LocalPacks , DeclaresThisPack))
312
330
LambdaParamPackReferences.push_back (Pack);
@@ -358,7 +376,7 @@ Sema::DiagnoseUnexpandedParameterPacks(SourceLocation Loc,
358
376
= Unexpanded[I].first .dyn_cast <const TemplateTypeParmType *>())
359
377
Name = TTP->getIdentifier ();
360
378
else
361
- Name = Unexpanded[I].first .get <NamedDecl *>()->getIdentifier ();
379
+ Name = Unexpanded[I].first .get <const NamedDecl *>()->getIdentifier ();
362
380
363
381
if (Name && NamesKnown.insert (Name).second )
364
382
Names.push_back (Name);
@@ -421,7 +439,7 @@ bool Sema::DiagnoseUnexpandedParameterPackInRequiresExpr(RequiresExpr *RE) {
421
439
llvm::SmallPtrSet<NamedDecl*, 8 > ParmSet (Parms.begin (), Parms.end ());
422
440
SmallVector<UnexpandedParameterPack, 2 > UnexpandedParms;
423
441
for (auto Parm : Unexpanded)
424
- if (ParmSet.contains (Parm.first .dyn_cast <NamedDecl*>()))
442
+ if (ParmSet.contains (Parm.first .dyn_cast <const NamedDecl *>()))
425
443
UnexpandedParms.push_back (Parm);
426
444
if (UnexpandedParms.empty ())
427
445
return false ;
@@ -672,109 +690,95 @@ bool Sema::CheckParameterPacksForExpansion(
672
690
bool &RetainExpansion, Optional<unsigned > &NumExpansions) {
673
691
ShouldExpand = true ;
674
692
RetainExpansion = false ;
675
- std::pair<IdentifierInfo *, SourceLocation> FirstPack;
676
- bool HaveFirstPack = false ;
677
- Optional<unsigned > NumPartialExpansions;
678
- SourceLocation PartiallySubstitutedPackLoc;
693
+ std::pair<const IdentifierInfo *, SourceLocation> FirstPack;
694
+ Optional<std::pair<unsigned , SourceLocation>> PartialExpansion;
695
+ Optional<unsigned > CurNumExpansions;
679
696
680
- for (UnexpandedParameterPack ParmPack : Unexpanded) {
697
+ for (auto [P, Loc] : Unexpanded) {
681
698
// Compute the depth and index for this parameter pack.
682
- unsigned Depth = 0 , Index = 0 ;
683
- IdentifierInfo *Name;
684
- bool IsVarDeclPack = false ;
685
-
686
- if (const TemplateTypeParmType *TTP =
687
- ParmPack.first .dyn_cast <const TemplateTypeParmType *>()) {
688
- Depth = TTP->getDepth ();
689
- Index = TTP->getIndex ();
690
- Name = TTP->getIdentifier ();
691
- } else {
692
- NamedDecl *ND = ParmPack.first .get <NamedDecl *>();
693
- if (isa<VarDecl>(ND))
694
- IsVarDeclPack = true ;
695
- else
696
- std::tie (Depth, Index) = getDepthAndIndex (ND);
697
-
698
- Name = ND->getIdentifier ();
699
- }
700
-
701
- // Determine the size of this argument pack.
699
+ Optional<std::pair<unsigned , unsigned >> Pos;
702
700
unsigned NewPackSize;
703
- if (IsVarDeclPack) {
704
- // Figure out whether we're instantiating to an argument pack or not.
705
- typedef LocalInstantiationScope::DeclArgumentPack DeclArgumentPack;
706
-
707
- llvm::PointerUnion<Decl *, DeclArgumentPack *> *Instantiation =
708
- CurrentInstantiationScope->findInstantiationOf (
709
- ParmPack.first .get <NamedDecl *>());
710
- if (Instantiation->is <DeclArgumentPack *>()) {
711
- // We could expand this function parameter pack.
712
- NewPackSize = Instantiation->get <DeclArgumentPack *>()->size ();
713
- } else {
701
+ const auto *ND = P.dyn_cast <const NamedDecl *>();
702
+ if (ND && isa<VarDecl>(ND)) {
703
+ const auto *DAP =
704
+ CurrentInstantiationScope->findInstantiationOf (ND)
705
+ ->dyn_cast <LocalInstantiationScope::DeclArgumentPack *>();
706
+ if (!DAP) {
714
707
// We can't expand this function parameter pack, so we can't expand
715
708
// the pack expansion.
716
709
ShouldExpand = false ;
717
710
continue ;
718
711
}
712
+ NewPackSize = DAP->size ();
713
+ } else if (ND) {
714
+ Pos = getDepthAndIndex (ND);
715
+ } else if (const auto *TTP = P.dyn_cast <const TemplateTypeParmType *>()) {
716
+ Pos = {TTP->getDepth (), TTP->getIndex ()};
717
+ ND = TTP->getDecl ();
718
+ // FIXME: We either should have some fallback for canonical TTP, or
719
+ // never have canonical TTP here.
720
+ } else if (const auto *STP =
721
+ P.dyn_cast <const SubstTemplateTypeParmPackType *>()) {
722
+ NewPackSize = STP->getNumArgs ();
723
+ ND = STP->getReplacedParameter ()->getDecl ();
719
724
} else {
725
+ const auto *SEP = P.get <const SubstNonTypeTemplateParmPackExpr *>();
726
+ NewPackSize = SEP->getArgumentPack ().pack_size ();
727
+ ND = SEP->getParameterPack ();
728
+ }
729
+
730
+ if (Pos) {
720
731
// If we don't have a template argument at this depth/index, then we
721
732
// cannot expand the pack expansion. Make a note of this, but we still
722
733
// want to check any parameter packs we *do* have arguments for.
723
- if (Depth >= TemplateArgs.getNumLevels () ||
724
- !TemplateArgs.hasTemplateArgument (Depth, Index )) {
734
+ if (Pos-> first >= TemplateArgs.getNumLevels () ||
735
+ !TemplateArgs.hasTemplateArgument (Pos-> first , Pos-> second )) {
725
736
ShouldExpand = false ;
726
737
continue ;
727
738
}
728
-
729
739
// Determine the size of the argument pack.
730
- NewPackSize = TemplateArgs (Depth, Index).pack_size ();
731
- }
732
-
733
- // C++0x [temp.arg.explicit]p9:
734
- // Template argument deduction can extend the sequence of template
735
- // arguments corresponding to a template parameter pack, even when the
736
- // sequence contains explicitly specified template arguments.
737
- if (!IsVarDeclPack && CurrentInstantiationScope) {
738
- if (NamedDecl *PartialPack
739
- = CurrentInstantiationScope->getPartiallySubstitutedPack ()){
740
- unsigned PartialDepth, PartialIndex;
741
- std::tie (PartialDepth, PartialIndex) = getDepthAndIndex (PartialPack);
742
- if (PartialDepth == Depth && PartialIndex == Index) {
740
+ NewPackSize = TemplateArgs (Pos->first , Pos->second ).pack_size ();
741
+ // C++0x [temp.arg.explicit]p9:
742
+ // Template argument deduction can extend the sequence of template
743
+ // arguments corresponding to a template parameter pack, even when the
744
+ // sequence contains explicitly specified template arguments.
745
+ if (CurrentInstantiationScope)
746
+ if (const NamedDecl *PartialPack =
747
+ CurrentInstantiationScope->getPartiallySubstitutedPack ();
748
+ PartialPack && getDepthAndIndex (PartialPack) == *Pos) {
743
749
RetainExpansion = true ;
744
750
// We don't actually know the new pack size yet.
745
- NumPartialExpansions = NewPackSize;
746
- PartiallySubstitutedPackLoc = ParmPack.second ;
751
+ PartialExpansion = {NewPackSize, Loc};
747
752
continue ;
748
753
}
749
- }
750
754
}
751
755
752
- if (!NumExpansions) {
756
+ // FIXME: Workaround for Canonical TTP.
757
+ const IdentifierInfo *Name = ND ? ND->getIdentifier () : nullptr ;
758
+ if (!CurNumExpansions) {
753
759
// The is the first pack we've seen for which we have an argument.
754
760
// Record it.
755
- NumExpansions = NewPackSize;
756
- FirstPack.first = Name;
757
- FirstPack.second = ParmPack.second ;
758
- HaveFirstPack = true ;
759
- continue ;
760
- }
761
-
762
- if (NewPackSize != *NumExpansions) {
761
+ CurNumExpansions = NewPackSize;
762
+ FirstPack = {Name, Loc};
763
+ } else if (NewPackSize != *CurNumExpansions) {
763
764
// C++0x [temp.variadic]p5:
764
765
// All of the parameter packs expanded by a pack expansion shall have
765
766
// the same number of arguments specified.
766
- if (HaveFirstPack)
767
- Diag (EllipsisLoc, diag::err_pack_expansion_length_conflict)
768
- << FirstPack.first << Name << *NumExpansions << NewPackSize
769
- << SourceRange (FirstPack.second ) << SourceRange (ParmPack.second );
770
- else
771
- Diag (EllipsisLoc, diag::err_pack_expansion_length_conflict_multilevel)
772
- << Name << *NumExpansions << NewPackSize
773
- << SourceRange (ParmPack.second );
767
+ Diag (EllipsisLoc, diag::err_pack_expansion_length_conflict)
768
+ << FirstPack.first << Name << *CurNumExpansions << NewPackSize
769
+ << SourceRange (FirstPack.second ) << SourceRange (Loc);
774
770
return true ;
775
771
}
776
772
}
777
773
774
+ if (NumExpansions && CurNumExpansions &&
775
+ *NumExpansions != *CurNumExpansions) {
776
+ Diag (EllipsisLoc, diag::err_pack_expansion_length_conflict_multilevel)
777
+ << FirstPack.first << *CurNumExpansions << *NumExpansions
778
+ << SourceRange (FirstPack.second );
779
+ return true ;
780
+ }
781
+
778
782
// If we're performing a partial expansion but we also have a full expansion,
779
783
// expand to the number of common arguments. For example, given:
780
784
//
@@ -784,17 +788,18 @@ bool Sema::CheckParameterPacksForExpansion(
784
788
//
785
789
// ... a call to 'A<int, int>().f<int>' should expand the pack once and
786
790
// retain an expansion.
787
- if (NumPartialExpansions ) {
788
- if (NumExpansions && *NumExpansions < *NumPartialExpansions ) {
791
+ if (PartialExpansion ) {
792
+ if (CurNumExpansions && *CurNumExpansions < PartialExpansion-> first ) {
789
793
NamedDecl *PartialPack =
790
794
CurrentInstantiationScope->getPartiallySubstitutedPack ();
791
795
Diag (EllipsisLoc, diag::err_pack_expansion_length_conflict_partial)
792
- << PartialPack << *NumPartialExpansions << *NumExpansions
793
- << SourceRange (PartiallySubstitutedPackLoc );
796
+ << PartialPack << PartialExpansion-> first << *CurNumExpansions
797
+ << SourceRange (PartialExpansion-> second );
794
798
return true ;
795
799
}
796
-
797
- NumExpansions = NumPartialExpansions;
800
+ NumExpansions = PartialExpansion->first ;
801
+ } else {
802
+ NumExpansions = CurNumExpansions;
798
803
}
799
804
800
805
return false ;
@@ -807,47 +812,48 @@ Optional<unsigned> Sema::getNumArgumentsInExpansion(QualType T,
807
812
CollectUnexpandedParameterPacksVisitor (Unexpanded).TraverseType (Pattern);
808
813
809
814
Optional<unsigned > Result;
810
- for (unsigned I = 0 , N = Unexpanded.size (); I != N; ++I) {
811
- // Compute the depth and index for this parameter pack.
812
- unsigned Depth;
813
- unsigned Index;
815
+ auto setResultSz = [&Result](unsigned Size) {
816
+ assert ((!Result || *Result == Size) && " inconsistent pack sizes" );
817
+ Result = Size;
818
+ };
819
+ auto setResultPos = [&](const std::pair<unsigned , unsigned > &Pos) -> bool {
820
+ unsigned Depth = Pos.first , Index = Pos.second ;
821
+ if (Depth >= TemplateArgs.getNumLevels () ||
822
+ !TemplateArgs.hasTemplateArgument (Depth, Index))
823
+ // The pattern refers to an unknown template argument. We're not ready to
824
+ // expand this pack yet.
825
+ return true ;
826
+ // Determine the size of the argument pack.
827
+ setResultSz (TemplateArgs (Depth, Index).pack_size ());
828
+ return false ;
829
+ };
814
830
815
- if (const TemplateTypeParmType *TTP
816
- = Unexpanded[I].first .dyn_cast <const TemplateTypeParmType *>()) {
817
- Depth = TTP->getDepth ();
818
- Index = TTP->getIndex ();
831
+ for (auto [I, _] : Unexpanded) {
832
+ if (const auto *TTP = I.dyn_cast <const TemplateTypeParmType *>()) {
833
+ if (setResultPos ({TTP->getDepth (), TTP->getIndex ()}))
834
+ return None;
835
+ } else if (const auto *STP =
836
+ I.dyn_cast <const SubstTemplateTypeParmPackType *>()) {
837
+ setResultSz (STP->getNumArgs ());
838
+ } else if (const auto *SEP =
839
+ I.dyn_cast <const SubstNonTypeTemplateParmPackExpr *>()) {
840
+ setResultSz (SEP->getArgumentPack ().pack_size ());
819
841
} else {
820
- NamedDecl *ND = Unexpanded[I].first .get <NamedDecl *>();
842
+ const auto *ND = I.get <const NamedDecl *>();
843
+ // Function parameter pack or init-capture pack.
821
844
if (isa<VarDecl>(ND)) {
822
- // Function parameter pack or init-capture pack.
823
- typedef LocalInstantiationScope::DeclArgumentPack DeclArgumentPack;
824
-
825
- llvm::PointerUnion<Decl *, DeclArgumentPack *> *Instantiation
826
- = CurrentInstantiationScope->findInstantiationOf (
827
- Unexpanded[I].first .get <NamedDecl *>());
828
- if (Instantiation->is <Decl*>())
845
+ const auto *DAP =
846
+ CurrentInstantiationScope->findInstantiationOf (ND)
847
+ ->dyn_cast <LocalInstantiationScope::DeclArgumentPack *>();
848
+ if (!DAP)
829
849
// The pattern refers to an unexpanded pack. We're not ready to expand
830
850
// this pack yet.
831
851
return None;
832
-
833
- unsigned Size = Instantiation->get <DeclArgumentPack *>()->size ();
834
- assert ((!Result || *Result == Size) && " inconsistent pack sizes" );
835
- Result = Size;
836
- continue ;
852
+ setResultSz (DAP->size ());
853
+ } else if (setResultPos (getDepthAndIndex (ND))) {
854
+ return None;
837
855
}
838
-
839
- std::tie (Depth, Index) = getDepthAndIndex (ND);
840
856
}
841
- if (Depth >= TemplateArgs.getNumLevels () ||
842
- !TemplateArgs.hasTemplateArgument (Depth, Index))
843
- // The pattern refers to an unknown template argument. We're not ready to
844
- // expand this pack yet.
845
- return None;
846
-
847
- // Determine the size of the argument pack.
848
- unsigned Size = TemplateArgs (Depth, Index).pack_size ();
849
- assert ((!Result || *Result == Size) && " inconsistent pack sizes" );
850
- Result = Size;
851
857
}
852
858
853
859
return Result;
0 commit comments