Skip to content

Commit f89ab12

Browse files
Darksonnjannau
authored andcommitted
drm_gem: add mutex to drm_gem_object.gpuva
There are two main ways that GPUVM might be used: * staged mode, where VM_BIND ioctls update the GPUVM immediately so that the GPUVM reflects the state of the VM *including* staged changes that are not yet applied to the GPU's virtual address space. * immediate mode, where the GPUVM state is updated during run_job(), i.e., in the DMA fence signalling critical path, to ensure that the GPUVM and the GPU's virtual address space has the same state at all times. Currently, only Panthor uses GPUVM in immediate mode, but the Rust drivers Tyr and Nova will also use GPUVM in immediate mode, so it is worth to support both staged and immediate mode well in GPUVM. To use immediate mode, the GEMs gpuva list must be modified during the fence signalling path, which means that it must be protected by a lock that is fence signalling safe. For this reason, a mutex is added to struct drm_gem_object that is intended to achieve this purpose. Adding it directly in the GEM object both makes it easier to use GPUVM in immediate mode, but also makes it possible to take the gpuva lock from core drm code. As a follow-up, another change that should probably be made to support immediate mode is a mechanism to postpone cleanup of vm_bo objects, as dropping a vm_bo object in the fence signalling path is problematic for two reasons: * When using DRM_GPUVM_RESV_PROTECTED, you cannot remove the vm_bo from the extobj/evicted lists during the fence signalling path. * Dropping a vm_bo could lead to the GEM object getting destroyed. The requirement that GEM object cleanup is fence signalling safe is dubious and likely to be violated in practice. Panthor already has its own custom implementation of postponing vm_bo cleanup. Reviewed-by: Boris Brezillon <boris.brezillon@collabora.com> Signed-off-by: Alice Ryhl <aliceryhl@google.com> Link: https://lore.kernel.org/r/20250827-gpuva-mutex-in-gem-v3-1-bd89f5a82c0d@google.com Signed-off-by: Danilo Krummrich <dakr@kernel.org>
1 parent 5b24503 commit f89ab12

2 files changed

Lines changed: 20 additions & 6 deletions

File tree

drivers/gpu/drm/drm_gem.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,7 @@ void drm_gem_private_object_init(struct drm_device *dev,
187187
kref_init(&obj->refcount);
188188
obj->handle_count = 0;
189189
obj->size = size;
190+
mutex_init(&obj->gpuva.lock);
190191
dma_resv_init(&obj->_resv);
191192
if (!obj->resv)
192193
obj->resv = &obj->_resv;
@@ -210,6 +211,7 @@ void drm_gem_private_object_fini(struct drm_gem_object *obj)
210211
WARN_ON(obj->dma_buf);
211212

212213
dma_resv_fini(&obj->_resv);
214+
mutex_destroy(&obj->gpuva.lock);
213215
}
214216
EXPORT_SYMBOL(drm_gem_private_object_fini);
215217

include/drm/drm_gem.h

Lines changed: 18 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -398,16 +398,28 @@ struct drm_gem_object {
398398
struct dma_resv _resv;
399399

400400
/**
401-
* @gpuva:
402-
*
403-
* Provides the list of GPU VAs attached to this GEM object.
404-
*
405-
* Drivers should lock list accesses with the GEMs &dma_resv lock
406-
* (&drm_gem_object.resv) or a custom lock if one is provided.
401+
* @gpuva: Fields used by GPUVM to manage mappings pointing to this GEM object.
407402
*/
408403
struct {
404+
/**
405+
* @gpuva.list: list of GPUVM mappings attached to this GEM object.
406+
*
407+
* Drivers should lock list accesses with either the GEMs
408+
* &dma_resv lock (&drm_gem_object.resv) or the
409+
* &drm_gem_object.gpuva.lock mutex.
410+
*/
409411
struct list_head list;
410412

413+
/**
414+
* @gpuva.lock: lock protecting access to &drm_gem_object.gpuva.list
415+
* when the resv lock can't be used.
416+
*
417+
* Should only be used when the VM is being modified in a fence
418+
* signalling path, otherwise you should use &drm_gem_object.resv to
419+
* protect accesses to &drm_gem_object.gpuva.list.
420+
*/
421+
struct mutex lock;
422+
411423
#ifdef CONFIG_LOCKDEP
412424
struct lockdep_map *lock_dep_map;
413425
#endif

0 commit comments

Comments
 (0)