From 3ee2e98aff4fdddda626d61f2e45bf25bd76d4f5 Mon Sep 17 00:00:00 2001 From: Dave Airlie Date: Mon, 23 Oct 2017 06:48:30 +0100 Subject: [PATCH] st/program: add support for gs/tes/tcs nir shaders. This probably needs more work but this just add the initial code to convert gs/tcs/tes nir based shaders in the state tracker. Reviewed-by: Timothy Arceri Signed-off-by: Dave Airlie --- src/mesa/state_tracker/st_glsl_to_nir.cpp | 12 ++++++ src/mesa/state_tracker/st_program.c | 45 +++++++++++++++++++++-- src/mesa/state_tracker/st_program.h | 3 ++ 3 files changed, 56 insertions(+), 4 deletions(-) diff --git a/src/mesa/state_tracker/st_glsl_to_nir.cpp b/src/mesa/state_tracker/st_glsl_to_nir.cpp index 4effd8074ed..e9a8d6414e7 100644 --- a/src/mesa/state_tracker/st_glsl_to_nir.cpp +++ b/src/mesa/state_tracker/st_glsl_to_nir.cpp @@ -359,6 +359,11 @@ st_finalize_nir(struct st_context *st, struct gl_program *prog, nir_shader *nir) case MESA_SHADER_VERTEX: shader_program = ((struct st_vertex_program *)prog)->shader_program; break; + case MESA_SHADER_GEOMETRY: + case MESA_SHADER_TESS_CTRL: + case MESA_SHADER_TESS_EVAL: + shader_program = ((struct st_common_program *)prog)->shader_program; + break; case MESA_SHADER_FRAGMENT: shader_program = ((struct st_fragment_program *)prog)->shader_program; break; @@ -451,6 +456,7 @@ st_nir_get_mesa_program(struct gl_context *ctx, _mesa_associate_uniform_storage(ctx, shader_program, prog, true); struct st_vertex_program *stvp; + struct st_common_program *stp; struct st_fragment_program *stfp; struct st_compute_program *stcp; @@ -459,6 +465,12 @@ st_nir_get_mesa_program(struct gl_context *ctx, stvp = (struct st_vertex_program *)prog; stvp->shader_program = shader_program; break; + case MESA_SHADER_GEOMETRY: + case MESA_SHADER_TESS_CTRL: + case MESA_SHADER_TESS_EVAL: + stp = (struct st_common_program *)prog; + stp->shader_program = shader_program; + break; case MESA_SHADER_FRAGMENT: stfp = (struct st_fragment_program *)prog; stfp->shader_program = shader_program; diff --git a/src/mesa/state_tracker/st_program.c b/src/mesa/state_tracker/st_program.c index 1695f4835db..335d45ba282 100644 --- a/src/mesa/state_tracker/st_program.c +++ b/src/mesa/state_tracker/st_program.c @@ -1576,6 +1576,16 @@ st_translate_geometry_program(struct st_context *st, { struct ureg_program *ureg; + if (stgp->shader_program) { + nir_shader *nir = st_glsl_to_nir(st, &stgp->Base, stgp->shader_program, + MESA_SHADER_GEOMETRY); + + stgp->tgsi.type = PIPE_SHADER_IR_NIR; + stgp->tgsi.ir.nir = nir; + + return true; + } + ureg = ureg_create_with_screen(PIPE_SHADER_GEOMETRY, st->pipe->screen); if (ureg == NULL) return false; @@ -1609,7 +1619,7 @@ st_get_basic_variant(struct st_context *st, struct pipe_context *pipe = st->pipe; struct st_basic_variant *v; struct st_basic_variant_key key; - + struct pipe_shader_state tgsi = {0}; memset(&key, 0, sizeof(key)); key.st = st->has_shareable_shaders ? NULL : st; @@ -1624,16 +1634,23 @@ st_get_basic_variant(struct st_context *st, /* create new */ v = CALLOC_STRUCT(st_basic_variant); if (v) { + + if (prog->tgsi.type == PIPE_SHADER_IR_NIR) { + tgsi.type = PIPE_SHADER_IR_NIR; + tgsi.ir.nir = nir_shader_clone(NULL, prog->tgsi.ir.nir); + st_finalize_nir(st, &prog->Base, tgsi.ir.nir); + } else + tgsi = prog->tgsi; /* fill in new variant */ switch (pipe_shader) { case PIPE_SHADER_TESS_CTRL: - v->driver_shader = pipe->create_tcs_state(pipe, &prog->tgsi); + v->driver_shader = pipe->create_tcs_state(pipe, &tgsi); break; case PIPE_SHADER_TESS_EVAL: - v->driver_shader = pipe->create_tes_state(pipe, &prog->tgsi); + v->driver_shader = pipe->create_tes_state(pipe, &tgsi); break; case PIPE_SHADER_GEOMETRY: - v->driver_shader = pipe->create_gs_state(pipe, &prog->tgsi); + v->driver_shader = pipe->create_gs_state(pipe, &tgsi); break; default: assert(!"unhandled shader type"); @@ -1662,6 +1679,16 @@ st_translate_tessctrl_program(struct st_context *st, { struct ureg_program *ureg; + if (sttcp->shader_program) { + nir_shader *nir = st_glsl_to_nir(st, &sttcp->Base, sttcp->shader_program, + MESA_SHADER_TESS_EVAL); + + sttcp->tgsi.type = PIPE_SHADER_IR_NIR; + sttcp->tgsi.ir.nir = nir; + + return true; + } + ureg = ureg_create_with_screen(PIPE_SHADER_TESS_CTRL, st->pipe->screen); if (ureg == NULL) return false; @@ -1687,6 +1714,16 @@ st_translate_tesseval_program(struct st_context *st, { struct ureg_program *ureg; + if (sttep->shader_program) { + nir_shader *nir = st_glsl_to_nir(st, &sttep->Base, sttep->shader_program, + MESA_SHADER_TESS_EVAL); + + sttep->tgsi.type = PIPE_SHADER_IR_NIR; + sttep->tgsi.ir.nir = nir; + + return true; + } + ureg = ureg_create_with_screen(PIPE_SHADER_TESS_EVAL, st->pipe->screen); if (ureg == NULL) return false; diff --git a/src/mesa/state_tracker/st_program.h b/src/mesa/state_tracker/st_program.h index 27cc9b6e92f..6049fba517b 100644 --- a/src/mesa/state_tracker/st_program.h +++ b/src/mesa/state_tracker/st_program.h @@ -260,6 +260,9 @@ struct st_common_program struct glsl_to_tgsi_visitor* glsl_to_tgsi; uint64_t affected_states; /**< ST_NEW_* flags to mark dirty when binding */ + /* used when bypassing glsl_to_tgsi: */ + struct gl_shader_program *shader_program; + struct st_basic_variant *variants; /** SHA1 hash of linked tgsi shader program, used for on-disk cache */ -- 2.30.2