Merge branches 'x86/urgent', 'x86/amd-iommu', 'x86/apic', 'x86/cleanups', 'x86/core...
[pandora-kernel.git] / drivers / char / isicom.c
1 /*
2  *      This program is free software; you can redistribute it and/or
3  *      modify it under the terms of the GNU General Public License
4  *      as published by the Free Software Foundation; either version
5  *      2 of the License, or (at your option) any later version.
6  *
7  *      Original driver code supplied by Multi-Tech
8  *
9  *      Changes
10  *      1/9/98  alan@redhat.com         Merge to 2.0.x kernel tree
11  *                                      Obtain and use official major/minors
12  *                                      Loader switched to a misc device
13  *                                      (fixed range check bug as a side effect)
14  *                                      Printk clean up
15  *      9/12/98 alan@redhat.com         Rough port to 2.1.x
16  *
17  *      10/6/99 sameer                  Merged the ISA and PCI drivers to
18  *                                      a new unified driver.
19  *
20  *      3/9/99  sameer                  Added support for ISI4616 cards.
21  *
22  *      16/9/99 sameer                  We do not force RTS low anymore.
23  *                                      This is to prevent the firmware
24  *                                      from getting confused.
25  *
26  *      26/10/99 sameer                 Cosmetic changes:The driver now
27  *                                      dumps the Port Count information
28  *                                      along with I/O address and IRQ.
29  *
30  *      13/12/99 sameer                 Fixed the problem with IRQ sharing.
31  *
32  *      10/5/00  sameer                 Fixed isicom_shutdown_board()
33  *                                      to not lower DTR on all the ports
34  *                                      when the last port on the card is
35  *                                      closed.
36  *
37  *      10/5/00  sameer                 Signal mask setup command added
38  *                                      to  isicom_setup_port and
39  *                                      isicom_shutdown_port.
40  *
41  *      24/5/00  sameer                 The driver is now SMP aware.
42  *
43  *
44  *      27/11/00 Vinayak P Risbud       Fixed the Driver Crash Problem
45  *
46  *
47  *      03/01/01  anil .s               Added support for resetting the
48  *                                      internal modems on ISI cards.
49  *
50  *      08/02/01  anil .s               Upgraded the driver for kernel
51  *                                      2.4.x
52  *
53  *      11/04/01  Kevin                 Fixed firmware load problem with
54  *                                      ISIHP-4X card
55  *
56  *      30/04/01  anil .s               Fixed the remote login through
57  *                                      ISI port problem. Now the link
58  *                                      does not go down before password
59  *                                      prompt.
60  *
61  *      03/05/01  anil .s               Fixed the problem with IRQ sharing
62  *                                      among ISI-PCI cards.
63  *
64  *      03/05/01  anil .s               Added support to display the version
65  *                                      info during insmod as well as module
66  *                                      listing by lsmod.
67  *
68  *      10/05/01  anil .s               Done the modifications to the source
69  *                                      file and Install script so that the
70  *                                      same installation can be used for
71  *                                      2.2.x and 2.4.x kernel.
72  *
73  *      06/06/01  anil .s               Now we drop both dtr and rts during
74  *                                      shutdown_port as well as raise them
75  *                                      during isicom_config_port.
76  *
77  *      09/06/01 acme@conectiva.com.br  use capable, not suser, do
78  *                                      restore_flags on failure in
79  *                                      isicom_send_break, verify put_user
80  *                                      result
81  *
82  *      11/02/03  ranjeeth              Added support for 230 Kbps and 460 Kbps
83  *                                      Baud index extended to 21
84  *
85  *      20/03/03  ranjeeth              Made to work for Linux Advanced server.
86  *                                      Taken care of license warning.
87  *
88  *      10/12/03  Ravindra              Made to work for Fedora Core 1 of
89  *                                      Red Hat Distribution
90  *
91  *      06/01/05  Alan Cox              Merged the ISI and base kernel strands
92  *                                      into a single 2.6 driver
93  *
94  *      ***********************************************************
95  *
96  *      To use this driver you also need the support package. You
97  *      can find this in RPM format on
98  *              ftp://ftp.linux.org.uk/pub/linux/alan
99  *
100  *      You can find the original tools for this direct from Multitech
101  *              ftp://ftp.multitech.com/ISI-Cards/
102  *
103  *      Having installed the cards the module options (/etc/modprobe.conf)
104  *
105  *      options isicom   io=card1,card2,card3,card4 irq=card1,card2,card3,card4
106  *
107  *      Omit those entries for boards you don't have installed.
108  *
109  *      TODO
110  *              Merge testing
111  *              64-bit verification
112  */
113
114 #include <linux/module.h>
115 #include <linux/firmware.h>
116 #include <linux/kernel.h>
117 #include <linux/tty.h>
118 #include <linux/tty_flip.h>
119 #include <linux/termios.h>
120 #include <linux/fs.h>
121 #include <linux/sched.h>
122 #include <linux/serial.h>
123 #include <linux/mm.h>
124 #include <linux/interrupt.h>
125 #include <linux/timer.h>
126 #include <linux/delay.h>
127 #include <linux/ioport.h>
128
129 #include <linux/uaccess.h>
130 #include <linux/io.h>
131 #include <asm/system.h>
132
133 #include <linux/pci.h>
134
135 #include <linux/isicom.h>
136
137 #define InterruptTheCard(base) outw(0, (base) + 0xc)
138 #define ClearInterrupt(base) inw((base) + 0x0a)
139
140 #define pr_dbg(str...) pr_debug("ISICOM: " str)
141 #ifdef DEBUG
142 #define isicom_paranoia_check(a, b, c) __isicom_paranoia_check((a), (b), (c))
143 #else
144 #define isicom_paranoia_check(a, b, c) 0
145 #endif
146
147 static int isicom_probe(struct pci_dev *, const struct pci_device_id *);
148 static void __devexit isicom_remove(struct pci_dev *);
149
150 static struct pci_device_id isicom_pci_tbl[] = {
151         { PCI_DEVICE(VENDOR_ID, 0x2028) },
152         { PCI_DEVICE(VENDOR_ID, 0x2051) },
153         { PCI_DEVICE(VENDOR_ID, 0x2052) },
154         { PCI_DEVICE(VENDOR_ID, 0x2053) },
155         { PCI_DEVICE(VENDOR_ID, 0x2054) },
156         { PCI_DEVICE(VENDOR_ID, 0x2055) },
157         { PCI_DEVICE(VENDOR_ID, 0x2056) },
158         { PCI_DEVICE(VENDOR_ID, 0x2057) },
159         { PCI_DEVICE(VENDOR_ID, 0x2058) },
160         { 0 }
161 };
162 MODULE_DEVICE_TABLE(pci, isicom_pci_tbl);
163
164 static struct pci_driver isicom_driver = {
165         .name           = "isicom",
166         .id_table       = isicom_pci_tbl,
167         .probe          = isicom_probe,
168         .remove         = __devexit_p(isicom_remove)
169 };
170
171 static int prev_card = 3;       /*      start servicing isi_card[0]     */
172 static struct tty_driver *isicom_normal;
173
174 static void isicom_tx(unsigned long _data);
175 static void isicom_start(struct tty_struct *tty);
176
177 static DEFINE_TIMER(tx, isicom_tx, 0, 0);
178
179 /*   baud index mappings from linux defns to isi */
180
181 static signed char linuxb_to_isib[] = {
182         -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 11, 13, 15, 16, 17, 18, 19, 20, 21
183 };
184
185 struct  isi_board {
186         unsigned long           base;
187         int                     irq;
188         unsigned char           port_count;
189         unsigned short          status;
190         unsigned short          port_status; /* each bit for each port */
191         unsigned short          shift_count;
192         struct isi_port         *ports;
193         signed char             count;
194         spinlock_t              card_lock; /* Card wide lock 11/5/00 -sameer */
195         unsigned long           flags;
196         unsigned int            index;
197 };
198
199 struct  isi_port {
200         unsigned short          magic;
201         struct tty_port         port;
202         u16                     channel;
203         u16                     status;
204         struct isi_board        *card;
205         unsigned char           *xmit_buf;
206         int                     xmit_head;
207         int                     xmit_tail;
208         int                     xmit_cnt;
209 };
210
211 static struct isi_board isi_card[BOARD_COUNT];
212 static struct isi_port  isi_ports[PORT_COUNT];
213
214 /*
215  *      Locking functions for card level locking. We need to own both
216  *      the kernel lock for the card and have the card in a position that
217  *      it wants to talk.
218  */
219
220 static inline int WaitTillCardIsFree(unsigned long base)
221 {
222         unsigned int count = 0;
223         unsigned int a = in_atomic(); /* do we run under spinlock? */
224
225         while (!(inw(base + 0xe) & 0x1) && count++ < 100)
226                 if (a)
227                         mdelay(1);
228                 else
229                         msleep(1);
230
231         return !(inw(base + 0xe) & 0x1);
232 }
233
234 static int lock_card(struct isi_board *card)
235 {
236         unsigned long base = card->base;
237         unsigned int retries, a;
238
239         for (retries = 0; retries < 10; retries++) {
240                 spin_lock_irqsave(&card->card_lock, card->flags);
241                 for (a = 0; a < 10; a++) {
242                         if (inw(base + 0xe) & 0x1)
243                                 return 1;
244                         udelay(10);
245                 }
246                 spin_unlock_irqrestore(&card->card_lock, card->flags);
247                 msleep(10);
248         }
249         printk(KERN_WARNING "ISICOM: Failed to lock Card (0x%lx)\n",
250                 card->base);
251
252         return 0;       /* Failed to acquire the card! */
253 }
254
255 static void unlock_card(struct isi_board *card)
256 {
257         spin_unlock_irqrestore(&card->card_lock, card->flags);
258 }
259
260 /*
261  *  ISI Card specific ops ...
262  */
263
264 /* card->lock HAS to be held */
265 static void raise_dtr(struct isi_port *port)
266 {
267         struct isi_board *card = port->card;
268         unsigned long base = card->base;
269         u16 channel = port->channel;
270
271         if (WaitTillCardIsFree(base))
272                 return;
273
274         outw(0x8000 | (channel << card->shift_count) | 0x02, base);
275         outw(0x0504, base);
276         InterruptTheCard(base);
277         port->status |= ISI_DTR;
278 }
279
280 /* card->lock HAS to be held */
281 static inline void drop_dtr(struct isi_port *port)
282 {
283         struct isi_board *card = port->card;
284         unsigned long base = card->base;
285         u16 channel = port->channel;
286
287         if (WaitTillCardIsFree(base))
288                 return;
289
290         outw(0x8000 | (channel << card->shift_count) | 0x02, base);
291         outw(0x0404, base);
292         InterruptTheCard(base);
293         port->status &= ~ISI_DTR;
294 }
295
296 /* card->lock HAS to be held */
297 static inline void raise_rts(struct isi_port *port)
298 {
299         struct isi_board *card = port->card;
300         unsigned long base = card->base;
301         u16 channel = port->channel;
302
303         if (WaitTillCardIsFree(base))
304                 return;
305
306         outw(0x8000 | (channel << card->shift_count) | 0x02, base);
307         outw(0x0a04, base);
308         InterruptTheCard(base);
309         port->status |= ISI_RTS;
310 }
311
312 /* card->lock HAS to be held */
313 static inline void drop_rts(struct isi_port *port)
314 {
315         struct isi_board *card = port->card;
316         unsigned long base = card->base;
317         u16 channel = port->channel;
318
319         if (WaitTillCardIsFree(base))
320                 return;
321
322         outw(0x8000 | (channel << card->shift_count) | 0x02, base);
323         outw(0x0804, base);
324         InterruptTheCard(base);
325         port->status &= ~ISI_RTS;
326 }
327
328 /* card->lock MUST NOT be held */
329 static inline void raise_dtr_rts(struct isi_port *port)
330 {
331         struct isi_board *card = port->card;
332         unsigned long base = card->base;
333         u16 channel = port->channel;
334
335         if (!lock_card(card))
336                 return;
337
338         outw(0x8000 | (channel << card->shift_count) | 0x02, base);
339         outw(0x0f04, base);
340         InterruptTheCard(base);
341         port->status |= (ISI_DTR | ISI_RTS);
342         unlock_card(card);
343 }
344
345 /* card->lock HAS to be held */
346 static void drop_dtr_rts(struct isi_port *port)
347 {
348         struct isi_board *card = port->card;
349         unsigned long base = card->base;
350         u16 channel = port->channel;
351
352         if (WaitTillCardIsFree(base))
353                 return;
354
355         outw(0x8000 | (channel << card->shift_count) | 0x02, base);
356         outw(0x0c04, base);
357         InterruptTheCard(base);
358         port->status &= ~(ISI_RTS | ISI_DTR);
359 }
360
361 /*
362  *      ISICOM Driver specific routines ...
363  *
364  */
365
366 static inline int __isicom_paranoia_check(struct isi_port const *port,
367         char *name, const char *routine)
368 {
369         if (!port) {
370                 printk(KERN_WARNING "ISICOM: Warning: bad isicom magic for "
371                         "dev %s in %s.\n", name, routine);
372                 return 1;
373         }
374         if (port->magic != ISICOM_MAGIC) {
375                 printk(KERN_WARNING "ISICOM: Warning: NULL isicom port for "
376                         "dev %s in %s.\n", name, routine);
377                 return 1;
378         }
379
380         return 0;
381 }
382
383 /*
384  *      Transmitter.
385  *
386  *      We shovel data into the card buffers on a regular basis. The card
387  *      will do the rest of the work for us.
388  */
389
390 static void isicom_tx(unsigned long _data)
391 {
392         unsigned long flags, base;
393         unsigned int retries;
394         short count = (BOARD_COUNT-1), card;
395         short txcount, wrd, residue, word_count, cnt;
396         struct isi_port *port;
397         struct tty_struct *tty;
398
399         /*      find next active board  */
400         card = (prev_card + 1) & 0x0003;
401         while (count-- > 0) {
402                 if (isi_card[card].status & BOARD_ACTIVE)
403                         break;
404                 card = (card + 1) & 0x0003;
405         }
406         if (!(isi_card[card].status & BOARD_ACTIVE))
407                 goto sched_again;
408
409         prev_card = card;
410
411         count = isi_card[card].port_count;
412         port = isi_card[card].ports;
413         base = isi_card[card].base;
414
415         spin_lock_irqsave(&isi_card[card].card_lock, flags);
416         for (retries = 0; retries < 100; retries++) {
417                 if (inw(base + 0xe) & 0x1)
418                         break;
419                 udelay(2);
420         }
421         if (retries >= 100)
422                 goto unlock;
423
424         for (; count > 0; count--, port++) {
425                 /* port not active or tx disabled to force flow control */
426                 if (!(port->port.flags & ASYNC_INITIALIZED) ||
427                                 !(port->status & ISI_TXOK))
428                         continue;
429
430                 tty = port->port.tty;
431
432                 if (tty == NULL)
433                         continue;
434
435                 txcount = min_t(short, TX_SIZE, port->xmit_cnt);
436                 if (txcount <= 0 || tty->stopped || tty->hw_stopped)
437                         continue;
438
439                 if (!(inw(base + 0x02) & (1 << port->channel)))
440                         continue;
441
442                 pr_dbg("txing %d bytes, port%d.\n", txcount,
443                         port->channel + 1);
444                 outw((port->channel << isi_card[card].shift_count) | txcount,
445                         base);
446                 residue = NO;
447                 wrd = 0;
448                 while (1) {
449                         cnt = min_t(int, txcount, (SERIAL_XMIT_SIZE
450                                         - port->xmit_tail));
451                         if (residue == YES) {
452                                 residue = NO;
453                                 if (cnt > 0) {
454                                         wrd |= (port->port.xmit_buf[port->xmit_tail]
455                                                                         << 8);
456                                         port->xmit_tail = (port->xmit_tail + 1)
457                                                 & (SERIAL_XMIT_SIZE - 1);
458                                         port->xmit_cnt--;
459                                         txcount--;
460                                         cnt--;
461                                         outw(wrd, base);
462                                 } else {
463                                         outw(wrd, base);
464                                         break;
465                                 }
466                         }
467                         if (cnt <= 0)
468                                 break;
469                         word_count = cnt >> 1;
470                         outsw(base, port->port.xmit_buf+port->xmit_tail, word_count);
471                         port->xmit_tail = (port->xmit_tail
472                                 + (word_count << 1)) & (SERIAL_XMIT_SIZE - 1);
473                         txcount -= (word_count << 1);
474                         port->xmit_cnt -= (word_count << 1);
475                         if (cnt & 0x0001) {
476                                 residue = YES;
477                                 wrd = port->port.xmit_buf[port->xmit_tail];
478                                 port->xmit_tail = (port->xmit_tail + 1)
479                                         & (SERIAL_XMIT_SIZE - 1);
480                                 port->xmit_cnt--;
481                                 txcount--;
482                         }
483                 }
484
485                 InterruptTheCard(base);
486                 if (port->xmit_cnt <= 0)
487                         port->status &= ~ISI_TXOK;
488                 if (port->xmit_cnt <= WAKEUP_CHARS)
489                         tty_wakeup(tty);
490         }
491
492 unlock:
493         spin_unlock_irqrestore(&isi_card[card].card_lock, flags);
494         /*      schedule another tx for hopefully in about 10ms */
495 sched_again:
496         mod_timer(&tx, jiffies + msecs_to_jiffies(10));
497 }
498
499 /*
500  *      Main interrupt handler routine
501  */
502
503 static irqreturn_t isicom_interrupt(int irq, void *dev_id)
504 {
505         struct isi_board *card = dev_id;
506         struct isi_port *port;
507         struct tty_struct *tty;
508         unsigned long base;
509         u16 header, word_count, count, channel;
510         short byte_count;
511         unsigned char *rp;
512
513         if (!card || !(card->status & FIRMWARE_LOADED))
514                 return IRQ_NONE;
515
516         base = card->base;
517
518         /* did the card interrupt us? */
519         if (!(inw(base + 0x0e) & 0x02))
520                 return IRQ_NONE;
521
522         spin_lock(&card->card_lock);
523
524         /*
525          * disable any interrupts from the PCI card and lower the
526          * interrupt line
527          */
528         outw(0x8000, base+0x04);
529         ClearInterrupt(base);
530
531         inw(base);              /* get the dummy word out */
532         header = inw(base);
533         channel = (header & 0x7800) >> card->shift_count;
534         byte_count = header & 0xff;
535
536         if (channel + 1 > card->port_count) {
537                 printk(KERN_WARNING "ISICOM: isicom_interrupt(0x%lx): "
538                         "%d(channel) > port_count.\n", base, channel+1);
539                 outw(0x0000, base+0x04); /* enable interrupts */
540                 spin_unlock(&card->card_lock);
541                 return IRQ_HANDLED;
542         }
543         port = card->ports + channel;
544         if (!(port->port.flags & ASYNC_INITIALIZED)) {
545                 outw(0x0000, base+0x04); /* enable interrupts */
546                 spin_unlock(&card->card_lock);
547                 return IRQ_HANDLED;
548         }
549
550         tty = port->port.tty;
551         if (tty == NULL) {
552                 word_count = byte_count >> 1;
553                 while (byte_count > 1) {
554                         inw(base);
555                         byte_count -= 2;
556                 }
557                 if (byte_count & 0x01)
558                         inw(base);
559                 outw(0x0000, base+0x04); /* enable interrupts */
560                 spin_unlock(&card->card_lock);
561                 return IRQ_HANDLED;
562         }
563
564         if (header & 0x8000) {          /* Status Packet */
565                 header = inw(base);
566                 switch (header & 0xff) {
567                 case 0: /* Change in EIA signals */
568                         if (port->port.flags & ASYNC_CHECK_CD) {
569                                 if (port->status & ISI_DCD) {
570                                         if (!(header & ISI_DCD)) {
571                                         /* Carrier has been lost  */
572                                                 pr_dbg("interrupt: DCD->low.\n"
573                                                         );
574                                                 port->status &= ~ISI_DCD;
575                                                 tty_hangup(tty);
576                                         }
577                                 } else if (header & ISI_DCD) {
578                                 /* Carrier has been detected */
579                                         pr_dbg("interrupt: DCD->high.\n");
580                                         port->status |= ISI_DCD;
581                                         wake_up_interruptible(&port->port.open_wait);
582                                 }
583                         } else {
584                                 if (header & ISI_DCD)
585                                         port->status |= ISI_DCD;
586                                 else
587                                         port->status &= ~ISI_DCD;
588                         }
589
590                         if (port->port.flags & ASYNC_CTS_FLOW) {
591                                 if (port->port.tty->hw_stopped) {
592                                         if (header & ISI_CTS) {
593                                                 port->port.tty->hw_stopped = 0;
594                                                 /* start tx ing */
595                                                 port->status |= (ISI_TXOK
596                                                         | ISI_CTS);
597                                                 tty_wakeup(tty);
598                                         }
599                                 } else if (!(header & ISI_CTS)) {
600                                         port->port.tty->hw_stopped = 1;
601                                         /* stop tx ing */
602                                         port->status &= ~(ISI_TXOK | ISI_CTS);
603                                 }
604                         } else {
605                                 if (header & ISI_CTS)
606                                         port->status |= ISI_CTS;
607                                 else
608                                         port->status &= ~ISI_CTS;
609                         }
610
611                         if (header & ISI_DSR)
612                                 port->status |= ISI_DSR;
613                         else
614                                 port->status &= ~ISI_DSR;
615
616                         if (header & ISI_RI)
617                                 port->status |= ISI_RI;
618                         else
619                                 port->status &= ~ISI_RI;
620
621                         break;
622
623                 case 1: /* Received Break !!! */
624                         tty_insert_flip_char(tty, 0, TTY_BREAK);
625                         if (port->port.flags & ASYNC_SAK)
626                                 do_SAK(tty);
627                         tty_flip_buffer_push(tty);
628                         break;
629
630                 case 2: /* Statistics            */
631                         pr_dbg("isicom_interrupt: stats!!!.\n");
632                         break;
633
634                 default:
635                         pr_dbg("Intr: Unknown code in status packet.\n");
636                         break;
637                 }
638         } else {                                /* Data   Packet */
639
640                 count = tty_prepare_flip_string(tty, &rp, byte_count & ~1);
641                 pr_dbg("Intr: Can rx %d of %d bytes.\n", count, byte_count);
642                 word_count = count >> 1;
643                 insw(base, rp, word_count);
644                 byte_count -= (word_count << 1);
645                 if (count & 0x0001) {
646                         tty_insert_flip_char(tty,  inw(base) & 0xff,
647                                 TTY_NORMAL);
648                         byte_count -= 2;
649                 }
650                 if (byte_count > 0) {
651                         pr_dbg("Intr(0x%lx:%d): Flip buffer overflow! dropping "
652                                 "bytes...\n", base, channel + 1);
653                 /* drain out unread xtra data */
654                 while (byte_count > 0) {
655                                 inw(base);
656                                 byte_count -= 2;
657                         }
658                 }
659                 tty_flip_buffer_push(tty);
660         }
661         outw(0x0000, base+0x04); /* enable interrupts */
662         spin_unlock(&card->card_lock);
663
664         return IRQ_HANDLED;
665 }
666
667 static void isicom_config_port(struct isi_port *port)
668 {
669         struct isi_board *card = port->card;
670         struct tty_struct *tty;
671         unsigned long baud;
672         unsigned long base = card->base;
673         u16 channel_setup, channel = port->channel,
674                 shift_count = card->shift_count;
675         unsigned char flow_ctrl;
676
677         tty = port->port.tty;
678
679         if (tty == NULL)
680                 return;
681         /* FIXME: Switch to new tty baud API */
682         baud = C_BAUD(tty);
683         if (baud & CBAUDEX) {
684                 baud &= ~CBAUDEX;
685
686                 /*  if CBAUDEX bit is on and the baud is set to either 50 or 75
687                  *  then the card is programmed for 57.6Kbps or 115Kbps
688                  *  respectively.
689                  */
690
691                 /* 1,2,3,4 => 57.6, 115.2, 230, 460 kbps resp. */
692                 if (baud < 1 || baud > 4)
693                         port->port.tty->termios->c_cflag &= ~CBAUDEX;
694                 else
695                         baud += 15;
696         }
697         if (baud == 15) {
698
699                 /*  the ASYNC_SPD_HI and ASYNC_SPD_VHI options are set
700                  *  by the set_serial_info ioctl ... this is done by
701                  *  the 'setserial' utility.
702                  */
703
704                 if ((port->port.flags & ASYNC_SPD_MASK) == ASYNC_SPD_HI)
705                         baud++; /*  57.6 Kbps */
706                 if ((port->port.flags & ASYNC_SPD_MASK) == ASYNC_SPD_VHI)
707                         baud += 2; /*  115  Kbps */
708                 if ((port->port.flags & ASYNC_SPD_MASK) == ASYNC_SPD_SHI)
709                         baud += 3; /* 230 kbps*/
710                 if ((port->port.flags & ASYNC_SPD_MASK) == ASYNC_SPD_WARP)
711                         baud += 4; /* 460 kbps*/
712         }
713         if (linuxb_to_isib[baud] == -1) {
714                 /* hang up */
715                 drop_dtr(port);
716                 return;
717         } else
718                 raise_dtr(port);
719
720         if (WaitTillCardIsFree(base) == 0) {
721                 outw(0x8000 | (channel << shift_count) | 0x03, base);
722                 outw(linuxb_to_isib[baud] << 8 | 0x03, base);
723                 channel_setup = 0;
724                 switch (C_CSIZE(tty)) {
725                 case CS5:
726                         channel_setup |= ISICOM_CS5;
727                         break;
728                 case CS6:
729                         channel_setup |= ISICOM_CS6;
730                         break;
731                 case CS7:
732                         channel_setup |= ISICOM_CS7;
733                         break;
734                 case CS8:
735                         channel_setup |= ISICOM_CS8;
736                         break;
737                 }
738
739                 if (C_CSTOPB(tty))
740                         channel_setup |= ISICOM_2SB;
741                 if (C_PARENB(tty)) {
742                         channel_setup |= ISICOM_EVPAR;
743                         if (C_PARODD(tty))
744                                 channel_setup |= ISICOM_ODPAR;
745                 }
746                 outw(channel_setup, base);
747                 InterruptTheCard(base);
748         }
749         if (C_CLOCAL(tty))
750                 port->port.flags &= ~ASYNC_CHECK_CD;
751         else
752                 port->port.flags |= ASYNC_CHECK_CD;
753
754         /* flow control settings ...*/
755         flow_ctrl = 0;
756         port->port.flags &= ~ASYNC_CTS_FLOW;
757         if (C_CRTSCTS(tty)) {
758                 port->port.flags |= ASYNC_CTS_FLOW;
759                 flow_ctrl |= ISICOM_CTSRTS;
760         }
761         if (I_IXON(tty))
762                 flow_ctrl |= ISICOM_RESPOND_XONXOFF;
763         if (I_IXOFF(tty))
764                 flow_ctrl |= ISICOM_INITIATE_XONXOFF;
765
766         if (WaitTillCardIsFree(base) == 0) {
767                 outw(0x8000 | (channel << shift_count) | 0x04, base);
768                 outw(flow_ctrl << 8 | 0x05, base);
769                 outw((STOP_CHAR(tty)) << 8 | (START_CHAR(tty)), base);
770                 InterruptTheCard(base);
771         }
772
773         /*      rx enabled -> enable port for rx on the card    */
774         if (C_CREAD(tty)) {
775                 card->port_status |= (1 << channel);
776                 outw(card->port_status, base + 0x02);
777         }
778 }
779
780 /* open et all */
781
782 static inline void isicom_setup_board(struct isi_board *bp)
783 {
784         int channel;
785         struct isi_port *port;
786         unsigned long flags;
787
788         spin_lock_irqsave(&bp->card_lock, flags);
789         if (bp->status & BOARD_ACTIVE) {
790                 spin_unlock_irqrestore(&bp->card_lock, flags);
791                 return;
792         }
793         port = bp->ports;
794         bp->status |= BOARD_ACTIVE;
795         for (channel = 0; channel < bp->port_count; channel++, port++)
796                 drop_dtr_rts(port);
797         spin_unlock_irqrestore(&bp->card_lock, flags);
798 }
799
800 static int isicom_setup_port(struct isi_port *port)
801 {
802         struct isi_board *card = port->card;
803         unsigned long flags;
804
805         if (port->port.flags & ASYNC_INITIALIZED)
806                 return 0;
807         if (tty_port_alloc_xmit_buf(&port->port) < 0)
808                 return -ENOMEM;
809
810         spin_lock_irqsave(&card->card_lock, flags);
811         if (port->port.tty)
812                 clear_bit(TTY_IO_ERROR, &port->port.tty->flags);
813         if (port->port.count == 1)
814                 card->count++;
815
816         port->xmit_cnt = port->xmit_head = port->xmit_tail = 0;
817
818         /*      discard any residual data       */
819         if (WaitTillCardIsFree(card->base) == 0) {
820                 outw(0x8000 | (port->channel << card->shift_count) | 0x02,
821                                 card->base);
822                 outw(((ISICOM_KILLTX | ISICOM_KILLRX) << 8) | 0x06, card->base);
823                 InterruptTheCard(card->base);
824         }
825
826         isicom_config_port(port);
827         port->port.flags |= ASYNC_INITIALIZED;
828         spin_unlock_irqrestore(&card->card_lock, flags);
829
830         return 0;
831 }
832
833 static int block_til_ready(struct tty_struct *tty, struct file *filp,
834         struct isi_port *port)
835 {
836         struct isi_board *card = port->card;
837         int do_clocal = 0, retval;
838         unsigned long flags;
839         DECLARE_WAITQUEUE(wait, current);
840
841         /* block if port is in the process of being closed */
842
843         if (tty_hung_up_p(filp) || port->port.flags & ASYNC_CLOSING) {
844                 pr_dbg("block_til_ready: close in progress.\n");
845                 interruptible_sleep_on(&port->port.close_wait);
846                 if (port->port.flags & ASYNC_HUP_NOTIFY)
847                         return -EAGAIN;
848                 else
849                         return -ERESTARTSYS;
850         }
851
852         /* if non-blocking mode is set ... */
853
854         if ((filp->f_flags & O_NONBLOCK) ||
855                         (tty->flags & (1 << TTY_IO_ERROR))) {
856                 pr_dbg("block_til_ready: non-block mode.\n");
857                 port->port.flags |= ASYNC_NORMAL_ACTIVE;
858                 return 0;
859         }
860
861         if (C_CLOCAL(tty))
862                 do_clocal = 1;
863
864         /* block waiting for DCD to be asserted, and while
865                                                 callout dev is busy */
866         retval = 0;
867         add_wait_queue(&port->port.open_wait, &wait);
868
869         spin_lock_irqsave(&card->card_lock, flags);
870         if (!tty_hung_up_p(filp))
871                 port->port.count--;
872         port->port.blocked_open++;
873         spin_unlock_irqrestore(&card->card_lock, flags);
874
875         while (1) {
876                 raise_dtr_rts(port);
877
878                 set_current_state(TASK_INTERRUPTIBLE);
879                 if (tty_hung_up_p(filp) || !(port->port.flags & ASYNC_INITIALIZED)) {
880                         if (port->port.flags & ASYNC_HUP_NOTIFY)
881                                 retval = -EAGAIN;
882                         else
883                                 retval = -ERESTARTSYS;
884                         break;
885                 }
886                 if (!(port->port.flags & ASYNC_CLOSING) &&
887                                 (do_clocal || (port->status & ISI_DCD))) {
888                         break;
889                 }
890                 if (signal_pending(current)) {
891                         retval = -ERESTARTSYS;
892                         break;
893                 }
894                 schedule();
895         }
896         set_current_state(TASK_RUNNING);
897         remove_wait_queue(&port->port.open_wait, &wait);
898         spin_lock_irqsave(&card->card_lock, flags);
899         if (!tty_hung_up_p(filp))
900                 port->port.count++;
901         port->port.blocked_open--;
902         spin_unlock_irqrestore(&card->card_lock, flags);
903         if (retval)
904                 return retval;
905         port->port.flags |= ASYNC_NORMAL_ACTIVE;
906         return 0;
907 }
908
909 static int isicom_open(struct tty_struct *tty, struct file *filp)
910 {
911         struct isi_port *port;
912         struct isi_board *card;
913         unsigned int board;
914         int error, line;
915
916         line = tty->index;
917         if (line < 0 || line > PORT_COUNT-1)
918                 return -ENODEV;
919         board = BOARD(line);
920         card = &isi_card[board];
921
922         if (!(card->status & FIRMWARE_LOADED))
923                 return -ENODEV;
924
925         /*  open on a port greater than the port count for the card !!! */
926         if (line > ((board * 16) + card->port_count - 1))
927                 return -ENODEV;
928
929         port = &isi_ports[line];
930         if (isicom_paranoia_check(port, tty->name, "isicom_open"))
931                 return -ENODEV;
932
933         isicom_setup_board(card);
934
935         port->port.count++;
936         tty->driver_data = port;
937         port->port.tty = tty;
938         error = isicom_setup_port(port);
939         if (error == 0)
940                 error = block_til_ready(tty, filp, port);
941         return error;
942 }
943
944 /* close et all */
945
946 static inline void isicom_shutdown_board(struct isi_board *bp)
947 {
948         if (bp->status & BOARD_ACTIVE)
949                 bp->status &= ~BOARD_ACTIVE;
950 }
951
952 /* card->lock HAS to be held */
953 static void isicom_shutdown_port(struct isi_port *port)
954 {
955         struct isi_board *card = port->card;
956         struct tty_struct *tty;
957
958         tty = port->port.tty;
959
960         if (!(port->port.flags & ASYNC_INITIALIZED))
961                 return;
962
963         tty_port_free_xmit_buf(&port->port);
964         port->port.flags &= ~ASYNC_INITIALIZED;
965         /* 3rd October 2000 : Vinayak P Risbud */
966         port->port.tty = NULL;
967
968         /*Fix done by Anil .S on 30-04-2001
969         remote login through isi port has dtr toggle problem
970         due to which the carrier drops before the password prompt
971         appears on the remote end. Now we drop the dtr only if the
972         HUPCL(Hangup on close) flag is set for the tty*/
973
974         if (C_HUPCL(tty))
975                 /* drop dtr on this port */
976                 drop_dtr(port);
977
978         /* any other port uninits  */
979         if (tty)
980                 set_bit(TTY_IO_ERROR, &tty->flags);
981
982         if (--card->count < 0) {
983                 pr_dbg("isicom_shutdown_port: bad board(0x%lx) count %d.\n",
984                         card->base, card->count);
985                 card->count = 0;
986         }
987
988         /* last port was closed, shutdown that boad too */
989         if (C_HUPCL(tty)) {
990                 if (!card->count)
991                         isicom_shutdown_board(card);
992         }
993 }
994
995 static void isicom_flush_buffer(struct tty_struct *tty)
996 {
997         struct isi_port *port = tty->driver_data;
998         struct isi_board *card = port->card;
999         unsigned long flags;
1000
1001         if (isicom_paranoia_check(port, tty->name, "isicom_flush_buffer"))
1002                 return;
1003
1004         spin_lock_irqsave(&card->card_lock, flags);
1005         port->xmit_cnt = port->xmit_head = port->xmit_tail = 0;
1006         spin_unlock_irqrestore(&card->card_lock, flags);
1007
1008         tty_wakeup(tty);
1009 }
1010
1011 static void isicom_close(struct tty_struct *tty, struct file *filp)
1012 {
1013         struct isi_port *port = tty->driver_data;
1014         struct isi_board *card;
1015         unsigned long flags;
1016
1017         if (!port)
1018                 return;
1019         card = port->card;
1020         if (isicom_paranoia_check(port, tty->name, "isicom_close"))
1021                 return;
1022
1023         pr_dbg("Close start!!!.\n");
1024
1025         spin_lock_irqsave(&card->card_lock, flags);
1026         if (tty_hung_up_p(filp)) {
1027                 spin_unlock_irqrestore(&card->card_lock, flags);
1028                 return;
1029         }
1030
1031         if (tty->count == 1 && port->port.count != 1) {
1032                 printk(KERN_WARNING "ISICOM:(0x%lx) isicom_close: bad port "
1033                         "count tty->count = 1 port count = %d.\n",
1034                         card->base, port->port.count);
1035                 port->port.count = 1;
1036         }
1037         if (--port->port.count < 0) {
1038                 printk(KERN_WARNING "ISICOM:(0x%lx) isicom_close: bad port "
1039                         "count for channel%d = %d", card->base, port->channel,
1040                         port->port.count);
1041                 port->port.count = 0;
1042         }
1043
1044         if (port->port.count) {
1045                 spin_unlock_irqrestore(&card->card_lock, flags);
1046                 return;
1047         }
1048         port->port.flags |= ASYNC_CLOSING;
1049         tty->closing = 1;
1050         spin_unlock_irqrestore(&card->card_lock, flags);
1051
1052         if (port->port.closing_wait != ASYNC_CLOSING_WAIT_NONE)
1053                 tty_wait_until_sent(tty, port->port.closing_wait);
1054         /* indicate to the card that no more data can be received
1055            on this port */
1056         spin_lock_irqsave(&card->card_lock, flags);
1057         if (port->port.flags & ASYNC_INITIALIZED) {
1058                 card->port_status &= ~(1 << port->channel);
1059                 outw(card->port_status, card->base + 0x02);
1060         }
1061         isicom_shutdown_port(port);
1062         spin_unlock_irqrestore(&card->card_lock, flags);
1063
1064         isicom_flush_buffer(tty);
1065         tty_ldisc_flush(tty);
1066
1067         spin_lock_irqsave(&card->card_lock, flags);
1068         tty->closing = 0;
1069
1070         if (port->port.blocked_open) {
1071                 spin_unlock_irqrestore(&card->card_lock, flags);
1072                 if (port->port.close_delay) {
1073                         pr_dbg("scheduling until time out.\n");
1074                         msleep_interruptible(
1075                                 jiffies_to_msecs(port->port.close_delay));
1076                 }
1077                 spin_lock_irqsave(&card->card_lock, flags);
1078                 wake_up_interruptible(&port->port.open_wait);
1079         }
1080         port->port.flags &= ~(ASYNC_NORMAL_ACTIVE | ASYNC_CLOSING);
1081         wake_up_interruptible(&port->port.close_wait);
1082         spin_unlock_irqrestore(&card->card_lock, flags);
1083 }
1084
1085 /* write et all */
1086 static int isicom_write(struct tty_struct *tty, const unsigned char *buf,
1087         int count)
1088 {
1089         struct isi_port *port = tty->driver_data;
1090         struct isi_board *card = port->card;
1091         unsigned long flags;
1092         int cnt, total = 0;
1093
1094         if (isicom_paranoia_check(port, tty->name, "isicom_write"))
1095                 return 0;
1096
1097         spin_lock_irqsave(&card->card_lock, flags);
1098
1099         while (1) {
1100                 cnt = min_t(int, count, min(SERIAL_XMIT_SIZE - port->xmit_cnt
1101                                 - 1, SERIAL_XMIT_SIZE - port->xmit_head));
1102                 if (cnt <= 0)
1103                         break;
1104
1105                 memcpy(port->port.xmit_buf + port->xmit_head, buf, cnt);
1106                 port->xmit_head = (port->xmit_head + cnt) & (SERIAL_XMIT_SIZE
1107                         - 1);
1108                 port->xmit_cnt += cnt;
1109                 buf += cnt;
1110                 count -= cnt;
1111                 total += cnt;
1112         }
1113         if (port->xmit_cnt && !tty->stopped && !tty->hw_stopped)
1114                 port->status |= ISI_TXOK;
1115         spin_unlock_irqrestore(&card->card_lock, flags);
1116         return total;
1117 }
1118
1119 /* put_char et all */
1120 static int isicom_put_char(struct tty_struct *tty, unsigned char ch)
1121 {
1122         struct isi_port *port = tty->driver_data;
1123         struct isi_board *card = port->card;
1124         unsigned long flags;
1125
1126         if (isicom_paranoia_check(port, tty->name, "isicom_put_char"))
1127                 return 0;
1128
1129         spin_lock_irqsave(&card->card_lock, flags);
1130         if (port->xmit_cnt >= SERIAL_XMIT_SIZE - 1) {
1131                 spin_unlock_irqrestore(&card->card_lock, flags);
1132                 return 0;
1133         }
1134
1135         port->port.xmit_buf[port->xmit_head++] = ch;
1136         port->xmit_head &= (SERIAL_XMIT_SIZE - 1);
1137         port->xmit_cnt++;
1138         spin_unlock_irqrestore(&card->card_lock, flags);
1139         return 1;
1140 }
1141
1142 /* flush_chars et all */
1143 static void isicom_flush_chars(struct tty_struct *tty)
1144 {
1145         struct isi_port *port = tty->driver_data;
1146
1147         if (isicom_paranoia_check(port, tty->name, "isicom_flush_chars"))
1148                 return;
1149
1150         if (port->xmit_cnt <= 0 || tty->stopped || tty->hw_stopped ||
1151                         !port->port.xmit_buf)
1152                 return;
1153
1154         /* this tells the transmitter to consider this port for
1155            data output to the card ... that's the best we can do. */
1156         port->status |= ISI_TXOK;
1157 }
1158
1159 /* write_room et all */
1160 static int isicom_write_room(struct tty_struct *tty)
1161 {
1162         struct isi_port *port = tty->driver_data;
1163         int free;
1164
1165         if (isicom_paranoia_check(port, tty->name, "isicom_write_room"))
1166                 return 0;
1167
1168         free = SERIAL_XMIT_SIZE - port->xmit_cnt - 1;
1169         if (free < 0)
1170                 free = 0;
1171         return free;
1172 }
1173
1174 /* chars_in_buffer et all */
1175 static int isicom_chars_in_buffer(struct tty_struct *tty)
1176 {
1177         struct isi_port *port = tty->driver_data;
1178         if (isicom_paranoia_check(port, tty->name, "isicom_chars_in_buffer"))
1179                 return 0;
1180         return port->xmit_cnt;
1181 }
1182
1183 /* ioctl et all */
1184 static inline void isicom_send_break(struct isi_port *port,
1185         unsigned long length)
1186 {
1187         struct isi_board *card = port->card;
1188         unsigned long base = card->base;
1189
1190         if (!lock_card(card))
1191                 return;
1192
1193         outw(0x8000 | ((port->channel) << (card->shift_count)) | 0x3, base);
1194         outw((length & 0xff) << 8 | 0x00, base);
1195         outw((length & 0xff00), base);
1196         InterruptTheCard(base);
1197
1198         unlock_card(card);
1199 }
1200
1201 static int isicom_tiocmget(struct tty_struct *tty, struct file *file)
1202 {
1203         struct isi_port *port = tty->driver_data;
1204         /* just send the port status */
1205         u16 status = port->status;
1206
1207         if (isicom_paranoia_check(port, tty->name, "isicom_ioctl"))
1208                 return -ENODEV;
1209
1210         return  ((status & ISI_RTS) ? TIOCM_RTS : 0) |
1211                 ((status & ISI_DTR) ? TIOCM_DTR : 0) |
1212                 ((status & ISI_DCD) ? TIOCM_CAR : 0) |
1213                 ((status & ISI_DSR) ? TIOCM_DSR : 0) |
1214                 ((status & ISI_CTS) ? TIOCM_CTS : 0) |
1215                 ((status & ISI_RI ) ? TIOCM_RI  : 0);
1216 }
1217
1218 static int isicom_tiocmset(struct tty_struct *tty, struct file *file,
1219         unsigned int set, unsigned int clear)
1220 {
1221         struct isi_port *port = tty->driver_data;
1222         unsigned long flags;
1223
1224         if (isicom_paranoia_check(port, tty->name, "isicom_ioctl"))
1225                 return -ENODEV;
1226
1227         spin_lock_irqsave(&port->card->card_lock, flags);
1228         if (set & TIOCM_RTS)
1229                 raise_rts(port);
1230         if (set & TIOCM_DTR)
1231                 raise_dtr(port);
1232
1233         if (clear & TIOCM_RTS)
1234                 drop_rts(port);
1235         if (clear & TIOCM_DTR)
1236                 drop_dtr(port);
1237         spin_unlock_irqrestore(&port->card->card_lock, flags);
1238
1239         return 0;
1240 }
1241
1242 static int isicom_set_serial_info(struct isi_port *port,
1243         struct serial_struct __user *info)
1244 {
1245         struct serial_struct newinfo;
1246         int reconfig_port;
1247
1248         if (copy_from_user(&newinfo, info, sizeof(newinfo)))
1249                 return -EFAULT;
1250
1251         lock_kernel();
1252
1253         reconfig_port = ((port->port.flags & ASYNC_SPD_MASK) !=
1254                 (newinfo.flags & ASYNC_SPD_MASK));
1255
1256         if (!capable(CAP_SYS_ADMIN)) {
1257                 if ((newinfo.close_delay != port->port.close_delay) ||
1258                                 (newinfo.closing_wait != port->port.closing_wait) ||
1259                                 ((newinfo.flags & ~ASYNC_USR_MASK) !=
1260                                 (port->port.flags & ~ASYNC_USR_MASK))) {
1261                         unlock_kernel();
1262                         return -EPERM;
1263                 }
1264                 port->port.flags = ((port->port.flags & ~ASYNC_USR_MASK) |
1265                                 (newinfo.flags & ASYNC_USR_MASK));
1266         } else {
1267                 port->port.close_delay = newinfo.close_delay;
1268                 port->port.closing_wait = newinfo.closing_wait;
1269                 port->port.flags = ((port->port.flags & ~ASYNC_FLAGS) |
1270                                 (newinfo.flags & ASYNC_FLAGS));
1271         }
1272         if (reconfig_port) {
1273                 unsigned long flags;
1274                 spin_lock_irqsave(&port->card->card_lock, flags);
1275                 isicom_config_port(port);
1276                 spin_unlock_irqrestore(&port->card->card_lock, flags);
1277         }
1278         unlock_kernel();
1279         return 0;
1280 }
1281
1282 static int isicom_get_serial_info(struct isi_port *port,
1283         struct serial_struct __user *info)
1284 {
1285         struct serial_struct out_info;
1286
1287         lock_kernel();
1288         memset(&out_info, 0, sizeof(out_info));
1289 /*      out_info.type = ? */
1290         out_info.line = port - isi_ports;
1291         out_info.port = port->card->base;
1292         out_info.irq = port->card->irq;
1293         out_info.flags = port->port.flags;
1294 /*      out_info.baud_base = ? */
1295         out_info.close_delay = port->port.close_delay;
1296         out_info.closing_wait = port->port.closing_wait;
1297         unlock_kernel();
1298         if (copy_to_user(info, &out_info, sizeof(out_info)))
1299                 return -EFAULT;
1300         return 0;
1301 }
1302
1303 static int isicom_ioctl(struct tty_struct *tty, struct file *filp,
1304         unsigned int cmd, unsigned long arg)
1305 {
1306         struct isi_port *port = tty->driver_data;
1307         void __user *argp = (void __user *)arg;
1308         int retval;
1309
1310         if (isicom_paranoia_check(port, tty->name, "isicom_ioctl"))
1311                 return -ENODEV;
1312
1313         switch (cmd) {
1314         case TCSBRK:
1315                 retval = tty_check_change(tty);
1316                 if (retval)
1317                         return retval;
1318                 tty_wait_until_sent(tty, 0);
1319                 if (!arg)
1320                         isicom_send_break(port, HZ/4);
1321                 return 0;
1322
1323         case TCSBRKP:
1324                 retval = tty_check_change(tty);
1325                 if (retval)
1326                         return retval;
1327                 tty_wait_until_sent(tty, 0);
1328                 isicom_send_break(port, arg ? arg * (HZ/10) : HZ/4);
1329                 return 0;
1330         case TIOCGSERIAL:
1331                 return isicom_get_serial_info(port, argp);
1332
1333         case TIOCSSERIAL:
1334                 return isicom_set_serial_info(port, argp);
1335
1336         default:
1337                 return -ENOIOCTLCMD;
1338         }
1339         return 0;
1340 }
1341
1342 /* set_termios et all */
1343 static void isicom_set_termios(struct tty_struct *tty,
1344         struct ktermios *old_termios)
1345 {
1346         struct isi_port *port = tty->driver_data;
1347         unsigned long flags;
1348
1349         if (isicom_paranoia_check(port, tty->name, "isicom_set_termios"))
1350                 return;
1351
1352         if (tty->termios->c_cflag == old_termios->c_cflag &&
1353                         tty->termios->c_iflag == old_termios->c_iflag)
1354                 return;
1355
1356         spin_lock_irqsave(&port->card->card_lock, flags);
1357         isicom_config_port(port);
1358         spin_unlock_irqrestore(&port->card->card_lock, flags);
1359
1360         if ((old_termios->c_cflag & CRTSCTS) &&
1361                         !(tty->termios->c_cflag & CRTSCTS)) {
1362                 tty->hw_stopped = 0;
1363                 isicom_start(tty);
1364         }
1365 }
1366
1367 /* throttle et all */
1368 static void isicom_throttle(struct tty_struct *tty)
1369 {
1370         struct isi_port *port = tty->driver_data;
1371         struct isi_board *card = port->card;
1372
1373         if (isicom_paranoia_check(port, tty->name, "isicom_throttle"))
1374                 return;
1375
1376         /* tell the card that this port cannot handle any more data for now */
1377         card->port_status &= ~(1 << port->channel);
1378         outw(card->port_status, card->base + 0x02);
1379 }
1380
1381 /* unthrottle et all */
1382 static void isicom_unthrottle(struct tty_struct *tty)
1383 {
1384         struct isi_port *port = tty->driver_data;
1385         struct isi_board *card = port->card;
1386
1387         if (isicom_paranoia_check(port, tty->name, "isicom_unthrottle"))
1388                 return;
1389
1390         /* tell the card that this port is ready to accept more data */
1391         card->port_status |= (1 << port->channel);
1392         outw(card->port_status, card->base + 0x02);
1393 }
1394
1395 /* stop et all */
1396 static void isicom_stop(struct tty_struct *tty)
1397 {
1398         struct isi_port *port = tty->driver_data;
1399
1400         if (isicom_paranoia_check(port, tty->name, "isicom_stop"))
1401                 return;
1402
1403         /* this tells the transmitter not to consider this port for
1404            data output to the card. */
1405         port->status &= ~ISI_TXOK;
1406 }
1407
1408 /* start et all */
1409 static void isicom_start(struct tty_struct *tty)
1410 {
1411         struct isi_port *port = tty->driver_data;
1412
1413         if (isicom_paranoia_check(port, tty->name, "isicom_start"))
1414                 return;
1415
1416         /* this tells the transmitter to consider this port for
1417            data output to the card. */
1418         port->status |= ISI_TXOK;
1419 }
1420
1421 static void isicom_hangup(struct tty_struct *tty)
1422 {
1423         struct isi_port *port = tty->driver_data;
1424         unsigned long flags;
1425
1426         if (isicom_paranoia_check(port, tty->name, "isicom_hangup"))
1427                 return;
1428
1429         spin_lock_irqsave(&port->card->card_lock, flags);
1430         isicom_shutdown_port(port);
1431         spin_unlock_irqrestore(&port->card->card_lock, flags);
1432
1433         port->port.count = 0;
1434         port->port.flags &= ~ASYNC_NORMAL_ACTIVE;
1435         port->port.tty = NULL;
1436         wake_up_interruptible(&port->port.open_wait);
1437 }
1438
1439
1440 /*
1441  * Driver init and deinit functions
1442  */
1443
1444 static const struct tty_operations isicom_ops = {
1445         .open                   = isicom_open,
1446         .close                  = isicom_close,
1447         .write                  = isicom_write,
1448         .put_char               = isicom_put_char,
1449         .flush_chars            = isicom_flush_chars,
1450         .write_room             = isicom_write_room,
1451         .chars_in_buffer        = isicom_chars_in_buffer,
1452         .ioctl                  = isicom_ioctl,
1453         .set_termios            = isicom_set_termios,
1454         .throttle               = isicom_throttle,
1455         .unthrottle             = isicom_unthrottle,
1456         .stop                   = isicom_stop,
1457         .start                  = isicom_start,
1458         .hangup                 = isicom_hangup,
1459         .flush_buffer           = isicom_flush_buffer,
1460         .tiocmget               = isicom_tiocmget,
1461         .tiocmset               = isicom_tiocmset,
1462 };
1463
1464 static int __devinit reset_card(struct pci_dev *pdev,
1465         const unsigned int card, unsigned int *signature)
1466 {
1467         struct isi_board *board = pci_get_drvdata(pdev);
1468         unsigned long base = board->base;
1469         unsigned int sig, portcount = 0;
1470         int retval = 0;
1471
1472         dev_dbg(&pdev->dev, "ISILoad:Resetting Card%d at 0x%lx\n", card + 1,
1473                 base);
1474
1475         inw(base + 0x8);
1476
1477         msleep(10);
1478
1479         outw(0, base + 0x8); /* Reset */
1480
1481         msleep(1000);
1482
1483         sig = inw(base + 0x4) & 0xff;
1484
1485         if (sig != 0xa5 && sig != 0xbb && sig != 0xcc && sig != 0xdd &&
1486                         sig != 0xee) {
1487                 dev_warn(&pdev->dev, "ISILoad:Card%u reset failure (Possible "
1488                         "bad I/O Port Address 0x%lx).\n", card + 1, base);
1489                 dev_dbg(&pdev->dev, "Sig=0x%x\n", sig);
1490                 retval = -EIO;
1491                 goto end;
1492         }
1493
1494         msleep(10);
1495
1496         portcount = inw(base + 0x2);
1497         if (!(inw(base + 0xe) & 0x1) || (portcount != 0 && portcount != 4 &&
1498                                 portcount != 8 && portcount != 16)) {
1499                 dev_err(&pdev->dev, "ISILoad:PCI Card%d reset failure.\n",
1500                         card + 1);
1501                 retval = -EIO;
1502                 goto end;
1503         }
1504
1505         switch (sig) {
1506         case 0xa5:
1507         case 0xbb:
1508         case 0xdd:
1509                 board->port_count = (portcount == 4) ? 4 : 8;
1510                 board->shift_count = 12;
1511                 break;
1512         case 0xcc:
1513         case 0xee:
1514                 board->port_count = 16;
1515                 board->shift_count = 11;
1516                 break;
1517         }
1518         dev_info(&pdev->dev, "-Done\n");
1519         *signature = sig;
1520
1521 end:
1522         return retval;
1523 }
1524
1525 static int __devinit load_firmware(struct pci_dev *pdev,
1526         const unsigned int index, const unsigned int signature)
1527 {
1528         struct isi_board *board = pci_get_drvdata(pdev);
1529         const struct firmware *fw;
1530         unsigned long base = board->base;
1531         unsigned int a;
1532         u16 word_count, status;
1533         int retval = -EIO;
1534         char *name;
1535         u8 *data;
1536
1537         struct stframe {
1538                 u16     addr;
1539                 u16     count;
1540                 u8      data[0];
1541         } *frame;
1542
1543         switch (signature) {
1544         case 0xa5:
1545                 name = "isi608.bin";
1546                 break;
1547         case 0xbb:
1548                 name = "isi608em.bin";
1549                 break;
1550         case 0xcc:
1551                 name = "isi616em.bin";
1552                 break;
1553         case 0xdd:
1554                 name = "isi4608.bin";
1555                 break;
1556         case 0xee:
1557                 name = "isi4616.bin";
1558                 break;
1559         default:
1560                 dev_err(&pdev->dev, "Unknown signature.\n");
1561                 goto end;
1562         }
1563
1564         retval = request_firmware(&fw, name, &pdev->dev);
1565         if (retval)
1566                 goto end;
1567
1568         retval = -EIO;
1569
1570         for (frame = (struct stframe *)fw->data;
1571                         frame < (struct stframe *)(fw->data + fw->size);
1572                         frame = (struct stframe *)((u8 *)(frame + 1) +
1573                                 frame->count)) {
1574                 if (WaitTillCardIsFree(base))
1575                         goto errrelfw;
1576
1577                 outw(0xf0, base);       /* start upload sequence */
1578                 outw(0x00, base);
1579                 outw(frame->addr, base); /* lsb of address */
1580
1581                 word_count = frame->count / 2 + frame->count % 2;
1582                 outw(word_count, base);
1583                 InterruptTheCard(base);
1584
1585                 udelay(100); /* 0x2f */
1586
1587                 if (WaitTillCardIsFree(base))
1588                         goto errrelfw;
1589
1590                 status = inw(base + 0x4);
1591                 if (status != 0) {
1592                         dev_warn(&pdev->dev, "Card%d rejected load header:\n"
1593                                 KERN_WARNING "Address:0x%x\n"
1594                                 KERN_WARNING "Count:0x%x\n"
1595                                 KERN_WARNING "Status:0x%x\n",
1596                                 index + 1, frame->addr, frame->count, status);
1597                         goto errrelfw;
1598                 }
1599                 outsw(base, frame->data, word_count);
1600
1601                 InterruptTheCard(base);
1602
1603                 udelay(50); /* 0x0f */
1604
1605                 if (WaitTillCardIsFree(base))
1606                         goto errrelfw;
1607
1608                 status = inw(base + 0x4);
1609                 if (status != 0) {
1610                         dev_err(&pdev->dev, "Card%d got out of sync.Card "
1611                                 "Status:0x%x\n", index + 1, status);
1612                         goto errrelfw;
1613                 }
1614         }
1615
1616 /* XXX: should we test it by reading it back and comparing with original like
1617  * in load firmware package? */
1618         for (frame = (struct stframe *)fw->data;
1619                         frame < (struct stframe *)(fw->data + fw->size);
1620                         frame = (struct stframe *)((u8 *)(frame + 1) +
1621                                 frame->count)) {
1622                 if (WaitTillCardIsFree(base))
1623                         goto errrelfw;
1624
1625                 outw(0xf1, base); /* start download sequence */
1626                 outw(0x00, base);
1627                 outw(frame->addr, base); /* lsb of address */
1628
1629                 word_count = (frame->count >> 1) + frame->count % 2;
1630                 outw(word_count + 1, base);
1631                 InterruptTheCard(base);
1632
1633                 udelay(50); /* 0xf */
1634
1635                 if (WaitTillCardIsFree(base))
1636                         goto errrelfw;
1637
1638                 status = inw(base + 0x4);
1639                 if (status != 0) {
1640                         dev_warn(&pdev->dev, "Card%d rejected verify header:\n"
1641                                 KERN_WARNING "Address:0x%x\n"
1642                                 KERN_WARNING "Count:0x%x\n"
1643                                 KERN_WARNING "Status: 0x%x\n",
1644                                 index + 1, frame->addr, frame->count, status);
1645                         goto errrelfw;
1646                 }
1647
1648                 data = kmalloc(word_count * 2, GFP_KERNEL);
1649                 if (data == NULL) {
1650                         dev_err(&pdev->dev, "Card%d, firmware upload "
1651                                 "failed, not enough memory\n", index + 1);
1652                         goto errrelfw;
1653                 }
1654                 inw(base);
1655                 insw(base, data, word_count);
1656                 InterruptTheCard(base);
1657
1658                 for (a = 0; a < frame->count; a++)
1659                         if (data[a] != frame->data[a]) {
1660                                 kfree(data);
1661                                 dev_err(&pdev->dev, "Card%d, firmware upload "
1662                                         "failed\n", index + 1);
1663                                 goto errrelfw;
1664                         }
1665                 kfree(data);
1666
1667                 udelay(50); /* 0xf */
1668
1669                 if (WaitTillCardIsFree(base))
1670                         goto errrelfw;
1671
1672                 status = inw(base + 0x4);
1673                 if (status != 0) {
1674                         dev_err(&pdev->dev, "Card%d verify got out of sync. "
1675                                 "Card Status:0x%x\n", index + 1, status);
1676                         goto errrelfw;
1677                 }
1678         }
1679
1680         /* xfer ctrl */
1681         if (WaitTillCardIsFree(base))
1682                 goto errrelfw;
1683
1684         outw(0xf2, base);
1685         outw(0x800, base);
1686         outw(0x0, base);
1687         outw(0x0, base);
1688         InterruptTheCard(base);
1689         outw(0x0, base + 0x4); /* for ISI4608 cards */
1690
1691         board->status |= FIRMWARE_LOADED;
1692         retval = 0;
1693
1694 errrelfw:
1695         release_firmware(fw);
1696 end:
1697         return retval;
1698 }
1699
1700 /*
1701  *      Insmod can set static symbols so keep these static
1702  */
1703 static unsigned int card_count;
1704
1705 static int __devinit isicom_probe(struct pci_dev *pdev,
1706         const struct pci_device_id *ent)
1707 {
1708         unsigned int signature, index;
1709         int retval = -EPERM;
1710         struct isi_board *board = NULL;
1711
1712         if (card_count >= BOARD_COUNT)
1713                 goto err;
1714
1715         retval = pci_enable_device(pdev);
1716         if (retval) {
1717                 dev_err(&pdev->dev, "failed to enable\n");
1718                 goto err;
1719         }
1720
1721         dev_info(&pdev->dev, "ISI PCI Card(Device ID 0x%x)\n", ent->device);
1722
1723         /* allot the first empty slot in the array */
1724         for (index = 0; index < BOARD_COUNT; index++)
1725                 if (isi_card[index].base == 0) {
1726                         board = &isi_card[index];
1727                         break;
1728                 }
1729
1730         board->index = index;
1731         board->base = pci_resource_start(pdev, 3);
1732         board->irq = pdev->irq;
1733         card_count++;
1734
1735         pci_set_drvdata(pdev, board);
1736
1737         retval = pci_request_region(pdev, 3, ISICOM_NAME);
1738         if (retval) {
1739                 dev_err(&pdev->dev, "I/O Region 0x%lx-0x%lx is busy. Card%d "
1740                         "will be disabled.\n", board->base, board->base + 15,
1741                         index + 1);
1742                 retval = -EBUSY;
1743                 goto errdec;
1744         }
1745
1746         retval = request_irq(board->irq, isicom_interrupt,
1747                         IRQF_SHARED | IRQF_DISABLED, ISICOM_NAME, board);
1748         if (retval < 0) {
1749                 dev_err(&pdev->dev, "Could not install handler at Irq %d. "
1750                         "Card%d will be disabled.\n", board->irq, index + 1);
1751                 goto errunrr;
1752         }
1753
1754         retval = reset_card(pdev, index, &signature);
1755         if (retval < 0)
1756                 goto errunri;
1757
1758         retval = load_firmware(pdev, index, signature);
1759         if (retval < 0)
1760                 goto errunri;
1761
1762         for (index = 0; index < board->port_count; index++)
1763                 tty_register_device(isicom_normal, board->index * 16 + index,
1764                                 &pdev->dev);
1765
1766         return 0;
1767
1768 errunri:
1769         free_irq(board->irq, board);
1770 errunrr:
1771         pci_release_region(pdev, 3);
1772 errdec:
1773         board->base = 0;
1774         card_count--;
1775         pci_disable_device(pdev);
1776 err:
1777         return retval;
1778 }
1779
1780 static void __devexit isicom_remove(struct pci_dev *pdev)
1781 {
1782         struct isi_board *board = pci_get_drvdata(pdev);
1783         unsigned int i;
1784
1785         for (i = 0; i < board->port_count; i++)
1786                 tty_unregister_device(isicom_normal, board->index * 16 + i);
1787
1788         free_irq(board->irq, board);
1789         pci_release_region(pdev, 3);
1790         board->base = 0;
1791         card_count--;
1792         pci_disable_device(pdev);
1793 }
1794
1795 static int __init isicom_init(void)
1796 {
1797         int retval, idx, channel;
1798         struct isi_port *port;
1799
1800         for (idx = 0; idx < BOARD_COUNT; idx++) {
1801                 port = &isi_ports[idx * 16];
1802                 isi_card[idx].ports = port;
1803                 spin_lock_init(&isi_card[idx].card_lock);
1804                 for (channel = 0; channel < 16; channel++, port++) {
1805                         tty_port_init(&port->port);
1806                         port->magic = ISICOM_MAGIC;
1807                         port->card = &isi_card[idx];
1808                         port->channel = channel;
1809                         port->port.close_delay = 50 * HZ/100;
1810                         port->port.closing_wait = 3000 * HZ/100;
1811                         port->status = 0;
1812                         /*  . . .  */
1813                 }
1814                 isi_card[idx].base = 0;
1815                 isi_card[idx].irq = 0;
1816         }
1817
1818         /* tty driver structure initialization */
1819         isicom_normal = alloc_tty_driver(PORT_COUNT);
1820         if (!isicom_normal) {
1821                 retval = -ENOMEM;
1822                 goto error;
1823         }
1824
1825         isicom_normal->owner                    = THIS_MODULE;
1826         isicom_normal->name                     = "ttyM";
1827         isicom_normal->major                    = ISICOM_NMAJOR;
1828         isicom_normal->minor_start              = 0;
1829         isicom_normal->type                     = TTY_DRIVER_TYPE_SERIAL;
1830         isicom_normal->subtype                  = SERIAL_TYPE_NORMAL;
1831         isicom_normal->init_termios             = tty_std_termios;
1832         isicom_normal->init_termios.c_cflag     = B9600 | CS8 | CREAD | HUPCL |
1833                 CLOCAL;
1834         isicom_normal->flags                    = TTY_DRIVER_REAL_RAW |
1835                 TTY_DRIVER_DYNAMIC_DEV;
1836         tty_set_operations(isicom_normal, &isicom_ops);
1837
1838         retval = tty_register_driver(isicom_normal);
1839         if (retval) {
1840                 pr_dbg("Couldn't register the dialin driver\n");
1841                 goto err_puttty;
1842         }
1843
1844         retval = pci_register_driver(&isicom_driver);
1845         if (retval < 0) {
1846                 printk(KERN_ERR "ISICOM: Unable to register pci driver.\n");
1847                 goto err_unrtty;
1848         }
1849
1850         mod_timer(&tx, jiffies + 1);
1851
1852         return 0;
1853 err_unrtty:
1854         tty_unregister_driver(isicom_normal);
1855 err_puttty:
1856         put_tty_driver(isicom_normal);
1857 error:
1858         return retval;
1859 }
1860
1861 static void __exit isicom_exit(void)
1862 {
1863         del_timer_sync(&tx);
1864
1865         pci_unregister_driver(&isicom_driver);
1866         tty_unregister_driver(isicom_normal);
1867         put_tty_driver(isicom_normal);
1868 }
1869
1870 module_init(isicom_init);
1871 module_exit(isicom_exit);
1872
1873 MODULE_AUTHOR("MultiTech");
1874 MODULE_DESCRIPTION("Driver for the ISI series of cards by MultiTech");
1875 MODULE_LICENSE("GPL");