Signed-off-by: Zebediah Figura zfigura@codeweavers.com --- dlls/d3dcompiler_43/d3dcompiler_private.h | 24 +--- dlls/d3dcompiler_43/hlsl.y | 137 ++++++++++++---------- dlls/d3dcompiler_43/utils.c | 76 ++---------- 3 files changed, 91 insertions(+), 146 deletions(-)
diff --git a/dlls/d3dcompiler_43/d3dcompiler_private.h b/dlls/d3dcompiler_43/d3dcompiler_private.h index 387e932a6cc..31cf1ed582d 100644 --- a/dlls/d3dcompiler_43/d3dcompiler_private.h +++ b/dlls/d3dcompiler_43/d3dcompiler_private.h @@ -841,30 +841,10 @@ struct hlsl_ir_swizzle DWORD swizzle; };
-enum hlsl_ir_deref_type -{ - HLSL_IR_DEREF_VAR, - HLSL_IR_DEREF_ARRAY, - HLSL_IR_DEREF_RECORD, -}; - struct hlsl_deref { - enum hlsl_ir_deref_type type; - union - { - struct hlsl_ir_var *var; - struct - { - struct hlsl_ir_node *array; - struct hlsl_ir_node *index; - } array; - struct - { - struct hlsl_ir_node *record; - struct hlsl_struct_field *field; - } record; - } v; + struct hlsl_ir_var *var; + struct hlsl_ir_node *offset; };
struct hlsl_ir_deref diff --git a/dlls/d3dcompiler_43/hlsl.y b/dlls/d3dcompiler_43/hlsl.y index cc868757a26..67177ad831b 100644 --- a/dlls/d3dcompiler_43/hlsl.y +++ b/dlls/d3dcompiler_43/hlsl.y @@ -538,8 +538,7 @@ static struct hlsl_ir_assignment *make_simple_assignment(struct hlsl_ir_var *lhs return NULL;
init_node(&assign->node, HLSL_IR_ASSIGNMENT, rhs->data_type, rhs->loc); - assign->lhs.type = HLSL_IR_DEREF_VAR; - assign->lhs.v.var = lhs; + assign->lhs.var = lhs; assign->rhs = rhs; if (type_is_single_reg(lhs->data_type)) assign->writemask = (1 << lhs->data_type->dimx) - 1; @@ -547,6 +546,21 @@ static struct hlsl_ir_assignment *make_simple_assignment(struct hlsl_ir_var *lhs return assign; }
+static struct hlsl_ir_constant *new_uint_constant(unsigned int n, const struct source_location loc) +{ + struct hlsl_type *type; + struct hlsl_ir_constant *c; + + if (!(type = new_hlsl_type(d3dcompiler_strdup("uint"), HLSL_CLASS_SCALAR, HLSL_TYPE_UINT, 1, 1))) + return NULL; + + if (!(c = d3dcompiler_alloc(sizeof(*c)))) + return NULL; + init_node(&c->node, HLSL_IR_CONSTANT, type, loc); + c->v.value.u[0] = n; + return c; +} + static struct hlsl_ir_deref *new_var_deref(struct hlsl_ir_var *var, const struct source_location loc) { struct hlsl_ir_deref *deref = d3dcompiler_alloc(sizeof(*deref)); @@ -557,60 +571,72 @@ static struct hlsl_ir_deref *new_var_deref(struct hlsl_ir_var *var, const struct return NULL; } init_node(&deref->node, HLSL_IR_DEREF, var->data_type, loc); - deref->src.type = HLSL_IR_DEREF_VAR; - deref->src.v.var = var; + deref->src.var = var; return deref; }
-static struct hlsl_ir_node *get_var_deref(struct hlsl_ir_node *node) +static struct hlsl_ir_deref *new_deref(struct hlsl_ir_node *var_node, struct hlsl_ir_node *offset, + struct hlsl_type *data_type, const struct source_location loc) { - struct hlsl_ir_assignment *assign; + struct hlsl_ir_node *add = NULL; struct hlsl_ir_deref *deref; struct hlsl_ir_var *var; - char name[27];
- if (node->type == HLSL_IR_DEREF) - return node; + if (var_node->type == HLSL_IR_DEREF) + { + const struct hlsl_deref *src = &deref_from_node(var_node)->src;
- sprintf(name, "<deref-%p>", node); - if (!(var = new_synthetic_var(name, node->data_type, node->loc))) - return NULL; + var = src->var; + if (src->offset) + { + if (!(add = new_binary_expr(HLSL_IR_BINOP_ADD, src->offset, offset, loc))) + return NULL; + list_add_after(&offset->entry, &add->entry); + offset = add; + } + } + else + { + struct hlsl_ir_assignment *assign; + char name[27]; + + sprintf(name, "<deref-%p>", var_node); + if (!(var = new_synthetic_var(name, var_node->data_type, var_node->loc))) + return NULL;
- TRACE("Synthesized variable %p for %s node.\n", var, debug_node_type(node->type)); + TRACE("Synthesized variable %p for %s node.\n", var, debug_node_type(var_node->type));
- if (!(assign = make_simple_assignment(var, node))) - return NULL; - list_add_after(&node->entry, &assign->node.entry); + if (!(assign = make_simple_assignment(var, var_node))) + return NULL;
- if (!(deref = new_var_deref(var, var->loc))) + list_add_after(&var_node->entry, &assign->node.entry); + } + + if (!(deref = d3dcompiler_alloc(sizeof(*deref)))) return NULL; - list_add_after(&assign->node.entry, &deref->node.entry); - return &deref->node; + init_node(&deref->node, HLSL_IR_DEREF, data_type, loc); + deref->src.var = var; + deref->src.offset = offset; + list_add_after(&offset->entry, &deref->node.entry); + return deref; }
static struct hlsl_ir_deref *new_record_deref(struct hlsl_ir_node *record, - struct hlsl_struct_field *field, const struct source_location loc) + const struct hlsl_struct_field *field, const struct source_location loc) { - struct hlsl_ir_deref *deref; + struct hlsl_ir_constant *c;
- if (!(record = get_var_deref(record))) - return NULL; - - if (!(deref = d3dcompiler_alloc(sizeof(*deref)))) + if (!(c = new_uint_constant(field->reg_offset * 4, loc))) return NULL; + list_add_after(&record->entry, &c->node.entry);
- init_node(&deref->node, HLSL_IR_DEREF, field->type, loc); - deref->src.type = HLSL_IR_DEREF_RECORD; - deref->src.v.record.record = record; - deref->src.v.record.field = field; - return deref; + return new_deref(record, &c->node, field->type, loc); }
static struct hlsl_ir_deref *new_array_deref(struct hlsl_ir_node *array, struct hlsl_ir_node *index, const struct source_location loc) { const struct hlsl_type *expr_type = array->data_type; - struct hlsl_ir_deref *deref; struct hlsl_type *data_type;
TRACE("Array dereference from type %s.\n", debug_hlsl_type(expr_type)); @@ -621,6 +647,7 @@ static struct hlsl_ir_deref *new_array_deref(struct hlsl_ir_node *array, } else if (expr_type->type == HLSL_CLASS_MATRIX || expr_type->type == HLSL_CLASS_VECTOR) { + /* This needs to be lowered now, while we still have type information. */ FIXME("Index of matrix or vector type.\n"); return NULL; } @@ -633,17 +660,21 @@ static struct hlsl_ir_deref *new_array_deref(struct hlsl_ir_node *array, return NULL; }
- if (!(array = get_var_deref(array))) - return NULL; + if (data_type->reg_size > 1) + { + struct hlsl_ir_constant *c; + struct hlsl_ir_node *mul;
- if (!(deref = d3dcompiler_alloc(sizeof(*deref)))) - return NULL; + if (!(c = new_uint_constant(data_type->reg_size * 4, loc))) + return NULL; + list_add_after(&index->entry, &c->node.entry); + if (!(mul = new_binary_expr(HLSL_IR_BINOP_MUL, index, &c->node, loc))) + return NULL; + list_add_after(&c->node.entry, &mul->entry); + index = mul; + }
- init_node(&deref->node, HLSL_IR_DEREF, data_type, loc); - deref->src.type = HLSL_IR_DEREF_ARRAY; - deref->src.v.array.array = array; - deref->src.v.array.index = index; - return deref; + return new_deref(array, index, data_type, loc); }
static void struct_var_initializer(struct list *list, struct hlsl_ir_var *var, @@ -2748,22 +2779,6 @@ static unsigned int index_instructions(struct list *instrs, unsigned int index) return index; }
-/* Walk the chain of derefs and retrieve the actual variable we care about. */ -static struct hlsl_ir_var *hlsl_var_from_deref(const struct hlsl_deref *deref) -{ - switch (deref->type) - { - case HLSL_IR_DEREF_VAR: - return deref->v.var; - case HLSL_IR_DEREF_ARRAY: - return hlsl_var_from_deref(&deref_from_node(deref->v.array.array)->src); - case HLSL_IR_DEREF_RECORD: - return hlsl_var_from_deref(&deref_from_node(deref->v.record.record)->src); - } - assert(0); - return NULL; -} - /* Compute the earliest and latest liveness for each variable. In the case that * a variable is accessed inside of a loop, we promote its liveness to extend * to at least the range of the entire loop. Note that we don't need to do this @@ -2781,10 +2796,12 @@ static void compute_liveness_recurse(struct list *instrs, unsigned int loop_firs case HLSL_IR_ASSIGNMENT: { struct hlsl_ir_assignment *assignment = assignment_from_node(instr); - var = hlsl_var_from_deref(&assignment->lhs); + var = assignment->lhs.var; if (!var->first_write) var->first_write = loop_first ? min(instr->index, loop_first) : instr->index; assignment->rhs->last_read = instr->index; + if (assignment->lhs.offset) + assignment->lhs.offset->last_read = instr->index; break; } case HLSL_IR_CONSTANT: @@ -2800,10 +2817,10 @@ static void compute_liveness_recurse(struct list *instrs, unsigned int loop_firs case HLSL_IR_DEREF: { struct hlsl_ir_deref *deref = deref_from_node(instr); - var = hlsl_var_from_deref(&deref->src); + var = deref->src.var; var->last_read = loop_last ? max(instr->index, loop_last) : instr->index; - if (deref->src.type == HLSL_IR_DEREF_ARRAY) - deref->src.v.array.index->last_read = instr->index; + if (deref->src.offset) + deref->src.offset->last_read = instr->index; break; } case HLSL_IR_EXPR: diff --git a/dlls/d3dcompiler_43/utils.c b/dlls/d3dcompiler_43/utils.c index ac9da97f27c..4b1f99de65d 100644 --- a/dlls/d3dcompiler_43/utils.c +++ b/dlls/d3dcompiler_43/utils.c @@ -1437,29 +1437,6 @@ static unsigned int invert_swizzle(unsigned int *swizzle, unsigned int writemask return new_writemask; }
-static BOOL validate_lhs_deref(const struct hlsl_ir_node *lhs) -{ - struct hlsl_ir_deref *deref; - - if (lhs->type != HLSL_IR_DEREF) - { - hlsl_report_message(lhs->loc, HLSL_LEVEL_ERROR, "invalid lvalue"); - return FALSE; - } - - deref = deref_from_node(lhs); - - if (deref->src.type == HLSL_IR_DEREF_VAR) - return TRUE; - if (deref->src.type == HLSL_IR_DEREF_ARRAY) - return validate_lhs_deref(deref->src.v.array.array); - if (deref->src.type == HLSL_IR_DEREF_RECORD) - return validate_lhs_deref(deref->src.v.record.record); - - assert(0); - return FALSE; -} - struct hlsl_ir_node *make_assignment(struct hlsl_ir_node *lhs, enum parse_assign_op assign_op, struct hlsl_ir_node *rhs) { @@ -1513,12 +1490,6 @@ struct hlsl_ir_node *make_assignment(struct hlsl_ir_node *lhs, enum parse_assign lhs = lhs_inner; }
- if (!validate_lhs_deref(lhs)) - { - d3dcompiler_free(assign); - return NULL; - } - TRACE("Creating proper assignment expression.\n"); if (writemask == BWRITERSP_WRITEMASK_ALL) type = lhs->data_type; @@ -1562,26 +1533,12 @@ struct hlsl_ir_node *make_assignment(struct hlsl_ir_node *lhs, enum parse_assign enum hlsl_ir_expr_op op = op_from_assignment(assign_op); struct hlsl_ir_node *expr;
- if (assign->lhs.type != HLSL_IR_DEREF_VAR) - { - FIXME("LHS expression not supported in compound assignments yet.\n"); - assign->rhs = rhs; - } - else - { - TRACE("Adding an expression for the compound assignment.\n"); - expr = new_binary_expr(op, lhs, rhs, lhs->loc); - list_add_after(&rhs->entry, &expr->entry); - assign->rhs = expr; - } - } - else - { - list_remove(&lhs->entry); - /* Don't recursively free the deref; we just copied its members. */ - d3dcompiler_free(lhs); - assign->rhs = rhs; + TRACE("Adding an expression for the compound assignment.\n"); + expr = new_binary_expr(op, lhs, rhs, lhs->loc); + list_add_after(&rhs->entry, &expr->entry); + rhs = expr; } + assign->rhs = rhs;
return &assign->node; } @@ -1879,23 +1836,14 @@ static void debug_dump_ir_var(const struct hlsl_ir_var *var)
static void debug_dump_deref(const struct hlsl_deref *deref) { - switch (deref->type) + wine_dbg_printf("deref("); + debug_dump_ir_var(deref->var); + wine_dbg_printf(")"); + if (deref->offset) { - case HLSL_IR_DEREF_VAR: - wine_dbg_printf("deref("); - debug_dump_ir_var(deref->v.var); - wine_dbg_printf(")"); - break; - case HLSL_IR_DEREF_ARRAY: - debug_dump_src(deref->v.array.array); - wine_dbg_printf("["); - debug_dump_src(deref->v.array.index); - wine_dbg_printf("]"); - break; - case HLSL_IR_DEREF_RECORD: - debug_dump_src(deref->v.record.record); - wine_dbg_printf(".%s", debugstr_a(deref->v.record.field->name)); - break; + wine_dbg_printf("["); + debug_dump_src(deref->offset); + wine_dbg_printf("]"); } }
Signed-off-by: Zebediah Figura zfigura@codeweavers.com --- dlls/d3dcompiler_43/d3dcompiler_private.h | 10 +-- dlls/d3dcompiler_43/hlsl.y | 97 +++++++++++------------ dlls/d3dcompiler_43/utils.c | 18 ++--- 3 files changed, 62 insertions(+), 63 deletions(-)
diff --git a/dlls/d3dcompiler_43/d3dcompiler_private.h b/dlls/d3dcompiler_43/d3dcompiler_private.h index 31cf1ed582d..6c2f234c4dd 100644 --- a/dlls/d3dcompiler_43/d3dcompiler_private.h +++ b/dlls/d3dcompiler_43/d3dcompiler_private.h @@ -648,9 +648,9 @@ enum hlsl_ir_node_type HLSL_IR_ASSIGNMENT = 0, HLSL_IR_CONSTANT, HLSL_IR_CONSTRUCTOR, - HLSL_IR_DEREF, HLSL_IR_EXPR, HLSL_IR_IF, + HLSL_IR_LOAD, HLSL_IR_LOOP, HLSL_IR_JUMP, HLSL_IR_SWIZZLE, @@ -847,7 +847,7 @@ struct hlsl_deref struct hlsl_ir_node *offset; };
-struct hlsl_ir_deref +struct hlsl_ir_load { struct hlsl_ir_node node; struct hlsl_deref src; @@ -1004,10 +1004,10 @@ static inline struct hlsl_ir_expr *expr_from_node(const struct hlsl_ir_node *nod return CONTAINING_RECORD(node, struct hlsl_ir_expr, node); }
-static inline struct hlsl_ir_deref *deref_from_node(const struct hlsl_ir_node *node) +static inline struct hlsl_ir_load *load_from_node(const struct hlsl_ir_node *node) { - assert(node->type == HLSL_IR_DEREF); - return CONTAINING_RECORD(node, struct hlsl_ir_deref, node); + assert(node->type == HLSL_IR_LOAD); + return CONTAINING_RECORD(node, struct hlsl_ir_load, node); }
static inline struct hlsl_ir_constant *constant_from_node(const struct hlsl_ir_node *node) diff --git a/dlls/d3dcompiler_43/hlsl.y b/dlls/d3dcompiler_43/hlsl.y index 67177ad831b..5130114976e 100644 --- a/dlls/d3dcompiler_43/hlsl.y +++ b/dlls/d3dcompiler_43/hlsl.y @@ -561,30 +561,30 @@ static struct hlsl_ir_constant *new_uint_constant(unsigned int n, const struct s return c; }
-static struct hlsl_ir_deref *new_var_deref(struct hlsl_ir_var *var, const struct source_location loc) +static struct hlsl_ir_load *new_var_load(struct hlsl_ir_var *var, const struct source_location loc) { - struct hlsl_ir_deref *deref = d3dcompiler_alloc(sizeof(*deref)); + struct hlsl_ir_load *load = d3dcompiler_alloc(sizeof(*load));
- if (!deref) + if (!load) { ERR("Out of memory.\n"); return NULL; } - init_node(&deref->node, HLSL_IR_DEREF, var->data_type, loc); - deref->src.var = var; - return deref; + init_node(&load->node, HLSL_IR_LOAD, var->data_type, loc); + load->src.var = var; + return load; }
-static struct hlsl_ir_deref *new_deref(struct hlsl_ir_node *var_node, struct hlsl_ir_node *offset, +static struct hlsl_ir_load *new_load(struct hlsl_ir_node *var_node, struct hlsl_ir_node *offset, struct hlsl_type *data_type, const struct source_location loc) { struct hlsl_ir_node *add = NULL; - struct hlsl_ir_deref *deref; + struct hlsl_ir_load *load; struct hlsl_ir_var *var;
- if (var_node->type == HLSL_IR_DEREF) + if (var_node->type == HLSL_IR_LOAD) { - const struct hlsl_deref *src = &deref_from_node(var_node)->src; + const struct hlsl_deref *src = &load_from_node(var_node)->src;
var = src->var; if (src->offset) @@ -612,16 +612,16 @@ static struct hlsl_ir_deref *new_deref(struct hlsl_ir_node *var_node, struct hls list_add_after(&var_node->entry, &assign->node.entry); }
- if (!(deref = d3dcompiler_alloc(sizeof(*deref)))) + if (!(load = d3dcompiler_alloc(sizeof(*load)))) return NULL; - init_node(&deref->node, HLSL_IR_DEREF, data_type, loc); - deref->src.var = var; - deref->src.offset = offset; - list_add_after(&offset->entry, &deref->node.entry); - return deref; + init_node(&load->node, HLSL_IR_LOAD, data_type, loc); + load->src.var = var; + load->src.offset = offset; + list_add_after(&offset->entry, &load->node.entry); + return load; }
-static struct hlsl_ir_deref *new_record_deref(struct hlsl_ir_node *record, +static struct hlsl_ir_load *new_record_load(struct hlsl_ir_node *record, const struct hlsl_struct_field *field, const struct source_location loc) { struct hlsl_ir_constant *c; @@ -630,16 +630,16 @@ static struct hlsl_ir_deref *new_record_deref(struct hlsl_ir_node *record, return NULL; list_add_after(&record->entry, &c->node.entry);
- return new_deref(record, &c->node, field->type, loc); + return new_load(record, &c->node, field->type, loc); }
-static struct hlsl_ir_deref *new_array_deref(struct hlsl_ir_node *array, +static struct hlsl_ir_load *new_array_load(struct hlsl_ir_node *array, struct hlsl_ir_node *index, const struct source_location loc) { const struct hlsl_type *expr_type = array->data_type; struct hlsl_type *data_type;
- TRACE("Array dereference from type %s.\n", debug_hlsl_type(expr_type)); + TRACE("Array load from type %s.\n", debug_hlsl_type(expr_type));
if (expr_type->type == HLSL_CLASS_ARRAY) { @@ -674,7 +674,7 @@ static struct hlsl_ir_deref *new_array_deref(struct hlsl_ir_node *array, index = mul; }
- return new_deref(array, index, data_type, loc); + return new_load(array, index, data_type, loc); }
static void struct_var_initializer(struct list *list, struct hlsl_ir_var *var, @@ -683,7 +683,7 @@ static void struct_var_initializer(struct list *list, struct hlsl_ir_var *var, struct hlsl_type *type = var->data_type; struct hlsl_struct_field *field; struct hlsl_ir_node *assignment; - struct hlsl_ir_deref *deref; + struct hlsl_ir_load *load; unsigned int i = 0;
if (initializer_size(initializer) != components_count_type(type)) @@ -707,14 +707,13 @@ static void struct_var_initializer(struct list *list, struct hlsl_ir_var *var, } if (components_count_type(field->type) == components_count_type(node->data_type)) { - deref = new_record_deref(&new_var_deref(var, var->loc)->node, field, node->loc); - if (!deref) + if (!(load = new_record_load(&new_var_load(var, var->loc)->node, field, node->loc))) { ERR("Out of memory.\n"); break; } - list_add_tail(list, &deref->node.entry); - assignment = make_assignment(&deref->node, ASSIGN_OP_ASSIGN, node); + list_add_tail(list, &load->node.entry); + assignment = make_assignment(&load->node, ASSIGN_OP_ASSIGN, node); list_add_tail(list, &assignment->entry); } else @@ -805,7 +804,7 @@ static struct list *declare_vars(struct hlsl_type *basic_type, DWORD modifiers, if (v->initializer.args_count) { unsigned int size = initializer_size(&v->initializer); - struct hlsl_ir_deref *deref; + struct hlsl_ir_load *load;
TRACE("Variable with initializer.\n"); if (type->type <= HLSL_CLASS_LAST_NUMERIC @@ -861,9 +860,9 @@ static struct list *declare_vars(struct hlsl_type *basic_type, DWORD modifiers, list_move_tail(statements_list, v->initializer.instrs); d3dcompiler_free(v->initializer.instrs);
- deref = new_var_deref(var, var->loc); - list_add_tail(statements_list, &deref->node.entry); - assignment = make_assignment(&deref->node, ASSIGN_OP_ASSIGN, v->initializer.args[0]); + load = new_var_load(var, var->loc); + list_add_tail(statements_list, &load->node.entry); + assignment = make_assignment(&load->node, ASSIGN_OP_ASSIGN, v->initializer.args[0]); d3dcompiler_free(v->initializer.args); list_add_tail(statements_list, &assignment->entry); } @@ -1221,8 +1220,8 @@ static unsigned int evaluate_array_dimension(struct hlsl_ir_node *node) } } case HLSL_IR_CONSTRUCTOR: - case HLSL_IR_DEREF: case HLSL_IR_EXPR: + case HLSL_IR_LOAD: case HLSL_IR_SWIZZLE: FIXME("Unhandled type %s.\n", debug_node_type(node->type)); return 0; @@ -2248,7 +2247,7 @@ primary_expr: C_FLOAT } | VAR_IDENTIFIER { - struct hlsl_ir_deref *deref; + struct hlsl_ir_load *load; struct hlsl_ir_var *var;
if (!(var = get_variable(hlsl_ctx.cur_scope, $1))) @@ -2258,9 +2257,9 @@ primary_expr: C_FLOAT set_parse_status(&hlsl_ctx.status, PARSE_ERR); YYABORT; } - if ((deref = new_var_deref(var, get_location(&@1)))) + if ((load = new_var_load(var, get_location(&@1)))) { - if (!($$ = make_list(&deref->node))) + if (!($$ = make_list(&load->node))) YYABORT; } else @@ -2325,14 +2324,14 @@ postfix_expr: primary_expr { if (!strcmp($3, field->name)) { - struct hlsl_ir_deref *deref = new_record_deref(node, field, loc); + struct hlsl_ir_load *load = new_record_load(node, field, loc);
- if (!deref) + if (!load) { ERR("Out of memory\n"); YYABORT; } - $$ = append_unop($1, &deref->node); + $$ = append_unop($1, &load->node); break; } } @@ -2365,7 +2364,7 @@ postfix_expr: primary_expr } | postfix_expr '[' expr ']' { - struct hlsl_ir_deref *deref; + struct hlsl_ir_load *load;
if (node_from_list($3)->data_type->type != HLSL_CLASS_SCALAR) { @@ -2375,13 +2374,13 @@ postfix_expr: primary_expr YYABORT; }
- if (!(deref = new_array_deref(node_from_list($1), node_from_list($3), get_location(&@2)))) + if (!(load = new_array_load(node_from_list($1), node_from_list($3), get_location(&@2)))) { free_instr_list($1); free_instr_list($3); YYABORT; } - $$ = append_binop($1, $3, &deref->node); + $$ = append_binop($1, $3, &load->node); } /* "var_modifiers" doesn't make sense in this case, but it's needed in the grammar to avoid shift/reduce conflicts. */ @@ -2814,15 +2813,6 @@ static void compute_liveness_recurse(struct list *instrs, unsigned int loop_firs constructor->args[i]->last_read = instr->index; break; } - case HLSL_IR_DEREF: - { - struct hlsl_ir_deref *deref = deref_from_node(instr); - var = deref->src.var; - var->last_read = loop_last ? max(instr->index, loop_last) : instr->index; - if (deref->src.offset) - deref->src.offset->last_read = instr->index; - break; - } case HLSL_IR_EXPR: { struct hlsl_ir_expr *expr = expr_from_node(instr); @@ -2849,6 +2839,15 @@ static void compute_liveness_recurse(struct list *instrs, unsigned int loop_firs jump->return_value->last_read = instr->index; break; } + case HLSL_IR_LOAD: + { + struct hlsl_ir_load *load = load_from_node(instr); + var = load->src.var; + var->last_read = loop_last ? max(instr->index, loop_last) : instr->index; + if (load->src.offset) + load->src.offset->last_read = instr->index; + break; + } case HLSL_IR_LOOP: { struct hlsl_ir_loop *loop = loop_from_node(instr); diff --git a/dlls/d3dcompiler_43/utils.c b/dlls/d3dcompiler_43/utils.c index 4b1f99de65d..440ad491884 100644 --- a/dlls/d3dcompiler_43/utils.c +++ b/dlls/d3dcompiler_43/utils.c @@ -1450,7 +1450,7 @@ struct hlsl_ir_node *make_assignment(struct hlsl_ir_node *lhs, enum parse_assign return NULL; }
- while (lhs->type != HLSL_IR_DEREF) + while (lhs->type != HLSL_IR_LOAD) { struct hlsl_ir_node *lhs_inner;
@@ -1527,7 +1527,7 @@ struct hlsl_ir_node *make_assignment(struct hlsl_ir_node *lhs, enum parse_assign
rhs = implicit_conversion(rhs, type, &rhs->loc);
- assign->lhs = deref_from_node(lhs)->src; + assign->lhs = load_from_node(lhs)->src; if (assign_op != ASSIGN_OP_ASSIGN) { enum hlsl_ir_expr_op op = op_from_assignment(assign_op); @@ -1791,9 +1791,9 @@ const char *debug_node_type(enum hlsl_ir_node_type type) "HLSL_IR_ASSIGNMENT", "HLSL_IR_CONSTANT", "HLSL_IR_CONSTRUCTOR", - "HLSL_IR_DEREF", "HLSL_IR_EXPR", "HLSL_IR_IF", + "HLSL_IR_LOAD", "HLSL_IR_LOOP", "HLSL_IR_JUMP", "HLSL_IR_SWIZZLE", @@ -2096,8 +2096,8 @@ static void debug_dump_instr(const struct hlsl_ir_node *instr) case HLSL_IR_EXPR: debug_dump_ir_expr(expr_from_node(instr)); break; - case HLSL_IR_DEREF: - debug_dump_deref(&deref_from_node(instr)->src); + case HLSL_IR_LOAD: + debug_dump_deref(&load_from_node(instr)->src); break; case HLSL_IR_CONSTANT: debug_dump_ir_constant(constant_from_node(instr)); @@ -2195,9 +2195,9 @@ static void free_ir_constant(struct hlsl_ir_constant *constant) d3dcompiler_free(constant); }
-static void free_ir_deref(struct hlsl_ir_deref *deref) +static void free_ir_load(struct hlsl_ir_load *load) { - d3dcompiler_free(deref); + d3dcompiler_free(load); }
static void free_ir_swizzle(struct hlsl_ir_swizzle *swizzle) @@ -2245,8 +2245,8 @@ void free_instr(struct hlsl_ir_node *node) case HLSL_IR_CONSTANT: free_ir_constant(constant_from_node(node)); break; - case HLSL_IR_DEREF: - free_ir_deref(deref_from_node(node)); + case HLSL_IR_LOAD: + free_ir_load(load_from_node(node)); break; case HLSL_IR_SWIZZLE: free_ir_swizzle(swizzle_from_node(node));
Signed-off-by: Zebediah Figura zfigura@codeweavers.com --- dlls/d3dcompiler_43/d3dcompiler_private.h | 10 ++ dlls/d3dcompiler_43/hlsl.y | 132 +++++++++++----------- 2 files changed, 78 insertions(+), 64 deletions(-)
diff --git a/dlls/d3dcompiler_43/d3dcompiler_private.h b/dlls/d3dcompiler_43/d3dcompiler_private.h index 6c2f234c4dd..0a8f85e7974 100644 --- a/dlls/d3dcompiler_43/d3dcompiler_private.h +++ b/dlls/d3dcompiler_43/d3dcompiler_private.h @@ -595,6 +595,7 @@ enum hlsl_sampler_dim HLSL_SAMPLER_DIM_2D, HLSL_SAMPLER_DIM_3D, HLSL_SAMPLER_DIM_CUBE, + HLSL_SAMPLER_DIM_MAX = HLSL_SAMPLER_DIM_CUBE };
enum hlsl_matrix_majority @@ -983,6 +984,15 @@ struct hlsl_parse_ctx const struct hlsl_ir_function_decl *cur_function;
enum hlsl_matrix_majority matrix_majority; + + struct + { + struct hlsl_type *scalar[HLSL_TYPE_LAST_SCALAR + 1]; + struct hlsl_type *sampler[HLSL_SAMPLER_DIM_MAX + 1]; + struct hlsl_type *Void; + } builtin_types; + + struct hlsl_type *builtin_void, builtin_int, *builtin_uint, *builtin_float; };
extern struct hlsl_parse_ctx hlsl_ctx DECLSPEC_HIDDEN; diff --git a/dlls/d3dcompiler_43/hlsl.y b/dlls/d3dcompiler_43/hlsl.y index 5130114976e..51adf1106af 100644 --- a/dlls/d3dcompiler_43/hlsl.y +++ b/dlls/d3dcompiler_43/hlsl.y @@ -213,6 +213,15 @@ static void declare_predefined_types(struct hlsl_scope *scope) }; char name[10];
+ static const char *const sampler_names[] = + { + "sampler", + "sampler1D", + "sampler2D", + "sampler3D", + "samplerCUBE" + }; + for (bt = 0; bt <= HLSL_TYPE_LAST_SCALAR; ++bt) { for (y = 1; y <= 4; ++y) @@ -234,12 +243,23 @@ static void declare_predefined_types(struct hlsl_scope *scope) sprintf(name, "%s", names[bt]); type = new_hlsl_type(d3dcompiler_strdup(name), HLSL_CLASS_SCALAR, bt, x, y); add_type_to_scope(scope, type); + hlsl_ctx.builtin_types.scalar[bt] = type; } } } } }
+ for (bt = 0; bt <= HLSL_SAMPLER_DIM_MAX; ++bt) + { + type = new_hlsl_type(d3dcompiler_strdup(sampler_names[bt]), HLSL_CLASS_OBJECT, HLSL_TYPE_SAMPLER, 1, 1); + type->sampler_dim = bt; + hlsl_ctx.builtin_types.sampler[bt] = type; + } + + hlsl_ctx.builtin_types.Void = new_hlsl_type(d3dcompiler_strdup("void"), HLSL_CLASS_OBJECT, HLSL_TYPE_VOID, 1, 1); + add_type_to_scope(scope, hlsl_ctx.builtin_types.Void); + /* DX8 effects predefined types */ type = new_hlsl_type(d3dcompiler_strdup("DWORD"), HLSL_CLASS_SCALAR, HLSL_TYPE_INT, 1, 1); add_type_to_scope(scope, type); @@ -548,15 +568,11 @@ static struct hlsl_ir_assignment *make_simple_assignment(struct hlsl_ir_var *lhs
static struct hlsl_ir_constant *new_uint_constant(unsigned int n, const struct source_location loc) { - struct hlsl_type *type; struct hlsl_ir_constant *c;
- if (!(type = new_hlsl_type(d3dcompiler_strdup("uint"), HLSL_CLASS_SCALAR, HLSL_TYPE_UINT, 1, 1))) - return NULL; - if (!(c = d3dcompiler_alloc(sizeof(*c)))) return NULL; - init_node(&c->node, HLSL_IR_CONSTANT, type, loc); + init_node(&c->node, HLSL_IR_CONSTANT, hlsl_ctx.builtin_types.scalar[HLSL_TYPE_UINT], loc); c->v.value.u[0] = n; return c; } @@ -1818,60 +1834,48 @@ type: base_type $$ = new_hlsl_type(NULL, HLSL_CLASS_MATRIX, $3->base_type, $5, $7); }
-base_type: KW_VOID - { - $$ = new_hlsl_type(d3dcompiler_strdup("void"), HLSL_CLASS_OBJECT, HLSL_TYPE_VOID, 1, 1); - } - | KW_SAMPLER - { - $$ = new_hlsl_type(d3dcompiler_strdup("sampler"), HLSL_CLASS_OBJECT, HLSL_TYPE_SAMPLER, 1, 1); - $$->sampler_dim = HLSL_SAMPLER_DIM_GENERIC; - } - | KW_SAMPLER1D - { - $$ = new_hlsl_type(d3dcompiler_strdup("sampler1D"), HLSL_CLASS_OBJECT, HLSL_TYPE_SAMPLER, 1, 1); - $$->sampler_dim = HLSL_SAMPLER_DIM_1D; - } - | KW_SAMPLER2D - { - $$ = new_hlsl_type(d3dcompiler_strdup("sampler2D"), HLSL_CLASS_OBJECT, HLSL_TYPE_SAMPLER, 1, 1); - $$->sampler_dim = HLSL_SAMPLER_DIM_2D; - } - | KW_SAMPLER3D - { - $$ = new_hlsl_type(d3dcompiler_strdup("sampler3D"), HLSL_CLASS_OBJECT, HLSL_TYPE_SAMPLER, 1, 1); - $$->sampler_dim = HLSL_SAMPLER_DIM_3D; - } - | KW_SAMPLERCUBE - { - $$ = new_hlsl_type(d3dcompiler_strdup("samplerCUBE"), HLSL_CLASS_OBJECT, HLSL_TYPE_SAMPLER, 1, 1); - $$->sampler_dim = HLSL_SAMPLER_DIM_CUBE; - } - | TYPE_IDENTIFIER - { - struct hlsl_type *type; +base_type:
- type = get_type(hlsl_ctx.cur_scope, $1, TRUE); - $$ = type; - d3dcompiler_free($1); - } - | KW_STRUCT TYPE_IDENTIFIER - { - struct hlsl_type *type; - - type = get_type(hlsl_ctx.cur_scope, $2, TRUE); - if (type->type != HLSL_CLASS_STRUCT) - { - hlsl_message("Line %u: redefining %s as a structure.\n", - hlsl_ctx.line_no, $2); - set_parse_status(&hlsl_ctx.status, PARSE_ERR); - } - else - { - $$ = type; - } - d3dcompiler_free($2); - } + KW_VOID + { + $$ = hlsl_ctx.builtin_types.Void; + } + | KW_SAMPLER + { + $$ = hlsl_ctx.builtin_types.sampler[HLSL_SAMPLER_DIM_GENERIC]; + } + | KW_SAMPLER1D + { + $$ = hlsl_ctx.builtin_types.sampler[HLSL_SAMPLER_DIM_1D]; + } + | KW_SAMPLER2D + { + $$ = hlsl_ctx.builtin_types.sampler[HLSL_SAMPLER_DIM_2D]; + } + | KW_SAMPLER3D + { + $$ = hlsl_ctx.builtin_types.sampler[HLSL_SAMPLER_DIM_3D]; + } + | KW_SAMPLERCUBE + { + $$ = hlsl_ctx.builtin_types.sampler[HLSL_SAMPLER_DIM_3D]; + } + | TYPE_IDENTIFIER + { + $$ = get_type(hlsl_ctx.cur_scope, $1, TRUE); + d3dcompiler_free($1); + } + | KW_STRUCT TYPE_IDENTIFIER + { + $$ = get_type(hlsl_ctx.cur_scope, $2, TRUE); + if ($$->type != HLSL_CLASS_STRUCT) + { + hlsl_message("Line %u: redefining %s as a structure.\n", + hlsl_ctx.line_no, $2); + set_parse_status(&hlsl_ctx.status, PARSE_ERR); + } + d3dcompiler_free($2); + }
declaration_statement: declaration | struct_declaration @@ -2211,8 +2215,8 @@ primary_expr: C_FLOAT ERR("Out of memory.\n"); YYABORT; } - init_node(&c->node, HLSL_IR_CONSTANT, new_hlsl_type(d3dcompiler_strdup("float"), - HLSL_CLASS_SCALAR, HLSL_TYPE_FLOAT, 1, 1), get_location(&@1)); + init_node(&c->node, HLSL_IR_CONSTANT, + hlsl_ctx.builtin_types.scalar[HLSL_TYPE_FLOAT], get_location(&@1)); c->v.value.f[0] = $1; if (!($$ = make_list(&c->node))) YYABORT; @@ -2225,8 +2229,8 @@ primary_expr: C_FLOAT ERR("Out of memory.\n"); YYABORT; } - init_node(&c->node, HLSL_IR_CONSTANT, new_hlsl_type(d3dcompiler_strdup("int"), - HLSL_CLASS_SCALAR, HLSL_TYPE_INT, 1, 1), get_location(&@1)); + init_node(&c->node, HLSL_IR_CONSTANT, + hlsl_ctx.builtin_types.scalar[HLSL_TYPE_INT], get_location(&@1)); c->v.value.i[0] = $1; if (!($$ = make_list(&c->node))) YYABORT; @@ -2239,8 +2243,8 @@ primary_expr: C_FLOAT ERR("Out of memory.\n"); YYABORT; } - init_node(&c->node, HLSL_IR_CONSTANT, new_hlsl_type(d3dcompiler_strdup("bool"), - HLSL_CLASS_SCALAR, HLSL_TYPE_BOOL, 1, 1), get_location(&@1)); + init_node(&c->node, HLSL_IR_CONSTANT, + hlsl_ctx.builtin_types.scalar[HLSL_TYPE_BOOL], get_location(&@1)); c->v.value.b[0] = $1; if (!($$ = make_list(&c->node))) YYABORT;
Hi,
While running your changed tests, I think I found new failures. Being a bot and all I'm not very good at pattern recognition, so I might be wrong, but could you please double-check?
Full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=72017
Your paranoid android.
=== debiant (build log) ===
error: patch failed: dlls/d3dcompiler_43/hlsl.y:548 Task: Patch failed to apply
=== debiant (build log) ===
error: patch failed: dlls/d3dcompiler_43/hlsl.y:548 Task: Patch failed to apply
On 5/20/20 12:20 AM, Marvin wrote:
Hi,
While running your changed tests, I think I found new failures. Being a bot and all I'm not very good at pattern recognition, so I might be wrong, but could you please double-check?
Full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=72017
Your paranoid android.
=== debiant (build log) ===
error: patch failed: dlls/d3dcompiler_43/hlsl.y:548 Task: Patch failed to apply
=== debiant (build log) ===
error: patch failed: dlls/d3dcompiler_43/hlsl.y:548 Task: Patch failed to apply
I thought I waited long enough, but it seems this got misapplied on top of the quartz/filtermapper series :-/
On Wed, May 20, 2020 at 3:23 AM Zebediah Figura z.figura12@gmail.com wrote:
Signed-off-by: Zebediah Figura zfigura@codeweavers.com
dlls/d3dcompiler_43/d3dcompiler_private.h | 10 ++ dlls/d3dcompiler_43/hlsl.y | 132 +++++++++++----------- 2 files changed, 78 insertions(+), 64 deletions(-)
diff --git a/dlls/d3dcompiler_43/d3dcompiler_private.h b/dlls/d3dcompiler_43/d3dcompiler_private.h index 6c2f234c4dd..0a8f85e7974 100644 --- a/dlls/d3dcompiler_43/d3dcompiler_private.h +++ b/dlls/d3dcompiler_43/d3dcompiler_private.h @@ -595,6 +595,7 @@ enum hlsl_sampler_dim HLSL_SAMPLER_DIM_2D, HLSL_SAMPLER_DIM_3D, HLSL_SAMPLER_DIM_CUBE,
- HLSL_SAMPLER_DIM_MAX = HLSL_SAMPLER_DIM_CUBE
};
enum hlsl_matrix_majority @@ -983,6 +984,15 @@ struct hlsl_parse_ctx const struct hlsl_ir_function_decl *cur_function;
enum hlsl_matrix_majority matrix_majority;
- struct
- {
struct hlsl_type *scalar[HLSL_TYPE_LAST_SCALAR + 1];
struct hlsl_type *sampler[HLSL_SAMPLER_DIM_MAX + 1];
struct hlsl_type *Void;
Curse you, C keywords...
- } builtin_types;
- struct hlsl_type *builtin_void, builtin_int, *builtin_uint, *builtin_float;
I assume these are remnants of a previous version of the patch.
On Wed, May 20, 2020 at 3:18 AM Zebediah Figura z.figura12@gmail.com wrote:
@@ -633,17 +660,21 @@ static struct hlsl_ir_deref *new_array_deref(struct hlsl_ir_node *array, return NULL; }
- if (!(array = get_var_deref(array)))
return NULL;
- if (data_type->reg_size > 1)
- {
Doesn't this need to happen even for reg_size == 1 now that we're using a scalar offset?
struct hlsl_ir_constant *c;
struct hlsl_ir_node *mul;
- if (!(deref = d3dcompiler_alloc(sizeof(*deref))))
return NULL;
if (!(c = new_uint_constant(data_type->reg_size * 4, loc)))
return NULL;
list_add_after(&index->entry, &c->node.entry);
if (!(mul = new_binary_expr(HLSL_IR_BINOP_MUL, index, &c->node, loc)))
return NULL;
list_add_after(&c->node.entry, &mul->entry);
index = mul;
- }
- init_node(&deref->node, HLSL_IR_DEREF, data_type, loc);
- deref->src.type = HLSL_IR_DEREF_ARRAY;
- deref->src.v.array.array = array;
- deref->src.v.array.index = index;
- return deref;
- return new_deref(array, index, data_type, loc);
}
static void struct_var_initializer(struct list *list, struct hlsl_ir_var *var,
@@ -1513,12 +1490,6 @@ struct hlsl_ir_node *make_assignment(struct hlsl_ir_node *lhs, enum parse_assign lhs = lhs_inner; }
- if (!validate_lhs_deref(lhs))
- {
d3dcompiler_free(assign);
return NULL;
- }
- TRACE("Creating proper assignment expression.\n"); if (writemask == BWRITERSP_WRITEMASK_ALL) type = lhs->data_type;
@@ -1562,26 +1533,12 @@ struct hlsl_ir_node *make_assignment(struct hlsl_ir_node *lhs, enum parse_assign enum hlsl_ir_expr_op op = op_from_assignment(assign_op); struct hlsl_ir_node *expr;
if (assign->lhs.type != HLSL_IR_DEREF_VAR)
{
FIXME("LHS expression not supported in compound assignments yet.\n");
assign->rhs = rhs;
}
else
{
TRACE("Adding an expression for the compound assignment.\n");
expr = new_binary_expr(op, lhs, rhs, lhs->loc);
list_add_after(&rhs->entry, &expr->entry);
assign->rhs = expr;
}
- }
- else
- {
list_remove(&lhs->entry);
/* Don't recursively free the deref; we just copied its members. */
d3dcompiler_free(lhs);
assign->rhs = rhs;
TRACE("Adding an expression for the compound assignment.\n");
expr = new_binary_expr(op, lhs, rhs, lhs->loc);
list_add_after(&rhs->entry, &expr->entry);
}rhs = expr;
- assign->rhs = rhs;
I guess this is one of the cases where using a struct hlsl_deref for both lvalues and rvalues comes in handy (to some degree).