summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatt Turner <mattst88@gmail.com>2014-03-11 13:14:08 -0700
committerMatt Turner <mattst88@gmail.com>2014-03-24 11:06:26 -0700
commit9630ba6c6e754b438cf67c7d76ec1c99488df3ba (patch)
tree9a2f42ada5bfad10dea963c546ab1f1374e12db1
parentdc0f5099fa3cb564c25eb892fde93cacd29df8f1 (diff)
i965/vec4: Let dead code eliminate trim dead channels.
That is, modify mad dst, a, b, c to be mad dst.xyz, a, b, c if dst.w is never read. total instructions in shared programs: 811869 -> 805582 (-0.77%) instructions in affected programs: 168287 -> 162000 (-3.74%) Reviewed-by: Eric Anholt <eric@anholt.net>
-rw-r--r--src/mesa/drivers/dri/i965/brw_vec4.cpp29
1 files changed, 26 insertions, 3 deletions
diff --git a/src/mesa/drivers/dri/i965/brw_vec4.cpp b/src/mesa/drivers/dri/i965/brw_vec4.cpp
index 135cc425dc..673086d5aa 100644
--- a/src/mesa/drivers/dri/i965/brw_vec4.cpp
+++ b/src/mesa/drivers/dri/i965/brw_vec4.cpp
@@ -343,8 +343,20 @@ vec4_visitor::dead_code_eliminate()
if (inst->dst.file != GRF || inst->has_side_effects())
continue;
- assert(this->virtual_grf_end[inst->dst.reg] >= pc);
- if (this->virtual_grf_end[inst->dst.reg] == pc) {
+ int write_mask = inst->dst.writemask;
+
+ for (int c = 0; c < 4; c++) {
+ if (write_mask & (1 << c)) {
+ assert(this->virtual_grf_end[inst->dst.reg * 4 + c] >= pc);
+ if (this->virtual_grf_end[inst->dst.reg * 4 + c] == pc) {
+ write_mask &= ~(1 << c);
+ }
+ }
+ }
+
+ if (write_mask == 0) {
+ progress = true;
+
/* Don't dead code eliminate instructions that write to the
* accumulator as a side-effect. Instead just set the destination
* to the null register to free it.
@@ -363,7 +375,18 @@ vec4_visitor::dead_code_eliminate()
}
break;
}
- progress = true;
+ } else if (inst->dst.writemask != write_mask) {
+ switch (inst->opcode) {
+ case SHADER_OPCODE_TXF_CMS:
+ case SHADER_OPCODE_GEN4_SCRATCH_READ:
+ case VS_OPCODE_PULL_CONSTANT_LOAD:
+ case VS_OPCODE_PULL_CONSTANT_LOAD_GEN7:
+ break;
+ default:
+ progress = true;
+ inst->dst.writemask = write_mask;
+ break;
+ }
}
}