From: Honglei Huang <[email protected]> Wire up the SVM subsystem:
Kconfig: - CONFIG_DRM_AMDGPU_SVM option (depends on DEVICE_PRIVATE, selects DRM_GPUSVM, HMM_MIRROR, MMU_NOTIFIER), default y Makefile: - Build amdgpu_svm.o, amdgpu_svm_attr.o, amdgpu_svm_fault.o, amdgpu_svm_range.o when CONFIG_DRM_AMDGPU_SVM=y - KBUILD_EXTRA_SYMBOLS for drm Module.symvers (drm_gpusvm exports) - clean-svm phony target for development convenience amdgpu_drv.c: - Register DRM_IOCTL_DEF_DRV(AMDGPU_GEM_SVM) in ioctl table amdgpu_vm.c: - Initialize vm->svm = NULL in amdgpu_vm_init - Call amdgpu_svm_init in amdgpu_vm_make_compute - Call amdgpu_svm_close + amdgpu_svm_fini in amdgpu_vm_fini - Route GPU page faults through amdgpu_svm_handle_fault when SVM context exists, falling back to svm_range_restore_pages otherwise Signed-off-by: Honglei Huang <[email protected]> --- drivers/gpu/drm/amd/amdgpu/Kconfig | 11 +++++++++++ drivers/gpu/drm/amd/amdgpu/Makefile | 13 +++++++++++++ drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c | 2 ++ drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c | 20 +++++++++++++++++++- 4 files changed, 45 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/amdgpu/Kconfig b/drivers/gpu/drm/amd/amdgpu/Kconfig index 7f515be51..337314011 100644 --- a/drivers/gpu/drm/amd/amdgpu/Kconfig +++ b/drivers/gpu/drm/amd/amdgpu/Kconfig @@ -82,6 +82,17 @@ config DRM_AMDGPU_USERPTR This option selects CONFIG_HMM and CONFIG_HMM_MIRROR if it isn't already selected to enabled full userptr support. +config DRM_AMDGPU_SVM + bool "Enable AMDGPU SVM support (experimental)" + depends on DRM_AMDGPU + depends on DEVICE_PRIVATE + select DRM_GPUSVM + select HMM_MIRROR + select MMU_NOTIFIER + default y + help + Experimental SVM support based on DRM GPUSVM. + config DRM_AMD_ISP bool "Enable AMD Image Signal Processor IP support" depends on DRM_AMDGPU && ACPI diff --git a/drivers/gpu/drm/amd/amdgpu/Makefile b/drivers/gpu/drm/amd/amdgpu/Makefile index 6a7e9bfec..a40a42995 100644 --- a/drivers/gpu/drm/amd/amdgpu/Makefile +++ b/drivers/gpu/drm/amd/amdgpu/Makefile @@ -44,6 +44,10 @@ ccflags-y := -I$(FULL_AMD_PATH)/include/asic_reg \ subdir-ccflags-y += -Wno-override-init subdir-ccflags-$(CONFIG_DRM_AMDGPU_WERROR) += -Werror +ifneq ($(wildcard $(objtree)/drivers/gpu/drm/Module.symvers),) +KBUILD_EXTRA_SYMBOLS += $(objtree)/drivers/gpu/drm/Module.symvers +endif + amdgpu-y := amdgpu_drv.o # add KMS driver @@ -317,6 +321,15 @@ amdgpu-$(CONFIG_VGA_SWITCHEROO) += amdgpu_atpx_handler.o amdgpu-$(CONFIG_ACPI) += amdgpu_acpi.o amdgpu-$(CONFIG_HMM_MIRROR) += amdgpu_hmm.o +# svm support +amdgpu-$(CONFIG_DRM_AMDGPU_SVM) += amdgpu_svm.o amdgpu_svm_attr.o \ + amdgpu_svm_fault.o amdgpu_svm_range.o + +.PHONY: clean-svm +clean-svm: + rm -f $(obj)/amdgpu_svm.o $(obj)/amdgpu_svm_attr.o $(obj)/amdgpu_svm_fault.o $(obj)/amdgpu_svm_range.o \ + $(obj)/.amdgpu_svm.o.cmd $(obj)/.amdgpu_svm_attr.o.cmd $(obj)/.amdgpu_svm_fault.o.cmd $(obj)/.amdgpu_svm_range.o.cmd + include $(FULL_AMD_PATH)/pm/Makefile amdgpu-y += $(AMD_POWERPLAY_FILES) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c index a44baa9ee..d5ccacdf2 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c @@ -51,6 +51,7 @@ #include "amdgpu_ras.h" #include "amdgpu_reset.h" #include "amdgpu_sched.h" +#include "amdgpu_svm.h" #include "amdgpu_xgmi.h" #include "amdgpu_userq.h" #include "amdgpu_userq_fence.h" @@ -3064,6 +3065,7 @@ const struct drm_ioctl_desc amdgpu_ioctls_kms[] = { DRM_IOCTL_DEF_DRV(AMDGPU_USERQ_SIGNAL, amdgpu_userq_signal_ioctl, DRM_AUTH|DRM_RENDER_ALLOW), DRM_IOCTL_DEF_DRV(AMDGPU_USERQ_WAIT, amdgpu_userq_wait_ioctl, DRM_AUTH|DRM_RENDER_ALLOW), DRM_IOCTL_DEF_DRV(AMDGPU_GEM_LIST_HANDLES, amdgpu_gem_list_handles_ioctl, DRM_AUTH|DRM_RENDER_ALLOW), + DRM_IOCTL_DEF_DRV(AMDGPU_GEM_SVM, amdgpu_gem_svm_ioctl, DRM_AUTH|DRM_RENDER_ALLOW), }; static const struct drm_driver amdgpu_kms_driver = { diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c index 429947f75..86603d2b3 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c @@ -43,6 +43,7 @@ #include "amdgpu_xgmi.h" #include "amdgpu_dma_buf.h" #include "amdgpu_res_cursor.h" +#include "amdgpu_svm.h" #include "kfd_svm.h" /** @@ -2606,6 +2607,7 @@ int amdgpu_vm_init(struct amdgpu_device *adev, struct amdgpu_vm *vm, int r, i; vm->va = RB_ROOT_CACHED; + vm->svm = NULL; for (i = 0; i < AMDGPU_MAX_VMHUBS; i++) vm->reserved_vmid[i] = NULL; INIT_LIST_HEAD(&vm->evicted); @@ -2766,6 +2768,10 @@ int amdgpu_vm_make_compute(struct amdgpu_device *adev, struct amdgpu_vm *vm) vm->is_compute_context = true; vm->need_tlb_fence = true; + r = amdgpu_svm_init(adev, vm); + if (r) + goto unreserve_bo; + unreserve_bo: amdgpu_bo_unreserve(vm->root.bo); return r; @@ -2798,6 +2804,9 @@ void amdgpu_vm_fini(struct amdgpu_device *adev, struct amdgpu_vm *vm) unsigned long flags; int i; + amdgpu_svm_close(vm); + amdgpu_svm_fini(vm); + amdgpu_amdkfd_gpuvm_destroy_cb(adev, vm); root = amdgpu_bo_ref(vm->root.bo); @@ -2976,8 +2985,10 @@ bool amdgpu_vm_handle_fault(struct amdgpu_device *adev, u32 pasid, bool write_fault) { bool is_compute_context = false; + bool has_svm = false; struct amdgpu_bo *root; unsigned long irqflags; + uint64_t fault_addr = addr; uint64_t value, flags; struct amdgpu_vm *vm; int r; @@ -2987,6 +2998,7 @@ bool amdgpu_vm_handle_fault(struct amdgpu_device *adev, u32 pasid, if (vm) { root = amdgpu_bo_ref(vm->root.bo); is_compute_context = vm->is_compute_context; + has_svm = !!vm->svm; } else { root = NULL; } @@ -2997,7 +3009,13 @@ bool amdgpu_vm_handle_fault(struct amdgpu_device *adev, u32 pasid, addr /= AMDGPU_GPU_PAGE_SIZE; - if (is_compute_context && !svm_range_restore_pages(adev, pasid, vmid, + if (is_compute_context && has_svm && !amdgpu_svm_handle_fault(adev, pasid, addr, + ts, write_fault)) { + amdgpu_bo_unref(&root); + return true; + } + + if (is_compute_context && !has_svm && !svm_range_restore_pages(adev, pasid, vmid, node_id, addr, ts, write_fault)) { amdgpu_bo_unref(&root); return true; -- 2.34.1
