[Mesa-dev] [PATCH 19/27] i965/fs/nir: Append nir_intrinsic_load_ubo entries to the gather table
Abdiel Janulgue
abdiel.janulgue at linux.intel.com
Tue Apr 28 13:08:16 PDT 2015
When the const block and offset are immediate values. Otherwise just
fall-back to the previous method of uploading the UBO constant data to
GRF using pull constants.
Signed-off-by: Abdiel Janulgue <abdiel.janulgue at linux.intel.com>
---
src/mesa/drivers/dri/i965/brw_fs.h | 2 ++
src/mesa/drivers/dri/i965/brw_fs_nir.cpp | 59 ++++++++++++++++++++++++++++++++
2 files changed, 61 insertions(+)
diff --git a/src/mesa/drivers/dri/i965/brw_fs.h b/src/mesa/drivers/dri/i965/brw_fs.h
index a48b2bb..5247fa1 100644
--- a/src/mesa/drivers/dri/i965/brw_fs.h
+++ b/src/mesa/drivers/dri/i965/brw_fs.h
@@ -418,6 +418,8 @@ public:
void setup_builtin_uniform_values(ir_variable *ir);
int implied_mrf_writes(fs_inst *inst);
bool generate_ubo_gather_table(ir_expression* ir);
+ bool nir_generate_ubo_gather_table(nir_intrinsic_instr *instr, fs_reg &dest,
+ bool has_indirect);
virtual void dump_instructions();
virtual void dump_instructions(const char *name);
diff --git a/src/mesa/drivers/dri/i965/brw_fs_nir.cpp b/src/mesa/drivers/dri/i965/brw_fs_nir.cpp
index 3972581..b68f221 100644
--- a/src/mesa/drivers/dri/i965/brw_fs_nir.cpp
+++ b/src/mesa/drivers/dri/i965/brw_fs_nir.cpp
@@ -1377,6 +1377,9 @@ fs_visitor::nir_emit_intrinsic(nir_intrinsic_instr *instr)
has_indirect = true;
/* fallthrough */
case nir_intrinsic_load_ubo: {
+ if (nir_generate_ubo_gather_table(instr, dest, has_indirect))
+ break;
+
nir_const_value *const_index = nir_src_as_const_value(instr->src[0]);
fs_reg surf_index;
@@ -1774,3 +1777,59 @@ fs_visitor::nir_emit_jump(nir_jump_instr *instr)
unreachable("unknown jump");
}
}
+
+bool
+fs_visitor::nir_generate_ubo_gather_table(nir_intrinsic_instr *instr, fs_reg &dest,
+ bool has_indirect)
+{
+ nir_const_value *const_index = nir_src_as_const_value(instr->src[0]);
+
+ if (!const_index || has_indirect || !brw->fs_ubo_gather || !brw->has_resource_streamer)
+ return false;
+
+ /* Only allow 16 registers (128 uniform components) as push constants.
+ */
+ unsigned int max_push_components = 16 * 8;
+ unsigned param_index = uniforms + ubo_uniforms;
+ if ((MAX2(param_index, num_direct_uniforms) +
+ instr->num_components) > max_push_components)
+ return false;
+
+ fs_reg uniform_reg;
+ if (dispatch_width == 16) {
+ for (int i = 0; i < (int) this->nr_ubo_gather_table; i++) {
+ if ((this->ubo_gather_table[i].const_block ==
+ const_index->u[0]) &&
+ (this->ubo_gather_table[i].const_offset ==
+ (unsigned) instr->const_index[0])) {
+ uniform_reg = fs_reg(UNIFORM, this->ubo_gather_table[i].reg);
+ break;
+ }
+ }
+ if (uniform_reg.file != UNIFORM) {
+ /* Unlikely but this means that SIMD8 wasn't able to allocate push constant
+ * registers for this ubo load. Fall back to pull-constant method.
+ */
+ return false;
+ }
+ }
+
+ if (uniform_reg.file != UNIFORM) {
+ uniform_reg = fs_reg(UNIFORM, param_index);
+ int gather = this->nr_ubo_gather_table++;
+
+ assert(instr->num_components <= 4);
+ ubo_uniforms += instr->num_components;
+ this->ubo_gather_table[gather].reg = uniform_reg.reg;
+ this->ubo_gather_table[gather].const_block = const_index->u[0];
+ this->ubo_gather_table[gather].const_offset = instr->const_index[0];
+ }
+
+ for (unsigned j = 0; j < instr->num_components; j++) {
+ fs_reg src = offset(retype(uniform_reg, dest.type), j);
+ emit(MOV(dest, src));
+ dest = offset(dest, 1);
+ }
+
+ return true;
+}
--
1.9.1
More information about the mesa-dev
mailing list