Merge pull request #240 from vibe-d/fix_worker_task_scheduling

Fix a worker task scheduling issue for busy worker tasks.
This commit is contained in:
Leonid Kramer 2020-12-18 15:31:05 +01:00 committed by GitHub
commit 0c1ea531b8
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 13 additions and 4 deletions

View file

@ -132,7 +132,7 @@ struct ScopedMutexLock(M)
@property bool locked() const { return m_locked; } @property bool locked() const { return m_locked; }
void unlock() void unlock()
in (this.locked) in { assert(this.locked); }
do { do {
enforce(m_locked); enforce(m_locked);
m_mutex.unlock(); m_mutex.unlock();
@ -140,13 +140,13 @@ struct ScopedMutexLock(M)
} }
bool tryLock() bool tryLock()
in (!this.locked) in { assert(!this.locked); }
do { do {
return m_locked = m_mutex.tryLock(); return m_locked = m_mutex.tryLock();
} }
void lock() void lock()
in (!this.locked) in { assert(!this.locked); }
do { do {
m_locked = true; m_locked = true;
m_mutex.lock(); m_mutex.lock();

View file

@ -346,7 +346,16 @@ private final class WorkerThread : Thread {
try { try {
if (m_pool.m_state.lock.term) return; if (m_pool.m_state.lock.term) return;
logDebug("entering worker thread"); logDebug("entering worker thread");
handleWorkerTasks();
// There is an issue where a task that periodically calls yield()
// but otherwise only performs a CPU computation will cause a
// call to runEventLoopOnce() or yield() called from the global
// thread context to not return before the task is finished. For
// this reason we start a task here, which in turn is scheduled
// properly together with such a task, and also is schduled
// according to the task priorities.
runTask(&handleWorkerTasks).joinUninterruptible();
logDebug("Worker thread exit."); logDebug("Worker thread exit.");
} catch (Throwable th) { } catch (Throwable th) {
th.logException!(LogLevel.fatal)("Worker thread terminated due to uncaught error"); th.logException!(LogLevel.fatal)("Worker thread terminated due to uncaught error");