]> git.baikalelectronics.ru Git - kernel.git/commit
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)
commit18142dcb876a0bc975f6dd44fcdff39506fe64b6
treea71095e7fabe20021f8482ca557819a985766b67
parentc069e8aa113fcf1d24a2f5a71776c21874143475
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 dcc9a0df0e8e ("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: fd8bcd067df5 ("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