1. RH850 U2A HSM 开发环境搭建与验证
任务说明
本案例完成RH850 U2A芯片上HSM(硬件安全模块)的初始化与基础配置,包括:使能HSM时钟、配置内存保护单元(MPU)以隔离HSM专用内存、注册并启用HSM安全中断。最终通过读取HSM状态寄存器验证初始化是否成功。
硬件依赖
- RH850 U2A 系列MCU(本文以U2A8为例)
- HSM固件已烧录至HSM专用Flash区域(地址0xFBE00000起)
- 编译器:GHS MULTI 或 IAR,支持RH850内核
关键寄存器与配置说明
HSM模块在RH850 U2A中作为独立安全岛运行,主核通过以下寄存器完成初始化:
- HSMCLKCTL(0xFF42E000):时钟使能控制,bit0置1使能HSM主时钟
- HSMMPUCTL(0xFF42E010):MPU使能控制,bit0置1使能HSM内存保护
- HSMMPUADDR(0xFF42E014):MPU保护区域起始地址
- HSMMPUSIZE(0xFF42E018):MPU保护区域大小(以4KB为单位)
- HSMINTCTL(0xFF42E020):中断控制,bit0置1使能安全中断输出
- HSMSTAT(0xFF42E024):状态寄存器,bit0为1表示HSM已就绪
完整初始化代码
#include "rh850_regs.h"
/* HSM寄存器基地址 */
#define HSM_BASE 0xFF42E000u
#define HSMCLKCTL (*(volatile uint32_t*)(HSM_BASE + 0x00u))
#define HSMMPUCTL (*(volatile uint32_t*)(HSM_BASE + 0x10u))
#define HSMMPUADDR (*(volatile uint32_t*)(HSM_BASE + 0x14u))
#define HSMMPUSIZE (*(volatile uint32_t*)(HSM_BASE + 0x18u))
#define HSMINTCTL (*(volatile uint32_t*)(HSM_BASE + 0x20u))
#define HSMSTAT (*(volatile uint32_t*)(HSM_BASE + 0x24u))
/* HSM专用内存区域(安全Flash与SRAM) */
#define HSM_MPU_START 0xFBE00000u
#define HSM_MPU_SIZE_KB 512u /* 512KB保护区域 */
/* 等待HSM就绪超时值 */
#define HSM_READY_TIMEOUT 10000u
/**
* HSM模块初始化
* @return 0=成功, 1=超时错误
*/
uint32_t HSM_Init(void)
{
uint32_t timeout;
/* 1. 使能HSM时钟 */
HSMCLKCTL |= 0x1u;
/* 2. 配置MPU保护区域 */
HSMMPUADDR = HSM_MPU_START;
HSMMPUSIZE = (HSM_MPU_SIZE_KB / 4u) - 1u; /* 寄存器值=大小/4KB-1 */
HSMMPUCTL |= 0x1u; /* 使能MPU */
/* 3. 使能HSM安全中断 */
HSMINTCTL |= 0x1u;
/* 4. 等待HSM固件完成自启动 */
timeout = HSM_READY_TIMEOUT;
while ((HSMSTAT & 0x1u) == 0u)
{
if (--timeout == 0u)
{
return 1u; /* 超时错误 */
}
}
return 0u; /* 初始化成功 */
}
调用与验证
在主程序启动阶段(时钟树初始化完成后)调用HSM_Init()。验证方法如下:
- 调用
HSM_Init()后检查返回值:返回0表示初始化成功,返回1表示HSM固件未在预期时间内就绪 - 读取
HSMSTAT寄存器bit0,若为1则确认HSM已正常运行 - 若初始化失败,依次检查:HSM固件是否已烧录、时钟使能位是否成功置位、MPU地址配置是否与固件实际加载地址一致
预期输出
当HSM固件正常烧录且硬件连接正确时,HSM_Init()返回0,且HSMSTAT寄存器bit0读取值为1。
常见问题
- 初始化超时:确认HSM固件已烧录至0xFBE00000起始地址,且固件版本与芯片型号匹配
- MPU配置错误:HSMMPUSIZE寄存器值需按4KB粒度计算,若固件实际占用超过配置值会导致HSM访问异常
- 中断未触发:确认HSMINTCTL使能后,还需在中断控制器(INTC)中使能对应的HSM中断通道