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.

J722SXH01EVM: Frame loss during CAN transmission

Part Number: J722SXH01EVM

Tool/software:

1.rtos sdk version is j722s-rtos-sdk-v11

2.When debugging the CAN transceiver of TDA4VEN, I encountered an issue: when transmitting and receiving messages simultaneously on the same CAN bus, frame loss occurs during message transmission. The transmission is using the buffer method and receive is using the fifo0.Additionally, the return value of MCAN_txBufAddReq() is normal.

2.1 The CAN baud rate is 500k and the sampling point is 80%

3.vt_can.c and vt_can.h codes are as follows
3.1. The entry function of vt_can.c is int32_t vtcan_init (void), the can send function is int32_t vtcan_txmsg (stCANTypeMsgBaseInfo TxMsgInfo, uint8_t TxMsgBufNum), and the can interrupt is void vtcan_mcan0IntrISR (void *arg)

#include "can/vt_can.h"
#include <stdbool.h>
#include <stdint.h>
#include <string.h>

#define APP_MCAN_TX_BUFF_SIZE                    MCAN0_TOTAL_TX_MSG
#define APP_MCAN_TX_EVENT_FIFO_CNT               (0x0U)
#define APP_MCAN_TX_FIFO_SIZE                    (0U)
#define APP_MCAN_FIFO_0_NUM                      (64U)
#define APP_MCAN_FIFO_1_NUM                      (64U)
#define APP_MCAN_STD_ID_FILTER_NUM               (128U)
#define APP_MCAN_EXT_ID_FILTER_NUM               (0U)

static uint32_t             gMcan0BaseAddr;
static HwiP_Object          gMcan0HwiObject;
static uint32_t Mcan0IsrIntrStatus;
//SemaphoreP_Object gMcan0TxDoneSem, gMcan0RxDoneSem;
MCAN_StdMsgIDFilterElement MCAN0_canSTDIDFilter[MCAN0_TOTAL_RX_MSG];
MCAN_StdMsgIDFilterElement MCAN1_canSTDIDFilter[MCAN1_TOTAL_RX_MSG];

typedef struct{
	uint8_t CAN0BusErr;
    uint8_t CAN1BusErr;
}stBusOffFlagInfo;
stBusOffFlagInfo MCANBusOffInfo;

MCAN_BitTimingParams MCAN0_canFDBitTimings[] =
{
    /* 500kbps 80% and 2000 kbps 80% */
    /* This is default baud*/
    {
        0x0FU, /* Nominal Baud Rate Pre-scaler */
        0x06U, /* Nominal Time segment before sample point */
        0x01U, /* Nominal Time segment after sample point */
        0x00U, /* Nominal (Re)Synchronization Jump Width */
        0x07U, /* Data Baud Rate Pre-scaler */
        0x02U, /* Data Time segment before sample point */
        0x00U, /* Data Time segment after sample point */
        0x00U  /* Data (Re)Synchronization Jump Width */
    },
};

MCAN_InitParams MCAN0_canFDInitParams[] =
{
    {
#ifdef  CAN0_MODULE_CANFD
        0x01U, /* FD Operation Enable */
        0x01U, /* Bit Rate Switch Enable */
#else
        0x00U, /* FD Operation Enable */
        0x00U, /* Bit Rate Switch Enable */
#endif
        0x00U, /* Transmit Pause */
        0x00U, /* FEdge Filtering during Bus Integration */
        0x00U, /* Protocol Exception Handling Disable */
        0x01U, /* Disable Automatic Retransmission */
        0x01U, /* Wakeup Request Enable */
        0x01U, /* Auto-Wakeup Enable */
        0x00U, /* Emulation/Debug Suspend Enable */
        0x00U, /* Emulation/Debug Suspend Fast Ack Enable */
        0x00U, /* Clock Stop Fast Ack Enable */
        0x00U, /* Start value of the Message RAM Watchdog Counter */
        {
            0x0AU, /* Transmitter Delay Compensation Offset */
            0x06U,  /* Transmitter Delay Compensation Filter Window Length */
        },
        0x00U, /* Transmitter Delay Compensation Enable */
    },
};

MCAN_ConfigParams MCAN0_canFDConfigParams[] =
{
    /* Config 0 */
    {
        0x0U, /* Bus Monitoring Mode */
        0x0U, /* Restricted Operation Mode */
        0xFU, /* Timestamp Counter Prescaler */
        0x0U, /* Timestamp source selection */
        MCAN_TIMEOUT_SELECT_CONT, /* Time-out counter source select */
        0xFFFFU, /* Start value of the Timeout Counter (down-counter) */
        0x0U, /* Time-out Counter Enable */
        {
            0x1U, /* Reject Remote Frames Extended */
            0x1U, /* Reject Remote Frames Standard */
            0x2U, /* Accept Non-matching Frames Extended */
            0x2U, /* Accept Non-matching Frames Standard */
        },
    },
};

MCAN_MsgRAMConfigParams MCAN0_canFDRAMConfigParams[] =
{
    {
        .lss = APP_MCAN_STD_ID_FILTER_NUM,      /* List Size: Standard ID */
        .lse = APP_MCAN_EXT_ID_FILTER_NUM,      /* List Size: Extended ID*/
        .txBufCnt = APP_MCAN_TX_BUFF_SIZE,           /* Number of Dedicated Transmit Buffers */
        .txFIFOCnt = APP_MCAN_TX_FIFO_SIZE,            /* Transmit FIFO/Queue Size */
        .txBufMode = MCAN_TX_MEM_TYPE_BUF,                              /* Tx FIFO/Queue Mode */
        .txEventFIFOCnt = APP_MCAN_TX_EVENT_FIFO_CNT,          /* Tx Buffer Element Size */
        .rxFIFO0Cnt = APP_MCAN_FIFO_0_NUM,           /* Event FIFO Size */
        .rxFIFO0OpMode = MCAN_RX_FIFO_OPERATION_MODE_BLOCKING,                              /* Rx FIFO0 Operation Mode */
        .rxFIFO1Cnt = APP_MCAN_FIFO_1_NUM,             /* Rx FIFO1 Size */
        .rxFIFO1OpMode = MCAN_RX_FIFO_OPERATION_MODE_BLOCKING,                              /* Rx FIFO1 Operation Mode */
        .rxBufElemSize = MCAN_ELEM_SIZE_64BYTES,          /* Rx Buffer Element Size */
        .rxFIFO0ElemSize = MCAN_ELEM_SIZE_64BYTES,          /* Rx FIFO0 Element Size */
        .rxFIFO1ElemSize = MCAN_ELEM_SIZE_64BYTES,          /* Rx FIFO1 Element Size */
        .txEventFIFOWaterMark = 0U,                         /* Tx Event FIFO Watermark */
        .rxFIFO0WaterMark = 0U,                         /* RX FIFO0 Watermark */
        .rxFIFO1WaterMark = 0U,                         /* RX FIFO1 FIFO Watermark */
    },
};

st_mcanParams sMCAN0Params[] =
{
    /* mcanConfigParams,
     * printEnable,
     */
    {

        {
            (&MCAN0_canFDBitTimings[0U]), /* mcan module bit timing parameters */
            (&MCAN0_canFDInitParams[0U]), /* mcan module initialization parameters */
            (&MCAN0_canFDConfigParams[0U]), /* mcan module configuration parameters */
            (&MCAN0_canFDRAMConfigParams[0U]), /* mcan module MSG RAM configuration parameters */
            MCAN0_TOTAL_TX_MSG, /* tx message number */
            MCAN0_TOTAL_RX_MSG, /* standard ID message filter number */
            (MCAN_INTR_MASK_ALL),  /* Interrupt Enable/Disable Mask */
            (MCAN_INTR_MASK_ALL),  /* Interrupt Line Select Mask */
            (MCAN_INTR_LINE_NUM_0)  /* Interrupt Line Select */
        },
        TRUE,
    },
};

/**
    return ID:   0, no more message
 */
stCANTypeMsgBaseInfo vtcan_mcan0ReadRxMSG(void)
{
    uint32_t ackIdx = 0;
    stCANTypeMsgBaseInfo RxMsgInfo = { 0 };
    MCAN_RxFIFOStatus fifoStatus = { 0 };
    MCAN_RxBufElement rxMsg;

    memset(&rxMsg, 0x0, sizeof(rxMsg));

    MCAN_getRxFIFOStatus(gMcan0BaseAddr, &fifoStatus);
    // DebugP_log("fifoStatus %d, %d, %d, %d, %d\n", fifoStatus.num, fifoStatus.getIdx, fifoStatus.fillLvl,fifoStatus.putIdx);
    ackIdx = fifoStatus.getIdx;

    if (fifoStatus.fillLvl) {
        MCAN_readMsgRam(gMcan0BaseAddr, MCAN_MEM_TYPE_FIFO, fifoStatus.getIdx, (uint32_t)fifoStatus.num, &rxMsg);
        MCAN_writeRxFIFOAck(gMcan0BaseAddr, (uint32_t)fifoStatus.num, ackIdx);

        RxMsgInfo.ID = rxMsg.id >> MCAN_STD_ID_SHIFT;
        RxMsgInfo.DLC = rxMsg.dlc;
        memcpy(&RxMsgInfo.u8Data, &rxMsg.data, RxMsgInfo.DLC);
    }

    return RxMsgInfo;
}

void vtcan_mcan0IntrISR(void *arg)
{
    uint32_t intrStatus;
    //stCANTypeMsgBaseInfo RxMsgInfo;
    uint32_t rxIntrMask = MCAN_INTR_SRC_DEDICATED_RX_BUFF_MSG |
    MCAN_INTR_SRC_RX_FIFO0_NEW_MSG |
    MCAN_INTR_SRC_RX_FIFO1_NEW_MSG |
    MCAN_INTR_SRC_HIGH_PRIO_MSG;

    intrStatus = MCAN_getIntrStatus(gMcan0BaseAddr);

    MCAN_clearIntrStatus(gMcan0BaseAddr, intrStatus);

    Mcan0IsrIntrStatus = (intrStatus & (~MCAN_getIntrLineSelectStatus(gMcan0BaseAddr)));

    if ((Mcan0IsrIntrStatus & MCAN_INTR_SRC_TRANS_COMPLETE) == MCAN_INTR_SRC_TRANS_COMPLETE)
    {      
        SemaphoreP_post(&gMcan0TxDoneSem);
    }

    if ((Mcan0IsrIntrStatus & rxIntrMask) != 0U)
    {
        if((Mcan0IsrIntrStatus & MCAN_INTR_SRC_DEDICATED_RX_BUFF_MSG) == MCAN_INTR_SRC_DEDICATED_RX_BUFF_MSG)
        {
        }
        else if(((Mcan0IsrIntrStatus & MCAN_INTR_SRC_RX_FIFO0_NEW_MSG)) ||
        ((Mcan0IsrIntrStatus & MCAN_INTR_SRC_RX_FIFO1_NEW_MSG)))
        {
            //RxMsgInfo = vtcan_mcan0ReadRxMSG();
            SemaphoreP_post(&gMcan0RxDoneSem);
        }
    }

    if((Mcan0IsrIntrStatus & MCAN_INTR_SRC_BUS_OFF_STATUS) == MCAN_INTR_SRC_BUS_OFF_STATUS)
    {
        vtcan_BusOffConfirm();
        SemaphoreP_post(&gMcan0TxDoneSem);
    }
}

static void vtcan_mcanGPIOInit(void)
{
    GPIO_setDirMode(CSL_MCU_GPIO0_BASE, VT_CAN_MCU_MCAN0_EN_PIN, GPIO_DIRECTION_OUTPUT);
    GPIO_setDirMode(CSL_MCU_GPIO0_BASE, VT_CAN_MCU_MCAN0_STB_PIN, GPIO_DIRECTION_OUTPUT);
    GPIO_setDirMode(CSL_MCU_GPIO0_BASE, VT_CAN_MCU_MCAN0_ERR_PIN, GPIO_DIRECTION_OUTPUT);
}

void vtcan_mcanTransceiver(uint8_t workmode)
{
	if(workmode == MCAN_TRANSCEIVER_NORMALMODE)
	{
		GPIO_pinWriteHigh(CSL_MCU_GPIO0_BASE, VT_CAN_MCU_MCAN0_EN_PIN);         
		GPIO_pinWriteHigh(CSL_MCU_GPIO0_BASE, VT_CAN_MCU_MCAN0_STB_PIN); 
		GPIO_pinWriteLow(CSL_MCU_GPIO0_BASE, VT_CAN_MCU_MCAN0_ERR_PIN); 
	}else if(workmode == MCAN_TRANSCEIVER_STANDBYMODE)
	{
		GPIO_pinWriteLow(CSL_MCU_GPIO0_BASE, VT_CAN_MCU_MCAN0_STB_PIN);
	} 
}

int32_t vtcan_mcanRegisterInterrupt(void)
{
    int32_t           status = CSL_PASS;
    HwiP_Params       hwiPrms;

	/* Register MCAN0 interrupt */
	HwiP_Params_init(&hwiPrms);
	hwiPrms.intNum      = CONFIG_MCAN0_INTR;
	hwiPrms.callback    = &vtcan_mcan0IntrISR;
	status              = HwiP_construct(&gMcan0HwiObject, &hwiPrms);
	if(status != SystemP_SUCCESS)
	{
		//DebugP_log("\nRegister MCAN0 interrupt FAILED...\n", -1);
	}
	gMcan0BaseAddr = (uint32_t) AddrTranslateP_getLocalAddr(CONFIG_MCAN0_BASE_ADDR);

    return status;
}
 
void vtcan_mcan0FilterAllAtOnce(uint16_t *MsgID)
{
	for(uint8_t i=0;i<MCAN0_TOTAL_RX_MSG;i++)
	{
		MCAN0_canSTDIDFilter[i].sfid2 = MCAN_STD_ID_MASK;
		MCAN0_canSTDIDFilter[i].sfid1 = *(MsgID + i);
		MCAN0_canSTDIDFilter[i].sfec = MCAN_STD_FILT_ELEM_FIFO0;//Store in Rx FIFO 0 if filter matches
		MCAN0_canSTDIDFilter[i].sft = MCAN_STD_FILT_TYPE_CLASSIC;//Classic filter: SFID1 = filter, SFID2 = mask
		/* Configure Standard ID filter element */
		MCAN_addStdMsgIDFilter(gMcan0BaseAddr, i, &MCAN0_canSTDIDFilter[i]);
	} 
}

void vtcan_mcan0FilterOneByOne(uint8_t bank,uint16_t MsgID)
{
	if(bank < MCAN0_TOTAL_RX_MSG)
	{
		MCAN0_canSTDIDFilter[bank].sfid2 = MCAN_STD_ID_MASK;
		MCAN0_canSTDIDFilter[bank].sfid1 = MsgID;
		MCAN0_canSTDIDFilter[bank].sfec = MCAN_STD_FILT_ELEM_FIFO0;//Store in Rx FIFO 0 if filter matches
		MCAN0_canSTDIDFilter[bank].sft = MCAN_STD_FILT_TYPE_CLASSIC;//Classic filter: SFID1 = filter, SFID2 = mask
		/* Configure Standard ID filter element */
		MCAN_addStdMsgIDFilter(gMcan0BaseAddr, bank, &MCAN0_canSTDIDFilter[bank]);
	}
}

static int32_t vtcan_mcanConfig(void)
{
    uint32_t    loopCnt;
    int32_t configStatus = CSL_PASS;
    st_mcanParams *MCAN0Params;

	MCAN0Params = &sMCAN0Params[0];
	/* Put MCAN in SW initialization mode */
	MCAN_setOpMode(gMcan0BaseAddr, MCAN_OPERATION_MODE_SW_INIT);
	while (MCAN_OPERATION_MODE_SW_INIT != MCAN_getOpMode(gMcan0BaseAddr))
	{}

	/* Initialize MCAN module */
	configStatus += MCAN_init(gMcan0BaseAddr, MCAN0Params->mcanConfigParams.initParams);
	if(configStatus != CSL_PASS)
	{
		//DebugP_log("\nMCAN Initialization FAILED...\n", -1);
	}

	/* Configure MCAN module */
	configStatus += MCAN_config(gMcan0BaseAddr, MCAN0Params->mcanConfigParams.configParams);
	if(configStatus != CSL_PASS)
	{
		//DebugP_log("\nMCAN Configuration FAILED...\n", -1);
	}

	/* Configure Bit timings */
	configStatus += MCAN_setBitTime(gMcan0BaseAddr, MCAN0Params->mcanConfigParams.bitTimings);
	if(configStatus != CSL_PASS)
	{
		//DebugP_log("\nMCAN Bit Time Configuration FAILED...\n", -1);
	}

	/* Configure Message RAM Sections */
	configStatus += MCAN_calcMsgRamParamsStartAddr(MCAN0Params->mcanConfigParams.ramConfig);
	if(configStatus != CSL_PASS)
	{
		//DebugP_log("\nMCAN Message RAM Addr Calculation FAILED...\n", -1);
	}

	configStatus += MCAN_msgRAMConfig(gMcan0BaseAddr, MCAN0Params->mcanConfigParams.ramConfig);
	if(configStatus != CSL_PASS)
	{
		//DebugP_log("\nMCAN Message RAM Configuration FAILED...\n", -1);
	}

	//can receive id fifliter
    uint16_t test_mcan0MsgID[] = {0x25F,0x24a,0x162,0x163,0x164,0x152,0x24c,0x262,0x265,0x74,0x112,0x114,0x25c,0x26c,0x82,0xB2,0x285,0x174,0x70,0x14C,0x88,0x90,0x93,0x96,0x98};
    vtcan_mcan0FilterAllAtOnce(test_mcan0MsgID);
	
	/* Take MCAN out of the SW initialization mode */
	MCAN_setOpMode(gMcan0BaseAddr, MCAN_OPERATION_MODE_NORMAL);
	while (MCAN_OPERATION_MODE_NORMAL != MCAN_getOpMode(gMcan0BaseAddr))
	{}

	/* Enable Interrupts */
	MCAN_enableIntr(gMcan0BaseAddr, MCAN0Params->mcanConfigParams.intrEnable,(uint32_t)TRUE);
	/* Select Interrupt Line */
	MCAN_selectIntrLine(gMcan0BaseAddr,MCAN0Params->mcanConfigParams.intrLineSelectMask,MCAN0Params->mcanConfigParams.intrLine);
	/* Enable Interrupt Line */
	MCAN_enableIntrLine(gMcan0BaseAddr,MCAN0Params->mcanConfigParams.intrLine,(uint32_t)TRUE);

	/* Enable interrupts for Tx Buffers */
	for (loopCnt = 0U ;
		loopCnt < MCAN0Params->mcanConfigParams.txMsgNum ;
		loopCnt++)
	{
		/* Enable Transmission interrupt */
		configStatus += MCAN_txBufTransIntrEnable(gMcan0BaseAddr,loopCnt,(uint32_t)TRUE);
		if(configStatus != CSL_PASS)
		{
			//DebugP_log("\nMCAN Tx Buffer Interrupt Enable FAILED...\n", -1);
		}
	}

    return configStatus;
}

static void vtcan_mcanConfigTxMsg(MCAN_TxBufElement *txMsg,stCANTypeMsgBaseInfo TxMsgInfo)
{
    uint8_t i;

    /* Initialize message to transmit */
    MCAN_initTxBufElement(txMsg);
    /* Standard message identifier 11 bit, stored into ID[28-18] */
    txMsg->id  = ((TxMsgInfo.ID & MCAN_STD_ID_MASK) << MCAN_STD_ID_SHIFT);
    txMsg->dlc = TxMsgInfo.DLC; /* Payload size is 64 bytes */

    #ifdef  CAN0_MODULE_CANFD
        txMsg->fdf = TRUE; /* CAN FD Frame Format */
    #else
        txMsg->fdf = FALSE; /* CAN FD Frame Format */
    #endif

    txMsg->xtd = FALSE; /* Extended id not configured */

    for (i = 0U; i < TxMsgInfo.DLC; i++)
    {
        txMsg->data[i] = TxMsgInfo.u8Data[i];
    }
}

int32_t vtcan_txmsg(stCANTypeMsgBaseInfo TxMsgInfo,uint8_t TxMsgBufNum)
{
    int32_t status = CSL_PASS;
    MCAN_TxBufElement  txMsg;

    /* Configure Tx Msg to transmit */
    vtcan_mcanConfigTxMsg(&txMsg,TxMsgInfo);

	/* Write message to Msg RAM */
	MCAN_writeMsgRam(gMcan0BaseAddr, MCAN_MEM_TYPE_BUF, TxMsgBufNum, &txMsg);

	/* Add request for transmission, This function will trigger transmission */
	status = MCAN_txBufAddReq(gMcan0BaseAddr, TxMsgBufNum);
	if (CSL_PASS != status)
	{
		DebugP_log("Error in Adding Mcan0 Transmission Request...\r\n");
	}
    return status;
}

void vtcan_BusOffConfirm(void)
{
    MCANBusOffInfo.CAN0BusErr = TRUE;
}

uint8_t vtcan_GetBusOffStaus(void)
{
   return MCANBusOffInfo.CAN0BusErr;
}

void vtcan_ClearBusOffStaus(void)
{
    MCANBusOffInfo.CAN0BusErr = FALSE;
}

void vtcan_BusOffRecovery(void)
{

	//Restart the CAN controller
	MCAN_setOpMode(gMcan0BaseAddr, MCAN_OPERATION_MODE_NORMAL);
	while (MCAN_OPERATION_MODE_NORMAL != MCAN_getOpMode(gMcan0BaseAddr))
	{}  
}

int32_t vtcan_init(void)
{
    int32_t   status = SystemP_SUCCESS;
    
    /* Construct Tx/Rx Semaphore objects */
    //DebugP_log("vtcan-mcu10 mcan start %s\r\n", __TIME__);
    
    status = SemaphoreP_constructBinary(&gMcan0TxDoneSem, 0);
    if(status != SystemP_SUCCESS)
    {
        //DebugP_log("\nConstruct McanTxDoneSem FAILED...\n", -1);
    }
	
    status = SemaphoreP_constructBinary(&gMcan0RxDoneSem, 0);
    if(status != SystemP_SUCCESS)
    {
        //DebugP_log("\nConstruct McanRxDoneSem FAILED...\n", -1);
    }
	
	//can transceiver(TJA1043) init
    vtcan_mcanGPIOInit();
    vtcan_mcanTransceiver(MCAN_TRANSCEIVER_NORMALMODE);
	
    status = vtcan_mcanRegisterInterrupt();
    status = vtcan_mcanConfig();

    return status;
}


                                            vt_can.c


#ifndef __VT_CAN_H__
#define __VT_CAN_H__

#ifdef __cplusplus
    extern "C" {
#endif

#include <stdint.h>
#include <string.h>
#include "FreeRTOS.h"
#include "task.h"
#include <drivers/mcan.h>
#include <kernel/dpl/DebugP.h>
#include <kernel/dpl/AddrTranslateP.h>
#include <kernel/dpl/SemaphoreP.h>
#include <drivers/mcan.h>
#include "ti_drivers_config.h"
#include "ti_drivers_open_close.h"
#include "ti_board_open_close.h"

/* ========================================================================== */
/*                           Macros & Typedefs                                */
/* ========================================================================== */
#define MCAN_TRANSCEIVER_STANDBYMODE 0
#define MCAN_TRANSCEIVER_NORMALMODE 1

#define MCAN0_TOTAL_TX_MSG 32
#define MCAN1_TOTAL_TX_MSG 1

#define MCAN0_TOTAL_RX_MSG 32
#define MCAN1_TOTAL_RX_MSG 1

//#define CAN0_MODULE_CANFD
//#define CAN1_MODULE_CANFD

#ifdef	CAN0_MODULE_CANFD	
	#define	CANType_CANMSG_LEN_MAX					64
#else
	#define CANType_CANMSG_LEN_MAX 					8
#endif

#define VTCAN_MCAN0_CH 0
#define VTCAN_MCAN1_CH 1

//TJA1043 pin
#define VT_CAN_MCU_MCAN0_EN_PIN          (0x07)
#define VT_CAN_MCU_MCAN0_STB_PIN         (0x04)
#define VT_CAN_MCU_MCAN0_ERR_PIN         (0x01)

typedef struct{
	uint16_t ID;
	uint8_t DLC;
	uint8_t u8Data[CANType_CANMSG_LEN_MAX];
}stCANTypeMsgBaseInfo;

typedef struct
{
    MCAN_BitTimingParams *bitTimings;
    /**< mcan module bit timing parameters. */
    MCAN_InitParams *initParams;
    /**< mcan module initialization parameters. */
    MCAN_ConfigParams *configParams;
    /**< mcan module configuration parameters. */
    MCAN_MsgRAMConfigParams *ramConfig;
    /**< mcan module MSG RAM configuration parameters. */
    uint32_t txMsgNum;
    /**< tx message number. */
    uint32_t stdIdFiltNum;
    /**< standard ID message filter number. */
    uint32_t intrEnable;
    /**< Interrupt Enable/Disable Mask. */
    uint32_t intrLineSelectMask;
    /**< Interrupt Line Select Mask. */
    uint32_t intrLine;
    /**< Interrupt Line Select. */
} st_mcanConfigParams_t;

typedef struct
{
    st_mcanConfigParams_t mcanConfigParams;
    /**< mcan configuration parameters Refer struct #st_mcanConfigParams_t. */
    Bool                  printEnable;
    /**< Enable/disable print statements, used for stress testing. */
} st_mcanParams;

SemaphoreP_Object gMcan0TxDoneSem;
SemaphoreP_Object gMcan0RxDoneSem;

int32_t vtcan_init(void);
int32_t vtcan_txmsg(stCANTypeMsgBaseInfo TxMsgInfo,uint8_t TxMsgBufNum);
stCANTypeMsgBaseInfo vtcan_mcan0ReadRxMSG(void);
void vtcan_BusOffRecovery(void);
void vtcan_mcanTransceiver(uint8_t workmode);
void vtcan_mcan0FilterAllAtOnce(uint16_t *MsgID);
void vtcan_mcan0FilterOneByOne(uint8_t bank, uint16_t MsgID);


#ifdef __cplusplus
}
#endif	// _cplusplus


#endif // __VT_CAN_H__

          vt_can.h

4.If you receive more than 3 messages sent consecutively by different CANIDs with different periods,the CAN transmission will lose frames. At the same time, the message ID to be received is also vt_can.c.(line 314)


In addition, when the CAN transmission is found to be lost, the CAN transmission completion interrupt (the code in the red box in the figure below) is not entered. However, receiving messages is normal.

5. Please help confirm whether there are any errors in the CAN configuration parameters in the code, and point out any other errors.

Thanks

  • Dear customer,

       Could you print the register MCAN_ECR MCAN_TXEFC and MCAN_PSR to check when issue happened? 

    Linjun 

  • Hi,

    1.The print command used is as follows

            BUG_INFO("MCAN_ECR: %0x", HW_RD_REG32((0x4e00000UL)+0x40));
            BUG_INFO("MCAN_TXFEC: %0x", HW_RD_REG32((0x4e00000UL)+0xF0));
            BUG_INFO("MCAN_PSR: %0x", HW_RD_REG32((0x4e00000UL)+0x44));

    2.When frame loss occurs, the print records of MCAN_ECR, MCAN_TXEFC, and MCAN_PSR are as follows

    [18:20:15.841]收←◆INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0201]MCAN_ECR: 8a8507ff
    INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0202]MCAN_TXFEC: 0
    INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0203]MCAN_PSR: 897407ff
    
    [18:21:06.342]收←◆INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0201]MCAN_ECR: 8a8507ff
    INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0202]MCAN_TXFEC: 0
    INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0203]MCAN_PSR: 897407ff
    
    [18:21:55.844]收←◆INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0201]MCAN_ECR: 8a8507ff
    INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0202]MCAN_TXFEC: 0
    INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0203]MCAN_PSR: 897407ff
    
    [18:21:59.520]收←◆INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0201]MCAN_ECR: 8a8507ff
    INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0202]MCAN_TXFEC: 0
    INFO:[00000000][/home/lys/j722s-dev/j722s-rtos-sdk-v11/mcu_plus_sdk_j722s_11_00_00_12/examples/vt_mcu10_app/app/CanConfig.c][0203]MCAN_PSR: 897407ff

    3.As mentioned above, whenever there is a frame loss, MCAN_ECR=0x8a8507ff、MCAN_TXFEC=0、MCAN_PSR=0x897407ff

    Thanks!

  • Hello,

    Based on Your MCAN_PSR register status , the CAN node went into bus off status .If CAN node enters into Busoff status then only 2 ways are possible either you need to recover from software by writing recovery mechanism or doing reset of hardware.

    Can you check why there is bus off triggered in your system , is it due to issue with Acknowledgement from other node or any other reasons ?

    Regards

    Tarun Mukesh

  • Hello,

    1. There is no external trigger for the controller bus off action.
    2.When CAN successfully sends, MCAN_PSR is also printed, and it is found that the MCAN_PSR value is also 0x897407ff.
    3. No bus off occurred when queried using the MCAN_getProtocolStatus(CONFIG_MCAN0_BASE_ADDR, &protStatusfunction.

    Thanks!

  • Hello,

    2.When CAN successfully sends, MCAN_PSR is also printed, and it is found that the MCAN_PSR value is also 0x897407ff.

    This MCAN_PSR is saying there is bus off in the system and ECR is showing high count of retransmission.

      BUG_INFO("MCAN_ECR: %0x", HW_RD_REG32((0x4e00000UL)+0x40));
            BUG_INFO("MCAN_TXFEC: %0x", HW_RD_REG32((0x4e00000UL)+0xF0));
            BUG_INFO("MCAN_PSR: %0x", HW_RD_REG32((0x4e00000UL)+0x44));

     Which CAN instance are you using ? 

    Regards

    Tarun Mukesh

  • Hello,

    1.

    This is not a CAN instance, I encoded it myself based on the macro definition provided by the following routine.

    #define CSL_MCU_MCAN0_MSGMEM_RAM_BASE                                                              (0x4e00000UL)
    #define MCAN_ECR                                           (0x40U)
    #define MCAN_PSR                                           (0x44U)
    #define MCAN_TXEFC                                       (0xf0U)
    2.I changed the way and when a frame is lost during CAN transmission, I obtained the bus status through MCAN_getErrCounts (gMnBaseAddr,&errCounter) and MCAN_getProtocolStatus (VNet MCAN0_SASE-ADDR,&protStatus), and did not find any bus errors.
    3.Please refer to the description in point 2 for accuracy
    4.Can you run the provided code on the development board to analyze the reasons faster in the general field.
    Thanks
  • Hello,

    Can you please read CAN instance core register  MCAN_ECR MCAN_TXEFC and MCAN_PSR ? 

    Regards

    Tarun Mukesh

  • Hello,

    We are currently using this set of CAN, not the register address you sent, right?

    Thanks

  • Hello,

    If it MCU_MCAN0 then it is as below

    Regards

    Tarun Mukesh

  • Hello,

    1.As shown in the figure below, when a frame loss occurs during CAN transmission, MCU_CAN_PSR=0x70F or MCU_CAN_PSR=0x717.

    2.When the host receives the following message sent by canoe, MCU_CN_PSR will report an error. If the host receives more than 120 frames of messages within 1 second, MCU_CN_PSR will report an error.

    Thanks!

  • Hello,

    MCU_CAN_PSR=0x70F or MCU_CAN_PSR=0x717.

    This shows no errors. 0x70F means CAN node is idle and 0x717 means CAN nodes is operating as receiver.

    MCU_CN_PSR will report an error.

    What Error is being reported ?

    The below appnote will guide you on type of error in PSR and provide a solution to fix . Can you please check it ?

    https://www.ti.com/lit/an/spradp4/spradp4.pdf

    Regards

    Tarun Mukesh

  • Hello,

    1. This is due to CAN sending frame loss printing, but normal transmission did not print MCU_CN_PSR. According to your explanation, since the value of PSR indicates that there is no error on the bus, I am puzzled as to why frame loss occurred.

    Sorry, my statement misled you as I did not print when CAN transmission was normal, only the PSR when CAN frame was lost.

    3. Later, I changed MCAN0ucanFDInitParams and found that when frame loss occurs, MCU_CN_PSR=0x708 or MCU_CN_PSR=0x710. These two values also indicate that there is no error and frame loss still occurs.

    4. The following are BitTimyParams and InitParams. We are using regular CAN (with a baud rate of 500K and a sampling rate of 80%), not CANFD. Please help confirm if the following parameters are correct

    MCAN_BitTimingParams MCAN0_canFDBitTimings[] =
    {
        /* 500kbps 80% and 2000 kbps 80% */
        /* This is default baud*/
        {
            0x0FU, /* Nominal Baud Rate Pre-scaler */
            0x06U, /* Nominal Time segment before sample point */
            0x01U, /* Nominal Time segment after sample point */
            0x00U, /* Nominal (Re)Synchronization Jump Width */
            0x07U, /* Data Baud Rate Pre-scaler */
            0x02U, /* Data Time segment before sample point */
            0x00U, /* Data Time segment after sample point */
            0x00U  /* Data (Re)Synchronization Jump Width */
        },
    };

    MCAN_InitParams MCAN0_canFDInitParams[] =
    {
        {
            0x00U, /* FD Operation Enable */
            0x00U, /* Bit Rate Switch Enable */
            0x00U, /* Transmit Pause */
            0x00U, /* FEdge Filtering during Bus Integration */
            0x00U, /* Protocol Exception Handling Disable */
            0x01U, /* Disable Automatic Retransmission */
            0x01U, /* Wakeup Request Enable */
            0x01U, /* Auto-Wakeup Enable */
            0x00U, /* Emulation/Debug Suspend Enable */
            0x00U, /* Emulation/Debug Suspend Fast Ack Enable */
            0x00U, /* Clock Stop Fast Ack Enable */
            MCAN_RWD_WDC_MAX, /* Start value of the Message RAM Watchdog Counter */
            {
                MCAN_TDCR_TDCF_MAX, /* Transmitter Delay Compensation Offset */
                MCAN_TDCR_TDCO_MAX,  /* Transmitter Delay Compensation Filter Window Length */
            },
            0x01U, /* Transmitter Delay Compensation Enable */
        },
    };

    In summary, the value of MCU_CN_PSR indicates that the bus is error free, but frame loss still occurs. Please help analyze as soon as possible.

    Thanks!

  •  Hello,

    In summary, the value of MCU_CN_PSR indicates that the bus is error free, but frame loss still occurs. Please help analyze as soon as possible.

    There are no errors in the bus as per PSR registers.Without errors we need to debug different ways and find out why it is happening.

    You can try below methods to debug,

    Approach 1

     Try using FIFO instead of and see still it is the same or not.

    Approach 2

    Try transmission only first rather than both transmission and reception at a time.

    Regards

    Tarun Mukesh