Introduction
The Yocto Project® (YP) is an open source collaboration project that helps developers create custom Linux-based operating systems regardless of the hardware architecture.
The project provides a flexible set of tools and a space where embedded developers worldwide can share technologies, software stacks, configurations, and best practices that can be used to create tailored Linux images for embedded and IOT devices, or anywhere a customized Linux OS is needed.
This tutorial will guide you through how to do an initial setup of the Yocto Project® environment and we will be targeting a Raspberry Pi 3 device.
This tutorial will also cover how to re-use existing Yocto Project environments that are available on Mender Hub which enables you to target a large variety of devices.
This is a high-level tutorial and the intention is not to cover the Yocto Project in detail. For detailed information we recommend that you read the Yocto Project Mega-Manual
Version notes
The tutorial has been verified on Ubuntu 22.04. as of 2022-05-31.
This tutorial uses kirkstone as the primary target, which is the current LTS release by the Yocto Project. You can find more infomation on releases here. Supported releases for following the tutorial are:
Yocto Project | Tutorial applies | Maintenance |
---|---|---|
nanbield (4.3) | development | |
mickledore (4.2) | current stable | |
langdale (4.1) | stable | |
kirkstone (4.0) | LTS | |
honister (3.4) | EOL | |
hardknott (3.3) | EOL | |
gatesgarth (3.2) | EOL | |
dunfell (3.1) | LTS | |
zeus (3.0) | EOL | |
warrior (2.7) | EOL | |
thud (2.6) | EOL | |
sumo (2.5) | EOL | |
rocko (2.4) | EOL |
Please note: a failure in the “tutorial applies” column indicates that the instructions do not work without modification. Depending on the combination of release and host Linux distribution, installing other python versions or dependencies might provide a functional state.
Prerequisites
To follow this tutorial, you will need:
- A Raspberry Pi 3 device You will only need the device to test the final result and you can complete the majority of the tutorial without an device.
- A Supported Linux Distribution: You should have a reasonably current Linux-based development host. You will have the best results with a recent release of Fedora, openSUSE, Debian, Ubuntu, or CentOS as these releases are frequently tested against the Yocto Project® and officially supported
- Required Packages for the Build Host:
To install the required packages on a Debian based distribution (Ubuntu etc) run:
sudo apt install gawk wget git diffstat unzip texinfo gcc build-essential \
chrpath socat cpio python3 python3-pip python3-pexpect xz-utils \
debianutils iputils-ping python3-git python3-jinja2 libegl1-mesa \
libsdl1.2-dev pylint xterm python3-subunit mesa-common-dev zstd liblz4-tool
Instructions for other Linux distributions (Fedora, CentOS, etc) are provided here.
Setting up the environment from scratch
The environment
There are many more concepts related to the Yocto Project®, and I will not attempt to cover all of them in this tutorial. For the curious reader there is more information here and here.
I would like to highlight two terms for the sake of this tutorial, which are explained below.
Layers
Extract from the Yocto Project documentation
Layers are repositories that contain related metadata (i.e. sets of instructions) that tell the OpenEmbedded build system how to build a target. The Yocto Project Layer Model facilitates collaboration, sharing, customization, and reuse within the Yocto Project development environment. Layers logically separate information for your project. For example, you can use a layer to hold all the configurations for a particular piece of hardware. Isolating hardware-specific configurations allows you to share other metadata by using a different layer where that metadata might be common across several pieces of hardware.
The majority of the content in layers is recipes. Similar to a cooking recipe which would list the ingredients and contain instructions on how to prepare the meal, the recipes in Yocto layers contain information about packages and the meta data which describes how to build and package a certain component.
Bitbake
Bitbake is the build engine which parses the recipes and executes tasks, and is comparable to the chef who would would read the cooking recipe and execute based on the listed instructions.
Core layers
Lets start preparing the Yocto Project environment. We will start with the core layers needed to be able to work with Yocto.
Create a workspace and change directory:
mkdir -p yocto/sources && cd yocto/sources
The first component we need is Poky. Poky is the Yocto Project reference distribution. It contains the Open-Embedded build system (BitBake and OE-Core) as well as a set of metadata to get you started building your own distribution.
git clone git://git.yoctoproject.org/poky -b kirkstone
Note that Poky is not a layer, and instead contains a collection of layers which are prefixed with meta
,
$ tree -L 1 poky/
poky/
├── bitbake
├── contrib
├── documentation
├── LICENSE
├── LICENSE.GPL-2.0-only
├── LICENSE.MIT
├── MAINTAINERS.md
├── Makefile
├── MEMORIAM
├── meta
├── meta-poky
├── meta-selftest
├── meta-skeleton
├── meta-yocto-bsp
├── oe-init-build-env
├── README.hardware.md -> meta-yocto-bsp/README.hardware.md
├── README.md -> README.poky.md
├── README.OE-Core.md
├── README.poky.md -> meta-poky/README.poky.md
├── README.qemu.md
└── scripts
With this done, we have the core components in place.
Raspberry Pi 3 layers
The Yocto Project’s “Layer Model” is utilized to add support for various hardware. Layers that contain support for a specific hardware are typically called “Board Support Package Layers”.
To support our target device (Raspberry Pi 3) we need to clone the meta-raspberrypi layer:
git clone https://github.com/agherzan/meta-raspberrypi -b kirkstone
The meta-raspberrypi layer has an additional dependency on the meta-openembedded layer:
git clone git://git.openembedded.org/meta-openembedded -b kirkstone
NOTE! meta-openembedded
is a collection of layers.
Initial configuration
We can now leave the sources
directory:
cd ..
To prepare the build environment we can use a script provided by Poky:
. sources/poky/oe-init-build-env build
- build is the directory where we would like to setup the build environment. You can change this to your flavor and needs, but for the sake of this tutorial I would recommend you to keep it as is.
Your shell has should have changed directory to build
and the oe-init-build-env
should have printed some information on your screen.
Running oe-init-build-env
will setup some basics for use and include the core layers in our build environment, but to create an environment targeting Raspberry Pi 3 we need to perform some additional steps.
Below we will add a couple of layers to our environment, and by doing this we are including the recipes that are provided by these layers to our build environment. Adding a layer to an existing build environment can have various impacts and it hard to cover them all here, but in the most simple example, we are just adding to our list of available packages and does not actually impact the output unless we explicitly include packages from a certain layer.
One simple example would the meta-python
layer which is included below as, adding this layer to your environment will not install any python
on your device, but it does add to the list of available packages, making it possible to install e.g python3
and provided modules. More on this in the How to install packages in Yocto Project tutorial.
As already mentioned, the meta-raspberrypi layer has dependencies on layers found in meta-openembedded
, so lets start with adding them.
Add meta-oe
to our build environment:
bitbake-layers add-layer ../sources/meta-openembedded/meta-oe/
Add meta-python
to our build environment:
bitbake-layers add-layer ../sources/meta-openembedded/meta-python/
Add meta-multimedia
to our build environment:
bitbake-layers add-layer ../sources/meta-openembedded/meta-multimedia/
Add meta-networking
to our build environment:
bitbake-layers add-layer ../sources/meta-openembedded/meta-networking/
Finally add meta-raspberrypi
to our build environment:
bitbake-layers add-layer ../sources/meta-raspberrypi
We can list what we have added so far:
bitbake-layers show-layers
The output should be:
layer path priority
==========================================================================
meta /tmp/yocto/sources/poky/meta 5
meta-poky /tmp/yocto/sources/poky/meta-poky 5
meta-yocto-bsp /tmp/yocto/sources/poky/meta-yocto-bsp 5
meta-oe /tmp/yocto/sources/meta-openembedded/meta-oe 6
meta-multimedia /tmp/yocto/sources/meta-openembedded/meta-multimedia 6
meta-python /tmp/yocto/sources/meta-openembedded/meta-python 7
meta-networking /tmp/yocto/sources/meta-openembedded/meta-networking 5
meta-raspberrypi /tmp/yocto/sources/meta-raspberrypi 9
We have not yet configured the environment to build for Raspberry Pi 3, and the default target is qemux86
.
Change target to Raspberry Pi 3:
echo 'MACHINE="raspberrypi3"'>> conf/local.conf
That is it, the environment is ready to build images for Raspberry Pi 3. How to actually build images is covered in the Working with images using Yocto Project tutorial.
Conclusion
In this tutorial we covered the basics on how to setup Yocto Project environment from scratch, targeting Raspberry Pi 3 while also covering some basic terms such as “layers”. Hopefully this will be helpful in getting you started quickly without the need of digging to deep in to the Yocto Project internals.
For further reading I would recommend the following links:
If this tutorial was useful to you, please press like, or leave a thank you note to the contributor who put valuable time into this and made it available to you. It will be much appreciated!