intel/fs: Add interference between SENDS sources
authorJason Ekstrand <jason.ekstrand@intel.com>
Tue, 29 Jan 2019 05:24:24 +0000 (23:24 -0600)
committerJason Ekstrand <jason@jlekstrand.net>
Tue, 29 Jan 2019 18:43:55 +0000 (18:43 +0000)
Reviewed-by: Iago Toral Quiroga <itoral@igalia.com>
src/intel/compiler/brw_fs_reg_allocate.cpp

index 5db5242452ea9d23480043723a6be3c878d3b0e4..6961cb1caf423f0ee68d19ee5948f0fc60ea1387 100644 (file)
@@ -695,6 +695,33 @@ fs_visitor::assign_regs(bool allow_spilling, bool spill_all)
       }
    }
 
+   /* From the Skylake PRM Vol. 2a docs for sends:
+    *
+    *    "It is required that the second block of GRFs does not overlap with
+    *    the first block."
+    *
+    * Normally, this is taken care of by fixup_sends_duplicate_payload() but
+    * in the case where one of the registers is an undefined value, the
+    * register allocator may decide that they don't interfere even though
+    * they're used as sources in the same instruction.  We also need to add
+    * interference here.
+    */
+   if (devinfo->gen >= 9) {
+      foreach_block_and_inst(block, fs_inst, inst, cfg) {
+         if (inst->opcode == SHADER_OPCODE_SEND && inst->ex_mlen > 0 &&
+             inst->src[2].file == VGRF &&
+             inst->src[3].file == VGRF &&
+             inst->src[2].nr != inst->src[3].nr) {
+            for (unsigned i = 0; i < inst->mlen; i++) {
+               for (unsigned j = 0; j < inst->ex_mlen; j++) {
+                  ra_add_node_interference(g, inst->src[2].nr + i,
+                                           inst->src[3].nr + j);
+               }
+            }
+         }
+      }
+   }
+
    /* Debug of register spilling: Go spill everything. */
    if (unlikely(spill_all)) {
       int reg = choose_spill_reg(g);