Build Custom Torizon OS Images
Introduction
This article will guide you through the first steps for using TorizonCore Builder to customize Torizon OS images.
The TorizonCore Builder Tool provides a series of commands that allow the quick and easy customization of a Toradex Easy Installer image for deployment and provisioning. Most commands allow for the customization of very specific items, meaning that the full customization of an image would require the execution of multiple such commands. This gives a great deal of flexibility to the user but it also makes the utilization of the tool more difficult. To simplify its usage, the tool provides the build command that allows the full customization of an image as a single step.
With TorizonCore Builder, you can customize Torizon OS images by:
- Creating a YAML configuration file that defines the changes you want to apply, such as device tree overlays, splash screens, kernel modules and more.
- Generating a custom image using the
buildcommand.
Please refer to the following specific articles for additional resources:
- Commands Manual article for detailed specification of the
buildCommand. - Adjust the Configuration File article for detailed explanation about editing the customization file.
- Customization Examples article for a few practical customization examples.
Prerequisites
- A Toradex SoM with Torizon installed
- Understanding the basics of the TorizonCore Builder.
- TorizonCore Builder installed.
Overview
To simplify the process of generating custom images for deployment and provisioning, the TorizonCore Builder tool provides the build command, whose inputs and outputs are depicted below:

The build process is fully controlled by a configuration file (usually named tcbuild.yaml) that informs the tool which base image to use, which modifications to apply (along with the associated data), and what output to produce.
The configuration file and the artifacts it references are common filesystem objects that can be version-controlled, such as files or directories, enabling reproducible builds. Common artifacts to customize an output image include splash screens, source files for device-tree, device-tree overlays, kernel modules, etc.
Version Controlling
To ensure reproducible builds, we recommend version-controlling all inputs to the build command -- including the configuration file and any files it references.
Moreover, if the configuration file employs variable substitution, the same values should be passed as arguments to build to ensure the same results.
The input image does not necessarily need to be version controlled by the user because Toradex already takes care of that -- so if you reference a certain quarterly or monthly release, you know that the exact referenced version will be available to you over the Internet (at least for a period of time).
Device-tree (DT) and device-tree overlay (DTO) source files are a kind of input to the build command that may require special treatment.
If you create your own DT or DTO source files then you would keep them under version control as usual. However, if you want to use DT and/or DTO source files supplied by Toradex, then the recommended approach is to set up a Git submodule referencing our device-trees repo -- this way, one could more easily keep in sync with upstream changes which is commonly desired.
Set up Development Environment
Before running the build command, it is necessary to have all the input artifacts, depending of the desired customizations. This might include:
- A splash screen image.
- The source code of the device tree and the device tree overlays.
- The source code of the external kernel modules.
- The file with the configuration changes captured from the device.
- The docker-compose (YAML) configuration file of the application container or the directory with the container images.
- The base Torizon OS image with Easy Installer format from Toradex (depending on the input mode) that you can download from the Toradex Download Links.
TorizonCore Builder runs inside a Docker container, mounting your current directory into it. This means it only has access to files within that directory.
To ensure all required files are accessible, we recommend the following:
- Create a dedicated project directory that contains everything required for customization.
- Source the
tcb-env-setup.shscript from within this directory.
An example project directory structure is as follows:
.
├── linux
├── device-trees
│ └── overlays
│ └── verdin-imx8mp_panel-cap-touch-7inch-dsi_overlay.dts
├── tcbuild.yaml
└── torizon-docker-verdin-imx8mp-Tezi_7.3.0+build.18
Where:
linuxcontains the Linux kernel sources or headers.device treesis the Toradex device tree directory.tcbuild.yamlis the configuration file.torizon-docker-verdin-imx8mp-Tezi_7.3.0+build.18is the unpacked base Torizon OS image directory.
Unless otherwise specified, run all subsequent TorizonCore Builder commands from your project directory. This ensures the container has access to everything it needs via the mounted working directory.
For more information about the TorizonCore Builder script, see Install TorizonCore Builder.
Download Source
TorizonCore Builder needs the source for both the Linux kernel and Toradex device trees to customize Torizon OS images.
Linux Kernel
The Linux kernel contains the device trees and headers that both device trees and overlays might reference.
Torizon OS images are built on top of Toradex BSPs. Depending on the module, they may use the upstream Linux kernel or vendor-specific downstream kernel. For more information, see the Release Matrix page. For details about lifecycle and OS releases, see Embedded Linux Support Strategy.
From the tabs below, clone the kernel for your specific module's SoC.
git clone -b toradex_6.6-2.2.x-imx git://git.toradex.com/linux-toradex.git linux
git clone -b linux-6.6.y git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
git clone -b toradex_ti-linux-6.6.y git://git.toradex.com/linux-toradex.git linux
Cloning the linux or linux-toradex repositories may take a while. You can use the --depth 1 option to clone only the latest commit. For more information, see the Git documentation.
Device Trees and Overlays
With the Linux Kernel repository cloned, you can view the available device trees for your device. From the tabs below, select the appropriate one for your device:
- Aquila AM69
- Verdin AM62P
- Verdin AM62
- Verdin iMX8M Plus
- Verdin iMX8M Mini
- Apalis iMX8
- Apalis iMX6
- Colibri iMX8X
- Colibri iMX7
- Colibri iMX6
- Colibri iMX6ULL
find linux -name "*am69*-aquila*.dts"
find linux -name "*am62*-verdin*.dts"
find linux -name "*am62p*-verdin*.dts"
find linux -name "*imx8mp-verdin*.dts"
find linux -name "*imx8mm-verdin*.dts"
For Apalis iMX8 QuadMax versions:
find linux -name "*imx8qm-apalis*.dts"
For Apalis iMX8 QuadPlus versions:
find linux -name "*imx8qp-apalis*.dts"
find linux -name "*imx6q-apalis*.dts"
For Colibri iMX8QuadXPlus versions:
find linux -name "*imx8qxp-colibri*.dts"
For Colibri iMX8DualX versions:
find linux -name "*imx8dx-colibri*.dts"
find linux -name "*imx7d-colibri*.dts"
find linux -name "*imx6dl-colibri*.dts"
find linux -name "*imx6ull-colibri*.dts"
For a complete list of device trees, see Device Trees on Toradex System on Modules.
Toradex provides device trees for different carrier boards. Device tree overlays that enable peripherals such as displays and cameras are also provided. From the tabs below, clone the kernel for your specific module's SoC.
git clone -b toradex_6.6-2.2.x-imx git://git.toradex.com/device-tree-overlays.git device-trees
git clone -b master git://git.toradex.com/device-tree-overlays.git device-trees
git clone -b toradex_ti-linux-6.6.y git://git.toradex.com/device-tree-overlays.git device-trees
You can check the available overlays for your device tree by passing a carrier board-level device tree to the torizoncore-builder dto list command. For example, for the imx6dl-colibri-eval-v3.dtb file, run the following command:
torizoncore-builder dto list --device-tree ./linux/arch/arm/boot/dts/imx6dl-colibri-eval-v3.dts
Make sure to copy the full path of the device tree file. Device trees for different modules may be in different paths.
Download a Torizon OS image
To create your customized image, TorizonCore Builder also needs a Torizon OS image to use as a base. This image provides the complete root file system, kernel, and configuration that will be modified.
You can download Torizon OS images from the Download Links page:
-
Match versions: Download a Torizon OS 7.x image, preferably the latest quarterly release for better stability. For a complete list of available releases, see the Release Matrix page.
-
Avoid evaluation containers: Select an image without evaluation containers, as the input image must not contain pre-provisioned container images.
See how it works in a minimal example:
Alternatively, you can fetch development-ready images directly from Torizon feeds. Read the next section for details.
Fetch Remote Images
Rather than downloading and extracting images manually, TorizonCore Builder can download them directly from the Toradex artifacts server during build time. This is useful for creating CI/CD pipelines and automating the image customization process.
Read the TorizonCore Builder command manual for specification details.
Notice that not all images allow the customization of every possible property that the "build" command provides; e.g. older images may not allow that kernel modules to be built from source and deployed with the image.
Hard-Coded URL
Manually specify the full URL of the image archive. For example:
input:
easy-installer:
remote: "https://artifacts.toradex.com:443/artifactory/torizoncore-oe-prod-frankfurt/dunfell-5.x.y/release/7/colibri-imx6/torizon-upstream/torizon-core-docker/oedeploy/torizon-core-docker-colibri-imx6-Tezi_5.3.0%2Bbuild.7.tar;sha256sum=49fc6a32ab3fc21a184fb8333c19ad53f22875975219883c1087d929bedf470f"
Note the presence of the optional sha256sum parameter. It ensures file integrity. If the checksum of the downloaded file does not match the provided value, the tool will stop the operation.
Dynamic URL
Instead of specifying the URL manually, you can provide the image specs and let TorizonCore Builder generate the URL. To do so, set the toradex-feed property. For example:
input:
easy-installer:
toradex-feed:
version: "5.3.0"
release: quarterly
machine: colibri-imx6
distro: torizon-upstream
variant: torizon-core-docker
build-number: "7"
# Required for monthly or nightly releases
#build-date: "202107"
For monthly and nightly releases, the build-date is required.
See how it works in a minimal example:
Create a Configuration File
You can create an initial configuration file with the following command:
torizoncore-builder build --create-template
The previous command will create a tcbuild.yaml file containing all possible configuration parameters accepted by the command.
TorizonCore Builder expects this configuration file to be named tcbuild.yaml.
For more information, see the Configuration File page.
Minimal Configuration File
A minimal configuration file has to specify at least one input and one output.
Using Local Images
Below it is assumed that the input is a previously downloaded Toradex Easy Installer image that is stored in a directory called images relative to the working directory (set by the alias of the tool).
# Sample configuration file:
input:
easy-installer:
local: images/torizon-core-docker-colibri-imx6-Tezi_5.3.0-devel-202105+build.12.tar
output:
easy-installer:
local: torizon-core-docker-colibri-imx6-Tezi_5.3.0.CUSTOM
As a general rule, the input image to be customized MUST NOT contain bundled container images – when choosing an image to download, e.g. from Toradex Easy Installer - OS and Demo Images be sure to download an image without evaluation containers.
The directory structure of such a "project" would look like this:
.
├── images
│ └── torizon-core-docker-colibri-imx6-Tezi_5.3.0-devel-202105+build.12.tar
└── tcbuild.yaml
Using Remote Images
In the sample configuration file below, Torizoncore Builder directly downloads an image from Toradex's artifacts server:
# Sample configuration file specifying a remote:
input:
easy-installer:
remote: "https://artifacts.toradex.com:443/artifactory/torizoncore-oe-prod-frankfurt/dunfell-5.x.y/release/1/colibri-imx6/torizon-upstream/torizon-core-docker/oedeploy/torizon-core-docker-colibri-imx6-Tezi_5.1.0%2Bbuild.1.tar;sha256sum=5d11dc0b6be688f6a7d159280e9bca15e26bc58732724e3e1dd66b0d0a6ada08"
output:
easy-installer:
local: torizon-core-docker-colibri-imx6-Tezi_5.1.0+build.1.CUSTOM
name: "My customized image"
Notice the presence of the sha256sum parameter which can be used to ensure that the downloaded file has a certain SHA-256 checksum – the tool will stop if the actual file checksum does not match that value (the Detailed Manual gives more information about how a remote location can be specified).
Simple Customization File
As an example, below is a minimal configuration file that customizes an image for the Verdin iMX8M Plus. This custom tcbuild.yaml file does the following:
- Uses the
imx8mp-verdin-wifi-dahlia.dtsdevice tree (instead of the defaultimx8mp-verdin-wifi-dev.dts). - Applies the
verdin-imx8mp_panel-cap-touch-7inch-dsi_overlay.dtsoverlay.
input:
# Target image
easy-installer:
local: torizon-docker-verdin-imx8mp-Tezi_7.3.0+build.18
customization:
device-tree:
include-dirs:
# Folder that contains common kernel header files like gpio.h
- linux/include
# Folder containing overlays included by verdin-imx8mp_panel-cap-touch-7inch-dsi_overlay.dts
- device-trees/overlays
# Top-level device tree source file that will be used.
# This file's name includes the name of the target SoC and carrier board.
# Note that we are including a a device tree source file (dts) and not a dtsi file.
custom: linux/arch/arm64/boot/dts/freescale/imx8mp-verdin-wifi-dahlia.dts
overlays:
add:
# Overlay to be applied
- device-trees/overlays/verdin-imx8mp_panel-cap-touch-7inch-dsi_overlay.dts
output:
easy-installer:
# Output folder
local: custom-torizon-docker-verdin-imx8mp
# Image name
name: Torizon OS - DSI 7" Touch
The snippet above considers a project folder structured as follows:
.
├── linux
├── device-trees
│ └── overlays
│ └── verdin-imx8mp_panel-cap-touch-7inch-dsi_overlay.dts
├── tcbuild.yaml
└── torizon-docker-verdin-imx8mp-Tezi_7.3.0+build.18
Build the Custom Image
To build the image, you can simply run:
torizoncore-builder build
If you are using a file name different from tcbuild.yaml, specify it with the -f flag:
torizoncore-builder build -f <configuration_file_name>
If the build completes successfully, TorizonCore Builder commits the changes to an OSTree repository. You can use the commit checksum later to verify that your device is running your custom image. The commit checksum is highlighted in the output example below:
torizoncore-builder build output
Building image as per configuration file 'tcbuild.yaml'...
=>> Handling input section
Copying Toradex Easy Installer image.
Unpacking TorizonCore Toradex Easy Installer image.
Importing OSTree revision 80078437b2cf6070717a424bb28982cf447621e93400c560da5877b89724635b from local repository...
1285 metadata, 9777 content objects imported; 649.7 MB content written
0 metadata, 0 content objects imported; 0 bytes content written
Unpacked OSTree from Toradex Easy Installer image:
Commit checksum: 80078437b2cf6070717a424bb28982cf447621e93400c560da5877b89724635b
TorizonCore Version: 7.3.0+build.18
=>> Handling customization section
=> Handling device-tree subsection
=> Selecting custom device-tree 'linux/arch/arm64/boot/dts/freescale/imx8mp-verdin-wifi-dahlia.dts'
'imx8mp-verdin-wifi-dahlia.dts' compiles successfully.
warning: removing currently applied device tree overlays
Device tree imx8mp-verdin-wifi-dahlia.dtb successfully applied.
=> Adding device-tree overlay 'device-trees/overlays/verdin-imx8mp_panel-cap-touch-7inch-dsi_overlay.dts'
'verdin-imx8mp_panel-cap-touch-7inch-dsi_overlay.dts' compiles successfully.
/tmp/tmpz82gq6x4: Device Tree Blob version 17, size=90080, boot CPU=0, string block size=7160, DT structure block size=82864
'verdin-imx8mp_panel-cap-touch-7inch-dsi_overlay.dtbo' can successfully modify the device tree 'imx8mp-verdin-wifi-dahlia.dtb'.
Overlay verdin-imx8mp_panel-cap-touch-7inch-dsi_overlay.dtbo successfully applied.
=>> Handling output section
Applying changes from STORAGE/dt.
Commit 18b812aba3a51cdeb53d8413848a64c6fd7c550c48760604538592bae2887045 has been generated for changes and is ready to be deployed.
Deploying commit ref: tcbuilder-20250814200735
Pulling OSTree with ref tcbuilder-20250814200735 from local archive repository...
Commit checksum: 18b812aba3a51cdeb53d8413848a64c6fd7c550c48760604538592bae2887045
TorizonCore Version: 7.3.0+build.18-tcbuilder.20250814200736
Default kernel arguments: quiet logo.nologo vt.global_cursor_default=0 plymouth.ignore-serial-consoles splash fbcon=map:3
1285 metadata, 9777 content objects imported; 649.7 MB content written
Pulling done.
Deploying OSTree with checksum 18b812aba3a51cdeb53d8413848a64c6fd7c550c48760604538592bae2887045
Bootloader found in unpacked image: U-Boot
Deploying done.
Copy files not under OSTree control from original deployment.
Packing rootfs...
Packing rootfs done.
=>> Build command successfully executed!
Deploy the Custom Image
You can deploy your image in different ways:
- Using Toradex Easy Installer: Install the image locally via USB stick, SD card or network.
- With the
deploycommand: Deploy your image directly through SSH with a TorizonCore lsBuilder command. - Using Torizon Cloud: Remotely deploy your image to one or more devices, enabling large-scale or field deployments.
Toradex Easy Installer
TorizonCore Builder generates images compatible with Toradex Easy Installer. You can copy the generated folder to a USB stick, for example, and proceed as follows:
SSH
You can deploy your custom image directly to the board over SSH with the torizoncore-builder deploy command. This command replaces the active OSTree commit with a new one, while keeping the previous commits available for rollback. When you run this command, TorizonCore Builder:
- Finds the latest built image in your local (host machine) OSTree repository.
- Transfers only the missing objects to the board via SSH.
- Registers the new commit for the next boot.
This operation only alters the OSTree, so it does not support deploying pre-provisioned containers.
To deploy your image:
-
Unpack your image. pass the image folder generated in the build process. For example:
torizoncore-builder images unpack torizon-docker-verdin-imx8mp-Tezi_7.3.0+build.18/ -
Deploy your image to the board:
torizoncore-builder deploy --remote-host <BOARD-IP> --remote-username <USERNAME> --remote-password <PASSWORD> --reboottipStarting with TorizonCore Builder 3.1.0, the default values for
--remote-usernameand--remote-passwordaretorizon. If either the username or password istorizon, you can omit the corresponding argument.
For more information about the images unpack and deploy commands, see TorizonCore Builder Tool - Commands Manual.
Torizon Cloud
You can also push images to Torizon Cloud using TorizonCore Builder commands. This method allows you to update devices in the field remotely, without physical access.
This operation does not support deploying pre-provisioned containers.
The steps are as follows:
-
Unpack your image. Pass the image folder generated in the build process. For example:
torizoncore-builder images unpack torizon-docker-verdin-imx8mp-Tezi_7.3.0+build.18/ -
Deploy your image to Torizon Cloud:
torizoncore-builder platform push --credentials credentials.zip --package-name <PACKAGE_NAME> --package-version <PACKAGE_VERSION> <UNPACKED-DIRECTORY>
Confirm the Image Deployment
After deploying your custom image, you can check whether it contains the same OSTree commit TorizonCore Builder generated.
To confirm your image deployment, run the following command on your target device:
# sudo ostree admin status
* torizon 80078437b2cf6070717a424bb28982cf447621e93400c560da5877b89724635b.0
Version: 7.3.0+build.18
origin refspec: tcbuilder:80078437b2cf6070717a424bb28982cf447621e93400c560da5877b89724635b
torizon 95dd4ed187473a623a5989ad9d44ff7528fb96f638f26dc2e3102b8584fa583d.0 (rollback)
Version: 7.3.0+build.18-tcbuilder.20250725030111
origin refspec: torizon
The output lists OSTree commits. Note that the latest and active commit is the one generated in the Build the Custom Image step.