fix(uart): HardwareSerial begin() causes Infinite Loop #2785
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
I found an issue while using HardwareSerial. Sometimes, when calling begin() function, the ClockPrescaler field inside huart->Init contains a garbage value. This wrong value is then passed to HAL_UART_Init(), and later used in UART_SetConfig() → UART_DIV_SAMPLING16() macro. When this happens, the MCU triggers an interrupt and get stuck in an infinite loop.
I didn't see this problem with every HardwareSerial instance. Although I couldn't exactly find what it depends on probably it is happening when the HardwareSerial object is a member of another class, and begin() is called from that class’s constructor.
I am using PlatformIO, but I replaced framework by Arduino Core STM32 version with the latest one from GitHub. I encountered this issue while using STM32H750VBT chip.
To solve this issue I added some functions and code blocks in uart.c and uart.h files.
Added clockPrescaler setter in uart_init() function for devices which support clockPrescaler for UART. However, while setting I needed value of connected Peripharel clock and clockPrescaler finder function.
Therefore, Added a function to calculate the correct ClockPrescaler based on the UART’s PCLK frequency.
Added a helper function to get the PCLK frequency. I inspected all the datasheets while making this function but I am newbie so that this function still needs more review and testing for different STM32 series.
Tried to make the solution generic. Changes passed from CI tool but review gonna be good.
Testing