cancel
Showing results for 
Search instead for 
Did you mean: 

Boot To App Jump Not Working

RHJ
Associate II

I am trying to implement a bootloader using STM32 F103 processor.  I have not used an Arm processor before, but I have read the various articles and posts, and I think I’m doing the jump-to-app as described.  But as soon as I execute the jump, the next instruction executed is the first instruction of the Reset_Handler in the boot code (at 0x08002930), not the Reset_Handler in the app code (at 0x0801018C).

I load the app code first but don't execute.  Then I load and run the boot code.

 

Boot linker file:

  RAM    (xrw)    : ORIGIN = 0x20000000,   LENGTH = 20K

  FLASH  (rx)     : ORIGIN = 0x8000000,    LENGTH = 48K

App linker file:

  RAM    (xrw)    : ORIGIN = 0x20000000,   LENGTH = 20K

  FLASH  (rx)     : ORIGIN = 0x800C000,    LENGTH = 80K

 

Memory Browser:

Boot ISR Vector Table at 0x08000000

_estack           0x20005000

Reset_Handler     0x08002931

 

App ISR Vector Table at 0x0800C000

_estack           0x20005000

Reset_Handler     0x0801018D

 

In the app I uncommented the define for USER_VECT_TAB_ADDRESS and set VECT_TAB_OFFSET to 0x0000C000.

The watchdog is disabled in the boot code.

 

In boot:

typedef void (*pFunction)(void) __attribute__((noreturn));

typedef unsigned long int  U32;  /* 32 bits */

#define FLASH_BASE         0x08000000UL /*!< FLASH base address in the alias region */

#define APP_OFFSET         (0x0000C000UL)

#define APP_START          (FLASH_BASE + APP_OFFSET)

 

void JumpToApp(void)

{

    volatile U32 JumpAddress = *(volatile U32*)(APP_START + 4);

    pFunction Jump = (pFunction)JumpAddress;

 

    __disable_irq();

 

    HAL_RCC_DeInit();

    HAL_DeInit();

    SysTick->CTRL = 0;

    SysTick->LOAD = 0;

    SysTick->VAL  = 0;

 

    SCB->VTOR = APP_START;

    __set_MSP(*(U32*)APP_START);

 

    Jump();

}

When I single step through JumpToApp, the JumpAddress is 0x801018D.  Everything seems ok until I single step into the Jump() instruction.  Then the next instruction is the Reset_Handler of the boot at 0x08002930, not the Reset_Handler of the app at 0x801018C.

 What am I missing?  Any input would be appreciated.

 

10 REPLIES 10

The well has truly been poisoned.

 

Stop using  __disable_irq(); it's not appropriate and has no counter-party enablement on the other side.

The goal is to "Disable" the interrupts your application is using at the SOURCE, by tearing that configuration down, not at the entire MCU level.

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
RHJ
Associate II

If this was intended as an answer/resolution to the question, I'm not following.  Not sure what "counter-party enablement" or "tearing that configuration down" means.  Is using __disable_irq() causing the problem?

 

FBL
ST Employee

Hello @RHJ 

You may need to check before, the application address which should be the initial stack pointer SP that needs to be in RAM;

if (((*__IO uint32_t* Flash_App_Address) & 0x2FFE0000)==0x20000000)

The first value stored in the vector table is the reset value of the SP.

This FAQ How to jump to system bootloader from application ... - STMicroelectronics Community

should be helpful as well.

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.

DavidNaviaux
Senior

RHJ,

Did you get this worked out?  I am having the same problem.  When I jump to the application code, ideally all registers would be as if a reset just occurred (i.e. interrupts, DMA, All timers off, etc.)  However, I am so isolated from what the actual hardware is doing because I have been mostly using the HAL functions which, for the most part, I don't understand the "under the hood" details.

Thanks,

David

RHJ
Associate II

No, it's still not working.  As far as I can tell, I have done all the suggested things.

-RHJ

I have to get this going by tomorrow morning, so I have a long night ahead of me.  I'm hoping I get a response to my other post (about to make it now).

RHJ,

I have started another post specific to my problem that I am hoping I will eventually get a resolution:

Jump to application from bootloader not working - STMicroelectronics Community

 

So I got mine working by re-enabling interrupts right before I write to SCB->VTOR.  I don't know why that made a difference, but it now successfully jumps to the app code instead of the boot vector.

 

Thank you RHJ!  I discovered that too.  

I was able to release the bootloader and application code this morning. 

I got some advice from "Piranha" to use a few lines of assembly at the reset_handler.  However, I was not experienced enough to make that work in the few hours I had to release the firmware.

Thanks again, Dave.