Mesa (main): nir/lower_tex: add lower_to_fragment_fetch_amd
GitLab Mirror
gitlab-mirror at kemper.freedesktop.org
Thu Oct 7 17:52:54 UTC 2021
Module: Mesa
Branch: main
Commit: f3723822a4f9adee30aab002b236cde1ef0d0b9f
URL: http://cgit.freedesktop.org/mesa/mesa/commit/?id=f3723822a4f9adee30aab002b236cde1ef0d0b9f
Author: Rhys Perry <pendingchaos02 at gmail.com>
Date: Wed Aug 4 16:17:39 2021 +0100
nir/lower_tex: add lower_to_fragment_fetch_amd
Signed-off-by: Rhys Perry <pendingchaos02 at gmail.com>
Reviewed-by: Jason Ekstrand <jason at jlekstrand.net>
Reviewed-by: Samuel Pitoiset <samuel.pitoiset at gmail.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/12214>
---
src/compiler/nir/nir.h | 6 ++++
src/compiler/nir/nir_lower_tex.c | 76 ++++++++++++++++++++++++++++++++++++++++
2 files changed, 82 insertions(+)
diff --git a/src/compiler/nir/nir.h b/src/compiler/nir/nir.h
index 3a4a439b461..5d076c75487 100644
--- a/src/compiler/nir/nir.h
+++ b/src/compiler/nir/nir.h
@@ -5222,6 +5222,12 @@ typedef struct nir_lower_tex_options {
*/
bool lower_tg4_offsets;
+ /**
+ * Lower txf_ms to fragment_mask_fetch and fragment_fetch and samples_identical to
+ * fragment_mask_fetch.
+ */
+ bool lower_to_fragment_fetch_amd;
+
/**
* To lower packed sampler return formats.
*
diff --git a/src/compiler/nir/nir_lower_tex.c b/src/compiler/nir/nir_lower_tex.c
index b19f671623b..30aa1e75249 100644
--- a/src/compiler/nir/nir_lower_tex.c
+++ b/src/compiler/nir/nir_lower_tex.c
@@ -1191,6 +1191,70 @@ nir_lower_txs_cube_array(nir_builder *b, nir_tex_instr *tex)
nir_ssa_def_rewrite_uses_after(&tex->dest.ssa, size, size->parent_instr);
}
+static void
+nir_lower_ms_txf_to_fragment_fetch(nir_builder *b, nir_tex_instr *tex)
+{
+ lower_offset(b, tex);
+
+ b->cursor = nir_before_instr(&tex->instr);
+
+ /* Create FMASK fetch. */
+ assert(tex->texture_index == 0);
+ nir_tex_instr *fmask_fetch = nir_tex_instr_create(b->shader, tex->num_srcs - 1);
+ fmask_fetch->op = nir_texop_fragment_mask_fetch_amd;
+ fmask_fetch->coord_components = tex->coord_components;
+ fmask_fetch->sampler_dim = tex->sampler_dim;
+ fmask_fetch->is_array = tex->is_array;
+ fmask_fetch->texture_non_uniform = tex->texture_non_uniform;
+ fmask_fetch->dest_type = nir_type_uint32;
+ nir_ssa_dest_init(&fmask_fetch->instr, &fmask_fetch->dest, 1, 32, NULL);
+
+ fmask_fetch->num_srcs = 0;
+ for (unsigned i = 0; i < tex->num_srcs; i++) {
+ if (tex->src[i].src_type == nir_tex_src_ms_index)
+ continue;
+ nir_tex_src *src = &fmask_fetch->src[fmask_fetch->num_srcs++];
+ src->src = nir_src_for_ssa(tex->src[i].src.ssa);
+ src->src_type = tex->src[i].src_type;
+ }
+
+ nir_builder_instr_insert(b, &fmask_fetch->instr);
+
+ /* Obtain new sample index. */
+ int ms_index = nir_tex_instr_src_index(tex, nir_tex_src_ms_index);
+ assert(ms_index >= 0);
+ nir_src sample = tex->src[ms_index].src;
+ nir_ssa_def *new_sample = NULL;
+ if (nir_src_is_const(sample) && (nir_src_as_uint(sample) == 0 || nir_src_as_uint(sample) == 7)) {
+ if (nir_src_as_uint(sample) == 7)
+ new_sample = nir_ushr(b, &fmask_fetch->dest.ssa, nir_imm_int(b, 28));
+ else
+ new_sample = nir_iand_imm(b, &fmask_fetch->dest.ssa, 0xf);
+ } else {
+ new_sample = nir_ubitfield_extract(b, &fmask_fetch->dest.ssa,
+ nir_imul_imm(b, sample.ssa, 4), nir_imm_int(b, 4));
+ }
+
+ /* Update instruction. */
+ tex->op = nir_texop_fragment_fetch_amd;
+ nir_instr_rewrite_src_ssa(&tex->instr, &tex->src[ms_index].src, new_sample);
+}
+
+static void
+nir_lower_samples_identical_to_fragment_fetch(nir_builder *b, nir_tex_instr *tex)
+{
+ b->cursor = nir_after_instr(&tex->instr);
+
+ nir_tex_instr *fmask_fetch = nir_instr_as_tex(nir_instr_clone(b->shader, &tex->instr));
+ fmask_fetch->op = nir_texop_fragment_mask_fetch_amd;
+ fmask_fetch->dest_type = nir_type_uint32;
+ nir_ssa_dest_init(&fmask_fetch->instr, &fmask_fetch->dest, 1, 32, NULL);
+ nir_builder_instr_insert(b, &fmask_fetch->instr);
+
+ nir_ssa_def_rewrite_uses(&tex->dest.ssa, nir_ieq_imm(b, &fmask_fetch->dest.ssa, 0));
+ nir_instr_remove_v(&tex->instr);
+}
+
static bool
nir_lower_tex_block(nir_block *block, nir_builder *b,
const nir_lower_tex_options *options,
@@ -1400,6 +1464,18 @@ nir_lower_tex_block(nir_block *block, nir_builder *b,
progress |= lower_tg4_offsets(b, tex);
continue;
}
+
+ if (options->lower_to_fragment_fetch_amd && tex->op == nir_texop_txf_ms) {
+ nir_lower_ms_txf_to_fragment_fetch(b, tex);
+ progress = true;
+ continue;
+ }
+
+ if (options->lower_to_fragment_fetch_amd && tex->op == nir_texop_samples_identical) {
+ nir_lower_samples_identical_to_fragment_fetch(b, tex);
+ progress = true;
+ continue;
+ }
}
return progress;
More information about the mesa-commit
mailing list