diff options
author | Linus Torvalds | 2012-05-21 20:20:23 -0700 |
---|---|---|
committer | Linus Torvalds | 2012-05-21 20:20:23 -0700 |
commit | 99262a3dafa3290866512ddfb32609198f8973e9 (patch) | |
tree | 6f74764150cd9c38d9ffacbeb5054b696537e154 /drivers/block | |
parent | bf67f3a5c456a18f2e8d062f7e88506ef2cd9837 (diff) | |
parent | c6190804f1dc5357b57825f0491eb31fc9ccf130 (diff) |
Merge tag 'virtio-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/rusty/linux-2.6-for-linus
Pull virtio updates from Rusty Russell.
* tag 'virtio-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/rusty/linux-2.6-for-linus:
virtio: fix typo in comment
virtio-mmio: Devices parameter parsing
virtio_blk: Drop unused request tracking list
virtio-blk: Fix hot-unplug race in remove method
virtio: Use ida to allocate virtio index
virtio: balloon: separate out common code between remove and freeze functions
virtio: balloon: drop restore_common()
9p: disconnect channel when PCI device is removed
virtio: update documentation to v0.9.5 of spec
Diffstat (limited to 'drivers/block')
-rw-r--r-- | drivers/block/virtio_blk.c | 21 |
1 files changed, 11 insertions, 10 deletions
diff --git a/drivers/block/virtio_blk.c b/drivers/block/virtio_blk.c index 0d39f2f4294a..693187df7601 100644 --- a/drivers/block/virtio_blk.c +++ b/drivers/block/virtio_blk.c @@ -29,9 +29,6 @@ struct virtio_blk /* The disk structure for the kernel. */ struct gendisk *disk; - /* Request tracking. */ - struct list_head reqs; - mempool_t *pool; /* Process context for config space updates */ @@ -55,7 +52,6 @@ struct virtio_blk struct virtblk_req { - struct list_head list; struct request *req; struct virtio_blk_outhdr out_hdr; struct virtio_scsi_inhdr in_hdr; @@ -99,7 +95,6 @@ static void blk_done(struct virtqueue *vq) } __blk_end_request_all(vbr->req, error); - list_del(&vbr->list); mempool_free(vbr, vblk->pool); } /* In case queue is stopped waiting for more buffers. */ @@ -184,7 +179,6 @@ static bool do_req(struct request_queue *q, struct virtio_blk *vblk, return false; } - list_add_tail(&vbr->list, &vblk->reqs); return true; } @@ -437,7 +431,6 @@ static int __devinit virtblk_probe(struct virtio_device *vdev) goto out_free_index; } - INIT_LIST_HEAD(&vblk->reqs); spin_lock_init(&vblk->lock); vblk->vdev = vdev; vblk->sg_elems = sg_elems; @@ -583,21 +576,29 @@ static void __devexit virtblk_remove(struct virtio_device *vdev) { struct virtio_blk *vblk = vdev->priv; int index = vblk->index; + struct virtblk_req *vbr; + unsigned long flags; /* Prevent config work handler from accessing the device. */ mutex_lock(&vblk->config_lock); vblk->config_enable = false; mutex_unlock(&vblk->config_lock); - /* Nothing should be pending. */ - BUG_ON(!list_empty(&vblk->reqs)); - /* Stop all the virtqueues. */ vdev->config->reset(vdev); flush_work(&vblk->config_work); del_gendisk(vblk->disk); + + /* Abort requests dispatched to driver. */ + spin_lock_irqsave(&vblk->lock, flags); + while ((vbr = virtqueue_detach_unused_buf(vblk->vq))) { + __blk_end_request_all(vbr->req, -EIO); + mempool_free(vbr, vblk->pool); + } + spin_unlock_irqrestore(&vblk->lock, flags); + blk_cleanup_queue(vblk->disk->queue); put_disk(vblk->disk); mempool_destroy(vblk->pool); |