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.

Trouble compiling after error is corrected.

Other Parts Discussed in Thread: MSP430G2553

Hello,

I am having some trouble with an error and recompiling after I remove the error (using CCS).  I was trying to write some code to send the MSP430G2553.  I was using example msp430g2XX3_ta_01.c noted below


#include <msp430g2553.h>
void main(void)
{
WDTCTL = WDTPW + WDTHOLD; // Stop WDT
P1DIR |= 0x01; // P1.0 output
CCTL0 = CCIE; // CCR0 interrupt enabled
CCR0 = 50000;
TACTL = TASSEL_2 + MC_2; // SMCLK, contmode
_BIS_SR(LPM0_bits + GIE); // Enter LPM0 w/ interrupt
}
// Timer A0 interrupt service routine
#pragma vector=TIMER0_A0_VECTOR
__interrupt void Timer_A (void)
{
P1OUT ^= 0x01; // Toggle P1.0
CCR0 += 50000; // Add Offset to CCR0
}

Basically, I want to add the relevant parts of this to my code so that my code would execute some stuff, pause in low power mode for a set amount of time and then execute some other stuff.  I worked the sample code into my code, compiled and got an error.  I tried to debug the error, but even after removing all of the new code, my original code will not compile.  I get the error "#10099-D program will not fit into available memory. placement with alignment fails for section "TIMER0_A0" size 0x4 . Available memory ranges: lnk_msp430g2553.cmd /my_project_name line 86 C/C++ Problem".  I suspect I have to delete a file that is created during the compiling operation (a *.out file perhaps?), but I don't know which one.  I can get around this error if I create a new project and copy/paste all of my original code in the new project, but creating a new project every time I have to debug will get time consuming.

Thanks

Jeff

  • Jeff Court said:
    placement with alignment fails for section "TIMER0_A0" size 0x4 .

    TIMER0A0 is a segment which holds the address ofh teTIMER0_A0 interrupt funciton. it has a size of two bytes (the 16 bit address of the ISR). However, for some reason the linekr wants to place 4 bytes in there. The most common cause for this is that you have two ISRs that are placed to the TIMER0_A0_VECTOR.
    You should clean your project (remove all intermediate files) and try to compile and link again.

    Deleting the .out file isn't a problem. it is the final file created when linkign succeeded. Deleting it will just have it rebuilt.

    However, I think you have not deleted enough, so the linker finds two ISRs where only one fits.

  • Hello Jens-Michael, 

    Thanks for your reply.  I was able to locate the "clean" button in CCS and it worked perfectly!

    I think you are correct and I am using two ISRs.  I am not familiar with the timer, so I just tried to have these two snippets without further modification

    #pragma vector=TIMER0_A0_VECTOR // for internal temp readings
    __interrupt void ta0_isr(void)
    {
    TACTL = 0;
    LPM0_EXIT; // Exit LPM0 on return
    }

    #pragma vector=TIMER0_A0_VECTOR
    __interrupt void Timer_A (void)
    {
    P1OUT ^= 0x01; // Toggle P1.0
    CCR0 += 50000; // Add Offset to CCR0
    }

    The first one is for part of a temperature reading, the second is for the delay & sleep code I am adding.  I suspected the original error was generated by those two snippets conflicting, but I am not sure how to fix it.  I haven't had a chance to debug much because of the "cleaning" issue.  Suggestions on what I should search for to get both of them to work (at different times in the code) would be greatly appreciated.

  • You cannot switch the ISR address at runtime. THis would require erasing and reqriting the whole 512 byte sector in which the complete vector resides (and maybe otehr code too).

    What you can do is to introduce a golbal 'switch' variable.
    volatile unsigned char init = 1;

    and in the ISR, you check

    if (init) {
      code to be executed on first use...
      init = 0;
    } else {
      code to be executed later...
    }

    However, this adds a few cycles to ISR execution time.

    Or you use a different CCR unit for the two tasks. Then you use two different ISRs: one for CCR0 (TIMER0_A0_VECTOR) for the 'regular' interrupt, and one for CCR1 (TIMER0_A1_VECTOR) for the 'one time' interrupt. (don't forget to clear the CCR1 IFG bit. The CCR0 IFG bti is auto-cleared when the CCR0 ISR is entered).

    P.s.: CCR1 shares its vector/ISR with the timer oveflow interrupt and all other CCRs except CCR0.

**Attention** This is a public forum