llvmpipe: start adding task/mesh support.

This is just some infrastructure for creating shaders and contexts.

task/mesh shaders are based on compute shaders and share nearly all
their code with compute.

Reviewed-by: Roland Scheidegger <sroland@vmware.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/23066>
This commit is contained in:
Dave Airlie
2023-05-17 11:47:55 +10:00
parent b0b81b279c
commit d9fae96618
5 changed files with 163 additions and 0 deletions
+16
View File
@@ -64,6 +64,12 @@ llvmpipe_destroy(struct pipe_context *pipe)
if (llvmpipe->csctx) {
lp_csctx_destroy(llvmpipe->csctx);
}
if (llvmpipe->task_ctx) {
lp_csctx_destroy(llvmpipe->task_ctx);
}
if (llvmpipe->mesh_ctx) {
lp_csctx_destroy(llvmpipe->mesh_ctx);
}
if (llvmpipe->blitter) {
util_blitter_destroy(llvmpipe->blitter);
}
@@ -240,6 +246,8 @@ llvmpipe_create_context(struct pipe_screen *screen, void *priv,
llvmpipe_init_vs_funcs(llvmpipe);
llvmpipe_init_gs_funcs(llvmpipe);
llvmpipe_init_tess_funcs(llvmpipe);
llvmpipe_init_task_funcs(llvmpipe);
llvmpipe_init_mesh_funcs(llvmpipe);
llvmpipe_init_rasterizer_funcs(llvmpipe);
llvmpipe_init_context_resource_funcs(&llvmpipe->pipe);
llvmpipe_init_surface_functions(llvmpipe);
@@ -283,6 +291,14 @@ llvmpipe_create_context(struct pipe_screen *screen, void *priv,
if (!llvmpipe->csctx)
goto fail;
llvmpipe->task_ctx = lp_csctx_create(&llvmpipe->pipe);
if (!llvmpipe->task_ctx)
goto fail;
llvmpipe->mesh_ctx = lp_csctx_create(&llvmpipe->pipe);
if (!llvmpipe->mesh_ctx)
goto fail;
llvmpipe->pipe.stream_uploader = u_upload_create_default(&llvmpipe->pipe);
if (!llvmpipe->pipe.stream_uploader)
goto fail;
@@ -74,6 +74,9 @@ struct llvmpipe_context {
const struct lp_velems_state *velems;
const struct lp_so_state *so;
struct lp_compute_shader *tss;
struct lp_compute_shader *mhs;
/** Other rendering state */
unsigned sample_mask;
unsigned min_samples;
@@ -171,6 +174,9 @@ struct llvmpipe_context {
unsigned nr_cs_instrs;
struct lp_cs_context *csctx;
struct lp_cs_context *task_ctx;
struct lp_cs_context *mesh_ctx;
/** Conditional query object and mode */
struct pipe_query *render_cond_query;
enum pipe_render_cond_flag render_cond_mode;
+6
View File
@@ -152,6 +152,12 @@ llvmpipe_init_gs_funcs(struct llvmpipe_context *llvmpipe);
void
llvmpipe_init_tess_funcs(struct llvmpipe_context *llvmpipe);
void
llvmpipe_init_task_funcs(struct llvmpipe_context *llvmpipe);
void
llvmpipe_init_mesh_funcs(struct llvmpipe_context *llvmpipe);
void
llvmpipe_init_rasterizer_funcs(struct llvmpipe_context *llvmpipe);
+134
View File
@@ -51,9 +51,12 @@
#include "util/mesa-sha1.h"
#include "nir_serialize.h"
#include "draw/draw_context.h"
/** Fragment shader number (for debugging) */
static unsigned cs_no = 0;
static unsigned task_no = 0;
static unsigned mesh_no = 0;
struct lp_cs_job_info {
unsigned grid_size[3];
@@ -1621,3 +1624,134 @@ lp_csctx_create(struct pipe_context *pipe)
csctx->pipe = pipe;
return csctx;
}
static void *
llvmpipe_create_ts_state(struct pipe_context *pipe,
const struct pipe_shader_state *templ)
{
struct lp_compute_shader *shader = CALLOC_STRUCT(lp_compute_shader);
if (!shader)
return NULL;
shader->no = task_no++;
shader->base.type = templ->type;
shader->base.ir.nir = templ->ir.nir;
shader->req_local_mem += ((struct nir_shader *)shader->base.ir.nir)->info.shared_size;
nir_tgsi_scan_shader(shader->base.ir.nir, &shader->info.base, false);
list_inithead(&shader->variants.list);
int nr_samplers = shader->info.base.file_max[TGSI_FILE_SAMPLER] + 1;
int nr_sampler_views = shader->info.base.file_max[TGSI_FILE_SAMPLER_VIEW] + 1;
int nr_images = shader->info.base.file_max[TGSI_FILE_IMAGE] + 1;
shader->variant_key_size = lp_cs_variant_key_size(MAX2(nr_samplers, nr_sampler_views), nr_images);
return shader;
}
static void
llvmpipe_bind_ts_state(struct pipe_context *pipe, void *_task)
{
struct llvmpipe_context *llvmpipe = llvmpipe_context(pipe);
if (llvmpipe->tss == _task)
return;
llvmpipe->tss = (struct lp_compute_shader *)_task;
}
static void
llvmpipe_delete_ts_state(struct pipe_context *pipe, void *_task)
{
struct llvmpipe_context *llvmpipe = llvmpipe_context(pipe);
struct lp_compute_shader *shader = _task;
struct lp_cs_variant_list_item *li, *next;
/* Delete all the variants */
LIST_FOR_EACH_ENTRY_SAFE(li, next, &shader->variants.list, list) {
llvmpipe_remove_cs_shader_variant(llvmpipe, li->base);
}
if (shader->base.ir.nir)
ralloc_free(shader->base.ir.nir);
FREE(shader);
}
void
llvmpipe_init_task_funcs(struct llvmpipe_context *llvmpipe)
{
llvmpipe->pipe.create_ts_state = llvmpipe_create_ts_state;
llvmpipe->pipe.bind_ts_state = llvmpipe_bind_ts_state;
llvmpipe->pipe.delete_ts_state = llvmpipe_delete_ts_state;
}
static void *
llvmpipe_create_ms_state(struct pipe_context *pipe,
const struct pipe_shader_state *templ)
{
struct llvmpipe_context *llvmpipe = llvmpipe_context(pipe);
struct lp_compute_shader *shader = CALLOC_STRUCT(lp_compute_shader);
if (!shader)
return NULL;
shader->no = mesh_no++;
shader->base.type = templ->type;
shader->base.ir.nir = templ->ir.nir;
shader->req_local_mem += ((struct nir_shader *)shader->base.ir.nir)->info.shared_size;
nir_tgsi_scan_shader(shader->base.ir.nir, &shader->info.base, false);
list_inithead(&shader->variants.list);
shader->draw_mesh_data = draw_create_mesh_shader(llvmpipe->draw, templ);
if (shader->draw_mesh_data == NULL) {
FREE(shader);
return NULL;
}
int nr_samplers = shader->info.base.file_max[TGSI_FILE_SAMPLER] + 1;
int nr_sampler_views = shader->info.base.file_max[TGSI_FILE_SAMPLER_VIEW] + 1;
int nr_images = shader->info.base.file_max[TGSI_FILE_IMAGE] + 1;
shader->variant_key_size = lp_cs_variant_key_size(MAX2(nr_samplers, nr_sampler_views), nr_images);
return shader;
}
static void
llvmpipe_bind_ms_state(struct pipe_context *pipe, void *_mesh)
{
struct llvmpipe_context *llvmpipe = llvmpipe_context(pipe);
if (llvmpipe->mhs == _mesh)
return;
llvmpipe->mhs = (struct lp_compute_shader *)_mesh;
draw_bind_mesh_shader(llvmpipe->draw, _mesh ? llvmpipe->mhs->draw_mesh_data : NULL);
}
static void
llvmpipe_delete_ms_state(struct pipe_context *pipe, void *_mesh)
{
struct llvmpipe_context *llvmpipe = llvmpipe_context(pipe);
struct lp_compute_shader *shader = _mesh;
struct lp_cs_variant_list_item *li, *next;
/* Delete all the variants */
LIST_FOR_EACH_ENTRY_SAFE(li, next, &shader->variants.list, list) {
llvmpipe_remove_cs_shader_variant(llvmpipe, li->base);
}
draw_delete_mesh_shader(llvmpipe->draw, shader->draw_mesh_data);
if (shader->base.ir.nir)
ralloc_free(shader->base.ir.nir);
FREE(shader);
}
void
llvmpipe_init_mesh_funcs(struct llvmpipe_context *llvmpipe)
{
llvmpipe->pipe.create_ms_state = llvmpipe_create_ms_state;
llvmpipe->pipe.bind_ms_state = llvmpipe_bind_ms_state;
llvmpipe->pipe.delete_ms_state = llvmpipe_delete_ms_state;
}
@@ -110,6 +110,7 @@ struct lp_compute_shader {
struct lp_tgsi_info info;
struct draw_mesh_shader *draw_mesh_data;
uint32_t req_local_mem;
/* For debugging/profiling purposes */