diff --git a/[refs] b/[refs] index fcc782bd26d1..e154c8dcdfe6 100644 --- a/[refs] +++ b/[refs] @@ -1,2 +1,2 @@ --- -refs/heads/master: b4780a3afb944765f4b94d79463e570e4472ccb6 +refs/heads/master: 7f340859f26e6de7069d0c4f234d948820c4fd47 diff --git a/trunk/drivers/staging/comedi/drivers/das800.c b/trunk/drivers/staging/comedi/drivers/das800.c index c30309cbc855..b72bbe98d543 100644 --- a/trunk/drivers/staging/comedi/drivers/das800.c +++ b/trunk/drivers/staging/comedi/drivers/das800.c @@ -107,6 +107,8 @@ cmd triggers supported: #define STATUS2_INTE 0X20 #define DAS800_ID 7 +#define DAS802_16_HALF_FIFO_SZ 128 + struct das800_board { const char *name; int ai_speed; @@ -483,92 +485,79 @@ static unsigned int das800_ai_get_sample(struct comedi_device *dev) static irqreturn_t das800_interrupt(int irq, void *d) { - short i; /* loop index */ - short dataPoint = 0; struct comedi_device *dev = d; - const struct das800_board *thisboard = comedi_board(dev); struct das800_private *devpriv = dev->private; - struct comedi_subdevice *s = dev->read_subdev; /* analog input subdevice */ - struct comedi_async *async; - int status; + struct comedi_subdevice *s = dev->read_subdev; + struct comedi_async *async = s ? s->async : NULL; unsigned long irq_flags; - static const int max_loops = 128; /* half-fifo size for cio-das802/16 */ - /* flags */ - int fifo_empty = 0; - int fifo_overflow = 0; + unsigned int status; + unsigned int val; + bool fifo_empty; + bool fifo_overflow; + int i; status = inb(dev->iobase + DAS800_STATUS); - /* if interrupt was not generated by board or driver not attached, quit */ if (!(status & IRQ)) return IRQ_NONE; - if (!(dev->attached)) + if (!dev->attached) return IRQ_HANDLED; - /* wait until here to initialize async, since we will get null dereference - * if interrupt occurs before driver is fully attached! - */ - async = s->async; - - /* if hardware conversions are not enabled, then quit */ spin_lock_irqsave(&dev->spinlock, irq_flags); status = das800_ind_read(dev, CONTROL1) & STATUS2_HCEN; - /* don't release spinlock yet since we want to make sure no one else disables hardware conversions */ + /* + * Don't release spinlock yet since we want to make sure + * no one else disables hardware conversions. + */ + + /* if hardware conversions are not enabled, then quit */ if (status == 0) { spin_unlock_irqrestore(&dev->spinlock, irq_flags); return IRQ_HANDLED; } - /* loop while card's fifo is not empty (and limit to half fifo for cio-das802/16) */ - for (i = 0; i < max_loops; i++) { - /* read 16 bits from dev->iobase and dev->iobase + 1 */ - dataPoint = inb(dev->iobase + DAS800_LSB); - dataPoint += inb(dev->iobase + DAS800_MSB) << 8; - if (thisboard->resolution == 12) { - fifo_empty = dataPoint & FIFO_EMPTY; - fifo_overflow = dataPoint & FIFO_OVF; - if (fifo_overflow) - break; + for (i = 0; i < DAS802_16_HALF_FIFO_SZ; i++) { + val = das800_ai_get_sample(dev); + if (s->maxdata == 0x0fff) { + fifo_empty = !!(val & FIFO_EMPTY); + fifo_overflow = !!(val & FIFO_OVF); } else { - fifo_empty = 0; /* cio-das802/16 has no fifo empty status bit */ + /* cio-das802/16 has no fifo empty status bit */ + fifo_empty = false; + fifo_overflow = !!(inb(dev->iobase + DAS800_GAIN) & + CIO_FFOV); } - if (fifo_empty) + if (fifo_empty || fifo_overflow) break; - /* strip off extraneous bits for 12 bit cards */ - if (thisboard->resolution == 12) - dataPoint = (dataPoint >> 4) & 0xfff; + + if (s->maxdata == 0x0fff) + val >>= 4; /* 12-bit sample */ + /* if there are more data points to collect */ - if (devpriv->count > 0 || devpriv->forever == 1) { + if (devpriv->count > 0 || devpriv->forever) { /* write data point to buffer */ - cfc_write_to_buffer(s, dataPoint); - if (devpriv->count > 0) - devpriv->count--; + cfc_write_to_buffer(s, val & s->maxdata); + devpriv->count--; } } async->events |= COMEDI_CB_BLOCK; - /* check for fifo overflow */ - if (thisboard->resolution == 12) { - fifo_overflow = dataPoint & FIFO_OVF; - /* else cio-das802/16 */ - } else { - fifo_overflow = inb(dev->iobase + DAS800_GAIN) & CIO_FFOV; - } + if (fifo_overflow) { spin_unlock_irqrestore(&dev->spinlock, irq_flags); - comedi_error(dev, "DAS800 FIFO overflow"); das800_cancel(dev, s); async->events |= COMEDI_CB_ERROR | COMEDI_CB_EOA; comedi_event(dev, s); async->events = 0; return IRQ_HANDLED; } - if (devpriv->count > 0 || devpriv->forever == 1) { + + if (devpriv->count > 0 || devpriv->forever) { /* Re-enable card's interrupt. * We already have spinlock, so indirect addressing is safe */ das800_ind_write(dev, CONTROL1_INTE | devpriv->do_bits, CONTROL1); spin_unlock_irqrestore(&dev->spinlock, irq_flags); - /* otherwise, stop taking data */ } else { + /* otherwise, stop taking data */ spin_unlock_irqrestore(&dev->spinlock, irq_flags); das800_disable(dev); async->events |= COMEDI_CB_EOA;