diff --git a/src/virglrenderer.c b/src/virglrenderer.c index 955ea87..06f8124 100644 --- a/src/virglrenderer.c +++ b/src/virglrenderer.c @@ -89,7 +89,27 @@ void virgl_renderer_fill_caps(uint32_t set, uint32_t version, int virgl_renderer_context_create(uint32_t handle, uint32_t nlen, const char *name) { - return vrend_renderer_context_create(handle, nlen, name); + struct virgl_context *ctx; + int ret; + + /* user context id must be greater than 0 */ + if (handle == 0) + return EINVAL; + + if (virgl_context_lookup(handle)) + return 0; + + ctx = vrend_renderer_context_create(handle, nlen, name); + if (!ctx) + return ENOMEM; + + ret = virgl_context_add(ctx); + if (ret) { + ctx->destroy(ctx); + return ret; + } + + return 0; } void virgl_renderer_context_destroy(uint32_t handle) diff --git a/src/vrend_decode.c b/src/vrend_decode.c index e8e1345..a2f1f4e 100644 --- a/src/vrend_decode.c +++ b/src/vrend_decode.c @@ -1387,59 +1387,37 @@ static int vrend_decode_copy_transfer3d(struct vrend_decode_ctx *ctx, int length static void vrend_decode_ctx_init_base(struct vrend_decode_ctx *dctx, uint32_t ctx_id); -static struct vrend_decode_ctx * -vrend_decode_ctx_lookup(uint32_t ctx_id) -{ - return ctx_id ? - (struct vrend_decode_ctx *)virgl_context_lookup(ctx_id) : - dec_ctx0; -} - -void vrend_renderer_context_create_internal(uint32_t handle, uint32_t nlen, - const char *debug_name) +struct virgl_context *vrend_renderer_context_create(uint32_t handle, + uint32_t nlen, + const char *debug_name) { struct vrend_decode_ctx *dctx; - dctx = vrend_decode_ctx_lookup(handle); - if (dctx) - return; - dctx = malloc(sizeof(struct vrend_decode_ctx)); if (!dctx) - return; + return NULL; vrend_decode_ctx_init_base(dctx, handle); dctx->grctx = vrend_create_context(handle, nlen, debug_name); if (!dctx->grctx) { free(dctx); - return; + return NULL; } dctx->ds = &dctx->ids; - if (handle) { - if (virgl_context_add(&dctx->base)) { - dctx->base.destroy(&dctx->base); - } - } else { - dec_ctx0 = dctx; - } -} - -int vrend_renderer_context_create(uint32_t handle, uint32_t nlen, const char *debug_name) -{ - /* context 0 is always available with no guarantees */ if (handle == 0) - return EINVAL; + dec_ctx0 = dctx; - vrend_renderer_context_create_internal(handle, nlen, debug_name); - return 0; + return &dctx->base; } struct vrend_context *vrend_lookup_renderer_ctx(uint32_t ctx_id) { - struct vrend_decode_ctx *dctx = vrend_decode_ctx_lookup(ctx_id); + struct vrend_decode_ctx *dctx = ctx_id ? + (struct vrend_decode_ctx *)virgl_context_lookup(ctx_id) : + dec_ctx0; return dctx ? dctx->grctx : NULL; } diff --git a/src/vrend_renderer.c b/src/vrend_renderer.c index cf63c1d..7d28822 100644 --- a/src/vrend_renderer.c +++ b/src/vrend_renderer.c @@ -5868,7 +5868,7 @@ int vrend_renderer_init(struct vrend_if_cbs *cbs, uint32_t flags) list_inithead(&vrend_state.waiting_query_list); list_inithead(&vrend_state.active_ctx_list); /* create 0 context */ - vrend_renderer_context_create_internal(0, strlen("HOST"), "HOST"); + vrend_renderer_context_create(0, strlen("HOST"), "HOST"); vrend_state.eventfd = -1; if (flags & VREND_USE_THREAD_SYNC) { @@ -10285,7 +10285,7 @@ void vrend_renderer_reset(void) vrend_object_fini_resource_table(); vrend_decode_reset(true); vrend_object_init_resource_table(); - vrend_renderer_context_create_internal(0, strlen("HOST"), "HOST"); + vrend_renderer_context_create(0, strlen("HOST"), "HOST"); } int vrend_renderer_get_poll_fd(void) diff --git a/src/vrend_renderer.h b/src/vrend_renderer.h index b8da54d..cba8c2b 100644 --- a/src/vrend_renderer.h +++ b/src/vrend_renderer.h @@ -44,6 +44,7 @@ struct virgl_gl_ctx_param { bool shared; }; +struct virgl_context; struct vrend_context; /* Number of mipmap levels for which to keep the backing iov offsets. @@ -164,8 +165,9 @@ void vrend_set_framebuffer_state(struct vrend_context *ctx, struct vrend_context *vrend_create_context(int id, uint32_t nlen, const char *debug_name); bool vrend_destroy_context(struct vrend_context *ctx); -int vrend_renderer_context_create(uint32_t handle, uint32_t nlen, const char *name); -void vrend_renderer_context_create_internal(uint32_t handle, uint32_t nlen, const char *name); +struct virgl_context *vrend_renderer_context_create(uint32_t handle, + uint32_t nlen, + const char *name); struct vrend_renderer_resource_create_args { uint32_t handle;