Skip to content

Commit 9f0197d

Browse files
Concurrency: Isolate global executor installation by MainActor
1 parent daa8209 commit 9f0197d

File tree

4 files changed

+18
-13
lines changed

4 files changed

+18
-13
lines changed

Sources/JavaScriptEventLoop/JavaScriptEventLoop.swift

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -102,14 +102,14 @@ public final class JavaScriptEventLoop: SerialExecutor, @unchecked Sendable {
102102
return eventLoop
103103
}
104104

105-
private static var didInstallGlobalExecutor = false
105+
@MainActor private static var didInstallGlobalExecutor = false
106106

107107
/// Set JavaScript event loop based executor to be the global executor
108108
/// Note that this should be called before any of the jobs are created.
109109
/// This installation step will be unnecessary after custom executor are
110110
/// introduced officially. See also [a draft proposal for custom
111111
/// executors](https://github.com/rjmccall/swift-evolution/blob/custom-executors/proposals/0000-custom-executors.md#the-default-global-concurrent-executor)
112-
public static func installGlobalExecutor() {
112+
@MainActor public static func installGlobalExecutor() {
113113
guard !didInstallGlobalExecutor else { return }
114114

115115
#if compiler(>=5.9)

Sources/JavaScriptEventLoop/WebWorkerTaskExecutor.swift

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -426,14 +426,15 @@ public final class WebWorkerTaskExecutor: TaskExecutor {
426426

427427
// MARK: Global Executor hack
428428

429-
private static var _mainThread: pthread_t?
430-
private static var _swift_task_enqueueGlobal_hook_original: UnsafeMutableRawPointer?
431-
private static var _swift_task_enqueueGlobalWithDelay_hook_original: UnsafeMutableRawPointer?
432-
private static var _swift_task_enqueueGlobalWithDeadline_hook_original: UnsafeMutableRawPointer?
429+
@MainActor private static var _mainThread: pthread_t?
430+
@MainActor private static var _swift_task_enqueueGlobal_hook_original: UnsafeMutableRawPointer?
431+
@MainActor private static var _swift_task_enqueueGlobalWithDelay_hook_original: UnsafeMutableRawPointer?
432+
@MainActor private static var _swift_task_enqueueGlobalWithDeadline_hook_original: UnsafeMutableRawPointer?
433433

434434
/// Install a global executor that forwards jobs from Web Worker threads to the main thread.
435435
///
436436
/// This function must be called once before using the Web Worker task executor.
437+
@MainActor
437438
public static func installGlobalExecutor() {
438439
#if canImport(wasi_pthread) && compiler(>=6.1) && _runtime(_multithreaded)
439440
// Ensure this function is called only once.

Sources/JavaScriptEventLoopTestSupport/JavaScriptEventLoopTestSupport.swift

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,9 @@ import JavaScriptEventLoop
2525
@available(macOS 14.0, iOS 17.0, watchOS 10.0, tvOS 17.0, *)
2626
@_cdecl("swift_javascriptkit_activate_js_executor_impl")
2727
func swift_javascriptkit_activate_js_executor_impl() {
28-
JavaScriptEventLoop.installGlobalExecutor()
28+
MainActor.assumeIsolated {
29+
JavaScriptEventLoop.installGlobalExecutor()
30+
}
2931
}
3032

3133
#endif

Sources/_CJavaScriptEventLoop/include/_CJavaScriptEventLoop.h

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@
99

1010
#define SWIFT_EXPORT_FROM(LIBRARY) __attribute__((__visibility__("default")))
1111

12+
#define SWIFT_NONISOLATED_UNSAFE __attribute__((swift_attr("nonisolated(unsafe)")))
13+
1214
/// A schedulable unit
1315
/// Note that this type layout is a part of public ABI, so we expect this field layout won't break in the future versions.
1416
/// Current implementation refers the `swift-5.5-RELEASE` implementation.
@@ -27,13 +29,13 @@ typedef SWIFT_CC(swift) void (*swift_task_enqueueGlobal_original)(
2729
Job *_Nonnull job);
2830

2931
SWIFT_EXPORT_FROM(swift_Concurrency)
30-
extern void *_Nullable swift_task_enqueueGlobal_hook;
32+
extern void *_Nullable swift_task_enqueueGlobal_hook SWIFT_NONISOLATED_UNSAFE;
3133

3234
/// A hook to take over global enqueuing with delay.
3335
typedef SWIFT_CC(swift) void (*swift_task_enqueueGlobalWithDelay_original)(
3436
unsigned long long delay, Job *_Nonnull job);
3537
SWIFT_EXPORT_FROM(swift_Concurrency)
36-
extern void *_Nullable swift_task_enqueueGlobalWithDelay_hook;
38+
extern void *_Nullable swift_task_enqueueGlobalWithDelay_hook SWIFT_NONISOLATED_UNSAFE;
3739

3840
typedef SWIFT_CC(swift) void (*swift_task_enqueueGlobalWithDeadline_original)(
3941
long long sec,
@@ -42,13 +44,13 @@ typedef SWIFT_CC(swift) void (*swift_task_enqueueGlobalWithDeadline_original)(
4244
long long tnsec,
4345
int clock, Job *_Nonnull job);
4446
SWIFT_EXPORT_FROM(swift_Concurrency)
45-
extern void *_Nullable swift_task_enqueueGlobalWithDeadline_hook;
47+
extern void *_Nullable swift_task_enqueueGlobalWithDeadline_hook SWIFT_NONISOLATED_UNSAFE;
4648

4749
/// A hook to take over main executor enqueueing.
4850
typedef SWIFT_CC(swift) void (*swift_task_enqueueMainExecutor_original)(
4951
Job *_Nonnull job);
5052
SWIFT_EXPORT_FROM(swift_Concurrency)
51-
extern void *_Nullable swift_task_enqueueMainExecutor_hook;
53+
extern void *_Nullable swift_task_enqueueMainExecutor_hook SWIFT_NONISOLATED_UNSAFE;
5254

5355
/// A hook to override the entrypoint to the main runloop used to drive the
5456
/// concurrency runtime and drain the main queue. This function must not return.
@@ -59,13 +61,13 @@ typedef SWIFT_CC(swift) void (*swift_task_asyncMainDrainQueue_original)();
5961
typedef SWIFT_CC(swift) void (*swift_task_asyncMainDrainQueue_override)(
6062
swift_task_asyncMainDrainQueue_original _Nullable original);
6163
SWIFT_EXPORT_FROM(swift_Concurrency)
62-
extern void *_Nullable swift_task_asyncMainDrainQueue_hook;
64+
extern void *_Nullable swift_task_asyncMainDrainQueue_hook SWIFT_NONISOLATED_UNSAFE;
6365

6466

6567
/// MARK: - thread local storage
6668

6769
extern _Thread_local void * _Nullable swjs_thread_local_event_loop;
6870

69-
extern _Thread_local void * _Nullable swjs_thread_local_task_executor_worker;
71+
extern _Thread_local void * _Nullable swjs_thread_local_task_executor_worker SWIFT_NONISOLATED_UNSAFE;
7072

7173
#endif

0 commit comments

Comments
 (0)