Skip to content

Commit 2b28cb1

Browse files
committed
Sema: Implement missing case in existential erasure
Fixes #61934.
1 parent 2b2beb6 commit 2b28cb1

File tree

2 files changed

+42
-0
lines changed

2 files changed

+42
-0
lines changed

lib/Sema/ConstraintSystem.cpp

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2284,6 +2284,20 @@ static Type typeEraseExistentialSelfReferences(Type refTy, Type baseTy,
22842284
}
22852285
}
22862286

2287+
// Parameterized protocol types whose arguments involve this type
2288+
// parameter are erased to the base type.
2289+
if (auto parameterized = dyn_cast<ParameterizedProtocolType>(t)) {
2290+
for (auto argType : parameterized->getArgs()) {
2291+
auto erasedArgType =
2292+
typeEraseExistentialSelfReferences(
2293+
argType, baseTy, TypePosition::Covariant,
2294+
existentialSig, containsFn, predicateFn, projectionFn,
2295+
force, metatypeDepth);
2296+
if (erasedArgType.getPointer() != argType.getPointer())
2297+
return parameterized->getBaseType();
2298+
}
2299+
}
2300+
22872301
if (auto lvalue = dyn_cast<LValueType>(t)) {
22882302
auto objTy = lvalue->getObjectType();
22892303
auto erasedTy =

test/Constraints/issue-67337.swift

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
// RUN: %target-typecheck-verify-swift -disable-availability-checking
2+
3+
protocol P<T> {
4+
associatedtype T
5+
func foo() -> any P<T>
6+
}
7+
8+
struct A: P {
9+
typealias T = Int
10+
func foo() -> any P<T> {
11+
self
12+
}
13+
}
14+
15+
struct B: P {
16+
typealias T = Int
17+
func foo() -> any P<T> {
18+
self
19+
}
20+
}
21+
22+
struct G<T> {
23+
let t: T
24+
}
25+
26+
let p: any P = A()
27+
let g = G(t: p.foo())
28+
let gg: G<any P> = g

0 commit comments

Comments
 (0)