i965/fs: Split "find what MRFs were used" to a helper function.
authorEric Anholt <eric@anholt.net>
Tue, 29 Oct 2013 19:18:10 +0000 (12:18 -0700)
committerEric Anholt <eric@anholt.net>
Thu, 31 Oct 2013 00:50:56 +0000 (17:50 -0700)
I'm going to need to reuse this for fixing register spilling on SIMD16.
Note that BRW_MAX_MRF is 16, which is the same as BRW_MAX_GRF -
GEN7_MRF_HACK_START.

Reviewed-by: Paul Berry <stereotype441@gmail.com>
src/mesa/drivers/dri/i965/brw_fs.h
src/mesa/drivers/dri/i965/brw_fs_reg_allocate.cpp

index 5f331e17a58108749859858aec89494d1dcf4523..50a045e4b4ba4d443db96a906e4c803cda9fbe9f 100644 (file)
@@ -289,6 +289,7 @@ public:
    void assign_urb_setup();
    bool assign_regs();
    void assign_regs_trivial();
+   void get_used_mrfs(bool *mrf_used);
    void setup_payload_interference(struct ra_graph *g, int payload_reg_count,
                                    int first_payload_node);
    void setup_mrf_hack_interference(struct ra_graph *g,
index 157c9ae4ffa91c1160a62a6b1f149e4f798e025d..0b00b91694bfe53ff2e075f133d5b0a51eaa0585 100644 (file)
@@ -347,18 +347,20 @@ fs_visitor::setup_payload_interference(struct ra_graph *g,
 }
 
 /**
- * Sets interference between virtual GRFs and usage of the high GRFs for SEND
- * messages (treated as MRFs in code generation).
+ * Sets the mrf_used array to indicate which MRFs are used by the shader IR
+ *
+ * This is used in assign_regs() to decide which of the GRFs that we use as
+ * MRFs on gen7 get normally register allocated, and in register spilling to
+ * see if we can actually use MRFs to do spills without overwriting normal MRF
+ * contents.
  */
 void
-fs_visitor::setup_mrf_hack_interference(struct ra_graph *g, int first_mrf_node)
+fs_visitor::get_used_mrfs(bool *mrf_used)
 {
-   int mrf_count = BRW_MAX_GRF - GEN7_MRF_HACK_START;
    int reg_width = dispatch_width / 8;
 
-   /* Identify all the MRFs used in the program. */
-   bool mrf_used[mrf_count];
-   memset(mrf_used, 0, sizeof(mrf_used));
+   memset(mrf_used, 0, BRW_MAX_MRF * sizeof(bool));
+
    foreach_list(node, &this->instructions) {
       fs_inst *inst = (fs_inst *)node;
 
@@ -380,9 +382,22 @@ fs_visitor::setup_mrf_hack_interference(struct ra_graph *g, int first_mrf_node)
          }
       }
    }
+}
+
+/**
+ * Sets interference between virtual GRFs and usage of the high GRFs for SEND
+ * messages (treated as MRFs in code generation).
+ */
+void
+fs_visitor::setup_mrf_hack_interference(struct ra_graph *g, int first_mrf_node)
+{
+   int reg_width = dispatch_width / 8;
+
+   bool mrf_used[BRW_MAX_MRF];
+   get_used_mrfs(mrf_used);
 
-   for (int i = 0; i < mrf_count; i++) {
-      /* Mark each payload reg node as being allocated to its physical register.
+   for (int i = 0; i < BRW_MAX_MRF; i++) {
+      /* Mark each MRF reg node as being allocated to its physical register.
        *
        * The alternative would be to have per-physical-register classes, which
        * would just be silly.