From f7d005c33c109ef034c9480334d3d25d91aa2d6d Mon Sep 17 00:00:00 2001 From: H Hartley Sweeten Date: Thu, 21 Apr 2016 12:04:44 -0700 Subject: [PATCH] staging: comedi: mite: make mite_ack_linkc() handle mite_sync_dma() The mite dma is always synced on a LINKC status. Some of the mite users sync the dma regadless of the status. Add a 'sync' parameter to mite_ack_linkc() to force a dma sync. Then do the dma sync as needed. Signed-off-by: H Hartley Sweeten Reviewed-by: Ian Abbott Signed-off-by: Greg Kroah-Hartman --- drivers/staging/comedi/drivers/mite.c | 10 ++++++-- drivers/staging/comedi/drivers/mite.h | 4 ++-- .../staging/comedi/drivers/ni_mio_common.c | 23 +++++-------------- drivers/staging/comedi/drivers/ni_pcidio.c | 9 ++------ drivers/staging/comedi/drivers/ni_tiocmd.c | 6 ++--- 5 files changed, 20 insertions(+), 32 deletions(-) diff --git a/drivers/staging/comedi/drivers/mite.c b/drivers/staging/comedi/drivers/mite.c index d97059217825..b8cf89887006 100644 --- a/drivers/staging/comedi/drivers/mite.c +++ b/drivers/staging/comedi/drivers/mite.c @@ -779,15 +779,21 @@ static unsigned int mite_get_status(struct mite_channel *mite_chan) } unsigned int mite_ack_linkc(struct mite_channel *mite_chan, - struct comedi_subdevice *s) + struct comedi_subdevice *s, + bool sync) { struct mite_struct *mite = mite_chan->mite; unsigned int status; status = mite_get_status(mite_chan); - if (status & CHSR_LINKC) + if (status & CHSR_LINKC) { writel(CHOR_CLRLC, mite->mite_io_addr + MITE_CHOR(mite_chan->channel)); + sync = true; + } + if (sync) + mite_sync_dma(mite_chan, s); + if (status & CHSR_XFERR) { dev_err(s->device->class_dev, "mite: transfer error %08x\n", status); diff --git a/drivers/staging/comedi/drivers/mite.h b/drivers/staging/comedi/drivers/mite.h index f8364edf8ce8..bf6128abc464 100644 --- a/drivers/staging/comedi/drivers/mite.h +++ b/drivers/staging/comedi/drivers/mite.h @@ -93,8 +93,8 @@ void mite_dma_arm(struct mite_channel *mite_chan); void mite_dma_disarm(struct mite_channel *mite_chan); void mite_sync_dma(struct mite_channel *mite_chan, struct comedi_subdevice *s); u32 mite_bytes_in_transit(struct mite_channel *mite_chan); -unsigned int mite_ack_linkc(struct mite_channel *mite_chan, - struct comedi_subdevice *s); +unsigned int mite_ack_linkc(struct mite_channel *, struct comedi_subdevice *, + bool sync); int mite_done(struct mite_channel *mite_chan); void mite_prep_dma(struct mite_channel *mite_chan, diff --git a/drivers/staging/comedi/drivers/ni_mio_common.c b/drivers/staging/comedi/drivers/ni_mio_common.c index a3b93c1adf34..dc024f27cc48 100644 --- a/drivers/staging/comedi/drivers/ni_mio_common.c +++ b/drivers/staging/comedi/drivers/ni_mio_common.c @@ -3632,10 +3632,8 @@ static void handle_cdio_interrupt(struct comedi_device *dev) unsigned long flags; spin_lock_irqsave(&devpriv->mite_channel_lock, flags); - if (devpriv->cdo_mite_chan) { - mite_ack_linkc(devpriv->cdo_mite_chan, s); - mite_sync_dma(devpriv->cdo_mite_chan, s); - } + if (devpriv->cdo_mite_chan) + mite_ack_linkc(devpriv->cdo_mite_chan, s, true); spin_unlock_irqrestore(&devpriv->mite_channel_lock, flags); cdio_status = ni_readl(dev, NI_M_CDIO_STATUS_REG); @@ -5150,21 +5148,12 @@ static irqreturn_t ni_E_interrupt(int irq, void *d) #ifdef PCIDMA if (devpriv->mite) { unsigned long flags_too; - unsigned int m_status; spin_lock_irqsave(&devpriv->mite_channel_lock, flags_too); - if (s_ai && devpriv->ai_mite_chan) { - m_status = mite_ack_linkc(devpriv->ai_mite_chan, s_ai); - if (m_status & CHSR_LINKC) - mite_sync_dma(devpriv->ai_mite_chan, s_ai); - } - - if (s_ao && devpriv->ao_mite_chan) { - m_status = mite_ack_linkc(devpriv->ao_mite_chan, s_ao); - if (m_status & CHSR_LINKC) - mite_sync_dma(devpriv->ao_mite_chan, s_ao); - } - + if (s_ai && devpriv->ai_mite_chan) + mite_ack_linkc(devpriv->ai_mite_chan, s_ai, false); + if (s_ao && devpriv->ao_mite_chan) + mite_ack_linkc(devpriv->ao_mite_chan, s_ao, false); spin_unlock_irqrestore(&devpriv->mite_channel_lock, flags_too); } #endif diff --git a/drivers/staging/comedi/drivers/ni_pcidio.c b/drivers/staging/comedi/drivers/ni_pcidio.c index b4c6bab57a26..4a34da5140e0 100644 --- a/drivers/staging/comedi/drivers/ni_pcidio.c +++ b/drivers/staging/comedi/drivers/ni_pcidio.c @@ -400,13 +400,8 @@ static irqreturn_t nidio_interrupt(int irq, void *d) spin_lock(&devpriv->mite_channel_lock); if (devpriv->di_mite_chan) { - unsigned int m_status = mite_ack_linkc(devpriv->di_mite_chan, - s); - - if (m_status & CHSR_LINKC) { - mite_sync_dma(devpriv->di_mite_chan, s); - /* XXX need to byteswap */ - } + mite_ack_linkc(devpriv->di_mite_chan, s, false); + /* XXX need to byteswap sync'ed dma */ } spin_unlock(&devpriv->mite_channel_lock); diff --git a/drivers/staging/comedi/drivers/ni_tiocmd.c b/drivers/staging/comedi/drivers/ni_tiocmd.c index 5228b9fc2a72..9007c57544bf 100644 --- a/drivers/staging/comedi/drivers/ni_tiocmd.c +++ b/drivers/staging/comedi/drivers/ni_tiocmd.c @@ -428,10 +428,8 @@ void ni_tio_handle_interrupt(struct ni_gpct *counter, break; } spin_lock_irqsave(&counter->lock, flags); - if (counter->mite_chan) { - mite_ack_linkc(counter->mite_chan, s); - mite_sync_dma(counter->mite_chan, s); - } + if (counter->mite_chan) + mite_ack_linkc(counter->mite_chan, s, true); spin_unlock_irqrestore(&counter->lock, flags); } EXPORT_SYMBOL_GPL(ni_tio_handle_interrupt);