cancel
Showing results for 
Search instead for 
Did you mean: 

CAN not working on STM32L431RCT6

YvanR
Associate II

"Board A" is a previous revision that used STM32F103C8T6 to communicate with a device over CAN. It works great.

"Board B" is a new revision of the same board, but I migrated to STM32L431RCT6 because I needed more IO and it was readily available. Long story short, I can't get the MCU to do anything on its CAN interface. 

I thought maybe I missed something when porting the code over, but I tried creating a new CubeIDE project that just sends and receives, but I get nothing.

The CAN transceiver itself is working fine. With another host transmitting on the bus I can see a nice clean signal on the RX pin (PB8) with 3.0V peaks. However, nothing shows up in the RX FIFO.

Likewise, when the MCU is asked to transmit, nothing shows up on the TX pin (PB9).

The CAN peripheral is configured like so. I'm running the bus at 250kb/s and the MCU is clocked at 80MHz.

 

 

void MX_CAN1_Init(void)
{
  hcan1.Instance = CAN1;
  hcan1.Init.Prescaler = 20;
  hcan1.Init.Mode = CAN_MODE_NORMAL;
  hcan1.Init.SyncJumpWidth = CAN_SJW_1TQ;
  hcan1.Init.TimeSeg1 = CAN_BS1_9TQ;
  hcan1.Init.TimeSeg2 = CAN_BS2_6TQ;
  hcan1.Init.TimeTriggeredMode = DISABLE;
  hcan1.Init.AutoBusOff = DISABLE;
  hcan1.Init.AutoWakeUp = DISABLE;
  hcan1.Init.AutoRetransmission = DISABLE;
  hcan1.Init.ReceiveFifoLocked = DISABLE;
  hcan1.Init.TransmitFifoPriority = DISABLE;
  if (HAL_CAN_Init(&hcan1) != HAL_OK)
  {
    Error_Handler();
  }
}

void HAL_CAN_MspInit(CAN_HandleTypeDef* canHandle)
{
  GPIO_InitTypeDef GPIO_InitStruct = {0};
  if(canHandle->Instance==CAN1)
  {
    __HAL_RCC_CAN1_CLK_ENABLE();
    __HAL_RCC_GPIOB_CLK_ENABLE();
    /**CAN1 GPIO Configuration
    PB8     ------> CAN1_RX
    PB9     ------> CAN1_TX
    */
    GPIO_InitStruct.Pin = CAN_RX_Pin|CAN_TX_Pin;
    GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
    GPIO_InitStruct.Pull = GPIO_NOPULL;
    GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH;
    GPIO_InitStruct.Alternate = GPIO_AF9_CAN1;
    HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);
    HAL_NVIC_SetPriority(CAN1_RX0_IRQn, 5, 0);
    HAL_NVIC_EnableIRQ(CAN1_RX0_IRQn);
  }
}

 

 

The filter is created and notification requests set up:

	uint32_t setup(void)
	{
		can_tx_header.IDE = CAN_ID_STD; // 11-bit ID
		can_tx_header.RTR = CAN_RTR_DATA; // Normal data
		can_tx_header.TransmitGlobalTime = DISABLE;

		CAN_FilterTypeDef can_filter;
		can_filter.FilterBank = 0;
		can_filter.FilterMode = CAN_FILTERMODE_IDMASK;
		can_filter.FilterScale = CAN_FILTERSCALE_32BIT;
		can_filter.FilterIdHigh = 0x0000;
		can_filter.FilterIdLow = 0x0000;
		can_filter.FilterMaskIdHigh = 0x0000;
		can_filter.FilterMaskIdLow = 0x0000;
		can_filter.FilterFIFOAssignment = CAN_RX_FIFO0;
		can_filter.FilterActivation = CAN_FILTER_ENABLE;
		can_filter.SlaveStartFilterBank = 14;
		if (HAL_CAN_ConfigFilter(hcan, &can_filter) != HAL_OK)
			return HAL_CAN_GetError(hcan);

		if (HAL_CAN_Start(hcan) != HAL_OK)
			return HAL_CAN_GetError(hcan);

		if (HAL_CAN_ActivateNotification(hcan, CAN_IT_RX_FIFO0_MSG_PENDING) != HAL_OK)
			return HAL_CAN_GetError(hcan);

		return HAL_OK;
	}

(This is in a class, hcan == &hcan1)  

I have no reason to believe this is interrupt-related. The interrupts are configured in the NVIC and function names match those in the startup file. Also other interrupts work OK. Also polling the interface does not yield any data, and again, transmitting does not yield results.

I am regularly checking HAL_CAN_GetState(&hcan1) but it does not return any errors.

Any ideas are welcome.

1 ACCEPTED SOLUTION

Accepted Solutions
YvanR
Associate II

Thanks @Tesla DeLorean I checked and confirmed your suggestions.

I was able to resolve the issue, though I don't 100% understand why.

The only hardware difference between the original board and the current one is the model of the transceiver. During manufacturing I had to substitute a Rohm BD41041FJ-C. While it is a 5V unit, as I said above, it was relaying CAN to logic levels as one would expect. I tried a second unit with the same hardware, same problem.

I swapped in a TI SN65HVD232, and it is running perfectly, just like the original unit. Interestingly the TI presents only 2.7V peak to the MCU.

View solution in original post

3 REPLIES 3

Check all the relevant clocks are enabled. GPIOB, CAN, etc.

Check the content of the peripheral registers.

Check initialization order.

Double check clocking speed of MCU, use HSE based clock, check PLL settings.

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
YvanR
Associate II

Thanks @Tesla DeLorean I checked and confirmed your suggestions.

I was able to resolve the issue, though I don't 100% understand why.

The only hardware difference between the original board and the current one is the model of the transceiver. During manufacturing I had to substitute a Rohm BD41041FJ-C. While it is a 5V unit, as I said above, it was relaying CAN to logic levels as one would expect. I tried a second unit with the same hardware, same problem.

I swapped in a TI SN65HVD232, and it is running perfectly, just like the original unit. Interestingly the TI presents only 2.7V peak to the MCU.

I believe you can mark your answer as a solution, since it was a defect in the external hardware