diff options
author | Hans Verkuil <hverkuil@xs4all.nl> | 2007-05-19 14:07:16 -0300 |
---|---|---|
committer | Mauro Carvalho Chehab <mchehab@infradead.org> | 2007-06-08 08:21:13 -0300 |
commit | dc02d50a6d71cba2b2edb78377af5a5965879a49 (patch) | |
tree | 199528db7b95dacd395004119614567b57725787 /drivers/media/video/ivtv/ivtv-queue.h | |
parent | ffeb9ec72e18e16d0b0835d959cdf01650758638 (diff) | |
download | lwn-dc02d50a6d71cba2b2edb78377af5a5965879a49.tar.gz lwn-dc02d50a6d71cba2b2edb78377af5a5965879a49.zip |
V4L/DVB (5675): Move big PIO accesses from the interrupt handler to a workhandler
Sliced VBI transfers use PIO instead of DMA. This was done inside the
interrupt handler, but since PIO accesses are very slow this meant that
a lot of time was spent inside the interrupt handler. All PIO copies are
now moved to a workqueue. This should fix various issues with missing time
ticks and remote key hits.
Signed-off-by: Hans Verkuil <hverkuil@xs4all.nl>
Signed-off-by: Mauro Carvalho Chehab <mchehab@infradead.org>
Diffstat (limited to 'drivers/media/video/ivtv/ivtv-queue.h')
-rw-r--r-- | drivers/media/video/ivtv/ivtv-queue.h | 39 |
1 files changed, 33 insertions, 6 deletions
diff --git a/drivers/media/video/ivtv/ivtv-queue.h b/drivers/media/video/ivtv/ivtv-queue.h index 903edd4b4381..2ed8d548255d 100644 --- a/drivers/media/video/ivtv/ivtv-queue.h +++ b/drivers/media/video/ivtv/ivtv-queue.h @@ -20,18 +20,43 @@ */ #define IVTV_DMA_UNMAPPED ((u32) -1) +#define SLICED_VBI_PIO 1 /* ivtv_buffer utility functions */ + +static inline int ivtv_might_use_pio(struct ivtv_stream *s) +{ + return s->dma == PCI_DMA_NONE || (SLICED_VBI_PIO && s->type == IVTV_ENC_STREAM_TYPE_VBI); +} + +static inline int ivtv_use_pio(struct ivtv_stream *s) +{ + struct ivtv *itv = s->itv; + + return s->dma == PCI_DMA_NONE || + (SLICED_VBI_PIO && s->type == IVTV_ENC_STREAM_TYPE_VBI && itv->vbi.sliced_in->service_set); +} + +static inline int ivtv_might_use_dma(struct ivtv_stream *s) +{ + return s->dma != PCI_DMA_NONE; +} + +static inline int ivtv_use_dma(struct ivtv_stream *s) +{ + return !ivtv_use_pio(s); +} + static inline void ivtv_buf_sync_for_cpu(struct ivtv_stream *s, struct ivtv_buffer *buf) { - if (s->dma != PCI_DMA_NONE) + if (ivtv_use_dma(s)) pci_dma_sync_single_for_cpu(s->itv->dev, buf->dma_handle, s->buf_size + 256, s->dma); } static inline void ivtv_buf_sync_for_device(struct ivtv_stream *s, struct ivtv_buffer *buf) { - if (s->dma != PCI_DMA_NONE) + if (ivtv_use_dma(s)) pci_dma_sync_single_for_device(s->itv->dev, buf->dma_handle, s->buf_size + 256, s->dma); } @@ -53,12 +78,14 @@ void ivtv_stream_free(struct ivtv_stream *s); static inline void ivtv_stream_sync_for_cpu(struct ivtv_stream *s) { - pci_dma_sync_single_for_cpu(s->itv->dev, s->SG_handle, - sizeof(struct ivtv_SG_element) * s->buffers, PCI_DMA_TODEVICE); + if (ivtv_use_dma(s)) + pci_dma_sync_single_for_cpu(s->itv->dev, s->SG_handle, + sizeof(struct ivtv_SG_element) * s->buffers, PCI_DMA_TODEVICE); } static inline void ivtv_stream_sync_for_device(struct ivtv_stream *s) { - pci_dma_sync_single_for_device(s->itv->dev, s->SG_handle, - sizeof(struct ivtv_SG_element) * s->buffers, PCI_DMA_TODEVICE); + if (ivtv_use_dma(s)) + pci_dma_sync_single_for_device(s->itv->dev, s->SG_handle, + sizeof(struct ivtv_SG_element) * s->buffers, PCI_DMA_TODEVICE); } |