[Mesa-dev] [RFC 3/7] i965/fs: Add a CHANNEL_IDS opcode
Jason Ekstrand
jason at jlekstrand.net
Mon Dec 5 19:59:54 UTC 2016
---
src/mesa/drivers/dri/i965/brw_defines.h | 6 ++++++
src/mesa/drivers/dri/i965/brw_fs.h | 3 +++
src/mesa/drivers/dri/i965/brw_fs_cse.cpp | 1 +
src/mesa/drivers/dri/i965/brw_fs_generator.cpp | 28 ++++++++++++++++++++++++++
src/mesa/drivers/dri/i965/brw_fs_nir.cpp | 14 +++----------
src/mesa/drivers/dri/i965/brw_shader.cpp | 2 ++
6 files changed, 43 insertions(+), 11 deletions(-)
diff --git a/src/mesa/drivers/dri/i965/brw_defines.h b/src/mesa/drivers/dri/i965/brw_defines.h
index f22a52f..16a72c4 100644
--- a/src/mesa/drivers/dri/i965/brw_defines.h
+++ b/src/mesa/drivers/dri/i965/brw_defines.h
@@ -1095,6 +1095,12 @@ enum opcode {
*/
SHADER_OPCODE_BROADCAST,
+ /* Takes no sources and returns the index of each channel in its respective
+ * SIMD channel in the destination register. The instruction must have
+ * WE_all set and the destination must have type BRW_REGISTER_TYPE_UW.
+ */
+ SHADER_OPCODE_CHANNEL_IDS,
+
VEC4_OPCODE_MOV_BYTES,
VEC4_OPCODE_PACK_BYTES,
VEC4_OPCODE_UNPACK_UNIFORM,
diff --git a/src/mesa/drivers/dri/i965/brw_fs.h b/src/mesa/drivers/dri/i965/brw_fs.h
index 002cee8..4ce0f56 100644
--- a/src/mesa/drivers/dri/i965/brw_fs.h
+++ b/src/mesa/drivers/dri/i965/brw_fs.h
@@ -437,6 +437,9 @@ private:
struct brw_reg msg_data,
unsigned msg_type);
+ void generate_channel_ids(fs_inst *inst,
+ struct brw_reg dst);
+
void generate_set_sample_id(fs_inst *inst,
struct brw_reg dst,
struct brw_reg src0,
diff --git a/src/mesa/drivers/dri/i965/brw_fs_cse.cpp b/src/mesa/drivers/dri/i965/brw_fs_cse.cpp
index 48220ef..02ccda1 100644
--- a/src/mesa/drivers/dri/i965/brw_fs_cse.cpp
+++ b/src/mesa/drivers/dri/i965/brw_fs_cse.cpp
@@ -79,6 +79,7 @@ is_expression(const fs_visitor *v, const fs_inst *const inst)
case FS_OPCODE_LINTERP:
case SHADER_OPCODE_FIND_LIVE_CHANNEL:
case SHADER_OPCODE_BROADCAST:
+ case SHADER_OPCODE_CHANNEL_IDS:
case SHADER_OPCODE_MOV_INDIRECT:
case SHADER_OPCODE_TEX_LOGICAL:
case SHADER_OPCODE_TXD_LOGICAL:
diff --git a/src/mesa/drivers/dri/i965/brw_fs_generator.cpp b/src/mesa/drivers/dri/i965/brw_fs_generator.cpp
index c5b50e1..3ef2d5b 100644
--- a/src/mesa/drivers/dri/i965/brw_fs_generator.cpp
+++ b/src/mesa/drivers/dri/i965/brw_fs_generator.cpp
@@ -1435,6 +1435,30 @@ fs_generator::generate_set_simd4x2_offset(fs_inst *inst,
brw_pop_insn_state(p);
}
+void
+fs_generator::generate_channel_ids(fs_inst *inst, struct brw_reg dst)
+{
+ assert(dst.type == BRW_REGISTER_TYPE_UW ||
+ dst.type == BRW_REGISTER_TYPE_W);
+ assert(inst->exec_size >= 8);
+
+ brw_push_insn_state(p);
+ brw_set_default_exec_size(p, BRW_EXECUTE_8);
+ brw_set_default_compression_control(p, BRW_COMPRESSION_NONE);
+ brw_set_default_mask_control(p, true);
+ brw_MOV(p, dst, brw_imm_v(0x76543210));
+
+ if (inst->exec_size > 8) {
+ assert(inst->exec_size == 16);
+ brw_ADD(p, vec8(suboffset(dst, 8)), vec8(dst), brw_imm_w(8));
+ }
+
+ brw_pop_insn_state(p);
+
+ if (inst->group > 0)
+ brw_ADD(p, dst, dst, brw_imm_w(inst->group));
+}
+
/* Sets vstride=1, width=4, hstride=0 of register src1 during
* the ADD instruction.
*/
@@ -2056,6 +2080,10 @@ fs_generator::generate_code(const cfg_t *cfg, int dispatch_width)
brw_broadcast(p, dst, src[0], src[1]);
break;
+ case SHADER_OPCODE_CHANNEL_IDS:
+ generate_channel_ids(inst, dst);
+ break;
+
case FS_OPCODE_SET_SAMPLE_ID:
generate_set_sample_id(inst, dst, src[0], src[1]);
break;
diff --git a/src/mesa/drivers/dri/i965/brw_fs_nir.cpp b/src/mesa/drivers/dri/i965/brw_fs_nir.cpp
index 855266f..9478bb8 100644
--- a/src/mesa/drivers/dri/i965/brw_fs_nir.cpp
+++ b/src/mesa/drivers/dri/i965/brw_fs_nir.cpp
@@ -4310,17 +4310,9 @@ fs_visitor::nir_emit_intrinsic(const fs_builder &bld, nir_intrinsic_instr *instr
}
case nir_intrinsic_load_channel_num: {
- fs_reg tmp = bld.vgrf(BRW_REGISTER_TYPE_UW);
- dest = retype(dest, BRW_REGISTER_TYPE_UD);
- const fs_builder allbld8 = bld.group(8, 0).exec_all();
- allbld8.MOV(tmp, brw_imm_v(0x76543210));
- if (dispatch_width > 8)
- allbld8.ADD(byte_offset(tmp, 16), tmp, brw_imm_uw(8u));
- if (dispatch_width > 16) {
- const fs_builder allbld16 = bld.group(16, 0).exec_all();
- allbld16.ADD(byte_offset(tmp, 32), tmp, brw_imm_uw(16u));
- }
- bld.MOV(dest, tmp);
+ fs_reg tmp = bld.vgrf(BRW_REGISTER_TYPE_W);
+ bld.exec_all().emit(SHADER_OPCODE_CHANNEL_IDS, tmp);
+ bld.MOV(retype(dest, BRW_REGISTER_TYPE_D), tmp);
break;
}
diff --git a/src/mesa/drivers/dri/i965/brw_shader.cpp b/src/mesa/drivers/dri/i965/brw_shader.cpp
index 25f745d..726bc7d 100644
--- a/src/mesa/drivers/dri/i965/brw_shader.cpp
+++ b/src/mesa/drivers/dri/i965/brw_shader.cpp
@@ -315,6 +315,8 @@ brw_instruction_name(const struct gen_device_info *devinfo, enum opcode op)
return "find_live_channel";
case SHADER_OPCODE_BROADCAST:
return "broadcast";
+ case SHADER_OPCODE_CHANNEL_IDS:
+ return "channel_ids";
case VEC4_OPCODE_MOV_BYTES:
return "mov_bytes";
--
2.5.0.400.gff86faf
More information about the mesa-dev
mailing list