On Sat Mar 16 04:34:38 2024 +0000, Zebediah Figura wrote:
Wait, how does vPos get into the symbol table in the first place? That doesn't seem right.
vPos doesn't get into `context->symbol_table`.
We enter the ```c if (!(entry = rb_get(&compiler->symbol_table, ®_symbol))) { FIXME("Unrecognized register (%s).\n", debug_vkd3d_symbol(®_symbol)); memset(register_info, 0, sizeof(*register_info)); return false; } ``` path.
But because this is a FIXME and not a compiler error, compilation continues using a zeroed `register_info` which, I think, results in a misscompilation.
---
In the fwidth.shader_test case in particular, we have a ``` mov r0, vPos ``` and when `spirv_compiler_emit_mov()` is called, we go through this path: ```c if (vkd3d_swizzle_is_equal(dst_reg_info.write_mask, src->swizzle, src_reg_info.write_mask)) { dst_id = spirv_compiler_get_register_id(compiler, &dst->reg); src_id = spirv_compiler_get_register_id(compiler, &src->reg);
vkd3d_spirv_build_op_copy_memory(builder, dst_id, src_id, SpvMemoryAccessMaskNone); return; } ```
and `spirv_compiler_get_register_id()` just ends up emitting a `SpvStorageClassPrivate` variable for the `src` register, instead of using the register in the input signature.
---
So patch 7/7 makes it throw a compiler error to avoid the misscompilation.
I guess a proper solution would be to map the registers whose type is `VKD3DSPR_MISCTYPE` to the right symbol in the input|output signature. In this case "VPOS", which gets assigned to type `VKD3DSPR_INPUT` and index 0. But I felt that that is out of the scope of this MR and maybe something for someone with more experience in spirv.c to handle.
(please tell me if I am missing something in my analysis!).