Mind Chasers Inc.
Mind Chasers Inc.

Build, Install, and Develop with NXP's Latest Yocto Linux BSP for the MCIMX8M-EVK

We show how to build the latest NXP Yocto BSP for the NXP MCIMX8M-EVK evaluation kit for the i.MX 8MQuad processor

X-ray Engineering Services


NXP has recently updated their MCIMX8M-EVK Yocto BSP to the Linux L5.4.70 kernel. We have found that some of NXP's Yocto Linux related documentation is confusing, so we have developed this article about how we perform basic development steps with the Yocto Project, Linux kernel, and user space in the context of our i.MX8 EVK.

The steps shown below can be followed to create a working EVK system from source using an Ubuntu 18.04 host as the Yocto build machine (and package server).

The Yocto Project itself has fantastic documentation, and there is a lot of it! If you're new to Yocto Project, then start with the Quick Build Guide. And don't overlook What I Wish I'd Known.

Listed below are some of the data points that we need to establish to move forward when building a Yocto image from source for our EVK:

  • The NXP i.MX 8MQuad is powered by a quad core 1.5 GHz ARM CORTEX-A53 with an auxiliary ARM M4
  • We are working with the NXP release "L5.4.70_2.3.3" patch release. This was developed using the Yocto Project Zeus (3.0) branch / release.
  • Zeus 3.0 was released October 2019 and is now EOL for support from the Yocto project.
  • We utilize the Wayland graphics back end. XWayland is also supported (Wayland with X11 support) by the BSP.
  • Our Yocto Machine: imx8mqevk
  • Our Yocto distro: "fsl-imx-wayland"
  • There is an EVKB and EVK. We are using the EVKB, and this has an upgrade to the WIFI over the EVK and a later revision of the i.MX8 SoC.
EVK Board

Initial Steps

As recommended by NXP, we're using the repo tool, which is a Python script developed by Google to pull all the necessary Git repositories at the correct commits based on NXP's GA release manifest. Refer to NXP's "i.MX Repo Manifest" README for additional details.

Below we install NXP's Yocto Project release in our /build/imx8/ folder:

$ mkdir -p /build/imx8; cd /build/imx8
$ repo init -u https://source.codeaurora.org/external/imx/imx-manifest  -b imx-linux-zeus -m imx-5.4.24-2.1.0.xml

Downloading Repo source from https://gerrit.googlesource.com/git-repo
Downloading manifest from https://source.codeaurora.org/external/imx/imx-manifest
repo has been initialized in /build/imx8

$ ls -a
.  ..  .repo

$ repo sync
repo sync has finished successfully.

$ ls
imx-setup-release.sh  README  README-IMXBSP  setup-environment  sources

$ ls sources/
base          meta-clang      meta-freescale-3rdparty  meta-imx                  meta-openembedded  meta-qt5   meta-timesys
meta-browser  meta-freescale  meta-freescale-distro    meta-nxp-demo-experience  meta-python2       meta-rust  poky

Create our Yocto Project build environment under the folder bld-wayland:

$ DISTRO=fsl-imx-wayland MACHINE=imx8mqevk source imx-setup-release.sh -b bld-wayland
Your build environment has been configured with:


$ pwd 

$ tree
└── conf
    ├── bblayers.conf
    ├── bblayers.conf.org
    ├── local.conf
    ├── local.conf.org
    ├── local.conf.sample
    └── templateconf.cfg

It may be instructive to realize that the Git repositories under sources are not on a branch and may have been modified during the previous setup:

cd /build/imx8/sources/meta-freescale

$ git branch
* (no branch)

The bitbake command below will build an sdcard image in the deploy folder that we can use to boot our NXP EVK.

$ bitbake imx-image-multimedia

Build Configuration:
BB_VERSION           = "1.44.0"
BUILD_SYS            = "x86_64-linux"
NATIVELSBSTRING      = "ubuntu-18.04"
TARGET_SYS           = "aarch64-poky-linux"
MACHINE              = "imx8mqevk"
DISTRO               = "fsl-imx-wayland"
DISTRO_VERSION       = "5.4-zeus"
TUNE_FEATURES        = "aarch64 cortexa53 crc crypto"
TARGET_FPU           = ""
meta-poky            = "HEAD:d88d62c20d7d8da85f02edb170dae0280624ad7e"
meta-python          = "HEAD:2b5dd1eb81cd08bc065bc76125f2856e9383e98b"
meta-freescale       = "HEAD:14f1a630a47375432f93c556927b879b51d84c4e"
meta-freescale-3rdparty = "HEAD:dbcc686f52c3c84db8cb86aa8973a4e373651b98"
meta-freescale-distro = "HEAD:ca27d12e4964d1336e662bcc60184bbff526c857"
meta-v2x             = "HEAD:ee68455d735ea9221e57ccbf469233b09ae06334"
meta-nxp-demo-experience = "HEAD:c7263d9f3cc7bbf44e7164ffeda494cf283d3dec"
meta-browser         = "HEAD:ee3be3b5986a4aa0e73df2204a625ae1fe5df37e"
meta-rust            = "HEAD:53bfa324891966a2daf5d36dc13d4a43725aebed"
meta-clang           = "HEAD:711e593d5984aad3bf35c51b7ac4482982bc16c7"
meta-filesystems     = "HEAD:2b5dd1eb81cd08bc065bc76125f2856e9383e98b"
meta-qt5             = "HEAD:21ce4c124d9a972d9122f87c64ac2773bf04c284"
meta-python2         = "HEAD:4400f9155ec193d028208cf0c66aeed2ba2b00ab"

When we want to come back to the build system, we can do the following:

$ cd /build/imx8

$ source sources/poky/oe-init-build-env bld-wayland/

### Shell environment set up for builds. ###

You can now run 'bitbake '

Common targets are:

You can also run generated qemu images with a command like 'runqemu qemux86'

Other commonly useful commands are:
 - 'devtool' and 'recipetool' handle common recipe tasks
 - 'bitbake-layers' handles common layer tasks
 - 'oe-pkgdata-util' handles common target package tasks

$ bitbake imx-image-multimedia

Burning our *.wic image on an SD Card

Let's first take a look at the image file system types we have configured:

$ bitbake imx-image-multimedia -e | grep ^IMAGE_FSTYPES
IMAGE_FSTYPES="wic.bmap  wic.bz2 tar.bz2"

Most documentation instructs the user to use dd to program an SD Card, but we use the open source tool Etcher on Windows 10. We find that this is a robust solution since dd sometimes fails to work as we expect.

We also decompress the *wic.bz2 file before using Etcher to program our SD Card. We run the following in our Ubuntu shell on our build machine:

$ cd /build/imx8/bld-wayland/tmp/deploy/images/imx8mqevk/

$ ls *.bz2
imx-image-multimedia-imx8mqevk-<date>.rootfs.tar.bz2     imx-image-multimedia-imx8mqevk.tar.bz2
imx-image-multimedia-imx8mqevk-<date>.rootfs.wic.bz2     imx-image-multimedia-imx8mqevk.wic.bz2

$ bunzip2 -vfk imx-image-multimedia-imx8mqevk.wic.bz2

$ file imx-image-multimedia-imx8mqevk.wic
imx-image-multimedia-imx8mqevk.wic: DOS/MBR boot sector; 
partition 1 : ID=0xc, active, start-CHS (0x80,0,1), end-CHS (0x3ff,3,32), startsector 16384, 170392 sectors; 	
partition 2 : ID=0x83, start-CHS (0x3ff,3,32), end-CHS (0x3ff,3,32), startsector 196608, 7106614 sectors

Note that the resulting *.wic image is ~3.5GB, but we expect this to grow significantly once we add a toolchain and other packages.

We transfer the resulting "*.wic" image to Windows 10 and burn the SD Card using a recent release of Etcher that supports *.wic formats. After programming is done, we insert it in the EVK SD Card slot, and the system does indeed boot Yocto Linux.

Note that we can also insert our burned SD Card back into our Ubuntu machine and make changes to the mounted partitions.

Notes on Directories and Source

imx-image-multimedia.bb can be found in sources/meta-imx/meta-sdk/recipes-fsl/images

As you may have noticed, there are several NXP layers under sources. Here's one way to determine where a recipe is located:

$ cd /build/imx8/sources/
$ find . -name 'linux-imx*bb'

We can see above that the linux-imx_5.4 recipe is located in the meta-imx/meta-bsp layer. This makes sense since NXP tells us that the purpose of this layer is to introduce new features into the Yocto Project build that might not have been availble for the Zeus release.

View the manifest:

$ cd /build/imx8/bld-wayland/tmp/deploy/images/imx8mqevk

$ more imx-image-multimedia-imx8mqevk.manifest | more
acl aarch64 2.2.52-r0
acl-dev aarch64 2.2.52-r0
adwaita-icon-theme-symbolic all 3.32.0-r0
alsa-conf aarch64 1.1.9-r0
alsa-plugins-pulseaudio-conf aarch64 1.1.9-r0
alsa-state imx8mqevk 0.2.0-r5
alsa-states imx8mqevk 0.2.0-r5
alsa-tools aarch64 1.1.7-r0
alsa-utils aarch64 1.1.9-r0

It can be confusing trying to determine where the source is hosted that is used to build our image. One way of determining this is shown below:

$ cd /build/imx8/bld-wayland/tmp/work/

$ ls
aarch64-mx8m-poky-linux  aarch64-poky-linux  all-poky-linux  imx8mqevk-poky-linux  x86_64-linux

$ grep url imx8mqevk-poky-linux/linux-imx/5.4-r0/git/.git/config 
	url = https://source.codeaurora.org/external/imx/linux-imx.git
$ grep url imx8mqevk-poky-linux/u-boot-imx/1_2020.04-r0/git/.git/config 
	url = https://source.codeaurora.org/external/imx/uboot-imx.git

Remote login via SSH

We find that our EVK Linux image supports Ethernet connectivity without requiring customization.

After boot up of our EVK and determination of our EVK's IP address, we add the IP address for the EVK board to /etc/hosts and login remotely:

ssh root@evk
The authenticity of host 'evk (' can't be established.
RSA key fingerprint is SHA256:ZOx862o0VxZf4NOaqEHROt9pU+mb4cN3t0VyvkIxffg.
Are you sure you want to continue connecting (yes/no)? yes
Warning: Permanently added 'evk,<ip address>' (RSA) to the list of known hosts.

# uname -a
Linux imx8mqevk 5.4.70-2.3.2+g8c73bc625c4d #1 SMP PREEMPT Sat Jun 19 23:10:47 UTC 2021 aarch64 aarch64 aarch64 GNU/Linux

# cat /proc/cpuinfo 
processor	: 0
BogoMIPS	: 16.66
Features	: fp asimd evtstrm aes pmull sha1 sha2 crc32 cpuid
CPU implementer	: 0x41
CPU architecture: 8
CPU variant	: 0x0
CPU part	: 0xd03
CPU revision	: 4

processor	: 1

processor	: 2

processor	: 3

DNF and package management

We add DNF package management support to our EVK target and build machine following Yocto documentation and our article "Use DNF Package Manager on a Yocto Linux Development System"

We also make the following customizations to our conf/local.conf file:

Add RPM package management:

IMAGE_FEATURES += "package-management"
PACKAGE_CLASSES ?= 'package_rpm'

Comment out Debian Package Management Directives:

# Switch to Debian packaging and include package-management in the image
# PACKAGE_CLASSES = "package_deb"
# EXTRA_IMAGE_FEATURES += "package-management"

Note that modifying local.conf with the IMAGE change is considered bad form, and we'll eventually create our own custom layer, image recipe, and packagegroup to add our customizations.

After rebuilding, don't forget to run "bitbake package-index" on the build machine. Next, on our EVK, we run:

# dnf makecache
timer: config: 11 ms
DNF version: 4.2.2
Command: dnf makecache 
Installroot: /
Releasever: zeus
cachedir: /var/cache/dnf
Base command: makecache
Extra commands: ['makecache']
Repository 'oe-packages' is missing name in configuration, using id.
Making cache files for all metadata files.
oe-packages: has expired and will be refreshed.
repo: downloading from remote: oe-packages
oe-packages: using metadata from Sun Jun 20 14:08:43 2021.
Last metadata expiration check: 0:00:04 ago on Sun Jun 20 14:53:21 2021.
No module defaults found
timer: sack setup: 3798 ms
Metadata cache created.
Cleaning up.

Adding the GNU Toolchain to our target

We add "tools-sdk" to our IMAGE_FEATURES variable to install a full SDK on our target. After modifying IMAGE_FEATURES, we re-run our build and inspect our updated rootfs:

$ bitbake imx-image-multimedia

$ cd /build/imx8/bld-wayland/tmp/work/imx8mqevk-poky-linux/imx-image-multimedia/1.0-r0/rootfs

$ find . -name autoconf

$ find . -name gcc

Let's also take a look at the updated manifest after updating the package-index:

$ bitbake package-index

$ cd /build/imx8/bld-wayland/tmp/deploy/images/imx8mqevk/

grep autoconf grep autoconf imx-image-multimedia-imx8mqevk.manifest 
autoconf aarch64 2.69

$ grep cmake imx-image-multimedia-imx8mqevk.manifest

As you can see above, cmake isn't included in the SDK, so let's add it by using dnf as described above:

build server:

$ bitbake cmake
$ bitbake package-index

imx shell:

# dnf makecache 
# dnf install cmake

Cleaning up. 

# cmake --version
cmake version 3.15.3

CMake suite maintained and supported by Kitware (kitware.com/cmake).

Obviously, creating customizations to an SD Card partition that will be later overwritten might not be what we want. We may want to move our rootfs off of the SD Card (i.e., use an NFS mount)

In Part 2 of this article we'll discuss topics like building the Linux Kernel outside of Yocto using a Yocto generated SDK and booting our EVK via TFTP and NFS.

References and Resources

Acronyms and Terms

  • SRC: i.MX8 System Reset Controller

Didn't find an answer to your question? Post your issue below or in our new FORUM, and we'll try our best to help you find a solution.

And please note that we update our site daily with new content related to our open source approach to network security and system design. If you would like to be notified about these changes, then please follow us on Twitter and join our mailing list.

Related articles on this site:

subscribe to mailing list:

Please help us improve this article by adding your comment or question:

your email address will be kept private
authenticate with a 3rd party for enhanced features, such as image upload
previous month
next month