From nobody Mon Jul 27 20:03:09 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; dmarc=fail(p=none dis=none) header.from=oss.nttdata.com Return-Path: Received: from lists1p.gnu.org (lists1p.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 178422181728065.94762558132936; Thu, 16 Jul 2026 10:10:17 -0700 (PDT) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists1p.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1wkPat-0007HN-TE; Thu, 16 Jul 2026 13:09:55 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists1p.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1wkPar-0007E8-Jt for qemu-devel@nongnu.org; Thu, 16 Jul 2026 13:09:53 -0400 Received: from oss.nttdata.com ([49.212.34.109]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1wkPao-0007Rh-Q4 for qemu-devel@nongnu.org; Thu, 16 Jul 2026 13:09:53 -0400 Received: by oss.nttdata.com (Postfix, from userid 1024) id 1FA8A202031E; Fri, 17 Jul 2026 02:09:24 +0900 (JST) From: Mitsuru Kariya To: qemu-devel@nongnu.org Cc: Mitsuru Kariya , Paolo Bonzini , Fam Zheng Subject: [PATCH 1/4] scsi-disk: Fix BlockBackend leak on unplug of empty CD-ROM Date: Fri, 17 Jul 2026 02:09:20 +0900 Message-ID: <20260716170923.2125858-2-Mitsuru.Kariya@oss.nttdata.com> X-Mailer: git-send-email 2.43.0 In-Reply-To: <20260716170923.2125858-1-Mitsuru.Kariya@oss.nttdata.com> References: <20260716170923.2125858-1-Mitsuru.Kariya@oss.nttdata.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Virus-Scanned: clamav-milter 1.4.3 at oss.nttdata.com X-Virus-Status: Clean 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=lists1p.gnu.org; Received-SPF: pass client-ip=49.212.34.109; envelope-from=kariyam@oss.nttdata.com; helo=oss.nttdata.com X-Spam_score_int: -18 X-Spam_score: -1.9 X-Spam_bar: - X-Spam_report: (-1.9 / 5.0 requ) BAYES_00=-1.9, 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.29 Precedence: list List-Id: qemu development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: qemu-devel-bounces+importer=patchew.org@nongnu.org X-ZM-MESSAGEID: 1784221819861158500 Content-Type: text/plain; charset="utf-8" When a scsi-cd is created without a backing drive (an empty CD-ROM), scsi_cd_realize() allocates an anonymous BlockBackend for the empty drive with blk_new() and attaches it to the device using blk_attach_dev(). blk_new() returns the backend with refcnt =3D=3D 1 (the creation reference owned by the caller) and blk_attach_dev() takes an additional reference for the device. The creation reference was never released, so on unplug blk_detach_dev() only drops the device's reference and the BlockBackend is leaked. Release the creation reference with blk_unref() right after blk_attach_dev(), matching the idiom already used in set_drive_helper() in hw/core/qdev-properties-system.c ("If we need to keep a reference, blk_attach_dev() took it"). Signed-off-by: Mitsuru Kariya --- hw/scsi/scsi-disk.c | 1 + 1 file changed, 1 insertion(+) diff --git a/hw/scsi/scsi-disk.c b/hw/scsi/scsi-disk.c index 5ba5b46c4f..d70af0d9b4 100644 --- a/hw/scsi/scsi-disk.c +++ b/hw/scsi/scsi-disk.c @@ -2627,6 +2627,7 @@ static void scsi_cd_realize(SCSIDevice *dev, Error **= errp) dev->conf.blk =3D blk_new(qemu_get_aio_context(), 0, BLK_PERM_ALL); ret =3D blk_attach_dev(dev->conf.blk, &dev->qdev); assert(ret =3D=3D 0); + blk_unref(dev->conf.blk); } =20 if (dev->conf.physical_block_size !=3D 0) { --=20 2.43.0 From nobody Mon Jul 27 20:03:09 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; dmarc=fail(p=none dis=none) header.from=oss.nttdata.com Return-Path: Received: from lists1p.gnu.org (lists1p.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1784221838903154.82895787982557; Thu, 16 Jul 2026 10:10:38 -0700 (PDT) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists1p.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1wkPau-0007HG-0y; Thu, 16 Jul 2026 13:09:56 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists1p.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1wkPar-0007EF-KG; Thu, 16 Jul 2026 13:09:53 -0400 Received: from oss.nttdata.com ([49.212.34.109]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1wkPao-0007Rj-Mz; Thu, 16 Jul 2026 13:09:53 -0400 Received: by oss.nttdata.com (Postfix, from userid 1024) id 3B36E2020241; Fri, 17 Jul 2026 02:09:24 +0900 (JST) From: Mitsuru Kariya To: qemu-devel@nongnu.org Cc: Mitsuru Kariya , Stefano Stabellini , Anthony PERARD , "Edgar E. Iglesias" , Kevin Wolf , Hanna Reitz , xen-devel@lists.xenproject.org (open list:X86 Xen CPUs), qemu-block@nongnu.org (open list:Block layer core) Subject: [PATCH 2/4] xen-block: Fix inverted error check in xen_cdrom_realize() Date: Fri, 17 Jul 2026 02:09:21 +0900 Message-ID: <20260716170923.2125858-3-Mitsuru.Kariya@oss.nttdata.com> X-Mailer: git-send-email 2.43.0 In-Reply-To: <20260716170923.2125858-1-Mitsuru.Kariya@oss.nttdata.com> References: <20260716170923.2125858-1-Mitsuru.Kariya@oss.nttdata.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Virus-Scanned: clamav-milter 1.4.3 at oss.nttdata.com X-Virus-Status: Clean 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=lists1p.gnu.org; Received-SPF: pass client-ip=49.212.34.109; envelope-from=kariyam@oss.nttdata.com; helo=oss.nttdata.com X-Spam_score_int: -18 X-Spam_score: -1.9 X-Spam_bar: - X-Spam_report: (-1.9 / 5.0 requ) BAYES_00=-1.9, 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.29 Precedence: list List-Id: qemu development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: qemu-devel-bounces+importer=patchew.org@nongnu.org X-ZM-MESSAGEID: 1784221839391158500 Content-Type: text/plain; charset="utf-8" xen_cdrom_realize() checks the return value of blk_attach_dev() with if (!rc) { error_setg_errno(errp, -rc, "failed to create drive"); return; } but blk_attach_dev() returns 0 on success and a negative errno on failure. The condition is inverted: a successful attach (rc =3D=3D 0) is reported as an error and fails realize, while a real failure (rc < 0) is silently ignored. Here blk_attach_dev() is called on a BlockBackend just created by blk_new(), so blk->dev is NULL and its only failure path (-EBUSY) cannot be taken. Replace the bogus check with an assertion, matching the other empty-drive realize paths (scsi-disk, ide, fdc, swim). Signed-off-by: Mitsuru Kariya Reviewed-by: Stefano Stabellini --- hw/block/xen-block.c | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/hw/block/xen-block.c b/hw/block/xen-block.c index 474c12fe4a..abf9df2eee 100644 --- a/hw/block/xen-block.c +++ b/hw/block/xen-block.c @@ -762,10 +762,7 @@ static void xen_cdrom_realize(XenBlockDevice *blockdev= , Error **errp) conf->blk =3D blk_new(qemu_get_aio_context(), 0, BLK_PERM_ALL); =20 rc =3D blk_attach_dev(conf->blk, DEVICE(blockdev)); - if (!rc) { - error_setg_errno(errp, -rc, "failed to create drive"); - return; - } + assert(rc =3D=3D 0); } =20 blockdev->info =3D VDISK_READONLY | VDISK_CDROM; --=20 2.43.0 From nobody Mon Jul 27 20:03:09 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; dmarc=fail(p=none dis=none) header.from=oss.nttdata.com Return-Path: Received: from lists1p.gnu.org (lists1p.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1784221823606795.6616603988147; Thu, 16 Jul 2026 10:10:23 -0700 (PDT) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists1p.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1wkPau-0007Hn-EY; Thu, 16 Jul 2026 13:09:56 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists1p.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1wkPar-0007ER-MI; Thu, 16 Jul 2026 13:09:53 -0400 Received: from oss.nttdata.com ([49.212.34.109]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1wkPao-0007Rg-NS; Thu, 16 Jul 2026 13:09:53 -0400 Received: by oss.nttdata.com (Postfix, from userid 1024) id 5766E2020242; Fri, 17 Jul 2026 02:09:24 +0900 (JST) From: Mitsuru Kariya To: qemu-devel@nongnu.org Cc: Mitsuru Kariya , Stefano Stabellini , Anthony PERARD , "Edgar E. Iglesias" , Kevin Wolf , Hanna Reitz , xen-devel@lists.xenproject.org (open list:X86 Xen CPUs), qemu-block@nongnu.org (open list:Block layer core) Subject: [PATCH 3/4] xen-block: Fix BlockBackend leak on unplug of empty CD-ROM Date: Fri, 17 Jul 2026 02:09:22 +0900 Message-ID: <20260716170923.2125858-4-Mitsuru.Kariya@oss.nttdata.com> X-Mailer: git-send-email 2.43.0 In-Reply-To: <20260716170923.2125858-1-Mitsuru.Kariya@oss.nttdata.com> References: <20260716170923.2125858-1-Mitsuru.Kariya@oss.nttdata.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Virus-Scanned: clamav-milter 1.4.3 at oss.nttdata.com X-Virus-Status: Clean 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=lists1p.gnu.org; Received-SPF: pass client-ip=49.212.34.109; envelope-from=kariyam@oss.nttdata.com; helo=oss.nttdata.com X-Spam_score_int: -18 X-Spam_score: -1.9 X-Spam_bar: - X-Spam_report: (-1.9 / 5.0 requ) BAYES_00=-1.9, 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.29 Precedence: list List-Id: qemu development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: qemu-devel-bounces+importer=patchew.org@nongnu.org X-ZM-MESSAGEID: 1784221825446158500 Content-Type: text/plain; charset="utf-8" When a Xen CD-ROM is created without a backing drive (an empty CD-ROM), xen_cdrom_realize() allocates an anonymous BlockBackend for the empty drive with blk_new() and attaches it to the device using blk_attach_dev(). blk_new() returns the backend with refcnt =3D=3D 1 (the creation reference owned by the caller) and blk_attach_dev() takes an additional reference for the device. The creation reference was never released, so on unplug blk_detach_dev() only drops the device's reference and the BlockBackend is leaked. Release the creation reference with blk_unref() right after blk_attach_dev(), matching the idiom already used in set_drive_helper() in hw/core/qdev-properties-system.c ("If we need to keep a reference, blk_attach_dev() took it"). Signed-off-by: Mitsuru Kariya Reviewed-by: Stefano Stabellini --- hw/block/xen-block.c | 1 + 1 file changed, 1 insertion(+) diff --git a/hw/block/xen-block.c b/hw/block/xen-block.c index abf9df2eee..e5e14e47ee 100644 --- a/hw/block/xen-block.c +++ b/hw/block/xen-block.c @@ -763,6 +763,7 @@ static void xen_cdrom_realize(XenBlockDevice *blockdev,= Error **errp) =20 rc =3D blk_attach_dev(conf->blk, DEVICE(blockdev)); assert(rc =3D=3D 0); + blk_unref(conf->blk); } =20 blockdev->info =3D VDISK_READONLY | VDISK_CDROM; --=20 2.43.0 From nobody Mon Jul 27 20:03:09 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; dmarc=fail(p=none dis=none) header.from=oss.nttdata.com Return-Path: Received: from lists1p.gnu.org (lists1p.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1784221818904902.8464433942198; Thu, 16 Jul 2026 10:10:18 -0700 (PDT) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists1p.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1wkPav-0007I3-QH; Thu, 16 Jul 2026 13:09:57 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists1p.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1wkPaq-0007Dh-HX for qemu-devel@nongnu.org; Thu, 16 Jul 2026 13:09:53 -0400 Received: from oss.nttdata.com ([49.212.34.109]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1wkPao-0007Rk-Dq for qemu-devel@nongnu.org; Thu, 16 Jul 2026 13:09:52 -0400 Received: by oss.nttdata.com (Postfix, from userid 1024) id 72F982020243; Fri, 17 Jul 2026 02:09:24 +0900 (JST) From: Mitsuru Kariya To: qemu-devel@nongnu.org Cc: Mitsuru Kariya , Fabiano Rosas , Laurent Vivier , Paolo Bonzini Subject: [PATCH 4/4] tests/qtest: drive_del: Add regression test for empty CD-ROM BlockBackend leak Date: Fri, 17 Jul 2026 02:09:23 +0900 Message-ID: <20260716170923.2125858-5-Mitsuru.Kariya@oss.nttdata.com> X-Mailer: git-send-email 2.43.0 In-Reply-To: <20260716170923.2125858-1-Mitsuru.Kariya@oss.nttdata.com> References: <20260716170923.2125858-1-Mitsuru.Kariya@oss.nttdata.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Virus-Scanned: clamav-milter 1.4.3 at oss.nttdata.com X-Virus-Status: Clean 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=lists1p.gnu.org; Received-SPF: pass client-ip=49.212.34.109; envelope-from=kariyam@oss.nttdata.com; helo=oss.nttdata.com X-Spam_score_int: -18 X-Spam_score: -1.9 X-Spam_bar: - X-Spam_report: (-1.9 / 5.0 requ) BAYES_00=-1.9, 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.29 Precedence: list List-Id: qemu development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: qemu-devel-bounces+importer=patchew.org@nongnu.org X-ZM-MESSAGEID: 1784221821281158500 Content-Type: text/plain; charset="utf-8" Add a regression test for the BlockBackend reference leak in scsi_cd_realize(): create an empty scsi-cd (which gets an anonymous BlockBackend), insert a medium, unplug the device, and check that the medium's blockdev node can then be deleted. Before the fix the leaked BlockBackend keeps the node in use and blockdev-del fails. Signed-off-by: Mitsuru Kariya --- tests/qtest/drive_del-test.c | 58 ++++++++++++++++++++++++++++++++++++ 1 file changed, 58 insertions(+) diff --git a/tests/qtest/drive_del-test.c b/tests/qtest/drive_del-test.c index 30d9451ddd..24793da852 100644 --- a/tests/qtest/drive_del-test.c +++ b/tests/qtest/drive_del-test.c @@ -320,6 +320,62 @@ static void test_empty_device_del(void) qtest_quit(qts); } =20 +static void test_insert_medium_and_device_del(void) +{ + QTestState *qts; + QDict *response; + + if (!has_device_builtin("virtio-scsi")) { + g_test_skip("Device virtio-scsi is not available"); + return; + } + + /* An empty scsi-cd creates an anonymous BlockBackend at realize. */ + qts =3D qtest_initf("-device virtio-scsi-%s -device scsi-cd,id=3Ddev0", + qvirtio_get_dev_type()); + + /* Create the blockdev node to be inserted as a medium. */ + blockdev_add_with_media(qts); + + /* Open tray. */ + response =3D qtest_qmp(qts, "{'execute': 'blockdev-open-tray'," + " 'arguments': {'id': 'dev0'}}"); + g_assert(response); + g_assert(qdict_haskey(response, "return")); + qobject_unref(response); + + /* + * Insert a medium into the empty drive. This adds a reference from + * the anonymous BlockBackend to the blockdev node. + */ + response =3D qtest_qmp(qts, "{'execute': 'blockdev-insert-medium'," + " 'arguments': {'id': 'dev0'," + " 'node-name': 'drive0'}}"); + g_assert(response); + g_assert(qdict_haskey(response, "return")); + qobject_unref(response); + + /* + * Unplug the device. This drops the last reference to the anonymous + * BlockBackend, so it is deleted and releases its reference to the + * blockdev node. + */ + device_del(qts, false); + + /* + * If the BlockBackend leaked, drive0 is still in use here and + * blockdev-del fails. + */ + response =3D qtest_qmp(qts, "{'execute': 'blockdev-del'," + " 'arguments': {'node-name': 'drive0'}}"); + g_assert(response); + g_assert(qdict_haskey(response, "return")); + qobject_unref(response); + g_assert(!has_blockdev(qts)); + + qtest_quit(qts); +} + static void test_device_add_and_del(void) { QTestState *qts; @@ -516,6 +572,8 @@ int main(int argc, char **argv) test_drive_add_device_add_and_del); qtest_add_func("/device_del/empty", test_empty_device_del); + qtest_add_func("/device_del/insert_medium", + test_insert_medium_and_device_del); qtest_add_func("/device_del/blockdev", test_blockdev_add_device_add_and_del); =20 --=20 2.43.0