I2C Pico USB Adapter: Part 3 - I2C

I expected implementing the I2C communication would be very easy. After all, the RP microcontrollers have hardware for this and the SDK has support for it. Alas, I did not take into account some limitations of the hardware and the way i2c-tiny-usb implements its commands.


As a quick refresh, I2C is a serial protocol over two wires, one for clock (SCL) e the other for data (SDA). SCL is always controlled by the master (the microcontroller), SDA can be controlled by the master or the slave. Both signals are normally high, thanks to pullup resistors. During normal communication, SDA only changes when SCL is low. The exceptions mark the beginning (START) and ending (STOP) of an I2C transaction.

The first byte sent by the master after a START condition is a 7 bit address plus a 1 bit read/write indicator. The device with the corresponding address (if there is one)  acknowledges this byte. Data bytes are sent after the address, each one acknowledged by the receiver.


As we saw in the previous post, the address byte is sent when we get the I2C_IO command in the SETUP stage, if it is a read, we then get the data from the I2C device; if it is a write, we wait until the DATA stage to send the data.

A special case is when there is no data to send or receive. This is used (as a hack) to check if there is a device with some address in the I2C bus. I say hack, because it is not part of the specification, and some devices will take some action when they are addressed, even before any data is transferred. For this reason, it is more common to use a zero-byte write operation instead of a zero-byte read operation.

The problem with the RP's I2C peripheral is that it automatically emits the START and the address when data is written. You do not have much control over the START and STOP conditions and cannot do zero-byte writes.

The solution is to do as i2c-tiny-usb does: implement I2C manually, using GPIO functions. Something I had done a long time ago, when I used PIC microcontrollers.

Comments

Popular posts from this blog

Using the PIO to Interface a PS/2 Keyboard