diff options
author | Mai M <mathew1800@gmail.com> | 2021-06-11 20:26:54 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-06-11 20:26:54 +0200 |
commit | 9951322e5a37a604e185ae7013af7c4cfc5c35f8 (patch) | |
tree | 6d765e2d635990de4acb98c1e2b6ce125546f629 /src/video_core | |
parent | Merge pull request #6443 from Morph1984/k-light-condition-variable (diff) | |
parent | common/host_memory: Implement a fallback if fastmem fails. (diff) | |
download | yuzu-9951322e5a37a604e185ae7013af7c4cfc5c35f8.tar yuzu-9951322e5a37a604e185ae7013af7c4cfc5c35f8.tar.gz yuzu-9951322e5a37a604e185ae7013af7c4cfc5c35f8.tar.bz2 yuzu-9951322e5a37a604e185ae7013af7c4cfc5c35f8.tar.lz yuzu-9951322e5a37a604e185ae7013af7c4cfc5c35f8.tar.xz yuzu-9951322e5a37a604e185ae7013af7c4cfc5c35f8.tar.zst yuzu-9951322e5a37a604e185ae7013af7c4cfc5c35f8.zip |
Diffstat (limited to 'src/video_core')
-rw-r--r-- | src/video_core/gpu_thread.cpp | 24 | ||||
-rw-r--r-- | src/video_core/rasterizer_accelerated.cpp | 56 |
2 files changed, 47 insertions, 33 deletions
diff --git a/src/video_core/gpu_thread.cpp b/src/video_core/gpu_thread.cpp index cd1fbb9bf..46f642b19 100644 --- a/src/video_core/gpu_thread.cpp +++ b/src/video_core/gpu_thread.cpp @@ -99,25 +99,13 @@ void ThreadManager::FlushRegion(VAddr addr, u64 size) { PushCommand(FlushRegionCommand(addr, size)); return; } - - // Asynchronous GPU mode - switch (Settings::values.gpu_accuracy.GetValue()) { - case Settings::GPUAccuracy::Normal: - PushCommand(FlushRegionCommand(addr, size)); - break; - case Settings::GPUAccuracy::High: - // TODO(bunnei): Is this right? Preserving existing behavior for now - break; - case Settings::GPUAccuracy::Extreme: { - auto& gpu = system.GPU(); - u64 fence = gpu.RequestFlush(addr, size); - PushCommand(GPUTickCommand(), true); - ASSERT(fence <= gpu.CurrentFlushRequestFence()); - break; - } - default: - UNIMPLEMENTED_MSG("Unsupported gpu_accuracy {}", Settings::values.gpu_accuracy.GetValue()); + if (!Settings::IsGPULevelExtreme()) { + return; } + auto& gpu = system.GPU(); + u64 fence = gpu.RequestFlush(addr, size); + PushCommand(GPUTickCommand(), true); + ASSERT(fence <= gpu.CurrentFlushRequestFence()); } void ThreadManager::InvalidateRegion(VAddr addr, u64 size) { diff --git a/src/video_core/rasterizer_accelerated.cpp b/src/video_core/rasterizer_accelerated.cpp index 6decd2546..4c9524702 100644 --- a/src/video_core/rasterizer_accelerated.cpp +++ b/src/video_core/rasterizer_accelerated.cpp @@ -2,6 +2,8 @@ // Licensed under GPLv2 or any later version // Refer to the license.txt file included. +#include <atomic> + #include "common/assert.h" #include "common/common_types.h" #include "common/div_ceil.h" @@ -10,35 +12,59 @@ namespace VideoCore { -RasterizerAccelerated::RasterizerAccelerated(Core::Memory::Memory& cpu_memory_) - : cpu_memory{cpu_memory_} {} +using namespace Core::Memory; + +RasterizerAccelerated::RasterizerAccelerated(Memory& cpu_memory_) : cpu_memory{cpu_memory_} {} RasterizerAccelerated::~RasterizerAccelerated() = default; void RasterizerAccelerated::UpdatePagesCachedCount(VAddr addr, u64 size, int delta) { - const auto page_end = Common::DivCeil(addr + size, Core::Memory::PAGE_SIZE); - for (auto page = addr >> Core::Memory::PAGE_BITS; page != page_end; ++page) { - auto& count = cached_pages.at(page >> 2).Count(page); + u64 uncache_begin = 0; + u64 cache_begin = 0; + u64 uncache_bytes = 0; + u64 cache_bytes = 0; + + std::atomic_thread_fence(std::memory_order_acquire); + const u64 page_end = Common::DivCeil(addr + size, PAGE_SIZE); + for (u64 page = addr >> PAGE_BITS; page != page_end; ++page) { + std::atomic_uint16_t& count = cached_pages.at(page >> 2).Count(page); if (delta > 0) { - ASSERT_MSG(count < UINT16_MAX, "Count may overflow!"); + ASSERT_MSG(count.load(std::memory_order::relaxed) < UINT16_MAX, "Count may overflow!"); } else if (delta < 0) { - ASSERT_MSG(count > 0, "Count may underflow!"); + ASSERT_MSG(count.load(std::memory_order::relaxed) > 0, "Count may underflow!"); } else { - ASSERT_MSG(true, "Delta must be non-zero!"); + ASSERT_MSG(false, "Delta must be non-zero!"); } // Adds or subtracts 1, as count is a unsigned 8-bit value - count += static_cast<u16>(delta); + count.fetch_add(static_cast<u16>(delta), std::memory_order_release); // Assume delta is either -1 or 1 - if (count == 0) { - cpu_memory.RasterizerMarkRegionCached(page << Core::Memory::PAGE_BITS, - Core::Memory::PAGE_SIZE, false); - } else if (count == 1 && delta > 0) { - cpu_memory.RasterizerMarkRegionCached(page << Core::Memory::PAGE_BITS, - Core::Memory::PAGE_SIZE, true); + if (count.load(std::memory_order::relaxed) == 0) { + if (uncache_bytes == 0) { + uncache_begin = page; + } + uncache_bytes += PAGE_SIZE; + } else if (uncache_bytes > 0) { + cpu_memory.RasterizerMarkRegionCached(uncache_begin << PAGE_BITS, uncache_bytes, false); + uncache_bytes = 0; } + if (count.load(std::memory_order::relaxed) == 1 && delta > 0) { + if (cache_bytes == 0) { + cache_begin = page; + } + cache_bytes += PAGE_SIZE; + } else if (cache_bytes > 0) { + cpu_memory.RasterizerMarkRegionCached(cache_begin << PAGE_BITS, cache_bytes, true); + cache_bytes = 0; + } + } + if (uncache_bytes > 0) { + cpu_memory.RasterizerMarkRegionCached(uncache_begin << PAGE_BITS, uncache_bytes, false); + } + if (cache_bytes > 0) { + cpu_memory.RasterizerMarkRegionCached(cache_begin << PAGE_BITS, cache_bytes, true); } } |