From d6c78db132503243a003082c10a9169e322b7641 Mon Sep 17 00:00:00 2001 From: Alistair Leslie-Hughes Date: Thu, 24 Jul 2025 06:52:52 +1000 Subject: [PATCH] Updated vkd3d to a4c25b81c59ae783a94c1b25714eb080231b86bd. --- libs/vkd3d/libs/vkd3d-shader/d3d_asm.c | 16 +- libs/vkd3d/libs/vkd3d-shader/d3dbc.c | 5 +- libs/vkd3d/libs/vkd3d-shader/dxil.c | 50 ++- libs/vkd3d/libs/vkd3d-shader/glsl.c | 16 +- libs/vkd3d/libs/vkd3d-shader/hlsl.c | 16 +- libs/vkd3d/libs/vkd3d-shader/hlsl.h | 9 +- libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c | 287 ++++++++++-------- libs/vkd3d/libs/vkd3d-shader/ir.c | 88 ++++-- libs/vkd3d/libs/vkd3d-shader/msl.c | 10 +- libs/vkd3d/libs/vkd3d-shader/spirv.c | 60 ++-- libs/vkd3d/libs/vkd3d-shader/tpf.c | 41 +-- .../libs/vkd3d-shader/vkd3d_shader_main.c | 59 ++-- .../libs/vkd3d-shader/vkd3d_shader_private.h | 58 ++-- 13 files changed, 384 insertions(+), 331 deletions(-) diff --git a/libs/vkd3d/libs/vkd3d-shader/d3d_asm.c b/libs/vkd3d/libs/vkd3d-shader/d3d_asm.c index 5e3e7daab83..c213007f2b4 100644 --- a/libs/vkd3d/libs/vkd3d-shader/d3d_asm.c +++ b/libs/vkd3d/libs/vkd3d-shader/d3d_asm.c @@ -388,13 +388,7 @@ static void shader_print_data_type(struct vkd3d_d3d_asm_compiler *compiler, enum { static const char *const data_type_names[] = { - [VKD3D_DATA_UNORM ] = "unorm", - [VKD3D_DATA_SNORM ] = "snorm", - [VKD3D_DATA_OPAQUE ] = "opaque", - [VKD3D_DATA_MIXED ] = "mixed", - [VKD3D_DATA_CONTINUED] = "", - [VKD3D_DATA_UNUSED ] = "", - [VKD3D_DATA_BOOL ] = "bool", + [VSIR_DATA_BOOL ] = "bool", [VSIR_DATA_F16 ] = "half", [VSIR_DATA_F32 ] = "float", [VSIR_DATA_F64 ] = "double", @@ -403,6 +397,12 @@ static void shader_print_data_type(struct vkd3d_d3d_asm_compiler *compiler, enum [VSIR_DATA_U16 ] = "uint16", [VSIR_DATA_U32 ] = "uint", [VSIR_DATA_U64 ] = "uint64", + [VSIR_DATA_SNORM ] = "snorm", + [VSIR_DATA_UNORM ] = "unorm", + [VSIR_DATA_OPAQUE ] = "opaque", + [VSIR_DATA_MIXED ] = "mixed", + [VSIR_DATA_CONTINUED] = "", + [VSIR_DATA_UNUSED ] = "", }; if (type < ARRAY_SIZE(data_type_names)) @@ -957,7 +957,7 @@ static void shader_print_reg_type(struct vkd3d_d3d_asm_compiler *compiler, return; } - if (reg->data_type == VKD3D_DATA_UNUSED) + if (reg->data_type == VSIR_DATA_UNUSED) return; if (reg->dimension < ARRAY_SIZE(dimensions)) diff --git a/libs/vkd3d/libs/vkd3d-shader/d3dbc.c b/libs/vkd3d/libs/vkd3d-shader/d3dbc.c index 49e1a529369..dd13757bf59 100644 --- a/libs/vkd3d/libs/vkd3d-shader/d3dbc.c +++ b/libs/vkd3d/libs/vkd3d-shader/d3dbc.c @@ -1685,7 +1685,7 @@ static const struct vkd3d_sm1_opcode_info *shader_sm1_get_opcode_info_from_vsir_ if (ins->dst_count != info->dst_count) { vkd3d_shader_error(d3dbc->message_context, &ins->location, VKD3D_SHADER_ERROR_D3DBC_INVALID_REGISTER_COUNT, - "Invalid destination parameter count %u for instruction \"%s\" (%#x); expected %u.", + "Invalid destination parameter count %zu for instruction \"%s\" (%#x); expected %u.", ins->dst_count, vsir_opcode_get_name(ins->opcode, ""), ins->opcode, info->dst_count); d3dbc->failed = true; return NULL; @@ -1693,7 +1693,7 @@ static const struct vkd3d_sm1_opcode_info *shader_sm1_get_opcode_info_from_vsir_ if (ins->src_count != info->src_count) { vkd3d_shader_error(d3dbc->message_context, &ins->location, VKD3D_SHADER_ERROR_D3DBC_INVALID_REGISTER_COUNT, - "Invalid source parameter count %u for instruction \"%s\" (%#x); expected %u.", + "Invalid source parameter count %zu for instruction \"%s\" (%#x); expected %u.", ins->src_count, vsir_opcode_get_name(ins->opcode, ""), ins->opcode, info->src_count); d3dbc->failed = true; return NULL; @@ -2018,6 +2018,7 @@ static void d3dbc_write_vsir_instruction(struct d3dbc_compiler *d3dbc, const str case VSIR_OP_SINCOS: case VSIR_OP_SLT: case VSIR_OP_TEXLD: + case VSIR_OP_TEXLDL: case VSIR_OP_TEXLDD: d3dbc_write_instruction(d3dbc, ins); break; diff --git a/libs/vkd3d/libs/vkd3d-shader/dxil.c b/libs/vkd3d/libs/vkd3d-shader/dxil.c index c3dd606f00f..66e3c1ecd36 100644 --- a/libs/vkd3d/libs/vkd3d-shader/dxil.c +++ b/libs/vkd3d/libs/vkd3d-shader/dxil.c @@ -2480,7 +2480,7 @@ static enum vsir_data_type vsir_data_type_from_dxil(const struct sm6_type *type) switch (type->u.width) { case 1: - return VKD3D_DATA_BOOL; + return VSIR_DATA_BOOL; case 8: return VSIR_DATA_U8; case 16: @@ -4473,7 +4473,7 @@ static void sm6_parser_emit_atomicrmw(struct sm6_parser *sm6, const struct dxil_ dst_param_init(&dst_params[0]); dst_params[1].reg = reg; - dst_params[1].reg.data_type = VKD3D_DATA_UNUSED; + dst_params[1].reg.data_type = VSIR_DATA_UNUSED; dst_params[1].reg.idx[1].rel_addr = NULL; dst_params[1].reg.idx[1].offset = ~0u; dst_params[1].reg.idx_count = 1; @@ -5301,7 +5301,7 @@ static void sm6_parser_emit_dx_stream(struct sm6_parser *sm6, enum dx_intrinsic_ "Output stream index %u is invalid.", i); } - register_init_with_id(&src_param->reg, VKD3DSPR_STREAM, VKD3D_DATA_UNUSED, i); + register_init_with_id(&src_param->reg, VKD3DSPR_STREAM, VSIR_DATA_UNUSED, i); src_param_init(src_param); if (op == DX_EMIT_THEN_CUT_STREAM) @@ -6009,7 +6009,7 @@ static void sm6_parser_emit_dx_get_sample_count(struct sm6_parser *sm6, enum dx_ src_param_init(src_param); instruction_dst_param_init_ssa_scalar(ins, sm6); - ins->dst->reg.data_type = VSIR_DATA_F32; + ins->dst->reg.data_type = VSIR_DATA_U32; } static void sm6_parser_emit_dx_get_sample_pos(struct sm6_parser *sm6, enum dx_intrinsic_opcode op, @@ -9041,25 +9041,25 @@ static enum vkd3d_shader_resource_type shader_resource_type_from_dxil_resource_k static const enum vsir_data_type data_type_table[] = { - [COMPONENT_TYPE_INVALID] = VKD3D_DATA_UNUSED, - [COMPONENT_TYPE_I1] = VKD3D_DATA_UNUSED, + [COMPONENT_TYPE_INVALID] = VSIR_DATA_UNUSED, + [COMPONENT_TYPE_I1] = VSIR_DATA_UNUSED, [COMPONENT_TYPE_I16] = VSIR_DATA_I32, [COMPONENT_TYPE_U16] = VSIR_DATA_U32, [COMPONENT_TYPE_I32] = VSIR_DATA_I32, [COMPONENT_TYPE_U32] = VSIR_DATA_U32, - [COMPONENT_TYPE_I64] = VKD3D_DATA_UNUSED, - [COMPONENT_TYPE_U64] = VKD3D_DATA_UNUSED, + [COMPONENT_TYPE_I64] = VSIR_DATA_UNUSED, + [COMPONENT_TYPE_U64] = VSIR_DATA_UNUSED, [COMPONENT_TYPE_F16] = VSIR_DATA_F32, [COMPONENT_TYPE_F32] = VSIR_DATA_F32, [COMPONENT_TYPE_F64] = VSIR_DATA_F64, - [COMPONENT_TYPE_SNORMF16] = VKD3D_DATA_SNORM, - [COMPONENT_TYPE_UNORMF16] = VKD3D_DATA_UNORM, - [COMPONENT_TYPE_SNORMF32] = VKD3D_DATA_SNORM, - [COMPONENT_TYPE_UNORMF32] = VKD3D_DATA_UNORM, + [COMPONENT_TYPE_SNORMF16] = VSIR_DATA_SNORM, + [COMPONENT_TYPE_UNORMF16] = VSIR_DATA_UNORM, + [COMPONENT_TYPE_SNORMF32] = VSIR_DATA_SNORM, + [COMPONENT_TYPE_UNORMF32] = VSIR_DATA_UNORM, [COMPONENT_TYPE_SNORMF64] = VSIR_DATA_F64, [COMPONENT_TYPE_UNORMF64] = VSIR_DATA_F64, - [COMPONENT_TYPE_PACKEDS8X32] = VKD3D_DATA_UNUSED, - [COMPONENT_TYPE_PACKEDU8X32] = VKD3D_DATA_UNUSED, + [COMPONENT_TYPE_PACKEDS8X32] = VSIR_DATA_UNUSED, + [COMPONENT_TYPE_PACKEDU8X32] = VSIR_DATA_UNUSED, }; static enum vsir_data_type vsir_data_type_from_dxil_component_type(enum dxil_component_type type, @@ -9067,9 +9067,8 @@ static enum vsir_data_type vsir_data_type_from_dxil_component_type(enum dxil_com { enum vsir_data_type data_type; - if (type >= ARRAY_SIZE(data_type_table) || (data_type = data_type_table[type]) == VKD3D_DATA_UNUSED) + if (type >= ARRAY_SIZE(data_type_table) || (data_type = data_type_table[type]) == VSIR_DATA_UNUSED) { - FIXME("Unhandled component type %u.\n", type); vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_INVALID_RESOURCES, "Resource descriptor component type %u is unhandled.", type); return VSIR_DATA_F32; @@ -9089,7 +9088,7 @@ static bool resources_load_additional_values(struct resource_additional_values * { unsigned int i, operand_count, tag, value; - info->data_type = VKD3D_DATA_UNUSED; + info->data_type = VSIR_DATA_UNUSED; info->byte_stride = 0; if (node->operand_count & 1) @@ -9199,9 +9198,8 @@ static struct vkd3d_shader_resource *sm6_parser_resources_load_common_info(struc if (kind == RESOURCE_KIND_TYPEDBUFFER || resource_kind_is_texture(kind)) { - if (resource_values.data_type == VKD3D_DATA_UNUSED) + if (resource_values.data_type == VSIR_DATA_UNUSED) { - WARN("No data type defined.\n"); vkd3d_shader_parser_error(&sm6->p, VKD3D_SHADER_ERROR_DXIL_INVALID_RESOURCES, "A typed resource has no data type."); } @@ -9303,9 +9301,9 @@ static enum vkd3d_result sm6_parser_resources_load_srv(struct sm6_parser *sm6, d->resource_type = ins->resource_type; d->kind = kind; d->reg_type = VKD3DSPR_RESOURCE; - d->reg_data_type = VKD3D_DATA_UNUSED; + d->reg_data_type = VSIR_DATA_UNUSED; d->resource_data_type = (ins->opcode == VSIR_OP_DCL) - ? ins->declaration.semantic.resource_data_type[0] : VKD3D_DATA_UNUSED; + ? ins->declaration.semantic.resource_data_type[0] : VSIR_DATA_UNUSED; init_resource_declaration(resource, VKD3DSPR_RESOURCE, d->reg_data_type, d->id, &d->range); @@ -9377,9 +9375,9 @@ static enum vkd3d_result sm6_parser_resources_load_uav(struct sm6_parser *sm6, d->resource_type = ins->resource_type; d->kind = values[0]; d->reg_type = VKD3DSPR_UAV; - d->reg_data_type = VKD3D_DATA_UNUSED; + d->reg_data_type = VSIR_DATA_UNUSED; d->resource_data_type = (ins->opcode == VSIR_OP_DCL_UAV_TYPED) - ? ins->declaration.semantic.resource_data_type[0] : VKD3D_DATA_UNUSED; + ? ins->declaration.semantic.resource_data_type[0] : VSIR_DATA_UNUSED; init_resource_declaration(resource, VKD3DSPR_UAV, d->reg_data_type, d->id, &d->range); @@ -9483,7 +9481,7 @@ static enum vkd3d_result sm6_parser_resources_load_sampler(struct sm6_parser *sm ins->declaration.sampler.src.modifiers = VKD3DSPSM_NONE; reg = &ins->declaration.sampler.src.reg; - vsir_register_init(reg, VKD3DSPR_SAMPLER, VKD3D_DATA_UNUSED, 3); + vsir_register_init(reg, VKD3DSPR_SAMPLER, VSIR_DATA_UNUSED, 3); reg->idx[0].offset = d->id; reg->idx[1].offset = d->range.first; reg->idx[2].offset = d->range.last; @@ -9493,8 +9491,8 @@ static enum vkd3d_result sm6_parser_resources_load_sampler(struct sm6_parser *sm d->resource_type = ins->resource_type; d->kind = RESOURCE_KIND_SAMPLER; d->reg_type = VKD3DSPR_SAMPLER; - d->reg_data_type = VKD3D_DATA_UNUSED; - d->resource_data_type = VKD3D_DATA_UNUSED; + d->reg_data_type = VSIR_DATA_UNUSED; + d->resource_data_type = VSIR_DATA_UNUSED; return VKD3D_OK; } diff --git a/libs/vkd3d/libs/vkd3d-shader/glsl.c b/libs/vkd3d/libs/vkd3d-shader/glsl.c index dc68e1792d9..e57a4aa2731 100644 --- a/libs/vkd3d/libs/vkd3d-shader/glsl.c +++ b/libs/vkd3d/libs/vkd3d-shader/glsl.c @@ -330,9 +330,9 @@ static void glsl_src_cleanup(struct glsl_src *src, struct vkd3d_string_buffer_ca static void shader_glsl_print_bitcast(struct vkd3d_string_buffer *dst, struct vkd3d_glsl_generator *gen, const char *src, enum vsir_data_type dst_data_type, enum vsir_data_type src_data_type, unsigned int size) { - if (dst_data_type == VKD3D_DATA_UNORM || dst_data_type == VKD3D_DATA_SNORM) + if (dst_data_type == VSIR_DATA_UNORM || dst_data_type == VSIR_DATA_SNORM) dst_data_type = VSIR_DATA_F32; - if (src_data_type == VKD3D_DATA_UNORM || src_data_type == VKD3D_DATA_SNORM) + if (src_data_type == VSIR_DATA_UNORM || src_data_type == VSIR_DATA_SNORM) src_data_type = VSIR_DATA_F32; if (dst_data_type == src_data_type) @@ -1175,8 +1175,8 @@ static void shader_glsl_store_uav_typed(struct vkd3d_glsl_generator *gen, const "Internal compiler error: Unhandled data type %#x.", data_type); /* fall through */ case VSIR_DATA_F32: - case VKD3D_DATA_UNORM: - case VKD3D_DATA_SNORM: + case VSIR_DATA_SNORM: + case VSIR_DATA_UNORM: vkd3d_string_buffer_printf(image_data, "vec4("); break; } @@ -1780,8 +1780,8 @@ static void shader_glsl_generate_uav_declaration(struct vkd3d_glsl_generator *ge uav->resource_data_type, uav->register_id); /* fall through */ case VSIR_DATA_F32: - case VKD3D_DATA_UNORM: - case VKD3D_DATA_SNORM: + case VSIR_DATA_SNORM: + case VSIR_DATA_UNORM: image_type_prefix = ""; read_format = "r32f"; break; @@ -1996,8 +1996,8 @@ static void shader_glsl_generate_sampler_declaration(struct vkd3d_glsl_generator switch (srv->resource_data_type) { case VSIR_DATA_F32: - case VKD3D_DATA_UNORM: - case VKD3D_DATA_SNORM: + case VSIR_DATA_SNORM: + case VSIR_DATA_UNORM: sampler_type_prefix = ""; break; case VSIR_DATA_I32: diff --git a/libs/vkd3d/libs/vkd3d-shader/hlsl.c b/libs/vkd3d/libs/vkd3d-shader/hlsl.c index 678ed324919..e2c68d4afb5 100644 --- a/libs/vkd3d/libs/vkd3d-shader/hlsl.c +++ b/libs/vkd3d/libs/vkd3d-shader/hlsl.c @@ -2998,7 +2998,6 @@ struct hlsl_ir_function_decl *hlsl_new_func_decl(struct hlsl_ctx *ctx, decl->return_type = return_type; decl->parameters = *parameters; decl->loc = *loc; - list_init(&decl->extern_vars); if (!hlsl_types_are_equal(return_type, ctx->builtin_types.Void)) { @@ -4066,20 +4065,23 @@ static void dump_instr(struct hlsl_ctx *ctx, struct vkd3d_string_buffer *buffer, } } -void hlsl_dump_function(struct hlsl_ctx *ctx, const struct hlsl_ir_function_decl *func) +void hlsl_dump_function(struct hlsl_ctx *ctx, const struct hlsl_ir_function_decl *func, + const char *description, const struct hlsl_block *processed_block) { struct vkd3d_string_buffer buffer; size_t i; vkd3d_string_buffer_init(&buffer); - vkd3d_string_buffer_printf(&buffer, "Dumping function %s.\n", func->func->name); + vkd3d_string_buffer_printf(&buffer, "Dumping %s \"%s\".\n", description, func->func->name); vkd3d_string_buffer_printf(&buffer, "Function parameters:\n"); for (i = 0; i < func->parameters.count; ++i) { dump_ir_var(ctx, &buffer, func->parameters.vars[i]); vkd3d_string_buffer_printf(&buffer, "\n"); } - if (func->has_body) + if (processed_block) + dump_block(ctx, &buffer, processed_block); + else if (func->has_body) dump_block(ctx, &buffer, &func->body); vkd3d_string_buffer_trace(&buffer); @@ -5009,8 +5011,8 @@ static void hlsl_ctx_cleanup(struct hlsl_ctx *ctx) vkd3d_free(ctx->constant_defs.regs); } -int hlsl_compile_shader(const struct vkd3d_shader_code *hlsl, const struct vkd3d_shader_compile_info *compile_info, - struct vkd3d_shader_code *out, struct vkd3d_shader_message_context *message_context) +int hlsl_compile_shader(const struct vkd3d_shader_compile_info *compile_info, + struct vkd3d_shader_message_context *message_context, struct vkd3d_shader_code *out) { enum vkd3d_shader_target_type target_type = compile_info->target_type; const struct vkd3d_shader_hlsl_source_info *hlsl_source_info; @@ -5062,7 +5064,7 @@ int hlsl_compile_shader(const struct vkd3d_shader_code *hlsl, const struct vkd3d if (!hlsl_ctx_init(&ctx, compile_info, profile, message_context)) return VKD3D_ERROR_OUT_OF_MEMORY; - if ((ret = hlsl_lexer_compile(&ctx, hlsl)) == 2) + if ((ret = hlsl_lexer_compile(&ctx, &compile_info->source)) == 2) { hlsl_ctx_cleanup(&ctx); return VKD3D_ERROR_OUT_OF_MEMORY; diff --git a/libs/vkd3d/libs/vkd3d-shader/hlsl.h b/libs/vkd3d/libs/vkd3d-shader/hlsl.h index 0dce2831c3e..47cc361a48a 100644 --- a/libs/vkd3d/libs/vkd3d-shader/hlsl.h +++ b/libs/vkd3d/libs/vkd3d-shader/hlsl.h @@ -645,12 +645,6 @@ struct hlsl_ir_function_decl * executed. Needed to deal with return statements in non-uniform control * flow, since some backends can't handle them. */ struct hlsl_ir_var *early_return_var; - - /* List of all the extern semantic variables; linked by the - * hlsl_ir_var.extern_entry fields. This exists as a convenience because - * it is often necessary to iterate all extern variables and these can be - * declared in as function parameters, or as the function return value. */ - struct list extern_vars; }; struct hlsl_ir_call @@ -1615,7 +1609,8 @@ struct hlsl_ir_node *hlsl_block_add_unary_expr(struct hlsl_ctx *ctx, struct hlsl void hlsl_block_cleanup(struct hlsl_block *block); bool hlsl_clone_block(struct hlsl_ctx *ctx, struct hlsl_block *dst_block, const struct hlsl_block *src_block); -void hlsl_dump_function(struct hlsl_ctx *ctx, const struct hlsl_ir_function_decl *func); +void hlsl_dump_function(struct hlsl_ctx *ctx, const struct hlsl_ir_function_decl *func, + const char *description, const struct hlsl_block *processed_block); void hlsl_dump_ir_function_decl(struct hlsl_ctx *ctx, struct vkd3d_string_buffer *buffer, const struct hlsl_ir_function_decl *f); void hlsl_dump_var_default_values(const struct hlsl_ir_var *var); diff --git a/libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c b/libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c index 7707412bf57..8bfa157a12b 100644 --- a/libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c +++ b/libs/vkd3d/libs/vkd3d-shader/hlsl_codegen.c @@ -186,30 +186,34 @@ static void prepend_uniform_copy(struct hlsl_ctx *ctx, struct hlsl_block *block, { struct hlsl_ir_node *store; struct hlsl_ir_load *load; - struct hlsl_ir_var *temp; - char *new_name; uniform->is_uniform = 1; list_add_tail(&ctx->extern_vars, &uniform->extern_entry); - if (!(new_name = hlsl_sprintf_alloc(ctx, "", uniform->name))) - return; - - if (!(temp = hlsl_new_var(ctx, new_name, uniform->data_type, - &uniform->loc, NULL, uniform->storage_modifiers, NULL))) + if (!uniform->temp_copy) { - vkd3d_free(new_name); - return; - } - list_add_before(&uniform->scope_entry, &temp->scope_entry); + struct hlsl_ir_var *temp; + char *new_name; - uniform->temp_copy = temp; + if (!(new_name = hlsl_sprintf_alloc(ctx, "", uniform->name))) + return; + + if (!(temp = hlsl_new_var(ctx, new_name, uniform->data_type, + &uniform->loc, NULL, uniform->storage_modifiers, NULL))) + { + vkd3d_free(new_name); + return; + } + list_add_tail(&ctx->dummy_scope->vars, &temp->scope_entry); + + uniform->temp_copy = temp; + } if (!(load = hlsl_new_var_load(ctx, uniform, &uniform->loc))) return; list_add_head(&block->instrs, &load->node.entry); - if (!(store = hlsl_new_simple_store(ctx, temp, &load->node))) + if (!(store = hlsl_new_simple_store(ctx, uniform->temp_copy, &load->node))) return; list_add_after(&load->node.entry, &store->entry); } @@ -300,9 +304,9 @@ static bool types_are_semantic_equivalent(struct hlsl_ctx *ctx, const struct hls == base_type_get_semantic_equivalent(type2->e.numeric.type); } -static struct hlsl_ir_var *add_semantic_var(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *func, - struct hlsl_ir_var *var, struct hlsl_type *type, uint32_t modifiers, struct hlsl_semantic *semantic, - uint32_t stream_index, bool output, bool force_align, bool create, const struct vkd3d_shader_location *loc) +static struct hlsl_ir_var *add_semantic_var(struct hlsl_ctx *ctx, struct list *semantic_vars, struct hlsl_ir_var *var, + struct hlsl_type *type, uint32_t modifiers, struct hlsl_semantic *semantic, uint32_t stream_index, bool output, + bool force_align, bool create, const struct vkd3d_shader_location *loc) { struct hlsl_semantic new_semantic; uint32_t index = semantic->index; @@ -323,7 +327,7 @@ static struct hlsl_ir_var *add_semantic_var(struct hlsl_ctx *ctx, struct hlsl_ir if (!new_name) return NULL; - LIST_FOR_EACH_ENTRY(ext_var, &func->extern_vars, struct hlsl_ir_var, extern_entry) + LIST_FOR_EACH_ENTRY(ext_var, semantic_vars, struct hlsl_ir_var, extern_entry) { if (!ascii_strcasecmp(ext_var->name, new_name)) { @@ -387,7 +391,7 @@ static struct hlsl_ir_var *add_semantic_var(struct hlsl_ctx *ctx, struct hlsl_ir ext_var->is_param = var->is_param; ext_var->force_align = force_align; list_add_before(&var->scope_entry, &ext_var->scope_entry); - list_add_tail(&func->extern_vars, &ext_var->extern_entry); + list_add_tail(semantic_vars, &ext_var->extern_entry); return ext_var; } @@ -409,7 +413,7 @@ static uint32_t combine_field_storage_modifiers(uint32_t modifiers, uint32_t fie return field_modifiers; } -static void prepend_input_copy(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *func, +static void prepend_input_copy(struct hlsl_ctx *ctx, struct list *semantic_vars, struct hlsl_block *block, uint32_t prim_index, struct hlsl_ir_load *lhs, uint32_t modifiers, struct hlsl_semantic *semantic, bool force_align) { @@ -455,7 +459,7 @@ static void prepend_input_copy(struct hlsl_ctx *ctx, struct hlsl_ir_function_dec return; prim_type_src->modifiers = var->data_type->modifiers & HLSL_PRIMITIVE_MODIFIERS_MASK; - if (!(input = add_semantic_var(ctx, func, var, prim_type_src, + if (!(input = add_semantic_var(ctx, semantic_vars, var, prim_type_src, modifiers, semantic, 0, false, force_align, true, loc))) return; ++semantic->index; @@ -469,7 +473,7 @@ static void prepend_input_copy(struct hlsl_ctx *ctx, struct hlsl_ir_function_dec } else { - if (!(input = add_semantic_var(ctx, func, var, vector_type_src, + if (!(input = add_semantic_var(ctx, semantic_vars, var, vector_type_src, modifiers, semantic, 0, false, force_align, true, loc))) return; ++semantic->index; @@ -496,7 +500,7 @@ static void prepend_input_copy(struct hlsl_ctx *ctx, struct hlsl_ir_function_dec } } -static void prepend_input_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *func, +static void prepend_input_copy_recurse(struct hlsl_ctx *ctx, struct list *semantic_vars, struct hlsl_block *block, uint32_t prim_index, struct hlsl_ir_load *lhs, uint32_t modifiers, struct hlsl_semantic *semantic, bool force_align) { @@ -533,7 +537,7 @@ static void prepend_input_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_ir_func if (hlsl_type_is_primitive_array(type)) prim_index = i; - prepend_input_copy_recurse(ctx, func, block, prim_index, + prepend_input_copy_recurse(ctx, semantic_vars, block, prim_index, element_load, element_modifiers, semantic, force_align); } else @@ -550,7 +554,7 @@ static void prepend_input_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_ir_func if (semantic->name) { warn_on_field_semantic(ctx, field, semantic); - prepend_input_copy_recurse(ctx, func, block, prim_index, + prepend_input_copy_recurse(ctx, semantic_vars, block, prim_index, element_load, element_modifiers, semantic, force_align); } else @@ -561,7 +565,7 @@ static void prepend_input_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_ir_func if (!(hlsl_clone_semantic(ctx, &semantic_copy, &field->semantic))) return; - prepend_input_copy_recurse(ctx, func, block, prim_index, + prepend_input_copy_recurse(ctx, semantic_vars, block, prim_index, element_load, element_modifiers, &semantic_copy, force_align); hlsl_cleanup_semantic(&semantic_copy); } @@ -570,13 +574,14 @@ static void prepend_input_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_ir_func } else { - prepend_input_copy(ctx, func, block, prim_index, lhs, modifiers, semantic, force_align); + prepend_input_copy(ctx, semantic_vars, block, prim_index, lhs, modifiers, semantic, force_align); } } /* Split inputs into two variables representing the semantic and temp registers, * and copy the former to the latter, so that writes to input variables work. */ -static void prepend_input_var_copy(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *func, struct hlsl_ir_var *var) +static void prepend_input_var_copy(struct hlsl_ctx *ctx, struct hlsl_block *body, + struct list *semantic_vars, struct hlsl_ir_var *var) { struct hlsl_semantic semantic_copy; struct hlsl_ir_load *load; @@ -594,14 +599,14 @@ static void prepend_input_var_copy(struct hlsl_ctx *ctx, struct hlsl_ir_function hlsl_block_cleanup(&block); return; } - prepend_input_copy_recurse(ctx, func, &block, 0, load, var->storage_modifiers, &semantic_copy, false); + prepend_input_copy_recurse(ctx, semantic_vars, &block, 0, load, var->storage_modifiers, &semantic_copy, false); hlsl_cleanup_semantic(&semantic_copy); - list_move_head(&func->body.instrs, &block.instrs); + list_move_head(&body->instrs, &block.instrs); } static void append_output_copy(struct hlsl_ctx *ctx, struct hlsl_block *block, - struct hlsl_ir_function_decl *func, struct hlsl_ir_load *rhs, uint32_t modifiers, + struct list *semantic_vars, struct hlsl_ir_load *rhs, uint32_t modifiers, struct hlsl_semantic *semantic, uint32_t stream_index, bool force_align, bool create) { struct hlsl_type *type = rhs->node.data_type, *vector_type; @@ -631,7 +636,7 @@ static void append_output_copy(struct hlsl_ctx *ctx, struct hlsl_block *block, struct hlsl_ir_var *output; struct hlsl_ir_node *load; - if (!(output = add_semantic_var(ctx, func, var, vector_type, modifiers, + if (!(output = add_semantic_var(ctx, semantic_vars, var, vector_type, modifiers, semantic, stream_index, true, force_align, create, loc))) return; ++semantic->index; @@ -652,9 +657,9 @@ static void append_output_copy(struct hlsl_ctx *ctx, struct hlsl_block *block, } } -static void append_output_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_block *block, - struct hlsl_ir_function_decl *func, const struct hlsl_type *type, struct hlsl_ir_load *rhs, - uint32_t modifiers, struct hlsl_semantic *semantic, uint32_t stream_index, bool force_align, bool create) +static void append_output_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_block *block, struct list *semantic_vars, + const struct hlsl_type *type, struct hlsl_ir_load *rhs, uint32_t modifiers, struct hlsl_semantic *semantic, + uint32_t stream_index, bool force_align, bool create) { struct vkd3d_shader_location *loc = &rhs->node.loc; struct hlsl_ir_var *var = rhs->src.var; @@ -684,7 +689,7 @@ static void append_output_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_block * element_modifiers = modifiers; force_align = true; - append_output_copy_recurse(ctx, block, func, element_type, element_load, + append_output_copy_recurse(ctx, block, semantic_vars, element_type, element_load, element_modifiers, semantic, stream_index, force_align, create); } else @@ -700,7 +705,7 @@ static void append_output_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_block * { warn_on_field_semantic(ctx, field, semantic); - append_output_copy_recurse(ctx, block, func, element_type, element_load, + append_output_copy_recurse(ctx, block, semantic_vars, element_type, element_load, element_modifiers, semantic, stream_index, force_align, create); } else @@ -711,7 +716,7 @@ static void append_output_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_block * if (!hlsl_clone_semantic(ctx, &semantic_copy, &field->semantic)) continue; - append_output_copy_recurse(ctx, block, func, element_type, element_load, + append_output_copy_recurse(ctx, block, semantic_vars, element_type, element_load, element_modifiers, &semantic_copy, stream_index, force_align, create); hlsl_cleanup_semantic(&semantic_copy); } @@ -720,14 +725,15 @@ static void append_output_copy_recurse(struct hlsl_ctx *ctx, struct hlsl_block * } else { - append_output_copy(ctx, block, func, rhs, modifiers, semantic, stream_index, force_align, create); + append_output_copy(ctx, block, semantic_vars, rhs, modifiers, semantic, stream_index, force_align, create); } } /* Split outputs into two variables representing the temp and semantic * registers, and copy the former to the latter, so that reads from output * variables work. */ -static void append_output_var_copy(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *func, struct hlsl_ir_var *var) +static void append_output_var_copy(struct hlsl_ctx *ctx, struct hlsl_block *body, + struct list *semantic_vars, struct hlsl_ir_var *var) { struct hlsl_semantic semantic_copy; struct hlsl_ir_load *load; @@ -735,11 +741,11 @@ static void append_output_var_copy(struct hlsl_ctx *ctx, struct hlsl_ir_function /* This redundant load is expected to be deleted later by DCE. */ if (!(load = hlsl_new_var_load(ctx, var, &var->loc))) return; - hlsl_block_add_instr(&func->body, &load->node); + hlsl_block_add_instr(body, &load->node); if (!hlsl_clone_semantic(ctx, &semantic_copy, &var->semantic)) return; - append_output_copy_recurse(ctx, &func->body, func, var->data_type, + append_output_copy_recurse(ctx, body, semantic_vars, var->data_type, load, var->storage_modifiers, &semantic_copy, 0, false, true); hlsl_cleanup_semantic(&semantic_copy); } @@ -3424,7 +3430,7 @@ static bool split_struct_copies(struct hlsl_ctx *ctx, struct hlsl_ir_node *instr struct stream_append_ctx { - struct hlsl_ir_function_decl *func; + struct list *semantic_vars; bool created[VKD3D_MAX_STREAM_COUNT]; }; @@ -3465,7 +3471,7 @@ static bool lower_stream_appends(struct hlsl_ctx *ctx, struct hlsl_ir_node *inst if (!hlsl_clone_semantic(ctx, &semantic_copy, &var->semantic)) return false; - append_output_copy_recurse(ctx, &block, append_ctx->func, type->e.so.type, hlsl_ir_load(rhs), + append_output_copy_recurse(ctx, &block, append_ctx->semantic_vars, type->e.so.type, hlsl_ir_load(rhs), var->storage_modifiers, &semantic_copy, var->regs[HLSL_REGSET_STREAM_OUTPUTS].index, false, !append_ctx->created[stream_index]); hlsl_cleanup_semantic(&semantic_copy); @@ -5292,7 +5298,7 @@ static void dump_function(struct rb_entry *entry, void *context) LIST_FOR_EACH_ENTRY(decl, &func->overloads, struct hlsl_ir_function_decl, entry) { if (decl->has_body) - hlsl_dump_function(ctx, decl); + hlsl_dump_function(ctx, decl, "function", NULL); } } @@ -5309,7 +5315,7 @@ static bool mark_indexable_var(struct hlsl_ctx *ctx, struct hlsl_deref *deref, return true; } -static void mark_indexable_vars(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry_func) +static void mark_indexable_vars(struct hlsl_ctx *ctx, struct hlsl_block *body) { struct hlsl_scope *scope; struct hlsl_ir_var *var; @@ -5320,7 +5326,7 @@ static void mark_indexable_vars(struct hlsl_ctx *ctx, struct hlsl_ir_function_de var->indexable = false; } - transform_derefs(ctx, mark_indexable_var, &entry_func->body); + transform_derefs(ctx, mark_indexable_var, body); } static char get_regset_name(enum hlsl_regset regset) @@ -5567,7 +5573,7 @@ static void compute_liveness_recurse(struct hlsl_block *block, unsigned int loop } } -static void compute_liveness(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry_func) +static void compute_liveness(struct hlsl_ctx *ctx, struct hlsl_block *body) { struct hlsl_scope *scope; struct hlsl_ir_var *var; @@ -5575,7 +5581,7 @@ static void compute_liveness(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl if (ctx->result) return; - index_instructions(&entry_func->body, 1); + index_instructions(body, 1); LIST_FOR_EACH_ENTRY(scope, &ctx->scopes, struct hlsl_scope, entry) { @@ -5583,7 +5589,7 @@ static void compute_liveness(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl var->first_write = var->last_read = 0; } - compute_liveness_recurse(&entry_func->body, 0, 0); + compute_liveness_recurse(body, 0, 0); } static void mark_vars_usage(struct hlsl_ctx *ctx) @@ -6366,7 +6372,7 @@ static void allocate_sincos_const_registers(struct hlsl_ctx *ctx, struct hlsl_bl } } -static void allocate_const_registers(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry_func) +static void allocate_const_registers(struct hlsl_ctx *ctx, struct hlsl_block *body) { struct register_allocator allocator_used = {0}; struct register_allocator allocator = {0}; @@ -6431,9 +6437,9 @@ static void allocate_const_registers(struct hlsl_ctx *ctx, struct hlsl_ir_functi } } - allocate_const_registers_recurse(ctx, &entry_func->body, &allocator); + allocate_const_registers_recurse(ctx, body, &allocator); - allocate_sincos_const_registers(ctx, &entry_func->body, &allocator); + allocate_sincos_const_registers(ctx, body, &allocator); vkd3d_free(allocator.allocations); } @@ -6442,7 +6448,7 @@ static void allocate_const_registers(struct hlsl_ctx *ctx, struct hlsl_ir_functi * index to all (simultaneously live) variables or intermediate values. Agnostic * as to how many registers are actually available for the current backend, and * does not handle constants. */ -static uint32_t allocate_temp_registers(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry_func) +static uint32_t allocate_temp_registers(struct hlsl_ctx *ctx, struct hlsl_block *body, struct list *semantic_vars) { struct register_allocator allocator = {0}; struct hlsl_scope *scope; @@ -6461,7 +6467,7 @@ static uint32_t allocate_temp_registers(struct hlsl_ctx *ctx, struct hlsl_ir_fun /* ps_1_* outputs are special and go in temp register 0. */ if (ctx->profile->major_version == 1 && ctx->profile->type == VKD3D_SHADER_TYPE_PIXEL) { - LIST_FOR_EACH_ENTRY(var, &entry_func->extern_vars, struct hlsl_ir_var, extern_entry) + LIST_FOR_EACH_ENTRY(var, semantic_vars, struct hlsl_ir_var, extern_entry) { if (var->is_output_semantic) { @@ -6472,15 +6478,16 @@ static uint32_t allocate_temp_registers(struct hlsl_ctx *ctx, struct hlsl_ir_fun } } - allocate_temp_registers_recurse(ctx, &entry_func->body, &allocator); + allocate_temp_registers_recurse(ctx, body, &allocator); vkd3d_free(allocator.allocations); if (allocator.indexable_count) - TRACE("Declaration of function \"%s\" required %u temp registers, and %u indexable temps.\n", - entry_func->func->name, allocator.reg_count, allocator.indexable_count); + TRACE("Declaration of %s function required %u temp registers, and %u indexable temps.\n", + ctx->is_patch_constant_func ? "patch constant" : "main", + allocator.reg_count, allocator.indexable_count); else - TRACE("Declaration of function \"%s\" required %u temp registers.\n", - entry_func->func->name, allocator.reg_count); + TRACE("Declaration of %s function required %u temp registers.\n", + ctx->is_patch_constant_func ? "patch constant" : "main", allocator.reg_count); return allocator.reg_count; } @@ -6630,8 +6637,7 @@ static void allocate_semantic_register(struct hlsl_ctx *ctx, struct hlsl_ir_var } } -static void allocate_semantic_registers(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry_func, - uint32_t *output_reg_count) +static void allocate_semantic_registers(struct hlsl_ctx *ctx, struct list *semantic_vars, uint32_t *output_reg_count) { struct register_allocator input_allocator = {0}, output_allocators[VKD3D_MAX_STREAM_COUNT] = {{0}}; struct register_allocator in_prim_allocator = {0}, patch_constant_out_patch_allocator = {0}; @@ -6645,7 +6651,7 @@ static void allocate_semantic_registers(struct hlsl_ctx *ctx, struct hlsl_ir_fun for (unsigned int i = 0; i < ARRAY_SIZE(output_allocators); ++i) output_allocators[i].prioritize_smaller_writemasks = true; - LIST_FOR_EACH_ENTRY(var, &entry_func->extern_vars, struct hlsl_ir_var, extern_entry) + LIST_FOR_EACH_ENTRY(var, semantic_vars, struct hlsl_ir_var, extern_entry) { if (var->is_input_semantic) { @@ -6986,7 +6992,7 @@ static const struct hlsl_ir_var *get_allocated_object(struct hlsl_ctx *ctx, enum return NULL; } -static void allocate_objects(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *func, enum hlsl_regset regset) +static void allocate_objects(struct hlsl_ctx *ctx, struct list *semantic_vars, enum hlsl_regset regset) { char regset_name = get_regset_name(regset); uint32_t min_index = 0, id = 0; @@ -6994,7 +7000,7 @@ static void allocate_objects(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl if (regset == HLSL_REGSET_UAVS && ctx->profile->type == VKD3D_SHADER_TYPE_PIXEL) { - LIST_FOR_EACH_ENTRY(var, &func->extern_vars, struct hlsl_ir_var, extern_entry) + LIST_FOR_EACH_ENTRY(var, semantic_vars, struct hlsl_ir_var, extern_entry) { if (var->semantic.name && (!ascii_strcasecmp(var->semantic.name, "color") || !ascii_strcasecmp(var->semantic.name, "sv_target"))) @@ -7840,8 +7846,8 @@ static void validate_and_record_stream_outputs(struct hlsl_ctx *ctx) } } -static void validate_max_output_size(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry_func, - uint32_t output_reg_count) +static void validate_max_output_size(struct hlsl_ctx *ctx, struct list *semantic_vars, + uint32_t output_reg_count, const struct vkd3d_shader_location *loc) { unsigned int max_output_size, comp_count = 0; unsigned int *reg_comp_count; @@ -7854,7 +7860,7 @@ static void validate_max_output_size(struct hlsl_ctx *ctx, struct hlsl_ir_functi if (!(reg_comp_count = hlsl_calloc(ctx, output_reg_count, sizeof(*reg_comp_count)))) return; - LIST_FOR_EACH_ENTRY(var, &entry_func->extern_vars, struct hlsl_ir_var, extern_entry) + LIST_FOR_EACH_ENTRY(var, semantic_vars, struct hlsl_ir_var, extern_entry) { if (!var->is_output_semantic) continue; @@ -7869,7 +7875,7 @@ static void validate_max_output_size(struct hlsl_ctx *ctx, struct hlsl_ir_functi max_output_size = ctx->max_vertex_count * comp_count; if (max_output_size > 1024) - hlsl_error(ctx, &entry_func->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_MAX_VERTEX_COUNT, + hlsl_error(ctx, loc, VKD3D_SHADER_ERROR_HLSL_INVALID_MAX_VERTEX_COUNT, "Max vertex count (%u) * output data component count (%u) = %u, which is greater than 1024.", ctx->max_vertex_count, comp_count, max_output_size); @@ -8183,15 +8189,15 @@ static void generate_vsir_signature_entry(struct hlsl_ctx *ctx, struct vsir_prog } } -static void generate_vsir_signature(struct hlsl_ctx *ctx, - struct vsir_program *program, struct hlsl_ir_function_decl *func) +static void generate_vsir_signature(struct hlsl_ctx *ctx, struct vsir_program *program, + struct hlsl_ir_function_decl *func, struct list *semantic_vars) { bool is_domain = program->shader_version.type == VKD3D_SHADER_TYPE_DOMAIN; struct hlsl_ir_var *var; ctx->is_patch_constant_func = func == ctx->patch_constant_func; - LIST_FOR_EACH_ENTRY(var, &func->extern_vars, struct hlsl_ir_var, extern_entry) + LIST_FOR_EACH_ENTRY(var, semantic_vars, struct hlsl_ir_var, extern_entry) { if (var->is_input_semantic) { @@ -8233,7 +8239,7 @@ static enum vsir_data_type vsir_data_type_from_hlsl_type(struct hlsl_ctx *ctx, c if (type->class == HLSL_CLASS_ARRAY) return vsir_data_type_from_hlsl_type(ctx, type->e.array.type); if (type->class == HLSL_CLASS_STRUCT) - return VKD3D_DATA_MIXED; + return VSIR_DATA_MIXED; if (type->class <= HLSL_CLASS_LAST_NUMERIC) { switch (type->e.numeric.type) @@ -8253,7 +8259,7 @@ static enum vsir_data_type vsir_data_type_from_hlsl_type(struct hlsl_ctx *ctx, c } } - return VKD3D_DATA_UNUSED; + return VSIR_DATA_UNUSED; } static enum vsir_data_type vsir_data_type_from_hlsl_instruction(struct hlsl_ctx *ctx, @@ -8782,7 +8788,7 @@ static void sm4_generate_vsir_rasterizer_sample_count(struct hlsl_ctx *ctx, vsir_dst_from_hlsl_node(&ins->dst[0], ctx, instr); src_param = &ins->src[0]; - vsir_src_param_init(src_param, VKD3DSPR_RASTERIZER, VKD3D_DATA_UNUSED, 0); + vsir_src_param_init(src_param, VKD3DSPR_RASTERIZER, VSIR_DATA_UNUSED, 0); src_param->reg.dimension = VSIR_DIMENSION_VEC4; src_param->swizzle = VKD3D_SHADER_SWIZZLE(X, X, X, X); } @@ -9397,6 +9403,10 @@ static void sm1_generate_vsir_instr_resource_load(struct hlsl_ctx *ctx, flags |= VKD3DSI_TEXLD_PROJECT; break; + case HLSL_RESOURCE_SAMPLE_LOD: + opcode = VSIR_OP_TEXLDL; + break; + case HLSL_RESOURCE_SAMPLE_LOD_BIAS: opcode = VSIR_OP_TEXLD; flags |= VKD3DSI_TEXLD_BIAS; @@ -9596,8 +9606,8 @@ static void sm1_generate_vsir_block(struct hlsl_ctx *ctx, struct hlsl_block *blo } } -static void sm1_generate_vsir(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry_func, - uint64_t config_flags, struct vsir_program *program) +static void sm1_generate_vsir(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *func, + struct list *semantic_vars, struct hlsl_block *body, uint64_t config_flags, struct vsir_program *program) { struct vkd3d_shader_version version = {0}; struct hlsl_block block; @@ -9612,18 +9622,18 @@ static void sm1_generate_vsir(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl } program->ssa_count = 0; - program->temp_count = allocate_temp_registers(ctx, entry_func); + program->temp_count = allocate_temp_registers(ctx, body, semantic_vars); if (ctx->result) return; - generate_vsir_signature(ctx, program, entry_func); + generate_vsir_signature(ctx, program, func, semantic_vars); hlsl_block_init(&block); sm1_generate_vsir_constant_defs(ctx, program, &block); sm1_generate_vsir_sampler_dcls(ctx, program, &block); - list_move_head(&entry_func->body.instrs, &block.instrs); + list_move_head(&body->instrs, &block.instrs); - sm1_generate_vsir_block(ctx, &entry_func->body, program); + sm1_generate_vsir_block(ctx, body, program); program->ssa_count = ctx->ssa_count; } @@ -11738,8 +11748,9 @@ static void sm4_generate_vsir_block(struct hlsl_ctx *ctx, struct hlsl_block *blo } } -static void sm4_generate_vsir_add_function(struct hlsl_ctx *ctx, - struct hlsl_ir_function_decl *func, uint64_t config_flags, struct vsir_program *program) +static void sm4_generate_vsir_add_function(struct hlsl_ctx *ctx, struct list *semantic_vars, + struct hlsl_ir_function_decl *func, struct hlsl_block *body, uint64_t config_flags, + struct vsir_program *program) { struct hlsl_block block = {0}; struct hlsl_scope *scope; @@ -11748,16 +11759,16 @@ static void sm4_generate_vsir_add_function(struct hlsl_ctx *ctx, ctx->is_patch_constant_func = func == ctx->patch_constant_func; - compute_liveness(ctx, func); - mark_indexable_vars(ctx, func); - temp_count = allocate_temp_registers(ctx, func); + compute_liveness(ctx, body); + mark_indexable_vars(ctx, body); + temp_count = allocate_temp_registers(ctx, body, semantic_vars); if (ctx->result) return; program->temp_count = max(program->temp_count, temp_count); hlsl_block_init(&block); - LIST_FOR_EACH_ENTRY(var, &func->extern_vars, struct hlsl_ir_var, extern_entry) + LIST_FOR_EACH_ENTRY(var, semantic_vars, struct hlsl_ir_var, extern_entry) { if ((var->is_input_semantic && var->last_read) || (var->is_output_semantic && var->first_write)) @@ -11786,11 +11797,11 @@ static void sm4_generate_vsir_add_function(struct hlsl_ctx *ctx, } } - list_move_head(&func->body.instrs, &block.instrs); + list_move_head(&body->instrs, &block.instrs); hlsl_block_cleanup(&block); - sm4_generate_vsir_block(ctx, &func->body, program); + sm4_generate_vsir_block(ctx, body, program); generate_vsir_add_program_instruction(ctx, program, &func->loc, VSIR_OP_RET, 0, 0); } @@ -12014,8 +12025,8 @@ static void generate_vsir_scan_required_features(struct hlsl_ctx *ctx, struct vs * STENCIL_REF, and TYPED_UAV_LOAD_ADDITIONAL_FORMATS. */ } -static void generate_vsir_scan_global_flags(struct hlsl_ctx *ctx, - struct vsir_program *program, const struct hlsl_ir_function_decl *entry_func) +static void generate_vsir_scan_global_flags(struct hlsl_ctx *ctx, struct vsir_program *program, + const struct list *semantic_vars, const struct hlsl_ir_function_decl *entry_func) { const struct vkd3d_shader_version *version = &program->shader_version; struct extern_resource *extern_resources; @@ -12041,7 +12052,7 @@ static void generate_vsir_scan_global_flags(struct hlsl_ctx *ctx, sm4_free_extern_resources(extern_resources, extern_resources_count); - LIST_FOR_EACH_ENTRY(var, &entry_func->extern_vars, struct hlsl_ir_var, extern_entry) + LIST_FOR_EACH_ENTRY(var, semantic_vars, struct hlsl_ir_var, extern_entry) { const struct hlsl_type *type = var->data_type; @@ -12123,7 +12134,7 @@ static void sm4_generate_vsir_add_dcl_sampler(struct hlsl_ctx *ctx, ins->flags |= VKD3DSI_SAMPLER_COMPARISON_MODE; src_param = &ins->declaration.sampler.src; - vsir_src_param_init(src_param, VKD3DSPR_SAMPLER, VKD3D_DATA_UNUSED, 0); + vsir_src_param_init(src_param, VKD3DSPR_SAMPLER, VSIR_DATA_UNUSED, 0); ins->declaration.sampler.range.first = array_first; ins->declaration.sampler.range.last = array_last; @@ -12179,9 +12190,9 @@ static enum vsir_data_type sm4_generate_vsir_get_format_type(const struct hlsl_t case HLSL_TYPE_FLOAT: case HLSL_TYPE_HALF: if (format->modifiers & HLSL_MODIFIER_UNORM) - return VKD3D_DATA_UNORM; + return VSIR_DATA_UNORM; if (format->modifiers & HLSL_MODIFIER_SNORM) - return VKD3D_DATA_SNORM; + return VSIR_DATA_SNORM; return VSIR_DATA_F32; case HLSL_TYPE_INT: @@ -12262,7 +12273,7 @@ static void sm4_generate_vsir_add_dcl_texture(struct hlsl_ctx *ctx, else vsir_resource = &ins->declaration.semantic.resource; - vsir_dst_param_init(&vsir_resource->reg, uav ? VKD3DSPR_UAV : VKD3DSPR_RESOURCE, VKD3D_DATA_UNUSED, 0); + vsir_dst_param_init(&vsir_resource->reg, uav ? VKD3DSPR_UAV : VKD3DSPR_RESOURCE, VSIR_DATA_UNUSED, 0); if (uav && component_type->e.resource.rasteriser_ordered) ins->flags = VKD3DSUF_RASTERISER_ORDERED_VIEW; @@ -12320,7 +12331,7 @@ static void sm4_generate_vsir_add_dcl_stream(struct hlsl_ctx *ctx, return; } - vsir_src_param_init(&ins->src[0], VKD3DSPR_STREAM, VKD3D_DATA_UNUSED, 1); + vsir_src_param_init(&ins->src[0], VKD3DSPR_STREAM, VSIR_DATA_UNUSED, 1); ins->src[0].reg.dimension = VSIR_DIMENSION_NONE; ins->src[0].reg.idx[0].offset = var->regs[HLSL_REGSET_STREAM_OUTPUTS].index; } @@ -12329,7 +12340,8 @@ static void sm4_generate_vsir_add_dcl_stream(struct hlsl_ctx *ctx, * vsir_program, so it can be used as input to tpf_compile() without relying * on ctx and entry_func. */ static void sm4_generate_vsir(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *func, - uint64_t config_flags, struct vsir_program *program) + struct list *semantic_vars, struct hlsl_block *body, struct list *patch_semantic_vars, + struct hlsl_block *patch_body, uint64_t config_flags, struct vsir_program *program) { struct vkd3d_shader_version version = {0}; struct extern_resource *extern_resources; @@ -12346,9 +12358,9 @@ static void sm4_generate_vsir(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl return; } - generate_vsir_signature(ctx, program, func); + generate_vsir_signature(ctx, program, func, semantic_vars); if (version.type == VKD3D_SHADER_TYPE_HULL) - generate_vsir_signature(ctx, program, ctx->patch_constant_func); + generate_vsir_signature(ctx, program, ctx->patch_constant_func, patch_semantic_vars); if (version.type == VKD3D_SHADER_TYPE_COMPUTE) { @@ -12415,16 +12427,17 @@ static void sm4_generate_vsir(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl if (version.type == VKD3D_SHADER_TYPE_HULL) generate_vsir_add_program_instruction(ctx, program, &ctx->patch_constant_func->loc, VSIR_OP_HS_CONTROL_POINT_PHASE, 0, 0); - sm4_generate_vsir_add_function(ctx, func, config_flags, program); + sm4_generate_vsir_add_function(ctx, semantic_vars, func, body, config_flags, program); if (version.type == VKD3D_SHADER_TYPE_HULL) { generate_vsir_add_program_instruction(ctx, program, &ctx->patch_constant_func->loc, VSIR_OP_HS_FORK_PHASE, 0, 0); - sm4_generate_vsir_add_function(ctx, ctx->patch_constant_func, config_flags, program); + sm4_generate_vsir_add_function(ctx, patch_semantic_vars, + ctx->patch_constant_func, patch_body, config_flags, program); } generate_vsir_scan_required_features(ctx, program); - generate_vsir_scan_global_flags(ctx, program, func); + generate_vsir_scan_global_flags(ctx, program, semantic_vars, func); program->ssa_count = ctx->ssa_count; } @@ -13565,15 +13578,14 @@ static bool lower_isinf(struct hlsl_ctx *ctx, struct hlsl_ir_node *node, struct return true; } -static void process_entry_function(struct hlsl_ctx *ctx, +static void process_entry_function(struct hlsl_ctx *ctx, struct list *semantic_vars, struct hlsl_block *body, const struct hlsl_block *global_uniform_block, struct hlsl_ir_function_decl *entry_func) { + struct stream_append_ctx stream_append_ctx = { .semantic_vars = semantic_vars }; const struct hlsl_ir_var *input_patch = NULL, *output_patch = NULL; const struct hlsl_profile_info *profile = ctx->profile; struct hlsl_block static_initializers, global_uniforms; - struct hlsl_block *const body = &entry_func->body; struct recursive_call_ctx recursive_call_ctx; - struct stream_append_ctx stream_append_ctx; uint32_t output_reg_count; struct hlsl_ir_var *var; unsigned int i; @@ -13581,6 +13593,8 @@ static void process_entry_function(struct hlsl_ctx *ctx, ctx->is_patch_constant_func = entry_func == ctx->patch_constant_func; + hlsl_clone_block(ctx, body, &entry_func->body); + if (!hlsl_clone_block(ctx, &static_initializers, &ctx->static_initializers)) return; list_move_head(&body->instrs, &static_initializers.instrs); @@ -13624,7 +13638,7 @@ static void process_entry_function(struct hlsl_ctx *ctx, hlsl_error(ctx, &entry_func->loc, VKD3D_SHADER_ERROR_HLSL_MISSING_SEMANTIC, "Entry point \"%s\" is missing a return value semantic.", entry_func->func->name); - append_output_var_copy(ctx, entry_func, entry_func->return_var); + append_output_var_copy(ctx, body, semantic_vars, entry_func->return_var); } for (i = 0; i < entry_func->parameters.count; ++i) @@ -13680,7 +13694,7 @@ static void process_entry_function(struct hlsl_ctx *ctx, } validate_and_record_prim_type(ctx, var); - prepend_input_var_copy(ctx, entry_func, var); + prepend_input_var_copy(ctx, body, semantic_vars, var); } else if (var->data_type->reg_size[HLSL_REGSET_STREAM_OUTPUTS]) { @@ -13716,7 +13730,7 @@ static void process_entry_function(struct hlsl_ctx *ctx, continue; } - prepend_input_var_copy(ctx, entry_func, var); + prepend_input_var_copy(ctx, body, semantic_vars, var); } if (var->storage_modifiers & HLSL_STORAGE_OUT) { @@ -13727,7 +13741,7 @@ static void process_entry_function(struct hlsl_ctx *ctx, hlsl_error(ctx, &var->loc, VKD3D_SHADER_ERROR_HLSL_INVALID_MODIFIER, "Output parameters are not allowed in geometry shaders."); else - append_output_var_copy(ctx, entry_func, var); + append_output_var_copy(ctx, body, semantic_vars, var); } } } @@ -13776,8 +13790,8 @@ static void process_entry_function(struct hlsl_ctx *ctx, hlsl_transform_ir(ctx, lower_resource_load_bias, body, NULL); } - compute_liveness(ctx, entry_func); - transform_derefs(ctx, divert_written_uniform_derefs_to_temp, &entry_func->body); + compute_liveness(ctx, body); + transform_derefs(ctx, divert_written_uniform_derefs_to_temp, body); loop_unrolling_execute(ctx, body); hlsl_run_const_passes(ctx, body); @@ -13797,7 +13811,7 @@ static void process_entry_function(struct hlsl_ctx *ctx, do { progress = vectorize_exprs(ctx, body); - compute_liveness(ctx, entry_func); + compute_liveness(ctx, body); progress |= hlsl_transform_ir(ctx, dce, body, NULL); progress |= hlsl_transform_ir(ctx, fold_swizzle_chains, body, NULL); progress |= hlsl_transform_ir(ctx, remove_trivial_swizzles, body, NULL); @@ -13810,7 +13824,7 @@ static void process_entry_function(struct hlsl_ctx *ctx, hlsl_transform_ir(ctx, lower_combined_samples, body, NULL); do - compute_liveness(ctx, entry_func); + compute_liveness(ctx, body); while (hlsl_transform_ir(ctx, dce, body, NULL)); hlsl_transform_ir(ctx, track_components_usage, body, NULL); @@ -13823,9 +13837,6 @@ static void process_entry_function(struct hlsl_ctx *ctx, { allocate_stream_outputs(ctx); validate_and_record_stream_outputs(ctx); - - memset(&stream_append_ctx, 0, sizeof(stream_append_ctx)); - stream_append_ctx.func = entry_func; hlsl_transform_ir(ctx, lower_stream_appends, body, &stream_append_ctx); } @@ -13866,7 +13877,7 @@ static void process_entry_function(struct hlsl_ctx *ctx, hlsl_run_folding_passes(ctx, body); do - compute_liveness(ctx, entry_func); + compute_liveness(ctx, body); while (hlsl_transform_ir(ctx, dce, body, NULL)); /* TODO: move forward, remove when no longer needed */ @@ -13875,27 +13886,28 @@ static void process_entry_function(struct hlsl_ctx *ctx, transform_derefs(ctx, clean_constant_deref_offset_srcs, body); do - compute_liveness(ctx, entry_func); + compute_liveness(ctx, body); while (hlsl_transform_ir(ctx, dce, body, NULL)); - compute_liveness(ctx, entry_func); + compute_liveness(ctx, body); mark_vars_usage(ctx); calculate_resource_register_counts(ctx); allocate_register_reservations(ctx, &ctx->extern_vars); - allocate_register_reservations(ctx, &entry_func->extern_vars); - allocate_semantic_registers(ctx, entry_func, &output_reg_count); + allocate_register_reservations(ctx, semantic_vars); + allocate_semantic_registers(ctx, semantic_vars, &output_reg_count); if (profile->type == VKD3D_SHADER_TYPE_GEOMETRY) - validate_max_output_size(ctx, entry_func, output_reg_count); + validate_max_output_size(ctx, semantic_vars, output_reg_count, &entry_func->loc); } int hlsl_emit_bytecode(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry_func, enum vkd3d_shader_target_type target_type, struct vkd3d_shader_code *out) { + struct hlsl_block global_uniform_block, body, patch_body; const struct hlsl_profile_info *profile = ctx->profile; - struct hlsl_block global_uniform_block; + struct list semantic_vars, patch_semantic_vars; struct hlsl_ir_var *var; parse_entry_function_attributes(ctx, entry_func); @@ -13914,6 +13926,9 @@ int hlsl_emit_bytecode(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry hlsl_error(ctx, &entry_func->loc, VKD3D_SHADER_ERROR_HLSL_MISSING_ATTRIBUTE, "Entry point \"%s\" is missing a [maxvertexcount] attribute.", entry_func->func->name); + list_init(&ctx->extern_vars); + list_init(&semantic_vars); + list_init(&patch_semantic_vars); hlsl_block_init(&global_uniform_block); LIST_FOR_EACH_ENTRY(var, &ctx->globals->vars, struct hlsl_ir_var, scope_entry) @@ -13922,13 +13937,13 @@ int hlsl_emit_bytecode(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry prepend_uniform_copy(ctx, &global_uniform_block, var); } - process_entry_function(ctx, &global_uniform_block, entry_func); + process_entry_function(ctx, &semantic_vars, &body, &global_uniform_block, entry_func); if (ctx->result) return ctx->result; if (profile->type == VKD3D_SHADER_TYPE_HULL) { - process_entry_function(ctx, &global_uniform_block, ctx->patch_constant_func); + process_entry_function(ctx, &patch_semantic_vars, &patch_body, &global_uniform_block, ctx->patch_constant_func); if (ctx->result) return ctx->result; } @@ -13937,21 +13952,26 @@ int hlsl_emit_bytecode(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry if (profile->major_version < 4) { - mark_indexable_vars(ctx, entry_func); - allocate_const_registers(ctx, entry_func); + mark_indexable_vars(ctx, &body); + allocate_const_registers(ctx, &body); sort_uniforms_by_bind_count(ctx, HLSL_REGSET_SAMPLERS); - allocate_objects(ctx, entry_func, HLSL_REGSET_SAMPLERS); + allocate_objects(ctx, &semantic_vars, HLSL_REGSET_SAMPLERS); } else { allocate_buffers(ctx); - allocate_objects(ctx, entry_func, HLSL_REGSET_TEXTURES); - allocate_objects(ctx, entry_func, HLSL_REGSET_UAVS); - allocate_objects(ctx, entry_func, HLSL_REGSET_SAMPLERS); + allocate_objects(ctx, &semantic_vars, HLSL_REGSET_TEXTURES); + allocate_objects(ctx, &semantic_vars, HLSL_REGSET_UAVS); + allocate_objects(ctx, &semantic_vars, HLSL_REGSET_SAMPLERS); } if (TRACE_ON()) + { rb_for_each_entry(&ctx->functions, dump_function, ctx); + hlsl_dump_function(ctx, entry_func, "processed entry point", &body); + if (profile->type == VKD3D_SHADER_TYPE_HULL) + hlsl_dump_function(ctx, ctx->patch_constant_func, "processed patch-constant function", &patch_body); + } if (ctx->result) return ctx->result; @@ -13969,7 +13989,7 @@ int hlsl_emit_bytecode(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry if (ctx->result) return ctx->result; - sm1_generate_vsir(ctx, entry_func, config_flags, &program); + sm1_generate_vsir(ctx, entry_func, &semantic_vars, &body, config_flags, &program); if (ctx->result) { vsir_program_cleanup(&program); @@ -13996,7 +14016,8 @@ int hlsl_emit_bytecode(struct hlsl_ctx *ctx, struct hlsl_ir_function_decl *entry if (ctx->result) return ctx->result; - sm4_generate_vsir(ctx, entry_func, config_flags, &program); + sm4_generate_vsir(ctx, entry_func, &semantic_vars, &body, + &patch_semantic_vars, &patch_body, config_flags, &program); if (ctx->result) { vsir_program_cleanup(&program); diff --git a/libs/vkd3d/libs/vkd3d-shader/ir.c b/libs/vkd3d/libs/vkd3d-shader/ir.c index c322d9dde01..92580a6a2df 100644 --- a/libs/vkd3d/libs/vkd3d-shader/ir.c +++ b/libs/vkd3d/libs/vkd3d-shader/ir.c @@ -604,7 +604,7 @@ static void vsir_src_param_init_io(struct vkd3d_shader_src_param *src, void vsir_src_param_init_label(struct vkd3d_shader_src_param *param, unsigned int label_id) { - vsir_src_param_init(param, VKD3DSPR_LABEL, VKD3D_DATA_UNUSED, 1); + vsir_src_param_init(param, VKD3DSPR_LABEL, VSIR_DATA_UNUSED, 1); param->reg.dimension = VSIR_DIMENSION_NONE; param->reg.idx[0].offset = label_id; } @@ -625,7 +625,7 @@ static void src_param_init_parameter_vec4(struct vkd3d_shader_src_param *src, ui static void vsir_src_param_init_resource(struct vkd3d_shader_src_param *src, unsigned int id, unsigned int idx) { - vsir_src_param_init(src, VKD3DSPR_RESOURCE, VKD3D_DATA_UNUSED, 2); + vsir_src_param_init(src, VKD3DSPR_RESOURCE, VSIR_DATA_UNUSED, 2); src->reg.idx[0].offset = id; src->reg.idx[1].offset = idx; src->reg.dimension = VSIR_DIMENSION_VEC4; @@ -634,7 +634,7 @@ static void vsir_src_param_init_resource(struct vkd3d_shader_src_param *src, uns static void vsir_src_param_init_sampler(struct vkd3d_shader_src_param *src, unsigned int id, unsigned int idx) { - vsir_src_param_init(src, VKD3DSPR_SAMPLER, VKD3D_DATA_UNUSED, 2); + vsir_src_param_init(src, VKD3DSPR_SAMPLER, VSIR_DATA_UNUSED, 2); src->reg.idx[0].offset = id; src->reg.idx[1].offset = idx; src->reg.dimension = VSIR_DIMENSION_NONE; @@ -661,7 +661,7 @@ static void src_param_init_ssa_scalar(struct vkd3d_shader_src_param *src, static void src_param_init_ssa_bool(struct vkd3d_shader_src_param *src, unsigned int idx) { - src_param_init_ssa_scalar(src, idx, VKD3D_DATA_BOOL); + src_param_init_ssa_scalar(src, idx, VSIR_DATA_BOOL); } static void src_param_init_ssa_float(struct vkd3d_shader_src_param *src, unsigned int idx) @@ -676,7 +676,7 @@ static void src_param_init_ssa_float4(struct vkd3d_shader_src_param *src, unsign static void src_param_init_temp_bool(struct vkd3d_shader_src_param *src, unsigned int idx) { - vsir_src_param_init(src, VKD3DSPR_TEMP, VKD3D_DATA_BOOL, 1); + vsir_src_param_init(src, VKD3DSPR_TEMP, VSIR_DATA_BOOL, 1); src->reg.idx[0].offset = idx; } @@ -719,7 +719,7 @@ static void vsir_dst_param_init_io(struct vkd3d_shader_dst_param *dst, enum vkd3 void vsir_dst_param_init_null(struct vkd3d_shader_dst_param *dst) { - vsir_dst_param_init(dst, VKD3DSPR_NULL, VKD3D_DATA_UNUSED, 0); + vsir_dst_param_init(dst, VKD3DSPR_NULL, VSIR_DATA_UNUSED, 0); dst->reg.dimension = VSIR_DIMENSION_NONE; dst->write_mask = 0; } @@ -745,7 +745,7 @@ static void dst_param_init_ssa_scalar(struct vkd3d_shader_dst_param *dst, static void dst_param_init_ssa_bool(struct vkd3d_shader_dst_param *dst, unsigned int idx) { - dst_param_init_ssa_scalar(dst, idx, VKD3D_DATA_BOOL); + dst_param_init_ssa_scalar(dst, idx, VSIR_DATA_BOOL); } static void dst_param_init_ssa_float(struct vkd3d_shader_dst_param *dst, unsigned int idx) @@ -760,7 +760,7 @@ static void dst_param_init_ssa_float4(struct vkd3d_shader_dst_param *dst, unsign static void dst_param_init_temp_bool(struct vkd3d_shader_dst_param *dst, unsigned int idx) { - vsir_dst_param_init(dst, VKD3DSPR_TEMP, VKD3D_DATA_BOOL, 1); + vsir_dst_param_init(dst, VKD3DSPR_TEMP, VSIR_DATA_BOOL, 1); dst->reg.idx[0].offset = idx; } @@ -792,6 +792,10 @@ void vsir_instruction_init(struct vkd3d_shader_instruction *ins, const struct vk memset(ins, 0, sizeof(*ins)); ins->location = *location; ins->opcode = opcode; + ins->resource_data_type[0] = VSIR_DATA_F32; + ins->resource_data_type[1] = VSIR_DATA_F32; + ins->resource_data_type[2] = VSIR_DATA_F32; + ins->resource_data_type[3] = VSIR_DATA_F32; } bool vsir_instruction_init_with_params(struct vsir_program *program, @@ -1180,7 +1184,7 @@ static enum vkd3d_result vsir_program_lower_udiv(struct vsir_program *program, { vkd3d_shader_error(ctx->message_context, &udiv->location, VKD3D_SHADER_ERROR_VSIR_INVALID_DEST_COUNT, - "Internal compiler error: invalid destination count %u for UDIV.", + "Internal compiler error: invalid destination count %zu for UDIV.", udiv->dst_count); return VKD3D_ERROR; } @@ -1321,7 +1325,7 @@ static enum vkd3d_result vsir_program_lower_sm4_sincos(struct vsir_program *prog { vkd3d_shader_error(ctx->message_context, &sincos->location, VKD3D_SHADER_ERROR_VSIR_INVALID_DEST_COUNT, - "Internal compiler error: invalid destination count %u for SINCOS.", + "Internal compiler error: invalid destination count %zu for SINCOS.", sincos->dst_count); return VKD3D_ERROR; } @@ -1497,6 +1501,34 @@ static enum vkd3d_result vsir_program_lower_texldd(struct vsir_program *program, return VKD3D_OK; } +static enum vkd3d_result vsir_program_lower_texldl(struct vsir_program *program, + struct vkd3d_shader_instruction *texldl) +{ + unsigned int idx = texldl->src[1].reg.idx[0].offset; + enum vkd3d_shader_swizzle_component w; + struct vkd3d_shader_src_param *srcs; + + VKD3D_ASSERT(texldl->src[1].reg.idx_count == 1); + VKD3D_ASSERT(!texldl->src[1].reg.idx[0].rel_addr); + + if (!(srcs = shader_src_param_allocator_get(&program->instructions.src_params, 4))) + return VKD3D_ERROR_OUT_OF_MEMORY; + + srcs[0] = texldl->src[0]; + vsir_src_param_init_resource(&srcs[1], idx, idx); + vsir_src_param_init_sampler(&srcs[2], idx, idx); + + texldl->opcode = VSIR_OP_SAMPLE_LOD; + texldl->src = srcs; + texldl->src_count = 4; + + w = vsir_swizzle_get_component(srcs[0].swizzle, 3); + srcs[3] = texldl->src[0]; + srcs[3].swizzle = vkd3d_shader_create_swizzle(w, w, w, w); + + return VKD3D_OK; +} + static enum vkd3d_result vsir_program_lower_dcl_input(struct vsir_program *program, struct vkd3d_shader_instruction *ins, struct vsir_transformation_context *ctx) { @@ -1668,6 +1700,11 @@ static enum vkd3d_result vsir_program_lower_instructions(struct vsir_program *pr return ret; break; + case VSIR_OP_TEXLDL: + if ((ret = vsir_program_lower_texldl(program, ins)) < 0) + return ret; + break; + case VSIR_OP_TEXBEM: case VSIR_OP_TEXBEML: case VSIR_OP_TEXCOORD: @@ -1675,7 +1712,6 @@ static enum vkd3d_result vsir_program_lower_instructions(struct vsir_program *pr case VSIR_OP_TEXDEPTH: case VSIR_OP_TEXDP3: case VSIR_OP_TEXDP3TEX: - case VSIR_OP_TEXLDL: case VSIR_OP_TEXM3x2PAD: case VSIR_OP_TEXM3x2TEX: case VSIR_OP_TEXM3x3DIFF: @@ -9321,7 +9357,7 @@ static void vsir_validate_label_register(struct validation_context *ctx, validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_PRECISION, "Invalid precision %#x for a LABEL register.", reg->precision); - if (reg->data_type != VKD3D_DATA_UNUSED) + if (reg->data_type != VSIR_DATA_UNUSED) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE, "Invalid data type %#x for a LABEL register.", reg->data_type); @@ -9400,7 +9436,7 @@ static void vsir_validate_sampler_register(struct validation_context *ctx, validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_PRECISION, "Invalid precision %#x for a SAMPLER register.", reg->precision); - if (reg->data_type != VKD3D_DATA_UNUSED) + if (reg->data_type != VSIR_DATA_UNUSED) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE, "Invalid data type %#x for a SAMPLER register.", reg->data_type); @@ -9426,7 +9462,7 @@ static void vsir_validate_resource_register(struct validation_context *ctx, validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_PRECISION, "Invalid precision %#x for a RESOURCE register.", reg->precision); - if (reg->data_type != VKD3D_DATA_UNUSED) + if (reg->data_type != VSIR_DATA_UNUSED) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE, "Invalid data type %#x for a RESOURCE register.", reg->data_type); @@ -9452,7 +9488,7 @@ static void vsir_validate_uav_register(struct validation_context *ctx, "Invalid precision %#x for a UAV register.", reg->precision); - if (reg->data_type != VKD3D_DATA_UNUSED) + if (reg->data_type != VSIR_DATA_UNUSED) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE, "Invalid data type %#x for a UAV register.", reg->data_type); @@ -9988,7 +10024,7 @@ static void vsir_validate_dst_count(struct validation_context *ctx, { if (instruction->dst_count != count) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DEST_COUNT, - "Invalid destination parameter count %u for instruction \"%s\" (%#x); expected %u.", + "Invalid destination parameter count %zu for instruction \"%s\" (%#x); expected %u.", instruction->dst_count, vsir_opcode_get_name(instruction->opcode, ""), instruction->opcode, count); } @@ -9998,7 +10034,7 @@ static void vsir_validate_src_count(struct validation_context *ctx, { if (instruction->src_count != count) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_SOURCE_COUNT, - "Invalid source parameter count %u for instruction \"%s\" (%#x); expected %u.", + "Invalid source parameter count %zu for instruction \"%s\" (%#x); expected %u.", instruction->src_count, vsir_opcode_get_name(instruction->opcode, ""), instruction->opcode, count); } @@ -10009,7 +10045,7 @@ static bool vsir_validate_src_min_count(struct validation_context *ctx, if (instruction->src_count < count) { validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_SOURCE_COUNT, - "Invalid source parameter count %u for instruction \"%s\" (%#x); expected at least %u.", + "Invalid source parameter count %zu for instruction \"%s\" (%#x); expected at least %u.", instruction->src_count, vsir_opcode_get_name(instruction->opcode, ""), instruction->opcode, count); return false; @@ -10024,7 +10060,7 @@ static bool vsir_validate_src_max_count(struct validation_context *ctx, if (instruction->src_count > count) { validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_SOURCE_COUNT, - "Invalid source parameter count %u for instruction \"%s\" (%#x); expected at most %u.", + "Invalid source parameter count %zu for instruction \"%s\" (%#x); expected at most %u.", instruction->src_count, vsir_opcode_get_name(instruction->opcode, ""), instruction->opcode, count); return false; @@ -10484,7 +10520,7 @@ static void vsir_validate_descriptors(struct validation_context *ctx) if (descriptor->resource_data_type >= VSIR_DATA_TYPE_COUNT) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE, "Descriptor %u has invalid resource data type %#x.", i, descriptor->resource_data_type); - else if ((descriptor->resource_data_type == VKD3D_DATA_UNUSED) + else if ((descriptor->resource_data_type == VSIR_DATA_UNUSED) != (descriptor->type == VKD3D_SHADER_DESCRIPTOR_TYPE_SAMPLER)) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE, "Descriptor %u has invalid resource data type %#x for descriptor type %#x.", @@ -10653,7 +10689,7 @@ static void vsir_validate_logic_elementwise_operation(struct validation_context { static const bool types[VSIR_DATA_TYPE_COUNT] = { - [VKD3D_DATA_BOOL] = true, + [VSIR_DATA_BOOL] = true, [VSIR_DATA_I32] = true, [VSIR_DATA_U32] = true, [VSIR_DATA_U64] = true, @@ -10673,7 +10709,7 @@ static void vsir_validate_comparison_operation(struct validation_context *ctx, dst_data_type = instruction->dst[0].reg.data_type; - if (dst_data_type != VSIR_DATA_U32 && dst_data_type != VKD3D_DATA_BOOL) + if (dst_data_type != VSIR_DATA_U32 && dst_data_type != VSIR_DATA_BOOL) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_DATA_TYPE, "Invalid data type %#x for result of comparison operation \"%s\" (%#x).", dst_data_type, vsir_opcode_get_name(instruction->opcode, ""), instruction->opcode); @@ -11326,7 +11362,7 @@ static void vsir_validate_itof(struct validation_context *ctx, const struct vkd3 { static const bool src_types[VSIR_DATA_TYPE_COUNT] = { - [VKD3D_DATA_BOOL] = true, + [VSIR_DATA_BOOL] = true, [VSIR_DATA_I32] = true, [VSIR_DATA_U32] = true, [VSIR_DATA_U64] = true, @@ -11345,7 +11381,7 @@ static void vsir_validate_itoi(struct validation_context *ctx, const struct vkd3 { static const bool types[VSIR_DATA_TYPE_COUNT] = { - [VKD3D_DATA_BOOL] = true, + [VSIR_DATA_BOOL] = true, [VSIR_DATA_I32] = true, [VSIR_DATA_U32] = true, [VSIR_DATA_U64] = true, @@ -11389,7 +11425,7 @@ static void vsir_validate_phi(struct validation_context *ctx, const struct vkd3d if (instruction->src_count % 2 != 0) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_SOURCE_COUNT, - "Invalid source count %u for a PHI instruction, it must be an even number.", + "Invalid source count %zu for a PHI instruction, it must be an even number.", instruction->src_count); incoming_count = instruction->src_count / 2; @@ -11471,7 +11507,7 @@ static void vsir_validate_switch_monolithic(struct validation_context *ctx, if (instruction->src_count % 2 != 1) validator_error(ctx, VKD3D_SHADER_ERROR_VSIR_INVALID_SOURCE_COUNT, - "Invalid source count %u for a monolithic SWITCH instruction, it must be an odd number.", + "Invalid source count %zu for a monolithic SWITCH instruction, it must be an odd number.", instruction->src_count); if (!vsir_register_is_label(&instruction->src[1].reg)) diff --git a/libs/vkd3d/libs/vkd3d-shader/msl.c b/libs/vkd3d/libs/vkd3d-shader/msl.c index ccfce0f4591..d95b95f9738 100644 --- a/libs/vkd3d/libs/vkd3d-shader/msl.c +++ b/libs/vkd3d/libs/vkd3d-shader/msl.c @@ -138,8 +138,8 @@ static void msl_print_resource_datatype(struct msl_generator *gen, switch (data_type) { case VSIR_DATA_F32: - case VKD3D_DATA_UNORM: - case VKD3D_DATA_SNORM: + case VSIR_DATA_SNORM: + case VSIR_DATA_UNORM: vkd3d_string_buffer_printf(buffer, "float"); break; case VSIR_DATA_I32: @@ -527,7 +527,7 @@ static void msl_print_bitcast(struct vkd3d_string_buffer *dst, struct msl_genera { bool write_cast = false; - if (dst_data_type == VKD3D_DATA_UNORM || dst_data_type == VKD3D_DATA_SNORM) + if (dst_data_type == VSIR_DATA_UNORM || dst_data_type == VSIR_DATA_SNORM) dst_data_type = VSIR_DATA_F32; switch (src_data_type) @@ -1320,8 +1320,8 @@ static void msl_store_uav_typed(struct msl_generator *gen, const struct vkd3d_sh "Internal compiler error: Unhandled data type %#x.", data_type); /* fall through */ case VSIR_DATA_F32: - case VKD3D_DATA_UNORM: - case VKD3D_DATA_SNORM: + case VSIR_DATA_SNORM: + case VSIR_DATA_UNORM: vkd3d_string_buffer_printf(image_data, "float4("); break; } diff --git a/libs/vkd3d/libs/vkd3d-shader/spirv.c b/libs/vkd3d/libs/vkd3d-shader/spirv.c index d99c7ee27ff..2e6d0c786d0 100644 --- a/libs/vkd3d/libs/vkd3d-shader/spirv.c +++ b/libs/vkd3d/libs/vkd3d-shader/spirv.c @@ -7588,7 +7588,7 @@ static void spirv_compiler_emit_bool_cast(struct spirv_compiler *compiler, const struct vkd3d_shader_src_param *src = instruction->src; uint32_t val_id; - VKD3D_ASSERT(src->reg.data_type == VKD3D_DATA_BOOL && dst->reg.data_type != VKD3D_DATA_BOOL); + VKD3D_ASSERT(src->reg.data_type == VSIR_DATA_BOOL && dst->reg.data_type != VSIR_DATA_BOOL); val_id = spirv_compiler_emit_load_src(compiler, src, dst->write_mask); if (dst->reg.data_type == VSIR_DATA_F16 || dst->reg.data_type == VSIR_DATA_F32) @@ -7639,9 +7639,9 @@ static enum vkd3d_result spirv_compiler_emit_alu_instruction(struct spirv_compil return VKD3D_ERROR_INVALID_SHADER; } - if (src->reg.data_type == VKD3D_DATA_BOOL) + if (src->reg.data_type == VSIR_DATA_BOOL) { - if (dst->reg.data_type == VKD3D_DATA_BOOL) + if (dst->reg.data_type == VSIR_DATA_BOOL) { /* VSIR supports logic ops AND/OR/XOR on bool values. */ op = spirv_compiler_map_logical_instruction(instruction); @@ -7955,7 +7955,7 @@ static void spirv_compiler_emit_movc(struct spirv_compiler *compiler, component_count = vsir_write_mask_component_count(dst->write_mask); type_id = spirv_compiler_get_type_id_for_dst(compiler, dst); - if (src[0].reg.data_type != VKD3D_DATA_BOOL) + if (src[0].reg.data_type != VSIR_DATA_BOOL) { if (instruction->opcode == VSIR_OP_CMP) condition_id = vkd3d_spirv_build_op_tr2(builder, &builder->function_stream, SpvOpFOrdGreaterThanEqual, @@ -8398,7 +8398,7 @@ static void spirv_compiler_emit_comparison_instruction(struct spirv_compiler *co result_id = vkd3d_spirv_build_op_tr2(builder, &builder->function_stream, op, type_id, src0_id, src1_id); - if (dst->reg.data_type != VKD3D_DATA_BOOL) + if (dst->reg.data_type != VSIR_DATA_BOOL) result_id = spirv_compiler_emit_bool_to_int(compiler, component_count, result_id, true); spirv_compiler_emit_store_reg(compiler, &dst->reg, dst->write_mask, result_id); } @@ -8579,7 +8579,7 @@ static void spirv_compiler_emit_discard(struct spirv_compiler *compiler, * a mismatch between the VSIR structure and the SPIR-V one, which would cause problems if * structurisation is necessary. Therefore we emit it as a function call. */ condition_id = spirv_compiler_emit_load_src(compiler, src, VKD3DSP_WRITEMASK_0); - if (src->reg.data_type != VKD3D_DATA_BOOL) + if (src->reg.data_type != VSIR_DATA_BOOL) condition_id = spirv_compiler_emit_int_to_bool(compiler, instruction->flags, src->reg.data_type, 1, condition_id); else if (instruction->flags & VKD3D_SHADER_CONDITIONAL_OP_Z) @@ -8652,7 +8652,7 @@ static void spirv_compiler_emit_branch(struct spirv_compiler *compiler, if (instruction->src_count == 3) spirv_compiler_emit_merge(compiler, src[1].reg.idx[0].offset, src[2].reg.idx[0].offset); else - ERR("Invalid branch with %u sources.\n", instruction->src_count); + ERR("Invalid branch with %zu sources.\n", instruction->src_count); } vkd3d_spirv_build_op_branch(builder, spirv_compiler_get_label_id(compiler, src[0].reg.idx[0].offset)); return; @@ -8666,7 +8666,7 @@ static void spirv_compiler_emit_branch(struct spirv_compiler *compiler, } condition_id = spirv_compiler_emit_load_src(compiler, &src[0], VKD3DSP_WRITEMASK_0); - if (src[0].reg.data_type != VKD3D_DATA_BOOL) + if (src[0].reg.data_type != VSIR_DATA_BOOL) condition_id = spirv_compiler_emit_int_to_bool(compiler, VKD3D_SHADER_CONDITIONAL_OP_NZ, src[0].reg.data_type, 1, condition_id); /* Emit the merge immediately before the branch instruction. */ @@ -8674,7 +8674,7 @@ static void spirv_compiler_emit_branch(struct spirv_compiler *compiler, spirv_compiler_emit_merge(compiler, src[3].reg.idx[0].offset, (instruction->src_count > 4) ? src[4].reg.idx[0].offset : 0); else - ERR("Invalid branch with %u sources.\n", instruction->src_count); + ERR("Invalid branch with %zu sources.\n", instruction->src_count); vkd3d_spirv_build_op_branch_conditional(builder, condition_id, spirv_compiler_get_label_id(compiler, src[1].reg.idx[0].offset), spirv_compiler_get_label_id(compiler, src[2].reg.idx[0].offset)); @@ -9922,16 +9922,20 @@ static void spirv_compiler_emit_bufinfo(struct spirv_compiler *compiler, static void spirv_compiler_emit_resinfo(struct spirv_compiler *compiler, const struct vkd3d_shader_instruction *instruction) { + enum vkd3d_shader_component_type component_type = VKD3D_SHADER_COMPONENT_UINT; struct vkd3d_spirv_builder *builder = &compiler->spirv_builder; const struct vkd3d_shader_dst_param *dst = instruction->dst; const struct vkd3d_shader_src_param *src = instruction->src; uint32_t type_id, lod_id, val_id, miplevel_count_id; - enum vkd3d_shader_component_type component_type; uint32_t constituents[VKD3D_VEC4_SIZE]; unsigned int i, size_component_count; struct vkd3d_shader_image image; bool supports_mipmaps; + if (instruction->flags & ~VKD3DSI_RESINFO_UINT) + spirv_compiler_error(compiler, VKD3D_SHADER_ERROR_SPV_NOT_IMPLEMENTED, + "Unhandled resinfo flags %#x.\n", instruction->flags & ~VKD3DSI_RESINFO_UINT); + vkd3d_spirv_enable_capability(builder, SpvCapabilityImageQuery); spirv_compiler_prepare_image(compiler, &image, &src[1].reg, NULL, VKD3D_IMAGE_FLAG_NONE); @@ -9963,21 +9967,10 @@ static void spirv_compiler_emit_resinfo(struct spirv_compiler *compiler, val_id = vkd3d_spirv_build_op_composite_construct(builder, type_id, constituents, i + 2); - component_type = VKD3D_SHADER_COMPONENT_FLOAT; - - type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, VKD3D_VEC4_SIZE); - if (instruction->flags == VKD3DSI_RESINFO_UINT) - { - /* SSA registers must match the specified result type. */ - if (!register_is_ssa(&dst->reg)) - val_id = vkd3d_spirv_build_op_bitcast(builder, type_id, val_id); - else - component_type = VKD3D_SHADER_COMPONENT_UINT; - } - else + if (!(instruction->flags & VKD3DSI_RESINFO_UINT)) { - if (instruction->flags) - FIXME("Unhandled flags %#x.\n", instruction->flags); + component_type = VKD3D_SHADER_COMPONENT_FLOAT; + type_id = vkd3d_spirv_get_type_id(builder, component_type, VKD3D_VEC4_SIZE); val_id = vkd3d_spirv_build_op_convert_utof(builder, type_id, val_id); } val_id = spirv_compiler_emit_swizzle(compiler, val_id, VKD3DSP_WRITEMASK_ALL, @@ -10013,6 +10006,7 @@ static uint32_t spirv_compiler_emit_query_sample_count(struct spirv_compiler *co static void spirv_compiler_emit_sample_info(struct spirv_compiler *compiler, const struct vkd3d_shader_instruction *instruction) { + enum vkd3d_shader_component_type component_type = VKD3D_SHADER_COMPONENT_UINT; struct vkd3d_spirv_builder *builder = &compiler->spirv_builder; const struct vkd3d_shader_dst_param *dst = instruction->dst; const struct vkd3d_shader_src_param *src = instruction->src; @@ -10020,6 +10014,10 @@ static void spirv_compiler_emit_sample_info(struct spirv_compiler *compiler, uint32_t type_id, val_id; unsigned int i; + if (instruction->flags & ~VKD3DSI_SAMPLE_INFO_UINT) + spirv_compiler_error(compiler, VKD3D_SHADER_ERROR_SPV_NOT_IMPLEMENTED, + "Unhandled sample info flags %#x.\n", instruction->flags & ~VKD3DSI_SAMPLE_INFO_UINT); + val_id = spirv_compiler_emit_query_sample_count(compiler, src); constituents[0] = val_id; @@ -10028,20 +10026,14 @@ static void spirv_compiler_emit_sample_info(struct spirv_compiler *compiler, type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_UINT, VKD3D_VEC4_SIZE); val_id = vkd3d_spirv_build_op_composite_construct(builder, type_id, constituents, VKD3D_VEC4_SIZE); - type_id = vkd3d_spirv_get_type_id(builder, VKD3D_SHADER_COMPONENT_FLOAT, VKD3D_VEC4_SIZE); - if (instruction->flags == VKD3DSI_SAMPLE_INFO_UINT) + if (!(instruction->flags & VKD3DSI_SAMPLE_INFO_UINT)) { - val_id = vkd3d_spirv_build_op_bitcast(builder, type_id, val_id); - } - else - { - if (instruction->flags) - FIXME("Unhandled flags %#x.\n", instruction->flags); + component_type = VKD3D_SHADER_COMPONENT_FLOAT; + type_id = vkd3d_spirv_get_type_id(builder, component_type, VKD3D_VEC4_SIZE); val_id = vkd3d_spirv_build_op_convert_utof(builder, type_id, val_id); } - val_id = spirv_compiler_emit_swizzle(compiler, val_id, VKD3DSP_WRITEMASK_ALL, - VKD3D_SHADER_COMPONENT_FLOAT, src->swizzle, dst->write_mask); + component_type, src->swizzle, dst->write_mask); spirv_compiler_emit_store_dst(compiler, dst, val_id); } diff --git a/libs/vkd3d/libs/vkd3d-shader/tpf.c b/libs/vkd3d/libs/vkd3d-shader/tpf.c index 8acd7bc0db5..2175298a0db 100644 --- a/libs/vkd3d/libs/vkd3d-shader/tpf.c +++ b/libs/vkd3d/libs/vkd3d-shader/tpf.c @@ -751,15 +751,15 @@ static const enum vkd3d_shader_resource_type resource_type_table[] = static const enum vsir_data_type data_type_table[] = { /* 0 */ VSIR_DATA_F32, - /* VKD3D_SM4_DATA_UNORM */ VKD3D_DATA_UNORM, - /* VKD3D_SM4_DATA_SNORM */ VKD3D_DATA_SNORM, + /* VKD3D_SM4_DATA_UNORM */ VSIR_DATA_UNORM, + /* VKD3D_SM4_DATA_SNORM */ VSIR_DATA_SNORM, /* VKD3D_SM4_DATA_INT */ VSIR_DATA_I32, /* VKD3D_SM4_DATA_UINT */ VSIR_DATA_U32, /* VKD3D_SM4_DATA_FLOAT */ VSIR_DATA_F32, - /* VKD3D_SM4_DATA_MIXED */ VKD3D_DATA_MIXED, + /* VKD3D_SM4_DATA_MIXED */ VSIR_DATA_MIXED, /* VKD3D_SM4_DATA_DOUBLE */ VSIR_DATA_F64, - /* VKD3D_SM4_DATA_CONTINUED */ VKD3D_DATA_CONTINUED, - /* VKD3D_SM4_DATA_UNUSED */ VKD3D_DATA_UNUSED, + /* VKD3D_SM4_DATA_CONTINUED */ VSIR_DATA_CONTINUED, + /* VKD3D_SM4_DATA_UNUSED */ VSIR_DATA_UNUSED, }; static bool shader_is_sm_5_1(const struct vkd3d_shader_sm4_parser *sm4) @@ -895,7 +895,7 @@ static void shader_sm4_read_dcl_resource(struct vkd3d_shader_instruction *ins, u >> VKD3D_SM4_RESOURCE_SAMPLE_COUNT_SHIFT; } - reg_data_type = VKD3D_DATA_UNUSED; + reg_data_type = VSIR_DATA_UNUSED; shader_sm4_read_dst_param(priv, &tokens, end, reg_data_type, &semantic->resource.reg); shader_sm4_set_descriptor_register_range(priv, &semantic->resource.reg.reg, &semantic->resource.range); @@ -957,7 +957,7 @@ static void shader_sm4_read_dcl_sampler(struct vkd3d_shader_instruction *ins, ui ins->flags = (opcode_token & VKD3D_SM4_SAMPLER_MODE_MASK) >> VKD3D_SM4_SAMPLER_MODE_SHIFT; if (ins->flags & ~VKD3D_SM4_SAMPLER_COMPARISON) FIXME("Unhandled sampler mode %#x.\n", ins->flags); - shader_sm4_read_src_param(priv, &tokens, end, VKD3D_DATA_UNUSED, &ins->declaration.sampler.src); + shader_sm4_read_src_param(priv, &tokens, end, VSIR_DATA_UNUSED, &ins->declaration.sampler.src); shader_sm4_set_descriptor_register_range(priv, &ins->declaration.sampler.src.reg, &ins->declaration.sampler.range); shader_sm4_read_register_space(priv, &tokens, end, &ins->declaration.sampler.range.space); } @@ -979,8 +979,7 @@ static void shader_sm4_read_dcl_index_range(struct vkd3d_shader_instruction *ins unsigned int *io_masks; uint32_t write_mask; - shader_sm4_read_dst_param(priv, &tokens, &tokens[token_count], VKD3D_DATA_OPAQUE, - &index_range->dst); + shader_sm4_read_dst_param(priv, &tokens, &tokens[token_count], VSIR_DATA_OPAQUE, &index_range->dst); index_range->register_count = *tokens; register_idx = index_range->dst.reg.idx[index_range->dst.reg.idx_count - 1].offset; @@ -1228,7 +1227,7 @@ static void shader_sm5_read_fcall(struct vkd3d_shader_instruction *ins, uint32_t const uint32_t *tokens, unsigned int token_count, struct vkd3d_shader_sm4_parser *priv) { ins->src[0].reg.u.fp_body_idx = *tokens++; - shader_sm4_read_src_param(priv, &tokens, &tokens[token_count], VKD3D_DATA_OPAQUE, &ins->src[0]); + shader_sm4_read_src_param(priv, &tokens, &tokens[token_count], VSIR_DATA_OPAQUE, &ins->src[0]); } static void shader_sm5_read_dcl_function_body(struct vkd3d_shader_instruction *ins, uint32_t opcode, @@ -1315,7 +1314,7 @@ static void shader_sm5_read_dcl_uav_raw(struct vkd3d_shader_instruction *ins, ui struct vkd3d_shader_raw_resource *resource = &ins->declaration.raw_resource; const uint32_t *end = &tokens[token_count]; - shader_sm4_read_dst_param(priv, &tokens, end, VKD3D_DATA_UNUSED, &resource->resource.reg); + shader_sm4_read_dst_param(priv, &tokens, end, VSIR_DATA_UNUSED, &resource->resource.reg); shader_sm4_set_descriptor_register_range(priv, &resource->resource.reg.reg, &resource->resource.range); ins->flags = (opcode_token & VKD3D_SM5_UAV_FLAGS_MASK) >> VKD3D_SM5_UAV_FLAGS_SHIFT; shader_sm4_read_register_space(priv, &tokens, end, &resource->resource.range.space); @@ -1327,7 +1326,7 @@ static void shader_sm5_read_dcl_uav_structured(struct vkd3d_shader_instruction * struct vkd3d_shader_structured_resource *resource = &ins->declaration.structured_resource; const uint32_t *end = &tokens[token_count]; - shader_sm4_read_dst_param(priv, &tokens, end, VKD3D_DATA_UNUSED, &resource->resource.reg); + shader_sm4_read_dst_param(priv, &tokens, end, VSIR_DATA_UNUSED, &resource->resource.reg); shader_sm4_set_descriptor_register_range(priv, &resource->resource.reg.reg, &resource->resource.range); ins->flags = (opcode_token & VKD3D_SM5_UAV_FLAGS_MASK) >> VKD3D_SM5_UAV_FLAGS_SHIFT; resource->byte_stride = *tokens++; @@ -1364,7 +1363,7 @@ static void shader_sm5_read_dcl_resource_structured(struct vkd3d_shader_instruct struct vkd3d_shader_structured_resource *resource = &ins->declaration.structured_resource; const uint32_t *end = &tokens[token_count]; - shader_sm4_read_dst_param(priv, &tokens, end, VKD3D_DATA_UNUSED, &resource->resource.reg); + shader_sm4_read_dst_param(priv, &tokens, end, VSIR_DATA_UNUSED, &resource->resource.reg); shader_sm4_set_descriptor_register_range(priv, &resource->resource.reg.reg, &resource->resource.range); resource->byte_stride = *tokens++; if (resource->byte_stride % 4) @@ -1378,7 +1377,7 @@ static void shader_sm5_read_dcl_resource_raw(struct vkd3d_shader_instruction *in struct vkd3d_shader_raw_resource *resource = &ins->declaration.raw_resource; const uint32_t *end = &tokens[token_count]; - shader_sm4_read_dst_param(priv, &tokens, end, VKD3D_DATA_UNUSED, &resource->resource.reg); + shader_sm4_read_dst_param(priv, &tokens, end, VSIR_DATA_UNUSED, &resource->resource.reg); shader_sm4_set_descriptor_register_range(priv, &resource->resource.reg.reg, &resource->resource.range); shader_sm4_read_register_space(priv, &tokens, end, &resource->resource.range.space); } @@ -1434,7 +1433,7 @@ static void init_sm4_lookup_tables(struct vkd3d_sm4_lookup_tables *lookup) * f -> VSIR_DATA_F32 * i -> VSIR_DATA_I32 * u -> VSIR_DATA_U32 - * O -> VKD3D_DATA_OPAQUE + * O -> VSIR_DATA_OPAQUE * R -> VKD3D_DATA_RESOURCE * S -> VKD3D_DATA_SAMPLER * U -> VKD3D_DATA_UAV @@ -1998,9 +1997,9 @@ static enum vsir_data_type map_data_type(char t) case 'u': return VSIR_DATA_U32; case 'O': - return VKD3D_DATA_OPAQUE; + return VSIR_DATA_OPAQUE; case '*': - return VKD3D_DATA_UNUSED; + return VSIR_DATA_UNUSED; default: ERR("Invalid data type '%c'.\n", t); return VSIR_DATA_F32; @@ -2743,6 +2742,10 @@ static void shader_sm4_read_instruction(struct vkd3d_shader_sm4_parser *sm4, str } } + if ((ins->opcode == VSIR_OP_SAMPLE_INFO && ins->flags & VKD3DSI_SAMPLE_INFO_UINT) + || (ins->opcode == VSIR_OP_RESINFO && ins->flags & VKD3DSI_RESINFO_UINT)) + ins->dst[0].reg.data_type = VSIR_DATA_U32; + return; fail: @@ -4087,14 +4090,14 @@ static void tpf_simple_instruction(struct tpf_compiler *tpf, const struct vkd3d_ if (ins->dst_count != dst_count) { - ERR("Invalid destination count %u for vsir instruction %#x (expected %u).\n", + ERR("Invalid destination count %zu for vsir instruction %#x (expected %u).\n", ins->dst_count, ins->opcode, dst_count); tpf->result = VKD3D_ERROR_INVALID_SHADER; return; } if (ins->src_count != src_count) { - ERR("Invalid source count %u for vsir instruction %#x (expected %u).\n", + ERR("Invalid source count %zu for vsir instruction %#x (expected %u).\n", ins->src_count, ins->opcode, src_count); tpf->result = VKD3D_ERROR_INVALID_SHADER; return; diff --git a/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_main.c b/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_main.c index 9c615c116e9..a3c00af5d8b 100644 --- a/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_main.c +++ b/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_main.c @@ -87,7 +87,7 @@ void vkd3d_string_buffer_truncate(struct vkd3d_string_buffer *buffer, size_t siz static bool vkd3d_string_buffer_resize(struct vkd3d_string_buffer *buffer, int rc) { - unsigned int new_buffer_size = rc >= 0 ? buffer->content_size + rc + 1 : buffer->buffer_size * 2; + size_t new_buffer_size = rc >= 0 ? buffer->content_size + rc + 1 : buffer->buffer_size * 2; if (!vkd3d_array_reserve((void **)&buffer->buffer, &buffer->buffer_size, new_buffer_size, 1)) { @@ -100,7 +100,7 @@ static bool vkd3d_string_buffer_resize(struct vkd3d_string_buffer *buffer, int r int vkd3d_string_buffer_vprintf(struct vkd3d_string_buffer *buffer, const char *format, va_list args) { - unsigned int rem; + size_t rem; va_list a; int rc; @@ -135,7 +135,7 @@ int vkd3d_string_buffer_printf(struct vkd3d_string_buffer *buffer, const char *f int vkd3d_string_buffer_print_f32(struct vkd3d_string_buffer *buffer, float f) { - unsigned int idx = buffer->content_size + 1; + size_t idx = buffer->content_size + 1; int ret; if (!(ret = vkd3d_string_buffer_printf(buffer, "%.8e", f)) && isfinite(f)) @@ -150,7 +150,7 @@ int vkd3d_string_buffer_print_f32(struct vkd3d_string_buffer *buffer, float f) int vkd3d_string_buffer_print_f64(struct vkd3d_string_buffer *buffer, double d) { - unsigned int idx = buffer->content_size + 1; + size_t idx = buffer->content_size + 1; int ret; if (!(ret = vkd3d_string_buffer_printf(buffer, "%.16e", d)) && isfinite(d)) @@ -1132,7 +1132,7 @@ static void vkd3d_shader_scan_sampler_declaration(struct vkd3d_shader_scan_conte struct vkd3d_shader_descriptor_info1 *d; if (!(d = vkd3d_shader_scan_add_descriptor(context, VKD3D_SHADER_DESCRIPTOR_TYPE_SAMPLER, - &sampler->src.reg, &sampler->range, VKD3D_SHADER_RESOURCE_NONE, VKD3D_DATA_UNUSED))) + &sampler->src.reg, &sampler->range, VKD3D_SHADER_RESOURCE_NONE, VSIR_DATA_UNUSED))) return; if (instruction->flags & VKD3DSI_SAMPLER_COMPARISON_MODE) @@ -1143,7 +1143,7 @@ static void vkd3d_shader_scan_combined_sampler_declaration( struct vkd3d_shader_scan_context *context, const struct vkd3d_shader_semantic *semantic) { vkd3d_shader_scan_add_descriptor(context, VKD3D_SHADER_DESCRIPTOR_TYPE_SAMPLER, &semantic->resource.reg.reg, - &semantic->resource.range, VKD3D_SHADER_RESOURCE_NONE, VKD3D_DATA_UNUSED); + &semantic->resource.range, VKD3D_SHADER_RESOURCE_NONE, VSIR_DATA_UNUSED); vkd3d_shader_scan_add_descriptor(context, VKD3D_SHADER_DESCRIPTOR_TYPE_SRV, &semantic->resource.reg.reg, &semantic->resource.range, semantic->resource_type, VSIR_DATA_F32); } @@ -1526,16 +1526,6 @@ static enum vkd3d_shader_resource_data_type vkd3d_resource_data_type_from_data_t { switch (data_type) { - case VKD3D_DATA_UNORM: - return VKD3D_SHADER_RESOURCE_DATA_UNORM; - case VKD3D_DATA_SNORM: - return VKD3D_SHADER_RESOURCE_DATA_SNORM; - case VKD3D_DATA_MIXED: - return VKD3D_SHADER_RESOURCE_DATA_MIXED; - case VKD3D_DATA_CONTINUED: - return VKD3D_SHADER_RESOURCE_DATA_CONTINUED; - case VKD3D_DATA_UNUSED: - return VKD3D_SHADER_RESOURCE_DATA_NONE; case VSIR_DATA_F32: return VKD3D_SHADER_RESOURCE_DATA_FLOAT; case VSIR_DATA_F64: @@ -1544,6 +1534,16 @@ static enum vkd3d_shader_resource_data_type vkd3d_resource_data_type_from_data_t return VKD3D_SHADER_RESOURCE_DATA_INT; case VSIR_DATA_U32: return VKD3D_SHADER_RESOURCE_DATA_UINT; + case VSIR_DATA_SNORM: + return VKD3D_SHADER_RESOURCE_DATA_SNORM; + case VSIR_DATA_UNORM: + return VKD3D_SHADER_RESOURCE_DATA_UNORM; + case VSIR_DATA_MIXED: + return VKD3D_SHADER_RESOURCE_DATA_MIXED; + case VSIR_DATA_CONTINUED: + return VKD3D_SHADER_RESOURCE_DATA_CONTINUED; + case VSIR_DATA_UNUSED: + return VKD3D_SHADER_RESOURCE_DATA_NONE; default: ERR("Invalid resource data type %#x.\n", data_type); return VKD3D_SHADER_RESOURCE_DATA_FLOAT; @@ -1785,6 +1785,7 @@ static int compile_hlsl(const struct vkd3d_shader_compile_info *compile_info, const struct shader_dump_data *dump_data, struct vkd3d_shader_code *out, struct vkd3d_shader_message_context *message_context) { + struct vkd3d_shader_compile_info preprocessed_info; struct vkd3d_shader_code preprocessed; int ret; @@ -1793,7 +1794,9 @@ static int compile_hlsl(const struct vkd3d_shader_compile_info *compile_info, vkd3d_shader_dump_shader(dump_data, preprocessed.code, preprocessed.size, SHADER_DUMP_TYPE_PREPROC); - ret = hlsl_compile_shader(&preprocessed, compile_info, out, message_context); + preprocessed_info = *compile_info; + preprocessed_info.source = preprocessed; + ret = hlsl_compile_shader(&preprocessed_info, message_context, out); vkd3d_shader_free_shader_code(&preprocessed); return ret; @@ -2187,7 +2190,7 @@ static struct vkd3d_shader_param_node *shader_param_allocator_node_create( } static void shader_param_allocator_init(struct vkd3d_shader_param_allocator *allocator, - unsigned int count, unsigned int stride) + size_t count, size_t stride) { allocator->count = max(count, MAX_REG_OUTPUT); allocator->stride = stride; @@ -2208,7 +2211,7 @@ static void shader_param_allocator_destroy(struct vkd3d_shader_param_allocator * } } -void *shader_param_allocator_get(struct vkd3d_shader_param_allocator *allocator, unsigned int count) +void *shader_param_allocator_get(struct vkd3d_shader_param_allocator *allocator, size_t count) { void *params; @@ -2234,7 +2237,7 @@ void *shader_param_allocator_get(struct vkd3d_shader_param_allocator *allocator, return params; } -bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *instructions, unsigned int reserve) +bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *instructions, size_t reserve) { memset(instructions, 0, sizeof(*instructions)); /* Size the parameter initial allocations so they are large enough for most shaders. The @@ -2245,7 +2248,7 @@ bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *instru return shader_instruction_array_reserve(instructions, reserve); } -bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *instructions, unsigned int reserve) +bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *instructions, size_t reserve) { if (!vkd3d_array_reserve((void **)&instructions->elements, &instructions->capacity, reserve, sizeof(*instructions->elements))) @@ -2257,7 +2260,7 @@ bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *ins } bool shader_instruction_array_insert_at(struct vkd3d_shader_instruction_array *instructions, - unsigned int idx, unsigned int count) + size_t idx, size_t count) { VKD3D_ASSERT(idx <= instructions->count); @@ -2285,7 +2288,7 @@ bool shader_instruction_array_add_icb(struct vkd3d_shader_instruction_array *ins static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params( struct vkd3d_shader_instruction_array *instructions, const struct vkd3d_shader_src_param *params, - unsigned int count); + size_t count); static bool shader_register_clone_relative_addresses(struct vkd3d_shader_register *reg, struct vkd3d_shader_instruction_array *instructions) @@ -2306,10 +2309,10 @@ static bool shader_register_clone_relative_addresses(struct vkd3d_shader_registe static struct vkd3d_shader_dst_param *shader_instruction_array_clone_dst_params( struct vkd3d_shader_instruction_array *instructions, const struct vkd3d_shader_dst_param *params, - unsigned int count) + size_t count) { struct vkd3d_shader_dst_param *dst_params; - unsigned int i; + size_t i; if (!(dst_params = shader_dst_param_allocator_get(&instructions->dst_params, count))) return NULL; @@ -2326,10 +2329,10 @@ static struct vkd3d_shader_dst_param *shader_instruction_array_clone_dst_params( static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params( struct vkd3d_shader_instruction_array *instructions, const struct vkd3d_shader_src_param *params, - unsigned int count) + size_t count) { struct vkd3d_shader_src_param *src_params; - unsigned int i; + size_t i; if (!(src_params = shader_src_param_allocator_get(&instructions->src_params, count))) return NULL; @@ -2347,7 +2350,7 @@ static struct vkd3d_shader_src_param *shader_instruction_array_clone_src_params( /* NOTE: Immediate constant buffers are not cloned, so the source must not be destroyed while the * destination is in use. This seems like a reasonable requirement given how this is currently used. */ bool shader_instruction_array_clone_instruction(struct vkd3d_shader_instruction_array *instructions, - unsigned int dst, unsigned int src) + size_t dst, size_t src) { struct vkd3d_shader_instruction *ins = &instructions->elements[dst]; diff --git a/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_private.h b/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_private.h index 42f3c42033f..a0d7faaa407 100644 --- a/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_private.h +++ b/libs/vkd3d/libs/vkd3d-shader/vkd3d_shader_private.h @@ -710,13 +710,7 @@ enum vkd3d_shader_register_precision enum vsir_data_type { - VKD3D_DATA_UNORM, - VKD3D_DATA_SNORM, - VKD3D_DATA_OPAQUE, - VKD3D_DATA_MIXED, - VKD3D_DATA_CONTINUED, - VKD3D_DATA_UNUSED, - VKD3D_DATA_BOOL, + VSIR_DATA_BOOL, VSIR_DATA_F16, VSIR_DATA_F32, @@ -729,6 +723,14 @@ enum vsir_data_type VSIR_DATA_U32, VSIR_DATA_U64, + VSIR_DATA_SNORM, + VSIR_DATA_UNORM, + + VSIR_DATA_OPAQUE, + VSIR_DATA_MIXED, + VSIR_DATA_CONTINUED, + VSIR_DATA_UNUSED, + VSIR_DATA_TYPE_COUNT, }; @@ -740,7 +742,7 @@ static inline bool data_type_is_integer(enum vsir_data_type data_type) static inline bool data_type_is_bool(enum vsir_data_type data_type) { - return data_type == VKD3D_DATA_BOOL; + return data_type == VSIR_DATA_BOOL; } static inline bool data_type_is_floating_point(enum vsir_data_type data_type) @@ -1281,8 +1283,8 @@ struct vkd3d_shader_instruction struct vkd3d_shader_location location; enum vkd3d_shader_opcode opcode; uint32_t flags; - unsigned int dst_count; - unsigned int src_count; + size_t dst_count; + size_t src_count; struct vkd3d_shader_dst_param *dst; struct vkd3d_shader_src_param *src; struct vkd3d_shader_texel_offset texel_offset; @@ -1377,22 +1379,22 @@ struct vkd3d_shader_param_allocator { struct vkd3d_shader_param_node *head; struct vkd3d_shader_param_node *current; - unsigned int count; - unsigned int stride; - unsigned int index; + size_t count; + size_t stride; + size_t index; }; -void *shader_param_allocator_get(struct vkd3d_shader_param_allocator *allocator, unsigned int count); +void *shader_param_allocator_get(struct vkd3d_shader_param_allocator *allocator, size_t count); static inline struct vkd3d_shader_src_param *shader_src_param_allocator_get( - struct vkd3d_shader_param_allocator *allocator, unsigned int count) + struct vkd3d_shader_param_allocator *allocator, size_t count) { VKD3D_ASSERT(allocator->stride == sizeof(struct vkd3d_shader_src_param)); return shader_param_allocator_get(allocator, count); } static inline struct vkd3d_shader_dst_param *shader_dst_param_allocator_get( - struct vkd3d_shader_param_allocator *allocator, unsigned int count) + struct vkd3d_shader_param_allocator *allocator, size_t count) { VKD3D_ASSERT(allocator->stride == sizeof(struct vkd3d_shader_dst_param)); return shader_param_allocator_get(allocator, count); @@ -1413,14 +1415,14 @@ struct vkd3d_shader_instruction_array struct vkd3d_shader_src_param *outpointid_param; }; -bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *instructions, unsigned int reserve); -bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *instructions, unsigned int reserve); +bool shader_instruction_array_init(struct vkd3d_shader_instruction_array *instructions, size_t reserve); +bool shader_instruction_array_reserve(struct vkd3d_shader_instruction_array *instructions, size_t reserve); bool shader_instruction_array_insert_at(struct vkd3d_shader_instruction_array *instructions, - unsigned int idx, unsigned int count); + size_t idx, size_t count); bool shader_instruction_array_add_icb(struct vkd3d_shader_instruction_array *instructions, struct vkd3d_shader_immediate_constant_buffer *icb); bool shader_instruction_array_clone_instruction(struct vkd3d_shader_instruction_array *instructions, - unsigned int dst, unsigned int src); + size_t dst, size_t src); void shader_instruction_array_destroy(struct vkd3d_shader_instruction_array *instructions); struct vsir_program_iterator @@ -1463,7 +1465,7 @@ static inline struct vkd3d_shader_instruction *vsir_program_iterator_next( /* When insertion takes place, argument `it' is updated to point to the same * instruction as before the insertion, but all other iterators and pointers * to the same container are invalidated and cannot be used any more. */ -static inline bool vsir_program_iterator_insert_after(struct vsir_program_iterator *it, unsigned int count) +static inline bool vsir_program_iterator_insert_after(struct vsir_program_iterator *it, size_t count) { return shader_instruction_array_insert_at(it->array, it->idx + 1, count); } @@ -1797,17 +1799,19 @@ void vkd3d_compute_md5(const void *dxbc, size_t size, uint32_t checksum[4], enum int preproc_lexer_parse(const struct vkd3d_shader_compile_info *compile_info, struct vkd3d_shader_code *out, struct vkd3d_shader_message_context *message_context); -int hlsl_compile_shader(const struct vkd3d_shader_code *hlsl, const struct vkd3d_shader_compile_info *compile_info, - struct vkd3d_shader_code *out, struct vkd3d_shader_message_context *message_context); +int hlsl_compile_shader(const struct vkd3d_shader_compile_info *compile_info, + struct vkd3d_shader_message_context *message_context, struct vkd3d_shader_code *out); static inline enum vkd3d_shader_component_type vkd3d_component_type_from_data_type( enum vsir_data_type data_type) { switch (data_type) { + case VSIR_DATA_BOOL: + return VKD3D_SHADER_COMPONENT_BOOL; case VSIR_DATA_F16: /* Minimum precision. TODO: native 16-bit */ case VSIR_DATA_F32: - case VKD3D_DATA_UNORM: - case VKD3D_DATA_SNORM: + case VSIR_DATA_SNORM: + case VSIR_DATA_UNORM: return VKD3D_SHADER_COMPONENT_FLOAT; case VSIR_DATA_F64: return VKD3D_SHADER_COMPONENT_DOUBLE; @@ -1818,12 +1822,10 @@ static inline enum vkd3d_shader_component_type vkd3d_component_type_from_data_ty return VKD3D_SHADER_COMPONENT_UINT; case VSIR_DATA_U64: return VKD3D_SHADER_COMPONENT_UINT64; - case VKD3D_DATA_BOOL: - return VKD3D_SHADER_COMPONENT_BOOL; default: FIXME("Unhandled data type %#x.\n", data_type); /* fall-through */ - case VKD3D_DATA_MIXED: + case VSIR_DATA_MIXED: return VKD3D_SHADER_COMPONENT_UINT; } } -- 2.50.1