新聞中心

        EEPW首頁 > 嵌入式系統 > 設計應用 > stm32 設置systick中斷搶先式優先級

        stm32 設置systick中斷搶先式優先級

        作者: 時間:2016-11-28 來源:網絡 收藏
        最近使用STM32時希望將systick的中斷優先級降低,但是CMSIS里給出的例子都是類似

        本文引用地址:http://www.104case.com/article/201611/322685.htm
        [plain]view plaincopy
        1. NVIC_InitStructure.NVIC_IRQChannel=TIM1_UP_IRQn;
        2. NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=0;
        3. NVIC_InitStructure.NVIC_IRQChannelSubPriority=0;
        4. NVIC_InitStructure.NVIC_IRQChannelCmd=ENABLE;
        5. NVIC_Init(&NVIC_InitStructure);
        還是沒有配置systick。

        后來閱讀CM3的技術參考手冊,講解了NVIC的配置。

        中斷分為內核中斷和芯片的中斷,配置的寄存器位置不同。芯片的中斷配置在NVIC的IP內,內核的中斷配置在SCB內。

        可以直接調用core_cm3.h里的函數

        [cpp]view plaincopy
        1. static__INLINEvoidNVIC_SetPriority(IRQn_TypeIRQn,uint32_tpriority)
        2. {
        3. if(IRQn<0){
        4. SCB->SHP[((uint32_t)(IRQn)&0xF)-4]=((priority<<(8-__NVIC_PRIO_BITS))&0xff);}
        5. else{
        6. NVIC->IP[(uint32_t)(IRQn)]=((priority<<(8-__NVIC_PRIO_BITS))&0xff);}
        7. }
        這個函數實現了兩類中斷優先級的配置。

        但是直觀上來看看不到搶先式優先級與子優先級。

        首先,配置優先級組,可以使用固件庫的程序,也可以用core_cm3.h的函數。

        [cpp]view plaincopy
        1. voidNVIC_PriorityGroupConfig(uint32_tNVIC_PriorityGroup)
        2. {
        3. SCB->AIRCR=AIRCR_VECTKEY_MASK|NVIC_PriorityGroup;
        4. }

        [cpp]view plaincopy
        1. static__INLINEvoidNVIC_SetPriorityGrouping(uint32_tPriorityGroup)
        2. {
        3. uint32_treg_value;
        4. uint32_tPriorityGroupTmp=(PriorityGroup&0x07);
        5. reg_value=SCB->AIRCR;
        6. reg_value&=~(SCB_AIRCR_VECTKEY_Msk|SCB_AIRCR_PRIGROUP_Msk);
        7. reg_value=(reg_value|
        8. (0x5FA<<SCB_AIRCR_VECTKEY_Pos)|
        9. (PriorityGroupTmp<<8));
        10. SCB->AIRCR=reg_value;
        11. }
        參數范圍為0~7,具體如下

        隨后配置各個中斷的優先級,對于外設的中斷可以使用固件庫的程序,比較直觀。如最前面所給出的例子,但是根據其實現,是不能夠用來配置內核中斷的,例如

        [cpp]view plaincopy
        1. NVIC_InitStructure.NVIC_IRQChannel=SysTick_IRQn;
        2. NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=0;
        3. NVIC_InitStructure.NVIC_IRQChannelSubPriority=0;
        4. NVIC_InitStructure.NVIC_IRQChannelCmd=ENABLE;
        5. NVIC_Init(&NVIC_InitStructure);
        這是錯誤的,因為內部使用IRQn尋址,而SysTick_IRQn為-1.

        所以對于Sysick使用core_cm3.h的函數

        [cpp]view plaincopy
        1. NVIC_SetPriority(SysTick_IRQn,4);
        這時不能顯式的看出搶先式優先級與子優先級,寫入的優先級需要根據優先級組的配置來選擇。

        [cpp]view plaincopy
        1. NVIC_SetPriority(SysTick_IRQn,n);
        2. n=0x00~0x03設置Systick為搶占優先級0
        3. n=0x04~0x07設置Systick為搶占優先級1
        4. n=0x08~0x0B設置Systick為搶占優先級2
        5. n=0x0C~0x0F設置Systick為搶占優先級3

        NVIC_SetPriority函數指定中斷優先級的寄存器位(STM32只用4位來表示優先級)的數據,例如中斷優先級組設置為了2,即高2位用于指定搶占式優先級,低2位用于指定響應優先級,0x00~0x03高2位為0,所以搶占優先級為0;0x04~0x07高2位為1,所以搶占優先級為1,以此類推。



        評論


        技術專區

        關閉
        主站蜘蛛池模板: 邢台市| 三河市| 吉隆县| 泰顺县| 东宁县| 蛟河市| 许昌市| 瓮安县| 饶阳县| 建湖县| 饶平县| 宣化县| 安平县| 营口市| 额济纳旗| 德兴市| 永修县| 东阿县| 兴化市| 故城县| 广汉市| 寿光市| 尉氏县| 北辰区| 丹巴县| 武川县| 广汉市| 赣榆县| 加查县| 崇义县| 丽江市| 任丘市| 莆田市| 乌兰浩特市| 连南| 苍南县| 鹤壁市| 当阳市| 德格县| 蓝田县| 新闻|