Conor McCarthy : vkd3d-shader/spirv: Implement support for descriptor array offsets.

Alexandre Julliard julliard at winehq.org
Fri Oct 15 15:39:49 CDT 2021


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

Author: Conor McCarthy <cmccarthy at codeweavers.com>
Date:   Fri Oct 15 01:37:43 2021 +0200

vkd3d-shader/spirv: Implement support for descriptor array offsets.

Signed-off-by: Conor McCarthy <cmccarthy 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    | 72 +++++++++++++++++++++++++++++++++++++++++++++--
 libs/vkd3d-shader/spirv.c | 12 +++++++-
 2 files changed, 81 insertions(+), 3 deletions(-)

diff --git a/include/vkd3d_shader.h b/include/vkd3d_shader.h
index 37b5936..3ba84a5 100644
--- a/include/vkd3d_shader.h
+++ b/include/vkd3d_shader.h
@@ -64,6 +64,11 @@ enum vkd3d_shader_structure_type
      * \since 1.3
      */
     VKD3D_SHADER_STRUCTURE_TYPE_PREPROCESS_INFO,
+    /**
+     * The structure is a vkd3d_shader_descriptor_offset_info structure.
+     * \since 1.3
+     */
+    VKD3D_SHADER_STRUCTURE_TYPE_DESCRIPTOR_OFFSET_INFO,
 
     VKD3D_FORCE_32_BIT_ENUM(VKD3D_SHADER_STRUCTURE_TYPE),
 };
@@ -208,8 +213,9 @@ struct vkd3d_shader_descriptor_binding
     /** The binding index of the descriptor. */
     unsigned int binding;
     /**
-     * The size of this descriptor array. Descriptor arrays are not supported in
-     * this version of vkd3d-shader, and therefore this value must be 1.
+     * The size of this descriptor array. If an offset is specified for this
+     * binding by the vkd3d_shader_descriptor_offset_info structure, counting
+     * starts at that offset.
      */
     unsigned int count;
 };
@@ -452,6 +458,68 @@ struct vkd3d_shader_transform_feedback_info
     unsigned int buffer_stride_count;
 };
 
+/**
+ * A chained structure containing descriptor offsets.
+ *
+ * This structure is optional.
+ *
+ * This structure extends vkd3d_shader_interface_info.
+ *
+ * This structure contains only input parameters.
+ *
+ * \since 1.3
+ */
+struct vkd3d_shader_descriptor_offset_info
+{
+    /** Must be set to VKD3D_SHADER_STRUCTURE_TYPE_DESCRIPTOR_OFFSET_INFO. */
+    enum vkd3d_shader_structure_type type;
+    /** Optional pointer to a structure containing further parameters. */
+    const void *next;
+
+    /**
+     * Pointer to an array of offsets into the descriptor arrays referenced by
+     * the 'bindings' array in struct vkd3d_shader_interface_info. This allows
+     * mapping multiple shader resource arrays to a single binding point in
+     * the target environment.
+     *
+     * For example, to map Direct3D constant buffer registers 'cb0[0:3]' and
+     * 'cb1[6:7]' to descriptors 8-12 and 4-5 in the Vulkan descriptor array in
+     * descriptor set 3 and with binding 2, set the following values in the
+     * 'bindings' array in struct vkd3d_shader_interface_info:
+     *
+     * \code
+     * type = VKD3D_SHADER_DESCRIPTOR_TYPE_CBV
+     * register_space = 0
+     * register_index = 0
+     * binding.set = 3
+     * binding.binding = 2
+     * binding.count = 4
+     *
+     * type = VKD3D_SHADER_DESCRIPTOR_TYPE_CBV
+     * register_space = 0
+     * register_index = 6
+     * binding.set = 3
+     * binding.binding = 2
+     * binding.count = 2
+     * \endcode
+     *
+     * and then pass \c {8, \c 4} as \a binding_offsets here.
+     *
+     * This field may be NULL, in which case the corresponding offsets are
+     * specified to be 0.
+     */
+    const unsigned int *binding_offsets;
+
+    /**
+     * Pointer to an array of offsets into the descriptor arrays referenced by
+     * the 'uav_counters' array in struct vkd3d_shader_interface_info. This
+     * works the same way as \ref binding_offsets above. UAV counter arrays are
+     * not supported in this version of vkd3d-shader, and therefore this field
+     * must either be NULL or specify 0 offsets.
+     */
+    const unsigned int *uav_counter_offsets;
+};
+
 /** The format of a shader to be compiled or scanned. */
 enum vkd3d_shader_source_type
 {
diff --git a/libs/vkd3d-shader/spirv.c b/libs/vkd3d-shader/spirv.c
index f9124fc..6cf438d 100644
--- a/libs/vkd3d-shader/spirv.c
+++ b/libs/vkd3d-shader/spirv.c
@@ -2231,6 +2231,7 @@ struct vkd3d_dxbc_compiler
     size_t control_flow_info_size;
 
     struct vkd3d_shader_interface_info shader_interface;
+    struct vkd3d_shader_descriptor_offset_info offset_info;
     struct vkd3d_push_constant_buffer_binding *push_constants;
     const struct vkd3d_shader_spirv_target_info *spirv_target_info;
 
@@ -2292,6 +2293,7 @@ struct vkd3d_dxbc_compiler *vkd3d_dxbc_compiler_create(const struct vkd3d_shader
     const struct vkd3d_shader_signature *patch_constant_signature = &shader_desc->patch_constant_signature;
     const struct vkd3d_shader_signature *output_signature = &shader_desc->output_signature;
     const struct vkd3d_shader_interface_info *shader_interface;
+    const struct vkd3d_shader_descriptor_offset_info *offset_info;
     const struct vkd3d_shader_spirv_target_info *target_info;
     struct vkd3d_dxbc_compiler *compiler;
     unsigned int max_element_count;
@@ -2385,6 +2387,13 @@ struct vkd3d_dxbc_compiler *vkd3d_dxbc_compiler_create(const struct vkd3d_shader
             for (i = 0; i < shader_interface->push_constant_buffer_count; ++i)
                 compiler->push_constants[i].pc = shader_interface->push_constant_buffers[i];
         }
+
+        if ((offset_info = vkd3d_find_struct(shader_interface->next, DESCRIPTOR_OFFSET_INFO)))
+        {
+            compiler->offset_info = *offset_info;
+            if (offset_info->uav_counter_offsets)
+                WARN("Ignoring UAV counter offsets %p.\n", offset_info->uav_counter_offsets);
+        }
     }
 
     compiler->scan_descriptor_info = scan_descriptor_info;
@@ -2546,6 +2555,7 @@ static struct vkd3d_shader_descriptor_binding vkd3d_dxbc_compiler_get_descriptor
 {
     const struct vkd3d_shader_interface_info *shader_interface = &compiler->shader_interface;
     unsigned int register_last = (range->last == ~0u) ? range->first : range->last;
+    const unsigned int *binding_offsets = compiler->offset_info.binding_offsets;
     enum vkd3d_shader_descriptor_type descriptor_type;
     enum vkd3d_shader_binding_flag resource_type_flag;
     struct vkd3d_shader_descriptor_binding binding;
@@ -2626,7 +2636,7 @@ static struct vkd3d_shader_descriptor_binding vkd3d_dxbc_compiler_get_descriptor
                     || current->binding.count <= register_last - current->register_index)
                 continue;
 
-            *binding_base_idx = current->register_index;
+            *binding_base_idx = current->register_index - (binding_offsets ? binding_offsets[i] : 0);
             return current->binding;
         }
         if (shader_interface->binding_count)




More information about the wine-cvs mailing list