會員登陸
帳號:

密碼:

記住我



忘記密碼?

現在註冊!
網站導航
最新下載
訪問統計 (自2012/5/3)


正在流覽:   1 名訪客





PIC32如何停止Priority 0~6,Priority 7繼續
高級會員
註冊日期:
2011/07/26 14:42
來自 高雄市
所屬群組:
註冊會員
文章: 79
等級: 7; EXP: 83
HP : 0 / 170
MP : 26 / 4188
離線
我使用的是PIC32MX695F512L,Compiler是XC32 v1.31。

UART的RX、TX是使用中斷,Priority 6
Timer中斷的Priority是7。

程式運行時,在某些必要的時段需要暫時停止UART的中斷,我是使用
INTDisableInterrupts()
來停止,但這樣子好像連Timer也一併停掉了。

在PIC24好像有
SRbits.IPL = 6;
來將Level 6以下的中斷停掉(獨留7可以繼續)

PIC32好像沒有這樣子的寫法

請問各位先進,PIC32有什麼方法可以讓我達到目的呢?

7月15日 11:20:50
轉換PDF檔 列印


Re: PIC32如何停止Priority 0~6,Priority 7繼續
版主
註冊日期:
2004/04/30 10:53
來自 CAE, Microchip
所屬群組:
站務管理者
註冊會員
MICROCHIP
文章: 14874
等級: 73; EXP: 63
HP : 1089 / 1815
MP : 4958 / 82924
離線
基本上 PIC32 的中斷優先權控制與 PIC24, dsPIC 類似。可以先參考一下 dsPICMOD dsPIC30F Module Training 教育訓練裡的 Interrupt 章節的說明。

PIC32 MCU Core 有 CPU 的中斷優先權的設定,查看一下暫存器 INTSTAT<RIPL2:0> 這就是設定 MCU 中斷優先權的位元,RIPL= 0x07 時所有的周邊中斷就無法中斷 MCU。如果 RIPL = 0x05,周邊的中斷設定值必須要大於 0x05 才可以讓 MCU 產生中斷。

參考下貼圖,周邊的 IPL 要跟 MCU 的 RIPL 比較過後才有中斷的可能 (IPL > RIPL)。

附加檔案:



jpg  擷取.JPG (43.47 KB)
16_5d2c20ea6f66b.jpg 671X378 px

7月15日 14:44:58
轉換PDF檔 列印


Re: PIC32如何停止Priority 0~6,Priority 7繼續
高級會員
註冊日期:
2011/07/26 14:42
來自 高雄市
所屬群組:
註冊會員
文章: 79
等級: 7; EXP: 83
HP : 0 / 170
MP : 26 / 4188
離線
照Ryang的意思看來,在一般程式(非中斷程式)裡,提高RIPL到6,就可以達到我的需求,是否如此呢?

可以直接修改RIPL嗎? 需求注意哪些事呢?

7月15日 15:54:44
轉換PDF檔 列印


Re: PIC32如何停止Priority 0~6,Priority 7繼續
高級會員
註冊日期:
2011/07/26 14:42
來自 高雄市
所屬群組:
註冊會員
文章: 79
等級: 7; EXP: 83
HP : 0 / 170
MP : 26 / 4188
離線
根據我對Ryang回覆的理解,把底下程式加到我的應用裡
intStatus = INTSTATbits.SRIPL;
INTSTATbits.SRIPL = 6;
...
... (受保護的程序)
...
INTSTATbits.SRIPL = intStatus;

可惜的是,失敗了....

請教各位先進與Ryang,我會錯意了還是程式哪裡錯了呢?

7月22日 08:32:15
轉換PDF檔 列印


Re: PIC32如何停止Priority 0~6,Priority 7繼續
版主
註冊日期:
2004/04/30 10:53
來自 CAE, Microchip
所屬群組:
站務管理者
註冊會員
MICROCHIP
文章: 14874
等級: 73; EXP: 63
HP : 1089 / 1815
MP : 4958 / 82924
離線
每個周邊都有自己的中斷優先權,他必須大於 CPU 的中斷優先權 (SRIPL) 後才可以產生中斷。

如果直接將 SRIPL = 7 之後,這時會停用所有的周邊中斷,測試一下在這情況下會不會有中斷發生呢?

這個功能我在 16-bit 的 PIC 上是沒有問題的,在 32-bit 上我沒試過。


/*************************************************************
//                dsPIC30F Interrupt Lab 2
//
// Purpose : 設定 Timer 中斷,以中斷動方式驅動 LED 閃爍
/* Timer1 每間隔 1 Sec. 閃爍 LED1 一次(_T1Interrupt), Interrupt Priority as 7 */
/* Timer2 每間隔 0.5 Sec. 閃爍 LED1 一次(_T2Interrupt), Interrupt Priority as 5 */
/* Timer3 每間隔 200mS 閃爍 LED1 一次(_T3Interrupt),,Interrupt Priority as 3 */
/* Timer4 每間隔 50mS 閃爍 LED1 一次(_T4Interrupt), Interrupt Priority as 1 */
//
//    CPU interrupt Priority Power-On default is Level 0
//  Press SW5 to increase the Priority Level of CPU
//    Press SW6 to decrease the Priority Level of CPU
//    Both SW5 & SW6 have key debunce function
//
// **************************************************************/


#include <p30fxxxx.h>
#include    <timer.h>
#include     "C30EVM_LCD.h"            // 將LCD函式的原型宣告檔案含入

#define        Fosc     7372800           // 頻率為 7.3728 MHz  
                                    
//---------------------------------------------------------------------------
// 請參考此處有關 Configuration bits 於程式中直接宣告的方式
// 更詳細的參數列表請參考 p30F4011.h
//---------------------------------------------------------------------------
       
_FOSC(CSW_FSCM_OFF & XT);        //    XT oscillator, Failsafe clock off
       
_FWDT(WDT_OFF);                  //    Watchdog timer disabled
      
_FBORPOR(PBOR_OFF & MCLR_EN);    //    Brown-out reset disabled, MCLR reset enabled
       
_FGS(CODE_PROT_OFF);             //    Code protect disabled

const char    My_String1[]="T1=7, T2=5, T3=3";    // Declare the LED line 1 String in ROM
const char    My_String2[]="T4=1, CPU Core=0";    // Declare the LED line 2 string in ROM

#define    LED1        LATEbits.LATE0         //定義LED為特定輸出埠腳位位元的替代符號,
#define    LED2        LATEbits.LATE1         //以加強程式的可讀性與簡潔
#define    LED3        LATEbits.LATE2
#define    LED4        LATEbits.LATE3
#define    DIR_LED1    TRISebits.TRISE0     //定義DIR_LED為特定輸出入埠腳位位元
#define    DIR_LED2    TRISebits.TRISE1    //的方向控制位元替代符號
#define    DIR_LED3    TRISebits.TRISE2
#define    DIR_LED4    TRISebits.TRISE3

#define    SW5            PORTEbits.RE8        //定義SW5與SW6為特定輸入埠腳位位元的替代符號
#define    SW6            PORTBbits.RB3
#define    DIR_SW5        TRISEbits.TRISE8     //定義DIR_LED7與DIR_LED8為特定輸出入埠腳位位元
#define    DIR_SW6        TRISBbits.TRISB3    //的方向控制位元替代符號

unsigned char debounce=0;
unsigned char i;

void Init_IO(void);
void Init_Timer1(void);
void Init_Timer2(void);
void Init_Timer3(void);
void Init_Timer4(void);

int    main( void )
{
    
Init_IO( );
    
Init_Timer1( );
    
Init_Timer2( );
    
Init_Timer3( );
    
Init_Timer4( );

    
OpenLCD( );                            // 使用 OpenLCD( )對 LCD 模組作初始化設定
                                        // 4 bits Data mode
                                        // 5 * 7 Character

    
setcurLCD(0,0) ;                    // 使用 setcurLCD( ) 設定游標於 (0,0)
    
putrsLCD( My_String1 ) ;            // 將存在 Program Memory 的字串使用
                                        // putrsLCD( ) 印出至 LCD
            
    
setcurLCD(0,1) ;
    
putrsLCD( My_String2 ) ;            // 使用 setcurLCD( ) 設定游標於 (0,1)
                                        // 將存在 Data Memory 的字串使用    


    
while(1)
    {
        if (
debounce==0)
            {
                if (!
SW5)
                    {
                    
SRbits.IPL++;
                    
setcurLCD(15,1);
                    
putcLCD('0'+ SRbits.IPL);
                    
debounce=30;
                    }
                if (!
SW6)
                    {
                    
SRbits.IPL--;
                    
setcurLCD(15,1);
                    
putcLCD('0'+ SRbits.IPL);
                    
debounce=30;
                    }
            }
        else
            {
                if (
SW5 & SW6)
                    {
                        
debounce--;
                        for (
i=0;i<100;i++);
                    }
                else
                    
debounce=30;    
            }        
    }
}


void _ISR _T1Interrupt(void)
{
    
LED1=!LED1;                            // Flash the LED1
    
IFS0bits.T1IF = 0 ;                    // Clear Timer1 Interrupt Flag
}
void _ISR _T2Interrupt(void)
{
    
LED2=!LED2;
    
IFS0bits.T2IF = 0 ;
}
void _ISR _T3Interrupt(void)
{
    
LED3=!LED3;
    
IFS0bits.T3IF = 0 ;
}
void _ISR _T4Interrupt(void)
{
    
LED4=!LED4;
    
IFS1bits.T4IF = 0 ;
}

void Init_IO(void)
{
    
ADPCFG = 0xFEB8;                    // Cnfig. ADC input, ADPCFG = 1111 1110 1011 1000
                                        // RB0-> VR2, RB1-> Ext AN1, RB2-> Rxt AN2
                                        // RB3-> Index, RB4-> QEA, RB5-> QEB
                                        // RB6-> VR1, RB7-> LCDE, RB8-> Analog Key (SW1~SW4)  
    
TRISB = 0xFFFF ;                    // Set PORTB as Digital Inputs
    
TRISBbits.TRISB7=0;                    // RB7 as LEDE output control
    
LATBbits.LATB7=0;                    // Disable LCD module
    
    
TRISE=0x0000;                         // LE1~LED6 are Output
    
LATE=0x00FF;                        // Turn all LED off
    
DIR_SW5  = 1 ;                        // Define SW5 & SW6 as Digital Inputs (Switch Push Low)
    
DIR_SW6  = 1 ;
}

/*************************************************/
// Timer 模組的初始化副程式
// 100mS Interrupt setting
/*************************************************/
void Init_Timer1(void)
{
        
ConfigIntTimer1( T1_INT_PRIOR_7 & T1_INT_ON ) ;        // Timer1 的中斷優先等級設 7 (最高)
                                                            // Timer1 的中斷 ON

        
OpenTimer1( T1_ON & T1_IDLE_STOP & T1_GATE_OFF &     // Timer1 Period as 2 Second
                    
T1_PS_1_256 & T1_SYNC_EXT_OFF & T1_SOURCE_INT ,
                        (
long)((Fosc/4/1000)*2000)/256) ;    // Period= 14400
}
void Init_Timer2(void)
{
        
ConfigIntTimer2( T2_INT_PRIOR_5 & T2_INT_ON ) ;        // Timer2 的中斷優先等級設 5 (最高)
                                                            // Timer2 的中斷 ON

        
OpenTimer2( T2_ON & T2_IDLE_STOP & T2_GATE_OFF &     // Timer2 Period as 1 Second
                    
T2_PS_1_256 & T2_32BIT_MODE_OFF & T2_SOURCE_INT ,
                        (
long)((Fosc/4/1000)* 1000 )/256 ) ;    // Period= 7200
}
void Init_Timer3(void)
{
        
ConfigIntTimer3( T3_INT_PRIOR_3 & T3_INT_ON ) ;        // Timer3 的中斷優先等級設 3 (最高)
                                                            // Timer3 的中斷 ON

        
OpenTimer3( T3_ON & T3_IDLE_STOP & T3_GATE_OFF &     // Timer3 Period as 500 ms
                    
T3_PS_1_256 & T3_SOURCE_INT ,
                        (
long)((Fosc/4/1000)* 500 )/256 ) ;
}
void Init_Timer4(void)
{
        
ConfigIntTimer4( T4_INT_PRIOR_1 & T4_INT_ON ) ;        // Timer4 的中斷優先等級設 1 (最高)
                                                            // Timer4 的中斷 ON

        
OpenTimer4( T4_ON & T4_IDLE_STOP & T4_GATE_OFF &     // Timer4 Period as 100 ms
                    
T4_PS_1_256 & T4_SOURCE_INT & T4_32BIT_MODE_OFF ,  
                        (
long)((Fosc/4/1000)* 100 )/256 ) ;
}

7月22日 10:03:00
轉換PDF檔 列印


Re: PIC32如何停止Priority 0~6,Priority 7繼續
高級會員
註冊日期:
2011/07/26 14:42
來自 高雄市
所屬群組:
註冊會員
文章: 79
等級: 7; EXP: 83
HP : 0 / 170
MP : 26 / 4188
離線
我測試的方式
1.使用一顆LED每半秒(透過Timer(Priority7)中斷)轉換一次燈號。
2.使用按鈕,程式大概如下
if (ButtonPress()) {
flag = 1 - flag;
LED2 = flag;
if (flag) {
INTSTATbits.SRIPL = 7;
} else {
INTSTATbits.SRIPL = 0;
}
}

執行時
1.應該會讓LED燈閃爍
2.按下按鈕後,因為IPL升為7,Timer沒法被中斷,所以LED應該不會閃爍
3.再按下按鈕,IPL降為0,Timer可被中斷,LED又開始閃爍

實際我看到的是:LED一直閃爍,不管按鈕怎麼按。
所以結論是:此方法失敗。

7月22日 10:30:33
轉換PDF檔 列印


Re: PIC32如何停止Priority 0~6,Priority 7繼續
高級會員
註冊日期:
2011/07/26 14:42
來自 高雄市
所屬群組:
註冊會員
文章: 79
等級: 7; EXP: 83
HP : 0 / 170
MP : 26 / 4188
離線
看了關於PIC32關於CPU文件
CP0 Register 12, Select 0(Status Register)有關於IPL(Status bit 12-10)的敘述,應該是這個才對

只是我並不清楚該如何在XC32下,怎麼寫才可以改變IPL的值,請各位先進幫忙,謝謝!

7月25日 17:50:45
轉換PDF檔 列印


Re: PIC32如何停止Priority 0~6,Priority 7繼續
高級會員
註冊日期:
2011/07/26 14:42
來自 高雄市
所屬群組:
註冊會員
文章: 79
等級: 7; EXP: 83
HP : 0 / 170
MP : 26 / 4188
離線
以下是將IPL設為7
__builtin_bcsc0(12, 0, 0x00001C00, 0x00001C00);

IPL設回0
__builtin_bcc0(12, 0, 0x00001C00);

只是,但不管主程序IPL設為多少,Timer(中斷我設IPL為7)、UART(中斷我設IPL為4),中斷一樣都在發生,有點氣餒。

7月26日 08:58:29
轉換PDF檔 列印






無法在此發表文章
可以在此觀看文章
無法回覆文章
無法編輯自己的文章
無法刪除自己的文章
無法發起投票調查
無法在此投票
無法上傳附加檔案
無法不經審核直接發表文章

[進階搜尋]


搜尋
Microchip連結
產品技術問題產品技術支援專線:0800-717718 台北02-25088600 新竹03-5778366 Ext. 8600 高雄07-2137830 MicrochipDIRECT 專線: 07-2137830
Powered by XOOPS © 2001-2012 The XOOPS Project