From c0951b797e7d0f2c6b0df2c0e18185c72d0cf1a1 Mon Sep 17 00:00:00 2001 From: Thomas Hellstrom Date: Tue, 20 Nov 2012 12:19:35 +0000 Subject: drm/vmwgfx: Refactor resource management Refactor resource management to make it easy to hook up resources that are backed up by buffers. In particular, resources and their backing buffers can be evicted and rebound, if supported by the device. To avoid query deadlocks, the query code is also modified somewhat. Signed-off-by: Thomas Hellstrom Reviewed-by: Brian Paul Reviewed-by: Dmitry Torokhov Signed-off-by: Dave Airlie --- drivers/gpu/drm/vmwgfx/vmwgfx_drv.c | 32 ++++++++++++++++++++------------ 1 file changed, 20 insertions(+), 12 deletions(-) (limited to 'drivers/gpu/drm/vmwgfx/vmwgfx_drv.c') diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c index 56973cd41735..91581fd5004b 100644 --- a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c +++ b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.c @@ -432,6 +432,7 @@ static int vmw_driver_load(struct drm_device *dev, unsigned long chipset) struct vmw_private *dev_priv; int ret; uint32_t svga_id; + enum vmw_res_type i; dev_priv = kzalloc(sizeof(*dev_priv), GFP_KERNEL); if (unlikely(dev_priv == NULL)) { @@ -448,15 +449,18 @@ static int vmw_driver_load(struct drm_device *dev, unsigned long chipset) mutex_init(&dev_priv->cmdbuf_mutex); mutex_init(&dev_priv->release_mutex); rwlock_init(&dev_priv->resource_lock); - idr_init(&dev_priv->context_idr); - idr_init(&dev_priv->surface_idr); - idr_init(&dev_priv->stream_idr); + + for (i = vmw_res_context; i < vmw_res_max; ++i) { + idr_init(&dev_priv->res_idr[i]); + INIT_LIST_HEAD(&dev_priv->res_lru[i]); + } + mutex_init(&dev_priv->init_mutex); init_waitqueue_head(&dev_priv->fence_queue); init_waitqueue_head(&dev_priv->fifo_queue); dev_priv->fence_queue_waiters = 0; atomic_set(&dev_priv->fifo_queue_waiters, 0); - INIT_LIST_HEAD(&dev_priv->surface_lru); + dev_priv->used_memory_size = 0; dev_priv->io_start = pci_resource_start(dev->pdev, 0); @@ -670,9 +674,9 @@ out_err2: out_err1: vmw_ttm_global_release(dev_priv); out_err0: - idr_destroy(&dev_priv->surface_idr); - idr_destroy(&dev_priv->context_idr); - idr_destroy(&dev_priv->stream_idr); + for (i = vmw_res_context; i < vmw_res_max; ++i) + idr_destroy(&dev_priv->res_idr[i]); + kfree(dev_priv); return ret; } @@ -680,9 +684,12 @@ out_err0: static int vmw_driver_unload(struct drm_device *dev) { struct vmw_private *dev_priv = vmw_priv(dev); + enum vmw_res_type i; unregister_pm_notifier(&dev_priv->pm_nb); + if (dev_priv->ctx.res_ht_initialized) + drm_ht_remove(&dev_priv->ctx.res_ht); if (dev_priv->ctx.cmd_bounce) vfree(dev_priv->ctx.cmd_bounce); if (dev_priv->enable_fb) { @@ -709,9 +716,9 @@ static int vmw_driver_unload(struct drm_device *dev) (void)ttm_bo_clean_mm(&dev_priv->bdev, TTM_PL_VRAM); (void)ttm_bo_device_release(&dev_priv->bdev); vmw_ttm_global_release(dev_priv); - idr_destroy(&dev_priv->surface_idr); - idr_destroy(&dev_priv->context_idr); - idr_destroy(&dev_priv->stream_idr); + + for (i = vmw_res_context; i < vmw_res_max; ++i) + idr_destroy(&dev_priv->res_idr[i]); kfree(dev_priv); @@ -935,7 +942,7 @@ static void vmw_master_drop(struct drm_device *dev, vmw_fp->locked_master = drm_master_get(file_priv->master); ret = ttm_vt_lock(&vmaster->lock, false, vmw_fp->tfile); - vmw_execbuf_release_pinned_bo(dev_priv, false, 0); + vmw_execbuf_release_pinned_bo(dev_priv); if (unlikely((ret != 0))) { DRM_ERROR("Unable to lock TTM at VT switch.\n"); @@ -987,7 +994,8 @@ static int vmwgfx_pm_notifier(struct notifier_block *nb, unsigned long val, * This empties VRAM and unbinds all GMR bindings. * Buffer contents is moved to swappable memory. */ - vmw_execbuf_release_pinned_bo(dev_priv, false, 0); + vmw_execbuf_release_pinned_bo(dev_priv); + vmw_resource_evict_all(dev_priv); ttm_bo_swapout_all(&dev_priv->bdev); break; -- cgit v1.2.3