?? msp430-tusb3410_demo.c
字號:
//------------------------------------------------------------------------------
// MSP430-TUSB3410 Reference Design Demo Code V1.00
//
// This demo software interfaces the MSP430 to the TUSB3410 USB-to-serial
// bridge controller. The program is part of the "MSP430 USB Connectivity
// using TUSB3410" application note (SLAA276). It is demonstrated how a blank
// USB configuration EEPROM is detected, and how it gets programmed with an
// image that is stored in MSP430 Flash memory. After this, a demo application
// is started. The demo receives characters from the TUSB3410 virtual COM port
// (VCP) with a baud rate of 460,800. The lower nibble of a received character
// is output to the LEDs 1...4 on the demo board. Also, on press or release of
// any push-button SW1...SW4, a byte is transmitted back to the PC containing
// the updated button state.
//
// MSP430 ressources used:
// o USART0 in UART mode for serial comm with TUSB3410
// o USART0 in I2C mode for comm with EEPROM
// o Timer_B7 for push-button query
//
// Andreas Dannenberg
// MSP430/TMS470 Applications
// Texas Instruments Inc.
// November 2005
//
// Built with IAR Embedded Workbench V3.30
//------------------------------------------------------------------------------
#include "msp430x16x.h"
//------------------------------------------------------------------------------
// I2C communication related definitions
//------------------------------------------------------------------------------
#define EEPROM_ADDRESS 0x50 // Address of EEPROM
#define OWN_ADDRESS 0x40 // I2C own address
//------------------------------------------------------------------------------
// Operate TUSB3410 RESET signal as open-drain output
//------------------------------------------------------------------------------
#define TUSB3410_RESET_LOW P3DIR |= 0x01
#define TUSB3410_RESET_HIGHZ P3DIR &= ~0x01
//------------------------------------------------------------------------------
// Misc definitions
//------------------------------------------------------------------------------
enum { false, true };
//------------------------------------------------------------------------------
// Globals used by I2C routines
//------------------------------------------------------------------------------
static unsigned char I2CBuffer[3];
static unsigned char I2CTxPtr;
//------------------------------------------------------------------------------
// Globals used by main() and ISRs
//------------------------------------------------------------------------------
static unsigned char ButtonState = 0;
static unsigned char ButtonSet = 0;
static unsigned char ButtonReleased = 0;
static unsigned char RxData;
static unsigned char DataReceived = 0;
//------------------------------------------------------------------------------
// The constant EEPROMImage[] contains the data to be loaded into the TUSB3410
// USB configuration EEPROM. It was generated using the tools provided in
// SLLC251 and then converted into a C constant. Note that the USB descriptor
// blocks contain checksums, therefore manual modification of the below EEPROM
// image is not recommended.
//
// USB vendor ID: 0x0451 (TI's VID)
// USB product ID: 0xbeef (This application's PID)
// USB product descriptor: "MSP430-TUSB3410 Reference Design"
//------------------------------------------------------------------------------
static const unsigned char EEPROMImage[] =
{
0x10, 0x34, 0x03, 0x12, 0x00, 0x33, 0x12, 0x01,
0x10, 0x01, 0xff, 0x00, 0x00, 0x08, 0x51, 0x04,
0xef, 0xbe, 0x01, 0x01, 0x01, 0x02, 0x00, 0x01,
0x05, 0x6c, 0x00, 0x34, 0x04, 0x03, 0x09, 0x04,
0x24, 0x03, 0x54, 0x00, 0x65, 0x00, 0x78, 0x00,
0x61, 0x00, 0x73, 0x00, 0x20, 0x00, 0x49, 0x00,
0x6e, 0x00, 0x73, 0x00, 0x74, 0x00, 0x72, 0x00,
0x75, 0x00, 0x6d, 0x00, 0x65, 0x00, 0x6e, 0x00,
0x74, 0x00, 0x73, 0x00, 0x42, 0x03, 0x4d, 0x00,
0x53, 0x00, 0x50, 0x00, 0x34, 0x00, 0x33, 0x00,
0x30, 0x00, 0x2d, 0x00, 0x54, 0x00, 0x55, 0x00,
0x53, 0x00, 0x42, 0x00, 0x33, 0x00, 0x34, 0x00,
0x31, 0x00, 0x30, 0x00, 0x20, 0x00, 0x52, 0x00,
0x65, 0x00, 0x66, 0x00, 0x65, 0x00, 0x72, 0x00,
0x65, 0x00, 0x6e, 0x00, 0x63, 0x00, 0x65, 0x00,
0x20, 0x00, 0x44, 0x00, 0x65, 0x00, 0x73, 0x00,
0x69, 0x00, 0x67, 0x00, 0x6e, 0x00, 0x00, 0x00,
0x00
};
//------------------------------------------------------------------------------
// Function prototypes
//------------------------------------------------------------------------------
void InitSystem(void);
void InitUART(void);
void Delay100(void);
void InitI2C(void);
unsigned char EEPROM_CheckNACK(void);
void EEPROM_ByteWrite(unsigned int Address, unsigned char Data);
unsigned char EEPROM_CurrentAddressRead(void);
unsigned char EEPROM_RandomRead(unsigned int Address);
void EEPROM_Write(unsigned int Address, unsigned char *Buffer,
unsigned int Count);
void EEPROM_Read(unsigned int Address, unsigned char *Buffer,
unsigned int Count);
unsigned int EEPROM_Verify(unsigned int Address, unsigned char *Buffer,
unsigned int Count);
//------------------------------------------------------------------------------
// void main(void)
//
// The main application code first initializes the MSP430 peripherals. Then,
// an event-processing loop is entered. While no event is pending, the MSP430
// rests in LPM0 with interrupts enabled.
//
// IN: ButtonState
// ButtonSet
// ButtonReleased
// DataReceived
// RxData
// OUT: ButtonState
// ButtonSet
// ButtonReleased
// DataReceived
//------------------------------------------------------------------------------
void main(void)
{
InitSystem();
// Initializes Timer_B7 to query the status of the push-buttons
// SW1, SW2, SW3, and SW4
TBCCTL0 = CM_1 + SCS + CAP + CCIE; // Capt. rising edge of P4.0
TBCCTL2 = CM_3 + SCS + CAP + CCIE; // Capt. rising edge of P4.2
TBCCTL4 = CM_3 + SCS + CAP + CCIE; // Capt. rising edge of P4.4
TBCCTL6 = CM_3 + SCS + CAP + CCIE; // Capt. rising edge of P4.6
TBCTL = TBSSEL_1 + ID_3 + MC_2; // ACLK / 8, continuous mode
// Activate UART0 RX interrupt operation
IE1 |= URXIE0; // Enable USART0 RX interrupt
IFG1 &= ~URXIFG0; // Ensure flag is cleared
while (1) // Main event processing loop
{
__disable_interrupt(); // Protect the following code
if (!ButtonSet && !ButtonReleased && !DataReceived)
{
__bis_SR_register(LPM0_bits + GIE); // Wait in LPM0 for event, int
__no_operation();
}
else
__enable_interrupt(); // Allow interrupts again
if (ButtonSet || ButtonReleased) // Button event pending?
{
while (!(IFG1 & UTXIFG0)); // Ensure USART is ready
__disable_interrupt(); // Protect the following code
U0TXBUF = ButtonState; // TX current button state
ButtonSet = 0; // Clear flags
ButtonReleased = 0;
__enable_interrupt(); // Allow interrupts again
}
if (DataReceived) // UART RX revent pending?
{
__disable_interrupt(); // Protect the following code
if (RxData & 0x01) // Check bit 0 of RX'd char...
P4OUT |= 0x02; // ...and set LED1 accordingly
else
P4OUT &= ~0x02;
if (RxData & 0x02) // Check bit 1 of RX'd char...
P4OUT |= 0x08; // ...and set LED2 accordingly
else
P4OUT &= ~0x08;
if (RxData & 0x04) // Check bit 2 of RX'd char...
P4OUT |= 0x20; // ...and set LED3 accordingly
else
P4OUT &= ~0x20;
if (RxData & 0x08) // Check bit 3 of RX'd char...
P4OUT |= 0x80; // ...and set LED4 accordingly
else
P4OUT &= ~0x80;
DataReceived = false; // Event was handled
__enable_interrupt(); // Allow interrupts again
}
}
}
//------------------------------------------------------------------------------
// void InitSystem(void)
//
// This function configures the MSP430. Peripherals are initialized, the
// external 8MHz crystal on LFXT1 is activated and used for ACLK and MCLK,
// and the contents of the external EEPROM is validated.
//
// IN: EEPROMImage[]
// OUT: -
//------------------------------------------------------------------------------
void InitSystem(void)
{
WDTCTL = WDTPW + WDTHOLD; // Stop Watchdog timer
// Port setup
P1OUT = 0x00; // Clear output latch
P1DIR = 0xfd; // All but P1.1 to output
P2OUT = 0x00; // Clear output latch
P2DIR = 0xfb; // All but P2.2 to output
P3OUT = 0x00; // Clear output latch
P3SEL = 0x3a; // Select I2C and UART0 pins
P3DIR = 0xd4; // P3.0/1/3/5 inp, others outp
P4OUT = 0x00; // Clear output latch
P4SEL = 0x55; // Timer funct. for P4.0/2/4/6
P4DIR = 0xaa; // P4.1/3/5/7 out, others inp
P5OUT = 0x00; // Clear output latch
P5DIR = 0xff; // All output
P6OUT = 0x00; // Clear output latch
P6DIR = 0xff; // All output
// Check if a button is held down during power-up. If so, trap software here.
// This is to allow the PC to invoke a BSL download, before the MSP430 RESET
// pin is switched to NMI mode, thus avoiding that any unintended device
// resets are caused by the TUSB3410 DTR signal.
if (P4IN & 0x55) // Check all buttons
{
P4OUT = 0xaa; // All LEDs on
while (1); // Loop forever
}
TUSB3410_RESET_LOW; // Hold TUSB3410 in reset
SVSCTL = 0xb0; // Enable SVS, monitor only
while ((SVSCTL & (SVSON + SVSOP)) != SVSON); // Wait until SVS is active,
// and voltage condition is met
// Clock system setup
BCSCTL1 |= XTS; // ACLK = LFXT1 = HF XTAL
__bic_SR_register(OSCOFF); // Turn on XT1 oscillator
do {
IFG1 &= ~OFIFG;
Delay100(); // SW delay ~125us @ def. DCO
} while (IFG1 & OFIFG); // Wait until XTAL is stable
BCSCTL2 |= SELM_3; // Select HF XTAL for MCLK
__enable_interrupt(); // Global interrupt enable
InitI2C(); // Configure USART0 for I2C
// Check if EEPROM is present. If so, verify EEPROM contents and program
// EEPROM image from MSP430 Flash memory if neccessary.
if (!EEPROM_CheckNACK())
if (!EEPROM_Verify(0, (void *)&EEPROMImage, sizeof EEPROMImage))
EEPROM_Write(0, (void *)&EEPROMImage, sizeof EEPROMImage);
WDTCTL = WDTPW + WDTHOLD + WDTNMI; // Stop WDT, deactivate RESET
TUSB3410_RESET_HIGHZ; // Resume TUSB3410 operation
InitUART(); // Configure USART0 for UART
}
//------------------------------------------------------------------------------
// void InitUART(void)
//
// This function initializes the USART0 module for UART mode. It is used to
// setup the communication link with the TUSB3410 controller. Using an ACLK
// of 8MHz, the resulting UART baud rate is 460,800.
//
// IN: -
// OUT: -
//------------------------------------------------------------------------------
void InitUART(void)
{
U0CTL = 0; // Ensure I2C mode is disabled
U0CTL = SWRST; // Hold USART logic in reset
ME1 |= UTXE0 + URXE0; // Enable USART0 TXD/RXD
U0CTL |= CHAR; // 8-bit character
U0TCTL = SSEL0; // UCLK = ACLK
U0BR0 = 17; // 8MHz / 460,800 = 17.xx
U0BR1 = 0;
U0MCTL = 0x52; // Modulation (See User's Guide)
U0CTL &= ~SWRST; // Release USART state machine
}
//------------------------------------------------------------------------------
// void Delay100(void)
//
// This function implements a 100 cycle compiler optimization level
// independent software delay.
//
// IN: -
// OUT: -
//------------------------------------------------------------------------------
void Delay100(void)
{
asm(" mov.w #33,R15 "); // Load loop counter
asm(" dec.w R15 "); // 1 Cycle
asm(" jnz $-2 "); // 2 Cycles
}
//------------------------------------------------------------------------------
// void InitI2C(void)
//
// This function initializes the USART0 module for I2C mode. It is used to
// setup the communication link with the external EEPROM. Using an ACLK of
// 8MHz, the resulting I2C bit rate is 100,000.
//
// IN: -
// OUT: -
//------------------------------------------------------------------------------
void InitI2C(void)
{
U0CTL = SWRST; // USART logic in reset state
U0CTL &= ~I2CEN; // Clear I2CEN bit
U0CTL = I2C + SYNC + MST; // I2C master mode, 7-bit addr
I2CTCTL = I2CTRX + I2CSSEL_1; // Byte mode, repeat mode, ACLK
I2CSA = EEPROM_ADDRESS; // I2C slave address
I2COA = OWN_ADDRESS; // Own address
I2CPSC = 3; // I2C prd = 4 * clock prd
I2CSCLH = 8; // SCL high prd = 10 * I2C prd
I2CSCLL = 8; // SCL low prd = 10 * I2C prd
U0CTL |= I2CEN; // Enable I2C module operation
}
//------------------------------------------------------------------------------
unsigned char EEPROM_CheckNACK(void)
{
while (I2CDCTL & I2CBUSY); // Wait for I2C module
U0CTL &= ~I2CEN;
I2CTCTL |= I2CRM; // Disable repeat mode
U0CTL |= I2CEN;
U0CTL |= MST; // I2C master mode
I2CTCTL |= I2CTRX; // Transmit mode (R/W bit = 0)
I2CIFG &= ~NACKIFG; // Clear interrupt flag
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -