diff options
author | H Hartley Sweeten <hsweeten@visionengravers.com> | 2014-11-04 10:54:43 -0700 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2014-11-07 09:34:02 -0800 |
commit | 6a51cfc62f523c70b000368b32cb46fa0d24f536 (patch) | |
tree | 5923fb51ef7bf7542fb0bb8e9c7184e708f9aa51 /drivers/staging/comedi/drivers/addi_apci_3120.c | |
parent | staging: comedi: addi_apci_3120: move apci3120_ao_insn_write() to driver source (diff) | |
download | linux-dev-6a51cfc62f523c70b000368b32cb46fa0d24f536.tar.xz linux-dev-6a51cfc62f523c70b000368b32cb46fa0d24f536.zip |
staging: comedi: addi_apci_3120: move apci3120_ai_insn_read() to driver source
Move this function, and its helper function, from the included hwdrv_apci31210.c
source file to the main driver source file.
Signed-off-by: H Hartley Sweeten <hsweeten@visionengravers.com>
Reviewed-by: Ian Abbott <abbotti@mev.co.uk>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/staging/comedi/drivers/addi_apci_3120.c')
-rw-r--r-- | drivers/staging/comedi/drivers/addi_apci_3120.c | 60 |
1 files changed, 60 insertions, 0 deletions
diff --git a/drivers/staging/comedi/drivers/addi_apci_3120.c b/drivers/staging/comedi/drivers/addi_apci_3120.c index c17a8408749f..70363faa99d6 100644 --- a/drivers/staging/comedi/drivers/addi_apci_3120.c +++ b/drivers/staging/comedi/drivers/addi_apci_3120.c @@ -281,6 +281,66 @@ static void apci3120_ai_reset_fifo(struct comedi_device *dev) #include "addi-data/hwdrv_apci3120.c" +static int apci3120_ai_eoc(struct comedi_device *dev, + struct comedi_subdevice *s, + struct comedi_insn *insn, + unsigned long context) +{ + unsigned int status; + + status = inw(dev->iobase + APCI3120_STATUS_REG); + if ((status & APCI3120_STATUS_EOC_INT) == 0) + return 0; + return -EBUSY; +} + +static int apci3120_ai_insn_read(struct comedi_device *dev, + struct comedi_subdevice *s, + struct comedi_insn *insn, + unsigned int *data) +{ + struct apci3120_private *devpriv = dev->private; + unsigned int divisor; + int ret; + int i; + + /* set mode for A/D conversions by software trigger with timer 0 */ + devpriv->mode = APCI3120_MODE_TIMER2_CLK_OSC | + APCI3120_MODE_TIMER2_AS_TIMER; + outb(devpriv->mode, dev->iobase + APCI3120_MODE_REG); + + /* load chanlist for single channel scan */ + if (!apci3120_setup_chan_list(dev, s, 1, &insn->chanspec)) + return -EINVAL; + + /* + * Timer 0 is used in MODE4 (software triggered strobe) to set the + * conversion time for each acquisition. Each conversion is triggered + * when the divisor is written to the timer, The conversion is done + * when the EOC bit in the status register is '0'. + */ + apci3120_timer_set_mode(dev, 0, APCI3120_TIMER_MODE4); + apci3120_timer_enable(dev, 0, true); + + /* fixed conversion time of 10 us */ + divisor = apci3120_ns_to_timer(dev, 0, 10000, CMDF_ROUND_NEAREST); + + apci3120_ai_reset_fifo(dev); + + for (i = 0; i < insn->n; i++) { + /* trigger conversion */ + apci3120_timer_write(dev, 0, divisor); + + ret = comedi_timeout(dev, s, insn, apci3120_ai_eoc, 0); + if (ret) + return ret; + + data[i] = inw(dev->iobase + 0); + } + + return insn->n; +} + static int apci3120_ao_ready(struct comedi_device *dev, struct comedi_subdevice *s, struct comedi_insn *insn, |