Skip to main content
DBara.1
Associate II
March 23, 2022
Question

STM32F407 HAL_UARTEx_ReceiveToIdle() function missing

  • March 23, 2022
  • 6 replies
  • 5629 views

Hello. I am working on a project where i need to get different lenghts of data using UART and preferebly with least possible amount of iterrupts, so ive settled to using HAL_UARTEx_ReceiveToIdle() function (when testing the project on F103), but when i moved the project onto F407, i cant seem to find this function.. Was it for some reason removed or renamed, or is my enviroment messing with me?..

This topic has been closed for replies.

6 replies

Tesla DeLorean
Guru
March 23, 2022

>>..with least possible amount of interrupts

Both these STM32 families interrupt for EVERY BYTE, the HAL decimates the call-back for you, and adds a lot of its own weight.

I suspect the ReceiveToIdle function was never added, as the HAL model for the U(S)ART is a bit of a hack that never really fit the paradigm most people had for buffering/handling serial comms.

The F1 is quite old, but has a lot of use, the F2/F4 perhaps less so, and might explain resource allocated to HAL support, adding functions, bug fixes or refactoring, etc.

You could always port the ReceiveToIdle functionality if critical.

Tips, Buy me a coffee, or three.. PayPal Venmo (See Profile) Up vote any posts that you find helpful, it shows what's working..
TDK
March 23, 2022
"If you feel a post has answered your question, please click ""Accept as Solution""."
DBara.1
DBara.1Author
Associate II
March 23, 2022

0693W00000LvWsrQAF.png

DBara.1
DBara.1Author
Associate II
March 23, 2022

0693W00000LvWswQAF.pngIm looking into Keil Uvision IDE suggestions and stm32f4xx_hal_uart.c file which stm32cubemx generated. Ive seen that it is there on the github, but hal_uart.c which cube generated seems to be different than the one in github

TDK
March 23, 2022

You might be on a much older version of the library. It's been in there for a bit. Update embedded packages in CubeMX. You can see which library version you're using in Project Manager -> Project -> MCU and Firmware Package.

"If you feel a post has answered your question, please click ""Accept as Solution""."
DBara.1
DBara.1Author
Associate II
March 23, 2022

Just updated to newest package version, still cant find the function. I guess its something on my end being not correct, will try to find a workaround, time to play with DMA i guess to save some time on iterrupts :)

TDK
March 24, 2022

Should be a solveable problem. Ensure you're looking at a file generated by CubeMX and not one copied into a directory somewhere. Delete the file and ensure it's replaced when you generate code.

"If you feel a post has answered your question, please click ""Accept as Solution""."
DBara.1
DBara.1Author
Associate II
March 24, 2022

For testing purposes, just created a new cubemx project, generated fresh code into a new folder, function is still missing. Where im checking - testing if Keil Uvision can autocomplete the function based on all the funcion names in files, aswell double checked the files in /Projectfolder/Drivers/STM32F4xx_HAL_Driver/Src/ Both HAL_UART.c and HAL_USART.c - function doesnt exist anywhere.

TDK
March 24, 2022
Not sure, sorry. Perhaps the files in the repository location were replaced manually. Perhaps IOC isn't using the latest library version. Those are things I would check. Could also generate the project for CubeIDE and see if results are different. Good luck.
"If you feel a post has answered your question, please click ""Accept as Solution""."
Piranha
Principal III
March 24, 2022

Take a note that even with interrupts, DMA and ***ToIdle() functions you still cannot receive continuous data stream with HAL, because it stops the reception after each of these operations. You can start it again, but inevitably sometimes some bytes will be lost in between. Also you will have to manage FIFO code (buffer indexes) in your application because HAL doesn't implement that also. In the end HAL is a useless broken bloatware, which creates more problems than solves, because it's made by incompetent developers.

For a sane implementation from competent developer, look here:

https://github.com/MaJerle/stm32-usart-uart-dma-rx-tx

KnarfB
Super User
March 24, 2022

@Piranha​ : Circular DMA never stops reception when using HAL_UART_Receive_DMA.

Piranha
Principal III
March 24, 2022

Yes, but that one doesn't use IDLE or RTO interrupts. But it looks like there are HAL_UARTEx_ReceiveToIdle_DMA(), which can do both - continuous reception with DMA in circular mode and report IDLE interrupts. Therefore my previous comment now is a bit misleading. WOW, it took them only 14 years to get UART working... If they keep this mind-blowing pace, they can even get Ethernet working by the end of this century! And why are the "Ex" functions located in "non-Ex" files?

But wait...

https://github.com/STMicroelectronics/STM32CubeF4/blob/3d6be4bd406f275728e0a321cc371c62a3100533/Projects/STM32F429ZI-Nucleo/Examples/UART/UART_ReceptionToIdle_CircularDMA/Src/main.c#L335

A software FIFO buffer is still not managed in a driver and must be managed in application code. Even now, when, because of using IDLE interrupt, the buffer management is not so trivial anymore. Also the example does unnecessary data copying... byte-by-byte! And this junk is presented as a solution and a high level abstraction layer? I'll show an abstraction layer:

res_t DRV_USART_RxDataGet(struct drv_usart_s *hDRV, void **ppbData);
void DRV_USART_RxDataAck(struct drv_usart_s *hDRV, size_t nbData);
 
res_t res;
void *pbData;
 
for (;;) {
	ulTaskNotifyTake(pdTRUE, portMAX_DELAY);
	while ((res = DRV_USART_RxDataGet(hDRV, &pbData)) > 0) {
		Application_DataProcess(pbData, res);
		DRV_USART_RxDataAck(hDRV, res);
	}
}

Continuous reception, IDLE interrupt, software FIFO, zero-copy and it can be implemented with or without DMA. The API usage is trivial and the driver internal code is not that complex either.