I2C

The I2C master library by Wayne Truchsess offers some significant advantages over the Wire/TWI library included in the standard arduino environment: It fixes some possible deadlock situations, it allows for communication using a repeated start condition as required by some devices, the code is much more compact and the structure is easier to understand.

API

This is a pre-instantiated singleton library. It is not possible to use more than one instance per sketch or to change the instance name.

The API syntax is very similar to the original C++ syntax. Some name mangeling was needed to distinguish the different variant of the read() and write() method. Apart from this replacing the dots in the method names for underscores is all it needs.

The pullup setting is missing because this function is not supported by the STM8 hardware.

Arduino syntax sduino syntax
I2C.begin() I2C_begin()
I2C.end() I2C_end()
I2C.timeOut(val) I2C_timeOut(val)
I2C.setSpeed(mode) I2C_setSpeed(mode)
I2C.pullup(active) not implemented
I2C.scan() I2C_scan()
n = I2C.available() n = I2C_available()
val = I2C.receive() val = I2C_receive()
I2C.write(addr, val) I2C_write(addr, val)
I2C.write(addr, reg, val) I2C_write_reg(addr, reg, val)
I2C.write(addr, reg, string) I2C_write_s(addr, reg, string)
I2C.write(addr, reg, *data, len) I2C_write_sn(addr, reg, *data, len)
I2C.read(addr, n) I2C_read(addr, n)
I2C.read(addr, reg, n) I2C_read_reg(addr, reg, n)
I2C.read(addr, n, *buf) I2C_readbuf(addr, n, *buf)
I2C.read(addr, reg, n, *buf) I2C_readbuf_reg(addr, reg, n, *buf)

Error codes

All functions return an error code. Return values for functions that use the timeOut feature will return at what point in the transmission the timeout occurred.

Looking at a full communication sequence between a master and slave (transmit data and then readback data) there a total of 7 points in the sequence where a timeout can occur. These are listed below and correspond to the returned value.

Errorcode Meaning: Waiting for...
0 Function executed with no errors
1 Waiting for successful completion of a Start bit
2 Waiting for ACK/NACK while addressing slave in transmit mode (MT)
3 Waiting for ACK/NACK while sending data to the slave
4 Waiting for successful completion of a Repeated Start
5 Waiting for ACK/NACK while addressing slave in receiver mode (MR)
6 Waiting for ACK/NACK while receiving data from the slave
7 Waiting for successful completion of the Stop bit

AVR error codes

For reference: The codes listed below where defined for the AVR, but they don't exist for the STM8 implementation. Combining the values of SR1 and SR2 it would be possible to implement most of these conditions (apart from 0x20), but so far I haven't seen any program needing these values, so I didn't implement this.

Status Codes for Master Transmitter Mode
0x08 A START condition has been transmitted
0x10 A repeated START condition has been transmitted
0x18 SLA+W has been transmitted; ACK has been received
0x20 SLA+W has been transmitted; NOT ACK has been received
0x28 Data byte has been transmitted; ACK has been received
0x30 Data byte has been transmitted; NOT ACK has been received
0x38 Arbitration lost in SLA+W or data bytes
Status Codes for Master Receiver Mode
0x08 A START condition has been transmitted
0x10 A repeated START condition has been transmitted
0x38 Arbitration lost in SLA+R or NOT ACK bit
0x40 SLA+R has been transmitted; ACK has been received
0x48 SLA+R has been transmitted; NOT ACK has been received
0x50 Data byte has been received; ACK has been returned
0x58 Data byte has been received; NOT ACK has been returned
Status Codes independed of mode
0xF8 No relevant state information available; TWINT = “0”
0x00 Bus error due to an illegal START or STOP condition

inner workings

start(): Sends start bit, does not wait for SB flag. sendAddress()

Further reading

Programming the I2C communication on the register level is quite complex for the STM8, especially in receive mode. The most detailed information on this topic is the

Downloading from the ST website requires a (free) registration. Somebody uploaded the full package to github: https://github.com/jiaohaitao/stsw-stm8004

There are some important notes on I2C implementation in the errata sheets: