[PATCH 2/9] regmap-i2c: avoid underflow when applying write length quirk
From: Peng Fan (OSS)
Date: Tue Nov 10 2026 - 03:38:16 EST
From: Peng Fan <peng.fan@xxxxxxx>
The adapter max_write_len quirk covers the whole write message, including
the register address, so regmap_get_i2c_bus() subtracts the register
address size to obtain the maximum raw payload. If max_write_len is not
larger than the register address size, that subtraction underflows and
produces a huge limit; when the sizes are equal it produces zero, which
regmap also treats as no limit.
No raw write can succeed with such an adapter because the register
address alone exceeds the quirk limit, so keep the current limit instead
of replacing it with a bogus value.
Fixes: ea030ca68819 ("regmap-i2c: Set regmap max raw r/w from quirks")
Signed-off-by: Peng Fan <peng.fan@xxxxxxx>
---
drivers/base/regmap/regmap-i2c.c | 11 ++++++++---
1 file changed, 8 insertions(+), 3 deletions(-)
diff --git a/drivers/base/regmap/regmap-i2c.c b/drivers/base/regmap/regmap-i2c.c
index 8663a4ec0a3d..eb3db02ad8fb 100644
--- a/drivers/base/regmap/regmap-i2c.c
+++ b/drivers/base/regmap/regmap-i2c.c
@@ -401,9 +401,14 @@ static const struct regmap_bus *regmap_get_i2c_bus(struct i2c_client *i2c,
max_read = quirks->max_read_len;
if (quirks->max_write_len &&
- (max_write == 0 || max_write > quirks->max_write_len))
- max_write = quirks->max_write_len -
- (config->reg_bits + config->pad_bits) / BITS_PER_BYTE;
+ (max_write == 0 || max_write > quirks->max_write_len)) {
+ size_t reg_reserve_size;
+
+ reg_reserve_size = (config->reg_bits + config->pad_bits) /
+ BITS_PER_BYTE;
+ if (quirks->max_write_len > reg_reserve_size)
+ max_write = quirks->max_write_len - reg_reserve_size;
+ }
if (max_read != bus->max_raw_read ||
max_write != bus->max_raw_write) {
--
2.51.0