VYPR
Moderate severityNVD Advisory· Published Nov 5, 2013· Updated Apr 29, 2026

CVE-2013-4497

CVE-2013-4497

Description

The XenAPI backend in OpenStack Compute (Nova) Folsom, Grizzly, and Havana before 2013.2 does not properly apply security groups (1) when resizing an image or (2) during live migration, which allows remote attackers to bypass intended restrictions.

Affected packages

Versions sourced from the GitHub Security Advisory.

PackageAffected versionsPatched versions
novaPyPI
< 12.0.0a012.0.0a0

Affected products

5
  • cpe:2.3:a:openstack:folsom:-:*:*:*:*:*:*:*
  • cpe:2.3:a:openstack:grizzly:-:*:*:*:*:*:*:*
  • OpenStack/Havana3 versions
    cpe:2.3:a:openstack:havana:*:*:*:*:*:*:*:*+ 2 more
    • cpe:2.3:a:openstack:havana:*:*:*:*:*:*:*:*range: <=havana-3
    • cpe:2.3:a:openstack:havana:havana-1:*:*:*:*:*:*:*
    • cpe:2.3:a:openstack:havana:havana-2:*:*:*:*:*:*:*

Patches

4
01de658210fd

xenapi: apply firewall rules in finish_migrate

https://github.com/openstack/novaJohn GarbuttOct 21, 2013via ghsa
1 file changed · +15 0
  • nova/virt/xenapi/vmops.py+15 0 modified
    @@ -277,8 +277,23 @@ def finish_migration(self, context, migration, instance, disk_info,
     
             self._attach_mapped_block_devices(instance, block_device_info)
     
    +        try:
    +            self.firewall_driver.setup_basic_filtering(
    +                    instance, network_info)
    +        except NotImplementedError:
    +            # NOTE(salvatore-orlando): setup_basic_filtering might be
    +            # empty or not implemented at all, as basic filter could
    +            # be implemented with VIF rules created by xapi plugin
    +            pass
    +
    +        self.firewall_driver.prepare_instance_filter(instance,
    +                                                     network_info)
    +
             # 5. Start VM
             self._start(instance, vm_ref=vm_ref)
    +
    +        self.firewall_driver.apply_instance_filter(instance, network_info)
    +
             self._update_instance_progress(context, instance,
                                            step=5,
                                            total_steps=RESIZE_TOTAL_STEPS)
    
df2ea2e3acde

xenapi: enforce filters after live-migration

https://github.com/openstack/novaJohn GarbuttSep 12, 2013via ghsa
3 files changed · +41 3
  • nova/tests/test_xenapi.py+21 1 modified
    @@ -2723,7 +2723,27 @@ def test_post_live_migration_at_destination(self):
             # ensure method is present
             stubs.stubout_session(self.stubs, stubs.FakeSessionForVMTests)
             self.conn = xenapi_conn.XenAPIDriver(fake.FakeVirtAPI(), False)
    -        self.conn.post_live_migration_at_destination(None, None, None, None)
    +
    +        fake_instance = "instance"
    +        fake_network_info = "network_info"
    +
    +        def fake_fw(instance, network_info):
    +            self.assertEquals(instance, fake_instance)
    +            self.assertEquals(network_info, fake_network_info)
    +            fake_fw.called += 1
    +
    +        fake_fw.called = 0
    +        _vmops = self.conn._vmops
    +        self.stubs.Set(_vmops.firewall_driver,
    +                       'setup_basic_filtering', fake_fw)
    +        self.stubs.Set(_vmops.firewall_driver,
    +                       'prepare_instance_filter', fake_fw)
    +        self.stubs.Set(_vmops.firewall_driver,
    +                       'apply_instance_filter', fake_fw)
    +
    +        self.conn.post_live_migration_at_destination(None, fake_instance,
    +                                                     fake_network_info, None)
    +        self.assertEqual(fake_fw.called, 3)
     
         def test_check_can_live_migrate_destination_with_block_migration(self):
             stubs.stubout_session(self.stubs, stubs.FakeSessionForVMTests)
    
  • nova/virt/xenapi/driver.py+2 2 modified
    @@ -1,4 +1,3 @@
    -# vim: tabstop=4 shiftwidth=4 softtabstop=4
     
     # Copyright (c) 2010 Citrix Systems, Inc.
     # Copyright 2010 OpenStack Foundation
    @@ -514,7 +513,8 @@ def post_live_migration_at_destination(self, ctxt, instance_ref,
             :params : block_migration: if true, post operation of block_migraiton.
             """
             # TODO(JohnGarbutt) look at moving/downloading ramdisk and kernel
    -        pass
    +        self._vmops.post_live_migration_at_destination(ctxt, instance_ref,
    +                network_info, block_device_info, block_device_info)
     
         def unfilter_instance(self, instance_ref, network_info):
             """Removes security groups configured for an instance."""
    
  • nova/virt/xenapi/vmops.py+18 0 modified
    @@ -1737,6 +1737,24 @@ def live_migrate(self, context, instance, destination_hostname,
                     recover_method(context, instance, destination_hostname,
                                    block_migration)
     
    +    def post_live_migration_at_destination(self, context, instance,
    +                                           network_info, block_migration,
    +                                           block_device_info):
    +        # FIXME(johngarbutt): we should block all traffic until we have
    +        # applied security groups, however this requires changes to XenServer
    +        try:
    +            self.firewall_driver.setup_basic_filtering(
    +                    instance, network_info)
    +        except NotImplementedError:
    +            # NOTE(salvatore-orlando): setup_basic_filtering might be
    +            # empty or not implemented at all, as basic filter could
    +            # be implemented with VIF rules created by xapi plugin
    +            pass
    +
    +        self.firewall_driver.prepare_instance_filter(instance,
    +                                                     network_info)
    +        self.firewall_driver.apply_instance_filter(instance, network_info)
    +
         def get_per_instance_usage(self):
             """Get usage info about each active instance."""
             usage = {}
    
5cced7a6dd32

xenapi: enforce filters after live-migration

https://github.com/openstack/novaJohn GarbuttSep 12, 2013via ghsa
3 files changed · +45 16
  • nova/tests/virt/xenapi/test_xenapi.py+21 1 modified
    @@ -3298,7 +3298,27 @@ def test_post_live_migration_at_destination(self):
             # ensure method is present
             stubs.stubout_session(self.stubs, stubs.FakeSessionForVMTests)
             self.conn = xenapi_conn.XenAPIDriver(fake.FakeVirtAPI(), False)
    -        self.conn.post_live_migration_at_destination(None, None, None, None)
    +
    +        fake_instance = "instance"
    +        fake_network_info = "network_info"
    +
    +        def fake_fw(instance, network_info):
    +            self.assertEquals(instance, fake_instance)
    +            self.assertEquals(network_info, fake_network_info)
    +            fake_fw.called += 1
    +
    +        fake_fw.called = 0
    +        _vmops = self.conn._vmops
    +        self.stubs.Set(_vmops.firewall_driver,
    +                       'setup_basic_filtering', fake_fw)
    +        self.stubs.Set(_vmops.firewall_driver,
    +                       'prepare_instance_filter', fake_fw)
    +        self.stubs.Set(_vmops.firewall_driver,
    +                       'apply_instance_filter', fake_fw)
    +
    +        self.conn.post_live_migration_at_destination(None, fake_instance,
    +                                                     fake_network_info, None)
    +        self.assertEqual(fake_fw.called, 3)
     
         def test_check_can_live_migrate_destination_with_block_migration(self):
             stubs.stubout_session(self.stubs, stubs.FakeSessionForVMTests)
    
  • nova/virt/xenapi/driver.py+2 3 modified
    @@ -1,4 +1,3 @@
    -# vim: tabstop=4 shiftwidth=4 softtabstop=4
     
     # Copyright (c) 2010 Citrix Systems, Inc.
     # Copyright 2010 OpenStack Foundation
    @@ -555,8 +554,8 @@ def post_live_migration_at_destination(self, ctxt, instance_ref,
             :params network_info: instance network information
             :params : block_migration: if true, post operation of block_migraiton.
             """
    -        # TODO(JohnGarbutt) look at moving/downloading ramdisk and kernel
    -        pass
    +        self._vmops.post_live_migration_at_destination(ctxt, instance_ref,
    +                network_info, block_device_info, block_device_info)
     
         def unfilter_instance(self, instance_ref, network_info):
             """Removes security groups configured for an instance."""
    
  • nova/virt/xenapi/vmops.py+22 12 modified
    @@ -451,18 +451,7 @@ def inject_instance_data_step(undo_mgr, vm_ref, vdis):
             @step
             def setup_network_step(undo_mgr, vm_ref):
                 self._create_vifs(instance, vm_ref, network_info)
    -
    -            try:
    -                self.firewall_driver.setup_basic_filtering(
    -                        instance, network_info)
    -            except NotImplementedError:
    -                # NOTE(salvatore-orlando): setup_basic_filtering might be
    -                # empty or not implemented at all, as basic filter could
    -                # be implemented with VIF rules created by xapi plugin
    -                pass
    -
    -            self.firewall_driver.prepare_instance_filter(instance,
    -                                                         network_info)
    +            self._prepare_instance_filter(instance, network_info)
     
             @step
             def boot_instance_step(undo_mgr, vm_ref):
    @@ -690,6 +679,19 @@ def _configure_new_instance_with_agent(self, instance, vm_ref,
                 # Reset network config
                 agent.resetnetwork()
     
    +    def _prepare_instance_filter(self, instance, network_info):
    +        try:
    +            self.firewall_driver.setup_basic_filtering(
    +                    instance, network_info)
    +        except NotImplementedError:
    +            # NOTE(salvatore-orlando): setup_basic_filtering might be
    +            # empty or not implemented at all, as basic filter could
    +            # be implemented with VIF rules created by xapi plugin
    +            pass
    +
    +        self.firewall_driver.prepare_instance_filter(instance,
    +                                                     network_info)
    +
         def _get_vm_opaque_ref(self, instance, check_rescue=False):
             """Get xapi OpaqueRef from a db record.
             :param check_rescue: if True will return the 'name'-rescue vm if it
    @@ -1904,6 +1906,14 @@ def live_migrate(self, context, instance, destination_hostname,
                     recover_method(context, instance, destination_hostname,
                                    block_migration)
     
    +    def post_live_migration_at_destination(self, context, instance,
    +                                           network_info, block_migration,
    +                                           block_device_info):
    +        # FIXME(johngarbutt): we should block all traffic until we have
    +        # applied security groups, however this requires changes to XenServer
    +        self._prepare_instance_filter(instance, network_info)
    +        self.firewall_driver.apply_instance_filter(instance, network_info)
    +
         def get_per_instance_usage(self):
             """Get usage info about each active instance."""
             usage = {}
    
ba0d007fb78b

xenapi: ensure finish_migration cleans on errors

https://github.com/openstack/novaJohn GarbuttJul 24, 2013via ghsa
3 files changed · +112 63
  • nova/tests/virt/xenapi/stubs.py+5 0 modified
    @@ -299,6 +299,9 @@ def fake_move_disks(self, instance, disk_info):
             vdi_rec['other_config']['nova_disk_type'] = 'root'
             return {'uuid': vdi_rec['uuid'], 'ref': vdi_ref}
     
    +    def fake_wait_for_instance_to_start(self, *args):
    +        pass
    +
         def fake_get_vdi(session, vm_ref):
             vdi_ref_parent = fake.create_vdi('derp-parent', fakesr)
             vdi_rec_parent = fake.get_record('VDI', vdi_ref_parent)
    @@ -320,6 +323,8 @@ def fake_generate_ephemeral(*args):
             pass
     
         stubs.Set(vmops.VMOps, '_destroy', fake_destroy)
    +    stubs.Set(vmops.VMOps, '_wait_for_instance_to_start',
    +              fake_wait_for_instance_to_start)
         stubs.Set(vm_utils, 'move_disks', fake_move_disks)
         stubs.Set(vm_utils, 'scan_default_sr', fake_sr)
         stubs.Set(vm_utils, 'get_vdi_for_vm_safely', fake_get_vdi)
    
  • nova/tests/virt/xenapi/test_vmops.py+47 17 modified
    @@ -404,7 +404,8 @@ def test_spawn_performs_rollback_and_throws_exception(self):
             self.assertRaises(test.TestingException, self._test_spawn,
                               throw_exception=test.TestingException())
     
    -    def test_finish_migration(self):
    +    def _test_finish_migration(self, power_on=True, resize_instance=True,
    +                               throw_exception=None):
             self._stub_out_common()
             self.mox.StubOutWithMock(vm_utils, "move_disks")
             self.mox.StubOutWithMock(self.vmops, "_attach_mapped_block_devices")
    @@ -416,49 +417,78 @@ def test_finish_migration(self):
             disk_info = "disk_info"
             network_info = "net_info"
             image_meta = {"id": "image_id"}
    -        resize_instance = True
             block_device_info = "bdi"
             session = self.vmops._session
     
    -        root_vdi = "root_vdi"
    +        self.vmops._ensure_instance_name_unique(name_label)
    +        self.vmops._ensure_enough_free_mem(instance)
    +
    +        di_type = "di_type"
    +        vm_utils.determine_disk_image_type(image_meta).AndReturn(di_type)
    +
    +        root_vdi = {"ref": "fake_ref"}
             vdis = {"root": root_vdi}
             vm_utils.move_disks(self.vmops._session, instance,
                                 disk_info).AndReturn(root_vdi)
     
    -        self.vmops._resize_up_root_vdi(instance, root_vdi)
    -
             kernel_file = "kernel"
             ramdisk_file = "ramdisk"
             vm_utils.create_kernel_and_ramdisk(context, session,
                     instance, name_label).AndReturn((kernel_file, ramdisk_file))
     
    -        di_type = "di_type"
    -        vm_utils.determine_disk_image_type(image_meta).AndReturn(di_type)
    -        self.vmops._ensure_instance_name_unique(name_label)
    -        self.vmops._ensure_enough_free_mem(instance)
             vm_ref = "fake_vm_ref"
             self.vmops._create_vm_record(context, instance, name_label, vdis,
                     di_type, kernel_file, ramdisk_file).AndReturn(vm_ref)
     
    -        self.vmops._attach_disks(instance, vm_ref, name_label, vdis, di_type)
    +        if resize_instance:
    +            self.vmops._resize_up_root_vdi(instance, root_vdi)
    +        self.vmops._attach_disks(instance, vm_ref, name_label, vdis, di_type,
    +                                 None, None)
    +        self.vmops._attach_mapped_block_devices(instance, block_device_info)
     
    +        self.vmops._inject_instance_metadata(instance, vm_ref)
    +        self.vmops._inject_auto_disk_config(instance, vm_ref)
             self.vmops._file_inject_vm_settings(instance, vm_ref, vdis,
                                                 network_info)
    -        self.vmops._create_vifs(instance, vm_ref, network_info)
             self.vmops.inject_network_info(instance, network_info, vm_ref)
    -        self.vmops._inject_instance_metadata(instance, vm_ref)
     
    -        self.vmops._attach_mapped_block_devices(instance, block_device_info)
    +        self.vmops._create_vifs(instance, vm_ref, network_info)
    +        self.vmops.firewall_driver.setup_basic_filtering(instance,
    +                network_info).AndRaise(NotImplementedError)
    +        self.vmops.firewall_driver.prepare_instance_filter(instance,
    +                                                           network_info)
     
    -        self.vmops._start(instance, vm_ref)
    +        if power_on:
    +            self.vmops._start(instance, vm_ref)
    +            self.vmops._wait_for_instance_to_start(instance, vm_ref)
     
    -        self.vmops._update_instance_progress(context, instance,
    -                                             step=5, total_steps=5)
    +        self.vmops.firewall_driver.apply_instance_filter(instance,
    +                                                         network_info)
    +
    +        last_call = self.vmops._update_instance_progress(context, instance,
    +                                                        step=5, total_steps=5)
    +        if throw_exception:
    +            last_call.AndRaise(throw_exception)
    +            self.vmops._destroy(instance, vm_ref, network_info=network_info)
    +            vm_utils.destroy_kernel_ramdisk(self.vmops._session, instance,
    +                                            kernel_file, ramdisk_file)
    +            vm_utils.safe_destroy_vdis(self.vmops._session, ["fake_ref"])
     
             self.mox.ReplayAll()
             self.vmops.finish_migration(context, migration, instance, disk_info,
                                         network_info, image_meta, resize_instance,
    -                                    block_device_info)
    +                                    block_device_info, power_on)
    +
    +    def test_finish_migration(self):
    +        self._test_finish_migration()
    +
    +    def test_finish_migration_no_power_on(self):
    +        self._test_finish_migration(power_on=False, resize_instance=False)
    +
    +    def test_finish_migrate_performs_rollback_on_error(self):
    +        self.assertRaises(test.TestingException, self._test_finish_migration,
    +                          power_on=False, resize_instance=False,
    +                          throw_exception=test.TestingException())
     
         def test_remove_hostname(self):
             vm, vm_ref = self.create_vm("dummy")
    
  • nova/virt/xenapi/vmops.py+60 46 modified
    @@ -274,39 +274,32 @@ def _restore_orig_vm_and_cleanup_orphan(self, instance,
         def finish_migration(self, context, migration, instance, disk_info,
                              network_info, image_meta, resize_instance,
                              block_device_info=None, power_on=True):
    -        root_vdi = vm_utils.move_disks(self._session, instance, disk_info)
    -        vdis = {'root': root_vdi}
     
    -        if resize_instance:
    -            self._resize_up_root_vdi(instance, root_vdi)
    +        def null_step_decorator(f):
    +            return f
     
    -        name_label = instance['name']
    +        def create_disks_step(undo_mgr, disk_image_type, image_meta,
    +                              name_label):
    +            #TODO(johngarbutt) clean up the move_disks if this is not run
    +            root_vdi = vm_utils.move_disks(self._session, instance, disk_info)
     
    -        kernel_file, ramdisk_file = vm_utils.create_kernel_and_ramdisk(
    -                context, self._session, instance, name_label)
    -
    -        disk_image_type = vm_utils.determine_disk_image_type(image_meta)
    -        self._ensure_instance_name_unique(name_label)
    -        self._ensure_enough_free_mem(instance)
    -        vm_ref = self._create_vm_record(context, instance, name_label,
    -                vdis, disk_image_type, kernel_file, ramdisk_file)
    -
    -        self._attach_disks(instance, vm_ref, name_label, vdis,
    -                           disk_image_type)
    +            def undo_create_disks():
    +                vm_utils.safe_destroy_vdis(self._session, [root_vdi['ref']])
     
    -        self._file_inject_vm_settings(instance, vm_ref, vdis, network_info)
    -        self._create_vifs(instance, vm_ref, network_info)
    -        self.inject_network_info(instance, network_info, vm_ref)
    -        self._inject_instance_metadata(instance, vm_ref)
    +            undo_mgr.undo_with(undo_create_disks)
    +            return {'root': root_vdi}
     
    -        self._attach_mapped_block_devices(instance, block_device_info)
    +        def completed_callback():
    +            self._update_instance_progress(context, instance,
    +                                           step=5,
    +                                           total_steps=RESIZE_TOTAL_STEPS)
     
    -        # 5. Start VM
    -        if power_on:
    -            self._start(instance, vm_ref)
    -        self._update_instance_progress(context, instance,
    -                                       step=5,
    -                                       total_steps=RESIZE_TOTAL_STEPS)
    +        self._spawn(context, instance, image_meta, null_step_decorator,
    +                    create_disks_step, first_boot=False, injected_files=None,
    +                    admin_password=None, network_info=network_info,
    +                    block_device_info=block_device_info, name_label=None,
    +                    rescue=False, power_on=power_on, resize=resize_instance,
    +                    completed_callback=completed_callback)
     
         def _start(self, instance, vm_ref=None, bad_volumes_callback=None):
             """Power on a VM instance."""
    @@ -336,6 +329,7 @@ def _start(self, instance, vm_ref=None, bad_volumes_callback=None):
         def spawn(self, context, instance, image_meta, injected_files,
                   admin_password, network_info=None, block_device_info=None,
                   name_label=None, rescue=False):
    +
             if block_device_info:
                 LOG.debug(_("Block device information present: %s")
                           % block_device_info, instance=instance)
    @@ -345,18 +339,9 @@ def spawn(self, context, instance, image_meta, injected_files,
             step = make_step_decorator(context, instance,
                                        self._update_instance_progress)
     
    -        if name_label is None:
    -            name_label = instance['name']
    -
    -        self._ensure_instance_name_unique(name_label)
    -        self._ensure_enough_free_mem(instance)
    -
    -        @step
    -        def determine_disk_image_type_step(undo_mgr):
    -            return vm_utils.determine_disk_image_type(image_meta)
    -
             @step
    -        def create_disks_step(undo_mgr, disk_image_type, image_meta):
    +        def create_disks_step(undo_mgr, disk_image_type, image_meta,
    +                              name_label):
                 vdis = vm_utils.get_vdis_for_instance(context, self._session,
                             instance, name_label, image_meta.get('id'),
                             disk_image_type, block_device_info=block_device_info)
    @@ -369,6 +354,25 @@ def undo_create_disks():
                 undo_mgr.undo_with(undo_create_disks)
                 return vdis
     
    +        self._spawn(context, instance, image_meta, step, create_disks_step,
    +                    True, injected_files, admin_password,
    +                    network_info, block_device_info, name_label, rescue)
    +
    +    def _spawn(self, context, instance, image_meta, step, create_disks_step,
    +               first_boot, injected_files=None, admin_password=None,
    +               network_info=None, block_device_info=None,
    +               name_label=None, rescue=False, power_on=True, resize=True,
    +               completed_callback=None):
    +        if name_label is None:
    +            name_label = instance['name']
    +
    +        self._ensure_instance_name_unique(name_label)
    +        self._ensure_enough_free_mem(instance)
    +
    +        @step
    +        def determine_disk_image_type_step(undo_mgr):
    +            return vm_utils.determine_disk_image_type(image_meta)
    +
             @step
             def create_kernel_ramdisk_step(undo_mgr):
                 kernel_file, ramdisk_file = vm_utils.create_kernel_and_ramdisk(
    @@ -410,12 +414,15 @@ def attach_disks_step(undo_mgr, vm_ref, vdis, disk_image_type):
                                     instance=instance)
     
                 root_vdi = vdis.get('root')
    -            if root_vdi:
    +            if root_vdi and resize:
                     self._resize_up_root_vdi(instance, root_vdi)
     
                 self._attach_disks(instance, vm_ref, name_label, vdis,
                                    disk_image_type, admin_password,
                                    injected_files)
    +            if not first_boot:
    +                self._attach_mapped_block_devices(instance,
    +                                                  block_device_info)
     
                 if rescue:
                     # NOTE(johannes): Attach root disk to rescue VM now, before
    @@ -427,7 +434,8 @@ def attach_disks_step(undo_mgr, vm_ref, vdis, disk_image_type):
             def inject_instance_data_step(undo_mgr, vm_ref, vdis):
                 self._inject_instance_metadata(instance, vm_ref)
                 self._inject_auto_disk_config(instance, vm_ref)
    -            self._inject_hostname(instance, vm_ref, rescue)
    +            if first_boot:
    +                self._inject_hostname(instance, vm_ref, rescue)
                 self._file_inject_vm_settings(instance, vm_ref, vdis, network_info)
                 self.inject_network_info(instance, network_info, vm_ref)
     
    @@ -449,14 +457,16 @@ def setup_network_step(undo_mgr, vm_ref):
     
             @step
             def boot_instance_step(undo_mgr, vm_ref):
    -            self._start(instance, vm_ref)
    -            self._wait_for_instance_to_start(instance, vm_ref)
    +            if power_on:
    +                self._start(instance, vm_ref)
    +                self._wait_for_instance_to_start(instance, vm_ref)
     
             @step
             def configure_booted_instance_step(undo_mgr, vm_ref):
    -            self._configure_new_instance_with_agent(instance, vm_ref,
    -                    injected_files, admin_password)
    -            self._remove_hostname(instance, vm_ref)
    +            if first_boot:
    +                self._configure_new_instance_with_agent(instance, vm_ref,
    +                        injected_files, admin_password)
    +                self._remove_hostname(instance, vm_ref)
     
             @step
             def apply_security_group_filters_step(undo_mgr):
    @@ -471,7 +481,8 @@ def apply_security_group_filters_step(undo_mgr):
                 # first step is something that completes rather quickly.
                 disk_image_type = determine_disk_image_type_step(undo_mgr)
     
    -            vdis = create_disks_step(undo_mgr, disk_image_type, image_meta)
    +            vdis = create_disks_step(undo_mgr, disk_image_type, image_meta,
    +                                     name_label)
                 kernel_file, ramdisk_file = create_kernel_ramdisk_step(undo_mgr)
     
                 vm_ref = create_vm_record_step(undo_mgr, vdis, disk_image_type,
    @@ -485,6 +496,9 @@ def apply_security_group_filters_step(undo_mgr):
     
                 configure_booted_instance_step(undo_mgr, vm_ref)
                 apply_security_group_filters_step(undo_mgr)
    +
    +            if completed_callback:
    +                completed_callback()
             except Exception:
                 msg = _("Failed to spawn, rolling back")
                 undo_mgr.rollback_and_reraise(msg=msg, instance=instance)
    

Vulnerability mechanics

Generated by null/stub on May 9, 2026. Inputs: CWE entries + fix-commit diffs from this CVE's patches. Citations validated against bundle.

References

10

News mentions

0

No linked articles in our index yet.