Module: Mesa Branch: main Commit: b2fcb34e9767177e887dc309babe6fd0176fc91c URL: http://cgit.freedesktop.org/mesa/mesa/commit/?id=b2fcb34e9767177e887dc309babe6fd0176fc91c
Author: Mike Blumenkrantz <[email protected]> Date: Mon Oct 17 11:00:37 2022 -0400 zink: rework sampler emission this simplifies all the different sampler metadata tracking fields to be more comprehensible it also increases some array sizes in case future work increases them outside the compiler areas Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/19327> --- .../drivers/zink/nir_to_spirv/nir_to_spirv.c | 65 ++++++++++++---------- 1 file changed, 37 insertions(+), 28 deletions(-) diff --git a/src/gallium/drivers/zink/nir_to_spirv/nir_to_spirv.c b/src/gallium/drivers/zink/nir_to_spirv/nir_to_spirv.c index d640ed72526..67c7214f99f 100644 --- a/src/gallium/drivers/zink/nir_to_spirv/nir_to_spirv.c +++ b/src/gallium/drivers/zink/nir_to_spirv/nir_to_spirv.c @@ -59,13 +59,15 @@ struct ntv_context { SpvId ssbos[5]; //8, 16, 32, unused, 64 nir_variable *ssbo_vars; - SpvId image_types[PIPE_MAX_SAMPLERS]; - SpvId images[PIPE_MAX_SAMPLERS]; - SpvId sampler_types[PIPE_MAX_SAMPLERS]; - SpvId samplers[PIPE_MAX_SAMPLERS]; - unsigned char sampler_array_sizes[PIPE_MAX_SAMPLERS]; - unsigned samplers_used : PIPE_MAX_SAMPLERS; - unsigned samplers_used_mediump : PIPE_MAX_SAMPLERS; + + SpvId image_types[PIPE_MAX_SHADER_IMAGES]; + SpvId images[PIPE_MAX_SHADER_IMAGES]; + SpvId sampler_types[PIPE_MAX_SHADER_SAMPLER_VIEWS]; + SpvId samplers[PIPE_MAX_SHADER_SAMPLER_VIEWS]; + nir_variable *sampler_var[PIPE_MAX_SHADER_SAMPLER_VIEWS]; /* driver_location -> variable */ + unsigned last_sampler; + nir_variable *image_var[PIPE_MAX_SHADER_IMAGES]; /* driver_location -> variable */ + SpvId entry_ifaces[PIPE_MAX_SHADER_INPUTS * 4 + PIPE_MAX_SHADER_OUTPUTS * 4]; size_t num_entry_ifaces; @@ -1006,7 +1008,6 @@ emit_image(struct ntv_context *ctx, struct nir_variable *var, bool bindless) bool mediump = (var->data.precision == GLSL_PRECISION_MEDIUM || var->data.precision == GLSL_PRECISION_LOW); int index = var->data.driver_location; - assert(!is_sampler || (!(ctx->samplers_used & (1 << index)))); assert(!is_sampler || !ctx->sampler_types[index]); assert(is_sampler || !ctx->image_types[index]); @@ -1014,7 +1015,6 @@ emit_image(struct ntv_context *ctx, struct nir_variable *var, bool bindless) var_type = spirv_builder_type_array(&ctx->builder, var_type, emit_uint_const(ctx, 32, glsl_get_aoa_size(var->type))); spirv_builder_emit_array_stride(&ctx->builder, var_type, sizeof(void*)); - ctx->sampler_array_sizes[index] = glsl_get_aoa_size(var->type); } SpvId pointer_type = spirv_builder_type_pointer(&ctx->builder, SpvStorageClassUniformConstant, @@ -1041,9 +1041,6 @@ emit_image(struct ntv_context *ctx, struct nir_variable *var, bool bindless) if (is_sampler) { ctx->sampler_types[index] = image_type; ctx->samplers[index] = var_id; - ctx->samplers_used |= 1 << index; - if (mediump) - ctx->samplers_used_mediump |= 1 << index; } else { ctx->image_types[index] = image_type; ctx->images[index] = var_id; @@ -3694,32 +3691,36 @@ emit_tex(struct ntv_context *ctx, nir_tex_instr *tex) } unsigned texture_index = tex->texture_index; - if (!tex_offset) { - /* convert constant index back to base + offset */ - unsigned last_sampler = util_last_bit(ctx->samplers_used); - for (unsigned i = 0; i < last_sampler; i++) { - if (!ctx->sampler_array_sizes[i]) { - if (i == texture_index) - /* this is a non-array sampler, so we don't need an access chain */ + nir_variable *var = bindless_var ? bindless_var : ctx->sampler_var[tex->texture_index]; + if (!tex_offset || !var) { + if (ctx->sampler_var[texture_index]) { + if (glsl_type_is_array(ctx->sampler_var[texture_index]->type)) + tex_offset = emit_uint_const(ctx, 32, 0); + assert(var); + } else { + /* convert constant index back to base + offset */ + for (int i = texture_index; i >= 0; i--) { + if (ctx->sampler_var[i]) { + assert(glsl_type_is_array(ctx->sampler_var[i]->type)); + if (!tex_offset) + tex_offset = emit_uint_const(ctx, 32, texture_index - i); + var = ctx->sampler_var[i]; + texture_index = i; break; - } else if (texture_index <= i + ctx->sampler_array_sizes[i] - 1) { - /* this is the first member of a sampler array */ - tex_offset = emit_uint_const(ctx, 32, texture_index - i); - texture_index = i; - break; + } } } } + assert(var); SpvId image_type = bindless ? get_bare_image_type(ctx, bindless_var, true) : ctx->sampler_types[texture_index]; assert(image_type); SpvId sampled_type = spirv_builder_type_sampled_image(&ctx->builder, image_type); assert(sampled_type); - assert(bindless || ctx->samplers_used & (1u << texture_index)); SpvId sampler_id = bindless ? bindless : ctx->samplers[texture_index]; if (tex_offset) { - SpvId ptr = spirv_builder_type_pointer(&ctx->builder, SpvStorageClassUniformConstant, sampled_type); - sampler_id = spirv_builder_emit_access_chain(&ctx->builder, ptr, sampler_id, &tex_offset, 1); + SpvId ptr = spirv_builder_type_pointer(&ctx->builder, SpvStorageClassUniformConstant, sampled_type); + sampler_id = spirv_builder_emit_access_chain(&ctx->builder, ptr, sampler_id, &tex_offset, 1); } SpvId load = spirv_builder_emit_load(&ctx->builder, sampled_type, sampler_id); @@ -3852,7 +3853,7 @@ emit_tex(struct ntv_context *ctx, nir_tex_instr *tex) const_offset, offset, min_lod, tex->is_sparse); } - if (!bindless_var && (ctx->samplers_used_mediump & (1 << tex->texture_index))) { + if (!bindless_var && (var->data.precision == GLSL_PRECISION_MEDIUM || var->data.precision == GLSL_PRECISION_LOW)) { spirv_builder_emit_decoration(&ctx->builder, result, SpvDecorationRelaxedPrecision); } @@ -4529,6 +4530,14 @@ nir_to_spirv(struct nir_shader *s, const struct zink_shader_info *sinfo, uint32_ nir_foreach_variable_with_modes(var, s, nir_var_mem_ssbo) emit_bo(&ctx, var, ssbo_counter > 1); + nir_foreach_variable_with_modes(var, s, nir_var_image) + ctx.image_var[var->data.driver_location] = var; + nir_foreach_variable_with_modes(var, s, nir_var_uniform) { + if (glsl_type_is_sampler(glsl_without_array(var->type))) { + ctx.sampler_var[var->data.driver_location] = var; + ctx.last_sampler = MAX2(ctx.last_sampler, var->data.driver_location); + } + } nir_foreach_variable_with_modes(var, s, nir_var_uniform | nir_var_image) { const struct glsl_type *type = glsl_without_array(var->type); if (glsl_type_is_sampler(type) || glsl_type_is_image(type))
