mirror of
				https://github.com/torvalds/linux.git
				synced 2025-11-04 10:40:15 +02:00 
			
		
		
		
	drm/shmem-helper: Fix locking for drm_gem_shmem_get_pages_sgt()
Other functions touching shmem->sgt take the pages lock, so do that here too. drm_gem_shmem_get_pages() & co take the same lock, so move to the _locked() variants to avoid recursive locking. Discovered while auditing locking to write the Rust abstractions. Fixes:2194a63a81("drm: Add library for shmem backed GEM objects") Fixes:4fa3d66f13("drm/shmem: Do dma_unmap_sg before purging pages") Signed-off-by: Asahi Lina <lina@asahilina.net> Reviewed-by: Javier Martinez Canillas <javierm@redhat.com> Signed-off-by: Javier Martinez Canillas <javierm@redhat.com> Link: https://patchwork.freedesktop.org/patch/msgid/20230205125124.2260-1-lina@asahilina.net (cherry picked from commitaa8c85affe) Signed-off-by: Javier Martinez Canillas <javierm@redhat.com>
This commit is contained in:
		
							parent
							
								
									38b2d8efd0
								
							
						
					
					
						commit
						ddddedaa0d
					
				
					 1 changed files with 34 additions and 20 deletions
				
			
		| 
						 | 
				
			
			@ -678,23 +678,7 @@ struct sg_table *drm_gem_shmem_get_sg_table(struct drm_gem_shmem_object *shmem)
 | 
			
		|||
}
 | 
			
		||||
EXPORT_SYMBOL_GPL(drm_gem_shmem_get_sg_table);
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * drm_gem_shmem_get_pages_sgt - Pin pages, dma map them, and return a
 | 
			
		||||
 *				 scatter/gather table for a shmem GEM object.
 | 
			
		||||
 * @shmem: shmem GEM object
 | 
			
		||||
 *
 | 
			
		||||
 * This function returns a scatter/gather table suitable for driver usage. If
 | 
			
		||||
 * the sg table doesn't exist, the pages are pinned, dma-mapped, and a sg
 | 
			
		||||
 * table created.
 | 
			
		||||
 *
 | 
			
		||||
 * This is the main function for drivers to get at backing storage, and it hides
 | 
			
		||||
 * and difference between dma-buf imported and natively allocated objects.
 | 
			
		||||
 * drm_gem_shmem_get_sg_table() should not be directly called by drivers.
 | 
			
		||||
 *
 | 
			
		||||
 * Returns:
 | 
			
		||||
 * A pointer to the scatter/gather table of pinned pages or errno on failure.
 | 
			
		||||
 */
 | 
			
		||||
struct sg_table *drm_gem_shmem_get_pages_sgt(struct drm_gem_shmem_object *shmem)
 | 
			
		||||
static struct sg_table *drm_gem_shmem_get_pages_sgt_locked(struct drm_gem_shmem_object *shmem)
 | 
			
		||||
{
 | 
			
		||||
	struct drm_gem_object *obj = &shmem->base;
 | 
			
		||||
	int ret;
 | 
			
		||||
| 
						 | 
				
			
			@ -705,7 +689,7 @@ struct sg_table *drm_gem_shmem_get_pages_sgt(struct drm_gem_shmem_object *shmem)
 | 
			
		|||
 | 
			
		||||
	WARN_ON(obj->import_attach);
 | 
			
		||||
 | 
			
		||||
	ret = drm_gem_shmem_get_pages(shmem);
 | 
			
		||||
	ret = drm_gem_shmem_get_pages_locked(shmem);
 | 
			
		||||
	if (ret)
 | 
			
		||||
		return ERR_PTR(ret);
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -727,10 +711,40 @@ struct sg_table *drm_gem_shmem_get_pages_sgt(struct drm_gem_shmem_object *shmem)
 | 
			
		|||
	sg_free_table(sgt);
 | 
			
		||||
	kfree(sgt);
 | 
			
		||||
err_put_pages:
 | 
			
		||||
	drm_gem_shmem_put_pages(shmem);
 | 
			
		||||
	drm_gem_shmem_put_pages_locked(shmem);
 | 
			
		||||
	return ERR_PTR(ret);
 | 
			
		||||
}
 | 
			
		||||
EXPORT_SYMBOL_GPL(drm_gem_shmem_get_pages_sgt);
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * drm_gem_shmem_get_pages_sgt - Pin pages, dma map them, and return a
 | 
			
		||||
 *				 scatter/gather table for a shmem GEM object.
 | 
			
		||||
 * @shmem: shmem GEM object
 | 
			
		||||
 *
 | 
			
		||||
 * This function returns a scatter/gather table suitable for driver usage. If
 | 
			
		||||
 * the sg table doesn't exist, the pages are pinned, dma-mapped, and a sg
 | 
			
		||||
 * table created.
 | 
			
		||||
 *
 | 
			
		||||
 * This is the main function for drivers to get at backing storage, and it hides
 | 
			
		||||
 * and difference between dma-buf imported and natively allocated objects.
 | 
			
		||||
 * drm_gem_shmem_get_sg_table() should not be directly called by drivers.
 | 
			
		||||
 *
 | 
			
		||||
 * Returns:
 | 
			
		||||
 * A pointer to the scatter/gather table of pinned pages or errno on failure.
 | 
			
		||||
 */
 | 
			
		||||
struct sg_table *drm_gem_shmem_get_pages_sgt(struct drm_gem_shmem_object *shmem)
 | 
			
		||||
{
 | 
			
		||||
	int ret;
 | 
			
		||||
	struct sg_table *sgt;
 | 
			
		||||
 | 
			
		||||
	ret = mutex_lock_interruptible(&shmem->pages_lock);
 | 
			
		||||
	if (ret)
 | 
			
		||||
		return ERR_PTR(ret);
 | 
			
		||||
	sgt = drm_gem_shmem_get_pages_sgt_locked(shmem);
 | 
			
		||||
	mutex_unlock(&shmem->pages_lock);
 | 
			
		||||
 | 
			
		||||
	return sgt;
 | 
			
		||||
}
 | 
			
		||||
EXPORT_SYMBOL(drm_gem_shmem_get_pages_sgt);
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * drm_gem_shmem_prime_import_sg_table - Produce a shmem GEM object from
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in a new issue