本帖最后由 傅沈骁 于 2025-3-3 16:54 编辑
STM32L562xx携带有TrustZone安全认证,在官方案例中有一个GPIO_IOToggle的案例,用来讲解STM32L562xx的TrustZone。
TrustZone安全由FLASH_OPTR寄存器中的TZEN选项位激活。
启用TrustZone后,SAU(security attribution unit)和IDAU(implementation defined attribution unit)基于安全和非安全状态定义访问权限。
SAU:提供8个SAU可配置区域用于安全归因。
IDAU:提供第一个内存分区作为非安全或非安全可调用属性,然后将其与SAU安全归因的结果相结合,并选择更高的安全状态。
基于IDAU安全属性,Flash、系统SRAM和外围设备存储空间被混叠两次,用于安全和非安全状态。然而,外部存储空间没有混叠。
下表展示了基于IDAU区域的典型SAU区域配置示例。用户可以根据需要为外部存储器拆分并选择安全、非安全或NSC区域。
当TrustZone安全处于激活状态时,外围设备可以是Securable或TrustZone感知类型,如下所示:
1. 安全:外围设备由AHB/APB防火墙门保护,该防火墙门由TZSC控制器控制以定义安全属性。
2. TrustZone感知:直接连接到AHB或APB总线的外围设备,正在实现特定的TrustZone行为,例如寄存器的子集是安全的。
下表总结了系统中支持安全和信任区的外围设备列表。
默认系统安全状态
CPU:复位后处于安全状态,boot地址必须位于安全地址
Memory map:重置后完全安全。因此,所有内存映射都是完全安全的。多达8个SAU可配置区域可用于安全归因。
Flash:闪存安全区域由水印用户选项定义。复位后,基于闪存块的区域非安全。
SRAM:所有SRAM在复位后处于安全状态。MPCBB(memory protection block based controller)安全。
外部存储:FSMC、OCTOSPI总线在复位后安全。MPCWMx(memory protection watermark based controller)安全。
外设:复位后安全外围设备非安全。TrustZone感知外设(GPIO除外)在重置后非安全。它们的安全配置寄存器是安全的。
GPIO:所有GPIO在复位后均安全。NVIC:复位后所有中断都是安全的。NVIC被存储为安全和非安全状态。TZIC:复位后禁用所有非法访问中断。
下面以GPIO翻转为例
在初始化阶段首先使能安全故障句柄
/* Enable SecureFault handler (HardFault is default) */
SCB->SHCSR |= SCB_SHCSR_SECUREFAULTENA_Msk;
在相关外设初始化中初始化全局TrustZone
/* GTZC initialisation */
MX_GTZC_S_Init();
GTZC包含三个子模块:
TZSC:TrustZone安全控制器。此子块定义从属/主外围设备的安全/特权状态。它还控制水印存储器外围控制器(MPCWM)的非安全区域大小。TZSC块通过与RCC和I/O逻辑共享,向一些外围设备(如RCC或GPIO)通知每个可安全外围设备的安全状态。
MPCBB:基于块的存储器保护控制器。该子块控制相关SRAM的所有块(256字节页)的安全状态。
TZIC:TrustZone非法访问控制器。此子块收集系统中的所有非法访问事件,并向NVIC生成安全中断。
初始化GPIO,所有IO口默认都为安全,随后将除了PG12外的所有IO口设置为非安全。
/* All IOs are by default allocated to secure */
/* Release them all to non-secure except PG.12 (LED10) kept as secure */
__HAL_RCC_GPIOA_CLK_ENABLE();
__HAL_RCC_GPIOB_CLK_ENABLE();
__HAL_RCC_GPIOC_CLK_ENABLE();
__HAL_RCC_GPIOD_CLK_ENABLE();
__HAL_RCC_GPIOE_CLK_ENABLE();
__HAL_RCC_GPIOF_CLK_ENABLE();
__HAL_RCC_GPIOG_CLK_ENABLE();
__HAL_RCC_GPIOH_CLK_ENABLE();
HAL_GPIO_ConfigPinAttributes(GPIOA, GPIO_PIN_All, GPIO_PIN_NSEC);
HAL_GPIO_ConfigPinAttributes(GPIOB, GPIO_PIN_All, GPIO_PIN_NSEC);
HAL_GPIO_ConfigPinAttributes(GPIOC, GPIO_PIN_All, GPIO_PIN_NSEC);
HAL_GPIO_ConfigPinAttributes(GPIOD, GPIO_PIN_All, GPIO_PIN_NSEC);
HAL_GPIO_ConfigPinAttributes(GPIOE, GPIO_PIN_All, GPIO_PIN_NSEC);
HAL_GPIO_ConfigPinAttributes(GPIOF, GPIO_PIN_All, GPIO_PIN_NSEC);
HAL_GPIO_ConfigPinAttributes(GPIOG, (GPIO_PIN_All & ~(GPIO_PIN_12)), GPIO_PIN_NSEC);
HAL_GPIO_ConfigPinAttributes(GPIOH, GPIO_PIN_All, GPIO_PIN_NSEC);
随后初始化非安全模式,该函数用于非安全初始化和切换
/**
* [url=home.php?mod=space&uid=247401]@brief[/url] Non-secure call function
* This function is responsible for Non-secure initialization and switch
* to non-secure state
* @retval None
*/
static void NonSecure_Init(void)
{
funcptr_NS NonSecure_ResetHandler;
SCB_NS->VTOR = VTOR_TABLE_NS_START_ADDR;
/* Set non-secure main stack (MSP_NS) */
__TZ_set_MSP_NS((*(uint32_t *)VTOR_TABLE_NS_START_ADDR));
/* Get non-secure reset handler */
NonSecure_ResetHandler = (funcptr_NS)(*((uint32_t *)((VTOR_TABLE_NS_START_ADDR) + 4U)));
/* Start non-secure state software application */
NonSecure_ResetHandler();
}
安全状态下的GTZC初始化函数如下
/**
* [url=home.php?mod=space&uid=247401]@brief[/url] GTZC_S Initialization Function
* @param None
* @retval None
*/
static void MX_GTZC_S_Init(void)
{
/* USER CODE BEGIN GTZC_S_Init 0 */
/* USER CODE END GTZC_S_Init 0 */
MPCBB_ConfigTypeDef MPCBB_NonSecureArea_Desc = {0};
/* USER CODE BEGIN GTZC_S_Init 1 */
/* USER CODE END GTZC_S_Init 1 */
MPCBB_NonSecureArea_Desc.SecureRWIllegalMode = GTZC_MPCBB_SRWILADIS_ENABLE;
MPCBB_NonSecureArea_Desc.InvertSecureState = GTZC_MPCBB_INVSECSTATE_NOT_INVERTED;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[0] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[1] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[2] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[3] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[4] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[5] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[6] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[7] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[8] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[9] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[10] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[11] = 0xFFFFFFFF;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[12] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[13] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[14] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[15] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[16] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[17] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[18] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[19] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[20] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[21] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[22] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[23] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_LockConfig_array[0] = 0x00000000;
if (HAL_GTZC_MPCBB_ConfigMem(SRAM1_BASE, &MPCBB_NonSecureArea_Desc) != HAL_OK)
{
Error_Handler();
}
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[0] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[1] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[2] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[3] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[4] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[5] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[6] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_SecConfig_array[7] = 0x00000000;
MPCBB_NonSecureArea_Desc.AttributeConfig.MPCBB_LockConfig_array[0] = 0x00000000;
if (HAL_GTZC_MPCBB_ConfigMem(SRAM2_BASE, &MPCBB_NonSecureArea_Desc) != HAL_OK)
{
Error_Handler();
}
/* USER CODE BEGIN GTZC_S_Init 2 */
/* USER CODE END GTZC_S_Init 2 */
}
在CubeMX中,可以选择外设是否安全来快速配置安全状态或者非安全状态。 |