iio: potentiometer: add driver for Microchip MCP413X/414X/415X/416X/423X/424X/425X/426X
Subsystems (2)
PATCH v4 1/1 iio: potentiometer: add driver for Microchip MCP413X/414X/415X/416X/423X/424X/425X/426X
The following functionalities are supported:
- write, read from volatile memory
Datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/22060b.pdf
---
Changes since v3:
- Added 'potentiometer' to subject
- Replaced mcp4131_exec with spi_write and mcp4131_read
- Narrowed mutex locking and unlocking places
Changes since v2:
- Removed unnecessary parentheses in MCP4131_WIPER_SHIFT macro
- Replaced the rx and tx SPI buffers with one buf that is ____cacheline_aligned
- Changed mutex locking position
- Replaced the devid with pointer to model configuration
- Removed positive ("Registered" & "Unregistered") dev_info prints
- Removed the mcp4131_remove callback
Changes since v1:
- One line summary changed
- Fixed module name and OF compatible
- Based code on Peter Rosin's code from mcp4531.c
- No additional sysfs attributes
- Deleted not used devid struct memeber
- Changed mcp4131_exec function arguments:
- write value is now u16
- no need to pass return buffer array - rx array from mcp4131_data is used
- Added missing new line characters to dev_info
--- .../bindings/iio/potentiometer/mcp4131.txt | 84 ++++ drivers/iio/potentiometer/Kconfig | 18 + drivers/iio/potentiometer/Makefile | 1 + drivers/iio/potentiometer/mcp4131.c | 492 +++++++++++++++++++++ 4 files changed, 595 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/potentiometer/mcp4131.txt create mode 100644 drivers/iio/potentiometer/mcp4131.c
Documentation/devicetree/bindings/iio/potentiometer/mcp4131.txt new file +84 -0
@@ -0,0 +1,84 @@ +* Microchip MCP413X/414X/415X/416X/423X/424X/425X/426X Digital Potentiometer + driver + +The node for this driver must be a child node of a SPI controller, hence +all mandatory properties described in + + Documentation/devicetree/bindings/spi/spi-bus.txt + +must be specified. + +Required properties: + - compatible: Must be one of the following, depending on the + model: + "microchip,mcp4131-502" + "microchip,mcp4131-103" + "microchip,mcp4131-503" + "microchip,mcp4131-104" + "microchip,mcp4132-502" + "microchip,mcp4132-103" + "microchip,mcp4132-503" + "microchip,mcp4132-104" + "microchip,mcp4141-502" + "microchip,mcp4141-103" + "microchip,mcp4141-503" + "microchip,mcp4141-104" + "microchip,mcp4142-502" + "microchip,mcp4142-103" + "microchip,mcp4142-503" + "microchip,mcp4142-104" + "microchip,mcp4151-502" + "microchip,mcp4151-103" + "microchip,mcp4151-503" + "microchip,mcp4151-104" + "microchip,mcp4152-502" + "microchip,mcp4152-103" + "microchip,mcp4152-503" + "microchip,mcp4152-104" + "microchip,mcp4161-502" + "microchip,mcp4161-103" + "microchip,mcp4161-503" + "microchip,mcp4161-104" + "microchip,mcp4162-502" + "microchip,mcp4162-103" + "microchip,mcp4162-503" + "microchip,mcp4162-104" + "microchip,mcp4231-502" + "microchip,mcp4231-103" + "microchip,mcp4231-503" + "microchip,mcp4231-104" + "microchip,mcp4232-502" + "microchip,mcp4232-103" + "microchip,mcp4232-503" + "microchip,mcp4232-104" + "microchip,mcp4241-502" + "microchip,mcp4241-103" + "microchip,mcp4241-503" + "microchip,mcp4241-104" + "microchip,mcp4242-502" + "microchip,mcp4242-103" + "microchip,mcp4242-503" + "microchip,mcp4242-104" + "microchip,mcp4251-502" + "microchip,mcp4251-103" + "microchip,mcp4251-503" + "microchip,mcp4251-104" + "microchip,mcp4252-502" + "microchip,mcp4252-103" + "microchip,mcp4252-503" + "microchip,mcp4252-104" + "microchip,mcp4261-502" + "microchip,mcp4261-103" + "microchip,mcp4261-503" + "microchip,mcp4261-104" + "microchip,mcp4262-502" + "microchip,mcp4262-103" + "microchip,mcp4262-503" + "microchip,mcp4262-104" + +Example: +mcp4131: mcp4131@0 { + compatible = "mcp4131-502"; + reg = <0>; + spi-max-frequency = <500000>; +};
drivers/iio/potentiometer/Kconfig +18 -0
@@ -5,6 +5,24 @@ menu "Digital potentiometers" +config MCP4131 + tristate "Microchip MCP413X/414X/415X/416X/423X/424X/425X/426X Digital Potentiometer driver" + depends on SPI + help + Say yes here to build support for the Microchip + MCP4131, MCP4132, + MCP4141, MCP4142, + MCP4151, MCP4152, + MCP4161, MCP4162, + MCP4231, MCP4232, + MCP4241, MCP4242, + MCP4251, MCP4252, + MCP4261, MCP4262, + digital potentiomenter chips. + + To compile this driver as a module, choose M here: the + module will be called mcp4131. + config MCP4531 tristate "Microchip MCP45xx/MCP46xx Digital Potentiometer driver" depends on I2C
drivers/iio/potentiometer/Makefile +1 -0
@@ -3,4 +3,5 @@ # # When adding new entries keep the list in alphabetical order +obj-$(CONFIG_MCP4131) += mcp4131.o obj-$(CONFIG_MCP4531) += mcp4531.o
drivers/iio/potentiometer/mcp4131.c new file +492 -0
492 lines not on this page · raw message
Signature · 1 line
2.7.4
Hi Slawomir,
drivers/iio/potentiometer/mcp4131.c line 41
Quoted 13 lines · Slawomir Stepien
The following functionalities are supported:
- write, read from volatile memoryDatasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/22060b.pdf
Signed-off-by Slawomir Stepien <[email protected]>---
drivers/iio/potentiometer/mcp4131.c new file +5
-0+#include <linux/module.h> +#include <linux/spi/spi.h> +#include <linux/err.h> + +#include <linux/iio/iio.h>
Give that you use that you have a some OF stuff in your driver you should also include <linux/of.h>. Same goes for <linux/mutex.h>. I am sure this builds fine without those includes, but you should explicitly include stuff that you use.
While you're at it you could also put the includes in alphabetic order.
Quoted 14 lines
drivers/iio/potentiometer/mcp4131.c new file +14
-0+static int mcp4131_read_raw (struct iio_dev *indio_dev, +struct iio_chan_spec const *chan, +int *val,int *val2,long mask) +{ +int err; +struct mcp4131_data *data =iio_priv (indio_dev); +int address = chan->channel; + +switch (mask) { +case IIO_CHAN_INFO_RAW : +mutex_lock (&data->lock); + + data->buf[0 ] = (address <<MCP4131_WIPER_SHIFT ) |MCP4131_READ ; + data->buf[1 ] =0 ;
drivers/iio/potentiometer/mcp4131.c line 185
Quoted 10 lines
drivers/iio/potentiometer/mcp4131.c new file +10
-0+ + err =mcp4131_read (data->spi, data->buf,2 ); +if (err) { +mutex_unlock (&data->lock); +return err; + } + +/* Error, bad address/command combination */ +if (!MCP4131_CMDERR (data->buf)) +return -EIO ;
Missing mutex unlock here.
Quoted 37 lines
drivers/iio/potentiometer/mcp4131.c new file +37
-0+ + *val =MCP4131_RAW (data->buf); +mutex_unlock (&data->lock); + +return IIO_VAL_INT ; + +case IIO_CHAN_INFO_SCALE : + *val =1000 * data->cfg->kohms; + *val2 = data->cfg->max_pos; +return IIO_VAL_FRACTIONAL ; + } + +return -EINVAL ; +} + +static int mcp4131_write_raw (struct iio_dev *indio_dev, +struct iio_chan_spec const *chan, +int val,int val2,long mask) +{ +int err; +struct mcp4131_data *data =iio_priv (indio_dev); +int address = chan->channel <<MCP4131_WIPER_SHIFT ; + +switch (mask) { +case IIO_CHAN_INFO_RAW : +if (val > data->cfg->max_pos || val <0 ) +return -EINVAL ; +break ; + +default : +return -EINVAL ; + } + +mutex_lock (&data->lock); + + data->buf[0 ] = address <<MCP4131_WIPER_SHIFT ; + data->buf[0 ] |=MCP4131_WRITE | (val >>8 );
drivers/iio/potentiometer/mcp4131.c line 232
Quoted 10 lines
drivers/iio/potentiometer/mcp4131.c new file +10
-0+ data->buf[1 ] = val &0xFF ;/* 8 bits here */ + + err =spi_write (data->spi, data->buf,2 ); +if (err) { +mutex_unlock (&data->lock); +return err; + } +mutex_unlock (&data->lock); + +return 0 ;
This last part could be written as:
err = spi_write(data->spi, data->buf, 2);
mutex_unlock(&data->lock);
return err;
Other than the things I noted driver looks good to me.
regards,
Joachim Eastwood
Quoted 11 lines · Joachim Eastwood
Hi Slawomir,
Quoted 7 lines · Slawomir Stepien
The following functionalities are supported:
- write, read from volatile memoryDatasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/22060b.pdf
Signed-off-by Slawomir Stepien <[email protected]>---
Quoted 10 lines
drivers/iio/potentiometer/mcp4131.c line 41
Quoted 5 lines
drivers/iio/potentiometer/mcp4131.c new file +5
-0+#include <linux/module.h> +#include <linux/spi/spi.h> +#include <linux/err.h> + +#include <linux/iio/iio.h> Give that you use that you have a some OF stuff in your driver you should also include <
linux/of.h>. Same goes for <linux/mutex.h>. I am sure this builds fine without those includes, but you should explicitly include stuff that you use.
Oh yes that's true.
Quoted 1 line
While you're at it you could also put the includes in alphabetic order.
OK
Quoted 18 lines
Quoted 18 lines
drivers/iio/potentiometer/mcp4131.c new file +18
-0+static int mcp4131_read_raw (struct iio_dev *indio_dev, +struct iio_chan_spec const *chan, +int *val,int *val2,long mask) +{ +int err; +struct mcp4131_data *data =iio_priv (indio_dev); +int address = chan->channel; + +switch (mask) { +case IIO_CHAN_INFO_RAW : +mutex_lock (&data->lock); + + data->buf[0 ] = (address <<MCP4131_WIPER_SHIFT ) |MCP4131_READ ; + data->buf[1 ] =0 ; + + err =mcp4131_read (data->spi, data->buf,2 ); +if (err) { +mutex_unlock (&data->lock);
Quoted 8 lines
drivers/iio/potentiometer/mcp4131.c line 185
Quoted 6 lines
drivers/iio/potentiometer/mcp4131.c new file +6
-0+return err; + } + +/* Error, bad address/command combination */ +if (!MCP4131_CMDERR (data->buf)) +return -EIO ;Missing mutex unlock here.
Oh ;) I'll fix that.
Quoted 52 lines
Quoted 37 lines
drivers/iio/potentiometer/mcp4131.c new file +37
-0+ + *val =MCP4131_RAW (data->buf); +mutex_unlock (&data->lock); + +return IIO_VAL_INT ; + +case IIO_CHAN_INFO_SCALE : + *val =1000 * data->cfg->kohms; + *val2 = data->cfg->max_pos; +return IIO_VAL_FRACTIONAL ; + } + +return -EINVAL ; +} + +static int mcp4131_write_raw (struct iio_dev *indio_dev, +struct iio_chan_spec const *chan, +int val,int val2,long mask) +{ +int err; +struct mcp4131_data *data =iio_priv (indio_dev); +int address = chan->channel <<MCP4131_WIPER_SHIFT ; + +switch (mask) { +case IIO_CHAN_INFO_RAW : +if (val > data->cfg->max_pos || val <0 ) +return -EINVAL ; +break ; + +default : +return -EINVAL ; + } + +mutex_lock (&data->lock); + + data->buf[0 ] = address <<MCP4131_WIPER_SHIFT ; + data->buf[0 ] |=MCP4131_WRITE | (val >>8 );drivers/iio/potentiometer/mcp4131.c line 232
Quoted 10 lines
drivers/iio/potentiometer/mcp4131.c new file +10
-0+ data->buf[1 ] = val &0xFF ;/* 8 bits here */ + + err =spi_write (data->spi, data->buf,2 ); +if (err) { +mutex_unlock (&data->lock); +return err; + } +mutex_unlock (&data->lock); + +return 0 ;This last part could be written as:
err =spi_write(data->spi, data->buf, 2);
mutex_unlock(&data->lock);
Quoted 1 line
return err;
OK
Quoted 5 lines
Other than the things I noted driver looks good to me.
regards,
Joachim Eastwood
Signature · 1 line
Slawomir Stepien