1、目标
实现KEY1中断,按下、松开按键,串口输出相应信息。
2、原理图
(1)按键:使用PA0引脚

(2)串口不是重点,略
3、配置GPIO
(1)使能GPIO;配置PA0为输入模式。
4、配置SYSCFG(系统配置控制器)
(1)系统配置控制器主要用于管理对可执行代码的存储区域的地址重映射、选择以太网 PHY 接口以及管理 GPIO 的外部中断线连接。
(2)将PA0映射到EXTI0。

(3)注意:STM32F1中GPIO与外部中断的映射配置是通过AFIO模块;STM32F4中是通过SYSCFG模块。
5、配置EXTI
(1)配置EXTI_RTSR、EXTI_FTSR,选择中断触发方式
(2)配置EXTI_IMR:允许EXTI发出中断

(3)清除中断

6、配置NVIC
(1)配置NVIC中的寄存器,允许NVIC把中断发给CPU。
(2)多个中断源汇聚到NVIC,NVIC的职责就是从多个中断源中取出优先级最高的中断,向CPU发出中断信号。 处理中断时,程序可以写NVIC的寄存器,清除中断。
7、程序
(1)GPIO 和 SYSCFG的配置
void key_init(void)
{
unsigned int *pReg = NULL;
pReg = (unsigned int *)(0x40023800 + 0x30);
*pReg |= (0x01 << 0); /* 使能GPIOA时钟 */
pReg = (unsigned int *)(0x40020000 + 0x00);
*pReg &= (~(0x03 << 0)); /* 配置PA0为输入模式 */
/* 将PA0映射到EXTI0 */
pReg = (unsigned int *)(0x40013800 + 0x08); /* SYSCFG_EXTICR1 */
*pReg &= ~(0x0F << 0); /* 清除EXTI0[3:0] */
*pReg |= (0x00 << 0); /* 选择PA0作为EXTI0输入源 */
}
(2)EXTI配置
void exti_init(void)
{
EXTI_TypeDef *pReg = NULL;
pReg = (EXTI_TypeDef *)(0x40013C00 + 0x00);
/* 配置EXTI0为双边沿触发 */
pReg->RTSR |= (0x01 << 0); /* 使能上升沿触发 */
pReg->FTSR |= (0x01 << 0); /* 使能下降沿触发 */
pReg->IMR |= (0x01 << 0); /* 使能EXTI0中断 */
}
(3)NVIC配置
void nvic_init(void)
{
NVIC_Type *pReg = NULL;
pReg = (NVIC_Type *)(0xE000E100);
pReg->ISER[0] = (0x01 << 6); /* 使能EXTI0中断 */
}
(4)CPU
CPSIE I ; 清除PRIMASK,使能中断
(5)中断程序
void EXTI0_IRQHandler(void)
{
unsigned int *pReg = (unsigned int *)(0x40020000 + 0x10);
if ((*pReg &(1<<0)) == 1)
{
puts("KEY1 pressed.\r\n");
}
else
{
puts("KEY1 released.\r\n");
}
pReg = (unsigned int *)(0x40013C00 + 0x14); /* EXTI_PR */
*pReg |= (0x01 << 0); /* 清除EXTI0的挂起位 */
pReg = (unsigned int *)(0xE000E100 + 0x180); /* NVIC_ICPR[0] */
*pReg |= (0x01 << 6); /* 清除NVIC的挂起位 */
/* 注:NVIC_ICPRx 软件写1,用于手动清除挂起位 */
}
(6)NVIC说明
- 若中断产生但并没有立即执行(例如有一个更高优先级的中断再处理),中断就会被挂起;
- 挂起位可以软件清零或者软件设置;
- NVIC 中 中断执行后,其挂起位会被硬件自动清零。