@@ -11,16 +11,28 @@ import Dispatch
11
11
import StdlibUnittest
12
12
import _Concurrency
13
13
14
+ // For sleep
15
+ #if canImport(Darwin)
16
+ import Darwin
17
+ #elseif canImport(Glibc)
18
+ import Glibc
19
+ #elseif canImport(Android)
20
+ import Android
21
+ #endif
22
+
14
23
final class NaiveQueueExecutor : TaskExecutor {
15
24
let queue : DispatchQueue
25
+ let sem : DispatchSemaphore
16
26
17
- init ( _ queue: DispatchQueue ) {
27
+ init ( _ sem : DispatchSemaphore , _ queue: DispatchQueue ) {
18
28
print ( " init \( Self . self) " )
29
+ self . sem = sem
19
30
self . queue = queue
20
31
}
21
32
22
33
deinit {
23
34
print ( " deinit \( Self . self) " )
35
+ sem. signal ( )
24
36
}
25
37
26
38
public func enqueue( _ _job: consuming ExecutorJob ) {
@@ -39,15 +51,16 @@ final class NaiveQueueExecutor: TaskExecutor {
39
51
}
40
52
41
53
nonisolated func nonisolatedFunc( expectedQueue queue: DispatchQueue ) async {
42
- // dispatchPrecondition(condition: .onQueue(queue))
54
+ dispatchPrecondition ( condition: . onQueue( queue) )
43
55
print ( " Invoked: \( #function) " )
44
56
}
45
57
46
58
@main struct Main {
47
59
48
60
static func main( ) async {
49
61
let queue = DispatchQueue ( label: " example-queue " )
50
- var executor : NaiveQueueExecutor ? = NaiveQueueExecutor ( queue)
62
+ let deinitSem = DispatchSemaphore ( value: 0 )
63
+ var executor : NaiveQueueExecutor ? = NaiveQueueExecutor ( deinitSem, queue)
51
64
52
65
// Task retains the executor, so it should never deinit before the task completes
53
66
// CHECK: init NaiveQueueExecutor
@@ -75,6 +88,8 @@ nonisolated func nonisolatedFunc(expectedQueue queue: DispatchQueue) async {
75
88
// CHECK: Task done
76
89
// CHECK-NEXT: deinit NaiveQueueExecutor
77
90
91
+ deinitSem. wait ( )
92
+
78
93
print ( " Done " )
79
94
// CHECK: Done
80
95
}
0 commit comments