mirror of
https://github.com/apple/swift.git
synced 2025-12-14 20:36:38 +01:00
I did this using a sed pattern and verified by hand that I was only touching target-swift-emit-silgen lines.
138 lines
6.1 KiB
Swift
138 lines
6.1 KiB
Swift
// RUN: %target-swift-emit-silgen %s -o /dev/null -verify
|
|
// RUN: %target-swift-emit-silgen -enforce-exclusivity=checked %s -o /dev/null -verify
|
|
|
|
func takeInOut<T>(_: inout T) {}
|
|
|
|
struct MutatorStruct {
|
|
mutating func f(_ x : inout MutatorStruct) {}
|
|
}
|
|
|
|
var global_property : MutatorStruct { get {} set {} }
|
|
|
|
var global_int_property : Int {
|
|
get { return 42 }
|
|
set {}
|
|
}
|
|
|
|
|
|
struct StructWithProperty {
|
|
var computed_int : Int {
|
|
get { return 42 }
|
|
set {}
|
|
}
|
|
|
|
var stored_int = 0
|
|
|
|
var computed_struct : MutatorStruct { get {} set {} }
|
|
}
|
|
|
|
var global_struct_property : StructWithProperty
|
|
var c_global_struct_property : StructWithProperty { get {} set {} }
|
|
|
|
func testInOutAlias() {
|
|
var x = 42
|
|
swap(&x, // expected-note {{previous aliasing argument}}
|
|
&x) // expected-error {{inout arguments are not allowed to alias each other}}
|
|
swap(&global_struct_property, // expected-note {{previous aliasing argument}}
|
|
&global_struct_property) // expected-error {{inout arguments are not allowed to alias each other}}
|
|
}
|
|
|
|
func testWriteback() {
|
|
var a = StructWithProperty()
|
|
a.computed_struct . // expected-note {{concurrent writeback occurred here}}
|
|
f(&a.computed_struct) // expected-error {{inout writeback to computed property 'computed_struct' occurs in multiple arguments to call, introducing invalid aliasing}}
|
|
|
|
swap(&global_struct_property.stored_int,
|
|
&global_struct_property.stored_int) // ok
|
|
swap(&global_struct_property.computed_int, // expected-note {{concurrent writeback occurred here}}
|
|
&global_struct_property.computed_int) // expected-error {{inout writeback to computed property 'computed_int' occurs in multiple arguments to call, introducing invalid aliasing}}
|
|
|
|
|
|
|
|
swap(&a.computed_int, // expected-note {{concurrent writeback occurred here}}
|
|
&a.computed_int) // expected-error {{inout writeback to computed property 'computed_int' occurs in multiple arguments to call, introducing invalid aliasing}}
|
|
|
|
|
|
global_property.f(&global_property) // expected-error {{inout writeback to computed property 'global_property' occurs in multiple arguments to call, introducing invalid aliasing}} expected-note {{concurrent writeback occurred here}}
|
|
|
|
a.computed_struct.f(&a.computed_struct) // expected-error {{inout writeback to computed property 'computed_struct' occurs in multiple arguments to call, introducing invalid aliasing}} expected-note {{concurrent writeback occurred here}}
|
|
}
|
|
|
|
func testComputedStructWithProperty() {
|
|
swap(&c_global_struct_property.stored_int, &c_global_struct_property.stored_int) // expected-error {{inout writeback to computed property 'c_global_struct_property' occurs in multiple arguments to call, introducing invalid aliasing}} expected-note {{concurrent writeback occurred here}}
|
|
|
|
var c_local_struct_property : StructWithProperty { get {} set {} }
|
|
swap(&c_local_struct_property.stored_int, &c_local_struct_property.stored_int) // expected-error {{inout writeback to computed property 'c_local_struct_property' occurs in multiple arguments to call, introducing invalid aliasing}} expected-note {{concurrent writeback occurred here}}
|
|
swap(&c_local_struct_property.stored_int, &c_global_struct_property.stored_int) // ok
|
|
}
|
|
|
|
|
|
var global_array : [[Int]]
|
|
|
|
func testMultiArray(_ i : Int, j : Int, array : [[Int]]) {
|
|
var array = array
|
|
swap(&array[i][j], // expected-note {{concurrent writeback occurred here}}
|
|
&array[i][i]) // expected-error {{inout writeback through subscript occurs in multiple arguments to call, introducing invalid aliasing}}
|
|
swap(&array[0][j], // expected-note {{concurrent writeback occurred here}}
|
|
&array[0][i]) // expected-error {{inout writeback through subscript occurs in multiple arguments to call, introducing invalid aliasing}}
|
|
swap(&global_array[0][j], // expected-note {{concurrent writeback occurred here}}
|
|
&global_array[0][i]) // expected-error {{inout writeback through subscript occurs in multiple arguments to call, introducing invalid aliasing}}
|
|
|
|
// TODO: This is obviously the same writeback problem, but isn't detectable
|
|
// with the current level of sophistication in SILGen.
|
|
swap(&array[1+0][j], &array[1+0][i])
|
|
|
|
swap(&global_array[0][j], &array[j][i]) // ok
|
|
}
|
|
|
|
struct ArrayWithoutAddressors<T> {
|
|
subscript(i: Int) -> T {
|
|
get { return value }
|
|
set {}
|
|
}
|
|
var value: T
|
|
}
|
|
|
|
var global_array_without_addressors: ArrayWithoutAddressors<ArrayWithoutAddressors<Int>>
|
|
|
|
func testMultiArrayWithoutAddressors(
|
|
_ i: Int, j: Int, array: ArrayWithoutAddressors<ArrayWithoutAddressors<Int>>
|
|
) {
|
|
var array = array
|
|
swap(&array[i][j], // expected-note {{concurrent writeback occurred here}}
|
|
&array[i][i]) // expected-error {{inout writeback through subscript occurs in multiple arguments to call, introducing invalid aliasing}}
|
|
swap(&array[0][j], // expected-note {{concurrent writeback occurred here}}
|
|
&array[0][i]) // expected-error {{inout writeback through subscript occurs in multiple arguments to call, introducing invalid aliasing}}
|
|
swap(&global_array_without_addressors[0][j], // expected-note {{concurrent writeback occurred here}}
|
|
&global_array_without_addressors[0][i]) // expected-error {{inout writeback through subscript occurs in multiple arguments to call, introducing invalid aliasing}}
|
|
|
|
// TODO: This is obviously the same writeback problem, but isn't detectable
|
|
// with the current level of sophistication in SILGen.
|
|
swap(&array[1+0][j], &array[1+0][i])
|
|
|
|
swap(&global_array_without_addressors[0][j], &array[j][i]) // ok
|
|
}
|
|
|
|
// rdar://43802132
|
|
struct ArrayWithReadModify<T> {
|
|
init(value: T) { self.property = value }
|
|
var property: T
|
|
subscript(i: Int) -> T {
|
|
_read { yield property }
|
|
_modify { yield &property }
|
|
}
|
|
}
|
|
|
|
func testArrayWithReadModify<T>(array: ArrayWithReadModify<T>) {
|
|
var copy = array
|
|
swap(©[0], ©[1])
|
|
swap(©[0], // expected-note {{concurrent writeback occurred here}}
|
|
©[0]) // expected-error {{inout writeback through subscript occurs in multiple arguments to call}}
|
|
}
|
|
|
|
// rdar://44147745
|
|
func testNestedArrayWithReadModify<T>(array: ArrayWithReadModify<ArrayWithReadModify<T>>) {
|
|
var copy = array
|
|
takeInOut(©[0][0])
|
|
}
|