STM32第十节(中级篇):EXTI(第一节)——EXTI功能框图及初始化结构体讲解(包括STM32中断应用总结)

目录

前言

STM32第十节(中级篇):EXTI(第一节)——EXTI功能框图及初始化结构体讲解(包括STM32中断应用总结)

EXTI功能框图

EXTI初始化结构体讲解

STM32中断应用总结

NVIC介绍

优先级

优先级的定义

优先级分组

中断编程的顺序

小结


前言

        在STM32的中级教程中,第十节涉及到外部中断(EXTI)的功能框图以及初始化结构体的讲解。在本节课中,我们将深入探讨外部中断的初始化结构体,这是配置外部中断功能所必需的步骤。了解如何正确地初始化外部中断结构体可以帮助开发人员充分利用STM32的中断功能,并实现更加灵活和高效的中断应用。除了讲解外部中断的功能框图和初始化结构体外,本节课还将对STM32中断应用进行总结。中断是一种在嵌入式系统中常用的技术,能够提高系统的响应速度和效率。通过总结STM32中断应用,我们可以更好地掌握中断的使用方法,从而更好地应用于实际项目中。


STM32第十节(中级篇):EXTI(第一节)——EXTI功能框图及初始化结构体讲解(包括STM32中断应用总结)

EXTI功能框图

EXTI初始化结构体讲解

        EXTI InitTypeDef

        1-EXTI Line:用于产生 中断/事件 线

/** @defgroup EXTI_Exported_Constants
  * @{
  */

/** @defgroup EXTI_Lines 
  * @{
  */

#define EXTI_Line0       ((uint32_t)0x00001)  /*!< External interrupt line 0 */
#define EXTI_Line1       ((uint32_t)0x00002)  /*!< External interrupt line 1 */
#define EXTI_Line2       ((uint32_t)0x00004)  /*!< External interrupt line 2 */
#define EXTI_Line3       ((uint32_t)0x00008)  /*!< External interrupt line 3 */
#define EXTI_Line4       ((uint32_t)0x00010)  /*!< External interrupt line 4 */
#define EXTI_Line5       ((uint32_t)0x00020)  /*!< External interrupt line 5 */
#define EXTI_Line6       ((uint32_t)0x00040)  /*!< External interrupt line 6 */
#define EXTI_Line7       ((uint32_t)0x00080)  /*!< External interrupt line 7 */
#define EXTI_Line8       ((uint32_t)0x00100)  /*!< External interrupt line 8 */
#define EXTI_Line9       ((uint32_t)0x00200)  /*!< External interrupt line 9 */
#define EXTI_Line10      ((uint32_t)0x00400)  /*!< External interrupt line 10 */
#define EXTI_Line11      ((uint32_t)0x00800)  /*!< External interrupt line 11 */
#define EXTI_Line12      ((uint32_t)0x01000)  /*!< External interrupt line 12 */
#define EXTI_Line13      ((uint32_t)0x02000)  /*!< External interrupt line 13 */
#define EXTI_Line14      ((uint32_t)0x04000)  /*!< External interrupt line 14 */
#define EXTI_Line15      ((uint32_t)0x08000)  /*!< External interrupt line 15 */
#define EXTI_Line16      ((uint32_t)0x10000)  /*!< External interrupt line 16 Connected to the PVD Output */
#define EXTI_Line17      ((uint32_t)0x20000)  /*!< External interrupt line 17 Connected to the RTC Alarm event */
#define EXTI_Line18      ((uint32_t)0x40000)  /*!< External interrupt line 18 Connected to the USB Device/USB OTG FS
                                                   Wakeup from suspend event */                                    
#define EXTI_Line19      ((uint32_t)0x80000)  /*!< External interrupt line 19 Connected to the Ethernet Wakeup event */
                                          
#define IS_EXTI_LINE(LINE) ((((LINE) & (uint32_t)0xFFF00000) == 0x00) && ((LINE) != (uint16_t)0x00))
#define IS_GET_EXTI_LINE(LINE) (((LINE) == EXTI_Line0) || ((LINE) == EXTI_Line1) || \
                            ((LINE) == EXTI_Line2) || ((LINE) == EXTI_Line3) || \
                            ((LINE) == EXTI_Line4) || ((LINE) == EXTI_Line5) || \
                            ((LINE) == EXTI_Line6) || ((LINE) == EXTI_Line7) || \
                            ((LINE) == EXTI_Line8) || ((LINE) == EXTI_Line9) || \
                            ((LINE) == EXTI_Line10) || ((LINE) == EXTI_Line11) || \
                            ((LINE) == EXTI_Line12) || ((LINE) == EXTI_Line13) || \
                            ((LINE) == EXTI_Line14) || ((LINE) == EXTI_Line15) || \
                            ((LINE) == EXTI_Line16) || ((LINE) == EXTI_Line17) || \
                            ((LINE) == EXTI_Line18) || ((LINE) == EXTI_Line19))

        2-EXTI Mode:EXTI模式(中断/事件)

/** 
  * @brief  EXTI mode enumeration  
  */

typedef enum
{
  EXTI_Mode_Interrupt = 0x00,
  EXTI_Mode_Event = 0x04
}EXTIMode_TypeDef;

#define IS_EXTI_MODE(MODE) (((MODE) == EXTI_Mode_Interrupt) || ((MODE) == EXTI_Mode_Event))

        3-EXTI Trigger:触发(上/下/上下)

/** 
  * @brief  EXTI Trigger enumeration  
  */

typedef enum
{
  EXTI_Trigger_Rising = 0x08,
  EXTI_Trigger_Falling = 0x0C,  
  EXTI_Trigger_Rising_Falling = 0x10
}EXTITrigger_TypeDef;

#define IS_EXTI_TRIGGER(TRIGGER) (((TRIGGER) == EXTI_Trigger_Rising) || \
                                  ((TRIGGER) == EXTI_Trigger_Falling) || \
                                  ((TRIGGER) == EXTI_Trigger_Rising_Falling))

        4-EXTI LineCmd:使能或者失能(IMR/EMR)

        以下代码为初始化代码,作用为EXTI初始化。我们可以发现里面有四个成员,先配置EXTI_LINE(0~19),从功能框图上看,我们要配置AFIO寄存器,所以他是位操作,决定我们编程某个位。

/** 
  * @brief  EXTI Init Structure definition  
  */

typedef struct
{
  uint32_t EXTI_Line;               /*!< Specifies the EXTI lines to be enabled or disabled.
                                         This parameter can be any combination of @ref EXTI_Lines */
   
  EXTIMode_TypeDef EXTI_Mode;       /*!< Specifies the mode for the EXTI lines.
                                         This parameter can be a value of @ref EXTIMode_TypeDef */

  EXTITrigger_TypeDef EXTI_Trigger; /*!< Specifies the trigger signal active edge for the EXTI lines.
                                         This parameter can be a value of @ref EXTIMode_TypeDef */

  FunctionalState EXTI_LineCmd;     /*!< Specifies the new state of the selected EXTI lines.
                                         This parameter can be set either to ENABLE or DISABLE */ 
}EXTI_InitTypeDef;

STM32中断应用总结

        在下方就是F103系列内外部中断清单:

         顾名思义,中断就是在执行主程序的中途给到一个或多个中断,程序先跳出主程序,优先执行高一级的中断函数。如果有更高级别的中断中断了该中断,那么系统就会优先执行更高级别的中断从而停止低一级别的终端,优先进行高级别的中断,再返回原先中断,再返回主函数执行原有程序。(简单来说就是套娃)

NVIC介绍

        在正式讲解中断优先级之前,我们先来了解一下NVIC。NVIC 是嵌套向量中断控制器,控制着整个芯片中断相关的功能,NVIC寄存器里有许多位可以扩展功能。在配置中断的时候我们一般只用 ISER、ICER 和 IP 这三个寄存器,ISER 用来使能中断,ICER 用来失能中断,IP 用来设置中断优先级。

/** @addtogroup CMSIS_CM3_NVIC CMSIS CM3 NVIC
  memory mapped structure for Nested Vectored Interrupt Controller (NVIC)
  @{
 */
typedef struct
{
  __IO uint32_t ISER[8];                      /*!< Offset: 0x000  Interrupt Set Enable Register           */
       uint32_t RESERVED0[24];                                   
  __IO uint32_t ICER[8];                      /*!< Offset: 0x080  Interrupt Clear Enable Register         */
       uint32_t RSERVED1[24];                                    
  __IO uint32_t ISPR[8];                      /*!< Offset: 0x100  Interrupt Set Pending Register          */
       uint32_t RESERVED2[24];                                   
  __IO uint32_t ICPR[8];                      /*!< Offset: 0x180  Interrupt Clear Pending Register        */
       uint32_t RESERVED3[24];                                   
  __IO uint32_t IABR[8];                      /*!< Offset: 0x200  Interrupt Active bit Register           */
       uint32_t RESERVED4[56];                                   
  __IO uint8_t  IP[240];                      /*!< Offset: 0x300  Interrupt Priority Register (8Bit wide) */
       uint32_t RESERVED5[644];                                  
  __O  uint32_t STIR;                         /*!< Offset: 0xE00  Software Trigger Interrupt Register     */
}  NVIC_Type;                                               
/*@}*/ /* end of group CMSIS_CM3_NVIC */

        以上就是中断—1 NVIC 结构体定义(来自固件库头文件 core_cm3.h)。

优先级

优先级的定义

        在 NVIC 有一个专门的寄存器:中断优先级寄存器 NVIC_IPRx,这个寄存器是用来配置外部中断的优先级,IPR的宽度为 8bit。但是绝大多数 CM3 芯片都会精简设计,以致实际上支持的优先级数减少,在 F103 中,只使用了高 4bit。

        用于表达优先级的这 4bit,又被分组成抢占优先级和子优先级。如果有多个中断同时响应,抢占优先级高的就会抢占抢占优先级低的优先得到执行,如果抢占优先级相同,就比较子优先级。如果抢占优先级和子优先级都相同的话,就比较他们的硬件中断编号,编号越小,优先级越高。

优先级分组

        而在这些优先级分组中,我们要靠SCB_AIRCR寄存器进行判断优先级分组。

中断编程的顺序

        1.使能中断请求

        2.配置中断优先级分组

        3.配置NVIC寄存器,初始化NVIC InitTypeDef

        4.编写中断服务函数

小结

        那么我们EXTI初始化结构体就讲到这里,下节课我们讲GPIO外部中断讲解。

  • 19
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
STM32是一款非常强大的微控制器,其包含了大量的IO口和外设,能够广泛应用于各种嵌入式系统中。在实际应用中,我们通常会使用中断来响应外部事件,如按键、定时器等。本文将介绍STM32中断的顺序,包括初始化IO口、开启AFIO时钟、EXTI配置、NVIC配置以及编写中断服务函数等。 1. 初始化IO口 在使用STM32的IO口前,我们首先需要对其进行初始化。具体而言,需要配置GPIO端口模式、输出类型、速度、上下拉等参数。以PA0引脚为例,其初始化代码如下: ```c GPIO_InitTypeDef GPIO_InitStructure; //开启GPIOA时钟 RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); //配置PA0为浮空输入模式 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING; GPIO_Init(GPIOA, &GPIO_InitStructure); ``` 2. 开启AFIO时钟 AFIO(Alternate Function I/O)是STM32中一种特殊的I/O功能,可以将某些I/O口用于其它功能,如复用为定时器、串口等外设。在使用AFIO前,需要先开启其时钟。代码如下: ```c RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE); ``` 3. EXTI配置 EXTI(External Interrupt)是STM32中一种外部中断功能,可以用于响应外部事件,如按键、定时器等。在使用EXTI前,需要配置其相关参数,如GPIO端口、触发方式等。以PA0引脚为例,其EXTI配置代码如下: ```c EXTI_InitTypeDef EXTI_InitStructure; //选择GPIOA作为EXTI输入源 GPIO_EXTILineConfig(GPIO_PortSourceGPIOA, GPIO_PinSource0); //配置EXTI线路为中断模式 EXTI_InitStructure.EXTI_Line = EXTI_Line0; EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising_Falling; EXTI_InitStructure.EXTI_LineCmd = ENABLE; EXTI_Init(&EXTI_InitStructure); ``` 4. NVIC配置 NVIC(Nested Vectored Interrupt Controller)是STM32中一种中断控制器,可以对所有中断进行优先级管理和嵌套管理。在使用中断前,需要配置其中断优先级和使能NVIC。以PA0引脚为例,其NVIC配置代码如下: ```c NVIC_InitTypeDef NVIC_InitStructure; //配置EXTI0中断优先级为0 NVIC_InitStructure.NVIC_IRQChannel = EXTI0_IRQn; NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&NVIC_InitStructure); ``` 5. 编写中断服务函数 最后,我们需要编写中断服务函数来处理中断事件。以PA0引脚为例,其中断服务函数代码如下: ```c void EXTI0_IRQHandler(void) { if(EXTI_GetITStatus(EXTI_Line0) != RESET) { //中断处理代码 EXTI_ClearITPendingBit(EXTI_Line0); } } ``` 中断服务函数需要在NVIC中配置的中断号对应,如EXTI0_IRQn对应PA0引脚的中断号。在函数中,我们可以编写中断处理代码来响应中断事件,如读取按键状态、改变LED灯状态等。最后,需要调用EXTI_ClearITPendingBit函数清除中断标志位,以便下一次中断发生时能够再次触发中断服务函数。 综上所述,STM32中断的顺序包括初始化IO口、开启AFIO时钟、EXTI配置、NVIC配置以及编写中断服务函数等。通过以上步骤,我们可以有效地使用STM32中断功能,实现各种外部事件响应。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值