I2C Working on two devices, not on the third

I'm using a JY901 gyroscope sensor, talking to it with I2C. Works perfectly with a standard Uno (R3), and I (eventually) got it working with a NodeMCU 12e. but I can't seem to get it working with the target device, a Heltec Lora 32 board.

The device address is on 0x50 - and both boards seem to find it okay with a port scan.

JY901 resources here

Node MCU Output - Works

4 SDA
5 SCL
Start Scan
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
50 .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
Scan Completed, 1 I2C Devices found.
Angle: Pitch -0.03 Roll 2.79 Yaw 98.65
Mag:236 -42 430
Angle: Pitch -0.03 Roll 2.79 Yaw 98.54
Mag:238 -40 430
Angle: Pitch -0.02 Roll 2.78 Yaw 98.62
Mag:241 -41 429

However, when I put this code on the Heltec, It finds the I2C port with the port scan (see below); it gets the CORRECT number of bytes to read when I poll the accelerometer but just returns zeros in the data fields.

Heltec Lora 32 (Fails)
21 SDA
22 SCL
Start Scan
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
50 .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
Scan Completed, 1 I2C Devices found.
Angle: Pitch 0.00 Roll 0.00 Yaw 0.00
Mag:0 0 0
Angle: Pitch 0.00 Roll 0.00 Yaw 0.00
Mag:0 0 0
Angle: Pitch 0.00 Roll 0.00 Yaw 0.00
Mag:0 0 0

I should add that I've externalised the power supply so, the voltage & current is identical in both instances. I have pull up resistors (4.7k-Ohm) to VCC on both the SCL & SDA (but these are on the sensor circuit and are the same in both instances)

Things I've tried:

  1. Changing the I2C clock speed (100k, 400k)
  2. I've confirmed that the I2C bus is working on the Heltec (by talking to another board)
  3. Tried endTransmission(false) and endTransmission(true) (Just in case it made any difference - it doesn't)
  4. I have an oscilloscope that (theoretically) traces I2C but as soon as I attach the probes, the device stops sending anything.

I've turned everything else off on the Heltec (no OLED or Lora going - just the serial port to the USB monitor)
I've attached the source (bit rough because of all the fiddling) but this is the read I2C function

void readRegisters(unsigned char deviceAddr,unsigned char addressToRead, unsigned char bytesToRead, char * dest)
{
   Wire.beginTransmission(deviceAddr);
  Wire.write(addressToRead);
  uint8_t ec=Wire.endTransmission(false); //endTransmission but keep the connection active
   Wire.requestFrom(deviceAddr, bytesToRead); //Ask for bytes, once done, bus is released by default
   while(Wire.available() < bytesToRead); //Hang out until we get the # of bytes we expect
   for(int x = 0 ; x < bytesToRead ; x++)
  {
      dest[x] = Wire.read();
    }
}

Anyone got any idea what might be causing the problem?

jy910.ino (10.3 KB)

what pullup resistors do you have on the I2C lines?
also try a web search for heltec esp32 lora i2c

@OP

Can you try changing/modifying your codes as follows and pls report the result.

void readRegisters(unsigned char deviceAddr,unsigned char addressToRead, unsigned char bytesToRead, char * dest)
{
   Wire.beginTransmission(deviceAddr);
  Wire.write(addressToRead);
  uint8_t ec=Wire.endTransmission();//(false); //endTransmission but keep the connection active
   Wire.requestFrom(deviceAddr, bytesToRead); //Ask for bytes, once done, bus is released by default
 //  while(Wire.available() < bytesToRead); //Hang out until we get the # of bytes we expect
   for(int x = 0 ; x < bytesToRead ; x++)
  {
      dest[x] = Wire.read();
    }
}

horace:
what pullup resistors do you have on the I2C lines?
also try a web search for heltec esp32 lora i2c

horace:
what pullup resistors do you have on the I2C lines?
also try a web search for heltec esp32 lora i2c

Thanks for getting back to me.

Re: pull-up resistors - I've tried 4.7k, 5k and 10k - no difference. However, I'm using a breadboard for these tests and I'm not 100% convinced of the connection. I'm going to try it again with a soldered circuit just in case. What's weird is it works on all the SoC;s I have EXCEPT the target device (typical)

Yeah, I've filled up two browser screens with "heltec esp32 lora i2c" results - nothing I've seen (yet) contributes anything. Again, what's strange is that the port-scan code FINDS the port. Just never receives anything useful back.

Thanks again

GolamMostafa:
@OP

Can you try changing/modifying your codes as follows and pls report the result.

void readRegisters(unsigned char deviceAddr,unsigned char addressToRead, unsigned char bytesToRead, char * dest)

{
  Wire.beginTransmission(deviceAddr);
 Wire.write(addressToRead);
 uint8_t ec=Wire.endTransmission();//(false); //endTransmission but keep the connection active
  Wire.requestFrom(deviceAddr, bytesToRead); //Ask for bytes, once done, bus is released by default
//  while(Wire.available() < bytesToRead); //Hang out until we get the # of bytes we expect
  for(int x = 0 ; x < bytesToRead ; x++)
 {
     dest[x] = Wire.read();
   }
}

Results of the code change are below. It returns non-null data but it's still rubbish (and doesn't change if you move the accelerometer)

I also tried adding a small delay after the transmission (10ms and 30ms) but, again, no change

21 SDA
22 SCL
Start Scan
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
50 .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..
Scan Completed, 1 I2C Devices found.
Angle: Pitch 0.00 Roll 0.00 Yaw 42.19
Mag:0 0 7680
Angle: Pitch 0.00 Roll 0.00 Yaw 42.19
Mag:0 0 7680
Angle: Pitch 0.00 Roll 0.00 Yaw 42.19
Mag:0 0 7680
Angle: Pitch 0.00 Roll 0.00 Yaw 42.19
Mag:0 0 7680

Bit perplexed with this one

I used a Picoscope to trace the I2C bus.

There's a jpg file attached of the scope trace and two exports of the packets I saw, One is from the Arduino Uno (which works perfectly) and you see the distinctive write to 0x50 data [0x3X], followed by three reads (it's in reverse order in the trace)

Arduino Uno - Working
50 A1 Read 0 ED FF 09 0 0 0
50 A1 Read 0 0F 01 0 0
50 A1 Read 0 EE FF 06 0 0 0
50 A1 Read 0 0F 01 0 0
50 A0 Write 0 34 0
50 A1 Read 0
50 A0 Write 0 30 0
50 A1 Read 0
50 A1 Read 0 EC FF 0 0
50 A1 Read 0 EF FF 0 0
50 A0 Write 0 34 0

But the Heltec, seems to do LOADS of writes but never seems to see a read

50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A1 Read 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0
50 A0 Write 0 3D 0

This is on the physical bus so, the implication, to me, is that somehow, the Heltec is sending the write request but the sensor isn't really responding. Unfortunately, the Heltec I2C layer (for some reason) believes it has and returns the correct number of bytes which happen to be all zero.

Not sure where to go from here. Nothing obvious occurs to me that I haven't already tried.

If anyone is still interested, here are the scope traces for the I2C bus.

This works with the Heltec Lora 32 V2.0 with I2C and the JY-901 accelerometer.

  1. Needs two pullup resistors on SCL and SDA to VCC (5kOhm worked okay for me)

  2. SDA is on PIN 21, SCL PIn 22. You can take power and ground from GND and 5V from the Heltec (Not the Vin side, the other side) It provides enough voltage and current for the JY-901.

I've attached the working code which also has the LoRa channel activated (which also works) to make sure the LoRa modem didn't draw too much power and kill the sensor.

Make sure you're using the latest Heltec code from here

JY901IIC.zip (3.5 KB)