Skip to content

Commit 0877aa1

Browse files
Merge pull request #79322 from AnthonyLatsis/charcharadon-carcharias
TypeResolution: Stop resolving unqualified protocol type aliases to `DependentMemberType` in structural stage
2 parents d9b6a82 + f3183be commit 0877aa1

File tree

3 files changed

+50
-40
lines changed

3 files changed

+50
-40
lines changed

lib/Sema/TypeCheckGeneric.cpp

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1127,11 +1127,6 @@ Type StructuralTypeRequest::evaluate(Evaluator &evaluator,
11271127
/*packElementOpener*/ nullptr)
11281128
.resolveType(underlyingTypeRepr);
11291129

1130-
// Don't build a generic siganture for a protocol extension, because this
1131-
// request might be evaluated while building a protocol requirement signature.
1132-
if (parentDC->getSelfProtocolDecl())
1133-
return result;
1134-
11351130
Type parent;
11361131
if (parentDC->isTypeContext())
11371132
parent = parentDC->getSelfInterfaceType();

lib/Sema/TypeCheckType.cpp

Lines changed: 34 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -560,15 +560,17 @@ Type TypeResolution::resolveTypeInContext(TypeDecl *typeDecl,
560560
selfType = foundDC->getSelfInterfaceType();
561561

562562
if (selfType->is<GenericTypeParamType>()) {
563-
if (isa<ProtocolDecl>(typeDecl->getDeclContext())) {
564-
if (isa<AssociatedTypeDecl>(typeDecl) ||
565-
(isa<TypeAliasDecl>(typeDecl) &&
566-
!cast<TypeAliasDecl>(typeDecl)->isGeneric() &&
567-
!isSpecialized)) {
568-
if (getStage() == TypeResolutionStage::Structural) {
569-
return DependentMemberType::get(selfType, typeDecl->getName());
570-
} else if (auto assocType = dyn_cast<AssociatedTypeDecl>(typeDecl)) {
571-
typeDecl = assocType->getAssociatedTypeAnchor();
563+
if (auto assocType = dyn_cast<AssociatedTypeDecl>(typeDecl)) {
564+
if (getStage() == TypeResolutionStage::Structural) {
565+
return DependentMemberType::get(selfType, typeDecl->getName());
566+
}
567+
568+
typeDecl = assocType->getAssociatedTypeAnchor();
569+
} else if (auto *aliasDecl = dyn_cast<TypeAliasDecl>(typeDecl)) {
570+
if (isa<ProtocolDecl>(typeDecl->getDeclContext()) &&
571+
getStage() == TypeResolutionStage::Structural) {
572+
if (aliasDecl && !aliasDecl->isGeneric()) {
573+
return adjustAliasType(aliasDecl->getStructuralType());
572574
}
573575
}
574576
}
@@ -5950,42 +5952,39 @@ TypeResolver::resolveExistentialType(ExistentialTypeRepr *repr,
59505952
if (constraintType->hasError())
59515953
return ErrorType::get(getASTContext());
59525954

5955+
if (constraintType->isConstraintType()) {
5956+
return ExistentialType::get(constraintType);
5957+
}
5958+
59535959
//TO-DO: generalize this and emit the same erorr for some P?
5954-
if (!constraintType->isConstraintType()) {
5955-
// Emit a tailored diagnostic for the incorrect optional
5956-
// syntax 'any P?' with a fix-it to add parenthesis.
5957-
auto wrapped = constraintType->getOptionalObjectType();
5958-
if (wrapped && (wrapped->is<ExistentialType>() ||
5959-
wrapped->is<ExistentialMetatypeType>())) {
5960-
std::string fix;
5961-
llvm::raw_string_ostream OS(fix);
5962-
constraintType->print(OS, PrintOptions::forDiagnosticArguments());
5963-
diagnose(repr->getLoc(), diag::incorrect_optional_any,
5964-
constraintType)
5960+
//
5961+
// Emit a tailored diagnostic for the incorrect optional
5962+
// syntax 'any P?' with a fix-it to add parenthesis.
5963+
auto wrapped = constraintType->getOptionalObjectType();
5964+
if (wrapped && (wrapped->is<ExistentialType>() ||
5965+
wrapped->is<ExistentialMetatypeType>())) {
5966+
std::string fix;
5967+
llvm::raw_string_ostream OS(fix);
5968+
constraintType->print(OS, PrintOptions::forDiagnosticArguments());
5969+
diagnose(repr->getLoc(), diag::incorrect_optional_any, constraintType)
59655970
.fixItReplace(repr->getSourceRange(), fix);
59665971

5967-
// Recover by returning the intended type, but mark the type
5968-
// representation as invalid to prevent it from being diagnosed elsewhere.
5969-
repr->setInvalid();
5970-
return constraintType;
5971-
}
5972-
5972+
// Recover by returning the intended type, but mark the type
5973+
// representation as invalid to prevent it from being diagnosed elsewhere.
5974+
repr->setInvalid();
5975+
} else if (constraintType->is<ExistentialType>()) {
59735976
// Diagnose redundant `any` on an already existential type e.g. any (any P)
59745977
// with a fix-it to remove first any.
5975-
if (constraintType->is<ExistentialType>()) {
5976-
diagnose(repr->getLoc(), diag::redundant_any_in_existential,
5977-
ExistentialType::get(constraintType))
5978-
.fixItRemove(repr->getAnyLoc());
5979-
return constraintType;
5980-
}
5981-
5978+
diagnose(repr->getLoc(), diag::redundant_any_in_existential,
5979+
ExistentialType::get(constraintType))
5980+
.fixItRemove(repr->getAnyLoc());
5981+
} else {
59825982
diagnose(repr->getLoc(), diag::any_not_existential,
59835983
constraintType->isTypeParameter(), constraintType)
59845984
.fixItRemove(repr->getAnyLoc());
5985-
return constraintType;
59865985
}
59875986

5988-
return ExistentialType::get(constraintType);
5987+
return constraintType;
59895988
}
59905989

59915990
NeverNullType TypeResolver::resolveMetatypeType(MetatypeTypeRepr *repr,
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
// RUN: %target-typecheck-verify-swift -target %target-swift-5.9-abi-triple -enable-upcoming-feature ExistentialAny
2+
3+
// REQUIRES: swift_feature_ExistentialAny
4+
5+
protocol P {
6+
typealias PAlias1 = P
7+
8+
func f1() -> any PAlias1
9+
func g1<T>(_: T) -> any PAlias1
10+
}
11+
extension P {
12+
typealias PAlias2 = P
13+
14+
func f2() -> any PAlias2 {}
15+
func g2<T>(_: T) -> any PAlias2 {}
16+
}

0 commit comments

Comments
 (0)