Hi All.
With some theoritical background-help from you experts, I started on building the hello-world program of custom-bootloader.
My setup, includes flashing three binaries to different sections of flash : Bootloader, App1, App2.
Thereafter, I intend to call App1 from Bootloader.
As the first step, I flashed the three binaries to three different non-overlapping regions of flash.
Following were the observations ::
* I flashed "Bootloader". Bootloader worked fine.
* I then flashed "App1" and "App2". Bootloader did not get called.
* I then flashed (again) "Bootloader. It got called fine.
Following are the linker-files of all the 3 binaries ::
Bootloader :
MEMORY { FLASH (rx) : ORIGIN = 0x00000000, LENGTH = 0x00010000 SRAM (rwx) : ORIGIN = 0x20000000, LENGTH = 0X00008000 } SECTIONS { /* code */ .text : { _text = .; /* ensure ISR vectors are not removed by linker */ KEEP(*(.isr_vector)) *(.text*) *(.rodata*) _etext = .; } > FLASH /* static data */ .data : AT(ADDR(.text) + SIZEOF(.text)) { _data = .; *(vtable) *(.data*) _edata = .; } > SRAM /* static uninitialized data */ .bss : { _bss = .; *(.bss*) *(COMMON) _ebss = .; } > SRAM }
App1 :
MEMORY { FLASH (rx) : ORIGIN = 0x00010001, LENGTH = 0x00020000 SRAM (rwx) : ORIGIN = 0x20000000, LENGTH = 0X00008000 } SECTIONS { /* code */ .text : { _text = .; /* ensure ISR vectors are not removed by linker */ KEEP(*(.isr_vector)) *(.text*) *(.rodata*) _etext = .; } > FLASH /* static data */ .data : AT(ADDR(.text) + SIZEOF(.text)) { _data = .; *(vtable) *(.data*) _edata = .; } > SRAM /* static uninitialized data */ .bss : { _bss = .; *(.bss*) *(COMMON) _ebss = .; } > SRAM }
App2 :
MEMORY { FLASH (rx) : ORIGIN = 0x00020001, LENGTH = 0x00030000 SRAM (rwx) : ORIGIN = 0x20000000, LENGTH = 0X00008000 } SECTIONS { /* code */ .text : { _text = .; /* ensure ISR vectors are not removed by linker */ KEEP(*(.isr_vector)) *(.text*) *(.rodata*) _etext = .; } > FLASH /* static data */ .data : AT(ADDR(.text) + SIZEOF(.text)) { _data = .; *(vtable) *(.data*) _edata = .; } > SRAM /* static uninitialized data */ .bss : { _bss = .; *(.bss*) *(COMMON) _ebss = .; } > SRAM }
As is evident, only the FLASH regions differ.
Also, I am using a common startup-file for compiling each of three binaries.
Following is the relevant section (I believe) ::
static unsigned long pulStack[256]; //***************************************************************************** // // The vector table. Note that the proper constructs must be placed on this to // ensure that it ends up at physical address 0x0000.0000. // //***************************************************************************** __attribute__ ((section(".isr_vector"))) void (* const g_pfnVectors[])(void) = { (void (*)(void))((unsigned long)pulStack + sizeof(pulStack)), // The initial stack pointer ResetISR, // The reset handler NmiSR, // The NMI handler FaultISR, // The hard fault handler IntDefaultHandler, // The MPU fault handler IntDefaultHandler, // The bus fault handler IntDefaultHandler, // The usage fault handler 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved IntDefaultHandler, // SVCall handler IntDefaultHandler, // Debug monitor handler 0, // Reserved IntDefaultHandler, // The PendSV handler IntDefaultHandler, // The SysTick handler IntDefaultHandler, // GPIO Port A IntDefaultHandler, // GPIO Port B IntDefaultHandler, // GPIO Port C IntDefaultHandler, // GPIO Port D IntDefaultHandler, // GPIO Port E IntDefaultHandler, // UART0 Rx and Tx UART1Handler, // UART1 Rx and Tx IntDefaultHandler, // SSI0 Rx and Tx IntDefaultHandler, // I2C0 Master and Slave IntDefaultHandler, // PWM Fault IntDefaultHandler, // PWM Generator 0 IntDefaultHandler, // PWM Generator 1 IntDefaultHandler, // PWM Generator 2 IntDefaultHandler, // Quadrature Encoder 0 IntDefaultHandler, // ADC Sequence 0 IntDefaultHandler, // ADC Sequence 1 IntDefaultHandler, // ADC Sequence 2 IntDefaultHandler, // ADC Sequence 3 IntDefaultHandler, // Watchdog timer IntDefaultHandler, // Timer 0 subtimer A IntDefaultHandler, // Timer 0 subtimer B IntDefaultHandler, // Timer 1 subtimer A IntDefaultHandler, // Timer 1 subtimer B IntDefaultHandler, // Timer 2 subtimer A IntDefaultHandler, // Timer 2 subtimer B IntDefaultHandler, // Analog Comparator 0 IntDefaultHandler, // Analog Comparator 1 IntDefaultHandler, // Analog Comparator 2 IntDefaultHandler, // System Control (PLL, OSC, BO) IntDefaultHandler, // FLASH Control IntDefaultHandler, // GPIO Port F IntDefaultHandler, // GPIO Port G IntDefaultHandler, // GPIO Port H IntDefaultHandler, // UART2 Rx and Tx IntDefaultHandler, // SSI1 Rx and Tx IntDefaultHandler, // Timer 3 subtimer A IntDefaultHandler, // Timer 3 subtimer B IntDefaultHandler, // I2C1 Master and Slave IntDefaultHandler, // Quadrature Encoder 1 IntDefaultHandler, // CAN0 IntDefaultHandler, // CAN1 IntDefaultHandler, // CAN2 IntDefaultHandler, // Ethernet IntDefaultHandler, // Hibernate IntDefaultHandler, // USB0 IntDefaultHandler, // PWM Generator 3 IntDefaultHandler, // uDMA Software Transfer IntDefaultHandler, // uDMA Error IntDefaultHandler, // ADC1 Sequence 0 IntDefaultHandler, // ADC1 Sequence 1 IntDefaultHandler, // ADC1 Sequence 2 IntDefaultHandler, // ADC1 Sequence 3 IntDefaultHandler, // I2S0 IntDefaultHandler, // External Bus Interface 0 IntDefaultHandler, // GPIO Port J IntDefaultHandler, // GPIO Port K IntDefaultHandler, // GPIO Port L IntDefaultHandler, // SSI2 Rx and Tx IntDefaultHandler, // SSI3 Rx and Tx #ifdef GPS_INTERFACE_ENABLED UART3Handler, // UART3 Rx and Tx #else IntDefaultHandler, // UART3 Rx and Tx #endif IntDefaultHandler, // UART4 Rx and Tx IntDefaultHandler, // UART5 Rx and Tx #ifdef MODBUS_INTERFACE_ENABLED UART6Handler, // UART6 Rx and Tx #else IntDefaultHandler, // UART6 Rx and Tx #endif IntDefaultHandler, // UART7 Rx and Tx 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved IntDefaultHandler, // I2C2 Master and Slave IntDefaultHandler, // I2C3 Master and Slave IntDefaultHandler, // Timer 4 subtimer A IntDefaultHandler, // Timer 4 subtimer B 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved 0, // Reserved IntDefaultHandler, // Timer 5 subtimer A IntDefaultHandler, // Timer 5 subtimer B IntDefaultHandler, // Wide Timer 0 subtimer A IntDefaultHandler, // Wide Timer 0 subtimer B IntDefaultHandler, // Wide Timer 1 subtimer A IntDefaultHandler, // Wide Timer 1 subtimer B IntDefaultHandler, // Wide Timer 2 subtimer A IntDefaultHandler, // Wide Timer 2 subtimer B IntDefaultHandler, // Wide Timer 3 subtimer A IntDefaultHandler, // Wide Timer 3 subtimer B IntDefaultHandler, // Wide Timer 4 subtimer A IntDefaultHandler, // Wide Timer 4 subtimer B IntDefaultHandler, // Wide Timer 5 subtimer A IntDefaultHandler, // Wide Timer 5 subtimer B IntDefaultHandler, // FPU IntDefaultHandler, // PECI 0 IntDefaultHandler, // LPC 0 IntDefaultHandler, // I2C4 Master and Slave IntDefaultHandler, // I2C5 Master and Slave IntDefaultHandler, // GPIO Port M IntDefaultHandler, // GPIO Port N IntDefaultHandler, // Quadrature Encoder 2 IntDefaultHandler, // Fan 0 0, // Reserved IntDefaultHandler, // GPIO Port P (Summary or P0) IntDefaultHandler, // GPIO Port P1 IntDefaultHandler, // GPIO Port P2 IntDefaultHandler, // GPIO Port P3 IntDefaultHandler, // GPIO Port P4 IntDefaultHandler, // GPIO Port P5 IntDefaultHandler, // GPIO Port P6 IntDefaultHandler, // GPIO Port P7 IntDefaultHandler, // GPIO Port Q (Summary or Q0) IntDefaultHandler, // GPIO Port Q1 IntDefaultHandler, // GPIO Port Q2 IntDefaultHandler, // GPIO Port Q3 IntDefaultHandler, // GPIO Port Q4 IntDefaultHandler, // GPIO Port Q5 IntDefaultHandler, // GPIO Port Q6 IntDefaultHandler, // GPIO Port Q7 IntDefaultHandler, // GPIO Port R IntDefaultHandler, // GPIO Port S IntDefaultHandler, // PWM 1 Generator 0 IntDefaultHandler, // PWM 1 Generator 1 IntDefaultHandler, // PWM 1 Generator 2 IntDefaultHandler, // PWM 1 Generator 3 IntDefaultHandler // PWM 1 Fault };
SInce all three binaries are flashed in different regions (with "Bootloader") being at the "starting location", Bootloader must always be called, irrespective of whether any other binary is flashed or not (of course, as long as it does not over-write the "Bootloader" binary).
Unfortunately, above is not happening.
Where am I being foolish? Will be grateful for pointers.
Thanks and Regards,
Ajay