Exemple #1
0
    def _write_fstab(self, image_rootfs):
        """overriden to generate fstab (temporarily) in rootfs. This is called
        from _create, make sure it doesn't get called from
        BaseImage.create()
        """
        if not image_rootfs:
            return

        fstab_path = image_rootfs + "/etc/fstab"
        if not os.path.isfile(fstab_path):
            return

        with open(fstab_path) as fstab:
            fstab_lines = fstab.readlines()

        if self._update_fstab(fstab_lines, self.parts):
            # copy rootfs dir to workdir to update fstab
            # as rootfs can be used by other tasks and can't be modified
            new_rootfs = os.path.realpath(os.path.join(self.workdir, "rootfs_copy"))
            copyhardlinktree(image_rootfs, new_rootfs)
            fstab_path = os.path.join(new_rootfs, 'etc/fstab')

            os.unlink(fstab_path)

            with open(fstab_path, "w") as fstab:
                fstab.writelines(fstab_lines)

            return new_rootfs
Exemple #2
0
    def _write_fstab(self, image_rootfs):
        """overriden to generate fstab (temporarily) in rootfs. This is called
        from _create, make sure it doesn't get called from
        BaseImage.create()
        """
        if not image_rootfs:
            return

        fstab_path = image_rootfs + "/etc/fstab"
        if not os.path.isfile(fstab_path):
            return

        with open(fstab_path) as fstab:
            fstab_lines = fstab.readlines()

        if self._update_fstab(fstab_lines, self.parts):
            # copy rootfs dir to workdir to update fstab
            # as rootfs can be used by other tasks and can't be modified
            new_rootfs = os.path.realpath(
                os.path.join(self.workdir, "rootfs_copy"))
            copyhardlinktree(image_rootfs, new_rootfs)
            fstab_path = os.path.join(new_rootfs, 'etc/fstab')

            os.unlink(fstab_path)

            with open(fstab_path, "w") as fstab:
                fstab.writelines(fstab_lines)

            return new_rootfs
Exemple #3
0
    def do_prepare_partition(cls, part, source_params, cr, cr_workdir,
                             oe_builddir, bootimg_dir, kernel_dir, krootfs_dir,
                             native_sysroot):
        """
        Called to do the actual content population for a partition i.e. it
        'prepares' the partition to be incorporated into the image.
        In this case, prepare content for legacy bios boot partition.
        """
        if part.rootfs_dir is None:
            if not 'ROOTFS_DIR' in krootfs_dir:
                raise WicError("Couldn't find --rootfs-dir, exiting")

            rootfs_dir = krootfs_dir['ROOTFS_DIR']
        else:
            if part.rootfs_dir in krootfs_dir:
                rootfs_dir = krootfs_dir[part.rootfs_dir]
            elif part.rootfs_dir:
                rootfs_dir = part.rootfs_dir
            else:
                raise WicError("Couldn't find --rootfs-dir=%s connection or "
                               "it is not a valid path, exiting" %
                               part.rootfs_dir)

        part.rootfs_dir = cls.__get_rootfs_dir(rootfs_dir)

        new_rootfs = None
        # Handle excluded paths.
        if part.exclude_path is not None:
            # We need a new rootfs directory we can delete files from. Copy to
            # workdir.
            new_rootfs = os.path.realpath(
                os.path.join(cr_workdir, "rootfs%d" % part.lineno))

            if os.path.lexists(new_rootfs):
                shutil.rmtree(os.path.join(new_rootfs))

            copyhardlinktree(part.rootfs_dir, new_rootfs)

            for orig_path in part.exclude_path:
                path = orig_path
                if os.path.isabs(path):
                    logger.error("Must be relative: --exclude-path=%s" %
                                 orig_path)
                    sys.exit(1)

                full_path = os.path.realpath(os.path.join(new_rootfs, path))

                # Disallow climbing outside of parent directory using '..',
                # because doing so could be quite disastrous (we will delete the
                # directory).
                if not full_path.startswith(new_rootfs):
                    logger.error("'%s' points to a path outside the rootfs" %
                                 orig_path)
                    sys.exit(1)

                if path.endswith(os.sep):
                    # Delete content only.
                    for entry in os.listdir(full_path):
                        full_entry = os.path.join(full_path, entry)
                        if os.path.isdir(
                                full_entry) and not os.path.islink(full_entry):
                            shutil.rmtree(full_entry)
                        else:
                            os.remove(full_entry)
                else:
                    # Delete whole directory.
                    shutil.rmtree(full_path)

        part.prepare_rootfs(cr_workdir, oe_builddir, new_rootfs
                            or part.rootfs_dir, native_sysroot)
Exemple #4
0
    def do_prepare_partition(cls, part, source_params, cr, cr_workdir,
                             oe_builddir, bootimg_dir, kernel_dir,
                             krootfs_dir, native_sysroot):
        """
        Called to do the actual content population for a partition i.e. it
        'prepares' the partition to be incorporated into the image.
        In this case, prepare content for legacy bios boot partition.
        """
        if part.rootfs_dir is None:
            if not 'ROOTFS_DIR' in krootfs_dir:
                raise WicError("Couldn't find --rootfs-dir, exiting")

            rootfs_dir = krootfs_dir['ROOTFS_DIR']
        else:
            if part.rootfs_dir in krootfs_dir:
                rootfs_dir = krootfs_dir[part.rootfs_dir]
            elif part.rootfs_dir:
                rootfs_dir = part.rootfs_dir
            else:
                raise WicError("Couldn't find --rootfs-dir=%s connection or "
                               "it is not a valid path, exiting" % part.rootfs_dir)

        real_rootfs_dir = cls.__get_rootfs_dir(rootfs_dir)

        # Handle excluded paths.
        if part.exclude_path is not None:
            # We need a new rootfs directory we can delete files from. Copy to
            # workdir.
            new_rootfs = os.path.realpath(os.path.join(cr_workdir, "rootfs"))

            if os.path.lexists(new_rootfs):
                shutil.rmtree(os.path.join(new_rootfs))

            copyhardlinktree(real_rootfs_dir, new_rootfs)

            real_rootfs_dir = new_rootfs

            for orig_path in part.exclude_path:
                path = orig_path
                if os.path.isabs(path):
                    logger.error("Must be relative: --exclude-path=%s" % orig_path)
                    sys.exit(1)

                full_path = os.path.realpath(os.path.join(new_rootfs, path))

                # Disallow climbing outside of parent directory using '..',
                # because doing so could be quite disastrous (we will delete the
                # directory).
                if not full_path.startswith(new_rootfs):
                    logger.error("'%s' points to a path outside the rootfs" % orig_path)
                    sys.exit(1)

                if path.endswith(os.sep):
                    # Delete content only.
                    for entry in os.listdir(full_path):
                        full_entry = os.path.join(full_path, entry)
                        if os.path.isdir(full_entry) and not os.path.islink(full_entry):
                            shutil.rmtree(full_entry)
                        else:
                            os.remove(full_entry)
                else:
                    # Delete whole directory.
                    shutil.rmtree(full_path)

        part.rootfs_dir = real_rootfs_dir
        part.prepare_rootfs(cr_workdir, oe_builddir,
                            real_rootfs_dir, native_sysroot)
Exemple #5
0
    def do_prepare_partition(cls, part, source_params, cr, cr_workdir,
                             oe_builddir, bootimg_dir, kernel_dir, krootfs_dir,
                             native_sysroot):
        """
        Called to do the actual content population for a partition i.e. it
        'prepares' the partition to be incorporated into the image.
        In this case, prepare content for legacy bios boot partition.
        """
        if part.rootfs_dir is None:
            if not 'ROOTFS_DIR' in krootfs_dir:
                raise WicError("Couldn't find --rootfs-dir, exiting")

            rootfs_dir = krootfs_dir['ROOTFS_DIR']
        else:
            if part.rootfs_dir in krootfs_dir:
                rootfs_dir = krootfs_dir[part.rootfs_dir]
            elif part.rootfs_dir:
                rootfs_dir = part.rootfs_dir
            else:
                raise WicError("Couldn't find --rootfs-dir=%s connection or "
                               "it is not a valid path, exiting" %
                               part.rootfs_dir)

        part.rootfs_dir = cls.__get_rootfs_dir(rootfs_dir)
        pseudo_dir = os.path.join(part.rootfs_dir, "../pseudo")
        if not os.path.lexists(pseudo_dir):
            logger.warn("%s folder does not exist. "
                        "Usernames and permissions will be invalid " %
                        pseudo_dir)
            pseudo_dir = None

        new_rootfs = None
        new_pseudo = None
        # Handle excluded paths.
        if part.exclude_path or part.include_path or part.change_directory:
            # We need a new rootfs directory we can delete files from. Copy to
            # workdir.
            new_rootfs = os.path.realpath(
                os.path.join(cr_workdir, "rootfs%d" % part.lineno))

            if os.path.lexists(new_rootfs):
                shutil.rmtree(os.path.join(new_rootfs))

            if part.change_directory:
                cd = part.change_directory
                if cd[-1] == '/':
                    cd = cd[:-1]
                orig_dir = cls.__validate_path("--change-directory",
                                               part.rootfs_dir, cd)
            else:
                orig_dir = part.rootfs_dir
            copyhardlinktree(orig_dir, new_rootfs)

            # Convert the pseudo directory to its new location
            if (pseudo_dir):
                new_pseudo = os.path.realpath(
                    os.path.join(cr_workdir, "pseudo%d" % part.lineno))
                if os.path.lexists(new_pseudo):
                    shutil.rmtree(new_pseudo)
                os.mkdir(new_pseudo)
                shutil.copy(os.path.join(pseudo_dir, "files.db"),
                            os.path.join(new_pseudo, "files.db"))

                pseudo_cmd = "%s -B -m %s -M %s" % (cls.__get_pseudo(
                    native_sysroot, new_rootfs,
                    new_pseudo), orig_dir, new_rootfs)
                exec_native_cmd(pseudo_cmd, native_sysroot)

            for in_path in part.include_path or []:
                #parse arguments
                include_path = in_path[0]
                if len(in_path) > 2:
                    logger.error(
                        "'Invalid number of arguments for include-path")
                    sys.exit(1)
                if len(in_path) == 2:
                    path = in_path[1]
                else:
                    path = None

                # Pack files to be included into a tar file.
                # We need to create a tar file, because that way we can keep the
                # permissions from the files even when they belong to different
                # pseudo enviroments.
                # If we simply copy files using copyhardlinktree/copytree... the
                # copied files will belong to the user running wic.
                tar_file = os.path.realpath(
                    os.path.join(cr_workdir,
                                 "include-path%d.tar" % part.lineno))
                if os.path.isfile(include_path):
                    parent = os.path.dirname(os.path.realpath(include_path))
                    tar_cmd = "tar c --owner=root --group=root -f %s -C %s %s" % (
                        tar_file, parent, os.path.relpath(
                            include_path, parent))
                    exec_native_cmd(tar_cmd, native_sysroot)
                else:
                    if include_path in krootfs_dir:
                        include_path = krootfs_dir[include_path]
                    include_path = cls.__get_rootfs_dir(include_path)
                    include_pseudo = os.path.join(include_path, "../pseudo")
                    if os.path.lexists(include_pseudo):
                        pseudo = cls.__get_pseudo(native_sysroot, include_path,
                                                  include_pseudo)
                        tar_cmd = "tar cf %s -C %s ." % (tar_file,
                                                         include_path)
                    else:
                        pseudo = None
                        tar_cmd = "tar c --owner=root --group=root -f %s -C %s ." % (
                            tar_file, include_path)
                    exec_native_cmd(tar_cmd, native_sysroot, pseudo)

                #create destination
                if path:
                    destination = cls.__validate_path("--include-path",
                                                      new_rootfs, path)
                    Path(destination).mkdir(parents=True, exist_ok=True)
                else:
                    destination = new_rootfs

                #extract destination
                untar_cmd = "tar xf %s -C %s" % (tar_file, destination)
                if new_pseudo:
                    pseudo = cls.__get_pseudo(native_sysroot, new_rootfs,
                                              new_pseudo)
                else:
                    pseudo = None
                exec_native_cmd(untar_cmd, native_sysroot, pseudo)
                os.remove(tar_file)

            for orig_path in part.exclude_path or []:
                path = orig_path

                full_path = cls.__validate_path("--exclude-path", new_rootfs,
                                                path)

                if not os.path.lexists(full_path):
                    continue

                if path.endswith(os.sep):
                    # Delete content only.
                    for entry in os.listdir(full_path):
                        full_entry = os.path.join(full_path, entry)
                        if os.path.isdir(
                                full_entry) and not os.path.islink(full_entry):
                            shutil.rmtree(full_entry)
                        else:
                            os.remove(full_entry)
                else:
                    # Delete whole directory.
                    shutil.rmtree(full_path)

        part.prepare_rootfs(cr_workdir,
                            oe_builddir,
                            new_rootfs or part.rootfs_dir,
                            native_sysroot,
                            pseudo_dir=new_pseudo or pseudo_dir)
    def do_prepare_partition(cls, part, source_params, cr, cr_workdir,
                             oe_builddir, bootimg_dir, kernel_dir, krootfs_dir,
                             native_sysroot):
        """
        Called to do the actual content population for a partition i.e. it
        'prepares' the partition to be incorporated into the image.
        In this case, prepare content for legacy bios boot partition.
        """
        if part.rootfs_dir is None:
            if not 'ROOTFS_DIR' in krootfs_dir:
                raise WicError("Couldn't find --rootfs-dir, exiting")

            rootfs_dir = krootfs_dir['ROOTFS_DIR']
        else:
            if part.rootfs_dir in krootfs_dir:
                rootfs_dir = krootfs_dir[part.rootfs_dir]
            elif part.rootfs_dir:
                rootfs_dir = part.rootfs_dir
            else:
                raise WicError("Couldn't find --rootfs-dir=%s connection or "
                               "it is not a valid path, exiting" %
                               part.rootfs_dir)

        part.rootfs_dir = cls.__get_rootfs_dir(rootfs_dir)

        new_rootfs = None
        # Handle excluded paths.
        if part.exclude_path or part.include_path or part.embed_rootfs:
            # We need a new rootfs directory we can delete files from. Copy to
            # workdir.
            new_rootfs = os.path.realpath(
                os.path.join(cr_workdir, "rootfs%d" % part.lineno))

            if os.path.lexists(new_rootfs):
                shutil.rmtree(os.path.join(new_rootfs))
            copyhardlinktree(part.rootfs_dir, new_rootfs)

            if os.path.lexists(os.path.join(new_rootfs, "../pseudo")):
                shutil.rmtree(os.path.join(new_rootfs, "../pseudo"))
            copytree(os.path.join(part.rootfs_dir, "../pseudo"),
                     os.path.join(new_rootfs, "../pseudo"))
            pseudo_cmd = "%s -B -m %s -M %s" % (cls.__get_pseudo(
                native_sysroot, new_rootfs), part.rootfs_dir, new_rootfs)
            exec_native_cmd(pseudo_cmd, native_sysroot)

            for path in part.include_path or []:
                copyhardlinktree(path, new_rootfs)

            for embed in part.embed_rootfs or []:
                [embed_rootfs, path] = embed
                #we need to remove the initial / for os.path.join to work
                if os.path.isabs(path):
                    path = path[1:]
                if embed_rootfs in krootfs_dir:
                    embed_rootfs = krootfs_dir[embed_rootfs]
                embed_rootfs = cls.__get_rootfs_dir(embed_rootfs)
                tar_file = os.path.realpath(os.path.join(
                    cr_workdir, "aux.tar"))
                tar_cmd = "%s tar cpf %s -C %s ." % (cls.__get_pseudo(
                    native_sysroot, embed_rootfs), tar_file, embed_rootfs)
                exec_native_cmd(tar_cmd, native_sysroot)
                untar_cmd = "%s tar xf %s -C %s ." % (cls.__get_pseudo(
                    native_sysroot,
                    new_rootfs), tar_file, os.path.join(new_rootfs, path))
                Path(os.path.join(new_rootfs, path)).mkdir(parents=True,
                                                           exist_ok=True)
                exec_native_cmd(untar_cmd, native_sysroot,
                                cls.__get_pseudo(native_sysroot, new_rootfs))
                os.remove(tar_file)

            for orig_path in part.exclude_path or []:
                path = orig_path
                if os.path.isabs(path):
                    logger.error("Must be relative: --exclude-path=%s" %
                                 orig_path)
                    sys.exit(1)

                full_path = os.path.realpath(os.path.join(new_rootfs, path))

                # Disallow climbing outside of parent directory using '..',
                # because doing so could be quite disastrous (we will delete the
                # directory).
                if not full_path.startswith(new_rootfs):
                    logger.error("'%s' points to a path outside the rootfs" %
                                 orig_path)
                    sys.exit(1)

                if path.endswith(os.sep):
                    # Delete content only.
                    for entry in os.listdir(full_path):
                        full_entry = os.path.join(full_path, entry)
                        if os.path.isdir(
                                full_entry) and not os.path.islink(full_entry):
                            shutil.rmtree(full_entry)
                        else:
                            os.remove(full_entry)
                else:
                    # Delete whole directory.
                    shutil.rmtree(full_path)

        part.prepare_rootfs(cr_workdir, oe_builddir, new_rootfs
                            or part.rootfs_dir, native_sysroot)
Exemple #7
0
    def do_prepare_partition(cls, part, source_params, cr, cr_workdir,
                             oe_builddir, bootimg_dir, kernel_dir, krootfs_dir,
                             native_sysroot):
        """
        Called to do the actual content population for a partition i.e. it
        'prepares' the partition to be incorporated into the image.
        In this case, prepare content for legacy bios boot partition.
        """
        if part.rootfs_dir is None:
            if not 'ROOTFS_DIR' in krootfs_dir:
                raise WicError("Couldn't find --rootfs-dir, exiting")

            rootfs_dir = krootfs_dir['ROOTFS_DIR']
        else:
            if part.rootfs_dir in krootfs_dir:
                rootfs_dir = krootfs_dir[part.rootfs_dir]
            elif part.rootfs_dir:
                rootfs_dir = part.rootfs_dir
            else:
                raise WicError("Couldn't find --rootfs-dir=%s connection or "
                               "it is not a valid path, exiting" %
                               part.rootfs_dir)

        part.rootfs_dir = cls.__get_rootfs_dir(rootfs_dir)
        part.has_fstab = os.path.exists(
            os.path.join(part.rootfs_dir, "etc/fstab"))
        pseudo_dir = os.path.join(part.rootfs_dir, "../pseudo")
        if not os.path.lexists(pseudo_dir):
            logger.warn("%s folder does not exist. "
                        "Usernames and permissions will be invalid " %
                        pseudo_dir)
            pseudo_dir = None

        new_rootfs = None
        new_pseudo = None
        # Handle excluded paths.
        if part.exclude_path or part.include_path or part.change_directory or part.update_fstab_in_rootfs:
            # We need a new rootfs directory we can safely modify without
            # interfering with other tasks. Copy to workdir.
            new_rootfs = os.path.realpath(
                os.path.join(cr_workdir, "rootfs%d" % part.lineno))

            if os.path.lexists(new_rootfs):
                shutil.rmtree(os.path.join(new_rootfs))

            if part.change_directory:
                cd = part.change_directory
                if cd[-1] == '/':
                    cd = cd[:-1]
                if os.path.isabs(cd):
                    logger.error("Must be relative: --change-directory=%s" %
                                 cd)
                    sys.exit(1)
                orig_dir = os.path.realpath(os.path.join(part.rootfs_dir, cd))
                if not orig_dir.startswith(part.rootfs_dir):
                    logger.error("'%s' points to a path outside the rootfs" %
                                 orig_dir)
                    sys.exit(1)

            else:
                orig_dir = part.rootfs_dir
            copyhardlinktree(orig_dir, new_rootfs)

            # Convert the pseudo directory to its new location
            if (pseudo_dir):
                new_pseudo = os.path.realpath(
                    os.path.join(cr_workdir, "pseudo%d" % part.lineno))
                if os.path.lexists(new_pseudo):
                    shutil.rmtree(new_pseudo)
                os.mkdir(new_pseudo)
                shutil.copy(os.path.join(pseudo_dir, "files.db"),
                            os.path.join(new_pseudo, "files.db"))

                pseudo_cmd = "%s -B -m %s -M %s" % (cls.__get_pseudo(
                    native_sysroot, new_rootfs,
                    new_pseudo), orig_dir, new_rootfs)
                exec_native_cmd(pseudo_cmd, native_sysroot)

            for path in part.include_path or []:
                copyhardlinktree(path, new_rootfs)

            for orig_path in part.exclude_path or []:
                path = orig_path
                if os.path.isabs(path):
                    logger.error("Must be relative: --exclude-path=%s" %
                                 orig_path)
                    sys.exit(1)

                full_path = os.path.realpath(os.path.join(new_rootfs, path))

                # Disallow climbing outside of parent directory using '..',
                # because doing so could be quite disastrous (we will delete the
                # directory).
                if not full_path.startswith(new_rootfs):
                    logger.error("'%s' points to a path outside the rootfs" %
                                 orig_path)
                    sys.exit(1)

                if new_pseudo:
                    pseudo = cls.__get_pseudo(native_sysroot, new_rootfs,
                                              new_pseudo)
                else:
                    pseudo = None
                if path.endswith(os.sep):
                    # Delete content only.
                    for entry in os.listdir(full_path):
                        full_entry = os.path.join(full_path, entry)
                        rm_cmd = "rm -rf %s" % (full_entry)
                        exec_native_cmd(rm_cmd, native_sysroot, pseudo)
                else:
                    # Delete whole directory.
                    rm_cmd = "rm -rf %s" % (full_path)
                    exec_native_cmd(rm_cmd, native_sysroot, pseudo)

            # Update part.has_fstab here as fstab may have been added or
            # removed by the above modifications.
            part.has_fstab = os.path.exists(
                os.path.join(new_rootfs, "etc/fstab"))
            if part.update_fstab_in_rootfs and part.has_fstab:
                fstab_path = os.path.join(new_rootfs, "etc/fstab")
                # Assume that fstab should always be owned by root with fixed permissions
                install_cmd = "install -m 0644 %s %s" % (
                    part.updated_fstab_path, fstab_path)
                if new_pseudo:
                    pseudo = cls.__get_pseudo(native_sysroot, new_rootfs,
                                              new_pseudo)
                else:
                    pseudo = None
                exec_native_cmd(install_cmd, native_sysroot, pseudo)

        part.prepare_rootfs(cr_workdir,
                            oe_builddir,
                            new_rootfs or part.rootfs_dir,
                            native_sysroot,
                            pseudo_dir=new_pseudo or pseudo_dir)