nir,treewide: add nir_image_intrinsic_type

We have 4 image intrinsic variants now. This enum is useful for
nir_rewrite_image_intrinsic() and it will be used by other NIR passes.

Signed-off-by: Samuel Pitoiset <samuel.pitoiset@gmail.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/40709>
This commit is contained in:
Samuel Pitoiset 2026-03-30 15:34:20 +02:00 committed by Marge Bot
parent cb469cc945
commit c4e3380187
22 changed files with 64 additions and 55 deletions

View file

@ -335,7 +335,7 @@ update_image_intrinsic(nir_builder *b, apply_layout_state *state, nir_intrinsic_
if (intrin->intrinsic == nir_intrinsic_image_deref_descriptor_amd) {
nir_def_replace(&intrin->def, desc);
} else {
nir_rewrite_image_intrinsic(intrin, desc, true);
nir_rewrite_image_intrinsic(intrin, desc, nir_image_intrinsic_type_bindless);
}
}

View file

@ -400,7 +400,7 @@ lower_preamble(nir_builder *b, nir_intrinsic_instr *intr, void *data)
if (ts) {
nir_rewrite_image_intrinsic(pintr, nir_imm_intN_t(b, base / 2, 16),
false);
nir_image_intrinsic_type_default);
} else if (new_ != NULL &&
pintr->intrinsic != nir_intrinsic_bindless_image_agx) {
nir_src_rewrite(use, new_);

View file

@ -347,8 +347,9 @@ lower_image_intrin(nir_builder *b, nir_intrinsic_instr *intr,
offs = offsetof(struct hk_storage_image_descriptor, tex);
}
nir_rewrite_image_intrinsic(
intr, load_image_handle(b, ctx, intr->src[0], offs), true);
nir_rewrite_image_intrinsic(intr,
load_image_handle(b, ctx, intr->src[0], offs),
nir_image_intrinsic_type_bindless);
return true;
}

View file

@ -831,7 +831,7 @@ lower_image_deref(nir_builder *b,
index = nir_imm_int(b, desc_index);
nir_rewrite_image_intrinsic(instr, index, false);
nir_rewrite_image_intrinsic(instr, index, nir_image_intrinsic_type_default);
}
static bool

View file

@ -98,7 +98,8 @@ lower_instr(nir_builder *b, nir_instr *instr, void *cb_data)
nir_build_deref_offset(b, deref, type_size_align_1),
var->data.driver_location);
}
nir_rewrite_image_intrinsic(intrinsic, src, bindless);
nir_rewrite_image_intrinsic(intrinsic, src,
bindless ? nir_image_intrinsic_type_bindless : nir_image_intrinsic_type_default);
if (!bindless)
nir_intrinsic_set_range_base(intrinsic, range_base);

View file

@ -2773,7 +2773,7 @@ nir_system_value_from_intrinsic(nir_intrinsic_op intrin)
void
nir_rewrite_image_intrinsic(nir_intrinsic_instr *intrin, nir_def *src,
bool bindless)
nir_image_intrinsic_type type)
{
enum gl_access_qualifier access = nir_intrinsic_access(intrin);
@ -2796,12 +2796,23 @@ nir_rewrite_image_intrinsic(nir_intrinsic_instr *intrin, nir_def *src,
explicit_coord = nir_intrinsic_explicit_coord(intrin);
switch (intrin->intrinsic) {
#define CASE(op) \
case nir_intrinsic_image_deref_##op: \
case nir_intrinsic_image_##op: \
case nir_intrinsic_bindless_image_##op: \
intrin->intrinsic = bindless ? nir_intrinsic_bindless_image_##op \
: nir_intrinsic_image_##op; \
#define CASE(op) \
case nir_intrinsic_image_deref_##op: \
case nir_intrinsic_image_##op: \
case nir_intrinsic_bindless_image_##op: \
switch (type) { \
case nir_image_intrinsic_type_default: \
intrin->intrinsic = nir_intrinsic_image_##op; \
break; \
case nir_image_intrinsic_type_bindless: \
intrin->intrinsic = nir_intrinsic_bindless_image_##op; \
break; \
case nir_image_intrinsic_type_heap: \
intrin->intrinsic = nir_intrinsic_image_heap_##op; \
break; \
default: \
UNREACHABLE("Invalid nir_image_intrinsic."); \
} \
break;
CASE(load)
CASE(sparse_load)

View file

@ -205,6 +205,16 @@ typedef enum {
nir_descriptor_type_acceleration_structure = 2,
} nir_descriptor_type;
/**
* NIR image intrinsics variants.
*/
typedef enum {
nir_image_intrinsic_type_default = 0,
nir_image_intrinsic_type_deref = 1,
nir_image_intrinsic_type_bindless = 2,
nir_image_intrinsic_type_heap = 3,
} nir_image_intrinsic_type;
/**
* Rounding modes.
*/
@ -2212,9 +2222,9 @@ nir_intrinsic_has_align(const nir_intrinsic_instr *intrin)
unsigned
nir_image_intrinsic_coord_components(const nir_intrinsic_instr *instr);
/* Converts a image_deref_* intrinsic into a image_* one */
/* Converts an image intrinsic into a different type. */
void nir_rewrite_image_intrinsic(nir_intrinsic_instr *instr,
nir_def *handle, bool bindless);
nir_def *handle, nir_image_intrinsic_type type);
/* Determine if an intrinsic can be arbitrarily reordered and eliminated. */
bool nir_intrinsic_can_reorder(nir_intrinsic_instr *instr);

View file

@ -271,7 +271,7 @@ nir_lower_cl_images(nir_shader *shader, bool lower_image_derefs, bool lower_samp
b.cursor = nir_before_instr(&intrin->instr);
/* Back-ends expect a 32-bit thing, not 64-bit */
nir_def *offset = nir_u2u32(&b, intrin->src[0].ssa);
nir_rewrite_image_intrinsic(intrin, offset, false);
nir_rewrite_image_intrinsic(intrin, offset, nir_image_intrinsic_type_default);
progress = true;
break;
}

View file

@ -605,7 +605,8 @@ lower_image_deref(struct tu_device *dev, nir_builder *b,
{
nir_deref_instr *deref = nir_src_as_deref(instr->src[0]);
nir_def *bindless = build_bindless(dev, b, deref, 0, shader, layout, 0, false);
nir_rewrite_image_intrinsic(instr, bindless, true);
nir_rewrite_image_intrinsic(instr, bindless,
nir_image_intrinsic_type_bindless);
}
static bool

View file

@ -101,7 +101,7 @@ lower(nir_builder *b, nir_instr *instr, void *data)
index = nir_iadd_imm(b, nir_imul_imm(b, index, 2), offset);
nir_rewrite_image_intrinsic(intr, nir_load_texture_handle_agx(b, index),
true);
nir_image_intrinsic_type_bindless);
} else if (instr->type == nir_instr_type_tex) {
nir_tex_instr *tex = nir_instr_as_tex(instr);

View file

@ -298,7 +298,7 @@ crocus_lower_storage_image_derefs_instr(nir_builder *b,
nir_def *index =
nir_iadd_imm(b, get_aoa_deref_offset(b, deref, 1),
var->data.driver_location);
nir_rewrite_image_intrinsic(intrin, index, false);
nir_rewrite_image_intrinsic(intrin, index, nir_image_intrinsic_type_default);
return true;
}

View file

@ -757,7 +757,7 @@ iris_lower_storage_image_derefs_instr(nir_builder *b,
nir_def *index =
nir_iadd_imm(b, get_aoa_deref_offset(b, deref, 1),
var->data.driver_location);
nir_rewrite_image_intrinsic(intrin, index, false);
nir_rewrite_image_intrinsic(intrin, index, nir_image_intrinsic_type_default);
return true;
}

View file

@ -348,7 +348,7 @@ static bool lower_resource_intrinsic(nir_builder *b, nir_intrinsic_instr *intrin
} else {
nir_intrinsic_set_image_dim(intrin, glsl_get_sampler_dim(deref->type));
nir_intrinsic_set_image_array(intrin, glsl_sampler_type_is_array(deref->type));
nir_rewrite_image_intrinsic(intrin, desc, true);
nir_rewrite_image_intrinsic(intrin, desc, nir_image_intrinsic_type_bindless);
}
break;
}

View file

@ -148,7 +148,7 @@ lower_image_intrinsic(nir_builder *b,
nir_deref_instr *deref = nir_src_as_deref(intrin->src[0]);
nir_def *resource = vulkan_resource_from_deref(b, deref, layout, 0);
nir_rewrite_image_intrinsic(intrin, resource, true);
nir_rewrite_image_intrinsic(intrin, resource, nir_image_intrinsic_type_bindless);
}
static bool

View file

@ -1857,7 +1857,9 @@ lower_image_intrinsic(nir_builder *b, nir_intrinsic_instr *intrin,
nir_def *handle =
build_load_var_deref_surface_handle(b, deref, non_uniform,
&is_bindless, state);
nir_rewrite_image_intrinsic(intrin, handle, is_bindless);
nir_rewrite_image_intrinsic(intrin, handle,
is_bindless ? nir_image_intrinsic_type_bindless
: nir_image_intrinsic_type_default);
return true;
}
@ -1878,7 +1880,9 @@ lower_image_size_intrinsic(nir_builder *b, nir_intrinsic_instr *intrin,
nir_def *handle =
build_load_var_deref_surface_handle(b, deref, non_uniform,
&is_bindless, state);
nir_rewrite_image_intrinsic(intrin, handle, is_bindless);
nir_rewrite_image_intrinsic(intrin, handle,
is_bindless ? nir_image_intrinsic_type_bindless
: nir_image_intrinsic_type_default);
nir_variable *var = nir_deref_instr_get_variable(deref);
const uint32_t set = var->data.descriptor_set;

View file

@ -890,7 +890,7 @@ lower_image_intrinsic(nir_builder *b, nir_intrinsic_instr *intrin,
}
index = nir_iadd_imm(b, index, binding_offset);
nir_rewrite_image_intrinsic(intrin, index, false);
nir_rewrite_image_intrinsic(intrin, index, nir_image_intrinsic_type_default);
}
return true;

View file

@ -382,7 +382,7 @@ lower_image_intrin(nir_builder *b, nir_intrinsic_instr *intr,
.access = nir_intrinsic_access(intr) | var->data.access,
.flags = msl_convert_access_flag(var->data.access));
nir_rewrite_image_intrinsic(intr, handle, true);
nir_rewrite_image_intrinsic(intr, handle, nir_image_intrinsic_type_bindless);
return true;
}

View file

@ -182,7 +182,8 @@ clc_lower_input_image_deref(nir_builder *b, struct clc_image_lower_context *cont
}
assert((in_var->data.access & ACCESS_NON_WRITEABLE) == 0);
nir_rewrite_image_intrinsic(intrinsic, nir_imm_int(b, image_binding), false);
nir_rewrite_image_intrinsic(intrinsic, nir_imm_int(b, image_binding),
nir_image_intrinsic_type_default);
break;
}
@ -205,7 +206,8 @@ clc_lower_input_image_deref(nir_builder *b, struct clc_image_lower_context *cont
}
assert((in_var->data.access & ACCESS_NON_WRITEABLE) == 0);
nir_rewrite_image_intrinsic(intrinsic, nir_imm_int(b, image_binding), false);
nir_rewrite_image_intrinsic(intrinsic, nir_imm_int(b, image_binding),
nir_image_intrinsic_type_default);
break;
}

View file

@ -152,7 +152,7 @@ lower_bindless_image_intr(nir_builder *b, nir_intrinsic_instr *intr, struct dxil
if (!handle)
return false;
nir_rewrite_image_intrinsic(intr, handle, true);
nir_rewrite_image_intrinsic(intr, handle, nir_image_intrinsic_type_bindless);
return true;
}

View file

@ -998,7 +998,7 @@ lower_edb_buffer_image_intrin(nir_builder *b, nir_intrinsic_instr *intrin,
nir_def_rewrite_uses_after(&intrin->def, res);
}
nir_rewrite_image_intrinsic(intrin, index, true);
nir_rewrite_image_intrinsic(intrin, index, nir_image_intrinsic_type_bindless);
break;
}
@ -1027,7 +1027,7 @@ lower_image_intrin(nir_builder *b, nir_intrinsic_instr *intrin,
b->cursor = nir_before_instr(&intrin->instr);
nir_def *desc = load_resource_deref_desc(b, 1, 32, deref, 0, ctx);
nir_rewrite_image_intrinsic(intrin, desc, true);
nir_rewrite_image_intrinsic(intrin, desc, nir_image_intrinsic_type_bindless);
/* On pre-Volta hardware, we don't have real null descriptors. Null
* descriptors work well enough for sampling but they may not return the

View file

@ -918,7 +918,8 @@ lower_img_intrinsic(nir_builder *b, nir_intrinsic_instr *intr,
nir_def_replace(&intr->def, res);
} else {
nir_rewrite_image_intrinsic(intr, get_img_index(b, deref, ctx), false);
nir_rewrite_image_intrinsic(intr, get_img_index(b, deref, ctx),
nir_image_intrinsic_type_default);
}
return true;

View file

@ -745,29 +745,7 @@ lower_heaps_image(nir_builder *b, nir_intrinsic_instr *intrin,
if (heap_offset == NULL)
return false;
nir_rewrite_image_intrinsic(intrin, heap_offset, false);
/* TODO: Roll this into nir_rewrite_image_intrinsic? */
switch (intrin->intrinsic) {
#define CASE(op) \
case nir_intrinsic_image_##op: \
intrin->intrinsic = nir_intrinsic_image_heap_##op; \
break;
CASE(load)
CASE(sparse_load)
CASE(store)
CASE(atomic)
CASE(atomic_swap)
CASE(size)
CASE(samples)
CASE(load_raw_intel)
CASE(store_raw_intel)
CASE(fragment_mask_load_amd)
CASE(store_block_agx)
#undef CASE
default:
UNREACHABLE("Unhanded image intrinsic");
}
nir_rewrite_image_intrinsic(intrin, heap_offset, nir_image_intrinsic_type_heap);
return true;
}