cancel
Showing results for 
Search instead for 
Did you mean: 

STM32G0 bootloader usart loop

KlemenPfce
Associate II

Hi,

I am using built-in usart bootloader on stm32g0. And I am also using the same usart for communication in my user app. I enabled the bootloader via boot option bits. When I start the debug session, I can see the flow stepping over through the program flow, going over HAL_Init()SystemClock_Config(),  MX_GPIO_Init() and MX_USART1_UART_Init(), and then the program flow comes to my first "HAL_UART_Receive(..." function. 

It is at this function that the program jumps to the Bootloader and the bootloader starts to respond to my uasrt commands. After I exit the bootloader, via the "Go command(I use address 0x08000000)", the program flow stops at breakpoint I have at "HAL_Init()" and then when I step over again, I see that as soon as I hit the "HAL_UART_Receive(..." function again, it goes back into bootloader.

 

So, my thinking now is that after I exit the bootloader, I should modify the boot bit (nBOOT0) in my user code, to disable it and then enabling it again via the uart command later, if i want to return to bootloader?

int main(void)
{

  /* USER CODE BEGIN 1 */

  /* USER CODE END 1 */

  /* MCU Configuration--------------------------------------------------------*/

  /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
  HAL_Init();

  /* USER CODE BEGIN Init */

  /* USER CODE END Init */

  /* Configure the system clock */
  SystemClock_Config();

  /* USER CODE BEGIN SysInit */

  /* USER CODE END SysInit */

  /* Initialize all configured peripherals */
  MX_GPIO_Init();
  MX_USART1_UART_Init();
  //MX_ADC1_Init();
  /* USER CODE BEGIN 2 */
  char tmp[1]; //Dummy variable for next line HAL uart receive function.
  HAL_UART_Receive(&huart1, tmp, 1, 500);
  //cha...

 

 

 

 

1 ACCEPTED SOLUTION

Accepted Solutions

RM0444 Rev 5 / Sections 2.5 Boot configuration and 3.4.2 FLASH option byte programming.

 

To give better visibility on the answered topics, please click on "Accept as Solution" on the reply which solved your issue or answered your question.

View solution in original post

6 REPLIES 6
SofLit
ST Employee

Hello @KlemenPfce 

If you configure the option bytes to Jump to the system memory and you didn't changed it to jump to the Flash memory (to run your application), indeed, the MCU keeps  running the system memory. So you need to restore the default option bytes boot config to jump to the Flash memory and, if needed, modify it again for system memory to execute bootloader program. Make sure you make a system reset after each change to let the MCU reading these new values at startup.

To give better visibility on the answered topics, please click on "Accept as Solution" on the reply which solved your issue or answered your question.
BarryWhit
Senior III

If you're using a really low-pin count package, perhaps this thread is relevant.

AKA "Life gets interesting when NRST and the UART share a pin".

- If someone's post helped resolve your issue, please thank them by clicking "Accept as Solution".
- Please post an update with details once you've solved your issue. Your experience may help others.

Yes, so I need to modify option bytes inside my code. But I cant find info on how to do it. Is there an AN or RM where this process is described?

RM0444 Rev 5 / Sections 2.5 Boot configuration and 3.4.2 FLASH option byte programming.

 

To give better visibility on the answered topics, please click on "Accept as Solution" on the reply which solved your issue or answered your question.

That's an interesting question. Is it really feasible to try and use this pin for both functions? what's the point of having a reset pin if it's disabled as soon as the user code launches? How would that work? I would have thought you have to pick one.

 

If you only want to modify (manually, one-time) option bytes, you can connect using CubeProgrammer's and use its dedicated "option bytes" pane.

 

Update: also, option bytes are persistent because they are stored in Flash memory. You should be very sure you know what you're doing before you start rewriting them periodically as part of your application's startup code. Flash has a finite number of write cycles. I really doubt they're meant to be used that way.

 

- If someone's post helped resolve your issue, please thank them by clicking "Accept as Solution".
- Please post an update with details once you've solved your issue. Your experience may help others.

Well, main purpose of bootloader is to enable remote updates after the product is deployed in field, so this is like a basic function of it. And since my product is installed in industrial environment it is usually powered up once and then left running for weeks or months. 

And since the bootloader bit will only be changed when a update request comes via the serial, which will be maybe once per year, I don't see the option bit be rewritten more then 20 or 30 times on product life span.

 

And yes, it can be done via CubeProgrammer, in fact, this is how I do it now for testing, but it is not really any use in the development/production chase, because if you have St-Link probe connected, you might as well just use the swdio connection and do it the "usual" way.