For performance, BO page mappings can stay in place even if the map counter has returned to 0. In these cases, the existing page mapping has to be reused by the next vmap operation. Otherwise a new mapping would be installed and the old mapping's pages leak.
Fix the issue by reusing existing page mappings for vmap operations.
Signed-off-by: Thomas Zimmermann tzimmermann@suse.de Fixes: 1086db71a1db ("drm/vram-helper: Remove invariant parameters from internal kmap function") Acked-by: Christian König christian.koenig@amd.com Tested-by: Eli Cohen elic@nvidia.com Reported-by: Eli Cohen elic@nvidia.com Cc: Daniel Vetter daniel.vetter@ffwll.ch Cc: Christian König christian.koenig@amd.com Cc: Maarten Lankhorst maarten.lankhorst@linux.intel.com Cc: Maxime Ripard mripard@kernel.org Cc: David Airlie airlied@linux.ie Cc: Daniel Vetter daniel@ffwll.ch Cc: dri-devel@lists.freedesktop.org --- drivers/gpu/drm/drm_gem_vram_helper.c | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-)
diff --git a/drivers/gpu/drm/drm_gem_vram_helper.c b/drivers/gpu/drm/drm_gem_vram_helper.c index 02ca22e90290..0b232a73c1b7 100644 --- a/drivers/gpu/drm/drm_gem_vram_helper.c +++ b/drivers/gpu/drm/drm_gem_vram_helper.c @@ -387,9 +387,16 @@ static int drm_gem_vram_kmap_locked(struct drm_gem_vram_object *gbo, if (gbo->vmap_use_count > 0) goto out;
- ret = ttm_bo_vmap(&gbo->bo, &gbo->map); - if (ret) - return ret; + /* + * VRAM helpers unmap the BO only on demand. So the previous + * page mapping might still be around. Only vmap if the there's + * no mapping present. + */ + if (dma_buf_map_is_null(&gbo->map)) { + ret = ttm_bo_vmap(&gbo->bo, &gbo->map); + if (ret) + return ret; + }
out: ++gbo->vmap_use_count; @@ -577,6 +584,7 @@ static void drm_gem_vram_bo_driver_move_notify(struct drm_gem_vram_object *gbo, return;
ttm_bo_vunmap(bo, &gbo->map); + dma_buf_map_clear(&gbo->map); /* explicitly clear mapping for next vmap call */ }
static int drm_gem_vram_bo_driver_move(struct drm_gem_vram_object *gbo,
dri-devel@lists.freedesktop.org