1. 板级支持包
1.1 用户应用层:
构建应用程序,例如:按下按键可以点亮LED
通过板级支持包知道板上的硬件有什么功能可以被实现
1.2 板级支持包
访问硬件的接口,提供具体硬件的功能,例如:点亮LED/按下按键程序有反馈
对板上的资源功能给出实现,并且提供用户应用程序的接口,例如:用户不需要知道GPIO的硬件特点,只需要知道调用这个函数就可以点亮LDE灯
1.3 底层驱动
HAL库驱动
2. 启动文件
芯片上电过程:
触发异常(上电复位异常)->中断向量表->用户程序
启动文件执行内容/步骤:
- 初始化堆栈指针
- 设置PC指针的值
- 设置中断向量表
- 配置系统时钟
- 调用C库函数_main, 初始化堆栈的工作,最终会跳转到我们自己编写的main
3. 中断/异常
(系统异常,外部中断)
CM3内核支持256个中断,包括16个内核中断和250个外部中断,同时具有256级的可编程中断设置。而STM32只使用了一部分。STM32拥有84个中断,包括16个内核中断和68个可屏蔽中断(STM32F107系列才使用了68个可屏蔽中断),还拥有16级可编程的中断优先级。STM32F103系列只使用了60个可屏蔽中断。
STM32中控制中断优先级的寄存器组是IP[240]。是由240个8bit的寄存器组成的。而STM32F103只用了前六十个(0 ~ 59)。在STM32F103系列单片机中,这8bit也没有全部使用,而是只使用了其高四位(4 ~ 7位)。下图是中断分组的分配情况
由上图可知,优先级分组:
4个bit位:划分【抢占优先级】和【子优先级/响应优先级】,可分为5组 优先级分组
NVIC_PriorityGroup_0: 0bit(无) 4bit(0-15)
NVIC_PriorityGroup_1: 1bit(0-1) 3bit(0-7)
NVIC_PriorityGroup_2: 2bit(0-3) 2bit(0-3)
NVIC_PriorityGroup_3: 3bit(0-7) 1bit(0-1)
NVIC_PriorityGroup_4: 4bit(0-15) 0bit(无)
中断响应顺序:抢占优先级 > 子优先级 > IRQ编号
---------(说明:数值越小,优先级越高)
这里需要关注的是,抢占优先级的级别高于子优先级。**高抢占优先级的中断可以在低抢占优先级中断执行的过程中被响应,反之则不行。这就是所谓的中断嵌套。**换句话说呢,就是高抢占优先级中断可以抢占低抢占优先级中断的执行。当多个中断同时到来,而且他们的抢占优先级相同,则先进入子优先级更高的中断。
**但是,当抢占优先级相同的情况下,高子优先级中断不能打断低子优先级中断,也就是不能实现中断嵌套。**这种情况下,高子优先级中断必须先等待低子优先级中断执行完成,在进行自己的中断。
软件部分:
通过 嵌套向量中断控制器NVIC , 编程设置优先级
4. 配置某个中断优先级的步骤如下:
-
- 配置中断优先级分组
-
- 配置某一中断的优先级
1. 配置中断优先级分组
示例代码:
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
2. 配置某一中断的优先级
配置某一中断优先级的步骤如下:
- 声明上述结构体
- 配置结构体成员变量的值
- 利用
NVIC_Init
函数初始化
示例代码:
NVIC_InitTypeDef NVIC_InitStructure; //声明结构体
NVIC_InitStructure.NVIC_IRQChannel = EXTI0_IRQn; //声明中断名称
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x02; //设置抢占优先级为2
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x03; //设置响应优先级为3
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能中断
NVIC_Init(&NVIC_InitStructure); //对上述配置进行初始化