mirror of
https://github.com/apple/swift.git
synced 2026-10-04 11:58:22 +02:00
51 lines
2.6 KiB
Plaintext
51 lines
2.6 KiB
Plaintext
// RUN: %target-sil-opt -enable-sil-verify-all -closure-specialization %s | %FileCheck %s
|
|
|
|
// A value captured more than once, with a mark_dependence on it, must still be specialized:
|
|
// uniqueCaptureArguments redirects the mark_dependence base onto the capture's identity cast.
|
|
|
|
import Builtin
|
|
|
|
class Storage {}
|
|
|
|
struct Val {}
|
|
|
|
sil private [readonly] [ossa] @takesClosure : $@convention(thin) (@guaranteed @noescape @callee_guaranteed (Val) -> Val) -> Val {
|
|
bb0(%0 : @guaranteed $@noescape @callee_guaranteed (Val) -> Val):
|
|
%v = struct $Val ()
|
|
%r = apply %0(%v) : $@noescape @callee_guaranteed (Val) -> Val
|
|
return %r : $Val
|
|
}
|
|
|
|
// %0 is captured twice; the specialized function takes it as two @guaranteed arguments and
|
|
// re-materializes the mark_dependence on the first one.
|
|
// CHECK-LABEL: sil {{.*}}@$s12takesClosure{{.*}}Tf1c_n : $@convention(thin) (@guaranteed Storage, @guaranteed Storage) -> Val {
|
|
// CHECK: [[PA:%[0-9]+]] = partial_apply [callee_guaranteed] [on_stack] {{%[0-9]+}}(%0, %1)
|
|
// CHECK: mark_dependence [[PA]] on %0
|
|
// CHECK-LABEL: } // end sil function '$s12takesClosure{{.*}}Tf1c_n'
|
|
sil private [ossa] @twiceCapturingClosure : $@convention(thin) (Val, @guaranteed Storage, @guaranteed Storage) -> Val {
|
|
bb0(%0 : $Val, %1 : @closureCapture @guaranteed $Storage, %2 : @closureCapture @guaranteed $Storage):
|
|
%r = struct $Val ()
|
|
return %r : $Val
|
|
}
|
|
|
|
// The apply is rewritten to a direct call passing the capture twice; the dead closure and its
|
|
// mark_dependence are deleted.
|
|
// CHECK-LABEL: sil [ossa] @testMultiplyCaptured : $@convention(method) (@guaranteed Storage) -> Val {
|
|
// CHECK-NOT: partial_apply
|
|
// CHECK-NOT: mark_dependence
|
|
// CHECK: [[F:%[0-9]+]] = function_ref @$s12takesClosure{{.*}}Tf1c_n
|
|
// CHECK: apply [[F]](%0, %0)
|
|
// CHECK-NOT: partial_apply
|
|
// CHECK-NOT: mark_dependence
|
|
// CHECK-LABEL: } // end sil function 'testMultiplyCaptured'
|
|
sil [ossa] @testMultiplyCaptured : $@convention(method) (@guaranteed Storage) -> Val {
|
|
bb0(%0 : @guaranteed $Storage):
|
|
%c = function_ref @twiceCapturingClosure : $@convention(thin) (Val, @guaranteed Storage, @guaranteed Storage) -> Val
|
|
%pa = partial_apply [callee_guaranteed] [on_stack] %c(%0, %0) : $@convention(thin) (Val, @guaranteed Storage, @guaranteed Storage) -> Val
|
|
%md = mark_dependence %pa : $@noescape @callee_guaranteed (Val) -> Val on %0 : $Storage
|
|
%f = function_ref @takesClosure : $@convention(thin) (@guaranteed @noescape @callee_guaranteed (Val) -> Val) -> Val
|
|
%r = apply %f(%md) : $@convention(thin) (@guaranteed @noescape @callee_guaranteed (Val) -> Val) -> Val
|
|
destroy_value %md
|
|
return %r : $Val
|
|
}
|