From: Francisco Casas fcasas@codeweavers.com
Considering row vectors from row_major matrices as having a different layout as regular vectors, and error out in that case, is left as todo. --- libs/vkd3d-shader/hlsl.h | 4 +++ libs/vkd3d-shader/hlsl.y | 1 + libs/vkd3d-shader/hlsl_codegen.c | 34 +++++++++++++++++++++++++ tests/entry-point-semantics.shader_test | 6 ++--- 4 files changed, 42 insertions(+), 3 deletions(-)
diff --git a/libs/vkd3d-shader/hlsl.h b/libs/vkd3d-shader/hlsl.h index 968299fb..bca05f51 100644 --- a/libs/vkd3d-shader/hlsl.h +++ b/libs/vkd3d-shader/hlsl.h @@ -213,6 +213,10 @@ struct hlsl_semantic /* In case the variable or field that stores this semantic has already reported to use a * duplicated output semantic, this value stores the last reported index + 1. Otherwise it is 0. */ uint32_t reported_duplicated_output_next_index; + /* In case the variable or field that stores this semantic has already reported to use a + * duplicated input semantic with incompatible values, this value stores the last reported + * index + 1. Otherwise it is 0. */ + uint32_t reported_duplicated_input_incompatible_next_index; };
/* A field within a struct type declaration, used in hlsl_type.e.fields. */ diff --git a/libs/vkd3d-shader/hlsl.y b/libs/vkd3d-shader/hlsl.y index a148d207..dfef622c 100644 --- a/libs/vkd3d-shader/hlsl.y +++ b/libs/vkd3d-shader/hlsl.y @@ -4577,6 +4577,7 @@ semantic: $$.index = atoi(p); $$.reported_missing = false; $$.reported_duplicated_output_next_index = 0; + $$.reported_duplicated_input_incompatible_next_index = 0; *p = 0; }
diff --git a/libs/vkd3d-shader/hlsl_codegen.c b/libs/vkd3d-shader/hlsl_codegen.c index 76e9a126..c9f5507a 100644 --- a/libs/vkd3d-shader/hlsl_codegen.c +++ b/libs/vkd3d-shader/hlsl_codegen.c @@ -232,6 +232,27 @@ static void validate_field_semantic(struct hlsl_ctx *ctx, struct hlsl_struct_fie } }
+static enum hlsl_base_type base_type_get_semantic_equivalent(enum hlsl_base_type base) +{ + if (base == HLSL_TYPE_BOOL) + return HLSL_TYPE_UINT; + if (base == HLSL_TYPE_INT) + return HLSL_TYPE_UINT; + if (base == HLSL_TYPE_HALF) + return HLSL_TYPE_FLOAT; + return base; +} + +static bool types_are_semantic_equivalent(struct hlsl_ctx *ctx, const struct hlsl_type *type1, + const struct hlsl_type *type2) +{ + if (type1->dimx != type2->dimx) + return false; + + return base_type_get_semantic_equivalent(type1->base_type) + == base_type_get_semantic_equivalent(type2->base_type); +} + static struct hlsl_ir_var *add_semantic_var(struct hlsl_ctx *ctx, struct hlsl_ir_var *var, struct hlsl_type *type, unsigned int modifiers, struct hlsl_semantic *semantic, uint32_t index, bool output, const struct vkd3d_shader_location *loc) @@ -259,6 +280,19 @@ static struct hlsl_ir_var *add_semantic_var(struct hlsl_ctx *ctx, struct hlsl_ir semantic->reported_duplicated_output_next_index = index + 1; } } + else + { + if (index >= semantic->reported_duplicated_input_incompatible_next_index + && !types_are_semantic_equivalent(ctx, ext_var->data_type, type)) + { + hlsl_error(ctx, loc, VKD3D_SHADER_ERROR_HLSL_INVALID_SEMANTIC, + "Input semantic "%s%u" is used multiple times with incompatible types.", + semantic->name, index); + hlsl_note(ctx, &ext_var->loc, HLSL_LEVEL_ERROR, + "First declaration of "%s%u" is here.", semantic->name, index); + semantic->reported_duplicated_input_incompatible_next_index = index + 1; + } + }
hlsl_release_string_buffer(ctx, name); return ext_var; diff --git a/tests/entry-point-semantics.shader_test b/tests/entry-point-semantics.shader_test index ddbc5862..72a33efb 100644 --- a/tests/entry-point-semantics.shader_test +++ b/tests/entry-point-semantics.shader_test @@ -284,14 +284,14 @@ float4 main(in uint2 a : TEXCOORD0, in int2 b : TEXCOORD0, in int2x1 c : TEXCOOR shader model >= 4.0
-[pixel shader fail todo] +[pixel shader fail] float4 main(in float2 a : TEXCOORD0, in float3 b : TEXCOORD0) : sv_target { return 0.0; }
-[pixel shader fail todo] +[pixel shader fail] float4 main(in float2 a : TEXCOORD0, in int2 b : TEXCOORD0) : sv_target { return 0.0; @@ -306,7 +306,7 @@ float4 main(in float2 a : TEXCOORD0, row_major float1x2 b : TEXCOORD0) : sv_targ return 0.0; }
-[pixel shader fail todo] +[pixel shader fail] float4 main(in float2 a : TEXCOORD0, row_major float2x1 b : TEXCOORD0) : sv_target { return 0.0;