Go Down

Topic: >Working, with library!< Interfacing ADS1213 22-bit ADC (Read 31059 times) previous topic - next topic


Hey Murdock,
I was wondering how deep into the code your clock calculations go. I was wanting to not use the internal clock because Mark Thoren, that I mentioned earlier from linear technology, told me that if your clocks are at the same frequency then the adc will pick up noise from the other devices. I would prefer not using the arduino clock for that reason. I am worried in your code the clock speed affects how the the arduino sends and recieve data.

I also looked at the multiplexing chanenls because I wasn't sure if it made you reset the oversampling each time, nor did I know the different chanel schemes. They are on page 13 of http://cds.linear.com/docs/Datasheet/2442f.pdf.

In order to change the speed/resolution or input channel, the first three bits shifted into the device are 101. This is compatible with the programming sequence of all LTC multichannel differential input ?? ADCs. If the sequence is set to 000 or 100, the following input data is ignored (don't care) and the previously selected speed/resolution and channel remain valid for the next conversion. Combinations other than 101, 100, and 000 of the three control bits should be avoided. If the first three bits shifted into the device are 101, then the following five bits select the input channel for the following conversion (see Tables 3 and 4). The next five bits select the speed/resolution and mode 1X (no Latency) 2X (double output rate with one conversion latency), see Table 4. If these five bits are set to all 0's, the previous speed
remains selected for the next conversion. This is useful in applications requiring a fixed output rate/resolution but
need to change the input channel.


I am trying to interface with ADS1211 ADC IC. I am currently using Cypress PSoC 1 MCU. Is the code for the Adruino comapatable with Cypress? The Cypress internal ADC was not accurant enough  for the application.
I just want to use the SPI to read voltages to my Cypress MCU.


I am currently using Cypress PSoC 1 MCU.

I don't often stop in the Chevy dealership to ask questions about my Harley.

Why are you here?
The art of getting good answers lies in asking good questions.


I thought I could find some smart people. But I guessed wrong.


I want to use geophone sensor with this ADS chip.
The output of the sensor is AC voltage varying in the amplitude
It has 2 terminal, positive and negative
How to connect its terminal to ADS1213 input??

should I connect its positive terminal to Non-Inverting Input AND its negative terminal to Inverting Input ?
positive terminal to Non-Inverting Input AND negative terminal to GROUND ?

I am a newbie here.

How to control the Multiplexer inside ADS1213 ??
I want to use 4 geophone sensor with 1 ADS1213
How much is the maximum frequency of ADS1213 multiplexer ??

Thank You


People seem to have trouble with Arduino 1.0. That's because they changed the standard Wiring.h library to Arduino.h. To make any library compatible with both previous Arduino versions and version 1.0, the following needs to be done:

Replace this:
#include <Wiring.h>

By this:
#if defined(ARDUINO) && ARDUINO >= 100
#include "Arduino.h"
#include "WProgram.h"

The new version of the library (with this changed) which is therefore compatible with Arduino 1.0 as well as previous versions, is attached to this post.


Jul 15, 2012, 09:21 pm Last Edit: Jul 15, 2012, 09:38 pm by V_king Reason: 1

trying to use ADS1211P with Murdocks' library, but keep receiving zeroes :(

I am reading the values from load cell and displacement tranducer, which output 0 to 5 V.
Tried single input as well as differential input without any changes :(

I used 10Mhz crystal, as in datasheet Figure 12 they were using the 10Mhz crystal as default for examples, with turbo mode 1, and gain 1.

Can not figure out what am I doing wrong?
Also, there is no mentioning in Murdocks' readme file about sdout pin from ads1213. Doesn't he use it?

the figure 12 from the crystal is attached to the message.


Hi V_king,
I don't use the SDOUT pin because the SDIO pin can be used as both an input and output pin. If you look in the code and check out the 'read' function, you will see this line:   DDRB &= ~_BV(_IO);
That sets the DDRB (data direction register) to input for the specified _IO pin. _BV(_IO) can be substituted for 1>>_IO. If you want to know exactly how it works, learn more about bit math and port manipulation.

I don't know what is wrong with your setup. Obviously, the communication with the ADS1211 doesn't succeed. Try using lower clock values, maybe that'll work. And try to write to and read from non-critical setting registers within the ADS1211. Try reading first.


Jul 22, 2012, 01:03 pm Last Edit: Jul 22, 2012, 05:44 pm by V_king Reason: 1
Hello Murdock,

thank you for the repy. The code in your first posts make some sence with register writing, but when I opened the library, the code is out of my league :)

Found some info in arduino site about bit math and port manipulation, and will try studying that. thanx for the reference.

Rebuild the circuit again, and got the chip working. might need new prototyping board :(

Getting stable 16 bit, 1000 Hz results at tmb 8 and dr 77. there is quite a bit of noise though :(

I wonder if anyone could suggest any cicuits for unipolar single ended sensors input to this differential adc? should I just simply ground the inverting pin? or maybe someone has tried and tested op-amp circuit (i am novice with op-amps).


Jul 23, 2012, 12:27 am Last Edit: Jul 23, 2012, 12:33 am by V_king Reason: 1
hello everyone,

been busy reading datasheets and thinking of using TI external voltage reference like REF5025, hopefully to reduce noise.

Played with settings and simple RC filter( 10k resistor and 0.2 uF capacitor seems to work best), at the moment I get 2 mV fluctuation, reading arduino 3.3V output. I need at least 1mV accuracy and  0.5 mV would be perfect.  

Also I wonder if op-amp on each channel would improve the signal quality?
There is a reference circuit in the TI REF50XX voltage reference datasheet, for data acquisition, attached in the file. They use OP365 opamp to filter the signal.
Those OP365 op amps are quite expensive (around £4 each :( ). Don't feel like cashing out to find out that they are useless. Maybe there are cheaper alternatives?

Nn the other hand, the whole circuit is on breadboard, near the computer, so it might be picking up the noise from surroundings ?

Finally, ramped up the sampling rate up to 100 kHz (using delayMicroseconds(10) ) and it looks like the results are more stable. Or is it just the same readings being shown? :)


Murdock's library is obviously wrong.  If you try to use the set clock function, it does not operate at 2 MHz.  It operates at 8 MHz which is the wrong timing for ADC.


Great that you have taken the time to look through the code and seem to have found a bug, but please elaborate. I cannot find a fault in the code.

Datasheet pages 22 and 23 list the desired serial clock frequency, which is a maximum of 1/10th the clock speed. I try to achieve that by using delayMicroseconds() to delay the write and read code. The whole code takes a bit longer in reality but this method makes sure that the code is never faster than the ADS1213.

This code (from the initalization routine) calculates the desired delay in microseconds for half a clock cycle (the cycle is delayed twice: once for clock high, once for clock low):
int _tscaler = (clockspdMHz)*10;
byte _SCLKdelay = 5*10/_tscaler+1;

clockspdMHz is a float which is given in the initialization routine. If you give 2.0, _tscaler will be 20. _SCLKdelay will then be 3, giving a maximum SCLK frequency of 166kHz.

So I don't see what you mean, it doesn't run at 8MHz. If you use the ATMega's built-in SPI (= TWI) hardware, then it runs at 8MHz standard. My code doesn't use that.


I realize this is an old thread at this point and I hope some are still following it as I have a question about interfacing with an ADS1211.  After reading through several posts including this one, I am trying to use the library Murdock posted on Apr 19, 2011 (ADS1213) to log data from a geophone.  I've read through the spec sheet for the ADS1211 several times and think I have a beginners handle on how it works. 

I followed the wiring diagram from the first post on this thread, including using the arduino's internal timer but all I get out is a bunch of 0's.  I also tried to follow nadabro's post (http://arduino.cc/forum/index.php?topic=73149.0) as he is working with the same sensors and ADC.  Is there anyhting that I might be missing?  I would like to use the internal clock instead of an external crystal if possible but if that is my problem please let me know.

I'm sure you need more information to help me so please let me know what you need.  Right now my code is the example code for switching channels in the library (I like to start with the examples until I understand them enough to change them for my needs).  Thanks for any help you can provide.


Hi dkolbay, the latest version of the library (compatible with Arduino 1.0) is here (from the march 28th 2012 post up there ^).

With these kind of problems, it's always wise to take a step back in order to analyze the problem, then determine the simplest test possible, and then try to get it working.

Yours is obviously not working correctly or it wouldn't be spewing out zeroes. There can be problems somewhere in the communication, but the most obvious problem is that the clock signal (not serial clock) you are feeding to the ADS1211 is not correct. But let's first devise a simple test, as your sketch right now involves multiple write and read operations, too many opportunities for errors.

The simplest test would involve as few operations as possible and as simple feedback as possible. This could be 1) writing to the command register that Vbias must be on, making Vbias output some voltage and 2) reading this voltage with an analog Arduino pin. You can make a sketch to do this test and make it output a victorious message when the test succeeds.

If you want to feed a clock signal to the ADS1211, you'll have to configure one of Arduino's timers to do so. Timers are quite simple pieces of hardware, they simply count and when they reach a number, they do something. You can read all about it in the Atmega328's datasheet (it might seem overwhelming but keep in mind that timers are very simple devices, albeit with many configuration options). What you want is to 1) take a timer that controls a port that is not used by the library and 2) make it produce a square wave (thus output 0v and 5v with equal periods).

So if you have the test sketch that outputs a square wave to the ADS1211's clock input, writes to the command register and sets the Vbias high, and then reads the Vbias voltage on an analog Arduino pin, you can hook everything up and start testing. If it still doesn't work, you only have a few things to check. If it does work, hooray, and you can start expanding the code to fit your needs.

I dug in my sketches folders and found some code to output a square wave on a pin using a timer, I use it for producing tones with a speaker. The .h file (it's just a C file, you can open it with the Arduino IDE) contains the functions that set the timer and set tones. The .ino file houses an example sketch. It does a lot of direct register manipulation using bit math. The constants like "TCCR2A" that you see in the code are defined in the avr/io.h file (Arduino includes it automatically I believe), they are simply bits of code that write or read a register (in the "TCCR2A" case) or define where a port bit is in the register with a number between 0 and 7 (in the "OC2A" case), and _BV(n) is function that shifts a binary 1 n places to the left (1<<n).

I hope this helps you solve the problem, and if not, come back here with some more details.


May 15, 2013, 10:35 pm Last Edit: May 16, 2013, 12:47 am by MrInternet Reason: 1
Hey Murdock,

I've also been trying to use the library and the wiring diagram that you provided in the original post.  The library I'm using is the one from March 28th, 2012 so I know it's compatible with Arduino 1.0 software.  The problem I am having is that the code seems to get stuck on the constructor portion of the code and I've found that it starts to fail at the point when defining the high/low instructions for the data ready portion.  

I believe be code is something like while(!(PIND & _BV(_DRDY)));  - don't have the code in front of me as I'm typing this so typing from memory.  I've measured the voltage coming out of the data ready pin and its low until the serial monitor is brought up and then it jumps up to high which I assume is fine.  I'm not sure why the constructor is failing at that particular point and was wondering if maybe it has to do with where the data ready pin is located?  I've set the data ready pin to 4 on the arduino so I know that it falls between the constraints you have in the constructor and can't for the life of me figure out why it won't go past this point in the constructor.  Any help would be greatly appreciated.

Some basic information:
- wired it to the same wiring diagram you provided earlier with the crystal in being located on pin 3
- data ready pin 4
- IO pin 10
- Sout pin 12
- Sclk pin 13
- CS pin 8
- Running the standard deviation example you provided running into noninverting channel 1 and grounded the inverting channel 1
- "Debugged" by using the pin 13 LED to turn on and just went through section by section.
- haven't gotten to the rest of the code thou because the constructor is failing right now and therefore can't go beyond that point.

Go Up