14
14
struct Point {
15
15
var x : Int
16
16
var y : Int
17
+ var z : Int ? = nil
17
18
18
19
mutating func setComponents( x: inout Int , y: inout Int ) async {
19
20
defer { ( x, y) = ( self . x, self . y) }
@@ -22,10 +23,12 @@ struct Point {
22
23
}
23
24
24
25
actor class TestActor {
26
+ // expected-note@+1{{mutable state is only available within the actor instance}}
25
27
var position = Point ( x: 0 , y: 0 )
26
28
var nextPosition = Point ( x: 0 , y: 1 )
27
29
var value1 : Int = 0
28
30
var value2 : Int = 1
31
+ var points : [ Point ] = [ ]
29
32
}
30
33
31
34
func modifyAsynchronously( _ foo: inout Int ) async { foo += 1 }
@@ -56,6 +59,15 @@ extension TestActor {
56
59
// expected-error@+1{{actor-isolated property 'position' cannot be passed 'inout' to 'async' function call}}
57
60
await modifyAsynchronously ( & position. x)
58
61
}
62
+
63
+ func nestedExprs( ) async {
64
+ // expected-error@+1{{actor-isolated property 'position' cannot be passed 'inout' to 'async' function call}}
65
+ await modifyAsynchronously ( & position. z!)
66
+
67
+ // expected-error@+1{{actor-isolated property 'points' cannot be passed 'inout' to 'async' function call}}
68
+ await modifyAsynchronously ( & points[ 0 ] . z!)
69
+ }
70
+
59
71
}
60
72
61
73
// internal method call
@@ -98,8 +110,8 @@ extension TestActor {
98
110
99
111
func callMutatingFunctionOnStruct( ) async {
100
112
// expected-error@+3:20{{cannot call mutating async function 'setComponents(x:y:)' on actor-isolated property 'position'}}
101
- // expected-error@+2:51 {{actor-isolated property 'nextPosition' cannot be passed 'inout' to 'async' function call}}
102
- // expected-error@+1:71 {{actor-isolated property 'nextPosition' cannot be passed 'inout' to 'async' function call}}
113
+ // expected-error@+2:38 {{actor-isolated property 'nextPosition' cannot be passed 'inout' to 'async' function call}}
114
+ // expected-error@+1:58 {{actor-isolated property 'nextPosition' cannot be passed 'inout' to 'async' function call}}
103
115
await position. setComponents ( x: & nextPosition. x, y: & nextPosition. y)
104
116
105
117
// expected-error@+3:20{{cannot call mutating async function 'setComponents(x:y:)' on actor-isolated property 'position'}}
@@ -132,6 +144,40 @@ extension TestActor {
132
144
}
133
145
}
134
146
147
+ actor class MyActor {
148
+ var points : [ Point ] = [ ]
149
+ var int : Int = 0
150
+ var maybeInt : Int ?
151
+ var maybePoint : Point ?
152
+ var myActor : TestActor = TestActor ( )
153
+
154
+ // Checking that various ways of unwrapping emit the right error messages at
155
+ // the right times and that illegal operations are caught
156
+ func modifyStuff( ) async {
157
+ // expected-error@+1{{actor-isolated property 'points' cannot be passed 'inout' to 'async' function call}}
158
+ await modifyAsynchronously ( & points[ 0 ] . x)
159
+ // expected-error@+1{{actor-isolated property 'points' cannot be passed 'inout' to 'async' function call}}
160
+ await modifyAsynchronously ( & points[ 0 ] . z!)
161
+ // expected-error@+1{{actor-isolated property 'int' cannot be passed 'inout' to 'async' function call}}
162
+ await modifyAsynchronously ( & int)
163
+ // expected-error@+1{{actor-isolated property 'maybeInt' cannot be passed 'inout' to 'async' function call}}
164
+ await modifyAsynchronously ( & maybeInt!)
165
+ // expected-error@+1{{actor-isolated property 'maybePoint' cannot be passed 'inout' to 'async' function call}}
166
+ await modifyAsynchronously ( & maybePoint!. z!)
167
+ // expected-error@+1{{actor-isolated property 'int' cannot be passed 'inout' to 'async' function call}}
168
+ await modifyAsynchronously ( & ( int) )
169
+
170
+ // This warning is emitted because this fails to typecheck before the
171
+ // async-ness is attached.
172
+ // expected-warning@+2{{no calls to 'async' functions occur within 'await' expression}}
173
+ // expected-error@+1{{cannot pass immutable value of type 'Int' as inout argument}}
174
+ await modifyAsynchronously ( & ( maybePoint? . z) !)
175
+ // expected-error@+2{{actor-isolated property 'position' can only be referenced inside the actor}}
176
+ // expected-error@+1{{actor-isolated property 'myActor' cannot be passed 'inout' to 'async' function call}}
177
+ await modifyAsynchronously ( & myActor. position. x)
178
+ }
179
+ }
180
+
135
181
// Verify global actor protection
136
182
137
183
@globalActor
@@ -159,3 +205,17 @@ func globalSyncFunction(_ foo: inout Int) { }
159
205
@MyGlobalActor func globalActorAsyncOkay( ) async { globalActorSyncFunction ( & number) }
160
206
@MyGlobalActor func globalActorAsyncOkay2( ) async { globalSyncFunction ( & number) }
161
207
@MyGlobalActor func globalActorSyncOkay( ) { globalSyncFunction ( & number) }
208
+
209
+ // Gently unwrap things that are fine
210
+ struct Cat {
211
+ mutating func meow( ) async { }
212
+ }
213
+
214
+ struct Dog {
215
+ var cat : Cat ?
216
+
217
+ mutating func woof( ) async {
218
+ // This used to cause the compiler to crash, but should be fine
219
+ await cat? . meow ( )
220
+ }
221
+ }
0 commit comments