We are running a survey to help us improve the experience for all of our members. If you see the survey appear, please take the time to tell us about your experience if you can.
You could simplify this to: LDR pc, main_address How are you checking the pc value? When running code the PC points at the instruction being fetched - not the one being executed.
LDR pc, main_address
reset_handler: # copy from flash(0x00000000) to ram eor r0, r0 ldr r1, ram_start ldr r2, ram_end sub r2, r2, r1 1: ldr r3, [r0], #4 str r3, [r1], #4 subs r2, #4 bne 1b # install a stack ldr sp, stack_top mov fp, sp # branch to main ldr pc, main_address b reset_handler ram_start: .extern __ram_start .word __ram_start // == 0x40000100ram_end: .extern __ram_end .word __ram_end // == 0x40000200stack_top: .word __ram_end + 0x1000 main_address: .extern main .word main
I am not familiar with the GNU assembler syntax as I use the ARM tools. However, based on the ARM syntax it looks what you are doing is getting the address of the label. Have you tried:.extern mainldr pc, =main
.extern mainldr pc, =main
Hmm... Since you mention a hardcoded value works, and decrement by 4, I wonder if the size is actually not a multiple of 4 when working it out? It looks like the code might loop if it wasn't.
Actually, pc is correctly loaded, and I guess there isa problem with my copy, but I dont see which one.main is a naked function and has no local variable,so it doesnot use the stack at all...When I replace the first sub to compute the size witha harcoded one (ie. mov r2, #0x1000), it works...