STM32H5: added support for TrustZone

- Unified TZ support for STM32L5, STM32H5, STM32U5
- Fixed/added example configuration files
- Expanded documentation
- Added new configurations to automated tests
pull/420/head
Daniele Lacamera 2024-04-10 08:37:06 +02:00
parent fbba5d8370
commit 3ec982109c
31 changed files with 751 additions and 202 deletions

View File

@ -239,12 +239,24 @@ jobs:
arch: arm
config-file: ./config/examples/stm32g0.config
stm32h5_test:
uses: ./.github/workflows/test-build.yml
with:
arch: arm
config-file: ./config/examples/stm32h5.config
stm32h5_dualbank_test:
uses: ./.github/workflows/test-build.yml
with:
arch: arm
config-file: ./config/examples/stm32h5-dualbank.config
stm32h5_wolfcrypt_tz:
uses: ./.github/workflows/test-build.yml
with:
arch: arm
config-file: ./config/examples/stm32h5-wolfcrypt-tz.config
stm32h7_test:
uses: ./.github/workflows/test-build.yml
with:
@ -289,6 +301,12 @@ jobs:
arch: arm
config-file: ./config/examples/stm32l5.config
stm32l5_wolfcrypt_tz:
uses: ./.github/workflows/test-build.yml
with:
arch: arm
config-file: ./config/examples/stm32l5-wolfcrypt-tz.config
stm32u5_nonsecure_dualbank_test:
uses: ./.github/workflows/test-build.yml
with:
@ -301,6 +319,12 @@ jobs:
arch: arm
config-file: ./config/examples/stm32u5.config
stm32u5_wolfcrypt_tz:
uses: ./.github/workflows/test-build.yml
with:
arch: arm
config-file: ./config/examples/stm32u5-wolfcrypt-tz.config
stm32wb_delta_enc_ext_test:
uses: ./.github/workflows/test-build.yml
with:

View File

@ -78,6 +78,7 @@ endif
MAIN_TARGET=factory.bin
TARGET_H_TEMPLATE:=include/target.h.in
ifeq ($(TZEN),1)
ifeq ($(TARGET),stm32l5)
# Don't build a contiguous image
MAIN_TARGET:=wolfboot.bin test-app/image_v1_signed.bin
@ -88,6 +89,12 @@ ifeq ($(TARGET),stm32u5)
MAIN_TARGET:=wolfboot.bin test-app/image_v1_signed.bin
endif
ifeq ($(TARGET),stm32h5)
# Don't build a contiguous image
MAIN_TARGET:=wolfboot.bin test-app/image_v1_signed.bin
endif
endif # TZEN=1
ifeq ($(TARGET),x86_64_efi)
MAIN_TARGET:=wolfboot.efi
endif

View File

@ -146,8 +146,6 @@ ifeq ($(ARCH),ARM)
WOLFBOOT_ORIGIN=0x0C000000
else
WOLFBOOT_ORIGIN=0x08000000
endif
ifneq ($(TZEN),1)
LSCRIPT_IN=hal/$(TARGET)-ns.ld
endif
endif
@ -160,6 +158,7 @@ ifeq ($(ARCH),ARM)
WOLFBOOT_ORIGIN=0x0C000000
else
WOLFBOOT_ORIGIN=0x08000000
LSCRIPT_IN=hal/$(TARGET)-ns.ld
endif
SPI_TARGET=stm32
endif
@ -172,8 +171,6 @@ ifeq ($(ARCH),ARM)
WOLFBOOT_ORIGIN=0x0C000000
else
WOLFBOOT_ORIGIN=0x08000000
endif
ifneq ($(TZEN),1)
LSCRIPT_IN=hal/$(TARGET)-ns.ld
endif
SPI_TARGET=stm32

View File

@ -18,10 +18,10 @@ V?=0
SPMATH?=1
RAM_CODE?=0
DUALBANK_SWAP?=1
WOLFBOOT_PARTITION_SIZE?=0x20000
WOLFBOOT_PARTITION_SIZE?=0xC0000
WOLFBOOT_SECTOR_SIZE?=0x2000
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08100000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x817F000
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0x81FE000
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08040000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x8140000
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0xFFFFFFFF
FLAGS_HOME=0
DISABLE_BACKUP=0

View File

@ -0,0 +1,29 @@
ARCH?=ARM
TZEN?=1
TARGET?=stm32h5
SIGN?=ECC256
HASH?=SHA256
DEBUG?=0
VTOR?=1
CORTEX_M0?=0
CORTEX_M33?=1
NO_ASM?=0
NO_MPU=1
EXT_FLASH?=0
SPI_FLASH?=0
ALLOW_DOWNGRADE?=0
NVM_FLASH_WRITEONCE?=1
WOLFBOOT_VERSION?=1
V?=0
SPMATH?=1
RAM_CODE?=0
DUALBANK_SWAP?=0
WOLFBOOT_PARTITION_SIZE?=0xC0000
WOLFBOOT_SECTOR_SIZE?=0x2000
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08040000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x8140000
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0x08010000
FLAGS_HOME=0
DISABLE_BACKUP=0
WOLFCRYPT_TZ=1
WOLFCRYPT_TZ_PKCS11=1

View File

@ -1,9 +1,9 @@
ARCH?=ARM
TZEN?=0
TZEN?=1
TARGET?=stm32h5
SIGN?=ECC256
HASH?=SHA256
DEBUG?=1
DEBUG?=0
VTOR?=1
CORTEX_M0?=0
CORTEX_M33?=1
@ -18,10 +18,10 @@ V?=0
SPMATH?=1
RAM_CODE?=0
DUALBANK_SWAP?=0
WOLFBOOT_PARTITION_SIZE?=0x20000
WOLFBOOT_PARTITION_SIZE?=0xC0000
WOLFBOOT_SECTOR_SIZE?=0x2000
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08100000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x817F000
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0x81FE000
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08040000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x8140000
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0x08010000
FLAGS_HOME=0
DISABLE_BACKUP=0

View File

@ -1,5 +1,5 @@
ARCH?=ARM
TZEN?=1
TZEN?=0
TARGET?=stm32l5
SIGN?=ECC256
HASH?=SHA256
@ -17,11 +17,12 @@ WOLFBOOT_VERSION?=1
V?=0
SPMATH?=1
RAM_CODE?=0
DUALBANK_SWAP?=0
WOLFBOOT_PARTITION_SIZE?=0x1F800
WOLFBOOT_SECTOR_SIZE?=0x800
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08040000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x805F800
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0x0807F000
FLAGS_HOME=0
DISABLE_BACKUP=0
DUALBANK_SWAP?=1
WOLFBOOT_PARTITION_SIZE?=0x30000
WOLFBOOT_SECTOR_SIZE?=0x2000
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08010000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x08110000
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0xFFFFFFFF
# Use a larger image header size to enforce alignment requirements for the interrupt vector table
IMAGE_HEADER_SIZE?=1024

View File

@ -3,7 +3,7 @@ TZEN?=0
TARGET?=stm32u5
SIGN?=ECC256
HASH?=SHA256
DEBUG?=1
DEBUG?=0
VTOR?=1
CORTEX_M0?=0
CORTEX_M33?=1

View File

@ -0,0 +1,29 @@
ARCH?=ARM
TZEN?=1
TARGET?=stm32u5
SIGN?=ECC256
HASH?=SHA256
DEBUG?=0
VTOR?=1
CORTEX_M0?=0
CORTEX_M33?=1
NO_ASM?=0
NO_MPU=1
EXT_FLASH?=0
SPI_FLASH?=0
ALLOW_DOWNGRADE?=0
NVM_FLASH_WRITEONCE?=1
WOLFBOOT_VERSION?=1
V?=0
SPMATH?=1
RAM_CODE?=0
DUALBANK_SWAP?=0
WOLFBOOT_PARTITION_SIZE?=0x1F800
WOLFBOOT_SECTOR_SIZE?=0x800
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08040000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x805F800
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0x0807F000
FLAGS_HOME=0
DISABLE_BACKUP=0
WOLFCRYPT_TZ=1
WOLFCRYPT_TZ_PKCS11=1

View File

@ -3,7 +3,7 @@ TZEN?=1
TARGET?=stm32u5
SIGN?=ECC256
HASH?=SHA256
DEBUG?=1
DEBUG?=0
VTOR?=1
CORTEX_M0?=0
CORTEX_M33?=1
@ -18,13 +18,10 @@ V?=0
SPMATH?=1
RAM_CODE?=0
DUALBANK_SWAP?=0
WOLFBOOT_PARTITION_SIZE?=0x20000
WOLFBOOT_SECTOR_SIZE?=0x2000
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08100000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x817F000
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0x81FE000
WOLFBOOT_PARTITION_SIZE?=0x1F800
WOLFBOOT_SECTOR_SIZE?=0x800
WOLFBOOT_PARTITION_BOOT_ADDRESS?=0x08040000
WOLFBOOT_PARTITION_UPDATE_ADDRESS?=0x805F800
WOLFBOOT_PARTITION_SWAP_ADDRESS?=0x0807F000
FLAGS_HOME=0
DISABLE_BACKUP=0
# Use a larger image header size to enforce alignment requirements for the interrupt vector table
IMAGE_HEADER_SIZE?=1024

View File

@ -12,7 +12,7 @@ are accessible from any software staged in non-secure domain.
When wolfBoot is compiled with the options `TZEN=1` and `WOLFCRYPT_TZ=1`,
a more complete set of components of the wolfCrypt crypto library are built-in
the bootloader, and they can be accessed by applications or OSs running in
the bootloader, and they can be accessed by applications or OSs running in
non-secure domain through non-secure callable APIs.
This feature is used to isolate the core crypto operations from the applications.
@ -22,7 +22,7 @@ This feature is used to isolate the core crypto operations from the applications
The `WOLFCRYPT_TZ_PKCS11` option provides a standard PKCS11 interface,
including a storage for PKCS11 objects in a dedicated flash area in secure mode.
This means that applications, TLS libraries and operating systems running in
This means that applications, TLS libraries and operating systems running in
non-secure domain can access wolfCrypt through a standard PKCS11 interface and
use the crypto library with pre-provisioned keys that are never exposed to the
non-secure domain.
@ -42,63 +42,63 @@ OPTION BYTES BANK: 0
Read Out Protection:
RDP : 0xAA (Level 0, no protection)
RDP : 0xAA (Level 0, no protection)
BOR Level:
BOR_LEV : 0x0 (BOR Level 0, reset level threshold is around 1.7 V)
BOR_LEV : 0x0 (BOR Level 0, reset level threshold is around 1.7 V)
User Configuration:
nRST_STOP : 0x1 (No reset generated when entering Stop mode)
nRST_STDBY : 0x1 (No reset generated when entering Standby mode)
nRST_SHDW : 0x1 (No reset generated when entering the Shutdown mode)
IWDG_SW : 0x1 (Software independent watchdog)
IWDG_STOP : 0x1 (IWDG counter active in stop mode)
IWDG_STDBY : 0x1 (IWDG counter active in standby mode)
WWDG_SW : 0x1 (Software window watchdog)
SWAP_BANK : 0x0 (Bank 1 and bank 2 address are not swapped)
DB256 : 0x1 (256Kb dual-bank Flash with contiguous addresses)
DBANK : 0x0 (Single bank mode with 128 bits data read width)
SRAM2_PE : 0x1 (SRAM2 parity check disable)
SRAM2_RST : 0x1 (SRAM2 is not erased when a system reset occurs)
nSWBOOT0 : 0x1 (BOOT0 taken from PH3/BOOT0 pin)
nBOOT0 : 0x1 (nBOOT0 = 1)
PA15_PUPEN : 0x1 (USB power delivery dead-battery disabled/ TDI pull-up activated)
TZEN : 0x1 (Global TrustZone security enabled)
HDP1EN : 0x0 (No HDP area 1)
HDP1_PEND : 0x0 (0x8000000)
HDP2EN : 0x0 (No HDP area 2)
HDP2_PEND : 0x0 (0x8000000)
NSBOOTADD0 : 0x100000 (0x8000000)
NSBOOTADD1 : 0x17F200 (0xBF90000)
SECBOOTADD0 : 0x180000 (0xC000000)
BOOT_LOCK : 0x0 (Boot based on the pad/option bit configuration)
nRST_STOP : 0x1 (No reset generated when entering Stop mode)
nRST_STDBY : 0x1 (No reset generated when entering Standby mode)
nRST_SHDW : 0x1 (No reset generated when entering the Shutdown mode)
IWDG_SW : 0x1 (Software independant watchdog)
IWDG_STOP : 0x1 (IWDG counter active in stop mode)
IWDG_STDBY : 0x1 (IWDG counter active in standby mode)
WWDG_SW : 0x1 (Software window watchdog)
SWAP_BANK : 0x0 (Bank 1 and bank 2 address are not swapped)
DB256 : 0x1 (256Kb dual-bank Flash with contiguous addresses)
DBANK : 0x0 (Single bank mode with 128 bits data read width)
SRAM2_PE : 0x1 (SRAM2 parity check disable)
SRAM2_RST : 0x1 (SRAM2 is not erased when a system reset occurs)
nSWBOOT0 : 0x1 (BOOT0 taken from PH3/BOOT0 pin)
nBOOT0 : 0x1 (nBOOT0 = 1)
PA15_PUPEN : 0x1 (USB power delivery dead-battery disabled/ TDI pull-up activated)
TZEN : 0x1 (Global TrustZone security enabled)
HDP1EN : 0x0 (No HDP area 1)
HDP1_PEND : 0x0 (0x8000000)
HDP2EN : 0x0 (No HDP area 2)
HDP2_PEND : 0x0 (0x8000000)
NSBOOTADD0 : 0x100000 (0x8000000)
NSBOOTADD1 : 0x17F200 (0xBF90000)
SECBOOTADD0 : 0x180000 (0xC000000)
BOOT_LOCK : 0x0 (Boot based on the pad/option bit configuration)
Secure Area 1:
SECWM1_PSTRT : 0x0 (0x8000000)
SECWM1_PEND : 0x39 (0x8039000)
SECWM1_PSTRT : 0x0 (0x8000000)
SECWM1_PEND : 0x39 (0x8039000)
Write Protection 1:
WRP1A_PSTRT : 0x7F (0x807F000)
WRP1A_PEND : 0x0 (0x8000000)
WRP1B_PSTRT : 0x7F (0x807F000)
WRP1B_PEND : 0x0 (0x8000000)
WRP1A_PSTRT : 0x7F (0x807F000)
WRP1A_PEND : 0x0 (0x8000000)
WRP1B_PSTRT : 0x7F (0x807F000)
WRP1B_PEND : 0x0 (0x8000000)
OPTION BYTES BANK: 1
Secure Area 2:
SECWM2_PSTRT : 0x7F (0x807F000)
SECWM2_PEND : 0x0 (0x8000000)
SECWM2_PSTRT : 0x7F (0x807F000)
SECWM2_PEND : 0x0 (0x8000000)
Write Protection 2:
WRP2A_PSTRT : 0x7F (0x80BF000)
WRP2A_PEND : 0x0 (0x8040000)
WRP2B_PSTRT : 0x7F (0x80BF000)
WRP2B_PEND : 0x0 (0x8040000)
WRP2A_PSTRT : 0x7F (0x80BF000)
WRP2A_PEND : 0x0 (0x8040000)
WRP2B_PSTRT : 0x7F (0x80BF000)
WRP2B_PEND : 0x0 (0x8040000)
```
@ -115,4 +115,117 @@ STM32_Programmer_CLI -c port=swd -d test-app/image_v1_signed.bin 0x08040000
- Green LED: ECDSA Sign/Verify test successful
### Example using STM32H563
- Copy the example configuration for STM32-L5 with support for wolfCrypt in
TrustZone-M and PKCS11 interface: `cp config/examples/stm32l5-wolfcrypt-tz.config .config`
- Run `make`. `wolfboot.elf` and the test applications are built as separate
objects. The application is signed and stored as `test-app/image_v1_signed.bin`.
- Ensure that the option bytes on your target device are set as follows:
```
OPTION BYTES BANK: 0
Product state:
PRODUCT_STATE: 0xED (Open)
BOR Level:
BOR_LEV : 0x0 (BOR Level 1, the threshold level is low (around 2.1 V))
BORH_EN : 0x0 (0x0)
User Configuration:
IO_VDD_HSLV : 0x0 (0x0)
IO_VDDIO2_HSLV: 0x0 (0x0)
IWDG_STOP : 0x1 (0x1)
IWDG_STDBY : 0x1 (0x1)
BOOT_UBE : 0xB4 (OEM-iRoT (user flash) selected)
SWAP_BANK : 0x0 (0x0)
IWDG_SW : 0x1 (0x1)
NRST_STOP : 0x1 (0x1)
NRST_STDBY : 0x1 (0x1)
OPTION BYTES BANK: 1
User Configuration 2:
TZEN : 0xB4 (Trust zone enabled)
SRAM2_ECC : 0x1 (SRAM2 ECC check disabled)
SRAM3_ECC : 0x1 (SRAM3 ECC check disabled)
BKPRAM_ECC : 0x1 (BKPRAM ECC check disabled)
SRAM2_RST : 0x1 (SRAM2 not erased when a system reset occurs)
SRAM1_3_RST : 0x1 (SRAM1 and SRAM3 not erased when a system reset occurs)
OPTION BYTES BANK: 2
Boot Configuration:
NSBOOTADD : 0x80400 (0x8040000)
NSBOOT_LOCK : 0xC3 (The SWAP_BANK and NSBOOTADD can still be modified following their individual rules.)
SECBOOT_LOCK : 0xC3 (The BOOT_UBE, SWAP_BANK and SECBOOTADD can still be modified following their individual rules.)
SECBOOTADD : 0xC0000 (0xC000000)
OPTION BYTES BANK: 3
Bank1 - Flash watermark area definition:
SECWM1_STRT : 0x0 (0x8000000)
SECWM1_END : 0x1F (0x803E000)
Write sector group protection 1:
WRPSGn1 : 0xFFFFFFFF (0x0)
OPTION BYTES BANK: 4
Bank2 - Flash watermark area definition:
SECWM2_STRT : 0x7F (0x81FE000)
SECWM2_END : 0x0 (0x8100000)
Write sector group protection 2:
WRPSGn2 : 0xFFFFFFFF (0x8000000)
OPTION BYTES BANK: 5
OTP write protection:
LOCKBL : 0x0 (0x0)
OPTION BYTES BANK: 6
Flash data bank 1 sectors:
EDATA1_EN : 0x0 (No Flash high-cycle data area)
EDATA1_STRT : 0x0 (0x0)
OPTION BYTES BANK: 7
Flash data bank 2 sectors :
EDATA2_EN : 0x0 (No Flash high-cycle data area)
EDATA2_STRT : 0x0 (0x0)
OPTION BYTES BANK: 8
Flash HDP bank 1:
HDP1_STRT : 0x1 (0x2000)
HDP1_END : 0x0 (0x0)
OPTION BYTES BANK: 9
Flash HDP bank 2:
HDP2_STRT : 0x1 (0x2000)
HDP2_END : 0x0 (0x0)
```
- Upload `wolfboot.bin` and the test application to the two different domains in flash:
```
STM32_Programmer_CLI -c port=swd -d wolfboot.bin 0x0C000000
STM32_Programmer_CLI -c port=swd -d test-app/image_v1_signed.bin 0x08040000
```
- After rebooting, the LED on the board should turn on sequentially:
- Red LED: Secure boot was successful. Application has started.
- Blue LED: PKCS11 Token has been initialized and stored
- Green LED: ECDSA Sign/Verify test successful

View File

@ -116,16 +116,16 @@ Example 1MB partitioning on STM32L4
### Scenario 1: TrustZone Enabled
__NOTE__: to run wolfBoot in secure mode with wolfCrypt as secure crypto engine,
please refer to [/docs/STM32-TZ.md](/docs/STM32-TZ.md).
#### Example Description
The implementation shows how to switch from secure application to non-secure application,
thanks to the system isolation performed, which splits the internal Flash and internal
SRAM memories into two halves:
- the first half for secure application
- the second half for non-secure application
SRAM memories into two parts:
- the first half is used by wolfboot running in secure mode and the secure application
- the remaining available space is used for non-secure application and update partition
The example configuration for this scenario is available in [/config/examples/stm32l5.config](/config/examples/stm32l5.config).
#### Hardware and Software environment
@ -145,7 +145,7 @@ SECWM2_PSTRT=0x1 SECWM2_PEND=0x0 No page of internal Flash Bank2 set as secur
#### How to use it
1. `cp ./config/examples/stm32l5.config .config`
2. `make TZEN=1`
2. `make`
3. Prepare board with option bytes configuration reported above
- `STM32_Programmer_CLI -c port=swd mode=hotplug -ob TZEN=1 DBANK=1`
- `STM32_Programmer_CLI -c port=swd mode=hotplug -ob SECWM1_PSTRT=0x0 SECWM1_PEND=0x7F SECWM2_PSTRT=0x1 SECWM2_PEND=0x0`
@ -160,12 +160,25 @@ SECWM2_PSTRT=0x1 SECWM2_PEND=0x0 No page of internal Flash Bank2 set as secur
* Linux: `/usr/local/STMicroelectronics/STM32Cube/STM32CubeProgrammer/bin/STM32_Programmer_CLI`
* Mac OS/X: `/Applications/STMicroelectronics/STM32Cube/STM32CubeProgrammer/STM32CubeProgrammer.app/Contents/MacOs/bin/STM32_Programmer_CLI`
### Scenario 2: Trustzone Enabled, wolfCrypt as secure engine for NS applications
### Scenario 2: Trustzone Disabled
This is similar to Scenario 1, but also includes wolfCrypt in secure mode, and
that can be accessed via PKCS11 interface by non-secure applications.
This option can be enabled with the `WOLFCRYPT_TZ=1` and `WOLFCRYPT_TZ_PKCS11=1`
options in your configuration. This enables a PKCS11 accessible from NS domain via
non-secure callables (NSC).
The example configuration for this scenario is available in [/config/examples/stm32l5-wolfcrypt-tz.config](/config/examples/stm32l5-wolfcrypt-tz.config).
For more information, see [/docs/STM32-TZ.md](/docs/STM32-TZ.md).
### Scenario 3: Trustzone Disabled, using DUAL BANK
#### Example Description
The implementation shows how to use STM32L5xx in DUAL_BANK mode, with TrustZone disabled.
The implementation shows how to use STM32L5xx in DUAL BANK mode, with TrustZone disabled.
The DUAL_BANK option is only available on this target when TrustZone is disabled (TZEN = 0).
The flash memory is segmented into two different banks:
@ -235,13 +248,23 @@ The STM32U5 is a Cortex-M33 (ARMv8-M).
Note: We have seen issues with vector table alignment, so the default image header size (IMAGE_HEADER_SIZE) has been increased to 1024 bytes to avoid potential issues.
### Scenario 1: TrustZone Enabled
### Scenario 1: TrustZone enabled, staging non-secure application
#### Example description
The implementation shows how to switch from secure application to non-secure application,
thanks to the system isolation performed, which splits the internal Flash and internal
SRAM memories into two parts:
- the first 256KB are used by wolfboot running in secure mode and the secure application
- the remaining available space is used for non-secure application and update partition
The example configuration for this scenario is available in [/config/examples/stm32u5.config](/config/examples/stm32u5.config).
#### Example Description
The implementation shows how to switch from secure application to non-secure application,
thanks to the system isolation performed, which splits the internal Flash and internal
SRAM memories into two halves:
SRAM memories into two parts:
- the first half for secure application
- the second half for non-secure application
@ -278,7 +301,21 @@ SECWM2_PSTRT=0x1 SECWM2_PEND=0x0 No page of internal Flash Bank2 set as secur
* Linux: `/usr/local/STMicroelectronics/STM32Cube/STM32CubeProgrammer/bin/STM32_Programmer_CLI`
* Mac OS/X: `/Applications/STMicroelectronics/STM32Cube/STM32CubeProgrammer/STM32CubeProgrammer.app/Contents/MacOs/bin/STM32_Programmer_CLI`
### Scenario 2: TrustZone Disabled
### Scenario 2: TrustZone Enabled, wolfCrypt as secure engine for NS applications
This is similar to Scenario 1, but also includes wolfCrypt in secure mode, and
that can be accessed via PKCS11 interface by non-secure applications.
This option can be enabled with the `WOLFCRYPT_TZ=1` and `WOLFCRYPT_TZ_PKCS11=1`
options in your configuration. This enables a PKCS11 accessible from NS domain via
non-secure callables (NSC).
The example configuration for this scenario is available in [/config/examples/stm32u5-wolfcrypt-tz.config](/config/examples/stm32u5-wolfcrypt-tz.config).
For more information, see [/docs/STM32-TZ.md](/docs/STM32-TZ.md).
### Scenario 3: TrustZone Disabled (DUAL BANK mode)
#### Example Description
@ -810,7 +847,52 @@ arm-none-eabi-gdb
## STM32H5
### DUALBANK mode (Trustzone disabled)
Like [STM32L5](#stm32l5) and [STM32U5](#stm32u5), STM32H5 support is also demonstrated
through different scenarios.
### Scenario 1: TrustZone enabled, staging non-secure application
#### Example description
The implementation shows how to switch from secure application to non-secure application,
thanks to the system isolation performed, which splits the internal Flash and internal
SRAM memories into two parts:
- the first 256KB are used by wolfboot running in secure mode and the secure application
- the remaining available space is used for non-secure application and update partition
The example configuration for this scenario is available in [/config/examples/stm32h5.config](/config/examples/stm32h5.config).
#### How to use it
- set the option bytes to enable trustzone:
`STM32_Programmer_CLI -c port=swd -ob TZEN=0xB4`
- set the option bytes to enable flash secure protection of first 256KB:
`STM32_Programmer_CLI -c port=swd -ob SECWM1_PSTRT=0x0 SECWM1_PEND=0x1F SECWM2_PSTRT=0x1F SECWM2_PEND=0x0`
- flash the wolfboot image to the secure partition:
`STM32_Programmer_CLI -c port=swd -d wolfboot.bin 0x0C000000`
- flash the application image to the non-secure partition:
`STM32_Programmer_CLI -c port=swd -d test-app/image_v1_signed.bin 0x08040000`
For a full list of all the option bytes tested with this configuration, refer to [STM32-TZ.md](/docs/STM32-TZ.md).
### Scenario 2: Trustzone Enabled, wolfCrypt as secure engine for NS applications
This is similar to Scenario 1, but also includes wolfCrypt in secure mode, and
that can be accessed via PKCS11 interface by non-secure applications.
This option can be enabled with the `WOLFCRYPT_TZ=1` and `WOLFCRYPT_TZ_PKCS11=1`
options in your configuration. This enables a PKCS11 accessible from NS domain via
non-secure callables (NSC).
The example configuration for this scenario is available in [/config/examples/stm32h5-wolfcrypt-tz.config](/config/examples/stm32h5-wolfcrypt-tz.config).
For more information, see [/docs/STM32-TZ.md](/docs/STM32-TZ.md).
### Scenario 3: DUALBANK mode (Trustzone disabled)
The STM32H5 can be configured to use hardware-assisted bank swapping to facilitate the update.
The configuration file to copy into `.config` is `config/examples/stm32h5-dualbank.config`.

View File

@ -33,12 +33,12 @@
#include "hal/stm32h5.h"
#endif
#include "hal/stm32_tz.h"
#include "image.h"
#include "hal.h"
#if defined (__ARM_FEATURE_CMSE) && (__ARM_FEATURE_CMSE == 3U) && (!defined(FLAGS_HOME) || !defined(DISABLE_BACKUP))
#define SCB_SHCSR (*(volatile uint32_t *)(0xE000ED24))
#define SCB_SHCSR_SECUREFAULT_EN (1<<19)
static void RAMFUNCTION hal_flash_nonsecure_unlock(void)
{
@ -120,6 +120,42 @@ void hal_tz_release_nonsecure_area(void)
#define release_nonsecure_area(...) do{}while(0)
#endif
#ifdef PLATFORM_stm32h5
#define GTZC1_BASE (0x50032400)
#define GTZC1_TZSC (*(volatile uint32_t *)(GTZC1_BASE + 0x00))
#define GTZC1_TZIC (*(volatile uint32_t *)(GTZC1_BASE + 0x0400))
#define GTZC1_MPCBB1_S ((volatile uint32_t *)(GTZC1_BASE + 0x0800 + 0x100))
#define GTZC1_MPCBB2_S ((volatile uint32_t *)(GTZC1_BASE + 0x0C00 + 0x100))
#define GTZC1_MPCBB3_S ((volatile uint32_t *)(GTZC1_BASE + 0x1000 + 0x100))
#define SET_GTZC1_MPCBBx_S_VCTR(bank,n,val) \
(*((volatile uint32_t *)(GTZC1_MPCBB##bank##_S) + n ))= val
void hal_gtzc_init(void)
{
int i;
/* One bit in the bitmask: 512B */
/* Configure SRAM1 as secure (Low 256 KB) */
for (i = 0; i < 16; i++) {
SET_GTZC1_MPCBBx_S_VCTR(1, i, 0xFFFFFFFF);
}
/* Configure SRAM2 as secure (64 KB) */
for (i = 0; i < 4; i++) {
SET_GTZC1_MPCBBx_S_VCTR(2, i, 0xFFFFFFFF);
}
/* Configure SRAM3 as non-secure (320 KB) */
for (i = 0; i < 20; i++) {
SET_GTZC1_MPCBBx_S_VCTR(3, i, 0x0);
}
}
#else
#define GTZC_MPCBB1_S_BASE (0x50032C00)
#define GTZC_MPCBB1_S_VCTR_BASE (GTZC_MPCBB1_S_BASE + 0x100)
@ -129,13 +165,14 @@ void hal_tz_release_nonsecure_area(void)
#define SET_GTZC_MPCBBx_S_VCTR(bank,n,val) \
(*((volatile uint32_t *)(GTZC_MPCBB##bank##_S_VCTR_BASE ) + n ))= val
void hal_gtzc_init(void)
{
int i;
/* Configure lower half of total RAM as secure
* 0x3000 0000 : 0x3001 FFFF - 128KB
*/
/* One bit in the bitmask: 256B */
/* Configure lower half of total RAM as secure
* 0x3000 0000 : 0x3001 FFFF - 128KB
*/
for (i = 0; i < 16; i++) {
SET_GTZC_MPCBBx_S_VCTR(1, i, 0xFFFFFFFF);
}
@ -147,43 +184,47 @@ void hal_gtzc_init(void)
SET_GTZC_MPCBBx_S_VCTR(1, i, 0x0);
}
/* Configure SRAM2 as non-secure
* 0x2003 0000 : 0x2003 FFFF - 64 KB
*/
/* Configure SRAM2 as non-secure
* 0x2003 0000 : 0x2003 FFFF - 64 KB
*/
for (i = 0; i < 8; i++) {
SET_GTZC_MPCBBx_S_VCTR(2, i, 0x0);
}
}
#endif
/* SAU registers, used to define memory mapped regions */
#define SAU_CTRL (*(volatile uint32_t *)(0xE000EDD0))
#define SAU_RNR (*(volatile uint32_t *)(0xE000EDD8)) /** SAU_RNR - region number register **/
#define SAU_RBAR (*(volatile uint32_t *)(0xE000EDDC)) /** SAU_RBAR - region base address register **/
#define SAU_RLAR (*(volatile uint32_t *)(0xE000EDE0)) /** SAU_RLAR - region limit address register **/
#ifdef PLATFORM_stm32h5
#define SAU_REGION_MASK 0x000000FF
#define SAU_ADDR_MASK 0xFFFFFFE0 /* LS 5 bit are reserved or used for flags */
/* Flag for the SAU region limit register */
#define SAU_REG_ENABLE (1 << 0) /* Indicates that the region is enabled. */
#define SAU_REG_SECURE (1 << 1) /* When on, the region is S or NSC */
#define SAU_INIT_CTRL_ENABLE (1 << 0)
#define SAU_INIT_CTRL_ALLNS (1 << 1)
static void sau_init_region(uint32_t region, uint32_t start_addr,
uint32_t end_addr, int secure)
void hal_tz_sau_init(void)
{
uint32_t secure_flag = 0;
if (secure)
secure_flag = SAU_REG_SECURE;
SAU_RNR = region & SAU_REGION_MASK;
SAU_RBAR = start_addr & SAU_ADDR_MASK;
SAU_RLAR = (end_addr & SAU_ADDR_MASK)
| secure_flag | SAU_REG_ENABLE;
uint32_t page_n = 0;
/* WIP: SAU is set up before staging */
/* Non-secure callable: NSC functions area */
sau_init_region(0, 0x0C038000, 0x0C040000, 1);
/* Non-Secure: application flash area (first bank) */
sau_init_region(1, 0x08040000, 0x080FFFFF, 0);
/* Non-Secure: application flash area (second bank) */
sau_init_region(2, 0x08140000, 0x081FFFFF, 0);
/* Secure RAM regions in SRAM1/SRAM2 */
sau_init_region(3, 0x30000000, 0x3004FFFF, 1);
/* Non-secure RAM region in SRAM3 */
sau_init_region(4, 0x20050000, 0x2008FFFF, 0);
/* Non-secure: internal peripherals */
sau_init_region(5, 0x40000000, 0x4FFFFFFF, 0);
/* Enable SAU */
SAU_CTRL = SAU_INIT_CTRL_ENABLE;
/* Enable securefault handler */
SCB_SHCSR |= SCB_SHCSR_SECUREFAULT_EN;
}
#else
void hal_tz_sau_init(void)
{
/* Non-secure callable: NSC functions area */
@ -205,6 +246,7 @@ void hal_tz_sau_init(void)
SCB_SHCSR |= SCB_SHCSR_SECUREFAULT_EN;
}
#endif
#ifdef WOLFCRYPT_SECURE_MODE
@ -229,22 +271,17 @@ static void hsi48_on(void)
RCC_CRRCR |= RCC_CRRCR_HSI48ON;
while ((RCC_CRRCR & RCC_CRRCR_HSI48RDY) == 0)
;
#endif
#ifdef PLATFORM_stm32u5
#else /* U5 and H5 */
RCC_CR |= RCC_CR_HSI48ON;
while ((RCC_CR & RCC_CR_HSI48RDY) == 0)
;
#endif
}
void hal_trng_init(void)
{
uint32_t reg_val;
hsi48_on();
#ifdef PLATFORM_stm32u5
#define RCC_AHB2_CLOCK_ER RCC_AHB2ENR1_CLOCK_ER
#endif
RCC_AHB2_CLOCK_ER |= TRNG_AHB2_CLOCK_ER;
reg_val = TRNG_CR;
@ -252,9 +289,9 @@ void hal_trng_init(void)
reg_val &= ~(0x7 << TRNG_CR_CLKDIV_SHIFT);
reg_val &= ~(0x3 << TRNG_CR_CONFIG2_SHIFT);
reg_val &= ~(0x7 << TRNG_CR_CONFIG3_SHIFT);
reg_val |= 0x0F << TRNG_CR_CONFIG1_SHIFT;
reg_val |= 0x0D << TRNG_CR_CONFIG3_SHIFT;
#ifdef PLATFORM_stm32u5 /* RM0456 40.6.2 */
reg_val |= 0x06 << TRNG_CR_CLKDIV_SHIFT;
#endif

57
hal/stm32_tz.h 100644
View File

@ -0,0 +1,57 @@
/* stm32_tz.h
*
* Copyright (C) 2024 wolfSSL Inc.
*
* This file is part of wolfBoot.
*
* wolfBoot is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfBoot is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
#ifndef STM32_TZ_INCLUDED
#define STM32_TZ_INCLUDED
#include <stdint.h>
/* SAU registers, used to define memory mapped regions */
#define SAU_CTRL (*(volatile uint32_t *)(0xE000EDD0))
#define SAU_RNR (*(volatile uint32_t *)(0xE000EDD8)) /** SAU_RNR - region number register **/
#define SAU_RBAR (*(volatile uint32_t *)(0xE000EDDC)) /** SAU_RBAR - region base address register **/
#define SAU_RLAR (*(volatile uint32_t *)(0xE000EDE0)) /** SAU_RLAR - region limit address register **/
#define SAU_REGION_MASK 0x000000FF
#define SAU_ADDR_MASK 0xFFFFFFE0 /* LS 5 bit are reserved or used for flags */
/* Flag for the SAU region limit register */
#define SAU_REG_ENABLE (1 << 0) /* Indicates that the region is enabled. */
#define SAU_REG_SECURE (1 << 1) /* When on, the region is S or NSC */
#define SAU_INIT_CTRL_ENABLE (1 << 0)
#define SAU_INIT_CTRL_ALLNS (1 << 1)
#define SCB_SHCSR (*(volatile uint32_t *)(0xE000ED24))
#define SCB_SHCSR_SECUREFAULT_EN (1<<19)
static inline void sau_init_region(uint32_t region, uint32_t start_addr,
uint32_t end_addr, int secure)
{
uint32_t secure_flag = 0;
if (secure)
secure_flag = SAU_REG_SECURE;
SAU_RNR = region & SAU_REGION_MASK;
SAU_RBAR = start_addr & SAU_ADDR_MASK;
SAU_RLAR = (end_addr & SAU_ADDR_MASK)
| secure_flag | SAU_REG_ENABLE;
}
#endif

View File

@ -1,7 +1,7 @@
MEMORY
{
FLASH (rx) : ORIGIN = 0x08000000, LENGTH = @BOOTLOADER_PARTITION_SIZE@
RAM (rwx) : ORIGIN = 0x20000000, LENGTH = 0x00020000 /* mapping TCM only */
RAM (rwx) : ORIGIN = 0x0A000000, LENGTH = 0x00020000 /* mapping TCM only */
}
SECTIONS

View File

@ -71,7 +71,8 @@ int RAMFUNCTION hal_flash_write(uint32_t address, const uint8_t *data, int len)
dst = (uint32_t *)address;
#if (TZ_SECURE())
if (address >= FLASH_BANK2_BASE)
if ( ((address < FLASH_BANK2_BASE) && (address >= WOLFBOOT_PARTITION_BOOT_ADDRESS)) ||
(address >= WOLFBOOT_PARTITION_UPDATE_ADDRESS))
hal_tz_claim_nonsecure_area(address, len);
/* Convert into secure address space */
dst = (uint32_t *)((address & (~FLASHMEM_ADDRESS_SPACE)) | FLASH_SECURE_MMAP_BASE);
@ -301,8 +302,8 @@ static void clock_pll_on(void)
}
#if TZ_SECURE()
static void periph_unsecure()
#if (TZ_SECURE())
static void periph_unsecure(void)
{
uint32_t pin;
@ -315,19 +316,16 @@ static void periph_unsecure()
PWR_CR2 |= PWR_CR2_IOSV;
/*Un-secure User LED GPIO pins */
#ifdef STM32_DISCOVERY
GPIO_SECCFGR(GPIOD_BASE) &= ~(1<<LED_USR_PIN);
GPIO_SECCFGR(GPIOG_BASE) &= ~(1<<LED_BOOT_PIN);
#else /* Nucleo board */
GPIO_SECCFGR(GPIOA_BASE) &= ~(1<<LED_BOOT_PIN);
GPIO_SECCFGR(GPIOB_BASE) &= ~(1<<LED_USR_PIN);
GPIO_SECCFGR(GPIOC_BASE) &= ~(1<<LED_EXTRA_PIN);
#endif
GPIO_SECCFGR(GPIOG_BASE) &= ~(1 << 4);
GPIO_SECCFGR(GPIOB_BASE) &= ~(1 << 0);
GPIO_SECCFGR(GPIOF_BASE) &= ~(1 << 4);
#if 0
/* Unsecure LPUART1 */
TZSC_PRIVCFGR2 &= ~(TZSC_PRIVCFG2_LPUARTPRIV);
GPIO_SECCFGR(GPIOG_BASE) &= ~(1<<UART1_TX_PIN);
GPIO_SECCFGR(GPIOG_BASE) &= ~(1<<UART1_RX_PIN);
#endif
}
#endif
@ -371,17 +369,22 @@ static uint8_t bootloader_copy_mem[BOOTLOADER_SIZE];
static void fork_bootloader(void)
{
uint8_t *data = (uint8_t *) FLASHMEM_ADDRESS_SPACE;
uint32_t data = (uint32_t) FLASHMEM_ADDRESS_SPACE;
uint32_t dst = FLASH_BANK2_BASE;
uint32_t r = 0, w = 0;
int i;
#if TZ_SECURE()
data = (uint32_t)((data & (~FLASHMEM_ADDRESS_SPACE)) | FLASH_SECURE_MMAP_BASE);
dst = (uint32_t)((dst & (~FLASHMEM_ADDRESS_SPACE)) | FLASH_SECURE_MMAP_BASE);
#endif
/* Return if content already matches */
if (memcmp(data, (const char*)FLASH_BANK2_BASE, BOOTLOADER_SIZE) == 0)
if (memcmp((void *)data, (const char*)dst, BOOTLOADER_SIZE) == 0)
return;
/* Read the wolfBoot image in RAM */
memcpy(bootloader_copy_mem, data, BOOTLOADER_SIZE);
memcpy(bootloader_copy_mem, (void*)data, BOOTLOADER_SIZE);
/* Mass-erase */
hal_flash_unlock();
@ -393,24 +396,27 @@ static void fork_bootloader(void)
void hal_init(void)
{
#if defined(DUALBANK_SWAP) && defined(__WOLFBOOT)
if ((FLASH_OPTSR_CUR & (FLASH_OPTSR_SWAP_BANK)) == 0)
fork_bootloader();
#endif
#if TZ_SECURE()
hal_tz_sau_init();
hal_gtzc_init();
#endif
clock_pll_on();
#if defined(DUALBANK_SWAP) && defined(__WOLFBOOT)
if ((FLASH_OPTSR_CUR & (FLASH_OPTSR_SWAP_BANK)) == 0)
fork_bootloader();
#endif
}
void hal_prepare_boot(void)
{
clock_pll_off();
#if TZ_SECURE()
#if (TZ_SECURE())
periph_unsecure();
#endif
}

View File

@ -263,7 +263,7 @@
#define FLASH_OPTSR_SWAP_BANK (1 << 31)
#endif
/* Register values (for both secure and non secure registers)
/* Register values (for both secure and non secure registers)
* RM0481 Table 75 */
#define FLASH_SR_BSY (1 << 0)
@ -277,7 +277,7 @@
#define FLASH_SR_OPTE (1 << 21)
#define FLASH_SR_OPTWE (1 << 22)
#define FLASH_CCR_CLR_BUSY (1 << 0)
#define FLASH_CCR_CLR_BUSY (1 << 0)
#define FLASH_CCR_CLR_WBNE (1 << 1)
#define FLASH_CCR_CLR_DBNE (1 << 3)
#define FLASH_CCR_CLR_EOP (1 << 16)
@ -335,6 +335,7 @@
#define GPIOB_BASE 0x52020400
#define GPIOC_BASE 0x52020800
#define GPIOD_BASE 0x52020C00
#define GPIOF_BASE 0x52021400
#define GPIOG_BASE 0x52021800
/* RCC AHB2 Clock Enable Register */
@ -343,8 +344,13 @@
#define GPIOB_AHB2_CLOCK_ER (1 << 1)
#define GPIOC_AHB2_CLOCK_ER (1 << 2)
#define GPIOD_AHB2_CLOCK_ER (1 << 3)
#define GPIOF_AHB2_CLOCK_ER (1 << 5)
#define GPIOG_AHB2_CLOCK_ER (1 << 6)
#define TRNG_AHB2_CLOCK_ER (1 << 18)
#define PKA_AHB2_CLOCK_ER (1 << 19)
#define SAES_AHB2_CLOCK_ER (1 << 20)
#define SRAM2_AHB2_CLOCK_ER (1 << 30)
#define SRAM3_AHB2_CLOCK_ER (1 << 31)
#define RCC_APB2_CLOCK_ER (*(volatile uint32_t *)(RCC_BASE + 0xA4))
#define UART1_APB2_CLOCK_ER_VAL (1 << 14)
@ -355,16 +361,12 @@
#define GPIO_SECCFGR(base) (*(volatile uint32_t *)(base + 0x30))
#ifdef STM32_DISCOVERY
#define LED_AHB2_ENABLE (GPIOD_AHB2_CLOCK_ER | GPIOG_AHB2_CLOCK_ER)
#define LED_BOOT_PIN (12) /* PG12 - Discovery - Green Led */
#define LED_USR_PIN (3) /* PD3 - Discovery - Red Led */
#else
#define LED_AHB2_ENABLE (GPIOA_AHB2_CLOCK_ER | GPIOB_AHB2_CLOCK_ER | \
GPIOC_AHB2_CLOCK_ER)
#define LED_BOOT_PIN (9) /* PA9 - Nucleo board - Red Led */
#define LED_USR_PIN (7) /* PC7 - Nucleo board - Green Led */
#define LED_EXTRA_PIN (7) /* PB7 - Nucleo board - Blue Led */
#endif
#define LED_AHB2_ENABLE (GPIOG_AHB2_CLOCK_ER | GPIOB_AHB2_CLOCK_ER | \
GPIOF_AHB2_CLOCK_ER)
#define LED_BOOT_PIN (4) /* PG4 - Nucleo board - Orange Led */
#define LED_USR_PIN (0) /* PB0 - Nucleo board - Green Led */
#define LED_EXTRA_PIN (4) /* PF4 - Nucleo board - Blue Led */
#endif /* STM32H5_DEF_INCLUDED */

View File

@ -1,8 +1,11 @@
MEMORY
{
FLASH (rx) : ORIGIN = @WOLFBOOT_ORIGIN@, LENGTH = @BOOTLOADER_PARTITION_SIZE@
RAM (rwx) : ORIGIN = 0x30000000, LENGTH = 0x00017FFF
FLASH_NSC(rx): ORIGIN = @WOLFBOOT_ORIGIN@ + 0x20000, LENGTH = 0x20000
FLASH (rx) : ORIGIN = @WOLFBOOT_ORIGIN@, LENGTH = @BOOTLOADER_PARTITION_SIZE@ - 0x20000
RAM (rwx) : ORIGIN = 0x30000000, LENGTH = 0x30000
RAM_KV (rw): ORIGIN = 0x30020000, LENGTH = 0x10000
RAM_HEAP (rw): ORIGIN = 0x30030000, LENGTH = 0x10000 /* 64KB Heap for wolfcrypt/PKCS11 */
FLASH_KEYVAULT(rw): ORIGIN = @WOLFBOOT_ORIGIN@ + 0x20000, LENGTH = 0x18000
FLASH_NSC(rx): ORIGIN = @WOLFBOOT_ORIGIN@ + 0x38000, LENGTH = 0x8000
}
SECTIONS
@ -25,6 +28,7 @@ SECTIONS
.gnu.sgstubs :
{
. += 0x400;
. = ALIGN(4);
*(.gnu.sgstubs*) /* Secure Gateway stubs */
. = ALIGN(4);
@ -53,7 +57,15 @@ SECTIONS
_end = .;
} > RAM
. = ALIGN(8);
}
END_STACK = ORIGIN(RAM) + LENGTH(RAM);
_keyvault_origin = ORIGIN(RAM_KV);
_keyvault_size = LENGTH(RAM_KV);
_flash_keyvault = ORIGIN(FLASH_KEYVAULT);
_flash_keyvault_size = LENGTH(FLASH_KEYVAULT);
_start_heap = ORIGIN(RAM_HEAP);
_heap_size = LENGTH(RAM_HEAP);

50
hal/stm32u5-ns.ld 100644
View File

@ -0,0 +1,50 @@
MEMORY
{
FLASH (rx) : ORIGIN = 0x08000000, LENGTH = @BOOTLOADER_PARTITION_SIZE@
RAM (rwx) : ORIGIN = 0x20000000, LENGTH = 0x00020000 /* mapping TCM only */
}
SECTIONS
{
.text :
{
_start_text = .;
KEEP(*(.isr_vector))
*(.text*)
*(.rodata*)
. = ALIGN(4);
_end_text = .;
} > FLASH
.edidx :
{
. = ALIGN(4);
*(.ARM.exidx*)
} > FLASH
_stored_data = .;
.data : AT (_stored_data)
{
_start_data = .;
KEEP(*(.data*))
. = ALIGN(4);
KEEP(*(.ramcode))
. = ALIGN(4);
_end_data = .;
} > RAM
.bss (NOLOAD) :
{
_start_bss = .;
__bss_start__ = .;
*(.bss*)
*(COMMON)
. = ALIGN(4);
_end_bss = .;
__bss_end__ = .;
_end = .;
} > RAM
. = ALIGN(4);
}
END_STACK = ORIGIN(RAM) + LENGTH(RAM);

View File

@ -164,6 +164,7 @@
/*** FLASH ***/
#define SYSCFG_APB2_CLOCK_ER_VAL (1 << 0) /* <<RM0438>> - RCC_APB2ENR - SYSCFGEN */
#if (TZ_SECURE())
/*Secure*/
#define FLASH_BASE (0x50022000) /* RM0456 - Table 4 */
@ -253,6 +254,8 @@
#define GPIOH_AHB2ENR1_CLOCK_ER (1 << 7)
#define TRNG_AHB2_CLOCK_ER (1 << 18)
#define RCC_AHB2_CLOCK_ER RCC_AHB2ENR1_CLOCK_ER
/* Reset */
#define OPTR_SWAP_BANK (1 << 20)

View File

@ -1,8 +1,11 @@
MEMORY
{
FLASH (rx) : ORIGIN = @WOLFBOOT_ORIGIN@, LENGTH = @BOOTLOADER_PARTITION_SIZE@
RAM (rwx) : ORIGIN = 0x30000000, LENGTH = 0x00017FFF
FLASH_NSC(rx): ORIGIN = @WOLFBOOT_ORIGIN@ + 0x20000, LENGTH = 0x20000
FLASH (rx) : ORIGIN = @WOLFBOOT_ORIGIN@, LENGTH = @BOOTLOADER_PARTITION_SIZE@ - 0x20000
RAM (rwx) : ORIGIN = 0x30000000, LENGTH = 0x00012000
RAM_HEAP (rw): ORIGIN = 0x30012000, LENGTH = 0xc000 /* 49152 B Heap for wolfcrypt/PKCS11 */
RAM_KV (rw): ORIGIN = 0x3001e000, LENGTH = 0x2000
FLASH_KEYVAULT(rw): ORIGIN = @WOLFBOOT_ORIGIN@ + 0x20000, LENGTH = 0x18000
FLASH_NSC(rx): ORIGIN = @WOLFBOOT_ORIGIN@ + 0x38000, LENGTH = 0x8000
}
SECTIONS
@ -25,6 +28,7 @@ SECTIONS
.gnu.sgstubs :
{
. += 0x400;
. = ALIGN(4);
*(.gnu.sgstubs*) /* Secure Gateway stubs */
. = ALIGN(4);
@ -53,7 +57,15 @@ SECTIONS
_end = .;
} > RAM
. = ALIGN(8);
}
END_STACK = ORIGIN(RAM) + LENGTH(RAM);
_keyvault_origin = ORIGIN(RAM_KV);
_keyvault_size = LENGTH(RAM_KV);
_flash_keyvault = ORIGIN(FLASH_KEYVAULT);
_flash_keyvault_size = LENGTH(FLASH_KEYVAULT);
_start_heap = ORIGIN(RAM_HEAP);
_heap_size = LENGTH(RAM_HEAP);

View File

@ -113,6 +113,7 @@ void hal_prepare_boot(void);
void hal_tz_claim_nonsecure_area(uint32_t address, int len);
void hal_tz_release_nonsecure_area(void);
void hal_tz_sau_init(void);
void hal_tz_sau_ns_region(void);
void hal_gtzc_init(void);
/* Needed by TZ to claim/release nonsecure flash areas */

View File

@ -254,6 +254,7 @@ extern int tolower(int c);
#endif
#if defined(SECURE_PKCS11)
# include <time.h>
# define HAVE_PWDBASED
# define HAVE_PBKDF2
# define WOLFPKCS11_CUSTOM_STORE
@ -268,7 +269,6 @@ extern int tolower(int c);
# define HAVE_SCRYPT
# define HAVE_AESGCM
# define HAVE_PKCS8
typedef unsigned long time_t;
#endif
#ifndef HAVE_PWDBASED
@ -412,10 +412,6 @@ extern int tolower(int c);
# define WOLFSSL_SMALL_STACK
#endif
#ifdef WOLFCRYPT_SECURE_MODE
typedef unsigned long time_t;
#endif
#endif /* WOLFBOOT_PKCS11_APP */
#endif /* !H_USER_SETTINGS_ */

View File

@ -647,9 +647,6 @@ ifeq ($(WOLFCRYPT_TZ_PKCS11),1)
./lib/wolfPKCS11/src/internal.o \
./lib/wolfPKCS11/src/slot.o \
./lib/wolfPKCS11/src/wolfpkcs11.o
endif
ifeq ($(WOLFCRYPT_TZ),1)
STACK_USAGE=16688
endif

View File

@ -326,10 +326,10 @@ void isr_empty(void)
* - Call the application entry point
*
*/
#if defined (__ARM_FEATURE_CMSE) && (__ARM_FEATURE_CMSE == 3U)
#define VTOR (*(volatile uint32_t *)(0xE002ED08)) // SCB_NS -> VTOR
#else
#define VTOR (*(volatile uint32_t *)(0xE000ED08))
#ifdef TZEN
#include "hal.h"
#endif
@ -353,6 +353,7 @@ void RAMFUNCTION do_boot(const uint32_t *app_offset)
app_entry = (void *)(*((uint32_t *)(app_offset + 1)));
/* Disable interrupts */
asm volatile("cpsid i");
/* Update IV */
VTOR = ((uint32_t)app_offset);
asm volatile("msr msplim, %0" ::"r"(0));

View File

@ -1,7 +1,7 @@
MEMORY
{
FLASH (rx) : ORIGIN = @WOLFBOOT_TEST_APP_ADDRESS@, LENGTH = @WOLFBOOT_TEST_APP_SIZE@
RAM (rwx) : ORIGIN = 0x20020000, LENGTH = 0x20000
RAM (rwx) : ORIGIN = 0x20050000, LENGTH = 0x40000
}
SECTIONS

View File

@ -90,7 +90,7 @@ ifeq ($(TZEN),1)
APP_OBJS+=./wcs/wc_encrypt.o
APP_OBJS+=./wcs/wc_port.o
endif
CFLAGS+=-DWOLFBOOT_SECURE_CALLS -Wstack-usage=12940
CFLAGS+=-DWOLFBOOT_SECURE_CALLS -Wstack-usage=12944
endif
else
APP_OBJS+=../hal/$(TARGET).o

View File

@ -29,9 +29,18 @@
#include "hal.h"
#include "wolfboot/wolfboot.h"
#ifdef SECURE_PKCS11
#include "wcs/user_settings.h"
#include <wolfssl/wolfcrypt/settings.h>
#include <wolfssl/wolfcrypt/wc_pkcs11.h>
#include <wolfssl/wolfcrypt/random.h>
extern const char pkcs11_library_name[];
extern const CK_FUNCTION_LIST wolfpkcs11nsFunctionList;
#endif
#define LED_BOOT_PIN (4) /* PG4 - Nucleo - Red Led */
#define LED_USR_PIN (0) /* PB0 - Nucleo - Green Led */
#define LED_USR2_PIN (4) /* PF4 - Nucleo - Orange Led */
#define LED_EXTRA_PIN (4) /* PF4 - Nucleo - Orange Led */
/*Non-Secure */
#define RCC_BASE (0x44020C00) /* RM0481 - Table 3 */
@ -40,17 +49,17 @@
#define GPIOF_BASE 0x42021400
#define GPIOG_MODER (*(volatile uint32_t *)(GPIOG_BASE + 0x00))
#define GPIOG_PUPDR (*(volatile uint32_t *)(GPIOG_BASE + 0x0C))
#define GPIOG_BSRR (*(volatile uint32_t *)(GPIOG_BASE + 0x18))
#define GPIOG_MODER (*(volatile uint32_t *)(GPIOG_BASE + 0x00))
#define GPIOG_PUPDR (*(volatile uint32_t *)(GPIOG_BASE + 0x0C))
#define GPIOG_BSRR (*(volatile uint32_t *)(GPIOG_BASE + 0x18))
#define GPIOB_MODER (*(volatile uint32_t *)(GPIOB_BASE + 0x00))
#define GPIOB_PUPDR (*(volatile uint32_t *)(GPIOB_BASE + 0x0C))
#define GPIOB_BSRR (*(volatile uint32_t *)(GPIOB_BASE + 0x18))
#define GPIOB_MODER (*(volatile uint32_t *)(GPIOB_BASE + 0x00))
#define GPIOB_PUPDR (*(volatile uint32_t *)(GPIOB_BASE + 0x0C))
#define GPIOB_BSRR (*(volatile uint32_t *)(GPIOB_BASE + 0x18))
#define GPIOF_MODER (*(volatile uint32_t *)(GPIOF_BASE + 0x00))
#define GPIOF_PUPDR (*(volatile uint32_t *)(GPIOF_BASE + 0x0C))
#define GPIOF_BSRR (*(volatile uint32_t *)(GPIOF_BASE + 0x18))
#define GPIOF_MODER (*(volatile uint32_t *)(GPIOF_BASE + 0x00))
#define GPIOF_PUPDR (*(volatile uint32_t *)(GPIOF_BASE + 0x0C))
#define GPIOF_BSRR (*(volatile uint32_t *)(GPIOF_BASE + 0x18))
#define RCC_AHB2ENR1_CLOCK_ER (*(volatile uint32_t *)(RCC_BASE + 0x8C ))
#define GPIOG_AHB2ENR1_CLOCK_ER (1 << 6)
@ -97,10 +106,10 @@ void usr_led_off(void)
GPIOB_BSRR |= (1 << (LED_USR_PIN + 16));
}
void usr2_led_on(void)
void extra_led_on(void)
{
uint32_t reg;
uint32_t pin = LED_USR2_PIN;
uint32_t pin = LED_EXTRA_PIN;
RCC_AHB2ENR1_CLOCK_ER|= GPIOF_AHB2ENR1_CLOCK_ER;
/* Delay after an RCC peripheral clock enabling */
@ -112,19 +121,103 @@ void usr2_led_on(void)
GPIOF_BSRR |= (1 << (pin));
}
void usr2_led_off(void)
void extra_led_off(void)
{
GPIOF_BSRR |= (1 << (LED_USR2_PIN + 16));
GPIOF_BSRR |= (1 << (LED_EXTRA_PIN + 16));
}
static char CaBuf[2048];
static uint8_t my_pubkey[200];
extern int ecdsa_sign_verify(int devId);
void main(void)
{
hal_init();
int ret;
uint32_t rand;
uint32_t i;
uint32_t klen = 200;
int otherkey_slot;
unsigned int devId = 0;
#ifdef SECURE_PKCS11
WC_RNG rng;
Pkcs11Token token;
Pkcs11Dev PKCS11_d;
unsigned long session;
char TokenPin[] = "0123456789ABCDEF";
char UserPin[] = "ABCDEF0123456789";
char SoPinName[] = "SO-PIN";
#endif
/* Turn on boot LED */
boot_led_on();
usr_led_on();
boot_led_off();
if (wolfBoot_current_firmware_version() > 1)
usr2_led_on();
#ifdef SECURE_PKCS11
wolfCrypt_Init();
PKCS11_d.heap = NULL,
PKCS11_d.func = (CK_FUNCTION_LIST *)&wolfpkcs11nsFunctionList;
ret = wc_Pkcs11Token_Init(&token, &PKCS11_d, 1, "EccKey",
(const byte*)TokenPin, strlen(TokenPin));
if (ret == 0) {
ret = wolfpkcs11nsFunctionList.C_OpenSession(1,
CKF_SERIAL_SESSION | CKF_RW_SESSION,
NULL, NULL, &session);
}
if (ret == 0) {
ret = wolfpkcs11nsFunctionList.C_InitToken(1,
(byte *)TokenPin, strlen(TokenPin), (byte *)SoPinName);
}
if (ret == 0) {
extra_led_on();
ret = wolfpkcs11nsFunctionList.C_Login(session, CKU_SO,
(byte *)TokenPin,
strlen(TokenPin));
}
if (ret == 0) {
ret = wolfpkcs11nsFunctionList.C_InitPIN(session,
(byte *)TokenPin,
strlen(TokenPin));
}
if (ret == 0) {
ret = wolfpkcs11nsFunctionList.C_Logout(session);
}
if (ret != 0) {
while(1)
;
}
if (ret == 0) {
ret = wc_CryptoDev_RegisterDevice(devId, wc_Pkcs11_CryptoDevCb,
&token);
if (ret != 0) {
while(1)
;
}
if (ret == 0) {
#ifdef HAVE_ECC
ret = ecdsa_sign_verify(devId);
if (ret != 0)
ret = 1;
else
usr_led_on();
#endif
}
wc_Pkcs11Token_Final(&token);
}
#else
/* Check if version > 1 and turn on user led */
if (wolfBoot_current_firmware_version() > 1) {
usr_led_on();
}
#endif /* SECURE_PKCS11 */
while(1)
;
/* Never reached */
}

View File

@ -34,7 +34,7 @@ extern void isr_tim2(void);
#endif
#ifndef STACK_PAINTING
#define STACK_PAINTING 1
#define STACK_PAINTING 0
#endif
static volatile unsigned int avail_mem = 0;

View File

@ -80,7 +80,9 @@ CK_FUNCTION_LIST wolfpkcs11nsFunctionList = {
const char pkcs11_library_name[]="wolfCrypt_secure_mode";
extern unsigned int _start_heap;
#ifndef NULL
#define NULL (((void *)0))
#endif
void * _sbrk(unsigned int incr)
{

View File

@ -48,6 +48,7 @@ extern int tolower(int c);
#define HAVE_WOLF_BIGINT
#define HAVE_PKCS11_STATIC
#define WOLF_CRYPTO_CB
#define MAX_CRYPTO_DEVID_CALLBACKS 2
/* ECC */