Trusted Firmware-M
Overview
Trusted Firmware-M (TF-M) implements the Secure Processing Environment (SPE) for Armv8-M, Armv8.1-M architectures (e.g. the Cortex-M33, Cortex-M23, Cortex-M55, Cortex-M85 processors) or dual-core platforms. It is the platform security architecture reference implementation aligning with PSA Certified guidelines, enabling chips, Real Time Operating Systems and devices to become PSA Certified.
A software stack running Trusted Firmware-M consists of three exectuable binaries:
- the bootloader, known as BL2
- the secure firmware, which is the Trusted Firmware
- the non-secure firmware, which is the user application
The non-secure firmware can make API calls (such as cryptography, protected storage, etc.) to the secure firmware via a library known as the NS (non-secure) interface.
Fetching
In your application's CMakeLists.txt
, list trusted-firmware-m
in IOTSDK_FETCH_LIST
, alongside any other components
you need to fetch:
This must be done before your application's
CMakeLists.txt
adds the Open IoT SDK.
Configuration
You also need to specify a list of Trusted Firmware-M configuration options in TFM_CMAKE_ARGS
, for example:
You must always set
TFM_PLATFORM
according to your target platform, which isarm/mps3/an552
(for Corstone-300) in the above snippet. The official list of platforms is documented in the TF-M Platforms webpage.Additionally, your application may require more options to be set depending on what features it needs:
- For all available options, see the Configuration documentation page
- For an example of setting multiple options, see this
CMakeLists.txt
This must be done before your application's
CMakeLists.txt
adds the Open IoT SDK.For our reference platforms, Corstone-300 and Corstone-310, you can find their
TFM_PLATFORM
values intemplates/platforms.cmake
ascorstone-300-TFM_PLATFORM
andcorstone-310-TFM_PLATFORM
respectively.
Build dependency
Trusted Firmware-M must be built before your application, because your application depends on the NS interface
(described in the Overview section) and the BL2 signing scripts, both of which are generated as parts of
the Trusted Firmware-M build process. To ensure the order is correct, call add_dependencies()
in your
CMakeLists.txt
:
Replace
my_application
with the actual name of your application executable.
Linking
You need to link your application against one of the following libraries:
tfm-ns-interface-bare-metal
, if your application is single-threadedtfm-ns-interface-cmsis-rtos
, if your application threads are based on the CMSIS-RTOS v2 APItfm-ns-interface-threadx
, if your application threads are based on AzureRTOS ThreadX
Image signing
Your non-secure application image must be signed using the signing script from Trusted Firmware-M. In the signed image, the exectuable binary is prepended with a header area containing information such as the image size, version, checksum, signature, etc. The bootloader uses this information to validate the image during the boot process.
To sign your application image, you can include the module SignTfmImage
from the Open IoT SDK and call the helper
function iotsdk_tf_m_sign_image()
in your CMakeLists.txt
:
list(APPEND CMAKE_MODULE_PATH ${open-iot-sdk_SOURCE_DIR}/components/trusted-firmware-m)
include(SignTfmImage)
iotsdk_tf_m_sign_image(my_application 0.0.0)
This will generate a signed image, my_application_signed.bin
, in your build directory.
Replace
my_application
with the actual name of your application executable. Replace0.0.0
with a version of your choice.
Optionally, you can merge the bootloader, the secure image and the non-secure application image into a single .elf
image to ease loading of the code onto the target. To do this:
This will generate a merged image, my_application_merged.elf
, in your build directory.
Replace
my_application
with the actual name of your application executable. Replace the three addresses with the actual ROM addresses of the bootloader, secure image and non-secure image.For our reference platforms, Corstone-300 and Corstone-310, you can find their ROM addresses in
templates/platforms.cmake
ascorstone-300-TFM_ADDRESSES
andcorstone-310-TFM_ADDRESSES
respectively.If you would like to create an integration test with
htrun
, then you must create a merged image and pass it tohtrun
which does not support loading more than one image.
Running
After building your application, you have two options for running it on an FVP or AVH. Take
FVP_Corstone_SSE-300_Ethos-U55
for example:
-
Load the bootloader
.elf
image, signed secure.bin
image and signed non-secure.bin
image separately:FVP_Corstone_SSE-300_Ethos-U55 -a __build/bl2.elf \ --data __build/_deps/trusted-firmware-m-build/bin/tfm_s_signed.bin@0x11000000 \ --data __build/my_application_signed.bin@0x01060000
The memory locations for
tfm_s_signed.bin
andmy_application_signed.bin
will change depending on which platform is being used. -
Load the merged
.elf
image, if you have callediotsdk_tf_m_merge_images()
during image signing.
To run it on an FPGA board, consult the application notes for the FPGA image. Generally, an FPGA board only allows you to load the images as separate files instead of a merged file.
Examples
To see the full context of the information in the sections above, you are advised to take a look at the Open IoT SDK examples for Trusted Firmware-M.
Documentation
For more details of how to use Trusted Firmware-M, see its official documentation.