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.

random stops while running code in debug CCSv5.1

Genius 4170 points
Other Parts Discussed in Thread: MSP430F5437A

Hello all,

I am having some troubles lately. Using CCS 5.1 with my own PCB and the MSP430F5437A. Since a few weeks I am getting random stops in my code execution while in debug mode. When I am just running the code, exiting debug mode, everything jsut works fine, but I will need the debug mode for developingnew things in this particular code.

I just do not know if those are known bugs or something in my coding. The point is that in some older versions of my Code nothing like that is happening in CCS 5.1 but in my newest codes I do enter debug mode, klick the resume ( or run ) button and the code will stop in some code , but I do not intend it to stop there, it just jalts like if there were an breakpoint, but I am sure there is not.

What do you suggest doing?

Maybe this is an code size problem, as it keeps growing and growing from one version to another ( i mean my program), I kind of lost track when this problem oocured the first time. BAck then I used the code size limited version of CCS, now I did buy the basic version for 445$ because my code was growing too big.

Any suggestions are welcome, since this is a really bad bug.

Thanks for helping,

Seb

  • Hi Seb,

    could you please provide us with a few more details to help see if we can figure this out with you?   Would you be willing to send you code, or a minimal version showing the behaviour, to us offline?  Is this reproducable?  Any further details would be great.

    Best Regards,

    Lisa

  • Hello I do not know if something is explainable on this screen. ( I now reviewd it and I guess it is big enough :) ) So anyway, on the screen you can see my CCS Debug window, You also see that there is NO breakpoint active, and the point where the pointer stopped is just some random code section.I did not single step into it, it just stops around those lines of code everytime I dstart debug. I can resume my debug though. After resuming once everything seems to work fine, also with breakpoints active. Of course I kind of could work with this bug, but it would be rather nice to have it working correct, especially because I get some more bugs like this, once I enter LPM3 in my code and start from the beginning ( which is intended by me and my software).

    My problem is kind of reproduceable. Every time I start debugging in my code code flow will stop  on some certain point, somewhere before LPM3 is entered, but it is NOT always the same instruction where it stops, but it is always in the same *.c file, which is noch the main.c

    I found some threads about unreasonable behaviour of breakpoints after entering IRQs. Though I am not having trouble entering my IRQs, its just that after I start debugging my Code it randomly stops in some instructions and I cannto say why this is.

    Thanks for taking care of my problem, hope there will be a solution.

    BEst wishes

    Seb

  • Hi Seb,

    would you be able to send us a reproducable test case?  Does your code still run normally?   We are also trying to determine whether or not this is better with the MSP team.

    Please keep us informed.

    Best Regards,

    Lisa

  • Hello,

    thanks for the fast reply, I wont be able to send you an exact code, since it is pretty long:

             name            origin    length      used     unused   attr    fill
    ----------------------  --------  ---------  --------  --------  ----  -------- 

    RAM                   00001c00   00004000  00002e05  000011fb  RWIX
    FLASH                 00005c00   0000a380  00006035  0000434b  RWIX

    And of course it is my code or that form our company  and I dont want anyone to take a close look at it :)

    What I will try to do is establish an minimal exampel. I will keep this post edited up to date now, spending a couple of minutes tweeking my code.

    1. I tried to disable all Interrupts by out commenting all the _EINT() instructions but the problem still is the same

    Next step will be to narrow down the code, it will get unfuncional for me but still compileable. So perhaps I will get insight on when this behaviour stops and starts, perhaps it has something to do with code size in general.

    2. I did comment out the enter LPM3 line, to see whether this is some LPM problem, strangely those random breaks occure before entering it, and afterwards also.

    Now the code only breaks in one point ( right when i want to write something to my attached LCD, thats why I also see it clearly where it stops ) before (with the enter LPM3 instructions) it did always stop in 2 occasions, the one mentioned and one before entering LPM3.

    3. I did not enter my real while(1)-loop with a lot of instructions, but did stop right before it in another while(1) with no instructions, still it stops without an breakpoint set, this time it does stop insice the while(1) which has no instructions in it, since it can never leave it.

    This might point something out. Perhaps the code stops after some number of instructions, but I do not know how and when.

    4. I still see inactive breakpoints, i will delete them all out in the CCS debug window

    Same behaviour, this does change nothing.

    5. I will comment out the line where it usually stops, it would make sense if the code stops now the amount of instructions later that i commented out.

    Indeed it seems like he is doing so, stopping a view steps later.

    So looking through all this, I would say somehow I have some breakpoints burned into my device on certain addresses, without me knowing it.

    Another point:

    I see this phenomenon on different boards of mine, as I have right now 2 PCBs that i am testing code on, I can see this behaviour on both of them with this certain code. When I debug prior codes ( that dont have this buggy behaviour) everythign works fine, so I guess I can exclude the PCBs and MSPs from the list of suspicioun :)

    What I cannot try is changing my PC switching to another one, since I only got this one to progam the devices.

    UPDATE #1

    What I do next is finding the newest version of my code where everything seemed to work fine and try to implement all the newer things again and thereby finding the problem or perhaps the problem of random breaks will not show up again.

    BAck then I did use the free CCS version ( code size limited ) now I am using the licensed version, so perhaps the compiler did trick me without me seeing it by putting the code in some way that makes the debugger halt...

    UPDATE #2

    I did set up my actual code on some older version and it does work fine without any breakpoints, now i am still wondering why this random breakpoints did happen, but it seems that i have quite found some workaround for myself right now



    I hope you can work with this information.

    Thanks again.

    Seb

  • Ok I put this into a new post, perhaps I will double post this also into the MSP Forum:

    I kind of circled the error into the hal_pmm library, which is provided by TI itself.

    I did some previous posts around changing Vcore levels in my controller, since i am working with LPMs and different working frequencies. As I want to achive eup to 25 MHz I need a high core voltage of 1,8 V. I have 2 routines of doing that: The first comes directly out of the instructions in the FamilyUserGuide, I did not double check it but it seems to work: here is hte code:

    void Set_VCore_Up (unsigned int level)                                    // Funktion zur VCore Erhöhung
    {
    PMMCTL0_H = 0xA5;                                                        // Open PMM registers for write access
    SVSMHCTL = SVSHE + SVSHRVL0 * level + SVMHE + SVSMHRRL0 * level;        // Set SVS/SVM high side new level
    SVSMLCTL = SVSLE + SVMLE + SVSMLRRL0 * level;                            // Set SVM low side to new level
    while ((PMMIFG & SVSMLDLYIFG) == 0);                                    // Wait till SVM is settled
    PMMIFG &= ~(SVMLVLRIFG + SVMLIFG);                                        // Clear already set flags
    PMMCTL0_L = PMMCOREV0 * level;                                            // Set VCore to new level
    if ((PMMIFG & SVMLIFG))                                                    // Wait till new level reached
    while ((PMMIFG & SVMLVLRIFG) == 0);
    SVSMLCTL = SVSLE + SVSLRVL0 * level + SVMLE + SVSMLRRL0 * level;        // Set SVS/SVM low side to new level
    PMMCTL0_H = 0x00;                                                        // Lock PMM registers for write access
    }

    Since I did not write that entire code of my own, I wanted to use the rather trustable hal_pmm. I already know that there is a error ( TI selfmade) in this library around some status low or high voltage levels, so here is the code, with the right lines:

    unsigned int SetVCoreUp (unsigned char level)
    {
      unsigned int PMMRIE_backup,SVSMHCTL_backup;

      // Open PMM registers for write access
      PMMCTL0_H = 0xA5;

      // Disable dedicated Interrupts to prevent that needed flags will be cleared
      PMMRIE_backup = PMMRIE;
      PMMRIE &= ~(SVSMHDLYIE | SVSMLDLYIE | SVMLVLRIE | SVMHVLRIE | SVMHVLRPE);
      // Set SVM highside to new level and check if a VCore increase is possible
      SVSMHCTL_backup = SVSMHCTL;
      PMMIFG &= ~(SVMHIFG | SVSMHDLYIFG);
      SVSMHCTL = SVMHE | SVMHFP | (SVSMHRRL0 * level);
      // Wait until SVM highside is settled
      while ((PMMIFG & SVSMHDLYIFG) == 0);
      // Disable full-performance mode to save energy
      SVSMHCTL &= ~_HAL_PMM_SVSFP ;
      // Check if a VCore increase is possible
      if ((PMMIFG & SVMHIFG) == SVMHIFG){            //-> Vcc is to low for a Vcore increase
          // recover the previous settings
          PMMIFG &= ~SVSMHDLYIFG;
          SVSMHCTL = SVSMHCTL_backup;
          // Wait until SVM highside is settled
          while ((PMMIFG & SVSMHDLYIFG) == 0);
          // Clear all Flags
          PMMIFG &= ~(SVMHVLRIFG | SVMHIFG | SVSMHDLYIFG | SVMLVLRIFG | SVMLIFG | SVSMLDLYIFG);
          // backup PMM-Interrupt-Register
          PMMRIE = PMMRIE_backup;
          
          // Lock PMM registers for write access
          PMMCTL0_H = 0x00;
          return PMM_STATUS_ERROR;                       // return: voltage not set
      }
      // Set also SVS highside to new level            //-> Vcc is high enough for a Vcore increase
      SVSMHCTL |= SVSHE | (SVSHRVL0 * level);
      // Set SVM low side to new level
      SVSMLCTL = SVMLE | SVMLFP | (SVSMLRRL0 * level);
      // Wait until SVM low side is settled
      while ((PMMIFG & SVSMLDLYIFG) == 0);
      // Clear already set flags
      PMMIFG &= ~(SVMLVLRIFG | SVMLIFG);
      // Set VCore to new level
      PMMCTL0_L = PMMCOREV0 * level;
      // Wait until new level reached
      if (PMMIFG & SVMLIFG)
      while ((PMMIFG & SVMLVLRIFG) == 0);
      // Set also SVS/SVM low side to new level
      PMMIFG &= ~SVSMLDLYIFG;
      SVSMLCTL |= SVSLE | (SVSLRVL0 * level);
      // wait for lowside delay flags
      while ((PMMIFG & SVSMLDLYIFG) == 0);

    // Disable SVS/SVM Low
    // Disable full-performance mode to save energy
      SVSMLCTL &= ~(_HAL_PMM_DISABLE_SVSL_+_HAL_PMM_DISABLE_SVML_+_HAL_PMM_SVSFP );

      // Clear all Flags
      PMMIFG &= ~(SVMHVLRIFG | SVMHIFG | SVSMHDLYIFG | SVMLVLRIFG | SVMLIFG | SVSMLDLYIFG);
      // backup PMM-Interrupt-Register
      PMMRIE = PMMRIE_backup;

      // Lock PMM registers for write access
      PMMCTL0_H = 0x00;
      return PMM_STATUS_OK;                               // return: OK
    }

    //****************************************************************************//
    // Set VCore down (Independent from the enabled Interrupts in PMMRIE)
    //****************************************************************************//
    unsigned int SetVCoreDown (unsigned char level)
    {
      unsigned int PMMRIE_backup;

      // Open PMM registers for write access
      PMMCTL0_H = 0xA5;

      // Disable dedicated Interrupts to prevent that needed flags will be cleared
      PMMRIE_backup = PMMRIE;
      //PMMRIE &= ~(SVSMHDLYIE | SVSMLDLYIE | SVMLVLRIE | SVMHVLRIE | SVMHVLRPE); --changed due to E2E
      PMMRIE &= ~(SVSMHDLYIE | SVSMLDLYIE | SVMLVLRIE | SVMHVLRIE | SVMHVLRPE | SVSHPE | SVSLPE);
      // Set SVM high side and SVM low side to new level
      PMMIFG &= ~(SVMHIFG | SVSMHDLYIFG | SVMLIFG | SVSMLDLYIFG);
      SVSMHCTL = SVMHE | SVMHFP | (SVSMHRRL0 * level);
      SVSMLCTL = SVMLE | SVMLFP | (SVSMLRRL0 * level);
      // Wait until SVM high side and SVM low side is settled
      while ((PMMIFG & SVSMHDLYIFG) == 0 || (PMMIFG & SVSMLDLYIFG) == 0);

      // Set VCore to new level
      PMMCTL0_L = PMMCOREV0 * level;

      // Set also SVS highside and SVS low side to new level
      PMMIFG &= ~(SVSHIFG | SVSMHDLYIFG | SVSLIFG | SVSMLDLYIFG);
      SVSMHCTL |= SVSHE | SVSHFP | (SVSHRVL0 * level);
      SVSMLCTL |= SVSLE | SVSLFP | (SVSLRVL0 * level);
      // Wait until SVS high side and SVS low side is settled
      while ((PMMIFG & SVSMHDLYIFG) == 0 || (PMMIFG & SVSMLDLYIFG) == 0);
      // Disable full-performance mode to save energy
      SVSMHCTL &= ~_HAL_PMM_SVSFP;
    // Disable SVS/SVM Low
    // Disable full-performance mode to save energy
      SVSMLCTL &= ~(_HAL_PMM_DISABLE_SVSL_+_HAL_PMM_DISABLE_SVML_+_HAL_PMM_SVSFP );
        
      // Clear all Flags
      PMMIFG &= ~(SVMHVLRIFG | SVMHIFG | SVSMHDLYIFG | SVMLVLRIFG | SVMLIFG | SVSMLDLYIFG);
      // backup PMM-Interrupt-Register
      PMMRIE = PMMRIE_backup;
      // Lock PMM registers for write access
      PMMCTL0_H = 0x00;

      if ((PMMIFG & SVMHIFG) == SVMHIFG)
        return PMM_STATUS_ERROR;                         // Highside is still to low for the adjusted VCore Level
      else return PMM_STATUS_OK;                        // Return: OK
    }

    Now in my code i am using some functions reducing or powering up the frequency of the CPU, in there i am switching the Vcore-levels as well.

    void clock_init(char a)
    {
        if(a==1)        // Mess Modus 25 MHz MCLK Takt
        {
            Enable_33V(ON);                                        // 3,3V Spannungsversorgung einschalten
            __delay_cycles(400);                                // Kurz warten zur stabilisierung der Spannungsversorgung

              Set_VCore_Up (1);
              Set_VCore_Up (2);
              Set_VCore_Up (3);

            P5SEL |= 0x0C;                                       // Port select XT2
            UCSCTL6 &= ~(XT2OFF);                                // Set XT1 & XT2 On
        do                                                        // Loop until XT1,XT2 & DCO stabilizes
        {
            UCSCTL7 &= ~(XT2OFFG + XT1LFOFFG + XT1HFOFFG + DCOFFG);        // Clear XT2,XT1,DCO fault flags
            SFRIFG1 &= ~OFIFG;                                  // Clear fault flags
        }while (SFRIFG1&OFIFG);                               // Test oscillator fault flag (OSC Fault Flag set again?)
            UCSCTL6 |= XT2DRIVE_3;                                // Set oscillator current and range
            UCSCTL4 |= SELM__XT2CLK + SELS__XT2CLK + SELA__XT1CLK;            // Set XT2CLK as MCLK clock source
            UCSCTL5 &= ~(DIVM_7);
            UCSCTL5 |= DIVM__1;                            // Set MCLK source divider to 0 (1,2,4,8,16,32)
        }
        else        // Menu-Darstellungmpdus: 25 MHz durch maximalen Teiler 32 zur Stromersparnis teilen
        {
            //UCSCTL6 |= XT2DRIVE_0;                                // Set oscillator current and range
            UCSCTL5 |= DIVM__16;                                // Set MCLK source divider to 0 (1,2,4,8,16,32)
              //UCSCTL4 = SELM__XT1CLK + SELS__XT1CLK;                 // MCLK = SMCLK = ACLK = VLO  funktioniert das auch mit der RTC???
              //Set_VCore_Up (2);
              //Set_VCore_Up (1);
              //Set_VCore_Up (0);
        }
    }

    This code works, but it wont put down the Vcore level again ( which in my opinion is not that bad since it doesnt cost 1µA in LPM)

    NOW the code that will make my debugger randomly break:

    void clock_init(char a)
    {
        if(a==1)        // Mess Modus 25 MHz MCLK Takt
        {
            Enable_33V(ON);                                        // 3,3V Spannungsversorgung einschalten
            __delay_cycles(400);                                // Kurz warten zur stabilisierung der Spannungsversorgung

            SetVCore(3);

            P5SEL |= 0x0C;                                       // Port select XT2
            UCSCTL6 &= ~(XT2OFF);                                // Set XT1 & XT2 On
        do                                                        // Loop until XT1,XT2 & DCO stabilizes
        {
            UCSCTL7 &= ~(XT2OFFG + XT1LFOFFG + XT1HFOFFG + DCOFFG);        // Clear XT2,XT1,DCO fault flags
            SFRIFG1 &= ~OFIFG;                                  // Clear fault flags
        }while (SFRIFG1&OFIFG);                               // Test oscillator fault flag (OSC Fault Flag set again?)
            UCSCTL6 |= XT2DRIVE_3;                                // Set oscillator current and range
            UCSCTL4 |= SELM__XT2CLK + SELS__XT2CLK + SELA__XT1CLK;            // Set XT2CLK as MCLK clock source
            UCSCTL5 &= ~(DIVM_7);
            UCSCTL5 |= DIVM__1;                            // Set MCLK source divider to 0 (1,2,4,8,16,32)
        }
        else        // Menu-Darstellungmpdus: 25 MHz durch maximalen Teiler 32 zur Stromersparnis teilen
        {
            //UCSCTL6 |= XT2DRIVE_0;                                // Set oscillator current and range
            UCSCTL5 |= DIVM__16;                                // Set MCLK source divider to 0 (1,2,4,8,16,32)
              //UCSCTL4 = SELM__XT1CLK + SELS__XT1CLK;                 // MCLK = SMCLK = ACLK = VLO  funktioniert das auch mit der RTC???
            SetVCore(0);
        }
    }

    And now TI it is your turn to tell me why the Vcore level is producing wring breakpoints...

    Thanks for still being with me.

    Seb

  • Hi Seb/MSP Team,


    Seb, I have moved your post so the MSP Team can hopefully take a look.

    MSP team, could you please have a look at the issues in this thread.

    Best Regards,

    Lisa

  • Sorry, I too do not kow why it stops.
    The MSP can set breakpoints not only on a code line, but also when a certain memory location is read/written or if a register changes its value or changes to a specific value. Those breakpoints are AFAIK not listed in the breakpoints view (as these are only position-dependent breakpoints).

    However, your screenshot has shown some other, serious problem, with your source code.

    the line
    P2DIR&=BIT7+BIT6+BIT5+BIT4+~BIT3+~BIT2+~BIT1+~BIT0;
    (and similar others) definitely doesn't do what you intend to do.

    Translating it into values, it does
    P2DIR &= 0x80+0x40+0x20+0x10+0xfff7+0xfffb+0xfffd+0xfffe = 0x(400)dd

    When doing bit operations, you should never use + or -, as these are arithmetical operators. The compiler won't complain as they are (take for themselves) valid operations. And adding bits will give the same result as ORing bits. If, and only if, each bit appears once at max. When using bitfields, or having the same bit twice in the assignments, the outcome of + is totally different from |.
    And when you invert a value (for clearing a bit) you'll set all other bits in this value, so you cannot add to an inversion without completely messing things up.
    If in the above line you want to clear BIT0..3 and keep BIT4..7 at current state, the proper operation would be

    P2DIR &= ~(BIT3|BIT2|BIT1|BIT0);
    FIRST group the bits by ORing them, then invert the result.

  • Hello,

    thanks for that tip. I will change my code into doing so. You are right about that, I didnt spent time thinking about it as it seemed right to me. And I do this operation right before entering LPM3, thats why I couldnt see any major issues when proceeding in my code.

    Thank You.

**Attention** This is a public forum