1. 中断系统概述
1.1 中断的基本概念
中断是嵌入式系统中实现异步事件处理的核心机制,允许处理器暂停当前任务,响应外部或内部事件,处理完成后返回原任务继续执行。
中断处理流程:
中断发生 → 保存现场 → 执行ISR → 恢复现场 → 继续执行
1.2 中断类型分类
1.2.1 按来源分类
- 外部中断:来自外设的硬件信号(GPIO、定时器等)
- 内部中断:处理器内部产生(除零、溢出等)
- 软件中断:由特定指令触发(SWI指令)
1.2.2 按优先级分类
- 可屏蔽中断:可通过程序控制是否响应
- 不可屏蔽中断(NMI):必须立即响应,用于紧急情况
2. 中断控制器与嵌套中断
2.1 常见中断控制器
NVIC(嵌套向量中断控制器)特点:
- 支持中断优先级分组
- 支持中断嵌套
- 提供尾链优化技术
- 支持动态优先级调整
// ARM Cortex-M NVIC配置示例
// 设置中断优先级分组(4位优先级,0位子优先级)
NVIC_SetPriorityGrouping(0x03);
// 配置具体外设中断优先级
NVIC_SetPriority(USART1_IRQn, 0x05); // 设置USART1中断优先级
NVIC_EnableIRQ(USART1_IRQn); // 使能USART1中断
2.2 中断嵌套机制
中断嵌套条件:
- 新中断优先级高于当前执行ISR的优先级
- 处理器中断系统支持嵌套
- 已正确配置中断优先级
// 中断嵌套处理示例
void USART1_IRQHandler(void)
{
// 高优先级中断处理中...
// 此时如果发生更高优先级中断,会嵌套执行
// 处理完成后返回此处继续执行
}
3. DMA技术原理与应用
3.1 DMA基本概念
DMA(直接内存访问)允许外设直接与内存进行数据传输,无需CPU介入,大幅提高数据传输效率。
DMA传输优势:
- 减少CPU开销
- 提高数据传输效率
- 支持后台数据传输
3.2 DMA传输模式
3.2.1 传输类型
- 内存到外设:如内存数据发送到UART
- 外设到内存:如ADC数据采集到内存
- 内存到内存:大数据块拷贝
3.2.2 传输方式
- 单次传输:每次请求传输一个数据
- 块传输:一次请求传输多个数据
- 循环传输:自动重复传输
// STM32 DMA配置示例
void dma_usart_tx_init(void)
{
DMA_Channel_TypeDef* dma_ch = DMA1_Channel4;
// 配置DMA通道
dma_ch->CCR = 0;
dma_ch->CCR |= DMA_CCR_DIR; // 内存到外设
dma_ch->CCR |= DMA_CCR_MINC; // 内存地址递增
dma_ch->CCR |= DMA_CCR_PSIZE_0; // 外设数据宽度8位
dma_ch->CCR |= DMA_CCR_MSIZE_0; // 内存数据宽度8位
dma_ch->CCR |= DMA_CCR_CIRC; // 循环模式
dma_ch->CNDTR = 256; // 传输数据量
dma_ch->CPAR = (uint32_t)&USART1->DR; // 外设地址
dma_ch->CMAR = (uint32_t)tx_buffer; // 内存地址
dma_ch->CCR |= DMA_CCR_EN; // 使能DMA
}
4. 中断与DMA的协同工作
4.1 典型应用场景
数据采集系统:
ADC采样 → DMA传输到内存 → 传输完成中断 → CPU处理数据
通信系统:
UART接收数据 → DMA存储到缓冲区 → 半满/全满中断 → CPU处理数据
4.2 性能优化策略
// 双缓冲区DMA应用示例
#define BUFFER_SIZE 1024
uint8_t dma_buffer1[BUFFER_SIZE];
uint8_t dma_buffer2[BUFFER_SIZE];
uint8_t* current_buffer = dma_buffer1;
void DMA1_Channel1_IRQHandler(void)
{
if(DMA1->ISR & DMA_ISR_TCIF1) {
// 传输完成中断
DMA1->IFCR |= DMA_IFCR_CTCIF1; // 清除标志
// 切换缓冲区
if(current_buffer == dma_buffer1) {
current_buffer = dma_buffer2;
} else {
current_buffer = dma_buffer1;
}
// 处理已完成传输的数据
process_completed_data();
}
}
5. 核心考点与真题解析
5.1 考点一:中断优先级与嵌套
例题1(2021年真题):
在ARM Cortex-M系列处理器中,关于中断优先级分组,以下描述正确的是()
A. 优先级分组固定为16级,不可配置
B. 可以配置为4位优先级+0位子优先级
C. 子优先级用于决定中断嵌套顺序
D. 优先级数值越小,优先级越低
解析:
正确答案是B。Cortex-M的NVIC支持灵活的中断优先级分组配置,可以配置为不同的优先级位数和子优先级位数组合。优先级数值越小优先级越高,子优先级用于相同优先级中断的仲裁。
5.2 考点二:DMA传输特性
例题2(2020年真题):
下列关于DMA传输的描述中,错误的是()
A. DMA传输不需要CPU参与数据搬运
B. DMA传输期间CPU可以执行其他任务
C. DMA传输速度总是比CPU编程传输快
D. DMA传输可以减少CPU中断次数
解析:
正确答案是C。DMA传输在大量数据搬运时通常比CPU编程传输快,但对于小数据量传输,由于DMA初始化开销,可能不如CPU直接传输快。
5.3 考点三:中断响应流程
例题3(2019年真题):
中断响应过程中,处理器首先执行的操作是()
A. 执行中断服务程序
B. 保存程序计数器PC
C. 保存所有寄存器
D. 查询中断向量表
解析:
正确答案是B。中断响应时,处理器首先自动保存程序计数器PC(返回地址),然后根据中断号查询中断向量表获取ISR地址,跳转到ISR执行。
6. 实战编程与优化
6.1 中断服务程序编写规范
// 规范的ISR编写示例
__attribute__((interrupt)) void EXTI0_IRQHandler(void)
{
// 1. 清除中断标志(尽早)
EXTI->PR = EXTI_PR_PR0;
// 2. 处理中断事件
handle_external_event();
// 3. 避免耗时操作
// 4. 注意可重入性问题
// 5. 尽量减少共享资源访问
}
// 中断处理中的延迟处理机制
volatile uint8_t irq_flag = 0;
void TIM2_IRQHandler(void)
{
TIM2->SR = 0; // 清除中断标志
irq_flag = 1; // 设置标志,主循环中处理
}
void main_loop(void)
{
while(1) {
if(irq_flag) {
irq_flag = 0;
process_timer_event(); // 在主循环中处理耗时操作
}
// 其他任务
}
}
6.2 DMA编程最佳实践
// DMA内存到内存传输优化
void dma_memcpy(void* dest, void* src, size_t size)
{
// 禁用DMA通道
DMA1_Channel1->CCR &= ~DMA_CCR_EN;
// 配置DMA传输
DMA1_Channel1->CNDTR = size;
DMA1_Channel1->CPAR = (uint32_t)src;
DMA1_Channel1->CMAR = (uint32_t)dest;
// 配置传输参数
DMA1_Channel1->CCR = DMA_CCR_MEM2MEM | // 内存到内存模式
DMA_CCR_PL_0 | // 中等优先级
DMA_CCR_MSIZE_0 | // 8位内存数据宽度
DMA_CCR_PSIZE_0 | // 8位外设数据宽度
DMA_CCR_MINC | // 内存地址递增
DMA_CCR_PINC; // 外设地址递增
// 使能DMA传输
DMA1_Channel1->CCR |= DMA_CCR_EN;
// 等待传输完成
while(DMA1_Channel1->CNDTR > 0);
}
7. 系统性能优化策略
7.1 中断延迟优化
减少中断延迟的方法:
- 优化ISR代码,减少执行时间
- 合理设置中断优先级
- 使用中断嵌套谨慎
- 避免在ISR中进行复杂计算
7.2 DMA使用场景选择
适合使用DMA的场景:
- 大量数据搬运(>16字节)
- 频繁的数据传输
- 实时性要求高的数据流
- 需要降低CPU负载的应用
8. 备考重点总结
- 掌握中断系统工作原理
- 中断响应流程和现场保护机制
- 中断优先级和嵌套规则
- 中断控制器(NVIC)配置方法
- 理解DMA技术应用
- DMA传输模式和配置方法
- DMA与中断的协同工作
- DMA性能优化技巧
- 熟悉实际编程实践
- ISR编写规范和注意事项
- DMA编程接口使用
- 系统性能优化方法
- 掌握相关真题考点
- 中断优先级分组配置
- DMA传输特性理解
- 中断响应流程分析
下一篇文章预告:将深入讲解嵌入式系统外设接口(GPIO、UART、SPI、I2C)的原理与应用编程。