Mesa (master): st/vega: Avoid unnecessary constant bufer upload.

Chia-I Wu olv at kemper.freedesktop.org
Wed Dec 1 12:22:40 UTC 2010


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

Author: Chia-I Wu <olv at lunarg.com>
Date:   Wed Dec  1 18:23:53 2010 +0800

st/vega: Avoid unnecessary constant bufer upload.

Remember the last uploaded data and avoid re-uploading.

---

 src/gallium/state_trackers/vega/renderer.c |   78 +++++++++++++++++-----------
 1 files changed, 48 insertions(+), 30 deletions(-)

diff --git a/src/gallium/state_trackers/vega/renderer.c b/src/gallium/state_trackers/vega/renderer.c
index 7d0ff32..9e0d5a3 100644
--- a/src/gallium/state_trackers/vega/renderer.c
+++ b/src/gallium/state_trackers/vega/renderer.c
@@ -83,7 +83,12 @@ struct renderer {
       struct pipe_framebuffer_state fb;
    } g3d;
 
-   struct pipe_resource *vs_const_buffer;
+   struct pipe_resource *vs_cbuf;;
+   VGfloat vs_cbuf_data[8];
+
+   struct pipe_resource *fs_cbuf;
+   VGfloat fs_cbuf_data[32];
+   VGint fs_cbuf_len;
 
    struct pipe_vertex_element velems[2];
    VGfloat vertices[4][2][4];
@@ -414,17 +419,28 @@ static void renderer_set_custom_fs(struct renderer *renderer,
 
    /* upload fs constant buffer */
    if (const_buffer_len) {
-      struct pipe_resource *cbuf;
-
-      cbuf = pipe_buffer_create(renderer->pipe->screen,
-            PIPE_BIND_CONSTANT_BUFFER, const_buffer_len);
-      pipe_buffer_write(renderer->pipe, cbuf, 0,
-            const_buffer_len, const_buffer);
-      renderer->pipe->set_constant_buffer(renderer->pipe,
-            PIPE_SHADER_FRAGMENT, 0, cbuf);
-
-      /* destroy cbuf automatically */
-      pipe_resource_reference(&cbuf, NULL);
+      struct pipe_resource *cbuf = renderer->fs_cbuf;
+
+      if (!cbuf || renderer->fs_cbuf_len != const_buffer_len ||
+          memcmp(renderer->fs_cbuf_data, const_buffer, const_buffer_len)) {
+         pipe_resource_reference(&cbuf, NULL);
+
+         cbuf = pipe_buffer_create(renderer->pipe->screen,
+               PIPE_BIND_CONSTANT_BUFFER, const_buffer_len);
+         pipe_buffer_write(renderer->pipe, cbuf, 0,
+               const_buffer_len, const_buffer);
+         renderer->pipe->set_constant_buffer(renderer->pipe,
+               PIPE_SHADER_FRAGMENT, 0, cbuf);
+
+         renderer->fs_cbuf = cbuf;
+         if (const_buffer_len <= sizeof(renderer->fs_cbuf_data)) {
+            memcpy(renderer->fs_cbuf_data, const_buffer, const_buffer_len);
+            renderer->fs_cbuf_len = const_buffer_len;
+         }
+         else {
+            renderer->fs_cbuf_len = 0;
+         }
+      }
    }
 }
 
@@ -1137,14 +1153,9 @@ void renderer_destroy(struct renderer *ctx)
          cso_delete_fragment_shader(ctx->cso, ctx->cached_fs[i]);
    }
 
-   pipe_resource_reference(&ctx->vs_const_buffer, NULL);
+   pipe_resource_reference(&ctx->vs_cbuf, NULL);
+   pipe_resource_reference(&ctx->fs_cbuf, NULL);
 
-#if 0
-   if (ctx->fs) {
-      cso_delete_fragment_shader(ctx->cso, ctx->fs);
-      ctx->fs = NULL;
-   }
-#endif
    FREE(ctx);
 }
 
@@ -1273,7 +1284,7 @@ void renderer_validate(struct renderer *renderer,
 
    if (dirty & FRAMEBUFFER_DIRTY) {
       struct pipe_framebuffer_state *fb = &renderer->g3d.fb;
-      struct pipe_resource **cbuf = &renderer->vs_const_buffer;
+      struct pipe_resource *cbuf;
       VGfloat vs_consts[8];
 
       memset(fb, 0, sizeof(struct pipe_framebuffer_state));
@@ -1296,17 +1307,24 @@ void renderer_validate(struct renderer *renderer,
       vs_consts[6] = 0.0f;
       vs_consts[7] = 0.0f;
 
-      pipe_resource_reference(cbuf, NULL);
-      *cbuf = pipe_buffer_create(renderer->pipe->screen, 
-				 PIPE_BIND_CONSTANT_BUFFER,
-				 sizeof(vs_consts));
-
-      if (*cbuf) {
-         pipe_buffer_write(renderer->pipe,
-               *cbuf, 0, sizeof(vs_consts), vs_consts);
+      /* upload if needed */
+      cbuf = renderer->vs_cbuf;
+      if (!cbuf ||
+          memcmp(renderer->vs_cbuf_data, vs_consts, sizeof(vs_consts)) != 0) {
+         pipe_resource_reference(&cbuf, NULL);
+         cbuf = pipe_buffer_create(renderer->pipe->screen,
+                                   PIPE_BIND_CONSTANT_BUFFER,
+                                   sizeof(vs_consts));
+         if (cbuf) {
+            pipe_buffer_write(renderer->pipe, cbuf, 0,
+                  sizeof(vs_consts), vs_consts);
+         }
+         renderer->pipe->set_constant_buffer(renderer->pipe,
+               PIPE_SHADER_VERTEX, 0, cbuf);
+
+         renderer->vs_cbuf = cbuf;
+         memcpy(renderer->vs_cbuf_data, vs_consts, sizeof(vs_consts));
       }
-      renderer->pipe->set_constant_buffer(renderer->pipe,
-            PIPE_SHADER_VERTEX, 0, *cbuf);
 
       /* we also got a new depth buffer */
       if (dirty & DEPTH_STENCIL_DIRTY) {




More information about the mesa-commit mailing list