diff mbox series

[13/26] RFC drm/xe/eudebug: userptr vm pread/pwrite

Message ID 20241216141721.2051279-1-mika.kuoppala@linux.intel.com (mailing list archive)
State New
Headers show
Series None | expand

Commit Message

Mika Kuoppala Dec. 16, 2024, 2:17 p.m. UTC
Implement debugger vm access for userptrs.

When bind is done, take ref to current task so that
we know from which vm the address was bound. Then during
debugger pread/pwrite we use this target task as
parameter to access the debuggee vm with access_process_vm().

This is based on suggestions from Thomas, Joonas and Simona.

Cc: Matthew Brost <matthew.brost@intel.com>
Cc: Andrzej Hajda <andrzej.hajda@intel.com>
Cc: Thomas Hellström <thomas.hellstrom@linux.intel.com>
Cc: Christian König <christian.koenig@amd.com>
Cc: Joonas Lahtinen <joonas.lahtinen@linux.intel.com>
Cc: Simona Vetter <simona@ffwll.ch>
Signed-off-by: Mika Kuoppala <mika.kuoppala@linux.intel.com>
---
 drivers/gpu/drm/xe/xe_eudebug.c  | 12 ++++++++++++
 drivers/gpu/drm/xe/xe_vm.c       | 11 +++++++++++
 drivers/gpu/drm/xe/xe_vm_types.h |  6 ++++++
 3 files changed, 29 insertions(+)
diff mbox series

Patch

diff --git a/drivers/gpu/drm/xe/xe_eudebug.c b/drivers/gpu/drm/xe/xe_eudebug.c
index 9d87df75348b..980b5a1383ad 100644
--- a/drivers/gpu/drm/xe/xe_eudebug.c
+++ b/drivers/gpu/drm/xe/xe_eudebug.c
@@ -3074,6 +3074,18 @@  static int xe_eudebug_vma_access(struct xe_vma *vma, u64 offset_in_vma,
 		xe_bo_put(bo);
 
 		return ret;
+	} else if (xe_vma_is_userptr(vma)) {
+		struct xe_userptr *userptr = &to_userptr_vma(vma)->userptr;
+
+		/*
+		 * XXX: access_remote_vm() would fit as userptr notifier has
+		 * mm ref so we would not need to carry task ref at all.
+		 * But access_remote_vm is not exported. access_process_vm()
+		 * is exported so use it instead.
+		 */
+		return access_process_vm(userptr->eudebug.task,
+					 xe_vma_userptr(vma), buf, bytes,
+					 write ? FOLL_WRITE : 0);
 	}
 
 	return -EINVAL;
diff --git a/drivers/gpu/drm/xe/xe_vm.c b/drivers/gpu/drm/xe/xe_vm.c
index 0f17bc8b627b..c23bb4547d66 100644
--- a/drivers/gpu/drm/xe/xe_vm.c
+++ b/drivers/gpu/drm/xe/xe_vm.c
@@ -999,6 +999,14 @@  static struct xe_vma *xe_vma_create(struct xe_vm *vm,
 			}
 
 			userptr->notifier_seq = LONG_MAX;
+#if IS_ENABLED(CONFIG_DRM_XE_EUDEBUG)
+			/*
+			 * We could use the mm which is on notifier. But
+			 * the access_remote_vm() is not exported. Thus
+			 * we get reference to task for access_process_vm()
+			 */
+			userptr->eudebug.task = get_task_struct(current);
+#endif
 		}
 
 		xe_vm_get(vm);
@@ -1023,6 +1031,9 @@  static void xe_vma_destroy_late(struct xe_vma *vma)
 		if (userptr->sg)
 			xe_hmm_userptr_free_sg(uvma);
 
+#if IS_ENABLED(CONFIG_DRM_XE_EUDEBUG)
+		put_task_struct(userptr->eudebug.task);
+#endif
 		/*
 		 * Since userptr pages are not pinned, we can't remove
 		 * the notifer until we're sure the GPU is not accessing
diff --git a/drivers/gpu/drm/xe/xe_vm_types.h b/drivers/gpu/drm/xe/xe_vm_types.h
index 557b047ebdd7..26176ccbcbbc 100644
--- a/drivers/gpu/drm/xe/xe_vm_types.h
+++ b/drivers/gpu/drm/xe/xe_vm_types.h
@@ -68,6 +68,12 @@  struct xe_userptr {
 #if IS_ENABLED(CONFIG_DRM_XE_USERPTR_INVAL_INJECT)
 	u32 divisor;
 #endif
+
+#if IS_ENABLED(CONFIG_DRM_XE_EUDEBUG)
+	struct {
+		struct task_struct *task;
+	} eudebug;
+#endif
 };
 
 struct xe_vma {