Update broken web addresses in the kernel.
[deliverable/linux.git] / drivers / staging / comedi / drivers / rtd520.c
1 /*
2 comedi/drivers/rtd520.c
3 Comedi driver for Real Time Devices (RTD) PCI4520/DM7520
4
5 COMEDI - Linux Control and Measurement Device Interface
6 Copyright (C) 2001 David A. Schleef <ds@schleef.org>
7
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 */
22 /*
23 Driver: rtd520
24 Description: Real Time Devices PCI4520/DM7520
25 Author: Dan Christian
26 Devices: [Real Time Devices] DM7520HR-1 (rtd520), DM7520HR-8,
27 PCI4520, PCI4520-8
28 Status: Works. Only tested on DM7520-8. Not SMP safe.
29
30 Configuration options:
31 [0] - PCI bus of device (optional)
32 If bus/slot is not specified, the first available PCI
33 device will be used.
34 [1] - PCI slot of device (optional)
35 */
36 /*
37 Created by Dan Christian, NASA Ames Research Center.
38
39 The PCI4520 is a PCI card. The DM7520 is a PC/104-plus card.
40 Both have:
41 8/16 12 bit ADC with FIFO and channel gain table
42 8 bits high speed digital out (for external MUX) (or 8 in or 8 out)
43 8 bits high speed digital in with FIFO and interrupt on change (or 8 IO)
44 2 12 bit DACs with FIFOs
45 2 bits output
46 2 bits input
47 bus mastering DMA
48 timers: ADC sample, pacer, burst, about, delay, DA1, DA2
49 sample counter
50 3 user timer/counters (8254)
51 external interrupt
52
53 The DM7520 has slightly fewer features (fewer gain steps).
54
55 These boards can support external multiplexors and multi-board
56 synchronization, but this driver doesn't support that.
57
58 Board docs: http://www.rtdusa.com/PC104/DM/analog%20IO/dm7520.htm
59 Data sheet: http://www.rtdusa.com/pdf/dm7520.pdf
60 Example source: http://www.rtdusa.com/examples/dm/dm7520.zip
61 Call them and ask for the register level manual.
62 PCI chip: http://www.plxtech.com/products/io/pci9080
63
64 Notes:
65 This board is memory mapped. There is some IO stuff, but it isn't needed.
66
67 I use a pretty loose naming style within the driver (rtd_blah).
68 All externally visible names should be rtd520_blah.
69 I use camelCase for structures (and inside them).
70 I may also use upper CamelCase for function names (old habit).
71
72 This board is somewhat related to the RTD PCI4400 board.
73
74 I borrowed heavily from the ni_mio_common, ni_atmio16d, mite, and
75 das1800, since they have the best documented code. Driver
76 cb_pcidas64.c uses the same DMA controller.
77
78 As far as I can tell, the About interrupt doesnt work if Sample is
79 also enabled. It turns out that About really isn't needed, since
80 we always count down samples read.
81
82 There was some timer/counter code, but it didn't follow the right API.
83
84 */
85
86 /*
87 driver status:
88
89 Analog-In supports instruction and command mode.
90
91 With DMA, you can sample at 1.15Mhz with 70% idle on a 400Mhz K6-2
92 (single channel, 64K read buffer). I get random system lockups when
93 using DMA with ALI-15xx based systems. I haven't been able to test
94 any other chipsets. The lockups happen soon after the start of an
95 acquistion, not in the middle of a long run.
96
97 Without DMA, you can do 620Khz sampling with 20% idle on a 400Mhz K6-2
98 (with a 256K read buffer).
99
100 Digital-IO and Analog-Out only support instruction mode.
101
102 */
103
104 #include <linux/interrupt.h>
105 #include <linux/delay.h>
106
107 #include "../comedidev.h"
108 #include "comedi_pci.h"
109
110 #define DRV_NAME "rtd520"
111
112 /*======================================================================
113 Driver specific stuff (tunable)
114 ======================================================================*/
115 /* Enable this to test the new DMA support. You may get hard lock ups */
116 /*#define USE_DMA*/
117
118 /* We really only need 2 buffers. More than that means being much
119 smarter about knowing which ones are full. */
120 #define DMA_CHAIN_COUNT 2 /* max DMA segments/buffers in a ring (min 2) */
121
122 /* Target period for periodic transfers. This sets the user read latency. */
123 /* Note: There are certain rates where we give this up and transfer 1/2 FIFO */
124 /* If this is too low, efficiency is poor */
125 #define TRANS_TARGET_PERIOD 10000000 /* 10 ms (in nanoseconds) */
126
127 /* Set a practical limit on how long a list to support (affects memory use) */
128 /* The board support a channel list up to the FIFO length (1K or 8K) */
129 #define RTD_MAX_CHANLIST 128 /* max channel list that we allow */
130
131 /* tuning for ai/ao instruction done polling */
132 #ifdef FAST_SPIN
133 #define WAIT_QUIETLY /* as nothing, spin on done bit */
134 #define RTD_ADC_TIMEOUT 66000 /* 2 msec at 33mhz bus rate */
135 #define RTD_DAC_TIMEOUT 66000
136 #define RTD_DMA_TIMEOUT 33000 /* 1 msec */
137 #else
138 /* by delaying, power and electrical noise are reduced somewhat */
139 #define WAIT_QUIETLY udelay (1)
140 #define RTD_ADC_TIMEOUT 2000 /* in usec */
141 #define RTD_DAC_TIMEOUT 2000 /* in usec */
142 #define RTD_DMA_TIMEOUT 1000 /* in usec */
143 #endif
144
145 /*======================================================================
146 Board specific stuff
147 ======================================================================*/
148
149 /* registers */
150 #define PCI_VENDOR_ID_RTD 0x1435
151 /*
152 The board has three memory windows: las0, las1, and lcfg (the PCI chip)
153 Las1 has the data and can be burst DMAed 32bits at a time.
154 */
155 #define LCFG_PCIINDEX 0
156 /* PCI region 1 is a 256 byte IO space mapping. Use??? */
157 #define LAS0_PCIINDEX 2 /* PCI memory resources */
158 #define LAS1_PCIINDEX 3
159 #define LCFG_PCISIZE 0x100
160 #define LAS0_PCISIZE 0x200
161 #define LAS1_PCISIZE 0x10
162
163 #define RTD_CLOCK_RATE 8000000 /* 8Mhz onboard clock */
164 #define RTD_CLOCK_BASE 125 /* clock period in ns */
165
166 /* Note: these speed are slower than the spec, but fit the counter resolution*/
167 #define RTD_MAX_SPEED 1625 /* when sampling, in nanoseconds */
168 /* max speed if we don't have to wait for settling */
169 #define RTD_MAX_SPEED_1 875 /* if single channel, in nanoseconds */
170
171 #define RTD_MIN_SPEED 2097151875 /* (24bit counter) in nanoseconds */
172 /* min speed when only 1 channel (no burst counter) */
173 #define RTD_MIN_SPEED_1 5000000 /* 200Hz, in nanoseconds */
174
175 #include "rtd520.h"
176 #include "plx9080.h"
177
178 /* Setup continuous ring of 1/2 FIFO transfers. See RTD manual p91 */
179 #define DMA_MODE_BITS (\
180 PLX_LOCAL_BUS_16_WIDE_BITS \
181 | PLX_DMA_EN_READYIN_BIT \
182 | PLX_DMA_LOCAL_BURST_EN_BIT \
183 | PLX_EN_CHAIN_BIT \
184 | PLX_DMA_INTR_PCI_BIT \
185 | PLX_LOCAL_ADDR_CONST_BIT \
186 | PLX_DEMAND_MODE_BIT)
187
188 #define DMA_TRANSFER_BITS (\
189 /* descriptors in PCI memory*/ PLX_DESC_IN_PCI_BIT \
190 /* interrupt at end of block */ | PLX_INTR_TERM_COUNT \
191 /* from board to PCI */ | PLX_XFER_LOCAL_TO_PCI)
192
193 /*======================================================================
194 Comedi specific stuff
195 ======================================================================*/
196
197 /*
198 The board has 3 input modes and the gains of 1,2,4,...32 (, 64, 128)
199 */
200 static const struct comedi_lrange rtd_ai_7520_range = { 18, {
201 /* +-5V input range gain steps */
202 BIP_RANGE(5.0),
203 BIP_RANGE(5.0 / 2),
204 BIP_RANGE(5.0 / 4),
205 BIP_RANGE(5.0 / 8),
206 BIP_RANGE(5.0 /
207 16),
208 BIP_RANGE(5.0 /
209 32),
210 /* +-10V input range gain steps */
211 BIP_RANGE(10.0),
212 BIP_RANGE(10.0 /
213 2),
214 BIP_RANGE(10.0 /
215 4),
216 BIP_RANGE(10.0 /
217 8),
218 BIP_RANGE(10.0 /
219 16),
220 BIP_RANGE(10.0 /
221 32),
222 /* +10V input range gain steps */
223 UNI_RANGE(10.0),
224 UNI_RANGE(10.0 /
225 2),
226 UNI_RANGE(10.0 /
227 4),
228 UNI_RANGE(10.0 /
229 8),
230 UNI_RANGE(10.0 /
231 16),
232 UNI_RANGE(10.0 /
233 32),
234
235 }
236 };
237
238 /* PCI4520 has two more gains (6 more entries) */
239 static const struct comedi_lrange rtd_ai_4520_range = { 24, {
240 /* +-5V input range gain steps */
241 BIP_RANGE(5.0),
242 BIP_RANGE(5.0 / 2),
243 BIP_RANGE(5.0 / 4),
244 BIP_RANGE(5.0 / 8),
245 BIP_RANGE(5.0 /
246 16),
247 BIP_RANGE(5.0 /
248 32),
249 BIP_RANGE(5.0 /
250 64),
251 BIP_RANGE(5.0 /
252 128),
253 /* +-10V input range gain steps */
254 BIP_RANGE(10.0),
255 BIP_RANGE(10.0 /
256 2),
257 BIP_RANGE(10.0 /
258 4),
259 BIP_RANGE(10.0 /
260 8),
261 BIP_RANGE(10.0 /
262 16),
263 BIP_RANGE(10.0 /
264 32),
265 BIP_RANGE(10.0 /
266 64),
267 BIP_RANGE(10.0 /
268 128),
269 /* +10V input range gain steps */
270 UNI_RANGE(10.0),
271 UNI_RANGE(10.0 /
272 2),
273 UNI_RANGE(10.0 /
274 4),
275 UNI_RANGE(10.0 /
276 8),
277 UNI_RANGE(10.0 /
278 16),
279 UNI_RANGE(10.0 /
280 32),
281 UNI_RANGE(10.0 /
282 64),
283 UNI_RANGE(10.0 /
284 128),
285 }
286 };
287
288 /* Table order matches range values */
289 static const struct comedi_lrange rtd_ao_range = { 4, {
290 RANGE(0, 5),
291 RANGE(0, 10),
292 RANGE(-5, 5),
293 RANGE(-10, 10),
294 }
295 };
296
297 /*
298 Board descriptions
299 */
300 struct rtdBoard {
301 const char *name; /* must be first */
302 int device_id;
303 int aiChans;
304 int aiBits;
305 int aiMaxGain;
306 int range10Start; /* start of +-10V range */
307 int rangeUniStart; /* start of +10V range */
308 };
309
310 static const struct rtdBoard rtd520Boards[] = {
311 {
312 .name = "DM7520",
313 .device_id = 0x7520,
314 .aiChans = 16,
315 .aiBits = 12,
316 .aiMaxGain = 32,
317 .range10Start = 6,
318 .rangeUniStart = 12,
319 },
320 {
321 .name = "PCI4520",
322 .device_id = 0x4520,
323 .aiChans = 16,
324 .aiBits = 12,
325 .aiMaxGain = 128,
326 .range10Start = 8,
327 .rangeUniStart = 16,
328 },
329 };
330
331 static DEFINE_PCI_DEVICE_TABLE(rtd520_pci_table) = {
332 {
333 PCI_VENDOR_ID_RTD, 0x7520, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, {
334 PCI_VENDOR_ID_RTD, 0x4520, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, {
335 0}
336 };
337
338 MODULE_DEVICE_TABLE(pci, rtd520_pci_table);
339
340 /*
341 * Useful for shorthand access to the particular board structure
342 */
343 #define thisboard ((const struct rtdBoard *)dev->board_ptr)
344
345 /*
346 This structure is for data unique to this hardware driver.
347 This is also unique for each board in the system.
348 */
349 struct rtdPrivate {
350 /* memory mapped board structures */
351 void *las0;
352 void *las1;
353 void *lcfg;
354
355 unsigned long intCount; /* interrupt count */
356 long aiCount; /* total transfer size (samples) */
357 int transCount; /* # to tranfer data. 0->1/2FIFO */
358 int flags; /* flag event modes */
359
360 /* PCI device info */
361 struct pci_dev *pci_dev;
362 int got_regions; /* non-zero if PCI regions owned */
363
364 /* channel list info */
365 /* chanBipolar tracks whether a channel is bipolar (and needs +2048) */
366 unsigned char chanBipolar[RTD_MAX_CHANLIST / 8]; /* bit array */
367
368 /* read back data */
369 unsigned int aoValue[2]; /* Used for AO read back */
370
371 /* timer gate (when enabled) */
372 u8 utcGate[4]; /* 1 extra allows simple range check */
373
374 /* shadow registers affect other registers, but cant be read back */
375 /* The macros below update these on writes */
376 u16 intMask; /* interrupt mask */
377 u16 intClearMask; /* interrupt clear mask */
378 u8 utcCtrl[4]; /* crtl mode for 3 utc + read back */
379 u8 dioStatus; /* could be read back (dio0Ctrl) */
380 #ifdef USE_DMA
381 /* Always DMA 1/2 FIFO. Buffer (dmaBuff?) is (at least) twice that size.
382 After transferring, interrupt processes 1/2 FIFO and passes to comedi */
383 s16 dma0Offset; /* current processing offset (0, 1/2) */
384 uint16_t *dma0Buff[DMA_CHAIN_COUNT]; /* DMA buffers (for ADC) */
385 dma_addr_t dma0BuffPhysAddr[DMA_CHAIN_COUNT]; /* physical addresses */
386 struct plx_dma_desc *dma0Chain; /* DMA descriptor ring for dmaBuff */
387 dma_addr_t dma0ChainPhysAddr; /* physical addresses */
388 /* shadow registers */
389 u8 dma0Control;
390 u8 dma1Control;
391 #endif /* USE_DMA */
392 unsigned fifoLen;
393 };
394
395 /* bit defines for "flags" */
396 #define SEND_EOS 0x01 /* send End Of Scan events */
397 #define DMA0_ACTIVE 0x02 /* DMA0 is active */
398 #define DMA1_ACTIVE 0x04 /* DMA1 is active */
399
400 /* Macros for accessing channel list bit array */
401 #define CHAN_ARRAY_TEST(array, index) \
402 (((array)[(index)/8] >> ((index) & 0x7)) & 0x1)
403 #define CHAN_ARRAY_SET(array, index) \
404 (((array)[(index)/8] |= 1 << ((index) & 0x7)))
405 #define CHAN_ARRAY_CLEAR(array, index) \
406 (((array)[(index)/8] &= ~(1 << ((index) & 0x7))))
407
408 /*
409 * most drivers define the following macro to make it easy to
410 * access the private structure.
411 */
412 #define devpriv ((struct rtdPrivate *)dev->private)
413
414 /* Macros to access registers */
415
416 /* Reset board */
417 #define RtdResetBoard(dev) \
418 writel (0, devpriv->las0+LAS0_BOARD_RESET)
419
420 /* Reset channel gain table read pointer */
421 #define RtdResetCGT(dev) \
422 writel (0, devpriv->las0+LAS0_CGT_RESET)
423
424 /* Reset channel gain table read and write pointers */
425 #define RtdClearCGT(dev) \
426 writel (0, devpriv->las0+LAS0_CGT_CLEAR)
427
428 /* Reset channel gain table read and write pointers */
429 #define RtdEnableCGT(dev, v) \
430 writel ((v > 0) ? 1 : 0, devpriv->las0+LAS0_CGT_ENABLE)
431
432 /* Write channel gain table entry */
433 #define RtdWriteCGTable(dev, v) \
434 writel (v, devpriv->las0+LAS0_CGT_WRITE)
435
436 /* Write Channel Gain Latch */
437 #define RtdWriteCGLatch(dev, v) \
438 writel (v, devpriv->las0+LAS0_CGL_WRITE)
439
440 /* Reset ADC FIFO */
441 #define RtdAdcClearFifo(dev) \
442 writel (0, devpriv->las0+LAS0_ADC_FIFO_CLEAR)
443
444 /* Set ADC start conversion source select (write only) */
445 #define RtdAdcConversionSource(dev, v) \
446 writel (v, devpriv->las0+LAS0_ADC_CONVERSION)
447
448 /* Set burst start source select (write only) */
449 #define RtdBurstStartSource(dev, v) \
450 writel (v, devpriv->las0+LAS0_BURST_START)
451
452 /* Set Pacer start source select (write only) */
453 #define RtdPacerStartSource(dev, v) \
454 writel (v, devpriv->las0+LAS0_PACER_START)
455
456 /* Set Pacer stop source select (write only) */
457 #define RtdPacerStopSource(dev, v) \
458 writel (v, devpriv->las0+LAS0_PACER_STOP)
459
460 /* Set Pacer clock source select (write only) 0=external 1=internal */
461 #define RtdPacerClockSource(dev, v) \
462 writel ((v > 0) ? 1 : 0, devpriv->las0+LAS0_PACER_SELECT)
463
464 /* Set sample counter source select (write only) */
465 #define RtdAdcSampleCounterSource(dev, v) \
466 writel (v, devpriv->las0+LAS0_ADC_SCNT_SRC)
467
468 /* Set Pacer trigger mode select (write only) 0=single cycle, 1=repeat */
469 #define RtdPacerTriggerMode(dev, v) \
470 writel ((v > 0) ? 1 : 0, devpriv->las0+LAS0_PACER_REPEAT)
471
472 /* Set About counter stop enable (write only) */
473 #define RtdAboutStopEnable(dev, v) \
474 writel ((v > 0) ? 1 : 0, devpriv->las0+LAS0_ACNT_STOP_ENABLE)
475
476 /* Set external trigger polarity (write only) 0=positive edge, 1=negative */
477 #define RtdTriggerPolarity(dev, v) \
478 writel ((v > 0) ? 1 : 0, devpriv->las0+LAS0_ETRG_POLARITY)
479
480 /* Start single ADC conversion */
481 #define RtdAdcStart(dev) \
482 writew (0, devpriv->las0+LAS0_ADC)
483
484 /* Read one ADC data value (12bit (with sign extend) as 16bit) */
485 /* Note: matches what DMA would get. Actual value >> 3 */
486 #define RtdAdcFifoGet(dev) \
487 readw (devpriv->las1+LAS1_ADC_FIFO)
488
489 /* Read two ADC data values (DOESNT WORK) */
490 #define RtdAdcFifoGet2(dev) \
491 readl (devpriv->las1+LAS1_ADC_FIFO)
492
493 /* FIFO status */
494 #define RtdFifoStatus(dev) \
495 readl (devpriv->las0+LAS0_ADC)
496
497 /* pacer start/stop read=start, write=stop*/
498 #define RtdPacerStart(dev) \
499 readl (devpriv->las0+LAS0_PACER)
500 #define RtdPacerStop(dev) \
501 writel (0, devpriv->las0+LAS0_PACER)
502
503 /* Interrupt status */
504 #define RtdInterruptStatus(dev) \
505 readw (devpriv->las0+LAS0_IT)
506
507 /* Interrupt mask */
508 #define RtdInterruptMask(dev, v) \
509 writew ((devpriv->intMask = (v)), devpriv->las0+LAS0_IT)
510
511 /* Interrupt status clear (only bits set in mask) */
512 #define RtdInterruptClear(dev) \
513 readw (devpriv->las0+LAS0_CLEAR)
514
515 /* Interrupt clear mask */
516 #define RtdInterruptClearMask(dev, v) \
517 writew ((devpriv->intClearMask = (v)), devpriv->las0+LAS0_CLEAR)
518
519 /* Interrupt overrun status */
520 #define RtdInterruptOverrunStatus(dev) \
521 readl (devpriv->las0+LAS0_OVERRUN)
522
523 /* Interrupt overrun clear */
524 #define RtdInterruptOverrunClear(dev) \
525 writel (0, devpriv->las0+LAS0_OVERRUN)
526
527 /* Pacer counter, 24bit */
528 #define RtdPacerCount(dev) \
529 readl (devpriv->las0+LAS0_PCLK)
530 #define RtdPacerCounter(dev, v) \
531 writel ((v) & 0xffffff, devpriv->las0+LAS0_PCLK)
532
533 /* Burst counter, 10bit */
534 #define RtdBurstCount(dev) \
535 readl (devpriv->las0+LAS0_BCLK)
536 #define RtdBurstCounter(dev, v) \
537 writel ((v) & 0x3ff, devpriv->las0+LAS0_BCLK)
538
539 /* Delay counter, 16bit */
540 #define RtdDelayCount(dev) \
541 readl (devpriv->las0+LAS0_DCLK)
542 #define RtdDelayCounter(dev, v) \
543 writel ((v) & 0xffff, devpriv->las0+LAS0_DCLK)
544
545 /* About counter, 16bit */
546 #define RtdAboutCount(dev) \
547 readl (devpriv->las0+LAS0_ACNT)
548 #define RtdAboutCounter(dev, v) \
549 writel ((v) & 0xffff, devpriv->las0+LAS0_ACNT)
550
551 /* ADC sample counter, 10bit */
552 #define RtdAdcSampleCount(dev) \
553 readl (devpriv->las0+LAS0_ADC_SCNT)
554 #define RtdAdcSampleCounter(dev, v) \
555 writel ((v) & 0x3ff, devpriv->las0+LAS0_ADC_SCNT)
556
557 /* User Timer/Counter (8254) */
558 #define RtdUtcCounterGet(dev, n) \
559 readb (devpriv->las0 \
560 + ((n <= 0) ? LAS0_UTC0 : ((1 == n) ? LAS0_UTC1 : LAS0_UTC2)))
561
562 #define RtdUtcCounterPut(dev, n, v) \
563 writeb ((v) & 0xff, devpriv->las0 \
564 + ((n <= 0) ? LAS0_UTC0 : ((1 == n) ? LAS0_UTC1 : LAS0_UTC2)))
565
566 /* Set UTC (8254) control byte */
567 #define RtdUtcCtrlPut(dev, n, v) \
568 writeb (devpriv->utcCtrl[(n) & 3] = (((n) & 3) << 6) | ((v) & 0x3f), \
569 devpriv->las0 + LAS0_UTC_CTRL)
570
571 /* Set UTCn clock source (write only) */
572 #define RtdUtcClockSource(dev, n, v) \
573 writew (v, devpriv->las0 \
574 + ((n <= 0) ? LAS0_UTC0_CLOCK : \
575 ((1 == n) ? LAS0_UTC1_CLOCK : LAS0_UTC2_CLOCK)))
576
577 /* Set UTCn gate source (write only) */
578 #define RtdUtcGateSource(dev, n, v) \
579 writew (v, devpriv->las0 \
580 + ((n <= 0) ? LAS0_UTC0_GATE : \
581 ((1 == n) ? LAS0_UTC1_GATE : LAS0_UTC2_GATE)))
582
583 /* User output N source select (write only) */
584 #define RtdUsrOutSource(dev, n, v) \
585 writel (v, devpriv->las0+((n <= 0) ? LAS0_UOUT0_SELECT : LAS0_UOUT1_SELECT))
586
587 /* Digital IO */
588 #define RtdDio0Read(dev) \
589 (readw (devpriv->las0+LAS0_DIO0) & 0xff)
590 #define RtdDio0Write(dev, v) \
591 writew ((v) & 0xff, devpriv->las0+LAS0_DIO0)
592
593 #define RtdDio1Read(dev) \
594 (readw (devpriv->las0+LAS0_DIO1) & 0xff)
595 #define RtdDio1Write(dev, v) \
596 writew ((v) & 0xff, devpriv->las0+LAS0_DIO1)
597
598 #define RtdDioStatusRead(dev) \
599 (readw (devpriv->las0+LAS0_DIO_STATUS) & 0xff)
600 #define RtdDioStatusWrite(dev, v) \
601 writew ((devpriv->dioStatus = (v)), devpriv->las0+LAS0_DIO_STATUS)
602
603 #define RtdDio0CtrlRead(dev) \
604 (readw (devpriv->las0+LAS0_DIO0_CTRL) & 0xff)
605 #define RtdDio0CtrlWrite(dev, v) \
606 writew ((v) & 0xff, devpriv->las0+LAS0_DIO0_CTRL)
607
608 /* Digital to Analog converter */
609 /* Write one data value (sign + 12bit + marker bits) */
610 /* Note: matches what DMA would put. Actual value << 3 */
611 #define RtdDacFifoPut(dev, n, v) \
612 writew ((v), devpriv->las1 +(((n) == 0) ? LAS1_DAC1_FIFO : LAS1_DAC2_FIFO))
613
614 /* Start single DAC conversion */
615 #define RtdDacUpdate(dev, n) \
616 writew (0, devpriv->las0 +(((n) == 0) ? LAS0_DAC1 : LAS0_DAC2))
617
618 /* Start single DAC conversion on both DACs */
619 #define RtdDacBothUpdate(dev) \
620 writew (0, devpriv->las0+LAS0_DAC)
621
622 /* Set DAC output type and range */
623 #define RtdDacRange(dev, n, v) \
624 writew ((v) & 7, devpriv->las0 \
625 +(((n) == 0) ? LAS0_DAC1_CTRL : LAS0_DAC2_CTRL))
626
627 /* Reset DAC FIFO */
628 #define RtdDacClearFifo(dev, n) \
629 writel (0, devpriv->las0+(((n) == 0) ? LAS0_DAC1_RESET : LAS0_DAC2_RESET))
630
631 /* Set source for DMA 0 (write only, shadow?) */
632 #define RtdDma0Source(dev, n) \
633 writel ((n) & 0xf, devpriv->las0+LAS0_DMA0_SRC)
634
635 /* Set source for DMA 1 (write only, shadow?) */
636 #define RtdDma1Source(dev, n) \
637 writel ((n) & 0xf, devpriv->las0+LAS0_DMA1_SRC)
638
639 /* Reset board state for DMA 0 */
640 #define RtdDma0Reset(dev) \
641 writel (0, devpriv->las0+LAS0_DMA0_RESET)
642
643 /* Reset board state for DMA 1 */
644 #define RtdDma1Reset(dev) \
645 writel (0, devpriv->las0+LAS0_DMA1_SRC)
646
647 /* PLX9080 interrupt mask and status */
648 #define RtdPlxInterruptRead(dev) \
649 readl (devpriv->lcfg+LCFG_ITCSR)
650 #define RtdPlxInterruptWrite(dev, v) \
651 writel (v, devpriv->lcfg+LCFG_ITCSR)
652
653 /* Set mode for DMA 0 */
654 #define RtdDma0Mode(dev, m) \
655 writel ((m), devpriv->lcfg+LCFG_DMAMODE0)
656
657 /* Set PCI address for DMA 0 */
658 #define RtdDma0PciAddr(dev, a) \
659 writel ((a), devpriv->lcfg+LCFG_DMAPADR0)
660
661 /* Set local address for DMA 0 */
662 #define RtdDma0LocalAddr(dev, a) \
663 writel ((a), devpriv->lcfg+LCFG_DMALADR0)
664
665 /* Set byte count for DMA 0 */
666 #define RtdDma0Count(dev, c) \
667 writel ((c), devpriv->lcfg+LCFG_DMASIZ0)
668
669 /* Set next descriptor for DMA 0 */
670 #define RtdDma0Next(dev, a) \
671 writel ((a), devpriv->lcfg+LCFG_DMADPR0)
672
673 /* Set mode for DMA 1 */
674 #define RtdDma1Mode(dev, m) \
675 writel ((m), devpriv->lcfg+LCFG_DMAMODE1)
676
677 /* Set PCI address for DMA 1 */
678 #define RtdDma1PciAddr(dev, a) \
679 writel ((a), devpriv->lcfg+LCFG_DMAADR1)
680
681 /* Set local address for DMA 1 */
682 #define RtdDma1LocalAddr(dev, a) \
683 writel ((a), devpriv->lcfg+LCFG_DMALADR1)
684
685 /* Set byte count for DMA 1 */
686 #define RtdDma1Count(dev, c) \
687 writel ((c), devpriv->lcfg+LCFG_DMASIZ1)
688
689 /* Set next descriptor for DMA 1 */
690 #define RtdDma1Next(dev, a) \
691 writel ((a), devpriv->lcfg+LCFG_DMADPR1)
692
693 /* Set control for DMA 0 (write only, shadow?) */
694 #define RtdDma0Control(dev, n) \
695 writeb (devpriv->dma0Control = (n), devpriv->lcfg+LCFG_DMACSR0)
696
697 /* Get status for DMA 0 */
698 #define RtdDma0Status(dev) \
699 readb (devpriv->lcfg+LCFG_DMACSR0)
700
701 /* Set control for DMA 1 (write only, shadow?) */
702 #define RtdDma1Control(dev, n) \
703 writeb (devpriv->dma1Control = (n), devpriv->lcfg+LCFG_DMACSR1)
704
705 /* Get status for DMA 1 */
706 #define RtdDma1Status(dev) \
707 readb (devpriv->lcfg+LCFG_DMACSR1)
708
709 /*
710 * The struct comedi_driver structure tells the Comedi core module
711 * which functions to call to configure/deconfigure (attac/detach)
712 * the board, and also about the kernel module that contains
713 * the device code.
714 */
715 static int rtd_attach(struct comedi_device *dev, struct comedi_devconfig *it);
716 static int rtd_detach(struct comedi_device *dev);
717
718 static struct comedi_driver rtd520Driver = {
719 .driver_name = DRV_NAME,
720 .module = THIS_MODULE,
721 .attach = rtd_attach,
722 .detach = rtd_detach,
723 };
724
725 static int rtd_ai_rinsn(struct comedi_device *dev, struct comedi_subdevice *s,
726 struct comedi_insn *insn, unsigned int *data);
727 static int rtd_ao_winsn(struct comedi_device *dev, struct comedi_subdevice *s,
728 struct comedi_insn *insn, unsigned int *data);
729 static int rtd_ao_rinsn(struct comedi_device *dev, struct comedi_subdevice *s,
730 struct comedi_insn *insn, unsigned int *data);
731 static int rtd_dio_insn_bits(struct comedi_device *dev,
732 struct comedi_subdevice *s,
733 struct comedi_insn *insn, unsigned int *data);
734 static int rtd_dio_insn_config(struct comedi_device *dev,
735 struct comedi_subdevice *s,
736 struct comedi_insn *insn, unsigned int *data);
737 static int rtd_ai_cmdtest(struct comedi_device *dev, struct comedi_subdevice *s,
738 struct comedi_cmd *cmd);
739 static int rtd_ai_cmd(struct comedi_device *dev, struct comedi_subdevice *s);
740 static int rtd_ai_cancel(struct comedi_device *dev, struct comedi_subdevice *s);
741 /* static int rtd_ai_poll (struct comedi_device *dev,struct comedi_subdevice *s); */
742 static int rtd_ns_to_timer(unsigned int *ns, int roundMode);
743 static irqreturn_t rtd_interrupt(int irq, void *d);
744 static int rtd520_probe_fifo_depth(struct comedi_device *dev);
745
746 /*
747 * Attach is called by the Comedi core to configure the driver
748 * for a particular board. If you specified a board_name array
749 * in the driver structure, dev->board_ptr contains that
750 * address.
751 */
752 static int rtd_attach(struct comedi_device *dev, struct comedi_devconfig *it)
753 { /* board name and options flags */
754 struct comedi_subdevice *s;
755 struct pci_dev *pcidev;
756 int ret;
757 resource_size_t physLas0; /* configuation */
758 resource_size_t physLas1; /* data area */
759 resource_size_t physLcfg; /* PLX9080 */
760 #ifdef USE_DMA
761 int index;
762 #endif
763
764 printk("comedi%d: rtd520 attaching.\n", dev->minor);
765
766 #if defined (CONFIG_COMEDI_DEBUG) && defined (USE_DMA)
767 /* You can set this a load time: modprobe comedi comedi_debug=1 */
768 if (0 == comedi_debug) /* force DMA debug printks */
769 comedi_debug = 1;
770 #endif
771
772 /*
773 * Allocate the private structure area. alloc_private() is a
774 * convenient macro defined in comedidev.h.
775 */
776 if (alloc_private(dev, sizeof(struct rtdPrivate)) < 0)
777 return -ENOMEM;
778
779 /*
780 * Probe the device to determine what device in the series it is.
781 */
782 for (pcidev = pci_get_device(PCI_VENDOR_ID_RTD, PCI_ANY_ID, NULL);
783 pcidev != NULL;
784 pcidev = pci_get_device(PCI_VENDOR_ID_RTD, PCI_ANY_ID, pcidev)) {
785 int i;
786
787 if (it->options[0] || it->options[1]) {
788 if (pcidev->bus->number != it->options[0]
789 || PCI_SLOT(pcidev->devfn) != it->options[1]) {
790 continue;
791 }
792 }
793 for (i = 0; i < ARRAY_SIZE(rtd520Boards); ++i) {
794 if (pcidev->device == rtd520Boards[i].device_id) {
795 dev->board_ptr = &rtd520Boards[i];
796 break;
797 }
798 }
799 if (dev->board_ptr)
800 break; /* found one */
801 }
802 if (!pcidev) {
803 if (it->options[0] && it->options[1]) {
804 printk("No RTD card at bus=%d slot=%d.\n",
805 it->options[0], it->options[1]);
806 } else {
807 printk("No RTD card found.\n");
808 }
809 return -EIO;
810 }
811 devpriv->pci_dev = pcidev;
812 dev->board_name = thisboard->name;
813
814 ret = comedi_pci_enable(pcidev, DRV_NAME);
815 if (ret < 0) {
816 printk("Failed to enable PCI device and request regions.\n");
817 return ret;
818 }
819 devpriv->got_regions = 1;
820
821 /*
822 * Initialize base addresses
823 */
824 /* Get the physical address from PCI config */
825 physLas0 = pci_resource_start(devpriv->pci_dev, LAS0_PCIINDEX);
826 physLas1 = pci_resource_start(devpriv->pci_dev, LAS1_PCIINDEX);
827 physLcfg = pci_resource_start(devpriv->pci_dev, LCFG_PCIINDEX);
828 /* Now have the kernel map this into memory */
829 /* ASSUME page aligned */
830 devpriv->las0 = ioremap_nocache(physLas0, LAS0_PCISIZE);
831 devpriv->las1 = ioremap_nocache(physLas1, LAS1_PCISIZE);
832 devpriv->lcfg = ioremap_nocache(physLcfg, LCFG_PCISIZE);
833
834 if (!devpriv->las0 || !devpriv->las1 || !devpriv->lcfg) {
835 return -ENOMEM;
836 }
837
838 DPRINTK("%s: LAS0=%llx, LAS1=%llx, CFG=%llx.\n", dev->board_name,
839 (unsigned long long)physLas0, (unsigned long long)physLas1,
840 (unsigned long long)physLcfg);
841 { /* The RTD driver does this */
842 unsigned char pci_latency;
843 u16 revision;
844 /*uint32_t epld_version; */
845
846 pci_read_config_word(devpriv->pci_dev, PCI_REVISION_ID,
847 &revision);
848 DPRINTK("%s: PCI revision %d.\n", dev->board_name, revision);
849
850 pci_read_config_byte(devpriv->pci_dev,
851 PCI_LATENCY_TIMER, &pci_latency);
852 if (pci_latency < 32) {
853 printk("%s: PCI latency changed from %d to %d\n",
854 dev->board_name, pci_latency, 32);
855 pci_write_config_byte(devpriv->pci_dev,
856 PCI_LATENCY_TIMER, 32);
857 } else {
858 DPRINTK("rtd520: PCI latency = %d\n", pci_latency);
859 }
860
861 /* Undocumented EPLD version (doesnt match RTD driver results) */
862 /*DPRINTK ("rtd520: Reading epld from %p\n",
863 devpriv->las0+0);
864 epld_version = readl (devpriv->las0+0);
865 if ((epld_version & 0xF0) >> 4 == 0x0F) {
866 DPRINTK("rtd520: pre-v8 EPLD. (%x)\n", epld_version);
867 } else {
868 DPRINTK("rtd520: EPLD version %x.\n", epld_version >> 4);
869 } */
870 }
871
872 /* Show board configuration */
873 printk("%s:", dev->board_name);
874
875 /*
876 * Allocate the subdevice structures. alloc_subdevice() is a
877 * convenient macro defined in comedidev.h.
878 */
879 if (alloc_subdevices(dev, 4) < 0) {
880 return -ENOMEM;
881 }
882
883 s = dev->subdevices + 0;
884 dev->read_subdev = s;
885 /* analog input subdevice */
886 s->type = COMEDI_SUBD_AI;
887 s->subdev_flags =
888 SDF_READABLE | SDF_GROUND | SDF_COMMON | SDF_DIFF | SDF_CMD_READ;
889 s->n_chan = thisboard->aiChans;
890 s->maxdata = (1 << thisboard->aiBits) - 1;
891 if (thisboard->aiMaxGain <= 32) {
892 s->range_table = &rtd_ai_7520_range;
893 } else {
894 s->range_table = &rtd_ai_4520_range;
895 }
896 s->len_chanlist = RTD_MAX_CHANLIST; /* devpriv->fifoLen */
897 s->insn_read = rtd_ai_rinsn;
898 s->do_cmd = rtd_ai_cmd;
899 s->do_cmdtest = rtd_ai_cmdtest;
900 s->cancel = rtd_ai_cancel;
901 /* s->poll = rtd_ai_poll; *//* not ready yet */
902
903 s = dev->subdevices + 1;
904 /* analog output subdevice */
905 s->type = COMEDI_SUBD_AO;
906 s->subdev_flags = SDF_WRITABLE;
907 s->n_chan = 2;
908 s->maxdata = (1 << thisboard->aiBits) - 1;
909 s->range_table = &rtd_ao_range;
910 s->insn_write = rtd_ao_winsn;
911 s->insn_read = rtd_ao_rinsn;
912
913 s = dev->subdevices + 2;
914 /* digital i/o subdevice */
915 s->type = COMEDI_SUBD_DIO;
916 s->subdev_flags = SDF_READABLE | SDF_WRITABLE;
917 /* we only support port 0 right now. Ignoring port 1 and user IO */
918 s->n_chan = 8;
919 s->maxdata = 1;
920 s->range_table = &range_digital;
921 s->insn_bits = rtd_dio_insn_bits;
922 s->insn_config = rtd_dio_insn_config;
923
924 /* timer/counter subdevices (not currently supported) */
925 s = dev->subdevices + 3;
926 s->type = COMEDI_SUBD_COUNTER;
927 s->subdev_flags = SDF_READABLE | SDF_WRITABLE;
928 s->n_chan = 3;
929 s->maxdata = 0xffff;
930
931 /* initialize board, per RTD spec */
932 /* also, initialize shadow registers */
933 RtdResetBoard(dev);
934 udelay(100); /* needed? */
935 RtdPlxInterruptWrite(dev, 0);
936 RtdInterruptMask(dev, 0); /* and sets shadow */
937 RtdInterruptClearMask(dev, ~0); /* and sets shadow */
938 RtdInterruptClear(dev); /* clears bits set by mask */
939 RtdInterruptOverrunClear(dev);
940 RtdClearCGT(dev);
941 RtdAdcClearFifo(dev);
942 RtdDacClearFifo(dev, 0);
943 RtdDacClearFifo(dev, 1);
944 /* clear digital IO fifo */
945 RtdDioStatusWrite(dev, 0); /* safe state, set shadow */
946 RtdUtcCtrlPut(dev, 0, 0x30); /* safe state, set shadow */
947 RtdUtcCtrlPut(dev, 1, 0x30); /* safe state, set shadow */
948 RtdUtcCtrlPut(dev, 2, 0x30); /* safe state, set shadow */
949 RtdUtcCtrlPut(dev, 3, 0); /* safe state, set shadow */
950 /* TODO: set user out source ??? */
951
952 /* check if our interrupt is available and get it */
953 ret = request_irq(devpriv->pci_dev->irq, rtd_interrupt,
954 IRQF_SHARED, DRV_NAME, dev);
955
956 if (ret < 0) {
957 printk("Could not get interrupt! (%u)\n",
958 devpriv->pci_dev->irq);
959 return ret;
960 }
961 dev->irq = devpriv->pci_dev->irq;
962 printk("( irq=%u )", dev->irq);
963
964 ret = rtd520_probe_fifo_depth(dev);
965 if (ret < 0) {
966 return ret;
967 }
968 devpriv->fifoLen = ret;
969 printk("( fifoLen=%d )", devpriv->fifoLen);
970
971 #ifdef USE_DMA
972 if (dev->irq > 0) {
973 printk("( DMA buff=%d )\n", DMA_CHAIN_COUNT);
974 /* The PLX9080 has 2 DMA controllers, but there could be 4 sources:
975 ADC, digital, DAC1, and DAC2. Since only the ADC supports cmd mode
976 right now, this isn't an issue (yet) */
977 devpriv->dma0Offset = 0;
978
979 for (index = 0; index < DMA_CHAIN_COUNT; index++) {
980 devpriv->dma0Buff[index] =
981 pci_alloc_consistent(devpriv->pci_dev,
982 sizeof(u16) *
983 devpriv->fifoLen / 2,
984 &devpriv->
985 dma0BuffPhysAddr[index]);
986 if (devpriv->dma0Buff[index] == NULL) {
987 ret = -ENOMEM;
988 goto rtd_attach_die_error;
989 }
990 /*DPRINTK ("buff[%d] @ %p virtual, %x PCI\n",
991 index,
992 devpriv->dma0Buff[index], devpriv->dma0BuffPhysAddr[index]); */
993 }
994
995 /* setup DMA descriptor ring (use cpu_to_le32 for byte ordering?) */
996 devpriv->dma0Chain =
997 pci_alloc_consistent(devpriv->pci_dev,
998 sizeof(struct plx_dma_desc) *
999 DMA_CHAIN_COUNT,
1000 &devpriv->dma0ChainPhysAddr);
1001 for (index = 0; index < DMA_CHAIN_COUNT; index++) {
1002 devpriv->dma0Chain[index].pci_start_addr =
1003 devpriv->dma0BuffPhysAddr[index];
1004 devpriv->dma0Chain[index].local_start_addr =
1005 DMALADDR_ADC;
1006 devpriv->dma0Chain[index].transfer_size =
1007 sizeof(u16) * devpriv->fifoLen / 2;
1008 devpriv->dma0Chain[index].next =
1009 (devpriv->dma0ChainPhysAddr + ((index +
1010 1) %
1011 (DMA_CHAIN_COUNT))
1012 * sizeof(devpriv->dma0Chain[0]))
1013 | DMA_TRANSFER_BITS;
1014 /*DPRINTK ("ring[%d] @%lx PCI: %x, local: %x, N: 0x%x, next: %x\n",
1015 index,
1016 ((long)devpriv->dma0ChainPhysAddr
1017 + (index * sizeof(devpriv->dma0Chain[0]))),
1018 devpriv->dma0Chain[index].pci_start_addr,
1019 devpriv->dma0Chain[index].local_start_addr,
1020 devpriv->dma0Chain[index].transfer_size,
1021 devpriv->dma0Chain[index].next); */
1022 }
1023
1024 if (devpriv->dma0Chain == NULL) {
1025 ret = -ENOMEM;
1026 goto rtd_attach_die_error;
1027 }
1028
1029 RtdDma0Mode(dev, DMA_MODE_BITS);
1030 RtdDma0Source(dev, DMAS_ADFIFO_HALF_FULL); /* set DMA trigger source */
1031 } else {
1032 printk("( no IRQ->no DMA )");
1033 }
1034 #endif /* USE_DMA */
1035
1036 if (dev->irq) { /* enable plx9080 interrupts */
1037 RtdPlxInterruptWrite(dev, ICS_PIE | ICS_PLIE);
1038 }
1039
1040 printk("\ncomedi%d: rtd520 driver attached.\n", dev->minor);
1041
1042 return 1;
1043
1044 #if 0
1045 /* hit an error, clean up memory and return ret */
1046 /* rtd_attach_die_error: */
1047 #ifdef USE_DMA
1048 for (index = 0; index < DMA_CHAIN_COUNT; index++) {
1049 if (NULL != devpriv->dma0Buff[index]) { /* free buffer memory */
1050 pci_free_consistent(devpriv->pci_dev,
1051 sizeof(u16) * devpriv->fifoLen / 2,
1052 devpriv->dma0Buff[index],
1053 devpriv->dma0BuffPhysAddr[index]);
1054 devpriv->dma0Buff[index] = NULL;
1055 }
1056 }
1057 if (NULL != devpriv->dma0Chain) {
1058 pci_free_consistent(devpriv->pci_dev,
1059 sizeof(struct plx_dma_desc)
1060 * DMA_CHAIN_COUNT,
1061 devpriv->dma0Chain,
1062 devpriv->dma0ChainPhysAddr);
1063 devpriv->dma0Chain = NULL;
1064 }
1065 #endif /* USE_DMA */
1066 /* subdevices and priv are freed by the core */
1067 if (dev->irq) {
1068 /* disable interrupt controller */
1069 RtdPlxInterruptWrite(dev, RtdPlxInterruptRead(dev)
1070 & ~(ICS_PLIE | ICS_DMA0_E | ICS_DMA1_E));
1071 free_irq(dev->irq, dev);
1072 }
1073
1074 /* release all regions that were allocated */
1075 if (devpriv->las0) {
1076 iounmap(devpriv->las0);
1077 }
1078 if (devpriv->las1) {
1079 iounmap(devpriv->las1);
1080 }
1081 if (devpriv->lcfg) {
1082 iounmap(devpriv->lcfg);
1083 }
1084 if (devpriv->pci_dev) {
1085 pci_dev_put(devpriv->pci_dev);
1086 }
1087 return ret;
1088 #endif
1089 }
1090
1091 /*
1092 * _detach is called to deconfigure a device. It should deallocate
1093 * resources.
1094 * This function is also called when _attach() fails, so it should be
1095 * careful not to release resources that were not necessarily
1096 * allocated by _attach(). dev->private and dev->subdevices are
1097 * deallocated automatically by the core.
1098 */
1099 static int rtd_detach(struct comedi_device *dev)
1100 {
1101 #ifdef USE_DMA
1102 int index;
1103 #endif
1104
1105 DPRINTK("comedi%d: rtd520: removing (%ld ints)\n",
1106 dev->minor, (devpriv ? devpriv->intCount : 0L));
1107 if (devpriv && devpriv->lcfg) {
1108 DPRINTK
1109 ("(int status 0x%x, overrun status 0x%x, fifo status 0x%x)...\n",
1110 0xffff & RtdInterruptStatus(dev),
1111 0xffff & RtdInterruptOverrunStatus(dev),
1112 (0xffff & RtdFifoStatus(dev)) ^ 0x6666);
1113 }
1114
1115 if (devpriv) {
1116 /* Shut down any board ops by resetting it */
1117 #ifdef USE_DMA
1118 if (devpriv->lcfg) {
1119 RtdDma0Control(dev, 0); /* disable DMA */
1120 RtdDma1Control(dev, 0); /* disable DMA */
1121 RtdPlxInterruptWrite(dev, ICS_PIE | ICS_PLIE);
1122 }
1123 #endif /* USE_DMA */
1124 if (devpriv->las0) {
1125 RtdResetBoard(dev);
1126 RtdInterruptMask(dev, 0);
1127 RtdInterruptClearMask(dev, ~0);
1128 RtdInterruptClear(dev); /* clears bits set by mask */
1129 }
1130 #ifdef USE_DMA
1131 /* release DMA */
1132 for (index = 0; index < DMA_CHAIN_COUNT; index++) {
1133 if (NULL != devpriv->dma0Buff[index]) {
1134 pci_free_consistent(devpriv->pci_dev,
1135 sizeof(u16) *
1136 devpriv->fifoLen / 2,
1137 devpriv->dma0Buff[index],
1138 devpriv->
1139 dma0BuffPhysAddr[index]);
1140 devpriv->dma0Buff[index] = NULL;
1141 }
1142 }
1143 if (NULL != devpriv->dma0Chain) {
1144 pci_free_consistent(devpriv->pci_dev,
1145 sizeof(struct plx_dma_desc) *
1146 DMA_CHAIN_COUNT, devpriv->dma0Chain,
1147 devpriv->dma0ChainPhysAddr);
1148 devpriv->dma0Chain = NULL;
1149 }
1150 #endif /* USE_DMA */
1151
1152 /* release IRQ */
1153 if (dev->irq) {
1154 /* disable interrupt controller */
1155 RtdPlxInterruptWrite(dev, RtdPlxInterruptRead(dev)
1156 & ~(ICS_PLIE | ICS_DMA0_E |
1157 ICS_DMA1_E));
1158 free_irq(dev->irq, dev);
1159 }
1160
1161 /* release all regions that were allocated */
1162 if (devpriv->las0) {
1163 iounmap(devpriv->las0);
1164 }
1165 if (devpriv->las1) {
1166 iounmap(devpriv->las1);
1167 }
1168 if (devpriv->lcfg) {
1169 iounmap(devpriv->lcfg);
1170 }
1171 if (devpriv->pci_dev) {
1172 if (devpriv->got_regions) {
1173 comedi_pci_disable(devpriv->pci_dev);
1174 }
1175 pci_dev_put(devpriv->pci_dev);
1176 }
1177 }
1178
1179 printk("comedi%d: rtd520: removed.\n", dev->minor);
1180
1181 return 0;
1182 }
1183
1184 /*
1185 Convert a single comedi channel-gain entry to a RTD520 table entry
1186 */
1187 static unsigned short rtdConvertChanGain(struct comedi_device *dev,
1188 unsigned int comediChan, int chanIndex)
1189 { /* index in channel list */
1190 unsigned int chan, range, aref;
1191 unsigned short r = 0;
1192
1193 chan = CR_CHAN(comediChan);
1194 range = CR_RANGE(comediChan);
1195 aref = CR_AREF(comediChan);
1196
1197 r |= chan & 0xf;
1198
1199 /* Note: we also setup the channel list bipolar flag array */
1200 if (range < thisboard->range10Start) { /* first batch are +-5 */
1201 r |= 0x000; /* +-5 range */
1202 r |= (range & 0x7) << 4; /* gain */
1203 CHAN_ARRAY_SET(devpriv->chanBipolar, chanIndex);
1204 } else if (range < thisboard->rangeUniStart) { /* second batch are +-10 */
1205 r |= 0x100; /* +-10 range */
1206 r |= ((range - thisboard->range10Start) & 0x7) << 4; /* gain */
1207 CHAN_ARRAY_SET(devpriv->chanBipolar, chanIndex);
1208 } else { /* last batch is +10 */
1209 r |= 0x200; /* +10 range */
1210 r |= ((range - thisboard->rangeUniStart) & 0x7) << 4; /* gain */
1211 CHAN_ARRAY_CLEAR(devpriv->chanBipolar, chanIndex);
1212 }
1213
1214 switch (aref) {
1215 case AREF_GROUND: /* on-board ground */
1216 break;
1217
1218 case AREF_COMMON:
1219 r |= 0x80; /* ref external analog common */
1220 break;
1221
1222 case AREF_DIFF:
1223 r |= 0x400; /* differential inputs */
1224 break;
1225
1226 case AREF_OTHER: /* ??? */
1227 break;
1228 }
1229 /*printk ("chan=%d r=%d a=%d -> 0x%x\n",
1230 chan, range, aref, r); */
1231 return r;
1232 }
1233
1234 /*
1235 Setup the channel-gain table from a comedi list
1236 */
1237 static void rtd_load_channelgain_list(struct comedi_device *dev,
1238 unsigned int n_chan, unsigned int *list)
1239 {
1240 if (n_chan > 1) { /* setup channel gain table */
1241 int ii;
1242 RtdClearCGT(dev);
1243 RtdEnableCGT(dev, 1); /* enable table */
1244 for (ii = 0; ii < n_chan; ii++) {
1245 RtdWriteCGTable(dev, rtdConvertChanGain(dev, list[ii],
1246 ii));
1247 }
1248 } else { /* just use the channel gain latch */
1249 RtdEnableCGT(dev, 0); /* disable table, enable latch */
1250 RtdWriteCGLatch(dev, rtdConvertChanGain(dev, list[0], 0));
1251 }
1252 }
1253
1254 /* determine fifo size by doing adc conversions until the fifo half
1255 empty status flag clears */
1256 static int rtd520_probe_fifo_depth(struct comedi_device *dev)
1257 {
1258 unsigned int chanspec = CR_PACK(0, 0, AREF_GROUND);
1259 unsigned i;
1260 static const unsigned limit = 0x2000;
1261 unsigned fifo_size = 0;
1262
1263 RtdAdcClearFifo(dev);
1264 rtd_load_channelgain_list(dev, 1, &chanspec);
1265 RtdAdcConversionSource(dev, 0); /* software */
1266 /* convert samples */
1267 for (i = 0; i < limit; ++i) {
1268 unsigned fifo_status;
1269 /* trigger conversion */
1270 RtdAdcStart(dev);
1271 udelay(1);
1272 fifo_status = RtdFifoStatus(dev);
1273 if ((fifo_status & FS_ADC_HEMPTY) == 0) {
1274 fifo_size = 2 * i;
1275 break;
1276 }
1277 }
1278 if (i == limit) {
1279 printk("\ncomedi: %s: failed to probe fifo size.\n", DRV_NAME);
1280 return -EIO;
1281 }
1282 RtdAdcClearFifo(dev);
1283 if (fifo_size != 0x400 && fifo_size != 0x2000) {
1284 printk
1285 ("\ncomedi: %s: unexpected fifo size of %i, expected 1024 or 8192.\n",
1286 DRV_NAME, fifo_size);
1287 return -EIO;
1288 }
1289 return fifo_size;
1290 }
1291
1292 /*
1293 "instructions" read/write data in "one-shot" or "software-triggered"
1294 mode (simplest case).
1295 This doesnt use interrupts.
1296
1297 Note, we don't do any settling delays. Use a instruction list to
1298 select, delay, then read.
1299 */
1300 static int rtd_ai_rinsn(struct comedi_device *dev,
1301 struct comedi_subdevice *s, struct comedi_insn *insn,
1302 unsigned int *data)
1303 {
1304 int n, ii;
1305 int stat;
1306
1307 /* clear any old fifo data */
1308 RtdAdcClearFifo(dev);
1309
1310 /* write channel to multiplexer and clear channel gain table */
1311 rtd_load_channelgain_list(dev, 1, &insn->chanspec);
1312
1313 /* set conversion source */
1314 RtdAdcConversionSource(dev, 0); /* software */
1315
1316 /* convert n samples */
1317 for (n = 0; n < insn->n; n++) {
1318 s16 d;
1319 /* trigger conversion */
1320 RtdAdcStart(dev);
1321
1322 for (ii = 0; ii < RTD_ADC_TIMEOUT; ++ii) {
1323 stat = RtdFifoStatus(dev);
1324 if (stat & FS_ADC_NOT_EMPTY) /* 1 -> not empty */
1325 break;
1326 WAIT_QUIETLY;
1327 }
1328 if (ii >= RTD_ADC_TIMEOUT) {
1329 DPRINTK
1330 ("rtd520: Error: ADC never finished! FifoStatus=0x%x\n",
1331 stat ^ 0x6666);
1332 return -ETIMEDOUT;
1333 }
1334
1335 /* read data */
1336 d = RtdAdcFifoGet(dev); /* get 2s comp value */
1337 /*printk ("rtd520: Got 0x%x after %d usec\n", d, ii+1); */
1338 d = d >> 3; /* low 3 bits are marker lines */
1339 if (CHAN_ARRAY_TEST(devpriv->chanBipolar, 0)) {
1340 data[n] = d + 2048; /* convert to comedi unsigned data */
1341 } else {
1342 data[n] = d;
1343 }
1344 }
1345
1346 /* return the number of samples read/written */
1347 return n;
1348 }
1349
1350 /*
1351 Get what we know is there.... Fast!
1352 This uses 1/2 the bus cycles of read_dregs (below).
1353
1354 The manual claims that we can do a lword read, but it doesn't work here.
1355 */
1356 static int ai_read_n(struct comedi_device *dev, struct comedi_subdevice *s,
1357 int count)
1358 {
1359 int ii;
1360
1361 for (ii = 0; ii < count; ii++) {
1362 short sample;
1363 s16 d;
1364
1365 if (0 == devpriv->aiCount) { /* done */
1366 d = RtdAdcFifoGet(dev); /* Read N and discard */
1367 continue;
1368 }
1369 #if 0
1370 if (0 == (RtdFifoStatus(dev) & FS_ADC_NOT_EMPTY)) { /* DEBUG */
1371 DPRINTK("comedi: READ OOPS on %d of %d\n", ii + 1,
1372 count);
1373 break;
1374 }
1375 #endif
1376 d = RtdAdcFifoGet(dev); /* get 2s comp value */
1377
1378 d = d >> 3; /* low 3 bits are marker lines */
1379 if (CHAN_ARRAY_TEST(devpriv->chanBipolar, s->async->cur_chan)) {
1380 sample = d + 2048; /* convert to comedi unsigned data */
1381 } else {
1382 sample = d;
1383 }
1384 if (!comedi_buf_put(s->async, sample))
1385 return -1;
1386
1387 if (devpriv->aiCount > 0) /* < 0, means read forever */
1388 devpriv->aiCount--;
1389 }
1390 return 0;
1391 }
1392
1393 /*
1394 unknown amout of data is waiting in fifo.
1395 */
1396 static int ai_read_dregs(struct comedi_device *dev, struct comedi_subdevice *s)
1397 {
1398 while (RtdFifoStatus(dev) & FS_ADC_NOT_EMPTY) { /* 1 -> not empty */
1399 short sample;
1400 s16 d = RtdAdcFifoGet(dev); /* get 2s comp value */
1401
1402 if (0 == devpriv->aiCount) { /* done */
1403 continue; /* read rest */
1404 }
1405
1406 d = d >> 3; /* low 3 bits are marker lines */
1407 if (CHAN_ARRAY_TEST(devpriv->chanBipolar, s->async->cur_chan)) {
1408 sample = d + 2048; /* convert to comedi unsigned data */
1409 } else {
1410 sample = d;
1411 }
1412 if (!comedi_buf_put(s->async, sample))
1413 return -1;
1414
1415 if (devpriv->aiCount > 0) /* < 0, means read forever */
1416 devpriv->aiCount--;
1417 }
1418 return 0;
1419 }
1420
1421 #ifdef USE_DMA
1422 /*
1423 Terminate a DMA transfer and wait for everything to quiet down
1424 */
1425 void abort_dma(struct comedi_device *dev, unsigned int channel)
1426 { /* DMA channel 0, 1 */
1427 unsigned long dma_cs_addr; /* the control/status register */
1428 uint8_t status;
1429 unsigned int ii;
1430 /* unsigned long flags; */
1431
1432 dma_cs_addr = (unsigned long)devpriv->lcfg
1433 + ((channel == 0) ? LCFG_DMACSR0 : LCFG_DMACSR1);
1434
1435 /* spinlock for plx dma control/status reg */
1436 /* spin_lock_irqsave( &dev->spinlock, flags ); */
1437
1438 /* abort dma transfer if necessary */
1439 status = readb(dma_cs_addr);
1440 if ((status & PLX_DMA_EN_BIT) == 0) { /* not enabled (Error?) */
1441 DPRINTK("rtd520: AbortDma on non-active channel %d (0x%x)\n",
1442 channel, status);
1443 goto abortDmaExit;
1444 }
1445
1446 /* wait to make sure done bit is zero (needed?) */
1447 for (ii = 0; (status & PLX_DMA_DONE_BIT) && ii < RTD_DMA_TIMEOUT; ii++) {
1448 WAIT_QUIETLY;
1449 status = readb(dma_cs_addr);
1450 }
1451 if (status & PLX_DMA_DONE_BIT) {
1452 printk("rtd520: Timeout waiting for dma %i done clear\n",
1453 channel);
1454 goto abortDmaExit;
1455 }
1456
1457 /* disable channel (required) */
1458 writeb(0, dma_cs_addr);
1459 udelay(1); /* needed?? */
1460 /* set abort bit for channel */
1461 writeb(PLX_DMA_ABORT_BIT, dma_cs_addr);
1462
1463 /* wait for dma done bit to be set */
1464 status = readb(dma_cs_addr);
1465 for (ii = 0;
1466 (status & PLX_DMA_DONE_BIT) == 0 && ii < RTD_DMA_TIMEOUT; ii++) {
1467 status = readb(dma_cs_addr);
1468 WAIT_QUIETLY;
1469 }
1470 if ((status & PLX_DMA_DONE_BIT) == 0) {
1471 printk("rtd520: Timeout waiting for dma %i done set\n",
1472 channel);
1473 }
1474
1475 abortDmaExit:
1476 /* spin_unlock_irqrestore( &dev->spinlock, flags ); */
1477 }
1478
1479 /*
1480 Process what is in the DMA transfer buffer and pass to comedi
1481 Note: this is not re-entrant
1482 */
1483 static int ai_process_dma(struct comedi_device *dev, struct comedi_subdevice *s)
1484 {
1485 int ii, n;
1486 s16 *dp;
1487
1488 if (devpriv->aiCount == 0) /* transfer already complete */
1489 return 0;
1490
1491 dp = devpriv->dma0Buff[devpriv->dma0Offset];
1492 for (ii = 0; ii < devpriv->fifoLen / 2;) { /* convert samples */
1493 short sample;
1494
1495 if (CHAN_ARRAY_TEST(devpriv->chanBipolar, s->async->cur_chan)) {
1496 sample = (*dp >> 3) + 2048; /* convert to comedi unsigned data */
1497 } else {
1498 sample = *dp >> 3; /* low 3 bits are marker lines */
1499 }
1500 *dp++ = sample; /* put processed value back */
1501
1502 if (++s->async->cur_chan >= s->async->cmd.chanlist_len)
1503 s->async->cur_chan = 0;
1504
1505 ++ii; /* number ready to transfer */
1506 if (devpriv->aiCount > 0) { /* < 0, means read forever */
1507 if (--devpriv->aiCount == 0) { /* done */
1508 /*DPRINTK ("rtd520: Final %d samples\n", ii); */
1509 break;
1510 }
1511 }
1512 }
1513
1514 /* now pass the whole array to the comedi buffer */
1515 dp = devpriv->dma0Buff[devpriv->dma0Offset];
1516 n = comedi_buf_write_alloc(s->async, ii * sizeof(s16));
1517 if (n < (ii * sizeof(s16))) { /* any residual is an error */
1518 DPRINTK("rtd520:ai_process_dma buffer overflow %d samples!\n",
1519 ii - (n / sizeof(s16)));
1520 s->async->events |= COMEDI_CB_ERROR;
1521 return -1;
1522 }
1523 comedi_buf_memcpy_to(s->async, 0, dp, n);
1524 comedi_buf_write_free(s->async, n);
1525
1526 /* always at least 1 scan -- 1/2 FIFO is larger than our max scan list */
1527 s->async->events |= COMEDI_CB_BLOCK | COMEDI_CB_EOS;
1528
1529 if (++devpriv->dma0Offset >= DMA_CHAIN_COUNT) { /* next buffer */
1530 devpriv->dma0Offset = 0;
1531 }
1532 return 0;
1533 }
1534 #endif /* USE_DMA */
1535
1536 /*
1537 Handle all rtd520 interrupts.
1538 Runs atomically and is never re-entered.
1539 This is a "slow handler"; other interrupts may be active.
1540 The data conversion may someday happen in a "bottom half".
1541 */
1542 static irqreturn_t rtd_interrupt(int irq, /* interrupt number (ignored) */
1543 void *d)
1544 { /* our data *//* cpu context (ignored) */
1545 struct comedi_device *dev = d; /* must be called "dev" for devpriv */
1546 u16 status;
1547 u16 fifoStatus;
1548 struct comedi_subdevice *s = dev->subdevices + 0; /* analog in subdevice */
1549
1550 if (!dev->attached) {
1551 return IRQ_NONE;
1552 }
1553
1554 devpriv->intCount++; /* DEBUG statistics */
1555
1556 fifoStatus = RtdFifoStatus(dev);
1557 /* check for FIFO full, this automatically halts the ADC! */
1558 if (!(fifoStatus & FS_ADC_NOT_FULL)) { /* 0 -> full */
1559 DPRINTK("rtd520: FIFO full! fifo_status=0x%x\n", (fifoStatus ^ 0x6666) & 0x7777); /* should be all 0s */
1560 goto abortTransfer;
1561 }
1562 #ifdef USE_DMA
1563 if (devpriv->flags & DMA0_ACTIVE) { /* Check DMA */
1564 u32 istatus = RtdPlxInterruptRead(dev);
1565
1566 if (istatus & ICS_DMA0_A) {
1567 if (ai_process_dma(dev, s) < 0) {
1568 DPRINTK
1569 ("rtd520: comedi read buffer overflow (DMA) with %ld to go!\n",
1570 devpriv->aiCount);
1571 RtdDma0Control(dev,
1572 (devpriv->dma0Control &
1573 ~PLX_DMA_START_BIT)
1574 | PLX_CLEAR_DMA_INTR_BIT);
1575 goto abortTransfer;
1576 }
1577
1578 /*DPRINTK ("rtd520: DMA transfer: %ld to go, istatus %x\n",
1579 devpriv->aiCount, istatus); */
1580 RtdDma0Control(dev,
1581 (devpriv->
1582 dma0Control & ~PLX_DMA_START_BIT)
1583 | PLX_CLEAR_DMA_INTR_BIT);
1584 if (0 == devpriv->aiCount) { /* counted down */
1585 DPRINTK("rtd520: Samples Done (DMA).\n");
1586 goto transferDone;
1587 }
1588 comedi_event(dev, s);
1589 } else {
1590 /*DPRINTK ("rtd520: No DMA ready: istatus %x\n", istatus); */
1591 }
1592 }
1593 /* Fall through and check for other interrupt sources */
1594 #endif /* USE_DMA */
1595
1596 status = RtdInterruptStatus(dev);
1597 /* if interrupt was not caused by our board, or handled above */
1598 if (0 == status) {
1599 return IRQ_HANDLED;
1600 }
1601
1602 if (status & IRQM_ADC_ABOUT_CNT) { /* sample count -> read FIFO */
1603 /* since the priority interrupt controller may have queued a sample
1604 counter interrupt, even though we have already finished,
1605 we must handle the possibility that there is no data here */
1606 if (!(fifoStatus & FS_ADC_HEMPTY)) { /* 0 -> 1/2 full */
1607 /*DPRINTK("rtd520: Sample int, reading 1/2FIFO. fifo_status 0x%x\n",
1608 (fifoStatus ^ 0x6666) & 0x7777); */
1609 if (ai_read_n(dev, s, devpriv->fifoLen / 2) < 0) {
1610 DPRINTK
1611 ("rtd520: comedi read buffer overflow (1/2FIFO) with %ld to go!\n",
1612 devpriv->aiCount);
1613 goto abortTransfer;
1614 }
1615 if (0 == devpriv->aiCount) { /* counted down */
1616 DPRINTK("rtd520: Samples Done (1/2). fifo_status was 0x%x\n", (fifoStatus ^ 0x6666) & 0x7777); /* should be all 0s */
1617 goto transferDone;
1618 }
1619 comedi_event(dev, s);
1620 } else if (devpriv->transCount > 0) { /* read often */
1621 /*DPRINTK("rtd520: Sample int, reading %d fifo_status 0x%x\n",
1622 devpriv->transCount, (fifoStatus ^ 0x6666) & 0x7777); */
1623 if (fifoStatus & FS_ADC_NOT_EMPTY) { /* 1 -> not empty */
1624 if (ai_read_n(dev, s, devpriv->transCount) < 0) {
1625 DPRINTK
1626 ("rtd520: comedi read buffer overflow (N) with %ld to go!\n",
1627 devpriv->aiCount);
1628 goto abortTransfer;
1629 }
1630 if (0 == devpriv->aiCount) { /* counted down */
1631 DPRINTK
1632 ("rtd520: Samples Done (N). fifo_status was 0x%x\n",
1633 (fifoStatus ^ 0x6666) & 0x7777);
1634 goto transferDone;
1635 }
1636 comedi_event(dev, s);
1637 }
1638 } else { /* wait for 1/2 FIFO (old) */
1639 DPRINTK
1640 ("rtd520: Sample int. Wait for 1/2. fifo_status 0x%x\n",
1641 (fifoStatus ^ 0x6666) & 0x7777);
1642 }
1643 } else {
1644 DPRINTK("rtd520: unknown interrupt source!\n");
1645 }
1646
1647 if (0xffff & RtdInterruptOverrunStatus(dev)) { /* interrupt overrun */
1648 DPRINTK
1649 ("rtd520: Interrupt overrun with %ld to go! over_status=0x%x\n",
1650 devpriv->aiCount, 0xffff & RtdInterruptOverrunStatus(dev));
1651 goto abortTransfer;
1652 }
1653
1654 /* clear the interrupt */
1655 RtdInterruptClearMask(dev, status);
1656 RtdInterruptClear(dev);
1657 return IRQ_HANDLED;
1658
1659 abortTransfer:
1660 RtdAdcClearFifo(dev); /* clears full flag */
1661 s->async->events |= COMEDI_CB_ERROR;
1662 devpriv->aiCount = 0; /* stop and don't transfer any more */
1663 /* fall into transferDone */
1664
1665 transferDone:
1666 RtdPacerStopSource(dev, 0); /* stop on SOFTWARE stop */
1667 RtdPacerStop(dev); /* Stop PACER */
1668 RtdAdcConversionSource(dev, 0); /* software trigger only */
1669 RtdInterruptMask(dev, 0); /* mask out SAMPLE */
1670 #ifdef USE_DMA
1671 if (devpriv->flags & DMA0_ACTIVE) {
1672 RtdPlxInterruptWrite(dev, /* disable any more interrupts */
1673 RtdPlxInterruptRead(dev) & ~ICS_DMA0_E);
1674 abort_dma(dev, 0);
1675 devpriv->flags &= ~DMA0_ACTIVE;
1676 /* if Using DMA, then we should have read everything by now */
1677 if (devpriv->aiCount > 0) {
1678 DPRINTK("rtd520: Lost DMA data! %ld remain\n",
1679 devpriv->aiCount);
1680 }
1681 }
1682 #endif /* USE_DMA */
1683
1684 if (devpriv->aiCount > 0) { /* there shouldn't be anything left */
1685 fifoStatus = RtdFifoStatus(dev);
1686 DPRINTK("rtd520: Finishing up. %ld remain, fifoStat=%x\n", devpriv->aiCount, (fifoStatus ^ 0x6666) & 0x7777); /* should read all 0s */
1687 ai_read_dregs(dev, s); /* read anything left in FIFO */
1688 }
1689
1690 s->async->events |= COMEDI_CB_EOA; /* signal end to comedi */
1691 comedi_event(dev, s);
1692
1693 /* clear the interrupt */
1694 status = RtdInterruptStatus(dev);
1695 RtdInterruptClearMask(dev, status);
1696 RtdInterruptClear(dev);
1697
1698 fifoStatus = RtdFifoStatus(dev); /* DEBUG */
1699 DPRINTK
1700 ("rtd520: Acquisition complete. %ld ints, intStat=%x, overStat=%x\n",
1701 devpriv->intCount, status,
1702 0xffff & RtdInterruptOverrunStatus(dev));
1703
1704 return IRQ_HANDLED;
1705 }
1706
1707 #if 0
1708 /*
1709 return the number of samples available
1710 */
1711 static int rtd_ai_poll(struct comedi_device *dev, struct comedi_subdevice *s)
1712 {
1713 /* TODO: This needs to mask interrupts, read_dregs, and then re-enable */
1714 /* Not sure what to do if DMA is active */
1715 return s->async->buf_write_count - s->async->buf_read_count;
1716 }
1717 #endif
1718
1719 /*
1720 cmdtest tests a particular command to see if it is valid.
1721 Using the cmdtest ioctl, a user can create a valid cmd
1722 and then have it executed by the cmd ioctl (asyncronously).
1723
1724 cmdtest returns 1,2,3,4 or 0, depending on which tests
1725 the command passes.
1726 */
1727
1728 static int rtd_ai_cmdtest(struct comedi_device *dev,
1729 struct comedi_subdevice *s, struct comedi_cmd *cmd)
1730 {
1731 int err = 0;
1732 int tmp;
1733
1734 /* step 1: make sure trigger sources are trivially valid */
1735
1736 tmp = cmd->start_src;
1737 cmd->start_src &= TRIG_NOW;
1738 if (!cmd->start_src || tmp != cmd->start_src) {
1739 err++;
1740 }
1741
1742 tmp = cmd->scan_begin_src;
1743 cmd->scan_begin_src &= TRIG_TIMER | TRIG_EXT;
1744 if (!cmd->scan_begin_src || tmp != cmd->scan_begin_src) {
1745 err++;
1746 }
1747
1748 tmp = cmd->convert_src;
1749 cmd->convert_src &= TRIG_TIMER | TRIG_EXT;
1750 if (!cmd->convert_src || tmp != cmd->convert_src) {
1751 err++;
1752 }
1753
1754 tmp = cmd->scan_end_src;
1755 cmd->scan_end_src &= TRIG_COUNT;
1756 if (!cmd->scan_end_src || tmp != cmd->scan_end_src) {
1757 err++;
1758 }
1759
1760 tmp = cmd->stop_src;
1761 cmd->stop_src &= TRIG_COUNT | TRIG_NONE;
1762 if (!cmd->stop_src || tmp != cmd->stop_src) {
1763 err++;
1764 }
1765
1766 if (err)
1767 return 1;
1768
1769 /* step 2: make sure trigger sources are unique
1770 and mutually compatible */
1771 /* note that mutual compatibility is not an issue here */
1772 if (cmd->scan_begin_src != TRIG_TIMER &&
1773 cmd->scan_begin_src != TRIG_EXT) {
1774 err++;
1775 }
1776 if (cmd->convert_src != TRIG_TIMER && cmd->convert_src != TRIG_EXT) {
1777 err++;
1778 }
1779 if (cmd->stop_src != TRIG_COUNT && cmd->stop_src != TRIG_NONE) {
1780 err++;
1781 }
1782
1783 if (err) {
1784 return 2;
1785 }
1786
1787 /* step 3: make sure arguments are trivially compatible */
1788
1789 if (cmd->start_arg != 0) {
1790 cmd->start_arg = 0;
1791 err++;
1792 }
1793
1794 if (cmd->scan_begin_src == TRIG_TIMER) {
1795 /* Note: these are time periods, not actual rates */
1796 if (1 == cmd->chanlist_len) { /* no scanning */
1797 if (cmd->scan_begin_arg < RTD_MAX_SPEED_1) {
1798 cmd->scan_begin_arg = RTD_MAX_SPEED_1;
1799 rtd_ns_to_timer(&cmd->scan_begin_arg,
1800 TRIG_ROUND_UP);
1801 err++;
1802 }
1803 if (cmd->scan_begin_arg > RTD_MIN_SPEED_1) {
1804 cmd->scan_begin_arg = RTD_MIN_SPEED_1;
1805 rtd_ns_to_timer(&cmd->scan_begin_arg,
1806 TRIG_ROUND_DOWN);
1807 err++;
1808 }
1809 } else {
1810 if (cmd->scan_begin_arg < RTD_MAX_SPEED) {
1811 cmd->scan_begin_arg = RTD_MAX_SPEED;
1812 rtd_ns_to_timer(&cmd->scan_begin_arg,
1813 TRIG_ROUND_UP);
1814 err++;
1815 }
1816 if (cmd->scan_begin_arg > RTD_MIN_SPEED) {
1817 cmd->scan_begin_arg = RTD_MIN_SPEED;
1818 rtd_ns_to_timer(&cmd->scan_begin_arg,
1819 TRIG_ROUND_DOWN);
1820 err++;
1821 }
1822 }
1823 } else {
1824 /* external trigger */
1825 /* should be level/edge, hi/lo specification here */
1826 /* should specify multiple external triggers */
1827 if (cmd->scan_begin_arg > 9) {
1828 cmd->scan_begin_arg = 9;
1829 err++;
1830 }
1831 }
1832 if (cmd->convert_src == TRIG_TIMER) {
1833 if (1 == cmd->chanlist_len) { /* no scanning */
1834 if (cmd->convert_arg < RTD_MAX_SPEED_1) {
1835 cmd->convert_arg = RTD_MAX_SPEED_1;
1836 rtd_ns_to_timer(&cmd->convert_arg,
1837 TRIG_ROUND_UP);
1838 err++;
1839 }
1840 if (cmd->convert_arg > RTD_MIN_SPEED_1) {
1841 cmd->convert_arg = RTD_MIN_SPEED_1;
1842 rtd_ns_to_timer(&cmd->convert_arg,
1843 TRIG_ROUND_DOWN);
1844 err++;
1845 }
1846 } else {
1847 if (cmd->convert_arg < RTD_MAX_SPEED) {
1848 cmd->convert_arg = RTD_MAX_SPEED;
1849 rtd_ns_to_timer(&cmd->convert_arg,
1850 TRIG_ROUND_UP);
1851 err++;
1852 }
1853 if (cmd->convert_arg > RTD_MIN_SPEED) {
1854 cmd->convert_arg = RTD_MIN_SPEED;
1855 rtd_ns_to_timer(&cmd->convert_arg,
1856 TRIG_ROUND_DOWN);
1857 err++;
1858 }
1859 }
1860 } else {
1861 /* external trigger */
1862 /* see above */
1863 if (cmd->convert_arg > 9) {
1864 cmd->convert_arg = 9;
1865 err++;
1866 }
1867 }
1868
1869 #if 0
1870 if (cmd->scan_end_arg != cmd->chanlist_len) {
1871 cmd->scan_end_arg = cmd->chanlist_len;
1872 err++;
1873 }
1874 #endif
1875 if (cmd->stop_src == TRIG_COUNT) {
1876 /* TODO check for rounding error due to counter wrap */
1877
1878 } else {
1879 /* TRIG_NONE */
1880 if (cmd->stop_arg != 0) {
1881 cmd->stop_arg = 0;
1882 err++;
1883 }
1884 }
1885
1886 if (err) {
1887 return 3;
1888 }
1889
1890 /* step 4: fix up any arguments */
1891
1892 if (cmd->chanlist_len > RTD_MAX_CHANLIST) {
1893 cmd->chanlist_len = RTD_MAX_CHANLIST;
1894 err++;
1895 }
1896 if (cmd->scan_begin_src == TRIG_TIMER) {
1897 tmp = cmd->scan_begin_arg;
1898 rtd_ns_to_timer(&cmd->scan_begin_arg,
1899 cmd->flags & TRIG_ROUND_MASK);
1900 if (tmp != cmd->scan_begin_arg) {
1901 err++;
1902 }
1903 }
1904 if (cmd->convert_src == TRIG_TIMER) {
1905 tmp = cmd->convert_arg;
1906 rtd_ns_to_timer(&cmd->convert_arg,
1907 cmd->flags & TRIG_ROUND_MASK);
1908 if (tmp != cmd->convert_arg) {
1909 err++;
1910 }
1911 if (cmd->scan_begin_src == TRIG_TIMER
1912 && (cmd->scan_begin_arg
1913 < (cmd->convert_arg * cmd->scan_end_arg))) {
1914 cmd->scan_begin_arg =
1915 cmd->convert_arg * cmd->scan_end_arg;
1916 err++;
1917 }
1918 }
1919
1920 if (err) {
1921 return 4;
1922 }
1923
1924 return 0;
1925 }
1926
1927 /*
1928 Execute a analog in command with many possible triggering options.
1929 The data get stored in the async structure of the subdevice.
1930 This is usually done by an interrupt handler.
1931 Userland gets to the data using read calls.
1932 */
1933 static int rtd_ai_cmd(struct comedi_device *dev, struct comedi_subdevice *s)
1934 {
1935 struct comedi_cmd *cmd = &s->async->cmd;
1936 int timer;
1937
1938 /* stop anything currently running */
1939 RtdPacerStopSource(dev, 0); /* stop on SOFTWARE stop */
1940 RtdPacerStop(dev); /* make sure PACER is stopped */
1941 RtdAdcConversionSource(dev, 0); /* software trigger only */
1942 RtdInterruptMask(dev, 0);
1943 #ifdef USE_DMA
1944 if (devpriv->flags & DMA0_ACTIVE) { /* cancel anything running */
1945 RtdPlxInterruptWrite(dev, /* disable any more interrupts */
1946 RtdPlxInterruptRead(dev) & ~ICS_DMA0_E);
1947 abort_dma(dev, 0);
1948 devpriv->flags &= ~DMA0_ACTIVE;
1949 if (RtdPlxInterruptRead(dev) & ICS_DMA0_A) { /*clear pending int */
1950 RtdDma0Control(dev, PLX_CLEAR_DMA_INTR_BIT);
1951 }
1952 }
1953 RtdDma0Reset(dev); /* reset onboard state */
1954 #endif /* USE_DMA */
1955 RtdAdcClearFifo(dev); /* clear any old data */
1956 RtdInterruptOverrunClear(dev);
1957 devpriv->intCount = 0;
1958
1959 if (!dev->irq) { /* we need interrupts for this */
1960 DPRINTK("rtd520: ERROR! No interrupt available!\n");
1961 return -ENXIO;
1962 }
1963
1964 /* start configuration */
1965 /* load channel list and reset CGT */
1966 rtd_load_channelgain_list(dev, cmd->chanlist_len, cmd->chanlist);
1967
1968 /* setup the common case and override if needed */
1969 if (cmd->chanlist_len > 1) {
1970 /*DPRINTK ("rtd520: Multi channel setup\n"); */
1971 RtdPacerStartSource(dev, 0); /* software triggers pacer */
1972 RtdBurstStartSource(dev, 1); /* PACER triggers burst */
1973 RtdAdcConversionSource(dev, 2); /* BURST triggers ADC */
1974 } else { /* single channel */
1975 /*DPRINTK ("rtd520: single channel setup\n"); */
1976 RtdPacerStartSource(dev, 0); /* software triggers pacer */
1977 RtdAdcConversionSource(dev, 1); /* PACER triggers ADC */
1978 }
1979 RtdAboutCounter(dev, devpriv->fifoLen / 2 - 1); /* 1/2 FIFO */
1980
1981 if (TRIG_TIMER == cmd->scan_begin_src) {
1982 /* scan_begin_arg is in nanoseconds */
1983 /* find out how many samples to wait before transferring */
1984 if (cmd->flags & TRIG_WAKE_EOS) {
1985 /* this may generate un-sustainable interrupt rates */
1986 /* the application is responsible for doing the right thing */
1987 devpriv->transCount = cmd->chanlist_len;
1988 devpriv->flags |= SEND_EOS;
1989 } else {
1990 /* arrange to transfer data periodically */
1991 devpriv->transCount
1992 =
1993 (TRANS_TARGET_PERIOD * cmd->chanlist_len) /
1994 cmd->scan_begin_arg;
1995 if (devpriv->transCount < cmd->chanlist_len) {
1996 /* tranfer after each scan (and avoid 0) */
1997 devpriv->transCount = cmd->chanlist_len;
1998 } else { /* make a multiple of scan length */
1999 devpriv->transCount =
2000 (devpriv->transCount +
2001 cmd->chanlist_len - 1)
2002 / cmd->chanlist_len;
2003 devpriv->transCount *= cmd->chanlist_len;
2004 }
2005 devpriv->flags |= SEND_EOS;
2006 }
2007 if (devpriv->transCount >= (devpriv->fifoLen / 2)) {
2008 /* out of counter range, use 1/2 fifo instead */
2009 devpriv->transCount = 0;
2010 devpriv->flags &= ~SEND_EOS;
2011 } else {
2012 /* interrupt for each tranfer */
2013 RtdAboutCounter(dev, devpriv->transCount - 1);
2014 }
2015
2016 DPRINTK
2017 ("rtd520: scanLen=%d tranferCount=%d fifoLen=%d\n scanTime(ns)=%d flags=0x%x\n",
2018 cmd->chanlist_len, devpriv->transCount, devpriv->fifoLen,
2019 cmd->scan_begin_arg, devpriv->flags);
2020 } else { /* unknown timing, just use 1/2 FIFO */
2021 devpriv->transCount = 0;
2022 devpriv->flags &= ~SEND_EOS;
2023 }
2024 RtdPacerClockSource(dev, 1); /* use INTERNAL 8Mhz clock source */
2025 RtdAboutStopEnable(dev, 1); /* just interrupt, dont stop */
2026
2027 /* BUG??? these look like enumerated values, but they are bit fields */
2028
2029 /* First, setup when to stop */
2030 switch (cmd->stop_src) {
2031 case TRIG_COUNT: /* stop after N scans */
2032 devpriv->aiCount = cmd->stop_arg * cmd->chanlist_len;
2033 if ((devpriv->transCount > 0)
2034 && (devpriv->transCount > devpriv->aiCount)) {
2035 devpriv->transCount = devpriv->aiCount;
2036 }
2037 break;
2038
2039 case TRIG_NONE: /* stop when cancel is called */
2040 devpriv->aiCount = -1; /* read forever */
2041 break;
2042
2043 default:
2044 DPRINTK("rtd520: Warning! ignoring stop_src mode %d\n",
2045 cmd->stop_src);
2046 }
2047
2048 /* Scan timing */
2049 switch (cmd->scan_begin_src) {
2050 case TRIG_TIMER: /* periodic scanning */
2051 timer = rtd_ns_to_timer(&cmd->scan_begin_arg,
2052 TRIG_ROUND_NEAREST);
2053 /* set PACER clock */
2054 /*DPRINTK ("rtd520: loading %d into pacer\n", timer); */
2055 RtdPacerCounter(dev, timer);
2056
2057 break;
2058
2059 case TRIG_EXT:
2060 RtdPacerStartSource(dev, 1); /* EXTERNALy trigger pacer */
2061 break;
2062
2063 default:
2064 DPRINTK("rtd520: Warning! ignoring scan_begin_src mode %d\n",
2065 cmd->scan_begin_src);
2066 }
2067
2068 /* Sample timing within a scan */
2069 switch (cmd->convert_src) {
2070 case TRIG_TIMER: /* periodic */
2071 if (cmd->chanlist_len > 1) { /* only needed for multi-channel */
2072 timer = rtd_ns_to_timer(&cmd->convert_arg,
2073 TRIG_ROUND_NEAREST);
2074 /* setup BURST clock */
2075 /*DPRINTK ("rtd520: loading %d into burst\n", timer); */
2076 RtdBurstCounter(dev, timer);
2077 }
2078
2079 break;
2080
2081 case TRIG_EXT: /* external */
2082 RtdBurstStartSource(dev, 2); /* EXTERNALy trigger burst */
2083 break;
2084
2085 default:
2086 DPRINTK("rtd520: Warning! ignoring convert_src mode %d\n",
2087 cmd->convert_src);
2088 }
2089 /* end configuration */
2090
2091 /* This doesn't seem to work. There is no way to clear an interrupt
2092 that the priority controller has queued! */
2093 RtdInterruptClearMask(dev, ~0); /* clear any existing flags */
2094 RtdInterruptClear(dev);
2095
2096 /* TODO: allow multiple interrupt sources */
2097 if (devpriv->transCount > 0) { /* transfer every N samples */
2098 RtdInterruptMask(dev, IRQM_ADC_ABOUT_CNT);
2099 DPRINTK("rtd520: Transferring every %d\n", devpriv->transCount);
2100 } else { /* 1/2 FIFO transfers */
2101 #ifdef USE_DMA
2102 devpriv->flags |= DMA0_ACTIVE;
2103
2104 /* point to first transfer in ring */
2105 devpriv->dma0Offset = 0;
2106 RtdDma0Mode(dev, DMA_MODE_BITS);
2107 RtdDma0Next(dev, /* point to first block */
2108 devpriv->dma0Chain[DMA_CHAIN_COUNT - 1].next);
2109 RtdDma0Source(dev, DMAS_ADFIFO_HALF_FULL); /* set DMA trigger source */
2110
2111 RtdPlxInterruptWrite(dev, /* enable interrupt */
2112 RtdPlxInterruptRead(dev) | ICS_DMA0_E);
2113 /* Must be 2 steps. See PLX app note about "Starting a DMA transfer" */
2114 RtdDma0Control(dev, PLX_DMA_EN_BIT); /* enable DMA (clear INTR?) */
2115 RtdDma0Control(dev, PLX_DMA_EN_BIT | PLX_DMA_START_BIT); /*start DMA */
2116 DPRINTK("rtd520: Using DMA0 transfers. plxInt %x RtdInt %x\n",
2117 RtdPlxInterruptRead(dev), devpriv->intMask);
2118 #else /* USE_DMA */
2119 RtdInterruptMask(dev, IRQM_ADC_ABOUT_CNT);
2120 DPRINTK("rtd520: Transferring every 1/2 FIFO\n");
2121 #endif /* USE_DMA */
2122 }
2123
2124 /* BUG: start_src is ASSUMED to be TRIG_NOW */
2125 /* BUG? it seems like things are running before the "start" */
2126 RtdPacerStart(dev); /* Start PACER */
2127 return 0;
2128 }
2129
2130 /*
2131 Stop a running data aquisition.
2132 */
2133 static int rtd_ai_cancel(struct comedi_device *dev, struct comedi_subdevice *s)
2134 {
2135 u16 status;
2136
2137 RtdPacerStopSource(dev, 0); /* stop on SOFTWARE stop */
2138 RtdPacerStop(dev); /* Stop PACER */
2139 RtdAdcConversionSource(dev, 0); /* software trigger only */
2140 RtdInterruptMask(dev, 0);
2141 devpriv->aiCount = 0; /* stop and don't transfer any more */
2142 #ifdef USE_DMA
2143 if (devpriv->flags & DMA0_ACTIVE) {
2144 RtdPlxInterruptWrite(dev, /* disable any more interrupts */
2145 RtdPlxInterruptRead(dev) & ~ICS_DMA0_E);
2146 abort_dma(dev, 0);
2147 devpriv->flags &= ~DMA0_ACTIVE;
2148 }
2149 #endif /* USE_DMA */
2150 status = RtdInterruptStatus(dev);
2151 DPRINTK
2152 ("rtd520: Acquisition canceled. %ld ints, intStat=%x, overStat=%x\n",
2153 devpriv->intCount, status,
2154 0xffff & RtdInterruptOverrunStatus(dev));
2155 return 0;
2156 }
2157
2158 /*
2159 Given a desired period and the clock period (both in ns),
2160 return the proper counter value (divider-1).
2161 Sets the original period to be the true value.
2162 Note: you have to check if the value is larger than the counter range!
2163 */
2164 static int rtd_ns_to_timer_base(unsigned int *nanosec, /* desired period (in ns) */
2165 int round_mode, int base)
2166 { /* clock period (in ns) */
2167 int divider;
2168
2169 switch (round_mode) {
2170 case TRIG_ROUND_NEAREST:
2171 default:
2172 divider = (*nanosec + base / 2) / base;
2173 break;
2174 case TRIG_ROUND_DOWN:
2175 divider = (*nanosec) / base;
2176 break;
2177 case TRIG_ROUND_UP:
2178 divider = (*nanosec + base - 1) / base;
2179 break;
2180 }
2181 if (divider < 2)
2182 divider = 2; /* min is divide by 2 */
2183
2184 /* Note: we don't check for max, because different timers
2185 have different ranges */
2186
2187 *nanosec = base * divider;
2188 return divider - 1; /* countdown is divisor+1 */
2189 }
2190
2191 /*
2192 Given a desired period (in ns),
2193 return the proper counter value (divider-1) for the internal clock.
2194 Sets the original period to be the true value.
2195 */
2196 static int rtd_ns_to_timer(unsigned int *ns, int round_mode)
2197 {
2198 return rtd_ns_to_timer_base(ns, round_mode, RTD_CLOCK_BASE);
2199 }
2200
2201 /*
2202 Output one (or more) analog values to a single port as fast as possible.
2203 */
2204 static int rtd_ao_winsn(struct comedi_device *dev,
2205 struct comedi_subdevice *s, struct comedi_insn *insn,
2206 unsigned int *data)
2207 {
2208 int i;
2209 int chan = CR_CHAN(insn->chanspec);
2210 int range = CR_RANGE(insn->chanspec);
2211
2212 /* Configure the output range (table index matches the range values) */
2213 RtdDacRange(dev, chan, range);
2214
2215 /* Writing a list of values to an AO channel is probably not
2216 * very useful, but that's how the interface is defined. */
2217 for (i = 0; i < insn->n; ++i) {
2218 int val = data[i] << 3;
2219 int stat = 0; /* initialize to avoid bogus warning */
2220 int ii;
2221
2222 /* VERIFY: comedi range and offset conversions */
2223
2224 if ((range > 1) /* bipolar */
2225 &&(data[i] < 2048)) {
2226 /* offset and sign extend */
2227 val = (((int)data[i]) - 2048) << 3;
2228 } else { /* unipolor */
2229 val = data[i] << 3;
2230 }
2231
2232 DPRINTK
2233 ("comedi: rtd520 DAC chan=%d range=%d writing %d as 0x%x\n",
2234 chan, range, data[i], val);
2235
2236 /* a typical programming sequence */
2237 RtdDacFifoPut(dev, chan, val); /* put the value in */
2238 RtdDacUpdate(dev, chan); /* trigger the conversion */
2239
2240 devpriv->aoValue[chan] = data[i]; /* save for read back */
2241
2242 for (ii = 0; ii < RTD_DAC_TIMEOUT; ++ii) {
2243 stat = RtdFifoStatus(dev);
2244 /* 1 -> not empty */
2245 if (stat & ((0 == chan) ? FS_DAC1_NOT_EMPTY :
2246 FS_DAC2_NOT_EMPTY))
2247 break;
2248 WAIT_QUIETLY;
2249 }
2250 if (ii >= RTD_DAC_TIMEOUT) {
2251 DPRINTK
2252 ("rtd520: Error: DAC never finished! FifoStatus=0x%x\n",
2253 stat ^ 0x6666);
2254 return -ETIMEDOUT;
2255 }
2256 }
2257
2258 /* return the number of samples read/written */
2259 return i;
2260 }
2261
2262 /* AO subdevices should have a read insn as well as a write insn.
2263 * Usually this means copying a value stored in devpriv. */
2264 static int rtd_ao_rinsn(struct comedi_device *dev,
2265 struct comedi_subdevice *s, struct comedi_insn *insn,
2266 unsigned int *data)
2267 {
2268 int i;
2269 int chan = CR_CHAN(insn->chanspec);
2270
2271 for (i = 0; i < insn->n; i++) {
2272 data[i] = devpriv->aoValue[chan];
2273 }
2274
2275 return i;
2276 }
2277
2278 /*
2279 Write a masked set of bits and the read back the port.
2280 We track what the bits should be (i.e. we don't read the port first).
2281
2282 DIO devices are slightly special. Although it is possible to
2283 * implement the insn_read/insn_write interface, it is much more
2284 * useful to applications if you implement the insn_bits interface.
2285 * This allows packed reading/writing of the DIO channels. The
2286 * comedi core can convert between insn_bits and insn_read/write
2287 */
2288 static int rtd_dio_insn_bits(struct comedi_device *dev,
2289 struct comedi_subdevice *s,
2290 struct comedi_insn *insn, unsigned int *data)
2291 {
2292 if (insn->n != 2)
2293 return -EINVAL;
2294
2295 /* The insn data is a mask in data[0] and the new data
2296 * in data[1], each channel cooresponding to a bit. */
2297 if (data[0]) {
2298 s->state &= ~data[0];
2299 s->state |= data[0] & data[1];
2300
2301 /* Write out the new digital output lines */
2302 RtdDio0Write(dev, s->state);
2303 }
2304 /* on return, data[1] contains the value of the digital
2305 * input lines. */
2306 data[1] = RtdDio0Read(dev);
2307
2308 /*DPRINTK("rtd520:port_0 wrote: 0x%x read: 0x%x\n", s->state, data[1]); */
2309
2310 return 2;
2311 }
2312
2313 /*
2314 Configure one bit on a IO port as Input or Output (hence the name :-).
2315 */
2316 static int rtd_dio_insn_config(struct comedi_device *dev,
2317 struct comedi_subdevice *s,
2318 struct comedi_insn *insn, unsigned int *data)
2319 {
2320 int chan = CR_CHAN(insn->chanspec);
2321
2322 /* The input or output configuration of each digital line is
2323 * configured by a special insn_config instruction. chanspec
2324 * contains the channel to be changed, and data[0] contains the
2325 * value COMEDI_INPUT or COMEDI_OUTPUT. */
2326 switch (data[0]) {
2327 case INSN_CONFIG_DIO_OUTPUT:
2328 s->io_bits |= 1 << chan; /* 1 means Out */
2329 break;
2330 case INSN_CONFIG_DIO_INPUT:
2331 s->io_bits &= ~(1 << chan);
2332 break;
2333 case INSN_CONFIG_DIO_QUERY:
2334 data[1] =
2335 (s->io_bits & (1 << chan)) ? COMEDI_OUTPUT : COMEDI_INPUT;
2336 return insn->n;
2337 break;
2338 default:
2339 return -EINVAL;
2340 }
2341
2342 DPRINTK("rtd520: port_0_direction=0x%x (1 means out)\n", s->io_bits);
2343 /* TODO support digital match interrupts and strobes */
2344 RtdDioStatusWrite(dev, 0x01); /* make Dio0Ctrl point to direction */
2345 RtdDio0CtrlWrite(dev, s->io_bits); /* set direction 1 means Out */
2346 RtdDioStatusWrite(dev, 0); /* make Dio0Ctrl clear interrupts */
2347
2348 /* port1 can only be all input or all output */
2349
2350 /* there are also 2 user input lines and 2 user output lines */
2351
2352 return 1;
2353 }
2354
2355 /*
2356 * A convenient macro that defines init_module() and cleanup_module(),
2357 * as necessary.
2358 */
2359 static int __devinit rtd520Driver_pci_probe(struct pci_dev *dev,
2360 const struct pci_device_id *ent)
2361 {
2362 return comedi_pci_auto_config(dev, rtd520Driver.driver_name);
2363 }
2364
2365 static void __devexit rtd520Driver_pci_remove(struct pci_dev *dev)
2366 {
2367 comedi_pci_auto_unconfig(dev);
2368 }
2369
2370 static struct pci_driver rtd520Driver_pci_driver = {
2371 .id_table = rtd520_pci_table,
2372 .probe = &rtd520Driver_pci_probe,
2373 .remove = __devexit_p(&rtd520Driver_pci_remove)
2374 };
2375
2376 static int __init rtd520Driver_init_module(void)
2377 {
2378 int retval;
2379
2380 retval = comedi_driver_register(&rtd520Driver);
2381 if (retval < 0)
2382 return retval;
2383
2384 rtd520Driver_pci_driver.name = (char *)rtd520Driver.driver_name;
2385 return pci_register_driver(&rtd520Driver_pci_driver);
2386 }
2387
2388 static void __exit rtd520Driver_cleanup_module(void)
2389 {
2390 pci_unregister_driver(&rtd520Driver_pci_driver);
2391 comedi_driver_unregister(&rtd520Driver);
2392 }
2393
2394 module_init(rtd520Driver_init_module);
2395 module_exit(rtd520Driver_cleanup_module);
2396
2397 MODULE_AUTHOR("Comedi http://www.comedi.org");
2398 MODULE_DESCRIPTION("Comedi low-level driver");
2399 MODULE_LICENSE("GPL");
This page took 0.183011 seconds and 5 git commands to generate.