From patchwork Tue May 31 09:15:21 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: "Denis V. Lunev" X-Patchwork-Id: 9144003 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 835C560777 for ; Tue, 31 May 2016 09:18:07 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 7575C2793B for ; Tue, 31 May 2016 09:18:07 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 6A0F228185; Tue, 31 May 2016 09:18:07 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-6.9 required=2.0 tests=BAYES_00,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 4EAE02793B for ; Tue, 31 May 2016 09:18:05 +0000 (UTC) Received: from localhost ([::1]:35351 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1b7foK-0007SN-Dn for patchwork-qemu-devel@patchwork.kernel.org; Tue, 31 May 2016 05:18:04 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:38252) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1b7fmE-0006ER-CS for qemu-devel@nongnu.org; Tue, 31 May 2016 05:15:55 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1b7fm9-0005VC-Kl for qemu-devel@nongnu.org; Tue, 31 May 2016 05:15:54 -0400 Received: from mailhub.sw.ru ([195.214.232.25]:22278 helo=relay.sw.ru) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1b7fm9-0005V4-74 for qemu-devel@nongnu.org; Tue, 31 May 2016 05:15:49 -0400 Received: from irbis.sw.ru ([10.30.2.139]) by relay.sw.ru (8.13.4/8.13.4) with ESMTP id u4V9FUaI003235; Tue, 31 May 2016 12:15:35 +0300 (MSK) From: "Denis V. Lunev" To: qemu-devel@nongnu.org Date: Tue, 31 May 2016 12:15:21 +0300 Message-Id: <1464686130-12265-3-git-send-email-den@openvz.org> X-Mailer: git-send-email 2.1.4 In-Reply-To: <1464686130-12265-1-git-send-email-den@openvz.org> References: <1464686130-12265-1-git-send-email-den@openvz.org> X-detected-operating-system: by eggs.gnu.org: OpenBSD 3.x X-Received-From: 195.214.232.25 Subject: [Qemu-devel] [PATCH 02/11] block/io: add bdrv_co_write_compressed X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Kevin Wolf , Pavel Butsykin , Jeff Cody , Markus Armbruster , Stefan Hajnoczi , den@openvz.org, John Snow Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP From: Pavel Butsykin This patch just adds the interface to the bdrv_co_pwritev_compressed, which is currently not used but will be useful for safe implementation of the bdrv_co_write_compressed callback in format drivers. Signed-off-by: Pavel Butsykin Signed-off-by: Denis V. Lunev CC: Jeff Cody CC: Markus Armbruster CC: Eric Blake CC: John Snow CC: Stefan Hajnoczi CC: Kevin Wolf Reviewed-by: Stefan Hajnoczi --- block/io.c | 78 +++++++++++++++++++++++++++++++++++++++++++---- include/block/block_int.h | 5 +++ qemu-img.c | 2 +- 3 files changed, 78 insertions(+), 7 deletions(-) diff --git a/block/io.c b/block/io.c index c5bb6ae..54cd9a4 100644 --- a/block/io.c +++ b/block/io.c @@ -1779,8 +1779,8 @@ int bdrv_is_allocated_above(BlockDriverState *top, return 0; } -int bdrv_pwrite_compressed(BlockDriverState *bs, int64_t offset, - const void *buf, int count) +int coroutine_fn bdrv_co_pwritev_compressed(BlockDriverState *bs, + int64_t offset, unsigned int bytes, QEMUIOVector *qiov) { BlockDriver *drv = bs->drv; int ret; @@ -1788,18 +1788,84 @@ int bdrv_pwrite_compressed(BlockDriverState *bs, int64_t offset, if (!drv) { return -ENOMEDIUM; } - if (!drv->bdrv_write_compressed) { + + if (!drv->bdrv_co_write_compressed) { return -ENOTSUP; } - ret = bdrv_check_byte_request(bs, offset, count); + + ret = bdrv_check_byte_request(bs, offset, bytes); if (ret < 0) { return ret; } assert(QLIST_EMPTY(&bs->dirty_bitmaps)); + assert(qemu_in_coroutine()); + + return drv->bdrv_co_write_compressed(bs, offset >> BDRV_SECTOR_BITS, + bytes >> BDRV_SECTOR_BITS, qiov); +} + +typedef struct BdrvWriteCompressedCo { + BlockDriverState *bs; + int64_t offset; + QEMUIOVector *qiov; + int ret; +} BdrvWriteCompressedCo; + +static void bdrv_write_compressed_co_entry(void *opaque) +{ + BdrvWriteCompressedCo *co = opaque; + + co->ret = bdrv_co_pwritev_compressed(co->bs, co->offset, co->qiov->size, + co->qiov); +} + +int bdrv_pwrite_compressed(BlockDriverState *bs, int64_t offset, + const void *buf, int count) +{ + BdrvWriteCompressedCo data; + QEMUIOVector qiov; + BlockDriver *drv = bs->drv; + struct iovec iov = { + .iov_base = (void *)buf, + .iov_len = count, + }; + qemu_iovec_init_external(&qiov, &iov, 1); - return drv->bdrv_write_compressed(bs, offset >> BDRV_SECTOR_BITS, buf, - count >> BDRV_SECTOR_BITS); + data = (BdrvWriteCompressedCo) { + .bs = bs, + .offset = offset, + .qiov = &qiov, + .ret = -EINPROGRESS, + }; + + if (!drv) { + return -ENOMEDIUM; + } + + if (drv->bdrv_write_compressed) { + int ret = bdrv_check_byte_request(bs, offset, count); + if (ret < 0) { + return ret; + } + assert(QLIST_EMPTY(&bs->dirty_bitmaps)); + return drv->bdrv_write_compressed(bs, offset >> BDRV_SECTOR_BITS, buf, + count >> BDRV_SECTOR_BITS); + } + + if (qemu_in_coroutine()) { + /* Fast-path if already in coroutine context */ + bdrv_write_compressed_co_entry(&data); + } else { + AioContext *aio_context = bdrv_get_aio_context(bs); + + Coroutine *co = qemu_coroutine_create(bdrv_write_compressed_co_entry); + qemu_coroutine_enter(co, &data); + while (data.ret == -EINPROGRESS) { + aio_poll(aio_context, true); + } + } + return data.ret; } int bdrv_save_vmstate(BlockDriverState *bs, const uint8_t *buf, diff --git a/include/block/block_int.h b/include/block/block_int.h index 30a9717..ccba9c9 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -207,6 +207,9 @@ struct BlockDriver { int (*bdrv_write_compressed)(BlockDriverState *bs, int64_t sector_num, const uint8_t *buf, int nb_sectors); + int coroutine_fn (*bdrv_co_write_compressed)(BlockDriverState *bs, + int64_t sector_num, int nb_sectors, QEMUIOVector *qiov); + int (*bdrv_snapshot_create)(BlockDriverState *bs, QEMUSnapshotInfo *sn_info); int (*bdrv_snapshot_goto)(BlockDriverState *bs, @@ -535,6 +538,8 @@ int coroutine_fn bdrv_co_preadv(BlockDriverState *bs, int coroutine_fn bdrv_co_pwritev(BlockDriverState *bs, int64_t offset, unsigned int bytes, QEMUIOVector *qiov, BdrvRequestFlags flags); +int coroutine_fn bdrv_co_pwritev_compressed(BlockDriverState *bs, + int64_t offset, unsigned int bytes, QEMUIOVector *qiov); int get_tmp_filename(char *filename, int size); BlockDriver *bdrv_probe_all(const uint8_t *buf, int buf_size, diff --git a/qemu-img.c b/qemu-img.c index eb744d4..ab54027 100644 --- a/qemu-img.c +++ b/qemu-img.c @@ -2024,7 +2024,7 @@ static int img_convert(int argc, char **argv) const char *preallocation = qemu_opt_get(opts, BLOCK_OPT_PREALLOC); - if (!drv->bdrv_write_compressed) { + if (!drv->bdrv_write_compressed && !drv->bdrv_co_write_compressed) { error_report("Compression not supported for this file format"); ret = -1; goto out;