STM32F4每个IO口都可以作为外部输入中断
STM32F4的中断控制器支持22个外部(中断/事件)请求
EXTI线0~15:外部IO口输入中断
EXTI线16:PVD输出
EXTI线17:RTC闹钟事件
EXTI线18:USB OTG 唤醒事件
EXTI线19:以太网唤醒事件
EXTI线20:USB OTG HS(在FS设置)唤醒事件
EXTI线21:RTC入侵和时间戳事件
EXTI线22:RTC唤醒事件
每个外部中断线可以独立的配置出发方式(上升沿,下降沿,双边沿),触发/屏蔽,专用状态位
(PA0,PB0,PC0,PD0,PE0,PF0,PG0,PH0,PI0)->EXTI线0
.....................
(PA15,PB15,PC15,PD15,PE15,PF15,PG15,PH15,PI15)->EXTI线15
IO口外部中断在中断向量表中只分配了7个中断向量,也就是只能使用7个中断函数
中断服务函数列表
EXTI0_IRQHander
EXTI2_IRQHander
EXTI3_IRQHander
EXTI4_IRQHander
EXTI9_5_IRQHander
EXTI15_10_IRQHander
外部中断常用库函数
void SYSCFG_EXTILineConfig() //设置IO口与中断线关系
void EXTI_Init() //初始化中断线,触发方式等
ITStatus EXTI_GetITStatus() //判断中断线状态,是否发生
void EXTI_ClearTPendingBit() //清除中断线上的中断标志位
RCC_APB2PeriphClockCmd() //使能SYSCFG时钟
外部中断配置步骤
1.使能SYSCFG时钟 RCC_APB2PeriphClockCmd()
2.初始化IO口为输入 GPIO_Init();
3.设置IO口与中断线的关系 SYSCFG_EXTILineConfig()
4.初始化线上关系,设置触发条件 EXTI_Init()
5.配置中断分组 NVIC_Init();
6.编写中断服务函数 EXTIx_IRQHander()
7.清除中断标志位 EXTI_ClearTPendingBit()
#include "stm32f4xx.h" #include "usart.h" #include "delay.h" #include "sys.h" #define PFout(n) BIT_ADDR(GPIOF_ODR_Addr,n) /* 输出 */ #define LED0 PFout( 9 ) /* DS0 */ void LED_Init( void ) { /* GPIOF9初始化设置 */ GPIO_InitTypeDef GPIO_InitStructure; RCC_AHB1PeriphClockCmd( RCC_AHB1Periph_GPIOF, ENABLE ); /* 使能GPIOF时钟 */ GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; /* LED对应IO口 */ GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; /* 普通输出模式 */ GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; /* 推挽输出 */ GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz; /* 100MHz */ GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; /*上拉 */ GPIO_Init( GPIOF, &GPIO_InitStructure ); /* 初始化GPIO */ GPIO_SetBits( GPIOF, GPIO_Pin_9 ); /* GPIOF9设置高,灯灭 */ /* GPIO_ResetBits(GPIOF,GPIO_Pin_9);//输出低电平,灯亮 */ } void mEXTI_Init() { NVIC_InitTypeDef NVIC_InitStructure; EXTI_InitTypeDef EXTI_InitStructure; GPIO_InitTypeDef GPIO_InitStructure; /* 使能SYSCFG时钟 RCC_APB2PeriphClockCmd() */ RCC_APB2PeriphClockCmd( RCC_APB2Periph_SYSCFG, ENABLE ); /* 使能SYSCFG时钟 */ /* GPIOF4初始化设置 */ RCC_AHB1PeriphClockCmd( RCC_AHB1Periph_GPIOE, ENABLE ); /* 使能GPIOF时钟 */ GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4; /* LED对应IO口 */ GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; /* 输入模式 */ GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz; /* 100MHz */ GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; /*上拉 */ GPIO_Init( GPIOE, &GPIO_InitStructure ); /* 初始化GPIO */ /* 设置IO口与中断线的关系 SYSCFG_EXTILineConfig() */ SYSCFG_EXTILineConfig( EXTI_PortSourceGPIOE, EXTI_PinSource4 ); /* PE4 连接到中断线4 */ /* 初始化线上关系,设置触发条件 EXTI_Init() */ EXTI_InitStructure.EXTI_Line = EXTI_Line4; /* 线4 */ EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; /* 中断事件 */ EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling; /*下降沿触发 */ EXTI_InitStructure.EXTI_LineCmd = ENABLE; /* 中断线使能 */ EXTI_Init( &EXTI_InitStructure ); /* 配置 */ /* 配置中断分组 NVIC_Init(); */ NVIC_InitStructure.NVIC_IRQChannel = EXTI4_IRQn; /* 外部中断4 */ NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x01; /* 抢占优先级1 */ NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02; /* 子优先级2 */ NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; /* 使能外部中断通道 */ NVIC_Init( &NVIC_InitStructure ); /* 配置 */ } /* 编写中断服务函数 EXTI4_IRQHandler() */ void EXTI4_IRQHandler( void ) { delay_ms( 10 ); /* 消抖 */ if ( GPIO_ReadInputDataBit( GPIOE, GPIO_Pin_4 ) == 0 ) { LED0 = !LED0; /* GPIO_ResetBits(GPIOF,GPIO_Pin_9);//输出低电平,灯亮 */ } /* 除中断标志位 EXTI_ClearTPendingBit() */ EXTI_ClearITPendingBit( EXTI_Line4 ); /* 清除LINE4上的中断标志位 */ } int main( void ) { delay_init( 168 ); /* 初始化延时函数 */ LED_Init(); /* 初始化LED */ mEXTI_Init(); /* 初始化中断 */ GPIO_ResetBits( GPIOF, GPIO_Pin_9 ); /* 输出低电平,灯亮 */ delay_ms( 1000 ); GPIO_SetBits( GPIOF, GPIO_Pin_9 ); /* 设置高,灯灭 */ while ( 1 ) ; }