From 2fb800fd1d1125bdb8cd498cf7b358098337ba73 Mon Sep 17 00:00:00 2001 From: Kenneth Graunke Date: Wed, 6 Feb 2019 03:04:15 -0800 Subject: [PATCH] tgsi_to_nir: use sampler variables and derefs MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit v2: fix is_shadow, is_array and txq Some drivers (eg. iris) need the presence of sampler variables and derefs so that they can count them to determine the number of samplers used. This change also makes the output NIR closer to what glsl_to_nir outputs. Signed-Off-By: Timur Kristóf Tested-by: Andre Heider Tested-by: Rob Clark Reviewed-by: Timothy Arceri Reviewed-by: Eric Anholt --- src/gallium/auxiliary/nir/tgsi_to_nir.c | 89 ++++++++++++++++++++++--- 1 file changed, 79 insertions(+), 10 deletions(-) diff --git a/src/gallium/auxiliary/nir/tgsi_to_nir.c b/src/gallium/auxiliary/nir/tgsi_to_nir.c index 7437c80679e..7984cea5a7b 100644 --- a/src/gallium/auxiliary/nir/tgsi_to_nir.c +++ b/src/gallium/auxiliary/nir/tgsi_to_nir.c @@ -70,6 +70,7 @@ struct ttn_compile { nir_variable **inputs; nir_variable **outputs; + nir_variable *samplers[PIPE_MAX_SAMPLERS]; nir_variable *input_var_face; nir_variable *input_var_position; @@ -1168,6 +1169,44 @@ setup_texture_info(nir_tex_instr *instr, unsigned texture) } } +static enum glsl_base_type +base_type_for_alu_type(nir_alu_type type) +{ + type = nir_alu_type_get_base_type(type); + + switch (type) { + case nir_type_float: + return GLSL_TYPE_FLOAT; + case nir_type_int: + return GLSL_TYPE_INT; + case nir_type_uint: + return GLSL_TYPE_UINT; + default: + unreachable("invalid type"); + } +} + +static nir_variable * +get_sampler_var(struct ttn_compile *c, int binding, + enum glsl_sampler_dim dim, + bool is_shadow, + bool is_array, + enum glsl_base_type base_type) +{ + nir_variable *var = c->samplers[binding]; + if (!var) { + const struct glsl_type *type = + glsl_sampler_type(dim, is_shadow, is_array, base_type); + var = nir_variable_create(c->build.shader, nir_var_uniform, type, + "sampler"); + var->data.binding = binding; + var->data.explicit_binding = true; + c->samplers[binding] = var; + } + + return var; +} + static void ttn_tex(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src) { @@ -1243,6 +1282,9 @@ ttn_tex(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src) num_srcs++; } + /* Deref sources */ + num_srcs += 2; + num_srcs += tgsi_inst->Texture.NumOffsets; instr = nir_tex_instr_create(b->shader, num_srcs); @@ -1274,14 +1316,12 @@ ttn_tex(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src) instr->coord_components++; assert(tgsi_inst->Src[samp].Register.File == TGSI_FILE_SAMPLER); - instr->texture_index = tgsi_inst->Src[samp].Register.Index; - instr->sampler_index = tgsi_inst->Src[samp].Register.Index; /* TODO if we supported any opc's which take an explicit SVIEW * src, we would use that here instead. But for the "legacy" * texture opc's the SVIEW index is same as SAMP index: */ - sview = instr->texture_index; + sview = tgsi_inst->Src[samp].Register.Index; if (op == nir_texop_lod) { instr->dest_type = nir_type_float; @@ -1291,8 +1331,23 @@ ttn_tex(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src) instr->dest_type = nir_type_float; } + nir_variable *var = + get_sampler_var(c, sview, instr->sampler_dim, + instr->is_shadow, + instr->is_array, + base_type_for_alu_type(instr->dest_type)); + + nir_deref_instr *deref = nir_build_deref_var(b, var); + unsigned src_number = 0; + instr->src[src_number].src = nir_src_for_ssa(&deref->dest.ssa); + instr->src[src_number].src_type = nir_tex_src_texture_deref; + src_number++; + instr->src[src_number].src = nir_src_for_ssa(&deref->dest.ssa); + instr->src[src_number].src_type = nir_tex_src_sampler_deref; + src_number++; + instr->src[src_number].src = nir_src_for_ssa(nir_swizzle(b, src[0], SWIZ(X, Y, Z, W), instr->coord_components, false)); @@ -1391,6 +1446,7 @@ ttn_tex(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src) } assert(src_number == num_srcs); + assert(src_number == instr->num_srcs); nir_ssa_dest_init(&instr->instr, &instr->dest, nir_tex_instr_dest_size(instr), @@ -1417,21 +1473,34 @@ ttn_txq(struct ttn_compile *c, nir_alu_dest dest, nir_ssa_def **src) struct tgsi_full_instruction *tgsi_inst = &c->token->FullInstruction; nir_tex_instr *txs, *qlv; - txs = nir_tex_instr_create(b->shader, 1); + txs = nir_tex_instr_create(b->shader, 2); txs->op = nir_texop_txs; setup_texture_info(txs, tgsi_inst->Texture.Texture); - qlv = nir_tex_instr_create(b->shader, 0); + qlv = nir_tex_instr_create(b->shader, 1); qlv->op = nir_texop_query_levels; setup_texture_info(qlv, tgsi_inst->Texture.Texture); assert(tgsi_inst->Src[1].Register.File == TGSI_FILE_SAMPLER); - txs->texture_index = tgsi_inst->Src[1].Register.Index; - qlv->texture_index = tgsi_inst->Src[1].Register.Index; + int tex_index = tgsi_inst->Src[1].Register.Index; + + nir_variable *var = + get_sampler_var(c, tex_index, txs->sampler_dim, + txs->is_shadow, + txs->is_array, + base_type_for_alu_type(txs->dest_type)); + + nir_deref_instr *deref = nir_build_deref_var(b, var); + + txs->src[0].src = nir_src_for_ssa(&deref->dest.ssa); + txs->src[0].src_type = nir_tex_src_texture_deref; + + qlv->src[0].src = nir_src_for_ssa(&deref->dest.ssa); + qlv->src[0].src_type = nir_tex_src_texture_deref; - /* only single src, the lod: */ - txs->src[0].src = nir_src_for_ssa(ttn_channel(b, src[0], X)); - txs->src[0].src_type = nir_tex_src_lod; + /* lod: */ + txs->src[1].src = nir_src_for_ssa(ttn_channel(b, src[0], X)); + txs->src[1].src_type = nir_tex_src_lod; nir_ssa_dest_init(&txs->instr, &txs->dest, nir_tex_instr_dest_size(txs), 32, NULL); -- 2.30.2