3 * Developed by Ivan Martinez and Frank Mori Hess, with valuable help from
4 * David Schleef and the rest of the Comedi developers comunity.
6 * Copyright (C) 2001-2003 Ivan Martinez <imr@oersted.dtu.dk>
7 * Copyright (C) 2001,2002 Frank Mori Hess <fmhess@users.sourceforge.net>
9 * COMEDI - Linux Control and Measurement Device Interface
10 * Copyright (C) 1997-8 David A. Schleef <ds@schleef.org>
12 * This program is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 2 of the License, or
15 * (at your option) any later version.
17 * This program is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
25 * Description: MeasurementComputing PCI-DAS series
26 * with the AMCC S5933 PCI controller
27 * Devices: [Measurement Computing] PCI-DAS1602/16 (cb_pcidas),
28 * PCI-DAS1602/16jr, PCI-DAS1602/12, PCI-DAS1200, PCI-DAS1200jr,
29 * PCI-DAS1000, PCI-DAS1001, PCI_DAS1002
30 * Author: Ivan Martinez <imr@oersted.dtu.dk>,
31 * Frank Mori Hess <fmhess@users.sourceforge.net>
35 * There are many reports of the driver being used with most of the
36 * supported cards. Despite no detailed log is maintained, it can
37 * be said that the driver is quite tested and stable.
39 * The boards may be autocalibrated using the comedi_calibrate
42 * Configuration options: not applicable, uses PCI auto config
44 * For commands, the scanned channels must be consecutive
45 * (i.e. 4-5-6-7, 2-3-4,...), and must all have the same
49 * For start_src == TRIG_EXT, the A/D EXTERNAL TRIGGER IN (pin 45) is used.
50 * For 1602 series, the start_arg is interpreted as follows:
51 * start_arg == 0 => gated trigger (level high)
52 * start_arg == CR_INVERT => gated trigger (level low)
53 * start_arg == CR_EDGE => Rising edge
54 * start_arg == CR_EDGE | CR_INVERT => Falling edge
55 * For the other boards the trigger will be done on rising edge
60 * analog triggering on 1602 series
63 #include <linux/module.h>
64 #include <linux/delay.h>
65 #include <linux/interrupt.h>
67 #include "../comedi_pci.h"
69 #include "comedi_8254.h"
71 #include "amcc_s5933.h"
73 #define AI_BUFFER_SIZE 1024 /* max ai fifo size */
74 #define AO_BUFFER_SIZE 1024 /* max ao fifo size */
77 * PCI BAR1 Register map (devpriv->pcibar1)
79 #define PCIDAS_CTRL_REG 0x00 /* INTERRUPT / ADC FIFO register */
80 #define PCIDAS_CTRL_INT(x) (((x) & 0x3) << 0)
81 #define PCIDAS_CTRL_INT_NONE PCIDAS_CTRL_INT(0) /* no int selected */
82 #define PCIDAS_CTRL_INT_EOS PCIDAS_CTRL_INT(1) /* int on end of scan */
83 #define PCIDAS_CTRL_INT_FHF PCIDAS_CTRL_INT(2) /* int on fifo half full */
84 #define PCIDAS_CTRL_INT_FNE PCIDAS_CTRL_INT(3) /* int on fifo not empty */
85 #define PCIDAS_CTRL_INT_MASK PCIDAS_CTRL_INT(3) /* mask of int select bits */
86 #define PCIDAS_CTRL_INTE BIT(2) /* int enable */
87 #define PCIDAS_CTRL_DAHFIE BIT(3) /* dac half full int enable */
88 #define PCIDAS_CTRL_EOAIE BIT(4) /* end of acq. int enable */
89 #define PCIDAS_CTRL_DAHFI BIT(5) /* dac half full status / clear */
90 #define PCIDAS_CTRL_EOAI BIT(6) /* end of acq. int status / clear */
91 #define PCIDAS_CTRL_INT_CLR BIT(7) /* int status / clear */
92 #define PCIDAS_CTRL_EOBI BIT(9) /* end of burst int status */
93 #define PCIDAS_CTRL_ADHFI BIT(10) /* half-full int status */
94 #define PCIDAS_CTRL_ADNEI BIT(11) /* fifo not empty int status (latch) */
95 #define PCIDAS_CTRL_ADNE BIT(12) /* fifo not empty status (realtime) */
96 #define PCIDAS_CTRL_DAEMIE BIT(12) /* dac empty int enable */
97 #define PCIDAS_CTRL_LADFUL BIT(13) /* fifo overflow / clear */
98 #define PCIDAS_CTRL_DAEMI BIT(14) /* dac fifo empty int status / clear */
100 #define PCIDAS_AI_REG 0x02 /* ADC CHANNEL MUX AND CONTROL reg */
101 #define PCIDAS_AI_FIRST(x) ((x) & 0xf)
102 #define PCIDAS_AI_LAST(x) (((x) & 0xf) << 4)
103 #define PCIDAS_AI_CHAN(x) (PCIDAS_AI_FIRST(x) | PCIDAS_AI_LAST(x))
104 #define PCIDAS_AI_GAIN(x) (((x) & 0x3) << 8)
105 #define PCIDAS_AI_SE BIT(10) /* Inputs in single-ended mode */
106 #define PCIDAS_AI_UNIP BIT(11) /* Analog front-end unipolar mode */
107 #define PCIDAS_AI_PACER(x) (((x) & 0x3) << 12)
108 #define PCIDAS_AI_PACER_SW PCIDAS_AI_PACER(0) /* software pacer */
109 #define PCIDAS_AI_PACER_INT PCIDAS_AI_PACER(1) /* int. pacer */
110 #define PCIDAS_AI_PACER_EXTN PCIDAS_AI_PACER(2) /* ext. falling edge */
111 #define PCIDAS_AI_PACER_EXTP PCIDAS_AI_PACER(3) /* ext. rising edge */
112 #define PCIDAS_AI_PACER_MASK PCIDAS_AI_PACER(3) /* pacer source bits */
113 #define PCIDAS_AI_EOC BIT(14) /* adc not busy */
115 #define PCIDAS_TRIG_REG 0x04 /* TRIGGER CONTROL/STATUS register */
116 #define PCIDAS_TRIG_SEL(x) (((x) & 0x3) << 0)
117 #define PCIDAS_TRIG_SEL_NONE PCIDAS_TRIG_SEL(0) /* no start trigger */
118 #define PCIDAS_TRIG_SEL_SW PCIDAS_TRIG_SEL(1) /* software start trigger */
119 #define PCIDAS_TRIG_SEL_EXT PCIDAS_TRIG_SEL(2) /* ext. start trigger */
120 #define PCIDAS_TRIG_SEL_ANALOG PCIDAS_TRIG_SEL(3) /* ext. analog trigger */
121 #define PCIDAS_TRIG_SEL_MASK PCIDAS_TRIG_SEL(3) /* start trigger mask */
122 #define PCIDAS_TRIG_POL BIT(2) /* invert trigger (1602 only) */
123 #define PCIDAS_TRIG_MODE BIT(3) /* edge/level trigerred (1602 only) */
124 #define PCIDAS_TRIG_EN BIT(4) /* enable external start trigger */
125 #define PCIDAS_TRIG_BURSTE BIT(5) /* burst mode enable */
126 #define PCIDAS_TRIG_CLR BIT(7) /* clear external trigger */
128 #define PCIDAS_CALIB_REG 0x06 /* CALIBRATION register */
129 #define PCIDAS_CALIB_8800_SEL BIT(8) /* select 8800 caldac */
130 #define PCIDAS_CALIB_TRIM_SEL BIT(9) /* select ad7376 trim pot */
131 #define PCIDAS_CALIB_DAC08_SEL BIT(10) /* select dac08 caldac */
132 #define PCIDAS_CALIB_SRC(x) (((x) & 0x7) << 11)
133 #define PCIDAS_CALIB_EN BIT(14) /* calibration source enable */
134 #define PCIDAS_CALIB_DATA BIT(15) /* serial data bit going to caldac */
136 #define PCIDAS_AO_REG 0x08 /* dac control and status register */
137 #define PCIDAS_AO_EMPTY BIT(0) /* fifo empty, write clear (1602) */
138 #define PCIDAS_AO_DACEN BIT(1) /* dac enable */
139 #define PCIDAS_AO_START BIT(2) /* start/arm fifo (1602) */
140 #define PCIDAS_AO_PACER(x) (((x) & 0x3) << 3) /* (1602) */
141 #define PCIDAS_AO_PACER_SW PCIDAS_AO_PACER(0) /* software pacer */
142 #define PCIDAS_AO_PACER_INT PCIDAS_AO_PACER(1) /* int. pacer */
143 #define PCIDAS_AO_PACER_EXTN PCIDAS_AO_PACER(2) /* ext. falling edge */
144 #define PCIDAS_AO_PACER_EXTP PCIDAS_AO_PACER(3) /* ext. rising edge */
145 #define PCIDAS_AO_PACER_MASK PCIDAS_AO_PACER(3) /* pacer source bits */
146 #define PCIDAS_AO_CHAN_EN(c) BIT(5 + ((c) & 0x1))
147 #define PCIDAS_AO_CHAN_MASK (PCIDAS_AO_CHAN_EN(0) | PCIDAS_AO_CHAN_EN(1))
148 #define PCIDAS_AO_UPDATE_BOTH BIT(7) /* update both dacs */
149 #define PCIDAS_AO_RANGE(c, r) (((r) & 0x3) << (8 + 2 * ((c) & 0x1)))
150 #define PCIDAS_AO_RANGE_MASK(c) PCIDAS_AO_RANGE((c), 0x3)
153 * PCI BAR2 Register map (devpriv->pcibar2)
155 #define PCIDAS_AI_DATA_REG 0x00
156 #define PCIDAS_AI_FIFO_CLR_REG 0x02
159 * PCI BAR3 Register map (dev->iobase)
161 #define PCIDAS_AI_8254_BASE 0x00
162 #define PCIDAS_8255_BASE 0x04
163 #define PCIDAS_AO_8254_BASE 0x08
166 * PCI BAR4 Register map (devpriv->pcibar4)
168 #define PCIDAS_AO_DATA_REG(x) (0x00 + ((x) * 2))
169 #define PCIDAS_AO_FIFO_REG 0x00
170 #define PCIDAS_AO_FIFO_CLR_REG 0x02
172 /* analog input ranges for most boards */
173 static const struct comedi_lrange cb_pcidas_ranges
= {
186 /* pci-das1001 input ranges */
187 static const struct comedi_lrange cb_pcidas_alt_ranges
= {
200 /* analog output ranges */
201 static const struct comedi_lrange cb_pcidas_ao_ranges
= {
215 enum cb_pcidas_boardid
{
220 BOARD_PCIDAS1602_16_JR
,
226 struct cb_pcidas_board
{
228 int ai_speed
; /* fastest conversion period in ns */
229 int ao_scan_speed
; /* analog output scan speed for 1602 series */
230 int fifo_size
; /* number of samples fifo can hold */
231 enum trimpot_model trimpot
;
232 unsigned int is_16bit
; /* ai/ao is 1=16-bit; 0=12-bit */
233 unsigned int use_alt_range
:1; /* use alternate ai range table */
234 unsigned int has_ao
:1; /* has 2 analog output channels */
235 unsigned int has_ao_fifo
:1; /* analog output has fifo */
236 unsigned int has_dac08
:1;
237 unsigned int is_1602
:1;
240 static const struct cb_pcidas_board cb_pcidas_boards
[] = {
241 [BOARD_PCIDAS1602_16
] = {
242 .name
= "pci-das1602/16",
244 .ao_scan_speed
= 10000,
253 [BOARD_PCIDAS1200
] = {
254 .name
= "pci-das1200",
260 [BOARD_PCIDAS1602_12
] = {
261 .name
= "pci-das1602/12",
263 .ao_scan_speed
= 4000,
270 [BOARD_PCIDAS1200_JR
] = {
271 .name
= "pci-das1200/jr",
276 [BOARD_PCIDAS1602_16_JR
] = {
277 .name
= "pci-das1602/16/jr",
285 [BOARD_PCIDAS1000
] = {
286 .name
= "pci-das1000",
291 [BOARD_PCIDAS1001
] = {
292 .name
= "pci-das1001",
299 [BOARD_PCIDAS1002
] = {
300 .name
= "pci-das1002",
308 struct cb_pcidas_private
{
309 struct comedi_8254
*ao_pacer
;
311 unsigned long s5933_config
;
312 unsigned long pcibar1
;
313 unsigned long pcibar2
;
314 unsigned long pcibar4
;
315 /* bits to write to registers */
317 unsigned int s5933_intcsr_bits
;
318 unsigned int ao_ctrl
;
320 unsigned short ai_buffer
[AI_BUFFER_SIZE
];
321 unsigned short ao_buffer
[AO_BUFFER_SIZE
];
322 unsigned int calibration_source
;
325 static inline unsigned int cal_enable_bits(struct comedi_device
*dev
)
327 struct cb_pcidas_private
*devpriv
= dev
->private;
329 return PCIDAS_CALIB_EN
| PCIDAS_CALIB_SRC(devpriv
->calibration_source
);
332 static int cb_pcidas_ai_eoc(struct comedi_device
*dev
,
333 struct comedi_subdevice
*s
,
334 struct comedi_insn
*insn
,
335 unsigned long context
)
337 struct cb_pcidas_private
*devpriv
= dev
->private;
340 status
= inw(devpriv
->pcibar1
+ PCIDAS_AI_REG
);
341 if (status
& PCIDAS_AI_EOC
)
346 static int cb_pcidas_ai_rinsn(struct comedi_device
*dev
,
347 struct comedi_subdevice
*s
,
348 struct comedi_insn
*insn
, unsigned int *data
)
350 struct cb_pcidas_private
*devpriv
= dev
->private;
351 unsigned int chan
= CR_CHAN(insn
->chanspec
);
352 unsigned int range
= CR_RANGE(insn
->chanspec
);
353 unsigned int aref
= CR_AREF(insn
->chanspec
);
358 /* enable calibration input if appropriate */
359 if (insn
->chanspec
& CR_ALT_SOURCE
) {
360 outw(cal_enable_bits(dev
),
361 devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
364 outw(0, devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
367 /* set mux limits and gain */
368 bits
= PCIDAS_AI_CHAN(chan
) | PCIDAS_AI_GAIN(range
);
369 /* set unipolar/bipolar */
370 if (comedi_range_is_unipolar(s
, range
))
371 bits
|= PCIDAS_AI_UNIP
;
372 /* set single-ended/differential */
373 if (aref
!= AREF_DIFF
)
374 bits
|= PCIDAS_AI_SE
;
375 outw(bits
, devpriv
->pcibar1
+ PCIDAS_AI_REG
);
378 outw(0, devpriv
->pcibar2
+ PCIDAS_AI_FIFO_CLR_REG
);
380 /* convert n samples */
381 for (n
= 0; n
< insn
->n
; n
++) {
382 /* trigger conversion */
383 outw(0, devpriv
->pcibar2
+ PCIDAS_AI_DATA_REG
);
385 /* wait for conversion to end */
386 ret
= comedi_timeout(dev
, s
, insn
, cb_pcidas_ai_eoc
, 0);
391 data
[n
] = inw(devpriv
->pcibar2
+ PCIDAS_AI_DATA_REG
);
394 /* return the number of samples read/written */
398 static int ai_config_insn(struct comedi_device
*dev
, struct comedi_subdevice
*s
,
399 struct comedi_insn
*insn
, unsigned int *data
)
401 struct cb_pcidas_private
*devpriv
= dev
->private;
403 unsigned int source
= data
[1];
406 case INSN_CONFIG_ALT_SOURCE
:
408 dev_err(dev
->class_dev
,
409 "invalid calibration source: %i\n",
413 devpriv
->calibration_source
= source
;
421 /* analog output insn for pcidas-1000 and 1200 series */
422 static int cb_pcidas_ao_nofifo_winsn(struct comedi_device
*dev
,
423 struct comedi_subdevice
*s
,
424 struct comedi_insn
*insn
,
427 struct cb_pcidas_private
*devpriv
= dev
->private;
428 unsigned int chan
= CR_CHAN(insn
->chanspec
);
429 unsigned int range
= CR_RANGE(insn
->chanspec
);
432 /* set channel and range */
433 spin_lock_irqsave(&dev
->spinlock
, flags
);
434 devpriv
->ao_ctrl
&= ~(PCIDAS_AO_UPDATE_BOTH
|
435 PCIDAS_AO_RANGE_MASK(chan
));
436 devpriv
->ao_ctrl
|= PCIDAS_AO_DACEN
| PCIDAS_AO_RANGE(chan
, range
);
437 outw(devpriv
->ao_ctrl
, devpriv
->pcibar1
+ PCIDAS_AO_REG
);
438 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
440 /* remember value for readback */
441 s
->readback
[chan
] = data
[0];
444 outw(data
[0], devpriv
->pcibar4
+ PCIDAS_AO_DATA_REG(chan
));
449 /* analog output insn for pcidas-1602 series */
450 static int cb_pcidas_ao_fifo_winsn(struct comedi_device
*dev
,
451 struct comedi_subdevice
*s
,
452 struct comedi_insn
*insn
, unsigned int *data
)
454 struct cb_pcidas_private
*devpriv
= dev
->private;
455 unsigned int chan
= CR_CHAN(insn
->chanspec
);
456 unsigned int range
= CR_RANGE(insn
->chanspec
);
460 outw(0, devpriv
->pcibar4
+ PCIDAS_AO_FIFO_CLR_REG
);
462 /* set channel and range */
463 spin_lock_irqsave(&dev
->spinlock
, flags
);
464 devpriv
->ao_ctrl
&= ~(PCIDAS_AO_CHAN_MASK
| PCIDAS_AO_RANGE_MASK(chan
) |
465 PCIDAS_AO_PACER_MASK
);
466 devpriv
->ao_ctrl
|= PCIDAS_AO_DACEN
| PCIDAS_AO_RANGE(chan
, range
) |
467 PCIDAS_AO_CHAN_EN(chan
) | PCIDAS_AO_START
;
468 outw(devpriv
->ao_ctrl
, devpriv
->pcibar1
+ PCIDAS_AO_REG
);
469 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
471 /* remember value for readback */
472 s
->readback
[chan
] = data
[0];
475 outw(data
[0], devpriv
->pcibar4
+ PCIDAS_AO_FIFO_REG
);
480 static int wait_for_nvram_ready(unsigned long s5933_base_addr
)
482 static const int timeout
= 1000;
485 for (i
= 0; i
< timeout
; i
++) {
486 if ((inb(s5933_base_addr
+
487 AMCC_OP_REG_MCSR_NVCMD
) & MCSR_NV_BUSY
)
495 static int nvram_read(struct comedi_device
*dev
, unsigned int address
,
498 struct cb_pcidas_private
*devpriv
= dev
->private;
499 unsigned long iobase
= devpriv
->s5933_config
;
501 if (wait_for_nvram_ready(iobase
) < 0)
504 outb(MCSR_NV_ENABLE
| MCSR_NV_LOAD_LOW_ADDR
,
505 iobase
+ AMCC_OP_REG_MCSR_NVCMD
);
506 outb(address
& 0xff, iobase
+ AMCC_OP_REG_MCSR_NVDATA
);
507 outb(MCSR_NV_ENABLE
| MCSR_NV_LOAD_HIGH_ADDR
,
508 iobase
+ AMCC_OP_REG_MCSR_NVCMD
);
509 outb((address
>> 8) & 0xff, iobase
+ AMCC_OP_REG_MCSR_NVDATA
);
510 outb(MCSR_NV_ENABLE
| MCSR_NV_READ
, iobase
+ AMCC_OP_REG_MCSR_NVCMD
);
512 if (wait_for_nvram_ready(iobase
) < 0)
515 *data
= inb(iobase
+ AMCC_OP_REG_MCSR_NVDATA
);
520 static int eeprom_read_insn(struct comedi_device
*dev
,
521 struct comedi_subdevice
*s
,
522 struct comedi_insn
*insn
, unsigned int *data
)
527 retval
= nvram_read(dev
, CR_CHAN(insn
->chanspec
), &nvram_data
);
531 data
[0] = nvram_data
;
536 static void cb_pcidas_calib_write(struct comedi_device
*dev
,
537 unsigned int val
, unsigned int len
,
540 struct cb_pcidas_private
*devpriv
= dev
->private;
541 unsigned int calib_bits
= cal_enable_bits(dev
);
546 calib_bits
|= PCIDAS_CALIB_TRIM_SEL
;
547 outw(calib_bits
, devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
550 /* write bitstream to calibration device */
551 for (bit
= 1 << (len
- 1); bit
; bit
>>= 1) {
553 calib_bits
|= PCIDAS_CALIB_DATA
;
555 calib_bits
&= ~PCIDAS_CALIB_DATA
;
557 outw(calib_bits
, devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
561 calib_bits
= cal_enable_bits(dev
);
565 outw(calib_bits
| PCIDAS_CALIB_8800_SEL
,
566 devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
570 /* latch value to trimpot/caldac */
571 outw(calib_bits
, devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
574 static int cb_pcidas_caldac_insn_write(struct comedi_device
*dev
,
575 struct comedi_subdevice
*s
,
576 struct comedi_insn
*insn
,
579 unsigned int chan
= CR_CHAN(insn
->chanspec
);
582 unsigned int val
= data
[insn
->n
- 1];
584 if (s
->readback
[chan
] != val
) {
585 /* write 11-bit channel/value to caldac */
586 cb_pcidas_calib_write(dev
, (chan
<< 8) | val
, 11,
588 s
->readback
[chan
] = val
;
595 /* 1602/16 pregain offset */
596 static void dac08_write(struct comedi_device
*dev
, unsigned int value
)
598 struct cb_pcidas_private
*devpriv
= dev
->private;
601 value
|= cal_enable_bits(dev
);
603 /* latch the new value into the caldac */
604 outw(value
, devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
606 outw(value
| PCIDAS_CALIB_DAC08_SEL
,
607 devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
609 outw(value
, devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
613 static int cb_pcidas_dac08_insn_write(struct comedi_device
*dev
,
614 struct comedi_subdevice
*s
,
615 struct comedi_insn
*insn
,
618 unsigned int chan
= CR_CHAN(insn
->chanspec
);
621 unsigned int val
= data
[insn
->n
- 1];
623 if (s
->readback
[chan
] != val
) {
624 dac08_write(dev
, val
);
625 s
->readback
[chan
] = val
;
632 static void cb_pcidas_trimpot_write(struct comedi_device
*dev
,
633 unsigned int chan
, unsigned int val
)
635 const struct cb_pcidas_board
*board
= dev
->board_ptr
;
637 switch (board
->trimpot
) {
639 /* write 7-bit value to trimpot */
640 cb_pcidas_calib_write(dev
, val
, 7, true);
643 /* write 10-bit channel/value to trimpot */
644 cb_pcidas_calib_write(dev
, (chan
<< 8) | val
, 10, true);
647 dev_err(dev
->class_dev
, "driver bug?\n");
652 static int cb_pcidas_trimpot_insn_write(struct comedi_device
*dev
,
653 struct comedi_subdevice
*s
,
654 struct comedi_insn
*insn
,
657 unsigned int chan
= CR_CHAN(insn
->chanspec
);
660 unsigned int val
= data
[insn
->n
- 1];
662 if (s
->readback
[chan
] != val
) {
663 cb_pcidas_trimpot_write(dev
, chan
, val
);
664 s
->readback
[chan
] = val
;
671 static int cb_pcidas_ai_check_chanlist(struct comedi_device
*dev
,
672 struct comedi_subdevice
*s
,
673 struct comedi_cmd
*cmd
)
675 unsigned int chan0
= CR_CHAN(cmd
->chanlist
[0]);
676 unsigned int range0
= CR_RANGE(cmd
->chanlist
[0]);
679 for (i
= 1; i
< cmd
->chanlist_len
; i
++) {
680 unsigned int chan
= CR_CHAN(cmd
->chanlist
[i
]);
681 unsigned int range
= CR_RANGE(cmd
->chanlist
[i
]);
683 if (chan
!= (chan0
+ i
) % s
->n_chan
) {
684 dev_dbg(dev
->class_dev
,
685 "entries in chanlist must be consecutive channels, counting upwards\n");
689 if (range
!= range0
) {
690 dev_dbg(dev
->class_dev
,
691 "entries in chanlist must all have the same gain\n");
698 static int cb_pcidas_ai_cmdtest(struct comedi_device
*dev
,
699 struct comedi_subdevice
*s
,
700 struct comedi_cmd
*cmd
)
702 const struct cb_pcidas_board
*board
= dev
->board_ptr
;
706 /* Step 1 : check if triggers are trivially valid */
708 err
|= comedi_check_trigger_src(&cmd
->start_src
, TRIG_NOW
| TRIG_EXT
);
709 err
|= comedi_check_trigger_src(&cmd
->scan_begin_src
,
710 TRIG_FOLLOW
| TRIG_TIMER
| TRIG_EXT
);
711 err
|= comedi_check_trigger_src(&cmd
->convert_src
,
712 TRIG_TIMER
| TRIG_NOW
| TRIG_EXT
);
713 err
|= comedi_check_trigger_src(&cmd
->scan_end_src
, TRIG_COUNT
);
714 err
|= comedi_check_trigger_src(&cmd
->stop_src
, TRIG_COUNT
| TRIG_NONE
);
719 /* Step 2a : make sure trigger sources are unique */
721 err
|= comedi_check_trigger_is_unique(cmd
->start_src
);
722 err
|= comedi_check_trigger_is_unique(cmd
->scan_begin_src
);
723 err
|= comedi_check_trigger_is_unique(cmd
->convert_src
);
724 err
|= comedi_check_trigger_is_unique(cmd
->stop_src
);
726 /* Step 2b : and mutually compatible */
728 if (cmd
->scan_begin_src
== TRIG_FOLLOW
&& cmd
->convert_src
== TRIG_NOW
)
730 if (cmd
->scan_begin_src
!= TRIG_FOLLOW
&& cmd
->convert_src
!= TRIG_NOW
)
732 if (cmd
->start_src
== TRIG_EXT
&&
733 (cmd
->convert_src
== TRIG_EXT
|| cmd
->scan_begin_src
== TRIG_EXT
))
739 /* Step 3: check if arguments are trivially valid */
741 switch (cmd
->start_src
) {
743 err
|= comedi_check_trigger_arg_is(&cmd
->start_arg
, 0);
746 /* External trigger, only CR_EDGE and CR_INVERT flags allowed */
748 & (CR_FLAGS_MASK
& ~(CR_EDGE
| CR_INVERT
))) != 0) {
749 cmd
->start_arg
&= ~(CR_FLAGS_MASK
&
750 ~(CR_EDGE
| CR_INVERT
));
753 if (!board
->is_1602
&& (cmd
->start_arg
& CR_INVERT
)) {
754 cmd
->start_arg
&= (CR_FLAGS_MASK
& ~CR_INVERT
);
760 if (cmd
->scan_begin_src
== TRIG_TIMER
) {
761 err
|= comedi_check_trigger_arg_min(&cmd
->scan_begin_arg
,
766 if (cmd
->convert_src
== TRIG_TIMER
) {
767 err
|= comedi_check_trigger_arg_min(&cmd
->convert_arg
,
771 err
|= comedi_check_trigger_arg_is(&cmd
->scan_end_arg
,
774 if (cmd
->stop_src
== TRIG_COUNT
)
775 err
|= comedi_check_trigger_arg_min(&cmd
->stop_arg
, 1);
777 err
|= comedi_check_trigger_arg_is(&cmd
->stop_arg
, 0);
782 /* step 4: fix up any arguments */
784 if (cmd
->scan_begin_src
== TRIG_TIMER
) {
785 arg
= cmd
->scan_begin_arg
;
786 comedi_8254_cascade_ns_to_timer(dev
->pacer
, &arg
, cmd
->flags
);
787 err
|= comedi_check_trigger_arg_is(&cmd
->scan_begin_arg
, arg
);
789 if (cmd
->convert_src
== TRIG_TIMER
) {
790 arg
= cmd
->convert_arg
;
791 comedi_8254_cascade_ns_to_timer(dev
->pacer
, &arg
, cmd
->flags
);
792 err
|= comedi_check_trigger_arg_is(&cmd
->convert_arg
, arg
);
798 /* Step 5: check channel list if it exists */
799 if (cmd
->chanlist
&& cmd
->chanlist_len
> 0)
800 err
|= cb_pcidas_ai_check_chanlist(dev
, s
, cmd
);
808 static int cb_pcidas_ai_cmd(struct comedi_device
*dev
,
809 struct comedi_subdevice
*s
)
811 const struct cb_pcidas_board
*board
= dev
->board_ptr
;
812 struct cb_pcidas_private
*devpriv
= dev
->private;
813 struct comedi_async
*async
= s
->async
;
814 struct comedi_cmd
*cmd
= &async
->cmd
;
815 unsigned int range0
= CR_RANGE(cmd
->chanlist
[0]);
819 /* make sure PCIDAS_CALIB_EN is disabled */
820 outw(0, devpriv
->pcibar1
+ PCIDAS_CALIB_REG
);
821 /* initialize before settings pacer source and count values */
822 outw(PCIDAS_TRIG_SEL_NONE
, devpriv
->pcibar1
+ PCIDAS_TRIG_REG
);
824 outw(0, devpriv
->pcibar2
+ PCIDAS_AI_FIFO_CLR_REG
);
826 /* set mux limits, gain and pacer source */
827 bits
= PCIDAS_AI_FIRST(CR_CHAN(cmd
->chanlist
[0])) |
828 PCIDAS_AI_LAST(CR_CHAN(cmd
->chanlist
[cmd
->chanlist_len
- 1])) |
829 PCIDAS_AI_GAIN(range0
);
830 /* set unipolar/bipolar */
831 if (comedi_range_is_unipolar(s
, range0
))
832 bits
|= PCIDAS_AI_UNIP
;
833 /* set singleended/differential */
834 if (CR_AREF(cmd
->chanlist
[0]) != AREF_DIFF
)
835 bits
|= PCIDAS_AI_SE
;
836 /* set pacer source */
837 if (cmd
->convert_src
== TRIG_EXT
|| cmd
->scan_begin_src
== TRIG_EXT
)
838 bits
|= PCIDAS_AI_PACER_EXTP
;
840 bits
|= PCIDAS_AI_PACER_INT
;
841 outw(bits
, devpriv
->pcibar1
+ PCIDAS_AI_REG
);
844 if (cmd
->scan_begin_src
== TRIG_TIMER
||
845 cmd
->convert_src
== TRIG_TIMER
) {
846 comedi_8254_update_divisors(dev
->pacer
);
847 comedi_8254_pacer_enable(dev
->pacer
, 1, 2, true);
850 /* enable interrupts */
851 spin_lock_irqsave(&dev
->spinlock
, flags
);
852 devpriv
->ctrl
|= PCIDAS_CTRL_INTE
;
853 devpriv
->ctrl
&= ~PCIDAS_CTRL_INT_MASK
;
854 if (cmd
->flags
& CMDF_WAKE_EOS
) {
855 if (cmd
->convert_src
== TRIG_NOW
&& cmd
->chanlist_len
> 1) {
856 /* interrupt end of burst */
857 devpriv
->ctrl
|= PCIDAS_CTRL_INT_EOS
;
859 /* interrupt fifo not empty */
860 devpriv
->ctrl
|= PCIDAS_CTRL_INT_FNE
;
863 /* interrupt fifo half full */
864 devpriv
->ctrl
|= PCIDAS_CTRL_INT_FHF
;
867 /* enable (and clear) interrupts */
869 PCIDAS_CTRL_EOAI
| PCIDAS_CTRL_INT_CLR
| PCIDAS_CTRL_LADFUL
,
870 devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
871 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
873 /* set start trigger and burst mode */
875 if (cmd
->start_src
== TRIG_NOW
) {
876 bits
|= PCIDAS_TRIG_SEL_SW
;
877 } else { /* TRIG_EXT */
878 bits
|= PCIDAS_TRIG_SEL_EXT
| PCIDAS_TRIG_EN
| PCIDAS_TRIG_CLR
;
879 if (board
->is_1602
) {
880 if (cmd
->start_arg
& CR_INVERT
)
881 bits
|= PCIDAS_TRIG_POL
;
882 if (cmd
->start_arg
& CR_EDGE
)
883 bits
|= PCIDAS_TRIG_MODE
;
886 if (cmd
->convert_src
== TRIG_NOW
&& cmd
->chanlist_len
> 1)
887 bits
|= PCIDAS_TRIG_BURSTE
;
888 outw(bits
, devpriv
->pcibar1
+ PCIDAS_TRIG_REG
);
893 static int cb_pcidas_ao_check_chanlist(struct comedi_device
*dev
,
894 struct comedi_subdevice
*s
,
895 struct comedi_cmd
*cmd
)
897 unsigned int chan0
= CR_CHAN(cmd
->chanlist
[0]);
899 if (cmd
->chanlist_len
> 1) {
900 unsigned int chan1
= CR_CHAN(cmd
->chanlist
[1]);
902 if (chan0
!= 0 || chan1
!= 1) {
903 dev_dbg(dev
->class_dev
,
904 "channels must be ordered channel 0, channel 1 in chanlist\n");
912 static int cb_pcidas_ao_cmdtest(struct comedi_device
*dev
,
913 struct comedi_subdevice
*s
,
914 struct comedi_cmd
*cmd
)
916 const struct cb_pcidas_board
*board
= dev
->board_ptr
;
917 struct cb_pcidas_private
*devpriv
= dev
->private;
920 /* Step 1 : check if triggers are trivially valid */
922 err
|= comedi_check_trigger_src(&cmd
->start_src
, TRIG_INT
);
923 err
|= comedi_check_trigger_src(&cmd
->scan_begin_src
,
924 TRIG_TIMER
| TRIG_EXT
);
925 err
|= comedi_check_trigger_src(&cmd
->convert_src
, TRIG_NOW
);
926 err
|= comedi_check_trigger_src(&cmd
->scan_end_src
, TRIG_COUNT
);
927 err
|= comedi_check_trigger_src(&cmd
->stop_src
, TRIG_COUNT
| TRIG_NONE
);
932 /* Step 2a : make sure trigger sources are unique */
934 err
|= comedi_check_trigger_is_unique(cmd
->scan_begin_src
);
935 err
|= comedi_check_trigger_is_unique(cmd
->stop_src
);
937 /* Step 2b : and mutually compatible */
942 /* Step 3: check if arguments are trivially valid */
944 err
|= comedi_check_trigger_arg_is(&cmd
->start_arg
, 0);
946 if (cmd
->scan_begin_src
== TRIG_TIMER
) {
947 err
|= comedi_check_trigger_arg_min(&cmd
->scan_begin_arg
,
948 board
->ao_scan_speed
);
951 err
|= comedi_check_trigger_arg_is(&cmd
->scan_end_arg
,
954 if (cmd
->stop_src
== TRIG_COUNT
)
955 err
|= comedi_check_trigger_arg_min(&cmd
->stop_arg
, 1);
957 err
|= comedi_check_trigger_arg_is(&cmd
->stop_arg
, 0);
962 /* step 4: fix up any arguments */
964 if (cmd
->scan_begin_src
== TRIG_TIMER
) {
965 unsigned int arg
= cmd
->scan_begin_arg
;
967 comedi_8254_cascade_ns_to_timer(devpriv
->ao_pacer
,
969 err
|= comedi_check_trigger_arg_is(&cmd
->scan_begin_arg
, arg
);
975 /* Step 5: check channel list if it exists */
976 if (cmd
->chanlist
&& cmd
->chanlist_len
> 0)
977 err
|= cb_pcidas_ao_check_chanlist(dev
, s
, cmd
);
985 /* cancel analog input command */
986 static int cb_pcidas_cancel(struct comedi_device
*dev
,
987 struct comedi_subdevice
*s
)
989 struct cb_pcidas_private
*devpriv
= dev
->private;
992 spin_lock_irqsave(&dev
->spinlock
, flags
);
993 /* disable interrupts */
994 devpriv
->ctrl
&= ~(PCIDAS_CTRL_INTE
| PCIDAS_CTRL_EOAIE
);
995 outw(devpriv
->ctrl
, devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
996 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
998 /* disable start trigger source and burst mode */
999 outw(PCIDAS_TRIG_SEL_NONE
, devpriv
->pcibar1
+ PCIDAS_TRIG_REG
);
1000 outw(PCIDAS_AI_PACER_SW
, devpriv
->pcibar1
+ PCIDAS_AI_REG
);
1005 static void cb_pcidas_ao_load_fifo(struct comedi_device
*dev
,
1006 struct comedi_subdevice
*s
,
1007 unsigned int nsamples
)
1009 struct cb_pcidas_private
*devpriv
= dev
->private;
1010 unsigned int nbytes
;
1012 nsamples
= comedi_nsamples_left(s
, nsamples
);
1013 nbytes
= comedi_buf_read_samples(s
, devpriv
->ao_buffer
, nsamples
);
1015 nsamples
= comedi_bytes_to_samples(s
, nbytes
);
1016 outsw(devpriv
->pcibar4
+ PCIDAS_AO_FIFO_REG
,
1017 devpriv
->ao_buffer
, nsamples
);
1020 static int cb_pcidas_ao_inttrig(struct comedi_device
*dev
,
1021 struct comedi_subdevice
*s
,
1022 unsigned int trig_num
)
1024 const struct cb_pcidas_board
*board
= dev
->board_ptr
;
1025 struct cb_pcidas_private
*devpriv
= dev
->private;
1026 struct comedi_async
*async
= s
->async
;
1027 struct comedi_cmd
*cmd
= &async
->cmd
;
1028 unsigned long flags
;
1030 if (trig_num
!= cmd
->start_arg
)
1033 cb_pcidas_ao_load_fifo(dev
, s
, board
->fifo_size
);
1035 /* enable dac half-full and empty interrupts */
1036 spin_lock_irqsave(&dev
->spinlock
, flags
);
1037 devpriv
->ctrl
|= PCIDAS_CTRL_DAEMIE
| PCIDAS_CTRL_DAHFIE
;
1039 /* enable and clear interrupts */
1040 outw(devpriv
->ctrl
| PCIDAS_CTRL_DAEMI
| PCIDAS_CTRL_DAHFI
,
1041 devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
1044 devpriv
->ao_ctrl
|= PCIDAS_AO_START
| PCIDAS_AO_DACEN
| PCIDAS_AO_EMPTY
;
1045 outw(devpriv
->ao_ctrl
, devpriv
->pcibar1
+ PCIDAS_AO_REG
);
1047 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1049 async
->inttrig
= NULL
;
1054 static int cb_pcidas_ao_cmd(struct comedi_device
*dev
,
1055 struct comedi_subdevice
*s
)
1057 struct cb_pcidas_private
*devpriv
= dev
->private;
1058 struct comedi_async
*async
= s
->async
;
1059 struct comedi_cmd
*cmd
= &async
->cmd
;
1061 unsigned long flags
;
1063 /* set channel limits, gain */
1064 spin_lock_irqsave(&dev
->spinlock
, flags
);
1065 for (i
= 0; i
< cmd
->chanlist_len
; i
++) {
1066 unsigned int chan
= CR_CHAN(cmd
->chanlist
[i
]);
1067 unsigned int range
= CR_RANGE(cmd
->chanlist
[i
]);
1069 /* enable channel */
1070 devpriv
->ao_ctrl
|= PCIDAS_AO_CHAN_EN(chan
);
1072 devpriv
->ao_ctrl
|= PCIDAS_AO_RANGE(chan
, range
);
1075 /* disable analog out before settings pacer source and count values */
1076 outw(devpriv
->ao_ctrl
, devpriv
->pcibar1
+ PCIDAS_AO_REG
);
1077 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1080 outw(0, devpriv
->pcibar4
+ PCIDAS_AO_FIFO_CLR_REG
);
1083 if (cmd
->scan_begin_src
== TRIG_TIMER
) {
1084 comedi_8254_update_divisors(devpriv
->ao_pacer
);
1085 comedi_8254_pacer_enable(devpriv
->ao_pacer
, 1, 2, true);
1088 /* set pacer source */
1089 spin_lock_irqsave(&dev
->spinlock
, flags
);
1090 switch (cmd
->scan_begin_src
) {
1092 devpriv
->ao_ctrl
|= PCIDAS_AO_PACER_INT
;
1095 devpriv
->ao_ctrl
|= PCIDAS_AO_PACER_EXTP
;
1098 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1099 dev_err(dev
->class_dev
, "error setting dac pacer source\n");
1102 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1104 async
->inttrig
= cb_pcidas_ao_inttrig
;
1109 /* cancel analog output command */
1110 static int cb_pcidas_ao_cancel(struct comedi_device
*dev
,
1111 struct comedi_subdevice
*s
)
1113 struct cb_pcidas_private
*devpriv
= dev
->private;
1114 unsigned long flags
;
1116 spin_lock_irqsave(&dev
->spinlock
, flags
);
1117 /* disable interrupts */
1118 devpriv
->ctrl
&= ~(PCIDAS_CTRL_DAHFIE
| PCIDAS_CTRL_DAEMIE
);
1119 outw(devpriv
->ctrl
, devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
1121 /* disable output */
1122 devpriv
->ao_ctrl
&= ~(PCIDAS_AO_DACEN
| PCIDAS_AO_PACER_MASK
);
1123 outw(devpriv
->ao_ctrl
, devpriv
->pcibar1
+ PCIDAS_AO_REG
);
1124 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1129 static void handle_ao_interrupt(struct comedi_device
*dev
, unsigned int status
)
1131 const struct cb_pcidas_board
*board
= dev
->board_ptr
;
1132 struct cb_pcidas_private
*devpriv
= dev
->private;
1133 struct comedi_subdevice
*s
= dev
->write_subdev
;
1134 struct comedi_async
*async
= s
->async
;
1135 struct comedi_cmd
*cmd
= &async
->cmd
;
1136 unsigned long flags
;
1138 if (status
& PCIDAS_CTRL_DAEMI
) {
1139 /* clear dac empty interrupt latch */
1140 spin_lock_irqsave(&dev
->spinlock
, flags
);
1141 outw(devpriv
->ctrl
| PCIDAS_CTRL_DAEMI
,
1142 devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
1143 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1144 if (inw(devpriv
->pcibar4
+ PCIDAS_AO_REG
) & PCIDAS_AO_EMPTY
) {
1145 if (cmd
->stop_src
== TRIG_COUNT
&&
1146 async
->scans_done
>= cmd
->stop_arg
) {
1147 async
->events
|= COMEDI_CB_EOA
;
1149 dev_err(dev
->class_dev
, "dac fifo underflow\n");
1150 async
->events
|= COMEDI_CB_ERROR
;
1153 } else if (status
& PCIDAS_CTRL_DAHFI
) {
1154 cb_pcidas_ao_load_fifo(dev
, s
, board
->fifo_size
/ 2);
1156 /* clear half-full interrupt latch */
1157 spin_lock_irqsave(&dev
->spinlock
, flags
);
1158 outw(devpriv
->ctrl
| PCIDAS_CTRL_DAHFI
,
1159 devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
1160 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1163 comedi_handle_events(dev
, s
);
1166 static irqreturn_t
cb_pcidas_interrupt(int irq
, void *d
)
1168 struct comedi_device
*dev
= d
;
1169 const struct cb_pcidas_board
*board
= dev
->board_ptr
;
1170 struct cb_pcidas_private
*devpriv
= dev
->private;
1171 struct comedi_subdevice
*s
= dev
->read_subdev
;
1172 struct comedi_async
*async
;
1173 struct comedi_cmd
*cmd
;
1174 int status
, s5933_status
;
1175 int half_fifo
= board
->fifo_size
/ 2;
1176 unsigned int num_samples
, i
;
1177 static const int timeout
= 10000;
1178 unsigned long flags
;
1186 s5933_status
= inl(devpriv
->s5933_config
+ AMCC_OP_REG_INTCSR
);
1188 if ((INTCSR_INTR_ASSERTED
& s5933_status
) == 0)
1191 /* make sure mailbox 4 is empty */
1192 inl_p(devpriv
->s5933_config
+ AMCC_OP_REG_IMB4
);
1193 /* clear interrupt on amcc s5933 */
1194 outl(devpriv
->s5933_intcsr_bits
| INTCSR_INBOX_INTR_STATUS
,
1195 devpriv
->s5933_config
+ AMCC_OP_REG_INTCSR
);
1197 status
= inw(devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
1199 /* check for analog output interrupt */
1200 if (status
& (PCIDAS_CTRL_DAHFI
| PCIDAS_CTRL_DAEMI
))
1201 handle_ao_interrupt(dev
, status
);
1202 /* check for analog input interrupts */
1203 /* if fifo half-full */
1204 if (status
& PCIDAS_CTRL_ADHFI
) {
1206 num_samples
= comedi_nsamples_left(s
, half_fifo
);
1207 insw(devpriv
->pcibar2
+ PCIDAS_AI_DATA_REG
,
1208 devpriv
->ai_buffer
, num_samples
);
1209 comedi_buf_write_samples(s
, devpriv
->ai_buffer
, num_samples
);
1211 if (cmd
->stop_src
== TRIG_COUNT
&&
1212 async
->scans_done
>= cmd
->stop_arg
)
1213 async
->events
|= COMEDI_CB_EOA
;
1215 /* clear half-full interrupt latch */
1216 spin_lock_irqsave(&dev
->spinlock
, flags
);
1217 outw(devpriv
->ctrl
| PCIDAS_CTRL_INT_CLR
,
1218 devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
1219 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1220 /* else if fifo not empty */
1221 } else if (status
& (PCIDAS_CTRL_ADNEI
| PCIDAS_CTRL_EOBI
)) {
1222 for (i
= 0; i
< timeout
; i
++) {
1225 /* break if fifo is empty */
1226 if ((inw(devpriv
->pcibar1
+ PCIDAS_CTRL_REG
) &
1227 PCIDAS_CTRL_ADNE
) == 0)
1229 val
= inw(devpriv
->pcibar2
+ PCIDAS_AI_DATA_REG
);
1230 comedi_buf_write_samples(s
, &val
, 1);
1232 if (cmd
->stop_src
== TRIG_COUNT
&&
1233 async
->scans_done
>= cmd
->stop_arg
) {
1234 async
->events
|= COMEDI_CB_EOA
;
1238 /* clear not-empty interrupt latch */
1239 spin_lock_irqsave(&dev
->spinlock
, flags
);
1240 outw(devpriv
->ctrl
| PCIDAS_CTRL_INT_CLR
,
1241 devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
1242 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1243 } else if (status
& PCIDAS_CTRL_EOAI
) {
1244 dev_err(dev
->class_dev
,
1245 "bug! encountered end of acquisition interrupt?\n");
1246 /* clear EOA interrupt latch */
1247 spin_lock_irqsave(&dev
->spinlock
, flags
);
1248 outw(devpriv
->ctrl
| PCIDAS_CTRL_EOAI
,
1249 devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
1250 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1252 /* check for fifo overflow */
1253 if (status
& PCIDAS_CTRL_LADFUL
) {
1254 dev_err(dev
->class_dev
, "fifo overflow\n");
1255 /* clear overflow interrupt latch */
1256 spin_lock_irqsave(&dev
->spinlock
, flags
);
1257 outw(devpriv
->ctrl
| PCIDAS_CTRL_LADFUL
,
1258 devpriv
->pcibar1
+ PCIDAS_CTRL_REG
);
1259 spin_unlock_irqrestore(&dev
->spinlock
, flags
);
1260 async
->events
|= COMEDI_CB_ERROR
;
1263 comedi_handle_events(dev
, s
);
1268 static int cb_pcidas_auto_attach(struct comedi_device
*dev
,
1269 unsigned long context
)
1271 struct pci_dev
*pcidev
= comedi_to_pci_dev(dev
);
1272 const struct cb_pcidas_board
*board
= NULL
;
1273 struct cb_pcidas_private
*devpriv
;
1274 struct comedi_subdevice
*s
;
1278 if (context
< ARRAY_SIZE(cb_pcidas_boards
))
1279 board
= &cb_pcidas_boards
[context
];
1282 dev
->board_ptr
= board
;
1283 dev
->board_name
= board
->name
;
1285 devpriv
= comedi_alloc_devpriv(dev
, sizeof(*devpriv
));
1289 ret
= comedi_pci_enable(dev
);
1293 devpriv
->s5933_config
= pci_resource_start(pcidev
, 0);
1294 devpriv
->pcibar1
= pci_resource_start(pcidev
, 1);
1295 devpriv
->pcibar2
= pci_resource_start(pcidev
, 2);
1296 dev
->iobase
= pci_resource_start(pcidev
, 3);
1298 devpriv
->pcibar4
= pci_resource_start(pcidev
, 4);
1300 /* disable and clear interrupts on amcc s5933 */
1301 outl(INTCSR_INBOX_INTR_STATUS
,
1302 devpriv
->s5933_config
+ AMCC_OP_REG_INTCSR
);
1304 ret
= request_irq(pcidev
->irq
, cb_pcidas_interrupt
, IRQF_SHARED
,
1305 dev
->board_name
, dev
);
1307 dev_dbg(dev
->class_dev
, "unable to allocate irq %d\n",
1311 dev
->irq
= pcidev
->irq
;
1313 dev
->pacer
= comedi_8254_init(dev
->iobase
+ PCIDAS_AI_8254_BASE
,
1314 I8254_OSC_BASE_10MHZ
, I8254_IO8
, 0);
1318 devpriv
->ao_pacer
= comedi_8254_init(dev
->iobase
+ PCIDAS_AO_8254_BASE
,
1319 I8254_OSC_BASE_10MHZ
,
1321 if (!devpriv
->ao_pacer
)
1324 ret
= comedi_alloc_subdevices(dev
, 7);
1328 s
= &dev
->subdevices
[0];
1329 /* analog input subdevice */
1330 dev
->read_subdev
= s
;
1331 s
->type
= COMEDI_SUBD_AI
;
1332 s
->subdev_flags
= SDF_READABLE
| SDF_GROUND
| SDF_DIFF
| SDF_CMD_READ
;
1333 /* WARNING: Number of inputs in differential mode is ignored */
1335 s
->len_chanlist
= s
->n_chan
;
1336 s
->maxdata
= board
->is_16bit
? 0xffff : 0x0fff;
1337 s
->range_table
= board
->use_alt_range
? &cb_pcidas_alt_ranges
1338 : &cb_pcidas_ranges
;
1339 s
->insn_read
= cb_pcidas_ai_rinsn
;
1340 s
->insn_config
= ai_config_insn
;
1341 s
->do_cmd
= cb_pcidas_ai_cmd
;
1342 s
->do_cmdtest
= cb_pcidas_ai_cmdtest
;
1343 s
->cancel
= cb_pcidas_cancel
;
1345 /* analog output subdevice */
1346 s
= &dev
->subdevices
[1];
1347 if (board
->has_ao
) {
1348 s
->type
= COMEDI_SUBD_AO
;
1349 s
->subdev_flags
= SDF_READABLE
| SDF_WRITABLE
| SDF_GROUND
;
1351 s
->maxdata
= board
->is_16bit
? 0xffff : 0x0fff;
1352 s
->range_table
= &cb_pcidas_ao_ranges
;
1353 /* default to no fifo (*insn_write) */
1354 s
->insn_write
= cb_pcidas_ao_nofifo_winsn
;
1356 ret
= comedi_alloc_subdev_readback(s
);
1360 if (board
->has_ao_fifo
) {
1361 dev
->write_subdev
= s
;
1362 s
->subdev_flags
|= SDF_CMD_WRITE
;
1363 /* use fifo (*insn_write) instead */
1364 s
->insn_write
= cb_pcidas_ao_fifo_winsn
;
1365 s
->do_cmdtest
= cb_pcidas_ao_cmdtest
;
1366 s
->do_cmd
= cb_pcidas_ao_cmd
;
1367 s
->cancel
= cb_pcidas_ao_cancel
;
1370 s
->type
= COMEDI_SUBD_UNUSED
;
1374 s
= &dev
->subdevices
[2];
1375 ret
= subdev_8255_init(dev
, s
, NULL
, PCIDAS_8255_BASE
);
1379 /* serial EEPROM, */
1380 s
= &dev
->subdevices
[3];
1381 s
->type
= COMEDI_SUBD_MEMORY
;
1382 s
->subdev_flags
= SDF_READABLE
| SDF_INTERNAL
;
1385 s
->insn_read
= eeprom_read_insn
;
1388 s
= &dev
->subdevices
[4];
1389 s
->type
= COMEDI_SUBD_CALIB
;
1390 s
->subdev_flags
= SDF_READABLE
| SDF_WRITABLE
| SDF_INTERNAL
;
1393 s
->insn_write
= cb_pcidas_caldac_insn_write
;
1395 ret
= comedi_alloc_subdev_readback(s
);
1399 for (i
= 0; i
< s
->n_chan
; i
++) {
1400 unsigned int val
= s
->maxdata
/ 2;
1402 /* write 11-bit channel/value to caldac */
1403 cb_pcidas_calib_write(dev
, (i
<< 8) | val
, 11, false);
1404 s
->readback
[i
] = val
;
1407 /* Calibration subdevice - trim potentiometer */
1408 s
= &dev
->subdevices
[5];
1409 s
->type
= COMEDI_SUBD_CALIB
;
1410 s
->subdev_flags
= SDF_WRITABLE
| SDF_INTERNAL
;
1411 if (board
->trimpot
== AD7376
) {
1414 } else { /* AD8402 */
1416 * For pci-das1602/16:
1418 * chan 1 : adc postgain offset
1423 s
->insn_write
= cb_pcidas_trimpot_insn_write
;
1425 ret
= comedi_alloc_subdev_readback(s
);
1429 for (i
= 0; i
< s
->n_chan
; i
++) {
1430 cb_pcidas_trimpot_write(dev
, i
, s
->maxdata
/ 2);
1431 s
->readback
[i
] = s
->maxdata
/ 2;
1435 s
= &dev
->subdevices
[6];
1436 if (board
->has_dac08
) {
1437 s
->type
= COMEDI_SUBD_CALIB
;
1438 s
->subdev_flags
= SDF_READABLE
| SDF_WRITABLE
| SDF_INTERNAL
;
1441 s
->insn_write
= cb_pcidas_dac08_insn_write
;
1443 ret
= comedi_alloc_subdev_readback(s
);
1447 for (i
= 0; i
< s
->n_chan
; i
++) {
1448 dac08_write(dev
, s
->maxdata
/ 2);
1449 s
->readback
[i
] = s
->maxdata
/ 2;
1452 s
->type
= COMEDI_SUBD_UNUSED
;
1455 /* make sure mailbox 4 is empty */
1456 inl(devpriv
->s5933_config
+ AMCC_OP_REG_IMB4
);
1457 /* Set bits to enable incoming mailbox interrupts on amcc s5933. */
1458 devpriv
->s5933_intcsr_bits
=
1459 INTCSR_INBOX_BYTE(3) | INTCSR_INBOX_SELECT(3) |
1460 INTCSR_INBOX_FULL_INT
;
1461 /* clear and enable interrupt on amcc s5933 */
1462 outl(devpriv
->s5933_intcsr_bits
| INTCSR_INBOX_INTR_STATUS
,
1463 devpriv
->s5933_config
+ AMCC_OP_REG_INTCSR
);
1468 static void cb_pcidas_detach(struct comedi_device
*dev
)
1470 struct cb_pcidas_private
*devpriv
= dev
->private;
1473 if (devpriv
->s5933_config
)
1474 outl(INTCSR_INBOX_INTR_STATUS
,
1475 devpriv
->s5933_config
+ AMCC_OP_REG_INTCSR
);
1476 kfree(devpriv
->ao_pacer
);
1478 comedi_pci_detach(dev
);
1481 static struct comedi_driver cb_pcidas_driver
= {
1482 .driver_name
= "cb_pcidas",
1483 .module
= THIS_MODULE
,
1484 .auto_attach
= cb_pcidas_auto_attach
,
1485 .detach
= cb_pcidas_detach
,
1488 static int cb_pcidas_pci_probe(struct pci_dev
*dev
,
1489 const struct pci_device_id
*id
)
1491 return comedi_pci_auto_config(dev
, &cb_pcidas_driver
,
1495 static const struct pci_device_id cb_pcidas_pci_table
[] = {
1496 { PCI_VDEVICE(CB
, 0x0001), BOARD_PCIDAS1602_16
},
1497 { PCI_VDEVICE(CB
, 0x000f), BOARD_PCIDAS1200
},
1498 { PCI_VDEVICE(CB
, 0x0010), BOARD_PCIDAS1602_12
},
1499 { PCI_VDEVICE(CB
, 0x0019), BOARD_PCIDAS1200_JR
},
1500 { PCI_VDEVICE(CB
, 0x001c), BOARD_PCIDAS1602_16_JR
},
1501 { PCI_VDEVICE(CB
, 0x004c), BOARD_PCIDAS1000
},
1502 { PCI_VDEVICE(CB
, 0x001a), BOARD_PCIDAS1001
},
1503 { PCI_VDEVICE(CB
, 0x001b), BOARD_PCIDAS1002
},
1506 MODULE_DEVICE_TABLE(pci
, cb_pcidas_pci_table
);
1508 static struct pci_driver cb_pcidas_pci_driver
= {
1509 .name
= "cb_pcidas",
1510 .id_table
= cb_pcidas_pci_table
,
1511 .probe
= cb_pcidas_pci_probe
,
1512 .remove
= comedi_pci_auto_unconfig
,
1514 module_comedi_pci_driver(cb_pcidas_driver
, cb_pcidas_pci_driver
);
1516 MODULE_AUTHOR("Comedi http://www.comedi.org");
1517 MODULE_DESCRIPTION("Comedi low-level driver");
1518 MODULE_LICENSE("GPL");