linux/drivers/dma
Anatolij Gustschin a646bd7f08 dma: ipu_idmac: do not lose valid received data in the irq handler
Currently when two or more buffers are queued by the camera driver
and so the double buffering is enabled in the idmac, we lose one
frame comming from CSI since the reporting of arrival of the first
frame is deferred by the DMAIC_7_EOF interrupt handler and reporting
of the arrival of the last frame is not done at all. So when requesting
N frames from the image sensor we actually receive N - 1 frames in
user space.

The reason for this behaviour is that the DMAIC_7_EOF interrupt
handler misleadingly assumes that the CUR_BUF flag is pointing to the
buffer used by the IDMAC. Actually it is not the case since the
CUR_BUF flag will be flipped by the FSU when the FSU is sending the
<TASK>_NEW_FRM_RDY signal when new frame data is delivered by the CSI.
When sending this singal, FSU updates the DMA_CUR_BUF and the
DMA_BUFx_RDY flags: the DMA_CUR_BUF is flipped, the DMA_BUFx_RDY
is cleared, indicating that the frame data is beeing written by
the IDMAC to the pointed buffer. DMA_BUFx_RDY is supposed to be
set to the ready state again by the MCU, when it has handled the
received data. DMAIC_7_CUR_BUF flag won't be flipped here by the
IPU, so waiting for this event in the EOF interrupt handler is wrong.
Actually there is no spurious interrupt as described in the comments,
this is the valid DMAIC_7_EOF interrupt indicating reception of the
frame from CSI.

The patch removes code that waits for flipping of the DMAIC_7_CUR_BUF
flag in the DMAIC_7_EOF interrupt handler. As the comment in the
current code denotes, this waiting doesn't help anyway. As a result
of this removal the reporting of the first arrived frame is not
deferred to the time of arrival of the next frame and the drivers
software flag 'ichan->active_buffer' is in sync with DMAIC_7_CUR_BUF
flag, so the reception of all requested frames works.

This has been verified on the hardware which is triggering the
image sensor by the programmable state machine, allowing to
obtain exact number of frames. On this hardware we do not tolerate
losing frames.

This patch also removes resetting the DMA_BUFx_RDY flags of
all channels in ipu_disable_channel() since transfers on other
DMA channels might be triggered by other running tasks and the
buffers should always be ready for data sending or reception.

Signed-off-by: Anatolij Gustschin <agust@denx.de>
Reviewed-by: Guennadi Liakhovetski <g.liakhovetski@gmx.de>
Tested-by: Guennadi Liakhovetski <g.liakhovetski@gmx.de>
Signed-off-by: Dan Williams <dan.j.williams@intel.com>
2011-02-14 02:28:16 -08:00
..
ioat drivers/dma/ioat: Use the ccflag-y instead of EXTRA_CFLAGS 2010-12-04 15:03:06 -08:00
ipu dma: ipu_idmac: do not lose valid received data in the irq handler 2011-02-14 02:28:16 -08:00
ppc4xx drivers/dma/ppc4xx: Use printf extension %pR for struct resource 2010-12-04 15:03:40 -08:00
amba-pl08x.c DMA: PL08x: fix channel pausing to timeout rather than lockup 2011-01-30 22:03:47 -08:00
at_hdmac_regs.h at_hdmac: implement a private tx_list 2009-09-08 17:53:03 -07:00
at_hdmac.c Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/djbw/async_tx 2011-01-17 10:54:41 -08:00
coh901318_lli.c include cleanup: Update gfp.h and slab.h includes to prepare for breaking implicit slab.h inclusion from percpu.h 2010-03-30 22:02:32 +09:00
coh901318_lli.h tree-wide: Assorted spelling fixes 2010-02-09 11:13:56 +01:00
coh901318.c Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/djbw/async_tx 2010-10-27 19:04:36 -07:00
dmaengine.c async_tx: make async_tx channel switching opt-in 2010-10-07 17:08:32 -07:00
dmatest.c dma: dmatest: fix potential sign bug 2010-08-04 14:27:47 -07:00
dw_dmac_regs.h dw_dmac: implement a private tx_list 2009-09-08 17:53:02 -07:00
dw_dmac.c DMAENGINE: extend the control command to include an arg 2010-05-17 16:30:42 -07:00
fsldma.c Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/djbw/async_tx 2011-01-17 10:54:41 -08:00
fsldma.h fsldma: fix issue of slow dma 2010-12-13 14:05:27 -08:00
imx-dma.c dma: imx-dma: fix imxdma_probe error path 2010-12-03 01:39:03 -08:00
imx-sdma.c dmaengine: imx-sdma: fix inconsistent naming in sdma_assign_cookie() 2011-01-29 22:35:10 -08:00
intel_mid_dma_regs.h intel_mid_dma: change the slave interface 2010-10-07 15:03:44 -07:00
intel_mid_dma.c Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/djbw/async_tx 2011-01-17 10:54:41 -08:00
iop-adma.c Update CONFIG_MD_RAID6_PQ to CONFIG_RAID6_PQ in drivers/dma/iop-adma.c 2011-01-14 17:58:12 -08:00
iovlock.c include cleanup: Update gfp.h and slab.h includes to prepare for breaking implicit slab.h inclusion from percpu.h 2010-03-30 22:02:32 +09:00
Kconfig Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/djbw/async_tx 2011-01-17 10:54:41 -08:00
Makefile drivers/dma/: Use the ccflag-y instead of EXTRA_CFLAGS 2010-12-03 01:51:43 -08:00
mpc512x_dma.c powerpc/512x: try to free dma descriptors in case of allocation failure 2010-12-29 22:29:36 -07:00
mv_xor.c mv_xor: fix race in tasklet function 2011-01-03 01:39:26 -08:00
mv_xor.h mv_xor: implement a private tx_list 2009-09-08 17:53:03 -07:00
pch_dma.c pch_dma: support new device ML7213 IOH 2011-01-14 16:24:53 -08:00
pl330.c DMA: PL330: Add dma api driver 2010-05-23 20:28:19 -07:00
shdma.c dma: shdma: don't register the global die notifier multiple times 2011-01-07 11:03:26 +09:00
shdma.h dma: shdma: NMI support. 2010-12-17 19:16:10 +09:00
ste_dma40_ll.c dmaengine: dma40: Add support to split up large elements 2011-01-04 17:20:43 -08:00
ste_dma40_ll.h dmaengine: dma40: Add support to split up large elements 2011-01-04 17:20:43 -08:00
ste_dma40.c dmaengine: dma40: Add support to split up large elements 2011-01-04 17:20:43 -08:00
timb_dma.c dma/timberdale: simplify conditional 2010-10-19 15:20:11 -07:00
txx9dmac.c Merge branch 'next' of git://git.kernel.org/pub/scm/linux/kernel/git/djbw/async_tx 2010-05-21 17:05:46 -07:00
txx9dmac.h txx9dmac: implement a private tx_list 2009-09-08 17:53:03 -07:00