Skip to contentSkip to conversation

iio: dac: mcp47feb02: reject out-of-range raw values

PATCH Applied David Carlier 4 participants 4 messages Oct 25 – Nov 3

Subsystems (2)
lore
Share & tools
lore
#0 lore raw

PATCH v2 1/1 iio: dac: mcp47feb02: reject out-of-range raw values

mcp47feb02_write_raw() writes the user supplied raw value to the DAC register without checking it against the chip resolution. The parts are 8, 10 or 12 bit, and the bits above the resolution are not implemented, so writing 300 to out_voltage0_raw on an 8-bit part sets the output to code 44 instead of failing, and -1 is written as 0xffff.

The out-of-range value is also cached in dac_data, so it is written back on resume and stored to EEPROM by store_eeprom.

Return -EINVAL for values outside [0, 2^resolution - 1].

Fixes bf394cc80369 ("iio: dac: adding support for Microchip MCP47FEB02")

---
Found by LLM-assisted code inspection, reviewed and verified by hand. Build tested with W=1 (=m and =y) only; no hardware was available for runtime testing.

v2:
- Use GENMASK() for the upper bound so it is safe up to 32 bits (Andy)
- Drop the Assisted-by tag, removed from the docs in 1e035297ffda (Joshua)
- Move the testing note below the --- (Joshua)

v1: https://lore.kernel.org/all/[email protected]/

---
 drivers/iio/dac/mcp47feb02-core.c | 3 +++
 1 file changed, 3 insertions(+)
drivers/iio/dac/mcp47feb02-core.c +3 -0
index 88bffbab0854..b5a2ac4a2e67 100644
@@ -696,6 +696,9 @@ static int mcp47feb02_write_raw(struct iio_dev *indio_dev, struct iio_chan_spec
 
 	switch (mask) {
 	case IIO_CHAN_INFO_RAW:
+		if (val < 0 || val > GENMASK(data->chip_features->resolution - 1, 0))
+			return -EINVAL;
+
 		ret = regmap_write(data->regmap, REG_ADDR(ch->address), val);
 		if (ret)
 			return ret;
Signature · 1 line
2.55.0
Reviewed-by on v2 1/1
#1 lore raw
Quoted 10 lines · David Carlier

mcp47feb02_write_raw() writes the user supplied raw value to the DAC register without checking it against the chip resolution. The parts are 8, 10 or 12 bit, and the bits above the resolution are not implemented, so writing 300 to out_voltage0_raw on an 8-bit part sets the output to code 44 instead of failing, and -1 is written as 0xffff.

The out-of-range value is also cached in dac_data, so it is written back on resume and stored to EEPROM by store_eeprom.

Return -EINVAL for values outside [0, 2^resolution - 1].

LGTM now,

Signature · 2 lines
With Best Regards,
Andy Shevchenko
maintainer Applied
#2 lore raw
In reply to David Carlier
Quoted 6 lines · On Sun, 25 Oct 2026 21:18:56 +0000 David Carlier <[email protected]> wrote:

mcp47feb02_write_raw() writes the user supplied raw value to the DAC register without checking it against the chip resolution. The parts are 8, 10 or 12 bit, and the bits above the resolution are not implemented, so writing 300 to out_voltage0_raw on an 8-bit part sets the output to code 44 instead of failing, and -1 is written as 0xffff.

Quoted 7 lines

The out-of-range value is also cached in dac_data, so it is written back on resume and stored to EEPROM by store_eeprom.

Return -EINVAL for values outside [0, 2^resolution - 1].

Fixes bf394cc80369 ("iio: dac: adding support for Microchip MCP47FEB02")

Good catch but given the fix will go in the same cycle as the driver I've dropped the table tag.

This is more about how I choose to queue this up than anything could know. I might have held it for next merge window in which case it would have wanted the stable tag.

Applied to the fixes-togreg branch of iio.git. I've just rebased that to reflect the char-misc pull going into Linus' tree (which was needed to get the driver for this patch). I'll rebase again on rc1 once available.

Given I'll be rebasing anyway, extra tags welcome (and I didn't hold off on applying as I might have done if aiming for no rebasing). Ariana, please take a look at this one.

Thanks,

Jonathan

Quoted 31 lines

---
Found by LLM-assisted code inspection, reviewed and verified by hand. Build tested with W=1 (=m and =y) only; no hardware was available for runtime testing.

v2:
- Use GENMASK() for the upper bound so it is safe up to 32 bits (Andy)
- Drop the Assisted-by tag, removed from the docs in 1e035297ffda (Joshua)
- Move the testing note below the --- (Joshua)

v1: https://lore.kernel.org/all/[email protected]/

---
 drivers/iio/dac/mcp47feb02-core.c | 3 +++
 1 file changed, 3 insertions(+)
drivers/iio/dac/mcp47feb02-core.c +3 -0
index 88bffbab0854..b5a2ac4a2e67 100644
@@ -696,6 +696,9 @@ static int mcp47feb02_write_raw(struct iio_dev *indio_dev, struct iio_chan_spec
 
 	switch (mask) {
 	case IIO_CHAN_INFO_RAW:
+		if (val < 0 || val > GENMASK(data->chip_features->resolution - 1, 0))
+			return -EINVAL;
+
 		ret = regmap_write(data->regmap, REG_ADDR(ch->address), val);
 		if (ret)
 			return ret;
#3 lore raw

Hi Jonathan,

I tested this patch on both I2C and SPI parts and found no issues. Thank you David for your contribution.

Best regards,
Ariana

Quoted 67 lines

Good catch but given the fix will go in the same cycle as the driver I've dropped the table tag.

This is more about how I choose to queue this up than anything could know.  I might have held it for next merge window in which case it would have wanted the stable tag.

Applied to the fixes-togreg branch of iio.git.  I've just rebased that
to reflect the char-misc pull going into Linus' tree (which was needed
to get the driver for this patch). I'll rebase again on rc1 once available.

Given I'll be rebasing anyway, extra tags welcome (and I didn't hold off on applying as I might have done if aiming for no rebasing). Ariana,
please take a look at this one.

Thanks,

Jonathan

Quoted 40 lines

---
Found by LLM-assisted code inspection, reviewed and verified by hand.
Build tested with W=1 (=m and =y) only; no hardware was available for
runtime testing.

v2:
- Use GENMASK() for the upper bound so it is safe up to 32 bits (Andy)
- Drop the Assisted-by tag, removed from the docs in 1e035297ffda (Joshua)
- Move the testing note below the --- (Joshua)

v1:
https://lore.kernel.org/all/[email protected]/
---
 drivers/iio/dac/mcp47feb02-core.c | 3 +++

 1 file changed, 3 insertions(+)
drivers/iio/dac/mcp47feb02-core.c +0 -0
index 88bffbab0854..b5a2ac4a2e67 100644
@@ -696,6 +696,9 @@ static int mcp47feb02_write_raw(struct iio_dev
 *indio_dev, struct iio_chan_spec
 
       switch (mask) {

      case IIO_CHAN_INFO_RAW:
+             if (val < 0 || val > GENMASK(data->chip_features-

Quoted 1 line

resolution - 1, 0))

+                     return -EINVAL;
+
              ret = regmap_write(data->regmap, REG_ADDR(ch-

Quoted 1 line

address), val);

              if (ret)
                      return ret;