From nobody Fri May 17 09:18:36 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail; 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=1612825018; cv=none; d=zohomail.com; s=zohoarc; b=EUcokKjJL0PGcPO3byjnffsqNduTIZYbzPl4sq8jDjA1a/SRKrVerFZuWDwHbReoMxuQdKoTYI5t0d9iIN6k/n+84O0ZUpS61H7xM2yhh0Af7abt0zAT5DSo2tCcFlYMuscAj5vWdXAvDUwh8fgKzjuBSvULcSCPcoJxuaJBdMQ= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1612825018; h=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=p5B7Hkc3AVjgiYD1v6iU+Yfxd/Ff2ptADNYOAKMq9Sg=; b=ZJIjncFFE3NsXEr66r6eYIQC2dSUgfLhH80BJBizn6mMFZanGJZEHxE4CDat0D4hhRru7HFCRgrPUhFTgqjkjMtErBP++kvcBOdpWwqUwN8XOLiNKFbI73drWRztXX9LvqYKo+J/F8z4oR5mSa6eA0B1R9+OSg2r4VhSOF9HV08= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=fail; 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 1612825016940982.1979923744154; Mon, 8 Feb 2021 14:56:56 -0800 (PST) Received: from localhost ([::1]:33004 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1l9FSh-00083L-M9 for importer@patchew.org; Mon, 08 Feb 2021 17:56:55 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]:56938) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1l9BXW-0008HB-LZ; Mon, 08 Feb 2021 13:45:38 -0500 Received: from fanzine.igalia.com ([178.60.130.6]:46558) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1l9BXN-0006o3-AN; Mon, 08 Feb 2021 13:45:38 -0500 Received: from [213.94.25.37] (helo=perseus.local) by fanzine.igalia.com with esmtpsa (Cipher TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim) id 1l9BWw-000566-H5; Mon, 08 Feb 2021 19:45:02 +0100 Received: from berto by perseus.local with local (Exim 4.92) (envelope-from ) id 1l9BWj-000081-KQ; Mon, 08 Feb 2021 19:44:49 +0100 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=igalia.com; s=20170329; h=Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-Id:Date:Subject:Cc:To:From; bh=p5B7Hkc3AVjgiYD1v6iU+Yfxd/Ff2ptADNYOAKMq9Sg=; b=LN5BD2/hl/Q9wmHRm887lqbaBbPZrQBP9Xw2b6XC7byEqUpG62wOxjVL8xg4Tz/vJXJMGbD8WYUaJ0DQ2MefZ/GubIS6IAT2fgVyAogDZbQ/z3243KJ4o9izYW0FNPtfW/WqO3pQQ0KWZGLsVQva2bPs7Ir5ufHpaLcQvlBhK/SQN8ubTDPZWls8z8cuf6R36Ag6AzReZ313NhwASGHddxT0YPXX512FyXO7gp6tx89NTgdd/G7eHXpq0V3BwYQdy14hPSllqMVbkdnEgz4whtMZTuIFYpkxtoskXsVo5Hxkra0KnO7zMmFKSDPRrp0Dvz2rfkxEd44T8ywUyHWDfw==; From: Alberto Garcia To: qemu-devel@nongnu.org Subject: [RFC PATCH v2 1/4] block: Allow changing bs->file on reopen Date: Mon, 8 Feb 2021 19:44:41 +0100 Message-Id: <670613fb7829ae2bf1329fca2e13bd51bd357024.1612809837.git.berto@igalia.com> X-Mailer: git-send-email 2.20.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable 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=178.60.130.6; envelope-from=berto@igalia.com; helo=fanzine.igalia.com X-Spam_score_int: -20 X-Spam_score: -2.1 X-Spam_bar: -- X-Spam_report: (-2.1 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, SPF_HELO_NONE=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: Kevin Wolf , Vladimir Sementsov-Ogievskiy , Alberto Garcia , qemu-block@nongnu.org, Max Reitz Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) Content-Type: text/plain; charset="utf-8" When the x-blockdev-reopen was added it allowed reconfiguring the graph by replacing backing files, but changing the 'file' option was forbidden. Because of this restriction some operations are not possible, notably inserting and removing block filters. This patch adds support for replacing the 'file' option. This is similar to replacing the backing file and the user is likewise responsible for the correctness of the resulting graph, otherwise this can lead to data corruption. Signed-off-by: Alberto Garcia --- include/block/block.h | 1 + block.c | 65 ++++++++++++++++++++++++++++++++++++++++++ tests/qemu-iotests/245 | 7 +++-- 3 files changed, 70 insertions(+), 3 deletions(-) diff --git a/include/block/block.h b/include/block/block.h index 82271d9ccd..6dd687a69e 100644 --- a/include/block/block.h +++ b/include/block/block.h @@ -196,6 +196,7 @@ typedef struct BDRVReopenState { bool backing_missing; bool replace_backing_bs; /* new_backing_bs is ignored if this is fals= e */ BlockDriverState *old_backing_bs; /* keep pointer for permissions upda= te */ + BlockDriverState *old_file_bs; /* keep pointer for permissions upda= te */ uint64_t perm, shared_perm; QDict *options; QDict *explicit_options; diff --git a/block.c b/block.c index 576b145cbf..19b62da4af 100644 --- a/block.c +++ b/block.c @@ -3978,6 +3978,10 @@ int bdrv_reopen_multiple(BlockReopenQueue *bs_queue,= Error **errp) refresh_list =3D bdrv_topological_dfs(refresh_list, found, state->old_backing_bs); } + if (state->old_file_bs) { + refresh_list =3D bdrv_topological_dfs(refresh_list, found, + state->old_file_bs); + } } =20 ret =3D bdrv_list_refresh_perms(refresh_list, bs_queue, &tran, errp); @@ -4196,6 +4200,61 @@ static int bdrv_reopen_parse_backing(BDRVReopenState= *reopen_state, return 0; } =20 +static int bdrv_reopen_parse_file(BDRVReopenState *reopen_state, + GSList **tran, + Error **errp) +{ + BlockDriverState *bs =3D reopen_state->bs; + BlockDriverState *new_file_bs; + QObject *value; + const char *str; + + value =3D qdict_get(reopen_state->options, "file"); + if (value =3D=3D NULL) { + return 0; + } + + /* The 'file' option only allows strings */ + assert(qobject_type(value) =3D=3D QTYPE_QSTRING); + + str =3D qobject_get_try_str(value); + new_file_bs =3D bdrv_lookup_bs(NULL, str, errp); + if (new_file_bs =3D=3D NULL) { + return -EINVAL; + } else if (bdrv_recurse_has_child(new_file_bs, bs)) { + error_setg(errp, "Making '%s' a file of '%s' " + "would create a cycle", str, bs->node_name); + return -EINVAL; + } + + assert(bs->file && bs->file->bs); + + /* If 'file' points to the current child then there's nothing to do */ + if (bs->file->bs =3D=3D new_file_bs) { + return 0; + } + + if (bs->file->frozen) { + error_setg(errp, "Cannot change the 'file' link of '%s' " + "from '%s' to '%s'", bs->node_name, + bs->file->bs->node_name, new_file_bs->node_name); + return -EPERM; + } + + /* Check AioContext compatibility */ + if (!bdrv_reopen_can_attach(bs, bs->file, new_file_bs, errp)) { + return -EINVAL; + } + + /* Store the old file bs because we'll need to refresh its permissions= */ + reopen_state->old_file_bs =3D bs->file->bs; + + /* And finally replace the child */ + bdrv_replace_child(bs->file, new_file_bs, tran); + + return 0; +} + /* * Prepares a BlockDriverState for reopen. All changes are staged in the * 'opaque' field of the BDRVReopenState, which is used and allocated by @@ -4347,6 +4406,12 @@ static int bdrv_reopen_prepare(BDRVReopenState *reop= en_state, } qdict_del(reopen_state->options, "backing"); =20 + ret =3D bdrv_reopen_parse_file(reopen_state, set_backings_tran, errp); + if (ret < 0) { + goto error; + } + qdict_del(reopen_state->options, "file"); + /* Options that are not handled are only okay if they are unchanged * compared to the old state. It is expected that some options are only * used for the initial open, but not reopen (e.g. filename) */ diff --git a/tests/qemu-iotests/245 b/tests/qemu-iotests/245 index e60c8326d3..f9d68b3958 100755 --- a/tests/qemu-iotests/245 +++ b/tests/qemu-iotests/245 @@ -145,8 +145,8 @@ class TestBlockdevReopen(iotests.QMPTestCase): self.reopen(opts, {'driver': 'raw'}, "Cannot change the option 'dr= iver'") self.reopen(opts, {'driver': ''}, "Invalid parameter ''") self.reopen(opts, {'driver': None}, "Invalid parameter type for 'd= river', expected: string") - self.reopen(opts, {'file': 'not-found'}, "Cannot change the option= 'file'") - self.reopen(opts, {'file': ''}, "Cannot change the option 'file'") + self.reopen(opts, {'file': 'not-found'}, "Cannot find device=3D no= r node_name=3Dnot-found") + self.reopen(opts, {'file': ''}, "Cannot find device=3D nor node_na= me=3D") self.reopen(opts, {'file': None}, "Invalid parameter type for 'fil= e', expected: BlockdevRef") self.reopen(opts, {'file.node-name': 'newname'}, "Cannot change th= e option 'node-name'") self.reopen(opts, {'file.driver': 'host_device'}, "Cannot change t= he option 'driver'") @@ -454,7 +454,8 @@ class TestBlockdevReopen(iotests.QMPTestCase): # More illegal operations self.reopen(opts[2], {'backing': 'hd1'}, "Making 'hd1' a backing file of 'hd2' would create a c= ycle") - self.reopen(opts[2], {'file': 'hd0-file'}, "Cannot change the opti= on 'file'") + self.reopen(opts[2], {'file': 'hd0-file'}, + "Conflicts with use by hd2 as 'file', which does not a= llow 'write, resize' on hd0-file") =20 result =3D self.vm.qmp('blockdev-del', conv_keys =3D True, node_na= me =3D 'hd2') self.assert_qmp(result, 'error/class', 'GenericError') --=20 2.20.1 From nobody Fri May 17 09:18:36 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail; 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=1612825128; cv=none; d=zohomail.com; s=zohoarc; b=SmedN+QLzqfrrdZmXb0nZ45sVg01uIrxuPnEavkoJaL/eiqgbvFfajtZ4Y6aE2DmgQFoYkySm5aFG1d2OEr5exdGuc6q8IH0q7ANCrMS2Xw+JaJ1Y0U4JGnH9RI6CyixsQe/54P5TSKZ4UZxnkTjraR7OOL4D6uCDuo1Wfrq/kE= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1612825128; h=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=D/3jKyHLwJmlaYsfs930G7WJY9pPcoP2AfxzDeDVO/w=; b=CfPqYq8oMcBiQQ46Yvim4z5sUjDsxGzicSnhhtowc18lZ7o9SfeRrdLJRnCbw+1K7vIQduQU5AMdelI5Gjh/25TokkC1oHmQl9FwXVJHWW83NKci4fCMBMP77ddgt8NZDtDh4mEQ588uACDWzX+PJrOQwaCScD2tzcUMUk1pvIM= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=fail; 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 1612825128596144.75438706822706; Mon, 8 Feb 2021 14:58:48 -0800 (PST) Received: from localhost ([::1]:42302 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1l9FUV-0003Ls-Dc for importer@patchew.org; Mon, 08 Feb 2021 17:58:47 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]:56982) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1l9BXX-0008Jp-Ti; Mon, 08 Feb 2021 13:45:39 -0500 Received: from fanzine.igalia.com ([178.60.130.6]:46561) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1l9BXN-0006o7-Ko; Mon, 08 Feb 2021 13:45:39 -0500 Received: from [213.94.25.37] (helo=perseus.local) by fanzine.igalia.com with esmtpsa (Cipher TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim) id 1l9BWw-000568-LL; Mon, 08 Feb 2021 19:45:02 +0100 Received: from berto by perseus.local with local (Exim 4.92) (envelope-from ) id 1l9BWj-000083-LF; Mon, 08 Feb 2021 19:44:49 +0100 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=igalia.com; s=20170329; h=Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-Id:Date:Subject:Cc:To:From; bh=D/3jKyHLwJmlaYsfs930G7WJY9pPcoP2AfxzDeDVO/w=; b=LQNZEzkcy6TRN12NQY1p3m0fWYiKmUXthPJ0Dsm3xrPiUlyMY9/gauoTIHlUs1VSbbCpRxZxz12X+hz12u7SEKDcmhnk3XQeuZXcsuW43X/OLPryWPCP8X1BAX8AGbB2Jpx9cocS6AVaU+Qc0QROs9sEaoU28DYDT0VI7glUGmlTtypyUJ0nwfJJj38s/dkYAbovlArRsqTcDmbwlzE1a4HKen/qf5O52qDEc4TBn1p7At/OhWJ1ZaZu+q18ALffyrcVP+I/GIinPwzVv1xSDLZM8ZzjMayAmRxjsNB7Yxeriwzs3gwomutWkeNvJ/yvd6OAwqX0GtDUWAvetIIpAg==; From: Alberto Garcia To: qemu-devel@nongnu.org Subject: [RFC PATCH v2 2/4] iotests: Update 245 to support replacing files with x-blockdev-reopen Date: Mon, 8 Feb 2021 19:44:42 +0100 Message-Id: <74cbe313dce107f6100751f1c42296769f05a7ef.1612809837.git.berto@igalia.com> X-Mailer: git-send-email 2.20.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable 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=178.60.130.6; envelope-from=berto@igalia.com; helo=fanzine.igalia.com X-Spam_score_int: -20 X-Spam_score: -2.1 X-Spam_bar: -- X-Spam_report: (-2.1 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, SPF_HELO_NONE=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: Kevin Wolf , Vladimir Sementsov-Ogievskiy , Alberto Garcia , qemu-block@nongnu.org, Max Reitz Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) Content-Type: text/plain; charset="utf-8" Signed-off-by: Alberto Garcia --- tests/qemu-iotests/245 | 54 +++++++++++++++++++++++++++++++++++++- tests/qemu-iotests/245.out | 4 +-- 2 files changed, 55 insertions(+), 3 deletions(-) diff --git a/tests/qemu-iotests/245 b/tests/qemu-iotests/245 index f9d68b3958..bad6911f0c 100755 --- a/tests/qemu-iotests/245 +++ b/tests/qemu-iotests/245 @@ -78,7 +78,7 @@ class TestBlockdevReopen(iotests.QMPTestCase): for line in log.split("\n"): if line.startswith("Pattern verification failed"): raise Exception("%s (command #%d)" % (line, found)) - if re.match("read .*/.* bytes at offset", line): + if re.match("(read|wrote) .*/.* bytes at offset", line): found +=3D 1 self.assertEqual(found, self.total_io_cmds, "Expected output of %d qemu-io commands, found %d= " % @@ -536,6 +536,58 @@ class TestBlockdevReopen(iotests.QMPTestCase): result =3D self.vm.qmp('blockdev-del', conv_keys =3D True, node_na= me =3D 'bv') self.assert_qmp(result, 'return', {}) =20 + def test_replace_file(self): + qemu_img('create', '-f', 'raw', hd_path[0], '10k') + qemu_img('create', '-f', 'raw', hd_path[1], '10k') + + hd0_opts =3D {'driver': 'file', + 'node-name': 'hd0-file', + 'filename': hd_path[0] } + hd1_opts =3D {'driver': 'file', + 'node-name': 'hd1-file', + 'filename': hd_path[1] } + + opts =3D {'driver': 'raw', 'node-name': 'hd', 'file': 'hd0-file'} + + result =3D self.vm.qmp('blockdev-add', conv_keys =3D False, **hd0_= opts) + self.assert_qmp(result, 'return', {}) + result =3D self.vm.qmp('blockdev-add', conv_keys =3D False, **hd1_= opts) + self.assert_qmp(result, 'return', {}) + result =3D self.vm.qmp('blockdev-add', conv_keys =3D False, **opts) + self.assert_qmp(result, 'return', {}) + + self.run_qemu_io("hd", "read -P 0 0 10k") + self.run_qemu_io("hd", "write -P 0xa0 0 10k") + + self.reopen(opts, {'file': 'hd1-file'}) + self.run_qemu_io("hd", "read -P 0 0 10k") + self.run_qemu_io("hd", "write -P 0xa1 0 10k") + + self.reopen(opts, {'file': 'hd0-file'}) + self.run_qemu_io("hd", "read -P 0xa0 0 10k") + + self.reopen(opts, {'file': 'hd1-file'}) + self.run_qemu_io("hd", "read -P 0xa1 0 10k") + + def test_insert_throttle_filter(self): + hd0_opts =3D hd_opts(0) + result =3D self.vm.qmp('blockdev-add', conv_keys =3D False, **hd0_= opts) + self.assert_qmp(result, 'return', {}) + + opts =3D { 'qom-type': 'throttle-group', 'id': 'group0', + 'props': { 'limits': { 'iops-total': 1000 } } } + result =3D self.vm.qmp('object-add', conv_keys =3D False, **opts) + self.assert_qmp(result, 'return', {}) + + opts =3D { 'driver': 'throttle', 'node-name': 'throttle0', + 'throttle-group': 'group0', 'file': 'hd0-file' } + result =3D self.vm.qmp('blockdev-add', conv_keys =3D False, **opts) + self.assert_qmp(result, 'return', {}) + + self.reopen(hd0_opts, {'file': 'throttle0'}) + + self.reopen(hd0_opts, {'file': 'hd0-file'}) + # Misc reopen tests with different block drivers @iotests.skip_if_unsupported(['quorum', 'throttle']) def test_misc_drivers(self): diff --git a/tests/qemu-iotests/245.out b/tests/qemu-iotests/245.out index 4b33dcaf5c..537a2b5b63 100644 --- a/tests/qemu-iotests/245.out +++ b/tests/qemu-iotests/245.out @@ -10,8 +10,8 @@ {"return": {}} {"data": {"id": "stream0", "type": "stream"}, "event": "BLOCK_JOB_PENDING"= , "timestamp": {"microseconds": "USECS", "seconds": "SECS"}} {"data": {"device": "stream0", "len": 3145728, "offset": 3145728, "speed":= 0, "type": "stream"}, "event": "BLOCK_JOB_COMPLETED", "timestamp": {"micro= seconds": "USECS", "seconds": "SECS"}} -..................... +....................... ---------------------------------------------------------------------- -Ran 21 tests +Ran 23 tests =20 OK --=20 2.20.1 From nobody Fri May 17 09:18:36 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail; 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=1612827892; cv=none; d=zohomail.com; s=zohoarc; b=C472vCJEHuOhrWYbHGf/J2UvgF1ft6xJmS5FqlmwJoE3equZbdFccWdvLR2/7nZwxLt2axu2nE1dKSvCZ8k+C39BYGgnStce38vqJtQOO7g/Dz2hNutnlpU4c32vlhdB8wWLPJRf8Gc7EHm2rKuvoNmoLu8X/cEA99bSQJc2/vw= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1612827892; h=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=7nFfZtvBeovHn4Wwh0jyWvZcZK3kI4SIwbW+mBSArbA=; b=YTOGqelqkTvZWVfTnIrhQzUH8Uqn8gsa2XQp7ARznq0ZmSk653NGCAtWH1IZPLItxwC4shL0PZez1zSaNWCYDMO4yCAzUFqa2iw5vSUdMEbm7bLLUzZee7XiF2wvqlcaSfU86A16/LKmj31gBRkSwEqDOZjE02RFgjYdPv8N8CY= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=fail; 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 1612827892955102.37764865302006; Mon, 8 Feb 2021 15:44:52 -0800 (PST) Received: from localhost ([::1]:39168 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1l9GD5-0002ub-TZ for importer@patchew.org; Mon, 08 Feb 2021 18:44:51 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]:56998) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1l9BXY-0008LL-OU; Mon, 08 Feb 2021 13:45:40 -0500 Received: from fanzine.igalia.com ([178.60.130.6]:46564) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1l9BXN-0006o5-KC; Mon, 08 Feb 2021 13:45:40 -0500 Received: from [213.94.25.37] (helo=perseus.local) by fanzine.igalia.com with esmtpsa (Cipher TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim) id 1l9BWw-000569-Ll; Mon, 08 Feb 2021 19:45:02 +0100 Received: from berto by perseus.local with local (Exim 4.92) (envelope-from ) id 1l9BWj-000085-MV; Mon, 08 Feb 2021 19:44:49 +0100 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=igalia.com; s=20170329; h=Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-Id:Date:Subject:Cc:To:From; bh=7nFfZtvBeovHn4Wwh0jyWvZcZK3kI4SIwbW+mBSArbA=; b=U4ANeCsJqdI3sT5utwgzqr/YHw/p2jru65ghQUHViuGaq/WanmdoHCpP3TUvtTgSGDod/ayvSy6Lkso9kZWB+d6CDLK6Vy0SQbuvOhznohzsQ0w1FAh62FwWvKxoSNP8LggMZAcUQPgMJOd4uWoAaKVBIQ7FC4DU0XFnjAxyc+WTT9AhMWODzrWeAeLpKmazcfboDwMcFUlfWKL5sDeczIjQ4EAEeeJZqQ2if5Sr8GdeGSS1mHZwZsw+OusY9Ix0qJBbfRWo6TN/ReVU++BrQOdt4rjjNPzABymRqcSsJIAw+G9itDAhmnovSa3gPMmq4VUTntYA0sYCZPYRagpAbQ==; From: Alberto Garcia To: qemu-devel@nongnu.org Subject: [RFC PATCH v2 3/4] block: Support multiple reopening with x-blockdev-reopen Date: Mon, 8 Feb 2021 19:44:43 +0100 Message-Id: <145882bca942bb629bce2b1f5546fe0946ccdfcd.1612809837.git.berto@igalia.com> X-Mailer: git-send-email 2.20.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable 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=178.60.130.6; envelope-from=berto@igalia.com; helo=fanzine.igalia.com X-Spam_score_int: -20 X-Spam_score: -2.1 X-Spam_bar: -- X-Spam_report: (-2.1 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, SPF_HELO_NONE=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: Kevin Wolf , Vladimir Sementsov-Ogievskiy , Alberto Garcia , qemu-block@nongnu.org, Max Reitz Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) Content-Type: text/plain; charset="utf-8" Signed-off-by: Alberto Garcia --- qapi/block-core.json | 2 +- include/block/block.h | 1 + block.c | 16 +++++-- blockdev.c | 85 +++++++++++++++++++++----------------- tests/qemu-iotests/155 | 9 ++-- tests/qemu-iotests/165 | 4 +- tests/qemu-iotests/245 | 27 +++++++----- tests/qemu-iotests/248 | 2 +- tests/qemu-iotests/248.out | 2 +- tests/qemu-iotests/298 | 4 +- 10 files changed, 89 insertions(+), 63 deletions(-) diff --git a/qapi/block-core.json b/qapi/block-core.json index c0e7c23331..b9fcf20a81 100644 --- a/qapi/block-core.json +++ b/qapi/block-core.json @@ -4177,7 +4177,7 @@ # Since: 4.0 ## { 'command': 'x-blockdev-reopen', - 'data': 'BlockdevOptions', 'boxed': true } + 'data': { 'options': ['BlockdevOptions'] } } =20 ## # @blockdev-del: diff --git a/include/block/block.h b/include/block/block.h index 6dd687a69e..fe4a220da9 100644 --- a/include/block/block.h +++ b/include/block/block.h @@ -372,6 +372,7 @@ BlockDriverState *bdrv_new_open_driver(BlockDriver *drv= , const char *node_name, BlockReopenQueue *bdrv_reopen_queue(BlockReopenQueue *bs_queue, BlockDriverState *bs, QDict *options, bool keep_old_opts); +void bdrv_reopen_queue_free(BlockReopenQueue *bs_queue); int bdrv_reopen_multiple(BlockReopenQueue *bs_queue, Error **errp); int bdrv_reopen_set_read_only(BlockDriverState *bs, bool read_only, Error **errp); diff --git a/block.c b/block.c index 19b62da4af..b4fef2308f 100644 --- a/block.c +++ b/block.c @@ -3933,6 +3933,17 @@ BlockReopenQueue *bdrv_reopen_queue(BlockReopenQueue= *bs_queue, NULL, 0, keep_old_opts); } =20 +void bdrv_reopen_queue_free(BlockReopenQueue *bs_queue) +{ + if (bs_queue) { + BlockReopenQueueEntry *bs_entry, *next; + QTAILQ_FOREACH_SAFE(bs_entry, bs_queue, entry, next) { + g_free(bs_entry); + } + g_free(bs_queue); + } +} + /* * Reopen multiple BlockDriverStates atomically & transactionally. * @@ -4024,10 +4035,7 @@ abort: } =20 cleanup: - QTAILQ_FOREACH_SAFE(bs_entry, bs_queue, entry, next) { - g_free(bs_entry); - } - g_free(bs_queue); + bdrv_reopen_queue_free(bs_queue); =20 return ret; } diff --git a/blockdev.c b/blockdev.c index 098a05709d..6b688c0f73 100644 --- a/blockdev.c +++ b/blockdev.c @@ -3528,38 +3528,16 @@ fail: visit_free(v); } =20 -void qmp_x_blockdev_reopen(BlockdevOptions *options, Error **errp) +void qmp_x_blockdev_reopen(BlockdevOptionsList *reopen_list, Error **errp) { - BlockDriverState *bs; - QObject *obj; - Visitor *v =3D qobject_output_visitor_new(&obj); - BlockReopenQueue *queue; - QDict *qdict; - - /* Check for the selected node name */ - if (!options->has_node_name) { - error_setg(errp, "Node name not specified"); - goto fail; - } - - bs =3D bdrv_find_node(options->node_name); - if (!bs) { - error_setg(errp, "Cannot find node named '%s'", options->node_name= ); - goto fail; - } - - /* Put all options in a QDict and flatten it */ - visit_type_BlockdevOptions(v, NULL, &options, &error_abort); - visit_complete(v, &obj); - qdict =3D qobject_to(QDict, obj); - - qdict_flatten(qdict); - - /* Perform the reopen operation */ + BlockReopenQueue *queue =3D NULL; + GSList *aio_ctxs =3D NULL; + GSList *visitors =3D NULL; + GSList *drained =3D NULL; BdrvNextIterator it; - GSList *aio_ctxs =3D NULL, *ctx; BlockDriverState *it_bs; =20 + /* Acquire all AIO contexts */ for (it_bs =3D bdrv_first(&it); it_bs; it_bs =3D bdrv_next(&it)) { AioContext *aio_context =3D bdrv_get_aio_context(it_bs); =20 @@ -3569,19 +3547,50 @@ void qmp_x_blockdev_reopen(BlockdevOptions *options= , Error **errp) } } =20 - bdrv_subtree_drained_begin(bs); - queue =3D bdrv_reopen_queue(NULL, bs, qdict, false); + /* Add each one of the BDS that we want to reopen to the queue */ + for (; reopen_list !=3D NULL; reopen_list =3D reopen_list->next) { + BlockdevOptions *options =3D reopen_list->value; + QDict *qdict; + Visitor *v; + BlockDriverState *bs; + QObject *obj; + + /* Check for the selected node name */ + if (!options->has_node_name) { + error_setg(errp, "Node name not specified"); + goto fail; + } + + bs =3D bdrv_find_node(options->node_name); + if (!bs) { + error_setg(errp, "Cannot find node named '%s'", options->node_= name); + goto fail; + } + + v =3D qobject_output_visitor_new(&obj); + visitors =3D g_slist_prepend(visitors, v); + + /* Put all options in a QDict and flatten it */ + visit_type_BlockdevOptions(v, NULL, &options, &error_abort); + visit_complete(v, &obj); + qdict =3D qobject_to(QDict, obj); + + qdict_flatten(qdict); + + bdrv_subtree_drained_begin(bs); + queue =3D bdrv_reopen_queue(queue, bs, qdict, false); + drained =3D g_slist_prepend(drained, bs); + } + + /* Perform the reopen operation */ bdrv_reopen_multiple(queue, errp); - bdrv_subtree_drained_end(bs); - - for (ctx =3D aio_ctxs; ctx !=3D NULL; ctx =3D ctx->next) { - AioContext *aio_context =3D ctx->data; - aio_context_release(aio_context); - } - g_slist_free(aio_ctxs); + queue =3D NULL; =20 fail: - visit_free(v); + bdrv_reopen_queue_free(queue); + g_slist_free_full(drained, (GDestroyNotify) bdrv_subtree_drained_end); + g_slist_free_full(aio_ctxs, (GDestroyNotify) aio_context_release); + g_slist_free_full(visitors, (GDestroyNotify) visit_free); } =20 void qmp_blockdev_del(const char *node_name, Error **errp) diff --git a/tests/qemu-iotests/155 b/tests/qemu-iotests/155 index 988f986144..5271f9541f 100755 --- a/tests/qemu-iotests/155 +++ b/tests/qemu-iotests/155 @@ -260,9 +260,12 @@ class TestBlockdevMirrorReopen(MirrorBaseClass): result =3D self.vm.qmp('blockdev-add', node_name=3D"backing", driver=3D"null-co") self.assert_qmp(result, 'return', {}) - result =3D self.vm.qmp('x-blockdev-reopen', node_name=3D"targe= t", - driver=3Diotests.imgfmt, file=3D"target-f= ile", - backing=3D"backing") + result =3D self.vm.qmp('x-blockdev-reopen', options =3D [{ + 'node-name': "target", + 'driver': iotests.imgfmt, + 'file': "target-file", + 'backing': "backing" + }]) self.assert_qmp(result, 'return', {}) =20 class TestBlockdevMirrorReopenIothread(TestBlockdevMirrorReopen): diff --git a/tests/qemu-iotests/165 b/tests/qemu-iotests/165 index fb56a769b4..32db5086e1 100755 --- a/tests/qemu-iotests/165 +++ b/tests/qemu-iotests/165 @@ -136,7 +136,7 @@ class TestPersistentDirtyBitmap(iotests.QMPTestCase): assert sha256_1 =3D=3D self.getSha256() =20 # Reopen to RW - result =3D self.vm.qmp('x-blockdev-reopen', **{ + result =3D self.vm.qmp('x-blockdev-reopen', options =3D [{ 'node-name': 'node0', 'driver': iotests.imgfmt, 'file': { @@ -144,7 +144,7 @@ class TestPersistentDirtyBitmap(iotests.QMPTestCase): 'filename': disk }, 'read-only': False - }) + }]) self.assert_qmp(result, 'return', {}) =20 # Check that bitmap is reopened to RW and we can write to it. diff --git a/tests/qemu-iotests/245 b/tests/qemu-iotests/245 index bad6911f0c..850c9f070b 100755 --- a/tests/qemu-iotests/245 +++ b/tests/qemu-iotests/245 @@ -84,8 +84,18 @@ class TestBlockdevReopen(iotests.QMPTestCase): "Expected output of %d qemu-io commands, found %d= " % (found, self.total_io_cmds)) =20 - # Run x-blockdev-reopen with 'opts' but applying 'newopts' - # on top of it. The original 'opts' dict is unmodified + # Run x-blockdev-reopen on a list of block devices + def reopenMultiple(self, opts, errmsg =3D None): + result =3D self.vm.qmp('x-blockdev-reopen', conv_keys =3D False, o= ptions =3D opts) + if errmsg: + self.assert_qmp(result, 'error/class', 'GenericError') + self.assert_qmp(result, 'error/desc', errmsg) + else: + self.assert_qmp(result, 'return', {}) + + # Run x-blockdev-reopen on a single block device (specified by + # 'opts') but applying 'newopts' on top of it. The original 'opts' + # dict is unmodified def reopen(self, opts, newopts =3D {}, errmsg =3D None): opts =3D copy.deepcopy(opts) =20 @@ -100,12 +110,7 @@ class TestBlockdevReopen(iotests.QMPTestCase): subdict =3D opts[prefix] subdict[key] =3D value =20 - result =3D self.vm.qmp('x-blockdev-reopen', conv_keys =3D False, *= *opts) - if errmsg: - self.assert_qmp(result, 'error/class', 'GenericError') - self.assert_qmp(result, 'error/desc', errmsg) - else: - self.assert_qmp(result, 'return', {}) + self.reopenMultiple([ opts ], errmsg) =20 =20 # Run query-named-block-nodes and return the specified entry @@ -141,10 +146,10 @@ class TestBlockdevReopen(iotests.QMPTestCase): # We cannot change any of these self.reopen(opts, {'node-name': 'not-found'}, "Cannot find node na= med 'not-found'") self.reopen(opts, {'node-name': ''}, "Cannot find node named ''") - self.reopen(opts, {'node-name': None}, "Invalid parameter type for= 'node-name', expected: string") + self.reopen(opts, {'node-name': None}, "Invalid parameter type for= 'options[0].node-name', expected: string") self.reopen(opts, {'driver': 'raw'}, "Cannot change the option 'dr= iver'") self.reopen(opts, {'driver': ''}, "Invalid parameter ''") - self.reopen(opts, {'driver': None}, "Invalid parameter type for 'd= river', expected: string") + self.reopen(opts, {'driver': None}, "Invalid parameter type for 'o= ptions[0].driver', expected: string") self.reopen(opts, {'file': 'not-found'}, "Cannot find device=3D no= r node_name=3Dnot-found") self.reopen(opts, {'file': ''}, "Cannot find device=3D nor node_na= me=3D") self.reopen(opts, {'file': None}, "Invalid parameter type for 'fil= e', expected: BlockdevRef") @@ -153,7 +158,7 @@ class TestBlockdevReopen(iotests.QMPTestCase): self.reopen(opts, {'file.filename': hd_path[1]}, "Cannot change th= e option 'filename'") self.reopen(opts, {'file.aio': 'native'}, "Cannot change the optio= n 'aio'") self.reopen(opts, {'file.locking': 'off'}, "Cannot change the opti= on 'locking'") - self.reopen(opts, {'file.filename': None}, "Invalid parameter type= for 'file.filename', expected: string") + self.reopen(opts, {'file.filename': None}, "Invalid parameter type= for 'options[0].file.filename', expected: string") =20 # node-name is optional in BlockdevOptions, but x-blockdev-reopen = needs it del opts['node-name'] diff --git a/tests/qemu-iotests/248 b/tests/qemu-iotests/248 index 18ba03467e..2b43853183 100755 --- a/tests/qemu-iotests/248 +++ b/tests/qemu-iotests/248 @@ -62,7 +62,7 @@ vm.get_qmp_events() =20 del blockdev_opts['file']['size'] vm.qmp_log('x-blockdev-reopen', filters=3D[filter_qmp_testfiles], - **blockdev_opts) + options =3D [ blockdev_opts ]) =20 vm.qmp_log('block-job-resume', device=3D'drive0') vm.event_wait('JOB_STATUS_CHANGE', timeout=3D1.0, diff --git a/tests/qemu-iotests/248.out b/tests/qemu-iotests/248.out index 369b25bf26..893f625347 100644 --- a/tests/qemu-iotests/248.out +++ b/tests/qemu-iotests/248.out @@ -2,7 +2,7 @@ {"return": {}} {"execute": "blockdev-mirror", "arguments": {"device": "drive0", "on-targe= t-error": "enospc", "sync": "full", "target": "target"}} {"return": {}} -{"execute": "x-blockdev-reopen", "arguments": {"driver": "qcow2", "file": = {"driver": "raw", "file": {"driver": "file", "filename": "TEST_DIR/PID-targ= et"}}, "node-name": "target"}} +{"execute": "x-blockdev-reopen", "arguments": {"options": [{"driver": "qco= w2", "file": {"driver": "raw", "file": {"driver": "file", "filename": "TEST= _DIR/PID-target"}}, "node-name": "target"}]}} {"return": {}} {"execute": "block-job-resume", "arguments": {"device": "drive0"}} {"return": {}} diff --git a/tests/qemu-iotests/298 b/tests/qemu-iotests/298 index d535946b5f..4efdb35b91 100644 --- a/tests/qemu-iotests/298 +++ b/tests/qemu-iotests/298 @@ -98,7 +98,7 @@ class TestPreallocateFilter(TestPreallocateBase): self.check_big() =20 def test_reopen_opts(self): - result =3D self.vm.qmp('x-blockdev-reopen', **{ + result =3D self.vm.qmp('x-blockdev-reopen', options =3D [{ 'node-name': 'disk', 'driver': iotests.imgfmt, 'file': { @@ -112,7 +112,7 @@ class TestPreallocateFilter(TestPreallocateBase): 'filename': disk } } - }) + }]) self.assert_qmp(result, 'return', {}) =20 self.vm.hmp_qemu_io('drive0', 'write 0 1M') --=20 2.20.1 From nobody Fri May 17 09:18:36 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail; 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=1612828068; cv=none; d=zohomail.com; s=zohoarc; b=ND6fQJ4fMmRYNzz8TAjKjTjhNe70Bhqe00sh5WnTZCl7v/k3dIKnVOUh7FrB8T5AkCEHXMjztbFSx32162ciEeumd9CPpbKncywBA1BkjquXX+oohdyka40MhAAOuBY/gMaBEN1lv0hYbq9eq1oM4CwELdvRHyCI694YkZQI6v4= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1612828068; h=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=PgM0mMAqMJNtmF60oidG6olTXXxwlo5tWPQ7kz8W8CY=; b=m7f1vU3RnrNlcUmydnojpXVy3JtApYxT9zjvzaKwlq/CA5i5gKqcDUs8V+N+GHPHvlb26V4n2k3cuuzhDEX8n0ceoudtU8xRELEDvntFE/mKSz9YYtssPfOanqEbc7kZcQfeynhKHFT+z3gSJ1EUu7SUubOco9/xzA/Ds14Dq6M= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=fail; 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 1612828068261712.1795758508822; Mon, 8 Feb 2021 15:47:48 -0800 (PST) Received: from localhost ([::1]:45634 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1l9GFv-0005bF-8H for importer@patchew.org; Mon, 08 Feb 2021 18:47:47 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]:57006) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1l9BXY-0008LW-Sl; Mon, 08 Feb 2021 13:45:40 -0500 Received: from fanzine.igalia.com ([178.60.130.6]:46559) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1l9BXN-0006o4-KE; Mon, 08 Feb 2021 13:45:40 -0500 Received: from [213.94.25.37] (helo=perseus.local) by fanzine.igalia.com with esmtpsa (Cipher TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim) id 1l9BWw-000567-MB; Mon, 08 Feb 2021 19:45:02 +0100 Received: from berto by perseus.local with local (Exim 4.92) (envelope-from ) id 1l9BWj-000087-Ni; Mon, 08 Feb 2021 19:44:49 +0100 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=igalia.com; s=20170329; h=Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-Id:Date:Subject:Cc:To:From; bh=PgM0mMAqMJNtmF60oidG6olTXXxwlo5tWPQ7kz8W8CY=; b=aIXSA4dtwRzqfSbXeQ3vyol4WnxhRPR5m7VNvd+jhDn7XYfOEFSRGOYzmLC2bd2NZJuuVn7VVUTCMB/XgvqOv9jcx0Tj2EjYAuSIXb0BiaCRJubdE8x2qUNc/KeflDaz0qW6XoiKWv8CmcCJWZJwB/xdBzL7TlxNZJWC5nViKlb7w8nwBFiT0btBJPl7LilePw7T3RL3fzMtsaBhz/zuB8EfU2iu/iPNca0871qguB+CmjrDiNznYGJL558cZ/xOiqb059S2rppV1z5tCLLfA/YjAQCVErkt8wrvWCgEthpgJlf+HpaspciFwAI328QNnaSkmvJNjJw5Evq5mt6VLQ==; From: Alberto Garcia To: qemu-devel@nongnu.org Subject: [RFC PATCH v2 4/4] iotests: Test reopening multiple devices at the same time Date: Mon, 8 Feb 2021 19:44:44 +0100 Message-Id: <8c976fdb937c8c07b3b9829e6b4e6760d62a130b.1612809837.git.berto@igalia.com> X-Mailer: git-send-email 2.20.1 In-Reply-To: References: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable 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=178.60.130.6; envelope-from=berto@igalia.com; helo=fanzine.igalia.com X-Spam_score_int: -20 X-Spam_score: -2.1 X-Spam_bar: -- X-Spam_report: (-2.1 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, SPF_HELO_NONE=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: Kevin Wolf , Vladimir Sementsov-Ogievskiy , Alberto Garcia , qemu-block@nongnu.org, Max Reitz Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) Content-Type: text/plain; charset="utf-8" Signed-off-by: Alberto Garcia --- tests/qemu-iotests/245 | 40 ++++++++++++++++++++++++++++++++++++++ tests/qemu-iotests/245.out | 4 ++-- 2 files changed, 42 insertions(+), 2 deletions(-) diff --git a/tests/qemu-iotests/245 b/tests/qemu-iotests/245 index 850c9f070b..d18dbbe638 100755 --- a/tests/qemu-iotests/245 +++ b/tests/qemu-iotests/245 @@ -574,6 +574,46 @@ class TestBlockdevReopen(iotests.QMPTestCase): self.reopen(opts, {'file': 'hd1-file'}) self.run_qemu_io("hd", "read -P 0xa1 0 10k") =20 + def test_swap_files(self): + opts0 =3D hd_opts(0) + opts2 =3D hd_opts(2) + + # Add hd0 and hd2 (none of them with backing files) + result =3D self.vm.qmp('blockdev-add', conv_keys =3D False, **opts= 0) + self.assert_qmp(result, 'return', {}) + result =3D self.vm.qmp('blockdev-add', conv_keys =3D False, **opts= 2) + self.assert_qmp(result, 'return', {}) + + # Write different data to both block devices + self.run_qemu_io("hd0", "write -P 0xa0 0 1k") + self.run_qemu_io("hd2", "write -P 0xa2 0 1k") + + # Check that the data reads correctly + self.run_qemu_io("hd0", "read -P 0xa0 0 1k") + self.run_qemu_io("hd2", "read -P 0xa2 0 1k") + + # It's not possible to make a block device use an image that + # is already being used by the other device. + self.reopen(opts0, {'file': 'hd2-file'}, + "Conflicts with use by hd0 as 'file', which does not a= llow 'write, resize' on hd2-file") + self.reopen(opts2, {'file': 'hd0-file'}, + "Conflicts with use by hd2 as 'file', which does not a= llow 'write, resize' on hd0-file") + + # But we can swap the images if we reopen both devices at the + # same time + opts0['file'] =3D 'hd2-file' + opts2['file'] =3D 'hd0-file' + self.reopenMultiple([opts0, opts2]) + self.run_qemu_io("hd0", "read -P 0xa2 0 1k") + self.run_qemu_io("hd2", "read -P 0xa0 0 1k") + + # And we can of course come back to the original state + opts0['file'] =3D 'hd0-file' + opts2['file'] =3D 'hd2-file' + self.reopenMultiple([opts0, opts2]) + self.run_qemu_io("hd0", "read -P 0xa0 0 1k") + self.run_qemu_io("hd2", "read -P 0xa2 0 1k") + def test_insert_throttle_filter(self): hd0_opts =3D hd_opts(0) result =3D self.vm.qmp('blockdev-add', conv_keys =3D False, **hd0_= opts) diff --git a/tests/qemu-iotests/245.out b/tests/qemu-iotests/245.out index 537a2b5b63..1f9debbd61 100644 --- a/tests/qemu-iotests/245.out +++ b/tests/qemu-iotests/245.out @@ -10,8 +10,8 @@ {"return": {}} {"data": {"id": "stream0", "type": "stream"}, "event": "BLOCK_JOB_PENDING"= , "timestamp": {"microseconds": "USECS", "seconds": "SECS"}} {"data": {"device": "stream0", "len": 3145728, "offset": 3145728, "speed":= 0, "type": "stream"}, "event": "BLOCK_JOB_COMPLETED", "timestamp": {"micro= seconds": "USECS", "seconds": "SECS"}} -....................... +........................ ---------------------------------------------------------------------- -Ran 23 tests +Ran 24 tests =20 OK --=20 2.20.1