diff --git a/src/Cafe/HW/Latte/Core/LatteShaderCache.cpp b/src/Cafe/HW/Latte/Core/LatteShaderCache.cpp index 1ba50dec..4659ff10 100644 --- a/src/Cafe/HW/Latte/Core/LatteShaderCache.cpp +++ b/src/Cafe/HW/Latte/Core/LatteShaderCache.cpp @@ -11,6 +11,7 @@ #include "Cafe/HW/Latte/Renderer/Renderer.h" #include "Cafe/HW/Latte/Renderer/OpenGL/RendererShaderGL.h" #include "Cafe/HW/Latte/Renderer/Vulkan/RendererShaderVk.h" +#include "Cafe/HW/Latte/Renderer/Metal/RendererShaderMtl.h" #include "Cafe/HW/Latte/Renderer/Metal/MetalPipelineCache.h" #include "Cafe/HW/Latte/Renderer/Vulkan/VulkanPipelineStableCache.h" @@ -158,12 +159,19 @@ bool LoadTGAFile(const std::vector& buffer, TGAFILE *tgaFile) void LatteShaderCache_finish() { - if (g_renderer->GetType() == RendererAPI::Vulkan) + if (g_renderer->GetType() == RendererAPI::Vulkan) + { RendererShaderVk::ShaderCacheLoading_end(); + } else if (g_renderer->GetType() == RendererAPI::OpenGL) + { RendererShaderGL::ShaderCacheLoading_end(); + } else if (g_renderer->GetType() == RendererAPI::Metal) + { + RendererShaderMtl::ShaderCacheLoading_end(); MetalPipelineCache::ShaderCacheLoading_end(); + } } uint32 LatteShaderCache_getShaderCacheExtraVersion(uint64 titleId) @@ -243,11 +251,18 @@ void LatteShaderCache_Load() fs::create_directories(ActiveSettings::GetCachePath("shaderCache/precompiled"), ec); // initialize renderer specific caches if (g_renderer->GetType() == RendererAPI::Vulkan) + { RendererShaderVk::ShaderCacheLoading_begin(cacheTitleId); + } else if (g_renderer->GetType() == RendererAPI::OpenGL) + { RendererShaderGL::ShaderCacheLoading_begin(cacheTitleId); + } else if (g_renderer->GetType() == RendererAPI::Metal) + { + RendererShaderMtl::ShaderCacheLoading_begin(cacheTitleId); MetalPipelineCache::ShaderCacheLoading_begin(cacheTitleId); + } // get cache file name const auto pathGeneric = ActiveSettings::GetCachePath("shaderCache/transferable/{:016x}_shaders.bin", cacheTitleId); const auto pathGenericPre1_25_0 = ActiveSettings::GetCachePath("shaderCache/transferable/{:016x}.bin", cacheTitleId); // before 1.25.0 @@ -776,11 +791,18 @@ void LatteShaderCache_Close() s_shaderCacheGeneric = nullptr; } if (g_renderer->GetType() == RendererAPI::Vulkan) - RendererShaderVk::ShaderCacheLoading_Close(); - else if (g_renderer->GetType() == RendererAPI::OpenGL) - RendererShaderGL::ShaderCacheLoading_Close(); - else if (g_renderer->GetType() == RendererAPI::Metal) - MetalPipelineCache::ShaderCacheLoading_Close(); + { + RendererShaderVk::ShaderCacheLoading_Close(); + } + else if (g_renderer->GetType() == RendererAPI::OpenGL) + { + RendererShaderGL::ShaderCacheLoading_Close(); + } + else if (g_renderer->GetType() == RendererAPI::Metal) + { + RendererShaderMtl::ShaderCacheLoading_Close(); + MetalPipelineCache::ShaderCacheLoading_Close(); + } // if Vulkan then also close pipeline cache if (g_renderer->GetType() == RendererAPI::Vulkan) diff --git a/src/Cafe/HW/Latte/Renderer/Metal/RendererShaderMtl.cpp b/src/Cafe/HW/Latte/Renderer/Metal/RendererShaderMtl.cpp index 0f674080..c8babb14 100644 --- a/src/Cafe/HW/Latte/Renderer/Metal/RendererShaderMtl.cpp +++ b/src/Cafe/HW/Latte/Renderer/Metal/RendererShaderMtl.cpp @@ -9,6 +9,8 @@ #include "config/CemuConfig.h" #include "util/helpers/helpers.h" +static bool s_isLoadingShadersMtl{false}; + extern std::atomic_int g_compiled_shaders_total; extern std::atomic_int g_compiled_shaders_async; @@ -62,7 +64,8 @@ public: s_compilationQueueMutex.unlock(); // compile job->CompileInternal(); - ++g_compiled_shaders_async; + if (job->ShouldCountCompilation()) + ++g_compiled_shaders_async; // mark as compiled cemu_assert_debug(job->m_compilationState.getValue() == RendererShaderMtl::COMPILATION_STATE::COMPILING); job->m_compilationState.setValue(RendererShaderMtl::COMPILATION_STATE::DONE); @@ -82,6 +85,21 @@ private: std::atomic m_threadsActive; } shaderMtlThreadPool; +// TODO: find out if it would be possible to cache compiled Metal shaders +void RendererShaderMtl::ShaderCacheLoading_begin(uint64 cacheTitleId) +{ + s_isLoadingShadersMtl = true; +} + +void RendererShaderMtl::ShaderCacheLoading_end() +{ + s_isLoadingShadersMtl = false; +} + +void RendererShaderMtl::ShaderCacheLoading_Close() +{ +} + void RendererShaderMtl::Initialize() { shaderMtlThreadPool.StartThreads(); @@ -124,7 +142,8 @@ void RendererShaderMtl::PreponeCompilation(bool isRenderThread) if (!isStillQueued) { m_compilationState.waitUntilValue(COMPILATION_STATE::DONE); - --g_compiled_shaders_async; // compilation caused a stall so we don't consider this one async + if (ShouldCountCompilation()) + --g_compiled_shaders_async; // compilation caused a stall so we don't consider this one async return; } else @@ -146,6 +165,11 @@ bool RendererShaderMtl::WaitForCompiled() return true; } +bool RendererShaderMtl::ShouldCountCompilation() const +{ + return !s_isLoadingShadersMtl && m_isGameShader; +} + void RendererShaderMtl::CompileInternal() { MTL::CompileOptions* options = MTL::CompileOptions::alloc()->init(); @@ -169,7 +193,8 @@ void RendererShaderMtl::CompileInternal() FinishCompilation(); // Count shader compilation - g_compiled_shaders_total++; + if (ShouldCountCompilation()) + g_compiled_shaders_total++; } void RendererShaderMtl::FinishCompilation() diff --git a/src/Cafe/HW/Latte/Renderer/Metal/RendererShaderMtl.h b/src/Cafe/HW/Latte/Renderer/Metal/RendererShaderMtl.h index ddf72d81..40d04c87 100644 --- a/src/Cafe/HW/Latte/Renderer/Metal/RendererShaderMtl.h +++ b/src/Cafe/HW/Latte/Renderer/Metal/RendererShaderMtl.h @@ -21,6 +21,10 @@ class RendererShaderMtl : public RendererShader }; public: + static void ShaderCacheLoading_begin(uint64 cacheTitleId); + static void ShaderCacheLoading_end(); + static void ShaderCacheLoading_Close(); + static void Initialize(); static void Shutdown(); @@ -61,6 +65,9 @@ private: std::string m_mslCode; + bool ShouldCountCompilation() const; + void CompileInternal(); + void FinishCompilation(); };