实验要求:Stm32外部中断实验
实验器材:stm32F407开发板
第一步:配置按键GPIO外设
void Key_Init()
{
GPIO_InitTypeDef GPIO_Initstructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB|RCC_AHB1Periph_GPIOA,ENABLE);//使能GPIOB和GPIOA口的时钟
GPIO_Initstructure.GPIO_Pin = GPIO_Pin_9|GPIO_Pin_8;//设置输入输出引脚
GPIO_Initstructure.GPIO_Mode = GPIO_Mode_IN;//设置为输入
GPIO_Initstructure.GPIO_PuPd = GPIO_PuPd_UP;//输入上拉
GPIO_Initstructure.GPIO_Speed =GPIO_Fast_Speed;//速度为高速
GPIO_Init(GPIOB,&GPIO_Initstructure);//GPIO的初始化
GPIO_Initstructure.GPIO_Pin = GPIO_Pin_0;//设置输入输入引脚
GPIO_Initstructure.GPIO_Mode = GPIO_Mode_IN;//设置为输入
GPIO_Initstructure.GPIO_PuPd = GPIO_PuPd_DOWN;//输入下拉
GPIO_Initstructure.GPIO_Speed =GPIO_Fast_Speed;//速度为高速
GPIO_Init(GPIOA,&GPIO_Initstructure);
}
第二步:按键中断的相关配置
//按键中断的配置
void Exit_Key_config()
{
// 第一步:初始化连接到EXIT的GPIO
Key_Init();
// 第二步:初始化EXIT
EXTI_InitTypeDef EXTI_Initstrcture;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG ,ENABLE);//使能SYSCFG 时钟,中断线时钟
SYSCFG_EXTILineConfig(EXTI_PortSourceGPIOA,EXTI_PinSource0);//PA0连接线0
SYSCFG_EXTILineConfig(EXTI_PortSourceGPIOB,EXTI_PinSource8);//PB8连接线8
SYSCFG_EXTILineConfig(EXTI_PortSourceGPIOB,EXTI_PinSource9);//PB9连接线9
/*EXTI0的中断初始化*/
/*************************************************/
/*************************************************/
EXTI_Initstrcture.EXTI_Line =EXTI_Line0;//线0
EXTI_Initstrcture.EXTI_Mode =EXTI_Mode_Interrupt;//中断事件
EXTI_Initstrcture.EXTI_Trigger = EXTI_Trigger_Rising; //上升沿触发
EXTI_Initstrcture.EXTI_LineCmd = ENABLE;//中断线使能
EXTI_Init(&EXTI_Initstrcture);
/*************************************************/
/*************************************************/
/*EXTI8和EXTI9*/
/*********************************************/
/*********************************************/
EXTI_Initstrcture.EXTI_Line = EXTI_Line8|EXTI_Line9;//线8和线9
EXTI_Initstrcture.EXTI_Mode = EXTI_Mode_Interrupt;//中断事件
EXTI_Initstrcture.EXTI_Trigger = EXTI_Trigger_Falling; //下降沿触发
EXTI_Initstrcture.EXTI_LineCmd = ENABLE;//中断线使能
EXTI_Init(&EXTI_Initstrcture);
/*********************************************/
/*********************************************/
// 第三步:配置NVIC
NVIC_config();
//第四步:编写中断服务函数
//中断函数一般在stm32f4xx_it.c里面
}
void NVIC_config()
{
NVIC_InitTypeDef NVIC_InitStructure;
//NVIC_PriorityGroupConfig(NVIC_PriorityGroup_0);//优先级组别为0组,即优先级分组优先级最高
NVIC_InitStructure.NVIC_IRQChannel = EXTI0_IRQn;//外部中断 0
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x00;//抢占优先级 0
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02;//响应优先级 2
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;//使能外部中断通道
NVIC_Init( &NVIC_InitStructure );//配置 NVIC
//
NVIC_InitStructure.NVIC_IRQChannel = EXTI9_5_IRQn;//外部中断 0
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x03;//抢占优先级 0
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02;//响应优先级 2
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;//使能外部中断通道
NVIC_Init( &NVIC_InitStructure );//配置 NVIC
}
第三步:对LED灯的连接的GPIO口进行配置
void Led_Init()
{
GPIO_InitTypeDef GPIO_Initstructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOF,ENABLE);//使能GPIOF口的时钟
GPIO_Initstructure.GPIO_Pin = GPIO_Pin_9|GPIO_Pin_10;//设置输入输出引脚
GPIO_Initstructure.GPIO_Mode = GPIO_Mode_OUT;//设置为输出
GPIO_Initstructure.GPIO_PuPd = GPIO_PuPd_UP;//输出上拉
GPIO_Initstructure.GPIO_Speed =GPIO_Fast_Speed;//输出速度为高速
GPIO_Initstructure.GPIO_OType = GPIO_OType_PP;//输出模式为推挽
GPIO_Init(GPIOF,&GPIO_Initstructure);//GPIO的初始化
GPIO_SetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);//GPIOF9,F10设置高,灯灭
}
/*****************************************
函数: void Led_flash()
作用: led闪烁
返回值:void
参数:void
作者:马伟
********************************************/
void Led_flash()
{
for(int i=0;i<5;i++)
{
GPIO_SetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);//GPIOF9,F10设置高,灯灭
delay_ms(300);
GPIO_ResetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);//GPIOF9,F10设置低,灯亮
delay_ms(300);
}
}
第四步:编写中断服务函数
#include "stm32f4xx_it.h"
#include "led.h"
#include "delay.h"
#include "key.h"
//中断服务函数
void EXTI0_IRQHandler(void)
{
delay_ms(10);
if(WK_UP ==1)
Led_flash();//中断0调用闪灯函数
EXTI_ClearITPendingBit(EXTI_Line0);
}
//中断服务函数
void EXTI9_5_IRQHandler(void)
{
delay_ms(10);
if(KEY0 == 0)
{
LED1=!LED1;
LED2=0;
delay_ms(200);
EXTI_ClearITPendingBit(EXTI_Line9);}
if(KEY1==0)
{ LED2=!LED2;
delay_ms(200);
EXTI_ClearITPendingBit(EXTI_Line8);}
}
备注:值得注意的是,对于每个编写的函数一定要加上相对应的头文件。这里只有核心代码,并没有给出相对应的头文件
全部代码如下
key.c
#include "key.h"
#include "delay.h"
#include "sys.h"
#include "stm32f4xx.h"
#include "led.h"
//按键所在GPIO口初始化
void Key_Init()
{
GPIO_InitTypeDef GPIO_Initstructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB|RCC_AHB1Periph_GPIOA,ENABLE);//使能GPIOB和GPIOA口的时钟
GPIO_Initstructure.GPIO_Pin = GPIO_Pin_9|GPIO_Pin_8;//设置输入输出引脚
GPIO_Initstructure.GPIO_Mode = GPIO_Mode_IN;//设置为输入
GPIO_Initstructure.GPIO_PuPd = GPIO_PuPd_UP;//输入上拉
GPIO_Initstructure.GPIO_Speed =GPIO_Fast_Speed;//速度为高速
GPIO_Init(GPIOB,&GPIO_Initstructure);//GPIO的初始化
GPIO_Initstructure.GPIO_Pin = GPIO_Pin_0;//设置输入输入引脚
GPIO_Initstructure.GPIO_Mode = GPIO_Mode_IN;//设置为输入
GPIO_Initstructure.GPIO_PuPd = GPIO_PuPd_DOWN;//输入下拉
GPIO_Initstructure.GPIO_Speed =GPIO_Fast_Speed;//速度为高速
GPIO_Init(GPIOA,&GPIO_Initstructure);
}
/*****************************************
函数: int Check_key( int mode)
作用: 按键检测
返回值:int
参数:int
作者:马伟
********************************************/
int Check_key( int mode)
{
static int key_mark=1 ;
if(mode==1) key_mark=1;
if(key_mark&&(KEY0==0||KEY1==0||WK_UP==1))
{
delay_ms(10);
key_mark=0;
if(KEY0==0) return 1;
else if(KEY1==0) return 2;
else if(WK_UP==1) return 3;
}
else if(KEY0==1&&KEY1==1&&WK_UP==0) key_mark=1 ;
return 0;
}
//按键中断的配置
void Exit_Key_config()
{
// 第一步:初始化连接到EXIT的GPIO
Key_Init();
// 第二步:初始化EXIT
EXTI_InitTypeDef EXTI_Initstrcture;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG ,ENABLE);//使能SYSCFG 时钟,中断线时钟
SYSCFG_EXTILineConfig(EXTI_PortSourceGPIOA,EXTI_PinSource0);//PA0连接线0
SYSCFG_EXTILineConfig(EXTI_PortSourceGPIOB,EXTI_PinSource8);//PB8连接线8
SYSCFG_EXTILineConfig(EXTI_PortSourceGPIOB,EXTI_PinSource9);//PB9连接线9
/*EXTI0的中断初始化*/
/*************************************************/
/*************************************************/
EXTI_Initstrcture.EXTI_Line =EXTI_Line0;//线0
EXTI_Initstrcture.EXTI_Mode =EXTI_Mode_Interrupt;//中断事件
EXTI_Initstrcture.EXTI_Trigger = EXTI_Trigger_Rising; //上升沿触发
EXTI_Initstrcture.EXTI_LineCmd = ENABLE;//中断线使能
EXTI_Init(&EXTI_Initstrcture);
/*************************************************/
/*************************************************/
/*EXTI8和EXTI9*/
/*********************************************/
/*********************************************/
EXTI_Initstrcture.EXTI_Line = EXTI_Line8|EXTI_Line9;//线8和线9
EXTI_Initstrcture.EXTI_Mode = EXTI_Mode_Interrupt;//中断事件
EXTI_Initstrcture.EXTI_Trigger = EXTI_Trigger_Falling; //下降沿触发
EXTI_Initstrcture.EXTI_LineCmd = ENABLE;//中断线使能
EXTI_Init(&EXTI_Initstrcture);
/*********************************************/
/*********************************************/
// 第三步:配置NVIC
NVIC_config();
//第四步:编写中断服务函数
//中断函数一般在stm32f4xx_it.c里面
}
void NVIC_config()
{
NVIC_InitTypeDef NVIC_InitStructure;
//NVIC_PriorityGroupConfig(NVIC_PriorityGroup_0);//优先级组别为0组,即优先级分组优先级最高
NVIC_InitStructure.NVIC_IRQChannel = EXTI0_IRQn;//外部中断 0
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x00;//抢占优先级 0
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02;//响应优先级 2
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;//使能外部中断通道
NVIC_Init( &NVIC_InitStructure );//配置 NVIC
//
NVIC_InitStructure.NVIC_IRQChannel = EXTI9_5_IRQn;//外部中断 0
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x03;//抢占优先级 0
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02;//响应优先级 2
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;//使能外部中断通道
NVIC_Init( &NVIC_InitStructure );//配置 NVIC
}
key.h
#ifndef __KEY_H
#define __KEY_H
#include "key.h"
#include "sys.h"
#define KEY0 GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_9) //PE4
#define KEY1 GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_8) //PE3
#define WK_UP GPIO_ReadInputDataBit(GPIOA,GPIO_Pin_0) //PA0
int Check_key( int mode);//按键检测
void Key_Init(void); //按键GPIO口初始化
void Exit_Key_config(void);//外部中断初始化
void NVIC_config(void);//NVIC相关配置
#endif
led.c
#include "led.h"
#include "delay.h"
/*初始化led所在口的时钟以及一些输入输出的相关设置*/
void Led_Init()
{
GPIO_InitTypeDef GPIO_Initstructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOF,ENABLE);//使能GPIOF口的时钟
GPIO_Initstructure.GPIO_Pin = GPIO_Pin_9|GPIO_Pin_10;//设置输入输出引脚
GPIO_Initstructure.GPIO_Mode = GPIO_Mode_OUT;//设置为输出
GPIO_Initstructure.GPIO_PuPd = GPIO_PuPd_UP;//输出上拉
GPIO_Initstructure.GPIO_Speed =GPIO_Fast_Speed;//输出速度为高速
GPIO_Initstructure.GPIO_OType = GPIO_OType_PP;//输出模式为推挽
GPIO_Init(GPIOF,&GPIO_Initstructure);//GPIO的初始化
GPIO_SetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);//GPIOF9,F10设置高,灯灭
}
/*****************************************
函数: void Led_flash()
作用: led闪烁
返回值:void
参数:void
作者:马伟
********************************************/
void Led_flash()
{
for(int i=0;i<5;i++)
{
GPIO_SetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);//GPIOF9,F10设置高,灯灭
delay_ms(300);
GPIO_ResetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);//GPIOF9,F10设置低,灯亮
delay_ms(300);
}
}
led.h
#ifndef __LED_H
#define __LED_H
#include "sys.h"
#define LED1 PFout(8) // D1
#define LED2 PFout(9) // D2
void Led_Init(void);//led初始化函数
void Led_flash(void);//LED闪烁函数
#endif
stm32f4xx_it.c
/**
******************************************************************************
* @file Project/STM32F4xx_StdPeriph_Templates/stm32f4xx_it.c
* @author MCD Application Team
* @version V1.4.0
* @date 04-August-2014
* @brief Main Interrupt Service Routines.
* This file provides template for all exceptions handler and
* peripherals interrupt service routine.
******************************************************************************
* @attention
*
* <h2><center>© COPYRIGHT 2014 STMicroelectronics</center></h2>
*
* Licensed under MCD-ST Liberty SW License Agreement V2, (the "License");
* You may not use this file except in compliance with the License.
* You may obtain a copy of the License at:
*
* http://www.st.com/software_license_agreement_liberty_v2
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
******************************************************************************
*/
/* Includes ------------------------------------------------------------------*/
#include "stm32f4xx_it.h"
#include "led.h"
#include "delay.h"
#include "key.h"
//中断服务函数
void EXTI0_IRQHandler(void)
{
delay_ms(10);
if(WK_UP ==1)
Led_flash();//中断0调用闪灯函数
EXTI_ClearITPendingBit(EXTI_Line0);
}
//中断服务函数
void EXTI9_5_IRQHandler(void)
{
delay_ms(10);
if(KEY0 == 0)
{
LED1=!LED1;
LED2=0;
delay_ms(200);
EXTI_ClearITPendingBit(EXTI_Line9);}
if(KEY1==0)
{ LED2=!LED2;
delay_ms(200);
EXTI_ClearITPendingBit(EXTI_Line8);}
}
/** @addtogroup Template_Project
* @{
*/
/* Private typedef -----------------------------------------------------------*/
/* Private define ------------------------------------------------------------*/
/* Private macro -------------------------------------------------------------*/
/* Private variables ---------------------------------------------------------*/
/* Private function prototypes -----------------------------------------------*/
/* Private functions ---------------------------------------------------------*/
/******************************************************************************/
/* Cortex-M4 Processor Exceptions Handlers */
/******************************************************************************/
/**
* @brief This function handles NMI exception.
* @param None
* @retval None
*/
void NMI_Handler(void)
{
}
/**
* @brief This function handles Hard Fault exception.
* @param None
* @retval None
*/
void HardFault_Handler(void)
{
/* Go to infinite loop when Hard Fault exception occurs */
while (1)
{
}
}
/**
* @brief This function handles Memory Manage exception.
* @param None
* @retval None
*/
void MemManage_Handler(void)
{
/* Go to infinite loop when Memory Manage exception occurs */
while (1)
{
}
}
/**
* @brief This function handles Bus Fault exception.
* @param None
* @retval None
*/
void BusFault_Handler(void)
{
/* Go to infinite loop when Bus Fault exception occurs */
while (1)
{
}
}
/**
* @brief This function handles Usage Fault exception.
* @param None
* @retval None
*/
void UsageFault_Handler(void)
{
/* Go to infinite loop when Usage Fault exception occurs */
while (1)
{
}
}
/**
* @brief This function handles SVCall exception.
* @param None
* @retval None
*/
void SVC_Handler(void)
{
}
/**
* @brief This function handles Debug Monitor exception.
* @param None
* @retval None
*/
void DebugMon_Handler(void)
{
}
/**
* @brief This function handles PendSVC exception.
* @param None
* @retval None
*/
void PendSV_Handler(void)
{
}
/**
* @brief This function handles SysTick Handler.
* @param None
* @retval None
*/
void SysTick_Handler(void)
{
}
/******************************************************************************/
/* STM32F4xx Peripherals Interrupt Handlers */
/* Add here the Interrupt Handler for the used peripheral(s) (PPP), for the */
/* available peripheral interrupt handler's name please refer to the startup */
/* file (startup_stm32f4xx.s). */
/******************************************************************************/
/**
* @brief This function handles PPP interrupt request.
* @param None
* @retval None
*/
/*void PPP_IRQHandler(void)
{
}*/
/**
* @}
*/
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
stm32f4xx_it.h
在/**
******************************************************************************
* @file Project/STM32F4xx_StdPeriph_Templates/stm32f4xx_it.h
* @author MCD Application Team
* @version V1.4.0
* @date 04-August-2014
* @brief This file contains the headers of the interrupt handlers.
******************************************************************************
* @attention
*
* <h2><center>© COPYRIGHT 2014 STMicroelectronics</center></h2>
*
* Licensed under MCD-ST Liberty SW License Agreement V2, (the "License");
* You may not use this file except in compliance with the License.
* You may obtain a copy of the License at:
*
* http://www.st.com/software_license_agreement_liberty_v2
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
******************************************************************************
*/
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __STM32F4xx_IT_H
#define __STM32F4xx_IT_H
#ifdef __cplusplus
extern "C" {
#endif
/* Includes ------------------------------------------------------------------*/
#include "stm32f4xx.h"
/* Exported types ------------------------------------------------------------*/
/* Exported constants --------------------------------------------------------*/
/* Exported macro ------------------------------------------------------------*/
/* Exported functions ------------------------------------------------------- */
void NMI_Handler(void);
void HardFault_Handler(void);
void MemManage_Handler(void);
void BusFault_Handler(void);
void UsageFault_Handler(void);
void SVC_Handler(void);
void DebugMon_Handler(void);
void PendSV_Handler(void);
void SysTick_Handler(void);
void EXTI0_IRQHandler(void);//中断服务函数
void EXTI9_5_IRQHandler(void);//中断服务函数
#ifdef __cplusplus
}
#endif
#endif /* __STM32F4xx_IT_H */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
这里插入代码片
main.c
在这里插入代码片#include "stm32f4xx.h"
#include "key.h"
#include "delay.h"
#include "led.h"
#include "sys.h"
#include "stm32f4xx_it.h"
#if(0)
int main(void)
{
int key;
delay_init(168); //延时初始化
Led_Init();//led初始化函数
Led_flash();//LED闪烁函数
Key_Init();
while(1)
{
key= Check_key(0);
switch (key)
{
case 1: Led_flash(); break;//LED闪烁函数
case 2: GPIO_ResetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);break;//GPIOF9,F10设置高,灯灭
case 3: GPIO_SetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);break;//GPIOF9,F10设置高,灯灭
default:;break;
}
}
return 0;
}
#endif
void main(void)
{
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_0);//设置系统中断优先级分组2
delay_init(168); //延时初始化
Exit_Key_config();//中断初始化
Led_Init();//led初始化函数
Led_flash();//LED闪烁函数
while(1)
GPIO_SetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);
}