This commit is contained in:
iwubcode 2025-12-15 17:14:35 -06:00 committed by GitHub
commit d4aefa0e4f
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 35 additions and 10 deletions

View File

@ -35,7 +35,7 @@ void AsyncShaderCompiler::QueueWorkItem(WorkItemPtr item, u32 priority)
} }
else else
{ {
std::lock_guard<std::mutex> guard(m_pending_work_lock); std::lock_guard guard(m_pending_work_lock);
m_pending_work.emplace(priority, std::move(item)); m_pending_work.emplace(priority, std::move(item));
m_worker_thread_wake.notify_one(); m_worker_thread_wake.notify_one();
} }
@ -45,7 +45,7 @@ void AsyncShaderCompiler::RetrieveWorkItems()
{ {
std::deque<WorkItemPtr> completed_work; std::deque<WorkItemPtr> completed_work;
{ {
std::lock_guard<std::mutex> guard(m_completed_work_lock); std::lock_guard guard(m_completed_work_lock);
m_completed_work.swap(completed_work); m_completed_work.swap(completed_work);
} }
@ -58,16 +58,29 @@ void AsyncShaderCompiler::RetrieveWorkItems()
bool AsyncShaderCompiler::HasPendingWork() bool AsyncShaderCompiler::HasPendingWork()
{ {
std::lock_guard<std::mutex> guard(m_pending_work_lock); std::lock_guard guard(m_pending_work_lock);
return !m_pending_work.empty() || m_busy_workers.load() != 0; return !m_pending_work.empty() || m_busy_workers.load() != 0;
} }
bool AsyncShaderCompiler::HasCompletedWork() bool AsyncShaderCompiler::HasCompletedWork()
{ {
std::lock_guard<std::mutex> guard(m_completed_work_lock); std::lock_guard guard(m_completed_work_lock);
return !m_completed_work.empty(); return !m_completed_work.empty();
} }
void AsyncShaderCompiler::ClearAllWork()
{
{
std::lock_guard guard(m_pending_work_lock);
m_pending_work.clear();
}
{
std::lock_guard guard(m_completed_work_lock);
m_completed_work.clear();
}
}
bool AsyncShaderCompiler::WaitUntilCompletion( bool AsyncShaderCompiler::WaitUntilCompletion(
const std::function<void(size_t, size_t)>& progress_callback) const std::function<void(size_t, size_t)>& progress_callback)
{ {
@ -89,8 +102,8 @@ bool AsyncShaderCompiler::WaitUntilCompletion(
size_t total_items; size_t total_items;
{ {
// Safe to hold both locks here, since nowhere else does. // Safe to hold both locks here, since nowhere else does.
std::lock_guard<std::mutex> pending_guard(m_pending_work_lock); std::lock_guard pending_guard(m_pending_work_lock);
std::lock_guard<std::mutex> completed_guard(m_completed_work_lock); std::lock_guard completed_guard(m_completed_work_lock);
total_items = m_completed_work.size() + m_pending_work.size() + m_busy_workers.load() + 1; total_items = m_completed_work.size() + m_pending_work.size() + m_busy_workers.load() + 1;
} }
@ -99,7 +112,7 @@ bool AsyncShaderCompiler::WaitUntilCompletion(
{ {
size_t remaining_items; size_t remaining_items;
{ {
std::lock_guard<std::mutex> pending_guard(m_pending_work_lock); std::lock_guard pending_guard(m_pending_work_lock);
if (m_pending_work.empty() && !m_busy_workers.load()) if (m_pending_work.empty() && !m_busy_workers.load())
return true; return true;
remaining_items = m_pending_work.size(); remaining_items = m_pending_work.size();
@ -164,7 +177,7 @@ void AsyncShaderCompiler::StopWorkerThreads()
// Signal worker threads to stop, and wake all of them. // Signal worker threads to stop, and wake all of them.
{ {
std::lock_guard<std::mutex> guard(m_pending_work_lock); std::lock_guard guard(m_pending_work_lock);
m_exit_flag.Set(); m_exit_flag.Set();
m_worker_thread_wake.notify_all(); m_worker_thread_wake.notify_all();
} }
@ -213,7 +226,7 @@ void AsyncShaderCompiler::WorkerThreadEntryPoint(void* param)
void AsyncShaderCompiler::WorkerThreadRun() void AsyncShaderCompiler::WorkerThreadRun()
{ {
std::unique_lock<std::mutex> pending_lock(m_pending_work_lock); std::unique_lock pending_lock(m_pending_work_lock);
while (!m_exit_flag.IsSet()) while (!m_exit_flag.IsSet())
{ {
m_worker_thread_wake.wait(pending_lock); m_worker_thread_wake.wait(pending_lock);
@ -228,7 +241,7 @@ void AsyncShaderCompiler::WorkerThreadRun()
if (item->Compile()) if (item->Compile())
{ {
std::lock_guard<std::mutex> completed_guard(m_completed_work_lock); std::lock_guard completed_guard(m_completed_work_lock);
m_completed_work.push_back(std::move(item)); m_completed_work.push_back(std::move(item));
} }

View File

@ -49,6 +49,9 @@ public:
bool HasPendingWork(); bool HasPendingWork();
bool HasCompletedWork(); bool HasCompletedWork();
// Clears both pending and completed work
void ClearAllWork();
// Calls progress_callback periodically, with completed_items, and total_items. // Calls progress_callback periodically, with completed_items, and total_items.
// Returns false if interrupted. // Returns false if interrupted.
bool WaitUntilCompletion(const std::function<void(size_t, size_t)>& progress_callback); bool WaitUntilCompletion(const std::function<void(size_t, size_t)>& progress_callback);

View File

@ -24,10 +24,16 @@ CustomShaderCache::CustomShaderCache()
CustomShaderCache::~CustomShaderCache() CustomShaderCache::~CustomShaderCache()
{ {
if (m_async_shader_compiler) if (m_async_shader_compiler)
{
m_async_shader_compiler->StopWorkerThreads(); m_async_shader_compiler->StopWorkerThreads();
m_async_shader_compiler->ClearAllWork();
}
if (m_async_uber_shader_compiler) if (m_async_uber_shader_compiler)
{
m_async_uber_shader_compiler->StopWorkerThreads(); m_async_uber_shader_compiler->StopWorkerThreads();
m_async_uber_shader_compiler->ClearAllWork();
}
} }
void CustomShaderCache::RetrieveAsyncShaders() void CustomShaderCache::RetrieveAsyncShaders()

View File

@ -109,7 +109,10 @@ void ShaderCache::Shutdown()
// This may leave shaders uncommitted to the cache, but it's better than blocking shutdown // This may leave shaders uncommitted to the cache, but it's better than blocking shutdown
// until everything has finished compiling. // until everything has finished compiling.
if (m_async_shader_compiler) if (m_async_shader_compiler)
{
m_async_shader_compiler->StopWorkerThreads(); m_async_shader_compiler->StopWorkerThreads();
m_async_shader_compiler->ClearAllWork();
}
ClosePipelineUIDCache(); ClosePipelineUIDCache();
} }