Roll your own IoT Linux with Buildroot
Getting Small
Whether you need a tiny OS for 1MB of flash memory or a complex Linux with a graphical stack, you can quickly set up a working operating system using Buildroot.
To put together a Linux-based IoT system, you need a quick and easy approach to getting a base system up and running. And while you are at it, you also need to keep an eye on the flash footprint – some IoT platforms only have 64MB flash memory. You will want to keep control of the software included in the system, and you'll want to be able to add your own applications easily. Last but not least, you will need to pay attention to security and comply with both open source and proprietary licenses.
The Buildroot build system [1] will help you with these tasks. Buildroot, which emerged in the early 2000s from the µClinux and Busybox projects, focuses on creating systems with a minimal footprint. Buildroot is easier to use and conceptually simpler than Yocto (see the article on Yocto starting on p. 16 of this issue). If you don't need Yocto's expansive capabilities, with its modular layer system and other advanced features, and you just want to generate an OS for an embedded device, Buildroot is often the better choice.
Buildroot can generate:
- a cross-compilation toolchain
- a root file system
- a Linux kernel image
- a bootloader for the target device
A selection tool based on the menu system of the Linux kernel lets you specify the required packages and the associated configuration options. This menu-driven approach helps ensure you have the components you need and makes it easy to leave out any components you don't need to minimize the flash footprint.
Once you decide which packages to include, Buildroot helps with downloading, patching, configuring, compiling, and finally installing each package (Figure 1). In addition, you can generate some metadata if so desired: a manifest of installed packages, license information (legal-info
), the footprint of each package (graph-size
), and the dependencies between the components (graph-depends
). All packages are built from the source code, which gives you maximum control over the configuration.
Unlike Ubuntu Core and Linux from Scratch, Buildroot relies on cross-compiling, which means the build happens on a processor architecture that is different from the system on which the build will eventually run. For example, you can build on a computer with an x86 architecture, even though the target system is an ARM. For many processor architectures in the embedded space, cross-compiling is the only realistic way to compile, because the target system is often far too slow and does not have enough memory. Additionally, cross-compiling lets you work with a different standard C library (such as Musl or uClibc) and a different Linux kernel.
However, cross-compiling presents a few challenges. Much of the work done by Buildroot is to overcome these challenges through special compilation options or source code patches. Cross-compiling requires a special toolchain consisting of the compiler, linker, and assembler for the target system, the Linux kernel headers, the C and C++ standard libraries, and optionally the cross-debugger. Buildroot creates this toolchain and optimizes it for the target platform as part of the build process. Alternatively, you can load and use an existing toolchain, such as the ARM GNU toolchain or the Bootlin toolchain.
Flexibility
One of the most important principles of Buildroot is flexibility. You need to be able to make all kinds of tweaks to the system to get exactly the results you require. The distribution primarily achieves this through a selection of packages. For example, Buildroot offers several basic options for the init system (systemd, classic SysVinit, its stripped-down Busybox version, or OpenRC) and more than 10 different web servers. Buildroot supports the Glibc, Musl, and uClibc C libraries. On top of this, 15 different root file systems are available. In addition to classic options like ext4 and embedded-specific variants like UBIFS for NAND flash, the file system options include a RAM file system that is linked into the Linux kernel.
You can store your choice of packages in a configuration file, which, in turn, can reference a number of other files that further specify the requirements. Some packages, such as the Linux kernel, have their own configuration file. There are also a number of items that are too complicated to save in the configuration file, including file ownership and permissions, as well as user names and passwords. You can define separate files for these items. Using rootfs, you then copy a directory structure (the rootfs overlay) and run a script after creating all the packages. The additional configuration files are usually stored in the boards/
directory.
Figure 2 shows the configuration files used in an example. Two different variants exist, each with a defconfig
: bmax_b1
and raspberrypi4_64
. The two variants share most of the rootfs overlay in the common/
directory, the user-defined table, and a post-build script that generates version and platform information. The two boards require slightly different configurations for the graphics stack though, and this is why they each have their own rootfs overlays.
To help you get started, Buildroot comes with configurations for around 230 recent SBCs (Single Board Computers) and SoMs (System-on-Modules) and about 40 configurations for simulations in Qemu. These are minimal configurations containing just a toolchain, a kernel, a bootloader, and a busybox. If required, the configurations might include firmware, for example, for a WiFi chip or a GPU. You then upload the results – usually an SD card image – directly to the board. Use the SD card to boot the device and access a shell, which you can adapt to your needs if necessary. As long as you know which CPU variant you are dealing with, and which bootloader and kernel options (device tree) you need to use, you can quite easily set up a basic configuration.
Buildroot's flexibility even allows it to incorporate non-standard features. For instance, you could include a read-only root filesystem with a separate writable partition, kernel and rootfs updates, along with A-B swapping between two partitions, and verified booting using a trusted hardware root. All of this is possible, but it can involve some hard work in individual cases.
Some projects use Buildroot to build a more managed and therefore less flexible distribution. They include SkiffOS, DahliaOS, Recalbox, Batocera Linux, and Home Assistant Operating System, among others. These distros are designed for specific use cases and make use of Buildroot's flexibility.
Your Own Applications
To generate a working product, an application needs to deliver the functionality of the IoT device. Sometimes this is limited to a few scripts such as PHP files that you use through the web server and are simply part of the rootfs overlay. However, you will usually need to compile and install one or more custom components.
Buildroot offers two approaches to compiling your own components. You will often set up separate package definitions for each of your components, consisting of just a few lines, especially if one of the supported build systems is used (Figure 1). For C/C++, these are Meson, Cmake, the Qmake autotools, and Waf. Other languages have language-specific build systems: Go for Golang, Cargo for Rust, Rebar for Erlang, Luarocks for Lua, MB or EUMM for Perl. Python plays a special role because it supports several build systems with Distutils, Setuptools, Pep517, Flit, and Maturin. The comprehensive Buildroot manual [2] explains how to create a package definition and which variables you need to use to fine-tune the build process.
Developers often look to avoid mixing their own package definitions with Buildroot's open source packages. The BR2_EXTERNAL
mechanism supports this desire by allowing the user to add custom package definitions to those belonging to Buildroot. Additionally, you can store your configuration and other files, such as the rootfs overlay, in the same BR2_EXTERNAL
repository. This keeps all your customizations neatly in one place.
Sometimes it is more convenient to compile application code outside of Buildroot. For example, in larger projects, you might find software developers who do not work with Buildroot on a daily basis. Also, it is easier to compile from an IDE if you are working directly with a build system that the development environment supports. This is why Buildroot provides an SDK containing the cross-compilation toolchain, all configured libraries, and the host tools. After all, you will need some of these host tools for the build. pkg-config
, for example, defines the compile options of a library, and protoc
generates the code for a Google protobuf definition. The SDK is available as a tarball that you can unpack anywhere. If you set up the IDE to use the SDK's cross-compiler, you can compile and debug directly from it.
Management
Once an IoT system is developed, updates and new generations will usually follow. It is important to maintain the underlying distribution with fixes for security issues and new features.
Buildroot has been around since 2001, making it one the oldest IoT build tools, and the project's continuity definitely makes it a proven product. Since 2009, the developers have kept to a fixed release schedule of four releases per year: 20XX.02, 20XX.05, 20XX.08, and 20XX.11. Each release goes through a one-month stabilization period, during which only fixes take place; the release is then maintained (bug fixes and security updates) for three months. A minor version is released about every month. The 20XX.02 release is an LTS (Long Term Support) release that will be maintained for a little over a year and again has minor releases added monthly.
Buildroot is community-driven, with about 100 people contributing to each release and a total of 1,500 changes per release. The community mainly communicates via the mailing list (lists.buildroot.org
) and on IRC #buildroot
on Open and Free Technology Community (OFTC). Twice a year, a developer meeting is held, with problems and new features on the agenda. In addition, the community discusses and decides on controversial changes in this scope. There is no controlling company behind the distribution. However, some companies and freelance consultants offer services related to Buildroot. These companies help customers get the operating system running on the IoT platform with all the necessary features. See the Buildroot website for more information.
The developers provide some tools to help you maintain buildroot. You can use make pkg-stats
to keep the packages in Buildroot up to date. Calling make pkg-stats
collects version information about the packages you select, searches for newer versions on the network, checks for Common Vulnerabilities and Exposures (CVE) reported via the NIST National Vulnerability Database, and prints the results in HTML and JSON. This report appears weekly for all packages [3]. Run it for your own configuration if you want a personalized report.
Further testing goes on continuously – 440 tests a week. The 270 configurations for SBCs, SoMs, and Qemu are bundled with Buildroot are also created weekly. Finally, there are 10 build servers that steadily generate arbitrary configurations. The reports from these servers are available online [4].
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
-
Valve and Arch Linux Announce Collaboration
Valve and Arch have come together for two projects that will have a serious impact on the Linux distribution.
-
Hacker Successfully Runs Linux on a CPU from the Early ‘70s
From the office of "Look what I can do," Dmitry Grinberg was able to get Linux running on a processor that was created in 1971.
-
OSI and LPI Form Strategic Alliance
With a goal of strengthening Linux and open source communities, this new alliance aims to nurture the growth of more highly skilled professionals.
-
Fedora 41 Beta Available with Some Interesting Additions
If you're a Fedora fan, you'll be excited to hear the beta version of the latest release is now available for testing and includes plenty of updates.
-
AlmaLinux Unveils New Hardware Certification Process
The AlmaLinux Hardware Certification Program run by the Certification Special Interest Group (SIG) aims to ensure seamless compatibility between AlmaLinux and a wide range of hardware configurations.
-
Wind River Introduces eLxr Pro Linux Solution
eLxr Pro offers an end-to-end Linux solution backed by expert commercial support.
-
Juno Tab 3 Launches with Ubuntu 24.04
Anyone looking for a full-blown Linux tablet need look no further. Juno has released the Tab 3.
-
New KDE Slimbook Plasma Available for Preorder
Powered by an AMD Ryzen CPU, the latest KDE Slimbook laptop is powerful enough for local AI tasks.
-
Rhino Linux Announces Latest "Quick Update"
If you prefer your Linux distribution to be of the rolling type, Rhino Linux delivers a beautiful and reliable experience.
-
Plasma Desktop Will Soon Ask for Donations
The next iteration of Plasma has reached the soft feature freeze for the 6.2 version and includes a feature that could be divisive.