From nobody Tue Feb 10 08:41:18 2026 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org ARC-Seal: i=1; a=rsa-sha256; t=1601212133; cv=none; d=zohomail.com; s=zohoarc; b=AhtqECuISg+VhH8OgxkSoj8vAquGbIQ5AqbBYg9mjLcMP+F3BbC+uNeYzQHCnPl2fIQuiBT3ZCLRQ3Vf1YVCK0wtQBMK6QvvwcvGGU1KSoftn4AcQL4oPvAQ+Nh6g8xB9w8CpXv6JBfptEqQz0Eo5CbNnapBl1gum0Z/J7t45xk= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1601212133; h=Content-Type:Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To; bh=qXKwxmh8I2zA6RYfD4qN01PDt4WgaWPBDj4wLrb6XuI=; b=BKd2zMapfDTXJEPMJNAd7ccRXN/b3S1qpVfMAuHLVSHa66YmNdIFPUmbaQuN2Y4Cpb8atbD+Y0LwlxAxrk2+fA/GZSM+ZtojYulwQ+PWh42HG0DugWquC6ndMMXpK5SFso83/WZ5mrTWm94OxUmo48xtXtFUX9Mo0svmbqV7tz8= ARC-Authentication-Results: i=1; mx.zohomail.com; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 160121213393645.77582970480921; Sun, 27 Sep 2020 06:08:53 -0700 (PDT) Received: from localhost ([::1]:36460 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1kMWQ8-0004XO-Of for importer@patchew.org; Sun, 27 Sep 2020 09:08:52 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:60872) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1kMWMS-0007qy-U9 for qemu-devel@nongnu.org; Sun, 27 Sep 2020 09:05:04 -0400 Received: from szxga06-in.huawei.com ([45.249.212.32]:60246 helo=huawei.com) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1kMWMQ-0003N2-C2 for qemu-devel@nongnu.org; Sun, 27 Sep 2020 09:05:04 -0400 Received: from DGGEMS402-HUB.china.huawei.com (unknown [172.30.72.58]) by Forcepoint Email with ESMTP id C68EDEBA499277E74A44; Sun, 27 Sep 2020 21:04:48 +0800 (CST) Received: from localhost (10.174.185.104) by DGGEMS402-HUB.china.huawei.com (10.3.19.202) with Microsoft SMTP Server id 14.3.487.0; Sun, 27 Sep 2020 21:04:39 +0800 From: Ying Fang To: Subject: [RFC PATCH 2/7] block-backend: rehandle block aios when EIO Date: Sun, 27 Sep 2020 21:04:15 +0800 Message-ID: <20200927130420.1095-3-fangying1@huawei.com> X-Mailer: git-send-email 2.28.0.windows.1 In-Reply-To: <20200927130420.1095-1-fangying1@huawei.com> References: <20200927130420.1095-1-fangying1@huawei.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Originating-IP: [10.174.185.104] X-CFilter-Loop: Reflected Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=45.249.212.32; envelope-from=fangying1@huawei.com; helo=huawei.com X-detected-operating-system: by eggs.gnu.org: First seen = 2020/09/27 09:04:49 X-ACL-Warn: Detected OS = Linux 3.11 and newer [fuzzy] X-Spam_score_int: -41 X-Spam_score: -4.2 X-Spam_bar: ---- X-Spam_report: (-4.2 / 5.0 requ) BAYES_00=-1.9, RCVD_IN_DNSWL_MED=-2.3, RCVD_IN_MSPIKE_H4=-0.01, RCVD_IN_MSPIKE_WL=-0.01, SPF_HELO_PASS=-0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: kwolf@redhat.com, Ying Fang , Jiahui Cen , zhang.zhanghailiang@huawei.com, mreitz@redhat.com Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" Content-Type: text/plain; charset="utf-8" When a backend device temporarily does not response, like a network disk do= wn due to some network faults, any IO to the coresponding virtual block device in VM would return I/O error. If the hypervisor returns the error to VM, the filesystem on this block device may not work as usual. And in many situatio= ns, the returned error is often an EIO. To avoid this unavailablity, we can store the failed AIOs, and resend them later. If the error is temporary, the retries can succeed and the AIOs can be successfully completed. Signed-off-by: Ying Fang Signed-off-by: Jiahui Cen --- block/block-backend.c | 89 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 89 insertions(+) diff --git a/block/block-backend.c b/block/block-backend.c index bf104a7cf5..90f1ca5753 100644 --- a/block/block-backend.c +++ b/block/block-backend.c @@ -365,6 +365,12 @@ BlockBackend *blk_new(AioContext *ctx, uint64_t perm, = uint64_t shared_perm) notifier_list_init(&blk->remove_bs_notifiers); notifier_list_init(&blk->insert_bs_notifiers); =20 + /* for rehandle */ + blk->reinfo.enable =3D false; + blk->reinfo.ts =3D NULL; + atomic_set(&blk->reinfo.in_flight, 0); + QTAILQ_INIT(&blk->reinfo.re_aios); + QLIST_INIT(&blk->aio_notifiers); =20 QTAILQ_INSERT_TAIL(&block_backends, blk, link); @@ -1425,8 +1431,16 @@ static const AIOCBInfo blk_aio_em_aiocb_info =3D { .get_aio_context =3D blk_aio_em_aiocb_get_aio_context, }; =20 +static void blk_rehandle_timer_cb(void *opaque); +static void blk_rehandle_aio_complete(BlkAioEmAIOCB *acb); + static void blk_aio_complete(BlkAioEmAIOCB *acb) { + if (acb->rwco.blk->reinfo.enable) { + blk_rehandle_aio_complete(acb); + return; + } + if (acb->has_returned) { acb->common.cb(acb->common.opaque, acb->rwco.ret); blk_dec_in_flight(acb->rwco.blk); @@ -1459,6 +1473,7 @@ static BlockAIOCB *blk_aio_prwv(BlockBackend *blk, in= t64_t offset, int bytes, .ret =3D NOT_DONE, }; acb->bytes =3D bytes; + acb->co_entry =3D co_entry; acb->has_returned =3D false; =20 co =3D qemu_coroutine_create(co_entry, acb); @@ -2054,6 +2069,20 @@ static int blk_do_set_aio_context(BlockBackend *blk,= AioContext *new_context, throttle_group_attach_aio_context(tgm, new_context); bdrv_drained_end(bs); } + + if (blk->reinfo.enable) { + if (blk->reinfo.ts) { + timer_del(blk->reinfo.ts); + timer_free(blk->reinfo.ts); + } + blk->reinfo.ts =3D aio_timer_new(new_context, QEMU_CLOCK_REALT= IME, + SCALE_MS, blk_rehandle_timer_cb, + blk); + if (atomic_read(&blk->reinfo.in_flight)) { + timer_mod(blk->reinfo.ts, + qemu_clock_get_ms(QEMU_CLOCK_REALTIME)); + } + } } =20 blk->ctx =3D new_context; @@ -2405,6 +2434,66 @@ static void blk_root_drained_end(BdrvChild *child, i= nt *drained_end_counter) } } =20 +static void blk_rehandle_insert_aiocb(BlockBackend *blk, BlkAioEmAIOCB *ac= b) +{ + assert(blk->reinfo.enable); + + atomic_inc(&blk->reinfo.in_flight); + QTAILQ_INSERT_TAIL(&blk->reinfo.re_aios, acb, list); + timer_mod(blk->reinfo.ts, qemu_clock_get_ms(QEMU_CLOCK_REALTIME) + + blk->reinfo.timer_interval_ms); +} + +static void blk_rehandle_remove_aiocb(BlockBackend *blk, BlkAioEmAIOCB *ac= b) +{ + QTAILQ_REMOVE(&blk->reinfo.re_aios, acb, list); + atomic_dec(&blk->reinfo.in_flight); +} + +static void blk_rehandle_timer_cb(void *opaque) +{ + BlockBackend *blk =3D opaque; + BlockBackendRehandleInfo *reinfo =3D &blk->reinfo; + BlkAioEmAIOCB *acb, *tmp; + Coroutine *co; + + aio_context_acquire(blk_get_aio_context(blk)); + QTAILQ_FOREACH_SAFE(acb, &reinfo->re_aios, list, tmp) { + if (acb->rwco.ret =3D=3D NOT_DONE) { + continue; + } + + blk_inc_in_flight(acb->rwco.blk); + acb->rwco.ret =3D NOT_DONE; + acb->has_returned =3D false; + + co =3D qemu_coroutine_create(acb->co_entry, acb); + bdrv_coroutine_enter(blk_bs(blk), co); + + acb->has_returned =3D true; + if (acb->rwco.ret !=3D NOT_DONE) { + blk_rehandle_remove_aiocb(acb->rwco.blk, acb); + replay_bh_schedule_oneshot_event(blk_get_aio_context(blk), + blk_aio_complete_bh, acb); + } + } + aio_context_release(blk_get_aio_context(blk)); +} + +static void blk_rehandle_aio_complete(BlkAioEmAIOCB *acb) +{ + if (acb->has_returned) { + blk_dec_in_flight(acb->rwco.blk); + if (acb->rwco.ret =3D=3D -EIO) { + blk_rehandle_insert_aiocb(acb->rwco.blk, acb); + return; + } + + acb->common.cb(acb->common.opaque, acb->rwco.ret); + qemu_aio_unref(acb); + } +} + void blk_register_buf(BlockBackend *blk, void *host, size_t size) { bdrv_register_buf(blk_bs(blk), host, size); --=20 2.23.0