vkd3d-shader/hlsl: Store the flatten type in struct hlsl_ir_if.

This commit is contained in:
Shaun Ren
2025-07-10 14:55:41 -04:00
committed by Henri Verbeet
parent cf688f87f1
commit 200e66ba4f
Notes: Henri Verbeet 2025-10-30 19:59:51 +01:00
Approved-by: Francisco Casas (@fcasas)
Approved-by: Elizabeth Figura (@zfigura)
Approved-by: Henri Verbeet (@hverbeet)
Merge-Request: https://gitlab.winehq.org/wine/vkd3d/-/merge_requests/1732
5 changed files with 47 additions and 19 deletions

View File

@@ -1976,14 +1976,15 @@ static struct hlsl_ir_node *hlsl_new_error_expr(struct hlsl_ctx *ctx)
return hlsl_new_expr(ctx, HLSL_OP0_ERROR, operands, ctx->builtin_types.error, &loc);
}
struct hlsl_ir_node *hlsl_new_if(struct hlsl_ctx *ctx, struct hlsl_ir_node *condition,
struct hlsl_block *then_block, struct hlsl_block *else_block, const struct vkd3d_shader_location *loc)
struct hlsl_ir_node *hlsl_new_if(struct hlsl_ctx *ctx, struct hlsl_ir_node *condition, struct hlsl_block *then_block,
struct hlsl_block *else_block, enum hlsl_if_flatten_type flatten_type, const struct vkd3d_shader_location *loc)
{
struct hlsl_ir_if *iff;
if (!(iff = hlsl_alloc(ctx, sizeof(*iff))))
return NULL;
init_node(&iff->node, HLSL_IR_IF, NULL, loc);
iff->flatten_type = flatten_type;
hlsl_src_from_node(&iff->condition, condition);
hlsl_block_init(&iff->then_block);
hlsl_block_add_block(&iff->then_block, then_block);
@@ -1993,10 +1994,11 @@ struct hlsl_ir_node *hlsl_new_if(struct hlsl_ctx *ctx, struct hlsl_ir_node *cond
return &iff->node;
}
void hlsl_block_add_if(struct hlsl_ctx *ctx, struct hlsl_block *block, struct hlsl_ir_node *condition,
struct hlsl_block *then_block, struct hlsl_block *else_block, const struct vkd3d_shader_location *loc)
void hlsl_block_add_if(struct hlsl_ctx *ctx, struct hlsl_block *block,
struct hlsl_ir_node *condition, struct hlsl_block *then_block, struct hlsl_block *else_block,
enum hlsl_if_flatten_type flatten_type, const struct vkd3d_shader_location *loc)
{
struct hlsl_ir_node *instr = hlsl_new_if(ctx, condition, then_block, else_block, loc);
struct hlsl_ir_node *instr = hlsl_new_if(ctx, condition, then_block, else_block, flatten_type, loc);
if (instr)
{
@@ -2674,7 +2676,8 @@ static struct hlsl_ir_node *clone_if(struct hlsl_ctx *ctx, struct clone_instr_ma
return NULL;
}
if (!(dst = hlsl_new_if(ctx, map_instr(map, src->condition.node), &then_block, &else_block, &src->node.loc)))
if (!(dst = hlsl_new_if(ctx, map_instr(map, src->condition.node),
&then_block, &else_block, src->flatten_type, &src->node.loc)))
{
hlsl_block_cleanup(&then_block);
hlsl_block_cleanup(&else_block);

View File

@@ -661,12 +661,20 @@ struct hlsl_ir_call
struct hlsl_ir_function_decl *decl;
};
enum hlsl_if_flatten_type
{
HLSL_IF_FLATTEN_DEFAULT,
HLSL_IF_FORCE_FLATTEN,
HLSL_IF_FORCE_BRANCH
};
struct hlsl_ir_if
{
struct hlsl_ir_node node;
struct hlsl_src condition;
struct hlsl_block then_block;
struct hlsl_block else_block;
enum hlsl_if_flatten_type flatten_type;
};
enum hlsl_loop_unroll_type
@@ -1586,8 +1594,9 @@ struct hlsl_ir_node *hlsl_block_add_expr(struct hlsl_ctx *ctx, struct hlsl_block
struct hlsl_type *data_type, const struct vkd3d_shader_location *loc);
struct hlsl_ir_node *hlsl_block_add_float_constant(struct hlsl_ctx *ctx, struct hlsl_block *block,
float f, const struct vkd3d_shader_location *loc);
void hlsl_block_add_if(struct hlsl_ctx *ctx, struct hlsl_block *block, struct hlsl_ir_node *condition,
struct hlsl_block *then_block, struct hlsl_block *else_block, const struct vkd3d_shader_location *loc);
void hlsl_block_add_if(struct hlsl_ctx *ctx, struct hlsl_block *block,
struct hlsl_ir_node *condition, struct hlsl_block *then_block, struct hlsl_block *else_block,
enum hlsl_if_flatten_type flatten_type, const struct vkd3d_shader_location *loc);
struct hlsl_ir_node *hlsl_block_add_index(struct hlsl_ctx *ctx, struct hlsl_block *block,
struct hlsl_ir_node *val, struct hlsl_ir_node *idx, const struct vkd3d_shader_location *loc);
struct hlsl_ir_node *hlsl_block_add_int_constant(struct hlsl_ctx *ctx, struct hlsl_block *block,
@@ -1704,8 +1713,8 @@ struct hlsl_ir_node *hlsl_new_copy(struct hlsl_ctx *ctx, struct hlsl_ir_node *no
struct hlsl_ir_function_decl *hlsl_new_func_decl(struct hlsl_ctx *ctx,
struct hlsl_type *return_type, const struct hlsl_func_parameters *parameters,
const struct hlsl_semantic *semantic, const struct vkd3d_shader_location *loc);
struct hlsl_ir_node *hlsl_new_if(struct hlsl_ctx *ctx, struct hlsl_ir_node *condition,
struct hlsl_block *then_block, struct hlsl_block *else_block, const struct vkd3d_shader_location *loc);
struct hlsl_ir_node *hlsl_new_if(struct hlsl_ctx *ctx, struct hlsl_ir_node *condition, struct hlsl_block *then_block,
struct hlsl_block *else_block, enum hlsl_if_flatten_type flatten_type, const struct vkd3d_shader_location *loc);
struct hlsl_type *hlsl_new_stream_output_type(struct hlsl_ctx *ctx,
enum hlsl_so_object_type so_type, struct hlsl_type *type);
struct hlsl_ir_node *hlsl_new_ternary_expr(struct hlsl_ctx *ctx, enum hlsl_ir_expr_op op,

View File

@@ -471,7 +471,7 @@ static void append_conditional_break(struct hlsl_ctx *ctx, struct hlsl_block *co
hlsl_block_init(&then_block);
hlsl_block_add_jump(ctx, &then_block, HLSL_IR_JUMP_BREAK, NULL, &condition->loc);
hlsl_block_add_if(ctx, cond_block, not, &then_block, NULL, &condition->loc);
hlsl_block_add_if(ctx, cond_block, not, &then_block, NULL, HLSL_IF_FLATTEN_DEFAULT, &condition->loc);
}
static void check_attribute_list_for_duplicates(struct hlsl_ctx *ctx, const struct parse_attribute_list *attrs)
@@ -9139,6 +9139,7 @@ selection_statement:
{
struct hlsl_ir_node *condition = node_from_block($4);
const struct parse_attribute_list *attributes = &$1;
enum hlsl_if_flatten_type flatten_type = HLSL_IF_FLATTEN_DEFAULT;
unsigned int i;
check_attribute_list_for_duplicates(ctx, attributes);
@@ -9147,10 +9148,19 @@ selection_statement:
{
const struct hlsl_attribute *attr = attributes->attrs[i];
if (!strcmp(attr->name, "branch")
|| !strcmp(attr->name, "flatten"))
if (!strcmp(attr->name, "branch"))
{
hlsl_warning(ctx, &@1, VKD3D_SHADER_WARNING_HLSL_IGNORED_ATTRIBUTE, "Unhandled attribute '%s'.", attr->name);
if (flatten_type == HLSL_IF_FORCE_FLATTEN)
hlsl_error(ctx, &@1, VKD3D_SHADER_ERROR_HLSL_INVALID_SYNTAX,
"The 'branch' and 'flatten' attributes are mutually exclusive.");
flatten_type = HLSL_IF_FORCE_BRANCH;
}
else if (!strcmp(attr->name, "flatten"))
{
if (flatten_type == HLSL_IF_FORCE_BRANCH)
hlsl_error(ctx, &@1, VKD3D_SHADER_ERROR_HLSL_INVALID_SYNTAX,
"The 'branch' and 'flatten' attributes are mutually exclusive.");
flatten_type = HLSL_IF_FORCE_FLATTEN;
}
else
{
@@ -9158,10 +9168,16 @@ selection_statement:
}
}
if (flatten_type == HLSL_IF_FORCE_BRANCH && hlsl_version_lt(ctx, 2, 1))
{
hlsl_error(ctx, &@1, VKD3D_SHADER_ERROR_HLSL_INCOMPATIBLE_PROFILE,
"The 'branch' attribute requires shader model 2.1 or higher.");
}
check_condition_type(ctx, condition);
condition = add_cast(ctx, $4, condition, hlsl_get_scalar_type(ctx, HLSL_TYPE_BOOL), &@4);
hlsl_block_add_if(ctx, $4, condition, $6.then_block, $6.else_block, &@2);
hlsl_block_add_if(ctx, $4, condition, $6.then_block, $6.else_block, flatten_type, &@2);
destroy_block($6.then_block);
destroy_block($6.else_block);

View File

@@ -1060,7 +1060,7 @@ static void insert_early_return_break(struct hlsl_ctx *ctx,
hlsl_block_add_jump(ctx, &then_block, HLSL_IR_JUMP_BREAK, NULL, &cf_instr->loc);
if (!(iff = hlsl_new_if(ctx, &load->node, &then_block, NULL, &cf_instr->loc)))
if (!(iff = hlsl_new_if(ctx, &load->node, &then_block, NULL, HLSL_IF_FLATTEN_DEFAULT, &cf_instr->loc)))
return;
list_add_after(&load->node.entry, &iff->entry);
}
@@ -1245,7 +1245,7 @@ static bool lower_return(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *fun
load = hlsl_block_add_simple_load(ctx, block, func->early_return_var, &cf_instr->loc);
not = hlsl_block_add_unary_expr(ctx, block, HLSL_OP1_LOGIC_NOT, load, &cf_instr->loc);
hlsl_block_add_if(ctx, block, not, &then_block, NULL, &cf_instr->loc);
hlsl_block_add_if(ctx, block, not, &then_block, NULL, HLSL_IF_FLATTEN_DEFAULT, &cf_instr->loc);
}
return has_early_return;
@@ -13866,7 +13866,7 @@ static struct hlsl_ir_if *loop_unrolling_generate_var_check(struct hlsl_ctx *ctx
load = hlsl_block_add_simple_load(ctx, dst, var, loc);
cond = hlsl_block_add_unary_expr(ctx, dst, HLSL_OP1_LOGIC_NOT, load, loc);
if (!(iff = hlsl_new_if(ctx, cond, &then_block, NULL, loc)))
if (!(iff = hlsl_new_if(ctx, cond, &then_block, NULL, HLSL_IF_FLATTEN_DEFAULT, loc)))
return NULL;
hlsl_block_add_instr(dst, iff);

View File

@@ -58,7 +58,7 @@ float main() : sv_target
return float4(0.9, 0.8, 0.7, 0.6);
}
[pixel shader fail todo]
[pixel shader fail]
float4 u;
float main() : sv_target