On Tue, Sep 8, 2026 at 10:13 AM Akihiko Odaki <[email protected]> wrote: > > Blob unmapping may be suspended because of remaining uses of the > mapping. virtio_gpu_process_cmdq() uses the following condition to > detect a suspended command: > > !cmd->finished && !(cmd->cmd_hdr.flags & VIRTIO_GPU_FLAG_FENCE) > > However, the guest may set VIRTIO_GPU_FLAG_FENCE for a command that > performs blob unmapping. Such a command will be incorrectly assumed > as not being suspended. Add a dedicated flag for the suspended state > to avoid overloading VIRTIO_GPU_FLAG_FENCE. > > Fixes: 640f9149c3dc ("virtio-gpu: Support suspension of commands processing") > Signed-off-by: Akihiko Odaki <[email protected]>
Reviewed-by: Marc-André Lureau <[email protected]> > --- > include/hw/virtio/virtio-gpu.h | 1 + > hw/display/virtio-gpu-virgl.c | 17 +++++++---------- > hw/display/virtio-gpu.c | 5 ++--- > 3 files changed, 10 insertions(+), 13 deletions(-) > > diff --git a/include/hw/virtio/virtio-gpu.h b/include/hw/virtio/virtio-gpu.h > index 9404e488208a..3eccc4bc39c3 100644 > --- a/include/hw/virtio/virtio-gpu.h > +++ b/include/hw/virtio/virtio-gpu.h > @@ -141,6 +141,7 @@ struct virtio_gpu_ctrl_command { > struct virtio_gpu_ctrl_hdr cmd_hdr; > uint32_t error; > bool finished; > + bool suspended; > QTAILQ_ENTRY(virtio_gpu_ctrl_command) next; > }; > > diff --git a/hw/display/virtio-gpu-virgl.c b/hw/display/virtio-gpu-virgl.c > index 9bda572426b2..c37df91e3ed1 100644 > --- a/hw/display/virtio-gpu-virgl.c > +++ b/hw/display/virtio-gpu-virgl.c > @@ -440,8 +440,7 @@ virtio_gpu_virgl_resource_unref(VirtIOGPU *g, > } > > static void virgl_cmd_resource_unref(VirtIOGPU *g, > - struct virtio_gpu_ctrl_command *cmd, > - bool *cmd_suspended) > + struct virtio_gpu_ctrl_command *cmd) > { > struct virtio_gpu_resource_unref unref; > struct virtio_gpu_virgl_resource *res; > @@ -457,7 +456,7 @@ static void virgl_cmd_resource_unref(VirtIOGPU *g, > return; > } > > - virtio_gpu_virgl_resource_unref(g, res, cmd_suspended); > + virtio_gpu_virgl_resource_unref(g, res, &cmd->suspended); > } > > void virtio_gpu_virgl_resource_destroy(VirtIOGPU *g, > @@ -946,8 +945,7 @@ static void virgl_cmd_resource_map_blob(VirtIOGPU *g, > } > > static void virgl_cmd_resource_unmap_blob(VirtIOGPU *g, > - struct virtio_gpu_ctrl_command > *cmd, > - bool *cmd_suspended) > + struct virtio_gpu_ctrl_command > *cmd) > { > struct virtio_gpu_resource_unmap_blob ublob; > struct virtio_gpu_virgl_resource *res; > @@ -964,7 +962,7 @@ static void virgl_cmd_resource_unmap_blob(VirtIOGPU *g, > return; > } > > - ret = virtio_gpu_virgl_unmap_resource_blob(g, res, cmd_suspended); > + ret = virtio_gpu_virgl_unmap_resource_blob(g, res, &cmd->suspended); > if (ret) { > cmd->error = VIRTIO_GPU_RESP_ERR_UNSPEC; > return; > @@ -1036,7 +1034,6 @@ static void virgl_cmd_set_scanout_blob(VirtIOGPU *g, > void virtio_gpu_virgl_process_cmd(VirtIOGPU *g, > struct virtio_gpu_ctrl_command *cmd) > { > - bool cmd_suspended = false; > int ret; > > VIRTIO_GPU_FILL_CMD(cmd->cmd_hdr); > @@ -1080,7 +1077,7 @@ void virtio_gpu_virgl_process_cmd(VirtIOGPU *g, > virgl_cmd_resource_flush(g, cmd); > break; > case VIRTIO_GPU_CMD_RESOURCE_UNREF: > - virgl_cmd_resource_unref(g, cmd, &cmd_suspended); > + virgl_cmd_resource_unref(g, cmd); > break; > case VIRTIO_GPU_CMD_CTX_ATTACH_RESOURCE: > /* TODO add security */ > @@ -1110,7 +1107,7 @@ void virtio_gpu_virgl_process_cmd(VirtIOGPU *g, > virgl_cmd_resource_map_blob(g, cmd); > break; > case VIRTIO_GPU_CMD_RESOURCE_UNMAP_BLOB: > - virgl_cmd_resource_unmap_blob(g, cmd, &cmd_suspended); > + virgl_cmd_resource_unmap_blob(g, cmd); > break; > case VIRTIO_GPU_CMD_SET_SCANOUT_BLOB: > virgl_cmd_set_scanout_blob(g, cmd); > @@ -1121,7 +1118,7 @@ void virtio_gpu_virgl_process_cmd(VirtIOGPU *g, > break; > } > > - if (cmd_suspended || cmd->finished) { > + if (cmd->suspended || cmd->finished) { > return; > } > if (cmd->error) { > diff --git a/hw/display/virtio-gpu.c b/hw/display/virtio-gpu.c > index d520f69e6453..dd6c09d1ddcf 100644 > --- a/hw/display/virtio-gpu.c > +++ b/hw/display/virtio-gpu.c > @@ -1193,11 +1193,10 @@ void virtio_gpu_process_cmdq(VirtIOGPU *g) > break; > } > > - /* process command */ > + cmd->suspended = false; > vgc->process_cmd(g, cmd); > > - /* command suspended */ > - if (!cmd->finished && !(cmd->cmd_hdr.flags & VIRTIO_GPU_FLAG_FENCE)) > { > + if (cmd->suspended) { > trace_virtio_gpu_cmd_suspended(cmd->cmd_hdr.type); > break; > } > > -- > 2.55.0 >
