34 #include "../comedidev.h"
38 #include <linux/sched.h>
39 #include <linux/slab.h>
42 #include <asm/ioctls.h>
43 #include <linux/serial.h>
44 #include <linux/poll.h>
75 #define devpriv ((struct serial2002_private *)dev->private)
83 static long tty_ioctl(
struct file *
f,
unsigned op,
unsigned long param)
85 if (f->
f_op->unlocked_ioctl)
86 return f->
f_op->unlocked_ioctl(f, op, param);
91 static int tty_write(
struct file *
f,
unsigned char *
buf,
int count)
99 result = f->
f_op->write(f, buf, count, &f->
f_pos);
109 static int tty_available(
struct file *f)
116 tty_ioctl(f,
FIONREAD, (
unsigned long)&result);
122 static int tty_read(
struct file *f,
int timeout)
149 (1000000 * (now.tv_sec -
start.tv_sec) +
150 now.tv_usec -
start.tv_usec);
151 if (elapsed > timeout)
155 elapsed) *
HZ) / 10000);
162 if (f->
f_op->read(f, &ch, 1, &f->
f_pos) == 1)
172 if (retries >= timeout)
176 if (f->
f_op->read(f, &ch, 1, &f->
f_pos) == 1) {
188 static void tty_setspeed(
struct file *f,
int speed)
198 tty_ioctl(f,
TCGETS, (
unsigned long)&settings);
200 settings.c_iflag = 0;
201 settings.c_oflag = 0;
202 settings.c_lflag = 0;
204 settings.c_cc[
VMIN] = 0;
205 settings.c_cc[
VTIME] = 0;
208 settings.c_cflag |=
B2400;
212 settings.c_cflag |=
B4800;
216 settings.c_cflag |=
B9600;
220 settings.c_cflag |=
B19200;
224 settings.c_cflag |=
B38400;
228 settings.c_cflag |=
B57600;
236 settings.c_cflag |=
B9600;
240 tty_ioctl(f,
TCSETS, (
unsigned long)&settings);
247 tty_ioctl(f,
TIOCGSERIAL, (
unsigned long)&settings);
249 tty_ioctl(f,
TIOCSSERIAL, (
unsigned long)&settings);
255 static void poll_digital(
struct file *f,
int channel)
259 cmd = 0x40 | (channel & 0x1f);
260 tty_write(f, &cmd, 1);
263 static void poll_channel(
struct file *f,
int channel)
267 cmd = 0x60 | (channel & 0x1f);
268 tty_write(f, &cmd, 1);
281 int data = tty_read(f, timeout);
287 }
else if (data & 0x80) {
288 result.value = (result.value << 7) | (data & 0x7f);
291 switch ((data >> 5) & 0x03) {
305 (result.value << 2) | ((data & 0x60) >> 5);
308 result.index = data & 0x1f;
320 ((data.
value << 5) & 0x20) | (data.
index & 0x1f);
321 tty_write(f, &ch, 1);
325 if (data.
value >= (1L << 30)) {
326 ch[
i] = 0x80 | ((data.
value >> 30) & 0x03);
329 if (data.
value >= (1L << 23)) {
330 ch[
i] = 0x80 | ((data.
value >> 23) & 0x7f);
333 if (data.
value >= (1L << 16)) {
334 ch[
i] = 0x80 | ((data.
value >> 16) & 0x7f);
337 if (data.
value >= (1L << 9)) {
338 ch[
i] = 0x80 | ((data.
value >> 9) & 0x7f);
341 ch[
i] = 0x80 | ((data.
value >> 2) & 0x7f);
343 ch[
i] = ((data.
value << 5) & 0x60) | (data.
index & 0x1f);
375 dig_in_config = kcalloc(32,
sizeof(
struct config_t),
377 dig_out_config = kcalloc(32,
sizeof(
struct config_t),
379 chan_in_config = kcalloc(32,
sizeof(
struct config_t),
381 chan_out_config = kcalloc(32,
sizeof(
struct config_t),
383 if (!dig_in_config || !dig_out_config
384 || !chan_in_config || !chan_out_config) {
386 goto err_alloc_configs;
390 poll_channel(
devpriv->tty, 31);
394 data = serial_read(
devpriv->tty, 1000);
395 if (data.kind !=
is_channel || data.index != 31
396 || !(data.value & 0xe0)) {
402 channel = data.value & 0x1f;
403 kind = (data.value >> 5) & 0x7;
404 command = (data.value >> 8) & 0x3;
407 cur_config = dig_in_config;
411 cur_config = dig_out_config;
415 cur_config = chan_in_config;
419 cur_config = chan_out_config;
423 cur_config = chan_in_config;
522 for (i = 0; i <= 4; i++) {
532 mapping =
devpriv->digital_in_mapping;
538 mapping =
devpriv->digital_out_mapping;
544 mapping =
devpriv->analog_in_mapping;
551 mapping =
devpriv->analog_out_mapping;
558 mapping =
devpriv->encoder_in_mapping;
572 unsigned int *maxdata_list;
575 for (chan = 0, j = 0; j < 32; j++) {
576 if (c[j].kind == kind)
591 if (kind == 1 || kind == 2) {
602 for (chan = 0, j = 0; j < 32; j++) {
603 if (c[j].kind == kind) {
612 range_table_list[chan] =
629 for (i = 0; i <= 4; i++) {
641 kfree(dig_in_config);
642 kfree(dig_out_config);
643 kfree(chan_in_config);
644 kfree(chan_out_config);
670 for (n = 0; n < insn->
n; n++) {
673 poll_digital(
devpriv->tty, chan);
679 data[
n] =
read.value;
692 for (n = 0; n < insn->
n; n++) {
711 for (n = 0; n < insn->
n; n++) {
714 poll_channel(
devpriv->tty, chan);
720 data[
n] =
read.value;
733 for (n = 0; n < insn->
n; n++) {
740 devpriv->ao_readback[chan] = data[
n];
752 for (n = 0; n < insn->
n; n++)
753 data[n] =
devpriv->ao_readback[chan];
766 for (n = 0; n < insn->
n; n++) {
769 poll_channel(
devpriv->tty, chan);
775 data[
n] =
read.value;
791 dev->
open = serial_2002_open;
792 dev->
close = serial_2002_close;
856 for (i = 0; i < 5; i++) {
870 .driver_name =
"serial2002",
872 .attach = serial2002_attach,
873 .detach = serial2002_detach,
874 .board_name = &serial2002_boards[0].
name,