If VIRTIO_GPU_F_BLOB_ALIGNMENT has been negotiated, both CREATE_BLOB and MAP_BLOB requests must be aligned to blob_alignment.
Introduce checks to ensure we don't send invalid requests to the device. Signed-off-by: Sergio Lopez <[email protected]> --- drivers/gpu/drm/virtio/virtgpu_drv.h | 2 +- drivers/gpu/drm/virtio/virtgpu_object.c | 6 ++++-- drivers/gpu/drm/virtio/virtgpu_prime.c | 7 +++++-- drivers/gpu/drm/virtio/virtgpu_vq.c | 12 +++++++++++- drivers/gpu/drm/virtio/virtgpu_vram.c | 10 ++++++++-- 5 files changed, 29 insertions(+), 8 deletions(-) diff --git a/drivers/gpu/drm/virtio/virtgpu_drv.h b/drivers/gpu/drm/virtio/virtgpu_drv.h index d1fa386a5a99..11a55d4ccd54 100644 --- a/drivers/gpu/drm/virtio/virtgpu_drv.h +++ b/drivers/gpu/drm/virtio/virtgpu_drv.h @@ -433,7 +433,7 @@ int virtio_gpu_cmd_map(struct virtio_gpu_device *vgdev, void virtio_gpu_cmd_unmap(struct virtio_gpu_device *vgdev, struct virtio_gpu_object *bo); -void +int virtio_gpu_cmd_resource_create_blob(struct virtio_gpu_device *vgdev, struct virtio_gpu_object *bo, struct virtio_gpu_object_params *params, diff --git a/drivers/gpu/drm/virtio/virtgpu_object.c b/drivers/gpu/drm/virtio/virtgpu_object.c index e6363c887500..6118344bff84 100644 --- a/drivers/gpu/drm/virtio/virtgpu_object.c +++ b/drivers/gpu/drm/virtio/virtgpu_object.c @@ -246,8 +246,10 @@ int virtio_gpu_object_create(struct virtio_gpu_device *vgdev, if (params->blob_mem == VIRTGPU_BLOB_MEM_GUEST) bo->guest_blob = true; - virtio_gpu_cmd_resource_create_blob(vgdev, bo, params, - ents, nents); + ret = virtio_gpu_cmd_resource_create_blob(vgdev, bo, params, + ents, nents); + if (ret) + goto err_put_objs; } else if (params->virgl) { virtio_gpu_cmd_resource_create_3d(vgdev, bo, params, objs, fence); diff --git a/drivers/gpu/drm/virtio/virtgpu_prime.c b/drivers/gpu/drm/virtio/virtgpu_prime.c index ce49282198cb..06593496c53f 100644 --- a/drivers/gpu/drm/virtio/virtgpu_prime.c +++ b/drivers/gpu/drm/virtio/virtgpu_prime.c @@ -257,8 +257,11 @@ static int virtgpu_dma_buf_init_obj(struct drm_device *dev, params.blob_flags = VIRTGPU_BLOB_FLAG_USE_SHAREABLE; params.size = attach->dmabuf->size; - virtio_gpu_cmd_resource_create_blob(vgdev, bo, ¶ms, - ents, nents); + ret = virtio_gpu_cmd_resource_create_blob(vgdev, bo, ¶ms, + ents, nents); + if (ret) + goto err_import; + bo->guest_blob = true; dma_buf_unpin(attach); diff --git a/drivers/gpu/drm/virtio/virtgpu_vq.c b/drivers/gpu/drm/virtio/virtgpu_vq.c index 8181b22b9b46..d558ba2d213a 100644 --- a/drivers/gpu/drm/virtio/virtgpu_vq.c +++ b/drivers/gpu/drm/virtio/virtgpu_vq.c @@ -1393,6 +1393,10 @@ int virtio_gpu_cmd_map(struct virtio_gpu_device *vgdev, struct virtio_gpu_vbuffer *vbuf; struct virtio_gpu_resp_map_info *resp_buf; + if (vgdev->has_blob_alignment && + !IS_ALIGNED(offset, vgdev->blob_alignment)) + return -EINVAL; + resp_buf = kzalloc(sizeof(*resp_buf), GFP_KERNEL); if (!resp_buf) return -ENOMEM; @@ -1426,7 +1430,7 @@ void virtio_gpu_cmd_unmap(struct virtio_gpu_device *vgdev, virtio_gpu_queue_ctrl_buffer(vgdev, vbuf); } -void +int virtio_gpu_cmd_resource_create_blob(struct virtio_gpu_device *vgdev, struct virtio_gpu_object *bo, struct virtio_gpu_object_params *params, @@ -1436,6 +1440,10 @@ virtio_gpu_cmd_resource_create_blob(struct virtio_gpu_device *vgdev, struct virtio_gpu_resource_create_blob *cmd_p; struct virtio_gpu_vbuffer *vbuf; + if (vgdev->has_blob_alignment && + !IS_ALIGNED(params->size, vgdev->blob_alignment)) + return -EINVAL; + cmd_p = virtio_gpu_alloc_cmd(vgdev, &vbuf, sizeof(*cmd_p)); memset(cmd_p, 0, sizeof(*cmd_p)); @@ -1456,6 +1464,8 @@ virtio_gpu_cmd_resource_create_blob(struct virtio_gpu_device *vgdev, if (nents) bo->attached = true; + + return 0; } void virtio_gpu_cmd_set_scanout_blob(struct virtio_gpu_device *vgdev, diff --git a/drivers/gpu/drm/virtio/virtgpu_vram.c b/drivers/gpu/drm/virtio/virtgpu_vram.c index 5ad3b7c6f73c..6c402eca5726 100644 --- a/drivers/gpu/drm/virtio/virtgpu_vram.c +++ b/drivers/gpu/drm/virtio/virtgpu_vram.c @@ -216,8 +216,14 @@ int virtio_gpu_vram_create(struct virtio_gpu_device *vgdev, return ret; } - virtio_gpu_cmd_resource_create_blob(vgdev, &vram->base, params, NULL, - 0); + ret = virtio_gpu_cmd_resource_create_blob(vgdev, &vram->base, params, + NULL, 0); + if (ret) { + drm_gem_free_mmap_offset(obj); + kfree(vram); + return ret; + } + if (params->blob_flags & VIRTGPU_BLOB_FLAG_USE_MAPPABLE) { ret = virtio_gpu_vram_map(&vram->base); if (ret) { -- 2.51.0
