Commit b3edf499 authored by Dave Airlie's avatar Dave Airlie

Merge branch 'vmwgfx-next' of https://gitlab.freedesktop.org/drawat/linux into drm-next

Resource dirtying improvement by Thomas,
user-space error logging improvement and
some other minor fixes.
Signed-off-by: default avatarDave Airlie <airlied@redhat.com>
From: Deepak Rawat <drawat@vmware.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20190423211630.61874-1-drawat@vmware.com
parents dbb92471 c601b12f
...@@ -499,12 +499,9 @@ static int vmw_binding_scrub_shader(struct vmw_ctx_bindinfo *bi, bool rebind) ...@@ -499,12 +499,9 @@ static int vmw_binding_scrub_shader(struct vmw_ctx_bindinfo *bi, bool rebind)
SVGA3dCmdSetShader body; SVGA3dCmdSetShader body;
} *cmd; } *cmd;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for shader "
"unbinding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_SET_SHADER; cmd->header.id = SVGA_3D_CMD_SET_SHADER;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -534,12 +531,9 @@ static int vmw_binding_scrub_render_target(struct vmw_ctx_bindinfo *bi, ...@@ -534,12 +531,9 @@ static int vmw_binding_scrub_render_target(struct vmw_ctx_bindinfo *bi,
SVGA3dCmdSetRenderTarget body; SVGA3dCmdSetRenderTarget body;
} *cmd; } *cmd;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for render target "
"unbinding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_SETRENDERTARGET; cmd->header.id = SVGA_3D_CMD_SETRENDERTARGET;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -576,12 +570,9 @@ static int vmw_binding_scrub_texture(struct vmw_ctx_bindinfo *bi, ...@@ -576,12 +570,9 @@ static int vmw_binding_scrub_texture(struct vmw_ctx_bindinfo *bi,
} body; } body;
} *cmd; } *cmd;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for texture "
"unbinding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_SETTEXTURESTATE; cmd->header.id = SVGA_3D_CMD_SETTEXTURESTATE;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -610,12 +601,10 @@ static int vmw_binding_scrub_dx_shader(struct vmw_ctx_bindinfo *bi, bool rebind) ...@@ -610,12 +601,10 @@ static int vmw_binding_scrub_dx_shader(struct vmw_ctx_bindinfo *bi, bool rebind)
SVGA3dCmdDXSetShader body; SVGA3dCmdDXSetShader body;
} *cmd; } *cmd;
cmd = vmw_fifo_reserve_dx(dev_priv, sizeof(*cmd), bi->ctx->id); cmd = VMW_FIFO_RESERVE_DX(dev_priv, sizeof(*cmd), bi->ctx->id);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for DX shader "
"unbinding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_SET_SHADER; cmd->header.id = SVGA_3D_CMD_DX_SET_SHADER;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
cmd->body.type = binding->shader_slot + SVGA3D_SHADERTYPE_MIN; cmd->body.type = binding->shader_slot + SVGA3D_SHADERTYPE_MIN;
...@@ -641,12 +630,9 @@ static int vmw_binding_scrub_cb(struct vmw_ctx_bindinfo *bi, bool rebind) ...@@ -641,12 +630,9 @@ static int vmw_binding_scrub_cb(struct vmw_ctx_bindinfo *bi, bool rebind)
SVGA3dCmdDXSetSingleConstantBuffer body; SVGA3dCmdDXSetSingleConstantBuffer body;
} *cmd; } *cmd;
cmd = vmw_fifo_reserve_dx(dev_priv, sizeof(*cmd), bi->ctx->id); cmd = VMW_FIFO_RESERVE_DX(dev_priv, sizeof(*cmd), bi->ctx->id);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for DX shader "
"unbinding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_SET_SINGLE_CONSTANT_BUFFER; cmd->header.id = SVGA_3D_CMD_DX_SET_SINGLE_CONSTANT_BUFFER;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -768,12 +754,9 @@ static int vmw_emit_set_sr(struct vmw_ctx_binding_state *cbs, ...@@ -768,12 +754,9 @@ static int vmw_emit_set_sr(struct vmw_ctx_binding_state *cbs,
view_id_size = cbs->bind_cmd_count*sizeof(uint32); view_id_size = cbs->bind_cmd_count*sizeof(uint32);
cmd_size = sizeof(*cmd) + view_id_size; cmd_size = sizeof(*cmd) + view_id_size;
cmd = vmw_fifo_reserve_dx(ctx->dev_priv, cmd_size, ctx->id); cmd = VMW_FIFO_RESERVE_DX(ctx->dev_priv, cmd_size, ctx->id);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for DX shader"
" resource binding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_SET_SHADER_RESOURCES; cmd->header.id = SVGA_3D_CMD_DX_SET_SHADER_RESOURCES;
cmd->header.size = sizeof(cmd->body) + view_id_size; cmd->header.size = sizeof(cmd->body) + view_id_size;
...@@ -807,12 +790,9 @@ static int vmw_emit_set_rt(struct vmw_ctx_binding_state *cbs) ...@@ -807,12 +790,9 @@ static int vmw_emit_set_rt(struct vmw_ctx_binding_state *cbs)
vmw_collect_view_ids(cbs, loc, SVGA3D_MAX_SIMULTANEOUS_RENDER_TARGETS); vmw_collect_view_ids(cbs, loc, SVGA3D_MAX_SIMULTANEOUS_RENDER_TARGETS);
view_id_size = cbs->bind_cmd_count*sizeof(uint32); view_id_size = cbs->bind_cmd_count*sizeof(uint32);
cmd_size = sizeof(*cmd) + view_id_size; cmd_size = sizeof(*cmd) + view_id_size;
cmd = vmw_fifo_reserve_dx(ctx->dev_priv, cmd_size, ctx->id); cmd = VMW_FIFO_RESERVE_DX(ctx->dev_priv, cmd_size, ctx->id);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for DX render-target"
" binding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_SET_RENDERTARGETS; cmd->header.id = SVGA_3D_CMD_DX_SET_RENDERTARGETS;
cmd->header.size = sizeof(cmd->body) + view_id_size; cmd->header.size = sizeof(cmd->body) + view_id_size;
...@@ -894,12 +874,9 @@ static int vmw_emit_set_so(struct vmw_ctx_binding_state *cbs) ...@@ -894,12 +874,9 @@ static int vmw_emit_set_so(struct vmw_ctx_binding_state *cbs)
so_target_size = cbs->bind_cmd_count*sizeof(SVGA3dSoTarget); so_target_size = cbs->bind_cmd_count*sizeof(SVGA3dSoTarget);
cmd_size = sizeof(*cmd) + so_target_size; cmd_size = sizeof(*cmd) + so_target_size;
cmd = vmw_fifo_reserve_dx(ctx->dev_priv, cmd_size, ctx->id); cmd = VMW_FIFO_RESERVE_DX(ctx->dev_priv, cmd_size, ctx->id);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for DX SO target"
" binding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_SET_SOTARGETS; cmd->header.id = SVGA_3D_CMD_DX_SET_SOTARGETS;
cmd->header.size = sizeof(cmd->body) + so_target_size; cmd->header.size = sizeof(cmd->body) + so_target_size;
...@@ -1011,12 +988,9 @@ static int vmw_emit_set_vb(struct vmw_ctx_binding_state *cbs) ...@@ -1011,12 +988,9 @@ static int vmw_emit_set_vb(struct vmw_ctx_binding_state *cbs)
set_vb_size = cbs->bind_cmd_count*sizeof(SVGA3dVertexBuffer); set_vb_size = cbs->bind_cmd_count*sizeof(SVGA3dVertexBuffer);
cmd_size = sizeof(*cmd) + set_vb_size; cmd_size = sizeof(*cmd) + set_vb_size;
cmd = vmw_fifo_reserve_dx(ctx->dev_priv, cmd_size, ctx->id); cmd = VMW_FIFO_RESERVE_DX(ctx->dev_priv, cmd_size, ctx->id);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for DX vertex buffer"
" binding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_SET_VERTEX_BUFFERS; cmd->header.id = SVGA_3D_CMD_DX_SET_VERTEX_BUFFERS;
cmd->header.size = sizeof(cmd->body) + set_vb_size; cmd->header.size = sizeof(cmd->body) + set_vb_size;
...@@ -1167,12 +1141,10 @@ static int vmw_binding_scrub_ib(struct vmw_ctx_bindinfo *bi, bool rebind) ...@@ -1167,12 +1141,10 @@ static int vmw_binding_scrub_ib(struct vmw_ctx_bindinfo *bi, bool rebind)
SVGA3dCmdDXSetIndexBuffer body; SVGA3dCmdDXSetIndexBuffer body;
} *cmd; } *cmd;
cmd = vmw_fifo_reserve_dx(dev_priv, sizeof(*cmd), bi->ctx->id); cmd = VMW_FIFO_RESERVE_DX(dev_priv, sizeof(*cmd), bi->ctx->id);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for DX index buffer "
"binding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_SET_INDEX_BUFFER; cmd->header.id = SVGA_3D_CMD_DX_SET_INDEX_BUFFER;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
if (rebind) { if (rebind) {
...@@ -1269,6 +1241,32 @@ void vmw_binding_state_reset(struct vmw_ctx_binding_state *cbs) ...@@ -1269,6 +1241,32 @@ void vmw_binding_state_reset(struct vmw_ctx_binding_state *cbs)
vmw_binding_drop(entry); vmw_binding_drop(entry);
} }
/**
* vmw_binding_dirtying - Return whether a binding type is dirtying its resource
* @binding_type: The binding type
*
* Each time a resource is put on the validation list as the result of a
* context binding referencing it, we need to determine whether that resource
* will be dirtied (written to by the GPU) as a result of the corresponding
* GPU operation. Currently rendertarget-, depth-stencil-, and
* stream-output-target bindings are capable of dirtying its resource.
*
* Return: Whether the binding type dirties the resource its binding points to.
*/
u32 vmw_binding_dirtying(enum vmw_ctx_binding_type binding_type)
{
static u32 is_binding_dirtying[vmw_ctx_binding_max] = {
[vmw_ctx_binding_rt] = VMW_RES_DIRTY_SET,
[vmw_ctx_binding_dx_rt] = VMW_RES_DIRTY_SET,
[vmw_ctx_binding_ds] = VMW_RES_DIRTY_SET,
[vmw_ctx_binding_so] = VMW_RES_DIRTY_SET,
};
/* Review this function as new bindings are added. */
BUILD_BUG_ON(vmw_ctx_binding_max != 11);
return is_binding_dirtying[binding_type];
}
/* /*
* This function is unused at run-time, and only used to hold various build * This function is unused at run-time, and only used to hold various build
* asserts important for code optimization assumptions. * asserts important for code optimization assumptions.
......
...@@ -205,5 +205,7 @@ extern void vmw_binding_state_free(struct vmw_ctx_binding_state *cbs); ...@@ -205,5 +205,7 @@ extern void vmw_binding_state_free(struct vmw_ctx_binding_state *cbs);
extern struct list_head * extern struct list_head *
vmw_binding_state_list(struct vmw_ctx_binding_state *cbs); vmw_binding_state_list(struct vmw_ctx_binding_state *cbs);
extern void vmw_binding_state_reset(struct vmw_ctx_binding_state *cbs); extern void vmw_binding_state_reset(struct vmw_ctx_binding_state *cbs);
extern u32 vmw_binding_dirtying(enum vmw_ctx_binding_type binding_type);
#endif #endif
...@@ -393,6 +393,7 @@ static void vmw_cmdbuf_ctx_process(struct vmw_cmdbuf_man *man, ...@@ -393,6 +393,7 @@ static void vmw_cmdbuf_ctx_process(struct vmw_cmdbuf_man *man,
__vmw_cmdbuf_header_free(entry); __vmw_cmdbuf_header_free(entry);
break; break;
case SVGA_CB_STATUS_COMMAND_ERROR: case SVGA_CB_STATUS_COMMAND_ERROR:
WARN_ONCE(true, "Command buffer error.\n");
entry->cb_header->status = SVGA_CB_STATUS_NONE; entry->cb_header->status = SVGA_CB_STATUS_NONE;
list_add_tail(&entry->list, &man->error); list_add_tail(&entry->list, &man->error);
schedule_work(&man->work); schedule_work(&man->work);
...@@ -511,17 +512,14 @@ static void vmw_cmdbuf_work_func(struct work_struct *work) ...@@ -511,17 +512,14 @@ static void vmw_cmdbuf_work_func(struct work_struct *work)
container_of(work, struct vmw_cmdbuf_man, work); container_of(work, struct vmw_cmdbuf_man, work);
struct vmw_cmdbuf_header *entry, *next; struct vmw_cmdbuf_header *entry, *next;
uint32_t dummy; uint32_t dummy;
bool restart[SVGA_CB_CONTEXT_MAX];
bool send_fence = false; bool send_fence = false;
struct list_head restart_head[SVGA_CB_CONTEXT_MAX]; struct list_head restart_head[SVGA_CB_CONTEXT_MAX];
int i; int i;
struct vmw_cmdbuf_context *ctx; struct vmw_cmdbuf_context *ctx;
bool global_block = false; bool global_block = false;
for_each_cmdbuf_ctx(man, i, ctx) { for_each_cmdbuf_ctx(man, i, ctx)
INIT_LIST_HEAD(&restart_head[i]); INIT_LIST_HEAD(&restart_head[i]);
restart[i] = false;
}
mutex_lock(&man->error_mutex); mutex_lock(&man->error_mutex);
spin_lock(&man->lock); spin_lock(&man->lock);
...@@ -533,23 +531,23 @@ static void vmw_cmdbuf_work_func(struct work_struct *work) ...@@ -533,23 +531,23 @@ static void vmw_cmdbuf_work_func(struct work_struct *work)
const char *cmd_name; const char *cmd_name;
list_del_init(&entry->list); list_del_init(&entry->list);
restart[entry->cb_context] = true;
global_block = true; global_block = true;
if (!vmw_cmd_describe(header, &error_cmd_size, &cmd_name)) { if (!vmw_cmd_describe(header, &error_cmd_size, &cmd_name)) {
DRM_ERROR("Unknown command causing device error.\n"); VMW_DEBUG_USER("Unknown command causing device error.\n");
DRM_ERROR("Command buffer offset is %lu\n", VMW_DEBUG_USER("Command buffer offset is %lu\n",
(unsigned long) cb_hdr->errorOffset); (unsigned long) cb_hdr->errorOffset);
__vmw_cmdbuf_header_free(entry); __vmw_cmdbuf_header_free(entry);
send_fence = true; send_fence = true;
continue; continue;
} }
DRM_ERROR("Command \"%s\" causing device error.\n", cmd_name); VMW_DEBUG_USER("Command \"%s\" causing device error.\n",
DRM_ERROR("Command buffer offset is %lu\n", cmd_name);
(unsigned long) cb_hdr->errorOffset); VMW_DEBUG_USER("Command buffer offset is %lu\n",
DRM_ERROR("Command size is %lu\n", (unsigned long) cb_hdr->errorOffset);
(unsigned long) error_cmd_size); VMW_DEBUG_USER("Command size is %lu\n",
(unsigned long) error_cmd_size);
new_start_offset = cb_hdr->errorOffset + error_cmd_size; new_start_offset = cb_hdr->errorOffset + error_cmd_size;
......
...@@ -156,12 +156,9 @@ static void vmw_hw_context_destroy(struct vmw_resource *res) ...@@ -156,12 +156,9 @@ static void vmw_hw_context_destroy(struct vmw_resource *res)
} }
vmw_execbuf_release_pinned_bo(dev_priv); vmw_execbuf_release_pinned_bo(dev_priv);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for surface "
"destruction.\n");
return; return;
}
cmd->header.id = SVGA_3D_CMD_CONTEXT_DESTROY; cmd->header.id = SVGA_3D_CMD_CONTEXT_DESTROY;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -210,7 +207,7 @@ static int vmw_gb_context_init(struct vmw_private *dev_priv, ...@@ -210,7 +207,7 @@ static int vmw_gb_context_init(struct vmw_private *dev_priv,
for (i = 0; i < SVGA_COTABLE_DX10_MAX; ++i) { for (i = 0; i < SVGA_COTABLE_DX10_MAX; ++i) {
uctx->cotables[i] = vmw_cotable_alloc(dev_priv, uctx->cotables[i] = vmw_cotable_alloc(dev_priv,
&uctx->res, i); &uctx->res, i);
if (unlikely(IS_ERR(uctx->cotables[i]))) { if (IS_ERR(uctx->cotables[i])) {
ret = PTR_ERR(uctx->cotables[i]); ret = PTR_ERR(uctx->cotables[i]);
goto out_cotables; goto out_cotables;
} }
...@@ -259,9 +256,8 @@ static int vmw_context_init(struct vmw_private *dev_priv, ...@@ -259,9 +256,8 @@ static int vmw_context_init(struct vmw_private *dev_priv,
return -ENOMEM; return -ENOMEM;
} }
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL)) {
DRM_ERROR("Fifo reserve failed.\n");
vmw_resource_unreference(&res); vmw_resource_unreference(&res);
return -ENOMEM; return -ENOMEM;
} }
...@@ -311,10 +307,8 @@ static int vmw_gb_context_create(struct vmw_resource *res) ...@@ -311,10 +307,8 @@ static int vmw_gb_context_create(struct vmw_resource *res)
goto out_no_fifo; goto out_no_fifo;
} }
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL)) {
DRM_ERROR("Failed reserving FIFO space for context "
"creation.\n");
ret = -ENOMEM; ret = -ENOMEM;
goto out_no_fifo; goto out_no_fifo;
} }
...@@ -345,12 +339,10 @@ static int vmw_gb_context_bind(struct vmw_resource *res, ...@@ -345,12 +339,10 @@ static int vmw_gb_context_bind(struct vmw_resource *res,
BUG_ON(bo->mem.mem_type != VMW_PL_MOB); BUG_ON(bo->mem.mem_type != VMW_PL_MOB);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for context "
"binding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_BIND_GB_CONTEXT; cmd->header.id = SVGA_3D_CMD_BIND_GB_CONTEXT;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
cmd->body.cid = res->id; cmd->body.cid = res->id;
...@@ -391,10 +383,8 @@ static int vmw_gb_context_unbind(struct vmw_resource *res, ...@@ -391,10 +383,8 @@ static int vmw_gb_context_unbind(struct vmw_resource *res,
submit_size = sizeof(*cmd2) + (readback ? sizeof(*cmd1) : 0); submit_size = sizeof(*cmd2) + (readback ? sizeof(*cmd1) : 0);
cmd = vmw_fifo_reserve(dev_priv, submit_size); cmd = VMW_FIFO_RESERVE(dev_priv, submit_size);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL)) {
DRM_ERROR("Failed reserving FIFO space for context "
"unbinding.\n");
mutex_unlock(&dev_priv->binding_mutex); mutex_unlock(&dev_priv->binding_mutex);
return -ENOMEM; return -ENOMEM;
} }
...@@ -441,12 +431,9 @@ static int vmw_gb_context_destroy(struct vmw_resource *res) ...@@ -441,12 +431,9 @@ static int vmw_gb_context_destroy(struct vmw_resource *res)
if (likely(res->id == -1)) if (likely(res->id == -1))
return 0; return 0;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for context "
"destruction.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DESTROY_GB_CONTEXT; cmd->header.id = SVGA_3D_CMD_DESTROY_GB_CONTEXT;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -487,10 +474,8 @@ static int vmw_dx_context_create(struct vmw_resource *res) ...@@ -487,10 +474,8 @@ static int vmw_dx_context_create(struct vmw_resource *res)
goto out_no_fifo; goto out_no_fifo;
} }
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL)) {
DRM_ERROR("Failed reserving FIFO space for context "
"creation.\n");
ret = -ENOMEM; ret = -ENOMEM;
goto out_no_fifo; goto out_no_fifo;
} }
...@@ -521,12 +506,9 @@ static int vmw_dx_context_bind(struct vmw_resource *res, ...@@ -521,12 +506,9 @@ static int vmw_dx_context_bind(struct vmw_resource *res,
BUG_ON(bo->mem.mem_type != VMW_PL_MOB); BUG_ON(bo->mem.mem_type != VMW_PL_MOB);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for context "
"binding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_BIND_CONTEXT; cmd->header.id = SVGA_3D_CMD_DX_BIND_CONTEXT;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -615,10 +597,8 @@ static int vmw_dx_context_unbind(struct vmw_resource *res, ...@@ -615,10 +597,8 @@ static int vmw_dx_context_unbind(struct vmw_resource *res,
submit_size = sizeof(*cmd2) + (readback ? sizeof(*cmd1) : 0); submit_size = sizeof(*cmd2) + (readback ? sizeof(*cmd1) : 0);
cmd = vmw_fifo_reserve(dev_priv, submit_size); cmd = VMW_FIFO_RESERVE(dev_priv, submit_size);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL)) {
DRM_ERROR("Failed reserving FIFO space for context "
"unbinding.\n");
mutex_unlock(&dev_priv->binding_mutex); mutex_unlock(&dev_priv->binding_mutex);
return -ENOMEM; return -ENOMEM;
} }
...@@ -665,12 +645,9 @@ static int vmw_dx_context_destroy(struct vmw_resource *res) ...@@ -665,12 +645,9 @@ static int vmw_dx_context_destroy(struct vmw_resource *res)
if (likely(res->id == -1)) if (likely(res->id == -1))
return 0; return 0;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for context "
"destruction.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_DESTROY_CONTEXT; cmd->header.id = SVGA_3D_CMD_DX_DESTROY_CONTEXT;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -751,7 +728,7 @@ static int vmw_context_define(struct drm_device *dev, void *data, ...@@ -751,7 +728,7 @@ static int vmw_context_define(struct drm_device *dev, void *data,
int ret; int ret;
if (!dev_priv->has_dx && dx) { if (!dev_priv->has_dx && dx) {
DRM_ERROR("DX contexts not supported by device.\n"); VMW_DEBUG_USER("DX contexts not supported by device.\n");
return -EINVAL; return -EINVAL;
} }
......
...@@ -171,12 +171,9 @@ static int vmw_cotable_unscrub(struct vmw_resource *res) ...@@ -171,12 +171,9 @@ static int vmw_cotable_unscrub(struct vmw_resource *res)
WARN_ON_ONCE(bo->mem.mem_type != VMW_PL_MOB); WARN_ON_ONCE(bo->mem.mem_type != VMW_PL_MOB);
lockdep_assert_held(&bo->resv->lock.base); lockdep_assert_held(&bo->resv->lock.base);
cmd = vmw_fifo_reserve_dx(dev_priv, sizeof(*cmd), SVGA3D_INVALID_ID); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (!cmd) { if (!cmd)
DRM_ERROR("Failed reserving FIFO space for cotable "
"binding.\n");
return -ENOMEM; return -ENOMEM;
}
WARN_ON(vcotbl->ctx->id == SVGA3D_INVALID_ID); WARN_ON(vcotbl->ctx->id == SVGA3D_INVALID_ID);
WARN_ON(bo->mem.mem_type != VMW_PL_MOB); WARN_ON(bo->mem.mem_type != VMW_PL_MOB);
...@@ -262,12 +259,9 @@ int vmw_cotable_scrub(struct vmw_resource *res, bool readback) ...@@ -262,12 +259,9 @@ int vmw_cotable_scrub(struct vmw_resource *res, bool readback)
if (readback) if (readback)
submit_size += sizeof(*cmd0); submit_size += sizeof(*cmd0);
cmd1 = vmw_fifo_reserve_dx(dev_priv, submit_size, SVGA3D_INVALID_ID); cmd1 = VMW_FIFO_RESERVE(dev_priv, submit_size);
if (!cmd1) { if (!cmd1)
DRM_ERROR("Failed reserving FIFO space for cotable "
"unbinding.\n");
return -ENOMEM; return -ENOMEM;
}
vcotbl->size_read_back = 0; vcotbl->size_read_back = 0;
if (readback) { if (readback) {
...@@ -351,13 +345,10 @@ static int vmw_cotable_readback(struct vmw_resource *res) ...@@ -351,13 +345,10 @@ static int vmw_cotable_readback(struct vmw_resource *res)
struct vmw_fence_obj *fence; struct vmw_fence_obj *fence;
if (!vcotbl->scrubbed) { if (!vcotbl->scrubbed) {
cmd = vmw_fifo_reserve_dx(dev_priv, sizeof(*cmd), cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
SVGA3D_INVALID_ID); if (!cmd)
if (!cmd) {
DRM_ERROR("Failed reserving FIFO space for cotable "
"readback.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_READBACK_COTABLE; cmd->header.id = SVGA_3D_CMD_DX_READBACK_COTABLE;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
cmd->body.cid = vcotbl->ctx->id; cmd->body.cid = vcotbl->ctx->id;
......
...@@ -699,6 +699,8 @@ extern int vmw_user_stream_lookup(struct vmw_private *dev_priv, ...@@ -699,6 +699,8 @@ extern int vmw_user_stream_lookup(struct vmw_private *dev_priv,
uint32_t *inout_id, uint32_t *inout_id,
struct vmw_resource **out); struct vmw_resource **out);
extern void vmw_resource_unreserve(struct vmw_resource *res, extern void vmw_resource_unreserve(struct vmw_resource *res,
bool dirty_set,
bool dirty,
bool switch_backup, bool switch_backup,
struct vmw_buffer_object *new_backup, struct vmw_buffer_object *new_backup,
unsigned long new_backup_offset); unsigned long new_backup_offset);
...@@ -811,7 +813,6 @@ extern int vmw_fifo_init(struct vmw_private *dev_priv, ...@@ -811,7 +813,6 @@ extern int vmw_fifo_init(struct vmw_private *dev_priv,
struct vmw_fifo_state *fifo); struct vmw_fifo_state *fifo);
extern void vmw_fifo_release(struct vmw_private *dev_priv, extern void vmw_fifo_release(struct vmw_private *dev_priv,
struct vmw_fifo_state *fifo); struct vmw_fifo_state *fifo);
extern void *vmw_fifo_reserve(struct vmw_private *dev_priv, uint32_t bytes);
extern void * extern void *
vmw_fifo_reserve_dx(struct vmw_private *dev_priv, uint32_t bytes, int ctx_id); vmw_fifo_reserve_dx(struct vmw_private *dev_priv, uint32_t bytes, int ctx_id);
extern void vmw_fifo_commit(struct vmw_private *dev_priv, uint32_t bytes); extern void vmw_fifo_commit(struct vmw_private *dev_priv, uint32_t bytes);
...@@ -827,6 +828,18 @@ extern int vmw_fifo_emit_dummy_query(struct vmw_private *dev_priv, ...@@ -827,6 +828,18 @@ extern int vmw_fifo_emit_dummy_query(struct vmw_private *dev_priv,
extern int vmw_fifo_flush(struct vmw_private *dev_priv, extern int vmw_fifo_flush(struct vmw_private *dev_priv,
bool interruptible); bool interruptible);
#define VMW_FIFO_RESERVE_DX(__priv, __bytes, __ctx_id) \
({ \
vmw_fifo_reserve_dx(__priv, __bytes, __ctx_id) ? : ({ \
DRM_ERROR("FIFO reserve failed at %s for %u bytes\n", \
__func__, (unsigned int) __bytes); \
NULL; \
}); \
})
#define VMW_FIFO_RESERVE(__priv, __bytes) \
VMW_FIFO_RESERVE_DX(__priv, __bytes, SVGA3D_INVALID_ID)
/** /**
* TTM glue - vmwgfx_ttm_glue.c * TTM glue - vmwgfx_ttm_glue.c
*/ */
...@@ -1311,6 +1324,20 @@ int vmw_host_get_guestinfo(const char *guest_info_param, ...@@ -1311,6 +1324,20 @@ int vmw_host_get_guestinfo(const char *guest_info_param,
char *buffer, size_t *length); char *buffer, size_t *length);
int vmw_host_log(const char *log); int vmw_host_log(const char *log);
/* VMW logging */
/**
* VMW_DEBUG_USER - Debug output for user-space debugging.
*
* @fmt: printf() like format string.
*
* This macro is for logging user-space error and debugging messages for e.g.
* command buffer execution errors due to malformed commands, invalid context,
* etc.
*/
#define VMW_DEBUG_USER(fmt, ...) \
DRM_DEBUG_DRIVER(fmt, ##__VA_ARGS__)
/** /**
* Inline helper functions * Inline helper functions
*/ */
......
This source diff could not be displayed because it is too large. You can view the blob instead.
...@@ -642,12 +642,11 @@ int vmw_fb_init(struct vmw_private *vmw_priv) ...@@ -642,12 +642,11 @@ int vmw_fb_init(struct vmw_private *vmw_priv)
struct vmw_fb_par *par; struct vmw_fb_par *par;
struct fb_info *info; struct fb_info *info;
unsigned fb_width, fb_height; unsigned fb_width, fb_height;
unsigned fb_bpp, fb_depth, fb_offset, fb_pitch, fb_size; unsigned int fb_bpp, fb_pitch, fb_size;
struct drm_display_mode *init_mode; struct drm_display_mode *init_mode;
int ret; int ret;
fb_bpp = 32; fb_bpp = 32;
fb_depth = 24;
/* XXX As shouldn't these be as well. */ /* XXX As shouldn't these be as well. */
fb_width = min(vmw_priv->fb_max_width, (unsigned)2048); fb_width = min(vmw_priv->fb_max_width, (unsigned)2048);
...@@ -655,7 +654,6 @@ int vmw_fb_init(struct vmw_private *vmw_priv) ...@@ -655,7 +654,6 @@ int vmw_fb_init(struct vmw_private *vmw_priv)
fb_pitch = fb_width * fb_bpp / 8; fb_pitch = fb_width * fb_bpp / 8;
fb_size = fb_pitch * fb_height; fb_size = fb_pitch * fb_height;
fb_offset = vmw_read(vmw_priv, SVGA_REG_FB_OFFSET);
info = framebuffer_alloc(sizeof(*par), device); info = framebuffer_alloc(sizeof(*par), device);
if (!info) if (!info)
......
...@@ -395,12 +395,8 @@ void *vmw_fifo_reserve_dx(struct vmw_private *dev_priv, uint32_t bytes, ...@@ -395,12 +395,8 @@ void *vmw_fifo_reserve_dx(struct vmw_private *dev_priv, uint32_t bytes,
WARN(1, "Command buffer has not been allocated.\n"); WARN(1, "Command buffer has not been allocated.\n");
ret = NULL; ret = NULL;
} }
if (IS_ERR_OR_NULL(ret)) { if (IS_ERR_OR_NULL(ret))
DRM_ERROR("Fifo reserve failure of %u bytes.\n",
(unsigned) bytes);
dump_stack();
return NULL; return NULL;
}
return ret; return ret;
} }
...@@ -544,7 +540,7 @@ int vmw_fifo_send_fence(struct vmw_private *dev_priv, uint32_t *seqno) ...@@ -544,7 +540,7 @@ int vmw_fifo_send_fence(struct vmw_private *dev_priv, uint32_t *seqno)
int ret = 0; int ret = 0;
uint32_t bytes = sizeof(u32) + sizeof(*cmd_fence); uint32_t bytes = sizeof(u32) + sizeof(*cmd_fence);
fm = vmw_fifo_reserve(dev_priv, bytes); fm = VMW_FIFO_RESERVE(dev_priv, bytes);
if (unlikely(fm == NULL)) { if (unlikely(fm == NULL)) {
*seqno = atomic_read(&dev_priv->marker_seq); *seqno = atomic_read(&dev_priv->marker_seq);
ret = -ENOMEM; ret = -ENOMEM;
...@@ -603,12 +599,9 @@ static int vmw_fifo_emit_dummy_legacy_query(struct vmw_private *dev_priv, ...@@ -603,12 +599,9 @@ static int vmw_fifo_emit_dummy_legacy_query(struct vmw_private *dev_priv,
SVGA3dCmdWaitForQuery body; SVGA3dCmdWaitForQuery body;
} *cmd; } *cmd;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL))
if (unlikely(cmd == NULL)) {
DRM_ERROR("Out of fifo space for dummy query.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_WAIT_FOR_QUERY; cmd->header.id = SVGA_3D_CMD_WAIT_FOR_QUERY;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -652,12 +645,9 @@ static int vmw_fifo_emit_dummy_gb_query(struct vmw_private *dev_priv, ...@@ -652,12 +645,9 @@ static int vmw_fifo_emit_dummy_gb_query(struct vmw_private *dev_priv,
SVGA3dCmdWaitForGBQuery body; SVGA3dCmdWaitForGBQuery body;
} *cmd; } *cmd;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL))
if (unlikely(cmd == NULL)) {
DRM_ERROR("Out of fifo space for dummy query.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_WAIT_FOR_GB_QUERY; cmd->header.id = SVGA_3D_CMD_WAIT_FOR_GB_QUERY;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -699,8 +689,3 @@ int vmw_fifo_emit_dummy_query(struct vmw_private *dev_priv, ...@@ -699,8 +689,3 @@ int vmw_fifo_emit_dummy_query(struct vmw_private *dev_priv,
return vmw_fifo_emit_dummy_legacy_query(dev_priv, cid); return vmw_fifo_emit_dummy_legacy_query(dev_priv, cid);
} }
void *vmw_fifo_reserve(struct vmw_private *dev_priv, uint32_t bytes)
{
return vmw_fifo_reserve_dx(dev_priv, bytes, SVGA3D_INVALID_ID);
}
...@@ -51,7 +51,7 @@ static int vmw_gmr2_bind(struct vmw_private *dev_priv, ...@@ -51,7 +51,7 @@ static int vmw_gmr2_bind(struct vmw_private *dev_priv,
uint32_t cmd_size = define_size + remap_size; uint32_t cmd_size = define_size + remap_size;
uint32_t i; uint32_t i;
cmd_orig = cmd = vmw_fifo_reserve(dev_priv, cmd_size); cmd_orig = cmd = VMW_FIFO_RESERVE(dev_priv, cmd_size);
if (unlikely(cmd == NULL)) if (unlikely(cmd == NULL))
return -ENOMEM; return -ENOMEM;
...@@ -110,11 +110,10 @@ static void vmw_gmr2_unbind(struct vmw_private *dev_priv, ...@@ -110,11 +110,10 @@ static void vmw_gmr2_unbind(struct vmw_private *dev_priv,
uint32_t define_size = sizeof(define_cmd) + 4; uint32_t define_size = sizeof(define_cmd) + 4;
uint32_t *cmd; uint32_t *cmd;
cmd = vmw_fifo_reserve(dev_priv, define_size); cmd = VMW_FIFO_RESERVE(dev_priv, define_size);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("GMR2 unbind failed.\n");
return; return;
}
define_cmd.gmrId = gmr_id; define_cmd.gmrId = gmr_id;
define_cmd.numPages = 0; define_cmd.numPages = 0;
......
...@@ -188,7 +188,7 @@ int vmw_get_cap_3d_ioctl(struct drm_device *dev, void *data, ...@@ -188,7 +188,7 @@ int vmw_get_cap_3d_ioctl(struct drm_device *dev, void *data,
struct vmw_fpriv *vmw_fp = vmw_fpriv(file_priv); struct vmw_fpriv *vmw_fp = vmw_fpriv(file_priv);
if (unlikely(arg->pad64 != 0 || arg->max_size == 0)) { if (unlikely(arg->pad64 != 0 || arg->max_size == 0)) {
DRM_ERROR("Illegal GET_3D_CAP argument.\n"); VMW_DEBUG_USER("Illegal GET_3D_CAP argument.\n");
return -EINVAL; return -EINVAL;
} }
...@@ -268,7 +268,7 @@ int vmw_present_ioctl(struct drm_device *dev, void *data, ...@@ -268,7 +268,7 @@ int vmw_present_ioctl(struct drm_device *dev, void *data,
return 0; return 0;
if (clips_ptr == NULL) { if (clips_ptr == NULL) {
DRM_ERROR("Variable clips_ptr must be specified.\n"); VMW_DEBUG_USER("Variable clips_ptr must be specified.\n");
ret = -EINVAL; ret = -EINVAL;
goto out_clips; goto out_clips;
} }
...@@ -291,7 +291,7 @@ int vmw_present_ioctl(struct drm_device *dev, void *data, ...@@ -291,7 +291,7 @@ int vmw_present_ioctl(struct drm_device *dev, void *data,
fb = drm_framebuffer_lookup(dev, file_priv, arg->fb_id); fb = drm_framebuffer_lookup(dev, file_priv, arg->fb_id);
if (!fb) { if (!fb) {
DRM_ERROR("Invalid framebuffer id.\n"); VMW_DEBUG_USER("Invalid framebuffer id.\n");
ret = -ENOENT; ret = -ENOENT;
goto out_no_fb; goto out_no_fb;
} }
...@@ -351,7 +351,7 @@ int vmw_present_readback_ioctl(struct drm_device *dev, void *data, ...@@ -351,7 +351,7 @@ int vmw_present_readback_ioctl(struct drm_device *dev, void *data,
return 0; return 0;
if (clips_ptr == NULL) { if (clips_ptr == NULL) {
DRM_ERROR("Argument clips_ptr must be specified.\n"); VMW_DEBUG_USER("Argument clips_ptr must be specified.\n");
ret = -EINVAL; ret = -EINVAL;
goto out_clips; goto out_clips;
} }
...@@ -374,14 +374,14 @@ int vmw_present_readback_ioctl(struct drm_device *dev, void *data, ...@@ -374,14 +374,14 @@ int vmw_present_readback_ioctl(struct drm_device *dev, void *data,
fb = drm_framebuffer_lookup(dev, file_priv, arg->fb_id); fb = drm_framebuffer_lookup(dev, file_priv, arg->fb_id);
if (!fb) { if (!fb) {
DRM_ERROR("Invalid framebuffer id.\n"); VMW_DEBUG_USER("Invalid framebuffer id.\n");
ret = -ENOENT; ret = -ENOENT;
goto out_no_fb; goto out_no_fb;
} }
vfb = vmw_framebuffer_to_vfb(fb); vfb = vmw_framebuffer_to_vfb(fb);
if (!vfb->bo) { if (!vfb->bo) {
DRM_ERROR("Framebuffer not buffer backed.\n"); VMW_DEBUG_USER("Framebuffer not buffer backed.\n");
ret = -EINVAL; ret = -EINVAL;
goto out_no_ttm_lock; goto out_no_ttm_lock;
} }
......
...@@ -64,11 +64,9 @@ static int vmw_cursor_update_image(struct vmw_private *dev_priv, ...@@ -64,11 +64,9 @@ static int vmw_cursor_update_image(struct vmw_private *dev_priv,
if (!image) if (!image)
return -EINVAL; return -EINVAL;
cmd = vmw_fifo_reserve(dev_priv, cmd_size); cmd = VMW_FIFO_RESERVE(dev_priv, cmd_size);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Fifo reserve failed.\n");
return -ENOMEM; return -ENOMEM;
}
memset(cmd, 0, sizeof(*cmd)); memset(cmd, 0, sizeof(*cmd));
...@@ -1202,7 +1200,7 @@ static int vmw_create_bo_proxy(struct drm_device *dev, ...@@ -1202,7 +1200,7 @@ static int vmw_create_bo_proxy(struct drm_device *dev,
vmw_bo_unreference(&res->backup); vmw_bo_unreference(&res->backup);
res->backup = vmw_bo_reference(bo_mob); res->backup = vmw_bo_reference(bo_mob);
res->backup_offset = 0; res->backup_offset = 0;
vmw_resource_unreserve(res, false, NULL, 0); vmw_resource_unreserve(res, false, false, false, NULL, 0);
mutex_unlock(&res->dev_priv->cmdbuf_mutex); mutex_unlock(&res->dev_priv->cmdbuf_mutex);
return 0; return 0;
...@@ -2468,13 +2466,11 @@ int vmw_kms_helper_dirty(struct vmw_private *dev_priv, ...@@ -2468,13 +2466,11 @@ int vmw_kms_helper_dirty(struct vmw_private *dev_priv,
dirty->unit = unit; dirty->unit = unit;
if (dirty->fifo_reserve_size > 0) { if (dirty->fifo_reserve_size > 0) {
dirty->cmd = vmw_fifo_reserve(dev_priv, dirty->cmd = VMW_FIFO_RESERVE(dev_priv,
dirty->fifo_reserve_size); dirty->fifo_reserve_size);
if (!dirty->cmd) { if (!dirty->cmd)
DRM_ERROR("Couldn't reserve fifo space "
"for dirty blits.\n");
return -ENOMEM; return -ENOMEM;
}
memset(dirty->cmd, 0, dirty->fifo_reserve_size); memset(dirty->cmd, 0, dirty->fifo_reserve_size);
} }
dirty->num_hits = 0; dirty->num_hits = 0;
...@@ -2604,12 +2600,9 @@ int vmw_kms_update_proxy(struct vmw_resource *res, ...@@ -2604,12 +2600,9 @@ int vmw_kms_update_proxy(struct vmw_resource *res,
if (!clips) if (!clips)
return 0; return 0;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd) * num_clips); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd) * num_clips);
if (!cmd) { if (!cmd)
DRM_ERROR("Couldn't reserve fifo space for proxy surface "
"update.\n");
return -ENOMEM; return -ENOMEM;
}
for (i = 0; i < num_clips; ++i, clips += increment, ++cmd) { for (i = 0; i < num_clips; ++i, clips += increment, ++cmd) {
box = &cmd->body.box; box = &cmd->body.box;
...@@ -2827,7 +2820,8 @@ int vmw_du_helper_plane_update(struct vmw_du_update_plane *update) ...@@ -2827,7 +2820,8 @@ int vmw_du_helper_plane_update(struct vmw_du_update_plane *update)
container_of(update->vfb, typeof(*vfbs), base); container_of(update->vfb, typeof(*vfbs), base);
ret = vmw_validation_add_resource(&val_ctx, &vfbs->surface->res, ret = vmw_validation_add_resource(&val_ctx, &vfbs->surface->res,
0, NULL, NULL); 0, VMW_RES_DIRTY_NONE, NULL,
NULL);
} }
if (ret) if (ret)
...@@ -2838,7 +2832,7 @@ int vmw_du_helper_plane_update(struct vmw_du_update_plane *update) ...@@ -2838,7 +2832,7 @@ int vmw_du_helper_plane_update(struct vmw_du_update_plane *update)
goto out_unref; goto out_unref;
reserved_size = update->calc_fifo_size(update, num_hits); reserved_size = update->calc_fifo_size(update, num_hits);
cmd_start = vmw_fifo_reserve(update->dev_priv, reserved_size); cmd_start = VMW_FIFO_RESERVE(update->dev_priv, reserved_size);
if (!cmd_start) { if (!cmd_start) {
ret = -ENOMEM; ret = -ENOMEM;
goto out_revert; goto out_revert;
......
...@@ -554,11 +554,9 @@ int vmw_kms_ldu_do_bo_dirty(struct vmw_private *dev_priv, ...@@ -554,11 +554,9 @@ int vmw_kms_ldu_do_bo_dirty(struct vmw_private *dev_priv,
} *cmd; } *cmd;
fifo_size = sizeof(*cmd) * num_clips; fifo_size = sizeof(*cmd) * num_clips;
cmd = vmw_fifo_reserve(dev_priv, fifo_size); cmd = VMW_FIFO_RESERVE(dev_priv, fifo_size);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Fifo reserve failed.\n");
return -ENOMEM; return -ENOMEM;
}
memset(cmd, 0, fifo_size); memset(cmd, 0, fifo_size);
for (i = 0; i < num_clips; i++, clips += increment) { for (i = 0; i < num_clips; i++, clips += increment) {
......
...@@ -146,9 +146,8 @@ static int vmw_setup_otable_base(struct vmw_private *dev_priv, ...@@ -146,9 +146,8 @@ static int vmw_setup_otable_base(struct vmw_private *dev_priv,
mob->pt_level += VMW_MOBFMT_PTDEPTH_1 - SVGA3D_MOBFMT_PTDEPTH_1; mob->pt_level += VMW_MOBFMT_PTDEPTH_1 - SVGA3D_MOBFMT_PTDEPTH_1;
} }
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL)) {
DRM_ERROR("Failed reserving FIFO space for OTable setup.\n");
ret = -ENOMEM; ret = -ENOMEM;
goto out_no_fifo; goto out_no_fifo;
} }
...@@ -202,12 +201,9 @@ static void vmw_takedown_otable_base(struct vmw_private *dev_priv, ...@@ -202,12 +201,9 @@ static void vmw_takedown_otable_base(struct vmw_private *dev_priv,
return; return;
bo = otable->page_table->pt_bo; bo = otable->page_table->pt_bo;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for OTable "
"takedown.\n");
return; return;
}
memset(cmd, 0, sizeof(*cmd)); memset(cmd, 0, sizeof(*cmd));
cmd->header.id = SVGA_3D_CMD_SET_OTABLE_BASE; cmd->header.id = SVGA_3D_CMD_SET_OTABLE_BASE;
...@@ -614,16 +610,14 @@ void vmw_mob_unbind(struct vmw_private *dev_priv, ...@@ -614,16 +610,14 @@ void vmw_mob_unbind(struct vmw_private *dev_priv,
BUG_ON(ret != 0); BUG_ON(ret != 0);
} }
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (cmd) {
DRM_ERROR("Failed reserving FIFO space for Memory "
"Object unbinding.\n");
} else {
cmd->header.id = SVGA_3D_CMD_DESTROY_GB_MOB; cmd->header.id = SVGA_3D_CMD_DESTROY_GB_MOB;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
cmd->body.mobid = mob->id; cmd->body.mobid = mob->id;
vmw_fifo_commit(dev_priv, sizeof(*cmd)); vmw_fifo_commit(dev_priv, sizeof(*cmd));
} }
if (bo) { if (bo) {
vmw_bo_fence_single(bo, NULL); vmw_bo_fence_single(bo, NULL);
ttm_bo_unreserve(bo); ttm_bo_unreserve(bo);
...@@ -683,12 +677,9 @@ int vmw_mob_bind(struct vmw_private *dev_priv, ...@@ -683,12 +677,9 @@ int vmw_mob_bind(struct vmw_private *dev_priv,
vmw_fifo_resource_inc(dev_priv); vmw_fifo_resource_inc(dev_priv);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for Memory "
"Object binding.\n");
goto out_no_cmd_space; goto out_no_cmd_space;
}
cmd->header.id = SVGA_3D_CMD_DEFINE_GB_MOB64; cmd->header.id = SVGA_3D_CMD_DEFINE_GB_MOB64;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
......
...@@ -124,7 +124,7 @@ static int vmw_overlay_send_put(struct vmw_private *dev_priv, ...@@ -124,7 +124,7 @@ static int vmw_overlay_send_put(struct vmw_private *dev_priv,
fifo_size = sizeof(*cmds) + sizeof(*flush) + sizeof(*items) * num_items; fifo_size = sizeof(*cmds) + sizeof(*flush) + sizeof(*items) * num_items;
cmds = vmw_fifo_reserve(dev_priv, fifo_size); cmds = VMW_FIFO_RESERVE(dev_priv, fifo_size);
/* hardware has hung, can't do anything here */ /* hardware has hung, can't do anything here */
if (!cmds) if (!cmds)
return -ENOMEM; return -ENOMEM;
...@@ -194,7 +194,7 @@ static int vmw_overlay_send_stop(struct vmw_private *dev_priv, ...@@ -194,7 +194,7 @@ static int vmw_overlay_send_stop(struct vmw_private *dev_priv,
int ret; int ret;
for (;;) { for (;;) {
cmds = vmw_fifo_reserve(dev_priv, sizeof(*cmds)); cmds = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmds));
if (cmds) if (cmds)
break; break;
......
...@@ -365,14 +365,6 @@ static int vmw_resource_do_validate(struct vmw_resource *res, ...@@ -365,14 +365,6 @@ static int vmw_resource_do_validate(struct vmw_resource *res,
list_add_tail(&res->mob_head, &res->backup->res_list); list_add_tail(&res->mob_head, &res->backup->res_list);
} }
/*
* Only do this on write operations, and move to
* vmw_resource_unreserve if it can be called after
* backup buffers have been unreserved. Otherwise
* sort out locking.
*/
res->res_dirty = true;
return 0; return 0;
out_bind_failed: out_bind_failed:
...@@ -386,6 +378,8 @@ static int vmw_resource_do_validate(struct vmw_resource *res, ...@@ -386,6 +378,8 @@ static int vmw_resource_do_validate(struct vmw_resource *res,
* command submission. * command submission.
* *
* @res: Pointer to the struct vmw_resource to unreserve. * @res: Pointer to the struct vmw_resource to unreserve.
* @dirty_set: Change dirty status of the resource.
* @dirty: When changing dirty status indicates the new status.
* @switch_backup: Backup buffer has been switched. * @switch_backup: Backup buffer has been switched.
* @new_backup: Pointer to new backup buffer if command submission * @new_backup: Pointer to new backup buffer if command submission
* switched. May be NULL. * switched. May be NULL.
...@@ -395,6 +389,8 @@ static int vmw_resource_do_validate(struct vmw_resource *res, ...@@ -395,6 +389,8 @@ static int vmw_resource_do_validate(struct vmw_resource *res,
* resource lru list, so that it can be evicted if necessary. * resource lru list, so that it can be evicted if necessary.
*/ */
void vmw_resource_unreserve(struct vmw_resource *res, void vmw_resource_unreserve(struct vmw_resource *res,
bool dirty_set,
bool dirty,
bool switch_backup, bool switch_backup,
struct vmw_buffer_object *new_backup, struct vmw_buffer_object *new_backup,
unsigned long new_backup_offset) unsigned long new_backup_offset)
...@@ -422,6 +418,9 @@ void vmw_resource_unreserve(struct vmw_resource *res, ...@@ -422,6 +418,9 @@ void vmw_resource_unreserve(struct vmw_resource *res,
if (switch_backup) if (switch_backup)
res->backup_offset = new_backup_offset; res->backup_offset = new_backup_offset;
if (dirty_set)
res->res_dirty = dirty;
if (!res->func->may_evict || res->id == -1 || res->pin_count) if (!res->func->may_evict || res->id == -1 || res->pin_count)
return; return;
...@@ -696,7 +695,7 @@ void vmw_resource_unbind_list(struct vmw_buffer_object *vbo) ...@@ -696,7 +695,7 @@ void vmw_resource_unbind_list(struct vmw_buffer_object *vbo)
if (!res->func->unbind) if (!res->func->unbind)
continue; continue;
(void) res->func->unbind(res, true, &val_buf); (void) res->func->unbind(res, res->res_dirty, &val_buf);
res->backup_dirty = true; res->backup_dirty = true;
res->res_dirty = false; res->res_dirty = false;
list_del_init(&res->mob_head); list_del_init(&res->mob_head);
...@@ -731,12 +730,9 @@ int vmw_query_readback_all(struct vmw_buffer_object *dx_query_mob) ...@@ -731,12 +730,9 @@ int vmw_query_readback_all(struct vmw_buffer_object *dx_query_mob)
dx_query_ctx = dx_query_mob->dx_query_ctx; dx_query_ctx = dx_query_mob->dx_query_ctx;
dev_priv = dx_query_ctx->dev_priv; dev_priv = dx_query_ctx->dev_priv;
cmd = vmw_fifo_reserve_dx(dev_priv, sizeof(*cmd), dx_query_ctx->id); cmd = VMW_FIFO_RESERVE_DX(dev_priv, sizeof(*cmd), dx_query_ctx->id);
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for "
"query MOB read back.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_READBACK_ALL_QUERY; cmd->header.id = SVGA_3D_CMD_DX_READBACK_ALL_QUERY;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -932,7 +928,7 @@ int vmw_resource_pin(struct vmw_resource *res, bool interruptible) ...@@ -932,7 +928,7 @@ int vmw_resource_pin(struct vmw_resource *res, bool interruptible)
res->pin_count++; res->pin_count++;
out_no_validate: out_no_validate:
vmw_resource_unreserve(res, false, NULL, 0UL); vmw_resource_unreserve(res, false, false, false, NULL, 0UL);
out_no_reserve: out_no_reserve:
mutex_unlock(&dev_priv->cmdbuf_mutex); mutex_unlock(&dev_priv->cmdbuf_mutex);
ttm_write_unlock(&dev_priv->reservation_sem); ttm_write_unlock(&dev_priv->reservation_sem);
...@@ -968,7 +964,7 @@ void vmw_resource_unpin(struct vmw_resource *res) ...@@ -968,7 +964,7 @@ void vmw_resource_unpin(struct vmw_resource *res)
ttm_bo_unreserve(&vbo->base); ttm_bo_unreserve(&vbo->base);
} }
vmw_resource_unreserve(res, false, NULL, 0UL); vmw_resource_unreserve(res, false, false, false, NULL, 0UL);
mutex_unlock(&dev_priv->cmdbuf_mutex); mutex_unlock(&dev_priv->cmdbuf_mutex);
ttm_read_unlock(&dev_priv->reservation_sem); ttm_read_unlock(&dev_priv->reservation_sem);
......
...@@ -130,12 +130,9 @@ static int vmw_sou_fifo_create(struct vmw_private *dev_priv, ...@@ -130,12 +130,9 @@ static int vmw_sou_fifo_create(struct vmw_private *dev_priv,
BUG_ON(!sou->buffer); BUG_ON(!sou->buffer);
fifo_size = sizeof(*cmd); fifo_size = sizeof(*cmd);
cmd = vmw_fifo_reserve(dev_priv, fifo_size); cmd = VMW_FIFO_RESERVE(dev_priv, fifo_size);
/* The hardware has hung, nothing we can do about it here. */ if (unlikely(cmd == NULL))
if (unlikely(cmd == NULL)) {
DRM_ERROR("Fifo reserve failed.\n");
return -ENOMEM; return -ENOMEM;
}
memset(cmd, 0, fifo_size); memset(cmd, 0, fifo_size);
cmd->header.cmdType = SVGA_CMD_DEFINE_SCREEN; cmd->header.cmdType = SVGA_CMD_DEFINE_SCREEN;
...@@ -182,12 +179,9 @@ static int vmw_sou_fifo_destroy(struct vmw_private *dev_priv, ...@@ -182,12 +179,9 @@ static int vmw_sou_fifo_destroy(struct vmw_private *dev_priv,
return 0; return 0;
fifo_size = sizeof(*cmd); fifo_size = sizeof(*cmd);
cmd = vmw_fifo_reserve(dev_priv, fifo_size); cmd = VMW_FIFO_RESERVE(dev_priv, fifo_size);
/* the hardware has hung, nothing we can do about it here */ if (unlikely(cmd == NULL))
if (unlikely(cmd == NULL)) {
DRM_ERROR("Fifo reserve failed.\n");
return -ENOMEM; return -ENOMEM;
}
memset(cmd, 0, fifo_size); memset(cmd, 0, fifo_size);
cmd->header.cmdType = SVGA_CMD_DESTROY_SCREEN; cmd->header.cmdType = SVGA_CMD_DESTROY_SCREEN;
...@@ -998,11 +992,9 @@ static int do_bo_define_gmrfb(struct vmw_private *dev_priv, ...@@ -998,11 +992,9 @@ static int do_bo_define_gmrfb(struct vmw_private *dev_priv,
if (depth == 32) if (depth == 32)
depth = 24; depth = 24;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (!cmd) { if (!cmd)
DRM_ERROR("Out of fifo space for dirty framebuffer command.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header = SVGA_CMD_DEFINE_GMRFB; cmd->header = SVGA_CMD_DEFINE_GMRFB;
cmd->body.format.bitsPerPixel = framebuffer->base.format->cpp[0] * 8; cmd->body.format.bitsPerPixel = framebuffer->base.format->cpp[0] * 8;
...@@ -1148,7 +1140,8 @@ int vmw_kms_sou_do_surface_dirty(struct vmw_private *dev_priv, ...@@ -1148,7 +1140,8 @@ int vmw_kms_sou_do_surface_dirty(struct vmw_private *dev_priv,
if (!srf) if (!srf)
srf = &vfbs->surface->res; srf = &vfbs->surface->res;
ret = vmw_validation_add_resource(&val_ctx, srf, 0, NULL, NULL); ret = vmw_validation_add_resource(&val_ctx, srf, 0, VMW_RES_DIRTY_NONE,
NULL, NULL);
if (ret) if (ret)
return ret; return ret;
......
...@@ -218,10 +218,8 @@ static int vmw_gb_shader_create(struct vmw_resource *res) ...@@ -218,10 +218,8 @@ static int vmw_gb_shader_create(struct vmw_resource *res)
goto out_no_fifo; goto out_no_fifo;
} }
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL)) {
DRM_ERROR("Failed reserving FIFO space for shader "
"creation.\n");
ret = -ENOMEM; ret = -ENOMEM;
goto out_no_fifo; goto out_no_fifo;
} }
...@@ -254,12 +252,9 @@ static int vmw_gb_shader_bind(struct vmw_resource *res, ...@@ -254,12 +252,9 @@ static int vmw_gb_shader_bind(struct vmw_resource *res,
BUG_ON(bo->mem.mem_type != VMW_PL_MOB); BUG_ON(bo->mem.mem_type != VMW_PL_MOB);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for shader "
"binding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_BIND_GB_SHADER; cmd->header.id = SVGA_3D_CMD_BIND_GB_SHADER;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -285,12 +280,9 @@ static int vmw_gb_shader_unbind(struct vmw_resource *res, ...@@ -285,12 +280,9 @@ static int vmw_gb_shader_unbind(struct vmw_resource *res,
BUG_ON(res->backup->base.mem.mem_type != VMW_PL_MOB); BUG_ON(res->backup->base.mem.mem_type != VMW_PL_MOB);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for shader "
"unbinding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_BIND_GB_SHADER; cmd->header.id = SVGA_3D_CMD_BIND_GB_SHADER;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -328,10 +320,8 @@ static int vmw_gb_shader_destroy(struct vmw_resource *res) ...@@ -328,10 +320,8 @@ static int vmw_gb_shader_destroy(struct vmw_resource *res)
mutex_lock(&dev_priv->binding_mutex); mutex_lock(&dev_priv->binding_mutex);
vmw_binding_res_list_scrub(&res->binding_head); vmw_binding_res_list_scrub(&res->binding_head);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL)) {
DRM_ERROR("Failed reserving FIFO space for shader "
"destruction.\n");
mutex_unlock(&dev_priv->binding_mutex); mutex_unlock(&dev_priv->binding_mutex);
return -ENOMEM; return -ENOMEM;
} }
...@@ -400,13 +390,9 @@ static int vmw_dx_shader_unscrub(struct vmw_resource *res) ...@@ -400,13 +390,9 @@ static int vmw_dx_shader_unscrub(struct vmw_resource *res)
if (!list_empty(&shader->cotable_head) || !shader->committed) if (!list_empty(&shader->cotable_head) || !shader->committed)
return 0; return 0;
cmd = vmw_fifo_reserve_dx(dev_priv, sizeof(*cmd), cmd = VMW_FIFO_RESERVE_DX(dev_priv, sizeof(*cmd), shader->ctx->id);
shader->ctx->id); if (unlikely(cmd == NULL))
if (unlikely(cmd == NULL)) {
DRM_ERROR("Failed reserving FIFO space for shader "
"scrubbing.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_BIND_SHADER; cmd->header.id = SVGA_3D_CMD_DX_BIND_SHADER;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -491,12 +477,9 @@ static int vmw_dx_shader_scrub(struct vmw_resource *res) ...@@ -491,12 +477,9 @@ static int vmw_dx_shader_scrub(struct vmw_resource *res)
return 0; return 0;
WARN_ON_ONCE(!shader->committed); WARN_ON_ONCE(!shader->committed);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL)) { if (unlikely(cmd == NULL))
DRM_ERROR("Failed reserving FIFO space for shader "
"scrubbing.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DX_BIND_SHADER; cmd->header.id = SVGA_3D_CMD_DX_BIND_SHADER;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -865,14 +848,13 @@ static int vmw_shader_define(struct drm_device *dev, struct drm_file *file_priv, ...@@ -865,14 +848,13 @@ static int vmw_shader_define(struct drm_device *dev, struct drm_file *file_priv,
ret = vmw_user_bo_lookup(tfile, buffer_handle, ret = vmw_user_bo_lookup(tfile, buffer_handle,
&buffer, NULL); &buffer, NULL);
if (unlikely(ret != 0)) { if (unlikely(ret != 0)) {
DRM_ERROR("Could not find buffer for shader " VMW_DEBUG_USER("Couldn't find buffer for shader creation.\n");
"creation.\n");
return ret; return ret;
} }
if ((u64)buffer->base.num_pages * PAGE_SIZE < if ((u64)buffer->base.num_pages * PAGE_SIZE <
(u64)size + (u64)offset) { (u64)size + (u64)offset) {
DRM_ERROR("Illegal buffer- or shader size.\n"); VMW_DEBUG_USER("Illegal buffer- or shader size.\n");
ret = -EINVAL; ret = -EINVAL;
goto out_bad_arg; goto out_bad_arg;
} }
...@@ -886,7 +868,7 @@ static int vmw_shader_define(struct drm_device *dev, struct drm_file *file_priv, ...@@ -886,7 +868,7 @@ static int vmw_shader_define(struct drm_device *dev, struct drm_file *file_priv,
shader_type = SVGA3D_SHADERTYPE_PS; shader_type = SVGA3D_SHADERTYPE_PS;
break; break;
default: default:
DRM_ERROR("Illegal shader type.\n"); VMW_DEBUG_USER("Illegal shader type.\n");
ret = -EINVAL; ret = -EINVAL;
goto out_bad_arg; goto out_bad_arg;
} }
......
...@@ -239,17 +239,17 @@ vmw_simple_resource_lookup(struct ttm_object_file *tfile, ...@@ -239,17 +239,17 @@ vmw_simple_resource_lookup(struct ttm_object_file *tfile,
base = ttm_base_object_lookup(tfile, handle); base = ttm_base_object_lookup(tfile, handle);
if (!base) { if (!base) {
DRM_ERROR("Invalid %s handle 0x%08lx.\n", VMW_DEBUG_USER("Invalid %s handle 0x%08lx.\n",
func->res_func.type_name, func->res_func.type_name,
(unsigned long) handle); (unsigned long) handle);
return ERR_PTR(-ESRCH); return ERR_PTR(-ESRCH);
} }
if (ttm_base_object_type(base) != func->ttm_res_type) { if (ttm_base_object_type(base) != func->ttm_res_type) {
ttm_base_object_unref(&base); ttm_base_object_unref(&base);
DRM_ERROR("Invalid type of %s handle 0x%08lx.\n", VMW_DEBUG_USER("Invalid type of %s handle 0x%08lx.\n",
func->res_func.type_name, func->res_func.type_name,
(unsigned long) handle); (unsigned long) handle);
return ERR_PTR(-EINVAL); return ERR_PTR(-EINVAL);
} }
......
...@@ -170,13 +170,12 @@ static int vmw_view_create(struct vmw_resource *res) ...@@ -170,13 +170,12 @@ static int vmw_view_create(struct vmw_resource *res)
return 0; return 0;
} }
cmd = vmw_fifo_reserve_dx(res->dev_priv, view->cmd_size, cmd = VMW_FIFO_RESERVE_DX(res->dev_priv, view->cmd_size, view->ctx->id);
view->ctx->id);
if (!cmd) { if (!cmd) {
DRM_ERROR("Failed reserving FIFO space for view creation.\n");
mutex_unlock(&dev_priv->binding_mutex); mutex_unlock(&dev_priv->binding_mutex);
return -ENOMEM; return -ENOMEM;
} }
memcpy(cmd, &view->cmd, view->cmd_size); memcpy(cmd, &view->cmd, view->cmd_size);
WARN_ON(cmd->body.view_id != view->view_id); WARN_ON(cmd->body.view_id != view->view_id);
/* Sid may have changed due to surface eviction. */ /* Sid may have changed due to surface eviction. */
...@@ -214,12 +213,9 @@ static int vmw_view_destroy(struct vmw_resource *res) ...@@ -214,12 +213,9 @@ static int vmw_view_destroy(struct vmw_resource *res)
if (!view->committed || res->id == -1) if (!view->committed || res->id == -1)
return 0; return 0;
cmd = vmw_fifo_reserve_dx(dev_priv, sizeof(*cmd), view->ctx->id); cmd = VMW_FIFO_RESERVE_DX(dev_priv, sizeof(*cmd), view->ctx->id);
if (!cmd) { if (!cmd)
DRM_ERROR("Failed reserving FIFO space for view "
"destruction.\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = vmw_view_destroy_cmds[view->view_type]; cmd->header.id = vmw_view_destroy_cmds[view->view_type];
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -338,12 +334,12 @@ int vmw_view_add(struct vmw_cmdbuf_res_manager *man, ...@@ -338,12 +334,12 @@ int vmw_view_add(struct vmw_cmdbuf_res_manager *man,
if (cmd_size != vmw_view_define_sizes[view_type] + if (cmd_size != vmw_view_define_sizes[view_type] +
sizeof(SVGA3dCmdHeader)) { sizeof(SVGA3dCmdHeader)) {
DRM_ERROR("Illegal view create command size.\n"); VMW_DEBUG_USER("Illegal view create command size.\n");
return -EINVAL; return -EINVAL;
} }
if (!vmw_view_id_ok(user_key, view_type)) { if (!vmw_view_id_ok(user_key, view_type)) {
DRM_ERROR("Illegal view add view id.\n"); VMW_DEBUG_USER("Illegal view add view id.\n");
return -EINVAL; return -EINVAL;
} }
...@@ -352,8 +348,7 @@ int vmw_view_add(struct vmw_cmdbuf_res_manager *man, ...@@ -352,8 +348,7 @@ int vmw_view_add(struct vmw_cmdbuf_res_manager *man,
ret = ttm_mem_global_alloc(vmw_mem_glob(dev_priv), size, &ttm_opt_ctx); ret = ttm_mem_global_alloc(vmw_mem_glob(dev_priv), size, &ttm_opt_ctx);
if (ret) { if (ret) {
if (ret != -ERESTARTSYS) if (ret != -ERESTARTSYS)
DRM_ERROR("Out of graphics memory for view" DRM_ERROR("Out of graphics memory for view creation\n");
" creation.\n");
return ret; return ret;
} }
...@@ -413,7 +408,7 @@ int vmw_view_remove(struct vmw_cmdbuf_res_manager *man, ...@@ -413,7 +408,7 @@ int vmw_view_remove(struct vmw_cmdbuf_res_manager *man,
struct vmw_resource **res_p) struct vmw_resource **res_p)
{ {
if (!vmw_view_id_ok(user_key, view_type)) { if (!vmw_view_id_ok(user_key, view_type)) {
DRM_ERROR("Illegal view remove view id.\n"); VMW_DEBUG_USER("Illegal view remove view id.\n");
return -EINVAL; return -EINVAL;
} }
...@@ -497,6 +492,30 @@ struct vmw_resource *vmw_view_lookup(struct vmw_cmdbuf_res_manager *man, ...@@ -497,6 +492,30 @@ struct vmw_resource *vmw_view_lookup(struct vmw_cmdbuf_res_manager *man,
vmw_view_key(user_key, view_type)); vmw_view_key(user_key, view_type));
} }
/**
* vmw_view_dirtying - Return whether a view type is dirtying its resource
* @res: Pointer to the view
*
* Each time a resource is put on the validation list as the result of a
* view pointing to it, we need to determine whether that resource will
* be dirtied (written to by the GPU) as a result of the corresponding
* GPU operation. Currently only rendertarget- and depth-stencil views are
* capable of dirtying its resource.
*
* Return: Whether the view type of @res dirties the resource it points to.
*/
u32 vmw_view_dirtying(struct vmw_resource *res)
{
static u32 view_is_dirtying[vmw_view_max] = {
[vmw_view_rt] = VMW_RES_DIRTY_SET,
[vmw_view_ds] = VMW_RES_DIRTY_SET,
};
/* Update this function as we add more view types */
BUILD_BUG_ON(vmw_view_max != 3);
return view_is_dirtying[vmw_view(res)->view_type];
}
const u32 vmw_view_destroy_cmds[] = { const u32 vmw_view_destroy_cmds[] = {
[vmw_view_sr] = SVGA_3D_CMD_DX_DESTROY_SHADERRESOURCE_VIEW, [vmw_view_sr] = SVGA_3D_CMD_DX_DESTROY_SHADERRESOURCE_VIEW,
[vmw_view_rt] = SVGA_3D_CMD_DX_DESTROY_RENDERTARGET_VIEW, [vmw_view_rt] = SVGA_3D_CMD_DX_DESTROY_RENDERTARGET_VIEW,
......
...@@ -157,4 +157,5 @@ extern struct vmw_resource *vmw_view_srf(struct vmw_resource *res); ...@@ -157,4 +157,5 @@ extern struct vmw_resource *vmw_view_srf(struct vmw_resource *res);
extern struct vmw_resource *vmw_view_lookup(struct vmw_cmdbuf_res_manager *man, extern struct vmw_resource *vmw_view_lookup(struct vmw_cmdbuf_res_manager *man,
enum vmw_view_type view_type, enum vmw_view_type view_type,
u32 user_key); u32 user_key);
extern u32 vmw_view_dirtying(struct vmw_resource *res);
#endif #endif
...@@ -111,7 +111,7 @@ struct vmw_stdu_update_gb_image { ...@@ -111,7 +111,7 @@ struct vmw_stdu_update_gb_image {
*/ */
struct vmw_screen_target_display_unit { struct vmw_screen_target_display_unit {
struct vmw_display_unit base; struct vmw_display_unit base;
const struct vmw_surface *display_srf; struct vmw_surface *display_srf;
enum stdu_content_type content_fb_type; enum stdu_content_type content_fb_type;
s32 display_width, display_height; s32 display_width, display_height;
...@@ -167,12 +167,9 @@ static int vmw_stdu_define_st(struct vmw_private *dev_priv, ...@@ -167,12 +167,9 @@ static int vmw_stdu_define_st(struct vmw_private *dev_priv,
SVGA3dCmdDefineGBScreenTarget body; SVGA3dCmdDefineGBScreenTarget body;
} *cmd; } *cmd;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL))
if (unlikely(cmd == NULL)) {
DRM_ERROR("Out of FIFO space defining Screen Target\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DEFINE_GB_SCREENTARGET; cmd->header.id = SVGA_3D_CMD_DEFINE_GB_SCREENTARGET;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -229,12 +226,9 @@ static int vmw_stdu_bind_st(struct vmw_private *dev_priv, ...@@ -229,12 +226,9 @@ static int vmw_stdu_bind_st(struct vmw_private *dev_priv,
memset(&image, 0, sizeof(image)); memset(&image, 0, sizeof(image));
image.sid = res ? res->id : SVGA3D_INVALID_ID; image.sid = res ? res->id : SVGA3D_INVALID_ID;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL))
if (unlikely(cmd == NULL)) {
DRM_ERROR("Out of FIFO space binding a screen target\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_BIND_GB_SCREENTARGET; cmd->header.id = SVGA_3D_CMD_BIND_GB_SCREENTARGET;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -296,12 +290,9 @@ static int vmw_stdu_update_st(struct vmw_private *dev_priv, ...@@ -296,12 +290,9 @@ static int vmw_stdu_update_st(struct vmw_private *dev_priv,
return -EINVAL; return -EINVAL;
} }
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL))
if (unlikely(cmd == NULL)) {
DRM_ERROR("Out of FIFO space updating a Screen Target\n");
return -ENOMEM; return -ENOMEM;
}
vmw_stdu_populate_update(cmd, stdu->base.unit, vmw_stdu_populate_update(cmd, stdu->base.unit,
0, stdu->display_width, 0, stdu->display_width,
...@@ -335,12 +326,9 @@ static int vmw_stdu_destroy_st(struct vmw_private *dev_priv, ...@@ -335,12 +326,9 @@ static int vmw_stdu_destroy_st(struct vmw_private *dev_priv,
if (unlikely(!stdu->defined)) if (unlikely(!stdu->defined))
return 0; return 0;
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(cmd == NULL))
if (unlikely(cmd == NULL)) {
DRM_ERROR("Out of FIFO space, screen target not destroyed\n");
return -ENOMEM; return -ENOMEM;
}
cmd->header.id = SVGA_3D_CMD_DESTROY_GB_SCREENTARGET; cmd->header.id = SVGA_3D_CMD_DESTROY_GB_SCREENTARGET;
cmd->header.size = sizeof(cmd->body); cmd->header.size = sizeof(cmd->body);
...@@ -533,6 +521,7 @@ static void vmw_stdu_bo_fifo_commit(struct vmw_kms_dirty *dirty) ...@@ -533,6 +521,7 @@ static void vmw_stdu_bo_fifo_commit(struct vmw_kms_dirty *dirty)
vmw_fifo_commit(dirty->dev_priv, sizeof(*cmd) + blit_size); vmw_fifo_commit(dirty->dev_priv, sizeof(*cmd) + blit_size);
stdu->display_srf->res.res_dirty = true;
ddirty->left = ddirty->top = S32_MAX; ddirty->left = ddirty->top = S32_MAX;
ddirty->right = ddirty->bottom = S32_MIN; ddirty->right = ddirty->bottom = S32_MIN;
} }
...@@ -629,20 +618,16 @@ static void vmw_stdu_bo_cpu_commit(struct vmw_kms_dirty *dirty) ...@@ -629,20 +618,16 @@ static void vmw_stdu_bo_cpu_commit(struct vmw_kms_dirty *dirty)
region.x2 = diff.rect.x2; region.x2 = diff.rect.x2;
region.y1 = diff.rect.y1; region.y1 = diff.rect.y1;
region.y2 = diff.rect.y2; region.y2 = diff.rect.y2;
ret = vmw_kms_update_proxy( ret = vmw_kms_update_proxy(&stdu->display_srf->res, &region,
(struct vmw_resource *) &stdu->display_srf->res, 1, 1);
(const struct drm_clip_rect *) &region, 1, 1);
if (ret) if (ret)
goto out_cleanup; goto out_cleanup;
dev_priv = vmw_priv(stdu->base.crtc.dev); dev_priv = vmw_priv(stdu->base.crtc.dev);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (!cmd)
if (!cmd) {
DRM_ERROR("Cannot reserve FIFO space to update STDU");
goto out_cleanup; goto out_cleanup;
}
vmw_stdu_populate_update(cmd, stdu->base.unit, vmw_stdu_populate_update(cmd, stdu->base.unit,
region.x1, region.x2, region.x1, region.x2,
...@@ -820,6 +805,7 @@ static void vmw_kms_stdu_surface_fifo_commit(struct vmw_kms_dirty *dirty) ...@@ -820,6 +805,7 @@ static void vmw_kms_stdu_surface_fifo_commit(struct vmw_kms_dirty *dirty)
cmd->body.dest.sid = stdu->display_srf->res.id; cmd->body.dest.sid = stdu->display_srf->res.id;
update = (struct vmw_stdu_update *) &blit[dirty->num_hits]; update = (struct vmw_stdu_update *) &blit[dirty->num_hits];
commit_size = sizeof(*cmd) + blit_size + sizeof(*update); commit_size = sizeof(*cmd) + blit_size + sizeof(*update);
stdu->display_srf->res.res_dirty = true;
} else { } else {
update = dirty->cmd; update = dirty->cmd;
commit_size = sizeof(*update); commit_size = sizeof(*update);
...@@ -876,7 +862,8 @@ int vmw_kms_stdu_surface_dirty(struct vmw_private *dev_priv, ...@@ -876,7 +862,8 @@ int vmw_kms_stdu_surface_dirty(struct vmw_private *dev_priv,
if (!srf) if (!srf)
srf = &vfbs->surface->res; srf = &vfbs->surface->res;
ret = vmw_validation_add_resource(&val_ctx, srf, 0, NULL, NULL); ret = vmw_validation_add_resource(&val_ctx, srf, 0, VMW_RES_DIRTY_NONE,
NULL, NULL);
if (ret) if (ret)
return ret; return ret;
......
...@@ -342,12 +342,9 @@ static void vmw_hw_surface_destroy(struct vmw_resource *res) ...@@ -342,12 +342,9 @@ static void vmw_hw_surface_destroy(struct vmw_resource *res)
if (res->id != -1) { if (res->id != -1) {
cmd = vmw_fifo_reserve(dev_priv, vmw_surface_destroy_size()); cmd = VMW_FIFO_RESERVE(dev_priv, vmw_surface_destroy_size());
if (unlikely(!cmd)) { if (unlikely(!cmd))
DRM_ERROR("Failed reserving FIFO space for surface "
"destruction.\n");
return; return;
}
vmw_surface_destroy_encode(res->id, cmd); vmw_surface_destroy_encode(res->id, cmd);
vmw_fifo_commit(dev_priv, vmw_surface_destroy_size()); vmw_fifo_commit(dev_priv, vmw_surface_destroy_size());
...@@ -414,10 +411,8 @@ static int vmw_legacy_srf_create(struct vmw_resource *res) ...@@ -414,10 +411,8 @@ static int vmw_legacy_srf_create(struct vmw_resource *res)
*/ */
submit_size = vmw_surface_define_size(srf); submit_size = vmw_surface_define_size(srf);
cmd = vmw_fifo_reserve(dev_priv, submit_size); cmd = VMW_FIFO_RESERVE(dev_priv, submit_size);
if (unlikely(!cmd)) { if (unlikely(!cmd)) {
DRM_ERROR("Failed reserving FIFO space for surface "
"creation.\n");
ret = -ENOMEM; ret = -ENOMEM;
goto out_no_fifo; goto out_no_fifo;
} }
...@@ -468,12 +463,10 @@ static int vmw_legacy_srf_dma(struct vmw_resource *res, ...@@ -468,12 +463,10 @@ static int vmw_legacy_srf_dma(struct vmw_resource *res,
BUG_ON(!val_buf->bo); BUG_ON(!val_buf->bo);
submit_size = vmw_surface_dma_size(srf); submit_size = vmw_surface_dma_size(srf);
cmd = vmw_fifo_reserve(dev_priv, submit_size); cmd = VMW_FIFO_RESERVE(dev_priv, submit_size);
if (unlikely(!cmd)) { if (unlikely(!cmd))
DRM_ERROR("Failed reserving FIFO space for surface "
"DMA.\n");
return -ENOMEM; return -ENOMEM;
}
vmw_bo_get_guest_ptr(val_buf->bo, &ptr); vmw_bo_get_guest_ptr(val_buf->bo, &ptr);
vmw_surface_dma_encode(srf, cmd, &ptr, bind); vmw_surface_dma_encode(srf, cmd, &ptr, bind);
...@@ -556,12 +549,9 @@ static int vmw_legacy_srf_destroy(struct vmw_resource *res) ...@@ -556,12 +549,9 @@ static int vmw_legacy_srf_destroy(struct vmw_resource *res)
*/ */
submit_size = vmw_surface_destroy_size(); submit_size = vmw_surface_destroy_size();
cmd = vmw_fifo_reserve(dev_priv, submit_size); cmd = VMW_FIFO_RESERVE(dev_priv, submit_size);
if (unlikely(!cmd)) { if (unlikely(!cmd))
DRM_ERROR("Failed reserving FIFO space for surface "
"eviction.\n");
return -ENOMEM; return -ENOMEM;
}
vmw_surface_destroy_encode(res->id, cmd); vmw_surface_destroy_encode(res->id, cmd);
vmw_fifo_commit(dev_priv, submit_size); vmw_fifo_commit(dev_priv, submit_size);
...@@ -748,11 +738,10 @@ int vmw_surface_define_ioctl(struct drm_device *dev, void *data, ...@@ -748,11 +738,10 @@ int vmw_surface_define_ioctl(struct drm_device *dev, void *data,
ttm_round_pot(num_sizes * sizeof(struct drm_vmw_size)) + ttm_round_pot(num_sizes * sizeof(struct drm_vmw_size)) +
ttm_round_pot(num_sizes * sizeof(struct vmw_surface_offset)); ttm_round_pot(num_sizes * sizeof(struct vmw_surface_offset));
desc = svga3dsurface_get_desc(req->format); desc = svga3dsurface_get_desc(req->format);
if (unlikely(desc->block_desc == SVGA3DBLOCKDESC_NONE)) { if (unlikely(desc->block_desc == SVGA3DBLOCKDESC_NONE)) {
DRM_ERROR("Invalid surface format for surface creation.\n"); VMW_DEBUG_USER("Invalid format %d for surface creation.\n",
DRM_ERROR("Format requested is: %d\n", req->format); req->format);
return -EINVAL; return -EINVAL;
} }
...@@ -764,8 +753,7 @@ int vmw_surface_define_ioctl(struct drm_device *dev, void *data, ...@@ -764,8 +753,7 @@ int vmw_surface_define_ioctl(struct drm_device *dev, void *data,
size, &ctx); size, &ctx);
if (unlikely(ret != 0)) { if (unlikely(ret != 0)) {
if (ret != -ERESTARTSYS) if (ret != -ERESTARTSYS)
DRM_ERROR("Out of graphics memory for surface" DRM_ERROR("Out of graphics memory for surface.\n");
" creation.\n");
goto out_unlock; goto out_unlock;
} }
...@@ -939,12 +927,12 @@ vmw_surface_handle_reference(struct vmw_private *dev_priv, ...@@ -939,12 +927,12 @@ vmw_surface_handle_reference(struct vmw_private *dev_priv,
ret = -EINVAL; ret = -EINVAL;
base = ttm_base_object_lookup_for_ref(dev_priv->tdev, handle); base = ttm_base_object_lookup_for_ref(dev_priv->tdev, handle);
if (unlikely(!base)) { if (unlikely(!base)) {
DRM_ERROR("Could not find surface to reference.\n"); VMW_DEBUG_USER("Could not find surface to reference.\n");
goto out_no_lookup; goto out_no_lookup;
} }
if (unlikely(ttm_base_object_type(base) != VMW_RES_SURFACE)) { if (unlikely(ttm_base_object_type(base) != VMW_RES_SURFACE)) {
DRM_ERROR("Referenced object is not a surface.\n"); VMW_DEBUG_USER("Referenced object is not a surface.\n");
goto out_bad_resource; goto out_bad_resource;
} }
...@@ -1022,8 +1010,8 @@ int vmw_surface_reference_ioctl(struct drm_device *dev, void *data, ...@@ -1022,8 +1010,8 @@ int vmw_surface_reference_ioctl(struct drm_device *dev, void *data,
ret = copy_to_user(user_sizes, &srf->base_size, ret = copy_to_user(user_sizes, &srf->base_size,
sizeof(srf->base_size)); sizeof(srf->base_size));
if (unlikely(ret != 0)) { if (unlikely(ret != 0)) {
DRM_ERROR("copy_to_user failed %p %u\n", VMW_DEBUG_USER("copy_to_user failed %p %u\n", user_sizes,
user_sizes, srf->num_sizes); srf->num_sizes);
ttm_ref_object_base_unref(tfile, base->handle, TTM_REF_USAGE); ttm_ref_object_base_unref(tfile, base->handle, TTM_REF_USAGE);
ret = -EFAULT; ret = -EFAULT;
} }
...@@ -1088,12 +1076,10 @@ static int vmw_gb_surface_create(struct vmw_resource *res) ...@@ -1088,12 +1076,10 @@ static int vmw_gb_surface_create(struct vmw_resource *res)
submit_len = sizeof(*cmd); submit_len = sizeof(*cmd);
} }
cmd = vmw_fifo_reserve(dev_priv, submit_len); cmd = VMW_FIFO_RESERVE(dev_priv, submit_len);
cmd2 = (typeof(cmd2))cmd; cmd2 = (typeof(cmd2))cmd;
cmd3 = (typeof(cmd3))cmd; cmd3 = (typeof(cmd3))cmd;
if (unlikely(!cmd)) { if (unlikely(!cmd)) {
DRM_ERROR("Failed reserving FIFO space for surface "
"creation.\n");
ret = -ENOMEM; ret = -ENOMEM;
goto out_no_fifo; goto out_no_fifo;
} }
...@@ -1171,12 +1157,9 @@ static int vmw_gb_surface_bind(struct vmw_resource *res, ...@@ -1171,12 +1157,9 @@ static int vmw_gb_surface_bind(struct vmw_resource *res,
submit_size = sizeof(*cmd1) + (res->backup_dirty ? sizeof(*cmd2) : 0); submit_size = sizeof(*cmd1) + (res->backup_dirty ? sizeof(*cmd2) : 0);
cmd1 = vmw_fifo_reserve(dev_priv, submit_size); cmd1 = VMW_FIFO_RESERVE(dev_priv, submit_size);
if (unlikely(!cmd1)) { if (unlikely(!cmd1))
DRM_ERROR("Failed reserving FIFO space for surface "
"binding.\n");
return -ENOMEM; return -ENOMEM;
}
cmd1->header.id = SVGA_3D_CMD_BIND_GB_SURFACE; cmd1->header.id = SVGA_3D_CMD_BIND_GB_SURFACE;
cmd1->header.size = sizeof(cmd1->body); cmd1->header.size = sizeof(cmd1->body);
...@@ -1221,12 +1204,9 @@ static int vmw_gb_surface_unbind(struct vmw_resource *res, ...@@ -1221,12 +1204,9 @@ static int vmw_gb_surface_unbind(struct vmw_resource *res,
BUG_ON(bo->mem.mem_type != VMW_PL_MOB); BUG_ON(bo->mem.mem_type != VMW_PL_MOB);
submit_size = sizeof(*cmd3) + (readback ? sizeof(*cmd1) : sizeof(*cmd2)); submit_size = sizeof(*cmd3) + (readback ? sizeof(*cmd1) : sizeof(*cmd2));
cmd = vmw_fifo_reserve(dev_priv, submit_size); cmd = VMW_FIFO_RESERVE(dev_priv, submit_size);
if (unlikely(!cmd)) { if (unlikely(!cmd))
DRM_ERROR("Failed reserving FIFO space for surface "
"unbinding.\n");
return -ENOMEM; return -ENOMEM;
}
if (readback) { if (readback) {
cmd1 = (void *) cmd; cmd1 = (void *) cmd;
...@@ -1280,10 +1260,8 @@ static int vmw_gb_surface_destroy(struct vmw_resource *res) ...@@ -1280,10 +1260,8 @@ static int vmw_gb_surface_destroy(struct vmw_resource *res)
vmw_view_surface_list_destroy(dev_priv, &srf->view_list); vmw_view_surface_list_destroy(dev_priv, &srf->view_list);
vmw_binding_res_list_scrub(&res->binding_head); vmw_binding_res_list_scrub(&res->binding_head);
cmd = vmw_fifo_reserve(dev_priv, sizeof(*cmd)); cmd = VMW_FIFO_RESERVE(dev_priv, sizeof(*cmd));
if (unlikely(!cmd)) { if (unlikely(!cmd)) {
DRM_ERROR("Failed reserving FIFO space for surface "
"destruction.\n");
mutex_unlock(&dev_priv->binding_mutex); mutex_unlock(&dev_priv->binding_mutex);
return -ENOMEM; return -ENOMEM;
} }
...@@ -1405,16 +1383,16 @@ int vmw_surface_gb_priv_define(struct drm_device *dev, ...@@ -1405,16 +1383,16 @@ int vmw_surface_gb_priv_define(struct drm_device *dev,
if (for_scanout) { if (for_scanout) {
if (!svga3dsurface_is_screen_target_format(format)) { if (!svga3dsurface_is_screen_target_format(format)) {
DRM_ERROR("Invalid Screen Target surface format."); VMW_DEBUG_USER("Invalid Screen Target surface format.");
return -EINVAL; return -EINVAL;
} }
if (size.width > dev_priv->texture_max_width || if (size.width > dev_priv->texture_max_width ||
size.height > dev_priv->texture_max_height) { size.height > dev_priv->texture_max_height) {
DRM_ERROR("%ux%u\n, exceeds max surface size %ux%u", VMW_DEBUG_USER("%ux%u\n, exceeds max surface size %ux%u",
size.width, size.height, size.width, size.height,
dev_priv->texture_max_width, dev_priv->texture_max_width,
dev_priv->texture_max_height); dev_priv->texture_max_height);
return -EINVAL; return -EINVAL;
} }
} else { } else {
...@@ -1422,14 +1400,14 @@ int vmw_surface_gb_priv_define(struct drm_device *dev, ...@@ -1422,14 +1400,14 @@ int vmw_surface_gb_priv_define(struct drm_device *dev,
desc = svga3dsurface_get_desc(format); desc = svga3dsurface_get_desc(format);
if (unlikely(desc->block_desc == SVGA3DBLOCKDESC_NONE)) { if (unlikely(desc->block_desc == SVGA3DBLOCKDESC_NONE)) {
DRM_ERROR("Invalid surface format.\n"); VMW_DEBUG_USER("Invalid surface format.\n");
return -EINVAL; return -EINVAL;
} }
} }
/* array_size must be null for non-GL3 host. */ /* array_size must be null for non-GL3 host. */
if (array_size > 0 && !dev_priv->has_dx) { if (array_size > 0 && !dev_priv->has_dx) {
DRM_ERROR("Tried to create DX surface on non-DX host.\n"); VMW_DEBUG_USER("Tried to create DX surface on non-DX host.\n");
return -EINVAL; return -EINVAL;
} }
...@@ -1651,7 +1629,7 @@ vmw_gb_surface_define_internal(struct drm_device *dev, ...@@ -1651,7 +1629,7 @@ vmw_gb_surface_define_internal(struct drm_device *dev,
if (ret == 0) { if (ret == 0) {
if (res->backup->base.num_pages * PAGE_SIZE < if (res->backup->base.num_pages * PAGE_SIZE <
res->backup_size) { res->backup_size) {
DRM_ERROR("Surface backup buffer too small.\n"); VMW_DEBUG_USER("Surface backup buffer too small.\n");
vmw_bo_unreference(&res->backup); vmw_bo_unreference(&res->backup);
ret = -EINVAL; ret = -EINVAL;
goto out_unlock; goto out_unlock;
......
...@@ -76,6 +76,8 @@ struct vmw_validation_res_node { ...@@ -76,6 +76,8 @@ struct vmw_validation_res_node {
u32 switching_backup : 1; u32 switching_backup : 1;
u32 first_usage : 1; u32 first_usage : 1;
u32 reserved : 1; u32 reserved : 1;
u32 dirty : 1;
u32 dirty_set : 1;
unsigned long private[0]; unsigned long private[0];
}; };
...@@ -299,6 +301,7 @@ int vmw_validation_add_bo(struct vmw_validation_context *ctx, ...@@ -299,6 +301,7 @@ int vmw_validation_add_bo(struct vmw_validation_context *ctx,
* @ctx: The validation context. * @ctx: The validation context.
* @res: The resource. * @res: The resource.
* @priv_size: Size of private, additional metadata. * @priv_size: Size of private, additional metadata.
* @dirty: Whether to change dirty status.
* @p_node: Output pointer of additional metadata address. * @p_node: Output pointer of additional metadata address.
* @first_usage: Whether this was the first time this resource was seen. * @first_usage: Whether this was the first time this resource was seen.
* *
...@@ -307,6 +310,7 @@ int vmw_validation_add_bo(struct vmw_validation_context *ctx, ...@@ -307,6 +310,7 @@ int vmw_validation_add_bo(struct vmw_validation_context *ctx,
int vmw_validation_add_resource(struct vmw_validation_context *ctx, int vmw_validation_add_resource(struct vmw_validation_context *ctx,
struct vmw_resource *res, struct vmw_resource *res,
size_t priv_size, size_t priv_size,
u32 dirty,
void **p_node, void **p_node,
bool *first_usage) bool *first_usage)
{ {
...@@ -321,8 +325,7 @@ int vmw_validation_add_resource(struct vmw_validation_context *ctx, ...@@ -321,8 +325,7 @@ int vmw_validation_add_resource(struct vmw_validation_context *ctx,
node = vmw_validation_mem_alloc(ctx, sizeof(*node) + priv_size); node = vmw_validation_mem_alloc(ctx, sizeof(*node) + priv_size);
if (!node) { if (!node) {
DRM_ERROR("Failed to allocate a resource validation " VMW_DEBUG_USER("Failed to allocate a resource validation entry.\n");
"entry.\n");
return -ENOMEM; return -ENOMEM;
} }
...@@ -358,6 +361,11 @@ int vmw_validation_add_resource(struct vmw_validation_context *ctx, ...@@ -358,6 +361,11 @@ int vmw_validation_add_resource(struct vmw_validation_context *ctx,
} }
out_fill: out_fill:
if (dirty) {
node->dirty_set = 1;
/* Overwriting previous information here is intentional! */
node->dirty = (dirty & VMW_RES_DIRTY_SET) ? 1 : 0;
}
if (first_usage) if (first_usage)
*first_usage = node->first_usage; *first_usage = node->first_usage;
if (p_node) if (p_node)
...@@ -366,6 +374,29 @@ int vmw_validation_add_resource(struct vmw_validation_context *ctx, ...@@ -366,6 +374,29 @@ int vmw_validation_add_resource(struct vmw_validation_context *ctx,
return 0; return 0;
} }
/**
* vmw_validation_res_set_dirty - Register a resource dirty set or clear during
* validation.
* @ctx: The validation context.
* @val_private: The additional meta-data pointer returned when the
* resource was registered with the validation context. Used to identify
* the resource.
* @dirty: Dirty information VMW_RES_DIRTY_XX
*/
void vmw_validation_res_set_dirty(struct vmw_validation_context *ctx,
void *val_private, u32 dirty)
{
struct vmw_validation_res_node *val;
if (!dirty)
return;
val = container_of(val_private, typeof(*val), private);
val->dirty_set = 1;
/* Overwriting previous information here is intentional! */
val->dirty = (dirty & VMW_RES_DIRTY_SET) ? 1 : 0;
}
/** /**
* vmw_validation_res_switch_backup - Register a backup MOB switch during * vmw_validation_res_switch_backup - Register a backup MOB switch during
* validation. * validation.
...@@ -450,15 +481,23 @@ void vmw_validation_res_unreserve(struct vmw_validation_context *ctx, ...@@ -450,15 +481,23 @@ void vmw_validation_res_unreserve(struct vmw_validation_context *ctx,
struct vmw_validation_res_node *val; struct vmw_validation_res_node *val;
list_splice_init(&ctx->resource_ctx_list, &ctx->resource_list); list_splice_init(&ctx->resource_ctx_list, &ctx->resource_list);
if (backoff)
list_for_each_entry(val, &ctx->resource_list, head) { list_for_each_entry(val, &ctx->resource_list, head) {
if (val->reserved) if (val->reserved)
vmw_resource_unreserve(val->res, vmw_resource_unreserve(val->res,
!backoff && false, false, false,
val->switching_backup, NULL, 0);
val->new_backup, }
val->new_backup_offset); else
} list_for_each_entry(val, &ctx->resource_list, head) {
if (val->reserved)
vmw_resource_unreserve(val->res,
val->dirty_set,
val->dirty,
val->switching_backup,
val->new_backup,
val->new_backup_offset);
}
} }
/** /**
......
...@@ -33,6 +33,10 @@ ...@@ -33,6 +33,10 @@
#include <linux/ww_mutex.h> #include <linux/ww_mutex.h>
#include <drm/ttm/ttm_execbuf_util.h> #include <drm/ttm/ttm_execbuf_util.h>
#define VMW_RES_DIRTY_NONE 0
#define VMW_RES_DIRTY_SET BIT(0)
#define VMW_RES_DIRTY_CLEAR BIT(1)
/** /**
* struct vmw_validation_mem - Custom interface to provide memory reservations * struct vmw_validation_mem - Custom interface to provide memory reservations
* for the validation code. * for the validation code.
...@@ -237,6 +241,7 @@ void vmw_validation_unref_lists(struct vmw_validation_context *ctx); ...@@ -237,6 +241,7 @@ void vmw_validation_unref_lists(struct vmw_validation_context *ctx);
int vmw_validation_add_resource(struct vmw_validation_context *ctx, int vmw_validation_add_resource(struct vmw_validation_context *ctx,
struct vmw_resource *res, struct vmw_resource *res,
size_t priv_size, size_t priv_size,
u32 dirty,
void **p_node, void **p_node,
bool *first_usage); bool *first_usage);
void vmw_validation_drop_ht(struct vmw_validation_context *ctx); void vmw_validation_drop_ht(struct vmw_validation_context *ctx);
...@@ -261,4 +266,6 @@ void *vmw_validation_mem_alloc(struct vmw_validation_context *ctx, ...@@ -261,4 +266,6 @@ void *vmw_validation_mem_alloc(struct vmw_validation_context *ctx,
int vmw_validation_preload_bo(struct vmw_validation_context *ctx); int vmw_validation_preload_bo(struct vmw_validation_context *ctx);
int vmw_validation_preload_res(struct vmw_validation_context *ctx, int vmw_validation_preload_res(struct vmw_validation_context *ctx,
unsigned int size); unsigned int size);
void vmw_validation_res_set_dirty(struct vmw_validation_context *ctx,
void *val_private, u32 dirty);
#endif #endif
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment