From 65570588275e0c3a9823018f0d781014c1512303 Mon Sep 17 00:00:00 2001 From: Samuel Pitoiset Date: Wed, 31 Aug 2016 22:52:46 +0200 Subject: nvc0: allow to resize the code segment dynamically When an application uses a ton of shaders, we need to evict them when the code segment is full but this is not really a good solution if monster shaders are used because code eviction will happen a lot. To avoid this, it seems better to dynamically resize the code segment area after each eviction. The maximum size is arbitrary fixed to 8MB which should be enough. Signed-off-by: Samuel Pitoiset Reviewed-by: Ilia Mirkin --- src/gallium/drivers/nouveau/nvc0/nvc0_program.c | 25 ++++++++++++++++++++++++- 1 file changed, 24 insertions(+), 1 deletion(-) (limited to 'src/gallium/drivers/nouveau/nvc0') diff --git a/src/gallium/drivers/nouveau/nvc0/nvc0_program.c b/src/gallium/drivers/nouveau/nvc0/nvc0_program.c index 66640eacbe8..9f29b2983cc 100644 --- a/src/gallium/drivers/nouveau/nvc0/nvc0_program.c +++ b/src/gallium/drivers/nouveau/nvc0/nvc0_program.c @@ -788,12 +788,35 @@ nvc0_program_upload(struct nvc0_context *nvc0, struct nvc0_program *prog) } debug_printf("WARNING: out of code space, evicting all shaders.\n"); + /* Make sure to synchronize before deleting the code segment. */ + IMMED_NVC0(nvc0->base.pushbuf, NVC0_3D(SERIALIZE), 0); + + if ((screen->text->size << 1) <= (1 << 23)) { + ret = nvc0_screen_resize_text_area(screen, screen->text->size << 1); + if (ret) { + NOUVEAU_ERR("Error allocating TEXT area: %d\n", ret); + return false; + } + nouveau_bufctx_reset(nvc0->bufctx_3d, NVC0_BIND_3D_TEXT); + BCTX_REFN_bo(nvc0->bufctx_3d, 3D_TEXT, + NV_VRAM_DOMAIN(&screen->base) | NOUVEAU_BO_RD, + screen->text); + if (screen->compute) { + nouveau_bufctx_reset(nvc0->bufctx_cp, NVC0_BIND_CP_TEXT); + BCTX_REFN_bo(nvc0->bufctx_cp, CP_TEXT, + NV_VRAM_DOMAIN(&screen->base) | NOUVEAU_BO_RD, + screen->text); + } + + /* Re-upload the builtin function into the new code segment. */ + nvc0_program_library_upload(nvc0); + } + ret = nvc0_program_alloc_code(nvc0, prog); if (ret) { NOUVEAU_ERR("shader too large (0x%x) to fit in code space ?\n", size); return false; } - IMMED_NVC0(nvc0->base.pushbuf, NVC0_3D(SERIALIZE), 0); /* All currently bound shaders have to be reuploaded. */ for (int i = 0; i < ARRAY_SIZE(progs); i++) { -- cgit v1.2.3