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.

MSP430G2553 and ADXL345 SPI

Other Parts Discussed in Thread: MSP430G2553, ENERGIA

Hi there, 

I've had my launch pad for about a week now and I've been able to flash lights and all those sorts of things. Now I am trying to use the SPI perpherial to interface the MSP430G2553 chip with an Analog Devices ADXL345 accelerometer. 

I have been through the sample code provided in the wiki plus many other versions I have found and have just about got my head around how to set some functions up to work. I have also tried the Energia software and SPI examples included. This helped a lot and I finially managed to get some sort of data flowing. But I'm pretty sure it was all nonsense and the Energia environment is too basic to help debug so I've been trying to put together the semi working code from the Energia example and some other examples in a Code Composer Studio Project. 

I seam to be able to transmit some information as I can see it on the oscilloscope (whether or not it is correct I'm not sure) but the code gets stuck in a while loop after transmission when it is waiting for a response and I don't know why as it seamed to work when it was within the Energia example. All I am trying to do at the moment is get the device ID so I know the correct information is being sent and received. 

Could anyone offer some advise on this? I don't really know what to try next.

I've attached my main.c file for viewing.

//Include Files
#include "msp430g2553.h"
#include <stdint.h>


//ADXL345 Register Addresses
#define	DEVID		0x00	//Device ID Register
#define THRESH_TAP	0x1D	//Tap Threshold
#define	OFSX		0x1E	//X-axis offset
#define	OFSY		0x1F	//Y-axis offset
#define	OFSZ		0x20	//Z-axis offset
#define	DURATION	0x21	//Tap Duration
#define	LATENT		0x22	//Tap latency
#define	WINDOW		0x23	//Tap window
#define	THRESH_ACT	0x24	//Activity Threshold
#define	THRESH_INACT	0x25	//Inactivity Threshold
#define	TIME_INACT	0x26	//Inactivity Time
#define	ACT_INACT_CTL	0x27	//Axis enable control for activity and inactivity detection
#define	THRESH_FF	0x28	//free-fall threshold
#define	TIME_FF		0x29	//Free-Fall Time
#define	TAP_AXES	0x2A	//Axis control for tap/double tap
#define ACT_TAP_STATUS	0x2B	//Source of tap/double tap
#define	BW_RATE		0x2C	//Data rate and power mode control
#define POWER_CTL	0x2D	//Power Control Register
#define	INT_ENABLE	0x2E	//Interrupt Enable Control
#define	INT_MAP		0x2F	//Interrupt Mapping Control
#define	INT_SOURCE	0x30	//Source of interrupts
#define	DATA_FORMAT	0x31	//Data format control
#define DATAX0		0x32	//X-Axis Data 0
#define DATAX1		0x33	//X-Axis Data 1
#define DATAY0		0x34	//Y-Axis Data 0
#define DATAY1		0x35	//Y-Axis Data 1
#define DATAZ0		0x36	//Z-Axis Data 0
#define DATAZ1		0x37	//Z-Axis Data 1
#define	FIFO_CTL	0x38	//FIFO control
#define	FIFO_STATUS	0x39	//FIFO status

//Other definitions
#define SPI_MODE_0 (UCCKPH)			    /* CPOL=0 CPHA=0 */
#define SPI_MODE_1 (0)                 	/* CPOL=0 CPHA=1 */
#define SPI_MODE_2 (UCCKPL | UCCKPH)    /* CPOL=1 CPHA=0 */
#define SPI_MODE_3 (UCCKPL)			    /* CPOL=1 CPHA=1 */
#define SPI_MODE_MASK (UCCKPL | UCCKPH)

#define DELAY_1000NS __delay_cycles(200);�������� // required delay is minimum 250ns

//*************Extra functions*******************



/**
 * spi_initialize() - Configure USCI UCB0 for SPI mode
 *
 * P2.0 - CS (active low)
 * P1.5 - SCLK
 * P1.6 - MISO aka SOMI
 * P1.7 - MOSI aka SIMO
 *
 */

void spi_initialize(void)
{
	UCB0CTL1 = UCSWRST | UCSSEL_2;      // Put USCI in reset mode, source USCI clock from SMCLK
	UCB0CTL0 = SPI_MODE_0 | UCMSB | UCSYNC | UCMST;  // Use SPI MODE 0 - CPOL=0 CPHA=0

	P1OUT  |= (BIT5 | BIT7);            // SPI output pins low
	P1SEL  |= BIT5 | BIT6 | BIT7;	    // configure P1.5, P1.6, P1.7 for USCI
	P1SEL2 |= BIT5 | BIT6 | BIT7;       // more required SPI configuration

	UCB0BR0 = 4 & 0xFF;   // set initial speed to 4MHz
	UCB0BR1 = (4 >> 8 ) & 0xFF;

	UCB0CTL1 &= ~UCSWRST;			    // release USCI for operation

	P2DIR |= BIT0;							//P2.0 set as output
	P2OUT |= BIT0;							//P2.0 set high
}

/***SPI_MODE_0
 * spi_set_divisor() - set new clock divider for USCI
 *
 * USCI speed is based on the SMCLK divided by BR0 and BR1
 *
 */

void spi_set_divisor(const uint16_t clkdiv)
{
	UCB0CTL1 |= UCSWRST;				// go into reset state
	UCB0BR0 = clkdiv & 0xFF;
	UCB0BR1 = (clkdiv >> 8 ) & 0xFF;
	UCB0CTL1 &= ~UCSWRST;				// release for operation
}



/**
 * spi_set_datamode() - mode 0 - 3
 */
void spi_set_datamode(const uint8_t mode)
{
    UCB0CTL1 |= UCSWRST;        // go into reset state
    switch(mode) {
    case 0: /* SPI_MODE0 */
        UCB0CTL0 = (UCB0CTL0 & ~SPI_MODE_MASK) | SPI_MODE_0;
        break;
    case 1: /* SPI_MODE1 */
        UCB0CTL0 = (UCB0CTL0 & ~SPI_MODE_MASK) | SPI_MODE_1;
        break;
    case 2: /* SPI_MODE2 */
        UCB0CTL0 = (UCB0CTL0 & ~SPI_MODE_MASK) | SPI_MODE_2;
        break;
    case 3: /* SPI_MODE3 */
        UCB0CTL0 = (UCB0CTL0 & ~SPI_MODE_MASK) | SPI_MODE_3;
        break;
    default:
        break;
    }
    UCB0CTL1 &= ~UCSWRST;       // release for operation
}


/**
 * spi_send() - send a byte and receive response
 */
uint8_t spi_send(const uint8_t _data)
{
	while (!(UC0IFG & UCB0TXIFG)); 		// wait for previous tx to complete
	UCB0TXBUF = _data; 					// setting TXBUF clears the TXIFG flag
	while (!(UC0IFG & UCB0RXIFG)); 		// wait for an rx character?
	return UCB0RXBUF; 					// reading clears RXIFG flag
}

//************Write data to SPI bus************
void spiWrite(char addr, char data)
{
	P2OUT ^= BIT0;							//Toggle P2.0 -> Set low to initiate transfer
	spi_send(addr);
	spi_send(data);
	P2OUT |= BIT0;							//P2.0 set high again to stop transfer
}

//***********Read data from address************
char spiRead(char reg_addr)
{
	char value;
	P2OUT ^= BIT0;
	value = spi_send(reg_addr);
	P2OUT |= BIT0;
	return(value);							//Return the value from the register accessed
}



//**************Main function********************

void main(void)
{
	WDTCTL = WDTPW + WDTHOLD;				// Stop watchdog timer
	spi_initialize();
	spi_set_datamode(3);

	char dataRead;

	dataRead = spiRead(DEVID);

	__delay_cycles(1000);

	if (dataRead == DEVID){
		P1OUT |= BIT0;
	}

	__delay_cycles(10000);



}

Thanks, 

Alex

**Attention** This is a public forum