ni_pcidio.c revision 25985edcedea6396277003854657b5f3cb31a628
1e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef/* 2e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef comedi/drivers/ni_pcidio.c 3e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef driver for National Instruments PCI-DIO-96/PCI-6508 42d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi National Instruments PCI-DIO-32HS 52d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi National Instruments PCI-6503 6e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 7e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef COMEDI - Linux Control and Measurement Device Interface 8e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef Copyright (C) 1999,2002 David A. Schleef <ds@schleef.org> 9e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 10e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef This program is free software; you can redistribute it and/or modify 11e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef it under the terms of the GNU General Public License as published by 12e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef the Free Software Foundation; either version 2 of the License, or 13e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef (at your option) any later version. 14e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 15e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef This program is distributed in the hope that it will be useful, 16e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef but WITHOUT ANY WARRANTY; without even the implied warranty of 17e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef GNU General Public License for more details. 19e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 20e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef You should have received a copy of the GNU General Public License 21e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef along with this program; if not, write to the Free Software 22e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 23e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 24e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef*/ 25e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef/* 26e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefDriver: ni_pcidio 27e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefDescription: National Instruments PCI-DIO32HS, PCI-DIO96, PCI-6533, PCI-6503 28e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefAuthor: ds 29e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefStatus: works 30e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefDevices: [National Instruments] PCI-DIO-32HS (ni_pcidio), PXI-6533, 31e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef PCI-DIO-96, PCI-DIO-96B, PXI-6508, PCI-6503, PCI-6503B, PCI-6503X, 32e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef PXI-6503, PCI-6533, PCI-6534 33e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefUpdated: Sun, 21 Apr 2002 21:03:38 -0700 34e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 35e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefThe DIO-96 appears as four 8255 subdevices. See the 8255 36e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefdriver notes for details. 37e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 38e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefThe DIO32HS board appears as one subdevice, with 32 channels. 39e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefEach channel is individually I/O configurable. The channel order 40e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefis 0=A0, 1=A1, 2=A2, ... 8=B0, 16=C0, 24=D0. The driver only 41e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefsupports simple digital I/O; no handshaking is supported. 42e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 43e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefDMA mostly works for the PCI-DIO32HS, but only in timed input mode. 44e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 45e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefThis driver could be easily modified to support AT-MIO32HS and 46e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefAT-MIO96. 47e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 48e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefThe PCI-6534 requires a firmware upload after power-up to work, the 49e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleeffirmware data and instructions for loading it with comedi_config 50e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefit are contained in the 51e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefcomedi_nonfree_firmware tarball available from http://www.comedi.org 52e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef*/ 53e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 54e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef/* 55e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef This driver is for both the NI PCI-DIO-32HS and the PCI-DIO-96, 56e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef which have very different architectures. But, since the '96 is 57e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef so simple, it is included here. 58e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 59e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef Manuals (available from ftp://ftp.natinst.com/support/manuals) 60e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 61e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 320938c.pdf PCI-DIO-96/PXI-6508/PCI-6503 User Manual 62e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 321464b.pdf AT/PCI-DIO-32HS User Manual 63e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 341329A.pdf PCI-6533 Register-Level Programmer Manual 64e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 341330A.pdf DAQ-DIO Technical Reference Manual 65e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 66e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef */ 67e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 68e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define USE_DMA 6956e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton/* #define DEBUG 1 */ 7056e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton/* #define DEBUG_FLAGS */ 71e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 7225436dc9d84f1be60ff549c9ab712bba2835f284Greg Kroah-Hartman#include <linux/interrupt.h> 734377a026500a3f59e9c41c23d03e55ff2e712379Greg Kroah-Hartman#include <linux/sched.h> 74e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#include "../comedidev.h" 75e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 76e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#include "mite.h" 77e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#include "8255.h" 78e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 79e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#undef DPRINTK 80e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#ifdef DEBUG 81e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define DPRINTK(format, args...) printk(format, ## args) 82e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#else 83e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define DPRINTK(format, args...) 84e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#endif 85e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 86e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define PCI_DIO_SIZE 4096 87e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define PCI_MITE_SIZE 4096 88e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 89e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef/* defines for the PCI-DIO-96 */ 90e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 91e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define NIDIO_8255_BASE(x) ((x)*4) 92e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define NIDIO_A 0 93e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define NIDIO_B 4 94e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define NIDIO_C 8 95e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define NIDIO_D 12 96e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 97e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef/* defines for the PCI-DIO-32HS */ 98e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 99e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Window_Address 4 /* W */ 100e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Interrupt_And_Window_Status 4 /* R */ 101e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define IntStatus1 (1<<0) 102e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define IntStatus2 (1<<1) 103e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define WindowAddressStatus_mask 0x7c 104e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 105e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Master_DMA_And_Interrupt_Control 5 /* W */ 106e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define InterruptLine(x) ((x)&3) 107e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define OpenInt (1<<2) 108e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Group_Status 5 /* R */ 109e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define DataLeft (1<<0) 110e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Req (1<<2) 111e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define StopTrig (1<<3) 112e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 113e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Group_1_Flags 6 /* R */ 114e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Group_2_Flags 7 /* R */ 115e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define TransferReady (1<<0) 116e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define CountExpired (1<<1) 117e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Waited (1<<5) 118e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define PrimaryTC (1<<6) 119e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define SecondaryTC (1<<7) 12056e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* #define SerialRose */ 12156e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* #define ReqRose */ 12256e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* #define Paused */ 123e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 124e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Group_1_First_Clear 6 /* W */ 125e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Group_2_First_Clear 7 /* W */ 126e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ClearWaited (1<<3) 127e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ClearPrimaryTC (1<<4) 128e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ClearSecondaryTC (1<<5) 129e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define DMAReset (1<<6) 130e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define FIFOReset (1<<7) 131e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ClearAll 0xf8 132e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 133e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Group_1_FIFO 8 /* W */ 134e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Group_2_FIFO 12 /* W */ 135e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 136e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Transfer_Count 20 137e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Chip_ID_D 24 138e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Chip_ID_I 25 139e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Chip_ID_O 26 140e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Chip_Version 27 141e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Port_IO(x) (28+(x)) 142e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Port_Pin_Directions(x) (32+(x)) 143e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Port_Pin_Mask(x) (36+(x)) 144e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Port_Pin_Polarities(x) (40+(x)) 145e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 146e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Master_Clock_Routing 45 147e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define RTSIClocking(x) (((x)&3)<<4) 148e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 149e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Group_1_Second_Clear 46 /* W */ 150e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Group_2_Second_Clear 47 /* W */ 151e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ClearExpired (1<<0) 152e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 153e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Port_Pattern(x) (48+(x)) 154e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 155e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Data_Path 64 156e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define FIFOEnableA (1<<0) 157e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define FIFOEnableB (1<<1) 158e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define FIFOEnableC (1<<2) 159e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define FIFOEnableD (1<<3) 160e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Funneling(x) (((x)&3)<<4) 161e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define GroupDirection (1<<7) 162e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 163e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_1 65 164e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define OpMode Protocol_Register_1 165e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define RunMode(x) ((x)&7) 166e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Numbered (1<<3) 167e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 168e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_2 66 169e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ClockReg Protocol_Register_2 170e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ClockLine(x) (((x)&3)<<5) 171e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define InvertStopTrig (1<<7) 172e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define DataLatching(x) (((x)&3)<<5) 173e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 174e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_3 67 175e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Sequence Protocol_Register_3 176e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 177e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_14 68 /* 16 bit */ 178e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ClockSpeed Protocol_Register_14 179e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 180e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_4 70 181e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ReqReg Protocol_Register_4 182e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ReqConditioning(x) (((x)&7)<<3) 183e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 184e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_5 71 185e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define BlockMode Protocol_Register_5 186e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 187e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define FIFO_Control 72 188e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ReadyLevel(x) ((x)&7) 189e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 190e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_6 73 191e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define LinePolarities Protocol_Register_6 192e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define InvertAck (1<<0) 193e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define InvertReq (1<<1) 194e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define InvertClock (1<<2) 195e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define InvertSerial (1<<3) 196e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define OpenAck (1<<4) 197e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define OpenClock (1<<5) 198e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 199e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_7 74 200e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define AckSer Protocol_Register_7 201e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define AckLine(x) (((x)&3)<<2) 202e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ExchangePins (1<<7) 203e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 204e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Interrupt_Control 75 205e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* bits same as flags */ 206e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 207e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define DMA_Line_Control_Group1 76 208e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define DMA_Line_Control_Group2 108 20956e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton/* channel zero is none */ 210e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic inline unsigned primary_DMAChannel_bits(unsigned channel) 211e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 212e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return channel & 0x3; 213e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 2140a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral 215e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic inline unsigned secondary_DMAChannel_bits(unsigned channel) 216e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 217e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return (channel << 2) & 0xc; 218e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 219e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 220e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Transfer_Size_Control 77 221e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define TransferWidth(x) ((x)&3) 222e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define TransferLength(x) (((x)&3)<<3) 223e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define RequireRLevel (1<<5) 224e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 225e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_15 79 226e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define DAQOptions Protocol_Register_15 227e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define StartSource(x) ((x)&0x3) 228e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define InvertStart (1<<2) 229e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define StopSource(x) (((x)&0x3)<<3) 230e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ReqStart (1<<6) 231e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define PreStart (1<<7) 232e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 233e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Pattern_Detection 81 234e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define DetectionMethod (1<<0) 235e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define InvertMatch (1<<1) 236e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define IE_Pattern_Detection (1<<2) 237e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 238e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_9 82 239e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ReqDelay Protocol_Register_9 240e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 241e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_10 83 242e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ReqNotDelay Protocol_Register_10 243e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 244e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_11 84 245e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define AckDelay Protocol_Register_11 246e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 247e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_12 85 248e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define AckNotDelay Protocol_Register_12 249e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 250e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_13 86 251e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Data1Delay Protocol_Register_13 252e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 253e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define Protocol_Register_8 88 /* 32 bit */ 254e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define StartDelay Protocol_Register_8 255e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 256e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefenum pci_6534_firmware_registers { /* 16 bit */ 257e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef Firmware_Control_Register = 0x100, 258e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef Firmware_Status_Register = 0x104, 259e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef Firmware_Data_Register = 0x108, 260e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef Firmware_Mask_Register = 0x10c, 261e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef Firmware_Debug_Register = 0x110, 262e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef}; 263e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef/* main fpga registers (32 bit)*/ 264e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefenum pci_6534_fpga_registers { 265e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_Control1_Register = 0x200, 266e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_Control2_Register = 0x204, 267e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_Irq_Mask_Register = 0x208, 268e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_Status_Register = 0x20c, 269e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_Signature_Register = 0x210, 270e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_SCALS_Counter_Register = 0x280, /*write-clear */ 271e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_SCAMS_Counter_Register = 0x284, /*write-clear */ 272e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_SCBLS_Counter_Register = 0x288, /*write-clear */ 273e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_SCBMS_Counter_Register = 0x28c, /*write-clear */ 274e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_Temp_Control_Register = 0x2a0, 275e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_DAR_Register = 0x2a8, 276e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_ELC_Read_Register = 0x2b8, 277e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_ELC_Write_Register = 0x2bc, 278e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef}; 279e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefenum FPGA_Control_Bits { 280e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef FPGA_Enable_Bit = 0x8000, 281e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef}; 282e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 283e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define TIMER_BASE 50 /* nanoseconds */ 284e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 285e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#ifdef USE_DMA 286e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define IntEn (CountExpired|Waited|PrimaryTC|SecondaryTC) 287e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#else 288e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define IntEn (TransferReady|CountExpired|Waited|PrimaryTC|SecondaryTC) 289e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#endif 290e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 291da91b2692e0939b307f9047192d2b9fe07793e7aBill Pembertonstatic int nidio_attach(struct comedi_device *dev, struct comedi_devconfig *it); 292da91b2692e0939b307f9047192d2b9fe07793e7aBill Pembertonstatic int nidio_detach(struct comedi_device *dev); 2930a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_cancel(struct comedi_device *dev, 2940a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s); 295e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 296139dfbdfacb02e3ef3df936d2fabd1ad5f14ea88Bill Pembertonstatic struct comedi_driver driver_pcidio = { 29768c3dbff9fc9f25872408d0e95980d41733d48d0Bill Pemberton .driver_name = "ni_pcidio", 29868c3dbff9fc9f25872408d0e95980d41733d48d0Bill Pemberton .module = THIS_MODULE, 29968c3dbff9fc9f25872408d0e95980d41733d48d0Bill Pemberton .attach = nidio_attach, 30068c3dbff9fc9f25872408d0e95980d41733d48d0Bill Pemberton .detach = nidio_detach, 301e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef}; 302e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 303a7195f3d92f5fc560e597598a56d9c394b65ee81Bill Pembertonstruct nidio_board { 304a7195f3d92f5fc560e597598a56d9c394b65ee81Bill Pemberton 305e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int dev_id; 306e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef const char *name; 307e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int n_8255; 308e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef unsigned int is_diodaq:1; 309e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef unsigned int uses_firmware:1; 310a7195f3d92f5fc560e597598a56d9c394b65ee81Bill Pemberton}; 311a7195f3d92f5fc560e597598a56d9c394b65ee81Bill Pemberton 312a7195f3d92f5fc560e597598a56d9c394b65ee81Bill Pembertonstatic const struct nidio_board nidio_boards[] = { 313e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3140a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x1150, 3150a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pci-dio-32hs", 3160a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 0, 3170a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 1, 3180a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 319e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3200a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x1320, 3210a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pxi-6533", 3220a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 0, 3230a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 1, 3240a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 325e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3260a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x12b0, 3270a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pci-6534", 3280a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 0, 3290a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 1, 3300a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .uses_firmware = 1, 3310a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 332e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3330a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x0160, 3340a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pci-dio-96", 3350a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 4, 3360a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 0, 3370a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 338e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3390a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x1630, 3400a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pci-dio-96b", 3410a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 4, 3420a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 0, 3430a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 344e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3450a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x13c0, 3460a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pxi-6508", 3470a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 4, 3480a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 0, 3490a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 350e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3510a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x0400, 3520a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pci-6503", 3530a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 1, 3540a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 0, 3550a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 356e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3570a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x1250, 3580a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pci-6503b", 3590a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 1, 3600a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 0, 3610a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 362e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3630a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x17d0, 3640a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pci-6503x", 3650a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 1, 3660a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 0, 3670a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 368e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 3690a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .dev_id = 0x1800, 3700a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .name = "pxi-6503", 3710a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .n_8255 = 1, 3720a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral .is_diodaq = 0, 3730a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral }, 374e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef}; 375e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 376b6ac161364eccce1bea4a23a9de395883e90d7abStoyan Gaydarov#define n_nidio_boards ARRAY_SIZE(nidio_boards) 377a7195f3d92f5fc560e597598a56d9c394b65ee81Bill Pemberton#define this_board ((const struct nidio_board *)dev->board_ptr) 378e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 379e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic DEFINE_PCI_DEVICE_TABLE(ni_pcidio_pci_table) = { 3804e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x1150)}, 3814e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x1320)}, 3824e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x12b0)}, 3834e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x0160)}, 3844e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x1630)}, 3854e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x13c0)}, 3864e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x0400)}, 3874e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x1250)}, 3884e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x17d0)}, 3894e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {PCI_DEVICE(PCI_VENDOR_ID_NI, 0x1800)}, 3904e40cee9c8a46d4231d28ae7ae6d9938cf0526d5Greg Kroah-Hartman {0} 391e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef}; 392e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 393e20903165f0f11827657e0c5d3bfbfdaed13207bDavid SchleefMODULE_DEVICE_TABLE(pci, ni_pcidio_pci_table); 394e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 3952e93aa5b5b8050090a22e162f9af6b18ca3ec47aBill Pembertonstruct nidio96_private { 396e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef struct mite_struct *mite; 397e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int boardtype; 398e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int dio; 399e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef unsigned short OpModeBits; 400e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef struct mite_channel *di_mite_chan; 401e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef struct mite_dma_descriptor_ring *di_mite_ring; 402e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef spinlock_t mite_channel_lock; 4032e93aa5b5b8050090a22e162f9af6b18ca3ec47aBill Pemberton}; 4042e93aa5b5b8050090a22e162f9af6b18ca3ec47aBill Pemberton#define devpriv ((struct nidio96_private *)dev->private) 405e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 4060a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_cmdtest(struct comedi_device *dev, 4070a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s, 4080a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_cmd *cmd); 409da91b2692e0939b307f9047192d2b9fe07793e7aBill Pembertonstatic int ni_pcidio_cmd(struct comedi_device *dev, struct comedi_subdevice *s); 4100a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_inttrig(struct comedi_device *dev, 4110a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s, unsigned int trignum); 412da91b2692e0939b307f9047192d2b9fe07793e7aBill Pembertonstatic int nidio_find_device(struct comedi_device *dev, int bus, int slot); 413e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic int ni_pcidio_ns_to_timer(int *nanosec, int round_mode); 4140a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int setup_mite_dma(struct comedi_device *dev, 4150a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s); 416e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 417e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#ifdef DEBUG_FLAGS 418e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic void ni_pcidio_print_flags(unsigned int flags); 419e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic void ni_pcidio_print_status(unsigned int status); 420e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#else 421e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ni_pcidio_print_flags(x) 422e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define ni_pcidio_print_status(x) 423e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#endif 424e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 425da91b2692e0939b307f9047192d2b9fe07793e7aBill Pembertonstatic int ni_pcidio_request_di_mite_channel(struct comedi_device *dev) 426e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 427e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef unsigned long flags; 428e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 4295f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman spin_lock_irqsave(&devpriv->mite_channel_lock, flags); 430e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef BUG_ON(devpriv->di_mite_chan); 431e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef devpriv->di_mite_chan = 4320a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral mite_request_channel_in_range(devpriv->mite, 4330a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->di_mite_ring, 1, 2); 434e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (devpriv->di_mite_chan == NULL) { 4355f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman spin_unlock_irqrestore(&devpriv->mite_channel_lock, flags); 436e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef comedi_error(dev, "failed to reserve mite dma channel."); 437e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -EBUSY; 438e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 439e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(primary_DMAChannel_bits(devpriv->di_mite_chan->channel) | 4400a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral secondary_DMAChannel_bits(devpriv->di_mite_chan->channel), 4410a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + DMA_Line_Control_Group1); 442e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mmiowb(); 4435f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman spin_unlock_irqrestore(&devpriv->mite_channel_lock, flags); 444e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 445e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 446e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 447da91b2692e0939b307f9047192d2b9fe07793e7aBill Pembertonstatic void ni_pcidio_release_di_mite_channel(struct comedi_device *dev) 448e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 449e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef unsigned long flags; 450e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 4515f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman spin_lock_irqsave(&devpriv->mite_channel_lock, flags); 452e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (devpriv->di_mite_chan) { 453e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_dma_disarm(devpriv->di_mite_chan); 454e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_dma_reset(devpriv->di_mite_chan); 455e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_release_channel(devpriv->di_mite_chan); 456e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef devpriv->di_mite_chan = NULL; 457e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(primary_DMAChannel_bits(0) | 4580a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral secondary_DMAChannel_bits(0), 4590a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + DMA_Line_Control_Group1); 460e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mmiowb(); 461e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 4625f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman spin_unlock_irqrestore(&devpriv->mite_channel_lock, flags); 463e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 464e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 465e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic int nidio96_8255_cb(int dir, int port, int data, unsigned long iobase) 466e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 467e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (dir) { 468e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(data, (void *)(iobase + port)); 469e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 470e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else { 471e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return readb((void *)(iobase + port)); 472e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 473e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 474e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 475da91b2692e0939b307f9047192d2b9fe07793e7aBill Pembertonvoid ni_pcidio_event(struct comedi_device *dev, struct comedi_subdevice *s) 476e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 4770a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral if (s-> 4780a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral async->events & (COMEDI_CB_EOA | COMEDI_CB_ERROR | 4790a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral COMEDI_CB_OVERFLOW)) { 480e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ni_pcidio_cancel(dev, s); 481e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 482e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef comedi_event(dev, s); 483e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 484e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 48570265d24e3404fe798b6edd55a02016b1edb49d7Jiri Slabystatic irqreturn_t nidio_interrupt(int irq, void *d) 486e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 48771b5f4f11971dea972832ad63a994c7e5b45db6bBill Pemberton struct comedi_device *dev = d; 48834c43922e62708d45e9660eee4b4f1fb7b4bf2c7Bill Pemberton struct comedi_subdevice *s = dev->subdevices; 489d163679ceec20c50f9aee880fa76c0c1185244a8Bill Pemberton struct comedi_async *async = s->async; 490e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef struct mite_struct *mite = devpriv->mite; 491e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 49256e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* int i, j; */ 493e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef long int AuxData = 0; 494790c55415aa31f4c732729f94d2c3a54f7d3bfc2Bill Pemberton short data1 = 0; 495790c55415aa31f4c732729f94d2c3a54f7d3bfc2Bill Pemberton short data2 = 0; 496e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int flags; 497e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int status; 498e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int work = 0; 499e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef unsigned int m_status = 0; 500e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef unsigned long irq_flags; 501e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 50256e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* interrupcions parasites */ 503e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (dev->attached == 0) { 50456e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* assume it's from another card */ 505e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return IRQ_NONE; 506e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 507e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 508e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef status = readb(devpriv->mite->daq_io_addr + 5090a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Interrupt_And_Window_Status); 510e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef flags = readb(devpriv->mite->daq_io_addr + Group_1_Flags); 511e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 512e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("ni_pcidio_interrupt: status=0x%02x,flags=0x%02x\n", 513e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef status, flags); 514e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ni_pcidio_print_flags(flags); 515e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ni_pcidio_print_status(status); 516e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 51756e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* printk("buf[0]=%08x\n",*(unsigned int *)async->prealloc_buf); */ 5182d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi /* printk("buf[4096]=%08x\n", 5192d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi *(unsigned int *)(async->prealloc_buf+4096)); */ 520e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 5215f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman spin_lock_irqsave(&devpriv->mite_channel_lock, irq_flags); 522e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (devpriv->di_mite_chan) 523e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef m_status = mite_get_status(devpriv->di_mite_chan); 524e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#ifdef MITE_DEBUG 525e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_print_chsr(m_status); 526e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#endif 5272d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi /* printk("mite_bytes_transferred: %d\n", 5282d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi mite_bytes_transferred(mite,DI_DMA_CHAN)); */ 5292d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi 53056e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* mite_dump_regs(mite); */ 531e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (m_status & CHSR_INT) { 532e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (m_status & CHSR_LINKC) { 533e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(CHOR_CLRLC, 5340a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral mite->mite_io_addr + 5350a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral MITE_CHOR(devpriv->di_mite_chan->channel)); 536e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_sync_input_dma(devpriv->di_mite_chan, s->async); 537e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* XXX need to byteswap */ 538e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 539e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (m_status & ~(CHSR_INT | CHSR_LINKC | CHSR_DONE | CHSR_DRDY | 5400a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral CHSR_DRQ1 | CHSR_MRDY)) { 541e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("unknown mite interrupt, disabling IRQ\n"); 542e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef async->events |= COMEDI_CB_EOA | COMEDI_CB_ERROR; 543e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef disable_irq(dev->irq); 544e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 545e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 5465f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman spin_unlock_irqrestore(&devpriv->mite_channel_lock, irq_flags); 547e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 548e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef while (status & DataLeft) { 549e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef work++; 550e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (work > 20) { 551e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("too much work in interrupt\n"); 552e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, 5530a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + 5540a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Master_DMA_And_Interrupt_Control); 555e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 556e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 557e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 558e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef flags &= IntEn; 559e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 560e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (flags & TransferReady) { 56156e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* DPRINTK("TransferReady\n"); */ 562e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef while (flags & TransferReady) { 563e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef work++; 564e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (work > 100) { 565e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("too much work in interrupt\n"); 566e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, 5670a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + 5682d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi Master_DMA_And_Interrupt_Control 5692d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi ); 570e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef goto out; 571e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 572e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef AuxData = 5730a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral readl(devpriv->mite->daq_io_addr + 5740a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Group_1_FIFO); 575e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef data1 = AuxData & 0xffff; 576e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef data2 = (AuxData & 0xffff0000) >> 16; 577e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef comedi_buf_put(async, data1); 578e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef comedi_buf_put(async, data2); 57956e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* DPRINTK("read:%d, %d\n",data1,data2); */ 580e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef flags = readb(devpriv->mite->daq_io_addr + 5810a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Group_1_Flags); 582e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 5832d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi /* DPRINTK("buf_int_count: %d\n", 5842d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi async->buf_int_count); */ 5852d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi /* DPRINTK("1) IntEn=%d,flags=%d,status=%d\n", 5862d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi IntEn,flags,status); */ 58756e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* ni_pcidio_print_flags(flags); */ 58856e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* ni_pcidio_print_status(status); */ 589e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef async->events |= COMEDI_CB_BLOCK; 590e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 591e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 592e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (flags & CountExpired) { 593e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("CountExpired\n"); 594e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(ClearExpired, 5950a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + 5960a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Group_1_Second_Clear); 597e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef async->events |= COMEDI_CB_EOA; 598e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 599e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, devpriv->mite->daq_io_addr + OpMode); 600e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 601e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else if (flags & Waited) { 602e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("Waited\n"); 603e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(ClearWaited, 6040a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + 6050a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Group_1_First_Clear); 606e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef async->events |= COMEDI_CB_EOA | COMEDI_CB_ERROR; 607e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 608e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else if (flags & PrimaryTC) { 609e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("PrimaryTC\n"); 610e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(ClearPrimaryTC, 6110a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + 6120a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Group_1_First_Clear); 613e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef async->events |= COMEDI_CB_EOA; 614e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else if (flags & SecondaryTC) { 615e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("SecondaryTC\n"); 616e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(ClearSecondaryTC, 6170a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + 6180a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Group_1_First_Clear); 619e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef async->events |= COMEDI_CB_EOA; 620e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 621e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#if 0 622e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef else { 623e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef printk("ni_pcidio: unknown interrupt\n"); 624e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef async->events |= COMEDI_CB_ERROR | COMEDI_CB_EOA; 625e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, 6260a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + 6270a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Master_DMA_And_Interrupt_Control); 628e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 629e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#endif 630e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef flags = readb(devpriv->mite->daq_io_addr + Group_1_Flags); 631e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef status = readb(devpriv->mite->daq_io_addr + 6320a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Interrupt_And_Window_Status); 6332d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi /* DPRINTK("loop end: IntEn=0x%02x,flags=0x%02x," 6342d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi "status=0x%02x\n", IntEn, flags, status); */ 63556e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* ni_pcidio_print_flags(flags); */ 63656e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton /* ni_pcidio_print_status(status); */ 637e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 638e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 6390a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralout: 640e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ni_pcidio_event(dev, s); 641e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#if 0 642e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (!tag) { 643e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x03, 6440a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + 6450a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Master_DMA_And_Interrupt_Control); 646e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 647e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#endif 648e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return IRQ_HANDLED; 649e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 650e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 651e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#ifdef DEBUG_FLAGS 652e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic const char *const flags_strings[] = { 653e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef "TransferReady", "CountExpired", "2", "3", 654e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef "4", "Waited", "PrimaryTC", "SecondaryTC", 655e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef}; 6560a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral 657e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic void ni_pcidio_print_flags(unsigned int flags) 658e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 659e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int i; 660e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 6612d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_INFO "group_1_flags:"); 662e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (i = 7; i >= 0; i--) { 6632d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi if (flags & (1 << i)) 664e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef printk(" %s", flags_strings[i]); 665e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 666e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef printk("\n"); 667e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 6680a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral 669e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic char *status_strings[] = { 670e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef "DataLeft1", "Reserved1", "Req1", "StopTrig1", 671e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef "DataLeft2", "Reserved2", "Req2", "StopTrig2", 672e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef}; 6730a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral 674e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic void ni_pcidio_print_status(unsigned int flags) 675e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 676e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int i; 677e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 6782d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_INFO "group_status:"); 679e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (i = 7; i >= 0; i--) { 6802d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi if (flags & (1 << i)) 681e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef printk(" %s", status_strings[i]); 682e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 683e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef printk("\n"); 684e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 685e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#endif 686e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 687e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#ifdef unused 6880a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic void debug_int(struct comedi_device *dev) 689e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 690e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int a, b; 691e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef static int n_int = 0; 692e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef struct timeval tv; 693e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 694e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef do_gettimeofday(&tv); 695e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef a = readb(devpriv->mite->daq_io_addr + Group_Status); 696e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef b = readb(devpriv->mite->daq_io_addr + Group_1_Flags); 697e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 698e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (n_int < 10) { 699e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("status 0x%02x flags 0x%02x time %06d\n", a, b, 700e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef (int)tv.tv_usec); 701e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 702e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 703e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef while (b & 1) { 704e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(0xff, devpriv->mite->daq_io_addr + Group_1_FIFO); 705e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef b = readb(devpriv->mite->daq_io_addr + Group_1_Flags); 706e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 707e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 708e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef b = readb(devpriv->mite->daq_io_addr + Group_1_Flags); 709e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 710e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (n_int < 10) { 711e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("new status 0x%02x\n", b); 712e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef n_int++; 713e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 714e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 715e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#endif 716e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 7170a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_insn_config(struct comedi_device *dev, 7180a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s, 7190a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_insn *insn, unsigned int *data) 720e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 721e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (insn->n != 1) 722e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -EINVAL; 723e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef switch (data[0]) { 724e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef case INSN_CONFIG_DIO_OUTPUT: 725e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->io_bits |= 1 << CR_CHAN(insn->chanspec); 726e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 727e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef case INSN_CONFIG_DIO_INPUT: 728e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->io_bits &= ~(1 << CR_CHAN(insn->chanspec)); 729e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 730e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef case INSN_CONFIG_DIO_QUERY: 731e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef data[1] = 7320a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral (s-> 7330a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral io_bits & (1 << CR_CHAN(insn->chanspec))) ? COMEDI_OUTPUT : 7340a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral COMEDI_INPUT; 735e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return insn->n; 736e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 737e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef default: 738e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -EINVAL; 739e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 740e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(s->io_bits, devpriv->mite->daq_io_addr + Port_Pin_Directions(0)); 741e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 742e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 1; 743e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 744e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 7450a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_insn_bits(struct comedi_device *dev, 7460a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s, 7470a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_insn *insn, unsigned int *data) 748e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 749e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (insn->n != 2) 750e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -EINVAL; 751e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (data[0]) { 752e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->state &= ~data[0]; 753e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->state |= (data[0] & data[1]); 754e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(s->state, devpriv->mite->daq_io_addr + Port_IO(0)); 755e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 756e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef data[1] = readl(devpriv->mite->daq_io_addr + Port_IO(0)); 757e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 758e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 2; 759e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 760e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 7610a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_cmdtest(struct comedi_device *dev, 7620a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s, struct comedi_cmd *cmd) 763e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 764e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int err = 0; 765e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int tmp; 766e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 767e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* step 1: make sure trigger sources are trivially valid */ 768e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 769e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef tmp = cmd->start_src; 770e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->start_src &= TRIG_NOW | TRIG_INT; 771e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (!cmd->start_src || tmp != cmd->start_src) 772e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 773e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 774e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef tmp = cmd->scan_begin_src; 775e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->scan_begin_src &= TRIG_TIMER | TRIG_EXT; 776e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (!cmd->scan_begin_src || tmp != cmd->scan_begin_src) 777e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 778e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 779e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef tmp = cmd->convert_src; 780e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->convert_src &= TRIG_NOW; 781e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (!cmd->convert_src || tmp != cmd->convert_src) 782e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 783e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 784e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef tmp = cmd->scan_end_src; 785e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->scan_end_src &= TRIG_COUNT; 786e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (!cmd->scan_end_src || tmp != cmd->scan_end_src) 787e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 788e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 789e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef tmp = cmd->stop_src; 790e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->stop_src &= TRIG_COUNT | TRIG_NONE; 791e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (!cmd->stop_src || tmp != cmd->stop_src) 792e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 793e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 794e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (err) 795e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 1; 796e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 7972d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi /* step 2: make sure trigger sources are unique and mutually 7982d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi compatible */ 799e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 800828684f9a6e096f9150bad523c43b75d74b9baddDirk Hohndel /* note that mutual compatibility is not an issue here */ 801e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->start_src != TRIG_NOW && cmd->start_src != TRIG_INT) 802e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 803e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->scan_begin_src != TRIG_TIMER && 8040a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral cmd->scan_begin_src != TRIG_EXT) 805e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 806e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 807e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (err) 808e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 2; 809e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 810e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* step 3: make sure arguments are trivially compatible */ 811e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 812e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->start_arg != 0) { 813e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* same for both TRIG_INT and TRIG_NOW */ 814e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->start_arg = 0; 815e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 816e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 817e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#define MAX_SPEED (TIMER_BASE) /* in nanoseconds */ 818e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 819e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->scan_begin_src == TRIG_TIMER) { 820e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->scan_begin_arg < MAX_SPEED) { 821e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->scan_begin_arg = MAX_SPEED; 822e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 823e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 82425985edcedea6396277003854657b5f3cb31a628Lucas De Marchi /* no minimum speed */ 825e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else { 826e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* TRIG_EXT */ 827e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* should be level/edge, hi/lo specification here */ 828e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->scan_begin_arg != 0) { 829e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->scan_begin_arg = 0; 830e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 831e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 832e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 833e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->convert_arg != 0) { 834e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->convert_arg = 0; 835e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 836e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 837e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 838e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->scan_end_arg != cmd->chanlist_len) { 839e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->scan_end_arg = cmd->chanlist_len; 840e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 841e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 842e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->stop_src == TRIG_COUNT) { 843e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* no limit */ 844e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else { 845e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* TRIG_NONE */ 846e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->stop_arg != 0) { 847e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef cmd->stop_arg = 0; 848e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 849e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 850e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 851e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 852e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (err) 853e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 3; 854e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 855e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* step 4: fix up any arguments */ 856e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 857e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->scan_begin_src == TRIG_TIMER) { 858e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef tmp = cmd->scan_begin_arg; 859e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ni_pcidio_ns_to_timer(&cmd->scan_begin_arg, 8600a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral cmd->flags & TRIG_ROUND_MASK); 861e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (tmp != cmd->scan_begin_arg) 862e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef err++; 863e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 864e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 865e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (err) 866e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 4; 867e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 868e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 869e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 870e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 871e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleefstatic int ni_pcidio_ns_to_timer(int *nanosec, int round_mode) 872e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 873e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int divider, base; 874e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 875e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef base = TIMER_BASE; 876e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 877e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef switch (round_mode) { 878e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef case TRIG_ROUND_NEAREST: 879e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef default: 880e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef divider = (*nanosec + base / 2) / base; 881e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 882e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef case TRIG_ROUND_DOWN: 883e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef divider = (*nanosec) / base; 884e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 885e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef case TRIG_ROUND_UP: 886e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef divider = (*nanosec + base - 1) / base; 887e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 888e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 889e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 890e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef *nanosec = base * divider; 891e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return divider; 892e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 893e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 8940a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_cmd(struct comedi_device *dev, struct comedi_subdevice *s) 895e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 896ea6d0d4cab4f4f2d6a88f3bce4707fe92696fd3fBill Pemberton struct comedi_cmd *cmd = &s->async->cmd; 897e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 898e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* XXX configure ports for input */ 899e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0x0000, devpriv->mite->daq_io_addr + Port_Pin_Directions(0)); 900e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 901e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (1) { 902e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* enable fifos A B C D */ 903e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x0f, devpriv->mite->daq_io_addr + Data_Path); 904e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 905e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* set transfer width a 32 bits */ 906e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(TransferWidth(0) | TransferLength(0), 9070a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Transfer_Size_Control); 908e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else { 909e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x03, devpriv->mite->daq_io_addr + Data_Path); 910e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(TransferWidth(3) | TransferLength(0), 9110a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Transfer_Size_Control); 912e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 913e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 914e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* protocol configuration */ 915e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->scan_begin_src == TRIG_TIMER) { 916e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* page 4-5, "input with internal REQs" */ 917e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0, devpriv->mite->daq_io_addr + OpMode); 918e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, devpriv->mite->daq_io_addr + ClockReg); 919e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(1, devpriv->mite->daq_io_addr + Sequence); 920e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x04, devpriv->mite->daq_io_addr + ReqReg); 921e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(4, devpriv->mite->daq_io_addr + BlockMode); 922e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(3, devpriv->mite->daq_io_addr + LinePolarities); 923e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0xc0, devpriv->mite->daq_io_addr + AckSer); 924e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(ni_pcidio_ns_to_timer(&cmd->scan_begin_arg, 9250a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral TRIG_ROUND_NEAREST), 9260a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + StartDelay); 927e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(1, devpriv->mite->daq_io_addr + ReqDelay); 928e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(1, devpriv->mite->daq_io_addr + ReqNotDelay); 929e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(1, devpriv->mite->daq_io_addr + AckDelay); 930e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x0b, devpriv->mite->daq_io_addr + AckNotDelay); 931e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x01, devpriv->mite->daq_io_addr + Data1Delay); 932e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* manual, page 4-5: ClockSpeed comment is incorrectly listed 933e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef * on DAQOptions */ 934e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(0, devpriv->mite->daq_io_addr + ClockSpeed); 935e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0, devpriv->mite->daq_io_addr + DAQOptions); 936e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else { 937e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* TRIG_EXT */ 938e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* page 4-5, "input with external REQs" */ 939e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0, devpriv->mite->daq_io_addr + OpMode); 940e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, devpriv->mite->daq_io_addr + ClockReg); 941e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0, devpriv->mite->daq_io_addr + Sequence); 942e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, devpriv->mite->daq_io_addr + ReqReg); 943e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(4, devpriv->mite->daq_io_addr + BlockMode); 944e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0, devpriv->mite->daq_io_addr + LinePolarities); 945e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, devpriv->mite->daq_io_addr + AckSer); 946e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(1, devpriv->mite->daq_io_addr + StartDelay); 947e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(1, devpriv->mite->daq_io_addr + ReqDelay); 948e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(1, devpriv->mite->daq_io_addr + ReqNotDelay); 949e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(1, devpriv->mite->daq_io_addr + AckDelay); 950e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x0C, devpriv->mite->daq_io_addr + AckNotDelay); 951e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x10, devpriv->mite->daq_io_addr + Data1Delay); 952e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(0, devpriv->mite->daq_io_addr + ClockSpeed); 953e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x60, devpriv->mite->daq_io_addr + DAQOptions); 954e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 955e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 956e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->stop_src == TRIG_COUNT) { 957e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(cmd->stop_arg, 9580a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Transfer_Count); 959e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else { 960e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* XXX */ 961e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 962e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 963e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#ifdef USE_DMA 964e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(ClearPrimaryTC | ClearSecondaryTC, 9650a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Group_1_First_Clear); 966e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 967e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef { 968e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int retval = setup_mite_dma(dev, s); 969e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (retval) 970e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return retval; 971e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 972e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#else 973e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, devpriv->mite->daq_io_addr + DMA_Line_Control_Group1); 974e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef#endif 975e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, devpriv->mite->daq_io_addr + DMA_Line_Control_Group2); 976e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 977e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* clear and enable interrupts */ 978e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0xff, devpriv->mite->daq_io_addr + Group_1_First_Clear); 9792d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi /* writeb(ClearExpired, 9802d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi devpriv->mite->daq_io_addr+Group_1_Second_Clear); */ 981e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 982e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(IntEn, devpriv->mite->daq_io_addr + Interrupt_Control); 983e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x03, 9840a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Master_DMA_And_Interrupt_Control); 985e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 986e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->stop_src == TRIG_NONE) { 987e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef devpriv->OpModeBits = DataLatching(0) | RunMode(7); 98856e9e16619a0c14dc948cf88b3a7aaa70ac92b45Bill Pemberton } else { /* TRIG_TIMER */ 989e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef devpriv->OpModeBits = Numbered | RunMode(7); 990e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 991e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (cmd->start_src == TRIG_NOW) { 992e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* start */ 993e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(devpriv->OpModeBits, 9940a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + OpMode); 995e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->async->inttrig = NULL; 996e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else { 997e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* TRIG_INT */ 998e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->async->inttrig = ni_pcidio_inttrig; 999e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1000e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1001e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef DPRINTK("ni_pcidio: command started\n"); 1002e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1003e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1004e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 10050a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int setup_mite_dma(struct comedi_device *dev, struct comedi_subdevice *s) 1006e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1007e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int retval; 1008e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1009e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef retval = ni_pcidio_request_di_mite_channel(dev); 1010e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (retval) 1011e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return retval; 1012e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1013e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef devpriv->di_mite_chan->dir = COMEDI_INPUT; 1014e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1015e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_prep_dma(devpriv->di_mite_chan, 32, 32); 1016e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1017e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_dma_arm(devpriv->di_mite_chan); 1018e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1019e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1020e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 10210a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_inttrig(struct comedi_device *dev, 10220a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s, unsigned int trignum) 1023e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1024e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (trignum != 0) 1025e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -EINVAL; 1026e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1027e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(devpriv->OpModeBits, devpriv->mite->daq_io_addr + OpMode); 1028e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->async->inttrig = NULL; 1029e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1030e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 1; 1031e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1032e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 10330a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_cancel(struct comedi_device *dev, 10340a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s) 1035e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1036e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, 10370a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Master_DMA_And_Interrupt_Control); 1038e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ni_pcidio_release_di_mite_channel(dev); 1039e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1040e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1041e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1042e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 10430a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int ni_pcidio_change(struct comedi_device *dev, 10440a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral struct comedi_subdevice *s, unsigned long new_size) 1045e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1046e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int ret; 1047e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1048e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ret = mite_buf_change(devpriv->di_mite_ring, s->async); 1049e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (ret < 0) 1050e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1051e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1052e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef memset(s->async->prealloc_buf, 0xaa, s->async->prealloc_bufsz); 1053e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1054e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1055e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1056e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 10570a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int pci_6534_load_fpga(struct comedi_device *dev, int fpga_index, 10582d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi u8 *data, int data_len) 1059e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1060e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef static const int timeout = 1000; 1061e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int i, j; 1062e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(0x80 | fpga_index, 10630a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Firmware_Control_Register); 1064e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(0xc0 | fpga_index, 10650a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Firmware_Control_Register); 1066e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (i = 0; 10670a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral (readw(devpriv->mite->daq_io_addr + 10680a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Firmware_Status_Register) & 0x2) == 0 && i < timeout; ++i) { 1069e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef udelay(1); 1070e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1071e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (i == timeout) { 10722d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_WARNING "ni_pcidio: failed to load fpga %i, " 10732d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi "waiting for status 0x2\n", fpga_index); 1074e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -EIO; 1075e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1076e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(0x80 | fpga_index, 10770a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Firmware_Control_Register); 1078e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (i = 0; 10790a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral readw(devpriv->mite->daq_io_addr + Firmware_Status_Register) != 10800a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral 0x3 && i < timeout; ++i) { 1081e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef udelay(1); 1082e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1083e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (i == timeout) { 10842d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_WARNING "ni_pcidio: failed to load fpga %i, " 10852d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi "waiting for status 0x3\n", fpga_index); 1086e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -EIO; 1087e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1088e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (j = 0; j + 1 < data_len;) { 1089e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef unsigned int value = data[j++]; 1090e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef value |= data[j++] << 8; 1091e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(value, 10920a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + Firmware_Data_Register); 1093e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (i = 0; 10940a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral (readw(devpriv->mite->daq_io_addr + 10950a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Firmware_Status_Register) & 0x2) == 0 10960a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral && i < timeout; ++i) { 1097e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef udelay(1); 1098e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1099e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (i == timeout) { 1100e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef printk("ni_pcidio: failed to load word into fpga %i\n", 11010a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral fpga_index); 1102e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -EIO; 1103e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1104e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (need_resched()) 1105e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef schedule(); 1106e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1107e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(0x0, devpriv->mite->daq_io_addr + Firmware_Control_Register); 1108e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1109e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1110e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 11110a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int pci_6534_reset_fpga(struct comedi_device *dev, int fpga_index) 1112e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1113e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return pci_6534_load_fpga(dev, fpga_index, NULL, 0); 1114e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1115e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 11160a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int pci_6534_reset_fpgas(struct comedi_device *dev) 1117e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1118e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int ret; 1119e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int i; 1120e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(0x0, devpriv->mite->daq_io_addr + Firmware_Control_Register); 1121e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (i = 0; i < 3; ++i) { 1122e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ret = pci_6534_reset_fpga(dev, i); 1123e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (ret < 0) 1124e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef break; 1125e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1126e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writew(0x0, devpriv->mite->daq_io_addr + Firmware_Mask_Register); 1127e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1128e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1129e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 11300a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic void pci_6534_init_main_fpga(struct comedi_device *dev) 1131e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1132e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0, devpriv->mite->daq_io_addr + FPGA_Control1_Register); 1133e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0, devpriv->mite->daq_io_addr + FPGA_Control2_Register); 1134e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0, devpriv->mite->daq_io_addr + FPGA_SCALS_Counter_Register); 1135e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0, devpriv->mite->daq_io_addr + FPGA_SCAMS_Counter_Register); 1136e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0, devpriv->mite->daq_io_addr + FPGA_SCBLS_Counter_Register); 1137e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0, devpriv->mite->daq_io_addr + FPGA_SCBMS_Counter_Register); 1138e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1139e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 11400a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int pci_6534_upload_firmware(struct comedi_device *dev, int options[]) 1141e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1142e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int ret; 1143e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef void *main_fpga_data, *scarab_a_data, *scarab_b_data; 1144e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int main_fpga_data_len, scarab_a_data_len, scarab_b_data_len; 1145e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1146e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (options[COMEDI_DEVCONF_AUX_DATA_LENGTH] == 0) 1147e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1148e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ret = pci_6534_reset_fpgas(dev); 1149e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (ret < 0) 1150e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1151e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef main_fpga_data = comedi_aux_data(options, 0); 1152e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef main_fpga_data_len = options[COMEDI_DEVCONF_AUX_DATA0_LENGTH]; 1153e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ret = pci_6534_load_fpga(dev, 2, main_fpga_data, main_fpga_data_len); 1154e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (ret < 0) 1155e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1156e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef pci_6534_init_main_fpga(dev); 1157e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef scarab_a_data = comedi_aux_data(options, 1); 1158e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef scarab_a_data_len = options[COMEDI_DEVCONF_AUX_DATA1_LENGTH]; 1159e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ret = pci_6534_load_fpga(dev, 0, scarab_a_data, scarab_a_data_len); 1160e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (ret < 0) 1161e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1162e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef scarab_b_data = comedi_aux_data(options, 2); 1163e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef scarab_b_data_len = options[COMEDI_DEVCONF_AUX_DATA2_LENGTH]; 1164e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ret = pci_6534_load_fpga(dev, 1, scarab_b_data, scarab_b_data_len); 1165e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (ret < 0) 1166e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1167e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1168e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1169e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 11700a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int nidio_attach(struct comedi_device *dev, struct comedi_devconfig *it) 1171e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 117234c43922e62708d45e9660eee4b4f1fb7b4bf2c7Bill Pemberton struct comedi_subdevice *s; 1173e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int i; 1174e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int ret; 1175e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int n_subdevices; 1176e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef unsigned int irq; 1177e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 11782d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_INFO "comedi%d: nidio:", dev->minor); 1179e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 11802d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi ret = alloc_private(dev, sizeof(struct nidio96_private)); 11812d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi if (ret < 0) 1182e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1183e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef spin_lock_init(&devpriv->mite_channel_lock); 1184e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1185e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ret = nidio_find_device(dev, it->options[0], it->options[1]); 1186e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (ret < 0) 1187e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1188e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1189e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ret = mite_setup(devpriv->mite); 1190e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (ret < 0) { 11912d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_WARNING "error setting up mite\n"); 1192e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1193e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1194e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef comedi_set_hw_dev(dev, &devpriv->mite->pcidev->dev); 1195e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef devpriv->di_mite_ring = mite_alloc_ring(devpriv->mite); 1196e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (devpriv->di_mite_ring == NULL) 1197e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -ENOMEM; 1198e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1199e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef dev->board_name = this_board->name; 1200e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef irq = mite_irq(devpriv->mite); 12012d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_INFO " %s", dev->board_name); 1202e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (this_board->uses_firmware) { 1203e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef ret = pci_6534_upload_firmware(dev, it->options); 1204e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (ret < 0) 1205e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1206e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 12072d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi if (!this_board->is_diodaq) 1208e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef n_subdevices = this_board->n_8255; 12092d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi else 1210e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef n_subdevices = 1; 12112d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi 12122d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi ret = alloc_subdevices(dev, n_subdevices); 12132d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi if (ret < 0) 1214e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return ret; 1215e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1216e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (!this_board->is_diodaq) { 1217e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (i = 0; i < this_board->n_8255; i++) { 1218e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef subdev_8255_init(dev, dev->subdevices + i, 12190a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral nidio96_8255_cb, 12200a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral (unsigned long)(devpriv->mite-> 12210a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral daq_io_addr + 12220a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral NIDIO_8255_BASE(i))); 1223e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1224e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } else { 1225e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 12262d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_INFO " rev=%d", 12270a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral readb(devpriv->mite->daq_io_addr + Chip_Version)); 1228e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1229e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s = dev->subdevices + 0; 1230e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1231e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef dev->read_subdev = s; 1232e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->type = COMEDI_SUBD_DIO; 1233e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->subdev_flags = 12340a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral SDF_READABLE | SDF_WRITABLE | SDF_LSAMPL | SDF_PACKED | 12350a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral SDF_CMD_READ; 1236e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->n_chan = 32; 1237e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->range_table = &range_digital; 1238e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->maxdata = 1; 1239e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->insn_config = &ni_pcidio_insn_config; 1240e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->insn_bits = &ni_pcidio_insn_bits; 1241e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->do_cmd = &ni_pcidio_cmd; 1242e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->do_cmdtest = &ni_pcidio_cmdtest; 1243e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->cancel = &ni_pcidio_cancel; 1244e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->len_chanlist = 32; /* XXX */ 1245e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->buf_change = &ni_pcidio_change; 1246e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef s->async_dma_dir = DMA_BIDIRECTIONAL; 1247e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1248e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0, devpriv->mite->daq_io_addr + Port_IO(0)); 1249e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0, devpriv->mite->daq_io_addr + Port_Pin_Directions(0)); 1250e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writel(0, devpriv->mite->daq_io_addr + Port_Pin_Mask(0)); 1251e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1252e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef /* disable interrupts on board */ 1253e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef writeb(0x00, 12540a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral devpriv->mite->daq_io_addr + 12550a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral Master_DMA_And_Interrupt_Control); 1256e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 12575f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman ret = request_irq(irq, nidio_interrupt, IRQF_SHARED, 12585f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman "ni_pcidio", dev); 12592d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi if (ret < 0) 12602d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_WARNING " irq not available"); 12612d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi 1262e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef dev->irq = irq; 1263e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1264e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1265e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef printk("\n"); 1266e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1267e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1268e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1269e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 12700a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int nidio_detach(struct comedi_device *dev) 1271e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1272e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int i; 1273e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1274e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (this_board && !this_board->is_diodaq) { 12752d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi for (i = 0; i < this_board->n_8255; i++) 1276e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef subdev_8255_cleanup(dev, dev->subdevices + i); 1277e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1278e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1279e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (dev->irq) 12805f74ea14c07fee91d3bdbaad88bff6264c6200e6Greg Kroah-Hartman free_irq(dev->irq, dev); 1281e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1282e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (devpriv) { 1283e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (devpriv->di_mite_ring) { 1284e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_free_ring(devpriv->di_mite_ring); 1285e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef devpriv->di_mite_ring = NULL; 1286e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1287e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (devpriv->mite) 1288e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_unsetup(devpriv->mite); 1289e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1290e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1291e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1292e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 12930a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukralstatic int nidio_find_device(struct comedi_device *dev, int bus, int slot) 1294e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef{ 1295e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef struct mite_struct *mite; 1296e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef int i; 1297e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1298e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (mite = mite_devices; mite; mite = mite->next) { 1299e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (mite->used) 1300e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef continue; 1301e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (bus || slot) { 1302e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (bus != mite->pcidev->bus->number || 13030a85b6f0ab0d2edb0d41b32697111ce0e4f43496Mithlesh Thukral slot != PCI_SLOT(mite->pcidev->devfn)) 1304e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef continue; 1305e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1306e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef for (i = 0; i < n_nidio_boards; i++) { 1307e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef if (mite_device_id(mite) == nidio_boards[i].dev_id) { 1308e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef dev->board_ptr = nidio_boards + i; 1309e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef devpriv->mite = mite; 1310e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1311e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return 0; 1312e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1313e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 1314e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef } 13152d2facda0b71609be294aa1fd5f56d2cdbcbb794Benjamin Adolphi printk(KERN_WARNING "no device found\n"); 1316e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef mite_list_devices(); 1317e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef return -EIO; 1318e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef} 1319e20903165f0f11827657e0c5d3bfbfdaed13207bDavid Schleef 1320727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomasstatic int __devinit driver_pcidio_pci_probe(struct pci_dev *dev, 1321727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas const struct pci_device_id *ent) 1322727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas{ 1323727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas return comedi_pci_auto_config(dev, driver_pcidio.driver_name); 1324727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas} 1325727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas 1326727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomasstatic void __devexit driver_pcidio_pci_remove(struct pci_dev *dev) 1327727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas{ 1328727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas comedi_pci_auto_unconfig(dev); 1329727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas} 1330727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas 1331727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomasstatic struct pci_driver driver_pcidio_pci_driver = { 1332727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas .id_table = ni_pcidio_pci_table, 1333727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas .probe = &driver_pcidio_pci_probe, 1334727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas .remove = __devexit_p(&driver_pcidio_pci_remove) 1335727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas}; 1336727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas 1337727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomasstatic int __init driver_pcidio_init_module(void) 1338727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas{ 1339727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas int retval; 1340727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas 1341727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas retval = comedi_driver_register(&driver_pcidio); 1342727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas if (retval < 0) 1343727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas return retval; 1344727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas 1345727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas driver_pcidio_pci_driver.name = (char *)driver_pcidio.driver_name; 1346727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas return pci_register_driver(&driver_pcidio_pci_driver); 1347727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas} 1348727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas 1349727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomasstatic void __exit driver_pcidio_cleanup_module(void) 1350727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas{ 1351727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas pci_unregister_driver(&driver_pcidio_pci_driver); 1352727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas comedi_driver_unregister(&driver_pcidio); 1353727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas} 1354727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomas 1355727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomasmodule_init(driver_pcidio_init_module); 1356727b286b44ea359d66f47d241cc2cdad36ed7bdcArun Thomasmodule_exit(driver_pcidio_cleanup_module); 13573c323c01b6bd5fd01be21a8f0cdc11e55997aa06Ian Abbott 13583c323c01b6bd5fd01be21a8f0cdc11e55997aa06Ian AbbottMODULE_AUTHOR("Comedi http://www.comedi.org"); 13593c323c01b6bd5fd01be21a8f0cdc11e55997aa06Ian AbbottMODULE_DESCRIPTION("Comedi low-level driver"); 13603c323c01b6bd5fd01be21a8f0cdc11e55997aa06Ian AbbottMODULE_LICENSE("GPL"); 1361