[Mesa-dev] [PATCH] winsys/radeon: Store GPU virtual memory addresses of BOs in a hash table
Marek Olšák
maraeo at gmail.com
Thu Mar 13 07:09:26 PDT 2014
Reviewed-by: Marek Olšák <marek.olsak at amd.com>
Marek
On Thu, Mar 13, 2014 at 9:34 AM, Michel Dänzer <michel at daenzer.net> wrote:
> From: Michel Dänzer <michel.daenzer at amd.com>
>
> This allows retrieving the existing BO and incrementing its reference count,
> instead of creating a separate winsys representation for it, when the kernel
> reports that the BO was already assigned a virtual memory address.
>
> This fixes problems with XWayland using radeonsi and the
> xf86-video-wlglamor driver, which calls GEM flink outside of the radeon
> winsys code and creates BOs from the flinked names using the same DRM file
> descriptor.
>
> Signed-off-by: Michel Dänzer <michel.daenzer at amd.com>
> ---
> src/gallium/winsys/radeon/drm/radeon_drm_bo.c | 74 ++++++++++-----------------
> 1 file changed, 26 insertions(+), 48 deletions(-)
>
> diff --git a/src/gallium/winsys/radeon/drm/radeon_drm_bo.c b/src/gallium/winsys/radeon/drm/radeon_drm_bo.c
> index 2ac060b..7dd5e7f 100644
> --- a/src/gallium/winsys/radeon/drm/radeon_drm_bo.c
> +++ b/src/gallium/winsys/radeon/drm/radeon_drm_bo.c
> @@ -120,6 +120,8 @@ struct radeon_bomgr {
> struct util_hash_table *bo_names;
> /* List of buffer handles. Protectded by bo_handles_mutex. */
> struct util_hash_table *bo_handles;
> + /* List of buffer virtual memory ranges. Protectded by bo_handles_mutex. */
> + struct util_hash_table *bo_vas;
> pipe_mutex bo_handles_mutex;
> pipe_mutex bo_va_mutex;
>
> @@ -260,48 +262,6 @@ static uint64_t radeon_bomgr_find_va(struct radeon_bomgr *mgr, uint64_t size, ui
> return offset;
> }
>
> -static void radeon_bomgr_force_va(struct radeon_bomgr *mgr, uint64_t va, uint64_t size)
> -{
> - size = align(size, 4096);
> -
> - pipe_mutex_lock(mgr->bo_va_mutex);
> - if (va >= mgr->va_offset) {
> - if (va > mgr->va_offset) {
> - struct radeon_bo_va_hole *hole;
> - hole = CALLOC_STRUCT(radeon_bo_va_hole);
> - if (hole) {
> - hole->size = va - mgr->va_offset;
> - hole->offset = mgr->va_offset;
> - list_add(&hole->list, &mgr->va_holes);
> - }
> - }
> - mgr->va_offset = va + size;
> - } else {
> - struct radeon_bo_va_hole *hole, *n;
> - uint64_t hole_end, va_end;
> -
> - /* Prune/free all holes that fall into the range
> - */
> - LIST_FOR_EACH_ENTRY_SAFE(hole, n, &mgr->va_holes, list) {
> - hole_end = hole->offset + hole->size;
> - va_end = va + size;
> - if (hole->offset >= va_end || hole_end <= va)
> - continue;
> - if (hole->offset >= va && hole_end <= va_end) {
> - list_del(&hole->list);
> - FREE(hole);
> - continue;
> - }
> - if (hole->offset >= va)
> - hole->offset = va_end;
> - else
> - hole_end = va;
> - hole->size = hole_end - hole->offset;
> - }
> - }
> - pipe_mutex_unlock(mgr->bo_va_mutex);
> -}
> -
> static void radeon_bomgr_free_va(struct radeon_bomgr *mgr, uint64_t va, uint64_t size)
> {
> struct radeon_bo_va_hole *hole;
> @@ -625,11 +585,19 @@ static struct pb_buffer *radeon_bomgr_create_bo(struct pb_manager *_mgr,
> radeon_bo_destroy(&bo->base);
> return NULL;
> }
> + pipe_mutex_lock(mgr->bo_handles_mutex);
> if (va.operation == RADEON_VA_RESULT_VA_EXIST) {
> - radeon_bomgr_free_va(mgr, bo->va, size);
> - bo->va = va.offset;
> - radeon_bomgr_force_va(mgr, bo->va, size);
> + struct pb_buffer *b = &bo->base;
> + struct radeon_bo *old_bo =
> + util_hash_table_get(mgr->bo_vas, (void*)(uintptr_t)va.offset);
> +
> + pipe_mutex_unlock(mgr->bo_handles_mutex);
> + pb_reference(&b, &old_bo->base);
> + return b;
> }
> +
> + util_hash_table_set(mgr->bo_vas, (void*)(uintptr_t)bo->va, bo);
> + pipe_mutex_unlock(mgr->bo_handles_mutex);
> }
>
> if (rdesc->initial_domains & RADEON_DOMAIN_VRAM)
> @@ -667,6 +635,7 @@ static void radeon_bomgr_destroy(struct pb_manager *_mgr)
> struct radeon_bomgr *mgr = radeon_bomgr(_mgr);
> util_hash_table_destroy(mgr->bo_names);
> util_hash_table_destroy(mgr->bo_handles);
> + util_hash_table_destroy(mgr->bo_vas);
> pipe_mutex_destroy(mgr->bo_handles_mutex);
> pipe_mutex_destroy(mgr->bo_va_mutex);
> FREE(mgr);
> @@ -700,6 +669,7 @@ struct pb_manager *radeon_bomgr_create(struct radeon_drm_winsys *rws)
> mgr->rws = rws;
> mgr->bo_names = util_hash_table_create(handle_hash, handle_compare);
> mgr->bo_handles = util_hash_table_create(handle_hash, handle_compare);
> + mgr->bo_vas = util_hash_table_create(handle_hash, handle_compare);
> pipe_mutex_init(mgr->bo_handles_mutex);
> pipe_mutex_init(mgr->bo_va_mutex);
>
> @@ -999,11 +969,19 @@ done:
> radeon_bo_destroy(&bo->base);
> return NULL;
> }
> + pipe_mutex_lock(mgr->bo_handles_mutex);
> if (va.operation == RADEON_VA_RESULT_VA_EXIST) {
> - radeon_bomgr_free_va(mgr, bo->va, bo->base.size);
> - bo->va = va.offset;
> - radeon_bomgr_force_va(mgr, bo->va, bo->base.size);
> + struct pb_buffer *b = &bo->base;
> + struct radeon_bo *old_bo =
> + util_hash_table_get(mgr->bo_vas, (void*)(uintptr_t)va.offset);
> +
> + pipe_mutex_unlock(mgr->bo_handles_mutex);
> + pb_reference(&b, &old_bo->base);
> + return b;
> }
> +
> + util_hash_table_set(mgr->bo_vas, (void*)(uintptr_t)bo->va, bo);
> + pipe_mutex_unlock(mgr->bo_handles_mutex);
> }
>
> memset(&args, 0, sizeof(args));
> --
> 1.9.0
>
> _______________________________________________
> mesa-dev mailing list
> mesa-dev at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/mesa-dev
More information about the mesa-dev
mailing list