Very stuck sending data from one ESP32 to another using I2C

KrisKasprzak

Well-known member
All,

I realize I'm breaking rules in asking a non Teensy question, but I had communications between 2 ESP32 using I2C working just fine, then I installed the latest Arduino IDE and ESP32 software. Communication fails even with the most basic .inos

I have 4k7 pullups on both SDA and SCL on both boards


I'm really stuck and need some help. I'm using ESP32 dev kit, arduino IDE. I'm using no standard I2C pins on both boards (and cannot be changed)

Per this code, the master will see the slave and return the correct address and uint8_t error = Wire.endTransmission(true); returns 0
Master
Code:
#include "Wire.h"

#define I2C_DEV_ADDR 0x44

void setup() {
  Serial.begin(115200);
  bool error = Wire.begin(13, 14);
  //bool error = Wire.begin(I2C_DEV_ADDR, 13, 14, 400000);
  Serial.println(error);

  Scanner(); // will find slave at 0x44 (correct)

}

void loop() {
  delay(500);
  Wire.beginTransmission(I2C_DEV_ADDR); // send to 0x44 (which was found in above)
  Wire.write(122); // send something
  uint8_t error = Wire.endTransmission(true);
  Serial.print("endTransmission = ");
  Serial.println(error);
  // will alwasy return 0

}


void Scanner() {
  byte error, address;
  int nDevices;
  Serial.println("Scanning...");
  nDevices = 0;
  for(address = 1; address < 127; address++ ) {
    Wire.beginTransmission(address);
    error = Wire.endTransmission();
    if (error == 0) {
      Serial.print("I2C device found at address 0x");
      if (address<16) {
        Serial.print("0");
      }
      Serial.println(address,HEX);
      nDevices++;
    }
    else if (error==4) {
      Serial.print("Unknow error at address 0x");
      if (address<16) {
        Serial.print("0");
      }
      Serial.println(address,HEX);
    }  
  }
  if (nDevices == 0) {
    Serial.println("No I2C devices found\n");
  }
  else {
    Serial.println("done\n");
  }
  delay(5000);        
}

Slave
bool error = Wire.begin(I2C_DEV_ADDR, 14, 25, 400000);
Serial.println(error); // no errors, error = 1
while (Wire.available()) { // never gets' anything
Code:
#include "Wire.h"

#define I2C_DEV_ADDR 0x44

void setup() {
  Serial.begin(115200);
  bool error = Wire.begin(I2C_DEV_ADDR, 14, 25, 400000);
  Serial.println(error); // no errors, error = 1
}

void loop() {
  delay(100);
  Serial.println("waiting...");
  while (Wire.available()) {
    Serial.write(Wire.read());
    // never gets any data...
  }
}


Anyone have a clue?

TIA
 
I have never seen this code written this way.
"bool error = Wire.begin(I2C_DEV_ADDR, 14, 25"

I always write it as Wire.begin(I2C_DEV_ADDR, with one number.

Perhaps start simple like that.

It is also possibility that I just never knew you could check for errors in the way that you are doing it.
 
Sorry not much help, I have only done a little with the ESP32 and also found that not all ESP32 are the same, S2, S3, C2, C3...
So i can only suggest some basic things I would do.

0) Double check wiring. I have tried to debug several things before just to find out some wire is wrong or lose or ...

1) Probably search on ESP32 and Arduino forums for clues if anyone else has run into this... If nothing found post there.
1a) Would check libraries and other ESP sources for issues and pull requests: https://github.com/espressif/arduino-esp32
2) Updated from what version to what version? i.e. IDE 2. There have not been any changes in the last 6 months or so... ESP32, I have seen several updates on boards. So that would be my first suspect... I have version 3.0.4 installed, If you are not up to the latest, I might try installing it. If you are, I might try going back to the last version 2.x of it and see if it works.

3) Debugging, I would hook up Logic Analyzer to the SCL/SDA pins and see if they see anything. I would probably try it with the two connected and if I see nothing maybe just the master.... If I did not have LA, I would use probably another board, or maybe the same one, to see if there is
any communications at all from the master... Could be as simple as jumpering SCL pin to an LED pin and see if there is any changes seen, then ditto for the SDA.

If it looks like the master is communicating, I would try to hook up something to slave to see if it communicates. Maybe a teensy, running the
scanner or ???

Sorry I know not much help, but that is what I would do
 
I would just try to see if the I2C is working on each ESP32 alone.
Connect up an I2C device and see if you can talk to it.
This will show whether the I2C is working on one and/or both of the ESP32s.
 
Maybe try attaching a callback (ie blink a led) to Wire.onReceive(cb) on the slave side.
 
SOLVED

No clue why this works today as I've tried this code in the past. Any way posting for others to use.

sender code
Code:
#include "Wire.h"

#define I2C_DEV_ADDR 0x44
byte val = 0;
uint8_t error = 0;

struct DATA {
  uint8_t cat = 0;
  uint8_t dog = 0;
};

DATA sender;

void setup() {
  pinMode(2, INPUT);
  Serial.begin(115200);
  delay(4000);
  bool error = Wire.begin(13, 14, 400000);
  //bool error = Wire.begin(I2C_DEV_ADDR, 13, 14, 400000);
  Serial.println(error);
  delay(4000);
  // test and verify the slave address
  Scanner();
 
}

void loop() {

  delay(500);

  sender.cat = val;
  sender.dog = analogRead(2);
  Wire.beginTransmission(I2C_DEV_ADDR);  // send to 0x44 (which was found in above)

  Wire.write((uint8_t*)&sender, (uint8_t)sizeof(sender));

  // send something
  error = Wire.endTransmission();
  Serial.print("cat = ");
  Serial.print(sender.cat);
  Serial.print(", dog = ");
  Serial.print(sender.dog);
  val++;
  sender.dog = val;

  if (val > 63) {
    val = 0;
  }

  Serial.print(", endTransmission = ");
  Serial.println(error);

}


void Scanner() {
  byte error, address;
  int nDevices;
  Serial.println("Scanning...");
  nDevices = 0;
  for (address = 1; address < 127; address++) {
    Wire.beginTransmission(address);
    error = Wire.endTransmission();
    if (error == 0) {
      Serial.print("I2C device found at address 0x");
      if (address < 16) {
        Serial.print("0");
      }
      Serial.println(address, HEX);
      nDevices++;
    } else if (error == 4) {
      Serial.print("Unknow error at address 0x");
      if (address < 16) {
        Serial.print("0");
      }
      Serial.println(address, HEX);
    }
  }
  if (nDevices == 0) {
    Serial.println("No I2C devices found\n");
  } else {
    Serial.println("done\n");
  }
  delay(500);
}


receiver code

Code:
#include "Wire.h"

#define I2C_DEV_ADDR 0x44

struct DATA {
  uint8_t cat = 0;
  uint8_t dog = 0;
};

DATA reader;

void setup() {
  Serial.begin(115200);

  bool error = Wire.begin(I2C_DEV_ADDR, 14, 25, 400000);
  Serial.println(error);  // no errors, error = 1

  Wire.onReceive(GetIt);
}

void GetIt(int Len) {
  Serial.print("Data Found: ");
  if (Wire.available()) {
    Wire.readBytes((uint8_t*)&reader, (uint8_t)sizeof(reader));
    Serial.print("cat ");
    Serial.print(reader.cat);
    Serial.print(" dog ");
    Serial.println(reader.dog);
  }
  Serial.println();
}

void loop() {
  delay(500);
  Serial.println("searching");
}
 
Back
Top