summaryrefslogtreecommitdiff
path: root/src/video_core/buffer_cache
diff options
context:
space:
mode:
Diffstat (limited to 'src/video_core/buffer_cache')
-rw-r--r--src/video_core/buffer_cache/buffer_cache.h53
1 files changed, 34 insertions, 19 deletions
diff --git a/src/video_core/buffer_cache/buffer_cache.h b/src/video_core/buffer_cache/buffer_cache.h
index 29746f61d..6c92e4c30 100644
--- a/src/video_core/buffer_cache/buffer_cache.h
+++ b/src/video_core/buffer_cache/buffer_cache.h
@@ -70,8 +70,8 @@ class BufferCache {
70 P::HAS_FULL_INDEX_AND_PRIMITIVE_SUPPORT; 70 P::HAS_FULL_INDEX_AND_PRIMITIVE_SUPPORT;
71 static constexpr bool NEEDS_BIND_UNIFORM_INDEX = P::NEEDS_BIND_UNIFORM_INDEX; 71 static constexpr bool NEEDS_BIND_UNIFORM_INDEX = P::NEEDS_BIND_UNIFORM_INDEX;
72 static constexpr bool NEEDS_BIND_STORAGE_INDEX = P::NEEDS_BIND_STORAGE_INDEX; 72 static constexpr bool NEEDS_BIND_STORAGE_INDEX = P::NEEDS_BIND_STORAGE_INDEX;
73 static constexpr bool NEEDS_BIND_TEXTURE_BUFFER_INDEX = P::NEEDS_BIND_TEXTURE_BUFFER_INDEX;
74 static constexpr bool USE_MEMORY_MAPS = P::USE_MEMORY_MAPS; 73 static constexpr bool USE_MEMORY_MAPS = P::USE_MEMORY_MAPS;
74 static constexpr bool SEPARATE_IMAGE_BUFFERS_BINDINGS = P::SEPARATE_IMAGE_BUFFER_BINDINGS;
75 75
76 static constexpr BufferId NULL_BUFFER_ID{0}; 76 static constexpr BufferId NULL_BUFFER_ID{0};
77 77
@@ -154,7 +154,7 @@ public:
154 void UnbindGraphicsTextureBuffers(size_t stage); 154 void UnbindGraphicsTextureBuffers(size_t stage);
155 155
156 void BindGraphicsTextureBuffer(size_t stage, size_t tbo_index, GPUVAddr gpu_addr, u32 size, 156 void BindGraphicsTextureBuffer(size_t stage, size_t tbo_index, GPUVAddr gpu_addr, u32 size,
157 PixelFormat format, bool is_written); 157 PixelFormat format, bool is_written, bool is_image);
158 158
159 void UnbindComputeStorageBuffers(); 159 void UnbindComputeStorageBuffers();
160 160
@@ -164,7 +164,7 @@ public:
164 void UnbindComputeTextureBuffers(); 164 void UnbindComputeTextureBuffers();
165 165
166 void BindComputeTextureBuffer(size_t tbo_index, GPUVAddr gpu_addr, u32 size, PixelFormat format, 166 void BindComputeTextureBuffer(size_t tbo_index, GPUVAddr gpu_addr, u32 size, PixelFormat format,
167 bool is_written); 167 bool is_written, bool is_image);
168 168
169 void FlushCachedWrites(); 169 void FlushCachedWrites();
170 170
@@ -197,6 +197,7 @@ public:
197 [[nodiscard]] bool IsRegionCpuModified(VAddr addr, size_t size); 197 [[nodiscard]] bool IsRegionCpuModified(VAddr addr, size_t size);
198 198
199 std::mutex mutex; 199 std::mutex mutex;
200 Runtime& runtime;
200 201
201private: 202private:
202 template <typename Func> 203 template <typename Func>
@@ -366,7 +367,6 @@ private:
366 Tegra::Engines::KeplerCompute& kepler_compute; 367 Tegra::Engines::KeplerCompute& kepler_compute;
367 Tegra::MemoryManager& gpu_memory; 368 Tegra::MemoryManager& gpu_memory;
368 Core::Memory::Memory& cpu_memory; 369 Core::Memory::Memory& cpu_memory;
369 Runtime& runtime;
370 370
371 SlotVector<Buffer> slot_buffers; 371 SlotVector<Buffer> slot_buffers;
372 DelayedDestructionRing<Buffer, 8> delayed_destruction_ring; 372 DelayedDestructionRing<Buffer, 8> delayed_destruction_ring;
@@ -394,8 +394,10 @@ private:
394 394
395 std::array<u32, NUM_STAGES> enabled_texture_buffers{}; 395 std::array<u32, NUM_STAGES> enabled_texture_buffers{};
396 std::array<u32, NUM_STAGES> written_texture_buffers{}; 396 std::array<u32, NUM_STAGES> written_texture_buffers{};
397 std::array<u32, NUM_STAGES> image_texture_buffers{};
397 u32 enabled_compute_texture_buffers = 0; 398 u32 enabled_compute_texture_buffers = 0;
398 u32 written_compute_texture_buffers = 0; 399 u32 written_compute_texture_buffers = 0;
400 u32 image_compute_texture_buffers = 0;
399 401
400 std::array<u32, NUM_STAGES> fast_bound_uniform_buffers{}; 402 std::array<u32, NUM_STAGES> fast_bound_uniform_buffers{};
401 403
@@ -431,8 +433,8 @@ BufferCache<P>::BufferCache(VideoCore::RasterizerInterface& rasterizer_,
431 Tegra::Engines::KeplerCompute& kepler_compute_, 433 Tegra::Engines::KeplerCompute& kepler_compute_,
432 Tegra::MemoryManager& gpu_memory_, Core::Memory::Memory& cpu_memory_, 434 Tegra::MemoryManager& gpu_memory_, Core::Memory::Memory& cpu_memory_,
433 Runtime& runtime_) 435 Runtime& runtime_)
434 : rasterizer{rasterizer_}, maxwell3d{maxwell3d_}, kepler_compute{kepler_compute_}, 436 : runtime{runtime_}, rasterizer{rasterizer_}, maxwell3d{maxwell3d_},
435 gpu_memory{gpu_memory_}, cpu_memory{cpu_memory_}, runtime{runtime_} { 437 kepler_compute{kepler_compute_}, gpu_memory{gpu_memory_}, cpu_memory{cpu_memory_} {
436 // Ensure the first slot is used for the null buffer 438 // Ensure the first slot is used for the null buffer
437 void(slot_buffers.insert(runtime, NullBufferParams{})); 439 void(slot_buffers.insert(runtime, NullBufferParams{}));
438 deletion_iterator = slot_buffers.end(); 440 deletion_iterator = slot_buffers.end();
@@ -703,13 +705,18 @@ template <class P>
703void BufferCache<P>::UnbindGraphicsTextureBuffers(size_t stage) { 705void BufferCache<P>::UnbindGraphicsTextureBuffers(size_t stage) {
704 enabled_texture_buffers[stage] = 0; 706 enabled_texture_buffers[stage] = 0;
705 written_texture_buffers[stage] = 0; 707 written_texture_buffers[stage] = 0;
708 image_texture_buffers[stage] = 0;
706} 709}
707 710
708template <class P> 711template <class P>
709void BufferCache<P>::BindGraphicsTextureBuffer(size_t stage, size_t tbo_index, GPUVAddr gpu_addr, 712void BufferCache<P>::BindGraphicsTextureBuffer(size_t stage, size_t tbo_index, GPUVAddr gpu_addr,
710 u32 size, PixelFormat format, bool is_written) { 713 u32 size, PixelFormat format, bool is_written,
714 bool is_image) {
711 enabled_texture_buffers[stage] |= 1U << tbo_index; 715 enabled_texture_buffers[stage] |= 1U << tbo_index;
712 written_texture_buffers[stage] |= (is_written ? 1U : 0U) << tbo_index; 716 written_texture_buffers[stage] |= (is_written ? 1U : 0U) << tbo_index;
717 if constexpr (SEPARATE_IMAGE_BUFFERS_BINDINGS) {
718 image_texture_buffers[stage] |= (is_image ? 1U : 0U) << tbo_index;
719 }
713 texture_buffers[stage][tbo_index] = GetTextureBufferBinding(gpu_addr, size, format); 720 texture_buffers[stage][tbo_index] = GetTextureBufferBinding(gpu_addr, size, format);
714} 721}
715 722
@@ -717,6 +724,7 @@ template <class P>
717void BufferCache<P>::UnbindComputeStorageBuffers() { 724void BufferCache<P>::UnbindComputeStorageBuffers() {
718 enabled_compute_storage_buffers = 0; 725 enabled_compute_storage_buffers = 0;
719 written_compute_storage_buffers = 0; 726 written_compute_storage_buffers = 0;
727 image_compute_texture_buffers = 0;
720} 728}
721 729
722template <class P> 730template <class P>
@@ -737,13 +745,17 @@ template <class P>
737void BufferCache<P>::UnbindComputeTextureBuffers() { 745void BufferCache<P>::UnbindComputeTextureBuffers() {
738 enabled_compute_texture_buffers = 0; 746 enabled_compute_texture_buffers = 0;
739 written_compute_texture_buffers = 0; 747 written_compute_texture_buffers = 0;
748 image_compute_texture_buffers = 0;
740} 749}
741 750
742template <class P> 751template <class P>
743void BufferCache<P>::BindComputeTextureBuffer(size_t tbo_index, GPUVAddr gpu_addr, u32 size, 752void BufferCache<P>::BindComputeTextureBuffer(size_t tbo_index, GPUVAddr gpu_addr, u32 size,
744 PixelFormat format, bool is_written) { 753 PixelFormat format, bool is_written, bool is_image) {
745 enabled_compute_texture_buffers |= 1U << tbo_index; 754 enabled_compute_texture_buffers |= 1U << tbo_index;
746 written_compute_texture_buffers |= (is_written ? 1U : 0U) << tbo_index; 755 written_compute_texture_buffers |= (is_written ? 1U : 0U) << tbo_index;
756 if constexpr (SEPARATE_IMAGE_BUFFERS_BINDINGS) {
757 image_compute_texture_buffers |= (is_image ? 1U : 0U) << tbo_index;
758 }
747 compute_texture_buffers[tbo_index] = GetTextureBufferBinding(gpu_addr, size, format); 759 compute_texture_buffers[tbo_index] = GetTextureBufferBinding(gpu_addr, size, format);
748} 760}
749 761
@@ -1057,7 +1069,6 @@ void BufferCache<P>::BindHostGraphicsStorageBuffers(size_t stage) {
1057 1069
1058template <class P> 1070template <class P>
1059void BufferCache<P>::BindHostGraphicsTextureBuffers(size_t stage) { 1071void BufferCache<P>::BindHostGraphicsTextureBuffers(size_t stage) {
1060 u32 binding_index = 0;
1061 ForEachEnabledBit(enabled_texture_buffers[stage], [&](u32 index) { 1072 ForEachEnabledBit(enabled_texture_buffers[stage], [&](u32 index) {
1062 const TextureBufferBinding& binding = texture_buffers[stage][index]; 1073 const TextureBufferBinding& binding = texture_buffers[stage][index];
1063 Buffer& buffer = slot_buffers[binding.buffer_id]; 1074 Buffer& buffer = slot_buffers[binding.buffer_id];
@@ -1066,9 +1077,12 @@ void BufferCache<P>::BindHostGraphicsTextureBuffers(size_t stage) {
1066 1077
1067 const u32 offset = buffer.Offset(binding.cpu_addr); 1078 const u32 offset = buffer.Offset(binding.cpu_addr);
1068 const PixelFormat format = binding.format; 1079 const PixelFormat format = binding.format;
1069 if constexpr (NEEDS_BIND_TEXTURE_BUFFER_INDEX) { 1080 if constexpr (SEPARATE_IMAGE_BUFFERS_BINDINGS) {
1070 runtime.BindTextureBuffer(binding_index, buffer, offset, size, format); 1081 if (((image_texture_buffers[stage] >> index) & 1) != 0) {
1071 ++binding_index; 1082 runtime.BindImageBuffer(buffer, offset, size, format);
1083 } else {
1084 runtime.BindTextureBuffer(buffer, offset, size, format);
1085 }
1072 } else { 1086 } else {
1073 runtime.BindTextureBuffer(buffer, offset, size, format); 1087 runtime.BindTextureBuffer(buffer, offset, size, format);
1074 } 1088 }
@@ -1139,7 +1153,6 @@ void BufferCache<P>::BindHostComputeStorageBuffers() {
1139 1153
1140template <class P> 1154template <class P>
1141void BufferCache<P>::BindHostComputeTextureBuffers() { 1155void BufferCache<P>::BindHostComputeTextureBuffers() {
1142 u32 binding_index = 0;
1143 ForEachEnabledBit(enabled_compute_texture_buffers, [&](u32 index) { 1156 ForEachEnabledBit(enabled_compute_texture_buffers, [&](u32 index) {
1144 const TextureBufferBinding& binding = compute_texture_buffers[index]; 1157 const TextureBufferBinding& binding = compute_texture_buffers[index];
1145 Buffer& buffer = slot_buffers[binding.buffer_id]; 1158 Buffer& buffer = slot_buffers[binding.buffer_id];
@@ -1148,9 +1161,12 @@ void BufferCache<P>::BindHostComputeTextureBuffers() {
1148 1161
1149 const u32 offset = buffer.Offset(binding.cpu_addr); 1162 const u32 offset = buffer.Offset(binding.cpu_addr);
1150 const PixelFormat format = binding.format; 1163 const PixelFormat format = binding.format;
1151 if constexpr (NEEDS_BIND_TEXTURE_BUFFER_INDEX) { 1164 if constexpr (SEPARATE_IMAGE_BUFFERS_BINDINGS) {
1152 runtime.BindTextureBuffer(binding_index, buffer, offset, size, format); 1165 if (((image_compute_texture_buffers >> index) & 1) != 0) {
1153 ++binding_index; 1166 runtime.BindImageBuffer(buffer, offset, size, format);
1167 } else {
1168 runtime.BindTextureBuffer(buffer, offset, size, format);
1169 }
1154 } else { 1170 } else {
1155 runtime.BindTextureBuffer(buffer, offset, size, format); 1171 runtime.BindTextureBuffer(buffer, offset, size, format);
1156 } 1172 }
@@ -1339,11 +1355,10 @@ void BufferCache<P>::UpdateComputeStorageBuffers() {
1339 ForEachEnabledBit(enabled_compute_storage_buffers, [&](u32 index) { 1355 ForEachEnabledBit(enabled_compute_storage_buffers, [&](u32 index) {
1340 // Resolve buffer 1356 // Resolve buffer
1341 Binding& binding = compute_storage_buffers[index]; 1357 Binding& binding = compute_storage_buffers[index];
1342 const BufferId buffer_id = FindBuffer(binding.cpu_addr, binding.size); 1358 binding.buffer_id = FindBuffer(binding.cpu_addr, binding.size);
1343 binding.buffer_id = buffer_id;
1344 // Mark as written if needed 1359 // Mark as written if needed
1345 if (((written_compute_storage_buffers >> index) & 1) != 0) { 1360 if (((written_compute_storage_buffers >> index) & 1) != 0) {
1346 MarkWrittenBuffer(buffer_id, binding.cpu_addr, binding.size); 1361 MarkWrittenBuffer(binding.buffer_id, binding.cpu_addr, binding.size);
1347 } 1362 }
1348 }); 1363 });
1349} 1364}