Merge pull request #85850 from kavon/suppressed-assoc-types-with-defaults-2

Test: additional test coverage for SuppressedAssociatedTypesWithDefaults
This commit is contained in:
Kavon Farvardin
2025-12-05 22:03:37 -08:00
committed by GitHub
2 changed files with 163 additions and 0 deletions

View File

@@ -50,3 +50,115 @@ protocol Iterable<Element>: ~Copyable {
associatedtype Element: ~Copyable
}
struct ReqC<T: Copyable> {}
func reqC<T: Copyable>(_ t: T) {} // expected-note 8{{'where T: Copyable' is implicit here}}
protocol ProvideA<A>: ~Copyable {
associatedtype A: ~Copyable, ProvideB
}
protocol ProvideB: ~Copyable {
associatedtype B: ~Copyable, ProvideA
}
// via bound-parameter requirement inference, all of these associated types become copyable
func inferenceRec<T: ProvideA>(_ t: T,
_ a1: ReqC<T.A>,
_ b2: ReqC<T.A.B>,
_ a3: ReqC<T.A.B.A>,
_ b4: ReqC<T.A.B.A.B>,
_ a5: ReqC<T.A.B.A.B.A>,
_ b6: ReqC<T.A.B.A.B.A.B>,
_ a7: ReqC<T.A.B.A.B.A.B.A>,
_ b8: ReqC<T.A.B.A.B.A.B.A.B>,
_ a9: ReqC<T.A.B.A.B.A.B.A.B.A>,
_ b10: ReqC<T.A.B.A.B.A.B.A.B.A.B>,
_ a11: ReqC<T.A.B.A.B.A.B.A.B.A.B.A>,
_ b12: ReqC<T.A.B.A.B.A.B.A.B.A.B.A.B>
) {}
// Otherwise, the archetypes infer Copyable based on the defaulting rule,
// no matter the depth.
func inferenceRec<T: ProvideA>(_ t: T,
_ a1: borrowing T.A,
_ b2: borrowing T.A.B,
_ a3: borrowing T.A.B.A,
_ b4: borrowing T.A.B.A.B,
_ a5: borrowing T.A.B.A.B.A,
_ b6: borrowing T.A.B.A.B.A.B,
_ a7: borrowing T.A.B.A.B.A.B.A,
_ b8: borrowing T.A.B.A.B.A.B.A.B,
_ a9: borrowing T.A.B.A.B.A.B.A.B.A,
_ b10: borrowing T.A.B.A.B.A.B.A.B.A.B,
_ a11: borrowing T.A.B.A.B.A.B.A.B.A.B.A,
_ b12: borrowing T.A.B.A.B.A.B.A.B.A.B.A.B
) {
reqC(a1)
reqC(b2) // expected-error {{requires that 'T.A.B' conform to 'Copyable'}}
reqC(a3)
reqC(b4) // expected-error {{requires that 'T.A.B.A.B' conform to 'Copyable'}}
reqC(a5)
reqC(b6) // expected-error {{requires that 'T.A.B.A.B.A.B' conform to 'Copyable'}}
reqC(a7)
reqC(b8) // expected-error {{requires that 'T.A.B.A.B.A.B.A.B' conform to 'Copyable'}}
reqC(a9)
reqC(b10) // expected-error {{requires that 'T.A.B.A.B.A.B.A.B.A.B' conform to 'Copyable'}}
reqC(a11)
reqC(b12) // expected-error {{requires that 'T.A.B.A.B.A.B.A.B.A.B.A.B' conform to 'Copyable'}}
}
protocol Gen<E>: ~Copyable {
associatedtype E: ~Copyable, Gen
associatedtype I: ~Copyable, Gen
func e() -> E
func i() -> I
}
func checkExistential(_ s: any Gen) {
reqC(s.e())
reqC(s.e().e())
reqC(s.e().e().e())
reqC(s.e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e().e())
reqC(s.i()) // expected-error {{requires that 'T' conform to 'Copyable'}}
reqC(s.i().e())
reqC(s.i().e().i()) // expected-error {{requires that 'T' conform to 'Copyable'}}
reqC(s.i().e().i().e())
}
protocol Veggie<A> {
associatedtype A: ~Copyable
associatedtype NeedsCopyable
}
protocol Carrot: Veggie
where Self.NeedsCopyable: ~Copyable {} // expected-error {{'Self.NeedsCopyable' required to be 'Copyable' but is marked with '~Copyable'}}
// expected-error @-1{{cannot suppress '~Copyable' on generic parameter 'Self.NeedsCopyable' defined in outer scope}}
protocol CarrotCake: Carrot where Self.A: ~Copyable {} // expected-error {{'Self.A' required to be 'Copyable' but is marked with '~Copyable'}}
// expected-error @-1{{cannot suppress '~Copyable' on generic parameter 'Self.A' defined in outer scope}}
protocol Bird {
associatedtype Song
}
protocol Eagle: Bird where Self.Song: ~Copyable {}// expected-error {{'Self.Song' required to be 'Copyable' but is marked with '~Copyable'}}
// expected-error @-1{{cannot suppress '~Copyable' on generic parameter 'Self.Song' defined in outer scope}}
protocol Pushable<Element> {
associatedtype Element: ~Copyable
}
struct Stack<Scope: Pushable> {}
func push<Val>(_ s: Stack<Val>, _ v: Val)
where Val.Element: ~Copyable {} // expected-error {{'Val.Element' required to be 'Copyable' but is marked with '~Copyable'}}
protocol Stackable<Element>: Pushable {}
extension Stackable where Element: ~Copyable {} // expected-error {{'Self.Element' required to be 'Copyable' but is marked with '~Copyable'}}

View File

@@ -79,6 +79,16 @@ extension Pri_IIII {}
func test2<X, Y, Z>(_ x: X, y: Y, z: Z) where
X: Pri_CI, Y: Pri_II, Z: Pri_IIII {}
struct RequireCopy<X: Copyable> {}
// CHECK-LABEL: .ImplyP@
// CHECK-NEXT: Generic signature: <V where V : Pri_CI, V.[Pri_CI]A : Copyable>
struct ImplyP<V> where V: Pri_CI {}
// CHECK-LABEL: .implied1@
// CHECK-NEXT: Generic signature: <T where T : Pri_CI, T.[Pri_CI]A : Copyable>
func implied1<T>(_ t: ImplyP<T>) {}
// CHECK-LABEL: .P3@
// CHECK: Requirement signature: <Self where Self.[P3]B : Copyable>
protocol P3 where Self: (~Copyable & ~Escapable) { associatedtype B: ~Escapable }
@@ -181,6 +191,28 @@ protocol Derived3<Elm>: Base where Elm: ~Copyable {}
// CHECK-NEXT: Requirement signature: <Self where Self : Base>
protocol Derived4<Elm>: Base, ~Copyable where Elm: ~Copyable {}
// CHECK-LABEL: .Derived5@
// CHECK-NEXT: Requirement signature: <Self where Self : Copyable, Self : Base, Self.[Base]Elm : Copyable>
protocol Derived5: Base {}
// CHECK-LABEL: .Derived6@
// CHECK-NEXT: Requirement signature: <Self where Self : Copyable, Self : Base, Self.[Base]Elm : Copyable>
protocol Derived6<Iter>: Base {}
// CHECK-LABEL: .SecondOrder@
// CHECK-NEXT: Requirement signature: <Self where Self : Derived6, Self.[Base]Iter : Copyable>
protocol SecondOrder: Derived6 {}
// CHECK-LABEL: .SecondOrderSupp1@
// CHECK-NEXT: Requirement signature: <Self where Self : Derived6>
protocol SecondOrderSupp1: Derived6 where Self.Iter: ~Copyable {}
// CHECK-LABEL: .Derived7@
// CHECK-NEXT: Requirement signature: <Self where Self : Copyable, Self : Base, Self.[Base]Elm : Copyable, Self.[Base]Iter : Copyable>
protocol Derived7: Base {
associatedtype Iter
}
// CHECK-LABEL: .SameType@
// CHECK-NEXT: Requirement signature: <Self where Self : Copyable, Self : Escapable,
@@ -231,3 +263,22 @@ func testExpansion1<T>(_ t: T, _ a: T.A, _ aa: T.A.A, _ aaa: T.A.A.A)
func testExpansion2<T>(_ t: borrowing T) where
T: ~Copyable & Ping, T.A: ~Copyable & Ping, T.A.A: ~Copyable & Ping,
T.B: Ping, T.B.B: Ping {}
// CHECK-LABEL: .Iterable@
// CHECK-NEXT: Requirement signature: <Self where Self : Escapable, Self.[Iterable]Element : Escapable>
protocol Iterable<Element>: ~Copyable {
associatedtype Element: ~Copyable
}
// CHECK-LABEL: .PersistedDictionary@
// CHECK-NEXT: Requirement signature: <Self where Self : Iterable, Self.[Iterable]Element == Self.[PersistedDictionary]Value, Self.[PersistedDictionary]Key : Escapable, Self.[PersistedDictionary]Strategy : Escapable>
protocol PersistedDictionary<Key, Value>: ~Copyable, Iterable<Self.Value> {
associatedtype Key: ~Copyable
associatedtype Value: ~Copyable
associatedtype Strategy: ~Copyable
}
// CHECK-LABEL: ExtensionDecl line={{.*}} base=PersistedDictionary
// CHECK-NEXT: Generic signature: <Self where Self : Copyable, Self : PersistedDictionary, Self.[Iterable]Element : Copyable, Self.[PersistedDictionary]Key : Copyable>
extension PersistedDictionary {}