2017-06-12 05:25 AM
Hello Community,
I have problem with starting main program after jump from bootloader. I am using ECLIPSE with SW4STM32 and CubeMX.
Ok, what I did:
1. I writed bootloader which is prepared with settings: Linker file: ——————————————————————————– /* Specify the memory areas */ MEMORY { BOOTLOADER (rx): ORIGIN = 0x08000000, LENGTH = 24K FIRMWARE (rx) : ORIGIN = 0x08006000, LENGTH = 256K – 24K RAM (xrw) : ORIGIN = 0x200000C0, LENGTH = 32K – 192 /* 192 for vector table */ } /* Main app start address symbol */ _main_app_start_address = 0x08006000;/* For main application, change BOOTLOADER by FIRMWARE */
REGION_ALIAS(“FLASH�?, BOOTLOADER ); ——————————————————————————– 2. Jump function:// disable global interrupt
__disable_irq();
// Disable all peripheral interrupts
HAL_NVIC_DisableIRQ(SysTick_IRQn);
HAL_NVIC_DisableIRQ(WWDG_IRQn);
HAL_NVIC_DisableIRQ(RTC_IRQn);
HAL_NVIC_DisableIRQ(FLASH_IRQn);
HAL_NVIC_DisableIRQ(RCC_IRQn);
HAL_NVIC_DisableIRQ(EXTI0_1_IRQn);
HAL_NVIC_DisableIRQ(EXTI2_3_IRQn);
HAL_NVIC_DisableIRQ(EXTI4_15_IRQn);
HAL_NVIC_DisableIRQ(DMA1_Channel1_IRQn);
HAL_NVIC_DisableIRQ(DMA1_Channel2_3_IRQn);
HAL_NVIC_DisableIRQ(DMA1_Channel4_5_IRQn);
HAL_NVIC_DisableIRQ(ADC1_IRQn);
HAL_NVIC_DisableIRQ(TIM1_BRK_UP_TRG_COM_IRQn);
HAL_NVIC_DisableIRQ(TIM1_CC_IRQn);
HAL_NVIC_DisableIRQ(TIM3_IRQn);
HAL_NVIC_DisableIRQ(TIM6_IRQn);
HAL_NVIC_DisableIRQ(TIM7_IRQn);
HAL_NVIC_DisableIRQ(TIM14_IRQn);
HAL_NVIC_DisableIRQ(TIM15_IRQn);
HAL_NVIC_DisableIRQ(TIM16_IRQn);
HAL_NVIC_DisableIRQ(TIM17_IRQn);
HAL_NVIC_DisableIRQ(I2C1_IRQn);
HAL_NVIC_DisableIRQ(I2C2_IRQn);
HAL_NVIC_DisableIRQ(SPI1_IRQn);
HAL_NVIC_DisableIRQ(SPI2_IRQn);
HAL_NVIC_DisableIRQ(USART1_IRQn);
HAL_NVIC_DisableIRQ(USART2_IRQn);
HAL_NVIC_DisableIRQ(USART3_6_IRQn);
// main app start address defined in linker file
extern uint32_t _main_app_start_address;
uint32_t MemoryAddr = (uint32_t)&_main_app_start_address;
uint32_t *pMem = (uint32_t *)MemoryAddr;
// First address is the stack pointer initial value
__set_MSP(*pMem); // Set stack pointer
// Now get main app entry point address
pMem++;
void (*pMainApp)(void) = (void (*)(void))(*pMem);
// Jump to main application (0x0800 6004)
pMainApp();�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?
3. I writedsimply FIRMWARE program which blinking one led using while loop and shoud blinking second led using IRQs –> void HAL_SYSTICK_Callback(void);
Blinking by IRQs not working. Blinking by while loop is working
4. Linker file from FIRMWARE:
——————————————————————————– /* Specify the memory areas */ MEMORY { BOOTLOADER (rx): ORIGIN = 0x08000000, LENGTH = 24K FIRMWARE (rx) : ORIGIN = 0x08006000, LENGTH = 256K – 24K RAM (xrw) : ORIGIN = 0x200000C0, LENGTH = 32K – 192 /* 192 for vector table */ } /* Main app start address symbol */ _main_app_start_address = 0x08006000;/* For main application, change BOOTLOADER by FIRMWARE */
REGION_ALIAS(“FLASH�?, FIRMWARE ); ——————————————————————————–5. In FIRMWARE program first function in main is Remap_Table();
void Remap_Table(void)
{
// Copy interrupt vector table to the RAM.
volatile uint32_t *VectorTable = (volatile uint32_t *)0x20000000;
uint32_t ui32_VectorIndex = 0;
for(ui32_VectorIndex = 0; ui32_VectorIndex < 48; ui32_VectorIndex++)
{
VectorTable[ui32_VectorIndex] = *(__IO uint32_t*)((uint32_t)FIRMWARE_START_ADDR + (ui32_VectorIndex << 2));
}
__HAL_RCC_AHB_FORCE_RESET();
// Enable SYSCFG peripheral clock
__HAL_RCC_SYSCFG_CLK_ENABLE();
__HAL_RCC_AHB_RELEASE_RESET();
// Remap RAM into 0x0000 0000
__HAL_SYSCFG_REMAPMEMORY_SRAM();
}�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?�?
I tried set __enable_irq(); after Remap_table(); and before main while loop and in other places from Remap_table() to main while loop and it does not work.
6. I did test with FIRMWARE and set in linker: ——————————————————————————– MEMORY { BOOTLOADER (rx): ORIGIN = 0x08000000, LENGTH = 24K FIRMWARE (rx) : ORIGIN = 0x08006000, LENGTH = 256K – 24K RAM (xrw) : ORIGIN = 0x200000C0, LENGTH = 32K – 192 /* 192 for vector table */ } /* Main app start address symbol */ _main_app_start_address = 0x08006000;/* For main application, change BOOTLOADER by FIRMWARE */
REGION_ALIAS(“FLASH�?, BOOTLOADER); ——————————————————————————– then I deleted Remap function and __enable_irq();, compiled it and writed it to MCU by programmer –> blinking by while loop and IRQs worked good.I heard about problem with starting FIRMWARE after custom bootloader witch is writed with HAL libraries. I think, I have this problem.Can someone give me some advice ?
MCU is STM32F030RCT6
Regards
Dawid
2017-06-12 06:11 AM
Is the boot loader calling from inside an interrupt?
You would definitely need the __enable_irq() if you disable it previously, the processor isn't going to magically reenable them via the reset handler.
2017-06-12 07:04 AM
Yes, jump function is inside interrupt.
__enable_irq(): is present in my main app after remap of course2017-06-12 07:36 AM
Yeeeeees ! It is working ! It was a problem.
Thank You very much. I really appreciate that.
For me topic is closed. Problem solved !
Best regards
Dawid Kozub
2017-06-12 09:24 AM
>>Yes, jump function is inside interrupt.
That is likely to be problematic, you should consider manipulating the stack frame so it returns to the application code rather than jumping from the interrupt state.
2017-06-12 10:13 AM
Hi
dawid
Dawid Kozub wrote:
Yeeeeees ! It is working ! It was a problem.
Thank You very much. I really appreciate that.
For me topic is closed. Problem solved !
Best regards
Dawid Kozub
2018-05-23 05:35 AM
Hi Dawid,
I have tow Soft like your program:
1/bootloader simple soft to jump to Main Application.
2/Appliucation contain a blink LED in while loop, and i'd like to make a Remapping vector table in RAM , but the Blink LED is KO.
can have an idea what you are make as config in your program to make a good remapping of VTABLE in RAM?
or what is the exact steps that we should made it ?
bellow my program:
int main(void)
{ // Copy interrupt vector table to the RAM.uint32_t ui32_VectorIndex = 0;
for(ui32_VectorIndex = 0; ui32_VectorIndex < 48; ui32_VectorIndex++) { VectorTable[ui32_VectorIndex] = *(__IO uint32_t*)((uint32_t)APPLICATION_RUN_BEGIN_ADDRESS + (ui32_VectorIndex << 2)); } //_HAL_RCC_AHB1_FORCE_RESET(); RCC->AHB1RSTR = 0xFFFFFFFFU; // Enable SYSCFG peripheral clock __HAL_RCC_SYSCFG_CLK_ENABLE(); // __HAL_RCC_AHB_RELEASE_RESET(); RCC->AHB1RSTR = 0x00000000U; // Remap RAM into 0x0000 0000 __HAL_SYSCFG_REMAPMEMORY_SRAM(); /* relocate vector table */ __disable_irq(); SCB->VTOR = (uint32_t)&VectorTable; //__DSB(); __enable_irq(); HAL_Init();/* Configure the system clock to 80 MHz */
SystemClock_Config(); /* -1- Enable each GPIO Clock (to be able to program the configuration registers) */ __HAL_RCC_GPIOA_CLK_ENABLE();/* -2- Configure IOs in output push-pull mode to drive external LEDs */
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP; GPIO_InitStruct.Pull = GPIO_PULLUP; GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_VERY_HIGH;GPIO_InitStruct.Pin = GPIO_PIN_5 | GPIO_PIN_12;
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);/* -3- Toggle IOs in an infinite loop */
while (1) { for (uint32_t i=0; i<0xFFFFF; i++); HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_5); HAL_GPIO_TogglePin(GPIOA, GPIO_PIN_12); }}Best Regards.
2018-05-23 09:02 AM
You seem to be mixing multiple concepts here.
What part specifically are you using? It helps to always frame the question so the context is clear to those other than yourself.
The moving of vectors to RAM is a Cortex-M0 specific thing, as these parts don't support the SCB->VTOR pointer. The interrupt tables on M3/M4 device are also typically a lot larger, not just 48 elements. Jumping to a new image on the M0+, M3, M4 and M7 just needs you to update the SCB->VTOR to match the new table. This is frequently done in the SystemInit() code.
They also don't run at 80 MHz.
Dawid's issue was doing the control transfer from an IRQ Handler, this tends to disable other interrupt at equal or higher preemption numbers.
2018-05-23 10:45 AM
Turvey.Clive.002
Thanks a lot for your response.I use the STM32L476RG.
My Gol is to have a 3 softs in one Chip:
1)Bootloader
2)Application1
3)Application2
Bootloader jump to Application 1
Application1 contain an interrupt TIM1 should Toggle a LED1
Application1 Jump to Application2
Application2 contain a an other interrupt TIM2 wich toggle LED2
so i need finnaly to Remap vector Table in RAM to guarantee the functionality of the tow interrupt.
Using tow Applications it's a Client Requierment.
What do you think ?
Regards.