zink: cache programs

Acked-by: Jordan Justen <jordan.l.justen@intel.com>
This commit is contained in:
Erik Faye-Lund 2019-03-26 13:52:09 +01:00
parent fba0293bef
commit 1cdbeefd2c
2 changed files with 61 additions and 9 deletions

View File

@ -257,12 +257,20 @@ zink_create_vs_state(struct pipe_context *pctx,
return zink_compile_nir(zink_screen(pctx->screen), nir);
}
static void
bind_stage(struct zink_context *ctx, enum pipe_shader_type stage,
struct zink_shader *shader)
{
assert(stage < PIPE_SHADER_COMPUTE);
ctx->gfx_stages[stage] = shader;
ctx->dirty |= ZINK_DIRTY_PROGRAM;
}
static void
zink_bind_vs_state(struct pipe_context *pctx,
void *cso)
{
struct zink_context *ctx = zink_context(pctx);
ctx->gfx_stages[PIPE_SHADER_VERTEX] = cso;
bind_stage(zink_context(pctx), PIPE_SHADER_VERTEX, cso);
}
static void
@ -289,8 +297,7 @@ static void
zink_bind_fs_state(struct pipe_context *pctx,
void *cso)
{
struct zink_context *ctx = zink_context(pctx);
ctx->gfx_stages[PIPE_SHADER_FRAGMENT] = cso;
bind_stage(zink_context(pctx), PIPE_SHADER_FRAGMENT, cso);
}
static void
@ -770,6 +777,40 @@ begin_render_pass(struct zink_cmdbuf *cmdbuf, struct zink_render_pass *rp,
vkCmdBeginRenderPass(cmdbuf->cmdbuf, &rpbi, VK_SUBPASS_CONTENTS_INLINE);
}
static uint32_t
hash_gfx_program(const void *key)
{
return _mesa_hash_data(key, sizeof(struct zink_shader *) * (PIPE_SHADER_TYPES - 1));
}
static bool
equals_gfx_program(const void *a, const void *b)
{
return memcmp(a, b, sizeof(struct zink_shader *) * (PIPE_SHADER_TYPES - 1)) == 0;
}
static struct zink_gfx_program *
get_gfx_program(struct zink_context *ctx)
{
if (ctx->dirty & ZINK_DIRTY_PROGRAM) {
struct hash_entry *entry = _mesa_hash_table_search(ctx->program_cache,
ctx->gfx_stages);
if (!entry) {
struct zink_gfx_program *prog;
prog = zink_create_gfx_program(zink_screen(ctx->base.screen)->dev,
ctx->gfx_stages);
entry = _mesa_hash_table_insert(ctx->program_cache, prog->stages, prog);
if (!entry)
return NULL;
}
ctx->curr_program = entry->data;
ctx->dirty &= ~ZINK_DIRTY_PROGRAM;
}
assert(ctx->curr_program);
return ctx->curr_program;
}
static void
zink_draw_vbo(struct pipe_context *pctx,
const struct pipe_draw_info *dinfo)
@ -788,8 +829,7 @@ zink_draw_vbo(struct pipe_context *pctx,
return;
}
struct zink_gfx_program *gfx_program = zink_create_gfx_program(screen->dev,
ctx->gfx_stages);
struct zink_gfx_program *gfx_program = get_gfx_program(ctx);
if (!gfx_program)
return;
@ -1217,6 +1257,12 @@ zink_context_create(struct pipe_screen *pscreen, void *priv, unsigned flags)
vkGetDeviceQueue(screen->dev, screen->gfx_queue, 0, &ctx->queue);
ctx->program_cache = _mesa_hash_table_create(NULL, hash_gfx_program, equals_gfx_program);
if (!ctx->program_cache)
goto fail;
ctx->dirty = ZINK_DIRTY_PROGRAM;
return &ctx->base;
fail:

View File

@ -36,12 +36,13 @@
struct blitter_context;
struct primconvert_context;
struct zink_resource;
struct zink_vertex_elements_state;
struct zink_rasterizer_state;
struct zink_blend_state;
struct zink_depth_stencil_alpha_state;
struct zink_gfx_program;
struct zink_rasterizer_state;
struct zink_resource;
struct zink_vertex_elements_state;
struct zink_sampler_view {
struct pipe_sampler_view base;
@ -54,6 +55,8 @@ zink_sampler_view(struct pipe_sampler_view *pview)
return (struct zink_sampler_view *)pview;
}
#define ZINK_DIRTY_PROGRAM (1 << 0)
struct zink_context {
struct pipe_context base;
struct slab_child_pool transfer_pool;
@ -71,6 +74,9 @@ struct zink_context {
struct zink_shader *gfx_stages[PIPE_SHADER_TYPES - 1];
struct zink_gfx_pipeline_state gfx_pipeline_state;
struct hash_table *program_cache;
struct zink_gfx_program *curr_program;
unsigned dirty;
struct primconvert_context *primconvert;