iio: pressure: rohm-bm1390: harden trigger handler against transient errors

bm1390_trigger_handler() returns from three error paths without calling
iio_trigger_notify_done(). The success path at the end does, so on a
transient regmap or read failure the trigger's use_count is never
decremented and iio_trigger_poll_chained() drops subsequent dispatches
until the trigger is reattached.

This is not a fix for a reported bug, only hardening against hardware
or bus glitches; if a glitch is persistent the device is wedged and
needs an unbind anyway, which is left to the user.

Split the function so the inner helper returns bool with the data-read
outcome, and the outer IRQ handler calls iio_trigger_notify_done()
once and reports the result via IRQ_RETVAL().

Signed-off-by: Stepan Ionichev <sozdayvek@gmail.com>
Reviewed-by: Matti Vaittinen <mazziesaccount@gmail.com>
Signed-off-by: Jonathan Cameron <jic23@kernel.org>
This commit is contained in:
Stepan Ionichev 2026-05-18 23:11:10 +05:00 committed by Jonathan Cameron
parent 331ca76fe5
commit d07bf43d17

View File

@ -621,17 +621,15 @@ static const struct iio_buffer_setup_ops bm1390_buffer_ops = {
.predisable = bm1390_buffer_predisable,
};
static irqreturn_t bm1390_trigger_handler(int irq, void *p)
static bool bm1390_handle_trigger(struct iio_dev *idev)
{
struct iio_poll_func *pf = p;
struct iio_dev *idev = pf->indio_dev;
struct bm1390_data *data = iio_priv(idev);
int ret, status;
/* DRDY is acked by reading status reg */
ret = regmap_read(data->regmap, BM1390_REG_STATUS, &status);
if (ret || !status)
return IRQ_NONE;
return false;
dev_dbg(data->dev, "DRDY trig status 0x%x\n", status);
@ -639,7 +637,7 @@ static irqreturn_t bm1390_trigger_handler(int irq, void *p)
ret = bm1390_pressure_read(data, &data->buf.pressure);
if (ret) {
dev_warn(data->dev, "sample read failed %d\n", ret);
return IRQ_NONE;
return false;
}
}
@ -648,15 +646,26 @@ static irqreturn_t bm1390_trigger_handler(int irq, void *p)
&data->buf.temp, sizeof(data->buf.temp));
if (ret) {
dev_warn(data->dev, "temp read failed %d\n", ret);
return IRQ_HANDLED;
return true;
}
}
iio_push_to_buffers_with_ts(idev, &data->buf, sizeof(data->buf),
data->timestamp);
return true;
}
static irqreturn_t bm1390_trigger_handler(int irq, void *p)
{
struct iio_poll_func *pf = p;
struct iio_dev *idev = pf->indio_dev;
bool result;
result = bm1390_handle_trigger(idev);
iio_trigger_notify_done(idev->trig);
return IRQ_HANDLED;
return IRQ_RETVAL(result);
}
/* Get timestamps and wake the thread if we need to read data */