radeonsi: support for external buffers (ext_external_objects)

So far, the callback to create a resource from a memory object had code
for importing textures only. Modified it to allow importing buffers too.

Fixes the following piglit tests:
- ext_external_objects/vk-buf-exchange
- ext_external_objects/vk-pix-buf-update-errors
- ext_external_objects/vk-vert-buf-update-errors
- ext_external_objects/vk-vert-buf-reuse

v2: Used si_alloc_buffer_struct instead of CALLOC
v3: Fixed indentation issue, removed free in case of unsuccessful
allocation, joined two if conditions together

Signed-off-by: Eleni Maria Stea <estea@igalia.com>
Reviewed-by: Marek Olšák <marek.olsak@amd.com>
Acked-by: Pierre-Eric Pelloux-Prayer <pierre-eric.pelloux-prayer@amd.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/6364>
This commit is contained in:
Eleni Maria Stea 2020-09-22 14:23:22 +03:00 committed by Marge Bot
parent df63491594
commit 03af98abe2
3 changed files with 54 additions and 7 deletions

View file

@ -731,6 +731,39 @@ static struct pipe_resource *si_buffer_from_user_memory(struct pipe_screen *scre
return &buf->b.b;
}
struct pipe_resource *si_buffer_from_winsys_buffer(struct pipe_screen *screen,
const struct pipe_resource *templ,
struct pb_buffer *imported_buf,
bool dedicated)
{
struct si_screen *sscreen = (struct si_screen *)screen;
struct si_resource *res = si_alloc_buffer_struct(screen, templ);
if (!res)
return 0;
res->buf = imported_buf;
res->gpu_address = sscreen->ws->buffer_get_virtual_address(res->buf);
res->bo_size = imported_buf->size;
res->bo_alignment = imported_buf->alignment;
res->domains = sscreen->ws->buffer_get_initial_domain(res->buf);
if (res->domains & RADEON_DOMAIN_VRAM)
res->vram_usage = res->bo_size;
else if (res->domains & RADEON_DOMAIN_GTT)
res->gart_usage = res->bo_size;
if (sscreen->ws->buffer_get_flags)
res->flags = sscreen->ws->buffer_get_flags(res->buf);
if (templ->flags & PIPE_RESOURCE_FLAG_SPARSE) {
res->b.b.flags |= SI_RESOURCE_FLAG_UNMAPPABLE;
res->flags |= RADEON_FLAG_SPARSE;
}
return &res->b.b;
}
static struct pipe_resource *si_resource_create(struct pipe_screen *screen,
const struct pipe_resource *templ)
{

View file

@ -1926,4 +1926,9 @@ static inline unsigned si_get_shader_wave_size(struct si_shader *shader)
#define PRINT_ERR(fmt, args...) \
fprintf(stderr, "EE %s:%d %s - " fmt, __FILE__, __LINE__, __func__, ##args)
struct pipe_resource *si_buffer_from_winsys_buffer(struct pipe_screen *screen,
const struct pipe_resource *templ,
struct pb_buffer *imported_buf,
bool dedicated);
#endif

View file

@ -2271,17 +2271,26 @@ static void si_memobj_destroy(struct pipe_screen *screen, struct pipe_memory_obj
free(memobj);
}
static struct pipe_resource *si_texture_from_memobj(struct pipe_screen *screen,
static struct pipe_resource *si_resource_from_memobj(struct pipe_screen *screen,
const struct pipe_resource *templ,
struct pipe_memory_object *_memobj,
uint64_t offset)
{
struct si_screen *sscreen = (struct si_screen *)screen;
struct si_memory_object *memobj = (struct si_memory_object *)_memobj;
struct pipe_resource *tex = si_texture_from_winsys_buffer(
sscreen, templ, memobj->buf, memobj->stride, offset,
PIPE_HANDLE_USAGE_FRAMEBUFFER_WRITE | PIPE_HANDLE_USAGE_SHADER_WRITE, memobj->b.dedicated);
if (!tex)
struct pipe_resource *res;
if (templ->target == PIPE_BUFFER)
res = si_buffer_from_winsys_buffer(screen, templ, memobj->buf,
memobj->b.dedicated);
else
res = si_texture_from_winsys_buffer(sscreen, templ, memobj->buf,
memobj->stride,
offset,
PIPE_HANDLE_USAGE_FRAMEBUFFER_WRITE | PIPE_HANDLE_USAGE_SHADER_WRITE,
memobj->b.dedicated);
if (!res)
return NULL;
/* si_texture_from_winsys_buffer doesn't increment refcount of
@ -2289,7 +2298,7 @@ static struct pipe_resource *si_texture_from_memobj(struct pipe_screen *screen,
*/
struct pb_buffer *buf = NULL;
pb_reference(&buf, memobj->buf);
return tex;
return res;
}
static bool si_check_resource_capability(struct pipe_screen *screen, struct pipe_resource *resource,
@ -2317,7 +2326,7 @@ void si_init_screen_texture_functions(struct si_screen *sscreen)
sscreen->b.resource_get_handle = si_texture_get_handle;
sscreen->b.resource_get_param = si_resource_get_param;
sscreen->b.resource_get_info = si_texture_get_info;
sscreen->b.resource_from_memobj = si_texture_from_memobj;
sscreen->b.resource_from_memobj = si_resource_from_memobj;
sscreen->b.memobj_create_from_handle = si_memobj_from_handle;
sscreen->b.memobj_destroy = si_memobj_destroy;
sscreen->b.check_resource_capability = si_check_resource_capability;