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.

CCS/MSP430F5529: MSP430 Spi clock settings

Part Number: MSP430F5529
Other Parts Discussed in Thread: LMP90100

Tool/software: Code Composer Studio

Dear all,

We are trying to establish a SPI communication between LMP90100 and MSP430f5529. We have an example code from TI but could not make it work. We have gone through the code and did not come across anything related to clock settings in MSP430. We are trying to get a clock signal from P2.7 of MSP430. Any suggestions? 

Kind Regards,

//******************************************************************************
//  Demo Application03 for MSP430/LMP90100 Interface Code Library v1.0
//  Normal Stream Read ADC Data (1 channel) with interrupt
//
//                MSP430F5528
//             -----------------
//         /|\|              XIN|-
//          | |                 |  32kHz
//          --|RST          XOUT|-
//            |                 |
//            |    P3.3/UCA0SIMO|--> SDI
//            |    P3.4/UCA0SOMI|<-- SDO
//            |     P2.7/UCA0CLK|--> CLK
//            |             P2.5|--> CSB
//            |             P2.4|<-- DRDYB
//            |                 |
//
//   Vishy Natarajan
//   Texas Instruments Inc.
//   October 2011
//   Built with CCE Version: 4.2 and IAR Embedded Workbench Version:  5.3x
//******************************************************************************
/*  Copyright 2011-2012 Texas Instruments Incorporated. All rights reserved.

  IMPORTANT: Your use of this Software is limited to those specific rights
  granted under the terms of a software license agreement between the user who
  downloaded the software, his/her employer (which must be your employer) and
  Texas Instruments Incorporated (the "License"). You may not use this Software
  unless you agree to abide by the terms of the License. The License limits your
  use, and you acknowledge, that the Software may not be modified, copied or
  distributed unless embedded on a Texas Instruments microcontroller which is
  integrated into your product. Other than for the foregoing purpose, you may
  not use, reproduce, copy, prepare derivative works of, modify, distribute,
  perform, display or sell this Software and/or its documentation for any
  purpose.

  YOU FURTHER ACKNOWLEDGE AND AGREE THAT THE SOFTWARE AND DOCUMENTATION ARE
  PROVIDED �AS IS� WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED,
  INCLUDING WITHOUT LIMITATION, ANY WARRANTY OF MERCHANTABILITY, TITLE,
  NON-INFRINGEMENT AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL TEXAS
  INSTRUMENTS OR ITS LICENSORS BE LIABLE OR OBLIGATED UNDER CONTRACT,
  NEGLIGENCE, STRICT LIABILITY, CONTRIBUTION, BREACH OF WARRANTY, OR OTHER LEGAL
  EQUITABLE THEORY ANY DIRECT OR INDIRECT DAMAGES OR EXPENSES INCLUDING BUT NOT
  LIMITED TO ANY INCIDENTAL, SPECIAL, INDIRECT, PUNITIVE OR CONSEQUENTIAL
  DAMAGES, LOST PROFITS OR LOST DATA, COST OF PROCUREMENT OF SUBSTITUTE GOODS,
  TECHNOLOGY, SERVICES, OR ANY CLAIMS BY THIRD PARTIES (INCLUDING BUT NOT
  LIMITED TO ANY DEFENSE THEREOF), OR OTHER SIMILAR COSTS.

  Should you have any questions regarding your right to use this Software,
  contact Texas Instruments Incorporated at www.TI.com.
*******************************************************************************/

#include <stdint.h>
#include "TI_LMP90100.h"
#include "TI_LMP90100_register_settings.h"
#include "TI_MSP430.h"
#include "TI_MSP430_hardware_board.h"
#include "TI_MSP430_spi.h"

void TI_LMP90100_WriteRegSettings(uint8_t *);                                  // Configure LMP90100 registers
void process_adc_output(uint32_t *);                                           // dummy adc data process function: toggles LED
volatile uint8_t LMP90100_ADCDataReady = 0;                                    // set to 1 in DRDYB interrupt service routine
#define SAMPLE_ARRAY_SIZE 16                                                   // Store last 16 ADC samples for processing
#define CH_DATA_SIZE 3                                                         // 3 bytes: ADC_DOUT2, ADC_DOUT1, ADC_DOUT0

//******************************************************************************
void main(void)
{

  uint8_t prev_URA;                                                            // Previous Upper Register Address (URA)
  uint8_t count, addr, i;
  uint8_t read_buf[CH_DATA_SIZE];
  uint32_t adc_data, adc_sample_array[SAMPLE_ARRAY_SIZE];


  WDTCTL = WDTPW+WDTHOLD;                                                      // Stop WDT

  TI_LMP90100_LED_PxOUT |= TI_LMP90100_LED_PIN;                                // Set LED ON
  TI_LMP90100_LED_PxDIR |= TI_LMP90100_LED_PIN;                                // Set pin direction is output



  // configure Port Pin to handle Data Ready Bar Output (DRDYB) from LMP90100
  TI_LMP90100_DRDYB_PxDIR &= ~TI_LMP90100_DRDYB_PIN;                           // Set up port pin for DRDYB
  TI_LMP90100_DRDYB_PxIES |= TI_LMP90100_DRDYB_PIN;                            // Interrupt Edge Select
  TI_LMP90100_DRDYB_PxIFG &= ~TI_LMP90100_DRDYB_PIN;                           // Clear Interrupt Flag
  TI_LMP90100_DRDYB_PxIE |= TI_LMP90100_DRDYB_PIN;                             // Enable Port interrupt

  TI_LMP90100_SPISetup();                                                      // Initilaize MSP430 SPI Block
  prev_URA = LMP90100_URA_END;                                                 // Initialize prev_URA to invalid segment


  TI_LMP90100_WriteRegSettings(&prev_URA);                                     // Set up LMP90100 for Channel 0 Scan

  addr = TI_LMP90100_ADC_DOUT2_REG;                                            // Start Reading from ADC_DOUT2 Register
  count = CH_DATA_SIZE;                                                        // bytes to read: ADC_DOUT2 - ADCDOUT0
  i = 0;
  while (1)
  {
    if (LMP90100_ADCDataReady)
    {
      LMP90100_ADCDataReady = 0;                                               // clear flag
      TI_LMP90100_SPINormalStreamReadADC(addr, read_buf, count, &prev_URA);    // read adc output into read_buf

      adc_data = ((uint32_t) read_buf[0] << 16)
                 | ((uint16_t) read_buf[1] << 8) | read_buf[2];                // form raw adc output data
      adc_sample_array[i] = adc_data;
      if (++i == SAMPLE_ARRAY_SIZE)                                            // sample array is full
      {
        process_adc_output(adc_sample_array);                                  // dummy app function: no error toggles led
        i = 0;
      }
    }
    __bis_SR_register(LPM0_bits + GIE);                                        // Enter LPM0, enable interrupts
    __no_operation();                                                          // For debugger
  }
}
//******************************************************************************
//  void TI_LMP90100_WriteRegSettings(uint8_t *)
//
//  DESCRIPTION:
//  LMP90100 registers are configured to the values defined LMP90100_register_settings.h
//  These register settings can easily be obtained from the "Register configuration file"
//  saved from Sensor AFE Software
//
//  ARGUMENTS:
//      pURA indicating the previous register segment that was accessed
//******************************************************************************

void TI_LMP90100_WriteRegSettings(uint8_t *pURA)
{

  TI_LMP90100_SPIWriteReg(TI_LMP90100_RESETCN_REG,
                          TI_LMP90100_RESETCN_REG_VALUE, pURA);                // register and conversion reset
  TI_LMP90100_SPIWriteReg(TI_LMP90100_SPI_HANDSHAKECN_REG,
                          TI_LMP90100_SPI_HANDSHAKECN_REG_VALUE, pURA);        // SDO high z delayed
  TI_LMP90100_SPIWriteReg(TI_LMP90100_SPI_STREAMCN_REG,
                          TI_LMP90100_SPI_STREAMCN_REG_VALUE, pURA);           // normal streaming
  TI_LMP90100_SPIWriteReg(TI_LMP90100_PWRCN_REG,
                          TI_LMP90100_PWRCN_REG_VALUE, pURA);                  // active mode
  TI_LMP90100_SPIWriteReg(TI_LMP90100_ADC_RESTART_REG,
                          TI_LMP90100_ADC_RESTART_REG_VALUE, pURA);            // disable restart conversion
  TI_LMP90100_SPIWriteReg(TI_LMP90100_GPIO_DIRCN_REG,
                          TI_LMP90100_GPIO_DIRCN_REG_VALUE, pURA);             // D6 is an output, D1-D5 are inputs
  TI_LMP90100_SPIWriteReg(TI_LMP90100_GPIO_DAT_REG,
                          TI_LMP90100_GPIO_DAT_REG_VALUE, pURA);               // Set D6 high
  TI_LMP90100_SPIWriteReg(TI_LMP90100_BGCALCN_REG,
                          TI_LMP90100_BGCALCN_REG_VALUE, pURA);                // Background calibration off
  TI_LMP90100_SPIWriteReg(TI_LMP90100_SPI_DRDYBCN_REG,
                          TI_LMP90100_SPI_DRDYBCN_REG_VALUE, pURA);            // enable DRDYB on D6
  TI_LMP90100_SPIWriteReg(TI_LMP90100_ADC_AUXCN_REG,
                          TI_LMP90100_ADC_AUXCN_REG_VALUE, pURA);              // disable external clock detection, internal clock
  TI_LMP90100_SPIWriteReg(TI_LMP90100_SPI_CRC_CN_REG,
                          TI_LMP90100_SPI_CRC_CN_REG_VALUE, pURA);             // Disable CRC
  TI_LMP90100_SPIWriteReg(TI_LMP90100_SENDIAG_THLDH_REG,
                          TI_LMP90100_SENDIAG_THLDH_REG_VALUE, pURA);          // Sensor Diagnostic Threshold High
  TI_LMP90100_SPIWriteReg(TI_LMP90100_SENDIAG_THLDL_REG,
                          TI_LMP90100_SENDIAG_THLDL_REG_VALUE, pURA);          // Sensor Diagnostic Threshold Low
  TI_LMP90100_SPIWriteReg(TI_LMP90100_SCALCN_REG,
                          TI_LMP90100_SCALCN_REG_VALUE, pURA);                 // Normal mode
  TI_LMP90100_SPIWriteReg(TI_LMP90100_ADC_DONE_REG,
                          TI_LMP90100_ADC_DONE_REG_VALUE, pURA);               // ADC Data unavailable
  // Set up scan register for conversion
  while (TI_LMP90100_SPIReadReg((TI_LMP90100_CH_STS_REG
                                 & TI_LMP90100_CH_SCAN_NRDY), pURA));          // wait if CH_SCAN_NRDY
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH_SCAN_REG,
                          TI_LMP90100_CH_SCAN_REG_VALUE, pURA);                // single CH continuous scan, ch# = 0
  // CH0 in use
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH0_INPUTCN_REG,
                          TI_LMP90100_CH0_INPUTCN_REG_VALUE, pURA);            // diable sensor diagnostics, default ref, vinp0 vinn1
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH0_CONFIG_REG,
                          TI_LMP90100_CH0_CONFIG_REG_VALUE, pURA);             // 26.83SPS, FGA off, buffer in signal path
  // CH1 not used
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH1_INPUTCN_REG,
                          TI_LMP90100_CH1_INPUTCN_REG_VALUE, pURA);            // disable sensor diagnostics, default ref, vinp2 vinn3
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH1_CONFIG_REG,
                          TI_LMP90100_CH1_CONFIG_REG_VALUE, pURA);             // 26.83SPS, FGA off, buffer in signal path
  // CH2 not used
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH2_INPUTCN_REG,
                          TI_LMP90100_CH2_INPUTCN_REG_VALUE, pURA);            // disable sensor diagnostics, default ref, vinp4 vinn5
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH2_CONFIG_REG,
                          TI_LMP90100_CH2_CONFIG_REG_VALUE, pURA);             // 214.65SPS, FGA off, buffer in signal path
  // CH3 not used
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH3_INPUTCN_REG,
                          TI_LMP90100_CH3_INPUTCN_REG_VALUE, pURA);            // disable sensor diagnostics, default ref, vinp6 vinn7
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH3_CONFIG_REG,
                          TI_LMP90100_CH3_CONFIG_REG_VALUE, pURA);             // 214.65SPS, FGA off, buffer in signal path
  // CH4 not used
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH4_INPUTCN_REG,
                          TI_LMP90100_CH4_INPUTCN_REG_VALUE, pURA);            // diable sensor diagnostics, default ref, vinp0 vinn1
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH4_CONFIG_REG,
                          TI_LMP90100_CH4_CONFIG_REG_VALUE, pURA);             // 214.65SPS, FGA off, buffer in signal path
  // CH5 not used
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH5_INPUTCN_REG,
                          TI_LMP90100_CH5_INPUTCN_REG_VALUE, pURA);            // disable sensor diagnostics, default ref, vinp2 vinn3
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH5_CONFIG_REG,
                          TI_LMP90100_CH5_CONFIG_REG_VALUE, pURA);             // 214.65SPS, FGA off, buffer in signal path
  // CH6 not used
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH6_INPUTCN_REG,
                          TI_LMP90100_CH6_INPUTCN_REG_VALUE, pURA);            // disable sensor diagnostics, default ref, vinp4 vinn5
  TI_LMP90100_SPIWriteReg(TI_LMP90100_CH6_CONFIG_REG,
                          TI_LMP90100_CH6_CONFIG_REG_VALUE, pURA);	       // 214.65SPS, FGA off, buffer in signal path

}
//******************************************************************************
//  void process_adc_output(uint32_t *)
//
//  DESCRIPTION:
//  Dummy ADC data process function: Toggles LED
//******************************************************************************
void process_adc_output(uint32_t *data)
{
    TI_LMP90100_LED_PxOUT ^= TI_LMP90100_LED_PIN;                               // Toggle LED
}
//******************************************************************************
// TI_LMP90100_SPI_DRDYB_PIN interrupt service routine
#pragma vector=TI_LMP90100_DRDYB_VECTOR
__interrupt void TI_LMP90100_DRDY_PORTx(void)
{
  TI_LMP90100_DRDYB_PxIFG &= ~TI_LMP90100_DRDYB_PIN;                           //  IFG cleared
  LMP90100_ADCDataReady = 1;                                                   // set flag
  __bic_SR_register_on_exit(LPM0_bits);                                        // Exit active CPU
}
//******************************************************************************
TI_LMP90100.hTI_LMP90100_register_settings.hTI_MSP430_spi.h
//******************************************************************************
//  Description:  This file contains functions that allow the MSP430 device to
//  access the SPI interface of the LMP90100.  There are multiple
//  instances of each function; the one to be compiled is selected by the
//  system variable TI_LMP90100_SER_INTF, defined in "TI_LMP90100_hardware_board.h".
//
//  MSP430/LMP90100 Interface Code Library v1.0
// 
//
//   Vishy Natarajan
//   Texas Instruments Inc.
//   October 2011
//   Built with CCE Version: 4.2 and IAR Embedded Workbench Version:  5.3x
//******************************************************************************
// Change Log:
//******************************************************************************
// Version:  1.00
// Comments: Initial Release Version
//******************************************************************************
/*  Copyright 2011-2012 Texas Instruments Incorporated. All rights reserved.

  IMPORTANT: Your use of this Software is limited to those specific rights
  granted under the terms of a software license agreement between the user who
  downloaded the software, his/her employer (which must be your employer) and
  Texas Instruments Incorporated (the "License"). You may not use this Software
  unless you agree to abide by the terms of the License. The License limits your
  use, and you acknowledge, that the Software may not be modified, copied or
  distributed unless embedded on a Texas Instruments microcontroller which is 
  integrated into your product. Other than for the foregoing purpose, you may 
  not use, reproduce, copy, prepare derivative works of, modify, distribute, 
  perform, display or sell this Software and/or its documentation for any 
  purpose.

  YOU FURTHER ACKNOWLEDGE AND AGREE THAT THE SOFTWARE AND DOCUMENTATION ARE
  PROVIDED �AS IS� WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED,
  INCLUDING WITHOUT LIMITATION, ANY WARRANTY OF MERCHANTABILITY, TITLE,
  NON-INFRINGEMENT AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL TEXAS
  INSTRUMENTS OR ITS LICENSORS BE LIABLE OR OBLIGATED UNDER CONTRACT,
  NEGLIGENCE, STRICT LIABILITY, CONTRIBUTION, BREACH OF WARRANTY, OR OTHER LEGAL
  EQUITABLE THEORY ANY DIRECT OR INDIRECT DAMAGES OR EXPENSES INCLUDING BUT NOT
  LIMITED TO ANY INCIDENTAL, SPECIAL, INDIRECT, PUNITIVE OR CONSEQUENTIAL
  DAMAGES, LOST PROFITS OR LOST DATA, COST OF PROCUREMENT OF SUBSTITUTE GOODS,
  TECHNOLOGY, SERVICES, OR ANY CLAIMS BY THIRD PARTIES (INCLUDING BUT NOT
  LIMITED TO ANY DEFENSE THEREOF), OR OTHER SIMILAR COSTS.

  Should you have any questions regarding your right to use this Software,
  contact Texas Instruments Incorporated at www.TI.com.
*******************************************************************************/

#include <stdint.h>
#include "TI_LMP90100.h"
#include "TI_MSP430.h"
#include "TI_MSP430_hardware_board.h"
#include "TI_MSP430_spi.h"


//******************************************************************************
// Support for 552x USCI_B0
//******************************************************************************
#if TI_LMP90100_SER_INTF == TI_LMP90100_SER_INTF_USCIB0_5xx

//------------------------------------------------------------------------------
//  void TI_LMP90100_SPISetup(void)
//
//  DESCRIPTION:
//  Configures the assigned interface to function as a SPI port and
//  initializes it.
//------------------------------------------------------------------------------
void TI_LMP90100_SPISetup(void)
{
  TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;
  TI_LMP90100_CSn_PxDIR |= TI_LMP90100_CSn_PIN;                                // /CS disable

  UCB0CTL1 |= UCSWRST;                                                         // **Disable USCI state machine**
  UCB0CTL0 |= UCMST+UCCKPH+UCMSB+UCSYNC;                                       // 3-pin, 8-bit SPI master 
  UCB0CTL1 |= UCSSEL_2;                                                        // SMCLK
  UCB0BR0 = 0x04;                                                              // UCLK/4
  UCB0BR1 = 0;
  TI_LMP90100_SPI_USCIB0_PxSEL1 |= TI_LMP90100_SPI_USCIB0_SIMO
                                   | TI_LMP90100_SPI_USCIB0_SOMI;              
  TI_LMP90100_SPI_USCIB0_PxSEL2 |= TI_LMP90100_SPI_USCIB0_UCLK;
                                                                               // SPI option select
  TI_LMP90100_SPI_USCIB0_PxDIR1 |= TI_LMP90100_SPI_USCIB0_SIMO;
  TI_LMP90100_SPI_USCIB0_PxDIR2 |= TI_LMP90100_SPI_USCIB0_UCLK;
                                                                               // SPI TXD out direction
  
  UCB0CTL1 &= ~UCSWRST;                                                        // **Initialize USCI state machine**
}

//------------------------------------------------------------------------------
//  void TI_LMP90100_SPIWriteReg(uint8_t addr, uint8_t value, uint8_t *pURA)
//
//  DESCRIPTION:
//  Writes "value" to a single configuration register at address "addr". If 
//  "addr" lies within the same segment as "*pURA", it takes 1 less transaction 
//  to write the value.
//------------------------------------------------------------------------------
void TI_LMP90100_SPIWriteReg(uint8_t addr, uint8_t value, uint8_t *pURA)
{
  uint8_t new_URA, inst;
  
  new_URA = (addr & LMP90100_URA_MASK)>>4;                                     // extract upper register address

  TI_LMP90100_CSn_PxOUT &= ~TI_LMP90100_CSn_PIN;                               // /CS enable 
  
  if (*pURA != new_URA)                                                        // if new and previous URA not same, add transaction 1
  {    
    inst = LMP90100_INSTRUCTION_BYTE1_WRITE;                                   // Transaction-1
    
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = inst;                                                          // Send instruction
  
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = new_URA;                                                       // Send upper register address 
    
    *pURA = new_URA;                                                           // save new URA
    
  }
  
  inst = LMP90100_WRITE_BIT | LMP90100_SIZE_1B |(addr & LMP90100_LRA_MASK);    // lower register address
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready
  UCB0TXBUF = inst;                                                            // Send lower register address
  
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready
  UCB0TXBUF = value;                                                           // Send data value  
  
  while (UCB0STAT & UCBUSY);                                                   // Wait for TX complete
  TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;                                // /CS disable
  
}

//------------------------------------------------------------------------------
//  uint8_t TI_LMP90100_SPIReadReg(uint8_t addr, unit8_t *pURA)
//
//  DESCRIPTION:
//  Reads a single configuration register at address "addr" and returns the
//  value read. If "addr" lies within the same segment as "*pURA", it takes 1 
//  less transaction to read the value.
//------------------------------------------------------------------------------
uint8_t TI_LMP90100_SPIReadReg(uint8_t addr, uint8_t *pURA)
{
  uint8_t x, new_URA, inst;

  new_URA = (addr & LMP90100_URA_MASK)>>4;                                     // extract upper register address
  
  TI_LMP90100_CSn_PxOUT &= ~TI_LMP90100_CSn_PIN;                               // /CS enable
  
  if (*pURA != new_URA)                                                        // if new and previous URA not same, add transaction 1
  {
    inst = LMP90100_INSTRUCTION_BYTE1_WRITE;                                   // Transaction-1
    
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = inst;                                                          // Send instruction
  
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = new_URA;                                                       // Send upper register address 
    
    *pURA = new_URA;                                                           // save new URA
    
 }
 
  inst = LMP90100_READ_BIT | LMP90100_SIZE_1B | (addr & LMP90100_LRA_MASK);    // Transaction-2
  
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready
  UCB0TXBUF = inst;                                                            // Send lower register address  
  
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready
  UCB0TXBUF = 0;                                                               // Dummy write so we can read data
  
  while (UCB0STAT & UCBUSY);                                                   // Wait for TX complete  
  x = UCB0RXBUF;                                                               // Read data
  
  TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;                                // /CS disable

  return x;
}

//------------------------------------------------------------------------------
//  void TI_LMP90100_SPINormalStreamWriteReg(uint8_t addr, uint8_t *buffer, uint8_t count, uint8_t *pURA)
//
//  DESCRIPTION:
//  Writes values to multiple configuration registers, the first register being
//  at address "addr".  First data byte is at "buffer", and both addr and
//  buffer are incremented sequentially (within the LMP90100 and MSP430,
//  respectively) until "count" writes have been performed. If "addr" lies within
//  the same segment as "*pURA", it takes 1 less transaction to write the value.
//------------------------------------------------------------------------------
void TI_LMP90100_SPINormalStreamWriteReg(uint8_t addr, uint8_t *buffer, 
                                         uint8_t count, uint8_t *pURA)
{
  uint8_t new_URA, inst, i;
  
  new_URA = (addr & LMP90100_URA_MASK)>>4;                                     // extract upper register address

  TI_LMP90100_CSn_PxOUT &= ~TI_LMP90100_CSn_PIN;                               // /CS enable
  
  if (*pURA != new_URA)                                                        // if new and previous URA not same, add transaction 1
  {    
    inst = LMP90100_INSTRUCTION_BYTE1_WRITE;                                   // Transaction-1
    
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = inst;                                                          // Send instruction
  
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = new_URA;                                                       // Send upper register address 
    
    *pURA = new_URA;                                                           // save new URA
    
  }
  
  inst = LMP90100_WRITE_BIT | LMP90100_SIZE_STREAM 
                            | (addr & LMP90100_LRA_MASK);                      // lower register address
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready
  UCB0TXBUF = inst;                                                            // Send lower register address
  
  for(i= 0; i < count; i++)
  {
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = *(buffer+i);                                                   // Send data value  
  }
  
   while (UCB0STAT & UCBUSY);                                                  // Wait for TX complete
   TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;                               // /CS disable
  
}

//------------------------------------------------------------------------------
//  void TI_LMP90100_SPIReadNormalStreamReg(uint8_t addr, unit8_t *buffer, uint8_t count, uint8_t *pURA)
//
//  DESCRIPTION:
//  Reads multiple configuration registers, the first register being at address
//  "addr".  Values read are deposited sequentially starting at address
//  "buffer", until "count" registers have been read. If "addr" lies within
//  the same segment as "*pURA", it takes 1 less transaction to read the value.
//------------------------------------------------------------------------------
void TI_LMP90100_SPINormalStreamReadReg(uint8_t addr, uint8_t *buffer, 
                                        uint8_t count, uint8_t *pURA)
{
  uint8_t i, new_URA, inst;

  new_URA = (addr & LMP90100_URA_MASK)>>4;                                     // extract upper register address
  
  TI_LMP90100_CSn_PxOUT &= ~TI_LMP90100_CSn_PIN;                               // /CS enable
  
  if (*pURA != new_URA)                                                        // if new and previous URA not same, add transaction 1
  {    
    inst = LMP90100_INSTRUCTION_BYTE1_WRITE;                                   // Transaction-1
    
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = inst;                                                          // Send instruction
  
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = new_URA;                                                       // Send upper register address 
    
    *pURA = new_URA;                                                           // save new URA
    
  }
 
  inst = LMP90100_READ_BIT | LMP90100_SIZE_STREAM 
                           | (addr & LMP90100_LRA_MASK);                       // Transaction-2
  
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready
  UCB0TXBUF = inst;                                                            // Send lower register address  
  
  for(i=0; i < count; i++)
  {
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = 0;                                                             // Dummy write so we can read data
  
    while (UCB0STAT & UCBUSY);                                                 // Wait for TX complete  
    *(buffer+i) = UCB0RXBUF;                                                   // Read data
  }
  TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;                                // /CS disable

}
//------------------------------------------------------------------------------
//  void TI_LMP90100_SPICRCCheck(uint8_t *buffer, uint8_t count)
//
//  DESCRIPTION: Checks if CRC read from the device matches computed result. 
//  CRC is computed for "count" bytes at address "buffer" and compared against CRC 
//  stored in "buffer[count]" and returns "CRC_PASS" or "CRC_FAIL" accordingly.
//
//------------------------------------------------------------------------------
uint8_t TI_LMP90100_SPICRCCheck (uint8_t *buffer, uint8_t count)
{
  uint8_t crc_data, crc_calc;
  
  crc_data = buffer[count];                                                    // extract CRC data
  crc_calc = TI_LMP90100_crc8MakeBitwise2(CRC8_INIT_REM, CRC8_POLY, 
                                           buffer, count);                     // calculate CRC for the adc output (size 3 bytes)  
  if (crc_data == crc_calc)
    return CRC_PASS;
  else
    return CRC_FAIL;
}

//------------------------------------------------------------------------------
//  void TI_LMP90100_SPINormalStreamReadADC(uint8_t addr, uint8_t *buffer, uint8_t count, uint8_t *pURA)
//
//  DESCRIPTION:
//  Special read function for reading ADC data registers. Reads multiple registers, 
//  the first register being at address"addr".  Values read are deposited sequentially 
//  starting at address "buffer", until "count" registers have been read. If "addr" lies 
//  within the same segment as "*pURA", it takes 1 less transaction to read the value.
//------------------------------------------------------------------------------
void TI_LMP90100_SPINormalStreamReadADC(uint8_t addr, uint8_t *buffer, 
                                        uint8_t count, uint8_t *pURA)
{
  uint8_t i, new_URA, inst;
  
  new_URA = (addr & LMP90100_URA_MASK)>>4;                                     // extract upper register address
  
  TI_LMP90100_CSn_PxOUT &= ~TI_LMP90100_CSn_PIN;                               // /CS enable
  
  if (*pURA != new_URA)                                                        // if new and previous URA not same, add transaction 1
  {    
    inst = LMP90100_INSTRUCTION_BYTE1_WRITE;                                   // Transaction-1
    
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = inst;                                                          // Send instruction
  
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = new_URA;                                                       // Send upper register address 
    
    *pURA = new_URA;                                                           // save new URA
    
  }
 
  inst = LMP90100_READ_BIT | LMP90100_SIZE_STREAM 
         | (addr & LMP90100_LRA_MASK);                                         // Transaction-2
  
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready
  UCB0TXBUF = inst;                                                            // Send lower register address  

  for(i=0; i<count; i++)
  {
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = 0;                                                             // Dummy write so we can read data
  
    while (UCB0STAT & UCBUSY);                                                 // Wait for TX complete  
    *(buffer+i) = UCB0RXBUF;                                                   // Read register data    
  }
    
  TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;                                // /CS disable
  
    
}
//------------------------------------------------------------------------------
//  void TI_LMP90100_SPIControlledStreamReadADC(uint8_t addr, uint8_t *buffer, uint8_t count, uint8_t *pURA)
//
//  DESCRIPTION:
//  Special read function for reading ADC data registers in Controlled Stream Mode.  
//  Reads multiple registers, the first register being at address"addr".  Values read  
//  are deposited sequentiallystarting at address "buffer", until "count" registers 
//  have been read. If "addr" lies within the same segment as "*pURA", it takes 1 less 
//  transaction to read the value.
//------------------------------------------------------------------------------
void TI_LMP90100_SPIControlledStreamReadADC(uint8_t addr, uint8_t *buffer, 
                                            uint8_t count, uint8_t *pURA)
{
  uint8_t i, new_URA, inst;
  static uint8_t repeat_controlled = 0;                                        // if set, LRA transaction is skipped
  

  new_URA = (addr & LMP90100_URA_MASK)>>4;                                     // extract upper register address

//  CS Enable/Disable done outside so it is for entire controlled stream transaction  
//  TI_LMP90100_CSn_PxOUT &= ~TI_LMP90100_CSn_PIN;                               // /CS enable 
  
  if (*pURA != new_URA)                                                        // if new and previous URA not same, add transaction 1
  {    
    inst = LMP90100_INSTRUCTION_BYTE1_WRITE;                                   // Transaction-1
    
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = inst;                                                          // Send instruction
  
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = new_URA;                                                       // Send upper register address 
    
    *pURA = new_URA;                                                           // save new URA
    if (repeat_controlled)
      repeat_controlled = 0;
  }
  if (!repeat_controlled)
  { 
    inst = LMP90100_READ_BIT | LMP90100_SIZE_STREAM 
         | (addr & LMP90100_LRA_MASK);                                         // Transaction-2
  
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = inst;                                                          // Send lower register address
    repeat_controlled = 1;
  }
  for(i=0; i<count; i++)
  {
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF = 0;                                                             // Dummy write so we can read data
  
    while (UCB0STAT & UCBUSY);                                                 // Wait for TX complete  
    *(buffer+i) = UCB0RXBUF;                                                   // Read register data    
  }
    
//  TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;                                // /CS disable
  
    
}
//------------------------------------------------------------------------------
//  void TI_LMP90100_SPIDataOnlyReadADC(uint8_t addr, uint8_t *buffer, uint8_t count, uint8_t *pURA)
//
//  DESCRIPTION:
//  Special read function for reading ADC data registers in Data only read mode. Values read 
//  deposited sequentialy starting at address "buffer", until "count" registers have been read. 
//  In order to use the data only read transaction capability of the LMP90100, the data first 
//  mode must be enabled by calling TI_LMP90100_SPIEnableDataFirstMode() function.
//------------------------------------------------------------------------------
void TI_LMP90100_SPIDataOnlyReadADC(uint8_t *buffer, uint8_t count)
{
  uint8_t i;
  
  TI_LMP90100_CSn_PxOUT &= ~TI_LMP90100_CSn_PIN;                               // /CS enable

  for(i=0; i<count; i++)
  {
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF =0;                                                              // Dummy write so we can read data     
    while (UCB0STAT & UCBUSY);                                                 // Wait for TX complete  
    *(buffer+i) = UCB0RXBUF;                                                   // Read register data    
  }
  
  TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;                                // /CS disable
      
}
//------------------------------------------------------------------------------
//  void TI_LMP90100_crc8MakeBitwise2(uint8_t crc, uint8_t poly, uint8_t *pmsg, uint8_t msg_size)
//
//  DESCRIPTION: Compute 8bit CRC of data "*pmsg" of size "msg_size" bytes using polynomial "poly" and init value "crc"
//    
//  
//------------------------------------------------------------------------------
uint8_t TI_LMP90100_crc8MakeBitwise2(uint8_t crc, uint8_t poly, uint8_t *pmsg, uint8_t msg_size)
{
  uint8_t i, j;
  uint8_t msg;
    
  for(i = 0 ; i < msg_size ; i ++)
  {
    msg = (*pmsg++ << 0);
    for(j = 0 ; j < 8 ; j++)
    {
      if((msg ^ crc) >> 7) 
        crc = (crc << 1) ^ poly; 
      else crc <<= 1;	
        msg <<= 1;
    }
  } 
  
  return(crc ^ CRC8_FINAL_XOR);
  
}
//------------------------------------------------------------------------------
//  void TI_LMP90100_SPIEnableDataFirstMode(uint8_t addr, uint8_t count, uint8_t *pURA)
//
//  DESCRIPTION:
//  Enables the data first mode of LMP90100. DATA_ONLY_1 and DATA_ONLY_2 registers are initialized 
//  to "addr" and "count-1" and the LMP90100 is placed in the data first mode. In order to use the 
//  data only read transaction capability of the LMP90100, the data first mode must be enabled.
//
//------------------------------------------------------------------------------
void TI_LMP90100_SPIEnableDataFirstMode(uint8_t addr, uint8_t count, uint8_t *pURA)
{
  TI_LMP90100_SPIWriteReg(TI_LMP90100_DATA_ONLY_1_REG, addr, pURA);            // Load DATA_ONLY_1 register with address
  TI_LMP90100_SPIWriteReg(TI_LMP90100_DATA_ONLY_2_REG, count-1, pURA);         // Load DATA_ONLY_2 register with count-1 
  
  TI_LMP90100_CSn_PxOUT &= ~TI_LMP90100_CSn_PIN;                               // /CS enable         

  
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready
  UCB0TXBUF = LMP90100_DATA_FIRST_MODE_INSTRUCTION_ENABLE;                     // write Data First mode instruction
  
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready  
  UCB0TXBUF = LMP90100_DATA_FIRST_MODE_INSTRUCTION_READ_MODE_STATUS;           // Write read mode status instruction
  while (UCB0STAT & UCBUSY);                                                   // Wait for TX complete
  while (!(UCB0RXBUF & LMP90100_DATA_FIRST_MODE_STATUS_FLAG))                  // wait for device to enter data first mode
  {
    UCB0TXBUF = LMP90100_DATA_FIRST_MODE_INSTRUCTION_READ_MODE_STATUS;         // Write device read mode status instruction
    while (UCB0STAT & UCBUSY);                                                 // Wait for TX complete
  }
  
  TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;                                // /CS disable  
}
//------------------------------------------------------------------------------
//  void TI_LMP90100_SPIDisableDataFirstMode(uint8_t *buffer, uint8_t count)
//
//  DESCRIPTION:
//  Disables the data first mode of LMP90100. Reads data bytes of the data only transaction 
//  and then disables the data first mode of LMP90100. The data only transaction bytes are 
//  deposited sequentially starting at address "buffer", until "count" registers have been read.
//   
//------------------------------------------------------------------------------
void TI_LMP90100_SPIDisableDataFirstMode(uint8_t *buffer, uint8_t count)
{
  uint8_t i;
  
  TI_LMP90100_CSn_PxOUT &= ~TI_LMP90100_CSn_PIN;                               // /CS enable
  
  // Method to disable data first mode: First read the data & then disable
  for(i=0; i<count; i++)
  {
    while (!(UCB0IFG&UCTXIFG));                                                // Wait for TXBUF ready
    UCB0TXBUF =0;                                                              // Dummy write so we can read data     
    while (UCB0STAT & UCBUSY);                                                 // Wait for TX complete  
    *(buffer+i) = UCB0TXBUF;                                                   // Read register data    
  }
  
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready
  UCB0TXBUF = LMP90100_DATA_FIRST_MODE_INSTRUCTION_DISABLE;                    // Disable Data First Mode
  while (!(UCB0IFG&UCTXIFG));                                                  // Wait for TXBUF ready    
  UCB0TXBUF = LMP90100_DATA_FIRST_MODE_INSTRUCTION_READ_MODE_STATUS;           // Write device read mode status instruction
  while (UCB0STAT & UCBUSY);                                                   // Wait for TX complete
  while (UCB0RXBUF & LMP90100_DATA_FIRST_MODE_STATUS_FLAG)                     // wait for device to exit data first mode
  {
    UCB0TXBUF = LMP90100_DATA_FIRST_MODE_INSTRUCTION_READ_MODE_STATUS;         // Write device read mode status instruction
    while (UCB0STAT & UCBUSY);                                                 // Wait for TX complete
  }
  
  TI_LMP90100_CSn_PxOUT |= TI_LMP90100_CSn_PIN;                                // /CS disable  
}
//------------------------------------------------------------------------------
#endif

  • Are you using the UCA0 or UCB0 peripheral? P2.7 is the UCA0CLK but your code uses UCB0 which means that you should be monitoring P3.2 instead. It would also be beneficial to have your TI_MSP430_hardware_board.h file, hopefully it initializes the P3.0-P3.2 pins since your code uses UCB0.

    Regards,
    Ryan

**Attention** This is a public forum