Convert shader to an immutable state object.
authorZack Rusin <zack@tungstengraphics.com>
Tue, 18 Sep 2007 17:24:44 +0000 (13:24 -0400)
committerZack Rusin <zack@tungstengraphics.com>
Tue, 18 Sep 2007 17:24:44 +0000 (13:24 -0400)
27 files changed:
src/mesa/pipe/cso_cache/cso_cache.c
src/mesa/pipe/cso_cache/cso_cache.h
src/mesa/pipe/failover/fo_context.h
src/mesa/pipe/failover/fo_state.c
src/mesa/pipe/failover/fo_state_emit.c
src/mesa/pipe/i915simple/i915_context.h
src/mesa/pipe/i915simple/i915_fpc.h
src/mesa/pipe/i915simple/i915_fpc_translate.c
src/mesa/pipe/i915simple/i915_state.c
src/mesa/pipe/i915simple/i915_state_derived.c
src/mesa/pipe/p_context.h
src/mesa/pipe/softpipe/sp_context.c
src/mesa/pipe/softpipe/sp_context.h
src/mesa/pipe/softpipe/sp_quad_fs.c
src/mesa/pipe/softpipe/sp_state.h
src/mesa/pipe/softpipe/sp_state_derived.c
src/mesa/pipe/softpipe/sp_state_fs.c
src/mesa/state_tracker/st_atom_fs.c
src/mesa/state_tracker/st_atom_vs.c
src/mesa/state_tracker/st_cache.c
src/mesa/state_tracker/st_cache.h
src/mesa/state_tracker/st_cb_clear.c
src/mesa/state_tracker/st_cb_drawpixels.c
src/mesa/state_tracker/st_cb_rasterpos.c
src/mesa/state_tracker/st_context.h
src/mesa/state_tracker/st_draw.c
src/mesa/state_tracker/st_program.h

index 4aaadf0..be653d9 100644 (file)
@@ -80,6 +80,8 @@ static struct cso_hash *_cso_hash_for_type(struct cso_cache *sc, enum cso_cache_
       hash = sc->depth_stencil_hash;
    case CSO_RASTERIZER:
       hash = sc->rasterizer_hash;
+   case CSO_SHADER:
+      hash = sc->shader_hash;
    }
 
    return hash;
@@ -96,6 +98,8 @@ static int _cso_size_for_type(enum cso_cache_type type)
       return sizeof(struct pipe_depth_stencil_state);
    case CSO_RASTERIZER:
       return sizeof(struct pipe_rasterizer_state);
+   case CSO_SHADER:
+      return sizeof(struct pipe_shader_state);
    }
    return 0;
 }
@@ -144,10 +148,11 @@ struct cso_cache *cso_cache_create(void)
 {
    struct cso_cache *sc = malloc(sizeof(struct cso_cache));
 
-   sc->blend_hash = cso_hash_create();
-   sc->sampler_hash = cso_hash_create();
+   sc->blend_hash         = cso_hash_create();
+   sc->sampler_hash       = cso_hash_create();
    sc->depth_stencil_hash = cso_hash_create();
-   sc->rasterizer_hash = cso_hash_create();
+   sc->rasterizer_hash    = cso_hash_create();
+   sc->shader_hash        = cso_hash_create();
 
    return sc;
 }
@@ -159,6 +164,6 @@ void cso_cache_delete(struct cso_cache *sc)
    cso_hash_delete(sc->sampler_hash);
    cso_hash_delete(sc->depth_stencil_hash);
    cso_hash_delete(sc->rasterizer_hash);
+   cso_hash_delete(sc->shader_hash);
    free(sc);
 }
-
index 23be9cd..d9793ca 100644 (file)
@@ -44,13 +44,15 @@ struct cso_cache {
    struct cso_hash *sampler_hash;
    struct cso_hash *depth_stencil_hash;
    struct cso_hash *rasterizer_hash;
+   struct cso_hash *shader_hash;
 };
 
 enum cso_cache_type {
    CSO_BLEND,
    CSO_SAMPLER,
    CSO_DEPTH_STENCIL,
-   CSO_RASTERIZER
+   CSO_RASTERIZER,
+   CSO_SHADER
 };
 
 unsigned cso_construct_key(void *item, int item_size);
index b05ceb8..9556a17 100644 (file)
@@ -70,14 +70,14 @@ struct failover_context {
    const struct pipe_sampler_state       *sampler[PIPE_MAX_SAMPLERS];
    const struct pipe_depth_stencil_state *depth_stencil;
    const struct pipe_rasterizer_state    *rasterizer;
+   const struct pipe_shader_state        *fragment_shader;
+   const struct pipe_shader_state        *vertex_shader;
 
    struct pipe_alpha_test_state alpha_test;
    struct pipe_blend_color blend_color;
    struct pipe_clear_color_state clear_color;
    struct pipe_clip_state clip;
    struct pipe_framebuffer_state framebuffer;
-   struct pipe_shader_state fragment_shader;
-   struct pipe_shader_state vertex_shader;
    struct pipe_poly_stipple poly_stipple;
    struct pipe_scissor_state scissor;
    struct pipe_mipmap_tree *texture[PIPE_MAX_SAMPLERS];
index 8e2b649..04ebd33 100644 (file)
@@ -125,28 +125,27 @@ failover_set_framebuffer_state(struct pipe_context *pipe,
 }
 
 static void
-failover_set_fs_state(struct pipe_context *pipe,
-                     const struct pipe_shader_state *fs)
+failover_bind_fs_state(struct pipe_context *pipe,
+                       const struct pipe_shader_state *fs)
 {
    struct failover_context *failover = failover_context(pipe);
 
-   failover->fragment_shader = *fs;
+   failover->fragment_shader = fs;
    failover->dirty |= FO_NEW_FRAGMENT_SHADER;
-   failover->hw->set_fs_state( failover->hw, fs );
+   failover->hw->bind_fs_state( failover->hw, fs );
 }
 
 static void
-failover_set_vs_state(struct pipe_context *pipe,
+failover_bind_vs_state(struct pipe_context *pipe,
                      const struct pipe_shader_state *vs)
 {
    struct failover_context *failover = failover_context(pipe);
 
-   failover->vertex_shader = *vs;
+   failover->vertex_shader = vs;
    failover->dirty |= FO_NEW_VERTEX_SHADER;
-   failover->hw->set_vs_state( failover->hw, vs );
+   failover->hw->bind_vs_state( failover->hw, vs );
 }
 
-
 static void 
 failover_set_polygon_stipple( struct pipe_context *pipe,
                              const struct pipe_poly_stipple *stipple )
@@ -258,14 +257,14 @@ failover_init_state_functions( struct failover_context *failover )
    failover->pipe.bind_sampler_state = failover_bind_sampler_state;
    failover->pipe.bind_depth_stencil_state = failover_bind_depth_stencil_state;
    failover->pipe.bind_rasterizer_state = failover_bind_rasterizer_state;
+   failover->pipe.bind_fs_state = failover_bind_fs_state;
+   failover->pipe.bind_vs_state = failover_bind_vs_state;
 
    failover->pipe.set_alpha_test_state = failover_set_alpha_test_state;
    failover->pipe.set_blend_color = failover_set_blend_color;
    failover->pipe.set_clip_state = failover_set_clip_state;
    failover->pipe.set_clear_color_state = failover_set_clear_color_state;
    failover->pipe.set_framebuffer_state = failover_set_framebuffer_state;
-   failover->pipe.set_fs_state = failover_set_fs_state;
-   failover->pipe.set_vs_state = failover_set_vs_state;
    failover->pipe.set_polygon_stipple = failover_set_polygon_stipple;
    failover->pipe.set_scissor_state = failover_set_scissor_state;
    failover->pipe.set_texture_state = failover_set_texture_state;
index 1c9573a..9d30407 100644 (file)
@@ -77,10 +77,10 @@ failover_state_emit( struct failover_context *failover )
       failover->sw->set_framebuffer_state( failover->sw, &failover->framebuffer );
 
    if (failover->dirty & FO_NEW_FRAGMENT_SHADER)
-      failover->sw->set_fs_state( failover->sw, &failover->fragment_shader );
+      failover->sw->bind_fs_state( failover->sw, failover->fragment_shader );
 
    if (failover->dirty & FO_NEW_VERTEX_SHADER)
-      failover->sw->set_vs_state( failover->sw, &failover->vertex_shader );
+      failover->sw->bind_vs_state( failover->sw, failover->vertex_shader );
 
    if (failover->dirty & FO_NEW_STIPPLE)
       failover->sw->set_polygon_stipple( failover->sw, &failover->poly_stipple );
index 3fab821..9052c92 100644 (file)
@@ -127,6 +127,7 @@ struct i915_context
    const struct pipe_sampler_state *sampler[PIPE_MAX_SAMPLERS];
    const struct pipe_depth_stencil_state   *depth_stencil;
    const struct pipe_rasterizer_state *rasterizer;
+   const struct pipe_shader_state *fs;
 
    struct pipe_alpha_test_state alpha_test;
    struct pipe_blend_color blend_color;
@@ -134,7 +135,6 @@ struct i915_context
    struct pipe_clip_state clip;
    struct pipe_constant_buffer constants[PIPE_SHADER_TYPES];
    struct pipe_framebuffer_state framebuffer;
-   struct pipe_shader_state fs;
    struct pipe_poly_stipple poly_stipple;
    struct pipe_scissor_state scissor;
    struct pipe_mipmap_tree *texture[PIPE_MAX_SAMPLERS];
index 59fcbf4..84e4c5a 100644 (file)
@@ -44,7 +44,7 @@
  * Program translation state
  */
 struct i915_fp_compile {
-   struct pipe_shader_state *shader;
+   const struct pipe_shader_state *shader;
 
    struct vertex_info *vertex_info;
 
index c2ad80c..32c5600 100644 (file)
@@ -872,11 +872,11 @@ i915_translate_instructions(struct i915_fp_compile *p,
 
 static struct i915_fp_compile *
 i915_init_compile(struct i915_context *i915,
-                  struct pipe_shader_state *fs)
+                  const struct pipe_shader_state *fs)
 {
    struct i915_fp_compile *p = CALLOC_STRUCT(i915_fp_compile);
 
-   p->shader = &i915->fs;
+   p->shader = i915->fs;
 
    p->vertex_info = &i915->current.vertex_info;
 
@@ -1032,8 +1032,8 @@ i915_fixup_depth_write(struct i915_fp_compile *p)
 void
 i915_translate_fragment_program( struct i915_context *i915 )
 {
-   struct i915_fp_compile *p = i915_init_compile(i915, &i915->fs);
-   const struct tgsi_token *tokens = i915->fs.tokens;
+   struct i915_fp_compile *p = i915_init_compile(i915, i915->fs);
+   const struct tgsi_token *tokens = i915->fs->tokens;
 
    i915_find_wpos_space(p);
 
index 1dfa10a..fe83564 100644 (file)
@@ -161,19 +161,29 @@ static void i915_set_polygon_stipple( struct pipe_context *pipe,
 }
 
 
+static const struct pipe_shader_state *
+i915_create_shader_state( struct pipe_context *pipe,
+                          const struct pipe_shader_state *templ )
+{
+
+   struct pipe_shader_state *shader = malloc(sizeof(struct pipe_shader_state));
+   memcpy(shader, templ, sizeof(struct pipe_shader_state));
+
+   return shader;
+}
 
-static void i915_set_fs_state( struct pipe_context *pipe,
+static void i915_bind_fs_state( struct pipe_context *pipe,
                                const struct pipe_shader_state *fs )
 {
    struct i915_context *i915 = i915_context(pipe);
 
-   memcpy(&i915->fs, fs, sizeof(*fs));
+   i915->fs = fs;
 
    i915->dirty |= I915_NEW_FS;
 }
 
 
-static void i915_set_vs_state( struct pipe_context *pipe,
+static void i915_bind_vs_state( struct pipe_context *pipe,
                                const struct pipe_shader_state *vs )
 {
    struct i915_context *i915 = i915_context(pipe);
@@ -182,6 +192,11 @@ static void i915_set_vs_state( struct pipe_context *pipe,
    draw_set_vertex_shader(i915->draw, vs);
 }
 
+static void i915_delete_shader_state( struct pipe_context *pipe,
+                                      const struct pipe_shader_state *shader )
+{
+   free((struct pipe_shader_state*)shader);
+}
 
 static void i915_set_constant_buffer(struct pipe_context *pipe,
                                      uint shader, uint index,
@@ -358,6 +373,10 @@ i915_init_state_functions( struct i915_context *i915 )
    i915->pipe.create_rasterizer_state = i915_create_rasterizer_state;
    i915->pipe.bind_rasterizer_state = i915_bind_rasterizer_state;
    i915->pipe.delete_rasterizer_state = i915_delete_rasterizer_state;
+   i915->pipe.create_shader_state = i915_create_shader_state;
+   i915->pipe.bind_fs_state = i915_bind_fs_state;
+   i915->pipe.bind_vs_state = i915_bind_vs_state;
+   i915->pipe.delete_shader_state = i915_delete_shader_state;
 
    i915->pipe.set_alpha_test_state = i915_set_alpha_test_state;
    i915->pipe.set_blend_color = i915_set_blend_color;
@@ -365,8 +384,6 @@ i915_init_state_functions( struct i915_context *i915 )
    i915->pipe.set_clear_color_state = i915_set_clear_color_state;
    i915->pipe.set_constant_buffer = i915_set_constant_buffer;
    i915->pipe.set_framebuffer_state = i915_set_framebuffer_state;
-   i915->pipe.set_fs_state = i915_set_fs_state;
-   i915->pipe.set_vs_state = i915_set_vs_state;
    i915->pipe.set_polygon_stipple = i915_set_polygon_stipple;
    i915->pipe.set_scissor_state = i915_set_scissor_state;
    i915->pipe.set_texture_state = i915_set_texture_state;
index 504bc10..8d404c5 100644 (file)
@@ -42,7 +42,7 @@
  */
 static void calculate_vertex_layout( struct i915_context *i915 )
 {
-   const uint inputsRead = i915->fs.inputs_read;
+   const uint inputsRead = i915->fs->inputs_read;
    const interp_mode colorInterp
       = i915->rasterizer->flatshade ? INTERP_CONSTANT : INTERP_LINEAR;
    struct vertex_info *vinfo = &i915->current.vertex_info;
index dda758f..c405051 100644 (file)
@@ -117,6 +117,16 @@ struct pipe_context {
    void (*delete_depth_stencil_state)(struct pipe_context *,
                                       const struct pipe_depth_stencil_state *);
 
+   const struct pipe_shader_state * (*create_shader_state)(
+      struct pipe_context *,
+      const struct pipe_shader_state *);
+   void (*bind_fs_state)(struct pipe_context *,
+                         const struct pipe_shader_state *);
+   void (*bind_vs_state)(struct pipe_context *,
+                         const struct pipe_shader_state *);
+   void (*delete_shader_state)(struct pipe_context *,
+                               const struct pipe_shader_state *);
+
    void (*set_alpha_test_state)( struct pipe_context *,
                                  const struct pipe_alpha_test_state * );
 
@@ -139,12 +149,6 @@ struct pipe_context {
    void (*set_framebuffer_state)( struct pipe_context *,
                                   const struct pipe_framebuffer_state * );
 
-   void (*set_fs_state)( struct pipe_context *,
-                        const struct pipe_shader_state * );
-
-   void (*set_vs_state)( struct pipe_context *,
-                        const struct pipe_shader_state * );
-
    void (*set_polygon_stipple)( struct pipe_context *,
                                const struct pipe_poly_stipple * );
 
index cf5fc22..25cb9d8 100644 (file)
@@ -251,17 +251,21 @@ struct pipe_context *softpipe_create( struct pipe_winsys *pipe_winsys,
 
    /* state setters */
    softpipe->pipe.create_blend_state = softpipe_create_blend_state;
-   softpipe->pipe.bind_blend_state = softpipe_bind_blend_state;
+   softpipe->pipe.bind_blend_state   = softpipe_bind_blend_state;
    softpipe->pipe.delete_blend_state = softpipe_delete_blend_state;
    softpipe->pipe.create_sampler_state = softpipe_create_sampler_state;
-   softpipe->pipe.bind_sampler_state = softpipe_bind_sampler_state;
+   softpipe->pipe.bind_sampler_state   = softpipe_bind_sampler_state;
    softpipe->pipe.delete_sampler_state = softpipe_delete_sampler_state;
    softpipe->pipe.create_depth_stencil_state = softpipe_create_depth_stencil_state;
-   softpipe->pipe.bind_depth_stencil_state = softpipe_bind_depth_stencil_state;
+   softpipe->pipe.bind_depth_stencil_state   = softpipe_bind_depth_stencil_state;
    softpipe->pipe.delete_depth_stencil_state = softpipe_delete_depth_stencil_state;
    softpipe->pipe.create_rasterizer_state = softpipe_create_rasterizer_state;
-   softpipe->pipe.bind_rasterizer_state = softpipe_bind_rasterizer_state;
+   softpipe->pipe.bind_rasterizer_state   = softpipe_bind_rasterizer_state;
    softpipe->pipe.delete_rasterizer_state = softpipe_delete_rasterizer_state;
+   softpipe->pipe.create_shader_state = softpipe_create_shader_state;
+   softpipe->pipe.bind_fs_state       = softpipe_bind_fs_state;
+   softpipe->pipe.bind_vs_state       = softpipe_bind_vs_state;
+   softpipe->pipe.delete_shader_state = softpipe_delete_shader_state;
 
    softpipe->pipe.set_alpha_test_state = softpipe_set_alpha_test_state;
    softpipe->pipe.set_blend_color = softpipe_set_blend_color;
@@ -270,8 +274,6 @@ struct pipe_context *softpipe_create( struct pipe_winsys *pipe_winsys,
    softpipe->pipe.set_constant_buffer = softpipe_set_constant_buffer;
    softpipe->pipe.set_feedback_state = softpipe_set_feedback_state;
    softpipe->pipe.set_framebuffer_state = softpipe_set_framebuffer_state;
-   softpipe->pipe.set_fs_state = softpipe_set_fs_state;
-   softpipe->pipe.set_vs_state = softpipe_set_vs_state;
    softpipe->pipe.set_polygon_stipple = softpipe_set_polygon_stipple;
    softpipe->pipe.set_scissor_state = softpipe_set_scissor_state;
    softpipe->pipe.set_texture_state = softpipe_set_texture_state;
index f1bb3d3..5c17c47 100644 (file)
@@ -74,6 +74,8 @@ struct softpipe_context {
    const struct pipe_sampler_state *sampler[PIPE_MAX_SAMPLERS];
    const struct pipe_depth_stencil_state   *depth_stencil;
    const struct pipe_rasterizer_state *rasterizer;
+   const struct pipe_shader_state *fs;
+   const struct pipe_shader_state *vs;
 
    struct pipe_alpha_test_state alpha_test;
    struct pipe_blend_color blend_color;
@@ -82,8 +84,6 @@ struct softpipe_context {
    struct pipe_constant_buffer constants[2];
    struct pipe_feedback_state feedback;
    struct pipe_framebuffer_state framebuffer;
-   struct pipe_shader_state fs;
-   struct pipe_shader_state vs;
    struct pipe_poly_stipple poly_stipple;
    struct pipe_scissor_state scissor;
    struct pipe_mipmap_tree *texture[PIPE_MAX_SAMPLERS];
index 46ad08a..25bc170 100755 (executable)
@@ -108,7 +108,7 @@ shade_quad(
    /* init machine state */
    tgsi_exec_machine_init(
       &machine,
-      softpipe->fs.tokens,
+      softpipe->fs->tokens,
       PIPE_MAX_SAMPLERS,
       qss->samplers );
 
index 62bd26c..04cc743 100644 (file)
@@ -88,11 +88,15 @@ void softpipe_set_constant_buffer(struct pipe_context *,
 void softpipe_set_feedback_state( struct pipe_context *,
                                   const struct pipe_feedback_state * );
 
-void softpipe_set_fs_state( struct pipe_context *,
-                            const struct pipe_shader_state * );
-
-void softpipe_set_vs_state( struct pipe_context *,
-                            const struct pipe_shader_state * );
+const struct pipe_shader_state *
+softpipe_create_shader_state( struct pipe_context *,
+                              const struct pipe_shader_state * );
+void softpipe_bind_fs_state( struct pipe_context *,
+                             const struct pipe_shader_state * );
+void softpipe_bind_vs_state( struct pipe_context *,
+                             const struct pipe_shader_state * );
+void softpipe_delete_shader_state( struct pipe_context *,
+                                   const struct pipe_shader_state * );
 
 void softpipe_set_polygon_stipple( struct pipe_context *,
                                  const struct pipe_poly_stipple * );
index 8c6bacf..9611a2a 100644 (file)
@@ -43,7 +43,7 @@
  */
 static void calculate_vertex_layout( struct softpipe_context *softpipe )
 {
-   const uint inputsRead = softpipe->fs.inputs_read;
+   const uint inputsRead = softpipe->fs->inputs_read;
    const interp_mode colorInterp
       = softpipe->rasterizer->flatshade ? INTERP_CONSTANT : INTERP_LINEAR;
    struct vertex_info *vinfo = &softpipe->vertex_info;
index 5ab2468..fbbde2f 100644 (file)
 #include "pipe/draw/draw_context.h"
 
 
-void softpipe_set_fs_state( struct pipe_context *pipe,
+const struct pipe_shader_state *
+softpipe_create_shader_state( struct pipe_context *pipe,
+                              const struct pipe_shader_state *templ )
+{
+   struct pipe_shader_state *shader = malloc(sizeof(struct pipe_shader_state));
+   memcpy(shader, templ, sizeof(struct pipe_shader_state));
+
+   return shader;
+}
+
+void softpipe_bind_fs_state( struct pipe_context *pipe,
                             const struct pipe_shader_state *fs )
 {
    struct softpipe_context *softpipe = softpipe_context(pipe);
 
-   memcpy(&softpipe->fs, fs, sizeof(*fs));
+   softpipe->fs = fs;
 
    softpipe->dirty |= SP_NEW_FS;
 }
 
 
-void softpipe_set_vs_state( struct pipe_context *pipe,
+void softpipe_bind_vs_state( struct pipe_context *pipe,
                             const struct pipe_shader_state *vs )
 {
    struct softpipe_context *softpipe = softpipe_context(pipe);
 
-   memcpy(&softpipe->vs, vs, sizeof(*vs));
+   softpipe->vs = vs;
 
    softpipe->dirty |= SP_NEW_VS;
 
@@ -57,6 +67,12 @@ void softpipe_set_vs_state( struct pipe_context *pipe,
 }
 
 
+void softpipe_delete_shader_state( struct pipe_context *pipe,
+                                   const struct pipe_shader_state *shader )
+{
+   free((struct pipe_shader_state*)shader);
+}
+
 void softpipe_set_constant_buffer(struct pipe_context *pipe,
                                   uint shader, uint index,
                                   const struct pipe_constant_buffer *buf)
index d066547..dc3e525 100644 (file)
@@ -38,6 +38,7 @@
 #include "pipe/tgsi/exec/tgsi_dump.h"
 
 #include "st_context.h"
+#include "st_cache.h"
 #include "st_atom.h"
 #include "st_program.h"
 
 static void compile_fs( struct st_context *st )
 {
    struct st_fragment_program *fp = st->fp;
+   struct pipe_shader_state fs;
+   struct pipe_shader_state *cached;
 
    /* XXX: fix static allocation of tokens:
     */
    tgsi_mesa_compile_fp_program( &fp->Base, fp->tokens, ST_FP_MAX_TOKENS );
 
-   fp->fs.inputs_read
+   memset(&fs, 0, sizeof(fs));
+   fs.inputs_read
       = tgsi_mesa_translate_fragment_input_mask(fp->Base.Base.InputsRead);
-   fp->fs.outputs_written
+   fs.outputs_written
       = tgsi_mesa_translate_fragment_output_mask(fp->Base.Base.OutputsWritten);
-   fp->fs.tokens = &fp->tokens[0];
+   fs.tokens = &fp->tokens[0];
+   cached = st_cached_shader_state(st, &fs);
+   fp->fsx = cached;
 
    if (TGSI_DEBUG)
       tgsi_dump( fp->tokens, TGSI_DUMP_VERBOSE );
@@ -92,8 +98,8 @@ static void update_fs( struct st_context *st )
       if (fp->dirty)
         compile_fs( st );
 
-      st->state.fs = fp->fs;
-      st->pipe->set_fs_state(st->pipe, &st->state.fs);
+      st->state.fs = fp->fsx;
+      st->pipe->bind_fs_state(st->pipe, st->state.fs);
    }
 }
 
index 289a3e4..18be713 100644 (file)
@@ -41,6 +41,7 @@
 #include "pipe/tgsi/exec/tgsi_core.h"
 
 #include "st_context.h"
+#include "st_cache.h"
 #include "st_atom.h"
 #include "st_program.h"
 
 static void compile_vs( struct st_context *st )
 {
    struct st_vertex_program *vp = st->vp;
-
+   struct pipe_shader_state vs;
+   struct pipe_shader_state *cached;
    /* XXX: fix static allocation of tokens:
     */
    tgsi_mesa_compile_vp_program( &vp->Base, vp->tokens, ST_FP_MAX_TOKENS );
 
-   vp->vs.inputs_read
+   memset(&vs, 0, sizeof(vs));
+   vs.inputs_read
       = tgsi_mesa_translate_vertex_input_mask(vp->Base.Base.InputsRead);
-   vp->vs.outputs_written
+   vs.outputs_written
       = tgsi_mesa_translate_vertex_output_mask(vp->Base.Base.OutputsWritten);
-   vp->vs.tokens = &vp->tokens[0];
+   vs.tokens = &vp->tokens[0];
+
+   cached = st_cached_shader_state(st, &vs);
+   vp->vs = cached;
 
    if (TGSI_DEBUG)
       tgsi_dump( vp->tokens, 0 );
@@ -110,7 +116,7 @@ static void update_vs( struct st_context *st )
 #endif
 
       st->state.vs = st->vp->vs;
-      st->pipe->set_vs_state(st->pipe, &st->state.vs);
+      st->pipe->bind_vs_state(st->pipe, st->state.vs);
    }
 }
 
index e9c7963..7b851e3 100644 (file)
@@ -111,3 +111,21 @@ struct pipe_rasterizer_state * st_cached_rasterizer_state(
    }
    return (struct pipe_rasterizer_state*)(cso_hash_iter_data(iter));
 }
+
+struct pipe_shader_state * st_cached_shader_state(
+   struct st_context *st,
+   const struct pipe_shader_state *templ)
+{
+   unsigned hash_key = cso_construct_key((void*)templ,
+                                         sizeof(struct pipe_shader_state));
+   struct cso_hash_iter iter = cso_find_state_template(st->cache,
+                                                       hash_key, CSO_SHADER,
+                                                       (void*)templ);
+   if (cso_hash_iter_is_null(iter)) {
+      const struct pipe_shader_state *created_state =
+         st->pipe->create_shader_state(st->pipe, templ);
+      iter = cso_insert_state(st->cache, hash_key, CSO_SHADER,
+                              (void*)created_state);
+   }
+   return (struct pipe_shader_state*)(cso_hash_iter_data(iter));
+}
index a06af31..6a897a9 100644 (file)
@@ -53,4 +53,8 @@ struct pipe_rasterizer_state *st_cached_rasterizer_state(
    struct st_context *st,
    const struct pipe_rasterizer_state *raster);
 
+struct pipe_shader_state *st_cached_shader_state(
+   struct st_context *st,
+   const struct pipe_shader_state *templ);
+
 #endif
index 584bc1c..2ea4986 100644 (file)
@@ -347,6 +347,7 @@ clear_with_quad(GLcontext *ctx,
    {
       static struct st_fragment_program *stfp = NULL;
       struct pipe_shader_state fs;
+      const struct pipe_shader_state *cached;
       if (!stfp) {
          stfp = make_color_shader(st);
       }
@@ -354,13 +355,15 @@ clear_with_quad(GLcontext *ctx,
       fs.inputs_read = tgsi_mesa_translate_fragment_input_mask(stfp->Base.Base.InputsRead);
       fs.outputs_written = tgsi_mesa_translate_fragment_output_mask(stfp->Base.Base.OutputsWritten);
       fs.tokens = &stfp->tokens[0];
-      pipe->set_fs_state(pipe, &fs);
+      cached = st_cached_shader_state(st, &fs);
+      pipe->bind_fs_state(pipe, cached);
    }
 
    /* vertex shader state: color/position pass-through */
    {
       static struct st_vertex_program *stvp = NULL;
       struct pipe_shader_state vs;
+      const struct pipe_shader_state *cached;
       if (!stvp) {
          stvp = make_vertex_shader(st);
       }
@@ -368,7 +371,8 @@ clear_with_quad(GLcontext *ctx,
       vs.inputs_read = stvp->Base.Base.InputsRead;
       vs.outputs_written = stvp->Base.Base.OutputsWritten;
       vs.tokens = &stvp->tokens[0];
-      pipe->set_vs_state(pipe, &vs);
+      cached = st_cached_shader_state(st, &vs);
+      pipe->bind_vs_state(pipe, cached);
    }
 
    /* viewport state: viewport matching window dims */
@@ -394,8 +398,8 @@ clear_with_quad(GLcontext *ctx,
    pipe->set_alpha_test_state(pipe, &st->state.alpha_test);
    pipe->bind_blend_state(pipe, st->state.blend);
    pipe->bind_depth_stencil_state(pipe, st->state.depth_stencil);
-   pipe->set_fs_state(pipe, &st->state.fs);
-   pipe->set_vs_state(pipe, &st->state.vs);
+   pipe->bind_fs_state(pipe, st->state.fs);
+   pipe->bind_vs_state(pipe, st->state.vs);
    pipe->bind_rasterizer_state(pipe, st->state.rasterizer);
    pipe->set_viewport_state(pipe, &ctx->st->state.viewport);
    /* OR:
index 78ede8e..37e4063 100644 (file)
@@ -329,19 +329,22 @@ draw_textured_quad(GLcontext *ctx, GLint x, GLint y, GLfloat z,
    {
       static struct st_fragment_program *stfp = NULL;
       struct pipe_shader_state fs;
+      struct pipe_shader_state *cached;
       if (!stfp) {
          stfp = make_fragment_shader(ctx->st);
       }
       memset(&fs, 0, sizeof(fs));
       fs.inputs_read = stfp->Base.Base.InputsRead;
       fs.tokens = &stfp->tokens[0];
-      pipe->set_fs_state(pipe, &fs);
+      cached = st_cached_shader_state(ctx->st, &fs);
+      pipe->bind_fs_state(pipe, cached);
    }
 
    /* vertex shader state: position + texcoord pass-through */
    {
       static struct st_vertex_program *stvp = NULL;
       struct pipe_shader_state vs;
+      struct pipe_shader_state *cached;
       if (!stvp) {
          stvp = make_vertex_shader(ctx->st);
       }
@@ -349,7 +352,8 @@ draw_textured_quad(GLcontext *ctx, GLint x, GLint y, GLfloat z,
       vs.inputs_read = stvp->Base.Base.InputsRead;
       vs.outputs_written = stvp->Base.Base.OutputsWritten;
       vs.tokens = &stvp->tokens[0];
-      pipe->set_vs_state(pipe, &vs);
+      cached = st_cached_shader_state(ctx->st, &vs);
+      pipe->bind_vs_state(pipe, cached);
    }
 
    /* texture sampling state: */
@@ -403,8 +407,8 @@ draw_textured_quad(GLcontext *ctx, GLint x, GLint y, GLfloat z,
 
    /* restore GL state */
    pipe->bind_rasterizer_state(pipe, ctx->st->state.rasterizer);
-   pipe->set_fs_state(pipe, &ctx->st->state.fs);
-   pipe->set_vs_state(pipe, &ctx->st->state.vs);
+   pipe->bind_fs_state(pipe, ctx->st->state.fs);
+   pipe->bind_vs_state(pipe, ctx->st->state.vs);
    pipe->set_texture_state(pipe, unit, ctx->st->state.texture[unit]);
    pipe->bind_sampler_state(pipe, unit, ctx->st->state.sampler[unit]);
    pipe->set_viewport_state(pipe, &ctx->st->state.viewport);
index 7bedf3f..98efe1a 100644 (file)
@@ -53,7 +53,7 @@ static void
 setup_vertex_attribs(GLcontext *ctx)
 {
    struct pipe_context *pipe = ctx->st->pipe;
-   const uint inputAttrs = ctx->st->state.vs.inputs_read;
+   const uint inputAttrs = ctx->st->state.vs->inputs_read;
    uint attr;
 
    /* all attributes come from the default attribute buffer */
@@ -84,7 +84,7 @@ static void
 setup_feedback(GLcontext *ctx)
 {
    struct pipe_context *pipe = ctx->st->pipe;
-   const uint outputAttrs = ctx->st->state.vs.outputs_written;
+   const uint outputAttrs = ctx->st->state.vs->outputs_written;
    struct pipe_feedback_state feedback;
    uint i;
 
@@ -307,7 +307,7 @@ st_RasterPos(GLcontext *ctx, const GLfloat v[4])
 
    /* extract values and update rasterpos state */
    {
-      const uint outputAttrs = ctx->st->state.vs.outputs_written;
+      const uint outputAttrs = ctx->st->state.vs->outputs_written;
       const float *pos, *color0, *color1, *tex0;
       float *buf = buf_map;
 
index 516d319..a8ae5d9 100644 (file)
@@ -78,6 +78,8 @@ struct st_context
       const struct pipe_sampler_state *sampler[PIPE_MAX_SAMPLERS];
       const struct pipe_depth_stencil_state *depth_stencil;
       const struct pipe_rasterizer_state  *rasterizer;
+      const struct pipe_shader_state *fs;
+      const struct pipe_shader_state *vs;
 
       struct pipe_alpha_test_state  alpha_test;
       struct pipe_blend_color  blend_color;
@@ -89,8 +91,6 @@ struct st_context
       struct pipe_mipmap_tree *texture[PIPE_MAX_SAMPLERS];
       struct pipe_poly_stipple poly_stipple;
       struct pipe_scissor_state scissor;
-      struct pipe_shader_state fs;
-      struct pipe_shader_state vs;
       struct pipe_viewport_state viewport;
    } state;
 
index f68e449..ac63a38 100644 (file)
@@ -193,7 +193,7 @@ st_draw_vbo(GLcontext *ctx,
    update_default_attribs_buffer(ctx);
 
    /* this must be after state validation */
-   attrsNeeded = ctx->st->state.vs.inputs_read;
+   attrsNeeded = ctx->st->state.vs->inputs_read;
 
    /* tell pipe about the vertex array element/attributes */
    for (attr = 0; attr < 16; attr++) {
@@ -395,14 +395,14 @@ st_feedback_draw_vbo(GLcontext *ctx,
    draw_set_viewport_state(draw, &st->state.viewport);
    draw_set_clip_state(draw, &st->state.clip);
    draw_set_rasterizer_state(draw, st->state.rasterizer);
-   draw_set_vertex_shader(draw, &st->state.vs);
+   draw_set_vertex_shader(draw, st->state.vs);
    /* XXX need to set vertex info too */
 
 
    update_default_attribs_buffer(ctx);
 
    /* this must be after state validation */
-   attrsNeeded = ctx->st->state.vs.inputs_read;
+   attrsNeeded = ctx->st->state.vs->inputs_read;
 
    /* tell draw module about the vertex array element/attributes */
    for (attr = 0; attr < 16; attr++) {
index 7a91983..a2f114b 100644 (file)
@@ -53,8 +53,8 @@ struct st_fragment_program
 
    struct tgsi_token tokens[ST_FP_MAX_TOKENS];
    GLboolean dirty;
-   
-   struct pipe_shader_state fs;
+
+   const struct pipe_shader_state *fsx;
    GLuint param_state;
 };
 
@@ -75,7 +75,7 @@ struct st_vertex_program
    struct x86_function  sse2_program;
 #endif
 
-   struct pipe_shader_state vs;
+   const struct pipe_shader_state *vs;
    GLuint param_state;
 };