This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

How to catch a runaway program

Other Parts Discussed in Thread: LM3S1968

I've got a code base running on a Stellaris LM3S1968 dev board and after recently enabling the RTC for the program, I have a random hangup.  It may occur an hour after running, or 70 hours.  I've had a watch point set on the bottom of the stack to make sure it's not a stack overflow that is causing the problem.  I'm pretty sure that it is the same failure each time, as the program counter is always at the same address, outside where I have my code, when I pause the chip to inspect what is going on.  When I do pause it, I don't have any stack trace information since where the code is executing is outside the memory range I've programmed.  Is there a way to reconstruct what's on the stack so that I can figure out where the code is dying?  Is there a way to track the PC so that I can see when it first jumps outside of where it should be?

  • Hi Chad,

    Toughie. Too bad you don't have trace or anything like that. Since the address when it runs off to always seems the same, how about setting a watchpoint on that address to halt the PC when it first jumps to there? Then maybe there will be some useful value in the linker register to give you a clue as to where the program may have been when it ran off into the weeds. Another suggestion is to fill that memory with a halt instruction so it halt when it reaches that location. If I come of with more suggestions, I'll let you know.

    ki

  • Ki-Soo Lee said:
    linker register

    I meant the Link Register.

  • Where do I find the bit pattern for the "halt" command?  I haven't found it in the TI docs I have and I have been unsuccessful finding it out on the internet.

  • After much searching, as the appropriate ARM documentation is referenced, but not actually available on their site,  I found that the opcode for a debug breakpoint is 0xbexx where xx is don't care.  We'll see how it works.

  • Setting all memory areas in the linker script (in my case lm3s1968.cmd) to fill = 0xbe00 did indeed do the trick.  After starting things up I came back from lunch and found a breakpoint triggered and was able to start debugging my memory.

    Here's an example line from my linker script:

    #define FILL_VALUE                0xbeff    //This is the opcode for a breakpoint, 0xbexx

    ... \\Next line is in MEMORY section

     SRAM (RWX) : origin = 0x20000000, length = 0x00010000, fill = FILL_VALUE


  • Great.  Thanks for posting the opcode and linker command file lines needed.

  • For posterity's sake, the problem ended up being that I was moving where the vector interrupt table was via the linker script, but I was not setting the NVIC_VTABLE register to point to it.  So, some random location in memory was getting called when any interrupt fired.  The solution, implemented in CCS v5.1 and using the StellarisWare libraries, was to add the following to main.c in the global area:

    extern void * g_pfnVectors;

    and then as soon as possible the following line:

    HWREG(NVIC_VTABLE) = (unsigned long)&g_pfnVectors;

    that seems to have cleared it up.