M3用8bits而STM32用高四位來表示搶占和子優先級:bit=1表示搶占;bit=0表示非搶占即子優先級;所以共有5中方案分組:
分組 Bit7 Bit6 Bit5 Bit4 說明:
第0組 0 0 0 0
第1組 1 0 0 0
第2組 1 1 0 0 搶占共有2^2=4(0~3);子優先級2^2=4(0~3),共4*4=16級嵌套
第3組 1 1 1 0 搶占共有2^3=4(0~7);子優先級2^1=2(0~1),共8*2=16級嵌套
第4組 1 1 1 1
到底誰優先:數字越小優先級越高,搶占級數字小的可剝奪搶占級數字大的
1搶占相同,子優先級不同:此時沒有搶占剝奪,此時按照子優先級順序排序
2搶占和子優先級都相同但有先后:此時無搶占剝奪,依照FIFO,前一個執行完了才能執行后者;
3搶占和子優先級都相同且同時到達:此時按照中斷向量表順序排先后
開關總中斷:
在STM32固件庫中(stm32f10x_nvic.c和stm32f10x_nvic.h,但在標准庫3.5版本中沒有改文件,NVIC控制放在了在了mis.c(優先級設置與分組)中和core.cm3.c(總中斷的開關控制)) 定義了四個函數操作PRIMASK位和FAULTMASK位,改變CPU的當前優先級,從而達到控制所有中斷的目的。
CPSID I ; PRIMASK=1, ;關中斷
CPSIE I ; PRIMASK=0, ;開中斷
CPSID F ; FAULTMASK=1, ;關異常
CPSIE F ; FAULTMASK=0 ;開異常
PRIMASK(總中斷控制位):只允許NMI和hard fault異常,其他中斷/異常都被屏蔽(當前CPU優先級=0)。
FAULTMASK(總異常控制位)::只允許NMI,其他所有中斷/異常都被屏蔽(當前CPU優先級=-1)。
下面兩個函數等效於關閉總中斷:
void NVIC_SETPRIMASK(void);
void NVIC_RESETPRIMASK(void);
void NVIC_SETFAULTMASK(void);
void NVIC_RESETFAULTMASK(void);
可以用宏定義開關:
#define EA=1 __set_PRIMASK(1);//__set_FAULTMASK(1)
#define EA=0 __set_PRIMASK(0);//__set_FAULTMASK(0)
***********************************************************************************
/THUMB指令不支持匯編內聯
//采用如下方法實現執行匯編指令WFI
//CHECK OK
//091209
__asm void WFI_SET(void)
{
WFI;
}
WFE 休眠並且在發生事件時被喚醒
WFI 休眠並且在發生中斷時被喚醒//進入待機模式
//check ok
//091202
void Sys_Standby(void)
{
SCB->SCR|=1<<2;//使能SLEEPDEEP位 (SYS->CTRL)
RCC->APB1ENR|=1<<28; //使能電源時鍾
PWR->CSR|=1<<8; //設置WKUP用於喚醒
PWR->CR|=1<<2; //清除Wake-up 標志
PWR->CR|=1<<1; //PDDS置位
WFI_SET(); //執行WFI指令
}