cancel
Showing results for 
Search instead for 
Did you mean: 

Enabling SFU_MPU_PROTECT_ENABLE causes a problem

ali rostami
Associate III

In my project the microcontroller is STM32F756VGT6, I changed the example "2_Images_OSC" of STM32f769I-Discovery to be compatible with this microcontroller.

Right now everything seems O.K and I can upgrade the application with SBSFU. But when I uncomment the definition of SFU_MPU_PROTECT_ENABLE I get to a problem and here is the message I get from terminal:

======================================================================
=              (C) COPYRIGHT 2017 STMicroelectronics                 =
=                                                                    =
=              Secure Boot and Secure Firmware Update                =
======================================================================
 
 
= [SBOOT] SECURE ENGINE INITIALIZATION SUCCESSFUL
= [SBOOT] STATE: CHECK STATUS ON RESET
          INFO: A Reboot has been triggered by a Software reset!
          Memory fault
========= End of Execution ==========

Here is the MPU config:

#define SFU_PROTECT_MPU_MAX_NB_SUBREG           (8U)
 
/**
  * @brief Region 0 - Enable the read/write operations for the full peripheral area in unprivileged
  *                   mode.
  *                   Execution capability disabled
  */
#define SFU_PROTECT_MPU_PERIPH_1_RGNV  MPU_REGION_NUMBER0
#define SFU_PROTECT_MPU_PERIPH_1_START 0x00000000U
#define SFU_PROTECT_MPU_PERIPH_1_SIZE  MPU_REGION_SIZE_4GB
#define SFU_PROTECT_MPU_PERIPH_1_SREG  0x83U               /*!< 4GB / 8 * 5 ==> only peripheral area allowed */
#define SFU_PROTECT_MPU_PERIPH_1_PERM  MPU_REGION_FULL_ACCESS
#define SFU_PROTECT_MPU_PERIPH_1_EXECV MPU_INSTRUCTION_ACCESS_DISABLE
#define SFU_PROTECT_MPU_PERIPH_1_TEXV  MPU_TEX_LEVEL0
#define SFU_PROTECT_MPU_PERIPH_1_B     MPU_ACCESS_BUFFERABLE
#define SFU_PROTECT_MPU_PERIPH_1_C     MPU_ACCESS_NOT_CACHEABLE
 
/**
  * @brief Region 1 - Enable the read/write operations for RCC peripheral area in privileged mode.
  *                   Execution capability disabled
  *                   Inner region inside the Region 0
  */
#define SFU_PROTECT_MPU_PERIPH_2_RGNV  MPU_REGION_NUMBER1
#define SFU_PROTECT_MPU_PERIPH_2_START RCC_BASE
#define SFU_PROTECT_MPU_PERIPH_2_SIZE  MPU_REGION_SIZE_1KB
#define SFU_PROTECT_MPU_PERIPH_2_SREG  0x00U               /*!< All subregions activated */
#define SFU_PROTECT_MPU_PERIPH_2_PERM  MPU_REGION_PRIV_RW
#define SFU_PROTECT_MPU_PERIPH_2_EXECV MPU_INSTRUCTION_ACCESS_DISABLE
#define SFU_PROTECT_MPU_PERIPH_2_TEXV  MPU_TEX_LEVEL0
#define SFU_PROTECT_MPU_PERIPH_2_B     MPU_ACCESS_BUFFERABLE
#define SFU_PROTECT_MPU_PERIPH_2_C     MPU_ACCESS_NOT_CACHEABLE
 
/**
  * @brief Region 2 - Enable the read/write operations for full flash area in unprivileged mode.
  *                   Execution capability disabled
  */
#define SFU_PROTECT_MPU_FLASHACC_RGNV  MPU_REGION_NUMBER2
#define SFU_PROTECT_MPU_FLASHACC_START FLASH_BASE          /*!< Flash memory area */
#define SFU_PROTECT_MPU_FLASHACC_SIZE  MPU_REGION_SIZE_1MB
#define SFU_PROTECT_MPU_FLASHACC_SREG  0x00U               /*!< All subregions activated */
#define SFU_PROTECT_MPU_FLASHACC_PERM  MPU_REGION_FULL_ACCESS
#define SFU_PROTECT_MPU_FLASHACC_EXECV MPU_INSTRUCTION_ACCESS_DISABLE
#define SFU_PROTECT_MPU_FLASHACC_TEXV  MPU_TEX_LEVEL0
#define SFU_PROTECT_MPU_FLASHACC_B     MPU_ACCESS_NOT_BUFFERABLE
#define SFU_PROTECT_MPU_FLASHACC_C     MPU_ACCESS_CACHEABLE
 
/**
  * @brief Region 3 - Enable the execution for SB/SFU Full area (SBSFU + SE + Keys) in unprivileged mode.
  *                   Read only capability configured
  *                   Inner region inside the Region 2
  */
#define SFU_PROTECT_MPU_FLASHEXE_RGNV  MPU_REGION_NUMBER3
#define SFU_PROTECT_MPU_FLASHEXE_START FLASH_BASE          /*!< Flash memory area */
#define SFU_PROTECT_MPU_FLASHEXE_SIZE  MPU_REGION_SIZE_128KB
#define SFU_PROTECT_MPU_FLASHEXE_SREG  0x00U               /*!< All subregions activated */
#define SFU_PROTECT_MPU_FLASHEXE_PERM  MPU_REGION_PRIV_RO_URO
#define SFU_PROTECT_MPU_FLASHEXE_EXECV MPU_INSTRUCTION_ACCESS_ENABLE
#define SFU_PROTECT_MPU_FLASHEXE_TEXV  MPU_TEX_LEVEL0
#define SFU_PROTECT_MPU_FLASHEXE_B     MPU_ACCESS_NOT_BUFFERABLE
#define SFU_PROTECT_MPU_FLASHEXE_C     MPU_ACCESS_CACHEABLE
 
/**
  * @brief Region 4 - Enable the read/write operation in privileged mode for Header of active slots
  *                   Execution capability disabled
  *                   Inner region inside the Region 2
  */
#define SFU_PROTECT_MPU_HEADER_RGNV  MPU_REGION_NUMBER4
#define SFU_PROTECT_MPU_HEADER_START SLOT_ACTIVE_1_HEADER
#define SFU_PROTECT_MPU_HEADER_SREG  0x00U                 /*!< All subregions activated */
#define SFU_PROTECT_MPU_HEADER_SIZE  MPU_REGION_SIZE_1KB
#define SFU_PROTECT_MPU_HEADER_PERM  MPU_REGION_PRIV_RW
#define SFU_PROTECT_MPU_HEADER_EXECV MPU_INSTRUCTION_ACCESS_DISABLE
#define SFU_PROTECT_MPU_HEADER_TEXV  MPU_TEX_LEVEL0
#define SFU_PROTECT_MPU_HEADER_B     MPU_ACCESS_NOT_BUFFERABLE
#define SFU_PROTECT_MPU_HEADER_C     MPU_ACCESS_CACHEABLE
 
/**
  * @brief Region 5 - Enable the read/write operation in unprivileged mode for RAM area.
  *                   Execution capability disabled
  */
#define SFU_PROTECT_MPU_SRAMACC_RGNV  MPU_REGION_NUMBER5
#define SFU_PROTECT_MPU_SRAMACC_START RAMDTCM_BASE         /*!< RAM memory area */
#define SFU_PROTECT_MPU_SRAMACC_SIZE  MPU_REGION_SIZE_512KB
#define SFU_PROTECT_MPU_SRAMACC_SREG  0xE0U                /*!< 512 Kbytes / 8 * 5 ==>  64K + 240K Kbytes */
#define SFU_PROTECT_MPU_SRAMACC_PERM  MPU_REGION_FULL_ACCESS
#define SFU_PROTECT_MPU_SRAMACC_EXECV MPU_INSTRUCTION_ACCESS_DISABLE
#define SFU_PROTECT_MPU_SRAMACC_TEXV  MPU_TEX_LEVEL0
#define SFU_PROTECT_MPU_SRAMACC_B     MPU_ACCESS_NOT_BUFFERABLE
#define SFU_PROTECT_MPU_SRAMACC_C     MPU_ACCESS_CACHEABLE
 
/**
  * @brief Region 6 - Enable the read/write operation in privileged mode for Secure Engine RAM area.
  *                   Execution capability disabled
  *                   Inner region inside the Region 5
  *                   Address must be aligned on 4KB as size is 4KB
  */
#define SFU_PROTECT_MPU_SRAM_SE_RGNV  MPU_REGION_NUMBER6
#define SFU_PROTECT_MPU_SRAM_SE_START SFU_SENG_RAM_ADDR_START  /*!< SE RAM memory area */
#define SFU_PROTECT_MPU_SRAM_SE_SIZE  MPU_REGION_SIZE_16KB
#define SFU_PROTECT_MPU_SRAM_SE_SREG  0xC0U                /*!< 16 Kbytes / 8 * 6 ==> 12 Kbytes */
#define SFU_PROTECT_MPU_SRAM_SE_PERM  MPU_REGION_PRIV_RW
#define SFU_PROTECT_MPU_SRAM_SE_EXECV MPU_INSTRUCTION_ACCESS_DISABLE
#define SFU_PROTECT_MPU_SRAM_SE_TEXV  MPU_TEX_LEVEL0
#define SFU_PROTECT_MPU_SRAM_SE_B     MPU_ACCESS_NOT_BUFFERABLE
#define SFU_PROTECT_MPU_SRAM_SE_C     MPU_ACCESS_CACHEABLE
 
/**
  * @brief Region 7 - Enable the execution for Secure Engine flash area in privileged mode.
  *                   Read only capability configured
  *                   Inner region inside the Region 3
  */
#define SFU_PROTECT_MPU_EXEC_SE_RGNV  MPU_REGION_NUMBER7
#define SFU_PROTECT_MPU_EXEC_SE_START FLASH_BASE           /*!< Flash memory area */
#define SFU_PROTECT_MPU_EXEC_SE_SIZE  MPU_REGION_SIZE_64KB
#define SFU_PROTECT_MPU_EXEC_SE_SREG  0x00U                /*!< All subregions activated */
#define SFU_PROTECT_MPU_EXEC_SE_PERM  MPU_REGION_PRIV_RO
#define SFU_PROTECT_MPU_EXEC_SE_EXECV MPU_INSTRUCTION_ACCESS_ENABLE
#define SFU_PROTECT_MPU_EXEC_SE_TEXV  MPU_TEX_LEVEL0
#define SFU_PROTECT_MPU_EXEC_SE_B     MPU_ACCESS_NOT_BUFFERABLE
#define SFU_PROTECT_MPU_EXEC_SE_C     MPU_ACCESS_CACHEABLE
 
/**
  * MPU configuration for UserApp execution
  * =======================================
  * Reconfiguration of existing regions (useless during UserApp execution)
  * MPU constraint = Region base address should be aligned on Region size
  */
 
/**
  * @brief Region 3 - Enable the execution for active slots in unprivileged mode.
  *                   Read only capability configured
  *                   Inner region inside the Region 2
  */
#define APP_PROTECT_MPU_FLASHEXE_RGNV  MPU_REGION_NUMBER3
#define APP_PROTECT_MPU_FLASHEXE_START FLASH_BASE
#define APP_PROTECT_MPU_FLASHEXE_SIZE  MPU_REGION_SIZE_1MB
#define APP_PROTECT_MPU_FLASHEXE_SREG  0xCCU               /*!< subregion 0 (activated): SBSFU
                                                                subregion 1 (de-activated) : Swap
                                                                subregions 2,3,4 (activated) : active slot(s) */
#define APP_PROTECT_MPU_FLASHEXE_PERM  MPU_REGION_PRIV_RO_URO
#define APP_PROTECT_MPU_FLASHEXE_EXECV MPU_INSTRUCTION_ACCESS_ENABLE
#define APP_PROTECT_MPU_FLASHEXE_TEXV  MPU_TEX_LEVEL0
#define APP_PROTECT_MPU_FLASHEXE_B     MPU_ACCESS_NOT_BUFFERABLE
#define APP_PROTECT_MPU_FLASHEXE_C     MPU_ACCESS_CACHEABLE

What is wrong with this MPU config?

10 REPLIES 10
ali rostami
Associate III

So any idea? @JHOUD​ @Jocelyn RICARD​ 

I also couldn't debug SBSFU with Keil, I found something about IAR or CubeIDE, but found nothing about Keil.

Fred
ST Employee

Hi @ali rostami​ ,

it seems you face an issue at this stage:

  TRACE("\r\n= [SBOOT] STATE: CHECK STATUS ON RESET");
 
  /* Check the wakeup sources */
  SFU_BOOT_ManageResetSources();
 
  /* RCC access done to identify the wakeup sources, we can switch to unpriviledged */
  SFU_MPU_EnterUnprivilegedMode();

So, at first sight, there can be 2 reasons:

  1. Check that the RCC registers used to get the reset source are accessible ==> Region 1 settings to be verified
  2. Check that after entering unprivileged mode, a particular access is rejected.

This might be related to the check done in : SFU_BOOT_SM_CheckUserFwStatus()

==> need to check your region 4 settings.

Finally, if no problem arises here, then it may be due to the RAM settings with region 5.

These are only ideas, you need to check these directions.

Thanks & Regards,

Fred

ali rostami
Associate III

Thanks dear @Fred​ 

Now I found out that the main application is being started.

By limiting its code, I got to that it fails in the configuration of USB in CDC.

So the MPU has an effect on the "MX_USB_DEVICE_Init" function.

After a few tests, I found that if in the body of "SFU_LL_SECU_SetProtectionMPU_UserApp" I reconfigured the MPU before returning from the function by this line:

HAL_MPU_Enable(MPU_PRIVILEGED_DEFAULT);

or this one:

HAL_MPU_Enable(MPU_HFNMI_PRIVDEF);

The USB works. So I think it shows that there are addresses that are not configured by MPU, so when we use one of these 2 lines, it uses the default config for that area.

But I checked the MPU configuration so many times, what do think?

Jocelyn RICARD
ST Employee

Hello Ali,

The USB registers are located in the 0x5000 0000 address which is not included in the MPU configuration. It is actually excluded from the default configuration because of SFU_PROTECT_MPU_PERIPH_1_SREG 0x83U.

Reason is to exclude the memory area that can be addressed through FMC and OSPI in a the range 0x60000000 to 0xE0000000. This exclusion is necessary to avoid the speculative accesses in this area which cause unexpected crashes.

So, the solution is to add a specific MPU region for this USB memory area or change value 0x83 to 0x87 to include this range by default just to make sure this is the root cause.

Best regards

Jocelyn

ali rostami
Associate III

Hi, @Jocelyn RICARD​ , thanks for your answer.

But are you sure?

I think this area is not excluded because as you said it's in the 0x5000 0000 address, which is located in Block 3 of the memory map, and by defining SFU_PROTECT_MPU_PERIPH_1_SREG  as 0x83 this block would be included because 0x83 causes block 0, block 1 and block 7 to be disabled and excluded. Please correct me if I'm wrong.

And about adding a new specific region, all 8 regions were used. I have no idea How can I do it?

Jocelyn RICARD
ST Employee

Hello @ali rostami​ ,

yes, my mistake. I'm used to another MPU configuration that simply disables all access to these regions. Here this is a setting to make regions not executable which is fine.

So, issue is somewhere else.

To understand why you get this you can use debugger an see what exactly generates this memory fault. I think this is the fastest and easiest way to go forward

Best regards

Jocelyn

ali rostami
Associate III

Hmm, Yeah thanks to your help @Jocelyn RICARD​ , I could finally debug the main application.

It seems the problem is with the unique ID registers of the microcontroller, which are located in the reserved portion of the memory map (UID_BASE = 0x1FF0F420UL). And as you know, it is not configured by MPU.

So as we just have only 8 regions for MPU in STM32F756, what can I do for this small region? Any idea?

Jocelyn RICARD
ST Employee

Hello @ali rostami​ 

Ok good catch !

One solution is to change:

/**
  * @brief Region 2 - Enable the read/write operations for full flash area in unprivileged mode.
  *                   Execution capability disabled
  */
#define SFU_PROTECT_MPU_FLASHACC_RGNV  MPU_REGION_NUMBER2
#define SFU_PROTECT_MPU_FLASHACC_START FLASH_BASE          /*!< Flash memory area */
#define SFU_PROTECT_MPU_FLASHACC_SIZE  MPU_REGION_SIZE_1MB
#define SFU_PROTECT_MPU_FLASHACC_SREG  0x00U               /*!< All subregions activated */
#define SFU_PROTECT_MPU_FLASHACC_PERM  MPU_REGION_FULL_ACCESS
#define SFU_PROTECT_MPU_FLASHACC_EXECV MPU_INSTRUCTION_ACCESS_DISABLE
#define SFU_PROTECT_MPU_FLASHACC_TEXV  MPU_TEX_LEVEL0
#define SFU_PROTECT_MPU_FLASHACC_B     MPU_ACCESS_NOT_BUFFERABLE
#define SFU_PROTECT_MPU_FLASHACC_C     MPU_ACCESS_CACHEABLE

Goal would be to enable region from 0x08000000 to 0x20000000 instead of 0x08000000 + 1MB

You can do this by setting:

...FLASHACC_START to 0

..FLASHACC_SIZE to 512 MB (512MB is exactly 0x20000000)

Then exclude the first 128 MB using:

...FLASHACC_SREG to 0x03

Best regards

Jocelyn

ali rostami
Associate III

Thanks @Jocelyn RICARD​  yeah, but it's a trade-off of using USB or more security, right?

The option bytes are now exposed, doesn't it make any problem? What if I config region 1 for the 3 UID bytes instead of RCC?