vkd3d-shader/hlsl: Write all writemask components for PSIZE and FOG outputs.

Matching fxc/d3dcompiler.
This commit is contained in:
Elizabeth Figura 2024-11-04 22:46:56 -06:00 committed by Henri Verbeet
parent a10ee075ff
commit 4290d85397
Notes: Henri Verbeet 2024-11-05 20:06:25 +01:00
Approved-by: Henri Verbeet (@hverbeet)
Merge-Request: https://gitlab.winehq.org/wine/vkd3d/-/merge_requests/1247
2 changed files with 23 additions and 8 deletions

View File

@ -6519,16 +6519,22 @@ static void generate_vsir_signature_entry(struct hlsl_ctx *ctx, struct vsir_prog
sysval = VKD3D_SHADER_SV_POSITION; sysval = VKD3D_SHADER_SV_POSITION;
} }
mask = (1 << var->data_type->dimx) - 1;
if (!ascii_strcasecmp(var->semantic.name, "PSIZE") && output if (!ascii_strcasecmp(var->semantic.name, "PSIZE") && output
&& program->shader_version.type == VKD3D_SHADER_TYPE_VERTEX && var->data_type->dimx > 1) && program->shader_version.type == VKD3D_SHADER_TYPE_VERTEX)
{
if (var->data_type->dimx > 1)
hlsl_error(ctx, &var->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_SEMANTIC, hlsl_error(ctx, &var->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_SEMANTIC,
"PSIZE output must have only 1 component in this shader model."); "PSIZE output must have only 1 component in this shader model.");
/* For some reason the writemask has all components set. */
mask = VKD3DSP_WRITEMASK_ALL;
}
if (!ascii_strcasecmp(var->semantic.name, "FOG") && output && program->shader_version.major < 3 if (!ascii_strcasecmp(var->semantic.name, "FOG") && output && program->shader_version.major < 3
&& program->shader_version.type == VKD3D_SHADER_TYPE_VERTEX && var->data_type->dimx > 1) && program->shader_version.type == VKD3D_SHADER_TYPE_VERTEX && var->data_type->dimx > 1)
hlsl_error(ctx, &var->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_SEMANTIC, hlsl_error(ctx, &var->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_SEMANTIC,
"FOG output must have only 1 component in this shader model."); "FOG output must have only 1 component in this shader model.");
mask = (1 << var->data_type->dimx) - 1;
use_mask = mask; /* FIXME: retrieve use mask accurately. */ use_mask = mask; /* FIXME: retrieve use mask accurately. */
component_type = VKD3D_SHADER_COMPONENT_FLOAT; component_type = VKD3D_SHADER_COMPONENT_FLOAT;
} }
@ -7251,6 +7257,8 @@ static void sm1_generate_vsir_init_dst_param_from_deref(struct hlsl_ctx *ctx,
if (deref->var->is_output_semantic) if (deref->var->is_output_semantic)
{ {
const char *semantic_name = deref->var->semantic.name;
version.major = ctx->profile->major_version; version.major = ctx->profile->major_version;
version.minor = ctx->profile->minor_version; version.minor = ctx->profile->minor_version;
version.type = ctx->profile->type; version.type = ctx->profile->type;
@ -7260,7 +7268,7 @@ static void sm1_generate_vsir_init_dst_param_from_deref(struct hlsl_ctx *ctx,
type = VKD3DSPR_TEMP; type = VKD3DSPR_TEMP;
register_index = 0; register_index = 0;
} }
else if (!sm1_register_from_semantic_name(&version, deref->var->semantic.name, else if (!sm1_register_from_semantic_name(&version, semantic_name,
deref->var->semantic.index, true, &type, &register_index)) deref->var->semantic.index, true, &type, &register_index))
{ {
VKD3D_ASSERT(reg.allocated); VKD3D_ASSERT(reg.allocated);
@ -7269,6 +7277,14 @@ static void sm1_generate_vsir_init_dst_param_from_deref(struct hlsl_ctx *ctx,
} }
else else
writemask = (1u << deref->var->data_type->dimx) - 1; writemask = (1u << deref->var->data_type->dimx) - 1;
if (version.type == VKD3D_SHADER_TYPE_PIXEL && (!ascii_strcasecmp(semantic_name, "PSIZE")
|| (!ascii_strcasecmp(semantic_name, "FOG") && version.major < 3)))
{
/* These are always 1-component, but for some reason are written
* with a writemask containing all components. */
writemask = VKD3DSP_WRITEMASK_ALL;
}
} }
else else
VKD3D_ASSERT(reg.allocated); VKD3D_ASSERT(reg.allocated);

View File

@ -438,7 +438,7 @@ static void check_signature_element(const struct vkd3d_shader_signature_element
ok(element->component_type == expect->component_type, "Got component type %#x.\n", element->component_type); ok(element->component_type == expect->component_type, "Got component type %#x.\n", element->component_type);
ok(element->register_index == expect->register_index, "Got register index %u.\n", element->register_index); ok(element->register_index == expect->register_index, "Got register index %u.\n", element->register_index);
ok(element->mask == expect->mask, "Got mask %#x.\n", element->mask); ok(element->mask == expect->mask, "Got mask %#x.\n", element->mask);
todo_if (expect->used_mask != expect->mask) todo_if (expect->used_mask != expect->mask && strcmp(expect->semantic_name, "PSIZE"))
ok(element->used_mask == expect->used_mask, "Got used mask %#x.\n", element->used_mask); ok(element->used_mask == expect->used_mask, "Got used mask %#x.\n", element->used_mask);
ok(element->min_precision == expect->min_precision, "Got minimum precision %#x.\n", element->min_precision); ok(element->min_precision == expect->min_precision, "Got minimum precision %#x.\n", element->min_precision);
} }
@ -574,8 +574,7 @@ static void test_scan_signatures(void)
{"TEXCOORD", 2, 0, VKD3D_SHADER_SV_NONE, VKD3D_SHADER_COMPONENT_FLOAT, 3, 0xf, 0xf}, {"TEXCOORD", 2, 0, VKD3D_SHADER_SV_NONE, VKD3D_SHADER_COMPONENT_FLOAT, 3, 0xf, 0xf},
{"COLOR", 0, 0, VKD3D_SHADER_SV_NONE, VKD3D_SHADER_COMPONENT_FLOAT, 4, 0xf, 0xf}, {"COLOR", 0, 0, VKD3D_SHADER_SV_NONE, VKD3D_SHADER_COMPONENT_FLOAT, 4, 0xf, 0xf},
{"FOG", 0, 0, VKD3D_SHADER_SV_NONE, VKD3D_SHADER_COMPONENT_FLOAT, 5, 0xf, 0xf}, {"FOG", 0, 0, VKD3D_SHADER_SV_NONE, VKD3D_SHADER_COMPONENT_FLOAT, 5, 0xf, 0xf},
/* FIXME: This doesn't match native, which always declares and writes all 4 components. */ {"PSIZE", 0, 0, VKD3D_SHADER_SV_NONE, VKD3D_SHADER_COMPONENT_FLOAT, 6, 0xf, 0x1},
{"PSIZE", 0, 0, VKD3D_SHADER_SV_NONE, VKD3D_SHADER_COMPONENT_FLOAT, 6, 0x1, 0x1},
}; };
static const char ps1_source[] = static const char ps1_source[] =