All of lore.kernel.org
 help / color / mirror / Atom feed
From: "Steve Sakoman" <steve@sakoman.com>
To: openembedded-core@lists.openembedded.org
Subject: [OE-core][dunfell 38/41] wic: Add --offset argument for partitions
Date: Wed, 30 Sep 2020 12:11:40 -1000	[thread overview]
Message-ID: <897aaff8961f7fe83634a3b0b94e19b43aea5857.1601502610.git.steve@sakoman.com> (raw)
In-Reply-To: <cover.1601502610.git.steve@sakoman.com>

From: Joshua Watt <JPEWhacker@gmail.com>

Add support for an --offset argument when defining a partition. Many
SoCs require that boot partitions be located at specific offsets. Prior
to this argument, most WKS files were using the --align attribute to
specify the location of these fixed partitions but this is not ideal
because in the event that the partition couldn't be placed in the
specified location, wic would move it to the next sector with that
alignment, often preventing the device from booting. Unlike the --align
argument, wic will fail if a partition cannot be placed at the exact
offset specified with --offset.

Changes in V2:
* Fixed a small typo that prevented test_fixed_size_error from passing

Signed-off-by: Joshua Watt <JPEWhacker@gmail.com>
Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>
(cherry picked from commit 467f84e12b96bc977d57575023517dd6f8ef7f29)
Signed-off-by: Steve Sakoman <steve@sakoman.com>
---
 meta/lib/oeqa/selftest/cases/wic.py      | 118 ++++++++++++++++++-----
 scripts/lib/wic/ksparser.py              |  46 +++++----
 scripts/lib/wic/partition.py             |   1 +
 scripts/lib/wic/plugins/imager/direct.py |  15 +++
 4 files changed, 135 insertions(+), 45 deletions(-)

diff --git a/meta/lib/oeqa/selftest/cases/wic.py b/meta/lib/oeqa/selftest/cases/wic.py
index 626a217e69..6d4068a527 100644
--- a/meta/lib/oeqa/selftest/cases/wic.py
+++ b/meta/lib/oeqa/selftest/cases/wic.py
@@ -639,41 +639,50 @@ class Wic2(WicTestCase):
             tempf.write("part " \
                      "--source rootfs --ondisk hda --align 4 --fixed-size %d "
                      "--fstype=ext4\n" % size)
-        wksname = os.path.splitext(os.path.basename(wkspath))[0]
 
-        return wkspath, wksname
+        return wkspath
 
-    def test_fixed_size(self):
-        """
-        Test creation of a simple image with partition size controlled through
-        --fixed-size flag
-        """
-        wkspath, wksname = Wic2._make_fixed_size_wks(200)
+    def _get_wic_partitions(self, wkspath, native_sysroot=None, ignore_status=False):
+        p = runCmd("wic create %s -e core-image-minimal -o %s" % (wkspath, self.resultdir),
+                   ignore_status=ignore_status)
+
+        if p.status:
+            return (p, None)
+
+        wksname = os.path.splitext(os.path.basename(wkspath))[0]
 
-        runCmd("wic create %s -e core-image-minimal -o %s" \
-                                   % (wkspath, self.resultdir))
-        os.remove(wkspath)
         wicout = glob(self.resultdir + "%s-*direct" % wksname)
-        self.assertEqual(1, len(wicout))
+
+        if not wicout:
+            return (p, None)
 
         wicimg = wicout[0]
 
-        native_sysroot = get_bb_var("RECIPE_SYSROOT_NATIVE", "wic-tools")
+        if not native_sysroot:
+            native_sysroot = get_bb_var("RECIPE_SYSROOT_NATIVE", "wic-tools")
 
         # verify partition size with wic
-        res = runCmd("parted -m %s unit mib p 2>/dev/null" % wicimg,
+        res = runCmd("parted -m %s unit kib p 2>/dev/null" % wicimg,
                      native_sysroot=native_sysroot)
 
         # parse parted output which looks like this:
         # BYT;\n
         # /var/tmp/wic/build/tmpfwvjjkf_-201611101222-hda.direct:200MiB:file:512:512:msdos::;\n
         # 1:0.00MiB:200MiB:200MiB:ext4::;\n
-        partlns = res.output.splitlines()[2:]
+        return (p, res.output.splitlines()[2:])
 
-        self.assertEqual(1, len(partlns),
-                         msg="Partition list '%s'" % res.output)
-        self.assertEqual("1:0.00MiB:200MiB:200MiB:ext4::;", partlns[0],
-                         msg="Partition list '%s'" % res.output)
+    def test_fixed_size(self):
+        """
+        Test creation of a simple image with partition size controlled through
+        --fixed-size flag
+        """
+        wkspath = Wic2._make_fixed_size_wks(200)
+        _, partlns = self._get_wic_partitions(wkspath)
+        os.remove(wkspath)
+
+        self.assertEqual(partlns, [
+                        "1:4.00kiB:204804kiB:204800kiB:ext4::;",
+                        ])
 
     def test_fixed_size_error(self):
         """
@@ -681,13 +690,72 @@ class Wic2(WicTestCase):
         --fixed-size flag. The size of partition is intentionally set to 1MiB
         in order to trigger an error in wic.
         """
-        wkspath, wksname = Wic2._make_fixed_size_wks(1)
-
-        self.assertEqual(1, runCmd("wic create %s -e core-image-minimal -o %s" \
-                                   % (wkspath, self.resultdir), ignore_status=True).status)
+        wkspath = Wic2._make_fixed_size_wks(1)
+        p, _ = self._get_wic_partitions(wkspath, ignore_status=True)
         os.remove(wkspath)
-        wicout = glob(self.resultdir + "%s-*direct" % wksname)
-        self.assertEqual(0, len(wicout))
+
+        self.assertNotEqual(p.status, 0, "wic exited successfully when an error was expected:\n%s" % p.output)
+
+    def test_offset(self):
+        native_sysroot = get_bb_var("RECIPE_SYSROOT_NATIVE", "wic-tools")
+
+        with NamedTemporaryFile("w", suffix=".wks") as tempf:
+            # Test that partitions are placed at the correct offsets, default KB
+            tempf.write("bootloader --ptable gpt\n" \
+                        "part /    --source rootfs --ondisk hda --offset 32     --fixed-size 100M --fstype=ext4\n" \
+                        "part /bar                 --ondisk hda --offset 102432 --fixed-size 100M --fstype=ext4\n")
+            tempf.flush()
+
+            _, partlns = self._get_wic_partitions(tempf.name, native_sysroot)
+            self.assertEqual(partlns, [
+                "1:32.0kiB:102432kiB:102400kiB:ext4:primary:;",
+                "2:102432kiB:204832kiB:102400kiB:ext4:primary:;",
+                ])
+
+        with NamedTemporaryFile("w", suffix=".wks") as tempf:
+            # Test that partitions are placed at the correct offsets, same with explicit KB
+            tempf.write("bootloader --ptable gpt\n" \
+                        "part /    --source rootfs --ondisk hda --offset 32K     --fixed-size 100M --fstype=ext4\n" \
+                        "part /bar                 --ondisk hda --offset 102432K --fixed-size 100M --fstype=ext4\n")
+            tempf.flush()
+
+            _, partlns = self._get_wic_partitions(tempf.name, native_sysroot)
+            self.assertEqual(partlns, [
+                "1:32.0kiB:102432kiB:102400kiB:ext4:primary:;",
+                "2:102432kiB:204832kiB:102400kiB:ext4:primary:;",
+                ])
+
+        with NamedTemporaryFile("w", suffix=".wks") as tempf:
+            # Test that partitions are placed at the correct offsets using MB
+            tempf.write("bootloader --ptable gpt\n" \
+                        "part /    --source rootfs --ondisk hda --offset 32K  --fixed-size 100M --fstype=ext4\n" \
+                        "part /bar                 --ondisk hda --offset 101M --fixed-size 100M --fstype=ext4\n")
+            tempf.flush()
+
+            _, partlns = self._get_wic_partitions(tempf.name, native_sysroot)
+            self.assertEqual(partlns, [
+                "1:32.0kiB:102432kiB:102400kiB:ext4:primary:;",
+                "2:103424kiB:205824kiB:102400kiB:ext4:primary:;",
+                ])
+
+        with NamedTemporaryFile("w", suffix=".wks") as tempf:
+            # Test that image creation fails if the partitions would overlap
+            tempf.write("bootloader --ptable gpt\n" \
+                        "part /    --source rootfs --ondisk hda --offset 32     --fixed-size 100M --fstype=ext4\n" \
+                        "part /bar                 --ondisk hda --offset 102431 --fixed-size 100M --fstype=ext4\n")
+            tempf.flush()
+
+            p, _ = self._get_wic_partitions(tempf.name, ignore_status=True)
+            self.assertNotEqual(p.status, 0, "wic exited successfully when an error was expected:\n%s" % p.output)
+
+        with NamedTemporaryFile("w", suffix=".wks") as tempf:
+            # Test that partitions are not allowed to overlap with the booloader
+            tempf.write("bootloader --ptable gpt\n" \
+                        "part /    --source rootfs --ondisk hda --offset 8 --fixed-size 100M --fstype=ext4\n")
+            tempf.flush()
+
+            p, _ = self._get_wic_partitions(tempf.name, ignore_status=True)
+            self.assertNotEqual(p.status, 0, "wic exited successfully when an error was expected:\n%s" % p.output)
 
     @only_for_arch(['i586', 'i686', 'x86_64'])
     def test_rawcopy_plugin_qemu(self):
diff --git a/scripts/lib/wic/ksparser.py b/scripts/lib/wic/ksparser.py
index 650b976223..f32315c631 100644
--- a/scripts/lib/wic/ksparser.py
+++ b/scripts/lib/wic/ksparser.py
@@ -51,26 +51,31 @@ class KickStartParser(ArgumentParser):
     def error(self, message):
         raise ArgumentError(None, message)
 
-def sizetype(arg):
-    """
-    Custom type for ArgumentParser
-    Converts size string in <num>[K|k|M|G] format into the integer value
-    """
-    if arg.isdigit():
-        return int(arg) * 1024
+def sizetype(default):
+    def f(arg):
+        """
+        Custom type for ArgumentParser
+        Converts size string in <num>[K|k|M|G] format into the integer value
+        """
+        try:
+            suffix = default
+            size = int(arg)
+        except ValueError:
+            try:
+                suffix = arg[-1:]
+                size = int(arg[:-1])
+            except ValueError:
+                raise ArgumentTypeError("Invalid size: %r" % arg)
+
+        if suffix == "k" or suffix == "K":
+            return size
+        if suffix == "M":
+            return size * 1024
+        if suffix == "G":
+            return size * 1024 * 1024
 
-    if not arg[:-1].isdigit():
         raise ArgumentTypeError("Invalid size: %r" % arg)
-
-    size = int(arg[:-1])
-    if arg.endswith("k") or arg.endswith("K"):
-        return size
-    if arg.endswith("M"):
-        return size * 1024
-    if arg.endswith("G"):
-        return size * 1024 * 1024
-
-    raise ArgumentTypeError("Invalid size: %r" % arg)
+    return f
 
 def overheadtype(arg):
     """
@@ -136,6 +141,7 @@ class KickStart():
         part.add_argument('mountpoint', nargs='?')
         part.add_argument('--active', action='store_true')
         part.add_argument('--align', type=int)
+        part.add_argument('--offset', type=sizetype("K"))
         part.add_argument('--exclude-path', nargs='+')
         part.add_argument('--include-path', nargs='+')
         part.add_argument("--extra-space", type=sizetype)
@@ -160,8 +166,8 @@ class KickStart():
         # --error, but since nesting mutually exclusive groups does not work,
         # ----extra-space/--overhead-factor are handled later
         sizeexcl = part.add_mutually_exclusive_group()
-        sizeexcl.add_argument('--size', type=sizetype, default=0)
-        sizeexcl.add_argument('--fixed-size', type=sizetype, default=0)
+        sizeexcl.add_argument('--size', type=sizetype("M"), default=0)
+        sizeexcl.add_argument('--fixed-size', type=sizetype("M"), default=0)
 
         part.add_argument('--source')
         part.add_argument('--sourceparams')
diff --git a/scripts/lib/wic/partition.py b/scripts/lib/wic/partition.py
index 2d95f78439..3490b4e75d 100644
--- a/scripts/lib/wic/partition.py
+++ b/scripts/lib/wic/partition.py
@@ -39,6 +39,7 @@ class Partition():
         self.mountpoint = args.mountpoint
         self.no_table = args.no_table
         self.num = None
+        self.offset = args.offset
         self.overhead_factor = args.overhead_factor
         self.part_name = args.part_name
         self.part_type = args.part_type
diff --git a/scripts/lib/wic/plugins/imager/direct.py b/scripts/lib/wic/plugins/imager/direct.py
index 2d06c242b6..1f65a7afe5 100644
--- a/scripts/lib/wic/plugins/imager/direct.py
+++ b/scripts/lib/wic/plugins/imager/direct.py
@@ -428,6 +428,21 @@ class PartitionedImage():
                     # increase the offset so we actually start the partition on right alignment
                     self.offset += align_sectors
 
+            if part.offset is not None:
+                offset = (part.offset * 1024) // self.sector_size
+
+                if offset * self.sector_size != part.offset * 1024:
+                    raise WicError("Could not place %s%s at offset %dK with sector size %d" % (part.disk, self.numpart, part.offset, self.sector_size))
+
+                delta = offset - self.offset
+                if delta < 0:
+                    raise WicError("Could not place %s%s at offset %dK: next free sector is %d (delta: %d)" % (part.disk, self.numpart, part.offset, offset, delta))
+
+                logger.debug("Skipping %d sectors to place %s%s at offset %dK",
+                             delta, part.disk, self.numpart, part.offset)
+
+                self.offset = offset
+
             part.start = self.offset
             self.offset += part.size_sec
 
-- 
2.17.1


  parent reply	other threads:[~2020-09-30 22:15 UTC|newest]

Thread overview: 42+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-09-30 22:11 [OE-core][dunfell 00/41] Patch review Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 01/41] python3-markupsafe: Import from meta-oe/meta-python Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 02/41] python3-jinja2: " Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 03/41] buildtools-tarball: Add python3-jinja2 Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 04/41] site: Make sys_siglist default to no Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 05/41] qemu : fix CVE-2020-16092 Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 06/41] bash : inlcude patch 17 & 18 Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 07/41] xserver-xorg: fix CVE-2020-14346/14361/14362 Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 08/41] libx11: fix CVE-2020-14363 Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 09/41] cve-update-db-native: be less magical about checking whether the cve-check class is enabled Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 10/41] cve-update-db-native: move -journal checking into do_fetch Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 11/41] cve-update-db-native: remove unused variable Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 12/41] alsa-plugins: improve .la removal Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 13/41] sato-screenshot: " Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 14/41] insane: Check for feature check variables not being used Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 15/41] insane: check for missing update-alternatives inherit Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 16/41] xinput-calibrator: change SRC_URI to branch with libinput support Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 17/41] dropbear/openssh: Lower priority of key generation Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 18/41] testexport: rename create_tarball method Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 19/41] packagegroups: remove strace and lttng-tools for rv32/musl Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 20/41] curl: Change SRC_URI from http to https Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 21/41] meta: add/fix invalid Upstream-Status tags Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 22/41] buildtools: Handle generic environment setup injection Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 23/41] buildtools-tarball: Fix conflicts with oe-selftest and other tooling Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 24/41] oeqa/qemurunner: Increase serial timeout Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 25/41] oeqa/selftest/incompatible_lib: Fix append usage Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 26/41] oeqa/selftest/containerimage: Update to match assumptions in configuration Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 27/41] ssh-pregen-hostkeys: Add a recipe with pregenerated ssh host keys Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 28/41] bash: fix CVE-2019-18276 Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 29/41] packagegroup: rrecommend perf also for musl on ARM Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 30/41] sysvinit rc: Use PSPLASH_FIFO_DIR for progress fifo Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 31/41] openssh: Allow enable/disable of rng-tools recommendation on sshd Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 32/41] sstate.bbclass: Check file ownership before doing 'touch -a' Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 33/41] kernel-yocto: add KBUILD_DEFCONFIG search location to failure message Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 34/41] linux-yocto/config: netfilter: Enable nat for ipv4 and ipv6 Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 35/41] linux-yocto/5.4: update to v5.4.64 Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 36/41] linux-yocto/5.4: update to v5.4.65 Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 37/41] lttng-modules: backport writeback.h changes from 2.12.x to fix kernel 5.4.62+ Steve Sakoman
2020-09-30 22:11 ` Steve Sakoman [this message]
2020-09-30 22:11 ` [OE-core][dunfell 39/41] wic: Fix --extra-space argument handling Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 40/41] wic: Fix error message when reporting invalid offset Steve Sakoman
2020-09-30 22:11 ` [OE-core][dunfell 41/41] wic: Add 512 Byte alignment to --offset Steve Sakoman

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=897aaff8961f7fe83634a3b0b94e19b43aea5857.1601502610.git.steve@sakoman.com \
    --to=steve@sakoman.com \
    --cc=openembedded-core@lists.openembedded.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.