Mesa (master): radv/winsys: use an array for the global BO list instead of a list

GitLab Mirror gitlab-mirror at kemper.freedesktop.org
Mon Feb 8 08:42:43 UTC 2021


Module: Mesa
Branch: master
Commit: eb625b7a5ff501852ba7ce2a309217859d7cb791
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=eb625b7a5ff501852ba7ce2a309217859d7cb791

Author: Samuel Pitoiset <samuel.pitoiset at gmail.com>
Date:   Wed Feb  3 10:47:08 2021 +0100

radv/winsys: use an array for the global BO list instead of a list

This allows to remove one 64-bit pointer from radv_amdgpu_winsys_bo.

Signed-off-by: Samuel Pitoiset <samuel.pitoiset at gmail.com>
Reviewed-by: Bas Nieuwenhuizen <bas at basnieuwenhuizen.nl>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/8859>

---

 src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.c     | 88 +++++++++++++++--------
 src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.h     |  1 -
 src/amd/vulkan/winsys/amdgpu/radv_amdgpu_cs.c     | 36 +++++-----
 src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.c |  7 +-
 src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.h | 12 ++--
 5 files changed, 87 insertions(+), 57 deletions(-)

diff --git a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.c b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.c
index 1a85bf305e9..049191873b2 100644
--- a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.c
+++ b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.c
@@ -317,6 +317,50 @@ static void radv_amdgpu_log_bo(struct radv_amdgpu_winsys_bo *bo,
 	u_rwlock_wrunlock(&ws->log_bo_list_lock);
 }
 
+static int radv_amdgpu_global_bo_list_add(struct radv_amdgpu_winsys_bo *bo)
+{
+	struct radv_amdgpu_winsys *ws = bo->ws;
+
+	if (!ws->debug_all_bos)
+		return VK_SUCCESS;
+
+	u_rwlock_wrlock(&ws->global_bo_list.lock);
+	if (ws->global_bo_list.count == ws->global_bo_list.capacity) {
+		unsigned capacity = MAX2(4, ws->global_bo_list.capacity * 2);
+		void *data = realloc(ws->global_bo_list.bos,
+				     capacity * sizeof(struct radv_amdgpu_winsys_bo *));
+		if (!data) {
+			u_rwlock_wrunlock(&ws->global_bo_list.lock);
+			return VK_ERROR_OUT_OF_HOST_MEMORY;
+		}
+
+		ws->global_bo_list.bos = (struct radv_amdgpu_winsys_bo **)data;
+		ws->global_bo_list.capacity = capacity;
+	}
+
+	ws->global_bo_list.bos[ws->global_bo_list.count++] = bo;
+	u_rwlock_wrunlock(&ws->global_bo_list.lock);
+	return VK_SUCCESS;
+}
+
+static void radv_amdgpu_global_bo_list_del(struct radv_amdgpu_winsys_bo *bo)
+{
+	struct radv_amdgpu_winsys *ws = bo->ws;
+
+	if (!ws->debug_all_bos)
+		return;
+
+	u_rwlock_wrlock(&ws->global_bo_list.lock);
+	for(unsigned i = ws->global_bo_list.count; i-- > 0;) {
+		if (ws->global_bo_list.bos[i] == bo) {
+			ws->global_bo_list.bos[i] = ws->global_bo_list.bos[ws->global_bo_list.count - 1];
+			--ws->global_bo_list.count;
+			break;
+		}
+	}
+	u_rwlock_wrunlock(&ws->global_bo_list.lock);
+}
+
 static void radv_amdgpu_winsys_bo_destroy(struct radeon_winsys_bo *_bo)
 {
 	struct radv_amdgpu_winsys_bo *bo = radv_amdgpu_winsys_bo(_bo);
@@ -334,12 +378,7 @@ static void radv_amdgpu_winsys_bo_destroy(struct radeon_winsys_bo *_bo)
 		free(bo->bos);
 		free(bo->ranges);
 	} else {
-		if (bo->ws->debug_all_bos) {
-			u_rwlock_wrlock(&bo->ws->global_bo_list_lock);
-			list_del(&bo->global_list_item);
-			bo->ws->num_buffers--;
-			u_rwlock_wrunlock(&bo->ws->global_bo_list_lock);
-		}
+		radv_amdgpu_global_bo_list_del(bo);
 		radv_amdgpu_bo_va_op(bo->ws, bo->bo, 0, bo->size, bo->base.va,
 				     0, 0, AMDGPU_VA_OP_UNMAP);
 		amdgpu_bo_free(bo->bo);
@@ -363,18 +402,6 @@ static void radv_amdgpu_winsys_bo_destroy(struct radeon_winsys_bo *_bo)
 	FREE(bo);
 }
 
-static void radv_amdgpu_add_buffer_to_global_list(struct radv_amdgpu_winsys_bo *bo)
-{
-	struct radv_amdgpu_winsys *ws = bo->ws;
-
-	if (bo->ws->debug_all_bos) {
-		u_rwlock_wrlock(&ws->global_bo_list_lock);
-		list_addtail(&bo->global_list_item, &ws->global_bo_list);
-		ws->num_buffers++;
-		u_rwlock_wrunlock(&ws->global_bo_list_lock);
-	}
-}
-
 static struct radeon_winsys_bo *
 radv_amdgpu_winsys_bo_create(struct radeon_winsys *_ws,
 			     uint64_t size,
@@ -532,7 +559,7 @@ radv_amdgpu_winsys_bo_create(struct radeon_winsys *_ws,
 		p_atomic_add(&ws->allocated_gtt,
 			     align64(bo->size, ws->info.gart_page_size));
 
-	radv_amdgpu_add_buffer_to_global_list(bo);
+	radv_amdgpu_global_bo_list_add(bo);
 	radv_amdgpu_log_bo(bo, false);
 
 	return (struct radeon_winsys_bo *)bo;
@@ -641,7 +668,7 @@ radv_amdgpu_winsys_bo_from_ptr(struct radeon_winsys *_ws,
 	p_atomic_add(&ws->allocated_gtt,
 		     align64(bo->size, ws->info.gart_page_size));
 
-	radv_amdgpu_add_buffer_to_global_list(bo);
+	radv_amdgpu_global_bo_list_add(bo);
 	radv_amdgpu_log_bo(bo, false);
 
 	return (struct radeon_winsys_bo *)bo;
@@ -723,7 +750,7 @@ radv_amdgpu_winsys_bo_from_fd(struct radeon_winsys *_ws,
 		p_atomic_add(&ws->allocated_gtt,
 			     align64(bo->size, ws->info.gart_page_size));
 
-	radv_amdgpu_add_buffer_to_global_list(bo);
+	radv_amdgpu_global_bo_list_add(bo);
 	radv_amdgpu_log_bo(bo, false);
 
 	return (struct radeon_winsys_bo *)bo;
@@ -938,28 +965,29 @@ static void radv_amdgpu_dump_bo_ranges(struct radeon_winsys *_ws, FILE *file)
 {
 	struct radv_amdgpu_winsys *ws = radv_amdgpu_winsys(_ws);
 	if (ws->debug_all_bos) {
-		struct radv_amdgpu_winsys_bo *bo;
 		struct radv_amdgpu_winsys_bo **bos = NULL;
 		int i = 0;
 
-		u_rwlock_rdlock(&ws->global_bo_list_lock);
-		bos = malloc(sizeof(*bos) * ws->num_buffers);
+		u_rwlock_rdlock(&ws->global_bo_list.lock);
+		bos = malloc(sizeof(*bos) * ws->global_bo_list.count);
 		if (!bos) {
-			u_rwlock_rdunlock(&ws->global_bo_list_lock);
+			u_rwlock_rdunlock(&ws->global_bo_list.lock);
 			fprintf(file, "  Failed to allocate memory to sort VA ranges for dumping\n");
 			return;
 		}
-		LIST_FOR_EACH_ENTRY(bo, &ws->global_bo_list, global_list_item) {
-			bos[i++] = bo;
+
+		for (i = 0; i < ws->global_bo_list.count; i++) {
+			bos[i] = ws->global_bo_list.bos[i];
 		}
-		qsort(bos, ws->num_buffers, sizeof(bos[0]), radv_amdgpu_bo_va_compare);
-		for (i = 0; i < ws->num_buffers; ++i) {
+		qsort(bos, ws->global_bo_list.count, sizeof(bos[0]), radv_amdgpu_bo_va_compare);
+
+		for (i = 0; i < ws->global_bo_list.count; ++i) {
 			fprintf(file, "  VA=%.16llx-%.16llx, handle=%d%s\n",
 			        (long long)bos[i]->base.va, (long long)(bos[i]->base.va + bos[i]->size),
 				bos[i]->bo_handle, bos[i]->is_virtual ? " sparse" : "");
 		}
 		free(bos);
-		u_rwlock_rdunlock(&ws->global_bo_list_lock);
+		u_rwlock_rdunlock(&ws->global_bo_list.lock);
 	} else
 		fprintf(file, "  To get BO VA ranges, please specify RADV_DEBUG=allbos\n");
 }
diff --git a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.h b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.h
index 0cced22bc56..2aa5732ecab 100644
--- a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.h
+++ b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_bo.h
@@ -54,7 +54,6 @@ struct radv_amdgpu_winsys_bo {
 			amdgpu_bo_handle bo;
 			bool is_shared;
 			uint32_t bo_handle;
-			struct list_head global_list_item;
 		};
 		/* virtual bo */
 		struct {
diff --git a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_cs.c b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_cs.c
index 69943533e39..34f2d95febb 100644
--- a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_cs.c
+++ b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_cs.c
@@ -724,17 +724,14 @@ radv_amdgpu_get_bo_list(struct radv_amdgpu_winsys *ws,
 	unsigned num_handles = 0;
 
 	if (ws->debug_all_bos) {
-		struct radv_amdgpu_winsys_bo *bo;
-
-		handles = malloc(sizeof(handles[0]) * ws->num_buffers);
+		handles = malloc(sizeof(handles[0]) * ws->global_bo_list.count);
 		if (!handles) {
 			return VK_ERROR_OUT_OF_HOST_MEMORY;
 		}
 
-		LIST_FOR_EACH_ENTRY(bo, &ws->global_bo_list, global_list_item) {
-			assert(num_handles < ws->num_buffers);
-			handles[num_handles].bo_handle = bo->bo_handle;
-			handles[num_handles].bo_priority = bo->priority;
+		for (uint32_t i = 0; i < ws->global_bo_list.count; i++) {
+			handles[i].bo_handle = ws->global_bo_list.bos[i]->bo_handle;
+			handles[i].bo_priority = ws->global_bo_list.bos[i]->priority;
 			num_handles++;
 		}
 	} else if (count == 1 && !num_extra_bo && !extra_cs && !radv_bo_list &&
@@ -919,7 +916,7 @@ radv_amdgpu_winsys_cs_submit_chained(struct radeon_winsys_ctx *_ctx,
 	}
 
 	if (aws->debug_all_bos)
-		u_rwlock_rdlock(&aws->global_bo_list_lock);
+		u_rwlock_rdlock(&aws->global_bo_list.lock);
 
 	/* Get the BO list. */
 	result = radv_amdgpu_get_bo_list(cs0->ws, cs_array, cs_count, NULL, 0,
@@ -960,7 +957,7 @@ radv_amdgpu_winsys_cs_submit_chained(struct radeon_winsys_ctx *_ctx,
 
 fail:
 	if (aws->debug_all_bos)
-		u_rwlock_rdunlock(&aws->global_bo_list_lock);
+		u_rwlock_rdunlock(&aws->global_bo_list.lock);
 	return result;
 }
 
@@ -994,7 +991,7 @@ radv_amdgpu_winsys_cs_submit_fallback(struct radeon_winsys_ctx *_ctx,
 	number_of_ibs = cs_count + !!initial_preamble_cs;
 
 	if (aws->debug_all_bos)
-		u_rwlock_rdlock(&aws->global_bo_list_lock);
+		u_rwlock_rdlock(&aws->global_bo_list.lock);
 
 	/* Get the BO list. */
 	result = radv_amdgpu_get_bo_list(cs0->ws, &cs_array[0], cs_count, NULL, 0,
@@ -1050,7 +1047,7 @@ radv_amdgpu_winsys_cs_submit_fallback(struct radeon_winsys_ctx *_ctx,
 
 fail:
 	if (aws->debug_all_bos)
-		u_rwlock_rdunlock(&aws->global_bo_list_lock);
+		u_rwlock_rdunlock(&aws->global_bo_list.lock);
 	return result;
 }
 
@@ -1209,7 +1206,7 @@ radv_amdgpu_winsys_cs_submit_sysmem(struct radeon_winsys_ctx *_ctx,
 		}
 
 		if (aws->debug_all_bos)
-			u_rwlock_rdlock(&aws->global_bo_list_lock);
+			u_rwlock_rdlock(&aws->global_bo_list.lock);
 
 		result = radv_amdgpu_get_bo_list(cs0->ws, &cs_array[i], cnt,
 						 (struct radv_amdgpu_winsys_bo **)bos,
@@ -1220,7 +1217,7 @@ radv_amdgpu_winsys_cs_submit_sysmem(struct radeon_winsys_ctx *_ctx,
 			free(ibs);
 			free(bos);
 			if (aws->debug_all_bos)
-				u_rwlock_rdunlock(&aws->global_bo_list_lock);
+				u_rwlock_rdunlock(&aws->global_bo_list.lock);
 			return result;
 		}
 
@@ -1239,7 +1236,7 @@ radv_amdgpu_winsys_cs_submit_sysmem(struct radeon_winsys_ctx *_ctx,
 
 		free(request.handles);
 		if (aws->debug_all_bos)
-			u_rwlock_rdunlock(&aws->global_bo_list_lock);
+			u_rwlock_rdunlock(&aws->global_bo_list.lock);
 
 		for (unsigned j = 0; j < number_of_ibs; j++) {
 			ws->buffer_destroy(bos[j]);
@@ -1310,17 +1307,18 @@ static void *radv_amdgpu_winsys_get_cpu_addr(void *_cs, uint64_t addr)
 		}
 	}
 	if(cs->ws->debug_all_bos) {
-		u_rwlock_rdlock(&cs->ws->global_bo_list_lock);
-		list_for_each_entry(struct radv_amdgpu_winsys_bo, bo,
-		                    &cs->ws->global_bo_list, global_list_item) {
+		u_rwlock_rdlock(&cs->ws->global_bo_list.lock);
+		for (uint32_t i = 0; i < cs->ws->global_bo_list.count; i++) {
+			struct radv_amdgpu_winsys_bo *bo = cs->ws->global_bo_list.bos[i];
 			if (addr >= bo->base.va && addr - bo->base.va < bo->size) {
 				if (amdgpu_bo_cpu_map(bo->bo, &ret) == 0) {
-					u_rwlock_rdunlock(&cs->ws->global_bo_list_lock);
+					u_rwlock_rdunlock(&cs->ws->global_bo_list.lock);
 					return (char *)ret + (addr - bo->base.va);
 				}
 			}
+
 		}
-		u_rwlock_rdunlock(&cs->ws->global_bo_list_lock);
+		u_rwlock_rdunlock(&cs->ws->global_bo_list.lock);
 	}
 	return ret;
 }
diff --git a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.c b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.c
index cbceefb7894..743257c5489 100644
--- a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.c
+++ b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.c
@@ -166,8 +166,10 @@ static void radv_amdgpu_winsys_destroy(struct radeon_winsys *rws)
 		amdgpu_cs_destroy_syncobj(ws->dev, ws->syncobj[i]);
 	free(ws->syncobj);
 
+	u_rwlock_destroy(&ws->global_bo_list.lock);
+	free(ws->global_bo_list.bos);
+
 	pthread_mutex_destroy(&ws->syncobj_lock);
-	u_rwlock_destroy(&ws->global_bo_list_lock);
 	u_rwlock_destroy(&ws->log_bo_list_lock);
 	ac_addrlib_destroy(ws->addrlib);
 	amdgpu_device_deinitialize(ws->dev);
@@ -204,8 +206,7 @@ radv_amdgpu_winsys_create(int fd, uint64_t debug_flags, uint64_t perftest_flags)
 	ws->zero_all_vram_allocs = debug_flags & RADV_DEBUG_ZERO_VRAM;
 	ws->use_llvm = debug_flags & RADV_DEBUG_LLVM;
 	ws->cs_bo_domain = radv_cmdbuffer_domain(&ws->info, perftest_flags);
-	list_inithead(&ws->global_bo_list);
-	u_rwlock_init(&ws->global_bo_list_lock);
+	u_rwlock_init(&ws->global_bo_list.lock);
 	list_inithead(&ws->log_bo_list);
 	u_rwlock_init(&ws->log_bo_list_lock);
 	pthread_mutex_init(&ws->syncobj_lock, NULL);
diff --git a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.h b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.h
index 55f932b879c..d354fe15bba 100644
--- a/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.h
+++ b/src/amd/vulkan/winsys/amdgpu/radv_amdgpu_winsys.h
@@ -50,15 +50,19 @@ struct radv_amdgpu_winsys {
 	bool zero_all_vram_allocs;
 	bool use_local_bos;
 	bool use_llvm;
-	unsigned num_buffers;
-
-	struct u_rwlock global_bo_list_lock;
-	struct list_head global_bo_list;
 
 	uint64_t allocated_vram;
 	uint64_t allocated_vram_vis;
 	uint64_t allocated_gtt;
 
+	/* Global BO list */
+	struct {
+		struct radv_amdgpu_winsys_bo **bos;
+		uint32_t count;
+		uint32_t capacity;
+		struct u_rwlock lock;
+	} global_bo_list;
+
 	/* syncobj cache */
 	pthread_mutex_t syncobj_lock;
 	uint32_t *syncobj;



More information about the mesa-commit mailing list