[elbe-devel] [PATCH 3/3] elbepack: rfs: add optional mmdebstrap bootstrapping

Thomas Weißschuh thomas.weissschuh at linutronix.de
Thu Feb 6 12:01:32 CET 2025


mmdebstrap is an alternative to debootstrap which uses apt internally.
It is faster and supports more repository layouts than plain apt.
For now its usage is opt-in.

mmdebootstrap has native support for cross-architecture bootstrapping,
so the custom logic can be disabled in that case.

Link: https://gitlab.mister-muffin.de/josch/mmdebstrap/
Co-developed-by: John Ogness <john.ogness at linutronix.de>
Signed-off-by: John Ogness <john.ogness at linutronix.de>
Signed-off-by: Thomas Weißschuh <thomas.weissschuh at linutronix.de>
Reviewed-by: John Ogness <john.ogness at linutronix.de>
---
 debian/control             |  2 ++
 elbepack/rfs.py            | 34 +++++++++++++++++++++++++++-------
 elbepack/schema/dbsfed.xsd | 14 ++++++++++++++
 3 files changed, 43 insertions(+), 7 deletions(-)

diff --git a/debian/control b/debian/control
index 196b0f319c49c0fb1b5475e1f381fb63adbb7bc7..c872822d6a76f4be2c66087f1b03cde2c75750df 100644
--- a/debian/control
+++ b/debian/control
@@ -112,6 +112,7 @@ Architecture: all
 Depends: ${misc:Depends}, ${python3:Depends},
   python3,
   android-sdk-libsparse-utils,
+  arch-test,
   binfmt-support,
   btrfs-progs,
   debootstrap,
@@ -123,6 +124,7 @@ Depends: ${misc:Depends}, ${python3:Depends},
   f2fs-tools,
   genisoimage,
   gnupg,
+  mmdebstrap,
   mtd-utils,
   python3-apt,
   python3-mako,
diff --git a/elbepack/rfs.py b/elbepack/rfs.py
index 353a94c99b75b7abdaa20af3a0140db15ff44ecd..3dbd3f1ec3d8c75a04e4b6a85611a694f9a57f27 100644
--- a/elbepack/rfs.py
+++ b/elbepack/rfs.py
@@ -154,12 +154,24 @@ class BuildEnv:
             k = strip_leading_whitespace_from_lines(key)
             return self.add_key(unarmor_openpgp_keyring(k), 'elbe-xml-primary-key.gpg')
 
-    def _strapcmd(self, arch, suite, cross):
+    def _strapcmd(self, arch, suite, cross, mmdebstrap):
         primary_mirror = self.xml.get_primary_mirror(
             self.rfs.fname('/cdrom/targetrepo'), hostsysroot=self.hostsysroot)
 
         keyring = False
-        strapcmd = ['debootstrap']
+
+        if mmdebstrap:
+            strapcmd = [
+                'mmdebstrap',
+                # Verbose output instead of progress bars.
+                '--verbose',
+                # ELBE might populate the chroot before running strapcmd.
+                '--skip=check/empty',
+                # Will this rootfs have a merged usr?
+                '--hook-dir=/usr/share/mmdebstrap/hooks/maybe-merged-usr',
+            ]
+        else:
+            strapcmd = ['debootstrap']
 
         # Should we use a special bootstrap variant?
         if self.xml.has('target/debootstrap/variant'):
@@ -173,11 +185,12 @@ class BuildEnv:
         if self.xml.has('target/debootstrap/exclude'):
             strapcmd.extend(['--exclude', self.xml.text('target/debootstrap/exclude')])
 
-        if cross:
+        if cross and not mmdebstrap:
             strapcmd.append('--foreign')
 
         if self.xml.has('project/noauth'):
-            strapcmd.append('--no-check-gpg')
+            if not mmdebstrap:
+                strapcmd.append('--no-check-gpg')
         elif self.xml.has('project/mirror/cdrom'):
             strapcmd.extend(['--keyring', self.rfs.fname('/elbe.keyring')])
             keyring = True
@@ -189,7 +202,12 @@ class BuildEnv:
                 strapcmd.extend(['--keyring', debootstrap_key_path])
                 keyring = True
 
-        strapcmd.extend(['--arch', arch, suite, self.rfs.path, primary_mirror])
+        strapcmd.extend(['--arch', arch, suite, self.rfs.path])
+        if mmdebstrap:
+            trusted = '[trusted=yes]' if self.xml.has('project/noauth') else ''
+            strapcmd.append(f'deb {trusted} {primary_mirror} {suite} main')
+        else:
+            strapcmd.append(primary_mirror)
 
         return strapcmd, keyring
 
@@ -222,15 +240,17 @@ class BuildEnv:
 
         host_arch = dpkg_architecture()
         cross = self.xml.is_cross(host_arch)
+        mmdebstrap = self.xml.has('target/debootstrap/type') and \
+            self.xml.text('target/debootstrap/type') == 'mmdebstrap'
 
         try:
             self.cdrom_mount()
-            cmd, keyring = self._strapcmd(arch, suite, cross)
+            cmd, keyring = self._strapcmd(arch, suite, cross, mmdebstrap)
             if keyring and self.xml.has('project/mirror/cdrom'):
                 self.convert_asc_to_gpg('/cdrom/targetrepo/repo.pub', '/elbe.keyring')
             do(cmd)
 
-            if cross:
+            if cross and not mmdebstrap:
                 ui = '/usr/share/elbe/qemu-elbe/' + self.xml.defs['userinterpr']
 
                 if not os.path.exists(ui):
diff --git a/elbepack/schema/dbsfed.xsd b/elbepack/schema/dbsfed.xsd
index db4a20d4472e18f4de3635441625642bfe96e211..4da14cd8fa8d652fd15e50296de9b9d6975f55d2 100644
--- a/elbepack/schema/dbsfed.xsd
+++ b/elbepack/schema/dbsfed.xsd
@@ -1211,9 +1211,23 @@ SPDX-FileCopyrightText: Linutronix GmbH
           </documentation>
         </annotation>
       </element>
+      <element name="type" type="rfs:bootstrap_type" minOccurs="0" maxOccurs="1">
+        <annotation>
+          <documentation>
+            Bootstrapper type. Either debootstrap (the default) or mmdebstrap.
+          </documentation>
+        </annotation>
+      </element>
     </all>
   </complexType>
 
+  <simpleType name="bootstrap_type">
+    <restriction base="string">
+      <enumeration value="debootstrap" />
+      <enumeration value="mmdebstrap" />
+    </restriction>
+  </simpleType>
+
   <complexType name="ubi_type">
     <annotation>
       <documentation>

-- 
2.48.1



More information about the elbe-devel mailing list