From nobody Tue Nov 4 15:33:38 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com Return-Path: Received: from lists.gnu.org (208.118.235.17 [208.118.235.17]) by mx.zohomail.com with SMTPS id 1530565880334683.4832365290816; Mon, 2 Jul 2018 14:11:20 -0700 (PDT) Received: from localhost ([::1]:35490 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1fa66I-000295-Fm for importer@patchew.org; Mon, 02 Jul 2018 17:11:10 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:56819) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1fa62l-0007jg-6i for qemu-devel@nongnu.org; Mon, 02 Jul 2018 17:07:32 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1fa62k-0002PL-7e for qemu-devel@nongnu.org; Mon, 02 Jul 2018 17:07:31 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:51388 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1fa62h-0002Mb-Px; Mon, 02 Jul 2018 17:07:27 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 6725A401EF2E; Mon, 2 Jul 2018 21:07:27 +0000 (UTC) Received: from localhost (ovpn-204-100.brq.redhat.com [10.40.204.100]) by smtp.corp.redhat.com (Postfix) with ESMTPS id CBC34111AF36; Mon, 2 Jul 2018 21:07:24 +0000 (UTC) From: Max Reitz To: qemu-block@nongnu.org Date: Mon, 2 Jul 2018 23:07:20 +0200 Message-Id: <20180702210721.4847-2-mreitz@redhat.com> In-Reply-To: <20180702210721.4847-1-mreitz@redhat.com> References: <20180702210721.4847-1-mreitz@redhat.com> X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 02 Jul 2018 21:07:27 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.5]); Mon, 02 Jul 2018 21:07:27 +0000 (UTC) for IP:'10.11.54.3' DOMAIN:'int-mx03.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'mreitz@redhat.com' RCPT:'' X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH 1/2] vmdk: Fix possible segfault with non-VMDK backing 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 , Fam Zheng , qemu-devel@nongnu.org, Max Reitz Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" VMDK performs a probing check in vmdk_co_create_opts() to prevent the user from assigning non-VMDK files as a backing file, because it only supports VMDK backing files. However, with the @backing runtime option, it is possible to assign arbitrary nodes as backing nodes, regardless of what the image header says. Therefore, VMDK may not just access backing nodes assuming they are VMDK nodes -- which it does, because it needs to compare the backing file's CID with the overlay's parentCID value, and naturally the backing file only has a CID when it's a VMDK file. Instead, it should report the CID of non-VMDK backing files not to match the overlay because clearly a non-present CID does not match. Without this change, vmdk_read_cid() reads from the backing file's bs->file, which may be NULL (in which case we get a segfault). Also, it interprets bs->opaque as a BDRVVmdkState and then reads from the .desc_offset field, which usually will just return some arbitrary value which then results in either garbage to be read, or bdrv_pread() to return an error, both of which result in a non-matching CID to be reported. (In a very unlikely case, we could read something that looks like a VMDK descriptor, and then get a CID which might actually match. But that is highly unlikely, and the only result would be that VMDK accepts the backing file which is not too bad (albeit unintentional).) ((And in theory, the seek to .desc_offset might leak data from another block driver's opaque object. But then again, the user should realize very quickly that a non-VMDK backing file does not work (because the read will very likely fail, due to the reasons given above), so this should not be exploitable.)) Signed-off-by: Max Reitz Reviewed-by: Fam Zheng --- block/vmdk.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/block/vmdk.c b/block/vmdk.c index 84f8bbe480..a9d0084e36 100644 --- a/block/vmdk.c +++ b/block/vmdk.c @@ -333,6 +333,12 @@ static int vmdk_is_cid_valid(BlockDriverState *bs) if (!s->cid_checked && bs->backing) { BlockDriverState *p_bs =3D bs->backing->bs; =20 + if (strcmp(p_bs->drv->format_name, "vmdk")) { + /* Backing file is not in vmdk format, so it does not have + * a CID, which makes the overlay's parent CID invalid */ + return 0; + } + if (vmdk_read_cid(p_bs, 0, &cur_pcid) !=3D 0) { /* read failure: report as not valid */ return 0; --=20 2.17.1 From nobody Tue Nov 4 15:33:38 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1530565757989821.6498022959217; Mon, 2 Jul 2018 14:09:17 -0700 (PDT) Received: from localhost ([::1]:35473 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1fa64P-00009L-6K for importer@patchew.org; Mon, 02 Jul 2018 17:09:13 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:56845) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1fa62p-0007n3-7u for qemu-devel@nongnu.org; Mon, 02 Jul 2018 17:07:39 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1fa62m-0002Qw-T7 for qemu-devel@nongnu.org; Mon, 02 Jul 2018 17:07:35 -0400 Received: from mx3-rdu2.redhat.com ([66.187.233.73]:57794 helo=mx1.redhat.com) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1fa62j-0002OQ-K8; Mon, 02 Jul 2018 17:07:29 -0400 Received: from smtp.corp.redhat.com (int-mx04.intmail.prod.int.rdu2.redhat.com [10.11.54.4]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 51C9972632; Mon, 2 Jul 2018 21:07:29 +0000 (UTC) Received: from localhost (ovpn-204-100.brq.redhat.com [10.40.204.100]) by smtp.corp.redhat.com (Postfix) with ESMTPS id E81122026D5B; Mon, 2 Jul 2018 21:07:28 +0000 (UTC) From: Max Reitz To: qemu-block@nongnu.org Date: Mon, 2 Jul 2018 23:07:21 +0200 Message-Id: <20180702210721.4847-3-mreitz@redhat.com> In-Reply-To: <20180702210721.4847-1-mreitz@redhat.com> References: <20180702210721.4847-1-mreitz@redhat.com> X-Scanned-By: MIMEDefang 2.78 on 10.11.54.4 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 02 Jul 2018 21:07:29 +0000 (UTC) X-Greylist: inspected by milter-greylist-4.5.16 (mx1.redhat.com [10.11.55.2]); Mon, 02 Jul 2018 21:07:29 +0000 (UTC) for IP:'10.11.54.4' DOMAIN:'int-mx04.intmail.prod.int.rdu2.redhat.com' HELO:'smtp.corp.redhat.com' FROM:'mreitz@redhat.com' RCPT:'' X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 66.187.233.73 Subject: [Qemu-devel] [PATCH 2/2] iotests: Add VMDK backing file correlation test 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 , Fam Zheng , qemu-devel@nongnu.org, Max Reitz Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" This new test verifies that VMDK backing file reads fail when the backing file has a non-matching CID. This includes non-VMDK backing files. Signed-off-by: Max Reitz --- tests/qemu-iotests/225 | 132 +++++++++++++++++++++++++++++++++++++ tests/qemu-iotests/225.out | 24 +++++++ tests/qemu-iotests/group | 1 + 3 files changed, 157 insertions(+) create mode 100755 tests/qemu-iotests/225 create mode 100644 tests/qemu-iotests/225.out diff --git a/tests/qemu-iotests/225 b/tests/qemu-iotests/225 new file mode 100755 index 0000000000..f2ee715685 --- /dev/null +++ b/tests/qemu-iotests/225 @@ -0,0 +1,132 @@ +#!/bin/bash +# +# Test vmdk backing file correlation +# +# Copyright (C) 2018 Red Hat, Inc. +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . +# + +# creator +owner=3Dmreitz@redhat.com + +seq=3D$(basename $0) +echo "QA output created by $seq" + +here=3D$PWD +status=3D1 # failure is the default! + +_cleanup() +{ + _cleanup_test_img + rm -f "$TEST_IMG.not_base" +} +trap "_cleanup; exit \$status" 0 1 2 3 15 + +# get standard environment, filters and checks +. ./common.rc +. ./common.filter +. ./common.qemu + +# This tests vmdk-specific low-level functionality +_supported_fmt vmdk +_supported_proto file +_supported_os Linux +_unsupported_imgopts "subformat=3DmonolithicFlat" \ + "subformat=3DtwoGbMaxExtentFlat" \ + "subformat=3DtwoGbMaxExtentSparse" + +TEST_IMG=3D"$TEST_IMG.base" _make_test_img 1M +TEST_IMG=3D"$TEST_IMG.not_base" _make_test_img 1M +_make_test_img -b "$TEST_IMG.base" + +make_opts() +{ + node_name=3D$1 + filename=3D$2 + backing=3D$3 + + if [ -z "$backing" ]; then + backing=3D"null" + else + backing=3D"'$backing'" + fi + + echo "{ 'node-name': '$node_name', + 'driver': 'vmdk', + 'file': { + 'driver': 'file', + 'filename': '$filename' + }, + 'backing': $backing }" +} + +overlay_opts=3D$(make_opts overlay "$TEST_IMG" backing) +base_opts=3D$(make_opts backing "$TEST_IMG.base") +not_base_opts=3D$(make_opts backing "$TEST_IMG.not_base") + +not_vmdk_opts=3D"{ 'node-name': 'backing', 'driver': 'null-co' }" + +echo +echo '=3D=3D=3D Testing fitting VMDK backing image =3D=3D=3D' +echo + +qemu_comm_method=3Dmonitor \ + _launch_qemu -blockdev "$base_opts" -blockdev "$overlay_opts" + +# Should not return an error +_send_qemu_cmd $QEMU_HANDLE 'qemu-io overlay "read 0 512"' 'ops' + +_cleanup_qemu + + +echo +echo '=3D=3D=3D Testing unrelated VMDK backing image =3D=3D=3D' +echo + +qemu_comm_method=3Dmonitor \ + _launch_qemu -blockdev "$not_base_opts" -blockdev "$overlay_opts" + +# Should fail (gracefully) +_send_qemu_cmd $QEMU_HANDLE 'qemu-io overlay "read 0 512"' 'failed' + +_cleanup_qemu + + +echo +echo '=3D=3D=3D Testing non-VMDK backing image =3D=3D=3D' +echo + +# FIXME: This is the reason why we have to use two -blockdev +# invocations. You can only fully override the backing file options +# if you either specify a node reference (as done here) or the new +# options contain file.filename (which in this case they do not). +# In other cases, file.filename will be set to whatever the image +# header of the overlay contains (which we do not want). I consider +# this a FIXME because with -blockdev, you cannot specify "partial" +# options, so setting file.filename but leaving the rest as specified +# by the user does not make sense. +qemu_comm_method=3Dmonitor \ + _launch_qemu -blockdev "$not_vmdk_opts" -blockdev "$overlay_opts" + +# Should fail (gracefully) +_send_qemu_cmd $QEMU_HANDLE 'qemu-io overlay "read 0 512"' 'failed' + +_cleanup_qemu + + +# success, all done +echo "*** done" +rm -f $seq.full +status=3D0 diff --git a/tests/qemu-iotests/225.out b/tests/qemu-iotests/225.out new file mode 100644 index 0000000000..4dc8ee282f --- /dev/null +++ b/tests/qemu-iotests/225.out @@ -0,0 +1,24 @@ +QA output created by 225 +Formatting 'TEST_DIR/t.IMGFMT.base', fmt=3DIMGFMT size=3D1048576 +Formatting 'TEST_DIR/t.IMGFMT.not_base', fmt=3DIMGFMT size=3D1048576 +Formatting 'TEST_DIR/t.IMGFMT', fmt=3DIMGFMT size=3D1048576 backing_file= =3DTEST_DIR/t.IMGFMT.base + +=3D=3D=3D Testing fitting VMDK backing image =3D=3D=3D + +QEMU X.Y.Z monitor - type 'help' for more information +(qemu) qemu-io overlay "read 0 512" +read 512/512 bytes at offset 0 +512 bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec) + +=3D=3D=3D Testing unrelated VMDK backing image =3D=3D=3D + +QEMU X.Y.Z monitor - type 'help' for more information +(qemu) qemu-io overlay "read 0 512" +read failed: Invalid argument + +=3D=3D=3D Testing non-VMDK backing image =3D=3D=3D + +QEMU X.Y.Z monitor - type 'help' for more information +(qemu) qemu-io overlay "read 0 512" +read failed: Invalid argument +*** done diff --git a/tests/qemu-iotests/group b/tests/qemu-iotests/group index eea75819d2..a6eedfe727 100644 --- a/tests/qemu-iotests/group +++ b/tests/qemu-iotests/group @@ -220,3 +220,4 @@ 218 rw auto quick 219 rw auto 221 rw auto quick +225 rw auto quick --=20 2.17.1