uasyncio.core: Fix scheduling in the presense of I/O completion callbacks.

wait() may finish prematurely due to I/O completion, and schedule new,
earlier than before tasks to run. So, after call to wait(), we need to
check current time and time of head task, and continue to wait if needed.
Recently introduced provisional utimeq.peektime() is used to optimize
querying time of a head task.
pull/170/head
Paul Sokolovsky 2017-04-08 01:34:57 +03:00
rodzic c440f8466e
commit bb3057ffed
1 zmienionych plików z 10 dodań i 4 usunięć

Wyświetl plik

@ -55,6 +55,16 @@ class EventLoop:
cur_task = [0, 0, 0]
while True:
if self.q:
# wait() may finish prematurely due to I/O completion,
# and schedule new, earlier than before tasks to run.
while 1:
t = self.q.peektime()
tnow = self.time()
delay = time.ticks_diff(t, tnow)
if delay <= 0:
break
self.wait(delay)
self.q.pop(cur_task)
t = cur_task[0]
cb = cur_task[1]
@ -62,10 +72,6 @@ class EventLoop:
if __debug__ and DEBUG:
log.debug("Next coroutine to run: %s", (t, cb, args))
# __main__.mem_info()
tnow = self.time()
delay = time.ticks_diff(t, tnow)
if delay > 0:
self.wait(delay)
else:
self.wait(-1)
# Assuming IO completion scheduled some tasks