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.

CCS/MSP430G2553: USCI(SPI) Interrupt and Timer interrupt

Part Number: MSP430G2553
Other Parts Discussed in Thread: CC430F6137

Tool/software: Code Composer Studio

Hello,

this might be an interesting theme for beginner, myself as well.

I'm trying to build a SPI communication between CC430f6137(Master) and MSP430g2553(Slave).

With the help of , I get the "SPI state machine " between two MSP430g2553, with a little bit modification, I simplifed the state machine between CC430f6137 and MSP430g2553,

and it works good with some assigned default strings.

The MSP430g2553 is used to get the data from sensor, and send the data with SPI to CC430f6137.

My problem is,

in MSP430g2553, I use another timer interrupt to deal with my sensor, instead of default strings the data will be send per SPI,

in the beginning CC430f6137 get the right strings like

RATE: 004.3000
VALUE: 000.1554
RATE: 0004.300
VALUE: 0000.154
RATE: 0004.400
VALUE: 0000.143

but after several seconds, I get some strings like

RATE: €7Ÿÿïþ
VALUE: çy·õ~ùÓ
RATE: =Ííø¿¿°½
VALUE: ñ·ûøþýëZ
RATE: ˜ù¿½Þ¶ù
VALUE: ý×þôÎæ,

I am searching a way to solve the conflict between USCI interrupt and timer interrupt.

Any idea and suggestions will be appreciated.

Thank you in advance.

--Qibin

  • Hello Qibin,

    It sounds like you are displaying your data via a command terminal on PC after sending it over. If that is the case, then you need to translate your data to ASCII characters before being displayed. the program to do this could be on either device, it just needs to be done before you send it to your PC.
  • Hi Jace,
    Thank you for replying. Yes, I have translated the float value to strings and the values like RATE: 004.3000 VALUE: 000.1554 are the data exactly what I need, but late it turns out like disaster. I was wondering how can I make the communication correctly with each single character right, and I have no idea about how long delay time should be, the delay time between transmitting of two single byte.
    And if there is someone came up with such kind of problems before, could you please share me.

    best regards,
    Qibin
  • And also, I have try out SPI communication between MSP430g2553 and CC430f6137(master), both side I used USCI ISR, without time interrupt

    and the communcation runs very good with nice string infomation transmission.

    Here are some code of slave MSP430g2553, in main() just initialized the setting, the USCI(SPI) ISR do part of tranmission FSM, and I think the conflict between USCI ISR and timer ISR is the key of the problem, I have not so much experience with that, and I am still searching a solution.

    int main(void)
    {
        WDTCTL = WDTPW | WDTHOLD;	// Stop watchdog timer
    
        init_SMS50();  // init clk,comparator, coresponding PINs
        init_clk();
        initSPI();
    
        __bis_SR_register(GIE);
    
        while(1)
    	{
        	__no_operation();
    	}
    }
    
    // cycle counter
    #pragma vector=TIMER0_A0_VECTOR
    __interrupt void Timer0_A0_Compare(void)
    {	TA0CCTL0 &= ~CCIFG; //clear interrupt flag
    
    	 comp_out = BIT0 & CACTL2;  // catch comparator output
    	 P2OUT = BIT0 & (~comp_out);  // inverte P2.0 as ~Q
    	 NOC ++;  // increment NOC
    	 if(comp_out)	NO1++;  //incrment NO1 if Q:HIGH
    
    	 if( NOC == MEASURE_CYCLES)
    	 {
    		ratio = (float) 100*NO1/NOC;  // save ratio in buffer [%]
    		NOC = 0;
    		NO1 = 0;
    	 }
    }
    
    
    #if defined(__TI_COMPILER_VERSION__) || defined(__IAR_SYSTEMS_ICC__)
    #pragma vector=USCIAB0RX_VECTOR
    __interrupt void USCIA0RX_ISR(void)
    #elif defined(__GNUC__)
    void __attribute__ ((interrupt(USCIAB0RX_VECTOR))) USCI0RX_ISR (void)
    #else
    #error Compiler not supported!
    #endif
    {
    	uca0_rx_val = UCA0RXBUF;
    	switch(SlaveMode)
    	{
    		case RX_REG_ADDRESS_MODE:		//prapare for tranmission
    			TransmitIndex = 0;
    			if(uca0_rx_val == MOISTURE_RATE)
    			{
    				TXByteCtr  = RATE_LENGTH;
    				CopyArray(RATE,TransmitBuffer,RATE_LENGTH);
    			}
    			else if(uca0_rx_val == MOISTURE_VALUE)
    			{
    				TXByteCtr  = VALUE_LENGTH;
    				CopyArray(VALUE,TransmitBuffer,VALUE_LENGTH);
    			}
    			SendUCA0Data(TransmitBuffer[TransmitIndex++]);	//transmit first byte
    			TXByteCtr--;
    			SlaveMode = TX_DATA_MODE;
    			break;
    		case TX_DATA_MODE:
    			if(TXByteCtr > 0)
    			{
    				SendUCA0Data(TransmitBuffer[TransmitIndex++]);
    				TXByteCtr--;
    			}
    			if(TXByteCtr == 0)
    			{
    				SlaveMode = IDLE_MODE;
    			}
    			break;
    		case IDLE_MODE:
    			SlaveMode = RX_REG_ADDRESS_MODE;
    			break;
    		default:break;
    	}
    
    }

  • In RX_REG_ADDRESS_MODE, if you receive anything other than MOISTURE_RATE or MOISTURE_VALUE, your TxByteCtr will go "negative" (0xFFFF) and you'll stay in TX_DATA_MODE and send out the next 65535 bytes in memory, which would match with your symptom. I suggest you add to the if()/elseif() an "else break;".

    How could this happen? One possibility is that the floating point divide in the timer ISR causes an overrun in the SPI, so the Rx byte sequence is disturbed.

    Unsolicited: "P2OUT = BIT0 & (~comp_out);" looks suspicious, since it zeroes all the bits in P2OUT except BIT0. Maybe this was intentional, but it doesn't look that way.

  • Hi Bruce,
    I took you advice, added "else break;" after if()/elseif(), and now the strange strings never showed up.
    As you mentioned of " P2OUT = BIT0& (~comp_out);", I need the first byte of register CACTL2, which is the output of comparator, and I need to PIN2.0 be convetered of comparator output and use this a feed back of the circuit.
    Thank you for your advice, very helpful.

**Attention** This is a public forum