diff options
| author | 2021-05-23 03:58:11 -0300 | |
|---|---|---|
| committer | 2021-07-22 21:51:29 -0400 | |
| commit | 48a17298d76cd8ed3bf2b53aca1e1ac097693976 (patch) | |
| tree | f0395bbe074b21c96d8a8bbe2ad9115dcbff92cf /src/shader_recompiler/backend/spirv/emit_context.cpp | |
| parent | spirv: Desambiguate descriptor names (diff) | |
| download | yuzu-48a17298d76cd8ed3bf2b53aca1e1ac097693976.tar.gz yuzu-48a17298d76cd8ed3bf2b53aca1e1ac097693976.tar.xz yuzu-48a17298d76cd8ed3bf2b53aca1e1ac097693976.zip | |
spirv: Support OpenGL uniform buffers and change bindings
Diffstat (limited to 'src/shader_recompiler/backend/spirv/emit_context.cpp')
| -rw-r--r-- | src/shader_recompiler/backend/spirv/emit_context.cpp | 102 |
1 files changed, 66 insertions, 36 deletions
diff --git a/src/shader_recompiler/backend/spirv/emit_context.cpp b/src/shader_recompiler/backend/spirv/emit_context.cpp index 0459c3925..0eb400223 100644 --- a/src/shader_recompiler/backend/spirv/emit_context.cpp +++ b/src/shader_recompiler/backend/spirv/emit_context.cpp | |||
| @@ -441,8 +441,13 @@ void VectorTypes::Define(Sirit::Module& sirit_ctx, Id base_type, std::string_vie | |||
| 441 | } | 441 | } |
| 442 | } | 442 | } |
| 443 | 443 | ||
| 444 | EmitContext::EmitContext(const Profile& profile_, IR::Program& program, u32& binding) | 444 | EmitContext::EmitContext(const Profile& profile_, IR::Program& program, Bindings& binding) |
| 445 | : Sirit::Module(profile_.supported_spirv), profile{profile_}, stage{program.stage} { | 445 | : Sirit::Module(profile_.supported_spirv), profile{profile_}, stage{program.stage} { |
| 446 | const bool is_unified{profile.unified_descriptor_binding}; | ||
| 447 | u32& uniform_binding{is_unified ? binding.unified : binding.uniform_buffer}; | ||
| 448 | u32& storage_binding{is_unified ? binding.unified : binding.storage_buffer}; | ||
| 449 | u32& texture_binding{is_unified ? binding.unified : binding.texture}; | ||
| 450 | u32& image_binding{is_unified ? binding.unified : binding.image}; | ||
| 446 | AddCapability(spv::Capability::Shader); | 451 | AddCapability(spv::Capability::Shader); |
| 447 | DefineCommonTypes(program.info); | 452 | DefineCommonTypes(program.info); |
| 448 | DefineCommonConstants(); | 453 | DefineCommonConstants(); |
| @@ -450,12 +455,12 @@ EmitContext::EmitContext(const Profile& profile_, IR::Program& program, u32& bin | |||
| 450 | DefineLocalMemory(program); | 455 | DefineLocalMemory(program); |
| 451 | DefineSharedMemory(program); | 456 | DefineSharedMemory(program); |
| 452 | DefineSharedMemoryFunctions(program); | 457 | DefineSharedMemoryFunctions(program); |
| 453 | DefineConstantBuffers(program.info, binding); | 458 | DefineConstantBuffers(program.info, uniform_binding); |
| 454 | DefineStorageBuffers(program.info, binding); | 459 | DefineStorageBuffers(program.info, storage_binding); |
| 455 | DefineTextureBuffers(program.info, binding); | 460 | DefineTextureBuffers(program.info, texture_binding); |
| 456 | DefineImageBuffers(program.info, binding); | 461 | DefineImageBuffers(program.info, image_binding); |
| 457 | DefineTextures(program.info, binding); | 462 | DefineTextures(program.info, texture_binding); |
| 458 | DefineImages(program.info, binding); | 463 | DefineImages(program.info, image_binding); |
| 459 | DefineAttributeMemAccess(program.info); | 464 | DefineAttributeMemAccess(program.info); |
| 460 | DefineGlobalMemoryFunctions(program.info); | 465 | DefineGlobalMemoryFunctions(program.info); |
| 461 | DefineLabels(program); | 466 | DefineLabels(program); |
| @@ -489,6 +494,20 @@ Id EmitContext::Def(const IR::Value& value) { | |||
| 489 | } | 494 | } |
| 490 | } | 495 | } |
| 491 | 496 | ||
| 497 | Id EmitContext::BitOffset8(const IR::Value& offset) { | ||
| 498 | if (offset.IsImmediate()) { | ||
| 499 | return Const((offset.U32() % 4) * 8); | ||
| 500 | } | ||
| 501 | return OpBitwiseAnd(U32[1], OpShiftLeftLogical(U32[1], Def(offset), Const(3u)), Const(24u)); | ||
| 502 | } | ||
| 503 | |||
| 504 | Id EmitContext::BitOffset16(const IR::Value& offset) { | ||
| 505 | if (offset.IsImmediate()) { | ||
| 506 | return Const(((offset.U32() / 2) % 2) * 16); | ||
| 507 | } | ||
| 508 | return OpBitwiseAnd(U32[1], OpShiftLeftLogical(U32[1], Def(offset), Const(3u)), Const(16u)); | ||
| 509 | } | ||
| 510 | |||
| 492 | void EmitContext::DefineCommonTypes(const Info& info) { | 511 | void EmitContext::DefineCommonTypes(const Info& info) { |
| 493 | void_id = TypeVoid(); | 512 | void_id = TypeVoid(); |
| 494 | 513 | ||
| @@ -496,6 +515,7 @@ void EmitContext::DefineCommonTypes(const Info& info) { | |||
| 496 | 515 | ||
| 497 | F32.Define(*this, TypeFloat(32), "f32"); | 516 | F32.Define(*this, TypeFloat(32), "f32"); |
| 498 | U32.Define(*this, TypeInt(32, false), "u32"); | 517 | U32.Define(*this, TypeInt(32, false), "u32"); |
| 518 | S32.Define(*this, TypeInt(32, true), "s32"); | ||
| 499 | 519 | ||
| 500 | private_u32 = Name(TypePointer(spv::StorageClass::Private, U32[1]), "private_u32"); | 520 | private_u32 = Name(TypePointer(spv::StorageClass::Private, U32[1]), "private_u32"); |
| 501 | 521 | ||
| @@ -889,28 +909,36 @@ void EmitContext::DefineConstantBuffers(const Info& info, u32& binding) { | |||
| 889 | if (info.constant_buffer_descriptors.empty()) { | 909 | if (info.constant_buffer_descriptors.empty()) { |
| 890 | return; | 910 | return; |
| 891 | } | 911 | } |
| 892 | if (True(info.used_constant_buffer_types & IR::Type::U8)) { | 912 | if (profile.support_descriptor_aliasing) { |
| 893 | DefineConstBuffers(*this, info, &UniformDefinitions::U8, binding, U8, 'u', sizeof(u8)); | 913 | if (True(info.used_constant_buffer_types & IR::Type::U8)) { |
| 894 | DefineConstBuffers(*this, info, &UniformDefinitions::S8, binding, S8, 's', sizeof(s8)); | 914 | DefineConstBuffers(*this, info, &UniformDefinitions::U8, binding, U8, 'u', sizeof(u8)); |
| 895 | } | 915 | DefineConstBuffers(*this, info, &UniformDefinitions::S8, binding, S8, 's', sizeof(s8)); |
| 896 | if (True(info.used_constant_buffer_types & IR::Type::U16)) { | 916 | } |
| 897 | DefineConstBuffers(*this, info, &UniformDefinitions::U16, binding, U16, 'u', sizeof(u16)); | 917 | if (True(info.used_constant_buffer_types & IR::Type::U16)) { |
| 898 | DefineConstBuffers(*this, info, &UniformDefinitions::S16, binding, S16, 's', sizeof(s16)); | 918 | DefineConstBuffers(*this, info, &UniformDefinitions::U16, binding, U16, 'u', |
| 899 | } | 919 | sizeof(u16)); |
| 900 | if (True(info.used_constant_buffer_types & IR::Type::U32)) { | 920 | DefineConstBuffers(*this, info, &UniformDefinitions::S16, binding, S16, 's', |
| 901 | DefineConstBuffers(*this, info, &UniformDefinitions::U32, binding, U32[1], 'u', | 921 | sizeof(s16)); |
| 902 | sizeof(u32)); | 922 | } |
| 903 | } | 923 | if (True(info.used_constant_buffer_types & IR::Type::U32)) { |
| 904 | if (True(info.used_constant_buffer_types & IR::Type::F32)) { | 924 | DefineConstBuffers(*this, info, &UniformDefinitions::U32, binding, U32[1], 'u', |
| 905 | DefineConstBuffers(*this, info, &UniformDefinitions::F32, binding, F32[1], 'f', | 925 | sizeof(u32)); |
| 906 | sizeof(f32)); | 926 | } |
| 907 | } | 927 | if (True(info.used_constant_buffer_types & IR::Type::F32)) { |
| 908 | if (True(info.used_constant_buffer_types & IR::Type::U32x2)) { | 928 | DefineConstBuffers(*this, info, &UniformDefinitions::F32, binding, F32[1], 'f', |
| 909 | DefineConstBuffers(*this, info, &UniformDefinitions::U32x2, binding, U32[2], 'u', | 929 | sizeof(f32)); |
| 910 | sizeof(u32[2])); | 930 | } |
| 911 | } | 931 | if (True(info.used_constant_buffer_types & IR::Type::U32x2)) { |
| 912 | for (const ConstantBufferDescriptor& desc : info.constant_buffer_descriptors) { | 932 | DefineConstBuffers(*this, info, &UniformDefinitions::U32x2, binding, U32[2], 'u', |
| 913 | binding += desc.count; | 933 | sizeof(u32[2])); |
| 934 | } | ||
| 935 | binding += static_cast<u32>(info.constant_buffer_descriptors.size()); | ||
| 936 | } else { | ||
| 937 | DefineConstBuffers(*this, info, &UniformDefinitions::U32x4, binding, U32[4], 'u', | ||
| 938 | sizeof(u32[4])); | ||
| 939 | for (const ConstantBufferDescriptor& desc : info.constant_buffer_descriptors) { | ||
| 940 | binding += desc.count; | ||
| 941 | } | ||
| 914 | } | 942 | } |
| 915 | } | 943 | } |
| 916 | 944 | ||
| @@ -920,35 +948,37 @@ void EmitContext::DefineStorageBuffers(const Info& info, u32& binding) { | |||
| 920 | } | 948 | } |
| 921 | AddExtension("SPV_KHR_storage_buffer_storage_class"); | 949 | AddExtension("SPV_KHR_storage_buffer_storage_class"); |
| 922 | 950 | ||
| 923 | if (True(info.used_storage_buffer_types & IR::Type::U8)) { | 951 | const IR::Type used_types{profile.support_descriptor_aliasing ? info.used_storage_buffer_types |
| 952 | : IR::Type::U32}; | ||
| 953 | if (True(used_types & IR::Type::U8)) { | ||
| 924 | DefineSsbos(*this, storage_types.U8, &StorageDefinitions::U8, info, binding, U8, | 954 | DefineSsbos(*this, storage_types.U8, &StorageDefinitions::U8, info, binding, U8, |
| 925 | sizeof(u8)); | 955 | sizeof(u8)); |
| 926 | DefineSsbos(*this, storage_types.S8, &StorageDefinitions::S8, info, binding, S8, | 956 | DefineSsbos(*this, storage_types.S8, &StorageDefinitions::S8, info, binding, S8, |
| 927 | sizeof(u8)); | 957 | sizeof(u8)); |
| 928 | } | 958 | } |
| 929 | if (True(info.used_storage_buffer_types & IR::Type::U16)) { | 959 | if (True(used_types & IR::Type::U16)) { |
| 930 | DefineSsbos(*this, storage_types.U16, &StorageDefinitions::U16, info, binding, U16, | 960 | DefineSsbos(*this, storage_types.U16, &StorageDefinitions::U16, info, binding, U16, |
| 931 | sizeof(u16)); | 961 | sizeof(u16)); |
| 932 | DefineSsbos(*this, storage_types.S16, &StorageDefinitions::S16, info, binding, S16, | 962 | DefineSsbos(*this, storage_types.S16, &StorageDefinitions::S16, info, binding, S16, |
| 933 | sizeof(u16)); | 963 | sizeof(u16)); |
| 934 | } | 964 | } |
| 935 | if (True(info.used_storage_buffer_types & IR::Type::U32)) { | 965 | if (True(used_types & IR::Type::U32)) { |
| 936 | DefineSsbos(*this, storage_types.U32, &StorageDefinitions::U32, info, binding, U32[1], | 966 | DefineSsbos(*this, storage_types.U32, &StorageDefinitions::U32, info, binding, U32[1], |
| 937 | sizeof(u32)); | 967 | sizeof(u32)); |
| 938 | } | 968 | } |
| 939 | if (True(info.used_storage_buffer_types & IR::Type::F32)) { | 969 | if (True(used_types & IR::Type::F32)) { |
| 940 | DefineSsbos(*this, storage_types.F32, &StorageDefinitions::F32, info, binding, F32[1], | 970 | DefineSsbos(*this, storage_types.F32, &StorageDefinitions::F32, info, binding, F32[1], |
| 941 | sizeof(f32)); | 971 | sizeof(f32)); |
| 942 | } | 972 | } |
| 943 | if (True(info.used_storage_buffer_types & IR::Type::U64)) { | 973 | if (True(used_types & IR::Type::U64)) { |
| 944 | DefineSsbos(*this, storage_types.U64, &StorageDefinitions::U64, info, binding, U64, | 974 | DefineSsbos(*this, storage_types.U64, &StorageDefinitions::U64, info, binding, U64, |
| 945 | sizeof(u64)); | 975 | sizeof(u64)); |
| 946 | } | 976 | } |
| 947 | if (True(info.used_storage_buffer_types & IR::Type::U32x2)) { | 977 | if (True(used_types & IR::Type::U32x2)) { |
| 948 | DefineSsbos(*this, storage_types.U32x2, &StorageDefinitions::U32x2, info, binding, U32[2], | 978 | DefineSsbos(*this, storage_types.U32x2, &StorageDefinitions::U32x2, info, binding, U32[2], |
| 949 | sizeof(u32[2])); | 979 | sizeof(u32[2])); |
| 950 | } | 980 | } |
| 951 | if (True(info.used_storage_buffer_types & IR::Type::U32x4)) { | 981 | if (True(used_types & IR::Type::U32x4)) { |
| 952 | DefineSsbos(*this, storage_types.U32x4, &StorageDefinitions::U32x4, info, binding, U32[4], | 982 | DefineSsbos(*this, storage_types.U32x4, &StorageDefinitions::U32x4, info, binding, U32[4], |
| 953 | sizeof(u32[4])); | 983 | sizeof(u32[4])); |
| 954 | } | 984 | } |