该篇主要:参考正点原子教程和安富莱教程
安富莱_STM32-V7_MPU及Cache部分.pdf
目录
1. 内存保护单元(MPU)介绍(了解)
1.1. 内存保护单元(memory protection unit),简称:MPU
1.1.1. MPU的功能:
1.1.2. MPU的好处:
MPU可作为管理员:管理权限、管理通行规则和路径
具体好处
1.2. MPU的使用:
1.2.1. MPU配置保护内存区域:
1.2.1.1. 默认配置的保护区域:背景区,序号(-1)
1.2.1.2. 可配置的保护内存区域:0-15
1.2.2. MPU设置内存区域的访问权限:MPU_REGION_XX_XX - XXX访问
1.2.3. MPU配置内存区域的访问属性:内存类型(Normal/Device/S..o..)
三种内存类型对应的情景:可缓存,可缓冲,可共享
可共享:主机(Master)间数据同步
不同配置下(访问属性:内存类型,是否缓存,是否缓冲,是否共享)的性能情况:
2. Cache简介(了解)
2.1. Cache简介:
2.2. Cache使用:对SRAM的-读操作、写操作
2.2.1. Core读Cache:读操作
2.2.2. Core写Cache:写操作
2.3. 数据不一致问题解决:
3. MPU相关寄存器介绍(熟悉)
3.1. MPU类型寄存器(MPU_TYPE):是否支持MPU,可配置8(F7)/16(H7)个保护区域
3.2. MPU控制寄存器(MPU_CTRL):设置MPU使能
PRIVDEFENA位的影响:
M3:
H7:
3.3. MPU区域编号寄存器(MPU_RNR):选中要配置的(0-7(F7)/0-15(H7))区域
3.4. MPU基地址寄存器(MPU_RBAR):设置区域的起始地址
3.5. MPU区域属性和容量寄存器(MPU_RASR):设置每个区域的属性【重点】
XN位:指令访问
AP位:访问权限,通常使用全访问
TEX位:设置Cache策略
SRD位:使能当前区域的子区域
4. MPU相关HAL库驱动介绍(掌握)
4.1. void HAL_MPU_Enable(uint32_t MPU_Control)
4.2. MPU HAL相关结构体-MPU_Region_InitTypeDef
5. MPU基本配置步骤(掌握)
5.1. 通过配置TEX C B S =>> 来配置内存类型,Cache策略
6. 编程实战——分析总框图!!!(掌握)
6.1. 实战代码
6.2. 分析总框图(全屏看)
可以通过微调整来实现程序高速运行,前提是稳定性
7. H7的内存模型:H7内存默认映射与属性
7.1. H7内存默认映射
8. 通过Keil Debug来查看MPU配置(MDK局限:只能显示8个区域)
8.1. 菜单栏打开:
8.2. Memory Protection Unit (MPU)工具
8.3. 执行完MPU配置代码后,在工具内查看MPU配置情况
9. 课堂总结
1. 内存保护单元(MPU)介绍(了解)
1.1. 内存保护单元(memory protection unit),简称:MPU
1.1.1. MPU的功能:
- 设置不同存储区域的存储器访问权限(特权级、用户级)
- 设置存储器(内存和外设)属性(可缓存、可缓冲、可共享)
1.1.2. MPU的好处:
MPU可作为管理员:管理权限、管理通行规则和路径
具体好处
1.2. MPU的使用:
1.2.1. MPU配置保护内存区域:
MPU可配置保护8/16个内存区域,每个区域最小要求256字节,且每个区域还可配置为8个子区域(大小一样)
H7的存储器映射:
- STM32的地址空间共4GB(即有2^32个地址),需要将地址和内存映射起来。
- ST将这些地址划分成块,根据不同芯片中内存大小,映射长度也不同。
- 每个地址映射1个(u8)字节
- F7可配置8个保护内存区域,单个区域>256字节,并且可细分为8个子区域
- H7可配置16个保护内存区域,单个区域>256字节,并且可细分为8个子区域
16(>256,不一致)*8(相同大小)
此处配置内存区域的范围是整个单片机的内核地址
1.2.1.1. 默认配置的保护区域:背景区,序号(-1)
对没有配置保护规则的内存区域统一管理
1.2.1.2. 可配置的保护内存区域:0-15
- 编号为优先级:0~15 优先级越来越高
- (配置)规则:访问属性和权限
- 重叠或嵌套下,重叠部分按着优先级高的内存区配置规则执行
1.2.2. MPU设置内存区域的访问权限:MPU_REGION_XX_XX
- XXX访问
1.2.3. MPU配置内存区域的访问属性:内存类型(Normal/Device/S..o..)
Strongly ordered:强序
三种内存类型对应的情景:可缓存,可缓冲,可共享
三种内存类型的性能体现
- Normal
- Device
- S..o..
可共享:主机(Master)间数据同步
- 适用范围:
-
- 多主机访问单从机时
- 另一个主机的数据可能还在缓存中,未同步到从机上
- 那当前主机访问的从机数据就是有误的
- 共享使能:
-
- 开启共享 ≈ 关闭Cache
- 开关共享: 读操作速度影响大,写操作基本没有影响
不同配置下(访问属性:内存类型,是否缓存,是否缓冲,是否共享)的性能情况:
2. Cache简介(了解)
Cache:高级缓存,结合MPU使用(由MPU来指定内存区域的Cache策略)
F4有MPU但是没有Cache,所以一般不用MPU
2.1. Cache简介:
- Cache:高级缓存(因为处于CPU中,主频与CPU一致)
-
- 可实现
- Cache分为:
-
- 数据缓存D-Cache
-
-
- 可解决CPU加速访问SRAM
-
SRAM主频<CPU主频
-
- 指令缓存I-Cache
- Cache操作:由MPU指定区域的Cache策略
-
- 使能
- 禁止
- 清空
- 无效化
2.2. Cache使用:对SRAM的-读操作、写操作
- 读写命中:Cache hit
- 读写丢失:Cache miss
2.2.1. Core读Cache:读操作
Core可以理解为CPU
RT RA对应处理方式的缩写
2.2.2. Core写Cache:写操作
Core可以理解为CPU
WT WB NWA对应处理方式的缩写
2.3. 数据不一致问题解决:
- 设置共享
浪费了Cache资源
- 软件对Cache进行维护:在读写操作之前,调用解决对应情况的api
Cache配置相关函数:SCB_EnableICache
SCB_DisableICache
SCB_InvalidateICache
SCB_EnableDCache
SCB_DisableDCache
SCB_InvalidateDCache
SCB_CleanDCache
SCB_CleanInvalidateDCache
SCB_InvalidateDCache_by_addr
SCB_CleanDCache_by_addr
SCB_CleanInvalidateDCache_by_addr
3. MPU相关寄存器介绍(熟悉)
Region:区域
📎Cortex M3权威指南(中文).pdf
📎STM32H7编程手册.pdf
3.1. MPU类型寄存器(MPU_TYPE):是否支持MPU,可配置8(F7)/16(H7)个保护区域
通过对DREGION的配置:MPU支持的区域数量
- 0:不支持MPU
- >0:支持MPU
-
- 0x08
- 0x10
3.2. MPU控制寄存器(MPU_CTRL):设置MPU使能
PRIVDEFENA位的影响:
M3:
H7:
3.3. MPU区域编号寄存器(MPU_RNR):选中要配置的(0-7(F7)/0-15(H7))区域
3.4. MPU基地址寄存器(MPU_RBAR):设置区域的起始地址
3.5. MPU区域属性和容量寄存器(MPU_RASR):设置每个区域的属性【重点】
XN位:指令访问
功能是在该区域能不能执行代码
AP位:访问权限,通常使用全访问
TEX位:设置Cache策略
不同配置下(访问属性:内存类型,是否缓存,是否缓冲,是否共享)的性能情况:
注意,性能由TEX,C,B,S等其他共同影响的
SRD位:使能当前区域的子区域
15:8的每一位,给0:子region使能,1:失能
直接给SRD0x00,代表全使能
4. MPU相关HAL库驱动介绍(掌握)
这里仅讲使能、配置(主要讲结构体)函数
4.1. void HAL_MPU_Enable(uint32_t MPU_Control)
MPU_HFNMI_PRIVDEF_NONE
MPU_HARDFAULT_NMI
MPU_PRIVILEGED_DEFAULT
MPU_HFNMI_PRIVDEF使用:HAL_MPU_Enable(MPU_PRIVILEGED_DEFAULT);
4.2. MPU HAL相关结构体-MPU_Region_InitTypeDef
将配置好的该结构体对象,传入
5. MPU基本配置步骤(掌握)
5.1. 通过配置TEX C B S =>> 来配置内存类型,Cache策略
6. 编程实战——分析总框图!!!(掌握)
解读工程📎H750-实验12 内存保护(MPU)实验.zip
6.1. 实战代码
/******************************************************************************************************* @file mpu.c* @author 正点原子团队(ALIENTEK)* @version V1.0* @date 2020-03-22* @brief MPU内存保护 驱动代码* @license Copyright (c) 2020-2032, 广州市星翼电子科技有限公司***************************************************************************************************** @attention** 实验平台:正点原子 STM32H750开发板* 在线视频:www.yuanzige.com* 技术论坛:www.openedv.com* 公司网址:www.alientek.com* 购买地址:openedv.taobao.com** 修改说明* V1.0 20200322* 第一次发布******************************************************************************************************/#include "./SYSTEM/usart/usart.h"
#include "./SYSTEM/delay/delay.h"
#include "./BSP/LED/led.h"
#include "./BSP/MPU/mpu.h"/*** @brief 设置某个区域的MPU保护* @param baseaddr: MPU保护区域的基址(首地址)* @param size:MPU保护区域的大小(必须是32的倍数,单位为字节)* @param rnum:MPU保护区编号,范围:0~15,最大支持16个保护区域* @param de:禁止指令访问;0,允许指令访问;1,禁止指令访问* @param ap:访问权限,访问关系如下:* @arg 0,无访问(特权&用户都不可访问)* @arg 1,仅支持特权读写访问* @arg 2,禁止用户写访问(特权可读写访问)* @arg 3,全访问(特权&用户都可访问)* @arg 4,无法预测(禁止设置为4!!!)* @arg 5,仅支持特权读访问* @arg 6,只读(特权&用户都不可以写)* @note 详见:STM32H7编程手册.pdf,4.6.6节,Table 91.* @param sen:是否允许共用;0,不允许;1,允许* @param cen:是否允许cache;0,不允许;1,允许* @param ben:是否允许缓冲;0,不允许;1,允许* @retval 0, 成功; 1, 错误;*/
uint8_t mpu_set_protection(uint32_t baseaddr, uint32_t size, uint32_t rnum, uint8_t de, uint8_t ap, uint8_t sen, uint8_t cen, uint8_t ben)
{MPU_Region_InitTypeDef mpu_region_init_handle; /* MPU初始化句柄 */HAL_MPU_Disable(); /* 配置MPU之前先关闭MPU,配置完成以后在使能MPU */mpu_region_init_handle.Enable = MPU_REGION_ENABLE; /* 使能该保护区域 */mpu_region_init_handle.Number = rnum; /* 设置保护区域 */mpu_region_init_handle.BaseAddress = baseaddr; /* 设置基址 */mpu_region_init_handle.Size = size; /* 设置保护区域大小 */mpu_region_init_handle.SubRegionDisable = 0X00; /* 禁止子区域 */mpu_region_init_handle.TypeExtField = MPU_TEX_LEVEL0; /* 设置类型扩展域为level0 */mpu_region_init_handle.AccessPermission = ap; /* 设置访问权限 */mpu_region_init_handle.DisableExec = de; /* 是否允许指令访问 */mpu_region_init_handle.IsShareable = sen; /* 是否允许共享 */mpu_region_init_handle.IsCacheable = cen; /* 是否允许cache */mpu_region_init_handle.IsBufferable = ben; /* 是否允许缓冲 */HAL_MPU_ConfigRegion(&mpu_region_init_handle); /* 配置MPU */HAL_MPU_Enable(MPU_PRIVILEGED_DEFAULT); /* 开启MPU */return 0;
}/*** @brief 设置需要保护的存储块* @note 必须对部分存储区域进行MPU保护,否则可能导致程序运行异常* 比如MCU屏不显示,摄像头采集数据出错等等问题* @param 无* @retval 无*/
void mpu_memory_protection(void)
{/* 保护整个DTCM,共128K字节,允许指令访问,禁止共用,允许cache,允许缓冲 */mpu_set_protection(0x20000000, MPU_REGION_SIZE_128KB, MPU_REGION_NUMBER1, MPU_INSTRUCTION_ACCESS_ENABLE,MPU_REGION_FULL_ACCESS, MPU_ACCESS_NOT_SHAREABLE, MPU_ACCESS_CACHEABLE, MPU_ACCESS_BUFFERABLE);/* 保护整个AXI SRAM,共512K字节,允许指令访问,禁止共用,允许cache,允许缓冲 */mpu_set_protection(0x24000000, MPU_REGION_SIZE_512KB,MPU_REGION_NUMBER2, MPU_INSTRUCTION_ACCESS_ENABLE,MPU_REGION_FULL_ACCESS, MPU_ACCESS_NOT_SHAREABLE, MPU_ACCESS_CACHEABLE, MPU_ACCESS_BUFFERABLE);/* 保护整个SRAM1~SRAM3,共288K字节,允许指令访问,禁止共用,允许cache,允许缓冲 */mpu_set_protection(0x30000000, MPU_REGION_SIZE_512KB,MPU_REGION_NUMBER3, MPU_INSTRUCTION_ACCESS_ENABLE,MPU_REGION_FULL_ACCESS, MPU_ACCESS_NOT_SHAREABLE, MPU_ACCESS_CACHEABLE, MPU_ACCESS_BUFFERABLE);/* 保护整个SRAM4,共64K字节,允许指令访问,禁止共用,允许cache,允许缓冲 */mpu_set_protection(0x38000000, MPU_REGION_SIZE_64KB, MPU_REGION_NUMBER4, MPU_INSTRUCTION_ACCESS_ENABLE,MPU_REGION_FULL_ACCESS, MPU_ACCESS_NOT_SHAREABLE, MPU_ACCESS_CACHEABLE, MPU_ACCESS_BUFFERABLE);/* 保护MCU LCD屏所在的FMC区域,,共64M字节,允许指令访问,禁止共用,禁止cache,禁止缓冲 */mpu_set_protection(0x60000000, MPU_REGION_SIZE_64MB, MPU_REGION_NUMBER5, MPU_INSTRUCTION_ACCESS_ENABLE,MPU_REGION_FULL_ACCESS, MPU_ACCESS_NOT_SHAREABLE, MPU_ACCESS_NOT_CACHEABLE, MPU_ACCESS_NOT_BUFFERABLE);/* 保护SDRAM区域,共64M字节,允许指令访问,禁止共用,允许cache,允许缓冲 */mpu_set_protection(0XC0000000, MPU_REGION_SIZE_64MB, MPU_REGION_NUMBER6, MPU_INSTRUCTION_ACCESS_ENABLE,MPU_REGION_FULL_ACCESS, MPU_ACCESS_NOT_SHAREABLE, MPU_ACCESS_CACHEABLE, MPU_ACCESS_BUFFERABLE);/* 保护整个NAND FLASH区域,共256M字节,禁止指令访问,禁止共用,禁止cache,禁止缓冲 */mpu_set_protection(0X80000000, MPU_REGION_SIZE_256MB, MPU_REGION_NUMBER7, MPU_INSTRUCTION_ACCESS_DISABLE,MPU_REGION_FULL_ACCESS, MPU_ACCESS_NOT_SHAREABLE, MPU_ACCESS_NOT_CACHEABLE, MPU_ACCESS_NOT_BUFFERABLE);
}/*** @brief MemManage错误处理中断* @note 进入此中断以后,将无法恢复程序运行!!** @param 无* @retval 无*/
void MemManage_Handler(void)
{LED1(0); /* 点亮LED1(GREEN LED) */printf("Mem Access Error!!\r\n"); /* 输出错误信息 */delay_ms(1000);printf("Soft Reseting...\r\n"); /* 提示软件重启 */delay_ms(1000);NVIC_SystemReset(); /* 软复位 */
}
6.2. 分析总框图(全屏看)
可以通过微调整来实现程序高速运行,前提是稳定性
7. H7的内存模型:H7内存默认映射与属性
参考H7的编程手册📎STM32H743勘误手册.pdf📎STM32H7xx参考手册(V3中文版).pdf📎STM32H7xx参考手册.pdf📎STM32H7编程手册.pdf
7.1. H7内存默认映射
8. 通过Keil Debug来查看MPU配置(MDK局限:只能显示8个区域)
8.1. 菜单栏打开:
8.2. Memory Protection Unit (MPU)工具
8.3. 执行完MPU配置代码后,在工具内查看MPU配置情况
9. 课堂总结
内存保护(MPU)实验(课堂总结).pdf