A userspace may create a userspace managed surface but not destroy it,
add hw_destroy function for userspace surfaces so that vmwgfx records the
destroy command and submits it when the userspace context is destroyed.

Signed-off-by: Maaz Mombasawala <maaz.mombasaw...@broadcom.com>
---
 drivers/gpu/drm/vmwgfx/vmwgfx_drv.h     |  1 +
 drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c |  7 ++++-
 drivers/gpu/drm/vmwgfx/vmwgfx_surface.c | 40 +++++++++++++++++++++++++
 3 files changed, 47 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h 
b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h
index 3e959d2a32bc..f6edeac99cf7 100644
--- a/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h
+++ b/drivers/gpu/drm/vmwgfx/vmwgfx_drv.h
@@ -267,6 +267,7 @@ struct vmw_surface {
 struct vmw_cmdbuf_surface {
        struct vmw_surface surface;
        struct ttm_base_object base;
+       bool cmdbuf_destroy;
 };
 
 struct vmw_fifo_state {
diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c 
b/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c
index 0468c9f4f293..70f816062fd2 100644
--- a/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c
+++ b/drivers/gpu/drm/vmwgfx/vmwgfx_execbuf.c
@@ -3374,6 +3374,8 @@ static int vmw_cmd_destroy_gb_surface(struct vmw_private 
*dev_priv,
                                      SVGA3dCmdHeader *header)
 {
        VMW_DECLARE_CMD_VAR(*cmd, SVGA3dCmdDestroyGBSurface);
+       struct vmw_resource *res;
+       struct vmw_cmdbuf_surface *surface;
        int ret;
 
        cmd = container_of(header, typeof(*cmd), header);
@@ -3382,10 +3384,13 @@ static int vmw_cmd_destroy_gb_surface(struct 
vmw_private *dev_priv,
                return -EINVAL;
 
        ret = vmw_cmd_res_check(dev_priv, sw_context, vmw_res_surface,
-                               VMW_RES_DIRTY_NONE, NULL, &cmd->body.sid, NULL);
+                               VMW_RES_DIRTY_NONE, NULL, &cmd->body.sid, &res);
        if (unlikely(ret))
                return ret;
 
+       surface = vmw_res_to_cmdbuf_srf(res);
+       surface->cmdbuf_destroy = true;
+
        ret = vmw_cmdbuf_surface_destroy(dev_priv, sw_context, cmd->body.sid);
        if (unlikely(ret))
                return ret;
diff --git a/drivers/gpu/drm/vmwgfx/vmwgfx_surface.c 
b/drivers/gpu/drm/vmwgfx/vmwgfx_surface.c
index 4f8fb45ab7fa..d4c9a7e51088 100644
--- a/drivers/gpu/drm/vmwgfx/vmwgfx_surface.c
+++ b/drivers/gpu/drm/vmwgfx/vmwgfx_surface.c
@@ -2403,6 +2403,43 @@ static void vmw_cmdbuf_surface_base_release(struct 
ttm_base_object **p_base)
 }
 
 
+static void vmw_cmdbuf_surface_hw_destroy(struct vmw_resource *res)
+{
+       struct vmw_private *dev_priv = res->dev_priv;
+       struct vmw_cmdbuf_surface *surface;
+       struct {
+               SVGA3dCmdHeader header;
+               SVGA3dCmdDestroyGBSurface body;
+       } *cmd;
+
+       if (res->id == -1)
+               return;
+
+       surface = vmw_res_to_cmdbuf_srf(res);
+       /**
+        * If userspace is submitting a destroy command there is no need for
+        * kernel to do so.
+        */
+       if (surface->cmdbuf_destroy)
+               return;
+
+       mutex_lock(&dev_priv->binding_mutex);
+       vmw_view_surface_list_destroy(dev_priv, &surface->surface.view_list);
+
+       cmd = VMW_CMD_RESERVE(dev_priv, sizeof(*cmd));
+       if (unlikely(!cmd)) {
+               mutex_unlock(&dev_priv->binding_mutex);
+               return;
+       }
+
+       cmd->header.id = SVGA_3D_CMD_DESTROY_GB_SURFACE;
+       cmd->header.size = sizeof(cmd->body);
+       cmd->body.sid = res->id;
+       vmw_cmd_commit(dev_priv, sizeof(*cmd));
+       mutex_unlock(&dev_priv->binding_mutex);
+}
+
+
 int vmw_cmdbuf_surface_define(struct vmw_private *dev_priv,
                              struct vmw_sw_context *sw_context,
                              struct vmw_surface_metadata *metadata,
@@ -2484,6 +2521,9 @@ int vmw_cmdbuf_surface_define(struct vmw_private 
*dev_priv,
                return ret;
        }
 
+       res->hw_destroy = vmw_cmdbuf_surface_hw_destroy;
+       surface->cmdbuf_destroy = false;
+
        return 0;
 }
 
-- 
2.34.1

Reply via email to