1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107
|
// RUN: %target-sil-opt -outliner %s -enable-sil-verify-all | %FileCheck %s
// REQUIRES: OS=macosx
sil_stage canonical
import Builtin
import Swift
import Foundation
@objc class MyObject {
@objc static func take(arg: Data?) -> Data?
}
sil @getData : $@convention(thin) () -> @owned Data
sil @$s10Foundation4DataV19_bridgeToObjectiveCSo6NSDataCyF : $@convention(method) (@guaranteed Data) -> @owned NSData
sil @$s10Foundation4DataV36_unconditionallyBridgeFromObjectiveCyACSo6NSDataCSgFZ : $@convention(method) (@guaranteed Optional<NSData>, @thin Data.Type) -> @owned Data
// We used to have a use-after release failure.
// CHECK-LABEL: sil [Osize] @test : $@convention(thin) (@owned MyObject) -> () {
// CHECK: bb0([[ARG:%.*]] : $MyObject):
// CHECK: [[META:%.*]] = metatype $@objc_metatype MyObject.Type
// CHECK: [[FUN1:%.*]] = function_ref @getData : $@convention(thin) () -> @owned Data
// CHECK: [[DATA:%.*]] = apply [[FUN1]]() : $@convention(thin) () -> @owned Data
// CHECK: release_value [[ARG]] : $MyObject
// CHECK: [[OUTLINED:%.*]] = function_ref @$s4main8MyObjectC4take3arg10Foundation4DataVSgAI_tFZToTembnb_ : $@convention(thin) (@owned Data, @objc_metatype MyObject.Type) -> @owned Optional<Data>
// CHECK: [[RES:%.*]] = apply [[OUTLINED]]([[DATA]], [[META]]) : $@convention(thin) (@owned Data, @objc_metatype MyObject.Type) -> @owned Optional<Data>
// CHECK: br bb1
// CHECK: bb1:
// CHECK: release_value [[RES]]
// CHECK: [[T:%.*]] = tuple ()
// CHECK: return [[T]] : $()
// CHECK: } // end sil function 'test'
sil [Osize] @test : $@convention(thin) (@owned MyObject) -> () {
bb0(%0: $MyObject):
%35 = metatype $@objc_metatype MyObject.Type
%41 = function_ref @getData : $@convention(thin) () -> @owned Data
%43 = apply %41() : $@convention(thin) () -> @owned Data
%44 = function_ref @$s10Foundation4DataV19_bridgeToObjectiveCSo6NSDataCyF : $@convention(method) (@guaranteed Data) -> @owned NSData
%45 = apply %44(%43) : $@convention(method) (@guaranteed Data) -> @owned NSData
%46 = enum $Optional<NSData>, #Optional.some!enumelt, %45 : $NSData
release_value %0 : $MyObject
release_value %43 : $Data
%50 = objc_method %35 : $@objc_metatype MyObject.Type, #MyObject.take!foreign : (MyObject.Type) -> (Data?) -> Data?, $@convention(objc_method) (Optional<NSData>, @objc_metatype MyObject.Type) -> @autoreleased Optional<NSData>
%51 = apply %50(%46, %35) : $@convention(objc_method) (Optional<NSData>, @objc_metatype MyObject.Type) -> @autoreleased Optional<NSData>
release_value %46 : $Optional<NSData>
switch_enum %51 : $Optional<NSData>, case #Optional.some!enumelt: bb5, case #Optional.none!enumelt: bb6
bb5(%54 : $NSData):
%55 = function_ref @$s10Foundation4DataV36_unconditionallyBridgeFromObjectiveCyACSo6NSDataCSgFZ : $@convention(method) (@guaranteed Optional<NSData>, @thin Data.Type) -> @owned Data
%56 = enum $Optional<NSData>, #Optional.some!enumelt, %54 : $NSData
%57 = metatype $@thin Data.Type
%58 = apply %55(%56, %57) : $@convention(method) (@guaranteed Optional<NSData>, @thin Data.Type) -> @owned Data
%59 = enum $Optional<Data>, #Optional.some!enumelt, %58 : $Data
release_value %56 : $Optional<NSData>
br bb7(%59 : $Optional<Data>)
bb6:
%62 = enum $Optional<Data>, #Optional.none!enumelt
br bb7(%62 : $Optional<Data>)
bb7(%64 : $Optional<Data>):
release_value %64 : $Optional<Data>
%102 = tuple ()
return %102 : $()
}
sil [Osize] @test_dont_crash : $@convention(thin) (@owned MyObject) -> () {
bb0(%0: $MyObject):
%35 = metatype $@objc_metatype MyObject.Type
%41 = function_ref @getData : $@convention(thin) () -> @owned Data
%43 = apply %41() : $@convention(thin) () -> @owned Data
%44 = function_ref @$s10Foundation4DataV19_bridgeToObjectiveCSo6NSDataCyF : $@convention(method) (@guaranteed Data) -> @owned NSData
%45 = apply %44(%43) : $@convention(method) (@guaranteed Data) -> @owned NSData
%46 = enum $Optional<NSData>, #Optional.some!enumelt, %45 : $NSData
br bb4
bb4:
release_value %0 : $MyObject
release_value %43 : $Data
%50 = objc_method %35 : $@objc_metatype MyObject.Type, #MyObject.take!foreign : (MyObject.Type) -> (Data?) -> Data?, $@convention(objc_method) (Optional<NSData>, @objc_metatype MyObject.Type) -> @autoreleased Optional<NSData>
%51 = apply %50(%46, %35) : $@convention(objc_method) (Optional<NSData>, @objc_metatype MyObject.Type) -> @autoreleased Optional<NSData>
release_value %46 : $Optional<NSData>
switch_enum %51 : $Optional<NSData>, case #Optional.some!enumelt: bb5, case #Optional.none!enumelt: bb6
bb5(%54 : $NSData):
%55 = function_ref @$s10Foundation4DataV36_unconditionallyBridgeFromObjectiveCyACSo6NSDataCSgFZ : $@convention(method) (@guaranteed Optional<NSData>, @thin Data.Type) -> @owned Data
%56 = enum $Optional<NSData>, #Optional.some!enumelt, %54 : $NSData
%57 = metatype $@thin Data.Type
%58 = apply %55(%56, %57) : $@convention(method) (@guaranteed Optional<NSData>, @thin Data.Type) -> @owned Data
%59 = enum $Optional<Data>, #Optional.some!enumelt, %58 : $Data
release_value %56 : $Optional<NSData>
br bb7(%59 : $Optional<Data>)
bb6:
%62 = enum $Optional<Data>, #Optional.none!enumelt
br bb7(%62 : $Optional<Data>)
bb7(%64 : $Optional<Data>):
release_value %64 : $Optional<Data>
%102 = tuple ()
return %102 : $()
}
|