--- hw/smbus.c | 55 +++++++++++++++++++++++++++-------------------------- hw/smbus.h | 35 +++++++++++++++------------------ hw/smbus_eeprom.c | 27 ++++++++++++++++--------- 3 files changed, 61 insertions(+), 56 deletions(-)
diff --git a/hw/smbus.c b/hw/smbus.c index 2711229..3f2d1f4 100644 --- a/hw/smbus.c +++ b/hw/smbus.c @@ -37,37 +37,38 @@ enum { static void smbus_do_quick_cmd(SMBusDevice *dev, int recv) { - SMBusDeviceInfo *t = container_of(dev->i2c.info, SMBusDeviceInfo, i2c); + SMBusDeviceClass *sc = SMBUS_DEVICE_GET_CLASS(dev); DPRINTF("Quick Command %d\n", recv); - if (t->quick_cmd) - t->quick_cmd(dev, recv); + if (sc->quick_cmd) { + sc->quick_cmd(dev, recv); + } } static void smbus_do_write(SMBusDevice *dev) { - SMBusDeviceInfo *t = container_of(dev->i2c.info, SMBusDeviceInfo, i2c); + SMBusDeviceClass *sc = SMBUS_DEVICE_GET_CLASS(dev); if (dev->data_len == 0) { smbus_do_quick_cmd(dev, 0); } else if (dev->data_len == 1) { DPRINTF("Send Byte\n"); - if (t->send_byte) { - t->send_byte(dev, dev->data_buf[0]); + if (sc->send_byte) { + sc->send_byte(dev, dev->data_buf[0]); } } else { dev->command = dev->data_buf[0]; DPRINTF("Command %d len %d\n", dev->command, dev->data_len - 1); - if (t->write_data) { - t->write_data(dev, dev->command, dev->data_buf + 1, - dev->data_len - 1); + if (sc->write_data) { + sc->write_data(dev, dev->command, dev->data_buf + 1, + dev->data_len - 1); } } } static void smbus_i2c_event(I2CSlave *s, enum i2c_event event) { - SMBusDevice *dev = FROM_I2C_SLAVE(SMBusDevice, s); + SMBusDevice *dev = SMBUS_DEVICE(s); switch (event) { case I2C_START_SEND: @@ -150,14 +151,14 @@ static void smbus_i2c_event(I2CSlave *s, enum i2c_event event) static int smbus_i2c_recv(I2CSlave *s) { - SMBusDeviceInfo *t = container_of(s->info, SMBusDeviceInfo, i2c); - SMBusDevice *dev = FROM_I2C_SLAVE(SMBusDevice, s); + SMBusDevice *dev = SMBUS_DEVICE(s); + SMBusDeviceClass *sc = SMBUS_DEVICE_GET_CLASS(dev); int ret; switch (dev->mode) { case SMBUS_RECV_BYTE: - if (t->receive_byte) { - ret = t->receive_byte(dev); + if (sc->receive_byte) { + ret = sc->receive_byte(dev); } else { ret = 0; } @@ -165,8 +166,8 @@ static int smbus_i2c_recv(I2CSlave *s) dev->mode = SMBUS_DONE; break; case SMBUS_READ_DATA: - if (t->read_data) { - ret = t->read_data(dev, dev->command, dev->data_len); + if (sc->read_data) { + ret = sc->read_data(dev, dev->command, dev->data_len); dev->data_len++; } else { ret = 0; @@ -184,7 +185,7 @@ static int smbus_i2c_recv(I2CSlave *s) static int smbus_i2c_send(I2CSlave *s, uint8_t data) { - SMBusDevice *dev = FROM_I2C_SLAVE(SMBusDevice, s); + SMBusDevice *dev = SMBUS_DEVICE(s); switch (dev->mode) { case SMBUS_WRITE_DATA: @@ -200,20 +201,20 @@ static int smbus_i2c_send(I2CSlave *s, uint8_t data) static int smbus_device_init(I2CSlave *i2c) { - SMBusDeviceInfo *t = container_of(i2c->info, SMBusDeviceInfo, i2c); - SMBusDevice *dev = FROM_I2C_SLAVE(SMBusDevice, i2c); + SMBusDevice *dev = SMBUS_DEVICE(i2c); + SMBusDeviceClass *sc = SMBUS_DEVICE_GET_CLASS(dev); - return t->init(dev); + return sc->init(dev); } -void smbus_register_device(SMBusDeviceInfo *info) +void smbus_register_device(I2CSlaveInfo *info) { - assert(info->i2c.qdev.size >= sizeof(SMBusDevice)); - info->i2c.init = smbus_device_init; - info->i2c.event = smbus_i2c_event; - info->i2c.recv = smbus_i2c_recv; - info->i2c.send = smbus_i2c_send; - i2c_register_slave_subclass(&info->i2c, TYPE_SMBUS_DEVICE); + assert(info->qdev.size >= sizeof(SMBusDevice)); + info->init = smbus_device_init; + info->event = smbus_i2c_event; + info->recv = smbus_i2c_recv; + info->send = smbus_i2c_send; + i2c_register_slave_subclass(info, TYPE_SMBUS_DEVICE); } /* Master device commands. */ diff --git a/hw/smbus.h b/hw/smbus.h index 9dd055c..fa9088a 100644 --- a/hw/smbus.h +++ b/hw/smbus.h @@ -26,30 +26,16 @@ #define TYPE_SMBUS_DEVICE "smbus-device" #define SMBUS_DEVICE(obj) \ - OBJECT_CHECK(SMBUSDevice, (obj), TYPE_SMBUS_DEVICE) + OBJECT_CHECK(SMBusDevice, (obj), TYPE_SMBUS_DEVICE) #define SMBUS_DEVICE_CLASS(klass) \ - OBJECT_CLASS_CHECK(SMBUSDeviceClass, (klass), TYPE_SMBUS_DEVICE) + OBJECT_CLASS_CHECK(SMBusDeviceClass, (klass), TYPE_SMBUS_DEVICE) #define SMBUS_DEVICE_GET_CLASS(obj) \ - OBJECT_GET_CLASS(SMBUSDeviceClass, (obj), TYPE_SMBUS_DEVICE) + OBJECT_GET_CLASS(SMBusDeviceClass, (obj), TYPE_SMBUS_DEVICE) typedef struct SMBusDeviceClass { I2CSlaveClass parent_class; -} SMBusDeviceClass; - -struct SMBusDevice { - /* The SMBus protocol is implemented on top of I2C. */ - I2CSlave i2c; - - /* Remaining fields for internal use only. */ - int mode; - int data_len; - uint8_t data_buf[34]; /* command + len + 32 bytes of data. */ - uint8_t command; -}; -typedef struct { - I2CSlaveInfo i2c; int (*init)(SMBusDevice *dev); void (*quick_cmd)(SMBusDevice *dev, uint8_t read); void (*send_byte)(SMBusDevice *dev, uint8_t val); @@ -64,9 +50,20 @@ typedef struct { byte at a time. The device is responsible for adding the length byte on block reads. */ uint8_t (*read_data)(SMBusDevice *dev, uint8_t cmd, int n); -} SMBusDeviceInfo; +} SMBusDeviceClass; + +struct SMBusDevice { + /* The SMBus protocol is implemented on top of I2C. */ + I2CSlave i2c; + + /* Remaining fields for internal use only. */ + int mode; + int data_len; + uint8_t data_buf[34]; /* command + len + 32 bytes of data. */ + uint8_t command; +}; -void smbus_register_device(SMBusDeviceInfo *info); +void smbus_register_device(I2CSlaveInfo *info); /* Master device commands. */ void smbus_quick_command(i2c_bus *bus, uint8_t addr, int read); diff --git a/hw/smbus_eeprom.c b/hw/smbus_eeprom.c index 5d080ab..2e8329f 100644 --- a/hw/smbus_eeprom.c +++ b/hw/smbus_eeprom.c @@ -104,19 +104,26 @@ static int smbus_eeprom_initfn(SMBusDevice *dev) return 0; } -static SMBusDeviceInfo smbus_eeprom_info = { - .i2c.qdev.name = "smbus-eeprom", - .i2c.qdev.size = sizeof(SMBusEEPROMDevice), - .i2c.qdev.props = (Property[]) { +static void smbus_eeprom_class_initfn(ObjectClass *klass, void *data) +{ + SMBusDeviceClass *sc = SMBUS_DEVICE_CLASS(klass); + + sc->init = smbus_eeprom_initfn; + sc->quick_cmd = eeprom_quick_cmd; + sc->send_byte = eeprom_send_byte; + sc->receive_byte = eeprom_receive_byte; + sc->write_data = eeprom_write_data; + sc->read_data = eeprom_read_data; +} + +static I2CSlaveInfo smbus_eeprom_info = { + .qdev.name = "smbus-eeprom", + .qdev.size = sizeof(SMBusEEPROMDevice), + .qdev.class_init = smbus_eeprom_class_initfn, + .qdev.props = (Property[]) { DEFINE_PROP_PTR("data", SMBusEEPROMDevice, data), DEFINE_PROP_END_OF_LIST(), }, - .init = smbus_eeprom_initfn, - .quick_cmd = eeprom_quick_cmd, - .send_byte = eeprom_send_byte, - .receive_byte = eeprom_receive_byte, - .write_data = eeprom_write_data, - .read_data = eeprom_read_data }; static void smbus_eeprom_register_devices(void) -- 1.7.4.1