Module: vkd3d Branch: master Commit: 4aaf6b88951903d96cccc1bbb63ce3bb80e15e7d URL: https://gitlab.winehq.org/wine/vkd3d/-/commit/4aaf6b88951903d96cccc1bbb63ce3...
Author: Francisco Casas fcasas@codeweavers.com Date: Fri Mar 10 17:23:49 2023 -0300
vkd3d-shader/hlsl: Use hlsl_ir_index for resource access.
This patch makes index expressions on resources hlsl_ir_index nodes instead of hlsl_ir_resource_load nodes, because it is not known if they will be used later as the lhs of an hlsl_ir_resource_store.
For now, the only benefit is consistency.
---
libs/vkd3d-shader/hlsl.c | 5 +++++ libs/vkd3d-shader/hlsl.h | 1 + libs/vkd3d-shader/hlsl.y | 42 ++++++++++++++++++++++------------------ libs/vkd3d-shader/hlsl_codegen.c | 20 ++++++++++++++++++- 4 files changed, 48 insertions(+), 20 deletions(-)
diff --git a/libs/vkd3d-shader/hlsl.c b/libs/vkd3d-shader/hlsl.c index 51da0510..9de37a93 100644 --- a/libs/vkd3d-shader/hlsl.c +++ b/libs/vkd3d-shader/hlsl.c @@ -1369,6 +1369,11 @@ bool hlsl_index_is_noncontiguous(struct hlsl_ir_index *index) return type->class == HLSL_CLASS_MATRIX && !hlsl_type_is_row_major(type); }
+bool hlsl_index_is_resource_access(struct hlsl_ir_index *index) +{ + return index->val.node->data_type->class == HLSL_CLASS_OBJECT; +} + struct hlsl_ir_node *hlsl_new_index(struct hlsl_ctx *ctx, struct hlsl_ir_node *val, struct hlsl_ir_node *idx, const struct vkd3d_shader_location *loc) { diff --git a/libs/vkd3d-shader/hlsl.h b/libs/vkd3d-shader/hlsl.h index b15950f4..45c17717 100644 --- a/libs/vkd3d-shader/hlsl.h +++ b/libs/vkd3d-shader/hlsl.h @@ -1106,6 +1106,7 @@ struct hlsl_ir_store *hlsl_new_store_component(struct hlsl_ctx *ctx, struct hlsl const struct hlsl_deref *lhs, unsigned int comp, struct hlsl_ir_node *rhs);
bool hlsl_index_is_noncontiguous(struct hlsl_ir_index *index); +bool hlsl_index_is_resource_access(struct hlsl_ir_index *index);
struct hlsl_ir_node *hlsl_new_index(struct hlsl_ctx *ctx, struct hlsl_ir_node *val, struct hlsl_ir_node *idx, const struct vkd3d_shader_location *loc); diff --git a/libs/vkd3d-shader/hlsl.y b/libs/vkd3d-shader/hlsl.y index 1ce65e84..a5814c0a 100644 --- a/libs/vkd3d-shader/hlsl.y +++ b/libs/vkd3d-shader/hlsl.y @@ -755,9 +755,7 @@ static bool add_array_access(struct hlsl_ctx *ctx, struct list *instrs, struct h && (expr_type->base_type == HLSL_TYPE_TEXTURE || expr_type->base_type == HLSL_TYPE_UAV) && expr_type->sampler_dim != HLSL_SAMPLER_DIM_GENERIC) { - struct hlsl_resource_load_params load_params = {.type = HLSL_RESOURCE_LOAD}; unsigned int dim_count = hlsl_sampler_dim_count(expr_type->sampler_dim); - struct hlsl_ir_node *resource_load;
if (index_type->class > HLSL_CLASS_VECTOR || index_type->dimx != dim_count) { @@ -777,13 +775,10 @@ static bool add_array_access(struct hlsl_ctx *ctx, struct list *instrs, struct h if (!(index = add_zero_mipmap_level(ctx, instrs, index, dim_count, loc))) return false;
- load_params.format = expr_type->e.resource_format; - load_params.resource = array; - load_params.coords = index; - - if (!(resource_load = hlsl_new_resource_load(ctx, &load_params, loc))) + if (!(return_index = hlsl_new_index(ctx, array, index, loc))) return false; - list_add_tail(instrs, &resource_load->entry); + list_add_tail(instrs, &return_index->entry); + return true; }
@@ -1716,7 +1711,7 @@ static struct hlsl_ir_node *add_assignment(struct hlsl_ctx *ctx, struct list *in if (!(rhs = add_implicit_conversion(ctx, instrs, rhs, lhs_type, &rhs->loc))) return NULL;
- while (lhs->type != HLSL_IR_LOAD && lhs->type != HLSL_IR_RESOURCE_LOAD && lhs->type != HLSL_IR_INDEX) + while (lhs->type != HLSL_IR_LOAD && lhs->type != HLSL_IR_INDEX) { if (lhs->type == HLSL_IR_EXPR && hlsl_ir_expr(lhs)->op == HLSL_OP1_CAST) { @@ -1753,17 +1748,19 @@ static struct hlsl_ir_node *add_assignment(struct hlsl_ctx *ctx, struct list *in } }
- if (lhs->type == HLSL_IR_RESOURCE_LOAD) + if (lhs->type == HLSL_IR_INDEX && hlsl_index_is_resource_access(hlsl_ir_index(lhs))) { - struct hlsl_ir_resource_load *load = hlsl_ir_resource_load(lhs); + struct hlsl_ir_node *load_coords = hlsl_ir_index(lhs)->idx.node; + struct hlsl_deref resource_deref; struct hlsl_type *resource_type; struct hlsl_ir_swizzle *coords; struct hlsl_ir_node *store; unsigned int dim_count;
- /* Such an lvalue was produced by an index expression. */ - assert(load->load_type == HLSL_RESOURCE_LOAD); - resource_type = hlsl_deref_get_type(ctx, &load->resource); + if (!hlsl_init_deref_from_index_chain(ctx, &resource_deref, hlsl_ir_index(lhs)->val.node)) + return NULL; + + resource_type = hlsl_deref_get_type(ctx, &resource_deref); assert(resource_type->class == HLSL_CLASS_OBJECT); assert(resource_type->base_type == HLSL_TYPE_TEXTURE || resource_type->base_type == HLSL_TYPE_UAV);
@@ -1778,16 +1775,23 @@ static struct hlsl_ir_node *add_assignment(struct hlsl_ctx *ctx, struct list *in "Resource store expressions must write to all components.");
/* Remove the (implicit) mipmap level from the load expression. */ - assert(load->coords.node->data_type->class == HLSL_CLASS_VECTOR); - assert(load->coords.node->data_type->base_type == HLSL_TYPE_UINT); - assert(load->coords.node->data_type->dimx == dim_count + 1); - if (!(coords = hlsl_new_swizzle(ctx, HLSL_SWIZZLE(X, Y, Z, W), dim_count, load->coords.node, &lhs->loc))) + assert(load_coords->data_type->class == HLSL_CLASS_VECTOR); + assert(load_coords->data_type->base_type == HLSL_TYPE_UINT); + assert(load_coords->data_type->dimx == dim_count + 1); + if (!(coords = hlsl_new_swizzle(ctx, HLSL_SWIZZLE(X, Y, Z, W), dim_count, load_coords, &lhs->loc))) + { + hlsl_cleanup_deref(&resource_deref); return NULL; + } list_add_tail(instrs, &coords->node.entry);
- if (!(store = hlsl_new_resource_store(ctx, &load->resource, &coords->node, rhs, &lhs->loc))) + if (!(store = hlsl_new_resource_store(ctx, &resource_deref, &coords->node, rhs, &lhs->loc))) + { + hlsl_cleanup_deref(&resource_deref); return NULL; + } list_add_tail(instrs, &store->entry); + hlsl_cleanup_deref(&resource_deref); } else if (lhs->type == HLSL_IR_INDEX && hlsl_index_is_noncontiguous(hlsl_ir_index(lhs))) { diff --git a/libs/vkd3d-shader/hlsl_codegen.c b/libs/vkd3d-shader/hlsl_codegen.c index c103841d..d23014e6 100644 --- a/libs/vkd3d-shader/hlsl_codegen.c +++ b/libs/vkd3d-shader/hlsl_codegen.c @@ -862,7 +862,8 @@ static bool lower_calls(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr, void * * record access before knowing if they will be used in the lhs of an assignment --in which case * they are lowered into a deref-- or as the load of an element within a larger value. * For the latter case, this pass takes care of lowering hlsl_ir_indexes into individual - * hlsl_ir_loads. */ + * hlsl_ir_loads, or individual hlsl_ir_resource_loads, in case the indexing is a + * resource access. */ static bool lower_index_loads(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr, void *context) { struct hlsl_deref var_deref; @@ -877,6 +878,23 @@ static bool lower_index_loads(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr, index = hlsl_ir_index(instr); val = index->val.node;
+ if (hlsl_index_is_resource_access(index)) + { + struct hlsl_resource_load_params params = {0}; + struct hlsl_ir_node *load; + + params.type = HLSL_RESOURCE_LOAD; + params.resource = val; + params.coords = index->idx.node; + params.format = val->data_type->e.resource_format; + + if (!(load = hlsl_new_resource_load(ctx, ¶ms, &instr->loc))) + return false; + list_add_before(&instr->entry, &load->entry); + hlsl_replace_node(instr, load); + return true; + } + if (!(var = hlsl_new_synthetic_var(ctx, "index-val", val->data_type, &instr->loc))) return false; hlsl_init_simple_deref_from_var(&var_deref, var);