mirror of
https://github.com/apple/swift.git
synced 2025-12-21 12:14:44 +01:00
Merge pull request #26395 from jckarter/opaque-type-class-constraint-substitution
Sema: Fix substitution of opaque types with generic base class constraints.
This commit is contained in:
@@ -3635,6 +3635,14 @@ OpaqueTypeArchetypeType::get(OpaqueTypeDecl *Decl,
|
||||
auto opaqueInterfaceTy = Decl->getUnderlyingInterfaceType();
|
||||
auto layout = signature->getLayoutConstraint(opaqueInterfaceTy);
|
||||
auto superclass = signature->getSuperclassBound(opaqueInterfaceTy);
|
||||
#if !DO_IT_CORRECTLY
|
||||
// Ad-hoc substitute the generic parameters of the superclass.
|
||||
// If we correctly applied the substitutions to the generic signature
|
||||
// constraints above, this would be unnecessary.
|
||||
if (superclass && superclass->hasTypeParameter()) {
|
||||
superclass = superclass.subst(Substitutions);
|
||||
}
|
||||
#endif
|
||||
SmallVector<ProtocolDecl*, 4> protos;
|
||||
for (auto proto : signature->getConformsTo(opaqueInterfaceTy)) {
|
||||
protos.push_back(proto);
|
||||
|
||||
@@ -222,6 +222,9 @@ Type TypeChecker::getOrCreateOpaqueResultType(TypeResolution resolution,
|
||||
diag::opaque_type_invalid_constraint);
|
||||
return constraintTypeLoc.getType();
|
||||
}
|
||||
|
||||
if (constraintType->hasArchetype())
|
||||
constraintType = constraintType->mapTypeOutOfContext();
|
||||
|
||||
// Create a generic signature for the opaque environment. This is the outer
|
||||
// generic signature with an added generic parameter representing the opaque
|
||||
|
||||
28
test/type/opaque_generic_superclass_constraint.swift
Normal file
28
test/type/opaque_generic_superclass_constraint.swift
Normal file
@@ -0,0 +1,28 @@
|
||||
// RUN: %target-swift-frontend -disable-availability-checking -emit-ir -verify %s
|
||||
|
||||
// rdar://problem/53318811
|
||||
|
||||
class Foo<T> {
|
||||
var x: T { fatalError() }
|
||||
}
|
||||
|
||||
func foo<T>(_: T) -> some Foo<T> {
|
||||
let localProp: some Foo<T> = Foo()
|
||||
return localProp
|
||||
}
|
||||
|
||||
class C<T> {
|
||||
func bar() -> some Foo<T> {
|
||||
return Foo()
|
||||
}
|
||||
|
||||
var prop: some Foo<T> = Foo()
|
||||
}
|
||||
|
||||
func bar() -> Int {
|
||||
var x = 0
|
||||
x = foo(0).x
|
||||
x = C<Int>().bar().x
|
||||
x = C<Int>().prop.x
|
||||
return x
|
||||
}
|
||||
Reference in New Issue
Block a user