1019 views|4 replies

118

Posts

1

Resources
The OP
 

[ST NUCLEO-U5A5ZJ-Q development board review] -6-FDCAN experience [Copy link]

This post was last edited by Murong Xuehua on 2024-3-4 12:54

The FDCAN of the U5 series devices is very convenient and can support both CAN-FD and classic CAN 2.0. The main tools and devices used in this experiment are:

  • STM32U5A5ZJ-Q
  • TJA1050 CAN transceiver
  • CAN LIN TOOL V5.0

CAN transmit and receive pins use PB8 and PB9:

Schematic diagram of TJA1050:

Configure in CubeIde:

FDCAN clock: 64Mhz

CAN related timing parameters and working modes:

Save and automatically generate code:

static void MX_FDCAN1_Init(void)
{

  /* USER CODE BEGIN FDCAN1_Init 0 */

  /* USER CODE END FDCAN1_Init 0 */

  /* USER CODE BEGIN FDCAN1_Init 1 */

  /* USER CODE END FDCAN1_Init 1 */
  hfdcan1.Instance = FDCAN1;
  hfdcan1.Init.ClockDivider = FDCAN_CLOCK_DIV1;
  hfdcan1.Init.FrameFormat = FDCAN_FRAME_CLASSIC;
  hfdcan1.Init.Mode = FDCAN_MODE_NORMAL;
  hfdcan1.Init.AutoRetransmission = ENABLE;
  hfdcan1.Init.TransmitPause = ENABLE;
  hfdcan1.Init.ProtocolException = DISABLE;
  hfdcan1.Init.NominalPrescaler = 16;
  hfdcan1.Init.NominalSyncJumpWidth = 1;
  hfdcan1.Init.NominalTimeSeg1 = 5;
  hfdcan1.Init.NominalTimeSeg2 = 2;
  hfdcan1.Init.DataPrescaler = 1;
  hfdcan1.Init.DataSyncJumpWidth = 1;
  hfdcan1.Init.DataTimeSeg1 = 1;
  hfdcan1.Init.DataTimeSeg2 = 1;
  hfdcan1.Init.StdFiltersNbr = 0;
  hfdcan1.Init.ExtFiltersNbr = 0;
  hfdcan1.Init.TxFifoQueueMode = FDCAN_TX_FIFO_OPERATION;
  if (HAL_FDCAN_Init(&hfdcan1) != HAL_OK)
  {
    Error_Handler();
  }
  /* USER CODE BEGIN FDCAN1_Init 2 */

  /* USER CODE END FDCAN1_Init 2 */

}

Add custom test data:

FDCAN_FilterTypeDef sFilterConfig;
FDCAN_TxHeaderTypeDef TxHeader;
FDCAN_RxHeaderTypeDef RxHeader;
uint8_t TxData0[] = {0x10, 0x32, 0x54, 0x76, 0x98, 0x00, 0x11, 0x22};
uint8_t TxData1[] = {0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55};
uint8_t TxData2[] = {0xFF, 0x00, 0xFF, 0x00, 0xFF, 0x00, 0xFF, 0x00};

Add the relevant filters:

void MY_FDCAN_CONFIG(void){
	/*##-1 Configure the FDCAN filters ########################################*/
	/* Configure standard ID reception filter to Rx FIFO 0 */
	sFilterConfig.IdType = FDCAN_STANDARD_ID;
	sFilterConfig.FilterIndex = 0;
	sFilterConfig.FilterType = FDCAN_FILTER_DUAL;
	sFilterConfig.FilterConfig = FDCAN_FILTER_TO_RXFIFO0;
	sFilterConfig.FilterID1 = 0x444;
	sFilterConfig.FilterID2 = 0x555;
	if (HAL_FDCAN_ConfigFilter(&hfdcan1, &sFilterConfig) != HAL_OK)
	{
		Error_Handler();
	}

	/* Configure extended ID reception filter to Rx FIFO 1 */
	sFilterConfig.IdType = FDCAN_EXTENDED_ID;
	sFilterConfig.FilterIndex = 0;
	sFilterConfig.FilterType = FDCAN_FILTER_RANGE_NO_EIDM;
	sFilterConfig.FilterConfig = FDCAN_FILTER_TO_RXFIFO1;
	sFilterConfig.FilterID1 = 0x1111111;
	sFilterConfig.FilterID2 = 0x2222222;
	if (HAL_FDCAN_ConfigFilter(&hfdcan1, &sFilterConfig) != HAL_OK)
	{
		Error_Handler();
	}

	/* Configure global filter:
	       Filter all remote frames with STD and EXT ID
	       Reject non matching frames with STD ID and EXT ID */
	if (HAL_FDCAN_ConfigGlobalFilter(&hfdcan1, FDCAN_REJECT, FDCAN_REJECT, FDCAN_FILTER_REMOTE, FDCAN_FILTER_REMOTE) != HAL_OK)
	{
		Error_Handler();
	}

	/*##-2 Start FDCAN controller (continuous listening CAN bus) ##############*/
	if (HAL_FDCAN_Start(&hfdcan1) != HAL_OK)
	{
		Error_Handler();
	}

	printf("\r\nBefore Add 0x444: HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) = %d", HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1));

	/*##-3 Transmit messages ##################################################*/
	/* Add message to Tx FIFO */
	TxHeader.Identifier = 0x444;
	TxHeader.IdType = FDCAN_STANDARD_ID;
	TxHeader.TxFrameType = FDCAN_DATA_FRAME;
	TxHeader.DataLength = FDCAN_DLC_BYTES_8;
	TxHeader.ErrorStateIndicator = FDCAN_ESI_ACTIVE;
	TxHeader.BitRateSwitch = FDCAN_BRS_OFF;
	TxHeader.FDFormat = FDCAN_CLASSIC_CAN;
	TxHeader.TxEventFifoControl = FDCAN_STORE_TX_EVENTS;
	TxHeader.MessageMarker = 0x52;
	if (HAL_FDCAN_AddMessageToTxFifoQ(&hfdcan1, &TxHeader, TxData0) != HAL_OK)
	{
		Error_Handler();
	}
	printf("\r\nAfter Add 0x444: HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) = %d", HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1));

	/* Add second message to Tx FIFO */
	TxHeader.Identifier = 0x1111112;
	TxHeader.IdType = FDCAN_EXTENDED_ID;
	TxHeader.TxFrameType = FDCAN_DATA_FRAME;
	TxHeader.DataLength = FDCAN_DLC_BYTES_8;
	TxHeader.ErrorStateIndicator = FDCAN_ESI_PASSIVE;
	TxHeader.BitRateSwitch = FDCAN_BRS_OFF;
	TxHeader.FDFormat = FDCAN_CLASSIC_CAN;
	TxHeader.TxEventFifoControl = FDCAN_STORE_TX_EVENTS;
	TxHeader.MessageMarker = 0xCC;
	if (HAL_FDCAN_AddMessageToTxFifoQ(&hfdcan1, &TxHeader, TxData1) != HAL_OK)
	{
		Error_Handler();
	}
	printf("\r\nAfter Add 0x1111112: HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) = %d", HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1));

	/* Add third message to Tx FIFO */
	TxHeader.Identifier = 0x1111113;
	TxHeader.IdType = FDCAN_EXTENDED_ID;
	TxHeader.TxFrameType = FDCAN_DATA_FRAME;
	TxHeader.DataLength = FDCAN_DLC_BYTES_8;
	TxHeader.ErrorStateIndicator = FDCAN_ESI_PASSIVE;
	TxHeader.BitRateSwitch = FDCAN_BRS_OFF;
	TxHeader.FDFormat = FDCAN_CLASSIC_CAN;
	TxHeader.TxEventFifoControl = FDCAN_STORE_TX_EVENTS;
	TxHeader.MessageMarker = 0xDD;
	if (HAL_FDCAN_AddMessageToTxFifoQ(&hfdcan1, &TxHeader, TxData2) != HAL_OK)
	{
		Error_Handler();
	}
	printf("\r\nAfter Add 0x1111113: HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) = %d", HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1));

	/* Wait transmissions complete */
	while (HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) != 3) {}

	printf("\r\n 3 CAN MSG Transmissions Complete.");

}//end of void MY_FDCAN_CONFIG(void)

In the main loop, the breathing light flashes once each time, and the number of times is packaged into can msg and sent to the host computer.

  while (1)
  {
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
	  static uint16_t dcycle_pulse = 0;
	  static uint8_t breath_cnt = 0;
	  //htim3.Init.Period = 999
	  while(dcycle_pulse <htim3.Init.Period){
		  __HAL_TIM_SET_COMPARE(&htim3, TIM_CHANNEL_2, dcycle_pulse);
		  dcycle_pulse += 50;
		  printf("\nLight Phase, Current DutyCycle = %u", dcycle_pulse*100/htim3.Init.Period);
		  HAL_Delay(100);
	  }
	  while(dcycle_pulse > 0){
		  __HAL_TIM_SET_COMPARE(&htim3, TIM_CHANNEL_2, dcycle_pulse);
		  dcycle_pulse -= 50;
		  printf("\nDim Phase, Current DutyCycle = %u", dcycle_pulse*100/htim3.Init.Period);
		  HAL_Delay(100);
	  }


	  printf("\r\nBefore Add 0x555: HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) = %d", HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1));

	  /* Wait for available Tx Fifo */
	  while (HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) == 0) {}

	  TxBreathLEDCnt[7] = breath_cnt++;
	  if (HAL_FDCAN_AddMessageToTxFifoQ(&hfdcan1, &TxHeader, TxBreathLEDCnt) != HAL_OK)
	  {
		  Error_Handler();
	  }


	  printf("\r\nAfter Add 0x555: HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) = %d", HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1));
	  printf("\r\nSTM32U5-TJA1050-USBCAN: Breath LED CAN MSG Transmissions Complete.");


  }//end of while

Hardware system:

Host computer data:

First, 3 frames of test data are received, and then the number of flashes of the breathing light is transmitted through the message with ID 555.

After this experience, I feel that it is very convenient to configure CubeIDE to use the fdcan peripheral. In the future, I will consider taking a deeper look at the reception, interrupt reception and other functions.

reference:

AN5348_Application Note for the FDCAN Peripheral on STM32 Devices.pdf

This post is from stm32/stm8

Latest reply

Your post is also very interesting! More informative than mine!   Details Published on 2024-3-4 11:50
 

118

Posts

1

Resources
2
 

6821

Posts

11

Resources
3
 

After this experience, I feel that it is very convenient to configure CubeIDE to use the fdcan peripheral. In the future, I will consider taking a deeper look at the reception, interrupt reception and other functions.

Thanks for sharing!

This post is from stm32/stm8

Comments

Thanks to Mr. Liu for sharing his experience in using the U5 series FDCAN. It has benefited me a lot!  Details Published on 2024-3-4 11:32
 
 

118

Posts

1

Resources
4
 
lugl4313820 posted on 2024-3-4 11:30 After this experience, I feel that it is very convenient to configure cubeide to use fdcan peripherals. I will consider further understanding the reception, interruption and reception functions in the future. ...

Thanks to Mr. Liu for sharing his experience in using the U5 series FDCAN. It has benefited me a lot!

This post is from stm32/stm8

Comments

Your post is also very interesting! More informative than mine!  Details Published on 2024-3-4 11:50
 
 
 

6821

Posts

11

Resources
5
 
Posted by Murong Xuehua on 2024-3-4 11:32 Thank you Mr. Liu for sharing your experience in using the U5 series FDCAN. It has benefited me a lot!

Your post is also very interesting! More informative than mine!

This post is from stm32/stm8
 
 
 

Guess Your Favourite
Just looking around
Find a datasheet?

EEWorld Datasheet Technical Support

EEWorld
subscription
account

EEWorld
service
account

Automotive
development
circle

About Us Customer Service Contact Information Datasheet Sitemap LatestNews

Room 1530, Zhongguancun MOOC Times Building, Block B, 18 Zhongguancun Street, Haidian District, Beijing 100190, China Tel:(010)82350740 Postcode:100190

Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号
快速回复 返回顶部 Return list