@@ -427,7 +427,7 @@ cdef class Loop:
427
427
if handle._cancelled:
428
428
self .remove_signal_handler(sig) # Remove it properly.
429
429
else :
430
- self ._call_soon_handle (handle)
430
+ self ._append_ready_handle (handle)
431
431
self .handler_async.send()
432
432
433
433
cdef _on_wake(self ):
@@ -667,10 +667,13 @@ cdef class Loop:
667
667
self ._call_soon_handle(handle)
668
668
return handle
669
669
670
- cdef inline _call_soon_handle (self , Handle handle):
670
+ cdef inline _append_ready_handle (self , Handle handle):
671
671
self ._check_closed()
672
672
self ._ready.append(handle)
673
673
self ._ready_len += 1
674
+
675
+ cdef inline _call_soon_handle(self , Handle handle):
676
+ self ._append_ready_handle(handle)
674
677
if not self .handler_idle.running:
675
678
self .handler_idle.start()
676
679
@@ -1281,7 +1284,11 @@ cdef class Loop:
1281
1284
""" Like call_soon(), but thread-safe."""
1282
1285
if not args:
1283
1286
args = None
1284
- handle = self ._call_soon(callback, args, context)
1287
+ cdef Handle handle = new_Handle(self , callback, args, context)
1288
+ self ._append_ready_handle(handle) # deque append is atomic
1289
+ # libuv async handler is thread-safe while the idle handler is not -
1290
+ # we only set the async handler here, which will start the idle handler
1291
+ # in _on_wake() from the loop and eventually call the callback.
1285
1292
self .handler_async.send()
1286
1293
return handle
1287
1294
0 commit comments