From: Henri Verbeet Subject: [PATCH vkd3d] vkd3d-shader: Keep track of declared SPIR-V output components. Message-Id: <20210226141453.6889-1-hverbeet@codeweavers.com> Date: Fri, 26 Feb 2021 15:14:53 +0100 Much like we do for input components, for much of the same reasons. Signed-off-by: Henri Verbeet --- libs/vkd3d-shader/spirv.c | 93 +++++++++++++++++++---------------------------- 1 file changed, 37 insertions(+), 56 deletions(-) diff --git a/libs/vkd3d-shader/spirv.c b/libs/vkd3d-shader/spirv.c index 1448d3b4..a7361aa5 100644 --- a/libs/vkd3d-shader/spirv.c +++ b/libs/vkd3d-shader/spirv.c @@ -4657,6 +4657,7 @@ static void vkd3d_dxbc_compiler_emit_output(struct vkd3d_dxbc_compiler *compiler enum vkd3d_shader_component_type component_type; const struct vkd3d_spirv_builtin *builtin; const struct vkd3d_shader_phase *phase; + struct vkd3d_symbol *symbol = NULL; struct vkd3d_symbol reg_symbol; SpvStorageClass storage_class; struct rb_entry *entry = NULL; @@ -4692,6 +4693,7 @@ static void vkd3d_dxbc_compiler_emit_output(struct vkd3d_dxbc_compiler *compiler component_type = builtin->component_type; if (!builtin->spirv_array_size) output_component_count = builtin->component_count; + component_idx = 0; } else { @@ -4717,23 +4719,24 @@ static void vkd3d_dxbc_compiler_emit_output(struct vkd3d_dxbc_compiler *compiler vkd3d_symbol_make_register(®_symbol, reg); - if (compiler->output_info[signature_idx].id) - { - id = compiler->output_info[signature_idx].id; - if (compiler->output_info[signature_idx].array_element_mask) - { - use_private_variable = true; - write_mask = VKD3DSP_WRITEMASK_ALL; - entry = rb_get(&compiler->symbol_table, ®_symbol); - } - } - else if (!use_private_variable && (entry = rb_get(&compiler->symbol_table, ®_symbol))) + if ((entry = rb_get(&compiler->symbol_table, ®_symbol))) { - id = RB_ENTRY_VALUE(entry, const struct vkd3d_symbol, entry)->id; + symbol = RB_ENTRY_VALUE(entry, struct vkd3d_symbol, entry); + id = symbol->id; } - else + + if (!symbol || ~symbol->info.reg.dcl_mask & signature_element->mask) { - if (builtin) + if (compiler->output_info[signature_idx].id) + { + id = compiler->output_info[signature_idx].id; + if (compiler->output_info[signature_idx].array_element_mask) + { + use_private_variable = true; + write_mask = VKD3DSP_WRITEMASK_ALL; + } + } + else if (builtin) { if (phase) id = vkd3d_dxbc_compiler_emit_shader_phase_builtin_variable(compiler, phase, builtin); @@ -4745,9 +4748,6 @@ static void vkd3d_dxbc_compiler_emit_output(struct vkd3d_dxbc_compiler *compiler calculate_sysval_array_mask(compiler, shader_signature, sysval); vkd3d_dxbc_compiler_emit_register_execution_mode(compiler, &dst->reg); - - if (component_idx) - FIXME("Unhandled component index %u.\n", component_idx); } else { @@ -4778,25 +4778,22 @@ static void vkd3d_dxbc_compiler_emit_output(struct vkd3d_dxbc_compiler *compiler vkd3d_spirv_build_op_decorate(builder, id, SpvDecorationPatch, NULL, 0); vkd3d_dxbc_compiler_decorate_xfb_output(compiler, id, output_component_count, signature_element); - } - - compiler->output_info[signature_idx].id = id; - compiler->output_info[signature_idx].component_type = component_type; - if (use_private_variable) - storage_class = SpvStorageClassPrivate; + compiler->output_info[signature_idx].id = id; + compiler->output_info[signature_idx].component_type = component_type; + } - if (entry) - var_id = RB_ENTRY_VALUE(entry, const struct vkd3d_symbol, entry)->id; - else if (!use_private_variable) - var_id = id; - else if (is_patch_constant) - var_id = compiler->hs.patch_constants_id; - else - var_id = vkd3d_dxbc_compiler_emit_variable(compiler, &builder->global_stream, - storage_class, VKD3D_SHADER_COMPONENT_FLOAT, VKD3D_VEC4_SIZE); - if (!entry) + if (!symbol) { + var_id = id; + if (use_private_variable) + storage_class = SpvStorageClassPrivate; + if (is_patch_constant) + var_id = compiler->hs.patch_constants_id; + else if (use_private_variable) + var_id = vkd3d_dxbc_compiler_emit_variable(compiler, &builder->global_stream, + storage_class, VKD3D_SHADER_COMPONENT_FLOAT, VKD3D_VEC4_SIZE); + vkd3d_symbol_set_register_info(®_symbol, var_id, storage_class, use_private_variable ? VKD3D_SHADER_COMPONENT_FLOAT : component_type, write_mask); reg_symbol.info.reg.is_aggregate = use_private_variable ? is_patch_constant : array_size; @@ -4816,6 +4813,11 @@ static void vkd3d_dxbc_compiler_emit_output(struct vkd3d_dxbc_compiler *compiler if (!is_patch_constant) vkd3d_dxbc_compiler_emit_register_debug_name(builder, var_id, reg); } + else + { + symbol->info.reg.dcl_mask |= signature_element->mask; + var_id = symbol->id; + } if (use_private_variable) { @@ -6100,33 +6102,12 @@ static void vkd3d_dxbc_compiler_leave_shader_phase(struct vkd3d_dxbc_compiler *c } } - if (phase->type == VKD3DSIH_HS_FORK_PHASE || phase->type == VKD3DSIH_HS_JOIN_PHASE) - { - signature = compiler->patch_constant_signature; - - memset(®, 0, sizeof(reg)); - reg.idx[1].offset = ~0u; - - for (i = 0; i < signature->element_count; ++i) - { - const struct vkd3d_shader_signature_element *e = &signature->elements[i]; - - reg.type = VKD3DSPR_OUTPUT; - reg.idx[0].offset = e->register_index; - vkd3d_symbol_make_register(®_symbol, ®); - - if ((entry = rb_get(&compiler->symbol_table, ®_symbol))) - { - rb_remove(&compiler->symbol_table, entry); - vkd3d_symbol_free(entry, NULL); - } - } - } - if (phase->instance_count) { + memset(®, 0, sizeof(reg)); reg.type = phase->type == VKD3DSIH_HS_FORK_PHASE ? VKD3DSPR_FORKINSTID : VKD3DSPR_JOININSTID; reg.idx[0].offset = ~0u; + reg.idx[1].offset = ~0u; vkd3d_symbol_make_register(®_symbol, ®); if ((entry = rb_get(&compiler->symbol_table, ®_symbol))) { -- 2.11.0