smbpbi: Optimize i2cReadDataBytes using combined ioctl transaction
Refactor i2cReadDataBytes to perform a single ioctl call that combines
both I2C write and read operations into one atomic transaction.
This change avoid race conditions when multiple sensors are queried at
same time.
Change-Id: Id30e25560c3dfba6d5eec87efde2a1cc3b554f8d
Signed-off-by: Potin Lai <potin.lai@quantatw.com>
diff --git a/src/smbpbi/SmbpbiSensor.cpp b/src/smbpbi/SmbpbiSensor.cpp
index 238cbcf..e0610fe 100644
--- a/src/smbpbi/SmbpbiSensor.cpp
+++ b/src/smbpbi/SmbpbiSensor.cpp
@@ -232,28 +232,34 @@
int ret = 0;
struct i2c_rdwr_ioctl_data args = {nullptr, 0};
- struct i2c_msg msg = {0, 0, 0, nullptr};
+ std::array<struct i2c_msg, 2> msgs = {
+ {{0, 0, 0, nullptr}, {0, 0, 0, nullptr}}};
std::array<uint8_t, 8> cmd{};
- msg.addr = addr;
- args.msgs = &msg;
- args.nmsgs = 1;
+ args.msgs = msgs.data();
+ args.nmsgs = msgs.size();
- msg.flags = 0;
- msg.buf = cmd.data();
+ msgs[0].addr = addr;
+ msgs[0].flags = 0;
+ msgs[0].buf = cmd.data();
// handle two bytes offset
if (offset > 255)
{
- msg.len = 2;
- msg.buf[0] = offset >> 8;
- msg.buf[1] = offset & 0xFF;
+ msgs[0].len = 2;
+ msgs[0].buf[0] = offset >> 8;
+ msgs[0].buf[1] = offset & 0xFF;
}
else
{
- msg.len = 1;
- msg.buf[0] = offset & 0xFF;
+ msgs[0].len = 1;
+ msgs[0].buf[0] = offset & 0xFF;
}
+ msgs[1].addr = addr;
+ msgs[1].flags = I2C_M_RD;
+ msgs[1].len = length;
+ msgs[1].buf = reading;
+
// write offset
// NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg)
ret = ioctl(fd, I2C_RDWR, &args);
@@ -261,17 +267,6 @@
{
return ret;
}
-
- msg.flags = I2C_M_RD;
- msg.len = length;
- msg.buf = reading;
-
- // NOLINTNEXTLINE(cppcoreguidelines-pro-type-vararg)
- ret = ioctl(fd, I2C_RDWR, &args);
- if (ret < 0)
- {
- return ret;
- }
return 0;
}