Merge branch 'v4l_for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/mchehab...
[cascardo/linux.git] / drivers / staging / dgnc / dgnc_cls.c
1 /*
2  * Copyright 2003 Digi International (www.digi.com)
3  *      Scott H Kilau <Scott_Kilau at digi dot com>
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; either version 2, or (at your option)
8  * any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY, EXPRESS OR IMPLIED; without even the
12  * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
13  * PURPOSE.  See the GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18  *
19  *
20  *      NOTE TO LINUX KERNEL HACKERS:  DO NOT REFORMAT THIS CODE!
21  *
22  *      This is shared code between Digi's CVS archive and the
23  *      Linux Kernel sources.
24  *      Changing the source just for reformatting needlessly breaks
25  *      our CVS diff history.
26  *
27  *      Send any bug fixes/changes to:  Eng.Linux at digi dot com.
28  *      Thank you.
29  *
30  */
31
32 #include <linux/kernel.h>
33 #include <linux/sched.h>        /* For jiffies, task states */
34 #include <linux/interrupt.h>    /* For tasklet and interrupt structs/defines */
35 #include <linux/delay.h>        /* For udelay */
36 #include <linux/io.h>           /* For read[bwl]/write[bwl] */
37 #include <linux/serial.h>       /* For struct async_serial */
38 #include <linux/serial_reg.h>   /* For the various UART offsets */
39 #include <linux/pci.h>
40
41 #include "dgnc_driver.h"        /* Driver main header file */
42 #include "dgnc_cls.h"
43 #include "dgnc_tty.h"
44 #include "dgnc_trace.h"
45
46 static inline void cls_parse_isr(struct dgnc_board *brd, uint port);
47 static inline void cls_clear_break(struct channel_t *ch, int force);
48 static inline void cls_set_cts_flow_control(struct channel_t *ch);
49 static inline void cls_set_rts_flow_control(struct channel_t *ch);
50 static inline void cls_set_ixon_flow_control(struct channel_t *ch);
51 static inline void cls_set_ixoff_flow_control(struct channel_t *ch);
52 static inline void cls_set_no_output_flow_control(struct channel_t *ch);
53 static inline void cls_set_no_input_flow_control(struct channel_t *ch);
54 static void cls_parse_modem(struct channel_t *ch, uchar signals);
55 static void cls_tasklet(unsigned long data);
56 static void cls_vpd(struct dgnc_board *brd);
57 static void cls_uart_init(struct channel_t *ch);
58 static void cls_uart_off(struct channel_t *ch);
59 static int cls_drain(struct tty_struct *tty, uint seconds);
60 static void cls_param(struct tty_struct *tty);
61 static void cls_assert_modem_signals(struct channel_t *ch);
62 static void cls_flush_uart_write(struct channel_t *ch);
63 static void cls_flush_uart_read(struct channel_t *ch);
64 static void cls_disable_receiver(struct channel_t *ch);
65 static void cls_enable_receiver(struct channel_t *ch);
66 static void cls_send_break(struct channel_t *ch, int msecs);
67 static void cls_send_start_character(struct channel_t *ch);
68 static void cls_send_stop_character(struct channel_t *ch);
69 static void cls_copy_data_from_uart_to_queue(struct channel_t *ch);
70 static void cls_copy_data_from_queue_to_uart(struct channel_t *ch);
71 static uint cls_get_uart_bytes_left(struct channel_t *ch);
72 static void cls_send_immediate_char(struct channel_t *ch, unsigned char);
73 static irqreturn_t cls_intr(int irq, void *voidbrd);
74
75 struct board_ops dgnc_cls_ops = {
76         .tasklet =                      cls_tasklet,
77         .intr =                         cls_intr,
78         .uart_init =                    cls_uart_init,
79         .uart_off =                     cls_uart_off,
80         .drain =                        cls_drain,
81         .param =                        cls_param,
82         .vpd =                          cls_vpd,
83         .assert_modem_signals =         cls_assert_modem_signals,
84         .flush_uart_write =             cls_flush_uart_write,
85         .flush_uart_read =              cls_flush_uart_read,
86         .disable_receiver =             cls_disable_receiver,
87         .enable_receiver =              cls_enable_receiver,
88         .send_break =                   cls_send_break,
89         .send_start_character =         cls_send_start_character,
90         .send_stop_character =          cls_send_stop_character,
91         .copy_data_from_queue_to_uart = cls_copy_data_from_queue_to_uart,
92         .get_uart_bytes_left =          cls_get_uart_bytes_left,
93         .send_immediate_char =          cls_send_immediate_char
94 };
95
96
97 static inline void cls_set_cts_flow_control(struct channel_t *ch)
98 {
99         uchar lcrb = readb(&ch->ch_cls_uart->lcr);
100         uchar ier = readb(&ch->ch_cls_uart->ier);
101         uchar isr_fcr = 0;
102
103         DPR_PARAM(("Setting CTSFLOW\n"));
104
105         /*
106          * The Enhanced Register Set may only be accessed when
107          * the Line Control Register is set to 0xBFh.
108          */
109         writeb(UART_EXAR654_ENHANCED_REGISTER_SET, &ch->ch_cls_uart->lcr);
110
111         isr_fcr = readb(&ch->ch_cls_uart->isr_fcr);
112
113         /* Turn on CTS flow control, turn off IXON flow control */
114         isr_fcr |= (UART_EXAR654_EFR_ECB | UART_EXAR654_EFR_CTSDSR);
115         isr_fcr &= ~(UART_EXAR654_EFR_IXON);
116
117         writeb(isr_fcr, &ch->ch_cls_uart->isr_fcr);
118
119         /* Write old LCR value back out, which turns enhanced access off */
120         writeb(lcrb, &ch->ch_cls_uart->lcr);
121
122         /*
123          * Enable interrupts for CTS flow, turn off interrupts for
124          * received XOFF chars
125          */
126         ier |= (UART_EXAR654_IER_CTSDSR);
127         ier &= ~(UART_EXAR654_IER_XOFF);
128         writeb(ier, &ch->ch_cls_uart->ier);
129
130         /* Set the usual FIFO values */
131         writeb((UART_FCR_ENABLE_FIFO), &ch->ch_cls_uart->isr_fcr);
132
133         writeb((UART_FCR_ENABLE_FIFO | UART_16654_FCR_RXTRIGGER_56 |
134                 UART_16654_FCR_TXTRIGGER_16 | UART_FCR_CLEAR_RCVR),
135                 &ch->ch_cls_uart->isr_fcr);
136
137         ch->ch_t_tlevel = 16;
138
139 }
140
141
142 static inline void cls_set_ixon_flow_control(struct channel_t *ch)
143 {
144         uchar lcrb = readb(&ch->ch_cls_uart->lcr);
145         uchar ier = readb(&ch->ch_cls_uart->ier);
146         uchar isr_fcr = 0;
147
148         DPR_PARAM(("Setting IXON FLOW\n"));
149
150         /*
151          * The Enhanced Register Set may only be accessed when
152          * the Line Control Register is set to 0xBFh.
153          */
154         writeb(UART_EXAR654_ENHANCED_REGISTER_SET, &ch->ch_cls_uart->lcr);
155
156         isr_fcr = readb(&ch->ch_cls_uart->isr_fcr);
157
158         /* Turn on IXON flow control, turn off CTS flow control */
159         isr_fcr |= (UART_EXAR654_EFR_ECB | UART_EXAR654_EFR_IXON);
160         isr_fcr &= ~(UART_EXAR654_EFR_CTSDSR);
161
162         writeb(isr_fcr, &ch->ch_cls_uart->isr_fcr);
163
164         /* Now set our current start/stop chars while in enhanced mode */
165         writeb(ch->ch_startc, &ch->ch_cls_uart->mcr);
166         writeb(0, &ch->ch_cls_uart->lsr);
167         writeb(ch->ch_stopc, &ch->ch_cls_uart->msr);
168         writeb(0, &ch->ch_cls_uart->spr);
169
170         /* Write old LCR value back out, which turns enhanced access off */
171         writeb(lcrb, &ch->ch_cls_uart->lcr);
172
173         /*
174          * Disable interrupts for CTS flow, turn on interrupts for
175          * received XOFF chars
176          */
177         ier &= ~(UART_EXAR654_IER_CTSDSR);
178         ier |= (UART_EXAR654_IER_XOFF);
179         writeb(ier, &ch->ch_cls_uart->ier);
180
181         /* Set the usual FIFO values */
182         writeb((UART_FCR_ENABLE_FIFO), &ch->ch_cls_uart->isr_fcr);
183
184         writeb((UART_FCR_ENABLE_FIFO | UART_16654_FCR_RXTRIGGER_16 |
185                 UART_16654_FCR_TXTRIGGER_16 | UART_FCR_CLEAR_RCVR),
186                 &ch->ch_cls_uart->isr_fcr);
187
188 }
189
190
191 static inline void cls_set_no_output_flow_control(struct channel_t *ch)
192 {
193         uchar lcrb = readb(&ch->ch_cls_uart->lcr);
194         uchar ier = readb(&ch->ch_cls_uart->ier);
195         uchar isr_fcr = 0;
196
197         DPR_PARAM(("Unsetting Output FLOW\n"));
198
199         /*
200          * The Enhanced Register Set may only be accessed when
201          * the Line Control Register is set to 0xBFh.
202          */
203         writeb(UART_EXAR654_ENHANCED_REGISTER_SET, &ch->ch_cls_uart->lcr);
204
205         isr_fcr = readb(&ch->ch_cls_uart->isr_fcr);
206
207         /* Turn off IXON flow control, turn off CTS flow control */
208         isr_fcr |= (UART_EXAR654_EFR_ECB);
209         isr_fcr &= ~(UART_EXAR654_EFR_CTSDSR | UART_EXAR654_EFR_IXON);
210
211         writeb(isr_fcr, &ch->ch_cls_uart->isr_fcr);
212
213         /* Write old LCR value back out, which turns enhanced access off */
214         writeb(lcrb, &ch->ch_cls_uart->lcr);
215
216         /*
217          * Disable interrupts for CTS flow, turn off interrupts for
218          * received XOFF chars
219          */
220         ier &= ~(UART_EXAR654_IER_CTSDSR);
221         ier &= ~(UART_EXAR654_IER_XOFF);
222         writeb(ier, &ch->ch_cls_uart->ier);
223
224         /* Set the usual FIFO values */
225         writeb((UART_FCR_ENABLE_FIFO), &ch->ch_cls_uart->isr_fcr);
226
227         writeb((UART_FCR_ENABLE_FIFO | UART_16654_FCR_RXTRIGGER_16 |
228                 UART_16654_FCR_TXTRIGGER_16 | UART_FCR_CLEAR_RCVR),
229                 &ch->ch_cls_uart->isr_fcr);
230
231         ch->ch_r_watermark = 0;
232         ch->ch_t_tlevel = 16;
233         ch->ch_r_tlevel = 16;
234
235 }
236
237
238 static inline void cls_set_rts_flow_control(struct channel_t *ch)
239 {
240         uchar lcrb = readb(&ch->ch_cls_uart->lcr);
241         uchar ier = readb(&ch->ch_cls_uart->ier);
242         uchar isr_fcr = 0;
243
244         DPR_PARAM(("Setting RTSFLOW\n"));
245
246         /*
247          * The Enhanced Register Set may only be accessed when
248          * the Line Control Register is set to 0xBFh.
249          */
250         writeb(UART_EXAR654_ENHANCED_REGISTER_SET, &ch->ch_cls_uart->lcr);
251
252         isr_fcr = readb(&ch->ch_cls_uart->isr_fcr);
253
254         /* Turn on RTS flow control, turn off IXOFF flow control */
255         isr_fcr |= (UART_EXAR654_EFR_ECB | UART_EXAR654_EFR_RTSDTR);
256         isr_fcr &= ~(UART_EXAR654_EFR_IXOFF);
257
258         writeb(isr_fcr, &ch->ch_cls_uart->isr_fcr);
259
260         /* Write old LCR value back out, which turns enhanced access off */
261         writeb(lcrb, &ch->ch_cls_uart->lcr);
262
263         /* Enable interrupts for RTS flow */
264         ier |= (UART_EXAR654_IER_RTSDTR);
265         writeb(ier, &ch->ch_cls_uart->ier);
266
267         /* Set the usual FIFO values */
268         writeb((UART_FCR_ENABLE_FIFO), &ch->ch_cls_uart->isr_fcr);
269
270         writeb((UART_FCR_ENABLE_FIFO | UART_16654_FCR_RXTRIGGER_56 |
271                 UART_16654_FCR_TXTRIGGER_16 | UART_FCR_CLEAR_RCVR),
272                 &ch->ch_cls_uart->isr_fcr);
273
274
275         ch->ch_r_watermark = 4;
276         ch->ch_r_tlevel = 8;
277
278 }
279
280
281 static inline void cls_set_ixoff_flow_control(struct channel_t *ch)
282 {
283         uchar lcrb = readb(&ch->ch_cls_uart->lcr);
284         uchar ier = readb(&ch->ch_cls_uart->ier);
285         uchar isr_fcr = 0;
286
287         DPR_PARAM(("Setting IXOFF FLOW\n"));
288
289         /*
290          * The Enhanced Register Set may only be accessed when
291          * the Line Control Register is set to 0xBFh.
292          */
293         writeb(UART_EXAR654_ENHANCED_REGISTER_SET, &ch->ch_cls_uart->lcr);
294
295         isr_fcr = readb(&ch->ch_cls_uart->isr_fcr);
296
297         /* Turn on IXOFF flow control, turn off RTS flow control */
298         isr_fcr |= (UART_EXAR654_EFR_ECB | UART_EXAR654_EFR_IXOFF);
299         isr_fcr &= ~(UART_EXAR654_EFR_RTSDTR);
300
301         writeb(isr_fcr, &ch->ch_cls_uart->isr_fcr);
302
303         /* Now set our current start/stop chars while in enhanced mode */
304         writeb(ch->ch_startc, &ch->ch_cls_uart->mcr);
305         writeb(0, &ch->ch_cls_uart->lsr);
306         writeb(ch->ch_stopc, &ch->ch_cls_uart->msr);
307         writeb(0, &ch->ch_cls_uart->spr);
308
309         /* Write old LCR value back out, which turns enhanced access off */
310         writeb(lcrb, &ch->ch_cls_uart->lcr);
311
312         /* Disable interrupts for RTS flow */
313         ier &= ~(UART_EXAR654_IER_RTSDTR);
314         writeb(ier, &ch->ch_cls_uart->ier);
315
316         /* Set the usual FIFO values */
317         writeb((UART_FCR_ENABLE_FIFO), &ch->ch_cls_uart->isr_fcr);
318
319         writeb((UART_FCR_ENABLE_FIFO | UART_16654_FCR_RXTRIGGER_16 |
320                 UART_16654_FCR_TXTRIGGER_16 | UART_FCR_CLEAR_RCVR),
321                 &ch->ch_cls_uart->isr_fcr);
322
323 }
324
325
326 static inline void cls_set_no_input_flow_control(struct channel_t *ch)
327 {
328         uchar lcrb = readb(&ch->ch_cls_uart->lcr);
329         uchar ier = readb(&ch->ch_cls_uart->ier);
330         uchar isr_fcr = 0;
331
332         DPR_PARAM(("Unsetting Input FLOW\n"));
333
334         /*
335          * The Enhanced Register Set may only be accessed when
336          * the Line Control Register is set to 0xBFh.
337          */
338         writeb(UART_EXAR654_ENHANCED_REGISTER_SET, &ch->ch_cls_uart->lcr);
339
340         isr_fcr = readb(&ch->ch_cls_uart->isr_fcr);
341
342         /* Turn off IXOFF flow control, turn off RTS flow control */
343         isr_fcr |= (UART_EXAR654_EFR_ECB);
344         isr_fcr &= ~(UART_EXAR654_EFR_RTSDTR | UART_EXAR654_EFR_IXOFF);
345
346         writeb(isr_fcr, &ch->ch_cls_uart->isr_fcr);
347
348         /* Write old LCR value back out, which turns enhanced access off */
349         writeb(lcrb, &ch->ch_cls_uart->lcr);
350
351         /* Disable interrupts for RTS flow */
352         ier &= ~(UART_EXAR654_IER_RTSDTR);
353         writeb(ier, &ch->ch_cls_uart->ier);
354
355         /* Set the usual FIFO values */
356         writeb((UART_FCR_ENABLE_FIFO), &ch->ch_cls_uart->isr_fcr);
357
358         writeb((UART_FCR_ENABLE_FIFO | UART_16654_FCR_RXTRIGGER_16 |
359                 UART_16654_FCR_TXTRIGGER_16 | UART_FCR_CLEAR_RCVR),
360                 &ch->ch_cls_uart->isr_fcr);
361
362         ch->ch_t_tlevel = 16;
363         ch->ch_r_tlevel = 16;
364
365 }
366
367
368 /*
369  * cls_clear_break.
370  * Determines whether its time to shut off break condition.
371  *
372  * No locks are assumed to be held when calling this function.
373  * channel lock is held and released in this function.
374  */
375 static inline void cls_clear_break(struct channel_t *ch, int force)
376 {
377         ulong lock_flags;
378
379         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
380                 return;
381
382         DGNC_LOCK(ch->ch_lock, lock_flags);
383
384         /* Bail if we aren't currently sending a break. */
385         if (!ch->ch_stop_sending_break) {
386                 DGNC_UNLOCK(ch->ch_lock, lock_flags);
387                 return;
388         }
389
390         /* Turn break off, and unset some variables */
391         if (ch->ch_flags & CH_BREAK_SENDING) {
392                 if (time_after(jiffies, ch->ch_stop_sending_break) || force) {
393                         uchar temp = readb(&ch->ch_cls_uart->lcr);
394                         writeb((temp & ~UART_LCR_SBC), &ch->ch_cls_uart->lcr);
395                         ch->ch_flags &= ~(CH_BREAK_SENDING);
396                         ch->ch_stop_sending_break = 0;
397                         DPR_IOCTL(("Finishing UART_LCR_SBC! finished: %lx\n",
398                                                                 jiffies));
399                 }
400         }
401         DGNC_UNLOCK(ch->ch_lock, lock_flags);
402 }
403
404
405 /* Parse the ISR register for the specific port */
406 static inline void cls_parse_isr(struct dgnc_board *brd, uint port)
407 {
408         struct channel_t *ch;
409         uchar isr = 0;
410         ulong lock_flags;
411
412         /*
413          * No need to verify board pointer, it was already
414          * verified in the interrupt routine.
415          */
416
417         if (port > brd->nasync)
418                 return;
419
420         ch = brd->channels[port];
421         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
422                 return;
423
424         /* Here we try to figure out what caused the interrupt to happen */
425         while (1) {
426
427                 isr = readb(&ch->ch_cls_uart->isr_fcr);
428
429                 /* Bail if no pending interrupt on port */
430                 if (isr & UART_IIR_NO_INT)
431                         break;
432
433                 DPR_INTR(("%s:%d port: %x isr: %x\n", __FILE__, __LINE__,
434                                                                  port, isr));
435
436                 /* Receive Interrupt pending */
437                 if (isr & (UART_IIR_RDI | UART_IIR_RDI_TIMEOUT)) {
438                         /* Read data from uart -> queue */
439                         brd->intr_rx++;
440                         ch->ch_intr_rx++;
441                         cls_copy_data_from_uart_to_queue(ch);
442                         dgnc_check_queue_flow_control(ch);
443                 }
444
445                 /* Transmit Hold register empty pending */
446                 if (isr & UART_IIR_THRI) {
447                         /* Transfer data (if any) from Write Queue -> UART. */
448                         DGNC_LOCK(ch->ch_lock, lock_flags);
449                         ch->ch_flags |= (CH_TX_FIFO_EMPTY | CH_TX_FIFO_LWM);
450                         brd->intr_tx++;
451                         ch->ch_intr_tx++;
452                         DGNC_UNLOCK(ch->ch_lock, lock_flags);
453                         cls_copy_data_from_queue_to_uart(ch);
454                 }
455
456                 /* Received Xoff signal/Special character */
457                 if (isr & UART_IIR_XOFF)
458                         /* Empty */
459
460                 /* CTS/RTS change of state */
461                 if (isr & UART_IIR_CTSRTS) {
462                         brd->intr_modem++;
463                         ch->ch_intr_modem++;
464                         /*
465                          * Don't need to do anything, the cls_parse_modem
466                          * below will grab the updated modem signals.
467                          */
468                 }
469
470                 /* Parse any modem signal changes */
471                 DPR_INTR(("MOD_STAT: sending to parse_modem_sigs\n"));
472                 cls_parse_modem(ch, readb(&ch->ch_cls_uart->msr));
473         }
474 }
475
476
477 /*
478  * cls_param()
479  * Send any/all changes to the line to the UART.
480  */
481 static void cls_param(struct tty_struct *tty)
482 {
483         uchar lcr = 0;
484         uchar uart_lcr = 0;
485         uchar ier = 0;
486         uchar uart_ier = 0;
487         uint baud = 9600;
488         int quot = 0;
489         struct dgnc_board *bd;
490         struct channel_t *ch;
491         struct un_t   *un;
492
493         if (!tty || tty->magic != TTY_MAGIC)
494                 return;
495
496         un = (struct un_t *) tty->driver_data;
497         if (!un || un->magic != DGNC_UNIT_MAGIC)
498                 return;
499
500         ch = un->un_ch;
501         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
502                 return;
503
504         bd = ch->ch_bd;
505         if (!bd || bd->magic != DGNC_BOARD_MAGIC)
506                 return;
507
508         DPR_PARAM(("param start: tdev: %x cflags: %x oflags: %x iflags: %x\n",
509                 ch->ch_tun.un_dev, ch->ch_c_cflag, ch->ch_c_oflag,
510                                                          ch->ch_c_iflag));
511
512         /*
513          * If baud rate is zero, flush queues, and set mval to drop DTR.
514          */
515         if ((ch->ch_c_cflag & (CBAUD)) == 0) {
516                 ch->ch_r_head = ch->ch_r_tail = 0;
517                 ch->ch_e_head = ch->ch_e_tail = 0;
518                 ch->ch_w_head = ch->ch_w_tail = 0;
519
520                 cls_flush_uart_write(ch);
521                 cls_flush_uart_read(ch);
522
523                 /* The baudrate is B0 so all modem lines are to be dropped. */
524                 ch->ch_flags |= (CH_BAUD0);
525                 ch->ch_mostat &= ~(UART_MCR_RTS | UART_MCR_DTR);
526                 cls_assert_modem_signals(ch);
527                 ch->ch_old_baud = 0;
528                 return;
529         } else if (ch->ch_custom_speed) {
530
531                 baud = ch->ch_custom_speed;
532                 /* Handle transition from B0 */
533                 if (ch->ch_flags & CH_BAUD0) {
534                         ch->ch_flags &= ~(CH_BAUD0);
535
536                         /*
537                          * Bring back up RTS and DTR...
538                          * Also handle RTS or DTR toggle if set.
539                          */
540                         if (!(ch->ch_digi.digi_flags & DIGI_RTS_TOGGLE))
541                                 ch->ch_mostat |= (UART_MCR_RTS);
542                         if (!(ch->ch_digi.digi_flags & DIGI_DTR_TOGGLE))
543                                 ch->ch_mostat |= (UART_MCR_DTR);
544                 }
545
546         } else {
547                 int iindex = 0;
548                 int jindex = 0;
549
550                 ulong bauds[4][16] = {
551                         { /* slowbaud */
552                                 0,      50,     75,     110,
553                                 134,    150,    200,    300,
554                                 600,    1200,   1800,   2400,
555                                 4800,   9600,   19200,  38400 },
556                         { /* slowbaud & CBAUDEX */
557                                 0,      57600,  115200, 230400,
558                                 460800, 150,    200,    921600,
559                                 600,    1200,   1800,   2400,
560                                 4800,   9600,   19200,  38400 },
561                         { /* fastbaud */
562                                 0,      57600,   76800, 115200,
563                                 131657, 153600, 230400, 460800,
564                                 921600, 1200,   1800,   2400,
565                                 4800,   9600,   19200,  38400 },
566                         { /* fastbaud & CBAUDEX */
567                                 0,      57600,  115200, 230400,
568                                 460800, 150,    200,    921600,
569                                 600,    1200,   1800,   2400,
570                                 4800,   9600,   19200,  38400 }
571                 };
572
573                 /*
574                  * Only use the TXPrint baud rate if the terminal
575                  * unit is NOT open
576                  */
577                 if (!(ch->ch_tun.un_flags & UN_ISOPEN) &&
578                                          (un->un_type == DGNC_PRINT))
579                         baud = C_BAUD(ch->ch_pun.un_tty) & 0xff;
580                 else
581                         baud = C_BAUD(ch->ch_tun.un_tty) & 0xff;
582
583                 if (ch->ch_c_cflag & CBAUDEX)
584                         iindex = 1;
585
586                 if (ch->ch_digi.digi_flags & DIGI_FAST)
587                         iindex += 2;
588
589                 jindex = baud;
590
591                 if ((iindex >= 0) && (iindex < 4) && (jindex >= 0) &&
592                                                                 (jindex < 16)) {
593                         baud = bauds[iindex][jindex];
594                 } else {
595                         DPR_IOCTL(("baud indices were out of range (%d)(%d)",
596                                 iindex, jindex));
597                         baud = 0;
598                 }
599
600                 if (baud == 0)
601                         baud = 9600;
602
603                 /* Handle transition from B0 */
604                 if (ch->ch_flags & CH_BAUD0) {
605                         ch->ch_flags &= ~(CH_BAUD0);
606
607                         /*
608                          * Bring back up RTS and DTR...
609                          * Also handle RTS or DTR toggle if set.
610                          */
611                         if (!(ch->ch_digi.digi_flags & DIGI_RTS_TOGGLE))
612                                 ch->ch_mostat |= (UART_MCR_RTS);
613                         if (!(ch->ch_digi.digi_flags & DIGI_DTR_TOGGLE))
614                                 ch->ch_mostat |= (UART_MCR_DTR);
615                 }
616         }
617
618         if (ch->ch_c_cflag & PARENB)
619                 lcr |= UART_LCR_PARITY;
620
621         if (!(ch->ch_c_cflag & PARODD))
622                 lcr |= UART_LCR_EPAR;
623
624         /*
625          * Not all platforms support mark/space parity,
626          * so this will hide behind an ifdef.
627          */
628 #ifdef CMSPAR
629         if (ch->ch_c_cflag & CMSPAR)
630                 lcr |= UART_LCR_SPAR;
631 #endif
632
633         if (ch->ch_c_cflag & CSTOPB)
634                 lcr |= UART_LCR_STOP;
635
636         switch (ch->ch_c_cflag & CSIZE) {
637         case CS5:
638                 lcr |= UART_LCR_WLEN5;
639                 break;
640         case CS6:
641                 lcr |= UART_LCR_WLEN6;
642                 break;
643         case CS7:
644                 lcr |= UART_LCR_WLEN7;
645                 break;
646         case CS8:
647         default:
648                 lcr |= UART_LCR_WLEN8;
649                 break;
650         }
651
652         ier = uart_ier = readb(&ch->ch_cls_uart->ier);
653         uart_lcr = readb(&ch->ch_cls_uart->lcr);
654
655         if (baud == 0)
656                 baud = 9600;
657
658         quot = ch->ch_bd->bd_dividend / baud;
659
660         if (quot != 0 && ch->ch_old_baud != baud) {
661                 ch->ch_old_baud = baud;
662                 writeb(UART_LCR_DLAB, &ch->ch_cls_uart->lcr);
663                 writeb((quot & 0xff), &ch->ch_cls_uart->txrx);
664                 writeb((quot >> 8), &ch->ch_cls_uart->ier);
665                 writeb(lcr, &ch->ch_cls_uart->lcr);
666         }
667
668         if (uart_lcr != lcr)
669                 writeb(lcr, &ch->ch_cls_uart->lcr);
670
671         if (ch->ch_c_cflag & CREAD)
672                 ier |= (UART_IER_RDI | UART_IER_RLSI);
673         else
674                 ier &= ~(UART_IER_RDI | UART_IER_RLSI);
675
676         /*
677          * Have the UART interrupt on modem signal changes ONLY when
678          * we are in hardware flow control mode, or CLOCAL/FORCEDCD is not set.
679          */
680         if ((ch->ch_digi.digi_flags & CTSPACE) ||
681                 (ch->ch_digi.digi_flags & RTSPACE) ||
682                 (ch->ch_c_cflag & CRTSCTS) ||
683                 !(ch->ch_digi.digi_flags & DIGI_FORCEDCD) ||
684                 !(ch->ch_c_cflag & CLOCAL))
685                         ier |= UART_IER_MSI;
686         else
687                         ier &= ~UART_IER_MSI;
688
689         ier |= UART_IER_THRI;
690
691         if (ier != uart_ier)
692                 writeb(ier, &ch->ch_cls_uart->ier);
693
694         if (ch->ch_digi.digi_flags & CTSPACE || ch->ch_c_cflag & CRTSCTS) {
695                 cls_set_cts_flow_control(ch);
696         } else if (ch->ch_c_iflag & IXON) {
697                 /*
698                  * If start/stop is set to disable, then we should
699                  * disable flow control
700                  */
701                 if ((ch->ch_startc == _POSIX_VDISABLE) ||
702                                          (ch->ch_stopc == _POSIX_VDISABLE))
703                         cls_set_no_output_flow_control(ch);
704                 else
705                         cls_set_ixon_flow_control(ch);
706         } else {
707                 cls_set_no_output_flow_control(ch);
708         }
709
710         if (ch->ch_digi.digi_flags & RTSPACE || ch->ch_c_cflag & CRTSCTS) {
711                 cls_set_rts_flow_control(ch);
712         } else if (ch->ch_c_iflag & IXOFF) {
713                 /*
714                  * If start/stop is set to disable, then we should disable
715                  * flow control
716                  */
717                 if ((ch->ch_startc == _POSIX_VDISABLE) ||
718                                 (ch->ch_stopc == _POSIX_VDISABLE))
719                         cls_set_no_input_flow_control(ch);
720                 else
721                         cls_set_ixoff_flow_control(ch);
722         } else {
723                 cls_set_no_input_flow_control(ch);
724         }
725
726         cls_assert_modem_signals(ch);
727
728         /* Get current status of the modem signals now */
729         cls_parse_modem(ch, readb(&ch->ch_cls_uart->msr));
730 }
731
732
733 /*
734  * Our board poller function.
735  */
736 static void cls_tasklet(unsigned long data)
737 {
738         struct dgnc_board *bd = (struct dgnc_board *) data;
739         struct channel_t *ch;
740         ulong  lock_flags;
741         int i;
742         int state = 0;
743         int ports = 0;
744
745         if (!bd || bd->magic != DGNC_BOARD_MAGIC) {
746                 APR(("poll_tasklet() - NULL or bad bd.\n"));
747                 return;
748         }
749
750         /* Cache a couple board values */
751         DGNC_LOCK(bd->bd_lock, lock_flags);
752         state = bd->state;
753         ports = bd->nasync;
754         DGNC_UNLOCK(bd->bd_lock, lock_flags);
755
756         /*
757          * Do NOT allow the interrupt routine to read the intr registers
758          * Until we release this lock.
759          */
760         DGNC_LOCK(bd->bd_intr_lock, lock_flags);
761
762         /*
763          * If board is ready, parse deeper to see if there is anything to do.
764          */
765         if ((state == BOARD_READY) && (ports > 0)) {
766
767                 /* Loop on each port */
768                 for (i = 0; i < ports; i++) {
769                         ch = bd->channels[i];
770                         if (!ch)
771                                 continue;
772
773                         /*
774                          * NOTE: Remember you CANNOT hold any channel
775                          * locks when calling input.
776                          * During input processing, its possible we
777                          * will call ld, which might do callbacks back
778                          * into us.
779                          */
780                         dgnc_input(ch);
781
782                         /*
783                          * Channel lock is grabbed and then released
784                          * inside this routine.
785                          */
786                         cls_copy_data_from_queue_to_uart(ch);
787                         dgnc_wakeup_writes(ch);
788
789                         /*
790                          * Check carrier function.
791                          */
792                         dgnc_carrier(ch);
793
794                         /*
795                          * The timing check of turning off the break is done
796                          * inside clear_break()
797                          */
798                         if (ch->ch_stop_sending_break)
799                                 cls_clear_break(ch, 0);
800                 }
801         }
802
803         DGNC_UNLOCK(bd->bd_intr_lock, lock_flags);
804
805 }
806
807
808 /*
809  * cls_intr()
810  *
811  * Classic specific interrupt handler.
812  */
813 static irqreturn_t cls_intr(int irq, void *voidbrd)
814 {
815         struct dgnc_board *brd = (struct dgnc_board *) voidbrd;
816         uint i = 0;
817         uchar poll_reg;
818         unsigned long lock_flags;
819
820         if (!brd) {
821                 APR(("Received interrupt (%d) with null board associated\n",
822                                                                          irq));
823                 return IRQ_NONE;
824         }
825
826         /*
827          * Check to make sure its for us.
828          */
829         if (brd->magic != DGNC_BOARD_MAGIC) {
830                 APR(("Received interrupt (%d) with a board pointer that wasn't ours!\n",
831                           irq));
832                 return IRQ_NONE;
833         }
834
835         DGNC_LOCK(brd->bd_intr_lock, lock_flags);
836
837         brd->intr_count++;
838
839         /*
840          * Check the board's global interrupt offset to see if we
841          * we actually do have an interrupt pending for us.
842          */
843         poll_reg = readb(brd->re_map_membase + UART_CLASSIC_POLL_ADDR_OFFSET);
844
845         /* If 0, no interrupts pending */
846         if (!poll_reg) {
847                 DPR_INTR((
848                          "Kernel interrupted to me, but no pending interrupts...\n"));
849                 DGNC_UNLOCK(brd->bd_intr_lock, lock_flags);
850                 return IRQ_NONE;
851         }
852
853         DPR_INTR(("%s:%d poll_reg: %x\n", __FILE__, __LINE__, poll_reg));
854
855         /* Parse each port to find out what caused the interrupt */
856         for (i = 0; i < brd->nasync; i++)
857                 cls_parse_isr(brd, i);
858
859         /*
860          * Schedule tasklet to more in-depth servicing at a better time.
861          */
862         tasklet_schedule(&brd->helper_tasklet);
863
864         DGNC_UNLOCK(brd->bd_intr_lock, lock_flags);
865
866         DPR_INTR(("dgnc_intr finish.\n"));
867         return IRQ_HANDLED;
868 }
869
870
871 static void cls_disable_receiver(struct channel_t *ch)
872 {
873         uchar tmp = readb(&ch->ch_cls_uart->ier);
874         tmp &= ~(UART_IER_RDI);
875         writeb(tmp, &ch->ch_cls_uart->ier);
876 }
877
878
879 static void cls_enable_receiver(struct channel_t *ch)
880 {
881         uchar tmp = readb(&ch->ch_cls_uart->ier);
882         tmp |= (UART_IER_RDI);
883         writeb(tmp, &ch->ch_cls_uart->ier);
884 }
885
886
887 static void cls_copy_data_from_uart_to_queue(struct channel_t *ch)
888 {
889         int qleft = 0;
890         uchar linestatus = 0;
891         uchar error_mask = 0;
892         ushort head;
893         ushort tail;
894         ulong lock_flags;
895
896         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
897                 return;
898
899         DGNC_LOCK(ch->ch_lock, lock_flags);
900
901         /* cache head and tail of queue */
902         head = ch->ch_r_head;
903         tail = ch->ch_r_tail;
904
905         /* Store how much space we have left in the queue */
906         qleft = (tail - head - 1);
907         if (qleft < 0)
908                 qleft += RQUEUEMASK + 1;
909
910         /*
911          * Create a mask to determine whether we should
912          * insert the character (if any) into our queue.
913          */
914         if (ch->ch_c_iflag & IGNBRK)
915                 error_mask |= UART_LSR_BI;
916
917         while (1) {
918                 linestatus = readb(&ch->ch_cls_uart->lsr);
919
920                 if (!(linestatus & (UART_LSR_DR)))
921                         break;
922
923                 /*
924                  * Discard character if we are ignoring the error mask.
925                 */
926                 if (linestatus & error_mask)  {
927                         uchar discard;
928                         linestatus = 0;
929                         discard = readb(&ch->ch_cls_uart->txrx);
930                         continue;
931                 }
932
933                 /*
934                  * If our queue is full, we have no choice but to drop some
935                  * data. The assumption is that HWFLOW or SWFLOW should have
936                  * stopped things way way before we got to this point.
937                  *
938                  * I decided that I wanted to ditch the oldest data first,
939                  * I hope thats okay with everyone? Yes? Good.
940                  */
941                 while (qleft < 1) {
942                         DPR_READ(("Queue full, dropping DATA:%x LSR:%x\n",
943                                 ch->ch_rqueue[tail], ch->ch_equeue[tail]));
944
945                         ch->ch_r_tail = tail = (tail + 1) & RQUEUEMASK;
946                         ch->ch_err_overrun++;
947                         qleft++;
948                 }
949
950                 ch->ch_equeue[head] = linestatus & (UART_LSR_BI | UART_LSR_PE
951                                                                  | UART_LSR_FE);
952                 ch->ch_rqueue[head] = readb(&ch->ch_cls_uart->txrx);
953                 dgnc_sniff_nowait_nolock(ch, "UART READ",
954                                                  ch->ch_rqueue + head, 1);
955
956                 qleft--;
957
958                 DPR_READ(("DATA/LSR pair: %x %x\n", ch->ch_rqueue[head],
959                                                          ch->ch_equeue[head]));
960
961                 if (ch->ch_equeue[head] & UART_LSR_PE)
962                         ch->ch_err_parity++;
963                 if (ch->ch_equeue[head] & UART_LSR_BI)
964                         ch->ch_err_break++;
965                 if (ch->ch_equeue[head] & UART_LSR_FE)
966                         ch->ch_err_frame++;
967
968                 /* Add to, and flip head if needed */
969                 head = (head + 1) & RQUEUEMASK;
970                 ch->ch_rxcount++;
971         }
972
973         /*
974          * Write new final heads to channel structure.
975          */
976         ch->ch_r_head = head & RQUEUEMASK;
977         ch->ch_e_head = head & EQUEUEMASK;
978
979         DGNC_UNLOCK(ch->ch_lock, lock_flags);
980 }
981
982
983 /*
984  * This function basically goes to sleep for secs, or until
985  * it gets signalled that the port has fully drained.
986  */
987 static int cls_drain(struct tty_struct *tty, uint seconds)
988 {
989         ulong lock_flags;
990         struct channel_t *ch;
991         struct un_t *un;
992         int rc = 0;
993
994         if (!tty || tty->magic != TTY_MAGIC)
995                 return -ENXIO;
996
997         un = (struct un_t *) tty->driver_data;
998         if (!un || un->magic != DGNC_UNIT_MAGIC)
999                 return -ENXIO;
1000
1001         ch = un->un_ch;
1002         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1003                 return -ENXIO;
1004
1005         DGNC_LOCK(ch->ch_lock, lock_flags);
1006         un->un_flags |= UN_EMPTY;
1007         DGNC_UNLOCK(ch->ch_lock, lock_flags);
1008
1009         /*
1010          * NOTE: Do something with time passed in.
1011          */
1012         rc = wait_event_interruptible(un->un_flags_wait,
1013                                          ((un->un_flags & UN_EMPTY) == 0));
1014
1015         /* If ret is non-zero, user ctrl-c'ed us */
1016         if (rc)
1017                 DPR_IOCTL(("%d Drain - User ctrl c'ed\n", __LINE__));
1018
1019         return rc;
1020 }
1021
1022
1023 /* Channel lock MUST be held before calling this function! */
1024 static void cls_flush_uart_write(struct channel_t *ch)
1025 {
1026         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1027                 return;
1028
1029         writeb((UART_FCR_ENABLE_FIFO | UART_FCR_CLEAR_XMIT),
1030                                                 &ch->ch_cls_uart->isr_fcr);
1031         udelay(10);
1032
1033         ch->ch_flags |= (CH_TX_FIFO_EMPTY | CH_TX_FIFO_LWM);
1034 }
1035
1036
1037 /* Channel lock MUST be held before calling this function! */
1038 static void cls_flush_uart_read(struct channel_t *ch)
1039 {
1040         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1041                 return;
1042
1043         /*
1044          * For complete POSIX compatibility, we should be purging the
1045          * read FIFO in the UART here.
1046          *
1047          * However, doing the statement below also incorrectly flushes
1048          * write data as well as just basically trashing the FIFO.
1049          *
1050          * I believe this is a BUG in this UART.
1051          * So for now, we will leave the code #ifdef'ed out...
1052          */
1053 #if 0
1054         writeb((UART_FCR_ENABLE_FIFO | UART_FCR_CLEAR_RCVR),
1055                                          &ch->ch_cls_uart->isr_fcr);
1056 #endif
1057         udelay(10);
1058 }
1059
1060
1061 static void cls_copy_data_from_queue_to_uart(struct channel_t *ch)
1062 {
1063         ushort head;
1064         ushort tail;
1065         int n;
1066         int qlen;
1067         uint len_written = 0;
1068         ulong lock_flags;
1069
1070         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1071                 return;
1072
1073         DGNC_LOCK(ch->ch_lock, lock_flags);
1074
1075         /* No data to write to the UART */
1076         if (ch->ch_w_tail == ch->ch_w_head) {
1077                 DGNC_UNLOCK(ch->ch_lock, lock_flags);
1078                 return;
1079         }
1080
1081         /* If port is "stopped", don't send any data to the UART */
1082         if ((ch->ch_flags & CH_FORCED_STOP) ||
1083                                  (ch->ch_flags & CH_BREAK_SENDING)) {
1084                 DGNC_UNLOCK(ch->ch_lock, lock_flags);
1085                 return;
1086         }
1087
1088         if (!(ch->ch_flags & (CH_TX_FIFO_EMPTY | CH_TX_FIFO_LWM))) {
1089                 DGNC_UNLOCK(ch->ch_lock, lock_flags);
1090                 return;
1091         }
1092
1093         n = 32;
1094
1095         /* cache head and tail of queue */
1096         head = ch->ch_w_head & WQUEUEMASK;
1097         tail = ch->ch_w_tail & WQUEUEMASK;
1098         qlen = (head - tail) & WQUEUEMASK;
1099
1100         /* Find minimum of the FIFO space, versus queue length */
1101         n = min(n, qlen);
1102
1103         while (n > 0) {
1104
1105                 /*
1106                  * If RTS Toggle mode is on, turn on RTS now if not already set,
1107                  * and make sure we get an event when the data transfer has
1108                  * completed.
1109                  */
1110                 if (ch->ch_digi.digi_flags & DIGI_RTS_TOGGLE) {
1111                         if (!(ch->ch_mostat & UART_MCR_RTS)) {
1112                                 ch->ch_mostat |= (UART_MCR_RTS);
1113                                 cls_assert_modem_signals(ch);
1114                         }
1115                         ch->ch_tun.un_flags |= (UN_EMPTY);
1116                 }
1117
1118                 /*
1119                  * If DTR Toggle mode is on, turn on DTR now if not already set,
1120                  * and make sure we get an event when the data transfer has
1121                  * completed.
1122                  */
1123                 if (ch->ch_digi.digi_flags & DIGI_DTR_TOGGLE) {
1124                         if (!(ch->ch_mostat & UART_MCR_DTR)) {
1125                                 ch->ch_mostat |= (UART_MCR_DTR);
1126                                 cls_assert_modem_signals(ch);
1127                         }
1128                         ch->ch_tun.un_flags |= (UN_EMPTY);
1129                 }
1130                 writeb(ch->ch_wqueue[ch->ch_w_tail], &ch->ch_cls_uart->txrx);
1131                 dgnc_sniff_nowait_nolock(ch, "UART WRITE",
1132                                             ch->ch_wqueue + ch->ch_w_tail, 1);
1133                 DPR_WRITE(("Tx data: %x\n", ch->ch_wqueue[ch->ch_w_tail]));
1134                 ch->ch_w_tail++;
1135                 ch->ch_w_tail &= WQUEUEMASK;
1136                 ch->ch_txcount++;
1137                 len_written++;
1138                 n--;
1139         }
1140
1141         if (len_written > 0)
1142                 ch->ch_flags &= ~(CH_TX_FIFO_EMPTY | CH_TX_FIFO_LWM);
1143
1144         DGNC_UNLOCK(ch->ch_lock, lock_flags);
1145
1146         return;
1147 }
1148
1149
1150 static void cls_parse_modem(struct channel_t *ch, uchar signals)
1151 {
1152         uchar msignals = signals;
1153         ulong lock_flags;
1154
1155         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1156                 return;
1157
1158         DPR_MSIGS(("cls_parse_modem: port: %d signals: %d\n",
1159                                          ch->ch_portnum, msignals));
1160
1161         /*
1162          * Do altpin switching. Altpin switches DCD and DSR.
1163          * This prolly breaks DSRPACE, so we should be more clever here.
1164          */
1165         DGNC_LOCK(ch->ch_lock, lock_flags);
1166         if (ch->ch_digi.digi_flags & DIGI_ALTPIN) {
1167                 uchar mswap = signals;
1168                 if (mswap & UART_MSR_DDCD) {
1169                         msignals &= ~UART_MSR_DDCD;
1170                         msignals |= UART_MSR_DDSR;
1171                 }
1172                 if (mswap & UART_MSR_DDSR) {
1173                         msignals &= ~UART_MSR_DDSR;
1174                         msignals |= UART_MSR_DDCD;
1175                 }
1176                 if (mswap & UART_MSR_DCD) {
1177                         msignals &= ~UART_MSR_DCD;
1178                         msignals |= UART_MSR_DSR;
1179                 }
1180                 if (mswap & UART_MSR_DSR) {
1181                         msignals &= ~UART_MSR_DSR;
1182                         msignals |= UART_MSR_DCD;
1183                 }
1184         }
1185         DGNC_UNLOCK(ch->ch_lock, lock_flags);
1186
1187         /*
1188          * Scrub off lower bits. They signify delta's, which I don't
1189          * care about
1190          */
1191         signals &= 0xf0;
1192
1193         DGNC_LOCK(ch->ch_lock, lock_flags);
1194         if (msignals & UART_MSR_DCD)
1195                 ch->ch_mistat |= UART_MSR_DCD;
1196         else
1197                 ch->ch_mistat &= ~UART_MSR_DCD;
1198
1199         if (msignals & UART_MSR_DSR)
1200                 ch->ch_mistat |= UART_MSR_DSR;
1201         else
1202                 ch->ch_mistat &= ~UART_MSR_DSR;
1203
1204         if (msignals & UART_MSR_RI)
1205                 ch->ch_mistat |= UART_MSR_RI;
1206         else
1207                 ch->ch_mistat &= ~UART_MSR_RI;
1208
1209         if (msignals & UART_MSR_CTS)
1210                 ch->ch_mistat |= UART_MSR_CTS;
1211         else
1212                 ch->ch_mistat &= ~UART_MSR_CTS;
1213         DGNC_UNLOCK(ch->ch_lock, lock_flags);
1214
1215
1216         DPR_MSIGS((
1217                 "Port: %d DTR: %d RTS: %d CTS: %d DSR: %d " "RI: %d CD: %d\n",
1218                 ch->ch_portnum,
1219                 !!((ch->ch_mistat | ch->ch_mostat) & UART_MCR_DTR),
1220                 !!((ch->ch_mistat | ch->ch_mostat) & UART_MCR_RTS),
1221                 !!((ch->ch_mistat | ch->ch_mostat) & UART_MSR_CTS),
1222                 !!((ch->ch_mistat | ch->ch_mostat) & UART_MSR_DSR),
1223                 !!((ch->ch_mistat | ch->ch_mostat) & UART_MSR_RI),
1224                 !!((ch->ch_mistat | ch->ch_mostat) & UART_MSR_DCD)));
1225 }
1226
1227
1228 /* Make the UART raise any of the output signals we want up */
1229 static void cls_assert_modem_signals(struct channel_t *ch)
1230 {
1231         uchar out;
1232
1233         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1234                 return;
1235
1236         out = ch->ch_mostat;
1237
1238         if (ch->ch_flags & CH_LOOPBACK)
1239                 out |= UART_MCR_LOOP;
1240
1241         writeb(out, &ch->ch_cls_uart->mcr);
1242
1243         /* Give time for the UART to actually drop the signals */
1244         udelay(10);
1245 }
1246
1247
1248 static void cls_send_start_character(struct channel_t *ch)
1249 {
1250         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1251                 return;
1252
1253         if (ch->ch_startc != _POSIX_VDISABLE) {
1254                 ch->ch_xon_sends++;
1255                 writeb(ch->ch_startc, &ch->ch_cls_uart->txrx);
1256         }
1257 }
1258
1259
1260 static void cls_send_stop_character(struct channel_t *ch)
1261 {
1262         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1263                 return;
1264
1265         if (ch->ch_stopc != _POSIX_VDISABLE) {
1266                 ch->ch_xoff_sends++;
1267                 writeb(ch->ch_stopc, &ch->ch_cls_uart->txrx);
1268         }
1269 }
1270
1271
1272 /* Inits UART */
1273 static void cls_uart_init(struct channel_t *ch)
1274 {
1275         uchar lcrb = readb(&ch->ch_cls_uart->lcr);
1276         uchar isr_fcr = 0;
1277
1278         writeb(0, &ch->ch_cls_uart->ier);
1279
1280         /*
1281          * The Enhanced Register Set may only be accessed when
1282          * the Line Control Register is set to 0xBFh.
1283          */
1284         writeb(UART_EXAR654_ENHANCED_REGISTER_SET, &ch->ch_cls_uart->lcr);
1285
1286         isr_fcr = readb(&ch->ch_cls_uart->isr_fcr);
1287
1288         /* Turn on Enhanced/Extended controls */
1289         isr_fcr |= (UART_EXAR654_EFR_ECB);
1290
1291         writeb(isr_fcr, &ch->ch_cls_uart->isr_fcr);
1292
1293         /* Write old LCR value back out, which turns enhanced access off */
1294         writeb(lcrb, &ch->ch_cls_uart->lcr);
1295
1296         /* Clear out UART and FIFO */
1297         readb(&ch->ch_cls_uart->txrx);
1298
1299         writeb((UART_FCR_ENABLE_FIFO|UART_FCR_CLEAR_RCVR|UART_FCR_CLEAR_XMIT),
1300                                                  &ch->ch_cls_uart->isr_fcr);
1301         udelay(10);
1302
1303         ch->ch_flags |= (CH_FIFO_ENABLED | CH_TX_FIFO_EMPTY | CH_TX_FIFO_LWM);
1304
1305         readb(&ch->ch_cls_uart->lsr);
1306         readb(&ch->ch_cls_uart->msr);
1307 }
1308
1309
1310 /*
1311  * Turns off UART.
1312  */
1313 static void cls_uart_off(struct channel_t *ch)
1314 {
1315         writeb(0, &ch->ch_cls_uart->ier);
1316 }
1317
1318
1319 /*
1320  * cls_get_uarts_bytes_left.
1321  * Returns 0 is nothing left in the FIFO, returns 1 otherwise.
1322  *
1323  * The channel lock MUST be held by the calling function.
1324  */
1325 static uint cls_get_uart_bytes_left(struct channel_t *ch)
1326 {
1327         uchar left = 0;
1328         uchar lsr = 0;
1329
1330         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1331                 return 0;
1332
1333         lsr = readb(&ch->ch_cls_uart->lsr);
1334
1335         /* Determine whether the Transmitter is empty or not */
1336         if (!(lsr & UART_LSR_TEMT)) {
1337                 if (ch->ch_flags & CH_TX_FIFO_EMPTY)
1338                         tasklet_schedule(&ch->ch_bd->helper_tasklet);
1339                 left = 1;
1340         } else {
1341                 ch->ch_flags |= (CH_TX_FIFO_EMPTY | CH_TX_FIFO_LWM);
1342                 left = 0;
1343         }
1344
1345         return left;
1346 }
1347
1348
1349 /*
1350  * cls_send_break.
1351  * Starts sending a break thru the UART.
1352  *
1353  * The channel lock MUST be held by the calling function.
1354  */
1355 static void cls_send_break(struct channel_t *ch, int msecs)
1356 {
1357         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1358                 return;
1359
1360         /*
1361          * If we receive a time of 0, this means turn off the break.
1362          */
1363         if (msecs == 0) {
1364                 /* Turn break off, and unset some variables */
1365                 if (ch->ch_flags & CH_BREAK_SENDING) {
1366                         uchar temp = readb(&ch->ch_cls_uart->lcr);
1367                         writeb((temp & ~UART_LCR_SBC), &ch->ch_cls_uart->lcr);
1368                         ch->ch_flags &= ~(CH_BREAK_SENDING);
1369                         ch->ch_stop_sending_break = 0;
1370                         DPR_IOCTL(("Finishing UART_LCR_SBC! finished: %lx\n",
1371                                                                      jiffies));
1372                 }
1373                 return;
1374         }
1375
1376         /*
1377          * Set the time we should stop sending the break.
1378          * If we are already sending a break, toss away the existing
1379          * time to stop, and use this new value instead.
1380          */
1381         ch->ch_stop_sending_break = jiffies + dgnc_jiffies_from_ms(msecs);
1382
1383         /* Tell the UART to start sending the break */
1384         if (!(ch->ch_flags & CH_BREAK_SENDING)) {
1385                 uchar temp = readb(&ch->ch_cls_uart->lcr);
1386                 writeb((temp | UART_LCR_SBC), &ch->ch_cls_uart->lcr);
1387                 ch->ch_flags |= (CH_BREAK_SENDING);
1388                 DPR_IOCTL((
1389                         "Port %d. Starting UART_LCR_SBC! start: %lx should end: %lx\n",
1390                         ch->ch_portnum, jiffies, ch->ch_stop_sending_break));
1391         }
1392 }
1393
1394
1395 /*
1396  * cls_send_immediate_char.
1397  * Sends a specific character as soon as possible to the UART,
1398  * jumping over any bytes that might be in the write queue.
1399  *
1400  * The channel lock MUST be held by the calling function.
1401  */
1402 static void cls_send_immediate_char(struct channel_t *ch, unsigned char c)
1403 {
1404         if (!ch || ch->magic != DGNC_CHANNEL_MAGIC)
1405                 return;
1406
1407         writeb(c, &ch->ch_cls_uart->txrx);
1408 }
1409
1410 static void cls_vpd(struct dgnc_board *brd)
1411 {
1412         ulong           vpdbase;        /* Start of io base of the card */
1413         u8 __iomem           *re_map_vpdbase;/* Remapped memory of the card */
1414         int i = 0;
1415
1416
1417         vpdbase = pci_resource_start(brd->pdev, 3);
1418
1419         /* No VPD */
1420         if (!vpdbase)
1421                 return;
1422
1423         re_map_vpdbase = ioremap(vpdbase, 0x400);
1424
1425         if (!re_map_vpdbase)
1426                 return;
1427
1428         /* Store the VPD into our buffer */
1429         for (i = 0; i < 0x40; i++) {
1430                 brd->vpd[i] = readb(re_map_vpdbase + i);
1431                 pr_info("%x ", brd->vpd[i]);
1432         }
1433         pr_info("\n");
1434
1435         if (re_map_vpdbase)
1436                 iounmap(re_map_vpdbase);
1437 }
1438