2020年2月21日 星期五

DSP TI TMS320F283xx eCAN初始化


在開始使用DSP2833x前,需要對它進行初始化,下面是初始化的步驟與TI 提供的eCAN初始參考程式。
CAN bit-timing需要根據系統需求去設置,其他需要設定的是開啟eCANA還是eCANB,由那兩個GPIO。

DSP2833x eCAN功能初始化步驟

InitSysCtrl()
將CAN module的Clock致能:在SysCtrlRegs.PCLKCR0.bit,將要用到的ECANAENCLK 與/或 
ECANBENCLK設為"1"。

InitECanGpio()
Step 1.設定CANRXA、CANTXA所對應的GPIO pin,在GPAPUD將這兩pin設為"0"
            使內部Pullup關閉。
Step 2.設置CANRXA所對應的GPIO pin,做為input,在GPAQSELx暫存器將這
            pin設為非同步(Asynchronous),因為它不是一般GPIO功能,而是周邊通
            訊功能。
Step 3.設定CANRXA、CANTXA所對應的兩個GPIO pin,在GPIO GUAMUX2將
           它們設為CANRXA, CANTXA。


InitECan()
Step 1. 將 CANTX、CANRX pins設為CAN功能。
             a. Write CANTIOC.3:0 = 0x08
             b. Write CANRIOC.3:0 = 0x08
Step 2.設置Master control暫存器CAMMC的SCB,"1"表示為High end CAN ccontroller,
           "0"表示為Standard Can controller
Step 3.初始化設定,將所有Mailbox的Message control暫存器MSGCTR設為"0",。
           將一些旗標暫存器CANTA, CANRMP, CANGIF0, CANGIF1寫入"1",確保它們
           被清除為"0"。
Step 4.要設置CAN bit timing前,要發設定CANMC.CCR為"1",請求修改CANBTC,再
            來就要等待CANES.CCE為"1",表示CPU允許CANBTC被設置。
Step 5.從CANBTC暫存器,來設置期望的CAN bit timing. 可以參考我另一篇
           "DSP TI TMS320F283xx eCAN module control 與 Bit-Timing設定"
Step 6.完成CANBTC設定後,將CANMC.CCR設為"0",要求回到正常模式。然後等待
            CANES.CCE為"0",表示CPU同意。
Step 7.發送、接收Mailbox都有對應的MSGID,在設置MSGID前,要將Mailbox disable,
            由CANME為"0"來完成。

#eCanaRegs不支援位元操作,所以要設置這些暫存器時,要先將暫存器先存到
ECanaShadow, 做為它的影子,然後在ECanaShadow上設置位元後,再存回eCanaRegs。


DSP2833x參考程式碼

DSP2833x_SysCtrl.c
InitSysCtrl(void)->InitPeripheralClocks();
    SysCtrlRegs.PCLKCR0.bit.ECANAENCLK=1;    // eCAN-A
    SysCtrlRegs.PCLKCR0.bit.ECANBENCLK=1;    // eCAN-B


DSP2833x_ECan.c
void InitECana(void)        // Initialize eCAN-A module
{
/* Create a shadow register structure for the CAN control registers. This is
needed, since only 32-bit access is allowed to these registers. 16-bit access
to these registers could potentially corrupt the register contents or return
false data. This is especially true while writing to/reading from a bit
(or group of bits) among bits 16 - 31 */

struct ECAN_REGS ECanaShadow;
    EALLOW;        // EALLOW enables access to protected bits

/* Configure eCAN RX and TX pins for CAN operation using eCAN regs*/  

    ECanaShadow.CANTIOC.all = ECanaRegs.CANTIOC.all;
    ECanaShadow.CANTIOC.bit.TXFUNC = 1;                            //設置CAN RX PIN做為CAN Receiver功能
    ECanaRegs.CANTIOC.all = ECanaShadow.CANTIOC.all;

    ECanaShadow.CANRIOC.all = ECanaRegs.CANRIOC.all;
    ECanaShadow.CANRIOC.bit.RXFUNC = 1;                           //設置CAN RX PIN做為CAN Receiver功能
    ECanaRegs.CANRIOC.all = ECanaShadow.CANRIOC.all;

/* Configure eCAN for HECC mode - (reqd to access mailboxes 16 thru 31) */
                                    // HECC mode also enables time-stamping feature
//設置SCB bit為1,表示eCAN做為HECC(High-end-CAN Controller)
//設置SCB bit為0,表示為SCC(Standard CAN Controller)
    ECanaShadow.CANMC.all = ECanaRegs.CANMC.all;
    ECanaShadow.CANMC.bit.SCB = 1;                                    
    ECanaRegs.CANMC.all = ECanaShadow.CANMC.all;    


/* Initialize all bits of 'Master Control Field' to zero */
// Some bits of MSGCTRL register come up in an unknown state. For proper operation,
// all bits (including reserved bits) of MSGCTRL must be initialized to zero

    ECanaMboxes.MBOX0.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX1.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX2.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX3.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX4.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX5.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX6.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX7.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX8.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX9.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX10.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX11.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX12.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX13.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX14.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX15.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX16.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX17.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX18.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX19.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX20.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX21.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX22.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX23.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX24.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX25.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX26.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX27.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX28.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX29.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX30.MSGCTRL.all = 0x00000000;
    ECanaMboxes.MBOX31.MSGCTRL.all = 0x00000000;

// TAn, RMPn, GIFn bits are all zero upon reset and are cleared again
//    as a matter of precaution.
    ECanaRegs.CANTA.all    = 0xFFFFFFFF;     //CANTA為Transmission ACK bit, 寫入"1"去清除。

    ECanaRegs.CANRMP.all = 0xFFFFFFFF;    //CANRMP為Receive message pending,
                                                                             //對應的bit表示這個mailbox有存message了,寫入"1"去清除。
    ECanaRegs.CANGIF0.all = 0xFFFFFFFF;    /* Clear all interrupt flag bits */  CANGIF0為Globe interrupt flag
    ECanaRegs.CANGIF1.all = 0xFFFFFFFF;

/* Configure bit timing parameters for eCANA*/

    ECanaShadow.CANMC.all = ECanaRegs.CANMC.all;
    ECanaShadow.CANMC.bit.CCR = 1 ;           //請求修改配置CANBTC、接收屏蔽CANGAM、LAM0。
    ECanaRegs.CANMC.all = ECanaShadow.CANMC.all;
    ECanaShadow.CANES.all = ECanaRegs.CANES.all;

    do
    {
        ECanaShadow.CANES.all = ECanaRegs.CANES.all;   
    } while(ECanaShadow.CANES.bit.CCE != 1 );       // 將值存到Shadon暫存器,等待CCE1為1後,
                                                                                 //可以開始去設置CANBTC暫存器
    ECanaShadow.CANBTC.all = 0;                      //設Shadown裡CANBTC為0。       
    #if (CPU_FRQ_150MHZ)           // CPU_FRQ_150MHz is defined in DSP2833x_Examples.h
        /* The following block for all 150 MHz SYSCLKOUT - default. Bit rate = 1 Mbps */
            ECanaShadow.CANBTC.bit.BRPREG = 9;
            ECanaShadow.CANBTC.bit.TSEG2REG = 2;
            ECanaShadow.CANBTC.bit.TSEG1REG = 10;
    #endif
    #if (CPU_FRQ_100MHZ)           // CPU_FRQ_100MHz is defined in DSP2833x_Examples.h
    /* The following block is only for 100 MHz SYSCLKOUT. Bit rate = 1 Mbps */
        ECanaShadow.CANBTC.bit.BRPREG = 9;
        ECanaShadow.CANBTC.bit.TSEG2REG = 1;
        ECanaShadow.CANBTC.bit.TSEG1REG = 6;
    #endif

    ECanaShadow.CANBTC.bit.SAM = 1;          //每個採樣點取樣3次。
    ECanaRegs.CANBTC.all = ECanaShadow.CANBTC.all;    //將Shadown裡的設置到實際暫存器。
    ECanaShadow.CANMC.all = ECanaRegs.CANMC.all;
    ECanaShadow.CANMC.bit.CCR = 0 ;                            // 設置CCR為0,回到正常模式,無法再改CANBTC。
    ECanaRegs.CANMC.all = ECanaShadow.CANMC.all;
    ECanaShadow.CANES.all = ECanaRegs.CANES.all;

    do
    {
       ECanaShadow.CANES.all = ECanaRegs.CANES.all;
    } while(ECanaShadow.CANES.bit.CCE != 0 );         // Wait for CCE bit to be  cleared..

/* Disable all Mailboxes  */
    ECanaRegs.CANME.all = 0;               // 在寫入MSGID前,先將CAN Mailbox關閉

    EDIS;
}

----------------------------------------------------------------------

void InitECanaGpio(void)
{
   EALLOW;

/* Enable internal pull-up for the selected CAN pins */
// Pull-ups can be enabled or disabled by the user.
// This will enable the pullups for the specified pins.
// Comment out other unwanted lines.

    GpioCtrlRegs.GPAPUD.bit.GPIO30 = 0;        // 關閉GPIO30內部Pullup
    GpioCtrlRegs.GPAPUD.bit.GPIO31 = 0;        // 關閉GPIO31內部Pullup
                                        
/* Set qualification for selected CAN pins to asynch only */
// Inputs are synchronized to SYSCLKOUT by default.
// This will select asynch (no qualification) for the selected pins.

    GpioCtrlRegs.GPAQSEL2.bit.GPIO30 = 3;   // Asynch qual for GPIO30 (CANRXA)
                                                                               //"3"表示Asychronous Qualification
/* Configure eCAN-A pins using GPIO regs*/
// This specifies which of the possible GPIO pins will be eCAN functional pins.
    GpioCtrlRegs.GPAMUX2.bit.GPIO30 = 1;    // Configure GPIO30 for CANRXA operation
    GpioCtrlRegs.GPAMUX2.bit.GPIO31 = 1;    // Configure GPIO31 for CANTXA operation

    EDIS;

}