Fedora kernel-2.6.17-1.2142_FC4 patched with stable patch-2.6.17.4-vs2.0.2-rc26.diff
[linux-2.6.git] / drivers / char / serial167.c
1 /*
2  * linux/drivers/char/serial167.c
3  *
4  * Driver for MVME166/7 board serial ports, which are via a CD2401.
5  * Based very much on cyclades.c.
6  *
7  * MVME166/7 work by Richard Hirst [richard@sleepie.demon.co.uk]
8  *
9  * ==============================================================
10  *
11  * static char rcsid[] =
12  * "$Revision: 1.36.1.4 $$Date: 1995/03/29 06:14:14 $";
13  *
14  *  linux/kernel/cyclades.c
15  *
16  * Maintained by Marcio Saito (cyclades@netcom.com) and
17  * Randolph Bentson (bentson@grieg.seaslug.org)
18  *
19  * Much of the design and some of the code came from serial.c
20  * which was copyright (C) 1991, 1992  Linus Torvalds.  It was
21  * extensively rewritten by Theodore Ts'o, 8/16/92 -- 9/14/92,
22  * and then fixed as suggested by Michael K. Johnson 12/12/92.
23  *
24  * This version does not support shared irq's.
25  *
26  * $Log: cyclades.c,v $
27  * Revision 1.36.1.4  1995/03/29  06:14:14  bentson
28  * disambiguate between Cyclom-16Y and Cyclom-32Ye;
29  *
30  * Changes:
31  *
32  * 200 lines of changes record removed - RGH 11-10-95, starting work on
33  * converting this to drive serial ports on mvme166 (cd2401).
34  *
35  * Arnaldo Carvalho de Melo <acme@conectiva.com.br> - 2000/08/25
36  * - get rid of verify_area
37  * - use get_user to access memory from userspace in set_threshold,
38  *   set_default_threshold and set_timeout
39  * - don't use the panic function in serial167_init
40  * - do resource release on failure on serial167_init
41  * - include missing restore_flags in mvme167_serial_console_setup
42  *
43  * Kars de Jong <jongk@linux-m68k.org> - 2004/09/06
44  * - replace bottom half handler with task queue handler
45  */
46
47 #include <linux/config.h>
48 #include <linux/errno.h>
49 #include <linux/signal.h>
50 #include <linux/sched.h>
51 #include <linux/timer.h>
52 #include <linux/tty.h>
53 #include <linux/interrupt.h>
54 #include <linux/serial.h>
55 #include <linux/serialP.h>
56 #include <linux/string.h>
57 #include <linux/fcntl.h>
58 #include <linux/ptrace.h>
59 #include <linux/serial167.h>
60 #include <linux/delay.h>
61 #include <linux/major.h>
62 #include <linux/mm.h>
63 #include <linux/console.h>
64 #include <linux/module.h>
65 #include <linux/bitops.h>
66
67 #include <asm/system.h>
68 #include <asm/io.h>
69 #include <asm/mvme16xhw.h>
70 #include <asm/bootinfo.h>
71 #include <asm/setup.h>
72
73 #include <linux/types.h>
74 #include <linux/kernel.h>
75
76 #include <asm/uaccess.h>
77 #include <linux/init.h>
78
79 #define SERIAL_PARANOIA_CHECK
80 #undef  SERIAL_DEBUG_OPEN
81 #undef  SERIAL_DEBUG_THROTTLE
82 #undef  SERIAL_DEBUG_OTHER
83 #undef  SERIAL_DEBUG_IO
84 #undef  SERIAL_DEBUG_COUNT
85 #undef  SERIAL_DEBUG_DTR
86 #undef  CYCLOM_16Y_HACK
87 #define  CYCLOM_ENABLE_MONITORING
88
89 #define WAKEUP_CHARS 256
90
91 #define STD_COM_FLAGS (0)
92
93 #define SERIAL_TYPE_NORMAL  1
94
95 static struct tty_driver *cy_serial_driver;
96 extern int serial_console;
97 static struct cyclades_port *serial_console_info = NULL;
98 static unsigned int serial_console_cflag = 0;
99 u_char initial_console_speed;
100
101 /* Base address of cd2401 chip on mvme166/7 */
102
103 #define BASE_ADDR (0xfff45000)
104 #define pcc2chip        ((volatile u_char *)0xfff42000)
105 #define PccSCCMICR      0x1d
106 #define PccSCCTICR      0x1e
107 #define PccSCCRICR      0x1f
108 #define PccTPIACKR      0x25
109 #define PccRPIACKR      0x27
110 #define PccIMLR         0x3f
111
112 /* This is the per-port data structure */
113 struct cyclades_port cy_port[] = {
114       /* CARD#  */
115         {-1 },      /* ttyS0 */
116         {-1 },      /* ttyS1 */
117         {-1 },      /* ttyS2 */
118         {-1 },      /* ttyS3 */
119 };
120 #define NR_PORTS        ARRAY_SIZE(cy_port)
121
122 /*
123  * tmp_buf is used as a temporary buffer by serial_write.  We need to
124  * lock it in case the copy_from_user blocks while swapping in a page,
125  * and some other program tries to do a serial write at the same time.
126  * Since the lock will only come under contention when the system is
127  * swapping and available memory is low, it makes sense to share one
128  * buffer across all the serial ports, since it significantly saves
129  * memory if large numbers of serial ports are open.
130  */
131 static unsigned char *tmp_buf = 0;
132
133 /*
134  * This is used to look up the divisor speeds and the timeouts
135  * We're normally limited to 15 distinct baud rates.  The extra
136  * are accessed via settings in info->flags.
137  *         0,     1,     2,     3,     4,     5,     6,     7,     8,     9,
138  *        10,    11,    12,    13,    14,    15,    16,    17,    18,    19,
139  *                                                  HI            VHI
140  */
141 static int baud_table[] = {
142            0,    50,    75,   110,   134,   150,   200,   300,   600,  1200,
143         1800,  2400,  4800,  9600, 19200, 38400, 57600, 76800,115200,150000,
144         0};
145
146 #if 0
147 static char baud_co[] = {  /* 25 MHz clock option table */
148         /* value =>    00    01   02    03    04 */
149         /* divide by    8    32   128   512  2048 */
150         0x00,  0x04,  0x04,  0x04,  0x04,  0x04,  0x03,  0x03,  0x03,  0x02,
151         0x02,  0x02,  0x01,  0x01,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00};
152
153 static char baud_bpr[] = {  /* 25 MHz baud rate period table */
154         0x00,  0xf5,  0xa3,  0x6f,  0x5c,  0x51,  0xf5,  0xa3,  0x51,  0xa3,
155         0x6d,  0x51,  0xa3,  0x51,  0xa3,  0x51,  0x36,  0x29,  0x1b,  0x15};
156 #endif
157
158 /* I think 166 brd clocks 2401 at 20MHz.... */
159
160 /* These values are written directly to tcor, and >> 5 for writing to rcor */
161 static u_char baud_co[] = {  /* 20 MHz clock option table */
162         0x00,  0x80,  0x80,  0x80,  0x80,  0x80,  0x80,  0x60,  0x60,  0x40,
163         0x40,  0x40,  0x20,  0x20,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00};
164
165 /* These values written directly to tbpr/rbpr */
166 static u_char baud_bpr[] = {  /* 20 MHz baud rate period table */
167         0x00,  0xc0,  0x80,  0x58,  0x6c,  0x40,  0xc0,  0x81,  0x40,  0x81,
168         0x57,  0x40,  0x81,  0x40,  0x81,  0x40,  0x2b,  0x20,  0x15,  0x10};
169
170 static u_char baud_cor4[] = {  /* receive threshold */
171         0x0a,  0x0a,  0x0a,  0x0a,  0x0a,  0x0a,  0x0a,  0x0a,  0x0a,  0x0a,
172         0x0a,  0x0a,  0x0a,  0x09,  0x09,  0x08,  0x08,  0x08,  0x08,  0x07};
173
174
175
176 static void shutdown(struct cyclades_port *);
177 static int startup (struct cyclades_port *);
178 static void cy_throttle(struct tty_struct *);
179 static void cy_unthrottle(struct tty_struct *);
180 static void config_setup(struct cyclades_port *);
181 extern void console_print(const char *);
182 #ifdef CYCLOM_SHOW_STATUS
183 static void show_status(int);
184 #endif
185
186 #ifdef CONFIG_REMOTE_DEBUG
187 static void debug_setup(void);
188 void queueDebugChar (int c);
189 int getDebugChar(void);
190
191 #define DEBUG_PORT      1
192 #define DEBUG_LEN       256
193
194 typedef struct {
195         int     in;
196         int     out;
197         unsigned char   buf[DEBUG_LEN];
198 } debugq;
199
200 debugq debugiq;
201 #endif
202
203 /*
204  * I have my own version of udelay(), as it is needed when initialising
205  * the chip, before the delay loop has been calibrated.  Should probably
206  * reference one of the vmechip2 or pccchip2 counter for an accurate
207  * delay, but this wild guess will do for now.
208  */
209
210 void my_udelay (long us)
211 {
212         u_char x;
213         volatile u_char *p = &x;
214         int i;
215
216         while (us--)
217                 for (i = 100; i; i--)
218                         x |= *p;
219 }
220
221 static inline int
222 serial_paranoia_check(struct cyclades_port *info, char *name,
223                       const char *routine)
224 {
225 #ifdef SERIAL_PARANOIA_CHECK
226     static const char *badmagic =
227         "Warning: bad magic number for serial struct (%s) in %s\n";
228     static const char *badinfo =
229         "Warning: null cyclades_port for (%s) in %s\n";
230     static const char *badrange =
231         "Warning: cyclades_port out of range for (%s) in %s\n";
232
233     if (!info) {
234         printk(badinfo, name, routine);
235         return 1;
236     }
237
238     if( (long)info < (long)(&cy_port[0])
239     || (long)(&cy_port[NR_PORTS]) < (long)info ){
240         printk(badrange, name, routine);
241         return 1;
242     }
243
244     if (info->magic != CYCLADES_MAGIC) {
245         printk(badmagic, name, routine);
246         return 1;
247     }
248 #endif
249         return 0;
250 } /* serial_paranoia_check */
251
252 #if 0
253 /* The following diagnostic routines allow the driver to spew
254    information on the screen, even (especially!) during interrupts.
255  */
256 void
257 SP(char *data){
258   unsigned long flags;
259     local_irq_save(flags);
260         console_print(data);
261     local_irq_restore(flags);
262 }
263 char scrn[2];
264 void
265 CP(char data){
266   unsigned long flags;
267     local_irq_save(flags);
268         scrn[0] = data;
269         console_print(scrn);
270     local_irq_restore(flags);
271 }/* CP */
272
273 void CP1(int data) { (data<10)?  CP(data+'0'): CP(data+'A'-10); }/* CP1 */
274 void CP2(int data) { CP1((data>>4) & 0x0f); CP1( data & 0x0f); }/* CP2 */
275 void CP4(int data) { CP2((data>>8) & 0xff); CP2(data & 0xff); }/* CP4 */
276 void CP8(long data) { CP4((data>>16) & 0xffff); CP4(data & 0xffff); }/* CP8 */
277 #endif
278
279 /* This routine waits up to 1000 micro-seconds for the previous
280    command to the Cirrus chip to complete and then issues the
281    new command.  An error is returned if the previous command
282    didn't finish within the time limit.
283  */
284 u_short
285 write_cy_cmd(volatile u_char *base_addr, u_char cmd)
286 {
287   unsigned long flags;
288   volatile int  i;
289
290     local_irq_save(flags);
291         /* Check to see that the previous command has completed */
292         for(i = 0 ; i < 100 ; i++){
293             if (base_addr[CyCCR] == 0){
294                 break;
295             }
296             my_udelay(10L);
297         }
298         /* if the CCR never cleared, the previous command
299             didn't finish within the "reasonable time" */
300         if ( i == 10 ) {
301             local_irq_restore(flags);
302             return (-1);
303         }
304
305         /* Issue the new command */
306         base_addr[CyCCR] = cmd;
307     local_irq_restore(flags);
308     return(0);
309 } /* write_cy_cmd */
310
311
312 /* cy_start and cy_stop provide software output flow control as a
313    function of XON/XOFF, software CTS, and other such stuff. */
314
315 static void
316 cy_stop(struct tty_struct *tty)
317 {
318   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
319   volatile unsigned char *base_addr = (unsigned char *)BASE_ADDR;
320   int channel;
321   unsigned long flags;
322
323 #ifdef SERIAL_DEBUG_OTHER
324     printk("cy_stop %s\n", tty->name); /* */
325 #endif
326
327     if (serial_paranoia_check(info, tty->name, "cy_stop"))
328         return;
329         
330     channel = info->line;
331
332     local_irq_save(flags);
333         base_addr[CyCAR] = (u_char)(channel); /* index channel */
334         base_addr[CyIER] &= ~(CyTxMpty|CyTxRdy);
335     local_irq_restore(flags);
336
337     return;
338 } /* cy_stop */
339
340 static void
341 cy_start(struct tty_struct *tty)
342 {
343   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
344   volatile unsigned char *base_addr = (unsigned char *)BASE_ADDR;
345   int channel;
346   unsigned long flags;
347
348 #ifdef SERIAL_DEBUG_OTHER
349     printk("cy_start %s\n", tty->name); /* */
350 #endif
351
352     if (serial_paranoia_check(info, tty->name, "cy_start"))
353         return;
354         
355     channel = info->line;
356
357     local_irq_save(flags);
358         base_addr[CyCAR] = (u_char)(channel);
359         base_addr[CyIER] |= CyTxMpty;
360     local_irq_restore(flags);
361
362     return;
363 } /* cy_start */
364
365
366 /*
367  * This routine is used by the interrupt handler to schedule
368  * processing in the software interrupt portion of the driver
369  * (also known as the "bottom half").  This can be called any
370  * number of times for any channel without harm.
371  */
372 static inline void
373 cy_sched_event(struct cyclades_port *info, int event)
374 {
375     info->event |= 1 << event; /* remember what kind of event and who */
376     schedule_work(&info->tqueue);
377 } /* cy_sched_event */
378
379
380 /* The real interrupt service routines are called
381    whenever the card wants its hand held--chars
382    received, out buffer empty, modem change, etc.
383  */
384 static irqreturn_t
385 cd2401_rxerr_interrupt(int irq, void *dev_id, struct pt_regs *fp)
386 {
387     struct tty_struct *tty;
388     struct cyclades_port *info;
389     volatile unsigned char *base_addr = (unsigned char *)BASE_ADDR;
390     unsigned char err, rfoc;
391     int channel;
392     char data;
393
394     /* determine the channel and change to that context */
395     channel = (u_short ) (base_addr[CyLICR] >> 2);
396     info = &cy_port[channel];
397     info->last_active = jiffies;
398
399     if ((err = base_addr[CyRISR]) & CyTIMEOUT) {
400         /* This is a receive timeout interrupt, ignore it */
401         base_addr[CyREOIR] = CyNOTRANS;
402         return IRQ_HANDLED;
403     }
404
405     /* Read a byte of data if there is any - assume the error
406      * is associated with this character */
407
408     if ((rfoc = base_addr[CyRFOC]) != 0)
409         data = base_addr[CyRDR];
410     else
411         data = 0;
412
413     /* if there is nowhere to put the data, discard it */
414     if(info->tty == 0) {
415         base_addr[CyREOIR] = rfoc ? 0 : CyNOTRANS;
416         return IRQ_HANDLED;
417     }
418     else { /* there is an open port for this data */
419         tty = info->tty;
420         if(err & info->ignore_status_mask){
421             base_addr[CyREOIR] = rfoc ? 0 : CyNOTRANS;
422             return IRQ_HANDLED;
423         }
424         if (tty_buffer_request_room(tty, 1) != 0){
425             if (err & info->read_status_mask){
426                 if(err & CyBREAK){
427                     tty_insert_flip_char(tty, data, TTY_BREAK);
428                     if (info->flags & ASYNC_SAK){
429                         do_SAK(tty);
430                     }
431                 }else if(err & CyFRAME){
432                     tty_insert_flip_char(tty, data, TTY_FRAME);
433                 }else if(err & CyPARITY){
434                     tty_insert_flip_char(tty, data, TTY_PARITY);
435                 }else if(err & CyOVERRUN){
436                     tty_insert_flip_char(tty, 0, TTY_OVERRUN);
437                     /*
438                        If the flip buffer itself is
439                        overflowing, we still loose
440                        the next incoming character.
441                      */
442                     tty_insert_flip_char(tty, data, TTY_NORMAL);
443                 }
444                 /* These two conditions may imply */
445                 /* a normal read should be done. */
446                 /* else if(data & CyTIMEOUT) */
447                 /* else if(data & CySPECHAR) */
448                 }else{
449                     tty_insert_flip_char(tty, 0, TTY_NORMAL);
450                 }
451             }else{
452                     tty_insert_flip_char(tty, data, TTY_NORMAL);
453             }
454         }else{
455             /* there was a software buffer overrun
456                and nothing could be done about it!!! */
457         }
458     }
459     schedule_delayed_work(&tty->flip.work, 1);
460     /* end of service */
461     base_addr[CyREOIR] = rfoc ? 0 : CyNOTRANS;
462     return IRQ_HANDLED;
463 } /* cy_rxerr_interrupt */
464
465 static irqreturn_t
466 cd2401_modem_interrupt(int irq, void *dev_id, struct pt_regs *fp)
467 {
468     struct cyclades_port *info;
469     volatile unsigned char *base_addr = (unsigned char *)BASE_ADDR;
470     int channel;
471     int mdm_change;
472     int mdm_status;
473
474
475     /* determine the channel and change to that context */
476     channel = (u_short ) (base_addr[CyLICR] >> 2);
477     info = &cy_port[channel];
478     info->last_active = jiffies;
479
480     mdm_change = base_addr[CyMISR];
481     mdm_status = base_addr[CyMSVR1];
482
483     if(info->tty == 0){ /* nowhere to put the data, ignore it */
484         ;
485     }else{
486         if((mdm_change & CyDCD)
487         && (info->flags & ASYNC_CHECK_CD)){
488             if(mdm_status & CyDCD){
489 /* CP('!'); */
490                 cy_sched_event(info, Cy_EVENT_OPEN_WAKEUP);
491             } else {
492 /* CP('@'); */
493                 cy_sched_event(info, Cy_EVENT_HANGUP);
494             }
495         }
496         if((mdm_change & CyCTS)
497         && (info->flags & ASYNC_CTS_FLOW)){
498             if(info->tty->stopped){
499                 if(mdm_status & CyCTS){
500                     /* !!! cy_start isn't used because... */
501                     info->tty->stopped = 0;
502                     base_addr[CyIER] |= CyTxMpty;
503                     cy_sched_event(info, Cy_EVENT_WRITE_WAKEUP);
504                 }
505             }else{
506                 if(!(mdm_status & CyCTS)){
507                     /* !!! cy_stop isn't used because... */
508                     info->tty->stopped = 1;
509                     base_addr[CyIER] &= ~(CyTxMpty|CyTxRdy);
510                 }
511             }
512         }
513         if(mdm_status & CyDSR){
514         }
515     }
516     base_addr[CyMEOIR] = 0;
517     return IRQ_HANDLED;
518 } /* cy_modem_interrupt */
519
520 static irqreturn_t
521 cd2401_tx_interrupt(int irq, void *dev_id, struct pt_regs *fp)
522 {
523     struct cyclades_port *info;
524     volatile unsigned char *base_addr = (unsigned char *)BASE_ADDR;
525     int channel;
526     int char_count, saved_cnt;
527     int outch;
528
529     /* determine the channel and change to that context */
530     channel = (u_short ) (base_addr[CyLICR] >> 2);
531
532 #ifdef CONFIG_REMOTE_DEBUG
533     if (channel == DEBUG_PORT) {
534         panic ("TxInt on debug port!!!");
535     }
536 #endif
537
538     info = &cy_port[channel];
539
540     /* validate the port number (as configured and open) */
541     if( (channel < 0) || (NR_PORTS <= channel) ){
542         base_addr[CyIER] &= ~(CyTxMpty|CyTxRdy);
543         base_addr[CyTEOIR] = CyNOTRANS;
544         return IRQ_HANDLED;
545     }
546     info->last_active = jiffies;
547     if(info->tty == 0){
548         base_addr[CyIER] &= ~(CyTxMpty|CyTxRdy);
549         if (info->xmit_cnt < WAKEUP_CHARS) {
550             cy_sched_event(info, Cy_EVENT_WRITE_WAKEUP);
551         }
552         base_addr[CyTEOIR] = CyNOTRANS;
553         return IRQ_HANDLED;
554     }
555
556     /* load the on-chip space available for outbound data */
557     saved_cnt = char_count = base_addr[CyTFTC];
558
559     if(info->x_char) { /* send special char */
560         outch = info->x_char;
561         base_addr[CyTDR] = outch;
562         char_count--;
563         info->x_char = 0;
564     }
565
566     if (info->x_break){
567         /*  The Cirrus chip requires the "Embedded Transmit
568             Commands" of start break, delay, and end break
569             sequences to be sent.  The duration of the
570             break is given in TICs, which runs at HZ
571             (typically 100) and the PPR runs at 200 Hz,
572             so the delay is duration * 200/HZ, and thus a
573             break can run from 1/100 sec to about 5/4 sec.
574             Need to check these values - RGH 141095.
575          */
576         base_addr[CyTDR] = 0; /* start break */
577         base_addr[CyTDR] = 0x81;
578         base_addr[CyTDR] = 0; /* delay a bit */
579         base_addr[CyTDR] = 0x82;
580         base_addr[CyTDR] = info->x_break*200/HZ;
581         base_addr[CyTDR] = 0; /* terminate break */
582         base_addr[CyTDR] = 0x83;
583         char_count -= 7;
584         info->x_break = 0;
585     }
586
587     while (char_count > 0){
588         if (!info->xmit_cnt){
589             base_addr[CyIER] &= ~(CyTxMpty|CyTxRdy);
590             break;
591         }
592         if (info->xmit_buf == 0){
593             base_addr[CyIER] &= ~(CyTxMpty|CyTxRdy);
594             break;
595         }
596         if (info->tty->stopped || info->tty->hw_stopped){
597             base_addr[CyIER] &= ~(CyTxMpty|CyTxRdy);
598             break;
599         }
600         /* Because the Embedded Transmit Commands have been
601            enabled, we must check to see if the escape
602            character, NULL, is being sent.  If it is, we
603            must ensure that there is room for it to be
604            doubled in the output stream.  Therefore we
605            no longer advance the pointer when the character
606            is fetched, but rather wait until after the check
607            for a NULL output character. (This is necessary
608            because there may not be room for the two chars
609            needed to send a NULL.
610          */
611         outch = info->xmit_buf[info->xmit_tail];
612         if( outch ){
613             info->xmit_cnt--;
614             info->xmit_tail = (info->xmit_tail + 1)
615                                       & (PAGE_SIZE - 1);
616             base_addr[CyTDR] = outch;
617             char_count--;
618         }else{
619             if(char_count > 1){
620                 info->xmit_cnt--;
621                 info->xmit_tail = (info->xmit_tail + 1)
622                                           & (PAGE_SIZE - 1);
623                 base_addr[CyTDR] = outch;
624                 base_addr[CyTDR] = 0;
625                 char_count--;
626                 char_count--;
627             }else{
628                 break;
629             }
630         }
631     }
632
633     if (info->xmit_cnt < WAKEUP_CHARS) {
634         cy_sched_event(info, Cy_EVENT_WRITE_WAKEUP);
635     }
636     base_addr[CyTEOIR] = (char_count != saved_cnt) ? 0 : CyNOTRANS;
637     return IRQ_HANDLED;
638 } /* cy_tx_interrupt */
639
640 static irqreturn_t
641 cd2401_rx_interrupt(int irq, void *dev_id, struct pt_regs *fp)
642 {
643     struct tty_struct *tty;
644     struct cyclades_port *info;
645     volatile unsigned char *base_addr = (unsigned char *)BASE_ADDR;
646     int channel;
647     char data;
648     int char_count;
649     int save_cnt;
650
651     /* determine the channel and change to that context */
652     channel = (u_short ) (base_addr[CyLICR] >> 2);
653     info = &cy_port[channel];
654     info->last_active = jiffies;
655     save_cnt = char_count = base_addr[CyRFOC];
656
657 #ifdef CONFIG_REMOTE_DEBUG
658     if (channel == DEBUG_PORT) {
659         while (char_count--) {
660             data = base_addr[CyRDR];
661             queueDebugChar(data);
662         }
663     }
664     else
665 #endif
666     /* if there is nowhere to put the data, discard it */
667     if(info->tty == 0){
668         while(char_count--){
669             data = base_addr[CyRDR];
670         }
671     }else{ /* there is an open port for this data */
672         tty = info->tty;
673         /* load # characters available from the chip */
674
675 #ifdef CYCLOM_ENABLE_MONITORING
676         ++info->mon.int_count;
677         info->mon.char_count += char_count;
678         if (char_count > info->mon.char_max)
679             info->mon.char_max = char_count;
680         info->mon.char_last = char_count;
681 #endif
682         while(char_count--){
683             data = base_addr[CyRDR];
684             tty_insert_flip_char(tty, data, TTY_NORMAL);
685 #ifdef CYCLOM_16Y_HACK
686             udelay(10L);
687 #endif
688         }
689         schedule_delayed_work(&tty->flip.work, 1);
690     }
691     /* end of service */
692     base_addr[CyREOIR] = save_cnt ? 0 : CyNOTRANS;
693     return IRQ_HANDLED;
694 } /* cy_rx_interrupt */
695
696 /*
697  * This routine is used to handle the "bottom half" processing for the
698  * serial driver, known also the "software interrupt" processing.
699  * This processing is done at the kernel interrupt level, after the
700  * cy#/_interrupt() has returned, BUT WITH INTERRUPTS TURNED ON.  This
701  * is where time-consuming activities which can not be done in the
702  * interrupt driver proper are done; the interrupt driver schedules
703  * them using cy_sched_event(), and they get done here.
704  *
705  * This is done through one level of indirection--the task queue.
706  * When a hardware interrupt service routine wants service by the
707  * driver's bottom half, it enqueues the appropriate tq_struct (one
708  * per port) to the keventd work queue and sets a request flag
709  * that the work queue be processed.
710  *
711  * Although this may seem unwieldy, it gives the system a way to
712  * pass an argument (in this case the pointer to the cyclades_port
713  * structure) to the bottom half of the driver.  Previous kernels
714  * had to poll every port to see if that port needed servicing.
715  */
716 static void
717 do_softint(void *private_)
718 {
719   struct cyclades_port *info = (struct cyclades_port *) private_;
720   struct tty_struct    *tty;
721
722     tty = info->tty;
723     if (!tty)
724         return;
725
726     if (test_and_clear_bit(Cy_EVENT_HANGUP, &info->event)) {
727         tty_hangup(info->tty);
728         wake_up_interruptible(&info->open_wait);
729         info->flags &= ~ASYNC_NORMAL_ACTIVE;
730     }
731     if (test_and_clear_bit(Cy_EVENT_OPEN_WAKEUP, &info->event)) {
732         wake_up_interruptible(&info->open_wait);
733     }
734     if (test_and_clear_bit(Cy_EVENT_WRITE_WAKEUP, &info->event)) {
735         tty_wakeup(tty);
736     }
737 } /* do_softint */
738
739
740 /* This is called whenever a port becomes active;
741    interrupts are enabled and DTR & RTS are turned on.
742  */
743 static int
744 startup(struct cyclades_port * info)
745 {
746   unsigned long flags;
747   volatile unsigned char *base_addr = (unsigned char *)BASE_ADDR;
748   int channel;
749
750     if (info->flags & ASYNC_INITIALIZED){
751         return 0;
752     }
753
754     if (!info->type){
755         if (info->tty){
756             set_bit(TTY_IO_ERROR, &info->tty->flags);
757         }
758         return 0;
759     }
760     if (!info->xmit_buf){
761         info->xmit_buf = (unsigned char *) get_zeroed_page (GFP_KERNEL);
762         if (!info->xmit_buf){
763             return -ENOMEM;
764         }
765     }
766
767     config_setup(info);
768
769     channel = info->line;
770
771 #ifdef SERIAL_DEBUG_OPEN
772     printk("startup channel %d\n", channel);
773 #endif
774
775     local_irq_save(flags);
776         base_addr[CyCAR] = (u_char)channel;
777         write_cy_cmd(base_addr,CyENB_RCVR|CyENB_XMTR);
778
779         base_addr[CyCAR] = (u_char)channel; /* !!! Is this needed? */
780         base_addr[CyMSVR1] = CyRTS;
781 /* CP('S');CP('1'); */
782         base_addr[CyMSVR2] = CyDTR;
783
784 #ifdef SERIAL_DEBUG_DTR
785         printk("cyc: %d: raising DTR\n", __LINE__);
786         printk("     status: 0x%x, 0x%x\n", base_addr[CyMSVR1], base_addr[CyMSVR2]);
787 #endif
788
789         base_addr[CyIER] |= CyRxData;
790         info->flags |= ASYNC_INITIALIZED;
791
792         if (info->tty){
793             clear_bit(TTY_IO_ERROR, &info->tty->flags);
794         }
795         info->xmit_cnt = info->xmit_head = info->xmit_tail = 0;
796
797     local_irq_restore(flags);
798
799 #ifdef SERIAL_DEBUG_OPEN
800     printk(" done\n");
801 #endif
802     return 0;
803 } /* startup */
804
805 void
806 start_xmit( struct cyclades_port *info )
807 {
808   unsigned long flags;
809   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
810   int channel;
811
812     channel = info->line;
813     local_irq_save(flags);
814         base_addr[CyCAR] = channel;
815         base_addr[CyIER] |= CyTxMpty;
816     local_irq_restore(flags);
817 } /* start_xmit */
818
819 /*
820  * This routine shuts down a serial port; interrupts are disabled,
821  * and DTR is dropped if the hangup on close termio flag is on.
822  */
823 static void
824 shutdown(struct cyclades_port * info)
825 {
826   unsigned long flags;
827   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
828   int channel;
829
830     if (!(info->flags & ASYNC_INITIALIZED)){
831 /* CP('$'); */
832         return;
833     }
834
835     channel = info->line;
836
837 #ifdef SERIAL_DEBUG_OPEN
838     printk("shutdown channel %d\n", channel);
839 #endif
840
841     /* !!! REALLY MUST WAIT FOR LAST CHARACTER TO BE
842        SENT BEFORE DROPPING THE LINE !!!  (Perhaps
843        set some flag that is read when XMTY happens.)
844        Other choices are to delay some fixed interval
845        or schedule some later processing.
846      */
847     local_irq_save(flags);
848         if (info->xmit_buf){
849             free_page((unsigned long) info->xmit_buf);
850             info->xmit_buf = 0;
851         }
852
853         base_addr[CyCAR] = (u_char)channel;
854         if (!info->tty || (info->tty->termios->c_cflag & HUPCL)) {
855             base_addr[CyMSVR1] = 0;
856 /* CP('C');CP('1'); */
857             base_addr[CyMSVR2] = 0;
858 #ifdef SERIAL_DEBUG_DTR
859             printk("cyc: %d: dropping DTR\n", __LINE__);
860             printk("     status: 0x%x, 0x%x\n", base_addr[CyMSVR1], base_addr[CyMSVR2]);
861 #endif
862         }
863         write_cy_cmd(base_addr,CyDIS_RCVR);
864          /* it may be appropriate to clear _XMIT at
865            some later date (after testing)!!! */
866
867         if (info->tty){
868             set_bit(TTY_IO_ERROR, &info->tty->flags);
869         }
870         info->flags &= ~ASYNC_INITIALIZED;
871     local_irq_restore(flags);
872
873 #ifdef SERIAL_DEBUG_OPEN
874     printk(" done\n");
875 #endif
876     return;
877 } /* shutdown */
878
879 /*
880  * This routine finds or computes the various line characteristics.
881  */
882 static void
883 config_setup(struct cyclades_port * info)
884 {
885   unsigned long flags;
886   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
887   int channel;
888   unsigned cflag;
889   int   i;
890   unsigned char ti, need_init_chan = 0;
891
892     if (!info->tty || !info->tty->termios){
893         return;
894     }
895     if (info->line == -1){
896         return;
897     }
898     cflag = info->tty->termios->c_cflag;
899
900     /* baud rate */
901     i = cflag & CBAUD;
902 #ifdef CBAUDEX
903 /* Starting with kernel 1.1.65, there is direct support for
904    higher baud rates.  The following code supports those
905    changes.  The conditional aspect allows this driver to be
906    used for earlier as well as later kernel versions.  (The
907    mapping is slightly different from serial.c because there
908    is still the possibility of supporting 75 kbit/sec with
909    the Cyclades board.)
910  */
911     if (i & CBAUDEX) {
912         if (i == B57600)
913             i = 16;
914         else if(i == B115200) 
915             i = 18;
916 #ifdef B78600
917         else if(i == B78600) 
918             i = 17;
919 #endif
920         else
921             info->tty->termios->c_cflag &= ~CBAUDEX;
922     }
923 #endif
924     if (i == 15) {
925             if ((info->flags & ASYNC_SPD_MASK) == ASYNC_SPD_HI)
926                     i += 1;
927             if ((info->flags & ASYNC_SPD_MASK) == ASYNC_SPD_VHI)
928                     i += 3;
929     }
930     /* Don't ever change the speed of the console port.  It will
931      * run at the speed specified in bootinfo, or at 19.2K */
932     /* Actually, it should run at whatever speed 166Bug was using */
933     /* Note info->timeout isn't used at present */
934     if (info != serial_console_info) {
935         info->tbpr = baud_bpr[i]; /* Tx BPR */
936         info->tco = baud_co[i]; /* Tx CO */
937         info->rbpr = baud_bpr[i]; /* Rx BPR */
938         info->rco = baud_co[i] >> 5; /* Rx CO */
939         if (baud_table[i] == 134) {
940             info->timeout = (info->xmit_fifo_size*HZ*30/269) + 2;
941             /* get it right for 134.5 baud */
942         } else if (baud_table[i]) {
943             info->timeout = (info->xmit_fifo_size*HZ*15/baud_table[i]) + 2;
944         /* this needs to be propagated into the card info */
945         } else {
946             info->timeout = 0;
947         }
948     }
949     /* By tradition (is it a standard?) a baud rate of zero
950        implies the line should be/has been closed.  A bit
951        later in this routine such a test is performed. */
952
953     /* byte size and parity */
954     info->cor7 = 0;
955     info->cor6 = 0;
956     info->cor5 = 0;
957     info->cor4 = (info->default_threshold
958                   ? info->default_threshold
959                   : baud_cor4[i]); /* receive threshold */
960     /* Following two lines added 101295, RGH. */
961     /* It is obviously wrong to access CyCORx, and not info->corx here,
962      * try and remember to fix it later! */
963     channel = info->line;
964     base_addr[CyCAR] = (u_char)channel;
965     if (C_CLOCAL(info->tty)) {
966         if (base_addr[CyIER] & CyMdmCh)
967             base_addr[CyIER] &= ~CyMdmCh; /* without modem intr */
968                                /* ignore 1->0 modem transitions */
969         if (base_addr[CyCOR4] & (CyDSR|CyCTS|CyDCD))
970             base_addr[CyCOR4] &= ~(CyDSR|CyCTS|CyDCD);
971                                /* ignore 0->1 modem transitions */
972         if (base_addr[CyCOR5] & (CyDSR|CyCTS|CyDCD))
973             base_addr[CyCOR5] &= ~(CyDSR|CyCTS|CyDCD);
974     } else {
975         if ((base_addr[CyIER] & CyMdmCh) != CyMdmCh)
976             base_addr[CyIER] |= CyMdmCh; /* with modem intr */
977                                /* act on 1->0 modem transitions */
978         if ((base_addr[CyCOR4] & (CyDSR|CyCTS|CyDCD)) != (CyDSR|CyCTS|CyDCD))
979             base_addr[CyCOR4] |= CyDSR|CyCTS|CyDCD;
980                                /* act on 0->1 modem transitions */
981         if ((base_addr[CyCOR5] & (CyDSR|CyCTS|CyDCD)) != (CyDSR|CyCTS|CyDCD))
982             base_addr[CyCOR5] |= CyDSR|CyCTS|CyDCD;
983     }
984     info->cor3 = (cflag & CSTOPB) ? Cy_2_STOP : Cy_1_STOP;
985     info->cor2 = CyETC;
986     switch(cflag & CSIZE){
987     case CS5:
988         info->cor1 = Cy_5_BITS;
989         break;
990     case CS6:
991         info->cor1 = Cy_6_BITS;
992         break;
993     case CS7:
994         info->cor1 = Cy_7_BITS;
995         break;
996     case CS8:
997         info->cor1 = Cy_8_BITS;
998         break;
999     }
1000     if (cflag & PARENB){
1001         if (cflag & PARODD){
1002             info->cor1 |= CyPARITY_O;
1003         }else{
1004             info->cor1 |= CyPARITY_E;
1005         }
1006     }else{
1007         info->cor1 |= CyPARITY_NONE;
1008     }
1009         
1010     /* CTS flow control flag */
1011 #if 0
1012     /* Don't complcate matters for now! RGH 141095 */
1013     if (cflag & CRTSCTS){
1014         info->flags |= ASYNC_CTS_FLOW;
1015         info->cor2 |= CyCtsAE;
1016     }else{
1017         info->flags &= ~ASYNC_CTS_FLOW;
1018         info->cor2 &= ~CyCtsAE;
1019     }
1020 #endif
1021     if (cflag & CLOCAL)
1022         info->flags &= ~ASYNC_CHECK_CD;
1023     else
1024         info->flags |= ASYNC_CHECK_CD;
1025
1026      /***********************************************
1027         The hardware option, CyRtsAO, presents RTS when
1028         the chip has characters to send.  Since most modems
1029         use RTS as reverse (inbound) flow control, this
1030         option is not used.  If inbound flow control is
1031         necessary, DTR can be programmed to provide the
1032         appropriate signals for use with a non-standard
1033         cable.  Contact Marcio Saito for details.
1034      ***********************************************/
1035
1036     channel = info->line;
1037
1038     local_irq_save(flags);
1039         base_addr[CyCAR] = (u_char)channel;
1040
1041         /* CyCMR set once only in mvme167_init_serial() */
1042         if (base_addr[CyLICR] != channel << 2)
1043             base_addr[CyLICR] = channel << 2;
1044         if (base_addr[CyLIVR] != 0x5c)
1045             base_addr[CyLIVR] = 0x5c;
1046
1047        /* tx and rx baud rate */
1048
1049         if (base_addr[CyCOR1] != info->cor1)
1050             need_init_chan = 1;
1051         if (base_addr[CyTCOR] != info->tco)
1052             base_addr[CyTCOR] = info->tco;
1053         if (base_addr[CyTBPR] != info->tbpr)
1054             base_addr[CyTBPR] = info->tbpr;
1055         if (base_addr[CyRCOR] != info->rco)
1056             base_addr[CyRCOR] = info->rco;
1057         if (base_addr[CyRBPR] != info->rbpr)
1058             base_addr[CyRBPR] = info->rbpr;
1059
1060         /* set line characteristics  according configuration */
1061
1062         if (base_addr[CySCHR1] != START_CHAR(info->tty))
1063             base_addr[CySCHR1] = START_CHAR(info->tty);
1064         if (base_addr[CySCHR2] != STOP_CHAR(info->tty))
1065             base_addr[CySCHR2] = STOP_CHAR(info->tty);
1066         if (base_addr[CySCRL] != START_CHAR(info->tty))
1067             base_addr[CySCRL] = START_CHAR(info->tty);
1068         if (base_addr[CySCRH] != START_CHAR(info->tty))
1069             base_addr[CySCRH] = START_CHAR(info->tty);
1070         if (base_addr[CyCOR1] != info->cor1)
1071             base_addr[CyCOR1] = info->cor1;
1072         if (base_addr[CyCOR2] != info->cor2)
1073             base_addr[CyCOR2] = info->cor2;
1074         if (base_addr[CyCOR3] != info->cor3)
1075             base_addr[CyCOR3] = info->cor3;
1076         if (base_addr[CyCOR4] != info->cor4)
1077             base_addr[CyCOR4] = info->cor4;
1078         if (base_addr[CyCOR5] != info->cor5)
1079             base_addr[CyCOR5] = info->cor5;
1080         if (base_addr[CyCOR6] != info->cor6)
1081             base_addr[CyCOR6] = info->cor6;
1082         if (base_addr[CyCOR7] != info->cor7)
1083             base_addr[CyCOR7] = info->cor7;
1084
1085         if (need_init_chan)
1086             write_cy_cmd(base_addr,CyINIT_CHAN);
1087
1088         base_addr[CyCAR] = (u_char)channel; /* !!! Is this needed? */
1089
1090         /* 2ms default rx timeout */
1091         ti = info->default_timeout ? info->default_timeout : 0x02;
1092         if (base_addr[CyRTPRL] != ti)
1093             base_addr[CyRTPRL] = ti;
1094         if (base_addr[CyRTPRH] != 0)
1095             base_addr[CyRTPRH] = 0;
1096
1097         /* Set up RTS here also ????? RGH 141095 */
1098         if(i == 0){ /* baud rate is zero, turn off line */
1099             if ((base_addr[CyMSVR2] & CyDTR) == CyDTR)
1100                 base_addr[CyMSVR2] = 0;
1101 #ifdef SERIAL_DEBUG_DTR
1102             printk("cyc: %d: dropping DTR\n", __LINE__);
1103             printk("     status: 0x%x, 0x%x\n", base_addr[CyMSVR1], base_addr[CyMSVR2]);
1104 #endif
1105         }else{
1106             if ((base_addr[CyMSVR2] & CyDTR) != CyDTR)
1107                 base_addr[CyMSVR2] = CyDTR;
1108 #ifdef SERIAL_DEBUG_DTR
1109             printk("cyc: %d: raising DTR\n", __LINE__);
1110             printk("     status: 0x%x, 0x%x\n", base_addr[CyMSVR1], base_addr[CyMSVR2]);
1111 #endif
1112         }
1113
1114         if (info->tty){
1115             clear_bit(TTY_IO_ERROR, &info->tty->flags);
1116         }
1117
1118     local_irq_restore(flags);
1119
1120 } /* config_setup */
1121
1122
1123 static void
1124 cy_put_char(struct tty_struct *tty, unsigned char ch)
1125 {
1126   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
1127   unsigned long flags;
1128
1129 #ifdef SERIAL_DEBUG_IO
1130     printk("cy_put_char %s(0x%02x)\n", tty->name, ch);
1131 #endif
1132
1133     if (serial_paranoia_check(info, tty->name, "cy_put_char"))
1134         return;
1135
1136     if (!tty || !info->xmit_buf)
1137         return;
1138
1139     local_irq_save(flags);
1140         if (info->xmit_cnt >= PAGE_SIZE - 1) {
1141             local_irq_restore(flags);
1142             return;
1143         }
1144
1145         info->xmit_buf[info->xmit_head++] = ch;
1146         info->xmit_head &= PAGE_SIZE - 1;
1147         info->xmit_cnt++;
1148     local_irq_restore(flags);
1149 } /* cy_put_char */
1150
1151
1152 static void
1153 cy_flush_chars(struct tty_struct *tty)
1154 {
1155   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
1156   unsigned long flags;
1157   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
1158   int channel;
1159                                 
1160 #ifdef SERIAL_DEBUG_IO
1161     printk("cy_flush_chars %s\n", tty->name); /* */
1162 #endif
1163
1164     if (serial_paranoia_check(info, tty->name, "cy_flush_chars"))
1165         return;
1166
1167     if (info->xmit_cnt <= 0 || tty->stopped
1168     || tty->hw_stopped || !info->xmit_buf)
1169         return;
1170
1171     channel = info->line;
1172
1173     local_irq_save(flags);
1174         base_addr[CyCAR] = channel;
1175         base_addr[CyIER] |= CyTxMpty;
1176     local_irq_restore(flags);
1177 } /* cy_flush_chars */
1178
1179
1180 /* This routine gets called when tty_write has put something into
1181     the write_queue.  If the port is not already transmitting stuff,
1182     start it off by enabling interrupts.  The interrupt service
1183     routine will then ensure that the characters are sent.  If the
1184     port is already active, there is no need to kick it.
1185  */
1186 static int
1187 cy_write(struct tty_struct * tty,
1188            const unsigned char *buf, int count)
1189 {
1190   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
1191   unsigned long flags;
1192   int c, total = 0;
1193
1194 #ifdef SERIAL_DEBUG_IO
1195     printk("cy_write %s\n", tty->name); /* */
1196 #endif
1197
1198     if (serial_paranoia_check(info, tty->name, "cy_write")){
1199         return 0;
1200     }
1201         
1202     if (!tty || !info->xmit_buf || !tmp_buf){
1203         return 0;
1204     }
1205
1206     while (1) {
1207             local_irq_save(flags);
1208             c = min_t(int, count, min(SERIAL_XMIT_SIZE - info->xmit_cnt - 1,
1209                                       SERIAL_XMIT_SIZE - info->xmit_head));
1210             if (c <= 0) {
1211                     local_irq_restore(flags);
1212                     break;
1213             }
1214
1215             memcpy(info->xmit_buf + info->xmit_head, buf, c);
1216             info->xmit_head = (info->xmit_head + c) & (SERIAL_XMIT_SIZE-1);
1217             info->xmit_cnt += c;
1218             local_irq_restore(flags);
1219
1220             buf += c;
1221             count -= c;
1222             total += c;
1223     }
1224
1225     if (info->xmit_cnt
1226     && !tty->stopped
1227     && !tty->hw_stopped ) {
1228         start_xmit(info);
1229     }
1230     return total;
1231 } /* cy_write */
1232
1233
1234 static int
1235 cy_write_room(struct tty_struct *tty)
1236 {
1237   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
1238   int   ret;
1239                                 
1240 #ifdef SERIAL_DEBUG_IO
1241     printk("cy_write_room %s\n", tty->name); /* */
1242 #endif
1243
1244     if (serial_paranoia_check(info, tty->name, "cy_write_room"))
1245         return 0;
1246     ret = PAGE_SIZE - info->xmit_cnt - 1;
1247     if (ret < 0)
1248         ret = 0;
1249     return ret;
1250 } /* cy_write_room */
1251
1252
1253 static int
1254 cy_chars_in_buffer(struct tty_struct *tty)
1255 {
1256   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
1257                                 
1258 #ifdef SERIAL_DEBUG_IO
1259     printk("cy_chars_in_buffer %s %d\n", tty->name, info->xmit_cnt); /* */
1260 #endif
1261
1262     if (serial_paranoia_check(info, tty->name, "cy_chars_in_buffer"))
1263         return 0;
1264
1265     return info->xmit_cnt;
1266 } /* cy_chars_in_buffer */
1267
1268
1269 static void
1270 cy_flush_buffer(struct tty_struct *tty)
1271 {
1272   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
1273   unsigned long flags;
1274                                 
1275 #ifdef SERIAL_DEBUG_IO
1276     printk("cy_flush_buffer %s\n", tty->name); /* */
1277 #endif
1278
1279     if (serial_paranoia_check(info, tty->name, "cy_flush_buffer"))
1280         return;
1281     local_irq_save(flags);
1282         info->xmit_cnt = info->xmit_head = info->xmit_tail = 0;
1283     local_irq_restore(flags);
1284     tty_wakeup(tty);
1285 } /* cy_flush_buffer */
1286
1287
1288 /* This routine is called by the upper-layer tty layer to signal
1289    that incoming characters should be throttled or that the
1290    throttle should be released.
1291  */
1292 static void
1293 cy_throttle(struct tty_struct * tty)
1294 {
1295   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
1296   unsigned long flags;
1297   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
1298   int channel;
1299
1300 #ifdef SERIAL_DEBUG_THROTTLE
1301   char buf[64];
1302         
1303     printk("throttle %s: %d....\n", tty_name(tty, buf),
1304            tty->ldisc.chars_in_buffer(tty));
1305     printk("cy_throttle %s\n", tty->name);
1306 #endif
1307
1308     if (serial_paranoia_check(info, tty->name, "cy_nthrottle")){
1309             return;
1310     }
1311
1312     if (I_IXOFF(tty)) {
1313         info->x_char = STOP_CHAR(tty);
1314             /* Should use the "Send Special Character" feature!!! */
1315     }
1316
1317     channel = info->line;
1318
1319     local_irq_save(flags);
1320         base_addr[CyCAR] = (u_char)channel;
1321         base_addr[CyMSVR1] = 0;
1322     local_irq_restore(flags);
1323
1324     return;
1325 } /* cy_throttle */
1326
1327
1328 static void
1329 cy_unthrottle(struct tty_struct * tty)
1330 {
1331   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
1332   unsigned long flags;
1333   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
1334   int channel;
1335
1336 #ifdef SERIAL_DEBUG_THROTTLE
1337   char buf[64];
1338         
1339     printk("throttle %s: %d....\n", tty_name(tty, buf),
1340            tty->ldisc.chars_in_buffer(tty));
1341     printk("cy_unthrottle %s\n", tty->name);
1342 #endif
1343
1344     if (serial_paranoia_check(info, tty->name, "cy_nthrottle")){
1345             return;
1346     }
1347
1348     if (I_IXOFF(tty)) {
1349         info->x_char = START_CHAR(tty);
1350         /* Should use the "Send Special Character" feature!!! */
1351     }
1352
1353     channel = info->line;
1354
1355     local_irq_save(flags);
1356         base_addr[CyCAR] = (u_char)channel;
1357         base_addr[CyMSVR1] = CyRTS;
1358     local_irq_restore(flags);
1359
1360     return;
1361 } /* cy_unthrottle */
1362
1363 static int
1364 get_serial_info(struct cyclades_port * info,
1365                            struct serial_struct * retinfo)
1366 {
1367   struct serial_struct tmp;
1368
1369 /* CP('g'); */
1370     if (!retinfo)
1371             return -EFAULT;
1372     memset(&tmp, 0, sizeof(tmp));
1373     tmp.type = info->type;
1374     tmp.line = info->line;
1375     tmp.port = info->line;
1376     tmp.irq = 0;
1377     tmp.flags = info->flags;
1378     tmp.baud_base = 0;          /*!!!*/
1379     tmp.close_delay = info->close_delay;
1380     tmp.custom_divisor = 0;     /*!!!*/
1381     tmp.hub6 = 0;               /*!!!*/
1382     return copy_to_user(retinfo,&tmp,sizeof(*retinfo)) ? -EFAULT : 0;
1383 } /* get_serial_info */
1384
1385 static int
1386 set_serial_info(struct cyclades_port * info,
1387                            struct serial_struct * new_info)
1388 {
1389   struct serial_struct new_serial;
1390   struct cyclades_port old_info;
1391
1392 /* CP('s'); */
1393     if (!new_info)
1394             return -EFAULT;
1395     if (copy_from_user(&new_serial,new_info,sizeof(new_serial)))
1396             return -EFAULT;
1397     old_info = *info;
1398
1399     if (!capable(CAP_SYS_ADMIN)) {
1400             if ((new_serial.close_delay != info->close_delay) ||
1401                 ((new_serial.flags & ASYNC_FLAGS & ~ASYNC_USR_MASK) !=
1402                  (info->flags & ASYNC_FLAGS & ~ASYNC_USR_MASK)))
1403                     return -EPERM;
1404             info->flags = ((info->flags & ~ASYNC_USR_MASK) |
1405                            (new_serial.flags & ASYNC_USR_MASK));
1406             goto check_and_exit;
1407     }
1408
1409
1410     /*
1411      * OK, past this point, all the error checking has been done.
1412      * At this point, we start making changes.....
1413      */
1414
1415     info->flags = ((info->flags & ~ASYNC_FLAGS) |
1416                     (new_serial.flags & ASYNC_FLAGS));
1417     info->close_delay = new_serial.close_delay;
1418
1419
1420 check_and_exit:
1421     if (info->flags & ASYNC_INITIALIZED){
1422         config_setup(info);
1423         return 0;
1424     }else{
1425         return startup(info);
1426     }
1427 } /* set_serial_info */
1428
1429 static int
1430 cy_tiocmget(struct tty_struct *tty, struct file *file)
1431 {
1432   struct cyclades_port * info = (struct cyclades_port *)tty->driver_data;
1433   int channel;
1434   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
1435   unsigned long flags;
1436   unsigned char status;
1437   unsigned int result;
1438
1439     channel = info->line;
1440
1441     local_irq_save(flags);
1442         base_addr[CyCAR] = (u_char)channel;
1443         status = base_addr[CyMSVR1] | base_addr[CyMSVR2];
1444     local_irq_restore(flags);
1445
1446     return    ((status  & CyRTS) ? TIOCM_RTS : 0)
1447             | ((status  & CyDTR) ? TIOCM_DTR : 0)
1448             | ((status  & CyDCD) ? TIOCM_CAR : 0)
1449             | ((status  & CyDSR) ? TIOCM_DSR : 0)
1450             | ((status  & CyCTS) ? TIOCM_CTS : 0);
1451 } /* cy_tiocmget */
1452
1453 static int
1454 cy_tiocmset(struct tty_struct *tty, struct file *file,
1455             unsigned int set, unsigned int clear)
1456 {
1457   struct cyclades_port * info = (struct cyclades_port *)tty->driver_data;
1458   int channel;
1459   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
1460   unsigned long flags;
1461   unsigned int arg;
1462           
1463     channel = info->line;
1464
1465         if (set & TIOCM_RTS){
1466             local_irq_save(flags);
1467                 base_addr[CyCAR] = (u_char)channel;
1468                 base_addr[CyMSVR1] = CyRTS;
1469             local_irq_restore(flags);
1470         }
1471         if (set & TIOCM_DTR){
1472             local_irq_save(flags);
1473             base_addr[CyCAR] = (u_char)channel;
1474 /* CP('S');CP('2'); */
1475             base_addr[CyMSVR2] = CyDTR;
1476 #ifdef SERIAL_DEBUG_DTR
1477             printk("cyc: %d: raising DTR\n", __LINE__);
1478             printk("     status: 0x%x, 0x%x\n", base_addr[CyMSVR1], base_addr[CyMSVR2]);
1479 #endif
1480             local_irq_restore(flags);
1481         }
1482
1483         if (clear & TIOCM_RTS){
1484             local_irq_save(flags);
1485                 base_addr[CyCAR] = (u_char)channel;
1486                 base_addr[CyMSVR1] = 0;
1487             local_irq_restore(flags);
1488         }
1489         if (clear & TIOCM_DTR){
1490             local_irq_save(flags);
1491             base_addr[CyCAR] = (u_char)channel;
1492 /* CP('C');CP('2'); */
1493             base_addr[CyMSVR2] = 0;
1494 #ifdef SERIAL_DEBUG_DTR
1495             printk("cyc: %d: dropping DTR\n", __LINE__);
1496             printk("     status: 0x%x, 0x%x\n", base_addr[CyMSVR1], base_addr[CyMSVR2]);
1497 #endif
1498             local_irq_restore(flags);
1499         }
1500
1501     return 0;
1502 } /* set_modem_info */
1503
1504 static void
1505 send_break( struct cyclades_port * info, int duration)
1506 { /* Let the transmit ISR take care of this (since it
1507      requires stuffing characters into the output stream).
1508    */
1509     info->x_break = duration;
1510     if (!info->xmit_cnt ) {
1511         start_xmit(info);
1512     }
1513 } /* send_break */
1514
1515 static int
1516 get_mon_info(struct cyclades_port * info, struct cyclades_monitor * mon)
1517 {
1518
1519    if (copy_to_user(mon, &info->mon, sizeof(struct cyclades_monitor)))
1520            return -EFAULT;
1521    info->mon.int_count  = 0;
1522    info->mon.char_count = 0;
1523    info->mon.char_max   = 0;
1524    info->mon.char_last  = 0;
1525    return 0;
1526 }
1527
1528 static int
1529 set_threshold(struct cyclades_port * info, unsigned long *arg)
1530 {
1531    volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
1532    unsigned long value;
1533    int channel;
1534    
1535    if (get_user(value, arg))
1536            return -EFAULT;
1537
1538    channel = info->line;
1539    info->cor4 &= ~CyREC_FIFO;
1540    info->cor4 |= value & CyREC_FIFO;
1541    base_addr[CyCOR4] = info->cor4;
1542    return 0;
1543 }
1544
1545 static int
1546 get_threshold(struct cyclades_port * info, unsigned long *value)
1547 {
1548    volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
1549    int channel;
1550    unsigned long tmp;
1551    
1552    channel = info->line;
1553
1554    tmp = base_addr[CyCOR4] & CyREC_FIFO;
1555    return put_user(tmp,value);
1556 }
1557
1558 static int
1559 set_default_threshold(struct cyclades_port * info, unsigned long *arg)
1560 {
1561    unsigned long value;
1562
1563    if (get_user(value, arg))
1564         return -EFAULT;
1565
1566    info->default_threshold = value & 0x0f;
1567    return 0;
1568 }
1569
1570 static int
1571 get_default_threshold(struct cyclades_port * info, unsigned long *value)
1572 {
1573    return put_user(info->default_threshold,value);
1574 }
1575
1576 static int
1577 set_timeout(struct cyclades_port * info, unsigned long *arg)
1578 {
1579    volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
1580    int channel;
1581    unsigned long value;
1582
1583    if (get_user(value, arg))
1584            return -EFAULT;
1585    
1586    channel = info->line;
1587
1588    base_addr[CyRTPRL] = value & 0xff;
1589    base_addr[CyRTPRH] = (value >> 8) & 0xff;
1590    return 0;
1591 }
1592
1593 static int
1594 get_timeout(struct cyclades_port * info, unsigned long *value)
1595 {
1596    volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
1597    int channel;
1598    unsigned long tmp;
1599    
1600    channel = info->line;
1601
1602    tmp = base_addr[CyRTPRL];
1603    return put_user(tmp,value);
1604 }
1605
1606 static int
1607 set_default_timeout(struct cyclades_port * info, unsigned long value)
1608 {
1609    info->default_timeout = value & 0xff;
1610    return 0;
1611 }
1612
1613 static int
1614 get_default_timeout(struct cyclades_port * info, unsigned long *value)
1615 {
1616    return put_user(info->default_timeout,value);
1617 }
1618
1619 static int
1620 cy_ioctl(struct tty_struct *tty, struct file * file,
1621             unsigned int cmd, unsigned long arg)
1622 {
1623   unsigned long val;
1624   struct cyclades_port * info = (struct cyclades_port *)tty->driver_data;
1625   int ret_val = 0;
1626
1627 #ifdef SERIAL_DEBUG_OTHER
1628     printk("cy_ioctl %s, cmd = %x arg = %lx\n", tty->name, cmd, arg); /* */
1629 #endif
1630
1631     switch (cmd) {
1632         case CYGETMON:
1633             ret_val = get_mon_info(info, (struct cyclades_monitor *)arg);
1634             break;
1635         case CYGETTHRESH:
1636             ret_val = get_threshold(info, (unsigned long *)arg);
1637             break;
1638         case CYSETTHRESH:
1639             ret_val = set_threshold(info, (unsigned long *)arg);
1640             break;
1641         case CYGETDEFTHRESH:
1642             ret_val = get_default_threshold(info, (unsigned long *)arg);
1643             break;
1644         case CYSETDEFTHRESH:
1645             ret_val = set_default_threshold(info, (unsigned long *)arg);
1646             break;
1647         case CYGETTIMEOUT:
1648             ret_val = get_timeout(info, (unsigned long *)arg);
1649             break;
1650         case CYSETTIMEOUT:
1651             ret_val = set_timeout(info, (unsigned long *)arg);
1652             break;
1653         case CYGETDEFTIMEOUT:
1654             ret_val = get_default_timeout(info, (unsigned long *)arg);
1655             break;
1656         case CYSETDEFTIMEOUT:
1657             ret_val = set_default_timeout(info, (unsigned long)arg);
1658             break;
1659         case TCSBRK:    /* SVID version: non-zero arg --> no break */
1660             ret_val = tty_check_change(tty);
1661             if (ret_val)
1662                     break;
1663             tty_wait_until_sent(tty,0);
1664             if (!arg)
1665                 send_break(info, HZ/4); /* 1/4 second */
1666             break;
1667         case TCSBRKP:   /* support for POSIX tcsendbreak() */
1668             ret_val = tty_check_change(tty);
1669             if (ret_val)
1670                 break;
1671             tty_wait_until_sent(tty,0);
1672             send_break(info, arg ? arg*(HZ/10) : HZ/4);
1673             break;
1674
1675 /* The following commands are incompletely implemented!!! */
1676         case TIOCGSOFTCAR:
1677             ret_val = put_user(C_CLOCAL(tty) ? 1 : 0, (unsigned long *) arg);
1678             break;
1679         case TIOCSSOFTCAR:
1680             ret_val = get_user(val, (unsigned long *) arg);
1681             if (ret_val)
1682                     break;
1683             tty->termios->c_cflag =
1684                     ((tty->termios->c_cflag & ~CLOCAL) | (val ? CLOCAL : 0));
1685             break;
1686         case TIOCGSERIAL:
1687             ret_val = get_serial_info(info, (struct serial_struct *) arg);
1688             break;
1689         case TIOCSSERIAL:
1690             ret_val = set_serial_info(info,
1691                                    (struct serial_struct *) arg);
1692             break;
1693         default:
1694             ret_val = -ENOIOCTLCMD;
1695     }
1696
1697 #ifdef SERIAL_DEBUG_OTHER
1698     printk("cy_ioctl done\n");
1699 #endif
1700
1701     return ret_val;
1702 } /* cy_ioctl */
1703
1704
1705
1706
1707 static void
1708 cy_set_termios(struct tty_struct *tty, struct termios * old_termios)
1709 {
1710   struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
1711
1712 #ifdef SERIAL_DEBUG_OTHER
1713     printk("cy_set_termios %s\n", tty->name);
1714 #endif
1715
1716     if (tty->termios->c_cflag == old_termios->c_cflag)
1717         return;
1718     config_setup(info);
1719
1720     if ((old_termios->c_cflag & CRTSCTS) &&
1721         !(tty->termios->c_cflag & CRTSCTS)) {
1722             tty->stopped = 0;
1723             cy_start(tty);
1724     }
1725 #ifdef tytso_patch_94Nov25_1726
1726     if (!(old_termios->c_cflag & CLOCAL) &&
1727         (tty->termios->c_cflag & CLOCAL))
1728             wake_up_interruptible(&info->open_wait);
1729 #endif
1730
1731     return;
1732 } /* cy_set_termios */
1733
1734
1735 static void
1736 cy_close(struct tty_struct * tty, struct file * filp)
1737 {
1738   struct cyclades_port * info = (struct cyclades_port *)tty->driver_data;
1739
1740 /* CP('C'); */
1741 #ifdef SERIAL_DEBUG_OTHER
1742     printk("cy_close %s\n", tty->name);
1743 #endif
1744
1745     if (!info
1746     || serial_paranoia_check(info, tty->name, "cy_close")){
1747         return;
1748     }
1749 #ifdef SERIAL_DEBUG_OPEN
1750     printk("cy_close %s, count = %d\n", tty->name, info->count);
1751 #endif
1752
1753     if ((tty->count == 1) && (info->count != 1)) {
1754         /*
1755          * Uh, oh.  tty->count is 1, which means that the tty
1756          * structure will be freed.  Info->count should always
1757          * be one in these conditions.  If it's greater than
1758          * one, we've got real problems, since it means the
1759          * serial port won't be shutdown.
1760          */
1761         printk("cy_close: bad serial port count; tty->count is 1, "
1762            "info->count is %d\n", info->count);
1763         info->count = 1;
1764     }
1765 #ifdef SERIAL_DEBUG_COUNT
1766     printk("cyc: %d: decrementing count to %d\n", __LINE__, info->count - 1);
1767 #endif
1768     if (--info->count < 0) {
1769         printk("cy_close: bad serial port count for ttys%d: %d\n",
1770                info->line, info->count);
1771 #ifdef SERIAL_DEBUG_COUNT
1772     printk("cyc: %d: setting count to 0\n", __LINE__);
1773 #endif
1774         info->count = 0;
1775     }
1776     if (info->count)
1777         return;
1778     info->flags |= ASYNC_CLOSING;
1779     if (info->flags & ASYNC_INITIALIZED)
1780         tty_wait_until_sent(tty, 3000); /* 30 seconds timeout */
1781     shutdown(info);
1782     if (tty->driver->flush_buffer)
1783         tty->driver->flush_buffer(tty);
1784     tty_ldisc_flush(tty);
1785     info->event = 0;
1786     info->tty = 0;
1787     if (info->blocked_open) {
1788         if (info->close_delay) {
1789             msleep_interruptible(jiffies_to_msecs(info->close_delay));
1790         }
1791         wake_up_interruptible(&info->open_wait);
1792     }
1793     info->flags &= ~(ASYNC_NORMAL_ACTIVE|ASYNC_CLOSING);
1794     wake_up_interruptible(&info->close_wait);
1795
1796 #ifdef SERIAL_DEBUG_OTHER
1797     printk("cy_close done\n");
1798 #endif
1799
1800     return;
1801 } /* cy_close */
1802
1803 /*
1804  * cy_hangup() --- called by tty_hangup() when a hangup is signaled.
1805  */
1806 void
1807 cy_hangup(struct tty_struct *tty)
1808 {
1809   struct cyclades_port * info = (struct cyclades_port *)tty->driver_data;
1810         
1811 #ifdef SERIAL_DEBUG_OTHER
1812     printk("cy_hangup %s\n", tty->name); /* */
1813 #endif
1814
1815     if (serial_paranoia_check(info, tty->name, "cy_hangup"))
1816         return;
1817     
1818     shutdown(info);
1819 #if 0
1820     info->event = 0;
1821     info->count = 0;
1822 #ifdef SERIAL_DEBUG_COUNT
1823     printk("cyc: %d: setting count to 0\n", __LINE__);
1824 #endif
1825     info->tty = 0;
1826 #endif
1827     info->flags &= ~ASYNC_NORMAL_ACTIVE;
1828     wake_up_interruptible(&info->open_wait);
1829 } /* cy_hangup */
1830
1831
1832
1833 /*
1834  * ------------------------------------------------------------
1835  * cy_open() and friends
1836  * ------------------------------------------------------------
1837  */
1838
1839 static int
1840 block_til_ready(struct tty_struct *tty, struct file * filp,
1841                            struct cyclades_port *info)
1842 {
1843   DECLARE_WAITQUEUE(wait, current);
1844   unsigned long flags;
1845   int channel;
1846   int retval;
1847   volatile u_char *base_addr = (u_char *)BASE_ADDR;
1848
1849     /*
1850      * If the device is in the middle of being closed, then block
1851      * until it's done, and then try again.
1852      */
1853     if (info->flags & ASYNC_CLOSING) {
1854         interruptible_sleep_on(&info->close_wait);
1855         if (info->flags & ASYNC_HUP_NOTIFY){
1856             return -EAGAIN;
1857         }else{
1858             return -ERESTARTSYS;
1859         }
1860     }
1861
1862     /*
1863      * If non-blocking mode is set, then make the check up front
1864      * and then exit.
1865      */
1866     if (filp->f_flags & O_NONBLOCK) {
1867         info->flags |= ASYNC_NORMAL_ACTIVE;
1868         return 0;
1869     }
1870
1871     /*
1872      * Block waiting for the carrier detect and the line to become
1873      * free (i.e., not in use by the callout).  While we are in
1874      * this loop, info->count is dropped by one, so that
1875      * cy_close() knows when to free things.  We restore it upon
1876      * exit, either normal or abnormal.
1877      */
1878     retval = 0;
1879     add_wait_queue(&info->open_wait, &wait);
1880 #ifdef SERIAL_DEBUG_OPEN
1881     printk("block_til_ready before block: %s, count = %d\n",
1882            tty->name, info->count);/**/
1883 #endif
1884     info->count--;
1885 #ifdef SERIAL_DEBUG_COUNT
1886     printk("cyc: %d: decrementing count to %d\n", __LINE__, info->count);
1887 #endif
1888     info->blocked_open++;
1889
1890     channel = info->line;
1891
1892     while (1) {
1893         local_irq_save(flags);
1894         base_addr[CyCAR] = (u_char)channel;
1895         base_addr[CyMSVR1] = CyRTS;
1896 /* CP('S');CP('4'); */
1897         base_addr[CyMSVR2] = CyDTR;
1898 #ifdef SERIAL_DEBUG_DTR
1899         printk("cyc: %d: raising DTR\n", __LINE__);
1900         printk("     status: 0x%x, 0x%x\n", base_addr[CyMSVR1], base_addr[CyMSVR2]);
1901 #endif
1902         local_irq_restore(flags);
1903         set_current_state(TASK_INTERRUPTIBLE);
1904         if (tty_hung_up_p(filp)
1905         || !(info->flags & ASYNC_INITIALIZED) ){
1906             if (info->flags & ASYNC_HUP_NOTIFY) {
1907                 retval = -EAGAIN;
1908             }else{
1909                 retval = -ERESTARTSYS;
1910             }
1911             break;
1912         }
1913         local_irq_save(flags);
1914             base_addr[CyCAR] = (u_char)channel;
1915 /* CP('L');CP1(1 && C_CLOCAL(tty)); CP1(1 && (base_addr[CyMSVR1] & CyDCD) ); */
1916             if (!(info->flags & ASYNC_CLOSING)
1917             && (C_CLOCAL(tty)
1918                 || (base_addr[CyMSVR1] & CyDCD))) {
1919                     local_irq_restore(flags);
1920                     break;
1921             }
1922         local_irq_restore(flags);
1923         if (signal_pending(current)) {
1924             retval = -ERESTARTSYS;
1925             break;
1926         }
1927 #ifdef SERIAL_DEBUG_OPEN
1928         printk("block_til_ready blocking: %s, count = %d\n",
1929                tty->name, info->count);/**/
1930 #endif
1931         schedule();
1932     }
1933     current->state = TASK_RUNNING;
1934     remove_wait_queue(&info->open_wait, &wait);
1935     if (!tty_hung_up_p(filp)){
1936         info->count++;
1937 #ifdef SERIAL_DEBUG_COUNT
1938     printk("cyc: %d: incrementing count to %d\n", __LINE__, info->count);
1939 #endif
1940     }
1941     info->blocked_open--;
1942 #ifdef SERIAL_DEBUG_OPEN
1943     printk("block_til_ready after blocking: %s, count = %d\n",
1944            tty->name, info->count);/**/
1945 #endif
1946     if (retval)
1947             return retval;
1948     info->flags |= ASYNC_NORMAL_ACTIVE;
1949     return 0;
1950 } /* block_til_ready */
1951
1952 /*
1953  * This routine is called whenever a serial port is opened.  It
1954  * performs the serial-specific initialization for the tty structure.
1955  */
1956 int
1957 cy_open(struct tty_struct *tty, struct file * filp)
1958 {
1959   struct cyclades_port  *info;
1960   int retval, line;
1961
1962 /* CP('O'); */
1963     line = tty->index;
1964     if ((line < 0) || (NR_PORTS <= line)){
1965         return -ENODEV;
1966     }
1967     info = &cy_port[line];
1968     if (info->line < 0){
1969         return -ENODEV;
1970     }
1971 #ifdef SERIAL_DEBUG_OTHER
1972     printk("cy_open %s\n", tty->name); /* */
1973 #endif
1974     if (serial_paranoia_check(info, tty->name, "cy_open")){
1975         return -ENODEV;
1976     }
1977 #ifdef SERIAL_DEBUG_OPEN
1978     printk("cy_open %s, count = %d\n", tty->name, info->count);/**/
1979 #endif
1980     info->count++;
1981 #ifdef SERIAL_DEBUG_COUNT
1982     printk("cyc: %d: incrementing count to %d\n", __LINE__, info->count);
1983 #endif
1984     tty->driver_data = info;
1985     info->tty = tty;
1986
1987     if (!tmp_buf) {
1988         tmp_buf = (unsigned char *) get_zeroed_page(GFP_KERNEL);
1989         if (!tmp_buf){
1990             return -ENOMEM;
1991         }
1992     }
1993
1994     /*
1995      * Start up serial port
1996      */
1997     retval = startup(info);
1998     if (retval){
1999         return retval;
2000     }
2001
2002     retval = block_til_ready(tty, filp, info);
2003     if (retval) {
2004 #ifdef SERIAL_DEBUG_OPEN
2005         printk("cy_open returning after block_til_ready with %d\n",
2006                retval);
2007 #endif
2008         return retval;
2009     }
2010
2011 #ifdef SERIAL_DEBUG_OPEN
2012     printk("cy_open done\n");/**/
2013 #endif
2014     return 0;
2015 } /* cy_open */
2016
2017
2018
2019 /*
2020  * ---------------------------------------------------------------------
2021  * serial167_init() and friends
2022  *
2023  * serial167_init() is called at boot-time to initialize the serial driver.
2024  * ---------------------------------------------------------------------
2025  */
2026
2027 /*
2028  * This routine prints out the appropriate serial driver version
2029  * number, and identifies which options were configured into this
2030  * driver.
2031  */
2032 static void
2033 show_version(void)
2034 {
2035     printk("MVME166/167 cd2401 driver\n");
2036 } /* show_version */
2037
2038 /* initialize chips on card -- return number of valid
2039    chips (which is number of ports/4) */
2040
2041 /*
2042  * This initialises the hardware to a reasonable state.  It should
2043  * probe the chip first so as to copy 166-Bug setup as a default for
2044  * port 0.  It initialises CMR to CyASYNC; that is never done again, so
2045  * as to limit the number of CyINIT_CHAN commands in normal running.
2046  *
2047  * ... I wonder what I should do if this fails ...
2048  */
2049
2050 void
2051 mvme167_serial_console_setup(int cflag)
2052 {
2053         volatile unsigned char* base_addr = (u_char *)BASE_ADDR;
2054         int ch;
2055         u_char spd;
2056         u_char rcor, rbpr, badspeed = 0;
2057         unsigned long flags;
2058
2059         local_irq_save(flags);
2060
2061         /*
2062          * First probe channel zero of the chip, to see what speed has
2063          * been selected.
2064          */
2065
2066         base_addr[CyCAR] = 0;
2067
2068         rcor = base_addr[CyRCOR] << 5;
2069         rbpr = base_addr[CyRBPR];
2070
2071         for (spd = 0; spd < sizeof(baud_bpr); spd++)
2072                 if (rbpr == baud_bpr[spd] && rcor == baud_co[spd])
2073                         break;
2074         if (spd >= sizeof(baud_bpr)) {
2075                 spd = 14;       /* 19200 */
2076                 badspeed = 1;   /* Failed to identify speed */
2077         }
2078         initial_console_speed = spd;
2079
2080         /* OK, we have chosen a speed, now reset and reinitialise */
2081
2082         my_udelay(20000L);      /* Allow time for any active o/p to complete */
2083         if(base_addr[CyCCR] != 0x00){
2084             local_irq_restore(flags);
2085             /* printk(" chip is never idle (CCR != 0)\n"); */
2086             return;
2087         }
2088
2089         base_addr[CyCCR] = CyCHIP_RESET;        /* Reset the chip */
2090         my_udelay(1000L);
2091
2092         if(base_addr[CyGFRCR] == 0x00){
2093             local_irq_restore(flags);
2094             /* printk(" chip is not responding (GFRCR stayed 0)\n"); */
2095             return;
2096         }
2097
2098         /*
2099          * System clock is 20Mhz, divided by 2048, so divide by 10 for a 1.0ms
2100          * tick
2101          */
2102
2103         base_addr[CyTPR] = 10;
2104
2105         base_addr[CyPILR1] = 0x01;    /* Interrupt level for modem change */
2106         base_addr[CyPILR2] = 0x02;    /* Interrupt level for tx ints */
2107         base_addr[CyPILR3] = 0x03;    /* Interrupt level for rx ints */
2108
2109         /*
2110          * Attempt to set up all channels to something reasonable, and
2111          * bang out a INIT_CHAN command.  We should then be able to limit
2112          * the ammount of fiddling we have to do in normal running.
2113          */
2114
2115         for (ch = 3; ch >= 0 ; ch--) {
2116                 base_addr[CyCAR] = (u_char)ch;
2117                 base_addr[CyIER] = 0;
2118                 base_addr[CyCMR] = CyASYNC;
2119                 base_addr[CyLICR] = (u_char)ch << 2;
2120                 base_addr[CyLIVR] = 0x5c;
2121                 base_addr[CyTCOR] = baud_co[spd];
2122                 base_addr[CyTBPR] = baud_bpr[spd];
2123                 base_addr[CyRCOR] = baud_co[spd] >> 5;
2124                 base_addr[CyRBPR] = baud_bpr[spd];
2125                 base_addr[CySCHR1] = 'Q' & 0x1f;
2126                 base_addr[CySCHR2] = 'X' & 0x1f;
2127                 base_addr[CySCRL] = 0;
2128                 base_addr[CySCRH] = 0;
2129                 base_addr[CyCOR1] = Cy_8_BITS | CyPARITY_NONE;
2130                 base_addr[CyCOR2] = 0;
2131                 base_addr[CyCOR3] = Cy_1_STOP;
2132                 base_addr[CyCOR4] = baud_cor4[spd];
2133                 base_addr[CyCOR5] = 0;
2134                 base_addr[CyCOR6] = 0;
2135                 base_addr[CyCOR7] = 0;
2136                 base_addr[CyRTPRL] = 2;
2137                 base_addr[CyRTPRH] = 0;
2138                 base_addr[CyMSVR1] = 0;
2139                 base_addr[CyMSVR2] = 0;
2140                 write_cy_cmd(base_addr,CyINIT_CHAN|CyDIS_RCVR|CyDIS_XMTR);
2141         }
2142
2143         /*
2144          * Now do specials for channel zero....
2145          */
2146
2147         base_addr[CyMSVR1] = CyRTS;
2148         base_addr[CyMSVR2] = CyDTR;
2149         base_addr[CyIER] = CyRxData;
2150         write_cy_cmd(base_addr,CyENB_RCVR|CyENB_XMTR);
2151
2152         local_irq_restore(flags);
2153
2154         my_udelay(20000L);      /* Let it all settle down */
2155
2156         printk("CD2401 initialised,  chip is rev 0x%02x\n", base_addr[CyGFRCR]);
2157         if (badspeed)
2158                 printk("  WARNING:  Failed to identify line speed, rcor=%02x,rbpr=%02x\n",
2159                                         rcor >> 5, rbpr);
2160 } /* serial_console_init */
2161
2162 static struct tty_operations cy_ops = {
2163         .open = cy_open,
2164         .close = cy_close,
2165         .write = cy_write,
2166         .put_char = cy_put_char,
2167         .flush_chars = cy_flush_chars,
2168         .write_room = cy_write_room,
2169         .chars_in_buffer = cy_chars_in_buffer,
2170         .flush_buffer = cy_flush_buffer,
2171         .ioctl = cy_ioctl,
2172         .throttle = cy_throttle,
2173         .unthrottle = cy_unthrottle,
2174         .set_termios = cy_set_termios,
2175         .stop = cy_stop,
2176         .start = cy_start,
2177         .hangup = cy_hangup,
2178         .tiocmget = cy_tiocmget,
2179         .tiocmset = cy_tiocmset,
2180 };
2181 /* The serial driver boot-time initialization code!
2182     Hardware I/O ports are mapped to character special devices on a
2183     first found, first allocated manner.  That is, this code searches
2184     for Cyclom cards in the system.  As each is found, it is probed
2185     to discover how many chips (and thus how many ports) are present.
2186     These ports are mapped to the tty ports 64 and upward in monotonic
2187     fashion.  If an 8-port card is replaced with a 16-port card, the
2188     port mapping on a following card will shift.
2189
2190     This approach is different from what is used in the other serial
2191     device driver because the Cyclom is more properly a multiplexer,
2192     not just an aggregation of serial ports on one card.
2193
2194     If there are more cards with more ports than have been statically
2195     allocated above, a warning is printed and the extra ports are ignored.
2196  */
2197 static int __init
2198 serial167_init(void)
2199 {
2200   struct cyclades_port *info;
2201   int ret = 0;
2202   int good_ports = 0;
2203   int port_num = 0;
2204   int index;
2205   int DefSpeed;
2206 #ifdef notyet
2207   struct sigaction sa;
2208 #endif
2209
2210     if (!(mvme16x_config &MVME16x_CONFIG_GOT_CD2401))
2211         return 0;
2212
2213     cy_serial_driver = alloc_tty_driver(NR_PORTS);
2214     if (!cy_serial_driver)
2215         return -ENOMEM;
2216
2217 #if 0
2218 scrn[1] = '\0';
2219 #endif
2220
2221     show_version();
2222
2223     /* Has "console=0,9600n8" been used in bootinfo to change speed? */
2224     if (serial_console_cflag)
2225         DefSpeed = serial_console_cflag & 0017;
2226     else {
2227         DefSpeed = initial_console_speed;
2228         serial_console_info = &cy_port[0];
2229         serial_console_cflag = DefSpeed | CS8;
2230 #if 0
2231         serial_console = 64; /*callout_driver.minor_start*/
2232 #endif
2233     }
2234
2235     /* Initialize the tty_driver structure */
2236     
2237     cy_serial_driver->owner = THIS_MODULE;
2238     cy_serial_driver->devfs_name = "tts/";
2239     cy_serial_driver->name = "ttyS";
2240     cy_serial_driver->major = TTY_MAJOR;
2241     cy_serial_driver->minor_start = 64;
2242     cy_serial_driver->type = TTY_DRIVER_TYPE_SERIAL;
2243     cy_serial_driver->subtype = SERIAL_TYPE_NORMAL;
2244     cy_serial_driver->init_termios = tty_std_termios;
2245     cy_serial_driver->init_termios.c_cflag =
2246             B9600 | CS8 | CREAD | HUPCL | CLOCAL;
2247     cy_serial_driver->flags = TTY_DRIVER_REAL_RAW;
2248     tty_set_operations(cy_serial_driver, &cy_ops);
2249
2250     ret = tty_register_driver(cy_serial_driver);
2251     if (ret) {
2252             printk(KERN_ERR "Couldn't register MVME166/7 serial driver\n");
2253             put_tty_driver(cy_serial_driver);
2254             return ret;
2255     }
2256
2257     port_num = 0;
2258     info = cy_port;
2259     for (index = 0; index < 1; index++) {
2260
2261         good_ports = 4;
2262
2263         if(port_num < NR_PORTS){
2264             while( good_ports-- && port_num < NR_PORTS){
2265                 /*** initialize port ***/
2266                 info->magic = CYCLADES_MAGIC;
2267                 info->type = PORT_CIRRUS;
2268                 info->card = index;
2269                 info->line = port_num;
2270                 info->flags = STD_COM_FLAGS;
2271                 info->tty = 0;
2272                 info->xmit_fifo_size = 12;
2273                 info->cor1 = CyPARITY_NONE|Cy_8_BITS;
2274                 info->cor2 = CyETC;
2275                 info->cor3 = Cy_1_STOP;
2276                 info->cor4 = 0x08; /* _very_ small receive threshold */
2277                 info->cor5 = 0;
2278                 info->cor6 = 0;
2279                 info->cor7 = 0;
2280                 info->tbpr = baud_bpr[DefSpeed]; /* Tx BPR */
2281                 info->tco = baud_co[DefSpeed]; /* Tx CO */
2282                 info->rbpr = baud_bpr[DefSpeed]; /* Rx BPR */
2283                 info->rco = baud_co[DefSpeed] >> 5; /* Rx CO */
2284                 info->close_delay = 0;
2285                 info->x_char = 0;
2286                 info->event = 0;
2287                 info->count = 0;
2288 #ifdef SERIAL_DEBUG_COUNT
2289     printk("cyc: %d: setting count to 0\n", __LINE__);
2290 #endif
2291                 info->blocked_open = 0;
2292                 info->default_threshold = 0;
2293                 info->default_timeout = 0;
2294                 INIT_WORK(&info->tqueue, do_softint, info);
2295                 init_waitqueue_head(&info->open_wait);
2296                 init_waitqueue_head(&info->close_wait);
2297                 /* info->session */
2298                 /* info->pgrp */
2299 /*** !!!!!!!! this may expose new bugs !!!!!!!!! *********/
2300                 info->read_status_mask = CyTIMEOUT| CySPECHAR| CyBREAK
2301                                        | CyPARITY| CyFRAME| CyOVERRUN;
2302                 /* info->timeout */
2303
2304                 printk("ttyS%d ", info->line);
2305                 port_num++;info++;
2306                 if(!(port_num & 7)){
2307                     printk("\n               ");
2308                 }
2309             }
2310         }
2311         printk("\n");
2312     }
2313     while( port_num < NR_PORTS){
2314         info->line = -1;
2315         port_num++;info++;
2316     }
2317 #ifdef CONFIG_REMOTE_DEBUG
2318     debug_setup();
2319 #endif
2320     ret = request_irq(MVME167_IRQ_SER_ERR, cd2401_rxerr_interrupt, 0,
2321                                 "cd2401_errors", cd2401_rxerr_interrupt);
2322     if (ret) {
2323             printk(KERN_ERR "Could't get cd2401_errors IRQ");
2324             goto cleanup_serial_driver;
2325     }
2326
2327     ret = request_irq(MVME167_IRQ_SER_MODEM, cd2401_modem_interrupt, 0,
2328                                 "cd2401_modem", cd2401_modem_interrupt);
2329     if (ret) {
2330             printk(KERN_ERR "Could't get cd2401_modem IRQ");
2331             goto cleanup_irq_cd2401_errors;
2332     }
2333
2334     ret = request_irq(MVME167_IRQ_SER_TX, cd2401_tx_interrupt, 0,
2335                                 "cd2401_txints", cd2401_tx_interrupt);
2336     if (ret) {
2337             printk(KERN_ERR "Could't get cd2401_txints IRQ");
2338             goto cleanup_irq_cd2401_modem;
2339     }
2340
2341     ret = request_irq(MVME167_IRQ_SER_RX, cd2401_rx_interrupt, 0,
2342                                 "cd2401_rxints", cd2401_rx_interrupt);
2343     if (ret) {
2344             printk(KERN_ERR "Could't get cd2401_rxints IRQ");
2345             goto cleanup_irq_cd2401_txints;
2346     }
2347
2348     /* Now we have registered the interrupt handlers, allow the interrupts */
2349
2350     pcc2chip[PccSCCMICR] = 0x15;                /* Serial ints are level 5 */
2351     pcc2chip[PccSCCTICR] = 0x15;
2352     pcc2chip[PccSCCRICR] = 0x15;
2353
2354     pcc2chip[PccIMLR] = 3;                      /* Allow PCC2 ints above 3!? */
2355
2356     return 0;
2357 cleanup_irq_cd2401_txints:
2358     free_irq(MVME167_IRQ_SER_TX, cd2401_tx_interrupt);
2359 cleanup_irq_cd2401_modem:
2360     free_irq(MVME167_IRQ_SER_MODEM, cd2401_modem_interrupt);
2361 cleanup_irq_cd2401_errors:
2362     free_irq(MVME167_IRQ_SER_ERR, cd2401_rxerr_interrupt);
2363 cleanup_serial_driver:
2364     if (tty_unregister_driver(cy_serial_driver))
2365             printk(KERN_ERR "Couldn't unregister MVME166/7 serial driver\n");
2366     put_tty_driver(cy_serial_driver);
2367     return ret;
2368 } /* serial167_init */
2369
2370 module_init(serial167_init);
2371
2372
2373 #ifdef CYCLOM_SHOW_STATUS
2374 static void
2375 show_status(int line_num)
2376 {
2377   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
2378   int channel;
2379   struct cyclades_port * info;
2380   unsigned long flags;
2381
2382     info = &cy_port[line_num];
2383     channel = info->line;
2384     printk("  channel %d\n", channel);/**/
2385
2386     printk(" cy_port\n");
2387     printk("  card line flags = %d %d %x\n",
2388                  info->card, info->line, info->flags);
2389     printk("  *tty read_status_mask timeout xmit_fifo_size = %lx %x %x %x\n",
2390                  (long)info->tty, info->read_status_mask,
2391                  info->timeout, info->xmit_fifo_size);
2392     printk("  cor1,cor2,cor3,cor4,cor5,cor6,cor7 = %x %x %x %x %x %x %x\n",
2393              info->cor1, info->cor2, info->cor3, info->cor4, info->cor5,
2394                         info->cor6, info->cor7);
2395     printk("  tbpr,tco,rbpr,rco = %d %d %d %d\n",
2396              info->tbpr, info->tco, info->rbpr, info->rco);
2397     printk("  close_delay event count = %d %d %d\n",
2398              info->close_delay, info->event, info->count);
2399     printk("  x_char blocked_open = %x %x\n",
2400              info->x_char, info->blocked_open);
2401     printk("  open_wait = %lx %lx %lx\n",
2402              (long)info->open_wait);
2403
2404
2405     local_irq_save(flags);
2406
2407 /* Global Registers */
2408
2409         printk(" CyGFRCR %x\n", base_addr[CyGFRCR]);
2410         printk(" CyCAR %x\n", base_addr[CyCAR]);
2411         printk(" CyRISR %x\n", base_addr[CyRISR]);
2412         printk(" CyTISR %x\n", base_addr[CyTISR]);
2413         printk(" CyMISR %x\n", base_addr[CyMISR]);
2414         printk(" CyRIR %x\n", base_addr[CyRIR]);
2415         printk(" CyTIR %x\n", base_addr[CyTIR]);
2416         printk(" CyMIR %x\n", base_addr[CyMIR]);
2417         printk(" CyTPR %x\n", base_addr[CyTPR]);
2418
2419         base_addr[CyCAR] = (u_char)channel;
2420
2421 /* Virtual Registers */
2422
2423 #if 0
2424         printk(" CyRIVR %x\n", base_addr[CyRIVR]);
2425         printk(" CyTIVR %x\n", base_addr[CyTIVR]);
2426         printk(" CyMIVR %x\n", base_addr[CyMIVR]);
2427         printk(" CyMISR %x\n", base_addr[CyMISR]);
2428 #endif
2429
2430 /* Channel Registers */
2431
2432         printk(" CyCCR %x\n", base_addr[CyCCR]);
2433         printk(" CyIER %x\n", base_addr[CyIER]);
2434         printk(" CyCOR1 %x\n", base_addr[CyCOR1]);
2435         printk(" CyCOR2 %x\n", base_addr[CyCOR2]);
2436         printk(" CyCOR3 %x\n", base_addr[CyCOR3]);
2437         printk(" CyCOR4 %x\n", base_addr[CyCOR4]);
2438         printk(" CyCOR5 %x\n", base_addr[CyCOR5]);
2439 #if 0
2440         printk(" CyCCSR %x\n", base_addr[CyCCSR]);
2441         printk(" CyRDCR %x\n", base_addr[CyRDCR]);
2442 #endif
2443         printk(" CySCHR1 %x\n", base_addr[CySCHR1]);
2444         printk(" CySCHR2 %x\n", base_addr[CySCHR2]);
2445 #if 0
2446         printk(" CySCHR3 %x\n", base_addr[CySCHR3]);
2447         printk(" CySCHR4 %x\n", base_addr[CySCHR4]);
2448         printk(" CySCRL %x\n", base_addr[CySCRL]);
2449         printk(" CySCRH %x\n", base_addr[CySCRH]);
2450         printk(" CyLNC %x\n", base_addr[CyLNC]);
2451         printk(" CyMCOR1 %x\n", base_addr[CyMCOR1]);
2452         printk(" CyMCOR2 %x\n", base_addr[CyMCOR2]);
2453 #endif
2454         printk(" CyRTPRL %x\n", base_addr[CyRTPRL]);
2455         printk(" CyRTPRH %x\n", base_addr[CyRTPRH]);
2456         printk(" CyMSVR1 %x\n", base_addr[CyMSVR1]);
2457         printk(" CyMSVR2 %x\n", base_addr[CyMSVR2]);
2458         printk(" CyRBPR %x\n", base_addr[CyRBPR]);
2459         printk(" CyRCOR %x\n", base_addr[CyRCOR]);
2460         printk(" CyTBPR %x\n", base_addr[CyTBPR]);
2461         printk(" CyTCOR %x\n", base_addr[CyTCOR]);
2462
2463     local_irq_restore(flags);
2464 } /* show_status */
2465 #endif
2466
2467
2468 #if 0
2469 /* Dummy routine in mvme16x/config.c for now */
2470
2471 /* Serial console setup. Called from linux/init/main.c */
2472
2473 void console_setup(char *str, int *ints)
2474 {
2475         char *s;
2476         int baud, bits, parity;
2477         int cflag = 0;
2478
2479         /* Sanity check. */
2480         if (ints[0] > 3 || ints[1] > 3) return;
2481
2482         /* Get baud, bits and parity */
2483         baud = 2400;
2484         bits = 8;
2485         parity = 'n';
2486         if (ints[2]) baud = ints[2];
2487         if ((s = strchr(str, ','))) {
2488                 do {
2489                         s++;
2490                 } while(*s >= '0' && *s <= '9');
2491                 if (*s) parity = *s++;
2492                 if (*s) bits   = *s - '0';
2493         }
2494
2495         /* Now construct a cflag setting. */
2496         switch(baud) {
2497                 case 1200:
2498                         cflag |= B1200;
2499                         break;
2500                 case 9600:
2501                         cflag |= B9600;
2502                         break;
2503                 case 19200:
2504                         cflag |= B19200;
2505                         break;
2506                 case 38400:
2507                         cflag |= B38400;
2508                         break;
2509                 case 2400:
2510                 default:
2511                         cflag |= B2400;
2512                         break;
2513         }
2514         switch(bits) {
2515                 case 7:
2516                         cflag |= CS7;
2517                         break;
2518                 default:
2519                 case 8:
2520                         cflag |= CS8;
2521                         break;
2522         }
2523         switch(parity) {
2524                 case 'o': case 'O':
2525                         cflag |= PARODD;
2526                         break;
2527                 case 'e': case 'E':
2528                         cflag |= PARENB;
2529                         break;
2530         }
2531
2532         serial_console_info = &cy_port[ints[1]];
2533         serial_console_cflag = cflag;
2534         serial_console = ints[1] + 64; /*callout_driver.minor_start*/
2535 }
2536 #endif
2537
2538 /*
2539  * The following is probably out of date for 2.1.x serial console stuff.
2540  *
2541  * The console is registered early on from arch/m68k/kernel/setup.c, and
2542  * it therefore relies on the chip being setup correctly by 166-Bug.  This
2543  * seems reasonable, as the serial port has been used to invoke the system
2544  * boot.  It also means that this function must not rely on any data
2545  * initialisation performed by serial167_init() etc.
2546  *
2547  * Of course, once the console has been registered, we had better ensure
2548  * that serial167_init() doesn't leave the chip non-functional.
2549  *
2550  * The console must be locked when we get here.
2551  */
2552
2553 void serial167_console_write(struct console *co, const char *str, unsigned count)
2554 {
2555         volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
2556         unsigned long flags;
2557         volatile u_char sink;
2558         u_char ier;
2559         int port;
2560         u_char do_lf = 0;
2561         int i = 0;
2562
2563         local_irq_save(flags);
2564
2565         /* Ensure transmitter is enabled! */
2566
2567         port = 0;
2568         base_addr[CyCAR] = (u_char)port;
2569         while (base_addr[CyCCR])
2570                 ;
2571         base_addr[CyCCR] = CyENB_XMTR;
2572
2573         ier = base_addr[CyIER];
2574         base_addr[CyIER] = CyTxMpty;
2575
2576         while (1) {
2577                 if (pcc2chip[PccSCCTICR] & 0x20)
2578                 {
2579                         /* We have a Tx int. Acknowledge it */
2580                         sink = pcc2chip[PccTPIACKR];
2581                         if ((base_addr[CyLICR] >> 2) == port) {
2582                                 if (i == count) {
2583                                         /* Last char of string is now output */
2584                                         base_addr[CyTEOIR] = CyNOTRANS;
2585                                         break;
2586                                 }
2587                                 if (do_lf) {
2588                                         base_addr[CyTDR] = '\n';
2589                                         str++;
2590                                         i++;
2591                                         do_lf = 0;
2592                                 }
2593                                 else if (*str == '\n') {
2594                                         base_addr[CyTDR] = '\r';
2595                                         do_lf = 1;
2596                                 }
2597                                 else {
2598                                         base_addr[CyTDR] = *str++;
2599                                         i++;
2600                                 }
2601                                 base_addr[CyTEOIR] = 0;
2602                         }
2603                         else
2604                                 base_addr[CyTEOIR] = CyNOTRANS;
2605                 }
2606         }
2607
2608         base_addr[CyIER] = ier;
2609
2610         local_irq_restore(flags);
2611 }
2612
2613 static struct tty_driver *serial167_console_device(struct console *c, int *index)
2614 {
2615         *index = c->index;
2616         return cy_serial_driver;
2617 }
2618
2619
2620 static int __init serial167_console_setup(struct console *co, char *options)
2621 {
2622         return 0;
2623 }
2624
2625
2626 static struct console sercons = {
2627         .name           = "ttyS",
2628         .write          = serial167_console_write,
2629         .device         = serial167_console_device,
2630         .setup          = serial167_console_setup,
2631         .flags          = CON_PRINTBUFFER,
2632         .index          = -1,
2633 };
2634
2635
2636 static int __init serial167_console_init(void)
2637 {
2638         if (vme_brdtype == VME_TYPE_MVME166 ||
2639                         vme_brdtype == VME_TYPE_MVME167 ||
2640                         vme_brdtype == VME_TYPE_MVME177) {
2641                 mvme167_serial_console_setup(0);
2642                 register_console(&sercons);
2643         }
2644         return 0;
2645 }
2646 console_initcall(serial167_console_init);
2647
2648 #ifdef CONFIG_REMOTE_DEBUG
2649 void putDebugChar (int c)
2650 {
2651         volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
2652         unsigned long flags;
2653         volatile u_char sink;
2654         u_char ier;
2655         int port;
2656
2657         local_irq_save(flags);
2658
2659         /* Ensure transmitter is enabled! */
2660
2661         port = DEBUG_PORT;
2662         base_addr[CyCAR] = (u_char)port;
2663         while (base_addr[CyCCR])
2664                 ;
2665         base_addr[CyCCR] = CyENB_XMTR;
2666
2667         ier = base_addr[CyIER];
2668         base_addr[CyIER] = CyTxMpty;
2669
2670         while (1) {
2671                 if (pcc2chip[PccSCCTICR] & 0x20)
2672                 {
2673                         /* We have a Tx int. Acknowledge it */
2674                         sink = pcc2chip[PccTPIACKR];
2675                         if ((base_addr[CyLICR] >> 2) == port) {
2676                                 base_addr[CyTDR] = c;
2677                                 base_addr[CyTEOIR] = 0;
2678                                 break;
2679                         }
2680                         else
2681                                 base_addr[CyTEOIR] = CyNOTRANS;
2682                 }
2683         }
2684
2685         base_addr[CyIER] = ier;
2686
2687         local_irq_restore(flags);
2688 }
2689
2690 int getDebugChar()
2691 {
2692         volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
2693         unsigned long flags;
2694         volatile u_char sink;
2695         u_char ier;
2696         int port;
2697         int i, c;
2698
2699         i = debugiq.out;
2700         if (i != debugiq.in) {
2701                 c = debugiq.buf[i];
2702                 if (++i == DEBUG_LEN)
2703                         i = 0;
2704                 debugiq.out = i;
2705                 return c;
2706         }
2707         /* OK, nothing in queue, wait in poll loop */
2708
2709         local_irq_save(flags);
2710
2711         /* Ensure receiver is enabled! */
2712
2713         port = DEBUG_PORT;
2714         base_addr[CyCAR] = (u_char)port;
2715 #if 0
2716         while (base_addr[CyCCR])
2717                 ;
2718         base_addr[CyCCR] = CyENB_RCVR;
2719 #endif
2720         ier = base_addr[CyIER];
2721         base_addr[CyIER] = CyRxData;
2722
2723         while (1) {
2724                 if (pcc2chip[PccSCCRICR] & 0x20)
2725                 {
2726                         /* We have a Rx int. Acknowledge it */
2727                         sink = pcc2chip[PccRPIACKR];
2728                         if ((base_addr[CyLICR] >> 2) == port) {
2729                                 int cnt = base_addr[CyRFOC];
2730                                 while (cnt-- > 0)
2731                                 {
2732                                         c = base_addr[CyRDR];
2733                                         if (c == 0)
2734                                                 printk ("!! debug char is null (cnt=%d) !!", cnt);
2735                                         else
2736                                                 queueDebugChar (c);
2737                                 }
2738                                 base_addr[CyREOIR] = 0;
2739                                 i = debugiq.out;
2740                                 if (i == debugiq.in)
2741                                         panic ("Debug input queue empty!");
2742                                 c = debugiq.buf[i];
2743                                 if (++i == DEBUG_LEN)
2744                                         i = 0;
2745                                 debugiq.out = i;
2746                                 break;
2747                         }
2748                         else
2749                                 base_addr[CyREOIR] = CyNOTRANS;
2750                 }
2751         }
2752
2753         base_addr[CyIER] = ier;
2754
2755         local_irq_restore(flags);
2756
2757         return (c);
2758 }
2759
2760 void queueDebugChar (int c)
2761 {
2762         int i;
2763
2764         i = debugiq.in;
2765         debugiq.buf[i] = c;
2766         if (++i == DEBUG_LEN)
2767                 i = 0;
2768         if (i != debugiq.out)
2769                 debugiq.in = i;
2770 }
2771
2772 static void
2773 debug_setup()
2774 {
2775   unsigned long flags;
2776   volatile unsigned char *base_addr = (u_char *)BASE_ADDR;
2777   int   i, cflag;
2778
2779     cflag = B19200;
2780
2781     local_irq_save(flags);
2782
2783     for (i = 0; i < 4; i++)
2784     {
2785         base_addr[CyCAR] = i;
2786         base_addr[CyLICR] = i << 2;
2787     }
2788
2789     debugiq.in = debugiq.out = 0;
2790
2791     base_addr[CyCAR] = DEBUG_PORT;
2792
2793     /* baud rate */
2794     i = cflag & CBAUD;
2795
2796     base_addr[CyIER] = 0;
2797
2798     base_addr[CyCMR] = CyASYNC;
2799     base_addr[CyLICR] = DEBUG_PORT << 2;
2800     base_addr[CyLIVR] = 0x5c;
2801
2802     /* tx and rx baud rate */
2803
2804     base_addr[CyTCOR] = baud_co[i];
2805     base_addr[CyTBPR] = baud_bpr[i];
2806     base_addr[CyRCOR] = baud_co[i] >> 5;
2807     base_addr[CyRBPR] = baud_bpr[i];
2808
2809     /* set line characteristics  according configuration */
2810
2811     base_addr[CySCHR1] = 0;
2812     base_addr[CySCHR2] = 0;
2813     base_addr[CySCRL] = 0;
2814     base_addr[CySCRH] = 0;
2815     base_addr[CyCOR1] = Cy_8_BITS | CyPARITY_NONE;
2816     base_addr[CyCOR2] = 0;
2817     base_addr[CyCOR3] = Cy_1_STOP;
2818     base_addr[CyCOR4] = baud_cor4[i];
2819     base_addr[CyCOR5] = 0;
2820     base_addr[CyCOR6] = 0;
2821     base_addr[CyCOR7] = 0;
2822
2823     write_cy_cmd(base_addr,CyINIT_CHAN);
2824     write_cy_cmd(base_addr,CyENB_RCVR);
2825
2826     base_addr[CyCAR] = DEBUG_PORT; /* !!! Is this needed? */
2827
2828     base_addr[CyRTPRL] = 2;
2829     base_addr[CyRTPRH] = 0;
2830
2831     base_addr[CyMSVR1] = CyRTS;
2832     base_addr[CyMSVR2] = CyDTR;
2833
2834     base_addr[CyIER] = CyRxData;
2835
2836     local_irq_restore(flags);
2837
2838 } /* debug_setup */
2839
2840 #endif
2841
2842 MODULE_LICENSE("GPL");