@@ -42,6 +42,69 @@ nvkm_uvmm_search(struct nvkm_client *client, u64 handle)
42
42
return nvkm_uvmm (object )-> vmm ;
43
43
}
44
44
45
+ static int
46
+ nvkm_uvmm_mthd_pfnclr (struct nvkm_uvmm * uvmm , void * argv , u32 argc )
47
+ {
48
+ struct nvkm_client * client = uvmm -> object .client ;
49
+ union {
50
+ struct nvif_vmm_pfnclr_v0 v0 ;
51
+ } * args = argv ;
52
+ struct nvkm_vmm * vmm = uvmm -> vmm ;
53
+ int ret = - ENOSYS ;
54
+ u64 addr , size ;
55
+
56
+ if (!(ret = nvif_unpack (ret , & argv , & argc , args -> v0 , 0 , 0 , false))) {
57
+ addr = args -> v0 .addr ;
58
+ size = args -> v0 .size ;
59
+ } else
60
+ return ret ;
61
+
62
+ if (!client -> super )
63
+ return - ENOENT ;
64
+
65
+ if (size ) {
66
+ mutex_lock (& vmm -> mutex );
67
+ ret = nvkm_vmm_pfn_unmap (vmm , addr , size );
68
+ mutex_unlock (& vmm -> mutex );
69
+ }
70
+
71
+ return ret ;
72
+ }
73
+
74
+ static int
75
+ nvkm_uvmm_mthd_pfnmap (struct nvkm_uvmm * uvmm , void * argv , u32 argc )
76
+ {
77
+ struct nvkm_client * client = uvmm -> object .client ;
78
+ union {
79
+ struct nvif_vmm_pfnmap_v0 v0 ;
80
+ } * args = argv ;
81
+ struct nvkm_vmm * vmm = uvmm -> vmm ;
82
+ int ret = - ENOSYS ;
83
+ u64 addr , size , * phys ;
84
+ u8 page ;
85
+
86
+ if (!(ret = nvif_unpack (ret , & argv , & argc , args -> v0 , 0 , 0 , true))) {
87
+ page = args -> v0 .page ;
88
+ addr = args -> v0 .addr ;
89
+ size = args -> v0 .size ;
90
+ phys = args -> v0 .phys ;
91
+ if (argc != (size >> page ) * sizeof (args -> v0 .phys [0 ]))
92
+ return - EINVAL ;
93
+ } else
94
+ return ret ;
95
+
96
+ if (!client -> super )
97
+ return - ENOENT ;
98
+
99
+ if (size ) {
100
+ mutex_lock (& vmm -> mutex );
101
+ ret = nvkm_vmm_pfn_map (vmm , page , addr , size , phys );
102
+ mutex_unlock (& vmm -> mutex );
103
+ }
104
+
105
+ return ret ;
106
+ }
107
+
45
108
static int
46
109
nvkm_uvmm_mthd_unmap (struct nvkm_uvmm * uvmm , void * argv , u32 argc )
47
110
{
@@ -78,7 +141,7 @@ nvkm_uvmm_mthd_unmap(struct nvkm_uvmm *uvmm, void *argv, u32 argc)
78
141
goto done ;
79
142
}
80
143
81
- nvkm_vmm_unmap_locked (vmm , vma );
144
+ nvkm_vmm_unmap_locked (vmm , vma , false );
82
145
ret = 0 ;
83
146
done :
84
147
mutex_unlock (& vmm -> mutex );
@@ -124,6 +187,11 @@ nvkm_uvmm_mthd_map(struct nvkm_uvmm *uvmm, void *argv, u32 argc)
124
187
goto fail ;
125
188
}
126
189
190
+ if (ret = - EINVAL , vma -> mapped && !vma -> memory ) {
191
+ VMM_DEBUG (vmm , "pfnmap %016llx" , addr );
192
+ goto fail ;
193
+ }
194
+
127
195
if (ret = - EINVAL , vma -> addr != addr || vma -> size != size ) {
128
196
if (addr + size > vma -> addr + vma -> size || vma -> memory ||
129
197
(vma -> refd == NVKM_VMA_PAGE_NONE && !vma -> mapref )) {
@@ -271,6 +339,8 @@ nvkm_uvmm_mthd(struct nvkm_object *object, u32 mthd, void *argv, u32 argc)
271
339
case NVIF_VMM_V0_PUT : return nvkm_uvmm_mthd_put (uvmm , argv , argc );
272
340
case NVIF_VMM_V0_MAP : return nvkm_uvmm_mthd_map (uvmm , argv , argc );
273
341
case NVIF_VMM_V0_UNMAP : return nvkm_uvmm_mthd_unmap (uvmm , argv , argc );
342
+ case NVIF_VMM_V0_PFNMAP : return nvkm_uvmm_mthd_pfnmap (uvmm , argv , argc );
343
+ case NVIF_VMM_V0_PFNCLR : return nvkm_uvmm_mthd_pfnclr (uvmm , argv , argc );
274
344
default :
275
345
break ;
276
346
}
0 commit comments