diff options
author | Marek Olšák <[email protected]> | 2019-11-25 17:58:45 -0500 |
---|---|---|
committer | Marek Olšák <[email protected]> | 2019-11-26 15:14:10 -0500 |
commit | ed1ff99da7026de3bb10ab4219f75424116124b1 (patch) | |
tree | f29626d0454ce27af0452a94e0545d46dfd5ded0 /src/mesa | |
parent | b8772a559a223be0817ba3abb4392d559fee9891 (diff) |
st/mesa: add st_variant base class to simplify code for shader variants
Reviewed-by: Timothy Arceri <[email protected]>
Diffstat (limited to 'src/mesa')
-rw-r--r-- | src/mesa/state_tracker/st_atom_shader.c | 18 | ||||
-rw-r--r-- | src/mesa/state_tracker/st_cb_bitmap.c | 2 | ||||
-rw-r--r-- | src/mesa/state_tracker/st_cb_drawpixels.c | 4 | ||||
-rw-r--r-- | src/mesa/state_tracker/st_cb_program.c | 31 | ||||
-rw-r--r-- | src/mesa/state_tracker/st_glsl_to_nir.cpp | 8 | ||||
-rw-r--r-- | src/mesa/state_tracker/st_program.c | 310 | ||||
-rw-r--r-- | src/mesa/state_tracker/st_program.h | 75 | ||||
-rw-r--r-- | src/mesa/state_tracker/st_shader_cache.c | 8 |
8 files changed, 149 insertions, 307 deletions
diff --git a/src/mesa/state_tracker/st_atom_shader.c b/src/mesa/state_tracker/st_atom_shader.c index b18b33e5000..10d21905780 100644 --- a/src/mesa/state_tracker/st_atom_shader.c +++ b/src/mesa/state_tracker/st_atom_shader.c @@ -109,10 +109,10 @@ st_update_fp( struct st_context *st ) if (st->shader_has_one_variant[MESA_SHADER_FRAGMENT] && !stfp->ati_fs && /* ATI_fragment_shader always has multiple variants */ !stfp->Base.ExternalSamplersUsed && /* external samplers need variants */ - stfp->fp_variants && - !stfp->fp_variants->key.drawpixels && - !stfp->fp_variants->key.bitmap) { - shader = stfp->fp_variants->driver_shader; + stfp->variants && + !st_fp_variant(stfp->variants)->key.drawpixels && + !st_fp_variant(stfp->variants)->key.bitmap) { + shader = stfp->variants->driver_shader; } else { struct st_fp_variant_key key; @@ -160,7 +160,7 @@ st_update_fp( struct st_context *st ) key.external = st_get_external_sampler_key(st, &stfp->Base); - shader = st_get_fp_variant(st, stfp, &key)->driver_shader; + shader = st_get_fp_variant(st, stfp, &key)->base.driver_shader; } st_reference_prog(st, &st->fp, stfp); @@ -186,9 +186,9 @@ st_update_vp( struct st_context *st ) assert(stvp->Base.Target == GL_VERTEX_PROGRAM_ARB); if (st->shader_has_one_variant[MESA_SHADER_VERTEX] && - stvp->vp_variants && - stvp->vp_variants->key.passthrough_edgeflags == st->vertdata_edgeflags) { - st->vp_variant = stvp->vp_variants; + stvp->variants && + st_vp_variant(stvp->variants)->key.passthrough_edgeflags == st->vertdata_edgeflags) { + st->vp_variant = st_vp_variant(stvp->variants); } else { struct st_common_variant_key key; @@ -236,7 +236,7 @@ st_update_vp( struct st_context *st ) st_reference_prog(st, &st->vp, stvp); cso_set_vertex_shader_handle(st->cso_context, - st->vp_variant->driver_shader); + st->vp_variant->base.driver_shader); } diff --git a/src/mesa/state_tracker/st_cb_bitmap.c b/src/mesa/state_tracker/st_cb_bitmap.c index 676fb12be55..112af82815a 100644 --- a/src/mesa/state_tracker/st_cb_bitmap.c +++ b/src/mesa/state_tracker/st_cb_bitmap.c @@ -212,7 +212,7 @@ setup_render_state(struct gl_context *ctx, cso_set_rasterizer(cso, &st->bitmap.rasterizer); /* fragment shader state: TEX lookup program */ - cso_set_fragment_shader_handle(cso, fpv->driver_shader); + cso_set_fragment_shader_handle(cso, fpv->base.driver_shader); /* vertex shader state: position + texcoord pass-through */ cso_set_vertex_shader_handle(cso, st->passthrough_vs); diff --git a/src/mesa/state_tracker/st_cb_drawpixels.c b/src/mesa/state_tracker/st_cb_drawpixels.c index 6b47548d33b..fc11bc3ae47 100644 --- a/src/mesa/state_tracker/st_cb_drawpixels.c +++ b/src/mesa/state_tracker/st_cb_drawpixels.c @@ -1363,7 +1363,7 @@ st_DrawPixels(struct gl_context *ctx, GLint x, GLint y, fpv = (format != GL_COLOR_INDEX) ? get_color_fp_variant(st) : get_color_index_fp_variant(st); - driver_fp = fpv->driver_shader; + driver_fp = fpv->base.driver_shader; if (ctx->Pixel.MapColorFlag && format != GL_COLOR_INDEX) { pipe_sampler_view_reference(&sv[1], @@ -1741,7 +1741,7 @@ st_CopyPixels(struct gl_context *ctx, GLint srcx, GLint srcy, rbRead = st_get_color_read_renderbuffer(ctx); - driver_fp = fpv->driver_shader; + driver_fp = fpv->base.driver_shader; if (ctx->Pixel.MapColorFlag) { pipe_sampler_view_reference(&sv[1], diff --git a/src/mesa/state_tracker/st_cb_program.c b/src/mesa/state_tracker/st_cb_program.c index 0bc6e90ee07..bf0b5e6a05f 100644 --- a/src/mesa/state_tracker/st_cb_program.c +++ b/src/mesa/state_tracker/st_cb_program.c @@ -87,12 +87,7 @@ st_delete_program(struct gl_context *ctx, struct gl_program *prog) struct st_context *st = st_context(ctx); struct st_program *stp = st_program(prog); - if (prog->Target == GL_VERTEX_PROGRAM_ARB) - st_release_vp_variants(st, stp); - if (prog->Target == GL_FRAGMENT_PROGRAM_ARB) - st_release_fp_variants(st, stp); - else - st_release_common_variants(st, stp); + st_release_variants(st, stp); if (stp->glsl_to_tgsi) free_glsl_to_tgsi_visitor(stp->glsl_to_tgsi); @@ -117,6 +112,8 @@ st_program_string_notify( struct gl_context *ctx, /* GLSL-to-NIR should not end up here. */ assert(!stp->shader_program); + st_release_variants(st, stp); + if (target == GL_FRAGMENT_PROGRAM_ARB || target == GL_FRAGMENT_SHADER_ATI) { if (target == GL_FRAGMENT_SHADER_ATI) { @@ -126,15 +123,12 @@ st_program_string_notify( struct gl_context *ctx, st_init_atifs_prog(ctx, prog); } - st_release_fp_variants(st, stp); if (!st_translate_fragment_program(st, stp)) return false; } else if (target == GL_VERTEX_PROGRAM_ARB) { - st_release_vp_variants(st, stp); if (!st_translate_vertex_program(st, stp)) return false; } else { - st_release_common_variants(st, stp); if (!st_translate_common_program(st, stp)) return false; } @@ -182,23 +176,8 @@ st_get_shader_program_completion_status(struct gl_context *ctx, if (!linked || !linked->Program) continue; - switch (i) { - case MESA_SHADER_VERTEX: - if (st_program(linked->Program)->vp_variants) - sh = st_program(linked->Program)->vp_variants->driver_shader; - break; - case MESA_SHADER_FRAGMENT: - if (st_program(linked->Program)->fp_variants) - sh = st_program(linked->Program)->fp_variants->driver_shader; - break; - case MESA_SHADER_TESS_CTRL: - case MESA_SHADER_TESS_EVAL: - case MESA_SHADER_GEOMETRY: - case MESA_SHADER_COMPUTE: - if (st_program(linked->Program)->variants) - sh = st_program(linked->Program)->variants->driver_shader; - break; - } + if (st_program(linked->Program)->variants) + sh = st_program(linked->Program)->variants->driver_shader; unsigned type = pipe_shader_type_from_mesa(i); diff --git a/src/mesa/state_tracker/st_glsl_to_nir.cpp b/src/mesa/state_tracker/st_glsl_to_nir.cpp index c7a1e12530d..7a417d98f14 100644 --- a/src/mesa/state_tracker/st_glsl_to_nir.cpp +++ b/src/mesa/state_tracker/st_glsl_to_nir.cpp @@ -785,13 +785,7 @@ st_link_nir(struct gl_context *ctx, st_store_ir_in_disk_cache(st, prog, true); - if (prog->info.stage == MESA_SHADER_VERTEX) - st_release_vp_variants(st, stp); - else if (prog->info.stage == MESA_SHADER_FRAGMENT) - st_release_fp_variants(st, stp); - else - st_release_common_variants(st, stp); - + st_release_variants(st, stp); st_finalize_program(st, prog); /* The GLSL IR won't be needed anymore. */ diff --git a/src/mesa/state_tracker/st_program.c b/src/mesa/state_tracker/st_program.c index 53781e6c01e..2dd9227ddd7 100644 --- a/src/mesa/state_tracker/st_program.c +++ b/src/mesa/state_tracker/st_program.c @@ -208,127 +208,23 @@ st_set_prog_affected_state_flags(struct gl_program *prog) } } -static void -delete_ir(struct pipe_shader_state *ir) -{ - if (ir->tokens) { - ureg_free_tokens(ir->tokens); - ir->tokens = NULL; - } - - /* Note: Any setup of ->ir.nir that has had pipe->create_*_state called on - * it has resulted in the driver taking ownership of the NIR. Those - * callers should be NULLing out the nir field in any pipe_shader_state - * that might have this called in order to indicate that. - * - * GLSL IR and ARB programs will have set gl_program->nir to the same - * shader as ir->ir.nir, so it will be freed by _mesa_delete_program(). - */ -} /** - * Delete a vertex program variant. Note the caller must unlink - * the variant from the linked list. + * Delete a shader variant. Note the caller must unlink the variant from + * the linked list. */ static void -delete_vp_variant(struct st_context *st, struct st_vp_variant *vpv) -{ - if (vpv->driver_shader) { - if (st->has_shareable_shaders || vpv->key.st == st) { - cso_delete_vertex_shader(st->cso_context, vpv->driver_shader); - } else { - st_save_zombie_shader(vpv->key.st, PIPE_SHADER_VERTEX, - vpv->driver_shader); - } - } - - if (vpv->draw_shader) - draw_delete_vertex_shader( st->draw, vpv->draw_shader ); - - if (vpv->tokens) - ureg_free_tokens(vpv->tokens); - - free( vpv ); -} - - - -/** - * Clean out any old compilations: - */ -void -st_release_vp_variants( struct st_context *st, - struct st_program *stvp ) -{ - struct st_vp_variant *vpv; - - for (vpv = stvp->vp_variants; vpv; ) { - struct st_vp_variant *next = vpv->next; - delete_vp_variant(st, vpv); - vpv = next; - } - - stvp->vp_variants = NULL; - - delete_ir(&stvp->state); -} - - - -/** - * Delete a fragment program variant. Note the caller must unlink - * the variant from the linked list. - */ -static void -delete_fp_variant(struct st_context *st, struct st_fp_variant *fpv) -{ - if (fpv->driver_shader) { - if (st->has_shareable_shaders || fpv->key.st == st) { - cso_delete_fragment_shader(st->cso_context, fpv->driver_shader); - } else { - st_save_zombie_shader(fpv->key.st, PIPE_SHADER_FRAGMENT, - fpv->driver_shader); - } - } - - free(fpv); -} - - -/** - * Free all variants of a fragment program. - */ -void -st_release_fp_variants(struct st_context *st, struct st_program *stfp) -{ - struct st_fp_variant *fpv; - - for (fpv = stfp->fp_variants; fpv; ) { - struct st_fp_variant *next = fpv->next; - delete_fp_variant(st, fpv); - fpv = next; - } - - stfp->fp_variants = NULL; - - delete_ir(&stfp->state); -} - - -/** - * Delete a basic program variant. Note the caller must unlink - * the variant from the linked list. - */ -static void -delete_common_variant(struct st_context *st, struct st_common_variant *v, - GLenum target) +delete_variant(struct st_context *st, struct st_variant *v, GLenum target) { if (v->driver_shader) { - if (st->has_shareable_shaders || v->key.st == st) { + if (st->has_shareable_shaders || v->st == st) { /* The shader's context matches the calling context, or we * don't care. */ switch (target) { + case GL_VERTEX_PROGRAM_ARB: + cso_delete_vertex_shader(st->cso_context, v->driver_shader); + break; case GL_TESS_CONTROL_PROGRAM_NV: cso_delete_tessctrl_shader(st->cso_context, v->driver_shader); break; @@ -338,6 +234,9 @@ delete_common_variant(struct st_context *st, struct st_common_variant *v, case GL_GEOMETRY_PROGRAM_NV: cso_delete_geometry_shader(st->cso_context, v->driver_shader); break; + case GL_FRAGMENT_PROGRAM_ARB: + cso_delete_fragment_shader(st->cso_context, v->driver_shader); + break; case GL_COMPUTE_PROGRAM_NV: cso_delete_compute_shader(st->cso_context, v->driver_shader); break; @@ -348,24 +247,23 @@ delete_common_variant(struct st_context *st, struct st_common_variant *v, /* We can't delete a shader with a context different from the one * that created it. Add it to the creating context's zombie list. */ - enum pipe_shader_type type; - switch (target) { - case GL_TESS_CONTROL_PROGRAM_NV: - type = PIPE_SHADER_TESS_CTRL; - break; - case GL_TESS_EVALUATION_PROGRAM_NV: - type = PIPE_SHADER_TESS_EVAL; - break; - case GL_GEOMETRY_PROGRAM_NV: - type = PIPE_SHADER_GEOMETRY; - break; - default: - unreachable(""); - } - st_save_zombie_shader(v->key.st, type, v->driver_shader); + enum pipe_shader_type type = + pipe_shader_type_from_mesa(_mesa_program_enum_to_shader_stage(target)); + + st_save_zombie_shader(v->st, type, v->driver_shader); } } + if (target == GL_VERTEX_PROGRAM_ARB) { + struct st_vp_variant *vpv = (struct st_vp_variant *)v; + + if (vpv->draw_shader) + draw_delete_vertex_shader( st->draw, vpv->draw_shader ); + + if (vpv->tokens) + ureg_free_tokens(vpv->tokens); + } + free(v); } @@ -374,18 +272,31 @@ delete_common_variant(struct st_context *st, struct st_common_variant *v, * Free all basic program variants. */ void -st_release_common_variants(struct st_context *st, struct st_program *p) +st_release_variants(struct st_context *st, struct st_program *p) { - struct st_common_variant *v; + struct st_variant *v; for (v = p->variants; v; ) { - struct st_common_variant *next = v->next; - delete_common_variant(st, v, p->Base.Target); + struct st_variant *next = v->next; + delete_variant(st, v, p->Base.Target); v = next; } p->variants = NULL; - delete_ir(&p->state); + + if (p->state.tokens) { + ureg_free_tokens(p->state.tokens); + p->state.tokens = NULL; + } + + /* Note: Any setup of ->ir.nir that has had pipe->create_*_state called on + * it has resulted in the driver taking ownership of the NIR. Those + * callers should be NULLing out the nir field in any pipe_shader_state + * that might have this called in order to indicate that. + * + * GLSL IR and ARB programs will have set gl_program->nir to the same + * shader as ir->ir.nir, so it will be freed by _mesa_delete_program(). + */ } void @@ -745,7 +656,7 @@ st_create_vp_variant(struct st_context *st, if (ST_DEBUG & DEBUG_PRINT_IR) nir_print_shader(state.ir.nir, stderr); - vpv->driver_shader = pipe->create_vs_state(pipe, &state); + vpv->base.driver_shader = pipe->create_vs_state(pipe, &state); /* When generating a NIR program, we usually don't have TGSI tokens. * However, we do create them for ARB_vertex_program / fixed-function VS @@ -798,7 +709,7 @@ st_create_vp_variant(struct st_context *st, if (ST_DEBUG & DEBUG_PRINT_IR) tgsi_dump(state.tokens, 0); - vpv->driver_shader = pipe->create_vs_state(pipe, &state); + vpv->base.driver_shader = pipe->create_vs_state(pipe, &state); /* Save this for selection/feedback/rasterpos. */ vpv->tokens = state.tokens; return vpv; @@ -817,7 +728,8 @@ st_get_vp_variant(struct st_context *st, struct st_vp_variant *vpv; /* Search for existing variant */ - for (vpv = stp->vp_variants; vpv; vpv = vpv->next) { + for (vpv = st_vp_variant(stp->variants); vpv; + vpv = st_vp_variant(vpv->base.next)) { if (memcmp(&vpv->key, key, sizeof(*key)) == 0) { break; } @@ -827,16 +739,18 @@ st_get_vp_variant(struct st_context *st, /* create now */ vpv = st_create_vp_variant(st, stp, key); if (vpv) { - for (unsigned index = 0; index < vpv->num_inputs; ++index) { - unsigned attr = stvp->index_to_input[index]; - if (attr == ST_DOUBLE_ATTRIB_PLACEHOLDER) - continue; - vpv->vert_attrib_mask |= 1u << attr; - } + vpv->base.st = key->st; + + for (unsigned index = 0; index < vpv->num_inputs; ++index) { + unsigned attr = stvp->index_to_input[index]; + if (attr == ST_DOUBLE_ATTRIB_PLACEHOLDER) + continue; + vpv->vert_attrib_mask |= 1u << attr; + } /* insert into list */ - vpv->next = stp->vp_variants; - stp->vp_variants = vpv; + vpv->base.next = stp->variants; + stp->variants = &vpv->base; } } @@ -1366,7 +1280,7 @@ st_create_fp_variant(struct st_context *st, if (ST_DEBUG & DEBUG_PRINT_IR) nir_print_shader(state.ir.nir, stderr); - variant->driver_shader = pipe->create_fs_state(pipe, &state); + variant->base.driver_shader = pipe->create_fs_state(pipe, &state); variant->key = *key; return variant; @@ -1498,7 +1412,7 @@ st_create_fp_variant(struct st_context *st, tgsi_dump(state.tokens, 0); /* fill in variant */ - variant->driver_shader = pipe->create_fs_state(pipe, &state); + variant->base.driver_shader = pipe->create_fs_state(pipe, &state); variant->key = *key; if (state.tokens != stfp->state.tokens) @@ -1517,7 +1431,8 @@ st_get_fp_variant(struct st_context *st, struct st_fp_variant *fpv; /* Search for existing variant */ - for (fpv = stfp->fp_variants; fpv; fpv = fpv->next) { + for (fpv = st_fp_variant(stfp->variants); fpv; + fpv = st_fp_variant(fpv->base.next)) { if (memcmp(&fpv->key, key, sizeof(*key)) == 0) { break; } @@ -1527,6 +1442,8 @@ st_get_fp_variant(struct st_context *st, /* create new */ fpv = st_create_fp_variant(st, stfp, key); if (fpv) { + fpv->base.st = key->st; + if (key->bitmap || key->drawpixels) { /* Regular variants should always come before the * bitmap & drawpixels variants, (unless there @@ -1534,17 +1451,17 @@ st_get_fp_variant(struct st_context *st, * st_update_fp can take a fast path when * shader_has_one_variant is set. */ - if (!stfp->fp_variants) { - stfp->fp_variants = fpv; + if (!stfp->variants) { + stfp->variants = &fpv->base; } else { /* insert into list after the first one */ - fpv->next = stfp->fp_variants->next; - stfp->fp_variants->next = fpv; + fpv->base.next = stfp->variants->next; + stfp->variants->next = &fpv->base; } } else { /* insert into list */ - fpv->next = stfp->fp_variants; - stfp->fp_variants = fpv; + fpv->base.next = stfp->variants; + stfp->variants = &fpv->base; } } } @@ -1744,25 +1661,24 @@ st_translate_common_program(struct st_context *st, /** * Get/create a basic program variant. */ -struct st_common_variant * +struct st_variant * st_get_common_variant(struct st_context *st, struct st_program *prog, const struct st_common_variant_key *key) { struct pipe_context *pipe = st->pipe; - struct st_common_variant *v; + struct st_variant *v; struct pipe_shader_state state = {0}; /* Search for existing variant */ for (v = prog->variants; v; v = v->next) { - if (memcmp(&v->key, key, sizeof(*key)) == 0) { + if (memcmp(&st_common_variant(v)->key, key, sizeof(*key)) == 0) break; - } } if (!v) { /* create new */ - v = CALLOC_STRUCT(st_common_variant); + v = (struct st_variant*)CALLOC_STRUCT(st_common_variant); if (v) { if (prog->state.type == PIPE_SHADER_IR_NIR) { bool finalize = false; @@ -1837,7 +1753,8 @@ st_get_common_variant(struct st_context *st, return NULL; } - v->key = *key; + st_common_variant(v)->key = *key; + v->st = key->st; /* insert into list */ v->next = prog->variants; @@ -1859,74 +1776,21 @@ destroy_program_variants(struct st_context *st, struct gl_program *target) if (!target || target == &_mesa_DummyProgram) return; - switch (target->Target) { - case GL_VERTEX_PROGRAM_ARB: - { - struct st_program *stvp = (struct st_program *) target; - struct st_vp_variant *vpv, **prevPtr = &stvp->vp_variants; - - for (vpv = stvp->vp_variants; vpv; ) { - struct st_vp_variant *next = vpv->next; - if (vpv->key.st == st) { - /* unlink from list */ - *prevPtr = next; - /* destroy this variant */ - delete_vp_variant(st, vpv); - } - else { - prevPtr = &vpv->next; - } - vpv = next; - } - } - break; - case GL_FRAGMENT_PROGRAM_ARB: - { - struct st_program *stfp = - (struct st_program *) target; - struct st_fp_variant *fpv, **prevPtr = &stfp->fp_variants; - - for (fpv = stfp->fp_variants; fpv; ) { - struct st_fp_variant *next = fpv->next; - if (fpv->key.st == st) { - /* unlink from list */ - *prevPtr = next; - /* destroy this variant */ - delete_fp_variant(st, fpv); - } - else { - prevPtr = &fpv->next; - } - fpv = next; - } + struct st_program *p = st_program(target); + struct st_variant *v, **prevPtr = &p->variants; + + for (v = p->variants; v; ) { + struct st_variant *next = v->next; + if (v->st == st) { + /* unlink from list */ + *prevPtr = next; + /* destroy this variant */ + delete_variant(st, v, target->Target); } - break; - case GL_GEOMETRY_PROGRAM_NV: - case GL_TESS_CONTROL_PROGRAM_NV: - case GL_TESS_EVALUATION_PROGRAM_NV: - case GL_COMPUTE_PROGRAM_NV: - { - struct st_program *p = st_program(target); - struct st_common_variant *v, **prevPtr = &p->variants; - - for (v = p->variants; v; ) { - struct st_common_variant *next = v->next; - if (v->key.st == st) { - /* unlink from list */ - *prevPtr = next; - /* destroy this variant */ - delete_common_variant(st, v, target->Target); - } - else { - prevPtr = &v->next; - } - v = next; - } + else { + prevPtr = &v->next; } - break; - default: - _mesa_problem(NULL, "Unexpected program target 0x%x in " - "destroy_program_variants_cb()", target->Target); + v = next; } } diff --git a/src/mesa/state_tracker/st_program.h b/src/mesa/state_tracker/st_program.h index 9ad23235bcb..62d82c2bf84 100644 --- a/src/mesa/state_tracker/st_program.h +++ b/src/mesa/state_tracker/st_program.h @@ -139,27 +139,36 @@ struct st_fp_variant_key struct st_external_sampler_key external; }; +/** + * Base class for shader variants. + */ +struct st_variant +{ + /** next in linked list */ + struct st_variant *next; + + /** st_context from the shader key */ + struct st_context *st; + + void *driver_shader; +}; /** * Variant of a fragment program. */ struct st_fp_variant { + struct st_variant base; + /** Parameters which generated this version of fragment program */ struct st_fp_variant_key key; - /** Driver's compiled shader */ - void *driver_shader; - /** For glBitmap variants */ uint bitmap_sampler; /** For glDrawPixels variants */ unsigned drawpix_sampler; unsigned pixelmap_sampler; - - /** next in linked list */ - struct st_fp_variant *next; }; @@ -190,6 +199,8 @@ struct st_common_variant_key */ struct st_vp_variant { + struct st_variant base; + /* Parameters which generated this translated version of a vertex * shader: */ @@ -201,15 +212,9 @@ struct st_vp_variant */ const struct tgsi_token *tokens; - /** Driver's compiled shader */ - void *driver_shader; - /** For using our private draw module (glRasterPos) */ struct draw_vertex_shader *draw_shader; - /** Next in linked list */ - struct st_vp_variant *next; - /** similar to that in st_vertex_program, but with edgeflags info too */ GLuint num_inputs; @@ -219,16 +224,14 @@ struct st_vp_variant /** - * Geometry program variant. + * Common shader variant. */ struct st_common_variant { + struct st_variant base; + /* Parameters which generated this variant. */ struct st_common_variant_key key; - - void *driver_shader; - - struct st_common_variant *next; }; @@ -243,14 +246,10 @@ struct st_program struct ati_fragment_shader *ati_fs; uint64_t affected_states; /**< ST_NEW_* flags to mark dirty when binding */ - /* used when bypassing glsl_to_tgsi: */ + /* used when bypassing glsl_to_tgsi: */ struct gl_shader_program *shader_program; - union { - struct st_common_variant *variants; - struct st_vp_variant *vp_variants; - struct st_fp_variant *fp_variants; - }; + struct st_variant *variants; }; @@ -285,6 +284,24 @@ st_reference_prog(struct st_context *st, (struct gl_program *) prog); } +static inline struct st_common_variant * +st_common_variant(struct st_variant *v) +{ + return (struct st_common_variant*)v; +} + +static inline struct st_vp_variant * +st_vp_variant(struct st_variant *v) +{ + return (struct st_vp_variant*)v; +} + +static inline struct st_fp_variant * +st_fp_variant(struct st_variant *v) +{ + return (struct st_fp_variant*)v; +} + /** * This defines mapping from Mesa VARYING_SLOTs to TGSI GENERIC slots. */ @@ -309,21 +326,13 @@ st_get_fp_variant(struct st_context *st, struct st_program *stfp, const struct st_fp_variant_key *key); -extern struct st_common_variant * +extern struct st_variant * st_get_common_variant(struct st_context *st, struct st_program *p, const struct st_common_variant_key *key); extern void -st_release_vp_variants( struct st_context *st, - struct st_program *stvp ); - -extern void -st_release_fp_variants( struct st_context *st, - struct st_program *stfp ); - -extern void -st_release_common_variants(struct st_context *st, struct st_program *p); +st_release_variants(struct st_context *st, struct st_program *p); extern void st_destroy_program_variants(struct st_context *st); diff --git a/src/mesa/state_tracker/st_shader_cache.c b/src/mesa/state_tracker/st_shader_cache.c index 6145281573f..17cd8b0b835 100644 --- a/src/mesa/state_tracker/st_shader_cache.c +++ b/src/mesa/state_tracker/st_shader_cache.c @@ -184,9 +184,9 @@ st_deserialise_ir_program(struct gl_context *ctx, struct blob_reader blob_reader; blob_reader_init(&blob_reader, buffer, size); - if (prog->info.stage == MESA_SHADER_VERTEX) { - st_release_vp_variants(st, stp); + st_release_variants(st, stp); + if (prog->info.stage == MESA_SHADER_VERTEX) { struct st_vertex_program *stvp = (struct st_vertex_program *)stp; stvp->num_inputs = blob_read_uint32(&blob_reader); blob_copy_bytes(&blob_reader, (uint8_t *) stvp->index_to_input, @@ -195,10 +195,6 @@ st_deserialise_ir_program(struct gl_context *ctx, sizeof(stvp->input_to_index)); blob_copy_bytes(&blob_reader, (uint8_t *) stvp->result_to_output, sizeof(stvp->result_to_output)); - } else if (prog->info.stage == MESA_SHADER_FRAGMENT) { - st_release_fp_variants(st, stp); - } else { - st_release_common_variants(st, stp); } if (prog->info.stage == MESA_SHADER_VERTEX || |