mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-05 07:28:11 +02:00
i965: add support for image AoA
V3: clamp array index to the correct size (the size of the current array rather than the inner array) Francisco Jerez. V2: avoid useless zero-initialization and addition for the first AoA level, avoid redundant temporary, make use of type_size_scalar(), rename aoa_size to element_size, assign the indirect indexing temporary directly to image.reladdr, and replace while loop with a for loop. All suggested by Francisco Jerez. Reviewed-by: Francisco Jerez <currojerez@riseup.net>
This commit is contained in:
parent
9285ed98f7
commit
fb77da89f5
2 changed files with 18 additions and 14 deletions
|
|
@ -1062,18 +1062,17 @@ fs_visitor::get_nir_image_deref(const nir_deref_var *deref)
|
|||
fs_reg image(UNIFORM, deref->var->data.driver_location,
|
||||
BRW_REGISTER_TYPE_UD);
|
||||
|
||||
if (deref->deref.child) {
|
||||
const nir_deref_array *deref_array =
|
||||
nir_deref_as_array(deref->deref.child);
|
||||
assert(deref->deref.child->deref_type == nir_deref_type_array &&
|
||||
deref_array->deref.child == NULL);
|
||||
const unsigned size = glsl_get_length(deref->var->type);
|
||||
for (const nir_deref *tail = &deref->deref; tail->child;
|
||||
tail = tail->child) {
|
||||
const nir_deref_array *deref_array = nir_deref_as_array(tail->child);
|
||||
assert(tail->child->deref_type == nir_deref_type_array);
|
||||
const unsigned size = glsl_get_length(tail->type);
|
||||
const unsigned element_size = type_size_scalar(deref_array->deref.type);
|
||||
const unsigned base = MIN2(deref_array->base_offset, size - 1);
|
||||
|
||||
image = offset(image, bld, base * BRW_IMAGE_PARAM_SIZE);
|
||||
image = offset(image, bld, base * element_size);
|
||||
|
||||
if (deref_array->deref_array_type == nir_deref_array_type_indirect) {
|
||||
fs_reg *tmp = new(mem_ctx) fs_reg(vgrf(glsl_type::int_type));
|
||||
fs_reg tmp = vgrf(glsl_type::int_type);
|
||||
|
||||
if (devinfo->gen == 7 && !devinfo->is_haswell) {
|
||||
/* IVB hangs when trying to access an invalid surface index with
|
||||
|
|
@ -1084,15 +1083,18 @@ fs_visitor::get_nir_image_deref(const nir_deref_var *deref)
|
|||
* of the possible outcomes of the hang. Clamp the index to
|
||||
* prevent access outside of the array bounds.
|
||||
*/
|
||||
bld.emit_minmax(*tmp, retype(get_nir_src(deref_array->indirect),
|
||||
BRW_REGISTER_TYPE_UD),
|
||||
bld.emit_minmax(tmp, retype(get_nir_src(deref_array->indirect),
|
||||
BRW_REGISTER_TYPE_UD),
|
||||
fs_reg(size - base - 1), BRW_CONDITIONAL_L);
|
||||
} else {
|
||||
bld.MOV(*tmp, get_nir_src(deref_array->indirect));
|
||||
bld.MOV(tmp, get_nir_src(deref_array->indirect));
|
||||
}
|
||||
|
||||
bld.MUL(*tmp, *tmp, fs_reg(BRW_IMAGE_PARAM_SIZE));
|
||||
image.reladdr = tmp;
|
||||
bld.MUL(tmp, tmp, fs_reg(element_size));
|
||||
if (image.reladdr)
|
||||
bld.ADD(*image.reladdr, *image.reladdr, tmp);
|
||||
else
|
||||
image.reladdr = new(mem_ctx) fs_reg(tmp);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -98,6 +98,8 @@ brw_nir_setup_glsl_uniform(gl_shader_stage stage, nir_variable *var,
|
|||
if (storage->type->is_image()) {
|
||||
brw_setup_image_uniform_values(stage, stage_prog_data,
|
||||
uniform_index, storage);
|
||||
uniform_index +=
|
||||
BRW_IMAGE_PARAM_SIZE * MAX2(storage->array_elements, 1);
|
||||
} else {
|
||||
gl_constant_value *components = storage->storage;
|
||||
unsigned vector_count = (MAX2(storage->array_elements, 1) *
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue