// RUN: %target-swift-emit-silgen %s | %FileCheck %s // RUN: %target-swift-frontend -emit-ir %s struct S {} class B {} class C: B {} class D: C {} func callMethodsOnOpaque(o: Opaque, t: T, u: U, tt: T.Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnStillOpaque(o: StillOpaque, t: T, u: U, tt: T.Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnConcreteValue(o: ConcreteValue, t: S, u: U, tt: S.Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnConcreteClass(o: ConcreteClass, t: C, u: U, tt: C.Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnConcreteClassVariance(o: ConcreteClassVariance, b: B, c: C, u: U, tt: C.Type) { _ = o.inAndOut(x: b) _ = o.inAndOutGeneric(x: c, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (c, (tt, { $0 }))) _ = o.variantOptionality(x: b) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (c, (tt, { $0 }))) } func callMethodsOnOpaqueTuple(o: OpaqueTuple, t: (T, T), u: U, tt: (T, T).Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnConcreteTuple(o: ConcreteTuple, t: (S, S), u: U, tt: (S, S).Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnOpaqueFunction(o: OpaqueFunction, t: @escaping (X) -> Y, u: U, tt: ((X) -> Y).Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnConcreteFunction(o: ConcreteFunction, t: @escaping (S) -> S, u: U, tt: ((S) -> S).Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnOpaqueMetatype(o: OpaqueMetatype, t: T.Type, u: U, tt: T.Type.Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnConcreteValueMetatype(o: ConcreteValueMetatype, t: S.Type, u: U, tt: S.Type.Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnConcreteClassMetatype(o: ConcreteClassMetatype, t: C.Type, u: U, tt: C.Type.Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } func callMethodsOnConcreteOptional(o: ConcreteOptional, t: S?, u: U, tt: S?.Type) { _ = o.inAndOut(x: t) _ = o.inAndOutGeneric(x: t, y: u) _ = o.inAndOutMetatypes(x: tt) _ = o.inAndOutTuples(x: (t, (tt, { $0 }))) _ = o.variantOptionality(x: t) _ = o.variantOptionalityMetatypes(x: tt) _ = o.variantOptionalityFunctions(x: { $0 }) _ = o.variantOptionalityTuples(x: (t, (tt, { $0 }))) } class Opaque { typealias ObnoxiousTuple = (T, (T.Type, (T) -> T)) func inAndOut(x: T) -> T { return x } func inAndOutGeneric(x: T, y: U) -> U { return y } func inAndOutMetatypes(x: T.Type) -> T.Type { return x } func inAndOutFunctions(x: @escaping (T) -> T) -> (T) -> T { return x } func inAndOutTuples(x: ObnoxiousTuple) -> ObnoxiousTuple { return x } func variantOptionality(x: T) -> T? { return x } func variantOptionalityMetatypes(x: T.Type) -> T.Type? { return x } func variantOptionalityFunctions(x: @escaping (T) -> T) -> ((T) -> T)? { return x } func variantOptionalityTuples(x: ObnoxiousTuple) -> ObnoxiousTuple? { return x } } // CHECK-LABEL: sil_vtable Opaque { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC8inAndOut1xxx_tF // Opaque.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction6OpaqueC18variantOptionality1xxSgx_tF // Opaque.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction6OpaqueCACyxGycfC // CHECK-NEXT: #Opaque.deinit!deallocator: @$s27vtable_thunks_reabstraction6OpaqueCfD // Opaque.__deallocating_deinit // CHECK-NEXT: } class StillOpaque: Opaque { override func variantOptionalityTuples(x: ObnoxiousTuple?) -> ObnoxiousTuple { return x! } } // CHECK-LABEL: sil_vtable StillOpaque { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC8inAndOut1xxx_tF [inherited] // Opaque.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction6OpaqueC18variantOptionality1xxSgx_tF [inherited] // Opaque.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction11StillOpaqueC24variantOptionalityTuples1xx_xm_xxcttx_xm_xxcttSg_tFAA0E0CAdeFx_xm_xxctt_tFTV [override] // vtable thunk for Opaque.variantOptionalityTuples(x:) dispatching to StillOpaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction11StillOpaqueCACyxGycfC [override] // Tuple becomes more optional -- needs new vtable entry // CHECK-NEXT: #StillOpaque.variantOptionalityTuples: (StillOpaque) -> ((T, (T.Type, (T) -> T))?) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction11StillOpaqueC24variantOptionalityTuples1xx_xm_xxcttx_xm_xxcttSg_tF // StillOpaque.variantOptionalityTuples(x:) // CHECK-NEXT: #StillOpaque.deinit!deallocator: @$s27vtable_thunks_reabstraction11StillOpaqueCfD // StillOpaque.__deallocating_deinit // CHECK-NEXT: } class ConcreteValue: Opaque { override func inAndOut(x: S) -> S { return x } override func inAndOutGeneric(x: S, y: Z) -> Z { return y } override func inAndOutMetatypes(x: S.Type) -> S.Type { return x } override func inAndOutFunctions(x: @escaping (S) -> S) -> (S) -> S { return x } override func inAndOutTuples(x: ObnoxiousTuple) -> ObnoxiousTuple { return x } override func variantOptionality(x: S?) -> S { return x! } override func variantOptionalityMetatypes(x: S.Type?) -> S.Type { return x! } override func variantOptionalityFunctions(x: ((S) -> S)?) -> (S) -> S { return x! } override func variantOptionalityTuples(x: ObnoxiousTuple?) -> ObnoxiousTuple { return x! } } // CHECK-LABEL: sil_vtable ConcreteValue { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction13ConcreteValueC8inAndOut1xAA1SVAG_tFAA6OpaqueCAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to ConcreteValue.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction13ConcreteValueC15inAndOutGeneric1x1yxAA1SV_xtlFAA6OpaqueCAdeFqd__x_qd__tlFTV [override] // vtable thunk for Opaque.inAndOutGeneric(x:y:) dispatching to ConcreteValue.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction13ConcreteValueC17inAndOutMetatypes1xAA1SVmAGm_tFAA6OpaqueCAdExmxm_tFTV [override] // vtable thunk for Opaque.inAndOutMetatypes(x:) dispatching to ConcreteValue.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction13ConcreteValueC17inAndOutFunctions1xAA1SVAGcA2Gc_tFAA6OpaqueCAdExxcxxc_tFTV [override] // vtable thunk for Opaque.inAndOutFunctions(x:) dispatching to ConcreteValue.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction13ConcreteValueC14inAndOutTuples1xAA1SV_AGm_A2GcttAG_AGm_A2Gctt_tFAA6OpaqueCAdEx_xm_xxcttx_xm_xxctt_tFTV [override] // vtable thunk for Opaque.inAndOutTuples(x:) dispatching to ConcreteValue.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction13ConcreteValueC18variantOptionality1xAA1SVAGSg_tFAA6OpaqueCAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to ConcreteValue.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction13ConcreteValueC27variantOptionalityMetatypes1xAA1SVmAGmSg_tFAA6OpaqueCAdExmSgxm_tFTV [override] // vtable thunk for Opaque.variantOptionalityMetatypes(x:) dispatching to ConcreteValue.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction13ConcreteValueC27variantOptionalityFunctions1xAA1SVAGcA2GcSg_tFAA6OpaqueCAdExxcSgxxc_tFTV [override] // vtable thunk for Opaque.variantOptionalityFunctions(x:) dispatching to ConcreteValue.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction13ConcreteValueC24variantOptionalityTuples1xAA1SV_AGm_A2GcttAG_AGm_A2GcttSg_tFAA6OpaqueCAdEx_xm_xxcttSgx_xm_xxctt_tFTV [override] // vtable thunk for Opaque.variantOptionalityTuples(x:) dispatching to ConcreteValue.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction13ConcreteValueCACycfC [override] // Value types becoming more optional -- needs new vtable entry // CHECK-NEXT: #ConcreteValue.variantOptionality: (ConcreteValue) -> (S?) -> S : @$s27vtable_thunks_reabstraction13ConcreteValueC18variantOptionality1xAA1SVAGSg_tF // ConcreteValue.variantOptionality(x:) // CHECK-NEXT: #ConcreteValue.variantOptionalityMetatypes: (ConcreteValue) -> (S.Type?) -> S.Type : @$s27vtable_thunks_reabstraction13ConcreteValueC27variantOptionalityMetatypes1xAA1SVmAGmSg_tF // ConcreteValue.variantOptionalityMetatypes(x:) // CHECK-NEXT: #ConcreteValue.variantOptionalityFunctions: (ConcreteValue) -> (((S) -> S)?) -> (S) -> S : @$s27vtable_thunks_reabstraction13ConcreteValueC27variantOptionalityFunctions1xAA1SVAGcA2GcSg_tF // ConcreteValue.variantOptionalityFunctions(x:) // CHECK-NEXT: #ConcreteValue.variantOptionalityTuples: (ConcreteValue) -> ((S, (S.Type, (S) -> S))?) -> (S, (S.Type, (S) -> S)) : @$s27vtable_thunks_reabstraction13ConcreteValueC24variantOptionalityTuples1xAA1SV_AGm_A2GcttAG_AGm_A2GcttSg_tF // ConcreteValue.variantOptionalityTuples(x:) // CHECK-NEXT: #ConcreteValue.deinit!deallocator: @$s27vtable_thunks_reabstraction13ConcreteValueCfD // ConcreteValue.__deallocating_deinit // CHECK-NEXT: } class ConcreteClass: Opaque { override func inAndOut(x: C) -> C { return x } override func inAndOutMetatypes(x: C.Type) -> C.Type { return x } override func inAndOutFunctions(x: @escaping (C) -> C) -> (C) -> C { return x } override func inAndOutTuples(x: ObnoxiousTuple) -> ObnoxiousTuple { return x } override func variantOptionality(x: C?) -> C { return x! } override func variantOptionalityMetatypes(x: C.Type?) -> C.Type { return x! } override func variantOptionalityFunctions(x: ((C) -> C)?) -> (C) -> C { return x! } override func variantOptionalityTuples(x: ObnoxiousTuple?) -> ObnoxiousTuple { return x! } } // CHECK-LABEL: sil_vtable ConcreteClass { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction13ConcreteClassC8inAndOut1xAA1CCAG_tFAA6OpaqueCAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to ConcreteClass.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction13ConcreteClassC17inAndOutMetatypes1xAA1CCmAGm_tF [override] // ConcreteClass.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction13ConcreteClassC17inAndOutFunctions1xAA1CCAGcA2Gc_tFAA6OpaqueCAdExxcxxc_tFTV [override] // vtable thunk for Opaque.inAndOutFunctions(x:) dispatching to ConcreteClass.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction13ConcreteClassC14inAndOutTuples1xAA1CC_AGm_A2GcttAG_AGm_A2Gctt_tFAA6OpaqueCAdEx_xm_xxcttx_xm_xxctt_tFTV [override] // vtable thunk for Opaque.inAndOutTuples(x:) dispatching to ConcreteClass.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction13ConcreteClassC18variantOptionality1xAA1CCAGSg_tFAA6OpaqueCAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to ConcreteClass.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction13ConcreteClassC27variantOptionalityMetatypes1xAA1CCmAGmSg_tF [override] // ConcreteClass.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction13ConcreteClassC27variantOptionalityFunctions1xAA1CCAGcA2GcSg_tFAA6OpaqueCAdExxcSgxxc_tFTV [override] // vtable thunk for Opaque.variantOptionalityFunctions(x:) dispatching to ConcreteClass.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction13ConcreteClassC24variantOptionalityTuples1xAA1CC_AGm_A2GcttAG_AGm_A2GcttSg_tFAA6OpaqueCAdEx_xm_xxcttSgx_xm_xxctt_tFTV [override] // vtable thunk for Opaque.variantOptionalityTuples(x:) dispatching to ConcreteClass.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction13ConcreteClassCACycfC [override] // Class references are ABI-compatible with optional class references, and // similarly for class metatypes. // // Function and tuple optionality change still needs a new vtable entry // as above. // CHECK-NEXT: #ConcreteClass.variantOptionalityFunctions: (ConcreteClass) -> (((C) -> C)?) -> (C) -> C : @$s27vtable_thunks_reabstraction13ConcreteClassC27variantOptionalityFunctions1xAA1CCAGcA2GcSg_tF // ConcreteClass.variantOptionalityFunctions(x:) // CHECK-NEXT: #ConcreteClass.variantOptionalityTuples: (ConcreteClass) -> ((C, (C.Type, (C) -> C))?) -> (C, (C.Type, (C) -> C)) : @$s27vtable_thunks_reabstraction13ConcreteClassC24variantOptionalityTuples1xAA1CC_AGm_A2GcttAG_AGm_A2GcttSg_tF // ConcreteClass.variantOptionalityTuples(x:) // CHECK-NEXT: #ConcreteClass.deinit!deallocator: @$s27vtable_thunks_reabstraction13ConcreteClassCfD // ConcreteClass.__deallocating_deinit // CHECK-NEXT: } class ConcreteClassVariance: Opaque { override func inAndOut(x: B) -> D { return x as! D } override func variantOptionality(x: B?) -> D { return x as! D } } // CHECK-LABEL: sil_vtable ConcreteClassVariance { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction21ConcreteClassVarianceC8inAndOut1xAA1DCAA1BC_tFAA6OpaqueCAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to ConcreteClassVariance.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction21ConcreteClassVarianceC18variantOptionality1xAA1DCAA1BCSg_tFAA6OpaqueCAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to ConcreteClassVariance.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF [inherited] // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction21ConcreteClassVarianceCACycfC [override] // No new vtable entries -- class references are ABI compatible with // optional class references. // CHECK-NEXT: #ConcreteClassVariance.deinit!deallocator: @$s27vtable_thunks_reabstraction21ConcreteClassVarianceCfD // ConcreteClassVariance.__deallocating_deinit // CHECK-NEXT: } class OpaqueTuple: Opaque<(U, U)> { override func inAndOut(x: (U, U)) -> (U, U) { return x } override func variantOptionality(x: (U, U)?) -> (U, U) { return x! } } // CHECK-LABEL: sil_vtable OpaqueTuple { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction11OpaqueTupleC8inAndOut1xx_xtx_xt_tFAA0D0CAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to OpaqueTuple.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction11OpaqueTupleC18variantOptionality1xx_xtx_xtSg_tFAA0D0CAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to OpaqueTuple.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF [inherited] // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction11OpaqueTupleCACyxGycfC [override] // Optionality change of tuple. // CHECK-NEXT: #OpaqueTuple.variantOptionality: (OpaqueTuple) -> ((U, U)?) -> (U, U) : @$s27vtable_thunks_reabstraction11OpaqueTupleC18variantOptionality1xx_xtx_xtSg_tF // OpaqueTuple.variantOptionality(x:) // CHECK-NEXT: #OpaqueTuple.deinit!deallocator: @$s27vtable_thunks_reabstraction11OpaqueTupleCfD // OpaqueTuple.__deallocating_deinit // CHECK-NEXT: } class ConcreteTuple: Opaque<(S, S)> { override func inAndOut(x: (S, S)) -> (S, S) { return x } override func variantOptionality(x: (S, S)?) -> (S, S) { return x! } } // CHECK-LABEL: sil_vtable ConcreteTuple { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction13ConcreteTupleC8inAndOut1xAA1SV_AGtAG_AGt_tFAA6OpaqueCAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to ConcreteTuple.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction13ConcreteTupleC18variantOptionality1xAA1SV_AGtAG_AGtSg_tFAA6OpaqueCAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to ConcreteTuple.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF [inherited] // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction13ConcreteTupleCACycfC [override] // Optionality change of tuple. // CHECK-NEXT: #ConcreteTuple.variantOptionality: (ConcreteTuple) -> ((S, S)?) -> (S, S) : @$s27vtable_thunks_reabstraction13ConcreteTupleC18variantOptionality1xAA1SV_AGtAG_AGtSg_tF // ConcreteTuple.variantOptionality(x:) // CHECK-NEXT: #ConcreteTuple.deinit!deallocator: @$s27vtable_thunks_reabstraction13ConcreteTupleCfD // ConcreteTuple.__deallocating_deinit // CHECK-NEXT: } class OpaqueFunction: Opaque<(U) -> V> { override func inAndOut(x: @escaping (U) -> V) -> (U) -> V { return x } override func variantOptionality(x: ((U) -> V)?) -> (U) -> V { return x! } } // CHECK-LABEL: sil_vtable OpaqueFunction { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction14OpaqueFunctionC8inAndOut1xq_xcq_xc_tFAA0D0CAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to OpaqueFunction.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction14OpaqueFunctionC18variantOptionality1xq_xcq_xcSg_tFAA0D0CAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to OpaqueFunction.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF [inherited] // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction14OpaqueFunctionCACyxq_GycfC [override] // Optionality change of function. // CHECK-NEXT: #OpaqueFunction.variantOptionality: (OpaqueFunction) -> (((U) -> V)?) -> (U) -> V : @$s27vtable_thunks_reabstraction14OpaqueFunctionC18variantOptionality1xq_xcq_xcSg_tF // OpaqueFunction.variantOptionality(x:) // CHECK-NEXT: #OpaqueFunction.deinit!deallocator: @$s27vtable_thunks_reabstraction14OpaqueFunctionCfD // OpaqueFunction.__deallocating_deinit // CHECK-NEXT: } class ConcreteFunction: Opaque<(S) -> S> { override func inAndOut(x: @escaping (S) -> S) -> (S) -> S { return x } override func variantOptionality(x: ((S) -> S)?) -> (S) -> S { return x! } } // CHECK-LABEL: sil_vtable ConcreteFunction { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction16ConcreteFunctionC8inAndOut1xAA1SVAGcA2Gc_tFAA6OpaqueCAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to ConcreteFunction.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction16ConcreteFunctionC18variantOptionality1xAA1SVAGcA2GcSg_tFAA6OpaqueCAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to ConcreteFunction.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF [inherited] // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction16ConcreteFunctionCACycfC [override] // Optionality change of function. // CHECK-NEXT: #ConcreteFunction.variantOptionality: (ConcreteFunction) -> (((S) -> S)?) -> (S) -> S : @$s27vtable_thunks_reabstraction16ConcreteFunctionC18variantOptionality1xAA1SVAGcA2GcSg_tF // ConcreteFunction.variantOptionality(x:) // CHECK-NEXT: #ConcreteFunction.deinit!deallocator: @$s27vtable_thunks_reabstraction16ConcreteFunctionCfD // ConcreteFunction.__deallocating_deinit // CHECK-NEXT: } class OpaqueMetatype: Opaque { override func inAndOut(x: U.Type) -> U.Type { return x } override func variantOptionality(x: U.Type?) -> U.Type { return x! } } // CHECK-LABEL: sil_vtable OpaqueMetatype { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction14OpaqueMetatypeC8inAndOut1xxmxm_tFAA0D0CAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to OpaqueMetatype.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction14OpaqueMetatypeC18variantOptionality1xxmxmSg_tFAA0D0CAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to OpaqueMetatype.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF [inherited] // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction14OpaqueMetatypeCACyxGycfC [override] // Optionality change of metatype. // CHECK-NEXT: #OpaqueMetatype.variantOptionality: (OpaqueMetatype) -> (U.Type?) -> U.Type : @$s27vtable_thunks_reabstraction14OpaqueMetatypeC18variantOptionality1xxmxmSg_tF // OpaqueMetatype.variantOptionality(x:) // CHECK-NEXT: #OpaqueMetatype.deinit!deallocator: @$s27vtable_thunks_reabstraction14OpaqueMetatypeCfD // OpaqueMetatype.__deallocating_deinit // CHECK-NEXT: } class ConcreteValueMetatype: Opaque { override func inAndOut(x: S.Type) -> S.Type { return x } override func variantOptionality(x: S.Type?) -> S.Type { return x! } } // CHECK-LABEL: sil_vtable ConcreteValueMetatype { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction21ConcreteValueMetatypeC8inAndOut1xAA1SVmAGm_tFAA6OpaqueCAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to ConcreteValueMetatype.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction21ConcreteValueMetatypeC18variantOptionality1xAA1SVmAGmSg_tFAA6OpaqueCAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to ConcreteValueMetatype.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF [inherited] // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction21ConcreteValueMetatypeCACycfC [override] // Optionality change of metatype. // CHECK-NEXT: #ConcreteValueMetatype.variantOptionality: (ConcreteValueMetatype) -> (S.Type?) -> S.Type : @$s27vtable_thunks_reabstraction21ConcreteValueMetatypeC18variantOptionality1xAA1SVmAGmSg_tF // ConcreteValueMetatype.variantOptionality(x:) // CHECK-NEXT: #ConcreteValueMetatype.deinit!deallocator: @$s27vtable_thunks_reabstraction21ConcreteValueMetatypeCfD // ConcreteValueMetatype.__deallocating_deinit // CHECK-NEXT: } class ConcreteClassMetatype: Opaque { override func inAndOut(x: C.Type) -> C.Type { return x } override func variantOptionality(x: C.Type?) -> C.Type { return x! } } // CHECK-LABEL: sil_vtable ConcreteClassMetatype { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction21ConcreteClassMetatypeC8inAndOut1xAA1CCmAGm_tFAA6OpaqueCAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to ConcreteClassMetatype.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction21ConcreteClassMetatypeC18variantOptionality1xAA1CCmAGmSg_tFAA6OpaqueCAdExSgx_tFTV [override] // vtable thunk for Opaque.variantOptionality(x:) dispatching to ConcreteClassMetatype.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF [inherited] // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction21ConcreteClassMetatypeCACycfC [override] // Class metatypes are ABI compatible with optional class metatypes. // CHECK-NEXT: #ConcreteClassMetatype.deinit!deallocator: @$s27vtable_thunks_reabstraction21ConcreteClassMetatypeCfD // ConcreteClassMetatype.__deallocating_deinit // CHECK-NEXT: } class ConcreteOptional: Opaque { override func inAndOut(x: S?) -> S? { return x } // FIXME: Should we allow this override in Sema? // override func variantOptionality(x: S??) -> S? { return x! } } // CHECK-LABEL: sil_vtable ConcreteOptional { // CHECK-NEXT: #Opaque.inAndOut: (Opaque) -> (T) -> T : @$s27vtable_thunks_reabstraction16ConcreteOptionalC8inAndOut1xAA1SVSgAH_tFAA6OpaqueCAdExx_tFTV [override] // vtable thunk for Opaque.inAndOut(x:) dispatching to ConcreteOptional.inAndOut(x:) // CHECK-NEXT: #Opaque.inAndOutGeneric: (Opaque) -> (T, U) -> U : @$s27vtable_thunks_reabstraction6OpaqueC15inAndOutGeneric1x1yqd__x_qd__tlF [inherited] // Opaque.inAndOutGeneric(x:y:) // CHECK-NEXT: #Opaque.inAndOutMetatypes: (Opaque) -> (T.Type) -> T.Type : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutMetatypes1xxmxm_tF [inherited] // Opaque.inAndOutMetatypes(x:) // CHECK-NEXT: #Opaque.inAndOutFunctions: (Opaque) -> (@escaping (T) -> T) -> (T) -> T : @$s27vtable_thunks_reabstraction6OpaqueC17inAndOutFunctions1xxxcxxc_tF [inherited] // Opaque.inAndOutFunctions(x:) // CHECK-NEXT: #Opaque.inAndOutTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T)) : @$s27vtable_thunks_reabstraction6OpaqueC14inAndOutTuples1xx_xm_xxcttx_xm_xxctt_tF [inherited] // Opaque.inAndOutTuples(x:) // CHECK-NEXT: #Opaque.variantOptionality: (Opaque) -> (T) -> T? : @$s27vtable_thunks_reabstraction6OpaqueC18variantOptionality1xxSgx_tF [inherited] // Opaque.variantOptionality(x:) // CHECK-NEXT: #Opaque.variantOptionalityMetatypes: (Opaque) -> (T.Type) -> T.Type? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityMetatypes1xxmSgxm_tF [inherited] // Opaque.variantOptionalityMetatypes(x:) // CHECK-NEXT: #Opaque.variantOptionalityFunctions: (Opaque) -> (@escaping (T) -> T) -> ((T) -> T)? : @$s27vtable_thunks_reabstraction6OpaqueC27variantOptionalityFunctions1xxxcSgxxc_tF [inherited] // Opaque.variantOptionalityFunctions(x:) // CHECK-NEXT: #Opaque.variantOptionalityTuples: (Opaque) -> ((T, (T.Type, (T) -> T))) -> (T, (T.Type, (T) -> T))? : @$s27vtable_thunks_reabstraction6OpaqueC24variantOptionalityTuples1xx_xm_xxcttSgx_xm_xxctt_tF [inherited] // Opaque.variantOptionalityTuples(x:) // CHECK-NEXT: #Opaque.init!allocator: (Opaque.Type) -> () -> Opaque : @$s27vtable_thunks_reabstraction16ConcreteOptionalCACycfC [override] // CHECK-NEXT: #ConcreteOptional.deinit!deallocator: @$s27vtable_thunks_reabstraction16ConcreteOptionalCfD // ConcreteOptional.__deallocating_deinit // CHECK-NEXT: } // Make sure we remap the method's innermost generic parameters // to the correct depth class GenericBase { func doStuff(t: T, u: U) {} init(t: T, u: U) {} } // CHECK-LABEL: sil_vtable GenericBase { // CHECK-NEXT: #GenericBase.doStuff: (GenericBase) -> (T, U) -> () : @$s27vtable_thunks_reabstraction11GenericBaseC7doStuff1t1uyx_qd__tlF // GenericBase.doStuff(t:u:) // CHECK-NEXT: #GenericBase.init!allocator: (GenericBase.Type) -> (T, U) -> GenericBase : @$s27vtable_thunks_reabstraction11GenericBaseC1t1uACyxGx_qd__tclufC // CHECK-NEXT: #GenericBase.deinit!deallocator: @$s27vtable_thunks_reabstraction11GenericBaseCfD // GenericBase.__deallocating_deinit // CHECK-NEXT: } class ConcreteSub : GenericBase { override func doStuff(t: Int, u: U) { super.doStuff(t: t, u: u) } override init(t: Int, u: U) { super.init(t: t, u: u) } } // CHECK-LABEL: sil_vtable ConcreteSub { // CHECK-NEXT: #GenericBase.doStuff: (GenericBase) -> (T, U) -> () : @$s27vtable_thunks_reabstraction11ConcreteSubC7doStuff1t1uySi_xtlFAA11GenericBaseCAdeFyx_qd__tlFTV [override] // vtable thunk for GenericBase.doStuff(t:u:) dispatching to ConcreteSub.doStuff(t:u:) // CHECK-NEXT: #GenericBase.init!allocator: (GenericBase.Type) -> (T, U) -> GenericBase : @$s27vtable_thunks_reabstraction11ConcreteSubC1t1uACSi_xtclufCAA11GenericBaseCAdeGyxGx_qd__tclufCTV [override] // CHECK-NEXT: #ConcreteSub.deinit!deallocator: @$s27vtable_thunks_reabstraction11ConcreteSubCfD // ConcreteSub.__deallocating_deinit // CHECK-NEXT: } class ConcreteBase { init(t: Int, u: U) {} func doStuff(t: Int, u: U) {} } // CHECK-LABEL: sil_vtable ConcreteBase { // CHECK-NEXT: #ConcreteBase.init!allocator: (ConcreteBase.Type) -> (Int, U) -> ConcreteBase : @$s27vtable_thunks_reabstraction12ConcreteBaseC1t1uACSi_xtclufC // CHECK-NEXT: #ConcreteBase.doStuff: (ConcreteBase) -> (Int, U) -> () : @$s27vtable_thunks_reabstraction12ConcreteBaseC7doStuff1t1uySi_xtlF // ConcreteBase.doStuff(t:u:) // CHECK-NEXT: #ConcreteBase.deinit!deallocator: @$s27vtable_thunks_reabstraction12ConcreteBaseCfD // ConcreteBase.__deallocating_deinit // CHECK-NEXT: } class GenericSub : ConcreteBase { override init(t: Int, u: U) { super.init(t: t, u: u) } override func doStuff(t: Int, u: U) { super.doStuff(t: t, u: u) } } // CHECK-LABEL: sil_vtable GenericSub { // CHECK-NEXT: #ConcreteBase.init!allocator: (ConcreteBase.Type) -> (Int, U) -> ConcreteBase : @$s27vtable_thunks_reabstraction10GenericSubC1t1uACyxGSi_qd__tclufC [override] // CHECK-NEXT: #ConcreteBase.doStuff: (ConcreteBase) -> (Int, U) -> () : @$s27vtable_thunks_reabstraction10GenericSubC7doStuff1t1uySi_qd__tlF [override] // GenericSub.doStuff(t:u:) // CHECK-NEXT: #GenericSub.deinit!deallocator: @$s27vtable_thunks_reabstraction10GenericSubCfD // GenericSub.__deallocating_deinit // CHECK-NEXT: } // Issue with generic parameter index class MoreGenericSub1 : GenericBase { override func doStuff(t: T, u: U) { super.doStuff(t: t, u: u) } } // CHECK-LABEL: sil_vtable MoreGenericSub1 { // CHECK-NEXT: #GenericBase.doStuff: (GenericBase) -> (T, U) -> () : @$s27vtable_thunks_reabstraction15MoreGenericSub1C7doStuff1t1uyx_qd__tlF [override] // MoreGenericSub1.doStuff(t:u:) // CHECK-NEXT: #GenericBase.init!allocator: (GenericBase.Type) -> (T, U) -> GenericBase : @$s27vtable_thunks_reabstraction15MoreGenericSub1C1t1uACyxq_Gx_qd__tclufC [override] // CHECK-NEXT: #MoreGenericSub1.deinit!deallocator: @$s27vtable_thunks_reabstraction15MoreGenericSub1CfD // MoreGenericSub1.__deallocating_deinit // CHECK-NEXT: } class MoreGenericSub2 : GenericBase { override func doStuff(t: T, u: U) { super.doStuff(t: t, u: u) } } // CHECK-LABEL: sil_vtable MoreGenericSub2 { // CHECK-NEXT: #GenericBase.doStuff: (GenericBase) -> (T, U) -> () : @$s27vtable_thunks_reabstraction15MoreGenericSub2C7doStuff1t1uyq__qd__tlF [override] // MoreGenericSub2.doStuff(t:u:) // CHECK-NEXT: #GenericBase.init!allocator: (GenericBase.Type) -> (T, U) -> GenericBase : @$s27vtable_thunks_reabstraction15MoreGenericSub2C1t1uACyxq_Gq__qd__tclufC [override] // CHECK-NEXT: #MoreGenericSub2.deinit!deallocator: @$s27vtable_thunks_reabstraction15MoreGenericSub2CfD // MoreGenericSub2.__deallocating_deinit // CHECK-NEXT: } protocol SE_0267_P1 {} class SE_0267_Base1 { func foo() where T: SE_0267_P1 {} } class SE_0267_Derived1: SE_0267_Base1 { override func foo() {} } // CHECK-LABEL: sil_vtable SE_0267_Derived1 { // CHECK-NEXT: #SE_0267_Base1.foo: (SE_0267_Base1) -> () -> () : @$s27vtable_thunks_reabstraction16SE_0267_Derived1C3fooyyFAA0D11_0267_Base1CADyyAA0D8_0267_P1RzlFTV [override] // CHECK-NEXT: #SE_0267_Base1.init // CHECK-NEXT: #SE_0267_Derived1.foo: (SE_0267_Derived1) -> () -> () : @$s27vtable_thunks_reabstraction16SE_0267_Derived1C3fooyyF // CHECK-NEXT: #SE_0267_Derived1.deinit // CHECK-NEXT: } class SE_0267_Base2 { func foo() -> T where T: FixedWidthInteger { fatalError() } } class SE_0267_Derived2: SE_0267_Base2 { override func foo() -> Int { return .zero } } // CHECK-LABEL: sil_vtable SE_0267_Derived2 { // CHECK-NEXT: #SE_0267_Base2.foo: (SE_0267_Base2) -> () -> T : @$s27vtable_thunks_reabstraction16SE_0267_Derived2C3fooSiyFAA0D11_0267_Base2CADxys17FixedWidthIntegerRzlFTV [override] // CHECK-NEXT: #SE_0267_Base2.init // CHECK-NEXT: #SE_0267_Derived2.deinit // CHECK-NEXT: }