diff options
author | Zac Medico <zmedico@gentoo.org> | 2018-04-16 01:29:36 -0700 |
---|---|---|
committer | Zac Medico <zmedico@gentoo.org> | 2018-04-16 01:46:21 -0700 |
commit | 1ee8971ba1cb34e6b3cd3d5fda23066b24630e3a (patch) | |
tree | c8f509b8329e4fd1d0aee334e8d142c0223c071c | |
parent | EventLoop: fix add_reader/writer to call source_remove (diff) | |
download | portage-1ee8971b.tar.gz portage-1ee8971b.tar.bz2 portage-1ee8971b.zip |
EventLoop: eliminate thread safety from call_soon
The call_soon method is used heavily by asyncio.Task to execute
coroutine steps, so it's important to eliminate the overhead
associated with thread safety.
-rw-r--r-- | pym/portage/util/_eventloop/EventLoop.py | 20 |
1 files changed, 14 insertions, 6 deletions
diff --git a/pym/portage/util/_eventloop/EventLoop.py b/pym/portage/util/_eventloop/EventLoop.py index 38e735999..4ef600a5b 100644 --- a/pym/portage/util/_eventloop/EventLoop.py +++ b/pym/portage/util/_eventloop/EventLoop.py @@ -506,12 +506,17 @@ class EventLoop(object): @return: an integer ID """ with self._thread_condition: - source_id = self._call_soon_id = self._new_source_id() - self._idle_callbacks[source_id] = self._idle_callback_class( - args=args, callback=callback, source_id=source_id) + source_id = self._idle_add(callback, *args) self._thread_condition.notify() return source_id + def _idle_add(self, callback, *args): + """Like idle_add(), but without thread safety.""" + source_id = self._call_soon_id = self._new_source_id() + self._idle_callbacks[source_id] = self._idle_callback_class( + args=args, callback=callback, source_id=source_id) + return source_id + def _run_idle_callbacks(self): # assumes caller has acquired self._thread_rlock if not self._idle_callbacks: @@ -810,11 +815,14 @@ class EventLoop(object): @return: a handle which can be used to cancel the callback @rtype: asyncio.Handle (or compatible) """ - return self._handle(self.idle_add( + return self._handle(self._idle_add( self._call_soon_callback(callback, args)), self) - # The call_soon method inherits thread safety from the idle_add method. - call_soon_threadsafe = call_soon + def call_soon_threadsafe(self, callback, *args): + """Like call_soon(), but thread safe.""" + # idle_add provides thread safety + return self._handle(self.idle_add( + self._call_soon_callback(callback, args)), self) def time(self): """Return the time according to the event loop's clock. |