姓名:周崇杰? ?學(xué)號(hào):16140120059? ? 專業(yè):機(jī)械設(shè)計(jì)制造及其自動(dòng)化
轉(zhuǎn)載自:http://blog.csdn.net/wuyuzun/article/details/72851940,有刪節(jié)
【嵌牛導(dǎo)讀】:?jiǎn)纹瑱C(jī)最重要處理外界情況的手段莫過(guò)于中斷了,本文總計(jì)了STM32單片機(jī)的中斷基本概念以及使用。
【嵌牛鼻子】:STM32單片機(jī),中斷侨把,NVIC。
【嵌牛提問(wèn)】:STM32單片機(jī)如何產(chǎn)生設(shè)定一個(gè)特定的中斷呢?
【嵌牛正文】:
前言:
1.要想學(xué)習(xí)STM32中斷看疗,要先掌握STM32對(duì)優(yōu)先級(jí)的定義;
2.有51單片機(jī)開(kāi)發(fā)經(jīng)驗(yàn)會(huì)比較容易理解中斷優(yōu)先級(jí)睦授;
3.本篇博文基于STM32F103ZET6芯片和3.5.0標(biāo)準(zhǔn)庫(kù)編寫两芳;
4.本篇博文從寄存器入手,最終實(shí)現(xiàn)編程的步驟去枷;如有不足之處怖辆,還請(qǐng)前輩多多指教是复;
一 基礎(chǔ)知識(shí)
1. cortex-m3支持256個(gè)中斷,其中包含了16個(gè)內(nèi)核中斷竖螃,240個(gè)外部中斷淑廊。(本博文只介紹60個(gè)外部可屏蔽中斷)
2. stm32只有84個(gè)中斷,包括16個(gè)內(nèi)核中斷和68個(gè)可屏蔽中斷
3. stm32f103上只有60個(gè)可屏蔽中斷斑鼻,f107上才有68個(gè)中斷
4.先占優(yōu)先級(jí)也就是搶占優(yōu)先級(jí)蒋纬,概念等同于51單片機(jī)中的中斷。假設(shè)有兩中斷先后觸發(fā)坚弱,已經(jīng)在執(zhí)行的中斷先占優(yōu)先級(jí)如果沒(méi)有后觸發(fā)的中斷 先占優(yōu)先級(jí)更高蜀备,就會(huì)先處理先占優(yōu)先級(jí)高的中斷。也就是說(shuō)又有較高的先占優(yōu)先級(jí)的中斷可以打斷先占優(yōu)先級(jí)較低的中斷荒叶。這是實(shí)現(xiàn)中斷嵌套的基礎(chǔ)碾阁。
次占優(yōu)先級(jí),也就是響應(yīng)優(yōu)先級(jí)些楣,只在同一先占優(yōu)先級(jí)的中斷同時(shí)觸發(fā)時(shí)起作用脂凶,先占優(yōu)先級(jí)相同,則優(yōu)先執(zhí)行次占優(yōu)先級(jí)較高的中斷愁茁。次占優(yōu)先級(jí)不會(huì)造成中斷嵌套蚕钦。 如果中斷的兩個(gè)優(yōu)先級(jí)都一致,則優(yōu)先執(zhí)行位于中斷向量表中位置較高的中斷鹅很。
NVIC是什么嘶居?
嵌套向量中斷控制器;用于為中斷分組促煮,從而分配搶占優(yōu)先級(jí)和響應(yīng)優(yōu)先級(jí)邮屁;
分組的方式有兩種:
(1)Cortex-m3內(nèi)核提供了一種3位寬度的PRIGROUP數(shù)據(jù)區(qū),用于指示一個(gè)8位數(shù)據(jù)序列中的小數(shù)點(diǎn)的位置菠齿,從而表示中斷優(yōu)先級(jí)的分組佑吝。見(jiàn)下表:
(2)而實(shí)際上STM32并沒(méi)有用到這么多中斷,所以在分組上只分了5個(gè)組绳匀,并且表示方法有所不同芋忿;見(jiàn)下表:
我們?cè)趹?yīng)用當(dāng)中只會(huì)用到STM32的分組(5組)方式,所以下面著重于5組分組方式疾棵;
二 中斷向量表 (STM32F10x系列)
(圖片來(lái)自STM32使用手冊(cè)盗飒,只需看,不需要熟記陋桂,知道大概這么多中斷就好)
三 配置中斷相關(guān)寄存器
/*
cortex-m3內(nèi)核分組方式(8組)結(jié)構(gòu)體表達(dá)方式:
*/
typedef struct
{
__IO uint32_t ISER[8];? ? ? ? ? 中斷使能設(shè)置寄存器/*!< 偏移量: 0x000? Interrupt Set Enable Register*/
uint32_t RESERVED0[24];
__IO uint32_t ICER[8];? ? ? ? ? ?中斷清除使能寄存器/*!<偏移量: 0x080? Interrupt Clear Enable Register */
uint32_t RSERVED1[24];
__IO uint32_t ISPR[8];? ? ? ? ? ? 中斷掛起設(shè)置寄存器/*!< 偏移量: 0x100? Interrupt Set Pending Register */
uint32_t RESERVED2[24];
__IO uint32_t ICPR[8];? ? ? ? ? ? 中斷清除掛起寄存器/*!<偏移量: 0x180? Interrupt Clear Pending Register */
uint32_t RESERVED3[24];
__IO uint32_t IABR[8];? ? ? ? ? ? ?中斷激活狀態(tài)位寄存器/*!< 偏移量: 0x200? Interrupt Active bit Register*/
uint32_t RESERVED4[56];
__IO uint8_t? IP[240];? ? ? ? ? ? 中斷優(yōu)先級(jí)寄存器/*!< 偏移量: 0x300? Interrupt Priority Register (8Bit wide)*/
uint32_t RESERVED5[644];? ? ? ? 軟件觸發(fā)方式寄存器
__O? uint32_t STIR;? ? ? ? ? ? ? ? ? ? ? ? ?/*!< 偏移量: 0xE00? Software Trigger Interrupt Register? ? */
}? NVIC_Type;
/*
STM32分組(5組)方式結(jié)構(gòu)體表達(dá)方式
typedef struct
{
vu32 ISER[2];
u32? RESERVED0[30];
vu32 ICER[2];
u32? RSERVED1[30];
vu32 ISPR[2];
u32? RESERVED2[30];
vu32 ICPR[2];
u32? RESERVED3[30];
vu32 IABR[2];
u32? RESERVED4[62];
vu32 IPR[15];
} NVIC_TypeDef;
*/
以上寄存器介紹:
對(duì)一些概念的解釋:
1. 掛起:當(dāng)置位中斷掛起寄存器的時(shí)候逆趣,相應(yīng)的中斷將會(huì)被掛起,這是這個(gè)中斷將不會(huì)立即執(zhí)行嗜历,而是等待可執(zhí)行的時(shí)候再執(zhí)行宣渗;比如高低級(jí)別的中斷同時(shí)產(chǎn)生抖所,就先掛起低級(jí)別的中斷,等高級(jí)別的中斷執(zhí)行完畢痕囱,解除并執(zhí)行低級(jí)中斷田轧;
2. 對(duì)中斷優(yōu)先級(jí)控制寄存器的解釋
推薦去觀看一位前輩的博客:
http://blog.csdn.net/DLUTXIE/article/details/7059184?locationNum=4&fps=1
四 編程步驟
(1)選擇優(yōu)先級(jí)分組
/*
1. 此函數(shù)在庫(kù)文件misc.h文件下;
2. 參數(shù)可參照下面圖片:
3. 功能:選擇分組方式鞍恢;
*/
void NVIC_PriorityGroupConfig(uint32_t NVIC_PriorityGroup);
栗子:NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
//搶占優(yōu)先級(jí)可選0~3傻粘,響應(yīng)優(yōu)先級(jí)可選0~3;
(2)選擇帮掉,配置弦悉,并使能中斷
NVIC_InitStructure.NVIC_IRQChannel = EXTI2_IRQn; //選擇EXTI2中斷
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x02; //搶占優(yōu)先級(jí)為2
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02; //響應(yīng)優(yōu)先級(jí)為2
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能EXTI2中斷;
NVIC_Init(&NVIC_InitStructure); //初始化以上參數(shù)蟆炊;
(3)寫出相應(yīng)中斷函數(shù)
栗子:
void EXTI2_IRQHandler(void)
{
//邏輯代碼稽莉;
EXTI_ClearITPendingBit(EXTI_Line2);
}