diff options
| author | 2021-03-27 22:30:24 +0100 | |
|---|---|---|
| committer | 2021-07-22 21:51:25 -0400 | |
| commit | 34aba9627a8fad20b3b173180e2f3d679dd32293 (patch) | |
| tree | a4f2faec67a793e8b44493532a683908dcefb4d8 /src/video_core/renderer_vulkan | |
| parent | shader: Fix alignment checks on RZ (diff) | |
| download | yuzu-34aba9627a8fad20b3b173180e2f3d679dd32293.tar.gz yuzu-34aba9627a8fad20b3b173180e2f3d679dd32293.tar.xz yuzu-34aba9627a8fad20b3b173180e2f3d679dd32293.zip | |
shader: Implement BRX
Diffstat (limited to 'src/video_core/renderer_vulkan')
| -rw-r--r-- | src/video_core/renderer_vulkan/vk_pipeline_cache.cpp | 50 |
1 files changed, 49 insertions, 1 deletions
diff --git a/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp b/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp index 8b2816c13..6cde01491 100644 --- a/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp +++ b/src/video_core/renderer_vulkan/vk_pipeline_cache.cpp | |||
| @@ -47,7 +47,7 @@ auto MakeSpan(Container& container) { | |||
| 47 | } | 47 | } |
| 48 | 48 | ||
| 49 | u64 MakeCbufKey(u32 index, u32 offset) { | 49 | u64 MakeCbufKey(u32 index, u32 offset) { |
| 50 | return (static_cast<u64>(index) << 32) | static_cast<u64>(offset); | 50 | return (static_cast<u64>(index) << 32) | offset; |
| 51 | } | 51 | } |
| 52 | 52 | ||
| 53 | class GenericEnvironment : public Shader::Environment { | 53 | class GenericEnvironment : public Shader::Environment { |
| @@ -114,11 +114,13 @@ public: | |||
| 114 | gpu_memory->ReadBlock(program_base + read_lowest, data.get(), code_size); | 114 | gpu_memory->ReadBlock(program_base + read_lowest, data.get(), code_size); |
| 115 | 115 | ||
| 116 | const u64 num_texture_types{static_cast<u64>(texture_types.size())}; | 116 | const u64 num_texture_types{static_cast<u64>(texture_types.size())}; |
| 117 | const u64 num_cbuf_values{static_cast<u64>(cbuf_values.size())}; | ||
| 117 | const u32 local_memory_size{LocalMemorySize()}; | 118 | const u32 local_memory_size{LocalMemorySize()}; |
| 118 | const u32 texture_bound{TextureBoundBuffer()}; | 119 | const u32 texture_bound{TextureBoundBuffer()}; |
| 119 | 120 | ||
| 120 | file.write(reinterpret_cast<const char*>(&code_size), sizeof(code_size)) | 121 | file.write(reinterpret_cast<const char*>(&code_size), sizeof(code_size)) |
| 121 | .write(reinterpret_cast<const char*>(&num_texture_types), sizeof(num_texture_types)) | 122 | .write(reinterpret_cast<const char*>(&num_texture_types), sizeof(num_texture_types)) |
| 123 | .write(reinterpret_cast<const char*>(&num_cbuf_values), sizeof(num_cbuf_values)) | ||
| 122 | .write(reinterpret_cast<const char*>(&local_memory_size), sizeof(local_memory_size)) | 124 | .write(reinterpret_cast<const char*>(&local_memory_size), sizeof(local_memory_size)) |
| 123 | .write(reinterpret_cast<const char*>(&texture_bound), sizeof(texture_bound)) | 125 | .write(reinterpret_cast<const char*>(&texture_bound), sizeof(texture_bound)) |
| 124 | .write(reinterpret_cast<const char*>(&start_address), sizeof(start_address)) | 126 | .write(reinterpret_cast<const char*>(&start_address), sizeof(start_address)) |
| @@ -130,6 +132,10 @@ public: | |||
| 130 | file.write(reinterpret_cast<const char*>(&key), sizeof(key)) | 132 | file.write(reinterpret_cast<const char*>(&key), sizeof(key)) |
| 131 | .write(reinterpret_cast<const char*>(&type), sizeof(type)); | 133 | .write(reinterpret_cast<const char*>(&type), sizeof(type)); |
| 132 | } | 134 | } |
| 135 | for (const auto [key, type] : cbuf_values) { | ||
| 136 | file.write(reinterpret_cast<const char*>(&key), sizeof(key)) | ||
| 137 | .write(reinterpret_cast<const char*>(&type), sizeof(type)); | ||
| 138 | } | ||
| 133 | if (stage == Shader::Stage::Compute) { | 139 | if (stage == Shader::Stage::Compute) { |
| 134 | const std::array<u32, 3> workgroup_size{WorkgroupSize()}; | 140 | const std::array<u32, 3> workgroup_size{WorkgroupSize()}; |
| 135 | const u32 shared_memory_size{SharedMemorySize()}; | 141 | const u32 shared_memory_size{SharedMemorySize()}; |
| @@ -212,6 +218,7 @@ protected: | |||
| 212 | 218 | ||
| 213 | std::vector<u64> code; | 219 | std::vector<u64> code; |
| 214 | std::unordered_map<u64, Shader::TextureType> texture_types; | 220 | std::unordered_map<u64, Shader::TextureType> texture_types; |
| 221 | std::unordered_map<u64, u32> cbuf_values; | ||
| 215 | 222 | ||
| 216 | u32 read_lowest = std::numeric_limits<u32>::max(); | 223 | u32 read_lowest = std::numeric_limits<u32>::max(); |
| 217 | u32 read_highest = 0; | 224 | u32 read_highest = 0; |
| @@ -267,6 +274,17 @@ public: | |||
| 267 | 274 | ||
| 268 | ~GraphicsEnvironment() override = default; | 275 | ~GraphicsEnvironment() override = default; |
| 269 | 276 | ||
| 277 | u32 ReadCbufValue(u32 cbuf_index, u32 cbuf_offset) override { | ||
| 278 | const auto& cbuf{maxwell3d->state.shader_stages[stage_index].const_buffers[cbuf_index]}; | ||
| 279 | ASSERT(cbuf.enabled); | ||
| 280 | u32 value{}; | ||
| 281 | if (cbuf_offset < cbuf.size) { | ||
| 282 | value = gpu_memory->Read<u32>(cbuf.address + cbuf_offset); | ||
| 283 | } | ||
| 284 | cbuf_values.emplace(MakeCbufKey(cbuf_index, cbuf_offset), value); | ||
| 285 | return value; | ||
| 286 | } | ||
| 287 | |||
| 270 | Shader::TextureType ReadTextureType(u32 cbuf_index, u32 cbuf_offset) override { | 288 | Shader::TextureType ReadTextureType(u32 cbuf_index, u32 cbuf_offset) override { |
| 271 | const auto& regs{maxwell3d->regs}; | 289 | const auto& regs{maxwell3d->regs}; |
| 272 | const auto& cbuf{maxwell3d->state.shader_stages[stage_index].const_buffers[cbuf_index]}; | 290 | const auto& cbuf{maxwell3d->state.shader_stages[stage_index].const_buffers[cbuf_index]}; |
| @@ -312,6 +330,18 @@ public: | |||
| 312 | 330 | ||
| 313 | ~ComputeEnvironment() override = default; | 331 | ~ComputeEnvironment() override = default; |
| 314 | 332 | ||
| 333 | u32 ReadCbufValue(u32 cbuf_index, u32 cbuf_offset) override { | ||
| 334 | const auto& qmd{kepler_compute->launch_description}; | ||
| 335 | ASSERT(((qmd.const_buffer_enable_mask.Value() >> cbuf_index) & 1) != 0); | ||
| 336 | const auto& cbuf{qmd.const_buffer_config[cbuf_index]}; | ||
| 337 | u32 value{}; | ||
| 338 | if (cbuf_offset < cbuf.size) { | ||
| 339 | value = gpu_memory->Read<u32>(cbuf.Address() + cbuf_offset); | ||
| 340 | } | ||
| 341 | cbuf_values.emplace(MakeCbufKey(cbuf_index, cbuf_offset), value); | ||
| 342 | return value; | ||
| 343 | } | ||
| 344 | |||
| 315 | Shader::TextureType ReadTextureType(u32 cbuf_index, u32 cbuf_offset) override { | 345 | Shader::TextureType ReadTextureType(u32 cbuf_index, u32 cbuf_offset) override { |
| 316 | const auto& regs{kepler_compute->regs}; | 346 | const auto& regs{kepler_compute->regs}; |
| 317 | const auto& qmd{kepler_compute->launch_description}; | 347 | const auto& qmd{kepler_compute->launch_description}; |
| @@ -386,8 +416,10 @@ public: | |||
| 386 | void Deserialize(std::ifstream& file) { | 416 | void Deserialize(std::ifstream& file) { |
| 387 | u64 code_size{}; | 417 | u64 code_size{}; |
| 388 | u64 num_texture_types{}; | 418 | u64 num_texture_types{}; |
| 419 | u64 num_cbuf_values{}; | ||
| 389 | file.read(reinterpret_cast<char*>(&code_size), sizeof(code_size)) | 420 | file.read(reinterpret_cast<char*>(&code_size), sizeof(code_size)) |
| 390 | .read(reinterpret_cast<char*>(&num_texture_types), sizeof(num_texture_types)) | 421 | .read(reinterpret_cast<char*>(&num_texture_types), sizeof(num_texture_types)) |
| 422 | .read(reinterpret_cast<char*>(&num_cbuf_values), sizeof(num_cbuf_values)) | ||
| 391 | .read(reinterpret_cast<char*>(&local_memory_size), sizeof(local_memory_size)) | 423 | .read(reinterpret_cast<char*>(&local_memory_size), sizeof(local_memory_size)) |
| 392 | .read(reinterpret_cast<char*>(&texture_bound), sizeof(texture_bound)) | 424 | .read(reinterpret_cast<char*>(&texture_bound), sizeof(texture_bound)) |
| 393 | .read(reinterpret_cast<char*>(&start_address), sizeof(start_address)) | 425 | .read(reinterpret_cast<char*>(&start_address), sizeof(start_address)) |
| @@ -403,6 +435,13 @@ public: | |||
| 403 | .read(reinterpret_cast<char*>(&type), sizeof(type)); | 435 | .read(reinterpret_cast<char*>(&type), sizeof(type)); |
| 404 | texture_types.emplace(key, type); | 436 | texture_types.emplace(key, type); |
| 405 | } | 437 | } |
| 438 | for (size_t i = 0; i < num_cbuf_values; ++i) { | ||
| 439 | u64 key; | ||
| 440 | u32 value; | ||
| 441 | file.read(reinterpret_cast<char*>(&key), sizeof(key)) | ||
| 442 | .read(reinterpret_cast<char*>(&value), sizeof(value)); | ||
| 443 | cbuf_values.emplace(key, value); | ||
| 444 | } | ||
| 406 | if (stage == Shader::Stage::Compute) { | 445 | if (stage == Shader::Stage::Compute) { |
| 407 | file.read(reinterpret_cast<char*>(&workgroup_size), sizeof(workgroup_size)) | 446 | file.read(reinterpret_cast<char*>(&workgroup_size), sizeof(workgroup_size)) |
| 408 | .read(reinterpret_cast<char*>(&shared_memory_size), sizeof(shared_memory_size)); | 447 | .read(reinterpret_cast<char*>(&shared_memory_size), sizeof(shared_memory_size)); |
| @@ -418,6 +457,14 @@ public: | |||
| 418 | return code[(address - read_lowest) / sizeof(u64)]; | 457 | return code[(address - read_lowest) / sizeof(u64)]; |
| 419 | } | 458 | } |
| 420 | 459 | ||
| 460 | u32 ReadCbufValue(u32 cbuf_index, u32 cbuf_offset) override { | ||
| 461 | const auto it{cbuf_values.find(MakeCbufKey(cbuf_index, cbuf_offset))}; | ||
| 462 | if (it == cbuf_values.end()) { | ||
| 463 | throw Shader::LogicError("Uncached read texture type"); | ||
| 464 | } | ||
| 465 | return it->second; | ||
| 466 | } | ||
| 467 | |||
| 421 | Shader::TextureType ReadTextureType(u32 cbuf_index, u32 cbuf_offset) override { | 468 | Shader::TextureType ReadTextureType(u32 cbuf_index, u32 cbuf_offset) override { |
| 422 | const auto it{texture_types.find(MakeCbufKey(cbuf_index, cbuf_offset))}; | 469 | const auto it{texture_types.find(MakeCbufKey(cbuf_index, cbuf_offset))}; |
| 423 | if (it == texture_types.end()) { | 470 | if (it == texture_types.end()) { |
| @@ -445,6 +492,7 @@ public: | |||
| 445 | private: | 492 | private: |
| 446 | std::unique_ptr<u64[]> code; | 493 | std::unique_ptr<u64[]> code; |
| 447 | std::unordered_map<u64, Shader::TextureType> texture_types; | 494 | std::unordered_map<u64, Shader::TextureType> texture_types; |
| 495 | std::unordered_map<u64, u32> cbuf_values; | ||
| 448 | std::array<u32, 3> workgroup_size{}; | 496 | std::array<u32, 3> workgroup_size{}; |
| 449 | u32 local_memory_size{}; | 497 | u32 local_memory_size{}; |
| 450 | u32 shared_memory_size{}; | 498 | u32 shared_memory_size{}; |