您的位置:首页 > 其它

STM32F103mini教程学习总结与心得(三)---->中断

2017-07-26 23:06 351 查看
1. NVIC中断优先级分组

(1)CM3内核支持256个中断,其中包含了16个内核中断和240个外部中断,并且具有256级的可编程中断设置。

(2)STM32并没有使用CM3内核的全部东西,而是只用了它的一部分。

(3)STM32有84个中断,包括16个内核中断和68个可屏蔽中断,具有16级可编程的中断优先级。

(4)STM32F103系列上面,又只有60个可屏蔽中断(在107系列才有68个)

2.中断管理方法:对STM32中断进行分组,组0~4。对每个中断设置一个抢占优先级和一个响应优先级值。

3.抢占优先级 & 响应优先级区别(数字越小,优先级越高):

(1)高优先级的抢占优先级是可以打断正在进行的低抢占优先级中断的。

(2)抢占优先级相同的中断,高响应优先级不可以打断低响应优先级的中断。

(3)抢占优先级相同的中断,当两个中断同时发生的情况下,哪个响应优先级高,哪个先执行。

(4)如果两个中断的抢占优先级和响应优先级都是一样的话,则看哪个中断先发生就先执行;

4.特别说明:一般情况,系统代码执行过程中,只设置一次中断优先级分组,设置好分组之后一般不会再改变分组。

5.中断优先级分组函数【在misc.c+core_m3.h文件中有说明】: void NVIC_PriorityGroupConfig(uint32_t NVIC_PriorityGroup);

6.中断设置相关寄存器 :

__IO uint8_t IP[240]; //中断优先级控制的寄存器组---->Interrupt Priority Registers

=================================>>>STM32F10x系列一共60个可屏蔽中断,使用IP[59]~IP[0]

__IO uint32_t ISER[8]; //中断使能寄存器组----->32位寄存器,ISER[0]的bit0~bit31分别对应中断0~31。ISER[1]的bit0~27对应中断32~59

__IO uint32_t ICER[8]; //中断失能寄存器组----->用来失能中断

__IO uint32_t ISPR[8]; //中断挂起寄存器组----->用来挂起中断

__IO uint32_t ICPR[8]; //中断解挂寄存器组----->用来解挂中断

__IO uint32_t IABR[8]; //中断激活标志位寄存器组----->如果对应位为1,说明该中断正在执行。

static __INLINE void NVIC_SetPendingIRQ(IRQn_Type IRQn);

static __INLINE uint32_t NVIC_GetPendingIRQ(IRQn_Type IRQn);

static __INLINE void NVIC_ClearPendingIRQ(IRQn_Type IRQn)

static __INLINE uint32_t NVIC_GetActive(IRQn_Type IRQn)

7.中断参数初始化函数

void NVIC_Init(NVIC_InitTypeDef* NVIC_InitStruct);

typedef struct

{

uint8_t NVIC_IRQChannel; //设置中断通道

uint8_t NVIC_IRQChannelPreemptionPriority;//设置响应优先级

uint8_t NVIC_IRQChannelSubPriority; //设置抢占优先级

FunctionalState NVIC_IRQChannelCmd; //使能/使能

} NVIC_InitTypeDef;

例:

NVIC_InitTypeDef NVIC_InitStructure;

NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;//串口1中断

NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=1 ;// 抢占优先级为1

NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2;// 子优先级位2

NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;//IRQ通道使能

NVIC_Init(&NVIC_InitStructure); //根据上面指定的参数初始化NVIC寄存器

8.中断优先级设置步骤

①系统运行后先设置中断优先级分组。调用函数:

void NVIC_PriorityGroupConfig(uint32_t NVIC_PriorityGroup);

整个系统执行过程中,只设置一次中断分组。

②针对每个中断,设置对应的抢占优先级和响应优先级:

void NVIC_Init(NVIC_InitTypeDef* NVIC_InitStruct);

③ 如果需要挂起/解挂,查看中断当前激活状态,分别调用相关函数即可。

9.中断实验步骤

(1)STM32的每个IO都可以作为外部中断输入。

(2)STM32的中断控制器支持19个外部中断/事件请求:
线0~15:对应外部IO口的输入中断。
线16:连接到PVD输出。
线17:连接到RTC闹钟事件。
线18:连接到USB唤醒事件。

(3)每个外部中断线可以独立的配置触发方式(上升沿,下降沿或者双边沿触发),触发/屏蔽,专用的状态位。

(4)STM32供IO使用的中断线只有16个,但是STM32F10x系列的IO口多达上百个,STM32F103ZET6(112),STM32F103RCT6(51)

(5)外部中断通用IO映射:GPIOx.0映射到EXTI0
[在AFIO_EXTICR1寄存器配置]GPIOx.1映射到EXTI1

     GPIOx.15映射到EXTI15

注意:同一时间,同一中断线上,只能有一个IO映射到该中断线上。例如,GPIOA.0接到了EXTI0上的时候,   GPIOB.0就不能接入EXTI0。

(6)对于每个中断线,可以设置相应的触发方式(上升
4000
沿触发,下降沿触发,边沿触发)以及使能。

(7)对于STM32F1,有16个中断线,但只有7个中断服务函数------->>IO口外部中断在中断向量表中只分配了7个中断向量,也就是只能使用7个中断服务函数======>①外部中断线0-4分配5个中断向量,均有各自的服务函数②外部中断线5~9分配一个中断向量,共用一个服务函数③外部中断线10~15分配一个中断向量,共用一个中断服务函数。

说明:开启了线5和线6的中断,那么只要中断触发,那么5-9中断服务函数就会被调用。

(8)中断服务函数列表:EXTI0_IRQHandler
 EXTI1_IRQHandler
 EXTI2_IRQHandler
 EXTI3_IRQHandler
 EXTI4_IRQHandler
 EXTI9_5_IRQHandler
 EXTI15_10_IRQHandler 

(9)外部中断常用库函数:

①void GPIO_EXTILineConfig(uint8_t GPIO_PortSource, uint8_t GPIO_PinSource);

//设置IO口与中断线的映射关系

exp: GPIO_EXTILineConfig(GPIO_PortSourceGPIOE,GPIO_PinSource2);

②void EXTI_Init(EXTI_InitTypeDef* EXTI_InitStruct);

//初始化中断线:触发方式等

③ITStatus EXTI_GetITStatus(uint32_t EXTI_Line);

//判断中断线中断状态,是否发生

④void EXTI_ClearITPendingBit(uint32_t EXTI_Line);------->>手动清零

//清除中断线上的中断标志位

⑤EXTI_Init函数:void EXTI_Init(EXTI_InitTypeDef* EXTI_InitStruct);

typedef struct

{

uint32_t EXTI_Line; //指定要配置的中断线

EXTIMode_TypeDef EXTI_Mode; //模式:事件 OR中断

EXTITrigger_TypeDef EXTI_Trigger;//触发方式:上升沿/下降沿/双沿触发

FunctionalState EXTI_LineCmd; //使能 OR失能

}EXTI_InitTypeDef;

例:

EXTI_InitStructure.EXTI_Line=EXTI_Line2;

EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;

EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling;

EXTI_InitStructure.EXTI_LineCmd = ENABLE;

EXTI_Init(&EXTI_InitStructure);

(10)外部中断的一般配置步骤:

①初始化IO口为输入。

GPIO_Init();

② 开启IO口复用时钟。

RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE);----->重要

设置IO口与中断线的映射关系。

void GPIO_EXTILineConfig();

初始化线上中断,设置触发条件等。

EXTI_Init();

配置中断分组(NVIC),并使能中断。

NVIC_Init();

⑥ 编写中断服务函数。

EXTIx_IRQHandler();

清除中断标志位

EXTI_ClearITPendingBit();

EXIT.c文件内容

#include "exit.h"
#include "key.h"
#include "LED.h"
#include "delay.h"
#include "usart.h"
#include "stm32f10x.h"

void EXIT_init(void)
{
EXTI_InitTypeDef EXTI_InitStruct;
NVIC_InitTypeDef NVIC_InitStruct;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE);

//设置IO口与中断线的映射关系
GPIO_EXTILineConfig(GPIO_PortSourceGPIOC,GPIO_PinSource5);//PC5

GPIO_EXTILineConfig(GPIO_PortSourceGPIOA,GPIO_PinSource15);//PA15

//初始化线上中断,设置触发条件等
//PC5--KEY0
EXTI_InitStruct.EXTI_Line = EXTI_Line5;
EXTI_InitStruct.EXTI_LineCmd = ENABLE;
EXTI_InitStruct.EXTI_Mode = EXTI_Mode_Interrupt;//外部中断触发
EXTI_InitStruct.EXTI_Trigger = EXTI_Trigger_Falling;
EXTI_Init(&EXTI_InitStruct);

//PA15--KEY1
EXTI_InitStruct.EXTI_Line = EXTI_Line15;
EXTI_InitStruct.EXTI_LineCmd = ENABLE;
EXTI_InitStruct.EXTI_Mode = EXTI_Mode_Interrupt;//外部中断触发
EXTI_InitStruct.EXTI_Trigger = EXTI_Trigger_Falling;
EXTI_Init(&EXTI_InitStruct);

//配置中断分组(NVIC),并使能中断
//PC5
NVIC_InitStruct.NVIC_IRQChannel = EXTI9_5_IRQn;
NVIC_InitStruct.NVIC_IRQChannelCmd = ENABLE;
NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority = 2;
NVIC_InitStruct.NVIC_IRQChannelSubPriority = 2;
NVIC_Init(&NVIC_InitStruct);

//PA15
NVIC_InitStruct.NVIC_IRQChannel = EXTI15_10_IRQn;
NVIC_InitStruct.NVIC_IRQChannelCmd = ENABLE;
NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority = 1;
NVIC_InitStruct.NVIC_IRQChannelSubPriority = 1;
NVIC_Init(&NVIC_InitStruct);

}

//PC5中断服务函数
void EXTI9_5_IRQHandler(void)
{
delay_ms(20);
if(KEY0 == 0)//按下key0,就切换led状态
{
LED0 = ~LED0;
LED1 = ~LED1;
printf("\r\n press Key0 change the led! \r\n");
}
EXTI_ClearITPendingBit(EXTI_Line5);
}

//PA15中断服务函数
void EXTI15_10_IRQHandler(void)
{
delay_ms(20);
if(KEY1 == 0)//按下key1,就切换led0的状态
{
LED0 = ~LED0;
//LED1 = ~LED1;
printf("\r\n press key1 change the led! \r\n");
}
EXTI_ClearITPendingBit(EXTI_Line15);
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  f1 stm32 中断