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.

Compiler/ADS8332EVM: SPI Initialisation and Data Reading

Part Number: ADS8332EVM

Tool/software: TI C/C++ Compiler

Hi,

I'm wondering if I can get some input on my code for the ADS8332.

The first thing I'm learning to do is turning on the ADS8332, and initialising it's registers. 

Does this look okay for writing to the CFR (bits 15:12 are 1110), and setting the CFR? I'm curious if there is anything I should do before this to wake it up after being un-powered.

void ADS_On(void) {

PORTA.OUTCLR = PIN0_bm;           // Bring CS low
mspi_xchange(0b11101101);             // Write to CFR, set CFR's auto-trigger mode
mspi_xchange(0b01111101);             // Set channel select mode, no tag bits
PORTA.OUTSET = PIN0_bm;           // Bring CS high

}

The next thing I'm wondering about is reading a value. First I've made a function to select the channel, and then I made a function to retrieve the data.

void Input_Channel (uint8_t channel) {

PORTA.OUTCLR = PIN0_bm;             // Bring CS Low
mspi_xchange((channel<<4) | 0x0);    // Write the desired channel to bits 15:12, and leave the rest of the bits as zero
mspi_xchange(0x00);                          // (rest of the don't care 12 bits)
PORTA.OUTSET = PIN0_bm;             // Bring CS High
}

Here is where I retrieve the 16-bit data

uint16_t Read_Data (void) {

PORTA.OUTCLR = PIN0_bm;                                   // Bring CS low
mspi_xchange(0b11010000);                                     // Set CMR to "Read Data", rest of the 12 bits aka the 'don't care' bits are set to zero
mspi_xchange(0x00);                                                 // (don't care bits)
uint8_t msb = mspi_xchange(0x00);                          // Read MSB of ADC data
uint16_t fullData = msb | mspi_xchange(0x00);         // Read LSB of data
PORTA.OUTSET = PIN0_bm;                                   // Bring CS high
return fullData;                                                
}

Very much appreciated the input, thanks.

  • Mitchell,

    We are looking into your request and will get back with you soon.
  • Much appreciated
  • Mitchell,

    In function ADS_On() you have chosen

    4bit CMR = 1110  : write CFR

    12bit CFR = 1101 0111 1101

    1101  : auto channel select, internal osc, auto trigger, 250ksps

    0111  : active high eoc\int/, EOC pin, no daisychain, no auto nap

    1101  : no nap, no deep power down, no TAG bit, normal operation

    Couple of comments on the above settings:

    See below Table 1 from Data Sheet. In auto channel select, no need to write channel number to CMR as the internal sequencer would take care of this. Also, with auto channel select, auto trigger and tag bit should be enabled. In above settings auto trigger is enabled but not TAG bit.

    Function Input_Channel() looks good. If you want manual channel select, do not set auto channel select.

    Function Read_Data(): Two comments

    a) Shift left msb 8bits and bit or the result with the lsb data

    b) 16 SCLK cycles per SPI read is fine if TAG is not set. With auto channel, TAG is required and so you need 24 SCLK cycles. See below table 7 from Data Sheet

    Thanks,

    Vishy

  • Hi Vishy,

    Thanks for your message.

    I've made the changes, but still receive zeros in my SPI exchanges to read the CFR register.

    /*********************************
    ADS8332 Read CFR
    **********************************/

    uint16_t Read_CFR(void) {

    PORTC.OUTCLR = PIN4_bm;
    SPI_Data_Transfer(0b11000000);
    SPI_Data_Transfer(0x00);
    uint8_t msb = SPI_Data_Transfer(0x00);
    uint16_t fullCFR = ((uint16_t)msb<<8) | SPI_Data_Transfer(0x00);
    PORTC.OUTSET = PIN4_bm;
    return fullCFR;

    }

    Could this be a problem of power supply? I'm using the original ADS8332 that requires a 10V supply, but I'm bypassing the op-amps and regulators so that 5V will be enough. I've only supplied power and ground connections to the J3 header though. Should I be making ground connections to the J2 header as well?

    This is the user guide I'm using http://www.ti.com/lit/ug/sbau176a/sbau176a.pdf

    Thanks,

    Mitch

  • >>>>> I'm using the original ADS8332 that requires a 10V supply, but I'm bypassing the op-amps and regulators so that 5V will be enough. I've only supplied power and ground connections to the J3 header though. Should I be making ground connections to the J2 header as well?

    Please refer to the schematic on page  12 : +5VA is output from LDO TL750L05. This LDO is powered by +10V supply. If you are not providing +10V at J3.1, it's not very clear to me how you have powered the ADS8332 device. See schematic snippet below

    >>>Should I be making ground connections to the J2 header as well?

    Yes: from the MCU you should connect the SPI lines and a ground to the J2 header.

    Please upload a simple schematic showing power connections to header J3 and MCU SPI line connections to header J2. Also, specify what jumper settings you are using.

    In your Read_CFR function, do only 16bit transfers: bring CSB high after 16bits SPI transfer. The serial interface works with CPOL = 1, CPHA = 0: MCU can read the data on the falling edge. See picture below

    Can you also connect scope probes on the SPI lines and check if the write and read access are happening fine? Please upload a scope shot also of the write and read access.

    Thanks,

    Vishy

  • Hi thanks for your help,

    You helped me to power the device. I got a +/-12V power supply, and I can read the CFR register, and ADC tag bits perfectly now. So I know that the SPI read/write is working.

    I'm having some difficulty though reading conversion results. I've noticed that in my Read_Data function, on the 3rd SPI transfer I can read the tag bits.. 4,5,6,7, etc after bit-shifting them, but I can't get the data. I expected the 16-bit data to come in on the 1st and 2nd SPI transfers, but I get all zeros. If it isn't too much trouble, would you mind looking through my Read_Data function? On the first SPI transfer, I give the CMR the 4-bit Read Data command (1101b), and then send zeros to get the results back. Those first two SPI transfers, msb and lsb, are where I expected to get the 16-bit data, and the third SPI transfer, xlsb, is where I get the tag bits. The CFR setting is 0001 1111 1111, so manual channel select, SCLK/2, and auto-trigger to avoid using the CONVST pin for now.

    /*********************************
    ADS8332 Read Data
    **********************************/

    uint16_t Read_Data(void) {

    PORTC.OUTCLR = PIN4_bm;                              // bring SS low
                                                                                  // perhaps should have a while loop to wait for data to be ready (could use INT pin, or other way of waiting for EOC)
    uint8_t msb = SPI_Data_Transfer(0b11010000); // I think this gives back the 8 msb of data. I also send the 1101b Read Data command to the CMR in bits 15:12
    uint8_t lsb = SPI_Data_Transfer(0x00);               // I think this gives back the 8 lsb of data
    uint8_t xlsb = SPI_Data_Transfer(0x00);             // First 3 bits of this are the tag bits, so they have to be bit shifted >> 5 (0bttt00000)
    PORTC.OUTSET = PIN4_bm;                             // bring SS high
    return xlsb;                                                            // Return just tag bits in xlsb for now

    }

  • Hello,

    It's not clear when the "Read_Data" function is called. You should monitor the status pin and call the function "Read_Data" whenever a conversion is done. For example, you can program the status pin as interrupt output in CFR_D6 bit and also program the polarity of this bit in CFR_D7. When the status pin interrupt is asserted, you call the function "Read_Data".  See status timing diagram below (here INT\ is active low, so you read after INT\ goes low)

    Thanks,

    Vishy

  • Hi Vishy,

    Thanks for the reply, your help has been great.

    My procedure or pseudocode is that I

    1. Initialise the CFR as 0xc6bd

    2. Select channel zero with 0x0000

    3. Then, in a while loop in main, check for an interrupt

    4. Poll/read the 24 bit data in that loop with 0xd00000

    The CFR read is fine, but I can't get the data. Is it correct to send 3 SPI exchanges (1st with 0xd0, then the 2nd, and 3rd with garbage bytes) to get the data after checking the status pin? Right now I get back 0xfffff0 no matter how I change the channel.

  • Mitchell,
    I found some basic sample code for this device. Please accept the friend request I send so I can mail you the code. Take a look at that example and see if it helps.
    Thanks,
    Vishy
  • Actually, there's an application note and associated sample code at the link below

    www.ti.com/.../litabsmultiplefilelist.tsp

    Please let me know if you have trouble accessing link.

    Thanks,
    Vishy