cancel
Showing results for 
Search instead for 
Did you mean: 

STM32U5 series bank swap not working

HParsons
Associate

First post, please let me know if I've made any mistakes in asking my question.

I'm trying to write a bootloader for a device using a STM32u585ZIT chip. When booting, it will read a partition table saved in flash to determine if it will boot from partition A (Address 0x08080000) or partition B (Address 0x08180000). I have decided on using the BANK_SWAP option byte to swap the addresses of these partitions so that I only need to write a single linker script for the application code. 

Here is the code I'm using to set the swap bit if we want to boot from partition B: 

if ((partitions.a == partitionStatusUpdate)
			|| ((partitions.a == partitionStatusActive)
					&& (partitions.b != partitionStatusUpdate))) {
		printf("Booting partition A\n");
	} else if ((partitions.b == partitionStatusUpdate)
			|| ((partitions.b == partitionStatusActive)
					&& (partitions.a != partitionStatusUpdate))) {
		if (HAL_FLASH_Unlock() != HAL_OK) {
			printf("Could not unlock flash!\n");
			NVIC_SystemReset();
		}
		if (HAL_FLASH_OB_Unlock() != HAL_OK) {
			printf("Could not unlock flash option bytes!\n");
			NVIC_SystemReset();
		}
		FLASH->OPTR |= FLASH_OPTR_SWAP_BANK;
		if (HAL_FLASH_OB_Lock() != HAL_OK) {
			printf("Could not lock flash!\n");
			NVIC_SystemReset();
		}
		if (HAL_FLASH_Lock() != HAL_OK) {
			printf("Could not lock flash option bytes!\n");
			NVIC_SystemReset();
		}
	}

 From what I gather from reference documents this should swap the banks' addresses, so I should only ever need to tell it to access the application at 0x08080000 after this point. However, using the following code (APP_ACTIVE_ADDR == 0x08080000):

appAddress = (uint32_t*) APP_ACTIVE_ADDR + 1;
GoToApplication = (pFunction) *appAddress;
__set_MSP(*(uint32_t*) APP_ACTIVE_ADDR);
SCB->VTOR = APP_ACTIVE_ADDR;
GoToApplication();

I am finding it only ever boots app A. 

I have searched around and found people asking similar questions regarding different chips, but the only question referring to the U5 specifically is this one, but I don't think the answer there is relevant to me because the original poster was using two separate linker scripts:

https://community.st.com/t5/stm32cubeprogrammer-mcus/mb1549c-swapbank-is-set-1-but-its-not-run-bank2-firmware-always/td-p/57235 

I assume I am missing some steps to make this work, but I cannot figure out what they are. Can anyone help? Please let me know if any extra information is required or if I have been unclear about anything.

1 REPLY 1
FBL
ST Employee

Hi @HParsons 

I guess you are missing OB launch loading. In fact, after setting the BANK_SWAP option byte, a system reset is usually required for the changes to take effect. Ensure that you are performing a system reset after programming the option bytes HAL_FLASH_OB_Launch(); An example is provided in Cube Firmware. It should be helpful.

STM32CubeU5/Projects/NUCLEO-U575ZI-Q/Examples/FLASH/FLASH_SwapBanks at main · STMicroelectronics/STM32CubeU5 (github.com)

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.


I'm out of offce with limited access to my emails.
Happy New Year!