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.

Sub-standard I/O for LaunchPad

The LaunchPad has a so-called Application UART that enables the F2xx1 chip to communicate via a USB virtual COM Port to terminal programs in the PC at up to 9.6kb/s.

I wrote some quick and dirty sub-standard I/O routines to facilitate this capability.

First, you need to call either “set_baud(baud_divider)” or “auto_baud(void)” to set a BAUDRATE to match that of the terminal program in the PC. After that, you can call “putchar(character)” to send characters (one character per call) to the PC. Optionally, you can also receive characters (one character per call) from the PC by calling “character = getchar()”

You need a SMCLK anywhere from 0.5MHz to 16MHz. The BAUDRATE can be anywhere from 1.2kb/s to 9.6kb/s. If you know both SMCLK and baud-rate (or at least the ratio of them), you can use “set_baud(SMCLK / BAUDRATE)”. Otherwise you could use “auto_baud()”. But then the user has to press the “Enter” key on the PC so that auto_baud can measure and set up the baud_divider automatically.

P1.1 (TXD) and P1.2 (RXD) are used and cannot be used for other purposes. TA2 is temporarily used for the duration of these routines. It can be freely used for other purposes, but not while these sub-standard I/O routines are running.

These routines are not “green”. But you can fix that easily. I marked those energy wasting part with /* wait */.

/*******************************************************************************
*                   Sub-Standard I/O for LaunchPad Board                       *
*                                OCY Nov 2010                                  *
*******************************************************************************/
#include <msp430.h>
#define RXD BIT2
#define TXD BIT1
__no_init int baud_divider;
//==============================================================================
int set_baud ( int i )
{
  baud_divider = i;
  return (i);
}
//==============================================================================
int auto_baud ( void )
{
  __no_init int zero;
  P1SEL |= RXD;
  TACCTL0 = 0;
  TACCTL1 = CM_2 | SCS | CAP;
  TACTL = TASSEL_2 | MC_2 | TACLR;
  while ((TACCTL1 & CCIFG) == 0) {/* wait */}
  zero = TACCR1;
  TACCTL1 = CM_1 | SCS | CAP;
  while ((TACCTL1 & CCIFG) == 0) {/* wait */}
  P1SEL &= ~RXD;
  TACTL = 0;
  return (baud_divider = TACCR1 - zero);
}
//==============================================================================
int putchar ( int i )
{
  TACCR0 = 0;
  TACCTL0 = OUT;
  TACCTL1 = 0;
  P1SEL |= TXD;
  P1DIR |= TXD;
  TACTL = TASSEL_2 | MC_2 | TACLR;
  i = (i + 0x100) << 1;
  do
  {
    TACCR0 += baud_divider;
    if (i & 1) TACCTL0 = OUTMOD_1;
    else TACCTL0 = OUTMOD_5;
    while ((TACCTL0 & CCIFG) == 0) {/* wait */}
  } while ((i = (i >> 1)) != 0);
  P1DIR &= ~TXD;
  P1SEL &= ~TXD;
  TACTL = 0;
  return 1;
}//=============================================================================
int getchar ( void )
{
  int byte = 0;
  P1SEL |= RXD;
  TACCTL0 = 0;
  TACCTL1 = CM_2 | SCS | CAP;
  TACTL = TASSEL_2 | MC_2 | TACLR;
  while ((TACCTL1 & CCIFG) == 0) {/* wait */}
  TACCR1 += baud_divider >> 1;
  for (int bit = 8; bit > 0; bit--)
  {
    TACCR1 += baud_divider;
    TACCTL1 = 0;
    while ((TACCTL1 & CCIFG) == 0) {/* wait */}
    if (TACCTL1 & CCI) byte |= 0x100;
    byte = byte >> 1;
  }
  P1SEL &= ~RXD;
  TACTL = 0;
  return (byte);
}
//==============================================================================

**Attention** This is a public forum