aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/iio/common
diff options
context:
space:
mode:
authorLinus Walleij <linus.walleij@linaro.org>2016-04-14 04:45:21 -0400
committerJonathan Cameron <jic23@kernel.org>2016-04-19 14:58:13 -0400
commit0e6f6871a1591f4bb0971809c45bc91a991f1967 (patch)
tree45aa87a59f586c7aff129809ca3cc017b4d36895 /drivers/iio/common
parent97865fe41322d83dac4373fe0a0de5b1a1b318c5 (diff)
iio: st_sensors: support open drain mode
Some types of ST Sensors can be connected to the same IRQ line as other peripherals using open drain. Add a device tree binding and a sensor data property to flip the right bit in the interrupt control register to enable open drain mode on the INT line. If the line is set to be open drain, also tag on IRQF_SHARED to the IRQ flags when requesting the interrupt, as the whole point of using open drain interrupt lines is to share them with more than one peripheral (wire-or). Cc: devicetree@vger.kernel.org Cc: Giuseppe Barba <giuseppe.barba@st.com> Cc: Denis Ciocca <denis.ciocca@st.com> Acked-by: Rob Herring <rob@kernel.org> Signed-off-by: Linus Walleij <linus.walleij@linaro.org> Signed-off-by: Jonathan Cameron <jic23@kernel.org>
Diffstat (limited to 'drivers/iio/common')
-rw-r--r--drivers/iio/common/st_sensors/st_sensors_core.c20
-rw-r--r--drivers/iio/common/st_sensors/st_sensors_trigger.c13
2 files changed, 33 insertions, 0 deletions
diff --git a/drivers/iio/common/st_sensors/st_sensors_core.c b/drivers/iio/common/st_sensors/st_sensors_core.c
index f5a2d445d0c0..dffe00692169 100644
--- a/drivers/iio/common/st_sensors/st_sensors_core.c
+++ b/drivers/iio/common/st_sensors/st_sensors_core.c
@@ -301,6 +301,14 @@ static int st_sensors_set_drdy_int_pin(struct iio_dev *indio_dev,
301 return -EINVAL; 301 return -EINVAL;
302 } 302 }
303 303
304 if (pdata->open_drain) {
305 if (!sdata->sensor_settings->drdy_irq.addr_od)
306 dev_err(&indio_dev->dev,
307 "open drain requested but unsupported.\n");
308 else
309 sdata->int_pin_open_drain = true;
310 }
311
304 return 0; 312 return 0;
305} 313}
306 314
@@ -321,6 +329,8 @@ static struct st_sensors_platform_data *st_sensors_of_probe(struct device *dev,
321 else 329 else
322 pdata->drdy_int_pin = defdata ? defdata->drdy_int_pin : 0; 330 pdata->drdy_int_pin = defdata ? defdata->drdy_int_pin : 0;
323 331
332 pdata->open_drain = of_property_read_bool(np, "drive-open-drain");
333
324 return pdata; 334 return pdata;
325} 335}
326#else 336#else
@@ -374,6 +384,16 @@ int st_sensors_init_sensor(struct iio_dev *indio_dev,
374 return err; 384 return err;
375 } 385 }
376 386
387 if (sdata->int_pin_open_drain) {
388 dev_info(&indio_dev->dev,
389 "set interrupt line to open drain mode\n");
390 err = st_sensors_write_data_with_mask(indio_dev,
391 sdata->sensor_settings->drdy_irq.addr_od,
392 sdata->sensor_settings->drdy_irq.mask_od, 1);
393 if (err < 0)
394 return err;
395 }
396
377 err = st_sensors_set_axis_enable(indio_dev, ST_SENSORS_ENABLE_ALL_AXIS); 397 err = st_sensors_set_axis_enable(indio_dev, ST_SENSORS_ENABLE_ALL_AXIS);
378 398
379 return err; 399 return err;
diff --git a/drivers/iio/common/st_sensors/st_sensors_trigger.c b/drivers/iio/common/st_sensors/st_sensors_trigger.c
index 6a8c98327945..da72279fcf99 100644
--- a/drivers/iio/common/st_sensors/st_sensors_trigger.c
+++ b/drivers/iio/common/st_sensors/st_sensors_trigger.c
@@ -64,6 +64,19 @@ int st_sensors_allocate_trigger(struct iio_dev *indio_dev,
64 "rising edge\n", irq_trig); 64 "rising edge\n", irq_trig);
65 irq_trig = IRQF_TRIGGER_RISING; 65 irq_trig = IRQF_TRIGGER_RISING;
66 } 66 }
67
68 /*
69 * If the interrupt pin is Open Drain, by definition this
70 * means that the interrupt line may be shared with other
71 * peripherals. But to do this we also need to have a status
72 * register and mask to figure out if this sensor was firing
73 * the IRQ or not, so we can tell the interrupt handle that
74 * it was "our" interrupt.
75 */
76 if (sdata->int_pin_open_drain &&
77 sdata->sensor_settings->drdy_irq.addr_stat_drdy)
78 irq_trig |= IRQF_SHARED;
79
67 err = request_threaded_irq(irq, 80 err = request_threaded_irq(irq,
68 iio_trigger_generic_data_rdy_poll, 81 iio_trigger_generic_data_rdy_poll,
69 NULL, 82 NULL,