Skip to content

Commit 2d36fcd

Browse files
committed
AST: Split off QueryOverrideSubs and LookUpConformanceInOverrideSubs
1 parent fcf7948 commit 2d36fcd

File tree

2 files changed

+96
-49
lines changed

2 files changed

+96
-49
lines changed

include/swift/AST/SubstitutionMap.h

Lines changed: 36 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -205,10 +205,10 @@ class SubstitutionMap {
205205
/// Variant of the above for when we have the generic signatures but not
206206
/// the decls for 'derived' and 'base'.
207207
static SubstitutionMap
208-
getOverrideSubstitutions(const ClassDecl *baseClass,
209-
const ClassDecl *derivedClass,
208+
getOverrideSubstitutions(const NominalTypeDecl *baseNominal,
209+
const NominalTypeDecl *derivedNominal,
210210
GenericSignature baseSig,
211-
GenericParamList *derivedParams);
211+
const GenericParamList *derivedParams);
212212

213213
/// Combine two substitution maps as follows.
214214
///
@@ -312,6 +312,39 @@ class LookUpConformanceInSubstitutionMap {
312312
ProtocolDecl *conformedProtocol) const;
313313
};
314314

315+
struct OverrideSubsInfo {
316+
ASTContext &Ctx;
317+
unsigned BaseDepth;
318+
unsigned OrigDepth;
319+
SubstitutionMap BaseSubMap;
320+
const GenericParamList *DerivedParams;
321+
322+
OverrideSubsInfo(const NominalTypeDecl *baseNominal,
323+
const NominalTypeDecl *derivedNominal,
324+
GenericSignature baseSig,
325+
const GenericParamList *derivedParams);
326+
};
327+
328+
struct QueryOverrideSubs {
329+
OverrideSubsInfo info;
330+
331+
explicit QueryOverrideSubs(const OverrideSubsInfo &info)
332+
: info(info) {}
333+
334+
Type operator()(SubstitutableType *type) const;
335+
};
336+
337+
struct LookUpConformanceInOverrideSubs {
338+
OverrideSubsInfo info;
339+
340+
explicit LookUpConformanceInOverrideSubs(const OverrideSubsInfo &info)
341+
: info(info) {}
342+
343+
ProtocolConformanceRef operator()(CanType type,
344+
Type substType,
345+
ProtocolDecl *proto) const;
346+
};
347+
315348
} // end namespace swift
316349

317350
namespace llvm {

lib/AST/SubstitutionMap.cpp

Lines changed: 60 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -523,62 +523,76 @@ SubstitutionMap::getOverrideSubstitutions(
523523
return getOverrideSubstitutions(baseClass, derivedClass, baseSig, derivedParams);
524524
}
525525

526-
SubstitutionMap
527-
SubstitutionMap::getOverrideSubstitutions(const ClassDecl *baseClass,
528-
const ClassDecl *derivedClass,
529-
GenericSignature baseSig,
530-
GenericParamList *derivedParams) {
531-
if (baseSig.isNull())
532-
return SubstitutionMap();
526+
OverrideSubsInfo::OverrideSubsInfo(const NominalTypeDecl *baseNominal,
527+
const NominalTypeDecl *derivedNominal,
528+
GenericSignature baseSig,
529+
const GenericParamList *derivedParams)
530+
: Ctx(baseSig->getASTContext()),
531+
BaseDepth(0),
532+
OrigDepth(0),
533+
DerivedParams(derivedParams) {
534+
535+
if (auto baseNominalSig = baseNominal->getGenericSignature()) {
536+
BaseDepth = baseNominalSig.getGenericParams().back()->getDepth() + 1;
537+
538+
auto derivedNominalTy = derivedNominal->getDeclaredInterfaceType();
539+
BaseSubMap = derivedNominalTy->getContextSubstitutionMap(
540+
baseNominal->getParentModule(), baseNominal);
541+
assert(!BaseSubMap.hasArchetypes());
542+
}
543+
544+
if (auto derivedNominalSig = derivedNominal->getGenericSignature())
545+
OrigDepth = derivedNominalSig.getGenericParams().back()->getDepth() + 1;
546+
}
533547

534-
unsigned baseDepth = 0;
535-
SubstitutionMap baseSubMap;
536-
if (auto baseClassSig = baseClass->getGenericSignature()) {
537-
baseDepth = baseClassSig.getGenericParams().back()->getDepth() + 1;
548+
Type QueryOverrideSubs::operator()(SubstitutableType *type) const {
549+
if (auto gp = type->getAs<GenericTypeParamType>()) {
550+
if (gp->getDepth() >= info.BaseDepth) {
551+
assert(gp->getDepth() == info.BaseDepth);
552+
if (info.DerivedParams != nullptr) {
553+
return info.DerivedParams->getParams()[gp->getIndex()]
554+
->getDeclaredInterfaceType();
555+
}
538556

539-
auto derivedClassTy = derivedClass->getDeclaredInterfaceType();
540-
baseSubMap = derivedClassTy->getContextSubstitutionMap(
541-
baseClass->getParentModule(), baseClass);
542-
assert(!baseSubMap.hasArchetypes());
557+
return GenericTypeParamType::get(
558+
gp->isTypeSequence(),
559+
gp->getDepth() + info.OrigDepth - info.BaseDepth,
560+
gp->getIndex(), info.Ctx);
561+
}
543562
}
544563

545-
unsigned origDepth = 0;
546-
if (auto derivedClassSig = derivedClass->getGenericSignature())
547-
origDepth = derivedClassSig.getGenericParams().back()->getDepth() + 1;
564+
return Type(type).subst(info.BaseSubMap);
565+
}
548566

549-
auto &ctx = baseSig->getASTContext();
567+
ProtocolConformanceRef
568+
LookUpConformanceInOverrideSubs::operator()(CanType type,
569+
Type substType,
570+
ProtocolDecl *proto) const {
571+
if (type->getRootGenericParam()->getDepth() >= info.BaseDepth)
572+
return ProtocolConformanceRef(proto);
550573

551-
return get(
552-
baseSig,
553-
[&](SubstitutableType *type) -> Type {
554-
if (auto gp = type->getAs<GenericTypeParamType>()) {
555-
if (gp->getDepth() >= baseDepth) {
556-
assert(gp->getDepth() == baseDepth);
557-
if (derivedParams != nullptr) {
558-
return derivedParams->getParams()[gp->getIndex()]
559-
->getDeclaredInterfaceType();
560-
}
561-
562-
return GenericTypeParamType::get(gp->isTypeSequence(),
563-
gp->getDepth() + origDepth - baseDepth,
564-
gp->getIndex(), ctx);
565-
}
566-
}
574+
if (auto conformance = info.BaseSubMap.lookupConformance(type, proto))
575+
return conformance;
567576

568-
return Type(type).subst(baseSubMap);
569-
},
570-
[&](CanType type, Type substType, ProtocolDecl *proto) {
571-
if (type->getRootGenericParam()->getDepth() >= baseDepth)
572-
return ProtocolConformanceRef(proto);
577+
if (substType->isTypeParameter())
578+
return ProtocolConformanceRef(proto);
573579

574-
if (auto conformance = baseSubMap.lookupConformance(type, proto))
575-
return conformance;
580+
return proto->getParentModule()->lookupConformance(substType, proto);
581+
}
576582

577-
if (substType->isTypeParameter())
578-
return ProtocolConformanceRef(proto);
583+
SubstitutionMap
584+
SubstitutionMap::getOverrideSubstitutions(const NominalTypeDecl *baseNominal,
585+
const NominalTypeDecl *derivedNominal,
586+
GenericSignature baseSig,
587+
const GenericParamList *derivedParams) {
588+
if (baseSig.isNull())
589+
return SubstitutionMap();
579590

580-
return proto->getParentModule()->lookupConformance(substType, proto);
581-
});
591+
OverrideSubsInfo info(baseNominal, derivedNominal, baseSig, derivedParams);
592+
593+
return get(baseSig,
594+
QueryOverrideSubs(info),
595+
LookUpConformanceInOverrideSubs(info));
582596
}
583597

584598
SubstitutionMap

0 commit comments

Comments
 (0)