qemu-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Qemu-devel] [PATCH 2/3] virtio-blk: Don't exit on invalid VQ data


From: Fam Zheng
Subject: [Qemu-devel] [PATCH 2/3] virtio-blk: Don't exit on invalid VQ data
Date: Tue, 22 Apr 2014 16:55:16 +0800

Set vdev's broken flag, instead of exit, if the VQ has invalid data.

Check VirtIODevice.broken in VQ output handler, and don't pop any more
request if set, until the device is reset.

Signed-off-by: Fam Zheng <address@hidden>
---
 hw/block/virtio-blk.c | 20 +++++++++++++++-----
 1 file changed, 15 insertions(+), 5 deletions(-)

diff --git a/hw/block/virtio-blk.c b/hw/block/virtio-blk.c
index 8a568e5..f69aca6 100644
--- a/hw/block/virtio-blk.c
+++ b/hw/block/virtio-blk.c
@@ -339,20 +339,23 @@ static void virtio_blk_handle_read(VirtIOBlockReq *req)
                    virtio_blk_rw_complete, req);
 }
 
-static void virtio_blk_handle_request(VirtIOBlockReq *req,
-    MultiReqBuffer *mrb)
+static int virtio_blk_handle_request(VirtIOBlockReq *req,
+                                     MultiReqBuffer *mrb)
 {
     uint32_t type;
+    VirtIODevice *vdev = VIRTIO_DEVICE(req->dev);
 
     if (req->elem.out_num < 1 || req->elem.in_num < 1) {
         error_report("virtio-blk missing headers");
-        exit(1);
+        virtio_set_broken(vdev);
+        return -EINVAL;
     }
 
     if (req->elem.out_sg[0].iov_len < sizeof(*req->out) ||
         req->elem.in_sg[req->elem.in_num - 1].iov_len < sizeof(*req->in)) {
         error_report("virtio-blk header not in correct element");
-        exit(1);
+        virtio_set_broken(vdev);
+        return -EINVAL;
     }
 
     req->out = (void *)req->elem.out_sg[0].iov_base;
@@ -389,6 +392,7 @@ static void virtio_blk_handle_request(VirtIOBlockReq *req,
         virtio_blk_req_complete(req, VIRTIO_BLK_S_UNSUPP);
         g_free(req);
     }
+    return 0;
 }
 
 static void virtio_blk_handle_output(VirtIODevice *vdev, VirtQueue *vq)
@@ -399,6 +403,10 @@ static void virtio_blk_handle_output(VirtIODevice *vdev, 
VirtQueue *vq)
         .num_writes = 0,
     };
 
+    if (virtio_broken(vdev)) {
+        return;
+    }
+
 #ifdef CONFIG_VIRTIO_BLK_DATA_PLANE
     /* Some guests kick before setting VIRTIO_CONFIG_S_DRIVER_OK so start
      * dataplane here instead of waiting for .set_status().
@@ -410,7 +418,9 @@ static void virtio_blk_handle_output(VirtIODevice *vdev, 
VirtQueue *vq)
 #endif
 
     while ((req = virtio_blk_get_request(s))) {
-        virtio_blk_handle_request(req, &mrb);
+        if (virtio_blk_handle_request(req, &mrb) < 0) {
+            return;
+        }
     }
 
     virtio_submit_multiwrite(s->bs, &mrb);
-- 
1.9.2




reply via email to

[Prev in Thread] Current Thread [Next in Thread]