iio: adc: stm32-adc: fix a regression when using dma and irq
authorOlivier Moysan <olivier.moysan@st.com>
Wed, 21 Oct 2020 08:53:13 +0000 (10:53 +0200)
committerJonathan Cameron <Jonathan.Cameron@huawei.com>
Sun, 1 Nov 2020 17:14:06 +0000 (17:14 +0000)
commit695e2f5c289bb7f8b85351dcfa35fa236e0200a4
treea71095e7fabe20021f8482ca557819a985766b67
parent15207a92e019803d62687455d8aa2ff9eb3dc82c
iio: adc: stm32-adc: fix a regression when using dma and irq

Since overrun interrupt support has been added, there's a regression when
two ADCs are used at the same time, with:
- an ADC configured to use IRQs. EOCIE bit is set. The handler is normally
  called in this case.
- an ADC configured to use DMA. EOCIE bit isn't set. EOC triggers the DMA
  request. It's then automatically cleared by DMA read. But the handler
  gets called due to status bit is temporarily set (IRQ triggered by the
  other ADC).

This is a regression as similar issue had been fixed earlier by
commit dcb10920179a ("iio: adc: stm32-adc:
fix a race when using several adcs with dma and irq").
Issue is that stm32_adc_eoc_enabled() returns non-zero value (always)
since OVR bit has been added and enabled for both DMA and IRQ case.

Remove OVR mask in IER register, and rely only on CSR status for overrun.
To avoid subsequent calls to interrupt routine on overrun, CSR OVR bit has
to be cleared. CSR OVR bit cannot be cleared directly by software.
To do this ADC must be stopped first, and OVR bit in ADC ISR has
to be cleared.
Also add a check in ADC IRQ handler to report spurious IRQs.

Fixes: cc06e67d8fa5 ("iio: adc: stm32-adc: Add check on overrun interrupt")
Signed-off-by: Olivier Moysan <olivier.moysan@st.com>
Signed-off-by: Fabrice Gasnier <fabrice.gasnier@st.com>
Cc: <Stable@vger.kernel.org>
Link: https://lore.kernel.org/r/20201021085313.5335-1-olivier.moysan@st.com
Signed-off-by: Jonathan Cameron <Jonathan.Cameron@huawei.com>
drivers/iio/adc/stm32-adc-core.c
drivers/iio/adc/stm32-adc.c