Skip to content

Commit eeaf06a

Browse files
author
Ben Skeggs
committed
drm/nouveau/svm: initial support for shared virtual memory
This uses HMM to mirror a process' CPU page tables into a channel's page tables, and keep them synchronised so that both the CPU and GPU are able to access the same memory at the same virtual address. While this code also supports Volta/Turing, it's only enabled for Pascal GPUs currently due to channel recovery being unreliable right now on the later GPUs. Signed-off-by: Ben Skeggs <[email protected]>
1 parent bfe91af commit eeaf06a

File tree

10 files changed

+818
-1
lines changed

10 files changed

+818
-1
lines changed

drivers/gpu/drm/nouveau/Kbuild

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ nouveau-y += nouveau_vga.o
3030
# DRM - memory management
3131
nouveau-y += nouveau_bo.o
3232
nouveau-y += nouveau_gem.o
33+
nouveau-$(CONFIG_DRM_NOUVEAU_SVM) += nouveau_svm.o
3334
nouveau-y += nouveau_mem.o
3435
nouveau-y += nouveau_prime.o
3536
nouveau-y += nouveau_sgdma.o

drivers/gpu/drm/nouveau/Kconfig

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,3 +71,14 @@ config DRM_NOUVEAU_BACKLIGHT
7171
help
7272
Say Y here if you want to control the backlight of your display
7373
(e.g. a laptop panel).
74+
75+
config DRM_NOUVEAU_SVM
76+
bool "(EXPERIMENTAL) Enable SVM (Shared Virtual Memory) support"
77+
depends on ARCH_HAS_HMM
78+
depends on DRM_NOUVEAU
79+
depends on STAGING
80+
select HMM_MIRROR
81+
default n
82+
help
83+
Say Y here if you want to enable experimental support for
84+
Shared Virtual Memory (SVM).

drivers/gpu/drm/nouveau/nouveau_chan.c

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@
4242
#include "nouveau_fence.h"
4343
#include "nouveau_abi16.h"
4444
#include "nouveau_vmm.h"
45+
#include "nouveau_svm.h"
4546

4647
MODULE_PARM_DESC(vram_pushbuf, "Create DMA push buffers in VRAM");
4748
int nouveau_vram_pushbuf;
@@ -95,6 +96,10 @@ nouveau_channel_del(struct nouveau_channel **pchan)
9596

9697
if (chan->fence)
9798
nouveau_fence(chan->drm)->context_del(chan);
99+
100+
if (cli)
101+
nouveau_svmm_part(chan->vmm->svmm, chan->inst);
102+
98103
nvif_object_fini(&chan->nvsw);
99104
nvif_object_fini(&chan->gart);
100105
nvif_object_fini(&chan->vram);
@@ -494,6 +499,10 @@ nouveau_channel_new(struct nouveau_drm *drm, struct nvif_device *device,
494499
nouveau_channel_del(pchan);
495500
}
496501

502+
ret = nouveau_svmm_join((*pchan)->vmm->svmm, (*pchan)->inst);
503+
if (ret)
504+
nouveau_channel_del(pchan);
505+
497506
done:
498507
cli->base.super = super;
499508
return ret;

drivers/gpu/drm/nouveau/nouveau_drm.c

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@
6262
#include "nouveau_usif.h"
6363
#include "nouveau_connector.h"
6464
#include "nouveau_platform.h"
65+
#include "nouveau_svm.h"
6566

6667
MODULE_PARM_DESC(config, "option string to pass to driver core");
6768
static char *nouveau_config;
@@ -549,6 +550,7 @@ nouveau_drm_device_init(struct drm_device *dev)
549550

550551
nouveau_debugfs_init(drm);
551552
nouveau_hwmon_init(dev);
553+
nouveau_svm_init(drm);
552554
nouveau_fbcon_init(dev);
553555
nouveau_led_init(dev);
554556

@@ -592,6 +594,7 @@ nouveau_drm_device_fini(struct drm_device *dev)
592594

593595
nouveau_led_fini(dev);
594596
nouveau_fbcon_fini(dev);
597+
nouveau_svm_fini(drm);
595598
nouveau_hwmon_fini(dev);
596599
nouveau_debugfs_fini(drm);
597600

@@ -737,6 +740,7 @@ nouveau_do_suspend(struct drm_device *dev, bool runtime)
737740
struct nouveau_drm *drm = nouveau_drm(dev);
738741
int ret;
739742

743+
nouveau_svm_suspend(drm);
740744
nouveau_led_suspend(dev);
741745

742746
if (dev->mode_config.num_crtc) {
@@ -813,7 +817,7 @@ nouveau_do_resume(struct drm_device *dev, bool runtime)
813817
}
814818

815819
nouveau_led_resume(dev);
816-
820+
nouveau_svm_resume(drm);
817821
return 0;
818822
}
819823

@@ -1033,6 +1037,7 @@ nouveau_ioctls[] = {
10331037
DRM_IOCTL_DEF_DRV(NOUVEAU_GROBJ_ALLOC, nouveau_abi16_ioctl_grobj_alloc, DRM_AUTH|DRM_RENDER_ALLOW),
10341038
DRM_IOCTL_DEF_DRV(NOUVEAU_NOTIFIEROBJ_ALLOC, nouveau_abi16_ioctl_notifierobj_alloc, DRM_AUTH|DRM_RENDER_ALLOW),
10351039
DRM_IOCTL_DEF_DRV(NOUVEAU_GPUOBJ_FREE, nouveau_abi16_ioctl_gpuobj_free, DRM_AUTH|DRM_RENDER_ALLOW),
1040+
DRM_IOCTL_DEF_DRV(NOUVEAU_SVM_INIT, nouveau_svmm_init, DRM_AUTH|DRM_RENDER_ALLOW),
10361041
DRM_IOCTL_DEF_DRV(NOUVEAU_GEM_NEW, nouveau_gem_ioctl_new, DRM_AUTH|DRM_RENDER_ALLOW),
10371042
DRM_IOCTL_DEF_DRV(NOUVEAU_GEM_PUSHBUF, nouveau_gem_ioctl_pushbuf, DRM_AUTH|DRM_RENDER_ALLOW),
10381043
DRM_IOCTL_DEF_DRV(NOUVEAU_GEM_CPU_PREP, nouveau_gem_ioctl_cpu_prep, DRM_AUTH|DRM_RENDER_ALLOW),

drivers/gpu/drm/nouveau/nouveau_drv.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,8 @@ struct nouveau_drm {
210210
bool have_disp_power_ref;
211211

212212
struct dev_pm_domain vga_pm_domain;
213+
214+
struct nouveau_svm *svm;
213215
};
214216

215217
static inline struct nouveau_drm *

0 commit comments

Comments
 (0)