From 6f1b89c224f0ea4ecf45cf0ef7a8927c5c88d763 Mon Sep 17 00:00:00 2001 From: Ed Bartosh Date: Tue, 13 Jun 2017 14:21:56 +0300 Subject: engine: implement listing wic images Implemented 'wic ls' functionality: - list image partitions - list directory content of vfat partitions [YOCTO #11283] (From OE-Core rev: 61667fabd5746caf773f73b3aeb2a04db13cba38) Signed-off-by: Ed Bartosh Signed-off-by: Richard Purdie --- scripts/lib/wic/engine.py | 84 +++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 82 insertions(+), 2 deletions(-) (limited to 'scripts/lib/wic') diff --git a/scripts/lib/wic/engine.py b/scripts/lib/wic/engine.py index e58beb7dce..95c8d1cc22 100644 --- a/scripts/lib/wic/engine.py +++ b/scripts/lib/wic/engine.py @@ -30,10 +30,15 @@ import logging import os +import tempfile + +from collections import namedtuple, OrderedDict +from distutils.spawn import find_executable from wic import WicError +from wic.filemap import sparse_copy from wic.pluginbase import PluginMgr -from wic.utils.misc import get_bitbake_var +from wic.utils.misc import get_bitbake_var, exec_cmd logger = logging.getLogger('wic') @@ -225,9 +230,84 @@ def wic_list(args, scripts_path): return False + +class Disk: + def __init__(self, imagepath, native_sysroot): + self.imagepath = imagepath + self.native_sysroot = native_sysroot + self._partitions = None + self._mdir = None + self._partimages = {} + + # find parted + self.paths = "/bin:/usr/bin:/usr/sbin:/sbin/" + if native_sysroot: + for path in self.paths.split(':'): + self.paths = "%s%s:%s" % (native_sysroot, path, self.paths) + + self.parted = find_executable("parted", self.paths) + if not self.parted: + raise WicError("Can't find executable parted") + + def __del__(self): + for path in self._partimages.values(): + os.unlink(path) + + @property + def partitions(self): + if self._partitions is None: + self._partitions = OrderedDict() + out = exec_cmd("%s -sm %s unit B print" % (self.parted, self.imagepath)) + parttype = namedtuple("Part", "pnum start end size fstype") + for line in out.splitlines()[2:]: + pnum, start, end, size, fstype = line.split(':')[:5] + partition = parttype(pnum, int(start[:-1]), int(end[:-1]), + int(size[:-1]), fstype) + self._partitions[pnum] = partition + + return self._partitions + + @property + def mdir(self): + if self._mdir is None: + self._mdir = find_executable("mdir", self.paths) + if not self._mdir: + raise WicError("Can't find executable mdir") + return self._mdir + + def _get_part_image(self, pnum): + if pnum not in self.partitions: + raise WicError("Partition %s is not in the image") + part = self.partitions[pnum] + if not part.fstype.startswith("fat"): + raise WicError("Not supported fstype: {}".format(part.fstype)) + if pnum not in self._partimages: + tmpf = tempfile.NamedTemporaryFile(prefix="wic-part") + dst_fname = tmpf.name + tmpf.close() + sparse_copy(self.imagepath, dst_fname, skip=part.start, length=part.size) + self._partimages[pnum] = dst_fname + + return self._partimages[pnum] + + def dir(self, pnum, path): + return exec_cmd("{} -i {} ::{}".format(self.mdir, + self._get_part_image(pnum), + path)) + def wic_ls(args, native_sysroot): """List contents of partitioned image or vfat partition.""" - pass + disk = Disk(args.path.image, native_sysroot) + if not args.path.part: + if disk.partitions: + print('Num Start End Size Fstype') + for part in disk.partitions.values(): + print("{:2s} {:12d} {:12d} {:12d} {}".format(\ + part.pnum, part.start, part.end, + part.size, part.fstype)) + else: + path = args.path.path or '/' + print(disk.dir(args.path.part, path)) def find_canned(scripts_path, file_name): """ -- cgit v1.2.3-54-g00ecf