Mesa (master): lima/ppir: introduce liveness internal live set

GitLab Mirror gitlab-mirror at kemper.freedesktop.org
Sat May 9 11:46:08 UTC 2020


Module: Mesa
Branch: master
Commit: cef1c73634493ef9766baa0b6a898369eff7686f
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=cef1c73634493ef9766baa0b6a898369eff7686f

Author: Erico Nunes <nunes.erico at gmail.com>
Date:   Mon Apr 13 15:21:52 2020 +0200

lima/ppir: introduce liveness internal live set

The current solution for handling registers that live and die within a
single instruction does not handle all cases. In particular, these
intra-instruction use register also conflict with registers that are
part of the live_in set.
Unfortunately, adding them to the live_in set is not an easy solution as
that would cause them to be propagated upwards. So, add a separate set
to handle these registers in the particular instructions, without
propagating them.

Signed-off-by: Erico Nunes <nunes.erico at gmail.com>
Reviewed-by: Vasily Khoruzhick <anarsoul at gmail.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/4535>

---

 src/gallium/drivers/lima/ir/pp/liveness.c | 11 +++++------
 src/gallium/drivers/lima/ir/pp/ppir.h     |  4 ++++
 src/gallium/drivers/lima/ir/pp/regalloc.c | 15 +++++++++++++++
 3 files changed, 24 insertions(+), 6 deletions(-)

diff --git a/src/gallium/drivers/lima/ir/pp/liveness.c b/src/gallium/drivers/lima/ir/pp/liveness.c
index ccc01a3545f..b17564b089d 100644
--- a/src/gallium/drivers/lima/ir/pp/liveness.c
+++ b/src/gallium/drivers/lima/ir/pp/liveness.c
@@ -129,11 +129,10 @@ ppir_liveness_instr_srcs(ppir_compiler *comp, ppir_instr *instr)
 
          /* if some other op on this same instruction is writing,
           * we just need to reserve a register for this particular
-          * instruction. Add the register to live_out to make that
-          * interference happen without propagating its liveness. */
+          * instruction. */
          if (src->node && src->node->instr == instr) {
-            instr->live_out[reg->regalloc_index].reg = reg;
-            _mesa_set_add(instr->live_out_set, &instr->live_out[reg->regalloc_index]);
+            instr->live_internal[reg->regalloc_index].reg = reg;
+            _mesa_set_add(instr->live_internal_set, &instr->live_internal[reg->regalloc_index]);
             continue;
          }
 
@@ -199,8 +198,8 @@ ppir_liveness_instr_dest(ppir_compiler *comp, ppir_instr *instr)
        * either dead code or a bug. For now, assign an interference to it to
        * ensure it doesn't get assigned a live register and overwrites it. */
       if (!live) {
-         instr->live_out[reg->regalloc_index].reg = reg;
-         _mesa_set_add(instr->live_out_set, &instr->live_out[reg->regalloc_index]);
+         instr->live_internal[reg->regalloc_index].reg = reg;
+         _mesa_set_add(instr->live_internal_set, &instr->live_internal[reg->regalloc_index]);
          continue;
       }
 
diff --git a/src/gallium/drivers/lima/ir/pp/ppir.h b/src/gallium/drivers/lima/ir/pp/ppir.h
index 357fcada8b7..6f2ff4090b4 100644
--- a/src/gallium/drivers/lima/ir/pp/ppir.h
+++ b/src/gallium/drivers/lima/ir/pp/ppir.h
@@ -328,8 +328,12 @@ typedef struct ppir_instr {
    /* for liveness analysis */
    struct ppir_liveness *live_in;
    struct ppir_liveness *live_out;
+   /* live_internal is to mark registers only live within an
+    * instruction, without propagation */
+   struct ppir_liveness *live_internal;
    struct set *live_in_set;
    struct set *live_out_set;
+   struct set *live_internal_set;
 } ppir_instr;
 
 typedef struct ppir_block {
diff --git a/src/gallium/drivers/lima/ir/pp/regalloc.c b/src/gallium/drivers/lima/ir/pp/regalloc.c
index 0b5af3c6bf4..4b5d3a8bb1d 100644
--- a/src/gallium/drivers/lima/ir/pp/regalloc.c
+++ b/src/gallium/drivers/lima/ir/pp/regalloc.c
@@ -599,6 +599,17 @@ static void ppir_regalloc_reset_liveness_info(ppir_compiler *comp)
                                                _mesa_hash_pointer,
                                                _mesa_key_pointer_equal);
 
+         if (instr->live_internal)
+            ralloc_free(instr->live_internal);
+         instr->live_internal = rzalloc_array(comp,
+               struct ppir_liveness, list_length(&comp->reg_list));
+
+         if (instr->live_internal_set)
+            _mesa_set_destroy(instr->live_internal_set, NULL);
+         instr->live_internal_set = _mesa_set_create(comp,
+                                               _mesa_hash_pointer,
+                                               _mesa_key_pointer_equal);
+
          if (instr->live_out)
             ralloc_free(instr->live_out);
          instr->live_out = rzalloc_array(comp,
@@ -648,6 +659,10 @@ static bool ppir_regalloc_prog_try(ppir_compiler *comp, bool *spilled)
 
    list_for_each_entry(ppir_block, block, &comp->block_list, list) {
       list_for_each_entry(ppir_instr, instr, &block->instr_list, list) {
+         set_foreach(instr->live_internal_set, entry) {
+            _mesa_set_add(instr->live_in_set, entry->key);
+            _mesa_set_add(instr->live_out_set, entry->key);
+         }
          ppir_all_interference(comp, g, instr->live_in_set);
          ppir_all_interference(comp, g, instr->live_out_set);
       }



More information about the mesa-commit mailing list