=?UTF-8?Q?J=C3=B3zef=20Kucia=20?=: vkd3d-shader: Add support for SPV_EXT_demote_to_helper_invocation.

Alexandre Julliard julliard at winehq.org
Wed Jul 31 13:43:29 CDT 2019


Module: vkd3d
Branch: master
Commit: 077e8b14597d17176850436674b94f4023620db1
URL:    https://source.winehq.org/git/vkd3d.git/?a=commit;h=077e8b14597d17176850436674b94f4023620db1

Author: Józef Kucia <jkucia at codeweavers.com>
Date:   Sat Jul  6 07:36:29 2019 +0200

vkd3d-shader: Add support for SPV_EXT_demote_to_helper_invocation.

Requires SPIRV-Headers commit dcce859e34cf0c23625ec75ac44df750aa2f4d70.

Signed-off-by: Józef Kucia <jkucia at codeweavers.com>
Signed-off-by: Henri Verbeet <hverbeet at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>

---

 include/vkd3d_shader.h    | 12 +++++++++++-
 libs/vkd3d-shader/spirv.c | 42 +++++++++++++++++++++++++++++++++++++++++-
 libs/vkd3d/state.c        |  2 ++
 3 files changed, 54 insertions(+), 2 deletions(-)

diff --git a/include/vkd3d_shader.h b/include/vkd3d_shader.h
index fcf5db8..6b4d3f5 100644
--- a/include/vkd3d_shader.h
+++ b/include/vkd3d_shader.h
@@ -224,6 +224,13 @@ enum vkd3d_shader_target
     VKD3D_FORCE_32_BIT_ENUM(VKD3D_SHADER_TARGET),
 };
 
+enum vkd3d_shader_target_extension
+{
+    VKD3D_SHADER_TARGET_EXTENSION_NONE,
+
+    VKD3D_SHADER_TARGET_EXTENSION_SPV_EXT_DEMOTE_TO_HELPER_INVOCATION,
+};
+
 struct vkd3d_shader_compile_arguments
 {
     enum vkd3d_shader_structure_type type;
@@ -231,8 +238,11 @@ struct vkd3d_shader_compile_arguments
 
     enum vkd3d_shader_target target;
 
+    unsigned int target_extension_count;
+    const enum vkd3d_shader_target_extension *target_extensions;
+
     unsigned int parameter_count;
-    struct vkd3d_shader_parameter *parameters;
+    const struct vkd3d_shader_parameter *parameters;
 
     bool dual_source_blending;
     const unsigned int *output_swizzles;
diff --git a/libs/vkd3d-shader/spirv.c b/libs/vkd3d-shader/spirv.c
index f17c7fa..0fb499e 100644
--- a/libs/vkd3d-shader/spirv.c
+++ b/libs/vkd3d-shader/spirv.c
@@ -266,6 +266,7 @@ struct vkd3d_spirv_builder
 {
     uint64_t capability_mask;
     uint64_t capability_draw_parameters : 1;
+    uint64_t capability_demote_to_helper_invocation : 1;
     uint32_t ext_instr_set_glsl_450;
     SpvExecutionModel execution_model;
 
@@ -311,6 +312,10 @@ static void vkd3d_spirv_enable_capability(struct vkd3d_spirv_builder *builder,
     {
         builder->capability_draw_parameters = 1;
     }
+    else if (cap == SpvCapabilityDemoteToHelperInvocationEXT)
+    {
+        builder->capability_demote_to_helper_invocation = 1;
+    }
     else
     {
         FIXME("Unhandled capability %#x.\n", cap);
@@ -1222,6 +1227,11 @@ static void vkd3d_spirv_build_op_kill(struct vkd3d_spirv_builder *builder)
     vkd3d_spirv_build_op(&builder->function_stream, SpvOpKill);
 }
 
+static void vkd3d_spirv_build_op_demote_to_helper_invocation(struct vkd3d_spirv_builder *builder)
+{
+    vkd3d_spirv_build_op(&builder->function_stream, SpvOpDemoteToHelperInvocationEXT);
+}
+
 static void vkd3d_spirv_build_op_return(struct vkd3d_spirv_builder *builder)
 {
     vkd3d_spirv_build_op(&builder->function_stream, SpvOpReturn);
@@ -1703,10 +1713,14 @@ static bool vkd3d_spirv_compile_module(struct vkd3d_spirv_builder *builder,
     }
     if (builder->capability_draw_parameters)
         vkd3d_spirv_build_op_capability(&stream, SpvCapabilityDrawParameters);
+    if (builder->capability_demote_to_helper_invocation)
+        vkd3d_spirv_build_op_capability(&stream, SpvCapabilityDemoteToHelperInvocationEXT);
 
     /* extensions */
     if (builder->capability_draw_parameters)
         vkd3d_spirv_build_op_extension(&stream, "SPV_KHR_shader_draw_parameters");
+    if (builder->capability_demote_to_helper_invocation)
+        vkd3d_spirv_build_op_extension(&stream, "SPV_EXT_demote_to_helper_invocation");
 
     if (builder->ext_instr_set_glsl_450)
         vkd3d_spirv_build_op_ext_inst_import(&stream, builder->ext_instr_set_glsl_450, "GLSL.std.450");
@@ -2148,6 +2162,21 @@ static bool vkd3d_dxbc_compiler_is_opengl_target(const struct vkd3d_dxbc_compile
     return vkd3d_dxbc_compiler_get_target(compiler) == VKD3D_SHADER_TARGET_SPIRV_OPENGL_4_5;
 }
 
+static bool vkd3d_dxbc_compiler_is_target_extension_supported(const struct vkd3d_dxbc_compiler *compiler,
+        enum vkd3d_shader_target_extension extension)
+{
+    const struct vkd3d_shader_compile_arguments *args = compiler->compile_args;
+    unsigned int i;
+
+    for (i = 0; args && i < args->target_extension_count; ++i)
+    {
+        if (args->target_extensions[i] == extension)
+            return true;
+    }
+
+    return false;
+}
+
 static bool vkd3d_dxbc_compiler_check_shader_visibility(const struct vkd3d_dxbc_compiler *compiler,
         enum vkd3d_shader_visibility visibility)
 {
@@ -6477,7 +6506,18 @@ static void vkd3d_dxbc_compiler_emit_kill(struct vkd3d_dxbc_compiler *compiler,
     merge_block_id = vkd3d_dxbc_compiler_emit_conditional_branch(compiler, instruction, target_id);
 
     vkd3d_spirv_build_op_label(builder, target_id);
-    vkd3d_spirv_build_op_kill(builder);
+
+    if (vkd3d_dxbc_compiler_is_target_extension_supported(compiler,
+            VKD3D_SHADER_TARGET_EXTENSION_SPV_EXT_DEMOTE_TO_HELPER_INVOCATION))
+    {
+        vkd3d_spirv_build_op_demote_to_helper_invocation(builder);
+        vkd3d_spirv_build_op_branch(builder, merge_block_id);
+    }
+    else
+    {
+        vkd3d_spirv_build_op_kill(builder);
+    }
+
     vkd3d_spirv_build_op_label(builder, merge_block_id);
 }
 
diff --git a/libs/vkd3d/state.c b/libs/vkd3d/state.c
index 7946680..26d4a7a 100644
--- a/libs/vkd3d/state.c
+++ b/libs/vkd3d/state.c
@@ -2254,6 +2254,8 @@ static HRESULT d3d12_pipeline_state_init_graphics(struct d3d12_pipeline_state *s
     ps_compile_args.type = VKD3D_SHADER_STRUCTURE_TYPE_COMPILE_ARGUMENTS;
     ps_compile_args.next = NULL;
     ps_compile_args.target = VKD3D_SHADER_TARGET_SPIRV_VULKAN_1_0;
+    ps_compile_args.target_extension_count = 0;
+    ps_compile_args.target_extensions = NULL;
     ps_compile_args.parameter_count = ARRAY_SIZE(ps_shader_parameters);
     ps_compile_args.parameters = ps_shader_parameters;
     ps_compile_args.dual_source_blending = is_dual_source_blending(&desc->BlendState.RenderTarget[0]);




More information about the wine-cvs mailing list