Allocating the MES context bitmap to track the process/gang index usage.

Signed-off-by: Prike Liang <[email protected]>
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c | 70 +++++++++++++++++++++++++
 drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h |  9 +++-
 2 files changed, 78 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c
index 8ba1c941c03d..f65f2a30154d 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c
@@ -962,9 +962,79 @@ void amdgpu_mes_rs64mem_fini(struct amdgpu_mes *mes)
                                      &mes->ctx_array_size_gpu_addr,
                                      (void **)&mes->ctx_array_size_cpu_ptr);
        }
+       
+       bitmap_free(mes->proc_ctx_bitmap);
+       bitmap_free(mes->gang_ctx_bitmap);
        mes->use_rs64mem = false;
 }
 
+/**
+ * amdgpu_mes_rs64mem_setup_bitmaps - allocate bitmaps after querying MES
+ *
+ * Called after QUERY_SCHEDULER_STATUS returns and MES has written
+ * the array sizes to the GPU buffer. Reads the sizes and allocates
+ * the tracking bitmaps.
+ *
+ * @mes: MES instance
+ *
+ * Returns 0 on success, negative errno on failure.
+ */
+int amdgpu_mes_rs64mem_setup_bitmaps(struct amdgpu_mes *mes)
+{
+       struct amdgpu_device *adev = container_of(mes, struct amdgpu_device, 
mes);
+
+       if (!mes->use_rs64mem || !mes->ctx_array_size_cpu_ptr)
+               return 0;
+
+       /*
+        * MES FW wrote the sizes to the GPU buffer:
+        *   ctx_array_size_cpu_ptr[0] = proc_ctx_array_size (N)
+        *   ctx_array_size_cpu_ptr[1] = gang_ctx_array_size (M)
+        */
+       mes->proc_ctx_array_size = mes->ctx_array_size_cpu_ptr[0];
+       mes->gang_ctx_array_size = mes->ctx_array_size_cpu_ptr[1];
+
+       /* Sanity check - MES FW typically returns N=50, M=300 */
+       if (mes->proc_ctx_array_size == 0 || mes->gang_ctx_array_size == 0) {
+               dev_warn(adev->dev,
+                        "MES returned zero ctx array sizes (proc=%u, gang=%u), 
"
+                        "disabling RS64 local memory optimization\n",
+                        mes->proc_ctx_array_size, mes->gang_ctx_array_size);
+               mes->use_rs64mem = false;
+               return 0;
+       }
+
+       /* Cap to safety limits */
+       if (mes->proc_ctx_array_size > AMDGPU_MES_PROC_CTX_ARRAY_MAX)
+               mes->proc_ctx_array_size = AMDGPU_MES_PROC_CTX_ARRAY_MAX;
+       if (mes->gang_ctx_array_size > AMDGPU_MES_GANG_CTX_ARRAY_MAX)
+               mes->gang_ctx_array_size = AMDGPU_MES_GANG_CTX_ARRAY_MAX;
+
+       dev_info(adev->dev,
+                "MES RS64 local memory: proc_ctx_array_size:%u, "
+                "gang_ctx_array_size:%u\n",
+                mes->proc_ctx_array_size, mes->gang_ctx_array_size);
+
+       /* Allocate bitmaps */
+       mes->proc_ctx_bitmap = bitmap_zalloc(mes->proc_ctx_array_size,
+                                            GFP_KERNEL);
+       if (!mes->proc_ctx_bitmap) {
+               mes->use_rs64mem = false;
+               return -ENOMEM;
+       }
+
+       mes->gang_ctx_bitmap = bitmap_zalloc(mes->gang_ctx_array_size,
+                                            GFP_KERNEL);
+       if (!mes->gang_ctx_bitmap) {
+               bitmap_free(mes->proc_ctx_bitmap);
+               mes->proc_ctx_bitmap = NULL;
+               mes->use_rs64mem = false;
+               return -ENOMEM;
+       }
+
+       return 0;
+}
+
 #if defined(CONFIG_DEBUG_FS)
 
 static int amdgpu_debugfs_mes_event_log_show(struct seq_file *m, void *unused)
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h
index 520bcd8ee202..5c50bc9616b7 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h
@@ -54,7 +54,8 @@ enum amdgpu_mes_priority_level {
 
 #define AMDGPU_MES_PROC_CTX_SIZE 0x1000 /* one page area */
 #define AMDGPU_MES_GANG_CTX_SIZE 0x1000 /* one page area */
-
+#define AMDGPU_MES_PROC_CTX_ARRAY_MAX  128
+#define AMDGPU_MES_GANG_CTX_ARRAY_MAX  512
 struct amdgpu_mes_funcs;
 
 enum amdgpu_mes_pipe {
@@ -176,6 +177,11 @@ struct amdgpu_mes {
        struct amdgpu_bo                *ctx_array_size_bo;
        uint64_t                        ctx_array_size_gpu_addr;
        uint32_t                        *ctx_array_size_cpu_ptr;
+
+       uint32_t                        proc_ctx_array_size;
+       unsigned long                   *proc_ctx_bitmap;
+       uint32_t                        gang_ctx_array_size;
+       unsigned long                   *gang_ctx_bitmap;
 };
 
 struct amdgpu_mes_hung_queue_hqd_info {
@@ -624,4 +630,5 @@ int amdgpu_mes_update_enforce_isolation(struct 
amdgpu_device *adev);
 
 int amdgpu_mes_rs64mem_init(struct amdgpu_mes *mes);
 void amdgpu_mes_rs64mem_fini(struct amdgpu_mes *mes);
+int amdgpu_mes_rs64mem_setup_bitmaps(struct amdgpu_mes *mes);
 #endif /* __AMDGPU_MES_H__ */
-- 
2.34.1

Reply via email to