Build a minimal Raspberry Pi OS from source
Raspberry Pi DIY
The detLFS project provides an ideal foundation for compiling Linux from source code, either to experience the fundamentals of how Linux works or to prepare an operating system for a project with very specific requirements.
The Linux From Scratch (LFS) project has been around for more than 20 years [1]. It does not deliver software as a result, but detailed instructions on how to create an executable Linux system from the source code itself. Why might you want to take this route? (1) You might be a masochist with too much time on your hands. (2) You have a project with very specific requirements. (3) You want to learn fundamentally how Linux works. The detLFS [2] project by Thomas Dettbarn answers these needs.
Unlike the pure theory of LFS, detLFS makes life far easier for anyone wanting to take on the challenge because the project provides a set of scripts instead of a manual. The scripts create a runnable, minimal Linux system for the Raspberry Pi almost without interaction. As a prerequisite you need a desktop Linux with the usual build tools (i.e., a compiler and make
), as well as ImageMagick/Netpbm for your own kernel logo. These tools can be found on any normal developer's computer; if in doubt, install them from your package manager. They are typically pseudo-packages named build-essentials, or something similar.
Simply downloading the repository and running the scripts is boring and basically pointless, because nobody gains anything from the minimal system the process creates. Understanding the process and knowing how to adapt it to your own needs is far more important.
How Linux Works
Whether on a Raspberry Pi or on a supercomputer, Linux basically always works in the same way. First, the hardware boots the kernel from disk. This part depends heavily on the platform. Without firmware, also known as BIOS in the desktop area, nothing works.
After startup, the kernel initializes its subsystems and drivers then passes control to the init process by starting the /sbin/init
program with process ID 1. On modern Linux systems, the systemd process adopts this ID shortly afterward. The init program then gradually starts all the application programs and processes that make up a system. The kernel itself remains in the background as a silent worker, stepping in whenever a program needs access to resources, such as during a program startup or for reading a file (Figure 1).
A minimal system comprises three components: the firmware, a kernel, and at least one init program. For a Raspberry Pi, whose only task is to control and switch something, this setup might be enough. detLFS is not quite as minimal. In addition to the init program, standard Linux programs or honed down versions (e.g., ls
, cp
, etc.) are also present.
To create your own minimal system with very little overhead, a script first collects all the required program sources. Subsequently, a second script generates a cross compiler along with companion programs, which are needed because you want to create an executable kernel and application programs for the Raspberry Pi ARM architecture on an x86 system. The schematic flow is shown in Figure 2. All scripts need to run within a single session; otherwise, you will have to repeat the export
commands, which are valid only within a single session.
Improvements
For this project, I provide a fork of the original scripts on GitHub [3], mainly because various bugfixes and optimizations significantly speed up the download and the process of building the system. Furthermore, the fork supports all hardware variants of the Raspberry Pi, not just versions 2 and 3. You can retrieve the software with the commands:
$ git clone https://github.com/bablokb/pi-detLFS $ rm -fr /data/projects/detLFS $ cp -a pi-detLFS/detLFS /data/projects $ cd /data/projects/detLFS
The last two commands copy the directory with the scripts to a suitable project directory and change to that location. If the directory is on a filesystem formatted with XFS or Btrfs, all of the later scripts run faster and they require less space because these filesystems only copy the references when duplicating files, not the data blocks.
After these preparations, run:
$ export BRANCH=rpi-4.19.y $ ./0_getit.sh |& tee 0_getit.log
The optional first line specifies the kernel branch the script fetches from the repository (various lines of development exist in separate branches). Without the export
command, the script uses the current default branch. Instead of setting the branch manually, you can alternatively copy the kernel configuration file .config
from a running Raspberry Pi into the detLFS directory:
$ sudo modprobe configs $ zcat /proc/config.gz > .config
The 0_getit.sh
script in the earlier set of commands downloads about 1.1GB of compressed sources, which when unpacked add up to about twice that. For each download, the script creates a file in the Downloads/
directory that follows the pattern .detlfs.<xxx>
(e.g., .detlfs.kernel
) (Figure 3). If you want to download something again, maybe because you want to try out a different kernel version, delete the file in question beforehand. In any case, check the 0_getit.log
file after execution – this applies in kind to all further steps.
Only the downloaded source packages end up in the Downloads/
directory. With the exception of the kernel, these are archives. The script immediately copies or unpacks the sources into the Sources.
directory. The scripts downstream of this step then make use of them.
Toolbox
The second step in the workflow creates the tools that the downstream scripts need and relates primarily to the cross compiler, which runs on a desktop system (x86), but generates code for the ARM variant:
$ ./1_buildtools.sh | & tee 1_buildtools.log
Fortunately, the normal desktop compiler also builds this cross compiler in the most time-consuming step in the whole process. Ready-made cross compilers can be found online and from the Raspberry Pi Foundation, but users report in forums having difficulties with these tools time and time again. Therefore, the detLFS project prefers building the programs itself.
The computer I used in this project, an AMD Ryzen 5 2400G, is not necessarily a top performer; in fact, it is basically geared toward office work with its integrated GPU. The quad-core processor claims to be an eight-core CPU to the operating system because of hyperthreading. If all the cores are used (to find out, use the -j 8
option with make
), the call described above takes about 18 minutes. If only one core is doing the work, it takes 62 minutes. However, hyperthreading doesn't offer too many benefits with this CPU because of the fairly small CPU cache: with four cores, the compiler run takes 22 minutes, which is only marginally longer than with the full core count.
Once created, the tools do their job no matter how many different kernel and system versions you want to try, so the runtime is only consumed once.
Buy this article as PDF
(incl. VAT)
Buy Linux Magazine
Subscribe to our Linux Newsletters
Find Linux and Open Source Jobs
Subscribe to our ADMIN Newsletters
Support Our Work
Linux Magazine content is made possible with support from readers like you. Please consider contributing when you’ve found an article to be beneficial.
News
-
Red Hat Enterprise Linux 9.5 Released
Notify your friends, loved ones, and colleagues that the latest version of RHEL is available with plenty of enhancements.
-
Linux Sees Massive Performance Increase from a Single Line of Code
With one line of code, Intel was able to increase the performance of the Linux kernel by 4,000 percent.
-
Fedora KDE Approved as an Official Spin
If you prefer the Plasma desktop environment and the Fedora distribution, you're in luck because there's now an official spin that is listed on the same level as the Fedora Workstation edition.
-
New Steam Client Ups the Ante for Linux
The latest release from Steam has some pretty cool tricks up its sleeve.
-
Gnome OS Transitioning Toward a General-Purpose Distro
If you're looking for the perfectly vanilla take on the Gnome desktop, Gnome OS might be for you.
-
Fedora 41 Released with New Features
If you're a Fedora fan or just looking for a Linux distribution to help you migrate from Windows, Fedora 41 might be just the ticket.
-
AlmaLinux OS Kitten 10 Gives Power Users a Sneak Preview
If you're looking to kick the tires of AlmaLinux's upstream version, the developers have a purrfect solution.
-
Gnome 47.1 Released with a Few Fixes
The latest release of the Gnome desktop is all about fixing a few nagging issues and not about bringing new features into the mix.
-
System76 Unveils an Ampere-Powered Thelio Desktop
If you're looking for a new desktop system for developing autonomous driving and software-defined vehicle solutions. System76 has you covered.
-
VirtualBox 7.1.4 Includes Initial Support for Linux kernel 6.12
The latest version of VirtualBox has arrived and it not only adds initial support for kernel 6.12 but another feature that will make using the virtual machine tool much easier.