mirror of
https://github.com/apple/swift.git
synced 2026-10-14 15:51:20 +02:00
Generic COM conformances carry interface adjustments rather than Swift witness tables. Select com_method for their requirements, including calls from protocol extensions, so IRGen can apply the adjustment to the foreign receiver. Materialize read-write property accesses through the foreign getter and setter. A COM interface does not provide a Swift coroutine accessor, and the setter must also perform writeback when the access throws.
59 lines
2.3 KiB
Swift
59 lines
2.3 KiB
Swift
// RUN: %empty-directory(%t)
|
|
// RUN: %target-swift-frontend -enable-experimental-com-interop -module-name COM -emit-module-path %t/COM.swiftmodule %S/../Inputs/COM.swift
|
|
// RUN: %target-swift-frontend -enable-experimental-com-interop -I %t -sil-verify-all -emit-silgen %s | %FileCheck %s
|
|
// RUN: %target-swift-frontend -enable-experimental-com-interop -I %t -sil-verify-all -emit-sil %s -o /dev/null
|
|
|
|
@com(interface: "10000000-0000-0000-0000-000000000001")
|
|
public protocol IProperties: AnyObject {
|
|
var value: CInt { get set }
|
|
subscript(_ index: CInt) -> CInt { get set }
|
|
}
|
|
|
|
// CHECK-LABEL: sil [ossa] @$s{{.*}}9increment
|
|
// CHECK: open_com_existential
|
|
// CHECK: [[GET:%.*]] = com_method {{%.*}}, #IProperties.value!getter
|
|
// CHECK: [[VALUE:%.*]] = apply [[GET]]
|
|
// CHECK: store [[VALUE]] to [trivial] [[TEMP:%[0-9]+]]
|
|
// CHECK-NOT: #IProperties.value!modify
|
|
// CHECK: [[SET:%.*]] = com_method {{%.*}}, #IProperties.value!setter
|
|
// CHECK: apply [[SET]]
|
|
// CHECK: dealloc_stack [[TEMP]]
|
|
// CHECK: return
|
|
public func increment(_ interface: any IProperties) {
|
|
interface.value += 1
|
|
}
|
|
|
|
// CHECK-LABEL: sil [ossa] @$s{{.*}}4edit
|
|
// CHECK: open_com_existential
|
|
// CHECK: [[GET:%.*]] = com_method {{%.*}}, #IProperties.subscript!getter
|
|
// CHECK: apply [[GET]]
|
|
// CHECK-NOT: #IProperties.subscript!modify
|
|
// CHECK: try_apply {{.*}}, normal [[NORMAL:bb[0-9]+]], error [[ERROR:bb[0-9]+]]
|
|
// CHECK: [[NORMAL]]
|
|
// CHECK: [[SET:%.*]] = com_method {{%.*}}, #IProperties.subscript!setter
|
|
// CHECK: apply [[SET]]
|
|
// CHECK: return
|
|
// CHECK: [[ERROR]]
|
|
// CHECK: [[SET:%.*]] = com_method {{%.*}}, #IProperties.subscript!setter
|
|
// CHECK: apply [[SET]]
|
|
// CHECK: throw
|
|
public func edit(_ interface: any IProperties, _ index: CInt,
|
|
_ body: (inout CInt) throws -> ()) rethrows {
|
|
try body(&interface[index])
|
|
}
|
|
|
|
// Generic receivers use the same foreign getter/setter materialization.
|
|
// CHECK-LABEL: sil [ossa] @$s{{.*}}7generic
|
|
// CHECK-NOT: #IProperties.value!modify
|
|
// CHECK: [[GET:%.*]] = com_method {{%.*}}, #IProperties.value!getter
|
|
// CHECK: [[VALUE:%.*]] = apply [[GET]]
|
|
// CHECK: store [[VALUE]] to [trivial] [[TEMP:%[0-9]+]]
|
|
// CHECK-NOT: #IProperties.value!modify
|
|
// CHECK: [[SET:%.*]] = com_method {{%.*}}, #IProperties.value!setter
|
|
// CHECK: apply [[SET]]
|
|
// CHECK: dealloc_stack [[TEMP]]
|
|
// CHECK: return
|
|
public func generic<T: IProperties>(_ interface: T) {
|
|
interface.value += 1
|
|
}
|