Mesa (nv50-compiler): nv50: insert MOVs also for PHI sources from dominating block

Christoph Bumiller chrisbmr at kemper.freedesktop.org
Sat Jul 31 16:31:50 UTC 2010


Module: Mesa
Branch: nv50-compiler
Commit: 5de5e4fd5c7c6d55e9b3aadbaae0ca34e2662e2c
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=5de5e4fd5c7c6d55e9b3aadbaae0ca34e2662e2c

Author: Christoph Bumiller <e0425955 at student.tuwien.ac.at>
Date:   Tue Jul 27 17:56:13 2010 +0200

nv50: insert MOVs also for PHI sources from dominating block

Otherwise we get live range conflicts for operands that are written
only in e.g. an ELSE block but not the IF block.

---

 src/gallium/drivers/nv50/nv50_pc_print.c    |   12 ++++---
 src/gallium/drivers/nv50/nv50_pc_regalloc.c |   53 +++++++++++++--------------
 2 files changed, 32 insertions(+), 33 deletions(-)

diff --git a/src/gallium/drivers/nv50/nv50_pc_print.c b/src/gallium/drivers/nv50/nv50_pc_print.c
index c2c3eb2..c812dbd 100644
--- a/src/gallium/drivers/nv50/nv50_pc_print.c
+++ b/src/gallium/drivers/nv50/nv50_pc_print.c
@@ -181,9 +181,11 @@ nv_print_address(const char c, int buf, struct nv_value *a, int offset)
 static INLINE void
 nv_print_cond(struct nv_instruction *nvi)
 {
-   PRINT("%s%s %s$c%i ",
+   char pfx = nv_value_allocated(nvi->flags_src->value->join) ? '$' : '%';
+
+   PRINT("%s%s %s%cc%i ",
          gree, nv_cond_name(nvi->cc),
-         mgta, nv_value_id(nvi->flags_src->value));
+         mgta, pfx, nv_value_id(nvi->flags_src->value));
 }
 
 static INLINE void
@@ -197,8 +199,8 @@ nv_print_value(struct nv_value *value, struct nv_value *ind, ubyte type)
    if (value->reg.file != NV_FILE_FLAGS)
       PRINT(" %s%s", gree, nv_type_name(type));
 
-   if (!nv_value_allocated(value))
-      reg_pfx = nv_value_allocated(value->join) ? '&' : '%';
+   if (!nv_value_allocated(value->join))
+      reg_pfx = '%';
 
    switch (value->reg.file) {
    case NV_FILE_GPR:
@@ -301,7 +303,7 @@ nv_print_instruction(struct nv_instruction *i)
          continue;
 
       if (i->src[j]->mod)
-         PRINT(" %s", nv_modifier_string(i->src[j]->mod));
+         PRINT(" %s%s", gree, nv_modifier_string(i->src[j]->mod));
 
       nv_print_ref(i->src[j],
                    (j == nv50_indirect_opnd(i)) ?
diff --git a/src/gallium/drivers/nv50/nv50_pc_regalloc.c b/src/gallium/drivers/nv50/nv50_pc_regalloc.c
index 3cec219..568384f 100644
--- a/src/gallium/drivers/nv50/nv50_pc_regalloc.c
+++ b/src/gallium/drivers/nv50/nv50_pc_regalloc.c
@@ -56,6 +56,25 @@ struct nv_pc_pass {
    uint pass_seq;
 };
 
+/* check if bf (future) can be reached from bp (past) */
+static boolean
+bb_reachable_by(struct nv_basic_block *bf, struct nv_basic_block *bp,
+                struct nv_basic_block *bt)
+{
+   if (bf == bp)
+      return TRUE;
+   if (bp == bt)
+      return FALSE;
+
+   if (bp->out[0] && bp->out[0] != bp &&
+       bb_reachable_by(bf, bp->out[0], bt))
+      return TRUE;
+   if (bp->out[1] && bp->out[1] != bp &&
+       bb_reachable_by(bf, bp->out[1], bt))
+      return TRUE;
+   return FALSE;
+}
+
 static void
 ranges_coalesce(struct nv_range *range)
 {
@@ -422,7 +441,7 @@ pass_generate_phi_movs(struct nv_pc_pass *ctx, struct nv_basic_block *b)
             if (!i->src[j])
                j = 3;
             else
-            if (i->src[j]->value->insn->bb == p)
+            if (bb_reachable_by(pn, i->src[j]->value->insn->bb, b))
                break;
          }
          if (j >= 4)
@@ -580,25 +599,6 @@ live_set_test(struct nv_basic_block *b, struct nv_ref *ref)
    return b->live_set[n / 32] & (1 << (n % 32));
 }
 
-/* check if bf (future) can be reached from bp (past) */
-static boolean
-bb_reachable_by(struct nv_basic_block *bf, struct nv_basic_block *bp,
-		struct nv_basic_block *bt)
-{
-   if (bf == bp)
-      return TRUE;
-   if (bp == bt)
-      return FALSE;
-
-   if (bp->out[0] && bp->out[0] != bp &&
-       bb_reachable_by(bf, bp->out[0], bt))
-      return TRUE;
-   if (bp->out[1] && bp->out[1] != bp &&
-       bb_reachable_by(bf, bp->out[1], bt))
-      return TRUE;
-   return FALSE;
-}
-
 /* The live set of a block contains those values that are live immediately
  * before the beginning of the block.
  */
@@ -918,12 +918,6 @@ pass_linear_scan(struct nv_pc_pass *ctx, int iter)
    return 0;
 }
 
-static int
-pass_eliminate_moves(struct nv_pc_pass *ctx)
-{
-   return 0;
-}
-
 int
 nv_pc_exec_pass1(struct nv_pc *pc)
 {
@@ -971,6 +965,11 @@ nv_pc_exec_pass1(struct nv_pc *pc)
       goto out;
    }
 
+#ifdef NV50_RA_DEBUG_LIVEI
+   for (i = 0; i < pc->num_values; ++i)
+      livei_print(&pc->values[i]);
+#endif
+
    for (i = 0; i < 2; ++i) {
       ret = pass_join_values(ctx, i);
       if (ret)
@@ -981,8 +980,6 @@ nv_pc_exec_pass1(struct nv_pc *pc)
    }
    assert(!ret && "joining");
 
-   ret = pass_eliminate_moves(ctx);
-
    for (i = 0; i < pc->num_values; ++i)
       livei_release(&pc->values[i]);
 




More information about the mesa-commit mailing list