diff --git a/Source/Async/ThreadPool.cpp b/Source/Async/ThreadPool.cpp index f9c5d8c9..26fea5cb 100644 --- a/Source/Async/ThreadPool.cpp +++ b/Source/Async/ThreadPool.cpp @@ -227,7 +227,7 @@ namespace Aurora::Async while ((!auThread->Exiting()) && - (!this->shutdown) && + ((this->shuttingdown_ & 2) != 2) && (!pJobRunner->bBreakEarly)) { AuUInt32 uCount {}; @@ -235,7 +235,7 @@ namespace Aurora::Async // Do work (blocking) if (!InternalRunOne(pJobRunner, true, uCount)) { - if (this->shutdown) + if ((this->shuttingdown_ & 2) == 2) { return ranOnce; } @@ -267,60 +267,24 @@ namespace Aurora::Async if (asyncLoop->GetSourceCount() > 1) { - bool bShouldTrySleepForKernel {}; - - if (runMode == ERunMode::eLowLatencyFreqKernel) + bool bShouldTrySleepForKernel = block; + if (!block) { - if (state->rateLimiter.CheckExchangePass()) - { - #if defined(AURORA_PLATFORM_WIN32) - bShouldTrySleepForKernel = asyncLoop->PumpNonblocking(); - #else - bShouldTrySleepForKernel = asyncLoop->IsSignaledPeek(); - #endif - } - else - { - if (!PollInternal(state, false, uCount)) - { - AuThreading::ContextYield(); - } - else - { - success = true; - } - } - } - else if (runMode == ERunMode::eLowLatencyYield) - { - AuThreading::ContextYield(); - block = false; - #if defined(AURORA_PLATFORM_WIN32) - bShouldTrySleepForKernel = asyncLoop->PumpNonblocking(); - #else - bShouldTrySleepForKernel = asyncLoop->IsSignaledPeek(); - #endif - } - else if (runMode == ERunMode::eEfficient) - { - bShouldTrySleepForKernel = block; - if (!block) - { - bShouldTrySleepForKernel = asyncLoop->IsSignaledPeek(); - } + bShouldTrySleepForKernel = asyncLoop->IsSignaledPeek(); } if (bShouldTrySleepForKernel) { - // epoll and such like can be checked without read success. kevent works on availablity, not scheduling read like iosubmit - // allow windows to atomically pump instead of wasting time buffering the primitives state - if ((AuBuild::kIsNtDerived && runMode == ERunMode::eEfficient) || - (!AuBuild::kIsNtDerived)) + AuAtomicAdd(&state->cvSleepCount, 1u); + if (block) { - AuAtomicAdd(&state->cvSleepCount, 1u); asyncLoop->WaitAny(0); - AuAtomicSub(&state->cvSleepCount, 1u); } + else + { + asyncLoop->PumpNonblocking(); + } + AuAtomicSub(&state->cvSleepCount, 1u); } success = PollInternal(state, false, uCount); @@ -333,7 +297,6 @@ namespace Aurora::Async EarlyExitTick(); - return success; } @@ -578,7 +541,7 @@ namespace Aurora::Async for (auto itr = state->pendingWorkItems.begin(); itr != state->pendingWorkItems.end(); ) { - if (state->threadObject->Exiting() || this->shutdown) + if (state->threadObject->Exiting()) { break; } @@ -666,6 +629,7 @@ namespace Aurora::Async AuList toBarrier; + // wait for regular prio work to complete { { AU_LOCK_GUARD(this->rwlock_->AsReadable()); @@ -701,6 +665,7 @@ namespace Aurora::Async } } + // increment abort cookies { for (const auto &id : toBarrier) { @@ -713,9 +678,7 @@ namespace Aurora::Async } } - // Time for fuckiness - - // Specify the root-level shutdown flag for 'ok, u can work, but you're shutting down after sync barrier' + // set shutdown flags { AuAtomicTestAndSet(&this->shuttingdown_, 1); } @@ -749,7 +712,7 @@ namespace Aurora::Async } // thread object: - if (!pGroup->IsSysThread()) // bug? + if (pState->bCreate) { pState->threadObject->SendExitSignal(); threads.push_back(pState->threadObject); @@ -773,8 +736,8 @@ namespace Aurora::Async pState->eventLs->Set(); } } - // Final sync to exit + // Final sync to exit { for (const auto &id : toBarrier) { @@ -799,7 +762,6 @@ namespace Aurora::Async } // Is dead flag - this->shutdown = true; this->shutdownEvent_->Set(); if (pLocalRunner) @@ -1156,8 +1118,7 @@ namespace Aurora::Async auto pA = this->GetThreadStateNoWarn(); - if (this->shutdown || - this->shuttingdown_ & 2) // fast + if (this->shuttingdown_ & 2) // fast { if (pA->rejecting) { @@ -1316,6 +1277,8 @@ namespace Aurora::Async threadState->asyncLoop->SourceAdd(threadState->eventLs); + threadState->bCreate = create; + if (!create) { threadState->threadObject = AuThreads::ThreadShared(AuThreads::ThreadInfo( diff --git a/Source/Async/ThreadState.hpp b/Source/Async/ThreadState.hpp index ffd298f5..1cfe776d 100644 --- a/Source/Async/ThreadState.hpp +++ b/Source/Async/ThreadState.hpp @@ -60,6 +60,7 @@ namespace Aurora::Async bool bAlreadyDoingExitTick {}; bool bBreakEarly {}; bool bIsKiller {}; + bool bCreate {}; // AuThreadPrimitives::SpinLock externalFencesLock;