Version in base suite: 21.0.0-2 Base version: glance_21.0.0-2 Target version: glance_21.0.0-2+deb11u1 Base file: /srv/ftp-master.debian.org/ftp/pool/main/g/glance/glance_21.0.0-2.dsc Target file: /srv/ftp-master.debian.org/policy/pool/main/g/glance/glance_21.0.0-2+deb11u1.dsc changelog | 10 + patches/cve-2022-47951-glance-stable-victoria.patch | 157 ++++++++++++++++++++ patches/series | 1 3 files changed, 168 insertions(+) diff -Nru glance-21.0.0/debian/changelog glance-21.0.0/debian/changelog --- glance-21.0.0/debian/changelog 2020-12-15 10:41:16.000000000 +0000 +++ glance-21.0.0/debian/changelog 2023-01-18 09:14:44.000000000 +0000 @@ -1,3 +1,13 @@ +glance (2:21.0.0-2+deb11u1) bullseye-security; urgency=medium + + * CVE-2022-47951: By supplying a specially created VMDK flat image which + references a specific backing file path, an authenticated user may convince + systems to return a copy of that file's contents from the server resulting + in unauthorized access to potentially sensitive data. Add upstream patch + cve-2022-47951-glance-stable-victoria.patch (Closes: #1029563). + + -- Thomas Goirand Wed, 18 Jan 2023 10:14:44 +0100 + glance (2:21.0.0-2) unstable; urgency=medium * Add variables: DEB_BUILD_OPTIONS: nocheck DEB_BUILD_PROFILES: nocheck in diff -Nru glance-21.0.0/debian/patches/cve-2022-47951-glance-stable-victoria.patch glance-21.0.0/debian/patches/cve-2022-47951-glance-stable-victoria.patch --- glance-21.0.0/debian/patches/cve-2022-47951-glance-stable-victoria.patch 1970-01-01 00:00:00.000000000 +0000 +++ glance-21.0.0/debian/patches/cve-2022-47951-glance-stable-victoria.patch 2023-01-18 09:14:44.000000000 +0000 @@ -0,0 +1,157 @@ +Subject: CVE-2022-47951: Enforce image safety during image_conversion + This does two things: + . + 1. It makes us check that the QCOW backing_file is unset on those + types of images. Nova and Cinder do this already to prevent an + arbitrary (and trivial to accomplish) host file exposure exploit. + 2. It makes us restrict VMDK files to only allowed subtypes. These + files can name arbitrary files on disk as extents, providing the + same sort of attack. Default that list to just the types we believe + are actually useful for openstack, and which are monolithic. + . + The configuration option to specify allowed subtypes is added in + glance's config and not in the import options so that we can extend + this check later to image ingest. The format_inspector can tell us + what the type and subtype is, and we could reject those images early + and even in the case where image_conversion is not enabled. +Author: Dan Smith +Date: Mon, 19 Dec 2022 15:00:35 +0000 +Bug: https://launchpad.net/bugs/1996188 +Debian-Bug: https://bugs.debian.org/1029563 +Change-Id: Idf561f6306cebf756c787d8eefdc452ce44bd5e0 +Origin: upstream, https://review.opendev.org/c/openstack/glance/+/871623 +Last-Update: 2022-01-18 + +diff --git a/glance/async_/flows/plugins/image_conversion.py b/glance/async_/flows/plugins/image_conversion.py +index a5165b0ab..8a6c759c6 100644 +--- a/glance/async_/flows/plugins/image_conversion.py ++++ b/glance/async_/flows/plugins/image_conversion.py +@@ -107,6 +107,29 @@ class _ConvertImage(task.Task): + image = self.image_repo.get(self.image_id) + image.virtual_size = virtual_size + ++ if 'backing-filename' in metadata: ++ LOG.warning('Refusing to process QCOW image with a backing file') ++ raise RuntimeError( ++ 'QCOW images with backing files are not allowed') ++ ++ if metadata.get('format') == 'vmdk': ++ create_type = metadata.get( ++ 'format-specific', {}).get( ++ 'data', {}).get('create-type') ++ allowed = CONF.image_format.vmdk_allowed_types ++ if not create_type: ++ raise RuntimeError(_('Unable to determine VMDK create-type')) ++ if not len(allowed): ++ LOG.warning(_('Refusing to process VMDK file as ' ++ 'vmdk_allowed_types is empty')) ++ raise RuntimeError(_('Image is a VMDK, but no VMDK createType ' ++ 'is specified')) ++ if create_type not in allowed: ++ LOG.warning(_('Refusing to process VMDK file with create-type ' ++ 'of %r which is not in allowed set of: %s'), ++ create_type, ','.join(allowed)) ++ raise RuntimeError(_('Invalid VMDK create-type specified')) ++ + if source_format == target_format: + LOG.debug("Source is already in target format, " + "not doing conversion for %s", self.image_id) +diff --git a/glance/common/config.py b/glance/common/config.py +index 2093117ad..532b784f2 100644 +--- a/glance/common/config.py ++++ b/glance/common/config.py +@@ -99,6 +99,18 @@ image_format_opts = [ + "image attribute"), + deprecated_opts=[cfg.DeprecatedOpt('disk_formats', + group='DEFAULT')]), ++ cfg.ListOpt('vmdk_allowed_types', ++ default=['streamOptimized', 'monolithicSparse'], ++ help=_("A list of strings describing allowed VMDK " ++ "'create-type' subformats that will be allowed. " ++ "This is recommended to only include " ++ "single-file-with-sparse-header variants to avoid " ++ "potential host file exposure due to processing named " ++ "extents. If this list is empty, then no VDMK image " ++ "types allowed. Note that this is currently only " ++ "checked during image conversion (if enabled), and " ++ "limits the types of VMDK images we will convert " ++ "from.")), + ] + task_opts = [ + cfg.IntOpt('task_time_to_live', +diff --git a/glance/tests/unit/async_/flows/plugins/test_image_conversion.py b/glance/tests/unit/async_/flows/plugins/test_image_conversion.py +index 2dc4dc6f7..064d2cd83 100644 +--- a/glance/tests/unit/async_/flows/plugins/test_image_conversion.py ++++ b/glance/tests/unit/async_/flows/plugins/test_image_conversion.py +@@ -105,6 +105,68 @@ class TestConvertImageTask(test_utils.BaseTestCase): + self.assertIn('-f', exc_mock.call_args[0]) + self.assertEqual("qcow2", image.disk_format) + ++ def _setup_image_convert_info_fail(self): ++ image_convert = image_conversion._ConvertImage(self.context, ++ self.task.task_id, ++ self.task_type, ++ self.img_repo, ++ self.image_id) ++ ++ self.task_repo.get.return_value = self.task ++ image = mock.MagicMock(image_id=self.image_id, virtual_size=None, ++ extra_properties={ ++ 'os_glance_import_task': self.task.task_id}, ++ disk_format='qcow2') ++ self.img_repo.get.return_value = image ++ return image_convert ++ ++ def test_image_convert_invalid_qcow(self): ++ data = {'format': 'qcow2', ++ 'backing-filename': '/etc/hosts'} ++ ++ convert = self._setup_image_convert_info_fail() ++ with mock.patch.object(processutils, 'execute') as exc_mock: ++ exc_mock.return_value = json.dumps(data), '' ++ e = self.assertRaises(RuntimeError, ++ convert.execute, 'file:///test/path.qcow') ++ self.assertEqual('QCOW images with backing files are not allowed', ++ str(e)) ++ ++ def _test_image_convert_invalid_vmdk(self): ++ data = {'format': 'vmdk', ++ 'format-specific': { ++ 'data': { ++ 'create-type': 'monolithicFlat', ++ }}} ++ ++ convert = self._setup_image_convert_info_fail() ++ with mock.patch.object(processutils, 'execute') as exc_mock: ++ exc_mock.return_value = json.dumps(data), '' ++ convert.execute('file:///test/path.vmdk') ++ ++ def test_image_convert_invalid_vmdk(self): ++ e = self.assertRaises(RuntimeError, ++ self._test_image_convert_invalid_vmdk) ++ self.assertEqual('Invalid VMDK create-type specified', str(e)) ++ ++ def test_image_convert_valid_vmdk_no_types(self): ++ with mock.patch.object(CONF.image_format, 'vmdk_allowed_types', ++ new=[]): ++ # We make it past the VMDK check and fail because our file ++ # does not exist ++ e = self.assertRaises(RuntimeError, ++ self._test_image_convert_invalid_vmdk) ++ self.assertEqual('Image is a VMDK, but no VMDK createType is ' ++ 'specified', str(e)) ++ ++ def test_image_convert_valid_vmdk(self): ++ with mock.patch.object(CONF.image_format, 'vmdk_allowed_types', ++ new=['monolithicSparse', 'monolithicFlat']): ++ # We make it past the VMDK check and fail because our file ++ # does not exist ++ self.assertRaises(FileNotFoundError, ++ self._test_image_convert_invalid_vmdk) ++ + @mock.patch.object(os, 'remove') + def test_image_convert_revert_success(self, mock_os_remove): + mock_os_remove.return_value = None +-- +2.25.1 + diff -Nru glance-21.0.0/debian/patches/series glance-21.0.0/debian/patches/series --- glance-21.0.0/debian/patches/series 2020-12-15 10:41:16.000000000 +0000 +++ glance-21.0.0/debian/patches/series 2023-01-18 09:14:44.000000000 +0000 @@ -1,2 +1,3 @@ sql_conn-registry.patch missing-files.patch +cve-2022-47951-glance-stable-victoria.patch