This provides a handy way to obtain sizes of devices. --- storage/devices.py | 132 +++++++++++++++++++++++++-------------------------- 1 files changed, 65 insertions(+), 67 deletions(-) diff --git a/storage/devices.py b/storage/devices.py index f75463f..d0b00b8 100644 --- a/storage/devices.py +++ b/storage/devices.py @@ -200,7 +200,7 @@ class Device(object): """ new = self.__class__.__new__(self.__class__) memo[id(self)] = new - shallow_copy_attrs = ('partedDisk', 'partedDevice', + shallow_copy_attrs = ('partedDisk', '_partedDevice', '_partedPartition', '_origPartedDisk', '_raidSet') for (attr, value) in self.__dict__.items(): @@ -411,6 +411,24 @@ class StorageDevice(Device): self.fstabComment = "" self._targetSize = self._size + self._partedDevice = None + + @property + def partedDevice(self): + if self.exists and self.status and not self._partedDevice: + log.debug("looking up parted Device: %s" % self.path) + + # We aren't guaranteed to be able to get a device. In + # particular, built-in USB flash readers show up as devices but + # do not always have any media present, so parted won't be able + # to find a device. + try: + self._partedDevice = parted.Device(path=self.path) + except _ped.DeviceException: + pass + + return self._partedDevice + def _getTargetSize(self): return self._targetSize @@ -440,10 +458,6 @@ class StorageDevice(Device): """ Device node representing this device. """ return "%s/%s" % (self._devDir, self.name) - def probe(self): - """ Probe for any missing information about this device. """ - raise NotImplementedError("probe method not defined for StorageDevice") - def updateSysfsPath(self): """ Update this device's sysfs path. """ log_method_call(self, self.name, status=self.status) @@ -515,10 +529,17 @@ class StorageDevice(Device): self.teardownParents(recursive=recursive) def _getSize(self): - """ Get the device's size, accounting for pending changes. """ + """ Get the device's size in MB, accounting for pending changes. """ + if self.exists and not self.mediaPresent: + return 0 + + if self.exists and self.partedDevice: + self._size = self.currentSize + size = self._size - if self.resizable and self.targetSize != size: + if self.exists and self.resizable and self.targetSize != size: size = self.targetSize + return size def _setSize(self, newsize): @@ -530,13 +551,15 @@ class StorageDevice(Device): size = property(lambda x: x._getSize(), lambda x, y: x._setSize(y), - doc="The device's size, accounting for pending changes") + doc="The device's size in MB, accounting for pending changes") @property def currentSize(self): """ The device's actual size. """ size = 0 - if self.exists: + if self.exists and self.partedDevice: + size = self.partedDevice.getSize() + elif self.exists: size = self._size return size @@ -656,19 +679,10 @@ class DiskDevice(StorageDevice): major=major, minor=minor, exists=True, sysfsPath=sysfsPath, parents=parents) - self.partedDevice = None self.partedDisk = None log.debug("looking up parted Device: %s" % self.path) - # We aren't guaranteed to be able to get a device. In particular, - # built-in USB flash readers show up as devices but do not always - # have any media present, so parted won't be able to find a device. - try: - self.partedDevice = parted.Device(path=self.path) - except _ped.DeviceException: - pass - if self.partedDevice: log.debug("creating parted Disk: %s" % self.path) if initlabel: @@ -693,8 +707,6 @@ class DiskDevice(StorageDevice): else: self._origPartedDisk = None - self.probe() - def __str__(self): s = StorageDevice.__str__(self) s += (" removable = %(removable)s partedDevice = %(partedDevice)r\n" @@ -719,12 +731,8 @@ class DiskDevice(StorageDevice): @property def size(self): """ The disk's size in MB """ - if not self.mediaPresent: - return 0 - - if not self._size: - self._size = self.partedDisk.device.getSize() - return self._size + return super(DiskDevice, self).size + #size = property(StorageDevice._getSize) def resetPartedDisk(self): """ Reset parted.Disk to reflect the actual layout of the disk. """ @@ -764,12 +772,7 @@ class DiskDevice(StorageDevice): pyparted should be able to tell us anything we want to know. size, disklabel type, maybe even partition layout """ - if not self.mediaPresent or not 'parted' in globals().keys(): - return - log_method_call(self, self.name, size=self.size, partedDevice=self.partedDevice) - if not self.size: - self._size = self.partedDevice.getSize() if not self.diskLabel: log.debug("setting %s diskLabel to %s" % (self.name, self.partedDisk.type)) @@ -1312,13 +1315,6 @@ class DMDevice(StorageDevice): {"target": self.target, "dmUuid": self.dmUuid}) return s - def probe(self): - """ Probe for any missing information about this device. - - target type, parents? - """ - raise NotImplementedError("probe method not defined for DMDevice") - @property def fstabSpec(self): """ Return the device specifier for use in /etc/fstab. """ @@ -1412,8 +1408,11 @@ class LUKSDevice(DMCryptDevice): @property def size(self): - # break off 2KB for the LUKS header - return float(self.slave.size) - (2.0 / 1024) + size = super(LUKSDevice, self).size + if not size: + # break off 2KB for the LUKS header + size = float(self.slave.size) - (2.0 / 1024) + return size def create(self, intf=None): """ Create the device. """ @@ -1439,6 +1438,10 @@ class LUKSDevice(DMCryptDevice): self.slave.setup() self.slave.format.setup() + # we always probe since the device may not be set up when we want + # information about it + self._size = self.currentSize + def teardown(self, recursive=False): """ Close, or tear down, a device. """ log_method_call(self, self.name, status=self.status) @@ -1896,13 +1899,6 @@ class LVMLogicalVolumeDevice(DMDevice): {"vgdev": self.vg, "percent": self.req_percent}) return s - def probe(self): - """ Probe for any missing information about this device. - - size - """ - raise NotImplementedError("probe method not defined for StorageDevice") - def _setSize(self, size): size = self.vg.align(numeric_type(size)) log.debug("trying to set lv %s size to %dMB" % (self.name, size)) @@ -1913,7 +1909,7 @@ class LVMLogicalVolumeDevice(DMDevice): log.debug("failed to set size: %dMB short" % (size - (self.vg.freeSpace + self._size),)) raise ValueError("not enough free space in volume group") - size = property(lambda d: d._size, _setSize) + size = property(StorageDevice._getSize, _setSize) @property def vg(self): @@ -1947,6 +1943,10 @@ class LVMLogicalVolumeDevice(DMDevice): self.vg.setup() lvm.lvactivate(self.vg.name, self._name) + # we always probe since the device may not be set up when we want + # information about it + self._size = self.currentSize + def teardown(self, recursive=None): """ Close, or tear down, a device. """ log_method_call(self, self.name, status=self.status) @@ -2053,8 +2053,9 @@ class MDRaidArrayDevice(StorageDevice): if not self.formatClass: raise DeviceError("cannot find class for 'mdmember'") - #self.probe() if self.exists and self.uuid: + # this is a hack to work around mdadm's insistence on giving + # really high minors to arrays it has no config entry for open("/etc/mdadm.conf", "a").write("ARRAY %s UUID=%s\n" % (self.path, self.uuid)) @@ -2064,6 +2065,7 @@ class MDRaidArrayDevice(StorageDevice): for device in self.devices: if size is None or device.size < size: size = device.size + return size def __str__(self): @@ -2199,6 +2201,11 @@ class MDRaidArrayDevice(StorageDevice): log.warning("failed to add member %s to md array %s: %s" % (device.path, self.path, e)) + if self.status: + # we always probe since the device may not be set up when we want + # information about it + self._size = self.currentSize + def _removeDevice(self, device): """ Remove a component device from the array. @@ -2276,6 +2283,10 @@ class MDRaidArrayDevice(StorageDevice): udev_settle() + # we always probe since the device may not be set up when we want + # information about it + self._size = self.currentSize + def teardown(self, recursive=None): """ Close, or tear down, a device. """ log_method_call(self, self.name, status=self.status) @@ -2449,6 +2460,10 @@ class DMRaidArrayDevice(DiskDevice): udev_settle() + # we always probe since the device may not be set up when we want + # information about it + self._size = self.currentSize + class MultipathDevice(DMDevice): """ A multipath device """ @@ -2475,13 +2490,6 @@ class MultipathDevice(DMDevice): parents=parents, sysfsPath=sysfsPath, exists=exists) - def probe(self): - """ Probe for any missing information about this device. - - size - """ - raise NotImplementedError("probe method not defined for MultipathDevice") - class NoDevice(StorageDevice): """ A nodev device for nodev filesystems like tmpfs. """ @@ -2672,6 +2680,7 @@ class iScsiDiskDevice(DiskDevice, NetworkStorageDevice): NetworkStorageDevice.__init__(self, self.iscsi_address) log.debug("created new iscsi disk %s %s:%d" % (self.iscsi_name, self.iscsi_address, self.iscsi_port)) + class OpticalDevice(StorageDevice): """ An optical drive, eg: cdrom, dvd+r, &c. @@ -2747,13 +2756,6 @@ class ZFCPDiskDevice(DiskDevice): {"devnum": self.devnum, "wwpn": self.wwpn, "fcplun": self.fcplun}) return s - def probe(self): - """ Probe for any missing information about this device. - - devnum, wwpn, fcplun - """ - raise NotImplementedError("probe method not defined for StorageDevice") - class DASDDevice(DiskDevice): """ A mainframe DASD. """ @@ -2765,10 +2767,6 @@ class DASDDevice(DiskDevice): major=major, minor=minor, parents=parents, sysfsPath=sysfsPath) - def probe(self): - """ Probe for any missing information about this device. """ - raise NotImplementedError("probe method not defined for StorageDevice") - class NFSDevice(StorageDevice, NetworkStorageDevice): """ An NFS device """ -- 1.6.0.6 _______________________________________________ Anaconda-devel-list mailing list Anaconda-devel-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/anaconda-devel-list