Mesa (master): glsl/linker: Free any IR discarded by optimization passes.

Kenneth Graunke kwg at kemper.freedesktop.org
Tue Nov 30 21:50:38 UTC 2010


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

Author: Kenneth Graunke <kenneth at whitecape.org>
Date:   Wed Nov 17 11:03:57 2010 -0800

glsl/linker: Free any IR discarded by optimization passes.

Previously, IR for a linked shader was allocated directly out of the
gl_shader object - meaning all of it lived as long as the shader.

Now, IR is allocated out of a temporary context, and any -live- IR is
reparented/stolen to (effectively) the gl_shader.  Any remaining IR can
be freed.

NOTE: This is a candidate for the 7.9 branch.

---

 src/glsl/linker.cpp |   23 +++++++++++++++++++----
 1 files changed, 19 insertions(+), 4 deletions(-)

diff --git a/src/glsl/linker.cpp b/src/glsl/linker.cpp
index 8d14c5a..cde70ad 100644
--- a/src/glsl/linker.cpp
+++ b/src/glsl/linker.cpp
@@ -726,7 +726,8 @@ get_main_function_signature(gl_shader *sh)
  * shader is returned.
  */
 static struct gl_shader *
-link_intrastage_shaders(struct gl_context *ctx,
+link_intrastage_shaders(void *mem_ctx,
+			struct gl_context *ctx,
 			struct gl_shader_program *prog,
 			struct gl_shader **shader_list,
 			unsigned num_shaders)
@@ -802,7 +803,7 @@ link_intrastage_shaders(struct gl_context *ctx,
 
    gl_shader *linked = ctx->Driver.NewShader(NULL, 0, main->Type);
    linked->ir = new(linked) exec_list;
-   clone_ir_list(linked, linked->ir, main->ir);
+   clone_ir_list(mem_ctx, linked->ir, main->ir);
 
    populate_symbol_table(linked);
 
@@ -1407,6 +1408,8 @@ assign_varying_locations(struct gl_shader_program *prog,
 void
 link_shaders(struct gl_context *ctx, struct gl_shader_program *prog)
 {
+   void *mem_ctx = talloc_init("temporary linker context");
+
    prog->LinkStatus = false;
    prog->Validated = false;
    prog->_Used = false;
@@ -1475,7 +1478,8 @@ link_shaders(struct gl_context *ctx, struct gl_shader_program *prog)
     */
    if (num_vert_shaders > 0) {
       gl_shader *const sh =
-	 link_intrastage_shaders(ctx, prog, vert_shader_list, num_vert_shaders);
+	 link_intrastage_shaders(mem_ctx, ctx, prog, vert_shader_list,
+				 num_vert_shaders);
 
       if (sh == NULL)
 	 goto done;
@@ -1489,7 +1493,8 @@ link_shaders(struct gl_context *ctx, struct gl_shader_program *prog)
 
    if (num_frag_shaders > 0) {
       gl_shader *const sh =
-	 link_intrastage_shaders(ctx, prog, frag_shader_list, num_frag_shaders);
+	 link_intrastage_shaders(mem_ctx, ctx, prog, frag_shader_list,
+				 num_frag_shaders);
 
       if (sh == NULL)
 	 goto done;
@@ -1598,4 +1603,14 @@ link_shaders(struct gl_context *ctx, struct gl_shader_program *prog)
 
 done:
    free(vert_shader_list);
+
+   for (unsigned i = 0; i < MESA_SHADER_TYPES; i++) {
+      if (prog->_LinkedShaders[i] == NULL)
+	 continue;
+
+      /* Retain any live IR, but trash the rest. */
+      reparent_ir(prog->_LinkedShaders[i]->ir, prog->_LinkedShaders[i]->ir);
+   }
+
+   talloc_free(mem_ctx);
 }




More information about the mesa-commit mailing list