Interfacing ADS7828 to Teensy 4.0 via I2C

smuscat

Member
Hi,

I am trying to interface ADS7828 to the Teensy 4.0 development board via I2C with no success. I read PJRC website article about Wire library which uses teensy to eprom with no avail. In the code below, simply I am trying to read(pot) channel 0 single-ended by first write the address byte and the command byte, afterwards reading Highbyte and the Low byte, which then by code gives a 12bit reading of the potentiometer. Kindly can someone help me on this, your help is much appreciated.


#include <Wire.h>


void setup() {

Serial.begin(9600);
Wire.begin();
}

void loop()
{
Wire.beginTransmission(90);//address byte slave address 0 0
Wire.send(132);//command byte reading channel 0 single-ended, external reference

Wire.endTransmission();

Wire.requestFrom(90,2);//address byte, then wait to read two consecutive bytes
while(Wire.available()==0);
int highbyte1=Wire.receive();

int lowbyte1=Wire.receive();
int a=highbyte1<<8;
int pot_1=a|lowbyte1;// adapting the high byte and the low byte to calculate 12bit reading
Serial.println(pot_1);//12 bit reading
Wire.end();
delay(500);
}
 
Thank you very much for your suggestion,

I changed from decimal to hexadecimal as indicated in the ammended code below, sorry with no avail, do have other suggestion please?



#include <Wire.h>


void setup() {

Serial.begin(9600);
Wire.begin();
}

void loop()
{
Wire.beginTransmission(0x48);
Wire.send(0x84);

Wire.endTransmission();

Wire.requestFrom(0x48,2);
while(Wire.available()==0);
int highbyte1=Wire.receive();

int lowbyte1=Wire.receive();
int a=highbyte1<<8;
int pot_1=a|lowbyte1;
//Serial.println(a);
Serial.println(pot_1);
Wire.end();
delay(500);
 
You could try running the Wire library Scanner example, just to check the address and make sure the chip is detected.
 
try Wire.read() as opposed to Wire.receive();?

Are you sure about the address? I took a quick scan of the data sheet and I'm not sure you just send an address to Wire w/o hardware inputs. Pin A0 A1 must be set high / low, LSB indicates read/write and the address built accordingly.

address = 10010 A0 A1 RW
A0 is state applied to A0 pin
A1 is state applied to A1 pin
RW is 1 for read 0 for write

Hence address if both A0 and A1 pins are low and you want to read, 10010001 is 145 (dec)
 
Last edited:
Hi smuscat, I have done this exact thing recently and managed to have it working well now.

I would check that you have appropriate pull up resistors on the I2C lines. I had 4k7 resistors and was running a clock freq of 400kHz and with the length of my cables and number of devices on the bus this was definitely not a hard enough pullup ie the signals were woefully rounded off. Working fine with 2k pullups now.
 
Hello,

Again thank you very much for your advice and time,

I applied your kind suggestions but in vain. Please see code below, Just ask is there any mistake in the code sequence? Again please advice

#include <Wire.h>


void setup() {

Serial.begin(9600);
Wire.begin();
}

void loop()
{
Wire.beginTransmission(144);
Wire.send(132);

Wire.endTransmission();

Wire.requestFrom(145,2);
while(Wire.available()==0);
int highbyte1=Wire.receive();

int lowbyte1=Wire.receive();
int a=highbyte1<<8;
int pot_1=a|lowbyte1;
//Serial.println(a);
Serial.println(pot_1);
Wire.end();
delay(500);
 
Hi Smuscat,

Recommend you look at the pullup resistors as well (not sure if you have done so?)

Are your connections made to the SDA0 and SCL0 pins? This is important as you have not defined pins other than default in your code.

I also not that in your wait for data, you are triggering once a single byte appears

while(Wire.available()==0)

Maybe change this to:

while(Wire,available()<2)

as you are waiting for 2 bytes?

Also this is a potentially code blocking line and I would recommend implementing some form of timeout here.
 
actually you may have to use 0x48 as the address...Wire.h expects 7 bit address, meaning you will need to knock off the (LSB) or the RW bit, so...

10010001
or
10010000

becomes
1001000 which is 0x48 or 72 dec

I agree with above that your initial while() will not get the second byte.

What value are you getting for highbyte1 and lowbyte1?
 
Hello all,

I did your kind recommendations, It worked for little time and the communication with the teensy via usb was interupted. I might have the wrong value of the pullup resistors 2K situated between SCL0 to 3.3V(from teensy 3.3V supply) and SDA0 to 3.3V(from teensy 3.3V supply). Please can you have a look at skech of the circuit attached and comment if there are any irregularities.

Wish all the best for your help
#include <Wire.h>


void setup() {

Serial.begin(9600);
Wire.begin();
}

void loop()
{
Wire.beginTransmission(72);
Wire.send(0x84);//10//2

Wire.endTransmission();

Wire.requestFrom(72,2);
while(Wire.available()>2);
int highbyte1=Wire.receive();

int lowbyte1=Wire.receive();
int a=highbyte1<<8;
int pot_1=a|lowbyte1;
//Serial.println(a);
Serial.println(pot_1);
Wire.end();
delay(500);
}
 

Attachments

  • ads7828wiring.png
    ads7828wiring.png
    41.7 KB · Views: 55
That looks correct.

However one issue you need to be very careful of is ensuring that SDA and SCL are not pulled up to or being driven to 5V. Is your ADC running off 3.3 or 5V?
 
One thing to think over is that the Teensy 4.1 is not 5V tolerant so if at some time you have accidentally pulled up to 5V maybe you have damaged the I2C bus IO on the Teensy?

Do you have an DSO or logic analyser to look at the signals?
 
Please can you have a look at skech of the circuit attached and comment if there are any irregularities.

Wish all the best for your help
#include <Wire.h>


void setup() {

Serial.begin(9600);
Wire.begin();
}

void loop()
{
Wire.beginTransmission(72);
Wire.send(0x84);//10//2

Wire.endTransmission();

Wire.requestFrom(72,2);
while(Wire.available()>2);
int highbyte1=Wire.receive();

int lowbyte1=Wire.receive();
int a=highbyte1<<8;
int pot_1=a|lowbyte1;
//Serial.println(a);
Serial.println(pot_1);
Wire.end();
delay(500);
}

The line "while(Wire.available()>2);" loops kinda suspicious.

Maybe you meant something like "if (Wire.available() >= 2) {" ??

Did you try running the Wire library Scanner example (as I recommended in msg #4)? If using Arduino IDE, it is very easy. Just click File > Examples > Wire > Scanner to open it. Upload to your Teensy and then watch the Arduino Serial Monitor for results. It can at least confirm if your I2C chip is connected properly and responding at the correct address.
 
Thank you Paul,

I did what you suggested, the I2C ADS7828 gives sometimes connected, sometimes not connected and gives errors, I am going to buy a new I2C chip so would be able to know if my teensy board is good.

Again thank you a million for your advice
 
Back
Top