From d200ef40deb092934026649919fad276981d997d Mon Sep 17 00:00:00 2001 From: "Unknown W. Brackets" Date: Sat, 29 Jan 2022 20:28:20 -0800 Subject: [PATCH] samplerjit: Compile sampler funcs together. We can't have the cache clear between nearest/linear, because then we'll call a bunch of int3's. --- GPU/Software/Sampler.cpp | 79 ++++++++++++++++++++++------------------ GPU/Software/Sampler.h | 1 + 2 files changed, 44 insertions(+), 36 deletions(-) diff --git a/GPU/Software/Sampler.cpp b/GPU/Software/Sampler.cpp index f2dbddeaa2..88b77e642e 100644 --- a/GPU/Software/Sampler.cpp +++ b/GPU/Software/Sampler.cpp @@ -141,23 +141,15 @@ NearestFunc SamplerJitCache::GetNearest(const SamplerID &id) { std::lock_guard guard(jitCacheLock); auto it = cache_.find(id); - if (it != cache_.end()) { + if (it != cache_.end()) return (NearestFunc)it->second; - } - // TODO: What should be the min size? Can we even hit this? - if (GetSpaceLeft() < 16384) { - Clear(); - } + Compile(id); -#if PPSSPP_ARCH(AMD64) && !PPSSPP_PLATFORM(UWP) - if (g_Config.bSoftwareRenderingJit) { - addresses_[id] = GetCodePointer(); - NearestFunc func = CompileNearest(id); - cache_[id] = (NearestFunc)func; - return func; - } -#endif + // Okay, should be there now. + it = cache_.find(id); + if (it != cache_.end()) + return (NearestFunc)it->second; return nullptr; } @@ -165,23 +157,15 @@ LinearFunc SamplerJitCache::GetLinear(const SamplerID &id) { std::lock_guard guard(jitCacheLock); auto it = cache_.find(id); - if (it != cache_.end()) { + if (it != cache_.end()) return (LinearFunc)it->second; - } - // TODO: What should be the min size? Can we even hit this? - if (GetSpaceLeft() < 16384) { - Clear(); - } + Compile(id); -#if PPSSPP_ARCH(AMD64) && !PPSSPP_PLATFORM(UWP) - if (g_Config.bSoftwareRenderingJit) { - addresses_[id] = GetCodePointer(); - LinearFunc func = CompileLinear(id); - cache_[id] = (NearestFunc)func; - return func; - } -#endif + // Okay, should be there now. + it = cache_.find(id); + if (it != cache_.end()) + return (LinearFunc)it->second; return nullptr; } @@ -189,24 +173,47 @@ FetchFunc SamplerJitCache::GetFetch(const SamplerID &id) { std::lock_guard guard(jitCacheLock); auto it = cache_.find(id); - if (it != cache_.end()) { + if (it != cache_.end()) return (FetchFunc)it->second; - } - // TODO: What should be the min size? Can we even hit this? + Compile(id); + + // Okay, should be there now. + it = cache_.find(id); + if (it != cache_.end()) + return (FetchFunc)it->second; + return nullptr; +} + +void SamplerJitCache::Compile(const SamplerID &id) { + // This should be sufficient. if (GetSpaceLeft() < 16384) { Clear(); } + // We compile them together so the cache can't possibly be cleared in between. + // We might vary between nearest and linear, so we can't clear between. #if PPSSPP_ARCH(AMD64) && !PPSSPP_PLATFORM(UWP) if (g_Config.bSoftwareRenderingJit) { - addresses_[id] = GetCodePointer(); - FetchFunc func = CompileFetch(id); - cache_[id] = (NearestFunc)func; - return func; + SamplerID fetchID = id; + fetchID.linear = false; + fetchID.fetch = true; + addresses_[fetchID] = GetCodePointer(); + cache_[fetchID] = (NearestFunc)CompileFetch(fetchID); + + SamplerID nearestID = id; + nearestID.linear = false; + nearestID.fetch = false; + addresses_[nearestID] = GetCodePointer(); + cache_[nearestID] = (NearestFunc)CompileNearest(nearestID); + + SamplerID linearID = id; + linearID.linear = true; + linearID.fetch = false; + addresses_[linearID] = GetCodePointer(); + cache_[linearID] = (NearestFunc)CompileLinear(linearID); } #endif - return nullptr; } template diff --git a/GPU/Software/Sampler.h b/GPU/Software/Sampler.h index 3c410cbed1..cdf451f32a 100644 --- a/GPU/Software/Sampler.h +++ b/GPU/Software/Sampler.h @@ -60,6 +60,7 @@ public: std::string DescribeCodePtr(const u8 *ptr) override; private: + void Compile(const SamplerID &id); FetchFunc CompileFetch(const SamplerID &id); NearestFunc CompileNearest(const SamplerID &id); LinearFunc CompileLinear(const SamplerID &id);