AnsweredAssumed Answered

Stuck in CAN TX Interrupt

Question asked by ebommer on Apr 20, 2015
I am currently have intermittent issue where I am getting stuck in  "void USB_HP_CAN_TX_IRQHandler(void)",  Everything works well from minutes to hours then I notice my CAN traffic stops, currently I TX one message every 20 mSec, I am the only module on the bus, so there should be no bus contention issues.  

During my troubleshooting I am noticing if I stop my code I am alway in my interrupt routine(CAN data will also stop if I am not in debug mode).  If I single step through my code while this issue is occuring I can get out of the interrupt routine.  So it seem like a timing issue, but I have no idea of how to fix it.

001./** @brief This function handles USB High Priority or CAN_TX interrupts.    */
002.void USB_HP_CAN_TX_IRQHandler(void)
003.{
004.    HAL_NVIC_ClearPendingIRQ(USB_HP_CAN_TX_IRQn);
005.    HAL_CAN_IRQHandler(&hcan);
006.     
007.    if(hcan.Instance->ESR > 0)
008.    {
009.        __HAL_CAN_CANCEL_TRANSMIT(&hcan,0);
010.    }
011.}
012. 
013./**
014.  * @brief  Initiates and transmits a CAN frame message.
015.  * @param  hcan: pointer to a CAN_HandleTypeDef structure that contains
016.  *         the configuration information for the specified CAN. 
017.  * @retval HAL status
018.  */
019.HAL_StatusTypeDef HAL_CAN_Transmit_IT(CAN_HandleTypeDef* hcan)
020.{
021.  uint32_t transmitmailbox = CAN_TXSTATUS_NOMAILBOX;
022. 
023.  /* Check the parameters */
024.  assert_param(IS_CAN_IDTYPE(hcan->pTxMsg->IDE));
025.  assert_param(IS_CAN_RTR(hcan->pTxMsg->RTR));
026.  assert_param(IS_CAN_DLC(hcan->pTxMsg->DLC));
027.   
028.  if((hcan->State == HAL_CAN_STATE_READY) || (hcan->State == HAL_CAN_STATE_BUSY_RX))
029.  {
030.    /* Process Locked */
031.    __HAL_LOCK(hcan);
032.     
033.    /* Select one empty transmit mailbox */
034.    if((hcan->Instance->TSR&CAN_TSR_TME0) == CAN_TSR_TME0)
035.    {
036.      transmitmailbox = 0;
037.    }
038.    else if((hcan->Instance->TSR&CAN_TSR_TME1) == CAN_TSR_TME1)
039.    {
040.      transmitmailbox = 1;
041.    }
042.    else if((hcan->Instance->TSR&CAN_TSR_TME2) == CAN_TSR_TME2)
043.    {
044.      transmitmailbox = 2;
045.    }
046. 
047.    if(transmitmailbox != CAN_TXSTATUS_NOMAILBOX)
048.    {
049.      /* Set up the Id */
050.      hcan->Instance->sTxMailBox[transmitmailbox].TIR &= CAN_TI0R_TXRQ;
051.      if(hcan->pTxMsg->IDE == CAN_ID_STD)
052.      {
053.        assert_param(IS_CAN_STDID(hcan->pTxMsg->StdId)); 
054.        hcan->Instance->sTxMailBox[transmitmailbox].TIR |= ((hcan->pTxMsg->StdId << 21) | \
055.                                                  hcan->pTxMsg->RTR);
056.      }
057.      else
058.      {
059.        assert_param(IS_CAN_EXTID(hcan->pTxMsg->ExtId));
060.        hcan->Instance->sTxMailBox[transmitmailbox].TIR |= ((hcan->pTxMsg->ExtId << 3) | \
061.                                                  hcan->pTxMsg->IDE | \
062.                                                  hcan->pTxMsg->RTR);
063.      }
064.     
065.      /* Set up the DLC */
066.      hcan->pTxMsg->DLC &= (uint8_t)0x0000000F;
067.      hcan->Instance->sTxMailBox[transmitmailbox].TDTR &= (uint32_t)0xFFFFFFF0;
068.      hcan->Instance->sTxMailBox[transmitmailbox].TDTR |= hcan->pTxMsg->DLC;
069. 
070.      /* Set up the data field */
071.      hcan->Instance->sTxMailBox[transmitmailbox].TDLR = (((uint32_t)hcan->pTxMsg->Data[3] << 24) |
072.                                             ((uint32_t)hcan->pTxMsg->Data[2] << 16) |
073.                                             ((uint32_t)hcan->pTxMsg->Data[1] << 8) |
074.                                             ((uint32_t)hcan->pTxMsg->Data[0]));
075.      hcan->Instance->sTxMailBox[transmitmailbox].TDHR = (((uint32_t)hcan->pTxMsg->Data[7] << 24) |
076.                                             ((uint32_t)hcan->pTxMsg->Data[6] << 16) |
077.                                             ((uint32_t)hcan->pTxMsg->Data[5] << 8) |
078.                                             ((uint32_t)hcan->pTxMsg->Data[4]));
079.     
080.      if(hcan->State == HAL_CAN_STATE_BUSY_RX)
081.      {
082.        /* Change CAN state */
083.        hcan->State = HAL_CAN_STATE_BUSY_TX_RX;
084.      }
085.      else
086.      {
087.        /* Change CAN state */
088.        hcan->State = HAL_CAN_STATE_BUSY_TX;
089.      }
090.       
091.      /* Set CAN error code to none */
092.      hcan->ErrorCode = HAL_CAN_ERROR_NONE;
093.       
094.      /* Process Unlocked */
095.      __HAL_UNLOCK(hcan);
096.       
097.      /* Enable Error warning Interrupt */
098.      __HAL_CAN_ENABLE_IT(hcan, CAN_IT_EWG);
099.       
100.      /* Enable Error passive Interrupt */
101.      __HAL_CAN_ENABLE_IT(hcan, CAN_IT_EPV);
102.       
103.      /* Enable Bus-off Interrupt */
104.      __HAL_CAN_ENABLE_IT(hcan, CAN_IT_BOF);
105.       
106.      /* Enable Last error code Interrupt */
107.      __HAL_CAN_ENABLE_IT(hcan, CAN_IT_LEC);
108.       
109.      /* Enable Error Interrupt */
110.      __HAL_CAN_ENABLE_IT(hcan, CAN_IT_ERR);
111.       
112.      /* Enable Transmit mailbox empty Interrupt */
113.      __HAL_CAN_ENABLE_IT(hcan, CAN_IT_TME);
114.       
115.      /* Request transmission */
116.      hcan->Instance->sTxMailBox[transmitmailbox].TIR |= CAN_TI0R_TXRQ;
117.    }
118.  }
119.  else
120.  {
121.    return HAL_BUSY;
122.  }
123.   
124.  return HAL_OK;
125.}
 

Outcomes