@@ -5016,7 +5016,8 @@ GenericEnvironment::forOpenedExistential(
5016
5016
5017
5017
// / Create a new generic environment for an element archetype.
5018
5018
GenericEnvironment *
5019
- GenericEnvironment::forOpenedElement (GenericSignature signature, UUID uuid) {
5019
+ GenericEnvironment::forOpenedElement (GenericSignature signature, UUID uuid,
5020
+ SubstitutionMap outerSubs) {
5020
5021
auto &ctx = signature->getASTContext ();
5021
5022
5022
5023
auto &openedElementEnvironments =
@@ -5038,7 +5039,8 @@ GenericEnvironment::forOpenedElement(GenericSignature signature, UUID uuid) {
5038
5039
OpenedElementEnvironmentData, Type>(
5039
5040
0 , 0 , 1 , numGenericParams);
5040
5041
void *mem = ctx.Allocate (bytes, alignof (GenericEnvironment));
5041
- auto *genericEnv = new (mem) GenericEnvironment (signature, uuid);
5042
+ auto *genericEnv = new (mem) GenericEnvironment (signature, uuid,
5043
+ outerSubs);
5042
5044
5043
5045
openedElementEnvironments[uuid] = genericEnv;
5044
5046
@@ -5621,41 +5623,76 @@ ASTContext::getOpenedElementSignature(CanGenericSignature baseGenericSig) {
5621
5623
}
5622
5624
#endif
5623
5625
5624
- SmallVector<GenericTypeParamType *, 2 > genericParams;
5626
+ // The pack element signature includes all type parameters and requirements
5627
+ // from the outer context, plus a new set of type parameters representing
5628
+ // open pack elements and their corresponding element requirements.
5629
+
5630
+ llvm::SmallMapVector<GenericTypeParamType *,
5631
+ GenericTypeParamType *, 2 > packElementParams;
5632
+ SmallVector<GenericTypeParamType *, 2 > genericParams (
5633
+ baseGenericSig.getGenericParams ().begin (), baseGenericSig.getGenericParams ().end ());
5625
5634
SmallVector<Requirement, 2 > requirements;
5626
5635
5636
+ auto packElementDepth =
5637
+ baseGenericSig.getInnermostGenericParams ().front ()->getDepth () + 1 ;
5638
+
5627
5639
for (auto paramType : baseGenericSig.getGenericParams ()) {
5628
- genericParams.push_back (paramType->asScalar (*this ));
5640
+ if (!paramType->isParameterPack ())
5641
+ continue ;
5642
+
5643
+ auto *elementParam = GenericTypeParamType::get (/* isParameterPack*/ false ,
5644
+ packElementDepth,
5645
+ packElementParams.size (),
5646
+ *this );
5647
+ genericParams.push_back (elementParam);
5648
+ packElementParams[paramType] = elementParam;
5629
5649
}
5630
5650
5631
5651
auto eraseParameterPackRec = [&](Type type) -> Type {
5632
5652
return type.transformRec ([&](Type t) -> Optional<Type> {
5633
- if (auto *paramType = t->getAs <GenericTypeParamType>())
5634
- return Type (paramType->asScalar (*this ));
5653
+ if (auto *paramType = t->getAs <GenericTypeParamType>()) {
5654
+ if (paramType->isParameterPack ()) {
5655
+ return Type (packElementParams[paramType]);
5656
+ }
5657
+
5658
+ return t;
5659
+ }
5635
5660
return None;
5636
5661
});
5637
5662
};
5638
5663
5639
5664
for (auto requirement : baseGenericSig.getRequirements ()) {
5665
+ requirements.push_back (requirement);
5666
+
5667
+ // If this requirement contains parameter packs, create a new requirement
5668
+ // for the corresponding pack element.
5640
5669
switch (requirement.getKind ()) {
5641
5670
case RequirementKind::SameShape:
5642
5671
// Drop same-shape requirements from the element signature.
5643
5672
break ;
5644
5673
case RequirementKind::Conformance:
5645
5674
case RequirementKind::Superclass:
5646
- case RequirementKind::SameType:
5647
- requirements.emplace_back (
5648
- requirement.getKind (),
5649
- eraseParameterPackRec (requirement.getFirstType ()),
5650
- eraseParameterPackRec (requirement.getSecondType ()));
5675
+ case RequirementKind::SameType: {
5676
+ auto firstType = eraseParameterPackRec (requirement.getFirstType ());
5677
+ auto secondType = eraseParameterPackRec (requirement.getSecondType ());
5678
+ if (firstType->isEqual (requirement.getFirstType ()) &&
5679
+ secondType->isEqual (requirement.getSecondType ()))
5680
+ break ;
5681
+
5682
+ requirements.emplace_back (requirement.getKind (),
5683
+ firstType, secondType);
5651
5684
break ;
5652
- case RequirementKind::Layout:
5653
- requirements.emplace_back (
5654
- requirement.getKind (),
5655
- eraseParameterPackRec (requirement.getFirstType ()),
5656
- requirement.getLayoutConstraint ());
5685
+ }
5686
+ case RequirementKind::Layout: {
5687
+ auto firstType = eraseParameterPackRec (requirement.getFirstType ());
5688
+ if (firstType->isEqual (requirement.getFirstType ()))
5689
+ break ;
5690
+
5691
+ requirements.emplace_back (requirement.getKind (), firstType,
5692
+ requirement.getLayoutConstraint ());
5657
5693
break ;
5658
5694
}
5695
+ }
5659
5696
}
5660
5697
5661
5698
auto elementSig = buildGenericSignature (
0 commit comments