This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

TMS320F280049: F280049 DCAN寄存器版收发问题

Part Number: TMS320F280049
Other Parts Discussed in Thread: C2000WARE

你好!附件是我使用寄存器配置F280049 DCAN收发的工程,但是收发失败,监控寄存器没有数据,请帮忙分析一下原因,看看配置哪里出了问题,谢谢!

  • #include "F28x_Project.h"
    #include "device.h"
    #include "math.h"
    
    ///////////DCan////////////////////////////
    typedef struct{
        Uint32 cob_id_ext:18;
        Uint32 cob_id:11;
        Uint32 rtr:1;
        Uint32 rsvd1:2;
    }CanFrameIdStr;
    
    typedef union{
        Uint32 frame_id;
        CanFrameIdStr strct;
    }CanFrameId;
    
    typedef struct{
        CanFrameId id;
        Uint8 len;
        Uint32  hdata;
        Uint32  ldata;
    }CanFrame;
    
    
    
    //////////////////////////////////////////////////
    void InitCan(void);
    
    int CanAppTx(int no,CanFrame *tx_frame);
    int CanAppRx(int no,CanFrame *rx_frame);
    
    //
    uint16_t Save_data;
    uint16_t can_tx_result;
    uint16_t can_rx_result;
    
    CanFrame tx_data;
    CanFrame rx_data;
    
    
    void main(void)
    {
        // 初始化时钟和外设 Initialize device clock and peripherals
        Device_init();
        // InitSysCtrl();  //本工程不能使用寄存器的InitSysCtrl();函数初始化。
    
        /*//库函数版配置
        // 初始化GPIO并设置为推挽输出 Initialize GPIO and configure the GPIO pin as a push-pull output
        Device_initGPIO();
        */
        InitGpio();  //寄存器指令配置
    
        //
        InitCan();
    
        // 初始化PIE并清空PIE寄存器,关闭CPU中断
        // Initialize PIE and clear PIE registers. Disables CPU interrupts.
        Interrupt_initModule();
    
        // 初始化PIE向量表
        // Initialize the PIE vector table with pointers to the shell Interrupt
        // Service Routines (ISR).
        Interrupt_initVectorTable();
    
        // Enable Global Interrupt (INTM) and realtime interrupt (DBGM)
        EINT;
        ERTM;
    
        for(;;)
        {
            //
            tx_data.ldata =0x1234;
            tx_data.hdata =0x4567;
            tx_data.len   =8;
            tx_data.id.frame_id = 0x256;
    
            can_tx_result = CanAppTx(0,&tx_data);
    
    
            //
            can_rx_result = CanAppRx(0,&rx_data);
    
        }
    }
    
    /////////////////////////////DCan////////////////////////////
    void InitCan( void )
    {
        int i;
    
        EALLOW;
        //引脚配置*************************************************
        //CAN_B_RX
        //mux = 2(0010)
        GpioCtrlRegs.GPAGMUX1.bit.GPIO13       = 0x0;//10
        GpioCtrlRegs.GPAMUX1.bit.GPIO13        = 0x2;//10
        GpioCtrlRegs.GPADIR.bit.GPIO13         = 0x0; //设置为输入
        GpioCtrlRegs.GPAPUD.bit.GPIO13         = 0x0; //使能上拉电阻
    
        //CAN_B_TX
        //mux = 2(0010)
        GpioCtrlRegs.GPAGMUX1.bit.GPIO12       = 0x0;//10
        GpioCtrlRegs.GPAMUX1.bit.GPIO12        = 0x2;//10
        GpioCtrlRegs.GPADIR.bit.GPIO12         = 0x1; //设置为输出
        GpioCtrlRegs.GPAPUD.bit.GPIO12        = 0x0; //使能上拉电阻
    
        //初始化开始*************************************************
        CanbRegs.CAN_CTL.bit.Init   = 1;
        CanbRegs.CAN_CTL.bit.CCE  = 1;
        /*设置寄存器写方向,将arb和mctl写入消息对象*/
        //CAN_IF1CMD
        while(CanbRegs.CAN_IF1CMD.bit.Busy)
        {
            ;
        }
        CanbRegs.CAN_IF1CMD.bit.DIR       = 1;
        CanbRegs.CAN_IF1CMD.bit.Mask      = 1;
        CanbRegs.CAN_IF1CMD.bit.Arb       = 1;
        CanbRegs.CAN_IF1CMD.bit.Control   = 1;
        CanbRegs.CAN_IF1MSK.all           = 0;
        CanbRegs.CAN_IF1ARB.bit.MsgVal    = 1;
        CanbRegs.CAN_IF1MCTL.bit.UMask    = 1;
        //CAN_IF2CMD
        while(CanbRegs.CAN_IF2CMD.bit.Busy)
        {
            ;
        }
        CanbRegs.CAN_IF2CMD.bit.DIR       = 1;
        CanbRegs.CAN_IF2CMD.bit.Mask      = 1;
        CanbRegs.CAN_IF2CMD.bit.Arb       = 1;
        CanbRegs.CAN_IF2CMD.bit.Control   = 1;
        CanbRegs.CAN_IF2MSK.all           = 0;
        CanbRegs.CAN_IF2ARB.bit.MsgVal    = 1;
        CanbRegs.CAN_IF2ARB.bit.Dir       = 1;
        CanbRegs.CAN_IF2MCTL.bit.UMask    = 1;
        CanbRegs.CAN_IF2MCTL.bit.RmtEn    = 1;
    
        /*1-16是接收,17-32是发送*/
        for(i=1;i<=16;i++)
        {
            CanbRegs.CAN_IF1CMD.bit.MSG_NUM =i;
            while(CanbRegs.CAN_IF1CMD.bit.Busy)
            {
                ;
            }
    
            CanbRegs.CAN_IF2CMD.bit.MSG_NUM =i + 16;
            while(CanbRegs.CAN_IF2CMD.bit.Busy)
            {
                ;
            }
        }
    
        /*最后一个设置为EOB,表示fifo的末尾*/
        CanbRegs.CAN_IF1MCTL.bit.EoB    = 1;
        CanbRegs.CAN_IF2MCTL.bit.EoB    = 1;
    
        CanbRegs.CAN_IF1CMD.bit.MSG_NUM =16;
        while(CanbRegs.CAN_IF1CMD.bit.Busy)
        {
            ;
        }
    
        CanbRegs.CAN_IF2CMD.bit.MSG_NUM =32;
        while(CanbRegs.CAN_IF2CMD.bit.Busy)
        {
            ;
        }
    
        /*设置寄存器读方向,清除mctl的intpnd和newdat位*/
    
        CanbRegs.CAN_IF1CMD.bit.TXRQST       = 1;
        CanbRegs.CAN_IF1CMD.bit.ClrIntPnd    = 1;
    
        CanbRegs.CAN_IF2CMD.bit.TxRqst       = 1;
        CanbRegs.CAN_IF2CMD.bit.ClrIntPnd    = 1;
    
        for(i=1;i<=16;i++)
        {
            CanbRegs.CAN_IF1CMD.bit.MSG_NUM =i;
            while(CanbRegs.CAN_IF1CMD.bit.Busy)
            {
                ;
            }
    
            CanbRegs.CAN_IF2CMD.bit.MSG_NUM =i + 16;
            while(CanbRegs.CAN_IF2CMD.bit.Busy)
            {
                ;
            }
    
        }
    
    
        volatile  Uint32  discardRead  = CanbRegs.CAN_ES.all;  //错误信息
    
        /*波特率设置500k*/
    
        ClkCfgRegs.CLKSRCCTL2.bit.CANBBCLKSEL = 0;  //内部时钟100MHz
    
        CanbRegs.CAN_BTR.bit.BRP      = 9;
        CanbRegs.CAN_BTR.bit.TSEG1    = 10;
        CanbRegs.CAN_BTR.bit.TSEG2    = 7;
        CanbRegs.CAN_BTR.bit.SJW      =3;
    
    
    
        //
        CanbRegs.CAN_CTL.bit.DAR  = 1;
        CanbRegs.CAN_CTL.bit.ABO  = 1;
    
        //完成复位
        CanbRegs.CAN_CTL.bit.Init  = 0;
        CanbRegs.CAN_CTL.bit.CCE  = 0;
    
        EDIS;
    
    }
    //*************接收数据***************************************
    int CanAppTx(int no,CanFrame *tx_frame)
    {
        Uint32 regbase;
        Uint32 cmd_regdata=0;
        Uint32 arb_regdata=0;
        Uint32 mctl_regdata=0;
        Uint32 dataA=0,dataB=0;
    
        int i,j;
        if(no==0)
        {
            //regbase = CANA_BASE;
        }
        else
        {
            //regbase = CANB_BASE;
        }
    
        //错误复位
        if(CanbRegs.CAN_ES.bit.EWarn)
        {
            CanbRegs.CAN_CTL.bit.Init = 1;
            CanbRegs.CAN_CTL.bit.SWR  = 1;
            CanbRegs.CAN_CTL.bit.DAR  = 1;
            CanbRegs.CAN_CTL.bit.ABO  = 1;
            CanbRegs.CAN_CTL.bit.Init = 0;
            return(0);
        }
    
    
        //
        while(CanbRegs.CAN_IF1CMD.bit.Busy)
        {
            ;
        }
        CanbRegs.CAN_IF1CMD.bit.Arb      = 1;
        CanbRegs.CAN_IF1CMD.bit.Mask     = 1;
        CanbRegs.CAN_IF1CMD.bit.Control  = 1;
        /*从17-32中寻找可以发送的邮箱*/
        for(i=17;i<=32;i++)
        {
            CanbRegs.CAN_IF1CMD.bit.MSG_NUM = i;
            while(CanbRegs.CAN_IF1CMD.bit.Busy)
            {
                ;
            }
            if(CanbRegs.CAN_IF1MCTL.bit.TxRqst==0)
            {
                break;
            }
        }
    
        if(i>=33)
        {
            return(-1);
        }
    
        /*读取当前邮箱配置信息*/
        CanbRegs.CAN_IF1CMD.bit.Control = 1;
        CanbRegs.CAN_IF1CMD.bit.MSG_NUM = i;
        while(CanbRegs.CAN_IF1CMD.bit.Busy)
        {
            ;
        }
    
        //
        CanbRegs.CAN_IF1CMD.bit.DIR = 1;
        CanbRegs.CAN_IF1CMD.bit.Arb = 1;
        CanbRegs.CAN_IF1CMD.bit.Control = 1;
        CanbRegs.CAN_IF1CMD.bit.DATA_A =1;
        CanbRegs.CAN_IF1CMD.bit.DATA_B =1;
        if(tx_frame->id.strct.rtr==0)
        {
            CanbRegs.CAN_IF1ARB.bit.Dir =1;
            CanbRegs.CAN_IF1ARB.bit.MsgVal =1;
            CanbRegs.CAN_IF1ARB.bit.ID = tx_frame->id.frame_id;
            CanbRegs.CAN_IF1MCTL.bit.TxRqst =0;
            CanbRegs.CAN_IF1MCTL.bit.DLC = tx_frame->len;
            CanbRegs.CAN_IF1MCTL.bit.TxRqst =1;
            //
            for(j=0;j<4;j++)
            {
                dataA = dataA<<8;
                dataA |= (tx_frame->hdata>>(j<<3))&0x0FF;
            }
    
            for(j=0;j<4;j++)
            {
                dataB = dataB<<8;
                dataB |= (tx_frame->ldata>>(j<<3))&0x0FF;
            }
    
        }
        else
        {
            CanbRegs.CAN_IF1MCTL.bit.DLC = tx_frame->len;
            CanbRegs.CAN_IF1MCTL.bit.TxRqst = 1;
        }
        //
        CanbRegs.CAN_IF1CMD.bit.MSG_NUM = i;
        while(CanbRegs.CAN_IF1CMD.bit.Busy)
        {
            ;
        }
    
    }
    
    //*************接收数据*******************************************
    /*1---rcv ok 0---no msg -1---msg lost*/
    int CanAppRx(int no,CanFrame *rx_frame)
    {
        Uint32 cmd_regdata=0;
        Uint32 arb_regdata=0;
        Uint32 mctl_regdata=0;
        Uint32 regbase;
        int i,j;
    
        //错误复位
        if(CanbRegs.CAN_ES.bit.EWarn)
        {
            CanbRegs.CAN_CTL.bit.Init = 1;
            CanbRegs.CAN_CTL.bit.SWR  = 1;
            CanbRegs.CAN_CTL.bit.DAR  = 1;
            CanbRegs.CAN_CTL.bit.ABO  = 1;
            CanbRegs.CAN_CTL.bit.Init = 0;
            return(0);
        }
    
        //
        while(CanbRegs.CAN_IF2CMD.bit.Busy)
        {
            ;
        }
        CanbRegs.CAN_IF2CMD.bit.Arb     = 1;
        CanbRegs.CAN_IF2CMD.bit.Control = 1;
        CanbRegs.CAN_IF2CMD.bit.DATA_A  = 1;
        CanbRegs.CAN_IF2CMD.bit.DATA_B  = 1;
        //
    
        for(i=1;i<=32;i++)
        {
            CanbRegs.CAN_IF2CMD.bit.MSG_NUM = i;
            while(CanbRegs.CAN_IF2CMD.bit.Busy)
            {
                ;
            }
            if(CanbRegs.CAN_IF2MCTL.bit.NewDat !=0)
            {
                break;
            }
        }
    
        //
        if(i>=17)
        {
            return(0);
        }
    
        if(CanbRegs.CAN_IF2MCTL.bit.MsgLst!=0)
        {
            return(-1);
        }
    
        //
    
        CanbRegs.CAN_IF2CMD.bit.Arb     = 1;
        CanbRegs.CAN_IF2CMD.bit.Mask    = 1;
        CanbRegs.CAN_IF2CMD.bit.Control = 1;
        CanbRegs.CAN_IF2CMD.bit.DATA_A  = 1;
        CanbRegs.CAN_IF2CMD.bit.DATA_B  = 1;
    
        CanbRegs.CAN_IF2CMD.bit.MSG_NUM = i;
        while(CanbRegs.CAN_IF2CMD.bit.Busy)
        {
            ;
        }
    
        //
        rx_frame->id.frame_id = 0;
        if(((CanbRegs.CAN_IF2ARB.bit.Dir)&&(!(CanbRegs.CAN_IF2MCTL.bit.TxRqst)))||
          ((!(CanbRegs.CAN_IF2ARB.bit.Dir))&&(CanbRegs.CAN_IF2MCTL.bit.TxRqst)))
        {
            rx_frame->id.strct.rtr = 1;
        }
    
        //
        rx_frame->id.frame_id |= CanbRegs.CAN_IF2ARB.bit.ID;  //获取报文ID
        rx_frame->len          = CanbRegs.CAN_IF2MCTL.bit.DLC; //获取报文长度
        //获取数据
        if(rx_frame->id.strct.rtr==0)
        {
            for(j=0;j<4;j++)
            {
                rx_frame->hdata  = CanbRegs.CAN_IF2DATB.all;
            }
    
            for(j=0;j<4;j++)
            {
                rx_frame->ldata = CanbRegs.CAN_IF2DATA.all;;
            }
        }
        else
        {
            rx_frame->hdata = 0;
            rx_frame->ldata = 0;
        }
    
        //
        CanbRegs.CAN_IF2CMD.bit.TxRqst = 1;
        CanbRegs.CAN_IF2CMD.bit.MSG_NUM = i;
        while(CanbRegs.CAN_IF2CMD.bit.Busy)
        {
            ;
        }
    
        return(1);
    
    }
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    
    

  • 8204.F280049C_Template.zip附件是整个工程,盼望回复,谢谢!

  • 你好,具体是transmit还是receive的寄存器没有反应?

    一般这款芯片都是基于driverlib编写的,看寄存器的话得花点时间,你有大概的方向说明一下吗?

  • 你好!收发寄存都没有数据。我是想参照库函数版本完成DCAN数据的收发功能,用1-16号邮箱作为接收,17-32号邮箱作为发送。其中发送时要先查询邮箱是否可用,不需要等待发送,譬如:当前是想用17号邮箱发送先看看17号邮箱是否空闲如果空闲就直接发送,如果17号邮箱正忙就自加到18号邮箱以此类推。谢谢!

  • 7701.F280049C_Template.zip我对照手册发现了几个问题,并更新了代码,但是还是没能实现DCAN报文的发送和接收功能,请帮忙看看分析一下原因,谢谢!

  • 你好,因为没经手过这款芯片的DCAN寄存器方式编程,我将你的工程的关键代码发送到英文E2E论坛咨询了一下,但是对方也没给出具体的问题所在,但是给出了2点建议,你可以参考一下:

    https://e2e.ti.com/support/microcontrollers/c2000-microcontrollers-group/c2000/f/c2000-microcontrollers-forum/1026132/tms320f280049-configure-can-module-in-register-mode 

  • 好的,感谢。其实,硬件是没有问题的,通过库函数配置已经验证过没有问题,现在就是想通过寄存器来配置,可以跟英文E2E论坛人员沟通一下c200ware的demod都是库函数配置,能否把C200WARE里面的这些DEMO出个寄存器版本的,谢谢!

  • 其实有些模块是有寄存器版本的,比如SCI,寄l存器版本的例程可以在这个路径找到:C:\ti\c2000\C2000Ware_3_04_00_00\device_support\f28004x\examples

    但是例程不多,而且没有CAN模块的,不知道后续会不会更新。