0
votes

I try to communicate, read and write, from Arduino - slave - to RPi - master - with Android Things.

If i R/W, with a level converter, from RPi to Arduino 5v (16Mhz), everything works fine.

So i decide to eliminate the level converter, and use a 3v3 Arduino mini pro (8Mhz).

The write works fine, but when i try to read from the Arduino, the signal stops.

5v_16Mhz
After the Setup to 9, 0 address, and reads to 9, the signal still low and received the data. No problem.

3v3_8Mhz
After the Setup to 9, 0 address, and read to 9, the signal goes high and the data stop.

I used the same example for the Slave:

#include <Wire.h>

byte RFID[20] = {9,8,7,6,5,4,3,2,1,1,2,3,4,5,6,7,8,9,1,2};


void setup() {
  Wire.begin(8);          // join i2c bus with address #8
  Wire.onRequest(requestEvent); // register event
  Wire.onReceive(receiveEvent); // register event
  Serial.begin(115200);     // start serial for output
  pinMode(13, OUTPUT);
}

void loop() {
  delay(100);
}

// function that executes whenever data is requested by master
// this function is registered as an event, see setup()
void requestEvent() {
  Serial.println("Master ask");
  digitalWrite(13, HIGH);
  delay(250);
  Wire.write(RFID, 20);
  digitalWrite(13, LOW);
}

// function should be executes whenever data is received from master
// this function is registered as an event, but it's called every time the RPi
// call the Device.
void receiveEvent(int howMany) {
  while (0 < Wire.available()) {
    byte RTC_syn = Wire.read(); // receive byte
    Serial.println(RTC_syn);
  }
}

I really don't know how drives the signal high...
Someone can help me?

2

2 Answers

0
votes

If i R/W, with a level converter, from RPi to Arduino 5v (16Mhz), everything works fine.

So i decide to eliminate the level converter, and use a 3v3 Arduino mini pro (8Mhz).

The write works fine, but when i try to read from the Arduino, the signal stops.

This is because level converter you had in the 5V/3.3V version does more than shift the voltage. It also acts as a nice high-impedance buffer between the two devices that helps keep the signal driven and avoids loading effects.

Without the buffer, your bus is likely experiencing a bit of loading. You can try to combat this by adding stronger pull-up resistors. The RPi3 has 1.8k pull-up resistors on the I2C lines, which generally works but can be marginal depending on the input impedance of the slave device. The Arduino Mini has pads to install I2C pull-ups but there are none by default.

The recommended pull-up resistance for a pure 3.3V I2C bus is closer to 1k, so you likely just need to add some stronger pull-ups between SCL/SDA and +3.3V. Anything you add will be in parallel to the RPi3 resistors so factor that into your calculation. For example, adding 4.7k resistors brings the effective resistance down to about 1.3k.

If you are unable to solve it with pull-ups, you can achieve the same buffer effect without level translation by using a line driver IC (random example).

-1
votes

If the level converter works, you should stick with it.

Communication protocols like I2C encode data into a series of logic HIGH and logic LOW signals. What does HIGH / LOW mean? It depends on the devices. For the majority of embedded devices, logic LOW will be ground, 0V.

For Arduinos and Raspberry Pis, the source voltage is different (3.3V versus 5V). This difference can lead to several potential issues.

  1. The 5V signal is too high for the Arduino to handle, causing the Arduino to stop working or reboot

  2. The 3.3V signal is not strong enough to be interpreted as logic HIGH. Embedded devices have circuits that round signals to HIGH/LOW, and the thresholds may not be entirely even. A 5V input may only accept 4.5V or higher, interpreting everything else as LOW or in an indeterminate state.