Files
swift-mirror/test/SILOptimizer/sil_combine_objc.sil
Josh Soref 730b16c569 Spelling siloptimizer
* access
* accessed
* accesses
* accessor
* acquiring
* across
* activated
* additive
* address
* addresses'
* aggregated
* analysis
* and
* appropriately
* archetype
* argument
* associated
* availability
* barriers
* because
* been
* beginning
* belongs
* beneficial
* blocks
* borrow
* builtin
* cannot
* canonical
* canonicalize
* clazz
* cleanup
* coalesceable
* coalesced
* comparisons
* completely
* component
* computed
* concrete
* conjunction
* conservatively
* constituent
* construct
* consuming
* containing
* covered
* creates
* critical
* dataflow
* declaration
* defined
* defining
* definition
* deinitialization
* deliberately
* dependencies
* dependent
* deserialized
* destroy
* deterministic
* deterministically
* devirtualizes
* diagnostic
* diagnostics
* differentiation
* disable
* discipline
* dominate
* dominates
* don't
* element
* eliminate
* eliminating
* elimination
* embedded
* encounter
* epilogue
* epsilon
* escape
* escaping
* essential
* evaluating
* evaluation
* evaluator
* executing
* existential
* existentials
* explicit
* expression
* extended
* extension
* extract
* for
* from
* function
* generic
* guarantee
* guaranteed
* happened
* heuristic
* however
* identifiable
* immediately
* implementation
* improper
* include
* infinite
* initialize
* initialized
* initializer
* inside
* instruction
* interference
* interferes
* interleaved
* internal
* intersection
* intractable
* intrinsic
* invalidates
* irreducible
* irrelevant
* language
* lifetime
* literal
* looks
* materialize
* meaning
* mergeable
* might
* mimics
* modification
* modifies
* multiple
* mutating
* necessarily
* necessary
* needsmultiplecopies
* nonetheless
* nothing
* occurred
* occurs
* optimization
* optimizing
* original
* outside
* overflow
* overlapping
* overridden
* owned
* ownership
* parallel
* parameter
* paths
* patterns
* pipeline
* plottable
* possible
* potentially
* practically
* preamble
* precede
* preceding
* predecessor
* preferable
* preparation
* probably
* projection
* properties
* property
* protocol
* reabstraction
* reachable
* recognized
* recursive
* recursively
* redundant
* reentrancy
* referenced
* registry
* reinitialization
* reload
* represent
* requires
* response
* responsible
* retrieving
* returned
* returning
* returns
* rewriting
* rewritten
* sample
* scenarios
* scope
* should
* sideeffects
* similar
* simplify
* simplifycfg
* somewhat
* spaghetti
* specialization
* specializations
* specialized
* specially
* statistically
* substitute
* substitution
* succeeds
* successful
* successfully
* successor
* superfluous
* surprisingly
* suspension
* swift
* targeted
* that
* that our
* the
* therefore
* this
* those
* threshold
* through
* transform
* transformation
* truncated
* ultimate
* unchecked
* uninitialized
* unlikely
* unmanaged
* unoptimized key
* updataflow
* usefulness
* utilities
* villain
* whenever
* writes

Signed-off-by: Josh Soref <jsoref@users.noreply.github.com>
2022-10-03 18:31:33 -04:00

189 lines
8.9 KiB
Plaintext

// RUN: %target-sil-opt -enable-objc-interop -enable-sil-verify-all %s -sil-combine | %FileCheck %s
// https://github.com/apple/swift/issues/47641, rdar://32511494
// XFAIL: *
sil_stage canonical
import Builtin
import Swift
class ZZZ {
@objc deinit
init()
}
class C {}
sil @stringcore_invariant_check : $@convention(thin) (@owned _LegacyStringCore) -> @owned Optional<_CocoaString>
sil @reabstraction_thunk : $@convention(thin) (@owned @callee_owned () -> @owned Optional<_CocoaString>) -> @out Optional<_CocoaString>
// CHECK-LABEL: sil @dead_closure_elimination : $@convention(thin) (@owned _LegacyStringCore) -> ()
// CHECK: bb0
// CHECK-NEXT: release_value
// CHECK-NEXT: tuple
// CHECK-NEXT: return
sil @dead_closure_elimination : $@convention(thin) (@owned _LegacyStringCore) -> () {
bb0(%0 : $_LegacyStringCore):
%1 = function_ref @stringcore_invariant_check : $@convention(thin) (@owned _LegacyStringCore) -> @owned Optional<_CocoaString>
%2 = partial_apply %1(%0) : $@convention(thin) (@owned _LegacyStringCore) -> @owned Optional<_CocoaString>
%3 = function_ref @reabstraction_thunk : $@convention(thin) (@owned @callee_owned () -> @owned Optional<_CocoaString>) -> @out Optional<_CocoaString>
%4 = partial_apply %3(%2) : $@convention(thin) (@owned @callee_owned () -> @owned Optional<_CocoaString>) -> @out Optional<_CocoaString>
strong_release %4 : $@callee_owned () -> @out Optional<_CocoaString>
%5 = tuple()
return %5 : $()
}
// CHECK-LABEL: sil @dead_closure_elimination2
// CHECK: bb0
// CHECK-NEXT: br bb1
// CHECK: bb1
// CHECK-NEXT: release_value
// CHECK-NEXT: tuple
// CHECK-NEXT: return
sil @dead_closure_elimination2 : $@convention(thin) (@owned _LegacyStringCore) -> () {
bb0(%0 : $_LegacyStringCore):
%1 = function_ref @stringcore_invariant_check : $@convention(thin) (@owned _LegacyStringCore) -> @owned Optional<_CocoaString>
%2 = partial_apply %1(%0) : $@convention(thin) (@owned _LegacyStringCore) -> @owned Optional<_CocoaString>
%3 = function_ref @reabstraction_thunk : $@convention(thin) (@owned @callee_owned () -> @owned Optional<_CocoaString>) -> @out Optional<_CocoaString>
%4 = partial_apply %3(%2) : $@convention(thin) (@owned @callee_owned () -> @owned Optional<_CocoaString>) -> @out Optional<_CocoaString>
br bb1
bb1:
strong_retain %4 : $@callee_owned () -> @out Optional<_CocoaString>
strong_release %4 : $@callee_owned () -> @out Optional<_CocoaString>
strong_release %4 : $@callee_owned () -> @out Optional<_CocoaString>
%5 = tuple()
return %5 : $()
}
// FIXME: <rdar://problem/20980377> Add dead array elimination to DeadObjectElimination
// CHECK-LABEL: test_dead_array
// CHECK: bb0(%0 : $ZZZ):
// DISABLED-CHECK-NEXT: strong_release %0
// DISABLED-CHECK-NEXT: tuple
// DISABLED-CHECK-NEXT: return
sil @test_dead_array : $@convention(thin) (@owned ZZZ) -> () {
bb0(%0 : $ZZZ):
%1 = integer_literal $Builtin.Word, 1
%2 = function_ref @_allocate_uninitialized_ZZZ : $@convention(thin) (Builtin.Word) -> @owned (Array<ZZZ>, Builtin.RawPointer)
%3 = apply %2(%1) : $@convention(thin) (Builtin.Word) -> @owned (Array<ZZZ>, Builtin.RawPointer)
%4 = tuple_extract %3 : $(Array<ZZZ>, Builtin.RawPointer), 0
%5 = tuple_extract %3 : $(Array<ZZZ>, Builtin.RawPointer), 1
%6 = pointer_to_address %5 : $Builtin.RawPointer to [strict] $*ZZZ
store %0 to %6 : $*ZZZ
%8 = struct_extract %4 : $Array<ZZZ>, #Array._buffer
%9 = struct_extract %8 : $_ArrayBuffer<ZZZ>, #_ArrayBuffer._storage
%10 = struct_extract %9 : $_BridgeStorage<__ContiguousArrayStorageBase, _NSArrayCore>, #_BridgeStorage.rawValue
strong_release %10 : $Builtin.BridgeObject
%12 = tuple ()
return %12 : $()
}
sil [_semantics "array.uninitialized"] @_allocate_uninitialized_ZZZ : $@convention(thin) (Builtin.Word) -> @owned (Array<ZZZ>, Builtin.RawPointer)
// dead_array test helpers
sil [thunk] @dead_array_run_closure : $@convention(thin) (@owned @callee_owned () -> Bool) -> () {
bb0(%0 : $@callee_owned () -> Bool):
%1 = apply %0() : $@callee_owned () -> Bool
%2 = tuple ()
return %2 : $()
}
sil @dead_array_closure : $@convention(thin) (@inout _HeapBuffer<C, Int>) -> Bool {
bb0(%0 : $*_HeapBuffer<C, Int>):
%1 = struct_element_addr %0 : $*_HeapBuffer<C, Int>, #_HeapBuffer._storage // user: %2
%2 = is_unique %1 : $*Optional<Builtin.NativeObject> // user: %3
%3 = struct $Bool (%2 : $Builtin.Int1) // user: %4
return %3 : $Bool // id: %4
}
// Mimics Swift._allocateUninitializedArray
sil [_semantics "array.uninitialized"] @dead_array_alloc : $@convention(thin) <τ_0_0> (Builtin.Word) -> @owned (Array<τ_0_0>, Builtin.RawPointer)
// <rdar://problem/20980377> HeapBuffer.swift test case spuriously reports a "unique" buffer
// CHECK-LABEL: sil @dead_array
// CHECK-NOT: release
// CHECK: retain_value %{{[0-9]+}} : $Optional<Builtin.NativeObject>
// CHECK: apply
// CHECK: strong_release %{{[0-9]+}} : $Builtin.BridgeObject
sil @dead_array : $@convention(thin) (@inout _HeapBuffer<C, Int>) -> () {
bb0(%0 : $*_HeapBuffer<C, Int>):
%1 = integer_literal $Builtin.Word, 1 // user: %3
%2 = function_ref @dead_array_alloc : $@convention(thin) <τ_0_0> (Builtin.Word) -> @owned (Array<τ_0_0>, Builtin.RawPointer)
%3 = apply %2<_HeapBuffer<C, Int>>(%1) : $@convention(thin) <τ_0_0> (Builtin.Word) -> @owned (Array<τ_0_0>, Builtin.RawPointer)
%4 = tuple_extract %3 : $(Array<_HeapBuffer<C, Int>>, Builtin.RawPointer), 0 // user: %15
%5 = tuple_extract %3 : $(Array<_HeapBuffer<C, Int>>, Builtin.RawPointer), 1 // user: %6
%6 = pointer_to_address %5 : $Builtin.RawPointer to [strict] $*_HeapBuffer<C, Int> // user: %9
%7 = load %0 : $*_HeapBuffer<C, Int> // users: %8, %9
%8 = struct_extract %7 : $_HeapBuffer<C, Int>, #_HeapBuffer._storage // user: %13
store %7 to %6 : $*_HeapBuffer<C, Int> // id: %9
%10 = function_ref @dead_array_run_closure : $@convention(thin) (@owned @callee_owned () -> Bool) -> () // user: %14
%11 = function_ref @dead_array_closure : $@convention(thin) (@inout _HeapBuffer<C, Int>) -> Bool // user: %12
%12 = partial_apply %11(%0) : $@convention(thin) (@inout _HeapBuffer<C, Int>) -> Bool // user: %14
retain_value %8 : $Optional<Builtin.NativeObject> // id: %13
%14 = apply %10(%12) : $@convention(thin) (@owned @callee_owned () -> Bool) -> ()
%15 = struct_extract %4 : $Array<_HeapBuffer<C, Int>>, #Array._buffer // user: %16
%16 = struct_extract %15 : $_ArrayBuffer<_HeapBuffer<C, Int>>, #_ArrayBuffer._storage // user: %17
%17 = struct_extract %16 : $_BridgeStorage<__ContiguousArrayStorageBase, _NSArrayCore>, #_BridgeStorage.rawValue // user: %18
strong_release %17 : $Builtin.BridgeObject // id: %18
%19 = tuple () // user: %20
return %19 : $() // id: %20
}
// Check that it does not crash the compiler.
// Int is ObjC-bridgeable in this case, but its conformance is not know,
// because Foundation is not imported yet.
// Therefore the cast may succeed from the compiler point of view.
// CHECK-LABEL: sil @cast_of_class_to_int
// CHECK: unconditional_checked_cast_addr
// CHECK: return
sil @cast_of_class_to_int : $@convention(thin) (C) -> Int {
bb0(%0 : $C):
%1 = alloc_stack $Int
%2 = alloc_stack $C
store %0 to %2 : $*C
unconditional_checked_cast_addr C in %2 : $*C to Int in %1 : $*Int
%4 = load %1 : $*Int
dealloc_stack %2 : $*C
dealloc_stack %1 : $*Int
return %4 : $Int
}
@objc(XX) protocol XX {
}
class XXImpl : XX {
@objc deinit
init()
}
// CHECK-LABEL: sil @remove_release_objc_metatype_to_object
// CHECK-NOT: strong_release {{%[0-9]+}} : $AnyObject
sil @remove_release_objc_metatype_to_object : $@convention(thin) () -> () {
bb0:
%0 = metatype $@thick XXImpl.Type // user: %1
%1 = thick_to_objc_metatype %0 : $@thick XXImpl.Type to $@objc_metatype XXImpl.Type // user: %2
%2 = objc_metatype_to_object %1 : $@objc_metatype XXImpl.Type to $AnyObject // users: %3, %4
debug_value %2 : $AnyObject // id: %3
strong_release %2 : $AnyObject // id: %4
%5 = tuple () // user: %6
return %5 : $() // id: %6
}
// CHECK-LABEL: sil @remove_release_objc_existential_metatype_to_object
// CHECK-NOT: strong_release {{%[0-9]+}} : $AnyObject
sil @remove_release_objc_existential_metatype_to_object: $@convention(thin) (@owned XX) -> () {
bb0(%0 : $XX):
debug_value %0 : $XX // id: %1
%2 = existential_metatype $@thick XX.Type, %0 : $XX // user: %3
%3 = thick_to_objc_metatype %2 : $@thick XX.Type to $@objc_metatype XX.Type // user: %4
%4 = objc_existential_metatype_to_object %3 : $@objc_metatype XX.Type to $AnyObject // users: %5, %6
debug_value %4 : $AnyObject, let, name "obj1" // id: %5
strong_release %4 : $AnyObject // id: %6
strong_release %0 : $XX // id: %7
%8 = tuple () // user: %9
return %8 : $() // id: %9
}