- Package selection by Priority
- Creating device nodes from a device table file
- Debugging package selection failures
- Flat file archives
- MultiArch support
- Debconf and pre-seeding
- Native handling
- Partial Mirrors
- Cascading configuration
- Patch Policy
Multistrap is a tool that does essentially the same job as debootstrap, using an entirely different method, and then extends the functionality to support automated creation of complete, bootable, root filesystems. It can merge packages from different repositories to make the rootfs. Extra packages are added to the rootfs simply by listing them - all dependencies are taken care of. Current development in multistrap is to support user-specified scripts being added as hooks during the unpacking phase to add customised startup scripts and configure things like device nodes.
It was designed primarily for making root filesystems for foreign architecture embedded systems, but in fact can be used for many tasks where one might also use debootstrap.
Its main limitation compared to debootstrap is that it uses apt and dpkg directly so can only work on a debian system - debootstrap depends on nothing but shell, wget, binutils and thus can run pretty-much anywhere.
The main advantage with multistrap is the flexibility to mix packages from different repositories and different suites and manage customised variants with configuration files.
Multistrap is available in squeeze or later. It is written in Perl and uses apt to chose a requested set of packages and their dependencies, then unpack (but not configure) those packages. This leaves a rootfs which just needs to be mounted (or chrooted) and configured with dpkg --configure -a.
Because it uses apt, the mixing of multiple repositories is automatic and apt features such as the use of proxies are all available.
For embedded use some modification to the generated rootfs are often needed in order to make it bootable enough to be configured. An example is given below of a script to do this. See Customising Rootfs below. Development is ongoing to incorporate such support into hooks which can be called during the multistrap operation.
You can choose to keep a copy of all the debs downloaded during the process (by setting the retainsources option to be the path in which they should be stored. This is the binary packages downloaded, not the corresponding sources. But does mean you have a cache of the stuff you made your rootfs with.
Basic syntax is:
multistrap [-a arch] -d [dir] -f config_file
nearly all the config is done in the config_file
You need a config file which contains at least one repository stanza, like:
[Debian] packages=ntpdate udev lrzsz netcat telnetd source=http://ftp.uk.debian.org/debian keyring=debian-archive-keyring suite=lenny
And you need to list that stanza title ('Debian') in the 'aptsources' line. And specify one repository in the bootstrap= line, which is used as the 'main' repository, from which the list of 'priority: Required' packages is taken.
A directory in which to prepare the rootfs, and an arch to use are the last two items (which can be specified on the command line).
Here is a minimal example, which just does makes a normal Debian rootfs. use a command like: sudo multistrap -a armel -d /multistrap-debian-lenny -f simple-config
[General] unpack=true bootstrap=Debian aptsources=Debian [Debian] packages= source=http://ftp.uk.debian.org/debian keyring=debian-archive-keyring suite=lenny
Package selection by Priority
Multistrap selects only Priority: required by default, and even that can be turned off by setting omitrequired=true in [General] section of the config file and then individually specifying all of the Priority: required packages which you do want installed.
grep-available -FPriority 'required' -sPackage grep-available -FPriority 'important' -sPackage
Note that the individual selection of required packages can lead to untested combinations and configurations. Take particular care with packages flagged as Essential: yes as these packages will not be listed as dependencies in most packages but will cause the system to fail entirely if omitted.
It is generally useful to test such configurations with your native architecture to at least ensure that the combination can be installed and that normal chroot operations can at least be performed.
Creating device nodes from a device table file
DeviceTableScripting allows multistrap to create device nodes from a simple device table text file.
Debugging package selection failures
Multistrap can report failure messages when apt is unable to resolve the entire dependency chain. It is not a bug in multistrap when this happens - the problem lies in the selection of packages and the mix of suites involved. There are various methods to debug such situations:
Mimic the call to apt - in the multistrap output, above the failure message, is a long line of commands to apt-get. Copy that entire line into an editor. Re-run the multistrap command with cleanup set to false to preserve the apt sources list and apt data, then run the entire apt-get command manually. This is now a normal apt debugging problem and relies on picking out which packages are actually causing the problem rather than those which are being ruled out by apt as a result of the problem. Somewhere in the dependency chain, you will find a package or a couple of packages which cannot be installed using the apt sources you have specified in your bootstrap instruction. Once you know which packages causing the problem, try to explicitly install only those packages using the same apt-get command. Use Ctrl-C to halt apt if you pick the wrong ones. You can continue to debug the problem by editing the long command to be a call to apt-cache options policy package to see why apt is preferring a particular version of a package.
Switch to the native architecture - trim down your package selection to the base package set (i.e. with only apt listed in the packages field for any included section) and create a temporary chroot on your desktop / laptop machine. In the adapted configuration, ensure that your aptsources line matches your bootstrap line even if your final installation would differ. Also change cleanup to false. chroot into the new directory and then use apt to see what the problems are with your package selection by individually trying to install each one using the apt sources which you are expecting apt to use in the bootstrap phase of your original config.
Note that explicitsuite is hard to get right. Think carefully about which packages are listed for which sections as every package in that section must be available at an installable version in the suite specified in that section. Sometimes, dependencies need to be specified explicitly, even when such dependencies would not be necessary without explicitsuite. When there are problems, use a native architecture, comment out some packages and work out what is needed by building the chroot with a partial package list then work inside the chroot to see what apt actually wants to get the selection you want.
Flat file archives
Multistrap checks your version of dpkg to see if multiple architectures can be supported in /etc/dpkg/dpkg.cfg.d/ and disables the relevant support if not found. You can check your own system with the same test:
dpkg --print-foreign-architectures ; echo $?
Zero on success, non-zero on error.
Debconf and pre-seeding
Steps for Squeeze and later
Inside the chroot (using qemu-static or after booting and using chroot, as appropriate):
A configscript which can be used with multistrap to do the configuration could look like:
export DEBIAN_FRONTEND=noninteractive DEBCONF_NONINTERACTIVE_SEEN=true export LC_ALL=C LANGUAGE=C LANG=C /var/lib/dpkg/info/dash.preinst install dpkg --configure -a mount proc -t proc /proc dpkg --configure -a umount /proc
To support multiple variants of a basic (common) configuration, multistrap is also being extended to allow configuration files to include other (more general) configuration files. i.e. the most detailed / specific configuration file is specified on the command line and that file includes another file which is shared by other configurations.
For discussion about these features, ask on the debian-embedded mailing list.
Package configuration of dash fails with a dpkg-divert error
During package configuration, if you get an error like:
# dpkg --configure dash Setting up dash (0.5.5.1-7.4em1) ... No diversion 'diversion of /bin/sh by dash', none removed. This should never be reached dpkg: error processing dash (--configure): subprocess installed post-installation script returned error exit status 1 Errors were encountered while processing: dash
You probably forgot to manually run dash preinst script. See section #Steps_for_Squeeze_and_later
- Never include whitespace changes, this is not python, there is no equivalent to PEP8.
- Never include stylistic changes - the current style of multistrap is the authoritative style for multistrap code, even if it is inconsistent in places.
- Each patch needs to be a single functional change, across multiple files where appropriate. Never include unrelated changes in a single patch.
- Each patch must be fully documented so that the reason for each change is clear. Bug reports in the Debian BTS are strongly recommended before existing functionality is changed or new functionality introduced.
- Documentation changes only to be made for changes in behaviour introduced via the functional changes already covered in a different patch.
- All patches must be against current git and rebased and resubmitted upon request.
- All translation changes need to be as bugs in the Debian BTS and the entire PO file must always be attached to the bug. Patches to a .po file are never acceptable. All .po changes must result in 100% of strings being translated with no fuzzy translations and no missing strings. All .po changes must be valid according to msgfmt -c.
- Send patches to bug reports in the Debian BTS.