@@ -1017,6 +1017,10 @@ class AssociatedTypeInference {
1017
1017
std::pair<Type, TypeDecl *>
1018
1018
computeDerivedTypeWitness (AssociatedTypeDecl *assocType);
1019
1019
1020
+ // / See if we have a generic parameter named the same as this associated
1021
+ // / type.
1022
+ Type computeGenericParamWitness (AssociatedTypeDecl *assocType) const ;
1023
+
1020
1024
// / Compute a type witness without using a specific potential witness.
1021
1025
llvm::Optional<AbstractTypeWitness>
1022
1026
computeAbstractTypeWitness (AssociatedTypeDecl *assocType);
@@ -2657,6 +2661,28 @@ AssociatedTypeInference::computeAbstractTypeWitness(
2657
2661
return llvm::None;
2658
2662
}
2659
2663
2664
+ // / Look for a generic parameter that matches the name of the
2665
+ // / associated type.
2666
+ Type AssociatedTypeInference::computeGenericParamWitness (
2667
+ AssociatedTypeDecl *assocType) const {
2668
+ if (auto genericSig = dc->getGenericSignatureOfContext ()) {
2669
+ // Ignore the generic parameters for AsyncIteratorProtocol.Failure and
2670
+ // AsyncSequence.Failure.
2671
+ if (!isAsyncIteratorProtocolFailure (assocType)) {
2672
+ for (auto *gp : genericSig.getInnermostGenericParams ()) {
2673
+ // Packs cannot witness associated type requirements.
2674
+ if (gp->isParameterPack ())
2675
+ continue ;
2676
+
2677
+ if (gp->getName () == assocType->getName ())
2678
+ return dc->mapTypeIntoContext (gp);
2679
+ }
2680
+ }
2681
+ }
2682
+
2683
+ return Type ();
2684
+ }
2685
+
2660
2686
void AssociatedTypeInference::collectAbstractTypeWitnesses (
2661
2687
TypeWitnessSystem &system,
2662
2688
ArrayRef<AssociatedTypeDecl *> unresolvedAssocTypes) const {
@@ -2705,39 +2731,14 @@ void AssociatedTypeInference::collectAbstractTypeWitnesses(
2705
2731
if (system.hasResolvedTypeWitness (assocType->getName ()))
2706
2732
continue ;
2707
2733
2708
- bool found = false ;
2709
-
2710
- // Look for a generic parameter that matches the name of the
2711
- // associated type.
2712
- if (auto genericSig = dc->getGenericSignatureOfContext ()) {
2713
- // Ignore the generic parameters for AsyncIteratorProtocol.Failure and
2714
- // AsyncSequence.Failure.
2715
- if (!isAsyncIteratorProtocolFailure (assocType)) {
2716
- for (auto *gp : genericSig.getInnermostGenericParams ()) {
2717
- // Packs cannot witness associated type requirements.
2718
- if (gp->isParameterPack ())
2719
- continue ;
2720
-
2721
- if (gp->getName () == assocType->getName ()) {
2722
- system.addTypeWitness (assocType->getName (),
2723
- dc->mapTypeIntoContext (gp),
2724
- /* preferred=*/ true );
2725
- found = true ;
2726
- break ;
2727
- }
2728
- }
2729
- }
2730
- }
2731
-
2732
- if (!found) {
2733
- // If we find a default type definition, feed it to the system.
2734
- if (const auto &typeWitness = computeDefaultTypeWitness (assocType)) {
2735
- bool preferred = (typeWitness->getDefaultedAssocType ()->getDeclContext ()
2736
- == conformance->getProtocol ());
2737
- system.addDefaultTypeWitness (typeWitness->getType (),
2738
- typeWitness->getDefaultedAssocType (),
2739
- preferred);
2740
- }
2734
+ if (auto gpType = computeGenericParamWitness (assocType)) {
2735
+ system.addTypeWitness (assocType->getName (), gpType, /* preferred=*/ true );
2736
+ } else if (const auto &typeWitness = computeDefaultTypeWitness (assocType)) {
2737
+ bool preferred = (typeWitness->getDefaultedAssocType ()->getDeclContext ()
2738
+ == conformance->getProtocol ());
2739
+ system.addDefaultTypeWitness (typeWitness->getType (),
2740
+ typeWitness->getDefaultedAssocType (),
2741
+ preferred);
2741
2742
}
2742
2743
}
2743
2744
}
@@ -3156,8 +3157,15 @@ AssociatedTypeDecl *AssociatedTypeInference::inferAbstractTypeWitnesses(
3156
3157
3157
3158
// If simplification failed, give up.
3158
3159
if (type->hasTypeParameter ()) {
3159
- LLVM_DEBUG (llvm::dbgs () << " -- Simplification failed: " << type << " \n " );
3160
- return assocType;
3160
+ if (auto gpType = computeGenericParamWitness (assocType)) {
3161
+ LLVM_DEBUG (llvm::dbgs () << " -- Found generic parameter as last resort: "
3162
+ << gpType << " \n " );
3163
+ type = gpType;
3164
+ typeWitnesses.insert (assocType, {type, reqDepth});
3165
+ } else {
3166
+ LLVM_DEBUG (llvm::dbgs () << " -- Simplification failed: " << type << " \n " );
3167
+ return assocType;
3168
+ }
3161
3169
}
3162
3170
3163
3171
if (const auto failed =
0 commit comments