Use comedi_timeout() to wait for the analog input end-of-conversion. Signed-off-by: H Hartley Sweeten <hsweeten@xxxxxxxxxxxxxxxxxxx> Cc: Ian Abbott <abbotti@xxxxxxxxx> Cc: Greg Kroah-Hartman <gregkh@xxxxxxxxxxxxxxxxxxx> --- drivers/staging/comedi/drivers/ni_daq_700.c | 53 ++++++++++++++++++----------- 1 file changed, 33 insertions(+), 20 deletions(-) diff --git a/drivers/staging/comedi/drivers/ni_daq_700.c b/drivers/staging/comedi/drivers/ni_daq_700.c index 7979a66..e56bfeb 100644 --- a/drivers/staging/comedi/drivers/ni_daq_700.c +++ b/drivers/staging/comedi/drivers/ni_daq_700.c @@ -109,14 +109,31 @@ static int daq700_dio_insn_config(struct comedi_device *dev, return insn->n; } +static int daq700_ai_eoc(struct comedi_device *dev, + struct comedi_subdevice *s, + struct comedi_insn *insn, + unsigned long context) +{ + unsigned int status; + + status = inb(dev->iobase + STA_R2); + if ((status & 0x03)) + return -EOVERFLOW; + status = inb(dev->iobase + STA_R1); + if ((status & 0x02)) + return -ENODATA; + if ((status & 0x11) == 0x01) + return 0; + return -EBUSY; +} + static int daq700_ai_rinsn(struct comedi_device *dev, struct comedi_subdevice *s, struct comedi_insn *insn, unsigned int *data) { - int n, i, chan; + int n, chan; int d; - unsigned int status; - enum { TIMEOUT = 100 }; + int ret; chan = CR_CHAN(insn->chanspec); /* write channel to multiplexer */ @@ -130,30 +147,26 @@ static int daq700_ai_rinsn(struct comedi_device *dev, outb(0x30, dev->iobase + CMO_R); /* mode 0 out0 L, from H */ /* mode 1 out0 H, L to H, start conversion */ outb(0x32, dev->iobase + CMO_R); + /* wait for conversion to end */ - for (i = 0; i < TIMEOUT; i++) { - status = inb(dev->iobase + STA_R2); - if ((status & 0x03) != 0) { + ret = comedi_timeout(dev, s, insn, daq700_ai_eoc, 0); + if (ret) { + switch (ret) { + case -EOVERFLOW: dev_info(dev->class_dev, "Overflow/run Error\n"); - return -EOVERFLOW; - } - status = inb(dev->iobase + STA_R1); - if ((status & 0x02) != 0) { + break; + case -ENODATA: dev_info(dev->class_dev, "Data Error\n"); - return -ENODATA; - } - if ((status & 0x11) == 0x01) { - /* ADC conversion complete */ + break; + default: + dev_info(dev->class_dev, + "timeout during ADC conversion\n"); break; } - udelay(1); - } - if (i == TIMEOUT) { - dev_info(dev->class_dev, - "timeout during ADC conversion\n"); - return -ETIMEDOUT; + return ret; } + /* read data */ d = inw(dev->iobase + ADFIFO_R); /* mangle the data as necessary */ -- 1.8.5.2 _______________________________________________ devel mailing list devel@xxxxxxxxxxxxxxxxxxxxxx http://driverdev.linuxdriverproject.org/mailman/listinfo/driverdev-devel