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.

INTERFACING MSP430 with ADXL345

Other Parts Discussed in Thread: MSP430F5438A, MSP430F5438

Hi,

I need to interface ADXL345 with MSP430F5438A for my final year project. I have used 4 wire SPI mode of interfacing. I have attached the my initial code which reads the Device Id of ADXL345. I have used USCI_A3 module for spi. The problem is i don't get any response from the msp430. When i checked the UCA3CLK pin10.0 with the CRO there is no clock coming out of it. I have attached my code . Pls check whether my code is correct and whether it needs any modification for proper working.

Thanks in advance :-)

---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

CCS5 - code

#include <stdio.h>
#include "msp430f5438.h"

// FUNCTION PROTOTYPES

    void CONFIGURE_SPI(void);
    void ENABLE_SPI(void);
    void DISABLE_SPI(void);
    void INITIALIZE_TIMER(void);
    void ENABLE_INTERRUPT(void);
    void DISABLE_INTERRUPT(void);
    void GET_DEVICE_ID(void);
    

// VARIABLE DECLARATION

int Data_received[1000][6];
int m,n,temp,i;
unsigned char DEVID;
//static int i=0;
int sign, value;
int x_data[100],y_data[100],z_data[100];

// SPI CONFIGURATION
// Using A3 module for SPI 4 wire Communication (port 10)
// pin10.0 = UCA3CLK
// pin10.4 = MOSI
// pin10.5 = MISO
// pin10.1 ------ BIT1 CHIP SELECT

void CONFIGURE_SPI()
{
    DISABLE_SPI();

    // Configuring the IO pins for SPI
    P10SEL = (BIT0 | BIT4 | BIT5);             // Enabling the peripheral module function of those pins
    P10DIR = BIT1;                     // Defining the direction of the bit0,3 and 4 as o/p ..
    P10DS = BIT1 ;                     // Making the Full output drive strength for those bits

    // Configuring the control registers for SPI
    UCA3CTL0 = (UCCKPH | UCCKPL | UCMSB | UCMST | UCMODE1 | UCSYNC ); // Configure the control register of SPI
    UCA3CTL1 |= UCSSEL1;                           // Configure the control register of SPI
    UCA3MCTL = 0x00;                           // No modulation control is performed

    //Bit rate
    UCA3BR0 = 02;
    UCA3BR1 = 00;
}

void ENABLE_SPI()
{
    UCA3CTL1 &= ~UCSWRST;
}

void DISABLE_SPI()
{
    UCA3CTL1 |= UCSWRST;
}

void DISABLE_INTERRUPT()  // Disable the Chip select pin of ADXL
{
    P10OUT |= BIT1 ;
}

void ENABLE_INTERRUPT()   // Enable the chip select pin of ADXL345
{
    P10OUT &= ~BIT1;
    
    // Delay to stabilise the ADXL
    TA0CCR0 = 0x6FFF;         // Set the value in TA0CCR0 to start the timer

    while(!(TA0CTL & TAIFG));     //TAIFG flag is set when the timer Counts to TA0CCR0
    TA0CTL &= ~TAIFG;         //Clear the TAIFG flag

    TA0CCR0 = 0x0000;         //Stop the timer
}

void INITIALIZE_TIMER()
{

    TA0CTL = TACLR ;
    TA0CTL = (TASSEL_2 | ID_3 | MC_1);

    /* TASSEL_2 = Timer A clock source select: 2 - SMCLK
    ID_3 = Timer A Input Divider 3 "/8"
    MC_1 = Timer A mode control - Up counter */

    TA0EX0 = TAIDEX_1;         // Further Dividing by 2 ;

}

void GET_DEVICE_ID()
{

    ENABLE_INTERRUPT();

    while(!(UCA3IFG & UCTXIFG));           //Check if the TXBUF is empty
    UCA3TXBUF = 0x80;     
    while(!(UCA3IFG & UCTXIFG));
    UCA3TXBUF = 0x00;                               // Sending dummy variable to enable the reception
    while(UCA3STAT & UCBUSY);

    DEVID = UCA3RXBUF;

    DISABLE_INTERRUPT();

}

// MAIN CLASS
int main()
{

    WDTCTL = WDTPW + WDTHOLD;     // STOP THE WATCHDOG TIMER
    P1DIR |= 0x01;               // Set P1.0 to output direction
    P7DIR |= BIT7;          // Power Supply to ADXL
    P7DS |= BIT7;
    P7OUT |= BIT7;



    DISABLE_INTERRUPT();
    CONFIGURE_SPI();

    INITIALIZE_TIMER();
    ENABLE_SPI();
    GET_DEVICE_ID();

    P1OUT = 0x00;

    if(DEVID == 0xE5)
    {
        P1OUT = 0x01;   // LED is ON when the DEVID matches 0xE5(Device Id of ADXL345)
    }

    return 0;

}


  • I removed the UCCKPH in the UCA3CTL0 as per the information given in ADXL345 data sheet (that is UCCKPL = 1 and UCCKPH = 0). Changed the values in UCA3BR0 and UCA3BR1 to 9 and 61 respectively. Defined the direction of the USCI_A3 module pin in port 10. Now i'm able to transmit the data but i couldn't receive any data. RXBUF always shows 0x00 as its value. Can someone please help me to sort out this problem. Thanks :-)
  • shriram nagarajan said:
    P10DIR = BIT1;                     // Defining the direction of the bit0,3 and 4 as o/p ..
        P10DS = BIT1 ;                     // Making the Full output drive strength for those bits

    the first comment does nto match what the code does. It only switches P10.1 to output. THe direction of P10.0,3 and 4 are controlled by the USCI anyway.
    It is, however, not necessary to set full drive strength for your CS pin. You're driving a control input, not a power LED. :)

    The names for ENABLE_INTERRUPT and DISABLE_INTERRUPT are highly misleading. No interupt (on the MSP side) is enabled/disabled here. You seem to set and clear the ADXL chip select signal, which is something completely different: it starts and ends a communication frame between the two SPI peers.
    Also, CCR0=0 does not stop the timer: it increases timer overflow frequency to TACLK/2. To stop the timer, you must clear the MCx bits in TACTL. Also, the timer immediately starts when you set MC_1. So setting TACCR= to 0x6fff does not start the timer, it just changes the behavior of the already running timer. It won't make much of a difference in your code, but if you later extend it...

    You don't require and shouldn't use 4-wire mode. 4-wire mode is used if the MSP is slave or if there is mroe than one SPI master ont the bus. The CS signal doe snot count as SPI wire,a stehre can be any number of CS signals (remember, SPI is a bus, there can be gazillions of slaves, each with its own CS signal)
    The use of 4-wire mode will put the USCI in sleep depending on the STE signal.
    Maybe that's the main problem.

  • shriram nagarajan said:
    I removed the UCCKPH in the UCA3CTL0 as per the information given in ADXL345 data sheet (that is UCCKPL = 1 and UCCKPH = 0).

    YOu should check the timing diagram. TIs definition of phase and polarity differs from the Motorola definition.
    It's possible that your receive problems come from a wrong polarity too. (IIRC, it is the polarity that's differently defined).

    Changing UCA3BR to 0x6109 gives a very, very, very low SPI baudrate, 644Bd on 16Mhz SMCLK (even 0x961 is quite slow, ~6kBd on 16Mhz clock). I don't think that's exactly what you want. And the direction of the SPI port pins, once seleced, is controlled by the USCI. No need to manually set it.

    However, a wrong polarity should not result in a 0x00 response, only in a garbled one (well, 0x00 is a possible effect, but anything else would be more likely, dependent on the data that is really sent).
    Did you check the line for a shortcut to GND?

  • Hello Jens,

    I made the following changes in msp 430. Now i'm receiving random values.

    1. I have defined the spi in 3 wire mode.

    2. Accelerometer follows clock polarity = 1 (cpol = 1) and clock phase = 1 (cpha = 1). TI definition of phase and polarity is CKPL = CPOL and CKPH = (complement(CPHA)). so i have included only CKPL in the UCA3CTL0.

    3. Now i am using ACLK to define the bit rate. ACLK = 32 KHz. The maximum baud rate that can be achieved in the ADXL 345 is 3200. so i have defined the value of UCA3BR0 = 40; UCA3BR1 = 0; so that i will have the BRCLK =  3200 .

    4. Regarding interrupt thing, i have renamed those functions as ENABLE_ADXL() and DISBLE_ADXL().

    Now the clock, chip select and input to the ADXL are proper. But I am not getting any proper waveform for the output from ADXL

    Ground connections are proper.

  • sorry i have set UCA3BR0 = 10 for the rate to be 3200.

  • Is it working Now? Could you post working code? I've trouble to setup I2C communication ADXL345 doesn't answer to my request...
    Thanks
  • I²C is something different. Create a new thread (and use the "insert code" function to properly format your code, and explain why you think your code and your hardware are correct).

**Attention** This is a public forum