[Mesa-dev] [PATCH 2/2] i965/fs: Add support for gl_HelperInvocation system value.
Matt Turner
mattst88 at gmail.com
Fri Nov 13 18:05:36 PST 2015
---
This code generates
mov(1) f0<1>UW g1.14<0,1,0>UW
mov(8) g2<1>UD 0x00000000UD
(+f0) sel(8) g3<1>D g2<8,8,1>D -1D
which I don't love because it uses the flag register, and likely uses
of gl_HelperInvocation will be in an if condition, in which case we
could have just used f0 directly.
Alternative implementation ideas:
- Shift dispatch mask with a vector-immediate, and then
resolve it to true/false with -(x & 1):
shr(8) tmp<1>UW g1.14<1,8,0>UB 0x76543210V
- Take advantage of the dispatch mask directly:
mov(8) dst<1>D, 0D { WE_all }
mov(8) dst<1>D, -1D
But optimization passes would have to be made to understand
that the first move in that sequence isn't dead...
Regardless, I couldn't make either of these other ideas work.
src/mesa/drivers/dri/i965/brw_fs_nir.cpp | 18 ++++++++++++++++++
1 file changed, 18 insertions(+)
diff --git a/src/mesa/drivers/dri/i965/brw_fs_nir.cpp b/src/mesa/drivers/dri/i965/brw_fs_nir.cpp
index c282f83..7cf32b5 100644
--- a/src/mesa/drivers/dri/i965/brw_fs_nir.cpp
+++ b/src/mesa/drivers/dri/i965/brw_fs_nir.cpp
@@ -250,6 +250,23 @@ emit_system_values_block(nir_block *block, void *void_visitor)
*reg = *v->emit_cs_work_group_id_setup();
break;
+ case nir_intrinsic_load_helper_invocation:
+ assert(v->stage == MESA_SHADER_FRAGMENT);
+ reg = &v->nir_system_values[SYSTEM_VALUE_HELPER_INVOCATION];
+ if (reg->file == BAD_FILE) {
+ const fs_builder abld =
+ v->bld.annotate("gl_HelperInvocation", NULL);
+
+ abld.emit(FS_OPCODE_MOV_DISPATCH_TO_FLAGS);
+ fs_reg zero = abld.vgrf(BRW_REGISTER_TYPE_D, 1);
+ fs_reg dst = abld.vgrf(BRW_REGISTER_TYPE_D, 1);
+ abld.MOV(zero, fs_reg(0));
+ set_predicate(BRW_PREDICATE_NORMAL,
+ abld.SEL(dst, zero, fs_reg(-1)));
+ *reg = dst;
+ }
+ break;
+
default:
break;
}
@@ -1703,6 +1720,7 @@ fs_visitor::nir_emit_fs_intrinsic(const fs_builder &bld,
break;
}
+ case nir_intrinsic_load_helper_invocation:
case nir_intrinsic_load_sample_mask_in:
case nir_intrinsic_load_sample_id: {
gl_system_value sv = nir_system_value_from_intrinsic(instr->intrinsic);
--
2.4.9
More information about the mesa-dev
mailing list