mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2025-12-21 22:20:14 +01:00
nir/glsl: set deref cast mode during function inlining
See code comment for details.
Issue: https://gitlab.freedesktop.org/mesa/mesa/-/issues/11535
Fixes: c6c150b4cd ("glsl_to_nir: support conversion of opaque function params")
Reviewed-by: Marek Olšák <marek.olsak@amd.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/30338>
This commit is contained in:
parent
aad503ecfa
commit
d681cf96fb
2 changed files with 36 additions and 6 deletions
|
|
@ -2528,13 +2528,8 @@ nir_visitor::visit(ir_dereference_variable *ir)
|
||||||
i++;
|
i++;
|
||||||
}
|
}
|
||||||
|
|
||||||
nir_variable_mode mode =
|
|
||||||
glsl_contains_opaque(ir->variable_referenced()->type) &&
|
|
||||||
ir->variable_referenced()->data.mode == ir_var_function_in ?
|
|
||||||
nir_var_uniform : nir_var_function_temp;
|
|
||||||
|
|
||||||
this->deref = nir_build_deref_cast(&b, nir_load_param(&b, i),
|
this->deref = nir_build_deref_cast(&b, nir_load_param(&b, i),
|
||||||
mode, ir->type, 0);
|
nir_var_function_temp, ir->type, 0);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -53,6 +53,30 @@ function_ends_in_jump(nir_function_impl *impl)
|
||||||
return nir_block_ends_in_jump(last_block);
|
return nir_block_ends_in_jump(last_block);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* A cast is used to deref function in/out params. However the bindless
|
||||||
|
* textures spec allows both uniforms and functions temps to be passed to a
|
||||||
|
* function param defined the same way. To deal with this we need to update
|
||||||
|
* this when we inline and know what variable mode we are dealing with.
|
||||||
|
*/
|
||||||
|
static void
|
||||||
|
fixup_cast_deref_mode(nir_deref_instr *deref)
|
||||||
|
{
|
||||||
|
nir_deref_instr *parent = nir_src_as_deref(deref->parent);
|
||||||
|
if (parent && parent->modes & nir_var_uniform &&
|
||||||
|
deref->modes & nir_var_function_temp) {
|
||||||
|
deref->modes |= nir_var_uniform;
|
||||||
|
deref->modes ^= nir_var_function_temp;
|
||||||
|
|
||||||
|
nir_foreach_use(use, &deref->def) {
|
||||||
|
if (nir_src_parent_instr(use)->type != nir_instr_type_deref)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
/* Recurse into children */
|
||||||
|
fixup_cast_deref_mode(nir_instr_as_deref(nir_src_parent_instr(use)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
nir_inline_function_impl(struct nir_builder *b,
|
nir_inline_function_impl(struct nir_builder *b,
|
||||||
const nir_function_impl *impl,
|
const nir_function_impl *impl,
|
||||||
|
|
@ -68,6 +92,17 @@ nir_inline_function_impl(struct nir_builder *b,
|
||||||
switch (instr->type) {
|
switch (instr->type) {
|
||||||
case nir_instr_type_deref: {
|
case nir_instr_type_deref: {
|
||||||
nir_deref_instr *deref = nir_instr_as_deref(instr);
|
nir_deref_instr *deref = nir_instr_as_deref(instr);
|
||||||
|
|
||||||
|
/* Note: This shouldn't change the mode of anything but the
|
||||||
|
* replaced nir_intrinsic_load_param intrinsics handled later in
|
||||||
|
* this switch table. Any incorrect modes should have already been
|
||||||
|
* detected by previous nir_vaidate calls.
|
||||||
|
*/
|
||||||
|
if (deref->deref_type == nir_deref_type_cast) {
|
||||||
|
fixup_cast_deref_mode(deref);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
if (deref->deref_type != nir_deref_type_var)
|
if (deref->deref_type != nir_deref_type_var)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue