Skip to content

Instantly share code, notes, and snippets.

@tai
Created February 8, 2022 15:46
Show Gist options
  • Save tai/8f5d05cbbe5e610a1ea8663984300e33 to your computer and use it in GitHub Desktop.
Save tai/8f5d05cbbe5e610a1ea8663984300e33 to your computer and use it in GitHub Desktop.
#include "I2CSlaveEx.h"
I2CSlaveEx::I2CSlaveEx(PinName sda, PinName scl) : _i2c() {
i2c_init(&_i2c, sda, scl);
i2c_frequency(&_i2c, 100000);
i2c_slave_mode(&_i2c, 1);
}
void I2CSlaveEx::frequency(int hz) {
i2c_frequency(&_i2c, hz);
}
void I2CSlaveEx::address(int address) {
int addr = (address & 0xFF) | 1;
i2c_slave_address(&_i2c, 0, addr, 0);
}
int I2CSlaveEx::receive(void) {
return i2c_slave_receive(&_i2c);
}
//
// I2C slave read that handles variable-length I2C master write.
//
// NOTE:
// - mbed I2CSlave API (and underlying C API) is simply broken and
// cannot read variable-length I2C master write.
//
#define LPC111x_I2C_DATA_RECV 0x80
#define I2C_STAT(x) ((x)->i2c->STAT)
int I2CSlaveEx::read(char *data, int length) {
uint8_t bi = 0;
while (bi < length) {
uint8_t ch = i2c_byte_read(&_i2c, 0);
uint8_t st = I2C_STAT(&_i2c);
if (st != LPC111x_I2C_DATA_RECV) {
break;
}
data[bi++] = ch;
}
return bi;
}
int I2CSlaveEx::read(void) {
return i2c_byte_read(&_i2c, 0);
}
int I2CSlaveEx::write(const char *data, int length) {
return i2c_slave_write(&_i2c, data, length);
}
int I2CSlaveEx::write(int data) {
return i2c_byte_write(&_i2c, data);
}
void I2CSlaveEx::stop(void) {
i2c_stop(&_i2c);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment