This adds all of the information used by the spirv backend to declare descriptor variables. Most of these are added to the internal vkd3d_shader_scan_descriptor_info1 structure, but patch 5/5 adds a flag to enum vkd3d_shader_descriptor_info_flag, which is public API.
The ultimate goal here is to declare SPIR-V descriptor variables from the scanned descriptor information, thereby avoiding the need to synthesize DCL instructions for frontends that don't have them (specifically sm1, but it may be that sm6 would benefit from this as well).
That work is visible here:
https://gitlab.winehq.org/zfigura/vkd3d/-/tree/himavant5
--
This is a follow-up to the already-approved 295, which I am submitting now so that we're not blocked on Alexandre's vacation.
-- v2: vkd3d-shader: Add a flag marking raw buffers to struct vkd3d_shader_descriptor_info. vkd3d-shader: Add structure stride to struct vkd3d_shader_descriptor_info1. vkd3d-shader: Add constant buffer size to struct vkd3d_shader_descriptor_info1. vkd3d-shader: Add sample count to struct vkd3d_shader_descriptor_info1. vkd3d-shader: Set descriptor flags in the caller to vkd3d_shader_scan_add_descriptor().
From: Zebediah Figura zfigura@codeweavers.com
Return the vkd3d_shader_descriptor_info1 from that function. --- libs/vkd3d-shader/vkd3d_shader_main.c | 27 +++++++++++++-------------- 1 file changed, 13 insertions(+), 14 deletions(-)
diff --git a/libs/vkd3d-shader/vkd3d_shader_main.c b/libs/vkd3d-shader/vkd3d_shader_main.c index 3a2432c1..00694d09 100644 --- a/libs/vkd3d-shader/vkd3d_shader_main.c +++ b/libs/vkd3d-shader/vkd3d_shader_main.c @@ -755,10 +755,10 @@ static void vkd3d_shader_scan_record_uav_atomic_op(struct vkd3d_shader_scan_cont vkd3d_shader_scan_add_uav_flag(context, reg, VKD3D_SHADER_DESCRIPTOR_INFO_FLAG_UAV_ATOMICS); }
-static bool vkd3d_shader_scan_add_descriptor(struct vkd3d_shader_scan_context *context, +static struct vkd3d_shader_descriptor_info1 *vkd3d_shader_scan_add_descriptor(struct vkd3d_shader_scan_context *context, enum vkd3d_shader_descriptor_type type, const struct vkd3d_shader_register *reg, const struct vkd3d_shader_register_range *range, enum vkd3d_shader_resource_type resource_type, - enum vkd3d_shader_resource_data_type resource_data_type, unsigned int flags) + enum vkd3d_shader_resource_data_type resource_data_type) { struct vkd3d_shader_scan_descriptor_info1 *info = context->scan_descriptor_info; struct vkd3d_shader_descriptor_info1 *d; @@ -767,7 +767,7 @@ static bool vkd3d_shader_scan_add_descriptor(struct vkd3d_shader_scan_context *c info->descriptor_count + 1, sizeof(*info->descriptors))) { ERR("Failed to allocate descriptor info.\n"); - return false; + return NULL; }
d = &info->descriptors[info->descriptor_count]; @@ -777,11 +777,10 @@ static bool vkd3d_shader_scan_add_descriptor(struct vkd3d_shader_scan_context *c d->register_index = range->first; d->resource_type = resource_type; d->resource_data_type = resource_data_type; - d->flags = flags; d->count = (range->last == ~0u) ? ~0u : range->last - range->first + 1; ++info->descriptor_count;
- return true; + return d; }
static void vkd3d_shader_scan_constant_buffer_declaration(struct vkd3d_shader_scan_context *context, @@ -793,24 +792,24 @@ static void vkd3d_shader_scan_constant_buffer_declaration(struct vkd3d_shader_sc return;
vkd3d_shader_scan_add_descriptor(context, VKD3D_SHADER_DESCRIPTOR_TYPE_CBV, &cb->src.reg, &cb->range, - VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0); + VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT); }
static void vkd3d_shader_scan_sampler_declaration(struct vkd3d_shader_scan_context *context, const struct vkd3d_shader_instruction *instruction) { const struct vkd3d_shader_sampler *sampler = &instruction->declaration.sampler; - unsigned int flags; + struct vkd3d_shader_descriptor_info1 *d;
if (!context->scan_descriptor_info) return;
+ if (!(d = vkd3d_shader_scan_add_descriptor(context, VKD3D_SHADER_DESCRIPTOR_TYPE_SAMPLER, + &sampler->src.reg, &sampler->range, VKD3D_SHADER_RESOURCE_NONE, VKD3D_SHADER_RESOURCE_DATA_UINT))) + return; + if (instruction->flags & VKD3DSI_SAMPLER_COMPARISON_MODE) - flags = VKD3D_SHADER_DESCRIPTOR_INFO_FLAG_SAMPLER_COMPARISON_MODE; - else - flags = 0; - vkd3d_shader_scan_add_descriptor(context, VKD3D_SHADER_DESCRIPTOR_TYPE_SAMPLER, &sampler->src.reg, &sampler->range, - VKD3D_SHADER_RESOURCE_NONE, VKD3D_SHADER_RESOURCE_DATA_UINT, flags); + d->flags |= VKD3D_SHADER_DESCRIPTOR_INFO_FLAG_SAMPLER_COMPARISON_MODE; }
static void vkd3d_shader_scan_resource_declaration(struct vkd3d_shader_scan_context *context, @@ -827,7 +826,7 @@ static void vkd3d_shader_scan_resource_declaration(struct vkd3d_shader_scan_cont else type = VKD3D_SHADER_DESCRIPTOR_TYPE_SRV; vkd3d_shader_scan_add_descriptor(context, type, &resource->reg.reg, &resource->range, - resource_type, resource_data_type, 0); + resource_type, resource_data_type); }
static void vkd3d_shader_scan_typed_resource_declaration(struct vkd3d_shader_scan_context *context, @@ -1155,7 +1154,7 @@ static int scan_with_parser(const struct vkd3d_shader_compile_info *compile_info
if (parser->shader_desc.flat_constant_count[i].external) vkd3d_shader_scan_add_descriptor(&context, VKD3D_SHADER_DESCRIPTOR_TYPE_CBV, ®, - &range, VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0); + &range, VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT); }
if (!ret && signature_info)
From: Zebediah Figura zfigura@codeweavers.com
--- libs/vkd3d-shader/vkd3d_shader_main.c | 15 +++++++++------ libs/vkd3d-shader/vkd3d_shader_private.h | 1 + 2 files changed, 10 insertions(+), 6 deletions(-)
diff --git a/libs/vkd3d-shader/vkd3d_shader_main.c b/libs/vkd3d-shader/vkd3d_shader_main.c index 00694d09..dbf49053 100644 --- a/libs/vkd3d-shader/vkd3d_shader_main.c +++ b/libs/vkd3d-shader/vkd3d_shader_main.c @@ -814,8 +814,9 @@ static void vkd3d_shader_scan_sampler_declaration(struct vkd3d_shader_scan_conte
static void vkd3d_shader_scan_resource_declaration(struct vkd3d_shader_scan_context *context, const struct vkd3d_shader_resource *resource, enum vkd3d_shader_resource_type resource_type, - enum vkd3d_shader_resource_data_type resource_data_type) + enum vkd3d_shader_resource_data_type resource_data_type, unsigned int sample_count) { + struct vkd3d_shader_descriptor_info1 *d; enum vkd3d_shader_descriptor_type type;
if (!context->scan_descriptor_info) @@ -825,8 +826,10 @@ static void vkd3d_shader_scan_resource_declaration(struct vkd3d_shader_scan_cont type = VKD3D_SHADER_DESCRIPTOR_TYPE_UAV; else type = VKD3D_SHADER_DESCRIPTOR_TYPE_SRV; - vkd3d_shader_scan_add_descriptor(context, type, &resource->reg.reg, &resource->range, - resource_type, resource_data_type); + if (!(d = vkd3d_shader_scan_add_descriptor(context, type, &resource->reg.reg, + &resource->range, resource_type, resource_data_type))) + return; + d->sample_count = sample_count; }
static void vkd3d_shader_scan_typed_resource_declaration(struct vkd3d_shader_scan_context *context, @@ -885,7 +888,7 @@ static void vkd3d_shader_scan_typed_resource_declaration(struct vkd3d_shader_sca }
vkd3d_shader_scan_resource_declaration(context, &semantic->resource, - semantic->resource_type, resource_data_type); + semantic->resource_type, resource_data_type, semantic->sample_count); }
static void vkd3d_shader_scan_error(struct vkd3d_shader_scan_context *context, @@ -919,12 +922,12 @@ static int vkd3d_shader_scan_instruction(struct vkd3d_shader_scan_context *conte case VKD3DSIH_DCL_RESOURCE_RAW: case VKD3DSIH_DCL_UAV_RAW: vkd3d_shader_scan_resource_declaration(context, &instruction->declaration.raw_resource.resource, - VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT); + VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0); break; case VKD3DSIH_DCL_RESOURCE_STRUCTURED: case VKD3DSIH_DCL_UAV_STRUCTURED: vkd3d_shader_scan_resource_declaration(context, &instruction->declaration.structured_resource.resource, - VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT); + VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0); break; case VKD3DSIH_IF: cf_info = vkd3d_shader_scan_push_cf_info(context); diff --git a/libs/vkd3d-shader/vkd3d_shader_private.h b/libs/vkd3d-shader/vkd3d_shader_private.h index c719085e..89bc0ece 100644 --- a/libs/vkd3d-shader/vkd3d_shader_private.h +++ b/libs/vkd3d-shader/vkd3d_shader_private.h @@ -1122,6 +1122,7 @@ struct vkd3d_shader_descriptor_info1 enum vkd3d_shader_resource_type resource_type; enum vkd3d_shader_resource_data_type resource_data_type; unsigned int flags; + unsigned int sample_count; unsigned int count; };
From: Zebediah Figura zfigura@codeweavers.com
--- libs/vkd3d-shader/vkd3d_shader_main.c | 16 ++++++++++++---- libs/vkd3d-shader/vkd3d_shader_private.h | 1 + 2 files changed, 13 insertions(+), 4 deletions(-)
diff --git a/libs/vkd3d-shader/vkd3d_shader_main.c b/libs/vkd3d-shader/vkd3d_shader_main.c index dbf49053..bb60085e 100644 --- a/libs/vkd3d-shader/vkd3d_shader_main.c +++ b/libs/vkd3d-shader/vkd3d_shader_main.c @@ -787,12 +787,15 @@ static void vkd3d_shader_scan_constant_buffer_declaration(struct vkd3d_shader_sc const struct vkd3d_shader_instruction *instruction) { const struct vkd3d_shader_constant_buffer *cb = &instruction->declaration.cb; + struct vkd3d_shader_descriptor_info1 *d;
if (!context->scan_descriptor_info) return;
- vkd3d_shader_scan_add_descriptor(context, VKD3D_SHADER_DESCRIPTOR_TYPE_CBV, &cb->src.reg, &cb->range, - VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT); + if (!(d = vkd3d_shader_scan_add_descriptor(context, VKD3D_SHADER_DESCRIPTOR_TYPE_CBV, + &cb->src.reg, &cb->range, VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT))) + return; + d->buffer_size = cb->size * 16; }
static void vkd3d_shader_scan_sampler_declaration(struct vkd3d_shader_scan_context *context, @@ -1152,12 +1155,17 @@ static int scan_with_parser(const struct vkd3d_shader_compile_info *compile_info
for (i = 0; i < ARRAY_SIZE(parser->shader_desc.flat_constant_count); ++i) { + unsigned int size = parser->shader_desc.flat_constant_count[i].external; struct vkd3d_shader_register_range range = {.space = 0, .first = i, .last = i}; struct vkd3d_shader_register reg = {.idx[0].offset = i, .idx_count = 1}; + struct vkd3d_shader_descriptor_info1 *d;
if (parser->shader_desc.flat_constant_count[i].external) - vkd3d_shader_scan_add_descriptor(&context, VKD3D_SHADER_DESCRIPTOR_TYPE_CBV, ®, - &range, VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT); + { + if ((d = vkd3d_shader_scan_add_descriptor(&context, VKD3D_SHADER_DESCRIPTOR_TYPE_CBV, ®, + &range, VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT))) + d->buffer_size = size * 16; + } }
if (!ret && signature_info) diff --git a/libs/vkd3d-shader/vkd3d_shader_private.h b/libs/vkd3d-shader/vkd3d_shader_private.h index 89bc0ece..04aba20d 100644 --- a/libs/vkd3d-shader/vkd3d_shader_private.h +++ b/libs/vkd3d-shader/vkd3d_shader_private.h @@ -1123,6 +1123,7 @@ struct vkd3d_shader_descriptor_info1 enum vkd3d_shader_resource_data_type resource_data_type; unsigned int flags; unsigned int sample_count; + unsigned int buffer_size; unsigned int count; };
From: Zebediah Figura zfigura@codeweavers.com
--- libs/vkd3d-shader/vkd3d_shader_main.c | 11 +++++++---- libs/vkd3d-shader/vkd3d_shader_private.h | 1 + 2 files changed, 8 insertions(+), 4 deletions(-)
diff --git a/libs/vkd3d-shader/vkd3d_shader_main.c b/libs/vkd3d-shader/vkd3d_shader_main.c index bb60085e..7c46590c 100644 --- a/libs/vkd3d-shader/vkd3d_shader_main.c +++ b/libs/vkd3d-shader/vkd3d_shader_main.c @@ -817,7 +817,8 @@ static void vkd3d_shader_scan_sampler_declaration(struct vkd3d_shader_scan_conte
static void vkd3d_shader_scan_resource_declaration(struct vkd3d_shader_scan_context *context, const struct vkd3d_shader_resource *resource, enum vkd3d_shader_resource_type resource_type, - enum vkd3d_shader_resource_data_type resource_data_type, unsigned int sample_count) + enum vkd3d_shader_resource_data_type resource_data_type, + unsigned int sample_count, unsigned int structure_stride) { struct vkd3d_shader_descriptor_info1 *d; enum vkd3d_shader_descriptor_type type; @@ -833,6 +834,7 @@ static void vkd3d_shader_scan_resource_declaration(struct vkd3d_shader_scan_cont &resource->range, resource_type, resource_data_type))) return; d->sample_count = sample_count; + d->structure_stride = structure_stride; }
static void vkd3d_shader_scan_typed_resource_declaration(struct vkd3d_shader_scan_context *context, @@ -891,7 +893,7 @@ static void vkd3d_shader_scan_typed_resource_declaration(struct vkd3d_shader_sca }
vkd3d_shader_scan_resource_declaration(context, &semantic->resource, - semantic->resource_type, resource_data_type, semantic->sample_count); + semantic->resource_type, resource_data_type, semantic->sample_count, 0); }
static void vkd3d_shader_scan_error(struct vkd3d_shader_scan_context *context, @@ -925,12 +927,13 @@ static int vkd3d_shader_scan_instruction(struct vkd3d_shader_scan_context *conte case VKD3DSIH_DCL_RESOURCE_RAW: case VKD3DSIH_DCL_UAV_RAW: vkd3d_shader_scan_resource_declaration(context, &instruction->declaration.raw_resource.resource, - VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0); + VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0, 0); break; case VKD3DSIH_DCL_RESOURCE_STRUCTURED: case VKD3DSIH_DCL_UAV_STRUCTURED: vkd3d_shader_scan_resource_declaration(context, &instruction->declaration.structured_resource.resource, - VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0); + VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0, + instruction->declaration.structured_resource.byte_stride); break; case VKD3DSIH_IF: cf_info = vkd3d_shader_scan_push_cf_info(context); diff --git a/libs/vkd3d-shader/vkd3d_shader_private.h b/libs/vkd3d-shader/vkd3d_shader_private.h index 04aba20d..bf925a44 100644 --- a/libs/vkd3d-shader/vkd3d_shader_private.h +++ b/libs/vkd3d-shader/vkd3d_shader_private.h @@ -1124,6 +1124,7 @@ struct vkd3d_shader_descriptor_info1 unsigned int flags; unsigned int sample_count; unsigned int buffer_size; + unsigned int structure_stride; unsigned int count; };
From: Zebediah Figura zfigura@codeweavers.com
--- include/vkd3d_shader.h | 2 ++ libs/vkd3d-shader/vkd3d_shader_main.c | 10 ++++++---- 2 files changed, 8 insertions(+), 4 deletions(-)
diff --git a/include/vkd3d_shader.h b/include/vkd3d_shader.h index e98aad4f..cfe54dbf 100644 --- a/include/vkd3d_shader.h +++ b/include/vkd3d_shader.h @@ -1339,6 +1339,8 @@ enum vkd3d_shader_descriptor_info_flag /** The descriptor is a UAV resource, on which the shader performs * atomic ops. \since 1.6 */ VKD3D_SHADER_DESCRIPTOR_INFO_FLAG_UAV_ATOMICS = 0x00000008, + /** The descriptor is a raw (byte-addressed) buffer. \since 1.9 */ + VKD3D_SHADER_DESCRIPTOR_INFO_FLAG_RAW_BUFFER = 0x00000010,
VKD3D_FORCE_32_BIT_ENUM(VKD3D_SHADER_DESCRIPTOR_INFO_FLAG), }; diff --git a/libs/vkd3d-shader/vkd3d_shader_main.c b/libs/vkd3d-shader/vkd3d_shader_main.c index 7c46590c..e31ab42c 100644 --- a/libs/vkd3d-shader/vkd3d_shader_main.c +++ b/libs/vkd3d-shader/vkd3d_shader_main.c @@ -818,7 +818,7 @@ static void vkd3d_shader_scan_sampler_declaration(struct vkd3d_shader_scan_conte static void vkd3d_shader_scan_resource_declaration(struct vkd3d_shader_scan_context *context, const struct vkd3d_shader_resource *resource, enum vkd3d_shader_resource_type resource_type, enum vkd3d_shader_resource_data_type resource_data_type, - unsigned int sample_count, unsigned int structure_stride) + unsigned int sample_count, unsigned int structure_stride, bool raw) { struct vkd3d_shader_descriptor_info1 *d; enum vkd3d_shader_descriptor_type type; @@ -835,6 +835,8 @@ static void vkd3d_shader_scan_resource_declaration(struct vkd3d_shader_scan_cont return; d->sample_count = sample_count; d->structure_stride = structure_stride; + if (raw) + d->flags |= VKD3D_SHADER_DESCRIPTOR_INFO_FLAG_RAW_BUFFER; }
static void vkd3d_shader_scan_typed_resource_declaration(struct vkd3d_shader_scan_context *context, @@ -893,7 +895,7 @@ static void vkd3d_shader_scan_typed_resource_declaration(struct vkd3d_shader_sca }
vkd3d_shader_scan_resource_declaration(context, &semantic->resource, - semantic->resource_type, resource_data_type, semantic->sample_count, 0); + semantic->resource_type, resource_data_type, semantic->sample_count, 0, false); }
static void vkd3d_shader_scan_error(struct vkd3d_shader_scan_context *context, @@ -927,13 +929,13 @@ static int vkd3d_shader_scan_instruction(struct vkd3d_shader_scan_context *conte case VKD3DSIH_DCL_RESOURCE_RAW: case VKD3DSIH_DCL_UAV_RAW: vkd3d_shader_scan_resource_declaration(context, &instruction->declaration.raw_resource.resource, - VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0, 0); + VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0, 0, true); break; case VKD3DSIH_DCL_RESOURCE_STRUCTURED: case VKD3DSIH_DCL_UAV_STRUCTURED: vkd3d_shader_scan_resource_declaration(context, &instruction->declaration.structured_resource.resource, VKD3D_SHADER_RESOURCE_BUFFER, VKD3D_SHADER_RESOURCE_DATA_UINT, 0, - instruction->declaration.structured_resource.byte_stride); + instruction->declaration.structured_resource.byte_stride, false); break; case VKD3DSIH_IF: cf_info = vkd3d_shader_scan_push_cf_info(context);
@@ -777,11 +777,10 @@ static bool vkd3d_shader_scan_add_descriptor(struct vkd3d_shader_scan_context *c d->register_index = range->first; d->resource_type = resource_type; d->resource_data_type = resource_data_type; - d->flags = flags; d->count = (range->last == ~0u) ? ~0u : range->last - range->first + 1; ++info->descriptor_count; - return true; + return d; } static void vkd3d_shader_scan_constant_buffer_declaration(struct vkd3d_shader_scan_context *context,
You can't quite do that like this though. As it is, this leaves d->flags uninitialised. We either need to initialise it in vkd3d_shader_scan_add_descriptor(), or in each of the callers. That's an issue in the later patches in this MR as well, and for me at least the tests catch it.