From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([140.186.70.92]:60411) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1RqSHy-0000B1-U0 for qemu-devel@nongnu.org; Thu, 26 Jan 2012 11:35:11 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1RqSHq-0003K7-RA for qemu-devel@nongnu.org; Thu, 26 Jan 2012 11:35:06 -0500 Received: from mx1.redhat.com ([209.132.183.28]:47811) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1RqSHq-0003K3-Em for qemu-devel@nongnu.org; Thu, 26 Jan 2012 11:34:58 -0500 From: Kevin Wolf Date: Thu, 26 Jan 2012 17:37:58 +0100 Message-Id: <1327595896-19623-5-git-send-email-kwolf@redhat.com> In-Reply-To: <1327595896-19623-1-git-send-email-kwolf@redhat.com> References: <1327595896-19623-1-git-send-email-kwolf@redhat.com> Subject: [Qemu-devel] [PATCH 04/22] block: check bdrv_in_use() before blockdev operations List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: anthony@codemonkey.ws Cc: kwolf@redhat.com, qemu-devel@nongnu.org From: Stefan Hajnoczi Long-running block operations like block migration and image streaming must have continual access to their block device. It is not safe to perform operations like hotplug, eject, change, resize, commit, or external snapshot while a long-running operation is in progress. This patch adds the missing bdrv_in_use() checks so that block migration and image streaming never have the rug pulled out from underneath them. Signed-off-by: Stefan Hajnoczi Signed-off-by: Kevin Wolf --- block.c | 4 ++++ blockdev.c | 16 +++++++++++++++- 2 files changed, 19 insertions(+), 1 deletions(-) diff --git a/block.c b/block.c index 3f072f6..43f6484 100644 --- a/block.c +++ b/block.c @@ -1020,6 +1020,10 @@ int bdrv_commit(BlockDriverState *bs) return -EACCES; } + if (bdrv_in_use(bs) || bdrv_in_use(bs->backing_hd)) { + return -EBUSY; + } + backing_drv = bs->backing_hd->drv; ro = bs->backing_hd->read_only; strncpy(filename, bs->backing_hd->filename, sizeof(filename)); diff --git a/blockdev.c b/blockdev.c index 1f83c88..0499ee6 100644 --- a/blockdev.c +++ b/blockdev.c @@ -592,12 +592,18 @@ void do_commit(Monitor *mon, const QDict *qdict) if (!strcmp(device, "all")) { bdrv_commit_all(); } else { + int ret; + bs = bdrv_find(device); if (!bs) { qerror_report(QERR_DEVICE_NOT_FOUND, device); return; } - bdrv_commit(bs); + ret = bdrv_commit(bs); + if (ret == -EBUSY) { + qerror_report(QERR_DEVICE_IN_USE, device); + return; + } } } @@ -616,6 +622,10 @@ void qmp_blockdev_snapshot_sync(const char *device, const char *snapshot_file, error_set(errp, QERR_DEVICE_NOT_FOUND, device); return; } + if (bdrv_in_use(bs)) { + error_set(errp, QERR_DEVICE_IN_USE, device); + return; + } pstrcpy(old_filename, sizeof(old_filename), bs->filename); @@ -667,6 +677,10 @@ void qmp_blockdev_snapshot_sync(const char *device, const char *snapshot_file, static void eject_device(BlockDriverState *bs, int force, Error **errp) { + if (bdrv_in_use(bs)) { + error_set(errp, QERR_DEVICE_IN_USE, bdrv_get_device_name(bs)); + return; + } if (!bdrv_dev_has_removable_media(bs)) { error_set(errp, QERR_DEVICE_NOT_REMOVABLE, bdrv_get_device_name(bs)); return; -- 1.7.6.5