[PATCH 14/14] staging: comedi: me_daq: fix me_ai_insn_read()

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



The comedi core expects (*insn_read) functions to return insn->n data
values. Refactor the function to work like the core expects. For
aesthetics, use the comedi_offset_munge() helper to munge the 2's
complement data.

This also fixes a minor issue when comedi_timeout() times out. Currently
this function just returns which leaves the ADC mode programmed for
software triggering. With the refactor the ADC mode is always disabled
when the function exits. This allows removing the unnecessary steps to
"stop any running conversions" at the start of the function.

Signed-off-by: H Hartley Sweeten <hsweeten@xxxxxxxxxxxxxxxxxxx>
Cc: Ian Abbott <abbotti@xxxxxxxxx>
Cc: Greg Kroah-Hartman <gregkh@xxxxxxxxxxxxxxxxxxx>
---
 drivers/staging/comedi/drivers/me_daq.c | 34 ++++++++++++++++-----------------
 1 file changed, 17 insertions(+), 17 deletions(-)

diff --git a/drivers/staging/comedi/drivers/me_daq.c b/drivers/staging/comedi/drivers/me_daq.c
index cfb3566..3bf0caa 100644
--- a/drivers/staging/comedi/drivers/me_daq.c
+++ b/drivers/staging/comedi/drivers/me_daq.c
@@ -243,8 +243,9 @@ static int me_ai_insn_read(struct comedi_device *dev,
 	unsigned int chan = CR_CHAN(insn->chanspec);
 	unsigned int range = CR_RANGE(insn->chanspec);
 	unsigned int aref = CR_AREF(insn->chanspec);
-	unsigned short val;
-	int ret;
+	unsigned int val;
+	int ret = 0;
+	int i;
 
 	/*
 	 * For differential operation, there are only 8 input channels
@@ -255,10 +256,6 @@ static int me_ai_insn_read(struct comedi_device *dev,
 			return -EINVAL;
 	}
 
-	/* stop any running conversion */
-	devpriv->ctrl1 &= ~ME_CTRL1_ADC_MODE_MASK;
-	writew(devpriv->ctrl1, dev->mmio + ME_CTRL1_REG);
-
 	/* clear chanlist and ad fifo */
 	devpriv->ctrl2 &= ~(ME_CTRL2_ADFIFO_ENA | ME_CTRL2_CHANLIST_ENA);
 	writew(devpriv->ctrl2, dev->mmio + ME_CTRL2_REG);
@@ -281,24 +278,27 @@ static int me_ai_insn_read(struct comedi_device *dev,
 	devpriv->ctrl1 |= ME_CTRL1_ADC_MODE_SOFT_TRIG;
 	writew(devpriv->ctrl1, dev->mmio + ME_CTRL1_REG);
 
-	/* start ai conversion */
-	readw(dev->mmio + ME_CTRL1_REG);
+	for (i = 0; i < insn->n; i++) {
+		/* start ai conversion */
+		readw(dev->mmio + ME_CTRL1_REG);
 
-	/* wait for ADC fifo not empty flag */
-	ret = comedi_timeout(dev, s, insn, me_ai_eoc, 0);
-	if (ret)
-		return ret;
+		/* wait for ADC fifo not empty flag */
+		ret = comedi_timeout(dev, s, insn, me_ai_eoc, 0);
+		if (ret)
+			break;
+
+		/* get value from ADC fifo */
+		val = readw(dev->mmio + ME_AI_FIFO_REG) & s->maxdata;
 
-	/* get value from ADC fifo */
-	val = readw(dev->mmio + ME_AI_FIFO_REG);
-	val = (val ^ 0x800) & 0x0fff;
-	data[0] = val;
+		/* munge 2's complement value to offset binary */
+		data[i] = comedi_offset_munge(s, val);
+	}
 
 	/* stop any running conversion */
 	devpriv->ctrl1 &= ~ME_CTRL1_ADC_MODE_MASK;
 	writew(devpriv->ctrl1, dev->mmio + ME_CTRL1_REG);
 
-	return 1;
+	return ret ? ret : insn->n;
 }
 
 static int me_ao_insn_write(struct comedi_device *dev,
-- 
2.5.1

_______________________________________________
devel mailing list
devel@xxxxxxxxxxxxxxxxxxxxxx
http://driverdev.linuxdriverproject.org/mailman/listinfo/driverdev-devel



[Index of Archives]     [Linux Driver Backports]     [DMA Engine]     [Linux GPIO]     [Linux SPI]     [Video for Linux]     [Linux USB Devel]     [Linux Coverity]     [Linux Audio Users]     [Linux Kernel]     [Linux SCSI]     [Yosemite Backpacking]
  Powered by Linux