[Mesa-dev] [PATCH 5/8] i965/fs: Fix register spilling for 16-wide.
Eric Anholt
eric at anholt.net
Tue Oct 29 21:28:10 CET 2013
Things blew up when I enabled the debug register spill code without
disabling 16-wide, so I decided to just fix 16-wide spilling.
We still don't generate 16-wide when register spilling happens as part of
allocation (since we expect it to be slower), but now we can experiment
with allowing it in some cases in the future.
---
src/mesa/drivers/dri/i965/brw_fs_generator.cpp | 8 ++++----
src/mesa/drivers/dri/i965/brw_fs_reg_allocate.cpp | 19 +++++++++----------
2 files changed, 13 insertions(+), 14 deletions(-)
diff --git a/src/mesa/drivers/dri/i965/brw_fs_generator.cpp b/src/mesa/drivers/dri/i965/brw_fs_generator.cpp
index ef85837..e16d874 100644
--- a/src/mesa/drivers/dri/i965/brw_fs_generator.cpp
+++ b/src/mesa/drivers/dri/i965/brw_fs_generator.cpp
@@ -756,8 +756,8 @@ fs_generator::generate_spill(fs_inst *inst, struct brw_reg src)
brw_MOV(p,
retype(brw_message_reg(inst->base_mrf + 1), BRW_REGISTER_TYPE_UD),
retype(src, BRW_REGISTER_TYPE_UD));
- brw_oword_block_write_scratch(p, brw_message_reg(inst->base_mrf), 1,
- inst->offset);
+ brw_oword_block_write_scratch(p, brw_message_reg(inst->base_mrf),
+ inst->mlen, inst->offset);
}
void
@@ -765,8 +765,8 @@ fs_generator::generate_unspill(fs_inst *inst, struct brw_reg dst)
{
assert(inst->mlen != 0);
- brw_oword_block_read_scratch(p, dst, brw_message_reg(inst->base_mrf), 1,
- inst->offset);
+ brw_oword_block_read_scratch(p, dst, brw_message_reg(inst->base_mrf),
+ dispatch_width / 8, inst->offset);
}
void
diff --git a/src/mesa/drivers/dri/i965/brw_fs_reg_allocate.cpp b/src/mesa/drivers/dri/i965/brw_fs_reg_allocate.cpp
index 50f3414..3abe127 100644
--- a/src/mesa/drivers/dri/i965/brw_fs_reg_allocate.cpp
+++ b/src/mesa/drivers/dri/i965/brw_fs_reg_allocate.cpp
@@ -547,15 +547,12 @@ fs_visitor::emit_unspill(fs_inst *inst, fs_reg dst, uint32_t spill_offset,
unspill_inst->ir = inst->ir;
unspill_inst->annotation = inst->annotation;
- /* Choose a MRF that won't conflict with an MRF that's live across the
- * spill. Nothing else will make it up to MRF 14/15.
- */
unspill_inst->base_mrf = 14;
unspill_inst->mlen = 1; /* header contains offset */
inst->insert_before(unspill_inst);
dst.reg_offset++;
- spill_offset += REG_SIZE;
+ spill_offset += dispatch_width * sizeof(float);
}
}
@@ -639,10 +636,10 @@ fs_visitor::choose_spill_reg(struct ra_graph *g)
void
fs_visitor::spill_reg(int spill_reg)
{
+ int reg_size = dispatch_width * sizeof(float);
int size = virtual_grf_sizes[spill_reg];
unsigned int spill_offset = c->last_scratch;
assert(ALIGN(spill_offset, 16) == spill_offset); /* oword read/write req. */
- c->last_scratch += size * REG_SIZE;
int spill_base_mrf = dispatch_width > 8 ? 13 : 14;
/* Spills may use MRFs 13-15 in the SIMD16 case. Our texturing is done
@@ -667,6 +664,8 @@ fs_visitor::spill_reg(int spill_reg)
spilled_any_registers = true;
}
+ c->last_scratch += size * reg_size;
+
/* Generate spill/unspill instructions for the objects being
* spilled. Right now, we spill or unspill the whole thing to a
* virtual grf of the same size. For most instructions, though, we
@@ -684,7 +683,7 @@ fs_visitor::spill_reg(int spill_reg)
inst->src[i].reg_offset = 0;
emit_unspill(inst, inst->src[i],
- spill_offset + REG_SIZE * inst->src[i].reg_offset,
+ spill_offset + reg_size * inst->src[i].reg_offset,
regs_read);
}
}
@@ -692,7 +691,7 @@ fs_visitor::spill_reg(int spill_reg)
if (inst->dst.file == GRF &&
inst->dst.reg == spill_reg) {
int subset_spill_offset = (spill_offset +
- REG_SIZE * inst->dst.reg_offset);
+ reg_size * inst->dst.reg_offset);
inst->dst.reg = virtual_grf_alloc(inst->regs_written);
inst->dst.reg_offset = 0;
@@ -715,11 +714,11 @@ fs_visitor::spill_reg(int spill_reg)
fs_inst *spill_inst = new(mem_ctx) fs_inst(FS_OPCODE_SPILL,
reg_null_f, spill_src);
spill_src.reg_offset++;
- spill_inst->offset = subset_spill_offset + chan * REG_SIZE;
+ spill_inst->offset = subset_spill_offset + chan * reg_size;
spill_inst->ir = inst->ir;
spill_inst->annotation = inst->annotation;
- spill_inst->base_mrf = 14;
- spill_inst->mlen = 2; /* header, value */
+ spill_inst->mlen = 1 + dispatch_width / 8; /* header, value */
+ spill_inst->base_mrf = spill_base_mrf;
inst->insert_after(spill_inst);
}
}
--
1.8.4.rc3
More information about the mesa-dev
mailing list