diff options
| author | 2021-04-14 21:36:36 -0300 | |
|---|---|---|
| committer | 2021-07-22 21:51:27 -0400 | |
| commit | 416e1b7441d34512fcb0ffed014daf7ca4bb62bd (patch) | |
| tree | fa14781ad4969613919a8bcd68b887b9b7a98304 /src/shader_recompiler/backend/spirv/emit_context.cpp | |
| parent | spirv: Implement Layer stores (diff) | |
| download | yuzu-416e1b7441d34512fcb0ffed014daf7ca4bb62bd.tar.gz yuzu-416e1b7441d34512fcb0ffed014daf7ca4bb62bd.tar.xz yuzu-416e1b7441d34512fcb0ffed014daf7ca4bb62bd.zip | |
spirv: Implement image buffers
Diffstat (limited to 'src/shader_recompiler/backend/spirv/emit_context.cpp')
| -rw-r--r-- | src/shader_recompiler/backend/spirv/emit_context.cpp | 70 |
1 files changed, 49 insertions, 21 deletions
diff --git a/src/shader_recompiler/backend/spirv/emit_context.cpp b/src/shader_recompiler/backend/spirv/emit_context.cpp index f96d5ae37..032cf5e03 100644 --- a/src/shader_recompiler/backend/spirv/emit_context.cpp +++ b/src/shader_recompiler/backend/spirv/emit_context.cpp | |||
| @@ -54,28 +54,30 @@ Id ImageType(EmitContext& ctx, const TextureDescriptor& desc) { | |||
| 54 | throw InvalidArgument("Invalid texture type {}", desc.type); | 54 | throw InvalidArgument("Invalid texture type {}", desc.type); |
| 55 | } | 55 | } |
| 56 | 56 | ||
| 57 | spv::ImageFormat GetImageFormat(ImageFormat format) { | ||
| 58 | switch (format) { | ||
| 59 | case ImageFormat::Typeless: | ||
| 60 | return spv::ImageFormat::Unknown; | ||
| 61 | case ImageFormat::R8_UINT: | ||
| 62 | return spv::ImageFormat::R8ui; | ||
| 63 | case ImageFormat::R8_SINT: | ||
| 64 | return spv::ImageFormat::R8i; | ||
| 65 | case ImageFormat::R16_UINT: | ||
| 66 | return spv::ImageFormat::R16ui; | ||
| 67 | case ImageFormat::R16_SINT: | ||
| 68 | return spv::ImageFormat::R16i; | ||
| 69 | case ImageFormat::R32_UINT: | ||
| 70 | return spv::ImageFormat::R32ui; | ||
| 71 | case ImageFormat::R32G32_UINT: | ||
| 72 | return spv::ImageFormat::Rg32ui; | ||
| 73 | case ImageFormat::R32G32B32A32_UINT: | ||
| 74 | return spv::ImageFormat::Rgba32ui; | ||
| 75 | } | ||
| 76 | throw InvalidArgument("Invalid image format {}", format); | ||
| 77 | } | ||
| 78 | |||
| 57 | Id ImageType(EmitContext& ctx, const ImageDescriptor& desc) { | 79 | Id ImageType(EmitContext& ctx, const ImageDescriptor& desc) { |
| 58 | const spv::ImageFormat format{[&] { | 80 | const spv::ImageFormat format{GetImageFormat(desc.format)}; |
| 59 | switch (desc.format) { | ||
| 60 | case ImageFormat::Typeless: | ||
| 61 | return spv::ImageFormat::Unknown; | ||
| 62 | case ImageFormat::R8_UINT: | ||
| 63 | return spv::ImageFormat::R8ui; | ||
| 64 | case ImageFormat::R8_SINT: | ||
| 65 | return spv::ImageFormat::R8i; | ||
| 66 | case ImageFormat::R16_UINT: | ||
| 67 | return spv::ImageFormat::R16ui; | ||
| 68 | case ImageFormat::R16_SINT: | ||
| 69 | return spv::ImageFormat::R16i; | ||
| 70 | case ImageFormat::R32_UINT: | ||
| 71 | return spv::ImageFormat::R32ui; | ||
| 72 | case ImageFormat::R32G32_UINT: | ||
| 73 | return spv::ImageFormat::Rg32ui; | ||
| 74 | case ImageFormat::R32G32B32A32_UINT: | ||
| 75 | return spv::ImageFormat::Rgba32ui; | ||
| 76 | } | ||
| 77 | throw InvalidArgument("Invalid image format {}", desc.format); | ||
| 78 | }()}; | ||
| 79 | const Id type{ctx.U32[1]}; | 81 | const Id type{ctx.U32[1]}; |
| 80 | switch (desc.type) { | 82 | switch (desc.type) { |
| 81 | case TextureType::Color1D: | 83 | case TextureType::Color1D: |
| @@ -388,6 +390,7 @@ EmitContext::EmitContext(const Profile& profile_, IR::Program& program, u32& bin | |||
| 388 | DefineConstantBuffers(program.info, binding); | 390 | DefineConstantBuffers(program.info, binding); |
| 389 | DefineStorageBuffers(program.info, binding); | 391 | DefineStorageBuffers(program.info, binding); |
| 390 | DefineTextureBuffers(program.info, binding); | 392 | DefineTextureBuffers(program.info, binding); |
| 393 | DefineImageBuffers(program.info, binding); | ||
| 391 | DefineTextures(program.info, binding); | 394 | DefineTextures(program.info, binding); |
| 392 | DefineImages(program.info, binding); | 395 | DefineImages(program.info, binding); |
| 393 | DefineAttributeMemAccess(program.info); | 396 | DefineAttributeMemAccess(program.info); |
| @@ -883,6 +886,31 @@ void EmitContext::DefineTextureBuffers(const Info& info, u32& binding) { | |||
| 883 | } | 886 | } |
| 884 | } | 887 | } |
| 885 | 888 | ||
| 889 | void EmitContext::DefineImageBuffers(const Info& info, u32& binding) { | ||
| 890 | image_buffers.reserve(info.image_buffer_descriptors.size()); | ||
| 891 | for (const ImageBufferDescriptor& desc : info.image_buffer_descriptors) { | ||
| 892 | if (desc.count != 1) { | ||
| 893 | throw NotImplementedException("Array of image buffers"); | ||
| 894 | } | ||
| 895 | const spv::ImageFormat format{GetImageFormat(desc.format)}; | ||
| 896 | const Id image_type{TypeImage(U32[4], spv::Dim::Buffer, false, false, false, 2, format)}; | ||
| 897 | const Id pointer_type{TypePointer(spv::StorageClass::UniformConstant, image_type)}; | ||
| 898 | const Id id{AddGlobalVariable(pointer_type, spv::StorageClass::UniformConstant)}; | ||
| 899 | Decorate(id, spv::Decoration::Binding, binding); | ||
| 900 | Decorate(id, spv::Decoration::DescriptorSet, 0U); | ||
| 901 | Name(id, fmt::format("imgbuf{}_{:02x}", desc.cbuf_index, desc.cbuf_offset)); | ||
| 902 | const ImageBufferDefinition def{ | ||
| 903 | .id = id, | ||
| 904 | .image_type = image_type, | ||
| 905 | }; | ||
| 906 | image_buffers.insert(image_buffers.end(), desc.count, def); | ||
| 907 | if (profile.supported_spirv >= 0x00010400) { | ||
| 908 | interfaces.push_back(id); | ||
| 909 | } | ||
| 910 | binding += desc.count; | ||
| 911 | } | ||
| 912 | } | ||
| 913 | |||
| 886 | void EmitContext::DefineTextures(const Info& info, u32& binding) { | 914 | void EmitContext::DefineTextures(const Info& info, u32& binding) { |
| 887 | textures.reserve(info.texture_descriptors.size()); | 915 | textures.reserve(info.texture_descriptors.size()); |
| 888 | for (const TextureDescriptor& desc : info.texture_descriptors) { | 916 | for (const TextureDescriptor& desc : info.texture_descriptors) { |