• <li id="00i08"><input id="00i08"></input></li>
  • <sup id="00i08"><tbody id="00i08"></tbody></sup>
    <abbr id="00i08"></abbr>
  • 新聞中心

    EEPW首頁(yè) > 嵌入式系統(tǒng) > 設(shè)計(jì)應(yīng)用 > STM學(xué)習(xí)筆記--STM32F10X中斷

    STM學(xué)習(xí)筆記--STM32F10X中斷

    作者: 時(shí)間:2016-09-16 來(lái)源:網(wǎng)絡(luò) 收藏

      CM3支持256個(gè),16個(gè)內(nèi)核+240個(gè)外部,并具有256級(jí)可編程中斷

    本文引用地址:http://www.czjhyjcfj.com/article/201609/297022.htm

      STM32支持76個(gè)中斷,16個(gè)內(nèi)核中斷+60個(gè)外部中斷,16個(gè)可編程優(yōu)先級(jí)

      16個(gè)內(nèi)核中斷:每個(gè)中斷占用地址為0X0000_0004

      

     

      60個(gè)可屏蔽中斷:其中0,1,2,3,4表示中斷編號(hào)IRQ Channels在STM32F10x_lib.h程序中體現(xiàn)

      

     

      

     

      

     

      16個(gè)中斷優(yōu)先級(jí)

      先看看嵌套中斷向量控制器的定義_map.h

      /*------------------------ Nested Vectored Interrupt Controller --------------*/

      typedef struct

      {

      vu32 ISER[2]; //Interrupt set-enable registers 2個(gè)32BITS

      u32 RESERVED0[30];

      vu32 ICER[2]; //Interrupt clear-enable registers

      u32 RSERVED1[30];

      vu32 ISPR[2]; //Interrupt set-pending registers

      u32 RESERVED2[30];

      vu32 ICPR[2]; //Interrupt clear-pending registers

      u32 RESERVED3[30];

      vu32 IABR[2]; //Interrupt active bit registers 只讀寄存器

      u32 RESERVED4[62];

      vu32 IPR[15]; //Interrupt priority registers

      } NVIC_TypeDef;

      其中vu32 IPR[15],表示Interrupt Priority Registers中斷優(yōu)先級(jí)寄存器

      表示15個(gè)32bit寄存器,每個(gè)屏蔽中斷占用8位,只用到高4位,低4位沒(méi)用到。

      每個(gè)屏蔽寄存器擁有的中斷編號(hào)為4個(gè),即32bit/8bit=4

      IPR[0]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷3,2,1,0

      IPR[1]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷7,6,5,4

      IPR[2]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷11,10,9,8

      IPR[3]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷15,14,13,12

      IPR[4]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷19,18,17,16

      IPR[5]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷23,22,21,20

      IPR[6]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷27,26,25,24

      IPR[7]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷31,30,29,28

      IPR[8]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷35,34,33,32

      IPR[9]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷39,38,37,36

      IPR[10]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷43,42,41,40

      IPR[11]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷47,46,45,44

      IPR[12]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷51,50,49,48

      IPR[13]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷55,54,53,52

      IPR[14]—[31-24] [23-16] [15-8] [7-4] 對(duì)應(yīng)中斷59,58,57,56

      IPR[15]—[31-24] [23-16] [15-8] [7-4] 未使用

      STM32將中斷分為5組,組數(shù)為0-5。由控制器SCB->AIRCR【10:8】寄存器控制

      

     

      例如如果AIRCR為100,則60個(gè)中斷(15個(gè)中斷優(yōu)先級(jí)寄存器)的每個(gè)中斷的高3位為搶占優(yōu)先級(jí),低1位為響應(yīng)優(yōu)先級(jí)。那么搶占優(yōu)先級(jí)可以設(shè)置7個(gè),由000~111,而響應(yīng)優(yōu)先級(jí)只能為0或者1。數(shù)值越小,表示優(yōu)先級(jí)越高,同時(shí)搶占優(yōu)先級(jí)高于響應(yīng)優(yōu)先級(jí)。如果搶占優(yōu)先級(jí)與響應(yīng)優(yōu)先級(jí)一致,則看哪個(gè)中斷先發(fā)生,哪個(gè)先執(zhí)行;高優(yōu)先級(jí)的搶占優(yōu)先級(jí)可以打斷正在進(jìn)行的低搶占優(yōu)先級(jí)的,高響應(yīng)優(yōu)先級(jí)的不能打斷低響應(yīng)優(yōu)先級(jí)的中斷。

      AIRCR—應(yīng)用程序中斷及復(fù)位控制寄存器,它是屬于SCB中的一個(gè)。

      //System control space memory map

      typedef struct

      {

      vuc32 CPUID;

      vu32 ICSR;

      vu32 VTOR;

      vu32 AIRCR;

      vu32 SCR;

      vu32 CCR;

      vu32 SHPR[3];

      vu32 SHCSR;

      vu32 CFSR;

      vu32 HFSR;

      vu32 DFSR;

      vu32 MMFAR;

      vu32 BFAR;

      vu32 AFSR;

      } SCB_TypeDef;

      

     

      如需修改SCB->AIRCR寄存器的值,首先得寫(xiě)入訪問(wèn)鑰匙0X05FA,遵循讀—改—寫(xiě)的操作步驟。

      下面是設(shè)置NVIC分組函數(shù):

      //設(shè)置NVIC分組

      //NVIC_Group:NVIC分組 0~4 總共5組

      void MY_NVIC_PriorityGroupConfig(u8 NVIC_Group)

      {

      u32 temp,temp1;

      temp1=(~NVIC_Group)&0x07;//取后三位

      temp1<<=8;

      temp=SCB->AIRCR; //讀取先前的設(shè)置

      temp&=0X0000F8FF; //清空先前分組

      temp|=0X05FA0000; //寫(xiě)入鑰匙

      temp|=temp1;

      SCB->AIRCR=temp; //設(shè)置分組

      }

      當(dāng)NVIC_Group=0;~NVIC_Group=0X1111 1111&0X0000 0111 ,得temp1=0X0000 0111即第0組 ,0位搶占優(yōu)先級(jí),4位相應(yīng)優(yōu)先級(jí)

      當(dāng)NVIC_Group=1;~NVIC_Group=0X1111 1110&0X0000 0111 ,得temp1=0X0000 0110即第1組,1位搶占優(yōu)先級(jí),3位相應(yīng)優(yōu)先級(jí)

      當(dāng)NVIC_Group=2;~NVIC_Group=0X1111 1101&0X0000 0111 ,得temp1=0X0000 0101即第2組,2位搶占優(yōu)先級(jí),2位相應(yīng)優(yōu)先級(jí)

      當(dāng)NVIC_Group=3;~NVIC_Group=0X1111 1100&0X0000 0111 ,得temp1=0X0000 0100即第3組,3位搶占優(yōu)先級(jí),1位相應(yīng)優(yōu)先級(jí)

      當(dāng)NVIC_Group=4;~NVIC_Group=0X1111 1011&0X0000 0111 ,得temp1=0X0000 0011即第4組,4位搶占優(yōu)先級(jí),0位相應(yīng)優(yōu)先級(jí)

      temp1<<=8;從第8位開(kāi)始

      接著讀改寫(xiě)。先清空先前分組,temp&=0X0000F8FF; //清空先前分組,高16位為0,低16位BIT11-8,為1000。再寫(xiě)入鑰匙,0X05FA0000,再寫(xiě)入分組temp1,最后將temp1寫(xiě)入SCB->AIRCR寄存器。

      NVIC配置理解

      NVIC初始化函數(shù)

      //設(shè)置NVIC

      //NVIC_PreemptionPriority:搶占優(yōu)先級(jí)

      //NVIC_SubPriority :響應(yīng)優(yōu)先級(jí)

      //NVIC_Channel :中斷編號(hào)

      //NVIC_Group :中斷分組 0~4

      //注意優(yōu)先級(jí)不能超過(guò)設(shè)定的組的范圍!否則會(huì)有意想不到的錯(cuò)誤

      //組劃分:

      //組0:0位搶占優(yōu)先級(jí),4位響應(yīng)優(yōu)先級(jí)

      //組1:1位搶占優(yōu)先級(jí),3位響應(yīng)優(yōu)先級(jí)

      //組2:2位搶占優(yōu)先級(jí),2位響應(yīng)優(yōu)先級(jí)

      //組3:3位搶占優(yōu)先級(jí),1位響應(yīng)優(yōu)先級(jí)

      //組4:4位搶占優(yōu)先級(jí),0位響應(yīng)優(yōu)先級(jí)

      //NVIC_SubPriority和NVIC_PreemptionPriority的原則是,數(shù)值越小,越優(yōu)先

      void MY_NVIC_Init(u8 NVIC_PreemptionPriority,u8 NVIC_SubPriority,u8 NVIC_Channel,u8 NVIC_Group)

      {

      u32 temp;

      u8 IPRADDR=NVIC_Channel/4; //每組只能存4個(gè),得到組地址

      u8 IPROFFSET=NVIC_Channel%4;//在組內(nèi)的偏移

      IPROFFSET=IPROFFSET*8+4; //得到偏移的確切位置

      MY_NVIC_PriorityGroupConfig(NVIC_Group);//設(shè)置分組

      temp=NVIC_PreemptionPriority<<(4-NVIC_Group);

      temp|=NVIC_SubPriority&(0x0f>>NVIC_Group);

      temp&=0xf;//取低四位

      if(NVIC_Channel<32)

      {

      NVIC->ISER[0]|=1<

      }

      else

      {

      NVIC->ISER[1]|=1<<(NVIC_Channel-32);

      }

      NVIC->IPR[IPRADDR]|=temp<

      }

      (1)

      u8 IPRADDR=NVIC_Channel/4; //每組只能存4個(gè),得到組地址

      u8 IPROFFSET=NVIC_Channel%4; //在組內(nèi)的偏移

      IPROFFSET=IPROFFSET*8+4; //得到偏移的確切位置

      對(duì)于窗口 WWDG_IPQChanel 的中斷編號(hào)為0X00,那么

      IPRADDR=0X00/4=0; //得到第0組,IPR[0]

      IPROFFSET=0X00%4=0; //在組內(nèi)的偏移為0

      IPROFFSET=0X00*8+4=4; //*8的意思是一個(gè)字節(jié),就是跳過(guò)一個(gè)中斷;+4的意思是,低4位無(wú)效

      在IPR[IPRADDR]的中斷組中,左移IPROFFSET的位置開(kāi)始設(shè)置中斷分組,temp為設(shè)置好的搶占優(yōu)先級(jí)及響應(yīng)優(yōu)先級(jí)。

      NVIC->IPR[IPRADDR]|=temp<

      (2)

      u32 temp;

      temp=NVIC_PreemptionPriority<<(4-NVIC_Group); //搶占優(yōu)先級(jí)設(shè)置

      temp|=NVIC_SubPriority&(0x0f>>NVIC_Group); //相應(yīng)優(yōu)先級(jí)設(shè)置

      temp&=0xf;//取低四位

      例:NVIC_Group分組為1,則為1位搶占優(yōu)先級(jí),3位響應(yīng)優(yōu)先級(jí)

      則NVIC_PreemptionPriority<<4-1

      temp|=NVIC_SubPriority&(0x0000 1111>>1)=(0000 0BBB)

      temp = (?AAA A000)|(0000 0BBB)

      = (?AAAABBB)

      那么AAAA只能是從0000-0001,BBB能從000-111剛好對(duì)應(yīng)起來(lái)。

      temp&=0X0F,因?yàn)橹皇莃it[7:4]有效。

      (3)

      if(NVIC_Channel<32)

      {

      NVIC->ISER[0]|=1<

      }

      else

      {

      NVIC->ISER[1]|=1<<(NVIC_Channel-32);

      }

      則表示對(duì)應(yīng)中斷(0~59)使能,若中斷編號(hào)小于32,則響應(yīng)使能中斷寄存器ISER[0],反之使能中斷寄存器ISER[1]。

      配置好NVIC后,接著配置外部中斷寄存器EXTI

      STM32的EXTI支持外部19個(gè)外部中斷/事件,具有獨(dú)立的中斷屏蔽及狀態(tài)位控制。

      線0~15對(duì)應(yīng)于外部IO的輸入中斷

      線16連接到PVD

      線17連接到RTC鬧鐘事件

      線18連接到USB喚醒事件

      /*------------------------ External Interrupt/Event Controller ---------------*/

      typedef struct

      {

      vu32 IMR; //中斷屏蔽寄存器 32bits,只有前19位有效

      vu32 EMR; //事件屏蔽寄存器

      vu32 RTSR; //上升沿觸發(fā)選擇寄存器

      vu32 FTSR; //下降沿觸發(fā)選擇寄存器

      vu32 SWIER; //軟件中斷寄存器 未設(shè)置IMR及EMR時(shí),設(shè)置1,掛起PR,在PR清除后響應(yīng)的SWIER清除

      vu32 PR; //中斷掛起寄存器 1表示中斷響應(yīng),0表示未發(fā)生,向該寄存器寫(xiě)1,則清除掛起位

      } EXTI_TypeDef

      注:如果使用外部IO中斷,還必須使用AFIO復(fù)用里的外部中斷配置寄存器EXTICR。高16位保留,低16位有效。STM32任何一個(gè)IO口都可以配置成中斷輸入,但是IO口的數(shù)目遠(yuǎn)遠(yuǎn)大于中斷線數(shù)(16個(gè))。

      GPIOA~GPIOG[15:0]分別對(duì)應(yīng)中斷線15:0,每條中斷線對(duì)應(yīng)于7個(gè)IO口。

      例如:中斷線0對(duì)應(yīng)于GPIOA.0,GPIOB.0,GPIOC.0,GPIOD.0,GPIOE.0,GPIOF.0,GPIOG.0

      

     

      EXTICR[0]~EXTICR[3]每個(gè)EXTICR只用到了低16位,高16位保留。

      typedef struct

      {

      vu32 EVCR;

      vu32 MAPR;

      vu32 EXTICR[4];

      } AFIO_TypeDef

      EXTICR[0] 對(duì)應(yīng)于EXTI0[3:0],EXTI1[3:0],EXTI2[3:0],EXTI3[3:0]

      EXTI0[3:0] 外部中斷線0

      0000àPA[0] 0001àPB[0] 0010àPC[0] 0011àPD[0] 0100àPE[0] 0101àPF[0] 0110àPG[0]

      EXTI1[3:0] 外部中斷線1

      0000àPA[1] 0001àPB[1] 0010àPC[1] 0011àPD[1] 0100àPE[1] 0101àPF[1] 0110àPG[1]

      EXTI2[3:0] 外部中斷線2

      0000àPA[2] 0001àPB[2] 0010àPC[2] 0011àPD[2] 0100àPE[2] 0101àPF[2] 0110àPG[2]

      EXTI3[3:0] 外部中斷線3

      0000àPA[3] 0001àPB[3] 0010àPC[3] 0011àPD[3] 0100àPE[3] 0101àPF[3] 0110àPG[3]

      EXTICR[1] 對(duì)應(yīng)于EXTI4[3:0],EXTI5[3:0],EXTI6[3:0],EXTI7[3:0] 外部中斷線4~7

      EXTICR[2] 對(duì)應(yīng)于EXTI8[3:0],EXTI9[3:0],EXTI10[3:0],EXTI11[3:0] 外部中斷線8~11

      EXTICR[3] 對(duì)應(yīng)于EXTI12[3:0],EXTI13[3:0],EXTI14[3:0],EXTI15[3:0] 外部中斷線12~15

      /////////////////////////////////////////////////////////////////

      //Ex_NVIC_Config專(zhuān)用定義

      #define GPIO_A 0

      #define GPIO_B 1

      #define GPIO_C 2

      #define GPIO_D 3

      #define GPIO_E 4

      #define GPIO_F 5

      #define GPIO_G 6

      #define FTIR 1 //下降沿觸發(fā)

      #define RTIR 2 //上升沿觸發(fā)

      BITx 范圍為0~15,對(duì)應(yīng)于IO口的位,對(duì)于外部中斷線。

      //外部中斷配置函數(shù)

      //只針對(duì)GPIOA~G;不包括PVD,RTC和USB喚醒這三個(gè)

      //參數(shù):GPIOx:0~6,代表GPIOA~G;BITx:需要使能的位;TRIM:觸發(fā)模式,1,下升沿;2,上降沿;3,任意電平觸發(fā)

      //該函數(shù)一次只能配置1個(gè)IO口,多個(gè)IO口,需多次調(diào)用

      //該函數(shù)會(huì)自動(dòng)開(kāi)啟對(duì)應(yīng)中斷,以及屏蔽線

      void Ex_NVIC_Config(u8 GPIOx,u8 BITx,u8 TRIM)

      {

      u8 EXTADDR;

      u8 EXTOFFSET;

      EXTADDR=BITx/4;//得到中斷寄存器組的編號(hào) 2/4=0

      EXTOFFSET=(BITx%4)*4; (2%4)*4 = 8

      RCC->APB2ENR|=0x01;//使能io復(fù)用時(shí)鐘

      AFIO->EXTICR[EXTADDR]&=~(0x000F<

      AFIO->EXTICR[EXTADDR]|=GPIOx<

      //自動(dòng)設(shè)置

      EXTI->IMR|=1<

      if(TRIM&0x01)

      {

      EXTI->FTSR|=1<

      }

      if(TRIM&0x02)

      {

      EXTI->RTSR|=1<

      }

      }

      EXTADDR=BITx/4;得到中斷寄存器的編號(hào)0~4 BITx【0~15】

      EXTOFFSET=(BITx%4)/4;得到中斷寄存器的偏移量 0,4,8,12



    關(guān)鍵詞: STM32F10X 中斷

    評(píng)論


    相關(guān)推薦

    技術(shù)專(zhuān)區(qū)

    關(guān)閉
    主站蜘蛛池模板: 南皮县| 元阳县| 衡阳市| 广州市| 岳阳市| 和田市| 通辽市| 苏州市| 武宁县| 武川县| 余江县| 永吉县| 凤庆县| 泸定县| 芜湖县| 大埔区| 灌阳县| 遵化市| 郑州市| 板桥市| 和龙市| 安新县| 开鲁县| 怀仁县| 西宁市| 金阳县| 襄垣县| 津南区| 江川县| 霸州市| 海口市| 大宁县| 武隆县| 岳西县| 万山特区| 疏附县| 兴城市| 佛坪县| 米易县| 招远市| 龙南县|