cancel
Showing results for 
Search instead for 
Did you mean: 

STM32F4 HAL CAN DUAL use,.. FIFO1 callback not invoked but frame is in FIFO1

Rudolph Berger
Associate
Posted on June 22, 2018 at 21:13

Hey Guys,

I have a problem using the CAN1 and CAN2 in dual use on the STM32F2427ZIT6 (custom board).

Hereby CAN1 is configured for FIFO0 Interrupt and,

CAN2 is configured for FIFO1 interrupt.

I managed to transmit and receive frames via CAN1. Also I manged to transmit frames with CAN2.

Furthermore if I send frames with the correct filter ID to CAN2 it does arrive in the FIFO1 memory.

(I can see it in the hcan2 handler instance with the RF1R bit switch to 1. Also I do see the frame data in the sFIFOMailbox[1] in the RDLR and RDHR fields.)

The problem is that the HAL_CAN_RxFifo1MsgPendingCallback is not called. Whereas when I use CAN1 the HAL_CAN_RxFifo0MsgPendingCallback works fine. So because I do receive the frame in the FIFO I think the filter settings are correct. Also the new firmware automatically is assigning the CAN1 handler for the filter settings in the ConfigFilter function.

Firmware version 1.21. is used.

my can_init function:

void Com::init_can(interface_can* _p_interface_can){   

   

    CAN_FilterTypeDef myFilter;

    myFilter.FilterBank = 0;    //ID 0-13 for CAN1, 14+ is CAN2

    myFilter.FilterMode = CAN_FILTERMODE_IDMASK;

    myFilter.FilterScale = CAN_FILTERSCALE_32BIT;

    myFilter.FilterIdHigh = 0x100<<5;    //11-bit ID, in top bits

    myFilter.FilterIdLow = 0x0000;

    myFilter.FilterMaskIdHigh = 0x700 << 5;     // resolves as 0x01xx        //before it was myFilter.FilterMaskIdHigh = 0xff<<5;

    myFilter.FilterMaskIdLow = 0x0000;

    myFilter.FilterFIFOAssignment = CAN_RX_FIFO0;

    myFilter.FilterActivation = ENABLE;

    myFilter.SlaveStartFilterBank = 14;

    HAL_CAN_ConfigFilter(can_handles_array[0],&myFilter);

    // ------------------------------------- //

    // CAN2 Config    // Filter IDs from 0x200 -> 0x2FF will be received

    myFilter.FilterBank = 18;    //ID 0-13 for CAN1, 14+ is CAN2

    myFilter.FilterMode = CAN_FILTERMODE_IDMASK;

    myFilter.FilterScale = CAN_FILTERSCALE_32BIT;

    myFilter.FilterIdHigh = 0x200<<5;    //11-bit ID, in top bits

    myFilter.FilterIdLow = 0x0000;

    myFilter.FilterMaskIdHigh = 0x700 << 5;     // resolves as 0x01xx    

    myFilter.FilterMaskIdLow = 0x0000;

    myFilter.FilterFIFOAssignment = CAN_RX_FIFO1;

    myFilter.FilterActivation = ENABLE;

    myFilter.SlaveStartFilterBank = 14;

    HAL_CAN_ConfigFilter(can_handles_array[1],&myFilter);

    HAL_CAN_Start(can_handles_array[0]);

    HAL_CAN_Start(can_handles_array[1]);

    HAL_CAN_ActivateNotification(can_handles_array[0], CAN_IT_RX_FIFO0_MSG_PENDING);

    HAL_CAN_ActivateNotification(can_handles_array[1], CAN_IT_RX_FIFO1_MSG_PENDING);

}

void HAL_CAN_RxFifo1MsgPendingCallback(CAN_HandleTypeDef *hcan)

{

  /* Get RX message */

    HAL_CAN_GetRxMessage(hcan, CAN_RX_FIFO1, &RxHeader_B2,RxData_B2);

    BaseType_t xHigherPriorityTaskWoken = pdFALSE;

    xSemaphoreGiveFromISR(xBinarySemaphore_CAN2Interrupt, &xHigherPriorityTaskWoken );

    portEND_SWITCHING_ISR( xHigherPriorityTaskWoken );

}

In the image you can see the CAN2 Bits after receiving the frame. The callback function was not invoked.0690X0000060LQWQA2.png

1 ACCEPTED SOLUTION

Accepted Solutions
Ben K
Senior III
Posted on June 24, 2018 at 14:42

In order to have the HAL callbacks operate, you have to make sure that

1. the related interrupt vector is enabled

NVIC_EnableIRQ(CAN2_RX1_IRQn);

2. the interrupt handler is implemented and contains the HAL handler redirection

void CAN2_RX1_IRQHandler(void) { HAL_CAN_IRQHandler(&hcan2); }

View solution in original post

5 REPLIES 5
T J
Lead
Posted on June 23, 2018 at 14:53

this line looks wrong, questioning what frame you are sending...specifically the 11bit MsgID

myFilter.FilterMaskIdHigh = 0xff<<5;

what is this ?, should it be the same for both ?

myFilter.SlaveStartFilterBank = 14;

What frame are you sending ?

the 11-bit MsgIDs are critical for the reception filters to work.

did you satisfy both interrupts ?

void CAN1_RX0_IRQHandler(void)

{

  /* USER CODE BEGIN CAN1_RX0_IRQn 0 */

    //CAN_Rx0_IRQFlag = true;

    //CAN_IRQFlag = true;

    checkCanRxFifos();

  /* USER CODE END CAN1_RX0_IRQn 0 */

  HAL_CAN_IRQHandler(&hcan1);

  /* USER CODE BEGIN CAN1_RX0_IRQn 1 */

  /* USER CODE END CAN1_RX0_IRQn 1 */

}

/**

* @brief This function handles CAN1 RX1 interrupt.

*/

void CAN1_RX1_IRQHandler(void)

{

  /* USER CODE BEGIN CAN1_RX1_IRQn 0 */

//    CAN_Rx1_IRQFlag = true;

//    CAN_IRQFlag = true;

    checkCanRxFifos();

  /* USER CODE END CAN1_RX1_IRQn 0 */

  HAL_CAN_IRQHandler(&hcan1);

  /* USER CODE BEGIN CAN1_RX1_IRQn 1 */

  /* USER CODE END CAN1_RX1_IRQn 1 */

}
Ben K
Senior III
Posted on June 24, 2018 at 14:42

In order to have the HAL callbacks operate, you have to make sure that

1. the related interrupt vector is enabled

NVIC_EnableIRQ(CAN2_RX1_IRQn);

2. the interrupt handler is implemented and contains the HAL handler redirection

void CAN2_RX1_IRQHandler(void) { HAL_CAN_IRQHandler(&hcan2); }

Posted on June 24, 2018 at 15:46

Thank you Ben, by default in CubeMX the interrupts on CAN are only enabled for RX0 so just be invoking HAL_CAN_ActivateNotification(hcan2, CAN_IT_RX_FIFO_MSG_PENDING) the NVIC_EnableIRQ(CAN2_RX1_IRQn) function is not invoked. This should maybe get changed in the next firmware update. Anyway thanks for your input.

PRABU Appunu
Associate II

hi

i have same issue while using CAN1 and CAN2 dual use ,

Target CPU is STM32F417IE

  1. CAN1 is configured for FIFO0 and NVIC interrupt enabled ( CAN1_RX0_IRQn,1,0)
  2. CAN2 is configured for FIFO1 and NVIC interrupt enabled ( CAN2_RX1_IRQn,2,0)

Issue :

  1. I am not able to receive message on CAN2 .CAN_RxFifo1MsgPendingCallback is not called .
  2. when i use Rxfifo1 for CAN1 then i am able to receive the Msg on FIFO1 and CAN_RxFifo1MsgPendingCallback is called .
  3.  

My Code :

static void CAN1_Filter_Config(void)

{

 CAN_FilterTypeDef sFilterConfig;

uint32_t Clk;

 /*##-2- Configure the CAN1 Filter ###########################################*/

 sFilterConfig.FilterBank = 0;

 sFilterConfig.FilterMode = CAN_FILTERMODE_IDMASK;

 sFilterConfig.FilterScale = CAN_FILTERSCALE_32BIT;

 sFilterConfig.FilterIdHigh = 0x0000;//

 sFilterConfig.FilterIdLow = 0x0000;

 sFilterConfig.FilterMaskIdHigh = 0x000;//; 0xFFE0;

 sFilterConfig.FilterMaskIdLow = 0x0000;

 sFilterConfig.FilterFIFOAssignment = CAN_RX_FIFO0;

 sFilterConfig.FilterActivation = ENABLE;

 sFilterConfig.SlaveStartFilterBank = 13;

 if (HAL_CAN_ConfigFilter(&hcan1, &sFilterConfig) != HAL_OK)

 {

  /* Filter configuration Error */

  Error_Handler();

 }

 /*##-3- Start the CAN peripheral ###########################################*/

 if (HAL_CAN_Start(&hcan1) != HAL_OK)

 {

  /* Start Error */

  Error_Handler();

 }

 /*##-4- Activate CAN RX notification

#######################################*/

 if (HAL_CAN_ActivateNotification(&hcan1, CAN_IT_RX_FIFO0_MSG_PENDING) != HAL_OK)

 {

  /* Notification Error */

Error_Handler();

 }

 /*##-5- Configure Transmission process #####################################*/

}

static void CAN2_Filter_Config(void)

{

 CAN_FilterTypeDef sFilterConfig;

uint32_t Clk;

 //hcan2.Instance = CAN1;

 /*##-2- Configure the CAN1 Filter ###########################################*/

 sFilterConfig.FilterBank = 14;

 sFilterConfig.FilterMode = CAN_FILTERMODE_IDMASK;//CAN_FILTERMODE_IDMASK;

 sFilterConfig.FilterScale = CAN_FILTERSCALE_32BIT;

 sFilterConfig.FilterIdHigh = 0x0000;//(0x321<< 5);

 sFilterConfig.FilterIdLow = 0x0000;

 sFilterConfig.FilterMaskIdHigh = 0x0000;//; 0xFFE0;

 sFilterConfig.FilterMaskIdLow = 0x0000;

 sFilterConfig.FilterFIFOAssignment = CAN_RX_FIFO1;

 sFilterConfig.FilterActivation = ENABLE;

 sFilterConfig.SlaveStartFilterBank = 27;

 if (HAL_CAN_ConfigFilter(&hcan2, &sFilterConfig) != HAL_OK)

 {

  /* Filter configuration Error */

  Error_Handler();

 }

 //

//hcan2.Instance = CAN2;

  

 /*##-3- Start the CAN peripheral ###########################################*/

 if (HAL_CAN_Start(&hcan2) != HAL_OK)

 {

  /* Start Error */

  Error_Handler();

 }

 /*##-4- Activate CAN RX notification #######################################*/

 if (HAL_CAN_ActivateNotification(&hcan2, CAN_IT_RX_FIFO1_MSG_PENDING) != HAL_OK)

 {

  /* Notification Error */

Error_Handler();

 }

 /*##-5- Configure Transmission process #####################################*/

}

Is it HAL driver issue ? for CAN_RxFifo1MsgPendingCallback not being called ?

or did i missed any configuraiton?

I would like to receive all messages ( Filter ID high and Low =0x0000 for both CAN1,2) in CAN1 and CAN2.

Is there any mistake in the filter configuraltion ?

Thanks for your timely reply

Prabu

T J
Lead

are you checking both IRQHandlers on both ports?

are you sure you have all four interrupts enabled ?

void CAN1_RX0_IRQHandler(void)
{
  /* USER CODE BEGIN CAN1_RX0_IRQn 0 */
    //CAN_Rx0_IRQFlag = true;
    //CAN_IRQFlag = true;
    checkCanRxFifos();
 
  /* USER CODE END CAN1_RX0_IRQn 0 */
  HAL_CAN_IRQHandler(&hcan1);
  /* USER CODE BEGIN CAN1_RX0_IRQn 1 */
 
  /* USER CODE END CAN1_RX0_IRQn 1 */
}
 
/**
* @brief This function handles CAN1 RX1 interrupt.
*/
void CAN1_RX1_IRQHandler(void)
{
  /* USER CODE BEGIN CAN1_RX1_IRQn 0 */
//    CAN_Rx1_IRQFlag = true;
//    CAN_IRQFlag = true;
    checkCanRxFifos();
 
  /* USER CODE END CAN1_RX1_IRQn 0 */
  HAL_CAN_IRQHandler(&hcan1);
  /* USER CODE BEGIN CAN1_RX1_IRQn 1 */
 
  /* USER CODE END CAN1_RX1_IRQn 1 */
}