Skip to main content
Associate III
July 3, 2024
Solved

STiRoT Provisioning of STM32H573 over SPI

  • July 3, 2024
  • 4 replies
  • 7342 views

Hi all,

we are developing a product with the STM32H573. The idea is to use the STiRoT for secure firmware update. The MCU is connected to a Linux CPU via SPI. Now we plan to do the provisioning during the production using the Linux CPU that has a ethrnet connection to the outside world. 

The question is: Is that possible? Is the boot pin required or is a jump to bootloader sufficient?

I have modified the provisioning scripts to use UART and I have tested it using the H573DK eval board, but it failed. This is because after programming the option bytes the bootloader is not starting again, as STiRoT gets activated. Maybe the sequence can be modified?

What are the detailed steps? E.g. what is the RSS doing and how?

 

Thx,

Roman

 

    

 

Best answer by Jocelyn RICARD

Hello Roman,

"Switch to lock", for testing purpose I would switch to closed in order to be able to regress the device.

Also, Boot0 can be tied to VDD, no need to set it back to VSS.

Otherwise, yes it looks good.

Best regards

Jocelyn

4 replies

Jocelyn RICARD
ST Employee
July 3, 2024

Hello @RomThi ,

When enabling STiROT, you have no way to enter bootloader through the BOOT0 pin. This is a security principle to have a single entry point after reset.

Now, to update the firmware you have 2 ways.

1) Use your own application to download the new firmware in the download slot

2) Jump in the system bootloader. The examples provided in the STM32CubeH5 give you the needed implementation (See LOADER_Run() for instance). You can consider system bootloader as a non secure application running in HDPL3. So, to make it work you need to configure the platfom security (GTZC, SAU, MPU, interrupts and GPIO) so that this non secure application can work properly.

The initial provisioning that should be done in factory is a different topic. Normally there shouldn't be any issue using the system bootloader interface to do this. But in this case you need to pull BOOT0 pin up.

You setup option bytes in open state, download the signed application, switch to provisioning, provision obk files (STiROT_config.obk, STiROT_data.obk and DA_config.obk), and then switch to closed state.

If you want to stay in open state, you will need to set BOOT_UBE to 0xB4 to boot from bootloader to be able to perform the provisioning in open state. Then once provisioning is done, set BOOT_UBE back to 0xC3 and reset, the STiROT should run as long as BOOT0 pin stays up. This case is just for testing as you stay in open state!

The provisioning sequence should be basically the same as with JTAG.

Best regards

Jocelyn

RomThiAuthor
Associate III
July 4, 2024

Hello Jocelyn,

thx for your quick response. Good to know, how to jump to the system bootloader properly. Thx for that.

But I still don't understand how the provisioning could work without JTAG or SWD.

Here is our setup, its not a big deal to connect the boot pin:
ProvSetup.png

Now I show you the sequence that I understood:
ProvSeq.png
In our scenario we have a basic firmware installed after production of the PCB. So some user code is running. As a first step we jump into the system bootloader. Here the first question (1), can we also jump in from the user application without the boot pin? The next four steps are clear for me marked with (OK). But than I am lost, see (2).
You wrote: "provision obk files (STiROT_config.obk, STiROT_data.obk and DA_config.obk), and then switch to closed state". How can this be done if the RSS is active due to the "provisioning" state? 

 

Best regards,

Roman

 

 

  

 

Jocelyn RICARD
ST Employee
July 4, 2024

Hello Roman,

You can see the RSS as a Secure Application that is launching system bootloader that is the non secure application.

You know in which boot state you are thanks to the table 26 of reference manual

JocelynRICARD_0-1720090406219.png

So, in provisioning state you launch the RSS, meaning you will be able to reconnect to the system bootloader.

You can launch the OBK provisioning through this path

Then you can request option byte change to change product stat to CLOSED.

As BOOT_UBE is set to 0xC3, it will automatically launch the STiROT.

 

Regarding first jump to system bootloader to avoid controlling the BOOT0 pin I made a quick check and it you cannot do this if TrustZone is not already enabled. I mean your simple firmware is probably running without TrustZone enabled and this is required to be able to setup the secure watermarks and secure boot address.

After enabling TrustZone in option bytes you have to go through a reset to enable the RSS that will allow changing secure related option bytes.

If TrustZone can be enabled in advance, it should be possible to avoid using BOOT0 pin.

Best regards

Jocelyn

 

 

Jocelyn RICARD
Jocelyn RICARDBest answer
ST Employee
July 4, 2024

Hello Roman,

"Switch to lock", for testing purpose I would switch to closed in order to be able to regress the device.

Also, Boot0 can be tied to VDD, no need to set it back to VSS.

Otherwise, yes it looks good.

Best regards

Jocelyn

RomThiAuthor
Associate III
July 5, 2024

Deleted

Jocelyn RICARD
ST Employee
July 16, 2024

Hello @RomThi ,

In order to make sure the full provisioning can be done through system bootloader, I created a small script to make things simple.

This script assumes that you have already a STiROT configuration properly setup and all files have been generated.

Here it is:

set Prog="C:\Program Files\STMicroelectronics\STM32Cube\STM32CubeProgrammer\bin\STM32_Programmer_CLI.exe"
set COMPORT=COM204
:: BOOT0 pin shoud be tied to VDD
:: Erase all, BOOT_UBE set to 0xB4 to ensure we boot on bootloader
:: Enable TrusteZone
%Prog% -c port=%COMPORT% -e all -ob BOOT_UBE=0xB4 -ob TZEN=0xB4
:: Reset some option bytes as it is done in orignal script
%Prog% -c port=%COMPORT% -ob SRAM2_RST=0 SRAM2_ECC=0 SECWM1_STRT=1 SECWM1_END=0 WRPSGn1=0xffffffff WRPSGn2=0xffffffff SECWM2_STRT=1 SECWM2_END=0 HDP1_STRT=1 HDP1_END=0 HDP2_STRT=1 HDP2_END=0 SECBOOT_LOCK=0xC3
:: Download application and set secure watermarks : To be adapted with actual mapping
%Prog% -c port=%COMPORT% -d ..\..\Applications\ROT\STiROT_Appli_TrustZone\Binary\appli_enc_sign.hex -ob SECWM1_STRT=0x0 SECWM1_END=0x2 SECWM2_STRT=0x7F SECWM2_END=0x0
:: Switch to provisioning state.
%Prog% -c port=%COMPORT% -ob PRODUCT_STATE=0x17
:: In provisiong state, RSS/bootloader is only boot option.
:: Provision DA and STiROT configuration 
%Prog% -c port=%COMPORT% -sdp ./../DA/Binary/DA_Config.obk -sdp ./Binary/STiRoT_Config.obk -sdp ./Binary/STiRoT_Data.obk
:: Enable STiROT and lock boot
%Prog% -c port=%COMPORT% -ob BOOT_UBE=0xC3 SECBOOT_LOCK=0xB4
:: Switch to Closed state
%Prog% -c port=%COMPORT% -ob PRODUCT_STATE=0x72
:: Once product state is closed, only possible boot is STiROT.
:: To reopen, launch regression script.

This is supposed to be run from STM32Cube_FW_H5_V1.3.0\Projects\STM32H573I-DK\ROT_Provisioning\DA\

I tested with last version of STM32CubeProgrammer 2.17

I used STiROT_Appli_TrustZone example meaning firmware is composed of secure and non secure applications.

If you have developped your own application you will need to adapt the secure watermark values at line 10

Warning: The last command that closes the product is stuck during around 40 seconds and then times out because it is not able to reconnect. I already raised sometime ago a ticket to manage this closure more properly: When closing, the programmer should just check it cannot connect any more and stop.

I hope this will help

Best regards

Jocelyn

RomThiAuthor
Associate III
July 17, 2024

Hello Jocelyn,

thank you very much. I have tested it and it works. Its very simple and understandable. 

 

But I got an error in line 17, because the SECBOOT_LOCK could not be set.

See here:

Error: Expected value for Option Byte "secboot_lock": 0xB4, found: 0x0
Error: Option Byte Programming failed Or modified by application after OB_LAUNCH

As it is woking, I will remove that step. Is that okay?

 

I have run my script from ".\Projects\STM32H573I-DK\ROT_Provisioning\STiROT" and i have used the "STiROT_Appli".

Here is my modified script:

set Prog="C:\Program Files\STMicroelectronics\STM32Cube\STM32CubeProgrammer\bin\STM32_Programmer_CLI.exe" 
set COMPORT=COM66 
:: BOOT0 pin shoud be tied to VDD 
:: Erase all, BOOT_UBE set to 0xB4 to ensure we boot on bootloader 
:: Enable TrusteZone 
%Prog% -c port=%COMPORT% -e all -ob BOOT_UBE=0xB4 -ob TZEN=0xB4 
:: Reset some option bytes as it is done in orignal script 
%Prog% -c port=%COMPORT% -ob SRAM2_RST=0 SRAM2_ECC=0 SECWM1_STRT=1 SECWM1_END=0 WRPSGn1=0xffffffff WRPSGn2=0xffffffff SECWM2_STRT=1 SECWM2_END=0 HDP1_STRT=1 HDP1_END=0 HDP2_STRT=1 HDP2_END=0 SECBOOT_LOCK=0xC3 
:: Download application and set secure watermarks : To be adapted with actual mapping 
%Prog% -c port=%COMPORT% -d ..\..\Applications\ROT\STiROT_Appli\Binary\appli_enc_sign.hex -ob SECWM1_STRT=0x0 SECWM1_END=0xF SECWM2_STRT=0x7F SECWM2_END=0x0 
:: Switch to provisioning state. 
%Prog% -c port=%COMPORT% -ob PRODUCT_STATE=0x17 
:: In provisiong state, RSS/bootloader is only boot option. 
:: Provision DA and STiROT configuration 
%Prog% -c port=%COMPORT% -sdp ./../DA/Binary/DA_Config.obk -sdp ./Binary/STiRoT_Config.obk -sdp ./Binary/STiRoT_Data.obk 
:: Enable STiROT and lock boot 
%Prog% -c port=%COMPORT% -ob BOOT_UBE=0xC3 
:: Switch to Closed state 
%Prog% -c port=%COMPORT% -ob PRODUCT_STATE=0x72 
:: Once product state is closed, only possible boot is STiROT. 
:: To reopen, launch regression script.
PAUSE

 

Best regards,

Roman

 

 

 

 

 

 

Jocelyn RICARD
ST Employee
July 24, 2024

Hello @RomThi ,

Yes I confirm this setting does not work in context of bootloader usage.

If you look into the original script, the comment associated to this setting is:

"SECBOOT_LOCK should be set to 0xB4 (locked) to be compliant with certification document"

Now, in STiROT context, this setting is redundant with BOOT_UBE which cannot be changed once in Closed state.

Best regards

Jocelyn