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.

IWR6843ISK: Adding CANFD to mmWave SDK Out of Box Demo Hard-Coded Config Version

Part Number: IWR6843ISK
Other Parts Discussed in Thread: UNIFLASH, , MMWAVEICBOOST, AWR1642

I have an IWR6843ISK and MMWAVEICBOOST and am trying to add CANFD transmission to the HCC out of box demo from the Industrial Toolbox. But I can only get it to work if I start debugging in CCS and then terminate debugging at any time before the sensor starts. If I terminate debugging after the sensor starts, just let it run, or flash the bin to the board with UniFlash, I get no output on the can bus.

Here is the code I have added to the demo:

CANFD_Handle                canHandle;
CANFD_MsgObjHandle          canTxMsgHandle;
volatile int                can_tx_done = 0;

static void CANFD_writeTestMsg()
{
    int32_t errCode = 0;

    uint8_t data[64];
    data[0] = 0x34;
    data[1] = 0x65;
    data[2] = 0xC9;
    uint32_t msgId = 65;
    int32_t retVal = CANFD_transmitData(canTxMsgHandle, msgId, CANFD_MCANFrameType_FD, sizeof(data), data, &errCode);
    if(retVal != 0)
    {
        can_tx_done = -1;
    }

    while(can_tx_done == 0);
    can_tx_done = 0;
}

static void cb_canfd_error(CANFD_Handle handle, CANFD_Reason reason, CANFD_ErrStatusResp* errStatusResp)
{
    can_tx_done = -100 - (int)reason;
}

static void cb_canfd_data(CANFD_MsgObjHandle handle, CANFD_Reason reason)
{
    switch(reason)
    {
    case CANFD_Reason_TX_COMPLETION:
        break;
    case CANFD_Reason_RX:
        break;
    case CANFD_Reason_TX_CANCELED:
        break;
    default:
        break;
    }
    can_tx_done = 200 + (int)reason;
}

static int32_t CANFD_config_timing(CANFD_Handle canHandle)
{
    /* Configuring 1Mbps and 5Mbps as nominal and data bit-rate respectively
         Prop seg: 8
         Ph seg 1: 6
         Ph Seg2 : 5
         Sync jump: 1
         BRP(Baud rate Prescaler): 2

         Nominal Bit rate = (40)/(((8+6+5)+1)*BRP) = 1Mhz

         Timing Params for Data Bit rate:
         Prop seg: 2
         Ph seg 1: 2
         Ph Seg2 : 3
         Sync jump: 1
         BRP(Baud rate Prescaler): 1

         Nominal Bit rate = (40)/(((2+2+3)+1)*BRP) = 5Mhz
     */

    CANFD_MCANBitTimingParams   mcanBitTimingParams;

    mcanBitTimingParams.nomBrp      = 0x2U;
    mcanBitTimingParams.nomPropSeg  = 0x8U;
    mcanBitTimingParams.nomPseg1    = 0x6U;
    mcanBitTimingParams.nomPseg2    = 0x5U;
    mcanBitTimingParams.nomSjw      = 0x1U;

    /*5MHz*/
    mcanBitTimingParams.dataBrp     = 0x1U;
    mcanBitTimingParams.dataPropSeg = 0x2U;
    mcanBitTimingParams.dataPseg1   = 0x2U;
    mcanBitTimingParams.dataPseg2   = 0x3U;
    mcanBitTimingParams.dataSjw     = 0x1U;

    int32_t errCode = 0;
    int32_t retVal = CANFD_configBitTime (canHandle, &mcanBitTimingParams, &errCode);
    if (retVal < 0)
    {
        System_printf("Error: CANFD Module configure bit time failed [Error code %d]\n", errCode);
        return -1;
    }
    System_printf("CANFD_configBitTime successful.\n");
    return 0;
}

static CANFD_Handle setup_CANFD()
{
    // information taken from mmWave SDK Docs and <mmWave SDK path>\packages\ti\drivers\canfd\test\xwr68xx\main.c
    CANFD_Handle canHandle = NULL;
    int32_t errCode = 0;

    // Intialize MCAN Config Params===========================================================================================
    CANFD_MCANInitParams mcanCfgParams;
    memset (&mcanCfgParams, sizeof(CANFD_MCANInitParams), 0);

    mcanCfgParams.fdMode          = 0x1U;
    mcanCfgParams.brsEnable       = 0x1U;
    mcanCfgParams.txpEnable       = 0x0U;
    mcanCfgParams.efbi            = 0x0U;
    mcanCfgParams.pxhddisable     = 0x0U;
    mcanCfgParams.darEnable       = 0x1U;
    mcanCfgParams.wkupReqEnable   = 0x1U;
    mcanCfgParams.autoWkupEnable  = 0x1U;
    mcanCfgParams.emulationEnable = 0x0U;
    mcanCfgParams.emulationFAck   = 0x0U;
    mcanCfgParams.clkStopFAck     = 0x0U;
    mcanCfgParams.wdcPreload      = 0x0U;
    mcanCfgParams.tdcEnable       = 0x1U;
    mcanCfgParams.tdcConfig.tdcf  = 0U;
    mcanCfgParams.tdcConfig.tdco  = 8U;
    mcanCfgParams.monEnable       = 0x0U;
    mcanCfgParams.asmEnable       = 0x0U;
    mcanCfgParams.tsPrescalar     = 0x0U;
    mcanCfgParams.tsSelect        = 0x0U;
    mcanCfgParams.timeoutSelect   = CANFD_MCANTimeOutSelect_CONT;
    mcanCfgParams.timeoutPreload  = 0x0U;
    mcanCfgParams.timeoutCntEnable= 0x0U;
    mcanCfgParams.filterConfig.rrfe        = 0x1U;
    mcanCfgParams.filterConfig.rrfs        = 0x1U;
    mcanCfgParams.filterConfig.anfe        = 0x3U;
    mcanCfgParams.filterConfig.anfs        = 0x3U;
    mcanCfgParams.msgRAMConfig.lss         = 127U;
    mcanCfgParams.msgRAMConfig.lse         = 64U;
    mcanCfgParams.msgRAMConfig.txBufNum    = 32U;
    mcanCfgParams.msgRAMConfig.txFIFOSize  = 0U;
    mcanCfgParams.msgRAMConfig.txBufMode   = 0U;
    mcanCfgParams.msgRAMConfig.txEventFIFOSize         = 0U;
    mcanCfgParams.msgRAMConfig.txEventFIFOWaterMark    = 0U;
    mcanCfgParams.msgRAMConfig.rxFIFO0size             = 64U;
    mcanCfgParams.msgRAMConfig.rxFIFO0OpMode           = 0U;
    mcanCfgParams.msgRAMConfig.rxFIFO0waterMark        = 0U;
    mcanCfgParams.msgRAMConfig.rxFIFO1size             = 64U;
    mcanCfgParams.msgRAMConfig.rxFIFO1waterMark        = 0U;
    mcanCfgParams.msgRAMConfig.rxFIFO1OpMode           = 0U;

    mcanCfgParams.eccConfig.enable         = 1U;
    mcanCfgParams.eccConfig.enableChk      = 1U;
    mcanCfgParams.eccConfig.enableRdModWr  = 1U;

    mcanCfgParams.errInterruptEnable   = 1U;
    mcanCfgParams.dataInterruptEnable  = 1U;
    mcanCfgParams.appErrCallBack       = cb_canfd_error;
    mcanCfgParams.appDataCallBack      = cb_canfd_data;
    // ===========================================================================================================================

    // init CANFD driver
    System_printf("Trying CANFD_init...\n");
    canHandle = CANFD_init(0, &mcanCfgParams, &errCode);
    if (canHandle == NULL)
    {
        System_printf("Error: CANFD Module Initialization failed [Error code %d]\n", errCode);
        return NULL;
    }
    System_printf("CANFD_init successful.\n");

    // ========================================================================================================================
    CANFD_config_timing(canHandle);
    // ========================================================================================================================
    return canHandle;
}

static CANFD_MsgObjHandle setup_CANFD_msg(CANFD_Handle canHandle)
{
    CANFD_MCANMsgObjCfgParams   txMsgObjectParams;
    int32_t                     errCode = 0;
    CANFD_MsgObjHandle          txMsgObjHandle = NULL;

    /* Setup the transmit message object */
    txMsgObjectParams.direction = CANFD_Direction_TX;
    txMsgObjectParams.msgIdType = CANFD_MCANXidType_11_BIT;
    txMsgObjectParams.msgIdentifier = 0x29E;

    txMsgObjHandle = CANFD_createMsgObject(canHandle, &txMsgObjectParams, &errCode);
    if (txMsgObjHandle == NULL)
    {
        System_printf("Error: CANFD create Tx message object failed [Error code %d]\n", errCode);
        return NULL;
    }
    System_printf("CANFD_createMsgObject successful.\n");
    return txMsgObjHandle;
}

void CAN_init()
{
    System_printf("Init peripheral clock...\n");
    int32_t ret = 0;
    int32_t errCode = 0;
    /* Configure the divide value for MCANA source clock */
    ret = SOC_setPeripheralClock(gMmwMssMCB.socHandle, SOC_MODULE_MCANA, SOC_CLKSOURCE_VCLK, 4U, &errCode);
    if(ret != 0) System_printf("Error 1: %d\n", errCode);

    /* Configure the divide value for MCANB source clock */
    ret = SOC_setPeripheralClock(gMmwMssMCB.socHandle, SOC_MODULE_MCANB, SOC_CLKSOURCE_VCLK, 4U, &errCode);
    if(ret != 0) System_printf("Error 2: %d\n", errCode);

    System_printf("Pinmux...\n");
    /* Setup the PINMUX to bring out the XWR68xx CANFD pins */
    Pinmux_Set_OverrideCtrl(SOC_XWR68XX_PINE14_PADAE, PINMUX_OUTEN_RETAIN_HW_CTRL, PINMUX_INPEN_RETAIN_HW_CTRL);
    Pinmux_Set_FuncSel(SOC_XWR68XX_PINE14_PADAE, SOC_XWR68XX_PINE14_PADAE_CANFD_TX);

    Pinmux_Set_OverrideCtrl(SOC_XWR68XX_PIND13_PADAD, PINMUX_OUTEN_RETAIN_HW_CTRL, PINMUX_INPEN_RETAIN_HW_CTRL);
    Pinmux_Set_FuncSel(SOC_XWR68XX_PIND13_PADAD, SOC_XWR68XX_PIND13_PADAD_CANFD_RX);

    /* Setup the PINMUX to bring out the XWR68xx CANFD-2 pins */
    Pinmux_Set_OverrideCtrl(SOC_XWR68XX_PINE15_PADAG, PINMUX_OUTEN_RETAIN_HW_CTRL, PINMUX_INPEN_RETAIN_HW_CTRL);
    Pinmux_Set_FuncSel(SOC_XWR68XX_PINE15_PADAG, SOC_XWR68XX_PINE15_PADAG_CANFD2_TX);

    Pinmux_Set_OverrideCtrl(SOC_XWR68XX_PINE13_PADAF, PINMUX_OUTEN_RETAIN_HW_CTRL, PINMUX_INPEN_RETAIN_HW_CTRL);
    Pinmux_Set_FuncSel(SOC_XWR68XX_PINE13_PADAF, SOC_XWR68XX_PINE13_PADAF_CANFD2_RX);

    System_printf("Initilizing CAN FD...\n");
    canHandle = setup_CANFD();
    if (canHandle == NULL)
    {
        MmwDemo_debugAssert (0);
        return;
    }
    canTxMsgHandle = setup_CANFD_msg(canHandle);
    if (canTxMsgHandle == NULL)
    {
        MmwDemo_debugAssert (0);
        return;
    }
}

Most of this code is copied directly from the canfd driver test in the mmwave sdk. I call CAN_init() at the end of the MmwDemo_initTask function from the demo and I call CANFD_writeTestMsg() at the end of the MmwDemo_transmitProcessedOutput function. Again, everything works perfectly, but only if I start debugging, and then terminate debugging before the sensor is started.

On another note, breakpoints I set in MmwDemo_transmitProcessedOutput don't seem to work. Is it not possible to use breakpoints in functions called from interrupts?

I am building the code with optimization disabled and none of the options to disable interrupts are enabled.