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.

GSM modem interfacing with msp430f2013

Other Parts Discussed in Thread: MSP430F2013, MAX3232

The msp430f2013 does not have UART ports. So I found that a software UART can be created and I followed the code from J H Davies book. As I have mentioned in the question, i am basically trying to interface a GSM modem to the MSP. My question are'

1. Is it possible to do this on a software UART?

2. Once I have compiled the software UART program, how do I check it? Can I do this on Hyperterminal or putty?

I have read the various discussions on this forum about software UART but my doubt is not cleared.

The code i used for software UART is below.

#include <io430x20x3.h> // Header file for this device
#include <stdint.h> // Integers of defined sizes
#include "uartlib.h" // Library for software UART
#define LED P1OUT_bit.P1OUT_0   // Output pin for LED (active high)
uint8_t RXBUF; // Buffer for received byte
uint8_t TXBUF; // Buffer for byte to transmit#define BITTIME ((1000000 + 4800)/9600) // Cycles of TACLK per bit , 1MHz
#define HALFTIME (BITTIME/2) // Cycles for half a bit
void UARTSetUp ( void )
{
TACTL = TASSEL_2 | MC_2; // TACLK = SMCLK = 1MHz
TACCTL0 = OUT | OUTMOD_0 | CCIFG;
TACCTL1 = CM_2 | CCIS_1 | SCS | CAP | OUTMOD_0 | CCIE;
RXIFG = 0; // Buffer empty , no byte received
TXIFG = 1; // Buffer empty , ready to accept TX
}
//----------------------------------------------------------------------
// Write byte to TXBUF; clears flag , starts transmitter if necessary
//----------------------------------------------------------------------
void WriteTXBUF ( const uint8_t TXData)
{
TXBUF = TXData; // Transfer data to buffer
TXIFG = 0; // Clear interrupt flag
TACCTL0_bit. CCIE = 1; // Enable interrupts if inactive ,
} // no effect if already running
//----------------------------------------------------------------------
// Read byte from RXBUF; clears flag
//----------------------------------------------------------------------
uint8_t ReadRXBUF ( void )
{
RXIFG = 0; // Clear interrupt flag
return RXBUF; // Read data from buffer
}
//----------------------------------------------------------------------
// ISR for Timer_A2 , channel 0: transmission
//----------------------------------------------------------------------
#pragma vector = TIMERA0_VECTOR
_ _interrupt void TIMERA0_ISR ( void ) // Acknowledged automatically
{
static uint8_t TXBitCount = 0; // Count bits transmitted
static uint16_t TXShiftReg; // Shift register for transmission
LED = 1; // Show start of activity
if (TXBitCount == 0) 
{ // Ready to start new byte
if (TXIFG == 0) 
{ // Byte available to transmit
TXShiftReg = TXBUF; // Load data from buffer
TXShiftReg |= BIT8; // Add stop bit after msb
TXIFG = 1; // Show that buffer is available
TXBitCount = 9; // Number of bits including stop bit
TACCR0 = TAR + BITTIME; // Delay until start of start bit
TACCTL0 = OUTMOD_5 | CCIE; // Clr output on compare for ST
else 
{ // No data available , shut down
TACCTL0 = OUT | OUTMOD_0 | CCIFG; // Idle: output high ,
} // disable interrupt , set flag for int 'pt when reenabled
else
{ // Send next bit
if (TXShiftReg & BIT0) 
{ // Send 1 next
TACCTL0 = OUTMOD_1 | CCIE; // Set output on compare
else 
{ // Send 0 next
TACCTL0 = OUTMOD_5 | CCIE; // Clear output on compare
}
TACCR0 += BITTIME; // Delay until next bit
TXShiftReg >>= 1; // Shift right , remove lsb
--TXBitCount; // Update bit counter
}
LED = 0; // Show end of activity
}
//----------------------------------------------------------------------
// ISR for Timer_A2 , channel 1 and timer core ( inactive): reception
//----------------------------------------------------------------------
#pragma vector = TIMERA1_VECTOR
_ _interrupt void TIMERA1_ISR ( void ) // NOT acknowledged automatically
{
static uint8_t RXBitCount = 0; // Count bits received
static uint8_t RXShiftReg; // Shift register for reception
LED = 1; // Show start of activity
TACCTL1_bit. CCIFG = 0; // Acknowledge interrupt , clear flag
if (TACCTL1_bit.CAP) 
{ // Capture mode , start bit detected
TACCTL1_bit.CAP = 0; // Switch to sampling (compare ) mode
TACCR1 += HALFTIME; // Wait for half a bit time
RXBitCount = 9; // Bits to receive including ST, SP
else 
{
switch (RXBitCount) 
{
case 9: // Start bit
if (TACCTL1_bit. SCCI) 
{ // Error: start bit should be low
TACCTL1_bit.CAP = 1; // Abandon reception
else 
{ // Correct: proceed to receive data
TACCR1 += BITTIME; // Wait for complete bit time
--RXBitCount; // Update bit counter
}
break ;
case 0: // Stop bit
if (TACCTL1_bit. SCCI) 
{ // Correct: stop bit should be high
RXBUF = RXShiftReg; // Store data into buffer
RXIFG = 1; // Raise flag to show new data
} // (discard byte if stop bit low)
TACCTL1_bit.CAP = 1; // Return to capture mode
break ;
default : // Data bit (lsb first), cases 1-8
RXShiftReg >>= 1; // Shift data , clear msb for new bit
if (TACCTL1_bit. SCCI) 
{
RXShiftReg |= BIT7; // Set received bit if high
}
TACCR1 += BITTIME; // Wait for complete bit time
--RXBitCount; // Update bit counter
break ;
}
}
LED = 0; // Show end of activity
}

  • Hi Niveditha,

    Niveditha U S said:
    1. Is it possible to do this on a software UART?

    Yes, it is possible.  The biggest concern is matching UART settings (Baud rate, data length, stop bits, parity).  If you are using logic level UART, you need to match voltages as well, if you are using RS-232, you need to put a RS-232 level shifter on the bus.

    Niveditha U S said:
    2. Once I have compiled the software UART program, how do I check it? Can I do this on Hyperterminal or putty?

    Yes, this is actually one of the easiest ways to test UART, as it allows you to directly control the opposite end of the UART stream.  The easiest way to set up this test method is using the back channel UART on the MSP-EXP430G2 launchpad.  You can easily port your code to run on a device supported by the G2 Launchpad.  The USB-Serial drivers for the launchpad are already included in CCS, so it is as close to a plug and play system as you can get.

    Mike

  • I am using RS 232 GSM, so I am using MAX3232 converter to connect to MSP430.

    In case of the hyperterminal testing, I performed the same procedure as I would to test a regular GSM modem, so the UART of MSP is supposed to echo back the characters typed, right? That didn't happen. I configured the right COM port and UART settings in Hyperterminal. I am not sure where I am going wrong.
  • Start with an example that uses USI for TX_UART, as it can be set for 10bits and will shift out the bits very precisely.
    RX, you do have to use a timer and 9600 is the limit and no other cycle-hogging-ISR can be active at the same time.
  • Is there any chance the transmission ISR has a bug? There doesn't seem to be any sort of loop that would transmit from a byte any other bit but the first one.

    Byte is validated twice with help of a if/else and the first bite is processed correctly. When the end of the outer if/else is reached the execution doesn't return up to process other 8 bits, flows down and returns from the ISR. Shouldn't the if/else be enclosed in a while loop or similar?

    // ----------------------------------------------------------------------
    // ISR for Timer_A2 , channel 0: transmission
    // ----------------------------------------------------------------------
    #pragma vector = TIMERA0_VECTOR
    __interrupt void TIMERA0_ISR (void) // Acknowledged automatically
    {
    	static uint8_t TXBitCount = 0; // Count bits transmitted
    	static uint16_t TXShiftReg; // Shift register for transmission
    	LED = 1; // Show start of activity
    	if (TXBitCount == 0) { // Ready to start new byte
    		if (TXIFG == 0) { // Byte available to transmit
    			TXShiftReg = TXBUF; // Load data from buffer
    			TXShiftReg |= BIT8; // Add stop bit after msb
    			TXIFG = 1; // Show that buffer is available
    			TXBitCount = 9; // Number of bits including stop bit
    			TACCR0 = TAR + BITTIME; // Delay until start of start bit
    			TACCTL0 = OUTMOD_5 | CCIE; // Clr output on compare for ST
    		} else { // No data available , shut down
    			TACCTL0 = OUT | OUTMOD_0 | CCIFG; // Idle: output high ,
    		} // disable interrupt , set flag for int 'pt when reenabled
    	} else { // Send next bit
    		if (TXShiftReg & BIT0) { // Send 1 next
    			TACCTL0 = OUTMOD_1 | CCIE; // Set output on compare
    		} else { // Send 0 next
    			TACCTL0 = OUTMOD_5 | CCIE; // Clear output on compare
    		}
    		TACCR0 += BITTIME; // Delay until next bit
    		TXShiftReg >>= 1; // Shift right , remove lsb
    		--TXBitCount; // Update bit counter
    	}
    	LED = 0; // Show end of activity
    }
    // ----------------------------------------------------------------------

    // ----------------------------------------------------------------------
    // ISR for Timer_A2 , channel 0: transmission
    // ----------------------------------------------------------------------
    #pragma vector = TIMERA0_VECTOR
    __interrupt void TIMERA0_ISR (void) // Acknowledged automatically
    {
        static uint8_t TXBitCount = 0; // Count bits transmitted
        static uint16_t TXShiftReg; // Shift register for transmission
        LED = 1; // Show start of activity
        if (TXBitCount == 0) { // Ready to start new byte
            if (TXIFG == 0) { // Byte available to transmit
                TXShiftReg = TXBUF; // Load data from buffer
                TXShiftReg |= BIT8; // Add stop bit after msb
                TXIFG = 1; // Show that buffer is available
                TXBitCount = 9; // Number of bits including stop bit
                TACCR0 = TAR + BITTIME; // Delay until start of start bit
                TACCTL0 = OUTMOD_5 | CCIE; // Clr output on compare for ST
            } else { // No data available , shut down
                TACCTL0 = OUT | OUTMOD_0 | CCIFG; // Idle: output high ,
            } // disable interrupt , set flag for int 'pt when reenabled
        } else { // Send next bit
            if (TXShiftReg & BIT0) { // Send 1 next
                TACCTL0 = OUTMOD_1 | CCIE; // Set output on compare
            } else { // Send 0 next
                TACCTL0 = OUTMOD_5 | CCIE; // Clear output on compare
            }
            TACCR0 += BITTIME; // Delay until next bit
            TXShiftReg >>= 1; // Shift right , remove lsb
            --TXBitCount; // Update bit counter
        }
        LED = 0; // Show end of activity
    }
    // ----------------------------------------------------------------------

**Attention** This is a public forum