Mesa (main): glsl: move gl_nir_link_opts() call out of the st code

GitLab Mirror gitlab-mirror at kemper.freedesktop.org
Sat Jun 4 03:57:01 UTC 2022


Module: Mesa
Branch: main
Commit: 1805ee8d7b02fa2ca0511b2158d3000c79496340
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=1805ee8d7b02fa2ca0511b2158d3000c79496340

Author: Timothy Arceri <tarceri at itsqueeze.com>
Date:   Tue May 31 09:55:02 2022 +1000

glsl: move gl_nir_link_opts() call out of the st code

Calling this directly in the linker code allows us to place it between
the varying linker and uniform linker calls which allows for better
optimisation/removal of uniforms.

Also in a later patch it allows us to insert a new nir based
lower_const_arrays_to_uniforms() call after the gl_nir_link_opts()
call. This is important because it allows the linking opts to
move constant arrays to later stages if possible before
lower_const_arrays_to_uniforms() turns them into uniforms.

Closes: https://gitlab.freedesktop.org/mesa/mesa/-/issues/6541

Acked-by: Emma Anholt <emma at anholt.net>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/16770>

---

 src/compiler/glsl/gl_nir_linker.c         | 48 ++++++++++++++++++++++++++++++-
 src/compiler/glsl/gl_nir_linker.h         |  2 --
 src/mesa/state_tracker/st_glsl_to_nir.cpp | 27 -----------------
 3 files changed, 47 insertions(+), 30 deletions(-)

diff --git a/src/compiler/glsl/gl_nir_linker.c b/src/compiler/glsl/gl_nir_linker.c
index 6b26b9c1042..e0b36a224d1 100644
--- a/src/compiler/glsl/gl_nir_linker.c
+++ b/src/compiler/glsl/gl_nir_linker.c
@@ -117,7 +117,7 @@ gl_nir_opts(nir_shader *nir)
    } while (progress);
 }
 
-void
+static void
 gl_nir_link_opts(nir_shader *producer, nir_shader *consumer)
 {
    if (producer->options->lower_to_scalar) {
@@ -756,6 +756,24 @@ gl_nir_link_spirv(const struct gl_constants *consts,
                   struct gl_shader_program *prog,
                   const struct gl_nir_linker_options *options)
 {
+   struct gl_linked_shader *linked_shader[MESA_SHADER_STAGES];
+   unsigned num_shaders = 0;
+
+   for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
+      if (prog->_LinkedShaders[i])
+         linked_shader[num_shaders++] = prog->_LinkedShaders[i];
+   }
+
+   /* Linking the stages in the opposite order (from fragment to vertex)
+    * ensures that inter-shader outputs written to in an earlier stage
+    * are eliminated if they are (transitively) not used in a later
+    * stage.
+    */
+   for (int i = num_shaders - 2; i >= 0; i--) {
+      gl_nir_link_opts(linked_shader[i]->Program->nir,
+                       linked_shader[i + 1]->Program->nir);
+   }
+
    for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
       struct gl_linked_shader *shader = prog->_LinkedShaders[i];
       if (shader) {
@@ -919,6 +937,34 @@ gl_nir_link_glsl(const struct gl_constants *consts,
          return false;
    }
 
+   if (prog->data->LinkStatus == LINKING_FAILURE)
+      return false;
+
+   struct gl_linked_shader *linked_shader[MESA_SHADER_STAGES];
+   unsigned num_shaders = 0;
+
+   for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
+      if (prog->_LinkedShaders[i])
+         linked_shader[num_shaders++] = prog->_LinkedShaders[i];
+   }
+
+   /* Linking the stages in the opposite order (from fragment to vertex)
+    * ensures that inter-shader outputs written to in an earlier stage
+    * are eliminated if they are (transitively) not used in a later
+    * stage.
+    */
+   for (int i = num_shaders - 2; i >= 0; i--) {
+      gl_nir_link_opts(linked_shader[i]->Program->nir,
+                       linked_shader[i + 1]->Program->nir);
+   }
+
+   /* Tidy up any left overs from the linking process for single shaders.
+    * For example varying arrays that get packed may have dead elements that
+    * can be now be eliminated now that array access has been lowered.
+    */
+   if (num_shaders == 1)
+      gl_nir_opts(linked_shader[0]->Program->nir);
+
    for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
       struct gl_linked_shader *shader = prog->_LinkedShaders[i];
       if (shader) {
diff --git a/src/compiler/glsl/gl_nir_linker.h b/src/compiler/glsl/gl_nir_linker.h
index 892f4d7660b..4454c110f6d 100644
--- a/src/compiler/glsl/gl_nir_linker.h
+++ b/src/compiler/glsl/gl_nir_linker.h
@@ -54,8 +54,6 @@ struct gl_nir_linker_options {
 
 void gl_nir_opts(nir_shader *nir);
 
-void gl_nir_link_opts(nir_shader *producer, nir_shader *consumer);
-
 bool gl_nir_link_spirv(const struct gl_constants *consts,
                        struct gl_shader_program *prog,
                        const struct gl_nir_linker_options *options);
diff --git a/src/mesa/state_tracker/st_glsl_to_nir.cpp b/src/mesa/state_tracker/st_glsl_to_nir.cpp
index 23c6e8f88a5..fa5bfc31f86 100644
--- a/src/mesa/state_tracker/st_glsl_to_nir.cpp
+++ b/src/mesa/state_tracker/st_glsl_to_nir.cpp
@@ -712,16 +712,6 @@ st_link_nir(struct gl_context *ctx,
       gl_nir_opts(linked_shader[0]->Program->nir);
 
    if (shader_program->data->spirv) {
-      /* Linking the stages in the opposite order (from fragment to vertex)
-       * ensures that inter-shader outputs written to in an earlier stage
-       * are eliminated if they are (transitively) not used in a later
-       * stage.
-       */
-      for (int i = num_shaders - 2; i >= 0; i--) {
-         gl_nir_link_opts(linked_shader[i]->Program->nir,
-                          linked_shader[i + 1]->Program->nir);
-      }
-
       static const gl_nir_linker_options opts = {
          true /*fill_parameters */
       };
@@ -731,23 +721,6 @@ st_link_nir(struct gl_context *ctx,
       if (!gl_nir_link_glsl(&ctx->Const, &ctx->Extensions, ctx->API,
                             shader_program))
          return GL_FALSE;
-
-      /* Linking the stages in the opposite order (from fragment to vertex)
-       * ensures that inter-shader outputs written to in an earlier stage
-       * are eliminated if they are (transitively) not used in a later
-       * stage.
-       */
-      for (int i = num_shaders - 2; i >= 0; i--) {
-         gl_nir_link_opts(linked_shader[i]->Program->nir,
-                          linked_shader[i + 1]->Program->nir);
-      }
-
-      /* Tidy up any left overs from the linking process for single shaders.
-       * For example varying arrays that get packed may have dead elements that
-       * can be now be eliminated now that array access has been lowered.
-       */
-      if (num_shaders == 1)
-         gl_nir_opts(linked_shader[0]->Program->nir);
    }
 
    for (unsigned i = 0; i < num_shaders; i++) {



More information about the mesa-commit mailing list