History

drm/amdgpu: Add input fence to sync bo map/unmap

This patch adds input fences to VM_IOCTL for buffer object. The kernel will map/unmap the BO only when the fence is signaled. The UAPI for the same has been approved here: https://gitlab.freedesktop.org/mesa/drm/-/merge_requests/392 V2: Bug fix (Arvind) V3: Bug fix (Arvind) V4: Rename UAPI objects as per UAPI review (Marek) V5: Addressed review comemnts from Christian - function should return error. - Add 'TODO' comment - The input fence should be independent of the operation. V6: Addressed review comemnts from Christian - Release the memory allocated by memdup_user(). V7: Addressed review comemnts from Christian - Drop the debug print and add "return r;" for the error handling. V11: Rebase v12: Fix 32-bit holes issue in sturct drm_amdgpu_gem_va. v13: Fix deadlock issue. v14: Fix merge conflict. v15: Fix review comment by renaming syncobj handles.

Arvind Yadav committed 2 years ago

Commit 38c67ec1 parent 189ee982 files · +50 −0Browse files

Unified · Split

2 files
  1. drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c +46 −0
  2. include/uapi/drm/amdgpu_drm.h +4 −0
drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c+46−0
@@ -45,6 +45,45 @@ · 44 unmodified lines
45#include "amdgpu_xgmi.h"45#include "amdgpu_xgmi.h"
46#include "amdgpu_vm.h"46#include "amdgpu_vm.h"
47 47
48static int
49amdgpu_gem_add_input_fence(struct drm_file *filp,
50 uint64_t syncobj_handles_array,
51 uint32_t num_syncobj_handles)
52{
53 struct dma_fence *fence;
54 uint32_t *syncobj_handles;
55 int ret, i;
56
57 if (!num_syncobj_handles)
58 return 0;
59
60 syncobj_handles = memdup_user(u64_to_user_ptr(syncobj_handles_array),
61 sizeof(uint32_t) * num_syncobj_handles);
62 if (IS_ERR(syncobj_handles))
63 return PTR_ERR(syncobj_handles);
64
65 for (i = 0; i < num_syncobj_handles; i++) {
66
67 if (!syncobj_handles[i]) {
68 ret = -EINVAL;
69 goto free_memdup;
70 }
71
72 ret = drm_syncobj_find_fence(filp, syncobj_handles[i], 0, 0, &fence);
73 if (ret)
74 goto free_memdup;
75
76 dma_fence_wait(fence, false);
77
78 /* TODO: optimize async handling */
79 dma_fence_put(fence);
80 }
81
82free_memdup:
83 kfree(syncobj_handles);
84 return ret;
85}
86
48static int87static int
49amdgpu_gem_update_timeline_node(struct drm_file *filp,88amdgpu_gem_update_timeline_node(struct drm_file *filp,
50 uint32_t syncobj_handle,89 uint32_t syncobj_handle,
@@ -854,6 +893,12 @@ int amdgpu_gem_va_ioctl(struct drm_device *dev, void *data, · 803 unmodified lines
854 abo = NULL;893 abo = NULL;
855 }894 }
856 895
896 r = amdgpu_gem_add_input_fence(filp,
897 args->input_fence_syncobj_handles,
898 args->num_syncobj_handles);
899 if (r)
900 goto error_put_gobj;
901
857 drm_exec_init(&exec, DRM_EXEC_INTERRUPTIBLE_WAIT |902 drm_exec_init(&exec, DRM_EXEC_INTERRUPTIBLE_WAIT |
858 DRM_EXEC_IGNORE_DUPLICATES, 0);903 DRM_EXEC_IGNORE_DUPLICATES, 0);
859 drm_exec_until_all_locked(&exec) {904 drm_exec_until_all_locked(&exec) {
@@ -928,6 +973,7 @@ int amdgpu_gem_va_ioctl(struct drm_device *dev, void *data, · 68 unmodified lines
928 973
929error:974error:
930 drm_exec_fini(&exec);975 drm_exec_fini(&exec);
976error_put_gobj:
931 drm_gem_object_put(gobj);977 drm_gem_object_put(gobj);
932 return r;978 return r;
933}979}
include/uapi/drm/amdgpu_drm.h+4−0
@@ -884,6 +884,10 @@ struct drm_amdgpu_gem_va { · 883 unmodified lines
884 * at vm_timeline_point.884 * at vm_timeline_point.
885 */885 */
886 __u32 vm_timeline_syncobj_out;886 __u32 vm_timeline_syncobj_out;
887 /** the number of syncobj handles in @input_fence_syncobj_handles */
888 __u32 num_syncobj_handles;
889 /** Array of sync object handle to wait for given input fences */
890 __u64 input_fence_syncobj_handles;
887};891};
888 892
889#define AMDGPU_HW_IP_GFX 0893#define AMDGPU_HW_IP_GFX 0