def _spawn_using_handoff(self, context, instance, xml, image_meta, handoff_info): image_properties = image_meta.get("properties", None) memory_snap_id = str(image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_MEM)) diskhash_snap_id = str(image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_DISK_HASH)) memhash_snap_id = str(image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_MEM_HASH)) basedisk_path = self._get_cache_image(context, instance, image_meta["id"]) basemem_path = self._get_cache_image(context, instance, memory_snap_id) diskhash_path = self._get_cache_image(context, instance, diskhash_snap_id) memhash_path = self._get_cache_image(context, instance, memhash_snap_id) base_vm_paths = [basedisk_path, basemem_path, diskhash_path, memhash_path] image_sha256 = image_properties.get(CloudletAPI.PROPERTY_KEY_BASE_UUID) snapshot_directory = libvirt_driver.CONF.libvirt.snapshots_directory fileutils.ensure_tree(snapshot_directory) synthesized_vm = None with utils.tempdir(dir=snapshot_directory) as tmpdir: uuidhex = uuid.uuid4().hex launch_diskpath = os.path.join(tmpdir, uuidhex + "-launch-disk") launch_memorypath = os.path.join(tmpdir, uuidhex + "-launch-memory") tmp_dir = mkdtemp(prefix="cloudlet-residue-") handoff_recv_datafile = os.path.join(tmp_dir, "handoff-data") # recv handoff data and synthesize disk img and memory snapshot try: ret_values = self._handoff_recv( base_vm_paths, image_sha256, handoff_recv_datafile, launch_diskpath, launch_memorypath ) # start VM launch_disk_size, launch_memory_size, disk_overlay_map, memory_overlay_map = ret_values synthesized_vm = self._handoff_launch_vm( xml, basedisk_path, basemem_path, launch_diskpath, launch_memorypath, int(launch_disk_size), int(launch_memory_size), disk_overlay_map, memory_overlay_map, ) # rettach NIC synthesis.rettach_nic(synthesized_vm.machine, synthesized_vm.old_xml_str, xml) except handoff.HandoffError as e: msg = "failed to perform VM handoff:\n" msg += str(e) raise exception.ImageNotFound(msg) finally: if os.path.exists(tmp_dir): shutil.rmtree(tmp_dir) if os.path.exists(launch_diskpath): os.remove(launch_diskpath) if os.path.exists(launch_memorypath): os.remove(launch_memorypath) return synthesized_vm
def resume_basevm(self, instance, xml, base_disk, base_memory, base_diskmeta, base_memmeta, base_hashvalue): """ resume base vm to create overlay vm """ options = synthesis.Options() options.TRIM_SUPPORT = True options.FREE_SUPPORT = False options.XRAY_SUPPORT = False options.DISK_ONLY = False options.ZIP_CONTAINER = True vm_overlay = synthesis.VM_Overlay(base_disk, options, base_mem=base_memory, base_diskmeta=base_diskmeta, base_memmeta=base_memmeta, base_hashvalue=base_hashvalue, nova_xml=xml, nova_util=libvirt_utils, nova_conn=self._conn) virt_dom = vm_overlay.resume_basevm() self.resumed_vm_dict[instance['uuid']] = vm_overlay synthesis.rettach_nic(virt_dom, vm_overlay.old_xml_str, xml)
def resume_basevm(self, instance, xml, base_disk, base_memory, base_diskmeta, base_memmeta, base_hashvalue): """ resume base vm to create overlay vm """ options = synthesis.Options() options.TRIM_SUPPORT = True options.FREE_SUPPORT = False options.XRAY_SUPPORT = False options.DISK_ONLY = False options.ZIP_CONTAINER = True vm_overlay = synthesis.VM_Overlay(base_disk, options, base_mem=base_memory, base_diskmeta=base_diskmeta, base_memmeta=base_memmeta, base_hashvalue=base_hashvalue, nova_xml=xml, nova_util=libvirt_utils, nova_conn=self._conn) virt_dom = vm_overlay.resume_basevm() self.resumed_vm_dict[instance['uuid']] = vm_overlay synthesis.rettach_nic(virt_dom, vm_overlay.old_xml_str, xml)
def _spawn_using_handoff(self, context, instance, xml, image_meta, handoff_info): image_properties = image_meta.get("properties", None) memory_snap_id = str( image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_MEM)) diskhash_snap_id = str( image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_DISK_HASH)) memhash_snap_id = str( image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_MEM_HASH)) basedisk_path = self._get_cache_image(context, instance, image_meta['id']) basemem_path = self._get_cache_image(context, instance, memory_snap_id) diskhash_path = self._get_cache_image(context, instance, diskhash_snap_id) memhash_path = self._get_cache_image(context, instance, memhash_snap_id) base_vm_paths = [ basedisk_path, basemem_path, diskhash_path, memhash_path ] image_sha256 = image_properties.get(CloudletAPI.PROPERTY_KEY_BASE_UUID) snapshot_directory = libvirt_driver.CONF.libvirt.snapshots_directory fileutils.ensure_tree(snapshot_directory) synthesized_vm = None with utils.tempdir(dir=snapshot_directory) as tmpdir: uuidhex = uuid.uuid4().hex launch_diskpath = os.path.join(tmpdir, uuidhex + "-launch-disk") launch_memorypath = os.path.join(tmpdir, uuidhex + "-launch-memory") tmp_dir = mkdtemp(prefix="cloudlet-residue-") handoff_recv_datafile = os.path.join(tmp_dir, "handoff-data") # recv handoff data and synthesize disk img and memory snapshot try: ret_values = self._handoff_recv(base_vm_paths, image_sha256, handoff_recv_datafile, launch_diskpath, launch_memorypath) # start VM launch_disk_size, launch_memory_size, \ disk_overlay_map, memory_overlay_map = ret_values synthesized_vm = self._handoff_launch_vm( xml, basedisk_path, basemem_path, launch_diskpath, launch_memorypath, int(launch_disk_size), int(launch_memory_size), disk_overlay_map, memory_overlay_map, ) # rettach NIC synthesis.rettach_nic(synthesized_vm.machine, synthesized_vm.old_xml_str, xml) except handoff.HandoffError as e: msg = "failed to perform VM handoff:\n" msg += str(e) raise exception.ImageNotFound(msg) finally: if os.path.exists(tmp_dir): shutil.rmtree(tmp_dir) if os.path.exists(launch_diskpath): os.remove(launch_diskpath) if os.path.exists(launch_memorypath): os.remove(launch_memorypath) return synthesized_vm
def _spawn_using_synthesis(self, context, instance, xml, image_meta, overlay_url): # download vm overlay overlay_package = VMOverlayPackage(overlay_url) meta_raw = overlay_package.read_meta() meta_info = msgpack.unpackb(meta_raw) basevm_sha256 = meta_info.get(Cloudlet_Const.META_BASE_VM_SHA256, None) image_properties = image_meta.get("properties", None) if image_properties is None: msg = "image does not have properties for cloudlet metadata" raise exception.ImageNotFound(msg) image_sha256 = image_properties.get(CloudletAPI.PROPERTY_KEY_BASE_UUID) # check basevm if basevm_sha256 != image_sha256: msg = "requested base vm is not compatible with openstack base disk %s != %s" \ % (basevm_sha256, image_sha256) raise exception.ImageNotFound(msg) memory_snap_id = str( image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_MEM)) diskhash_snap_id = str( image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_DISK_HASH)) memhash_snap_id = str( image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_MEM_HASH)) basedisk_path = self._get_cache_image(context, instance, image_meta['id']) basemem_path = self._get_cache_image(context, instance, memory_snap_id) diskhash_path = self._get_cache_image(context, instance, diskhash_snap_id) memhash_path = self._get_cache_image(context, instance, memhash_snap_id) # download blob fileutils.ensure_tree(libvirt_utils.get_instance_path(instance)) decomp_overlay = os.path.join( libvirt_utils.get_instance_path(instance), 'decomp_overlay') meta_info = compression.decomp_overlayzip(overlay_url, decomp_overlay) # recover VM launch_disk, launch_mem, fuse, delta_proc, fuse_proc = \ synthesis.recover_launchVM(basedisk_path, meta_info, decomp_overlay, base_mem=basemem_path, base_diskmeta=diskhash_path, base_memmeta=memhash_path) # resume VM LOG.info(_("Starting VM synthesis"), instance=instance) synthesized_vm = synthesis.SynthesizedVM(launch_disk, launch_mem, fuse, disk_only=False, qemu_args=False, nova_xml=xml, nova_conn=self._conn, nova_util=libvirt_utils) # testing non-thread resume delta_proc.start() fuse_proc.start() delta_proc.join() fuse_proc.join() LOG.info(_("Finish VM synthesis"), instance=instance) synthesized_vm.resume() # rettach NIC synthesis.rettach_nic(synthesized_vm.machine, synthesized_vm.old_xml_str, xml) return synthesized_vm
def _spawn_using_synthesis(self, context, instance, xml, image_meta, overlay_url): # download vm overlay overlay_package = VMOverlayPackage(overlay_url) meta_raw = overlay_package.read_meta() meta_info = msgpack.unpackb(meta_raw) basevm_sha256 = meta_info.get(Cloudlet_Const.META_BASE_VM_SHA256, None) image_properties = image_meta.get("properties", None) if image_properties is None: msg = "image does not have properties for cloudlet metadata" raise exception.ImageNotFound(msg) image_sha256 = image_properties.get(CloudletAPI.PROPERTY_KEY_BASE_UUID) # check basevm if basevm_sha256 != image_sha256: msg = "requested base vm is not compatible with openstack base disk %s != %s" % ( basevm_sha256, image_sha256, ) raise exception.ImageNotFound(msg) memory_snap_id = str(image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_MEM)) diskhash_snap_id = str(image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_DISK_HASH)) memhash_snap_id = str(image_properties.get(CloudletAPI.IMAGE_TYPE_BASE_MEM_HASH)) basedisk_path = self._get_cache_image(context, instance, image_meta["id"]) basemem_path = self._get_cache_image(context, instance, memory_snap_id) diskhash_path = self._get_cache_image(context, instance, diskhash_snap_id) memhash_path = self._get_cache_image(context, instance, memhash_snap_id) # download blob fileutils.ensure_tree(libvirt_utils.get_instance_path(instance)) decomp_overlay = os.path.join(libvirt_utils.get_instance_path(instance), "decomp_overlay") meta_info = compression.decomp_overlayzip(overlay_url, decomp_overlay) # recover VM launch_disk, launch_mem, fuse, delta_proc, fuse_proc = synthesis.recover_launchVM( basedisk_path, meta_info, decomp_overlay, base_mem=basemem_path, base_diskmeta=diskhash_path, base_memmeta=memhash_path, ) # resume VM LOG.info(_("Starting VM synthesis"), instance=instance) synthesized_vm = synthesis.SynthesizedVM( launch_disk, launch_mem, fuse, disk_only=False, qemu_args=False, nova_xml=xml, nova_conn=self._conn, nova_util=libvirt_utils, ) # testing non-thread resume delta_proc.start() fuse_proc.start() delta_proc.join() fuse_proc.join() LOG.info(_("Finish VM synthesis"), instance=instance) synthesized_vm.resume() # rettach NIC synthesis.rettach_nic(synthesized_vm.machine, synthesized_vm.old_xml_str, xml) return synthesized_vm