请选择 进入手机版 | 继续访问电脑版
查看: 1175|回复: 1

[分享] LPC55S16的CAN_FD初探

[复制链接]
  • TA的每日心情

    昨天 18:23
  • 签到天数: 588 天

    [LV.9]以坛为家II

    31

    主题

    1342

    帖子

    0

    金牌会员

    Rank: 6Rank: 6

    积分
    3564
    最后登录
    2024-4-16
    发表于 2020-11-8 22:45:19 | 显示全部楼层 |阅读模式
    本帖最后由 maoyanmcu 于 2020-11-8 22:47 编辑

    本人本身不是弄CAN总线通信的,所以日常使用CAN是比较少的。
    所以我是这篇就是直接参考了别人的一些资料来的,CAN_FD应该可以说是CAN的升级了,波特率更高,数据帧更长。帧结构也是发生了变化。
    1604845967(1).jpg
    1604846011(1).jpg
    本次实验在官方例程下可以找到。loopback是回环测试,外部不需要接CAN芯片就能直接测试。我选择上一个工程测试。
    1604846316(1).jpg
    外围电路使用一颗,TJA1050T芯片,作为收发芯片,物理层上不需要改变什么东西,只是协议上的变化。
    1.    MCAN_Init(EXAMPLE_MCAN, &mcanConfig, MCAN_CLK_FREQ);

    2.     /* Create MCAN handle structure and set call back function. */
    3.     MCAN_TransferCreateHandle(EXAMPLE_MCAN, &mcanHandle, mcan_callback, NULL);

    4.     /* Set Message RAM base address and clear to avoid BEU/BEC error. */
    5.     MCAN_SetMsgRAMBase(EXAMPLE_MCAN, MSG_RAM_BASE);
    6.     uint32_t *p = (uint32_t *)(MSG_RAM_BASE);
    7.     memset(p, 0, (8U + CAN_DATASIZE) * sizeof(uint8_t));

    8.     /* STD filter config. */
    9.     rxFilter.address  = STD_FILTER_OFS;
    10.     rxFilter.idFormat = kMCAN_FrameIDStandard;
    11.     rxFilter.listSize = 1U;
    12.     rxFilter.nmFrame  = kMCAN_reject0;
    13.     rxFilter.remFrame = kMCAN_rejectFrame;
    14.     MCAN_SetFilterConfig(EXAMPLE_MCAN, &rxFilter);

    15.     stdFilter.sfec = kMCAN_storeinFifo0;
    16.     /* Classic filter mode, only filter matching ID. */
    17.     stdFilter.sft   = kMCAN_classic;
    18.     stdFilter.sfid1 = rxIdentifier;
    19.     stdFilter.sfid2 = 0x7FFU;
    20.     MCAN_SetSTDFilterElement(EXAMPLE_MCAN, &rxFilter, &stdFilter, 0);

    21.     /* RX fifo0 config. */
    22.     rxFifo0.address       = RX_FIFO0_OFS;
    23.     rxFifo0.elementSize   = 1U;
    24.     rxFifo0.watermark     = 0;
    25.     rxFifo0.opmode        = kMCAN_FifoBlocking;
    26.     rxFifo0.datafieldSize = kMCAN_8ByteDatafield;
    27. #if (defined(USE_CANFD) && USE_CANFD)
    28.     rxFifo0.datafieldSize = BYTES_IN_MB;
    29. #endif
    30.     MCAN_SetRxFifo0Config(EXAMPLE_MCAN, &rxFifo0);

    31.     /* TX buffer config. */
    32.     memset(&txBuffer, 0, sizeof(txBuffer));
    33.     txBuffer.address       = TX_BUFFER_OFS;
    34.     txBuffer.dedicatedSize = 1U;
    35.     txBuffer.fqSize        = 0;
    36.     txBuffer.datafieldSize = kMCAN_8ByteDatafield;
    37. #if (defined(USE_CANFD) && USE_CANFD)
    38.     txBuffer.datafieldSize = BYTES_IN_MB;
    39. #endif
    40.     MCAN_SetTxBufferConfig(EXAMPLE_MCAN, &txBuffer);

    41.     /* Finish software initialization and enter normal mode, synchronizes to
    42.        CAN bus, ready for communication */
    43.     MCAN_EnterNormalMode(EXAMPLE_MCAN);

    44.     if ((node_type == 'A') || (node_type == 'a'))
    45.     {
    46.         PRINTF("Press any key to trigger one-shot transmission\r\n\r\n");
    47.     }
    48.     else
    49.     {
    50.         PRINTF("Start to Wait data from Node A\r\n\r\n");
    51.     }

    52.     while (1)
    53.     {
    54.         if ((node_type == 'A') || (node_type == 'a'))
    55.         {
    56.             GETCHAR();
    57.             /* Config TX frame data. */
    58.             memset(tx_data, 0, sizeof(uint8_t) * CAN_DATASIZE);
    59.             for (cnt = 0; cnt < CAN_DATASIZE; cnt++)
    60.             {
    61.                 tx_data[cnt] = cnt;
    62.             }
    63.             tx_data[0] += numMessage++;
    64.             txFrame.xtd  = kMCAN_FrameIDStandard;
    65.             txFrame.rtr  = kMCAN_FrameTypeData;
    66.             txFrame.fdf  = 0;
    67.             txFrame.brs  = 0;
    68.             txFrame.dlc  = 8U;
    69.             txFrame.id   = txIdentifier << STDID_OFFSET;
    70.             txFrame.data = tx_data;
    71.             txFrame.size = CAN_DATASIZE;
    72. #if (defined(USE_CANFD) && USE_CANFD)
    73.             txFrame.fdf = 1;
    74.             txFrame.brs = 1;
    75.             txFrame.dlc = DLC;
    76. #endif
    77.             txXfer.frame     = &txFrame;
    78.             txXfer.bufferIdx = 0;
    79.             MCAN_TransferSendNonBlocking(EXAMPLE_MCAN, &mcanHandle, &txXfer);

    80.             while (!txComplete)
    81.             {
    82.             }
    83.             txComplete = false;

    84.             /* Start receive data through Rx FIFO 0. */
    85.             memset(rx_data, 0, sizeof(uint8_t) * CAN_DATASIZE);
    86.             /* the MCAN engine can't auto to get rx payload size, we need set it. */
    87.             rxFrame.size = CAN_DATASIZE;
    88.             rxXfer.frame = &rxFrame;
    89.             MCAN_TransferReceiveFifoNonBlocking(EXAMPLE_MCAN, 0, &mcanHandle, &rxXfer);

    90.             /* Wait until message received. */
    91.             while (!rxComplete)
    92.             {
    93.             }
    94.             rxComplete = false;

    95.             /* After call the API of rMCAN_TransferReceiveFifoNonBlocking success, we can
    96.              * only get a point (rxFrame.data) to the fifo reading entrance.
    97.              * Copy the received frame data from the FIFO by the pointer(rxFrame.data). */
    98.             memcpy(rx_data, rxFrame.data, rxFrame.size);

    99.             PRINTF("Received Frame ID: 0x%x\r\n", rxFrame.id >> STDID_OFFSET);
    100.             PRINTF("Received Frame DATA: ");
    101.             cnt = 0;
    102.             while (cnt < rxFrame.size)
    103.             {
    104.                 PRINTF("0x%x ", rx_data[cnt++]);
    105.             }
    106.             PRINTF("\r\n");
    107.             PRINTF("Press any key to trigger the next transmission!\r\n\r\n");
    108.         }
    109.         else
    110.         {
    111.             memset(rx_data, 0, sizeof(uint8_t) * CAN_DATASIZE);
    112.             /* the MCAN engine can't auto to get rx payload size, we need set it. */
    113.             rxFrame.size = CAN_DATASIZE;
    114.             rxXfer.frame = &rxFrame;
    115.             MCAN_TransferReceiveFifoNonBlocking(EXAMPLE_MCAN, 0, &mcanHandle, &rxXfer);

    116.             while (!rxComplete)
    117.             {
    118.             }
    119.             rxComplete = false;

    120.             /* After call the API of rMCAN_TransferReceiveFifoNonBlocking success, we can
    121.              * only get a point (rxFrame.data) to the fifo reading entrance.
    122.              * Copy the received frame data from the FIFO by the pointer(rxFrame.data). */
    123.             memcpy(rx_data, rxFrame.data, rxFrame.size);

    124.             PRINTF("Received Frame ID: 0x%x\r\n", rxFrame.id >> STDID_OFFSET);
    125.             PRINTF("Received Frame DATA: ");

    126.             cnt = 0;
    127.             while (cnt < rxFrame.size)
    128.             {
    129.                 PRINTF("0x%x ", rx_data[cnt++]);
    130.             }
    131.             PRINTF("\r\n");

    132.             /* Copy received frame data to tx frame. */
    133.             memcpy(tx_data, rx_data, CAN_DATASIZE);

    134.             txFrame.xtd      = rxFrame.xtd;
    135.             txFrame.rtr      = rxFrame.rtr;
    136.             txFrame.fdf      = rxFrame.fdf;
    137.             txFrame.brs      = rxFrame.brs;
    138.             txFrame.dlc      = rxFrame.dlc;
    139.             txFrame.id       = txIdentifier << STDID_OFFSET;
    140.             txFrame.data     = tx_data;
    141.             txFrame.size     = rxFrame.size;
    142.             txXfer.frame     = &txFrame;
    143.             txXfer.bufferIdx = 0;

    144.             MCAN_TransferSendNonBlocking(EXAMPLE_MCAN, &mcanHandle, &txXfer);

    145.             while (!txComplete)
    146.             {
    147.             }
    148.             txComplete = false;
    149.             PRINTF("Wait Node A to trigger the next transmission!\r\n\r\n");
    150.         }
    151.     }
    复制代码
    具体代码就是我们通过串口发送“A”或者“a”时其CAN就会开始工作,发送数据并等回传数据。
    1604846546(1).jpg
    我是使用了逻辑分析仪测试CAN_H和CAN_L,端口发现是有数据的,不过解码部分就不行了,因为协议对不上。所以数据部分也没有对上。
    后期的话就是可以用两块板相互通信,目前就是验证了下可以发送数据,具体也没太深入研究,算初探吧。还要就是我买了新的J-LINK11发现其在KEIL下还是无法进行仿真,下载完程序后依旧是需要手动复位才能运行程序,不过在官方的IDE MCUXpresso工具中是正常的,不知道哪位有办法解决。
    该会员没有填写今日想说内容.
    回复

    使用道具 举报

  • TA的每日心情
    开心
    7 天前
  • 签到天数: 1335 天

    [LV.10]以坛为家III

    88

    主题

    4292

    帖子

    12

    版主

    Rank: 7Rank: 7Rank: 7

    积分
    9049
    最后登录
    2024-4-13
    发表于 2020-11-9 11:36:36 | 显示全部楼层
    CAN接口 都升级了啊!! 有些out了
    Jlink还停留在v8阶段呢
    该会员没有填写今日想说内容.
    回复 支持 反对

    使用道具 举报

    您需要登录后才可以回帖 注册/登录

    本版积分规则

    关闭

    站长推荐上一条 /4 下一条

    Archiver|手机版|小黑屋|恩智浦技术社区

    GMT+8, 2024-4-17 01:03 , Processed in 0.119242 second(s), 20 queries , MemCache On.

    Powered by Discuz! X3.4

    Copyright © 2001-2021, Tencent Cloud.

    快速回复 返回顶部 返回列表