cb_pcidas.c revision 0cdfbe157cd2244951568e6d3ffe3423ce7f2f50
1/* 2 comedi/drivers/cb_pcidas.c 3 4 Developed by Ivan Martinez and Frank Mori Hess, with valuable help from 5 David Schleef and the rest of the Comedi developers comunity. 6 7 Copyright (C) 2001-2003 Ivan Martinez <imr@oersted.dtu.dk> 8 Copyright (C) 2001,2002 Frank Mori Hess <fmhess@users.sourceforge.net> 9 10 COMEDI - Linux Control and Measurement Device Interface 11 Copyright (C) 1997-8 David A. Schleef <ds@schleef.org> 12 13 This program is free software; you can redistribute it and/or modify 14 it under the terms of the GNU General Public License as published by 15 the Free Software Foundation; either version 2 of the License, or 16 (at your option) any later version. 17 18 This program is distributed in the hope that it will be useful, 19 but WITHOUT ANY WARRANTY; without even the implied warranty of 20 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 21 GNU General Public License for more details. 22 23 You should have received a copy of the GNU General Public License 24 along with this program; if not, write to the Free Software 25 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 26 27************************************************************************ 28*/ 29/* 30Driver: cb_pcidas 31Description: MeasurementComputing PCI-DAS series with the AMCC S5933 PCI controller 32Author: Ivan Martinez <imr@oersted.dtu.dk>, 33 Frank Mori Hess <fmhess@users.sourceforge.net> 34Updated: 2003-3-11 35Devices: [Measurement Computing] PCI-DAS1602/16 (cb_pcidas), 36 PCI-DAS1602/16jr, PCI-DAS1602/12, PCI-DAS1200, PCI-DAS1200jr, 37 PCI-DAS1000, PCI-DAS1001, PCI_DAS1002 38 39Status: 40 There are many reports of the driver being used with most of the 41 supported cards. Despite no detailed log is maintained, it can 42 be said that the driver is quite tested and stable. 43 44 The boards may be autocalibrated using the comedi_calibrate 45 utility. 46 47Configuration options: 48 [0] - PCI bus of device (optional) 49 [1] - PCI slot of device (optional) 50 If bus/slot is not specified, the first supported 51 PCI device found will be used. 52 53For commands, the scanned channels must be consecutive 54(i.e. 4-5-6-7, 2-3-4,...), and must all have the same 55range and aref. 56 57AI Triggering: 58 For start_src == TRIG_EXT, the A/D EXTERNAL TRIGGER IN (pin 45) is used. 59 For 1602 series, the start_arg is interpreted as follows: 60 start_arg == 0 => gated trigger (level high) 61 start_arg == CR_INVERT => gated trigger (level low) 62 start_arg == CR_EDGE => Rising edge 63 start_arg == CR_EDGE | CR_INVERT => Falling edge 64 For the other boards the trigger will be done on rising edge 65*/ 66/* 67 68TODO: 69 70analog triggering on 1602 series 71*/ 72 73#include "../comedidev.h" 74#include <linux/delay.h> 75#include <linux/interrupt.h> 76 77#include "8253.h" 78#include "8255.h" 79#include "amcc_s5933.h" 80#include "comedi_fc.h" 81 82/* PCI vendor number of ComputerBoards/MeasurementComputing */ 83#define PCI_VENDOR_ID_CB 0x1307 84#define TIMER_BASE 100 /* 10MHz master clock */ 85#define AI_BUFFER_SIZE 1024 /* maximum fifo size of any supported board */ 86#define AO_BUFFER_SIZE 1024 /* maximum fifo size of any supported board */ 87#define NUM_CHANNELS_8800 8 88#define NUM_CHANNELS_7376 1 89#define NUM_CHANNELS_8402 2 90#define NUM_CHANNELS_DAC08 1 91 92/* Control/Status registers */ 93#define INT_ADCFIFO 0 /* INTERRUPT / ADC FIFO register */ 94#define INT_EOS 0x1 /* interrupt end of scan */ 95#define INT_FHF 0x2 /* interrupt fifo half full */ 96#define INT_FNE 0x3 /* interrupt fifo not empty */ 97#define INT_MASK 0x3 /* mask of interrupt select bits */ 98#define INTE 0x4 /* interrupt enable */ 99#define DAHFIE 0x8 /* dac half full interrupt enable */ 100#define EOAIE 0x10 /* end of acquisition interrupt enable */ 101#define DAHFI 0x20 /* dac half full read status / write interrupt clear */ 102#define EOAI 0x40 /* read end of acq. interrupt status / write clear */ 103#define INT 0x80 /* read interrupt status / write clear */ 104#define EOBI 0x200 /* read end of burst interrupt status */ 105#define ADHFI 0x400 /* read half-full interrupt status */ 106#define ADNEI 0x800 /* read fifo not empty interrupt latch status */ 107#define ADNE 0x1000 /* read, fifo not empty (realtime, not latched) status */ 108#define DAEMIE 0x1000 /* write, dac empty interrupt enable */ 109#define LADFUL 0x2000 /* read fifo overflow / write clear */ 110#define DAEMI 0x4000 /* dac fifo empty interrupt status / write clear */ 111 112#define ADCMUX_CONT 2 /* ADC CHANNEL MUX AND CONTROL register */ 113#define BEGIN_SCAN(x) ((x) & 0xf) 114#define END_SCAN(x) (((x) & 0xf) << 4) 115#define GAIN_BITS(x) (((x) & 0x3) << 8) 116#define UNIP 0x800 /* Analog front-end unipolar for range */ 117#define SE 0x400 /* Inputs in single-ended mode */ 118#define PACER_MASK 0x3000 /* pacer source bits */ 119#define PACER_INT 0x1000 /* internal pacer */ 120#define PACER_EXT_FALL 0x2000 /* external falling edge */ 121#define PACER_EXT_RISE 0x3000 /* external rising edge */ 122#define EOC 0x4000 /* adc not busy */ 123 124#define TRIG_CONTSTAT 4 /* TRIGGER CONTROL/STATUS register */ 125#define SW_TRIGGER 0x1 /* software start trigger */ 126#define EXT_TRIGGER 0x2 /* external start trigger */ 127#define ANALOG_TRIGGER 0x3 /* external analog trigger */ 128#define TRIGGER_MASK 0x3 /* mask of bits that determine start trigger */ 129#define TGPOL 0x04 /* invert the edge/level of the external trigger (1602 only) */ 130#define TGSEL 0x08 /* if set edge triggered, otherwise level trigerred (1602 only) */ 131#define TGEN 0x10 /* enable external start trigger */ 132#define BURSTE 0x20 /* burst mode enable */ 133#define XTRCL 0x80 /* clear external trigger */ 134 135#define CALIBRATION_REG 6 /* CALIBRATION register */ 136#define SELECT_8800_BIT 0x100 /* select 8800 caldac */ 137#define SELECT_TRIMPOT_BIT 0x200 /* select ad7376 trim pot */ 138#define SELECT_DAC08_BIT 0x400 /* select dac08 caldac */ 139#define CAL_SRC_BITS(x) (((x) & 0x7) << 11) 140#define CAL_EN_BIT 0x4000 /* read calibration source instead of analog input channel 0 */ 141#define SERIAL_DATA_IN_BIT 0x8000 /* serial data stream going to 8800 and 7376 */ 142 143#define DAC_CSR 0x8 /* dac control and status register */ 144enum dac_csr_bits { 145 DACEN = 0x2, /* dac enable */ 146 DAC_MODE_UPDATE_BOTH = 0x80, /* update both dacs when dac0 is written */ 147}; 148static inline unsigned int DAC_RANGE(unsigned int channel, unsigned int range) 149{ 150 return (range & 0x3) << (8 + 2 * (channel & 0x1)); 151} 152 153static inline unsigned int DAC_RANGE_MASK(unsigned int channel) 154{ 155 return 0x3 << (8 + 2 * (channel & 0x1)); 156}; 157 158/* bits for 1602 series only */ 159enum dac_csr_bits_1602 { 160 DAC_EMPTY = 0x1, /* dac fifo empty, read, write clear */ 161 DAC_START = 0x4, /* start/arm dac fifo operations */ 162 DAC_PACER_MASK = 0x18, /* bits that set dac pacer source */ 163 DAC_PACER_INT = 0x8, /* dac internal pacing */ 164 DAC_PACER_EXT_FALL = 0x10, /* dac external pacing, falling edge */ 165 DAC_PACER_EXT_RISE = 0x18, /* dac external pacing, rising edge */ 166}; 167static inline unsigned int DAC_CHAN_EN(unsigned int channel) 168{ 169 return 1 << (5 + (channel & 0x1)); /* enable channel 0 or 1 */ 170}; 171 172/* analog input fifo */ 173#define ADCDATA 0 /* ADC DATA register */ 174#define ADCFIFOCLR 2 /* ADC FIFO CLEAR */ 175 176/* pacer, counter, dio registers */ 177#define ADC8254 0 178#define DIO_8255 4 179#define DAC8254 8 180 181/* analog output registers for 100x, 1200 series */ 182static inline unsigned int DAC_DATA_REG(unsigned int channel) 183{ 184 return 2 * (channel & 0x1); 185} 186 187/* analog output registers for 1602 series*/ 188#define DACDATA 0 /* DAC DATA register */ 189#define DACFIFOCLR 2 /* DAC FIFO CLEAR */ 190 191/* bit in hexadecimal representation of range index that indicates unipolar input range */ 192#define IS_UNIPOLAR 0x4 193/* analog input ranges for most boards */ 194static const struct comedi_lrange cb_pcidas_ranges = { 195 8, 196 { 197 BIP_RANGE(10), 198 BIP_RANGE(5), 199 BIP_RANGE(2.5), 200 BIP_RANGE(1.25), 201 UNI_RANGE(10), 202 UNI_RANGE(5), 203 UNI_RANGE(2.5), 204 UNI_RANGE(1.25) 205 } 206}; 207 208/* pci-das1001 input ranges */ 209static const struct comedi_lrange cb_pcidas_alt_ranges = { 210 8, 211 { 212 BIP_RANGE(10), 213 BIP_RANGE(1), 214 BIP_RANGE(0.1), 215 BIP_RANGE(0.01), 216 UNI_RANGE(10), 217 UNI_RANGE(1), 218 UNI_RANGE(0.1), 219 UNI_RANGE(0.01) 220 } 221}; 222 223/* analog output ranges */ 224static const struct comedi_lrange cb_pcidas_ao_ranges = { 225 4, 226 { 227 BIP_RANGE(5), 228 BIP_RANGE(10), 229 UNI_RANGE(5), 230 UNI_RANGE(10), 231 } 232}; 233 234enum trimpot_model { 235 AD7376, 236 AD8402, 237}; 238 239struct cb_pcidas_board { 240 const char *name; 241 unsigned short device_id; 242 int ai_nchan; /* Inputs in single-ended mode */ 243 int ai_bits; /* analog input resolution */ 244 int ai_speed; /* fastest conversion period in ns */ 245 int ao_nchan; /* number of analog out channels */ 246 int has_ao_fifo; /* analog output has fifo */ 247 int ao_scan_speed; /* analog output speed for 1602 series (for a scan, not conversion) */ 248 int fifo_size; /* number of samples fifo can hold */ 249 const struct comedi_lrange *ranges; 250 enum trimpot_model trimpot; 251 unsigned has_dac08:1; 252 unsigned is_1602:1; 253}; 254 255static const struct cb_pcidas_board cb_pcidas_boards[] = { 256 { 257 .name = "pci-das1602/16", 258 .device_id = 0x1, 259 .ai_nchan = 16, 260 .ai_bits = 16, 261 .ai_speed = 5000, 262 .ao_nchan = 2, 263 .has_ao_fifo = 1, 264 .ao_scan_speed = 10000, 265 .fifo_size = 512, 266 .ranges = &cb_pcidas_ranges, 267 .trimpot = AD8402, 268 .has_dac08 = 1, 269 .is_1602 = 1, 270 }, { 271 .name = "pci-das1200", 272 .device_id = 0xF, 273 .ai_nchan = 16, 274 .ai_bits = 12, 275 .ai_speed = 3200, 276 .ao_nchan = 2, 277 .fifo_size = 1024, 278 .ranges = &cb_pcidas_ranges, 279 .trimpot = AD7376, 280 }, { 281 .name = "pci-das1602/12", 282 .device_id = 0x10, 283 .ai_nchan = 16, 284 .ai_bits = 12, 285 .ai_speed = 3200, 286 .ao_nchan = 2, 287 .has_ao_fifo = 1, 288 .ao_scan_speed = 4000, 289 .fifo_size = 1024, 290 .ranges = &cb_pcidas_ranges, 291 .trimpot = AD7376, 292 .is_1602 = 1, 293 }, { 294 .name = "pci-das1200/jr", 295 .device_id = 0x19, 296 .ai_nchan = 16, 297 .ai_bits = 12, 298 .ai_speed = 3200, 299 .fifo_size = 1024, 300 .ranges = &cb_pcidas_ranges, 301 .trimpot = AD7376, 302 }, { 303 .name = "pci-das1602/16/jr", 304 .device_id = 0x1C, 305 .ai_nchan = 16, 306 .ai_bits = 16, 307 .ai_speed = 5000, 308 .fifo_size = 512, 309 .ranges = &cb_pcidas_ranges, 310 .trimpot = AD8402, 311 .has_dac08 = 1, 312 .is_1602 = 1, 313 }, { 314 .name = "pci-das1000", 315 .device_id = 0x4C, 316 .ai_nchan = 16, 317 .ai_bits = 12, 318 .ai_speed = 4000, 319 .fifo_size = 1024, 320 .ranges = &cb_pcidas_ranges, 321 .trimpot = AD7376, 322 }, { 323 .name = "pci-das1001", 324 .device_id = 0x1a, 325 .ai_nchan = 16, 326 .ai_bits = 12, 327 .ai_speed = 6800, 328 .ao_nchan = 2, 329 .fifo_size = 1024, 330 .ranges = &cb_pcidas_alt_ranges, 331 .trimpot = AD7376, 332 }, { 333 .name = "pci-das1002", 334 .device_id = 0x1b, 335 .ai_nchan = 16, 336 .ai_bits = 12, 337 .ai_speed = 6800, 338 .ao_nchan = 2, 339 .fifo_size = 1024, 340 .ranges = &cb_pcidas_ranges, 341 .trimpot = AD7376, 342 }, 343}; 344 345struct cb_pcidas_private { 346 struct pci_dev *pci_dev; 347 /* base addresses */ 348 unsigned long s5933_config; 349 unsigned long control_status; 350 unsigned long adc_fifo; 351 unsigned long pacer_counter_dio; 352 unsigned long ao_registers; 353 /* divisors of master clock for analog input pacing */ 354 unsigned int divisor1; 355 unsigned int divisor2; 356 /* number of analog input samples remaining */ 357 unsigned int count; 358 /* bits to write to registers */ 359 unsigned int adc_fifo_bits; 360 unsigned int s5933_intcsr_bits; 361 unsigned int ao_control_bits; 362 /* fifo buffers */ 363 short ai_buffer[AI_BUFFER_SIZE]; 364 short ao_buffer[AO_BUFFER_SIZE]; 365 /* divisors of master clock for analog output pacing */ 366 unsigned int ao_divisor1; 367 unsigned int ao_divisor2; 368 /* number of analog output samples remaining */ 369 unsigned int ao_count; 370 /* cached values for readback */ 371 int ao_value[2]; 372 unsigned int caldac_value[NUM_CHANNELS_8800]; 373 unsigned int trimpot_value[NUM_CHANNELS_8402]; 374 unsigned int dac08_value; 375 unsigned int calibration_source; 376}; 377 378static inline unsigned int cal_enable_bits(struct comedi_device *dev) 379{ 380 struct cb_pcidas_private *devpriv = dev->private; 381 382 return CAL_EN_BIT | CAL_SRC_BITS(devpriv->calibration_source); 383} 384 385/* 386 * "instructions" read/write data in "one-shot" or "software-triggered" 387 * mode. 388 */ 389static int cb_pcidas_ai_rinsn(struct comedi_device *dev, 390 struct comedi_subdevice *s, 391 struct comedi_insn *insn, unsigned int *data) 392{ 393 struct cb_pcidas_private *devpriv = dev->private; 394 int n, i; 395 unsigned int bits; 396 static const int timeout = 10000; 397 int channel; 398 /* enable calibration input if appropriate */ 399 if (insn->chanspec & CR_ALT_SOURCE) { 400 outw(cal_enable_bits(dev), 401 devpriv->control_status + CALIBRATION_REG); 402 channel = 0; 403 } else { 404 outw(0, devpriv->control_status + CALIBRATION_REG); 405 channel = CR_CHAN(insn->chanspec); 406 } 407 /* set mux limits and gain */ 408 bits = BEGIN_SCAN(channel) | 409 END_SCAN(channel) | GAIN_BITS(CR_RANGE(insn->chanspec)); 410 /* set unipolar/bipolar */ 411 if (CR_RANGE(insn->chanspec) & IS_UNIPOLAR) 412 bits |= UNIP; 413 /* set singleended/differential */ 414 if (CR_AREF(insn->chanspec) != AREF_DIFF) 415 bits |= SE; 416 outw(bits, devpriv->control_status + ADCMUX_CONT); 417 418 /* clear fifo */ 419 outw(0, devpriv->adc_fifo + ADCFIFOCLR); 420 421 /* convert n samples */ 422 for (n = 0; n < insn->n; n++) { 423 /* trigger conversion */ 424 outw(0, devpriv->adc_fifo + ADCDATA); 425 426 /* wait for conversion to end */ 427 /* return -ETIMEDOUT if there is a timeout */ 428 for (i = 0; i < timeout; i++) { 429 if (inw(devpriv->control_status + ADCMUX_CONT) & EOC) 430 break; 431 } 432 if (i == timeout) 433 return -ETIMEDOUT; 434 435 /* read data */ 436 data[n] = inw(devpriv->adc_fifo + ADCDATA); 437 } 438 439 /* return the number of samples read/written */ 440 return n; 441} 442 443static int ai_config_insn(struct comedi_device *dev, struct comedi_subdevice *s, 444 struct comedi_insn *insn, unsigned int *data) 445{ 446 struct cb_pcidas_private *devpriv = dev->private; 447 int id = data[0]; 448 unsigned int source = data[1]; 449 450 switch (id) { 451 case INSN_CONFIG_ALT_SOURCE: 452 if (source >= 8) { 453 dev_err(dev->class_dev, 454 "invalid calibration source: %i\n", 455 source); 456 return -EINVAL; 457 } 458 devpriv->calibration_source = source; 459 break; 460 default: 461 return -EINVAL; 462 break; 463 } 464 return insn->n; 465} 466 467/* analog output insn for pcidas-1000 and 1200 series */ 468static int cb_pcidas_ao_nofifo_winsn(struct comedi_device *dev, 469 struct comedi_subdevice *s, 470 struct comedi_insn *insn, 471 unsigned int *data) 472{ 473 struct cb_pcidas_private *devpriv = dev->private; 474 int channel; 475 unsigned long flags; 476 477 /* set channel and range */ 478 channel = CR_CHAN(insn->chanspec); 479 spin_lock_irqsave(&dev->spinlock, flags); 480 devpriv->ao_control_bits &= 481 ~DAC_MODE_UPDATE_BOTH & ~DAC_RANGE_MASK(channel); 482 devpriv->ao_control_bits |= 483 DACEN | DAC_RANGE(channel, CR_RANGE(insn->chanspec)); 484 outw(devpriv->ao_control_bits, devpriv->control_status + DAC_CSR); 485 spin_unlock_irqrestore(&dev->spinlock, flags); 486 487 /* remember value for readback */ 488 devpriv->ao_value[channel] = data[0]; 489 /* send data */ 490 outw(data[0], devpriv->ao_registers + DAC_DATA_REG(channel)); 491 492 return 1; 493} 494 495/* analog output insn for pcidas-1602 series */ 496static int cb_pcidas_ao_fifo_winsn(struct comedi_device *dev, 497 struct comedi_subdevice *s, 498 struct comedi_insn *insn, unsigned int *data) 499{ 500 struct cb_pcidas_private *devpriv = dev->private; 501 int channel; 502 unsigned long flags; 503 504 /* clear dac fifo */ 505 outw(0, devpriv->ao_registers + DACFIFOCLR); 506 507 /* set channel and range */ 508 channel = CR_CHAN(insn->chanspec); 509 spin_lock_irqsave(&dev->spinlock, flags); 510 devpriv->ao_control_bits &= 511 ~DAC_CHAN_EN(0) & ~DAC_CHAN_EN(1) & ~DAC_RANGE_MASK(channel) & 512 ~DAC_PACER_MASK; 513 devpriv->ao_control_bits |= 514 DACEN | DAC_RANGE(channel, 515 CR_RANGE(insn-> 516 chanspec)) | DAC_CHAN_EN(channel) | 517 DAC_START; 518 outw(devpriv->ao_control_bits, devpriv->control_status + DAC_CSR); 519 spin_unlock_irqrestore(&dev->spinlock, flags); 520 521 /* remember value for readback */ 522 devpriv->ao_value[channel] = data[0]; 523 /* send data */ 524 outw(data[0], devpriv->ao_registers + DACDATA); 525 526 return 1; 527} 528 529/* analog output readback insn */ 530/* XXX loses track of analog output value back after an analog ouput command is executed */ 531static int cb_pcidas_ao_readback_insn(struct comedi_device *dev, 532 struct comedi_subdevice *s, 533 struct comedi_insn *insn, 534 unsigned int *data) 535{ 536 struct cb_pcidas_private *devpriv = dev->private; 537 538 data[0] = devpriv->ao_value[CR_CHAN(insn->chanspec)]; 539 540 return 1; 541} 542 543static int wait_for_nvram_ready(unsigned long s5933_base_addr) 544{ 545 static const int timeout = 1000; 546 unsigned int i; 547 548 for (i = 0; i < timeout; i++) { 549 if ((inb(s5933_base_addr + 550 AMCC_OP_REG_MCSR_NVCMD) & MCSR_NV_BUSY) 551 == 0) 552 return 0; 553 udelay(1); 554 } 555 return -1; 556} 557 558static int nvram_read(struct comedi_device *dev, unsigned int address, 559 uint8_t *data) 560{ 561 struct cb_pcidas_private *devpriv = dev->private; 562 unsigned long iobase = devpriv->s5933_config; 563 564 if (wait_for_nvram_ready(iobase) < 0) 565 return -ETIMEDOUT; 566 567 outb(MCSR_NV_ENABLE | MCSR_NV_LOAD_LOW_ADDR, 568 iobase + AMCC_OP_REG_MCSR_NVCMD); 569 outb(address & 0xff, iobase + AMCC_OP_REG_MCSR_NVDATA); 570 outb(MCSR_NV_ENABLE | MCSR_NV_LOAD_HIGH_ADDR, 571 iobase + AMCC_OP_REG_MCSR_NVCMD); 572 outb((address >> 8) & 0xff, iobase + AMCC_OP_REG_MCSR_NVDATA); 573 outb(MCSR_NV_ENABLE | MCSR_NV_READ, iobase + AMCC_OP_REG_MCSR_NVCMD); 574 575 if (wait_for_nvram_ready(iobase) < 0) 576 return -ETIMEDOUT; 577 578 *data = inb(iobase + AMCC_OP_REG_MCSR_NVDATA); 579 580 return 0; 581} 582 583static int eeprom_read_insn(struct comedi_device *dev, 584 struct comedi_subdevice *s, 585 struct comedi_insn *insn, unsigned int *data) 586{ 587 uint8_t nvram_data; 588 int retval; 589 590 retval = nvram_read(dev, CR_CHAN(insn->chanspec), &nvram_data); 591 if (retval < 0) 592 return retval; 593 594 data[0] = nvram_data; 595 596 return 1; 597} 598 599static void write_calibration_bitstream(struct comedi_device *dev, 600 unsigned int register_bits, 601 unsigned int bitstream, 602 unsigned int bitstream_length) 603{ 604 struct cb_pcidas_private *devpriv = dev->private; 605 static const int write_delay = 1; 606 unsigned int bit; 607 608 for (bit = 1 << (bitstream_length - 1); bit; bit >>= 1) { 609 if (bitstream & bit) 610 register_bits |= SERIAL_DATA_IN_BIT; 611 else 612 register_bits &= ~SERIAL_DATA_IN_BIT; 613 udelay(write_delay); 614 outw(register_bits, devpriv->control_status + CALIBRATION_REG); 615 } 616} 617 618static int caldac_8800_write(struct comedi_device *dev, unsigned int address, 619 uint8_t value) 620{ 621 struct cb_pcidas_private *devpriv = dev->private; 622 static const int num_caldac_channels = 8; 623 static const int bitstream_length = 11; 624 unsigned int bitstream = ((address & 0x7) << 8) | value; 625 static const int caldac_8800_udelay = 1; 626 627 if (address >= num_caldac_channels) { 628 comedi_error(dev, "illegal caldac channel"); 629 return -1; 630 } 631 632 if (value == devpriv->caldac_value[address]) 633 return 1; 634 635 devpriv->caldac_value[address] = value; 636 637 write_calibration_bitstream(dev, cal_enable_bits(dev), bitstream, 638 bitstream_length); 639 640 udelay(caldac_8800_udelay); 641 outw(cal_enable_bits(dev) | SELECT_8800_BIT, 642 devpriv->control_status + CALIBRATION_REG); 643 udelay(caldac_8800_udelay); 644 outw(cal_enable_bits(dev), devpriv->control_status + CALIBRATION_REG); 645 646 return 1; 647} 648 649static int caldac_write_insn(struct comedi_device *dev, 650 struct comedi_subdevice *s, 651 struct comedi_insn *insn, unsigned int *data) 652{ 653 const unsigned int channel = CR_CHAN(insn->chanspec); 654 655 return caldac_8800_write(dev, channel, data[0]); 656} 657 658static int caldac_read_insn(struct comedi_device *dev, 659 struct comedi_subdevice *s, 660 struct comedi_insn *insn, unsigned int *data) 661{ 662 struct cb_pcidas_private *devpriv = dev->private; 663 664 data[0] = devpriv->caldac_value[CR_CHAN(insn->chanspec)]; 665 666 return 1; 667} 668 669/* 1602/16 pregain offset */ 670static int dac08_write(struct comedi_device *dev, unsigned int value) 671{ 672 struct cb_pcidas_private *devpriv = dev->private; 673 674 if (devpriv->dac08_value == value) 675 return 1; 676 677 devpriv->dac08_value = value; 678 679 outw(cal_enable_bits(dev) | (value & 0xff), 680 devpriv->control_status + CALIBRATION_REG); 681 udelay(1); 682 outw(cal_enable_bits(dev) | SELECT_DAC08_BIT | (value & 0xff), 683 devpriv->control_status + CALIBRATION_REG); 684 udelay(1); 685 outw(cal_enable_bits(dev) | (value & 0xff), 686 devpriv->control_status + CALIBRATION_REG); 687 udelay(1); 688 689 return 1; 690} 691 692static int dac08_write_insn(struct comedi_device *dev, 693 struct comedi_subdevice *s, 694 struct comedi_insn *insn, unsigned int *data) 695{ 696 return dac08_write(dev, data[0]); 697} 698 699static int dac08_read_insn(struct comedi_device *dev, 700 struct comedi_subdevice *s, struct comedi_insn *insn, 701 unsigned int *data) 702{ 703 struct cb_pcidas_private *devpriv = dev->private; 704 705 data[0] = devpriv->dac08_value; 706 707 return 1; 708} 709 710static int trimpot_7376_write(struct comedi_device *dev, uint8_t value) 711{ 712 struct cb_pcidas_private *devpriv = dev->private; 713 static const int bitstream_length = 7; 714 unsigned int bitstream = value & 0x7f; 715 unsigned int register_bits; 716 static const int ad7376_udelay = 1; 717 718 register_bits = cal_enable_bits(dev) | SELECT_TRIMPOT_BIT; 719 udelay(ad7376_udelay); 720 outw(register_bits, devpriv->control_status + CALIBRATION_REG); 721 722 write_calibration_bitstream(dev, register_bits, bitstream, 723 bitstream_length); 724 725 udelay(ad7376_udelay); 726 outw(cal_enable_bits(dev), devpriv->control_status + CALIBRATION_REG); 727 728 return 0; 729} 730 731/* For 1602/16 only 732 * ch 0 : adc gain 733 * ch 1 : adc postgain offset */ 734static int trimpot_8402_write(struct comedi_device *dev, unsigned int channel, 735 uint8_t value) 736{ 737 struct cb_pcidas_private *devpriv = dev->private; 738 static const int bitstream_length = 10; 739 unsigned int bitstream = ((channel & 0x3) << 8) | (value & 0xff); 740 unsigned int register_bits; 741 static const int ad8402_udelay = 1; 742 743 register_bits = cal_enable_bits(dev) | SELECT_TRIMPOT_BIT; 744 udelay(ad8402_udelay); 745 outw(register_bits, devpriv->control_status + CALIBRATION_REG); 746 747 write_calibration_bitstream(dev, register_bits, bitstream, 748 bitstream_length); 749 750 udelay(ad8402_udelay); 751 outw(cal_enable_bits(dev), devpriv->control_status + CALIBRATION_REG); 752 753 return 0; 754} 755 756static int cb_pcidas_trimpot_write(struct comedi_device *dev, 757 unsigned int channel, unsigned int value) 758{ 759 const struct cb_pcidas_board *thisboard = comedi_board(dev); 760 struct cb_pcidas_private *devpriv = dev->private; 761 762 if (devpriv->trimpot_value[channel] == value) 763 return 1; 764 765 devpriv->trimpot_value[channel] = value; 766 switch (thisboard->trimpot) { 767 case AD7376: 768 trimpot_7376_write(dev, value); 769 break; 770 case AD8402: 771 trimpot_8402_write(dev, channel, value); 772 break; 773 default: 774 comedi_error(dev, "driver bug?"); 775 return -1; 776 break; 777 } 778 779 return 1; 780} 781 782static int trimpot_write_insn(struct comedi_device *dev, 783 struct comedi_subdevice *s, 784 struct comedi_insn *insn, unsigned int *data) 785{ 786 unsigned int channel = CR_CHAN(insn->chanspec); 787 788 return cb_pcidas_trimpot_write(dev, channel, data[0]); 789} 790 791static int trimpot_read_insn(struct comedi_device *dev, 792 struct comedi_subdevice *s, 793 struct comedi_insn *insn, unsigned int *data) 794{ 795 struct cb_pcidas_private *devpriv = dev->private; 796 unsigned int channel = CR_CHAN(insn->chanspec); 797 798 data[0] = devpriv->trimpot_value[channel]; 799 800 return 1; 801} 802 803static int cb_pcidas_ai_cmdtest(struct comedi_device *dev, 804 struct comedi_subdevice *s, 805 struct comedi_cmd *cmd) 806{ 807 const struct cb_pcidas_board *thisboard = comedi_board(dev); 808 struct cb_pcidas_private *devpriv = dev->private; 809 int err = 0; 810 int tmp; 811 int i, gain, start_chan; 812 813 /* step 1: trigger sources are trivially valid */ 814 815 tmp = cmd->start_src; 816 cmd->start_src &= TRIG_NOW | TRIG_EXT; 817 if (!cmd->start_src || tmp != cmd->start_src) 818 err++; 819 820 tmp = cmd->scan_begin_src; 821 cmd->scan_begin_src &= TRIG_FOLLOW | TRIG_TIMER | TRIG_EXT; 822 if (!cmd->scan_begin_src || tmp != cmd->scan_begin_src) 823 err++; 824 825 tmp = cmd->convert_src; 826 cmd->convert_src &= TRIG_TIMER | TRIG_NOW | TRIG_EXT; 827 if (!cmd->convert_src || tmp != cmd->convert_src) 828 err++; 829 830 tmp = cmd->scan_end_src; 831 cmd->scan_end_src &= TRIG_COUNT; 832 if (!cmd->scan_end_src || tmp != cmd->scan_end_src) 833 err++; 834 835 tmp = cmd->stop_src; 836 cmd->stop_src &= TRIG_COUNT | TRIG_NONE; 837 if (!cmd->stop_src || tmp != cmd->stop_src) 838 err++; 839 840 if (err) 841 return 1; 842 843 /* step 2: trigger sources are unique and mutually compatible */ 844 845 if (cmd->start_src != TRIG_NOW && cmd->start_src != TRIG_EXT) 846 err++; 847 if (cmd->scan_begin_src != TRIG_FOLLOW && 848 cmd->scan_begin_src != TRIG_TIMER && 849 cmd->scan_begin_src != TRIG_EXT) 850 err++; 851 if (cmd->convert_src != TRIG_TIMER && 852 cmd->convert_src != TRIG_EXT && cmd->convert_src != TRIG_NOW) 853 err++; 854 if (cmd->stop_src != TRIG_COUNT && cmd->stop_src != TRIG_NONE) 855 err++; 856 857 /* make sure trigger sources are compatible with each other */ 858 if (cmd->scan_begin_src == TRIG_FOLLOW && cmd->convert_src == TRIG_NOW) 859 err++; 860 if (cmd->scan_begin_src != TRIG_FOLLOW && cmd->convert_src != TRIG_NOW) 861 err++; 862 if (cmd->start_src == TRIG_EXT && 863 (cmd->convert_src == TRIG_EXT || cmd->scan_begin_src == TRIG_EXT)) 864 err++; 865 866 if (err) 867 return 2; 868 869 /* step 3: arguments are trivially compatible */ 870 871 switch (cmd->start_src) { 872 case TRIG_EXT: 873 /* External trigger, only CR_EDGE and CR_INVERT flags allowed */ 874 if ((cmd->start_arg 875 & (CR_FLAGS_MASK & ~(CR_EDGE | CR_INVERT))) != 0) { 876 cmd->start_arg &= 877 ~(CR_FLAGS_MASK & ~(CR_EDGE | CR_INVERT)); 878 err++; 879 } 880 if (!thisboard->is_1602 && (cmd->start_arg & CR_INVERT)) { 881 cmd->start_arg &= (CR_FLAGS_MASK & ~CR_INVERT); 882 err++; 883 } 884 break; 885 default: 886 if (cmd->start_arg != 0) { 887 cmd->start_arg = 0; 888 err++; 889 } 890 break; 891 } 892 893 if (cmd->scan_begin_src == TRIG_TIMER) { 894 if (cmd->scan_begin_arg < 895 thisboard->ai_speed * cmd->chanlist_len) { 896 cmd->scan_begin_arg = 897 thisboard->ai_speed * cmd->chanlist_len; 898 err++; 899 } 900 } 901 if (cmd->convert_src == TRIG_TIMER) { 902 if (cmd->convert_arg < thisboard->ai_speed) { 903 cmd->convert_arg = thisboard->ai_speed; 904 err++; 905 } 906 } 907 908 if (cmd->scan_end_arg != cmd->chanlist_len) { 909 cmd->scan_end_arg = cmd->chanlist_len; 910 err++; 911 } 912 if (cmd->stop_src == TRIG_NONE) { 913 /* TRIG_NONE */ 914 if (cmd->stop_arg != 0) { 915 cmd->stop_arg = 0; 916 err++; 917 } 918 } 919 920 if (err) 921 return 3; 922 923 /* step 4: fix up any arguments */ 924 925 if (cmd->scan_begin_src == TRIG_TIMER) { 926 tmp = cmd->scan_begin_arg; 927 i8253_cascade_ns_to_timer_2div(TIMER_BASE, 928 &(devpriv->divisor1), 929 &(devpriv->divisor2), 930 &(cmd->scan_begin_arg), 931 cmd->flags & TRIG_ROUND_MASK); 932 if (tmp != cmd->scan_begin_arg) 933 err++; 934 } 935 if (cmd->convert_src == TRIG_TIMER) { 936 tmp = cmd->convert_arg; 937 i8253_cascade_ns_to_timer_2div(TIMER_BASE, 938 &(devpriv->divisor1), 939 &(devpriv->divisor2), 940 &(cmd->convert_arg), 941 cmd->flags & TRIG_ROUND_MASK); 942 if (tmp != cmd->convert_arg) 943 err++; 944 } 945 946 if (err) 947 return 4; 948 949 /* check channel/gain list against card's limitations */ 950 if (cmd->chanlist) { 951 gain = CR_RANGE(cmd->chanlist[0]); 952 start_chan = CR_CHAN(cmd->chanlist[0]); 953 for (i = 1; i < cmd->chanlist_len; i++) { 954 if (CR_CHAN(cmd->chanlist[i]) != 955 (start_chan + i) % s->n_chan) { 956 comedi_error(dev, 957 "entries in chanlist must be consecutive channels, counting upwards\n"); 958 err++; 959 } 960 if (CR_RANGE(cmd->chanlist[i]) != gain) { 961 comedi_error(dev, 962 "entries in chanlist must all have the same gain\n"); 963 err++; 964 } 965 } 966 } 967 968 if (err) 969 return 5; 970 971 return 0; 972} 973 974static void cb_pcidas_load_counters(struct comedi_device *dev, unsigned int *ns, 975 int rounding_flags) 976{ 977 struct cb_pcidas_private *devpriv = dev->private; 978 979 i8253_cascade_ns_to_timer_2div(TIMER_BASE, &(devpriv->divisor1), 980 &(devpriv->divisor2), ns, 981 rounding_flags & TRIG_ROUND_MASK); 982 983 /* Write the values of ctr1 and ctr2 into counters 1 and 2 */ 984 i8254_load(devpriv->pacer_counter_dio + ADC8254, 0, 1, 985 devpriv->divisor1, 2); 986 i8254_load(devpriv->pacer_counter_dio + ADC8254, 0, 2, 987 devpriv->divisor2, 2); 988} 989 990static int cb_pcidas_ai_cmd(struct comedi_device *dev, 991 struct comedi_subdevice *s) 992{ 993 const struct cb_pcidas_board *thisboard = comedi_board(dev); 994 struct cb_pcidas_private *devpriv = dev->private; 995 struct comedi_async *async = s->async; 996 struct comedi_cmd *cmd = &async->cmd; 997 unsigned int bits; 998 unsigned long flags; 999 1000 /* make sure CAL_EN_BIT is disabled */ 1001 outw(0, devpriv->control_status + CALIBRATION_REG); 1002 /* initialize before settings pacer source and count values */ 1003 outw(0, devpriv->control_status + TRIG_CONTSTAT); 1004 /* clear fifo */ 1005 outw(0, devpriv->adc_fifo + ADCFIFOCLR); 1006 1007 /* set mux limits, gain and pacer source */ 1008 bits = BEGIN_SCAN(CR_CHAN(cmd->chanlist[0])) | 1009 END_SCAN(CR_CHAN(cmd->chanlist[cmd->chanlist_len - 1])) | 1010 GAIN_BITS(CR_RANGE(cmd->chanlist[0])); 1011 /* set unipolar/bipolar */ 1012 if (CR_RANGE(cmd->chanlist[0]) & IS_UNIPOLAR) 1013 bits |= UNIP; 1014 /* set singleended/differential */ 1015 if (CR_AREF(cmd->chanlist[0]) != AREF_DIFF) 1016 bits |= SE; 1017 /* set pacer source */ 1018 if (cmd->convert_src == TRIG_EXT || cmd->scan_begin_src == TRIG_EXT) 1019 bits |= PACER_EXT_RISE; 1020 else 1021 bits |= PACER_INT; 1022 outw(bits, devpriv->control_status + ADCMUX_CONT); 1023 1024 /* load counters */ 1025 if (cmd->convert_src == TRIG_TIMER) 1026 cb_pcidas_load_counters(dev, &cmd->convert_arg, 1027 cmd->flags & TRIG_ROUND_MASK); 1028 else if (cmd->scan_begin_src == TRIG_TIMER) 1029 cb_pcidas_load_counters(dev, &cmd->scan_begin_arg, 1030 cmd->flags & TRIG_ROUND_MASK); 1031 1032 /* set number of conversions */ 1033 if (cmd->stop_src == TRIG_COUNT) 1034 devpriv->count = cmd->chanlist_len * cmd->stop_arg; 1035 /* enable interrupts */ 1036 spin_lock_irqsave(&dev->spinlock, flags); 1037 devpriv->adc_fifo_bits |= INTE; 1038 devpriv->adc_fifo_bits &= ~INT_MASK; 1039 if (cmd->flags & TRIG_WAKE_EOS) { 1040 if (cmd->convert_src == TRIG_NOW && cmd->chanlist_len > 1) { 1041 /* interrupt end of burst */ 1042 devpriv->adc_fifo_bits |= INT_EOS; 1043 } else { 1044 /* interrupt fifo not empty */ 1045 devpriv->adc_fifo_bits |= INT_FNE; 1046 } 1047 } else { 1048 /* interrupt fifo half full */ 1049 devpriv->adc_fifo_bits |= INT_FHF; 1050 } 1051 1052 /* enable (and clear) interrupts */ 1053 outw(devpriv->adc_fifo_bits | EOAI | INT | LADFUL, 1054 devpriv->control_status + INT_ADCFIFO); 1055 spin_unlock_irqrestore(&dev->spinlock, flags); 1056 1057 /* set start trigger and burst mode */ 1058 bits = 0; 1059 if (cmd->start_src == TRIG_NOW) 1060 bits |= SW_TRIGGER; 1061 else if (cmd->start_src == TRIG_EXT) { 1062 bits |= EXT_TRIGGER | TGEN | XTRCL; 1063 if (thisboard->is_1602) { 1064 if (cmd->start_arg & CR_INVERT) 1065 bits |= TGPOL; 1066 if (cmd->start_arg & CR_EDGE) 1067 bits |= TGSEL; 1068 } 1069 } else { 1070 comedi_error(dev, "bug!"); 1071 return -1; 1072 } 1073 if (cmd->convert_src == TRIG_NOW && cmd->chanlist_len > 1) 1074 bits |= BURSTE; 1075 outw(bits, devpriv->control_status + TRIG_CONTSTAT); 1076 1077 return 0; 1078} 1079 1080static int cb_pcidas_ao_cmdtest(struct comedi_device *dev, 1081 struct comedi_subdevice *s, 1082 struct comedi_cmd *cmd) 1083{ 1084 const struct cb_pcidas_board *thisboard = comedi_board(dev); 1085 struct cb_pcidas_private *devpriv = dev->private; 1086 int err = 0; 1087 int tmp; 1088 1089 /* step 1: trigger sources are trivially valid */ 1090 1091 tmp = cmd->start_src; 1092 cmd->start_src &= TRIG_INT; 1093 if (!cmd->start_src || tmp != cmd->start_src) 1094 err++; 1095 1096 tmp = cmd->scan_begin_src; 1097 cmd->scan_begin_src &= TRIG_TIMER | TRIG_EXT; 1098 if (!cmd->scan_begin_src || tmp != cmd->scan_begin_src) 1099 err++; 1100 1101 tmp = cmd->convert_src; 1102 cmd->convert_src &= TRIG_NOW; 1103 if (!cmd->convert_src || tmp != cmd->convert_src) 1104 err++; 1105 1106 tmp = cmd->scan_end_src; 1107 cmd->scan_end_src &= TRIG_COUNT; 1108 if (!cmd->scan_end_src || tmp != cmd->scan_end_src) 1109 err++; 1110 1111 tmp = cmd->stop_src; 1112 cmd->stop_src &= TRIG_COUNT | TRIG_NONE; 1113 if (!cmd->stop_src || tmp != cmd->stop_src) 1114 err++; 1115 1116 if (err) 1117 return 1; 1118 1119 /* step 2: trigger sources are unique and mutually compatible */ 1120 1121 if (cmd->scan_begin_src != TRIG_TIMER && 1122 cmd->scan_begin_src != TRIG_EXT) 1123 err++; 1124 if (cmd->stop_src != TRIG_COUNT && cmd->stop_src != TRIG_NONE) 1125 err++; 1126 1127 if (err) 1128 return 2; 1129 1130 /* step 3: arguments are trivially compatible */ 1131 1132 if (cmd->start_arg != 0) { 1133 cmd->start_arg = 0; 1134 err++; 1135 } 1136 1137 if (cmd->scan_begin_src == TRIG_TIMER) { 1138 if (cmd->scan_begin_arg < thisboard->ao_scan_speed) { 1139 cmd->scan_begin_arg = thisboard->ao_scan_speed; 1140 err++; 1141 } 1142 } 1143 1144 if (cmd->scan_end_arg != cmd->chanlist_len) { 1145 cmd->scan_end_arg = cmd->chanlist_len; 1146 err++; 1147 } 1148 if (cmd->stop_src == TRIG_NONE) { 1149 /* TRIG_NONE */ 1150 if (cmd->stop_arg != 0) { 1151 cmd->stop_arg = 0; 1152 err++; 1153 } 1154 } 1155 1156 if (err) 1157 return 3; 1158 1159 /* step 4: fix up any arguments */ 1160 1161 if (cmd->scan_begin_src == TRIG_TIMER) { 1162 tmp = cmd->scan_begin_arg; 1163 i8253_cascade_ns_to_timer_2div(TIMER_BASE, 1164 &(devpriv->ao_divisor1), 1165 &(devpriv->ao_divisor2), 1166 &(cmd->scan_begin_arg), 1167 cmd->flags & TRIG_ROUND_MASK); 1168 if (tmp != cmd->scan_begin_arg) 1169 err++; 1170 } 1171 1172 if (err) 1173 return 4; 1174 1175 /* check channel/gain list against card's limitations */ 1176 if (cmd->chanlist && cmd->chanlist_len > 1) { 1177 if (CR_CHAN(cmd->chanlist[0]) != 0 || 1178 CR_CHAN(cmd->chanlist[1]) != 1) { 1179 comedi_error(dev, 1180 "channels must be ordered channel 0, channel 1 in chanlist\n"); 1181 err++; 1182 } 1183 } 1184 1185 if (err) 1186 return 5; 1187 1188 return 0; 1189} 1190 1191/* cancel analog input command */ 1192static int cb_pcidas_cancel(struct comedi_device *dev, 1193 struct comedi_subdevice *s) 1194{ 1195 struct cb_pcidas_private *devpriv = dev->private; 1196 unsigned long flags; 1197 1198 spin_lock_irqsave(&dev->spinlock, flags); 1199 /* disable interrupts */ 1200 devpriv->adc_fifo_bits &= ~INTE & ~EOAIE; 1201 outw(devpriv->adc_fifo_bits, devpriv->control_status + INT_ADCFIFO); 1202 spin_unlock_irqrestore(&dev->spinlock, flags); 1203 1204 /* disable start trigger source and burst mode */ 1205 outw(0, devpriv->control_status + TRIG_CONTSTAT); 1206 /* software pacer source */ 1207 outw(0, devpriv->control_status + ADCMUX_CONT); 1208 1209 return 0; 1210} 1211 1212static int cb_pcidas_ao_inttrig(struct comedi_device *dev, 1213 struct comedi_subdevice *s, 1214 unsigned int trig_num) 1215{ 1216 const struct cb_pcidas_board *thisboard = comedi_board(dev); 1217 struct cb_pcidas_private *devpriv = dev->private; 1218 unsigned int num_bytes, num_points = thisboard->fifo_size; 1219 struct comedi_async *async = s->async; 1220 struct comedi_cmd *cmd = &s->async->cmd; 1221 unsigned long flags; 1222 1223 if (trig_num != 0) 1224 return -EINVAL; 1225 1226 /* load up fifo */ 1227 if (cmd->stop_src == TRIG_COUNT && devpriv->ao_count < num_points) 1228 num_points = devpriv->ao_count; 1229 1230 num_bytes = cfc_read_array_from_buffer(s, devpriv->ao_buffer, 1231 num_points * sizeof(short)); 1232 num_points = num_bytes / sizeof(short); 1233 1234 if (cmd->stop_src == TRIG_COUNT) 1235 devpriv->ao_count -= num_points; 1236 /* write data to board's fifo */ 1237 outsw(devpriv->ao_registers + DACDATA, devpriv->ao_buffer, num_bytes); 1238 1239 /* enable dac half-full and empty interrupts */ 1240 spin_lock_irqsave(&dev->spinlock, flags); 1241 devpriv->adc_fifo_bits |= DAEMIE | DAHFIE; 1242 1243 /* enable and clear interrupts */ 1244 outw(devpriv->adc_fifo_bits | DAEMI | DAHFI, 1245 devpriv->control_status + INT_ADCFIFO); 1246 1247 /* start dac */ 1248 devpriv->ao_control_bits |= DAC_START | DACEN | DAC_EMPTY; 1249 outw(devpriv->ao_control_bits, devpriv->control_status + DAC_CSR); 1250 1251 spin_unlock_irqrestore(&dev->spinlock, flags); 1252 1253 async->inttrig = NULL; 1254 1255 return 0; 1256} 1257 1258static int cb_pcidas_ao_cmd(struct comedi_device *dev, 1259 struct comedi_subdevice *s) 1260{ 1261 struct cb_pcidas_private *devpriv = dev->private; 1262 struct comedi_async *async = s->async; 1263 struct comedi_cmd *cmd = &async->cmd; 1264 unsigned int i; 1265 unsigned long flags; 1266 1267 /* set channel limits, gain */ 1268 spin_lock_irqsave(&dev->spinlock, flags); 1269 for (i = 0; i < cmd->chanlist_len; i++) { 1270 /* enable channel */ 1271 devpriv->ao_control_bits |= 1272 DAC_CHAN_EN(CR_CHAN(cmd->chanlist[i])); 1273 /* set range */ 1274 devpriv->ao_control_bits |= DAC_RANGE(CR_CHAN(cmd->chanlist[i]), 1275 CR_RANGE(cmd-> 1276 chanlist[i])); 1277 } 1278 1279 /* disable analog out before settings pacer source and count values */ 1280 outw(devpriv->ao_control_bits, devpriv->control_status + DAC_CSR); 1281 spin_unlock_irqrestore(&dev->spinlock, flags); 1282 1283 /* clear fifo */ 1284 outw(0, devpriv->ao_registers + DACFIFOCLR); 1285 1286 /* load counters */ 1287 if (cmd->scan_begin_src == TRIG_TIMER) { 1288 i8253_cascade_ns_to_timer_2div(TIMER_BASE, 1289 &(devpriv->ao_divisor1), 1290 &(devpriv->ao_divisor2), 1291 &(cmd->scan_begin_arg), 1292 cmd->flags); 1293 1294 /* Write the values of ctr1 and ctr2 into counters 1 and 2 */ 1295 i8254_load(devpriv->pacer_counter_dio + DAC8254, 0, 1, 1296 devpriv->ao_divisor1, 2); 1297 i8254_load(devpriv->pacer_counter_dio + DAC8254, 0, 2, 1298 devpriv->ao_divisor2, 2); 1299 } 1300 /* set number of conversions */ 1301 if (cmd->stop_src == TRIG_COUNT) 1302 devpriv->ao_count = cmd->chanlist_len * cmd->stop_arg; 1303 /* set pacer source */ 1304 spin_lock_irqsave(&dev->spinlock, flags); 1305 switch (cmd->scan_begin_src) { 1306 case TRIG_TIMER: 1307 devpriv->ao_control_bits |= DAC_PACER_INT; 1308 break; 1309 case TRIG_EXT: 1310 devpriv->ao_control_bits |= DAC_PACER_EXT_RISE; 1311 break; 1312 default: 1313 spin_unlock_irqrestore(&dev->spinlock, flags); 1314 comedi_error(dev, "error setting dac pacer source"); 1315 return -1; 1316 break; 1317 } 1318 spin_unlock_irqrestore(&dev->spinlock, flags); 1319 1320 async->inttrig = cb_pcidas_ao_inttrig; 1321 1322 return 0; 1323} 1324 1325/* cancel analog output command */ 1326static int cb_pcidas_ao_cancel(struct comedi_device *dev, 1327 struct comedi_subdevice *s) 1328{ 1329 struct cb_pcidas_private *devpriv = dev->private; 1330 unsigned long flags; 1331 1332 spin_lock_irqsave(&dev->spinlock, flags); 1333 /* disable interrupts */ 1334 devpriv->adc_fifo_bits &= ~DAHFIE & ~DAEMIE; 1335 outw(devpriv->adc_fifo_bits, devpriv->control_status + INT_ADCFIFO); 1336 1337 /* disable output */ 1338 devpriv->ao_control_bits &= ~DACEN & ~DAC_PACER_MASK; 1339 outw(devpriv->ao_control_bits, devpriv->control_status + DAC_CSR); 1340 spin_unlock_irqrestore(&dev->spinlock, flags); 1341 1342 return 0; 1343} 1344 1345static void handle_ao_interrupt(struct comedi_device *dev, unsigned int status) 1346{ 1347 const struct cb_pcidas_board *thisboard = comedi_board(dev); 1348 struct cb_pcidas_private *devpriv = dev->private; 1349 struct comedi_subdevice *s = dev->write_subdev; 1350 struct comedi_async *async = s->async; 1351 struct comedi_cmd *cmd = &async->cmd; 1352 unsigned int half_fifo = thisboard->fifo_size / 2; 1353 unsigned int num_points; 1354 unsigned long flags; 1355 1356 async->events = 0; 1357 1358 if (status & DAEMI) { 1359 /* clear dac empty interrupt latch */ 1360 spin_lock_irqsave(&dev->spinlock, flags); 1361 outw(devpriv->adc_fifo_bits | DAEMI, 1362 devpriv->control_status + INT_ADCFIFO); 1363 spin_unlock_irqrestore(&dev->spinlock, flags); 1364 if (inw(devpriv->ao_registers + DAC_CSR) & DAC_EMPTY) { 1365 if (cmd->stop_src == TRIG_NONE || 1366 (cmd->stop_src == TRIG_COUNT 1367 && devpriv->ao_count)) { 1368 comedi_error(dev, "dac fifo underflow"); 1369 cb_pcidas_ao_cancel(dev, s); 1370 async->events |= COMEDI_CB_ERROR; 1371 } 1372 async->events |= COMEDI_CB_EOA; 1373 } 1374 } else if (status & DAHFI) { 1375 unsigned int num_bytes; 1376 1377 /* figure out how many points we are writing to fifo */ 1378 num_points = half_fifo; 1379 if (cmd->stop_src == TRIG_COUNT && 1380 devpriv->ao_count < num_points) 1381 num_points = devpriv->ao_count; 1382 num_bytes = 1383 cfc_read_array_from_buffer(s, devpriv->ao_buffer, 1384 num_points * sizeof(short)); 1385 num_points = num_bytes / sizeof(short); 1386 1387 if (async->cmd.stop_src == TRIG_COUNT) 1388 devpriv->ao_count -= num_points; 1389 /* write data to board's fifo */ 1390 outsw(devpriv->ao_registers + DACDATA, devpriv->ao_buffer, 1391 num_points); 1392 /* clear half-full interrupt latch */ 1393 spin_lock_irqsave(&dev->spinlock, flags); 1394 outw(devpriv->adc_fifo_bits | DAHFI, 1395 devpriv->control_status + INT_ADCFIFO); 1396 spin_unlock_irqrestore(&dev->spinlock, flags); 1397 } 1398 1399 comedi_event(dev, s); 1400} 1401 1402static irqreturn_t cb_pcidas_interrupt(int irq, void *d) 1403{ 1404 struct comedi_device *dev = (struct comedi_device *)d; 1405 const struct cb_pcidas_board *thisboard = comedi_board(dev); 1406 struct cb_pcidas_private *devpriv = dev->private; 1407 struct comedi_subdevice *s = dev->read_subdev; 1408 struct comedi_async *async; 1409 int status, s5933_status; 1410 int half_fifo = thisboard->fifo_size / 2; 1411 unsigned int num_samples, i; 1412 static const int timeout = 10000; 1413 unsigned long flags; 1414 1415 if (dev->attached == 0) 1416 return IRQ_NONE; 1417 1418 async = s->async; 1419 async->events = 0; 1420 1421 s5933_status = inl(devpriv->s5933_config + AMCC_OP_REG_INTCSR); 1422 1423 if ((INTCSR_INTR_ASSERTED & s5933_status) == 0) 1424 return IRQ_NONE; 1425 1426 /* make sure mailbox 4 is empty */ 1427 inl_p(devpriv->s5933_config + AMCC_OP_REG_IMB4); 1428 /* clear interrupt on amcc s5933 */ 1429 outl(devpriv->s5933_intcsr_bits | INTCSR_INBOX_INTR_STATUS, 1430 devpriv->s5933_config + AMCC_OP_REG_INTCSR); 1431 1432 status = inw(devpriv->control_status + INT_ADCFIFO); 1433 1434 /* check for analog output interrupt */ 1435 if (status & (DAHFI | DAEMI)) 1436 handle_ao_interrupt(dev, status); 1437 /* check for analog input interrupts */ 1438 /* if fifo half-full */ 1439 if (status & ADHFI) { 1440 /* read data */ 1441 num_samples = half_fifo; 1442 if (async->cmd.stop_src == TRIG_COUNT && 1443 num_samples > devpriv->count) { 1444 num_samples = devpriv->count; 1445 } 1446 insw(devpriv->adc_fifo + ADCDATA, devpriv->ai_buffer, 1447 num_samples); 1448 cfc_write_array_to_buffer(s, devpriv->ai_buffer, 1449 num_samples * sizeof(short)); 1450 devpriv->count -= num_samples; 1451 if (async->cmd.stop_src == TRIG_COUNT && devpriv->count == 0) { 1452 async->events |= COMEDI_CB_EOA; 1453 cb_pcidas_cancel(dev, s); 1454 } 1455 /* clear half-full interrupt latch */ 1456 spin_lock_irqsave(&dev->spinlock, flags); 1457 outw(devpriv->adc_fifo_bits | INT, 1458 devpriv->control_status + INT_ADCFIFO); 1459 spin_unlock_irqrestore(&dev->spinlock, flags); 1460 /* else if fifo not empty */ 1461 } else if (status & (ADNEI | EOBI)) { 1462 for (i = 0; i < timeout; i++) { 1463 /* break if fifo is empty */ 1464 if ((ADNE & inw(devpriv->control_status + 1465 INT_ADCFIFO)) == 0) 1466 break; 1467 cfc_write_to_buffer(s, inw(devpriv->adc_fifo)); 1468 if (async->cmd.stop_src == TRIG_COUNT && 1469 --devpriv->count == 0) { 1470 /* end of acquisition */ 1471 cb_pcidas_cancel(dev, s); 1472 async->events |= COMEDI_CB_EOA; 1473 break; 1474 } 1475 } 1476 /* clear not-empty interrupt latch */ 1477 spin_lock_irqsave(&dev->spinlock, flags); 1478 outw(devpriv->adc_fifo_bits | INT, 1479 devpriv->control_status + INT_ADCFIFO); 1480 spin_unlock_irqrestore(&dev->spinlock, flags); 1481 } else if (status & EOAI) { 1482 comedi_error(dev, 1483 "bug! encountered end of acquisition interrupt?"); 1484 /* clear EOA interrupt latch */ 1485 spin_lock_irqsave(&dev->spinlock, flags); 1486 outw(devpriv->adc_fifo_bits | EOAI, 1487 devpriv->control_status + INT_ADCFIFO); 1488 spin_unlock_irqrestore(&dev->spinlock, flags); 1489 } 1490 /* check for fifo overflow */ 1491 if (status & LADFUL) { 1492 comedi_error(dev, "fifo overflow"); 1493 /* clear overflow interrupt latch */ 1494 spin_lock_irqsave(&dev->spinlock, flags); 1495 outw(devpriv->adc_fifo_bits | LADFUL, 1496 devpriv->control_status + INT_ADCFIFO); 1497 spin_unlock_irqrestore(&dev->spinlock, flags); 1498 cb_pcidas_cancel(dev, s); 1499 async->events |= COMEDI_CB_EOA | COMEDI_CB_ERROR; 1500 } 1501 1502 comedi_event(dev, s); 1503 1504 return IRQ_HANDLED; 1505} 1506 1507static struct pci_dev *cb_pcidas_find_pci_device(struct comedi_device *dev, 1508 struct comedi_devconfig *it) 1509{ 1510 const struct cb_pcidas_board *thisboard; 1511 struct pci_dev *pcidev = NULL; 1512 int bus = it->options[0]; 1513 int slot = it->options[1]; 1514 int i; 1515 1516 for_each_pci_dev(pcidev) { 1517 /* is it not a computer boards card? */ 1518 if (pcidev->vendor != PCI_VENDOR_ID_CB) 1519 continue; 1520 /* loop through cards supported by this driver */ 1521 for (i = 0; i < ARRAY_SIZE(cb_pcidas_boards); i++) { 1522 thisboard = &cb_pcidas_boards[i]; 1523 if (thisboard->device_id != pcidev->device) 1524 continue; 1525 /* was a particular bus/slot requested? */ 1526 if (bus || slot) { 1527 /* are we on the wrong bus/slot? */ 1528 if (pcidev->bus->number != bus || 1529 PCI_SLOT(pcidev->devfn) != slot) { 1530 continue; 1531 } 1532 } 1533 dev_dbg(dev->class_dev, 1534 "Found %s on bus %i, slot %i\n", 1535 thisboard->name, 1536 pcidev->bus->number, PCI_SLOT(pcidev->devfn)); 1537 dev->board_ptr = thisboard; 1538 return pcidev; 1539 } 1540 } 1541 dev_err(dev->class_dev, "No supported card found\n"); 1542 return NULL; 1543} 1544 1545static int cb_pcidas_attach(struct comedi_device *dev, 1546 struct comedi_devconfig *it) 1547{ 1548 const struct cb_pcidas_board *thisboard; 1549 struct cb_pcidas_private *devpriv; 1550 struct comedi_subdevice *s; 1551 int i; 1552 int ret; 1553 1554 if (alloc_private(dev, sizeof(struct cb_pcidas_private)) < 0) 1555 return -ENOMEM; 1556 devpriv = dev->private; 1557 1558 devpriv->pci_dev = cb_pcidas_find_pci_device(dev, it); 1559 if (!devpriv->pci_dev) 1560 return -EIO; 1561 thisboard = comedi_board(dev); 1562 1563 if (comedi_pci_enable(devpriv->pci_dev, dev->driver->driver_name)) { 1564 dev_err(dev->class_dev, 1565 "Failed to enable PCI device and request regions\n"); 1566 return -EIO; 1567 } 1568 1569 devpriv->s5933_config = pci_resource_start(devpriv->pci_dev, 0); 1570 devpriv->control_status = pci_resource_start(devpriv->pci_dev, 1); 1571 devpriv->adc_fifo = pci_resource_start(devpriv->pci_dev, 2); 1572 devpriv->pacer_counter_dio = pci_resource_start(devpriv->pci_dev, 3); 1573 if (thisboard->ao_nchan) 1574 devpriv->ao_registers = pci_resource_start(devpriv->pci_dev, 4); 1575 1576 /* disable and clear interrupts on amcc s5933 */ 1577 outl(INTCSR_INBOX_INTR_STATUS, 1578 devpriv->s5933_config + AMCC_OP_REG_INTCSR); 1579 1580 if (request_irq(devpriv->pci_dev->irq, cb_pcidas_interrupt, 1581 IRQF_SHARED, dev->driver->driver_name, dev)) { 1582 dev_dbg(dev->class_dev, "unable to allocate irq %d\n", 1583 devpriv->pci_dev->irq); 1584 return -EINVAL; 1585 } 1586 dev->irq = devpriv->pci_dev->irq; 1587 1588 dev->board_name = thisboard->name; 1589 1590 ret = comedi_alloc_subdevices(dev, 7); 1591 if (ret) 1592 return ret; 1593 1594 s = dev->subdevices + 0; 1595 /* analog input subdevice */ 1596 dev->read_subdev = s; 1597 s->type = COMEDI_SUBD_AI; 1598 s->subdev_flags = SDF_READABLE | SDF_GROUND | SDF_DIFF | SDF_CMD_READ; 1599 /* WARNING: Number of inputs in differential mode is ignored */ 1600 s->n_chan = thisboard->ai_nchan; 1601 s->len_chanlist = thisboard->ai_nchan; 1602 s->maxdata = (1 << thisboard->ai_bits) - 1; 1603 s->range_table = thisboard->ranges; 1604 s->insn_read = cb_pcidas_ai_rinsn; 1605 s->insn_config = ai_config_insn; 1606 s->do_cmd = cb_pcidas_ai_cmd; 1607 s->do_cmdtest = cb_pcidas_ai_cmdtest; 1608 s->cancel = cb_pcidas_cancel; 1609 1610 /* analog output subdevice */ 1611 s = dev->subdevices + 1; 1612 if (thisboard->ao_nchan) { 1613 s->type = COMEDI_SUBD_AO; 1614 s->subdev_flags = SDF_READABLE | SDF_WRITABLE | SDF_GROUND; 1615 s->n_chan = thisboard->ao_nchan; 1616 /* 1617 * analog out resolution is the same as 1618 * analog input resolution, so use ai_bits 1619 */ 1620 s->maxdata = (1 << thisboard->ai_bits) - 1; 1621 s->range_table = &cb_pcidas_ao_ranges; 1622 s->insn_read = cb_pcidas_ao_readback_insn; 1623 if (thisboard->has_ao_fifo) { 1624 dev->write_subdev = s; 1625 s->subdev_flags |= SDF_CMD_WRITE; 1626 s->insn_write = cb_pcidas_ao_fifo_winsn; 1627 s->do_cmdtest = cb_pcidas_ao_cmdtest; 1628 s->do_cmd = cb_pcidas_ao_cmd; 1629 s->cancel = cb_pcidas_ao_cancel; 1630 } else { 1631 s->insn_write = cb_pcidas_ao_nofifo_winsn; 1632 } 1633 } else { 1634 s->type = COMEDI_SUBD_UNUSED; 1635 } 1636 1637 /* 8255 */ 1638 s = dev->subdevices + 2; 1639 ret = subdev_8255_init(dev, s, NULL, 1640 devpriv->pacer_counter_dio + DIO_8255); 1641 if (ret) 1642 return ret; 1643 1644 /* serial EEPROM, */ 1645 s = dev->subdevices + 3; 1646 s->type = COMEDI_SUBD_MEMORY; 1647 s->subdev_flags = SDF_READABLE | SDF_INTERNAL; 1648 s->n_chan = 256; 1649 s->maxdata = 0xff; 1650 s->insn_read = eeprom_read_insn; 1651 1652 /* 8800 caldac */ 1653 s = dev->subdevices + 4; 1654 s->type = COMEDI_SUBD_CALIB; 1655 s->subdev_flags = SDF_READABLE | SDF_WRITABLE | SDF_INTERNAL; 1656 s->n_chan = NUM_CHANNELS_8800; 1657 s->maxdata = 0xff; 1658 s->insn_read = caldac_read_insn; 1659 s->insn_write = caldac_write_insn; 1660 for (i = 0; i < s->n_chan; i++) 1661 caldac_8800_write(dev, i, s->maxdata / 2); 1662 1663 /* trim potentiometer */ 1664 s = dev->subdevices + 5; 1665 s->type = COMEDI_SUBD_CALIB; 1666 s->subdev_flags = SDF_READABLE | SDF_WRITABLE | SDF_INTERNAL; 1667 if (thisboard->trimpot == AD7376) { 1668 s->n_chan = NUM_CHANNELS_7376; 1669 s->maxdata = 0x7f; 1670 } else { 1671 s->n_chan = NUM_CHANNELS_8402; 1672 s->maxdata = 0xff; 1673 } 1674 s->insn_read = trimpot_read_insn; 1675 s->insn_write = trimpot_write_insn; 1676 for (i = 0; i < s->n_chan; i++) 1677 cb_pcidas_trimpot_write(dev, i, s->maxdata / 2); 1678 1679 /* dac08 caldac */ 1680 s = dev->subdevices + 6; 1681 if (thisboard->has_dac08) { 1682 s->type = COMEDI_SUBD_CALIB; 1683 s->subdev_flags = SDF_READABLE | SDF_WRITABLE | SDF_INTERNAL; 1684 s->n_chan = NUM_CHANNELS_DAC08; 1685 s->insn_read = dac08_read_insn; 1686 s->insn_write = dac08_write_insn; 1687 s->maxdata = 0xff; 1688 dac08_write(dev, s->maxdata / 2); 1689 } else 1690 s->type = COMEDI_SUBD_UNUSED; 1691 1692 /* make sure mailbox 4 is empty */ 1693 inl(devpriv->s5933_config + AMCC_OP_REG_IMB4); 1694 /* Set bits to enable incoming mailbox interrupts on amcc s5933. */ 1695 devpriv->s5933_intcsr_bits = 1696 INTCSR_INBOX_BYTE(3) | INTCSR_INBOX_SELECT(3) | 1697 INTCSR_INBOX_FULL_INT; 1698 /* clear and enable interrupt on amcc s5933 */ 1699 outl(devpriv->s5933_intcsr_bits | INTCSR_INBOX_INTR_STATUS, 1700 devpriv->s5933_config + AMCC_OP_REG_INTCSR); 1701 1702 return 1; 1703} 1704 1705static void cb_pcidas_detach(struct comedi_device *dev) 1706{ 1707 struct cb_pcidas_private *devpriv = dev->private; 1708 1709 if (devpriv) { 1710 if (devpriv->s5933_config) { 1711 outl(INTCSR_INBOX_INTR_STATUS, 1712 devpriv->s5933_config + AMCC_OP_REG_INTCSR); 1713 } 1714 } 1715 if (dev->irq) 1716 free_irq(dev->irq, dev); 1717 if (dev->subdevices) 1718 subdev_8255_cleanup(dev, dev->subdevices + 2); 1719 if (devpriv && devpriv->pci_dev) { 1720 if (devpriv->s5933_config) 1721 comedi_pci_disable(devpriv->pci_dev); 1722 pci_dev_put(devpriv->pci_dev); 1723 } 1724} 1725 1726static struct comedi_driver cb_pcidas_driver = { 1727 .driver_name = "cb_pcidas", 1728 .module = THIS_MODULE, 1729 .attach = cb_pcidas_attach, 1730 .detach = cb_pcidas_detach, 1731}; 1732 1733static int __devinit cb_pcidas_pci_probe(struct pci_dev *dev, 1734 const struct pci_device_id *ent) 1735{ 1736 return comedi_pci_auto_config(dev, &cb_pcidas_driver); 1737} 1738 1739static void __devexit cb_pcidas_pci_remove(struct pci_dev *dev) 1740{ 1741 comedi_pci_auto_unconfig(dev); 1742} 1743 1744static DEFINE_PCI_DEVICE_TABLE(cb_pcidas_pci_table) = { 1745 { PCI_DEVICE(PCI_VENDOR_ID_CB, 0x0001) }, 1746 { PCI_DEVICE(PCI_VENDOR_ID_CB, 0x000f) }, 1747 { PCI_DEVICE(PCI_VENDOR_ID_CB, 0x0010) }, 1748 { PCI_DEVICE(PCI_VENDOR_ID_CB, 0x0019) }, 1749 { PCI_DEVICE(PCI_VENDOR_ID_CB, 0x001c) }, 1750 { PCI_DEVICE(PCI_VENDOR_ID_CB, 0x004c) }, 1751 { PCI_DEVICE(PCI_VENDOR_ID_CB, 0x001a) }, 1752 { PCI_DEVICE(PCI_VENDOR_ID_CB, 0x001b) }, 1753 { 0 } 1754}; 1755MODULE_DEVICE_TABLE(pci, cb_pcidas_pci_table); 1756 1757static struct pci_driver cb_pcidas_pci_driver = { 1758 .name = "cb_pcidas", 1759 .id_table = cb_pcidas_pci_table, 1760 .probe = cb_pcidas_pci_probe, 1761 .remove = __devexit_p(cb_pcidas_pci_remove) 1762}; 1763module_comedi_pci_driver(cb_pcidas_driver, cb_pcidas_pci_driver); 1764 1765MODULE_AUTHOR("Comedi http://www.comedi.org"); 1766MODULE_DESCRIPTION("Comedi low-level driver"); 1767MODULE_LICENSE("GPL"); 1768