背景
很少demo或文章直接讲如何配置460的GPIO中断的,也许是太简单了,也许是应用场景比较少。这段时间正好要用到,简单写一下怎么配置。
使用场景
GPIO的中断配置主要是检测端口出现上升沿或下降沿后触发,可以用在按钮场景之类的地方。
初始化
直接上代码
c
/* PULL_DOWN IN */
#define PULL_DOWN_PORT (GPIO_PORT_B)
#define PULL_DOWN_PIN (GPIO_PIN_07)
#define PULL_DOWN_INT_IRQN (INT015_IRQn)
#define PULL_DOWN_INT_SRC_EIRQN (INT_SRC_PORT_EIRQ7)//PB07固定对应EIRQ7
void InitKey(void)
{
stc_extint_init_t stcExtIntInit;
stc_irq_signin_config_t stcIrqSignConfig;
stc_gpio_init_t stcGpioInit;
/* GPIO config */
(void)GPIO_StructInit(&stcGpioInit);
//stcGpioInit.u16Latch = PIN_LATCH_ON;
stcGpioInit.u16PinDir = PIN_DIR_IN;//输入模式
stcGpioInit.u16ExtInt = PIN_EXTINT_ON;//启用外部中断
stcGpioInit.u16PullUp = PIN_PU_OFF;//关闭内部上拉
(void)GPIO_Init(PULL_DOWN_PORT, PULL_DOWN_PIN, &stcGpioInit);
/* ExtInt config */
(void)EXTINT_StructInit(&stcExtIntInit);
stcExtIntInit.u32Filter = EXTINT_FILTER_ON;
stcExtIntInit.u32FilterClock = EXTINT_FCLK_DIV8;
stcExtIntInit.u32Edge = EXTINT_TRIG_FALLING;
(void)EXTINT_Init(EXTINT_CH07, &stcExtIntInit);
/* IRQ sign-in */
stcIrqSignConfig.enIntSrc = PULL_DOWN_INT_SRC_EIRQN;
stcIrqSignConfig.enIRQn = PULL_DOWN_INT_IRQN;
stcIrqSignConfig.pfnCallback = &PULL_DOWN_IrqHandle;
(void)INTC_IrqSignIn(&stcIrqSignConfig);
/* NVIC config */
NVIC_ClearPendingIRQ(stcIrqSignConfig.enIRQn);//清除指定中断的挂起状态
NVIC_SetPriority(stcIrqSignConfig.enIRQn, DDL_IRQ_PRIO_DEFAULT);//设置中断优先级
NVIC_EnableIRQ(stcIrqSignConfig.enIRQn);//使能中断
}
中断函数
c
uint8_t u8Count = 0U;
void PULL_DOWN_IrqHandle(void)
{
SET_LED_RED();
u8Count++;
// if (SET == EXTINT_GetExtIntStatus(EXTINT_CH07)) {
// u8Count++;
// }
// EXTINT_ClearExtIntStatus(EXTINT_CH07);
}
注意事项
1、代码中的INT_SRC_PORT_EIRQ7需要查询数据手册的引脚功能表来确认你的引脚对应的EIRQ编号,如下图我使用的PB07对应EIRQ7:

2、IRQ编号INT015_IRQn需要在规范范围内。查询参考手册的中断事件请求需要与选择表可知,IRQ0~31是所有中断通用的编号,32-127则需要根据表格中支持的范围来选择序号,最后的INT_VSSEL128-143则是向量共享中断选择寄存器。
INT_VSSEL需要做额外的配置,上述代码的写法对它是无效的,不过前32个编号基本是够用的。如果配置的编号不在规定内,会导致无法触发中断。


3、我的引脚外部电路做了上拉,所以关闭内部上拉检测下降沿即可检测按钮的按下。实际情况请根据你的电路和需求进行修改。