GD32的中断-外部中断的实现

电子说

1.2w人已加入

描述

处理器:GD32F103VET6

开发环境:MDK(keil 5) + STM32CubeMX

1.1 中断的作用

中断的主要作用就是允许一些紧急的任务“插队”,提前进行。比如,大家在排队做核酸检测,但是,现在来了一位男士,他说他有紧急情况,希望能够先做,在征得同意后,他先做了核酸,他做完了跑了,但大家仍然按照原来的顺序排队进行,这就是中断。

又如,你在玩游戏,但是一个重要电话进来了,你只得暂停当前的游戏,先接电话,接完电话继续玩。这也是中断。

在各种电子产品中,中断用得非常非常多,在我看来,它和GPIO、串口、定时器一起,是各种处理器学习的最重要的四个模块之一,我称之为“四大金刚”。

1.2 GD32的中断的执行及其优先级

对于GD32的中断,我们需要关注以下问题:

1.那些模块可以申请中断?绝大部分的模块,比如串口、定时器、SPI接口等都可以申请中断,这些可以申请中断的模块我们叫中断源。

2.某个模块申请中断,并获得系统同意后,系统将会做什么?中断申请并获得通过后,将会执行中断函数,中断函数执行完后又回到原来的地方继续执行。

GD32的各个模块的中断函数的函数名厂家已经帮我们取好了,在启动文件(.s文件)中,具体如图1所示。

GD32F103

图1 GD32的中断函数

3.如果有多个中断同时到来,处理器该怎么办呢?它会先去执行哪个中断的中断函数呢?通过每个中断的优先级才裁决先响应谁!优先级高的中断,它的中断函数将会获得优先执行。GD32的每个中断的优先级分为抢占式优先级和子优先级两部分,在实际应用中,一般我们都是只需要设置抢占式优先级即可,子优先级不用理会。抢占式优先级可以设置的值为0-15,值越小优先级越高,这点跟freertos操作系统的优先级刚好相反,freertos的是值越高优先级越高。

GD32的中断由一个叫NVIC的模块统一处理,NVIC全称叫嵌套中断向量控制器,抢占式优先级、子优先级、中断允许、中断失能都在它里面设置。

最后补充说明两点:

1.GD32的每一个模块都会有至少一个中断开关,只有这个开关处于使能状态,该模块的中断信号才能进入到NVIC内部。

2.中断函数中尽量不要有延时,如必须要延时,则延时要尽量小,要快进快出,不要影响后续的中断的响应!

1.3 GD32的外部中断

GD32F103VET6支持19个外部中断,注意,这里虽然用了外部两个字,但真正只有16来自于芯片的外部,有3个仍然是在芯片的内部。外部的16个中断分别为EXTI0~EXTI15,其中EXTI0可以从PA0、PB0、PC0等标号为0的引脚进入,EXTI1可以从PA1、PB1、PC1等标号为1引脚进入,其他外部中断同理。

在这16个从IO引脚进入的中断中,他们的中断函数分别为

●EXTI0-EXTI4都有自己独立的中断函数,他们的函数名分别为EXTI0_IRQHandler~ EXTI4_IRQHandler;

●外部中断5到9共用一个中断函数,函数名为EXTI9_5_IRQHandler;

●外部中断10到15共用一个中断函数,函数名为EXTI15_10_IRQHandler。

对于这些共用中断函数的外部中断,需要在中断函数的内部进一步判断是那个外部中断。

外部中断的触发方式可以有下降沿触发和上升沿触发,这个可以根据具体情况来选择。

1.4 外部中断应用示例

下面我们通过一个例子来学习外部中断的应用。

【例1】使用PE2外部的按键KEY0产生外部中断,每发生一次外部中断将LED0的状态反转一次。在整个过程中,LED1以1秒的频率闪烁。

【实现过程】

1.设置系统时钟源和系统时钟的频率为72MHz;

2.设置调试方式为Serial Wire;

3.设置与LED0相连的PE12,与LED1相连的PE13工作方式为输出;

4.设置与KEY0相连的PE2引脚的为外部中断引脚,抢占式优先级为3(由于系统滴答定时器的优先级为0,所以这个优先级比0低即可)。整个过程的步骤为:

(1)设置PE2的工作模式为外部中断,如图2所示。

GD32F103

图2 PE2引脚设置为外部中断示意图

(2)在GPIO中设置PE2的中断触发方式为下降沿触发(按键按下就触发),如图3所示。

GD32F103

图3 设置下降沿触发示意图

(3)设置外部中断2的抢占式优先级的值为3,实际上由于本工程中除了系统滴答定时器的中断,其他的中断都没有,所以这里设置不与滴答定时器的中断优先级相同即可(滴答定时器的中断优先级为0)。设置步骤和结果如图4所示。

GD32F103

图4 优先级设置示意图

注意,如果EXTI2的中断的优先级采用默认,也就是抢占式优先级为0,子优先级也为0,这两个优先级跟滴答定时器(System tick timer)的优先级一样,则可能在中断中使用延时函数HAL_Delay()时,有可能会使系统死机(延时函数HAL_Delay()通过tick 定时器的中断来工作,当进入EXTI2中断函数执行时,tick 定时器的中断得不到及时执行,所以会出现死机现象!)。

5.配置好中断后,接下来是配置工程名、工程存放路径等信息,然后点击生成代码,生成代码后,我们需要补充如下功能:

(1)在主函数的while循环中补充是的LED1闪烁的程序段,具体如图5所示。

GD32F103

图5 LED1闪烁程序段示意图

(2)编写中断服务回调函数,注意不是中断服务函数,该函数的内容如图6所示。

GD32F103

图6 EXTI2的中断回调(callback)函数

程序编写好后,编译程序并将程序下载到开发板中,可以看到LED1闪烁,LED0则是按下一次KEY0键LE0的状态反转一次,任务目标完成。

1.5 HAL库中中断函数的执行流程

在刚才的步骤中,有一步为编写中断服务回调函数,注意,为回调函数而不是中断服务函数,这跟我们前面的介绍是不是互相矛盾呢?我们通过观察CubeMX生成的工程的中断的执行流程来回答这个问题。这个流程如下:

①系统接收到EXTI2的中断请求并响应后,到.s文件中寻找到该中断函数的入口,如图7所示。

GD32F103

图7 外部中断EXTI2的中断服务函数的入口示意图

②由于函数的名字就是函数的入口,所以找到入口后,接下来执行函数EXTI2_IRQHandler,如图8所示。函数EXTI2_IRQHandler就是EXTI2的中断服务函数。

GD32F103

图8 中断服务函数EXTI2_IRQHandler的内容

③执行通用IO口外部中断函数HAL_GPIO_EXTI_IRQHandler(),这个函数是一个通用函数,其他的GPIO口的外部中断都调用这个函数,它的参数只有一个,就是中断的输入引脚标号,实际上就是外部中断线编号。函数HAL_GPIO_EXTI_IRQHandler的内容如图9所示。

GD32F103

图9 通用外部中断函数的内容示意图

由图9可以看到,在该函数中,在判断GPIO_Pin引脚对应的标志位为真后执行两个动作,分别是

●使用宏__HAL_GPIO_EXTI_CLEAR_IT(GPIO_Pin)来清除标志位,以便下一次的中断能够进来;

●调用中断回调函数HAL_GPIO_EXTI_Callback(),我们要实现的中断需要做的事情就在中断回调函数中实现,所以在前面的步骤中,我们编写的是中断回调函数的代码,而不是中断服务函数的代码,当然,大家也可以将代码内容直接写到中断服务函数中。

1.6 外部中断实验中涉及到的HAL库的函数/宏及其他相关知识

1.获取外部中断标志位和清除外部中断标志位

中断标志位被置1说明该中断获得了响应,获得响应后要在中断服务函数中清除该标志位,以使得下次该中断有中断申请到来时能获得响应。HAL库中,获取中断标志位和清除中断标志位分别用下面两个宏来完成。

●获取中断标志位:__HAL_GPIO_EXTI_GET_IT()

●清除中断标志位: __HAL_GPIO_EXTI_CLEAR_IT()

这两个宏都只有一个参数,就是外部中断输入引脚的编号。

注意,与HAL库中的函数不用,HAL库中宏名用两个下划线开始,其格式为

“__” + “HAL” + 模块名 + 执行动作名

2.外部中断回调函数HAL_GPIO_EXTI_Callback()

HAL库中回调函数使用Callback结尾,对于外部中断回调函数,它只有一个参数,这个参数就是外部中断的编号—也即外部中断输入IO引脚的标号。

3.HAL库初始化函数HAL_Init()

每次我们用STM32CubeMX生成工程时,主函数中的第一条语句就是执行函数HAL_Init()的内容,这个函数具体做什么呢?我们打开看一下,可以看到这个函数的内容如图10所示。

GD32F103

图10 HAL库初始化函数HAL_Init()的内容

由图可见,函数HAL_Init()主要所两个事,分别是:

①设置抢占式优先级的位数,这里是设置为4位,其值可以从015,所以抢占式优先级可以设置为015的任意数字。

②配置tick timer定时器,并设置它的优先级。

1.7 结论及注意事项

在本章的学习中,主要注意以下几点:

1.发生外部中断后,在系统提供的中断服务函数中已经清除了中断标志位,所以大家在编写中断回调函数的时候不需要再次清除中断标志位。

2.中断的优先级不要跟tick timer,也就是滴答定时器的中断优先级一样,否则在中断回调函数中使用HAL_Delay函数时会出现死机现象。

3.GD32/STM32的优先级是:优先级值越小的中断,它的中断优先级越高。

打开APP阅读更多精彩内容
声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉

全部0条评论

快来发表一下你的评论吧 !

×
20
完善资料,
赚取积分