diff --git a/libs/vkd3d-shader/hlsl.y b/libs/vkd3d-shader/hlsl.y index e34902952..4efa1cd28 100644 --- a/libs/vkd3d-shader/hlsl.y +++ b/libs/vkd3d-shader/hlsl.y @@ -544,16 +544,9 @@ static void check_loop_attributes(struct hlsl_ctx *ctx, const struct parse_attri hlsl_error(ctx, loc, VKD3D_SHADER_ERROR_HLSL_INVALID_SYNTAX, "Unroll attribute can't be used with 'fastopt' attribute."); } -static struct hlsl_default_value evaluate_static_expression(struct hlsl_ctx *ctx, - struct hlsl_block *block, struct hlsl_type *dst_type, const struct vkd3d_shader_location *loc) +static bool is_static_expression(struct hlsl_block *block) { - struct hlsl_default_value ret = {0}; struct hlsl_ir_node *node; - struct hlsl_block expr; - struct hlsl_src src; - - if (node_from_block(block)->data_type->class == HLSL_CLASS_ERROR) - return ret; LIST_FOR_EACH_ENTRY(node, &block->instrs, struct hlsl_ir_node, entry) { @@ -582,12 +575,28 @@ static struct hlsl_default_value evaluate_static_expression(struct hlsl_ctx *ctx case HLSL_IR_SWITCH: case HLSL_IR_STATEBLOCK_CONSTANT: case HLSL_IR_SYNC: - hlsl_error(ctx, &node->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_SYNTAX, - "Expected literal expression."); - break; + return false; } } + return true; +} + +static struct hlsl_default_value evaluate_static_expression(struct hlsl_ctx *ctx, + struct hlsl_block *block, struct hlsl_type *dst_type, const struct vkd3d_shader_location *loc) +{ + struct hlsl_default_value ret = {0}; + struct hlsl_ir_node *node; + struct hlsl_block expr; + struct hlsl_src src; + + if (node_from_block(block)->data_type->class == HLSL_CLASS_ERROR) + return ret; + + if (!is_static_expression(block)) + hlsl_error(ctx, &node_from_block(block)->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_SYNTAX, + "Expected literal expression."); + if (!hlsl_clone_block(ctx, &expr, &ctx->static_initializers)) return ret; hlsl_block_add_block(&expr, block); @@ -2670,7 +2679,7 @@ static struct hlsl_block *initialize_vars(struct hlsl_ctx *ctx, struct list *var if (v->initializer.args_count) { - bool is_default_values_initializer; + bool is_default_values_initializer, static_initialization; is_default_values_initializer = (ctx->cur_buffer != ctx->globals_buffer) || (var->storage_modifiers & HLSL_STORAGE_UNIFORM) @@ -2680,6 +2689,10 @@ static struct hlsl_block *initialize_vars(struct hlsl_ctx *ctx, struct list *var if (hlsl_type_is_shader(type)) is_default_values_initializer = false; + static_initialization = var->storage_modifiers & HLSL_STORAGE_STATIC + || (var->data_type->modifiers & HLSL_MODIFIER_CONST + && is_static_expression(v->initializer.instrs)); + if (is_default_values_initializer) { /* Default values might have been allocated already for another variable of the same name, @@ -2708,7 +2721,7 @@ static struct hlsl_block *initialize_vars(struct hlsl_ctx *ctx, struct list *var { hlsl_dump_var_default_values(var); } - else if (var->storage_modifiers & HLSL_STORAGE_STATIC) + else if (static_initialization) { hlsl_block_add_block(&ctx->static_initializers, v->initializer.instrs); } diff --git a/tests/hlsl/array-dimension.shader_test b/tests/hlsl/array-dimension.shader_test index 9977227cd..ae2519153 100644 --- a/tests/hlsl/array-dimension.shader_test +++ b/tests/hlsl/array-dimension.shader_test @@ -1,6 +1,6 @@ % Test what kinds of expressions are valid array dimensions. -[pixel shader todo] +[pixel shader] float4 main() : sv_target { const int dim = 4; @@ -18,7 +18,7 @@ float4 main() : sv_target } [test] -todo(sm<6) draw quad +draw quad probe (0, 0) f32(0.1, 0.1, 0.2, 0.4) [pixel shader fail] @@ -28,7 +28,7 @@ float a[CompileShader(ps_2_0, main())]; float4 main() : sv_target { return 0; } -[pixel shader todo] +[pixel shader] float4 main() : sv_target { const uint cap = 4; @@ -37,7 +37,7 @@ float4 main() : sv_target } [test] -todo(sm<6) draw quad +draw quad probe (0, 0) f32(1, 2, 3, 4) [pixel shader fail] @@ -48,7 +48,7 @@ float4 main() : sv_target return float4(array[0], array[1], array[2], array[3]); } -[pixel shader todo(sm<6) fail(sm>=6)] +[pixel shader fail(sm>=6)] float4 main() : sv_target { const uint4 cap = uint4(2, 4, 1, 0); @@ -57,10 +57,10 @@ float4 main() : sv_target } [test] -todo(sm<6) draw quad +draw quad probe (0, 0) f32(1, 2, 3, 4) -[pixel shader todo(sm<6) fail(sm>=6)] +[pixel shader fail(sm>=6)] struct nya { float a, b; @@ -74,10 +74,10 @@ float4 main() : sv_target } [test] -todo(sm<6) draw quad +draw quad probe (0, 0) f32(1, 2, 3, 4) -[pixel shader todo(sm<6) fail(sm>=6)] +[pixel shader fail(sm>=6)] float4 main() : sv_target { const float cap = 4; @@ -86,7 +86,7 @@ float4 main() : sv_target } [test] -todo(sm<6) draw quad +draw quad probe (0, 0) f32(1, 2, 3, 4) [pixel shader fail]