File: writeback_conflict_diagnostics.swift

package info (click to toggle)
swiftlang 6.0.3-2
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 2,519,992 kB
  • sloc: cpp: 9,107,863; ansic: 2,040,022; asm: 1,135,751; python: 296,500; objc: 82,456; f90: 60,502; lisp: 34,951; pascal: 19,946; sh: 18,133; perl: 7,482; ml: 4,937; javascript: 4,117; makefile: 3,840; awk: 3,535; xml: 914; fortran: 619; cs: 573; ruby: 573
file content (137 lines) | stat: -rw-r--r-- 6,267 bytes parent folder | download
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
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
// 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(&copy[0], &copy[1])
  swap(&copy[0], // expected-note {{concurrent writeback occurred here}}
       &copy[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(&copy[0][0])
}