[virglrenderer-devel] [PATCH 1/3] gallium: Add changes needed for TGSI_FILE_HW_ATOMIC

Tomeu Vizoso tomeu.vizoso at collabora.com
Thu Jul 19 13:41:40 UTC 2018


Signed-off-by: Tomeu Vizoso <tomeu.vizoso at collabora.com>
---
 src/gallium/auxiliary/tgsi/tgsi_strings.c  |  1 +
 src/gallium/auxiliary/tgsi/tgsi_ureg.c     | 82 +++++++++++++++++++++-
 src/gallium/auxiliary/tgsi/tgsi_ureg.h     |  7 ++
 src/gallium/include/pipe/p_shader_tokens.h |  1 +
 src/gallium/include/pipe/p_state.h         |  1 +
 5 files changed, 91 insertions(+), 1 deletion(-)

diff --git a/src/gallium/auxiliary/tgsi/tgsi_strings.c b/src/gallium/auxiliary/tgsi/tgsi_strings.c
index ce51306db75f..6e8001150ded 100644
--- a/src/gallium/auxiliary/tgsi/tgsi_strings.c
+++ b/src/gallium/auxiliary/tgsi/tgsi_strings.c
@@ -58,6 +58,7 @@ static const char *tgsi_file_names[] =
    "SVIEW",
    "BUFFER",
    "MEMORY",
+   "HWATOMIC",
 };
 
 const char *tgsi_semantic_names[TGSI_SEMANTIC_COUNT] =
diff --git a/src/gallium/auxiliary/tgsi/tgsi_ureg.c b/src/gallium/auxiliary/tgsi/tgsi_ureg.c
index b4423d4264ec..8a90005b00a1 100644
--- a/src/gallium/auxiliary/tgsi/tgsi_ureg.c
+++ b/src/gallium/auxiliary/tgsi/tgsi_ureg.c
@@ -76,6 +76,7 @@ struct ureg_tokens {
 #define UREG_MAX_SYSTEM_VALUE PIPE_MAX_ATTRIBS
 #define UREG_MAX_OUTPUT PIPE_MAX_SHADER_OUTPUTS
 #define UREG_MAX_CONSTANT_RANGE 32
+#define UREG_MAX_HW_ATOMIC_RANGE 32
 #define UREG_MAX_IMMEDIATE 4096
 #define UREG_MAX_ADDR 3
 #define UREG_MAX_PRED 1
@@ -89,6 +90,15 @@ struct const_decl {
    unsigned nr_constant_ranges;
 };
 
+struct hw_atomic_decl {
+   struct {
+      unsigned first;
+      unsigned last;
+      unsigned array_id;
+   } hw_atomic_range[UREG_MAX_HW_ATOMIC_RANGE];
+   unsigned nr_hw_atomic_ranges;
+};
+
 #define DOMAIN_DECL 0
 #define DOMAIN_INSN 1
 
@@ -164,6 +174,8 @@ struct ureg_program
    struct const_decl const_decls;
    struct const_decl const_decls2D[PIPE_MAX_CONSTANT_BUFFERS];
 
+   struct hw_atomic_decl hw_atomic_decls[PIPE_MAX_HW_ATOMIC_BUFFERS];
+
    unsigned properties[TGSI_PROPERTY_COUNT];
 
    unsigned nr_addrs;
@@ -490,6 +502,30 @@ out:
    return ureg_src_register(TGSI_FILE_CONSTANT, index);
 }
 
+
+/* Returns a new hw atomic register.  Keep track of which have been
+ * referred to so that we can emit decls later.
+ */
+void
+ureg_DECL_hw_atomic(struct ureg_program *ureg,
+                    unsigned first,
+                    unsigned last,
+                    unsigned buffer_id,
+                    unsigned array_id)
+{
+   struct hw_atomic_decl *decl = &ureg->hw_atomic_decls[buffer_id];
+
+   if (decl->nr_hw_atomic_ranges < UREG_MAX_HW_ATOMIC_RANGE) {
+      uint i = decl->nr_hw_atomic_ranges++;
+
+      decl->hw_atomic_range[i].first = first;
+      decl->hw_atomic_range[i].last = last;
+      decl->hw_atomic_range[i].array_id = array_id;
+   } else {
+      set_bad(ureg);
+   }
+}
+
 static struct ureg_dst alloc_temporary( struct ureg_program *ureg,
                                         boolean local )
 {
@@ -1326,6 +1362,35 @@ emit_property(struct ureg_program *ureg,
    out[1].prop_data.Data = data;
 }
 
+static void
+emit_decl_atomic_2d(struct ureg_program *ureg,
+                    unsigned first,
+                    unsigned last,
+                    unsigned index2D,
+                    unsigned array_id)
+{
+   union tgsi_any_token *out = get_tokens(ureg, DOMAIN_DECL, array_id ? 4 : 3);
+
+   out[0].value = 0;
+   out[0].decl.Type = TGSI_TOKEN_TYPE_DECLARATION;
+   out[0].decl.NrTokens = 3;
+   out[0].decl.File = TGSI_FILE_HW_ATOMIC;
+   out[0].decl.UsageMask = TGSI_WRITEMASK_XYZW;
+   out[0].decl.Dimension = 1;
+   out[0].decl.Array = array_id != 0;
+
+   out[1].value = 0;
+   out[1].decl_range.First = first;
+   out[1].decl_range.Last = last;
+
+   out[2].value = 0;
+   out[2].decl_dim.Index2D = index2D;
+
+   if (array_id) {
+      out[3].value = 0;
+      out[3].array.ArrayID = array_id;
+   }
+}
 
 static void emit_decls( struct ureg_program *ureg )
 {
@@ -1422,6 +1487,22 @@ static void emit_decls( struct ureg_program *ureg )
       }
    }
 
+   for (i = 0; i < PIPE_MAX_HW_ATOMIC_BUFFERS; i++) {
+      struct hw_atomic_decl *decl = &ureg->hw_atomic_decls[i];
+
+      if (decl->nr_hw_atomic_ranges) {
+         uint j;
+
+         for (j = 0; j < decl->nr_hw_atomic_ranges; j++) {
+            emit_decl_atomic_2d(ureg,
+                                decl->hw_atomic_range[j].first,
+                                decl->hw_atomic_range[j].last,
+                                i,
+                                decl->hw_atomic_range[j].array_id);
+         }
+      }
+   }
+
    if (ureg->nr_temps) {
       unsigned array = 0;
       for (i = 0; i < ureg->nr_temps;) {
@@ -1473,7 +1554,6 @@ static void copy_instructions( struct ureg_program *ureg )
           nr_tokens * sizeof out[0] );
 }
 
-
 static void
 fixup_header_size(struct ureg_program *ureg)
 {
diff --git a/src/gallium/auxiliary/tgsi/tgsi_ureg.h b/src/gallium/auxiliary/tgsi/tgsi_ureg.h
index 441a770fffd5..e62b0efc9f5c 100644
--- a/src/gallium/auxiliary/tgsi/tgsi_ureg.h
+++ b/src/gallium/auxiliary/tgsi/tgsi_ureg.h
@@ -253,6 +253,13 @@ struct ureg_src
 ureg_DECL_constant( struct ureg_program *,
                     unsigned index );
 
+void
+ureg_DECL_hw_atomic(struct ureg_program *ureg,
+                    unsigned first,
+                    unsigned last,
+                    unsigned buffer_id,
+                    unsigned array_id);
+
 struct ureg_dst
 ureg_DECL_temporary( struct ureg_program * );
 
diff --git a/src/gallium/include/pipe/p_shader_tokens.h b/src/gallium/include/pipe/p_shader_tokens.h
index ff723e04e74e..cf30b08b099a 100644
--- a/src/gallium/include/pipe/p_shader_tokens.h
+++ b/src/gallium/include/pipe/p_shader_tokens.h
@@ -80,6 +80,7 @@ enum tgsi_file_type {
    TGSI_FILE_SAMPLER_VIEW        =11,
    TGSI_FILE_BUFFER,
    TGSI_FILE_MEMORY,
+   TGSI_FILE_HW_ATOMIC,
    TGSI_FILE_COUNT      /**< how many TGSI_FILE_ types */
 };
 
diff --git a/src/gallium/include/pipe/p_state.h b/src/gallium/include/pipe/p_state.h
index c910fce3926d..9a6da2ff5d7f 100644
--- a/src/gallium/include/pipe/p_state.h
+++ b/src/gallium/include/pipe/p_state.h
@@ -76,6 +76,7 @@ struct pipe_reference
    int32_t count; /* atomic */
 };
 
+#define PIPE_MAX_HW_ATOMIC_BUFFERS 32
 
 
 /**
-- 
2.17.1



More information about the virglrenderer-devel mailing list