Take the 2-minute tour ×
Stack Overflow is a question and answer site for professional and enthusiast programmers. It's 100% free, no registration required.

I am trying to debug a function Reset_Handler() written in assembler (which I do not understand, but was provided as part of a standard library). Using GDB, I go through every single instruction using ni. Here is what I get:

(gdb) ni
0x08005dc4 in Reset_Handler ()
(gdb) ni
0x08005dc6 in Reset_Handler ()
(gdb) ni
0x08005dc6 in Reset_Handler ()
(gdb) ni
0x08005dc6 in Reset_Handler ()
(gdb) ni
0x08005dc6 in Reset_Handler ()

In effect, the program pointer gets "stuck" on 0x08005dc6. Is this normal behaviour, or should the program pointer be advancing each time I do ni? Below is the start of Reset_Handler():

    .section  .text.Reset_Handler
  .weak  Reset_Handler
  .type  Reset_Handler, %function
Reset_Handler:  

/* Copy the data segment initializers from flash to SRAM */  
  movs  r1, #0
  b  LoopCopyDataInit

CopyDataInit:
  ldr  r3, =_sidata
  ldr  r3, [r3, r1]
  str  r3, [r0, r1]
  adds  r1, r1, #4

LoopCopyDataInit:
  ldr  r0, =_sdata
  ldr  r3, =_edata
  adds  r2, r0, r1
  cmp  r2, r3
  bcc  CopyDataInit
  ldr  r2, =_sbss
  b  LoopFillZerobss
/* Zero fill the bss segment. */  
FillZerobss:
  movs  r3, #0
  str  r3, [r2], #4

EDIT: Here is the disassembled instructions:

disas
Dump of assembler code for function Reset_Handler:
   0x08005dc0 <+0>:     movs    r1, #0
   0x08005dc2 <+2>:     b.n     0x8005dcc <LoopCopyDataInit>
   0x08005dc4 <+4>:     ldr     r3, [pc, #40]   ; (0x8005df0 <LoopFillZerobss+16>)
=> 0x08005dc6 <+6>:     ldr     r3, [r3, r1]
   0x08005dc8 <+8>:     str     r3, [r0, r1]
   0x08005dca <+10>:    adds    r1, #4
   0x08005dcc <+0>:     ldr     r0, [pc, #36]   ; (0x8005df4 <LoopFillZerobss+20>)
   0x08005dce <+2>:     ldr     r3, [pc, #40]   ; (0x8005df8 <LoopFillZerobss+24>)
   0x08005dd0 <+4>:     adds    r2, r0, r1
   0x08005dd2 <+6>:     cmp     r2, r3
   0x08005dd4 <+8>:     bcc.n   0x8005dc4 <Reset_Handler+4>
   0x08005dd6 <+10>:    ldr     r2, [pc, #36]   ; (0x8005dfc <LoopFillZerobss+28>)
   0x08005dd8 <+12>:    b.n     0x8005de0 <LoopFillZerobss>
   0x08005dda <+0>:     movs    r3, #0
   0x08005ddc <+2>:     str.w   r3, [r2], #4
   0x08005de0 <+0>:     ldr     r3, [pc, #28]   ; (0x8005e00 <LoopFillZerobss+32>)
   0x08005de2 <+2>:     cmp     r2, r3
   0x08005de4 <+4>:     bcc.n   0x8005dda <FillZerobss>
   0x08005de6 <+6>:     bl      0x8005c64 <SystemInit>
   0x08005dea <+10>:    bl      0x8000184 <main>
   0x08005dee <+14>:    bx      lr
End of assembler dump.
share|improve this question

2 Answers 2

up vote 4 down vote accepted

Based on the code and disassembly you've posted, I'd guess that the address that's in _sidata is invalid. _sidata is loaded into r3, so when

 ldr     r3, [r3, r1]

is executed, an invalid access causes another processor reset, which then executes until it hits that instruction again. Or something like that.

Check what's in _sidata.


Some additional notes:

I see that the instruction at address xxxx uses r0 but I don't see where r0 has been initialized in reset_handler(). It's possible that the code that calls reset_handler() might have already set up r0 properly, but to know for sure we'd have to see the exception vector table and the code that the reset vector actually points to. (I'm assuming this is for an ARM7 or similar - let me know if I've guessed incorrectly), where the exception vector table might look something like (borrowed from ethernut.de) which would vector to a label named _start on reset:

.global __vectors
__vectors:
ldr     pc, [pc, #24]   /* Reset */
ldr     pc, [pc, #24]   /* Undefined instruction */
ldr     pc, [pc, #24]   /* Software interrupt */
ldr     pc, [pc, #24]   /* Prefetch abort */
ldr     pc, [pc, #24]   /* Data abort */
ldr     pc, [pc, #24]   /* Reserved */

/*
* On IRQ the PC will be loaded from AIC_IVR, which
* provides the address previously set in AIC_SVR.
* The interrupt routine will be called in ARM_MODE_IRQ
* with IRQ disabled and FIQ unchanged.
*/
ldr     pc, [pc, #-0xF20]   /* Interrupt request, auto vectoring. */
ldr     pc, [pc, #-0xF20]   /* Fast interrupt request, auto vectoring. */

.word   _start
.word   __undef
.word   __swi
.word   __prefetch_abort
.word   __data_abort
share|improve this answer

Well, it depends :-)

What it depends upon is the instruction at 0x08005dc6. It's quite possible that in a reset handler, you may have an instruction such as:

0x08005dc6 jmp 0x08005dc6

which would exhibit that behaviour.

You should check to see what's actually at that location, with something like:

disas 0x08005dc6 0x08005dcf
share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.
{"cc_re__cc_re__cc_by_sa_3_0": ["                  <li><a href=\"//area51.stackexchange.com\" title=\"proposing new sites in the Stack Exchange network\">Area 51</a></li>\r\n                        <li><a href=\"//careers.stackoverflow.com\">Stack Overflow Careers</a></li>\r\n                    \r\n                </ol>\r\n            </td>\r\n    </tr>\r\n</table>\r\n                </div>\r\n            </div>\r\n\r\n            <div id=\"copyright\">\r\n                site design / logo &#169; 2015 stack exchange inc; user contributions licensed under <a href=\"http://creativecommons.org/licenses/by-sa/3.0/\" rel=\"license\">cc by-sa 3.0</a>                   with <a href=\"http://blog.stackoverflow.com/2009/06/attribution-required/\" rel=\"license\">attribution required</a>\r\n            </div>\r\n            <div id=\"svnrev\">\r\n                rev 2015.1.30.2262\r\n            </div>\r\n            \r\n        </div>\r\n    </div>\r\n    <noscript>\r\n        <div id=\"noscript-warning\">Stack Overflow works best with JavaScript enabled<img src=\"http://pixel.quantserve.com/pixel/p-c1rF4kxgLUzNc.gif\" alt=\"\" class=\"dno\"></div>\r\n    </nos"], "copyright__copyright__copyright": ["struction at 0x08005dc6. It's quite possible that in a reset handler, you may have an instruction such as:\n\n0x08005dc6 jmp 0x08005dc6\n\nwhich would exhibit that behaviour.\n\nYou should check to see what's actually at that location, with something like:\n\ndisas 0x08005dc6 0x08005dcf\nshare|improve this answer\n\nYour Answer\n\n\u00a0\ndiscard\n\nBy posting your answer, you agree to the privacy policy and terms of service.\n\nNot the answer you're looking for? Browse other questions tagged or ask your own question."]}