From: Nikos Skalkotos Date: Fri, 16 Mar 2012 15:26:44 +0000 (+0200) Subject: Split DiskDevice constructor in 2 parts X-Git-Tag: v0.1~133 X-Git-Url: https://code.grnet.gr/git/snf-image-creator/commitdiff_plain/0db22eac4faec43647948a439a17541d81e92e5b Split DiskDevice constructor in 2 parts In the constructor only variable initialization is performed. This is needed because the constructor is executed before the DiskDevice instance is appended to the device list, and if something fails there, then the resources may be cleaned up in an incorrect order. --- diff --git a/image_creator/disk.py b/image_creator/disk.py index 809a1a3..4ca3fd2 100644 --- a/image_creator/disk.py +++ b/image_creator/disk.py @@ -10,6 +10,7 @@ import uuid import re import sys import guestfs +import time class DiskError(Exception): @@ -78,6 +79,7 @@ class Disk(object): # Take a snapshot and return it to the user size = blockdev('--getsize', sourcedev) cowfd, cow = tempfile.mkstemp() + os.close(cowfd) self._add_cleanup(os.unlink, cow) # Create 1G cow sparse file dd('if=/dev/null', 'of=%s' % cow, 'bs=1k', 'seek=%d' % (1024 * 1024)) @@ -92,9 +94,9 @@ class Disk(object): self._add_cleanup(dmsetup, 'remove', snapshot) finally: os.unlink(table) - new_device = DiskDevice("/dev/mapper/%s" % snapshot) self._devices.append(new_device) + new_device.enable() return new_device def destroy_device(self, device): @@ -105,9 +107,9 @@ class Disk(object): device.destroy() -def progress_generator(total): +def progress_generator(label=''): position = 0; - for i in progress.bar(range(total)): + for i in progress.bar(range(100),''): if i < position: continue position = yield @@ -121,19 +123,31 @@ class DiskDevice(object): def __init__(self, device, bootable=True): """Create a new DiskDevice.""" + self.device = device self.bootable = bootable self.progress_bar = None self.g = guestfs.GuestFS() - self.g.add_drive_opts(device, readonly=0) + self.g.add_drive_opts(self.device, readonly=0) #self.g.set_trace(1) #self.g.set_verbose(1) + self.guestfs_enabled = False + + def enable(self): + """Enable a newly created DiskDevice""" + + self.progressbar = progress_generator() + self.progressbar.next() eh = self.g.set_event_callback(self.progress_callback, guestfs.EVENT_PROGRESS) self.g.launch() + self.guestfs_enabled = True self.g.delete_event_callback(eh) + if self.progressbar is not None: + self.progressbar.send(100) + self.progressbar = None roots = self.g.inspect_os() if len(roots) == 0: @@ -147,20 +161,21 @@ class DiskDevice(object): def destroy(self): """Destroy this DiskDevice instance.""" - self.g.umount_all() - self.g.sync() - # Close the guestfs handler + + if self.guestfs_enabled: + self.g.umount_all() + self.g.sync() + + # Close the guestfs handler if open self.g.close() def progress_callback(self, ev, eh, buf, array): position = array[2] total = array[3] - - if self.progress_bar is None: - self.progress_bar = progress_generator(total) - self.progress_bar.next() - self.progress_bar.send(position) + assert self.progress_bar is not None + + self.progress_bar.send((position * 100)//total) if position == total: self.progress_bar = None