()EXTI外设 中断
static void EXTI_NVIC_Config(void) //加上static说明这个函数只能bsp_exti.c调用
{
NVIC_InitTypeDef NVIC_InitStruct;
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);//配置NVIC为优先级组1
NVIC_InitStruct.NVIC_IRQChannel = EXTI0_IRQn;//配置中断源为按键1
NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority = 1;//配置抢占优先级为1
NVIC_InitStruct.NVIC_IRQChannelSubPriority = 1;//配置响应(子)优先级为1
NVIC_InitStruct.NVIC_IRQChannelCmd = ENABLE;//使能中断通道
NVIC_Init(&NVIC_InitStruct);
}
void EXIT_Key_Config(void)
{
GPIO_InitTypeDef GPIO_InitStruct;
EXTI_InitTypeDef EXTI_InitStruct;
//配置中断优先级
EXTI_NVIC_Config();
/* In order open led */
//初始化GPIO
RCC_APB2PeriphClockCmd(EXIT_Key1_GPIO_CLK, ENABLE);//开启按键GPIOA的时钟
GPIO_InitStruct.GPIO_Pin = EXIT_Key1_GPIO_PIN; //选择按键用到的GPIO
GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IN_FLOATING; //配置浮空输入
//GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(EXIT_Key1_GPIO_PORT, &GPIO_InitStruct);
//初始化EXTI
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE); //开启按键GPIOA时钟
GPIO_EXTILineConfig(GPIO_PortSourceGPIOA, GPIO_PinSource0);//选择EXTI的信号源
EXTI_InitStruct.EXTI_Line = EXTI_Line0;//选择EXTI的信号源
EXTI_InitStruct.EXTI_Mode = EXTI_Mode_Interrupt; //模式为中断
EXTI_InitStruct.EXTI_Trigger = EXTI_Trigger_Rising; //上升沿中断
EXTI_InitStruct.EXTI_LineCmd = ENABLE; //使能中断
EXTI_Init(&EXTI_InitStruct); //取地址
}
先写个按键中断函数,在里面我们先初始化GPIO:开启GPIO的时钟,选择按键所在的GPIO,之后配置用的是哪个口,例如按键1用的是PA0,则为GPIOB里的,找到对应的寄存器,对第0位的电平变化即为控制按键电平输入的变化,IO模式设置为浮空输入,输入可以不用管速度,之后对结构体所在函数取地址。
然后初始化EXTI,就要开启EXTI的时钟,就是GPIOA口的时钟,之后我们要配置EXTI,选择中断信号源,因为我们要控制的按键1在PA0,而输入源为PA0,则选择中断线选择EXTI0。模式为中断模式,因为按键采用的是上升沿触发电平,所以采用上升沿中断,之后使能,然后取地址结构体。
到此为止,只是配置好要用的,具体的中断还没配置,我们需要配置中断等级,它分为抢占优先级和子优先级(响应优先级),优先看抢占优先级,且级数越低优先级越高、
而配置优先级,就是配置NVIC(提供中断的控制器)(Nested vectoredinterrupt controller,即嵌套向量中断控制器),我们直接用固件库里的优先级结构体NVIC_InitTypeDef 。 其中,NVIC可以用其中的寄存器八位表达,八位表达即可以配置2^8=256中中断,但是实际上用不了那么多,所以st公司只用高四位表达,低四位取零,这样2^4=16,只能表示16级中断嵌套。分为5组。用了大哥的图,我们设置成组1,之后配置中断源为按键1,配置抢占优先级和子优先级,之后使能中断通道,然后取地址结构体。当我们配完NVIC之后,我们就要编写中断函数,就是我们中断这个进程之后要干什么,再之后写入主函数
int main(){
LED_GPIO_Config();
EXIT_Key_Config();
}