Ejemplo n.º 1
0
    def test_match(self):
        """Test boot format populator helper match method"""
        if self.helper_class is None:
            return

        partition = PartitionDevice("testpartitiondev")
        storagedev = StorageDevice("teststoragedev")
        storagedev.bootable = True
        data = dict()

        fmt_class = get_device_format_class(self.helper_class._type_specifier)
        if fmt_class is None:
            self.skipTest("failed to look up format class for %s" %
                          self.helper_class._type_specifier)

        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier
        partition._bootable = self.helper_class._bootable
        min_size = fmt_class._min_size
        max_size = fmt_class._max_size
        partition._size = min_size
        storagedev._size = min_size

        if fmt_class._name:
            partition._parted_partition = FakePartedPart(
                partition, fmt_class._name)

        self.assertTrue(self.helper_class.match(data, partition))

        # These are only valid for partitions.
        self.assertFalse(self.helper_class.match(data, storagedev))

        data["ID_FS_TYPE"] += "x"
        self.assertFalse(self.helper_class.match(data, partition))
        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier

        if self.helper_class._bootable:
            partition._bootable = False
            self.assertFalse(self.helper_class.match(data, partition))
            partition._bootable = True

        if max_size:
            partition._size = max_size + 1
        elif min_size:
            partition._size = min_size - 1

        self.assertFalse(self.helper_class.match(data, partition))
        partition._size = min_size

        # we don't always match on the parted partition name, so allow
        # subclasses to decide
        if not self.name_mismatch_ok:
            orig = partition._parted_partition
            partition._parted_partition = FakePartedPart(
                partition, 'dontmatchanything')
            self.assertFalse(self.helper_class.match(data, partition))

            # shouldn't crash
            partition._parted_partition = None
            self.assertFalse(self.helper_class.match(data, partition))
            partition._parted_partition = orig
Ejemplo n.º 2
0
    def test_formats_methods(self):
        ##
        # get_device_format_class
        ##
        format_pairs = {
            None: formats.DeviceFormat,
            "bogus": None,
            "biosboot": formats.biosboot.BIOSBoot,
            "BIOS Boot": formats.biosboot.BIOSBoot,
            "nodev": formats.fs.NoDevFS
        }
        format_names = format_pairs.keys()
        format_values = [format_pairs[k] for k in format_names]

        self.assertEqual(
            [formats.get_device_format_class(x) for x in format_names],
            format_values)

        # A DeviceFormat object is returned if lookup by name fails
        for name in format_names:
            self.assertIs(formats.get_format(name).__class__,
                          formats.DeviceFormat if format_pairs[name] is None else format_pairs[name])
        # Consecutively constructed DeviceFormat objects have consecutive ids
        names = [key for key in format_pairs.keys() if format_pairs[key] is not None]
        objs = [formats.get_format(name) for name in names]
        ids = [obj.id for obj in objs]
        self.assertEqual(ids, list(range(ids[0], ids[0] + len(ids))))

        # Copy or deepcopy should preserve the id
        self.assertEqual(ids, [copy.copy(obj).id for obj in objs])
        self.assertEqual(ids, [copy.deepcopy(obj).id for obj in objs])
Ejemplo n.º 3
0
    def testFormatsMethods(self):
        ##
        ## get_device_format_class
        ##
        format_pairs = {
            None: None,
            "bogus": None,
            "biosboot": formats.biosboot.BIOSBoot,
            "BIOS Boot": formats.biosboot.BIOSBoot,
            "nodev": formats.fs.NoDevFS
        }
        format_names = format_pairs.keys()
        format_values = [format_pairs[k] for k in format_names]

        self.assertEqual(
            [formats.get_device_format_class(x) for x in format_names],
            format_values)

        ## A DeviceFormat object is returned if lookup by name fails
        for name in format_names:
            self.assertIs(
                formats.getFormat(name).__class__, formats.DeviceFormat
                if format_pairs[name] is None else format_pairs[name])
        ## Consecutively constructed DeviceFormat objects have consecutive ids
        names = [
            key for key in format_pairs.keys() if format_pairs[key] is not None
        ]
        objs = [formats.getFormat(name) for name in names]
        ids = [obj.id for obj in objs]
        self.assertEqual(ids, range(ids[0], ids[0] + len(ids)))

        ## Copy or deepcopy should preserve the id
        self.assertEqual(ids, [copy.copy(obj).id for obj in objs])
        self.assertEqual(ids, [copy.deepcopy(obj).id for obj in objs])
Ejemplo n.º 4
0
 def update_from_flags(self):
     if conf.storage.gpt:
         disklabel_class = get_device_format_class("disklabel")
         disklabel_types = disklabel_class.get_platform_label_types()
         if "gpt" not in disklabel_types:
             log.warning("GPT is not a supported disklabel on this platform. Using default "
                         "disklabel %s instead.", disklabel_types[0])
         else:
             disklabel_class.set_default_label_type("gpt")
Ejemplo n.º 5
0
 def update_from_flags(self):
     if flags.gpt:
         disklabel_class = get_device_format_class("disklabel")
         disklabel_types = disklabel_class.get_platform_label_types()
         if "gpt" not in disklabel_types:
             log.warning("GPT is not a supported disklabel on this platform. Using default "
                         "disklabel %s instead.", disklabel_types[0])
         else:
             disklabel_class.set_default_label_type("gpt")
Ejemplo n.º 6
0
    def test_match(self):
        """Test boot format populator helper match method"""
        if self.helper_class is None:
            return

        partition = PartitionDevice("testpartitiondev")
        storagedev = StorageDevice("teststoragedev")
        storagedev.bootable = True
        data = dict()

        fmt_class = get_device_format_class(self.helper_class._type_specifier)
        if fmt_class is None:
            self.skipTest("failed to look up format class for %s" % self.helper_class._type_specifier)

        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier
        partition._bootable = self.helper_class._bootable
        min_size = fmt_class._min_size
        max_size = fmt_class._max_size
        partition._size = min_size
        storagedev._size = min_size

        if fmt_class._name:
            partition._parted_partition = FakePartedPart(partition, fmt_class._name)

        self.assertTrue(self.helper_class.match(data, partition))

        # These are only valid for partitions.
        self.assertFalse(self.helper_class.match(data, storagedev))

        data["ID_FS_TYPE"] += "x"
        self.assertFalse(self.helper_class.match(data, partition))
        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier

        if self.helper_class._bootable:
            partition._bootable = False
            self.assertFalse(self.helper_class.match(data, partition))
            partition._bootable = True

        if max_size:
            partition._size = max_size + 1
        elif min_size:
            partition._size = min_size - 1

        self.assertFalse(self.helper_class.match(data, partition))
        partition._size = min_size

        # we don't always match on the parted partition name, so allow
        # subclasses to decide
        if not self.name_mismatch_ok:
            orig = partition._parted_partition
            partition._parted_partition = FakePartedPart(partition, 'dontmatchanything')
            self.assertFalse(self.helper_class.match(data, partition))

            # shouldn't crash
            partition._parted_partition = None
            self.assertFalse(self.helper_class.match(data, partition))
            partition._parted_partition = orig
Ejemplo n.º 7
0
 def _ctor_kwargs(self):
     kwargs = super()._ctor_kwargs()
     kwargs["level"] = "raid0"
     kwargs["parents"] = [Mock(name="member1", spec=StorageDevice),
                          Mock(name="member2", spec=StorageDevice)]
     mdmember = get_device_format_class("mdmember")
     for member in kwargs["parents"]:
         member.format = Mock(spec=mdmember, exists=True)
         member.protected = False
         member.readonly = False
     return kwargs
Ejemplo n.º 8
0
 def _ctor_kwargs(self):
     kwargs = super(MDRaidArrayDeviceMethodsTestCase, self)._ctor_kwargs()
     kwargs["level"] = "raid0"
     kwargs["parents"] = [Mock(name="member1", spec=StorageDevice),
                          Mock(name="member2", spec=StorageDevice)]
     mdmember = get_device_format_class("mdmember")
     for member in kwargs["parents"]:
         member.format = Mock(spec=mdmember, exists=True)
         member.protected = False
         member.readonly = False
     return kwargs
Ejemplo n.º 9
0
def _set_default_label_type():
    """Set up the default label type."""
    if not conf.storage.gpt:
        return

    disklabel_class = get_device_format_class("disklabel")
    disklabel_types = disklabel_class.get_platform_label_types()

    if "gpt" not in disklabel_types:
        log.warning("GPT is not a supported disklabel on this platform. "
                    "Using default disklabel %s instead.", disklabel_types[0])
        return

    disklabel_class.set_default_label_type("gpt")
Ejemplo n.º 10
0
    def test_get_helper(self, *args):
        if self.helper_class is None:
            return

        partition = PartitionDevice("testpartitiondev")
        data = dict()

        fmt_class = get_device_format_class(self.helper_class._type_specifier)
        if fmt_class is None:
            self.skipTest("failed to look up format class for %s" % self.helper_class._type_specifier)

        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier
        data["DEVTYPE"] = "partition"
        partition._bootable = self.helper_class._bootable
        partition._size = fmt_class._min_size
        self.assertEqual(get_format_helper(data, partition), self.helper_class)
Ejemplo n.º 11
0
    def test_get_helper(self, *args):
        if self.helper_class is None:
            return

        partition = PartitionDevice("testpartitiondev")
        data = dict()

        fmt_class = get_device_format_class(self.helper_class._type_specifier)
        if fmt_class is None:
            self.skipTest("failed to look up format class for %s" %
                          self.helper_class._type_specifier)

        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier
        data["DEVTYPE"] = "partition"
        partition._bootable = self.helper_class._bootable
        partition._size = fmt_class._min_size
        self.assertEqual(get_format_helper(data, partition), self.helper_class)
Ejemplo n.º 12
0
    def test_match(self):
        """Test boot format populator helper match method"""
        if self.helper_class is None:
            return

        partition = PartitionDevice("testpartitiondev")
        storagedev = StorageDevice("teststoragedev")
        storagedev.bootable = True
        data = dict()

        fmt_class = get_device_format_class(self.helper_class._type_specifier)
        if fmt_class is None:
            self.skipTest("failed to look up format class for %s" %
                          self.helper_class._type_specifier)

        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier
        partition._bootable = self.helper_class._bootable
        min_size = fmt_class._min_size
        max_size = fmt_class._max_size
        partition._size = min_size
        storagedev._size = min_size

        self.assertTrue(self.helper_class.match(data, partition))

        # These are only valid for partitions.
        self.assertFalse(self.helper_class.match(data, storagedev))

        data["ID_FS_TYPE"] += "x"
        self.assertFalse(self.helper_class.match(data, partition))
        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier

        if self.helper_class._bootable:
            partition._bootable = False
            self.assertFalse(self.helper_class.match(data, partition))
            partition._bootable = True

        if max_size:
            partition._size = max_size + 1
        elif min_size:
            partition._size = min_size - 1

        self.assertFalse(self.helper_class.match(data, partition))
        partition._size = min_size
Ejemplo n.º 13
0
    def test_match(self):
        """Test boot format populator helper match method"""
        if self.helper_class is None:
            return

        partition = PartitionDevice("testpartitiondev")
        storagedev = StorageDevice("teststoragedev")
        storagedev.bootable = True
        data = dict()

        fmt_class = get_device_format_class(self.helper_class._type_specifier)
        if fmt_class is None:
            self.skipTest("failed to look up format class for %s" % self.helper_class._type_specifier)

        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier
        partition._bootable = self.helper_class._bootable
        min_size = fmt_class._min_size
        max_size = fmt_class._max_size
        partition._size = min_size
        storagedev._size = min_size

        self.assertTrue(self.helper_class.match(data, partition))

        # These are only valid for partitions.
        self.assertFalse(self.helper_class.match(data, storagedev))

        data["ID_FS_TYPE"] += "x"
        self.assertFalse(self.helper_class.match(data, partition))
        data["ID_FS_TYPE"] = self.helper_class._base_type_specifier

        if self.helper_class._bootable:
            partition._bootable = False
            self.assertFalse(self.helper_class.match(data, partition))
            partition._bootable = True

        if max_size:
            partition._size = max_size + 1
        elif min_size:
            partition._size = min_size - 1

        self.assertFalse(self.helper_class.match(data, partition))
        partition._size = min_size
Ejemplo n.º 14
0
    def _parse_one_line(self, devspec, mountpoint, fstype, options, _dump="0", _passno="0"):
        """Parse an fstab entry for a device, return the corresponding device.

        The parameters correspond to the items in a single entry in the
        order in which they occur in the entry.

        :return: the device corresponding to the entry
        :rtype: :class:`blivet.devices.Device`
        """

        # no sense in doing any legwork for a noauto entry
        if "noauto" in options.split(","):
            log.info("ignoring noauto entry")
            raise UnrecognizedFSTabEntryError()

        # find device in the tree
        device = self.devicetree.resolve_device(devspec,
                                                crypt_tab=self.crypt_tab,
                                                blkid_tab=self.blkid_tab,
                                                options=options)

        if device:
            # fall through to the bottom of this block
            pass
        elif devspec.startswith("/dev/loop"):
            # FIXME: create devices.LoopDevice
            log.warning("completely ignoring your loop mount")
        elif ":" in devspec and fstype.startswith("nfs"):
            # NFS -- preserve but otherwise ignore
            device = NFSDevice(devspec,
                               fmt=get_format(fstype,
                                              exists=True,
                                              device=devspec))
        elif devspec.startswith("/") and fstype == "swap":
            # swap file
            device = FileDevice(devspec,
                                parents=get_containing_device(devspec, self.devicetree),
                                fmt=get_format(fstype,
                                               device=devspec,
                                               exists=True),
                                exists=True)
        elif fstype == "bind" or "bind" in options:
            # bind mount... set fstype so later comparison won't
            # turn up false positives
            fstype = "bind"

            # This is probably not going to do anything useful, so we'll
            # make sure to try again from FSSet.mount_filesystems. The bind
            # mount targets should be accessible by the time we try to do
            # the bind mount from there.
            parents = get_containing_device(devspec, self.devicetree)
            device = DirectoryDevice(devspec, parents=parents, exists=True)
            device.format = get_format("bind",
                                       device=device.path,
                                       exists=True)
        elif mountpoint in ("/proc", "/sys", "/dev/shm", "/dev/pts",
                            "/sys/fs/selinux", "/proc/bus/usb", "/sys/firmware/efi/efivars"):
            # drop these now -- we'll recreate later
            return None
        else:
            # nodev filesystem -- preserve or drop completely?
            fmt = get_format(fstype)
            fmt_class = get_device_format_class("nodev")
            if devspec == "none" or \
               (fmt_class and isinstance(fmt, fmt_class)):
                device = NoDevice(fmt=fmt)

        if device is None:
            log.error("failed to resolve %s (%s) from fstab", devspec,
                      fstype)
            raise UnrecognizedFSTabEntryError()

        device.setup()
        fmt = get_format(fstype, device=device.path, exists=True)
        if fstype != "auto" and None in (device.format.type, fmt.type):
            log.info("Unrecognized filesystem type for %s (%s)",
                     device.name, fstype)
            device.teardown()
            raise UnrecognizedFSTabEntryError()

        # make sure, if we're using a device from the tree, that
        # the device's format we found matches what's in the fstab
        ftype = getattr(fmt, "mount_type", fmt.type)
        dtype = getattr(device.format, "mount_type", device.format.type)
        if hasattr(fmt, "test_mount") and fstype != "auto" and ftype != dtype:
            log.info("fstab says %s at %s is %s", dtype, mountpoint, ftype)
            if fmt.test_mount():     # pylint: disable=no-member
                device.format = fmt
            else:
                device.teardown()
                raise FSTabTypeMismatchError(_(
                    "There is an entry in your /etc/fstab file that contains "
                    "an invalid or incorrect file system type. The file says that "
                    "{detected_type} at {mount_point} is {fstab_type}.").format(
                    detected_type=dtype,
                    mount_point=mountpoint,
                    fstab_type=ftype
                ))

        del ftype
        del dtype

        if hasattr(device.format, "mountpoint"):
            device.format.mountpoint = mountpoint

        device.format.options = options

        return device
Ejemplo n.º 15
0
    def _parse_one_line(self, devspec, mountpoint, fstype, options, _dump="0", _passno="0"):
        """Parse an fstab entry for a device, return the corresponding device.

        The parameters correspond to the items in a single entry in the
        order in which they occur in the entry.

        :return: the device corresponding to the entry
        :rtype: :class:`blivet.devices.Device`
        """

        # no sense in doing any legwork for a noauto entry
        if "noauto" in options.split(","):
            log.info("ignoring noauto entry")
            raise UnrecognizedFSTabEntryError()

        # find device in the tree
        device = self.devicetree.resolve_device(devspec,
                                                crypt_tab=self.crypt_tab,
                                                blkid_tab=self.blkid_tab,
                                                options=options)

        if device:
            # fall through to the bottom of this block
            pass
        elif devspec.startswith("/dev/loop"):
            # FIXME: create devices.LoopDevice
            log.warning("completely ignoring your loop mount")
        elif ":" in devspec and fstype.startswith("nfs"):
            # NFS -- preserve but otherwise ignore
            device = NFSDevice(devspec,
                               fmt=get_format(fstype,
                                              exists=True,
                                              device=devspec))
        elif devspec.startswith("/") and fstype == "swap":
            # swap file
            device = FileDevice(devspec,
                                parents=get_containing_device(devspec, self.devicetree),
                                fmt=get_format(fstype,
                                               device=devspec,
                                               exists=True),
                                exists=True)
        elif fstype == "bind" or "bind" in options:
            # bind mount... set fstype so later comparison won't
            # turn up false positives
            fstype = "bind"

            # This is probably not going to do anything useful, so we'll
            # make sure to try again from FSSet.mount_filesystems. The bind
            # mount targets should be accessible by the time we try to do
            # the bind mount from there.
            parents = get_containing_device(devspec, self.devicetree)
            device = DirectoryDevice(devspec, parents=parents, exists=True)
            device.format = get_format("bind",
                                       device=device.path,
                                       exists=True)
        elif mountpoint in ("/proc", "/sys", "/dev/shm", "/dev/pts",
                            "/sys/fs/selinux", "/proc/bus/usb", "/sys/firmware/efi/efivars"):
            # drop these now -- we'll recreate later
            return None
        else:
            # nodev filesystem -- preserve or drop completely?
            fmt = get_format(fstype)
            fmt_class = get_device_format_class("nodev")
            if devspec == "none" or \
               (fmt_class and isinstance(fmt, fmt_class)):
                device = NoDevice(fmt=fmt)

        if device is None:
            log.error("failed to resolve %s (%s) from fstab", devspec,
                      fstype)
            raise UnrecognizedFSTabEntryError()

        device.setup()
        fmt = get_format(fstype, device=device.path, exists=True)
        if fstype != "auto" and None in (device.format.type, fmt.type):
            log.info("Unrecognized filesystem type for %s (%s)",
                     device.name, fstype)
            device.teardown()
            raise UnrecognizedFSTabEntryError()

        # make sure, if we're using a device from the tree, that
        # the device's format we found matches what's in the fstab
        ftype = getattr(fmt, "mount_type", fmt.type)
        dtype = getattr(device.format, "mount_type", device.format.type)
        if hasattr(fmt, "test_mount") and fstype != "auto" and ftype != dtype:
            log.info("fstab says %s at %s is %s", dtype, mountpoint, ftype)
            if fmt.test_mount():     # pylint: disable=no-member
                device.format = fmt
            else:
                device.teardown()
                raise FSTabTypeMismatchError("%s: detected as %s, fstab says %s"
                                             % (mountpoint, dtype, ftype))
        del ftype
        del dtype

        if hasattr(device.format, "mountpoint"):
            device.format.mountpoint = mountpoint

        device.format.options = options

        return device