linux 2.6.16.38 w/ vs2.0.3-rc1
[linux-2.6.git] / drivers / char / rio / riotty.c
1 /*
2 ** -----------------------------------------------------------------------------
3 **
4 **  Perle Specialix driver for Linux
5 **  Ported from existing RIO Driver for SCO sources.
6  *
7  *  (C) 1990 - 2000 Specialix International Ltd., Byfleet, Surrey, UK.
8  *
9  *      This program is free software; you can redistribute it and/or modify
10  *      it under the terms of the GNU General Public License as published by
11  *      the Free Software Foundation; either version 2 of the License, or
12  *      (at your option) any later version.
13  *
14  *      This program is distributed in the hope that it will be useful,
15  *      but WITHOUT ANY WARRANTY; without even the implied warranty of
16  *      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  *      GNU General Public License for more details.
18  *
19  *      You should have received a copy of the GNU General Public License
20  *      along with this program; if not, write to the Free Software
21  *      Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 **
23 **      Module          : riotty.c
24 **      SID             : 1.3
25 **      Last Modified   : 11/6/98 10:33:47
26 **      Retrieved       : 11/6/98 10:33:50
27 **
28 **  ident @(#)riotty.c  1.3
29 **
30 ** -----------------------------------------------------------------------------
31 */
32 #ifdef SCCS_LABELS
33 static char *_riotty_c_sccs_ = "@(#)riotty.c    1.3";
34 #endif
35
36
37 #define __EXPLICIT_DEF_H__
38
39 #include <linux/module.h>
40 #include <linux/slab.h>
41 #include <linux/errno.h>
42 #include <linux/tty.h>
43 #include <linux/string.h>
44 #include <asm/io.h>
45 #include <asm/system.h>
46 #include <asm/string.h>
47 #include <asm/semaphore.h>
48 #include <asm/uaccess.h>
49
50 #include <linux/termios.h>
51
52 #include <linux/serial.h>
53
54 #include <linux/generic_serial.h>
55
56
57 #include "linux_compat.h"
58 #include "rio_linux.h"
59 #include "typdef.h"
60 #include "pkt.h"
61 #include "daemon.h"
62 #include "rio.h"
63 #include "riospace.h"
64 #include "top.h"
65 #include "cmdpkt.h"
66 #include "map.h"
67 #include "riotypes.h"
68 #include "rup.h"
69 #include "port.h"
70 #include "riodrvr.h"
71 #include "rioinfo.h"
72 #include "func.h"
73 #include "errors.h"
74 #include "pci.h"
75
76 #include "parmmap.h"
77 #include "unixrup.h"
78 #include "board.h"
79 #include "host.h"
80 #include "error.h"
81 #include "phb.h"
82 #include "link.h"
83 #include "cmdblk.h"
84 #include "route.h"
85 #include "control.h"
86 #include "cirrus.h"
87 #include "rioioctl.h"
88 #include "param.h"
89 #include "list.h"
90 #include "sam.h"
91
92 static void RIOClearUp(struct Port *PortP);
93 int RIOShortCommand(struct rio_info *p, struct Port *PortP, int command, int len, int arg);
94
95
96 extern int conv_vb[];           /* now defined in ttymgr.c */
97 extern int conv_bv[];           /* now defined in ttymgr.c */
98
99 /*
100 ** 16.09.1998 ARG - Fix to build riotty.k.o for Modular Kernel Support
101 **
102 ** ep.def.h is necessary for Modular Kernel Support
103 ** DO NOT place any kernel 'extern's after this line
104 ** or this source file will not build riotty.k.o
105 */
106 #ifdef uLYNX
107 #include <ep.def.h>
108 #endif
109
110 #ifdef NEED_THIS2
111 static struct old_sgttyb default_sg = {
112         B19200, B19200,         /* input and output speed */
113         'H' - '@',              /* erase char */
114         -1,                     /* 2nd erase char */
115         'U' - '@',              /* kill char */
116         ECHO | CRMOD,           /* mode */
117         'C' - '@',              /* interrupt character */
118         '\\' - '@',             /* quit char */
119         'Q' - '@',              /* start char */
120         'S' - '@',              /* stop char */
121         'D' - '@',              /* EOF */
122         -1,                     /* brk */
123         (LCRTBS | LCRTERA | LCRTKIL | LCTLECH), /* local mode word */
124         'Z' - '@',              /* process stop */
125         'Y' - '@',              /* delayed stop */
126         'R' - '@',              /* reprint line */
127         'O' - '@',              /* flush output */
128         'W' - '@',              /* word erase */
129         'V' - '@'               /* literal next char */
130 };
131 #endif
132
133
134 extern struct rio_info *p;
135
136
137 int riotopen(struct tty_struct *tty, struct file *filp)
138 {
139         register uint SysPort;
140         int Modem;
141         int repeat_this = 250;
142         struct Port *PortP;     /* pointer to the port structure */
143         unsigned long flags;
144         int retval = 0;
145
146         func_enter();
147
148         /* Make sure driver_data is NULL in case the rio isn't booted jet. Else gs_close
149            is going to oops.
150          */
151         tty->driver_data = NULL;
152
153         SysPort = rio_minor(tty);
154         Modem = rio_ismodem(tty);
155
156         if (p->RIOFailed) {
157                 rio_dprintk(RIO_DEBUG_TTY, "System initialisation failed\n");
158                 pseterr(ENXIO);
159                 func_exit();
160                 return -ENXIO;
161         }
162
163         rio_dprintk(RIO_DEBUG_TTY, "port open SysPort %d (%s) (mapped:%d)\n", SysPort, Modem ? "Modem" : "tty", p->RIOPortp[SysPort]->Mapped);
164
165         /*
166          ** Validate that we have received a legitimate request.
167          ** Currently, just check that we are opening a port on
168          ** a host card that actually exists, and that the port
169          ** has been mapped onto a host.
170          */
171         if (SysPort >= RIO_PORTS) {     /* out of range ? */
172                 rio_dprintk(RIO_DEBUG_TTY, "Illegal port number %d\n", SysPort);
173                 pseterr(ENXIO);
174                 func_exit();
175                 return -ENXIO;
176         }
177
178         /*
179          ** Grab pointer to the port stucture
180          */
181         PortP = p->RIOPortp[SysPort];   /* Get control struc */
182         rio_dprintk(RIO_DEBUG_TTY, "PortP: %p\n", PortP);
183         if (!PortP->Mapped) {   /* we aren't mapped yet! */
184                 /*
185                  ** The system doesn't know which RTA this port
186                  ** corresponds to.
187                  */
188                 rio_dprintk(RIO_DEBUG_TTY, "port not mapped into system\n");
189                 func_exit();
190                 pseterr(ENXIO);
191                 return -ENXIO;
192         }
193
194         tty->driver_data = PortP;
195
196         PortP->gs.tty = tty;
197         PortP->gs.count++;
198
199         rio_dprintk(RIO_DEBUG_TTY, "%d bytes in tx buffer\n", PortP->gs.xmit_cnt);
200
201         retval = gs_init_port(&PortP->gs);
202         if (retval) {
203                 PortP->gs.count--;
204                 return -ENXIO;
205         }
206         /*
207          ** If the host hasn't been booted yet, then
208          ** fail
209          */
210         if ((PortP->HostP->Flags & RUN_STATE) != RC_RUNNING) {
211                 rio_dprintk(RIO_DEBUG_TTY, "Host not running\n");
212                 pseterr(ENXIO);
213                 func_exit();
214                 return -ENXIO;
215         }
216
217         /*
218          ** If the RTA has not booted yet and the user has choosen to block
219          ** until the RTA is present then we must spin here waiting for
220          ** the RTA to boot.
221          */
222         /* I find the above code a bit hairy. I find the below code
223            easier to read and shorter. Now, if it works too that would
224            be great... -- REW 
225          */
226         rio_dprintk(RIO_DEBUG_TTY, "Checking if RTA has booted... \n");
227         while (!(PortP->HostP->Mapping[PortP->RupNum].Flags & RTA_BOOTED)) {
228                 if (!PortP->WaitUntilBooted) {
229                         rio_dprintk(RIO_DEBUG_TTY, "RTA never booted\n");
230                         func_exit();
231                         return -ENXIO;
232                 }
233
234                 /* Under Linux you'd normally use a wait instead of this
235                    busy-waiting. I'll stick with the old implementation for
236                    now. --REW
237                  */
238                 if (RIODelay(PortP, HUNDRED_MS) == RIO_FAIL) {
239                         rio_dprintk(RIO_DEBUG_TTY, "RTA_wait_for_boot: EINTR in delay \n");
240                         func_exit();
241                         return -EINTR;
242                 }
243                 if (repeat_this-- <= 0) {
244                         rio_dprintk(RIO_DEBUG_TTY, "Waiting for RTA to boot timeout\n");
245                         func_exit();
246                         return -EIO;
247                 }
248         }
249         rio_dprintk(RIO_DEBUG_TTY, "RTA has been booted\n");
250         rio_spin_lock_irqsave(&PortP->portSem, flags);
251         if (p->RIOHalted) {
252                 goto bombout;
253         }
254
255         /*
256          ** If the port is in the final throws of being closed,
257          ** we should wait here (politely), waiting
258          ** for it to finish, so that it doesn't close us!
259          */
260         while ((PortP->State & RIO_CLOSING) && !p->RIOHalted) {
261                 rio_dprintk(RIO_DEBUG_TTY, "Waiting for RIO_CLOSING to go away\n");
262                 if (repeat_this-- <= 0) {
263                         rio_dprintk(RIO_DEBUG_TTY, "Waiting for not idle closed broken by signal\n");
264                         RIOPreemptiveCmd(p, PortP, FCLOSE);
265                         retval = -EINTR;
266                         goto bombout;
267                 }
268                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
269                 if (RIODelay(PortP, HUNDRED_MS) == RIO_FAIL) {
270                         rio_spin_lock_irqsave(&PortP->portSem, flags);
271                         retval = -EINTR;
272                         goto bombout;
273                 }
274                 rio_spin_lock_irqsave(&PortP->portSem, flags);
275         }
276
277         if (!PortP->Mapped) {
278                 rio_dprintk(RIO_DEBUG_TTY, "Port unmapped while closing!\n");
279                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
280                 retval = -ENXIO;
281                 func_exit();
282                 return retval;
283         }
284
285         if (p->RIOHalted) {
286                 goto bombout;
287         }
288
289 /*
290 ** 15.10.1998 ARG - ESIL 0761 part fix
291 ** RIO has it's own CTSFLOW and RTSFLOW flags in 'Config' in the port structure,
292 ** we need to make sure that the flags are clear when the port is opened.
293 */
294         /* Uh? Suppose I turn these on and then another process opens
295            the port again? The flags get cleared! Not good. -- REW */
296         if (!(PortP->State & (RIO_LOPEN | RIO_MOPEN))) {
297                 PortP->Config &= ~(RIO_CTSFLOW | RIO_RTSFLOW);
298         }
299
300         if (!(PortP->firstOpen)) {      /* First time ? */
301                 rio_dprintk(RIO_DEBUG_TTY, "First open for this port\n");
302
303
304                 PortP->firstOpen++;
305                 PortP->CookMode = 0;    /* XXX RIOCookMode(tp); */
306                 PortP->InUse = NOT_INUSE;
307
308                 /* Tentative fix for bug PR27. Didn't work. */
309                 /* PortP->gs.xmit_cnt = 0; */
310
311                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
312 #ifdef NEED_THIS
313                 ttyseth(PortP, tp, (struct old_sgttyb *) &default_sg);
314 #endif
315
316                 /* Someone explain to me why this delay/config is
317                    here. If I read the docs correctly the "open"
318                    command piggybacks the parameters immediately.
319                    -- REW */
320                 RIOParam(PortP, OPEN, Modem, OK_TO_SLEEP);      /* Open the port */
321                 rio_spin_lock_irqsave(&PortP->portSem, flags);
322
323                 /*
324                  ** wait for the port to be not closed.
325                  */
326                 while (!(PortP->PortState & PORT_ISOPEN) && !p->RIOHalted) {
327                         rio_dprintk(RIO_DEBUG_TTY, "Waiting for PORT_ISOPEN-currently %x\n", PortP->PortState);
328 /*
329 ** 15.10.1998 ARG - ESIL 0759
330 ** (Part) fix for port being trashed when opened whilst RTA "disconnected"
331 ** Take out the limited wait - now wait for ever or until user
332 ** bangs us out.
333 **
334                         if (repeat_this -- <= 0) {
335                                 rio_dprint(RIO_DEBUG_TTY, ("Waiting for open to finish timed out.\n"));
336                                 RIOPreemptiveCmd(p, PortP, FCLOSE ); 
337                                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
338                                 return -EINTR;
339                         }
340 **
341 */
342                         rio_spin_unlock_irqrestore(&PortP->portSem, flags);
343                         if (RIODelay(PortP, HUNDRED_MS) == RIO_FAIL) {
344                                 rio_dprintk(RIO_DEBUG_TTY, "Waiting for open to finish broken by signal\n");
345                                 RIOPreemptiveCmd(p, PortP, FCLOSE);
346                                 func_exit();
347                                 return -EINTR;
348                         }
349                         rio_spin_lock_irqsave(&PortP->portSem, flags);
350                 }
351
352                 if (p->RIOHalted) {
353                         retval = -EIO;
354                       bombout:
355                         /*                    RIOClearUp( PortP ); */
356                         rio_spin_unlock_irqrestore(&PortP->portSem, flags);
357                         return retval;
358                 }
359                 rio_dprintk(RIO_DEBUG_TTY, "PORT_ISOPEN found\n");
360         }
361 #ifdef MODEM_SUPPORT
362         if (Modem) {
363                 rio_dprintk(RIO_DEBUG_TTY, "Modem - test for carrier\n");
364                 /*
365                  ** ACTION
366                  ** insert test for carrier here. -- ???
367                  ** I already see that test here. What's the deal? -- REW
368                  */
369                 if ((PortP->gs.tty->termios->c_cflag & CLOCAL) || (PortP->ModemState & MSVR1_CD)) {
370                         rio_dprintk(RIO_DEBUG_TTY, "open(%d) Modem carr on\n", SysPort);
371                         /*
372                            tp->tm.c_state |= CARR_ON;
373                            wakeup((caddr_t) &tp->tm.c_canq);
374                          */
375                         PortP->State |= RIO_CARR_ON;
376                         wake_up_interruptible(&PortP->gs.open_wait);
377                 } else {        /* no carrier - wait for DCD */
378
379                         /*
380                            while (!(PortP->gs.tty->termios->c_state & CARR_ON) &&
381                            !(filp->f_flags & O_NONBLOCK) && !p->RIOHalted )
382                          */
383                         while (!(PortP->State & RIO_CARR_ON) && !(filp->f_flags & O_NONBLOCK) && !p->RIOHalted) {
384
385                                 rio_dprintk(RIO_DEBUG_TTY, "open(%d) sleeping for carr on\n", SysPort);
386                                 /*
387                                    PortP->gs.tty->termios->c_state |= WOPEN;
388                                  */
389                                 PortP->State |= RIO_WOPEN;
390                                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
391                                 if (RIODelay(PortP, HUNDRED_MS) == RIO_FAIL)
392                                         {
393                                                 /*
394                                                  ** ACTION: verify that this is a good thing
395                                                  ** to do here. -- ???
396                                                  ** I think it's OK. -- REW
397                                                  */
398                                                 rio_dprintk(RIO_DEBUG_TTY, "open(%d) sleeping for carr broken by signal\n", SysPort);
399                                                 RIOPreemptiveCmd(p, PortP, FCLOSE);
400                                                 /*
401                                                    tp->tm.c_state &= ~WOPEN;
402                                                  */
403                                                 PortP->State &= ~RIO_WOPEN;
404                                                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
405                                                 func_exit();
406                                                 return -EINTR;
407                                         }
408                         }
409                         PortP->State &= ~RIO_WOPEN;
410                 }
411                 if (p->RIOHalted)
412                         goto bombout;
413                 rio_dprintk(RIO_DEBUG_TTY, "Setting RIO_MOPEN\n");
414                 PortP->State |= RIO_MOPEN;
415         } else
416 #endif
417         {
418                 /*
419                  ** ACTION
420                  ** Direct line open - force carrier (will probably mean
421                  ** that sleeping Modem line fubar)
422                  */
423                 PortP->State |= RIO_LOPEN;
424         }
425
426         if (p->RIOHalted) {
427                 goto bombout;
428         }
429
430         rio_dprintk(RIO_DEBUG_TTY, "high level open done\n");
431
432 #ifdef STATS
433         PortP->Stat.OpenCnt++;
434 #endif
435         /*
436          ** Count opens for port statistics reporting
437          */
438         if (PortP->statsGather)
439                 PortP->opens++;
440
441         rio_spin_unlock_irqrestore(&PortP->portSem, flags);
442         rio_dprintk(RIO_DEBUG_TTY, "Returning from open\n");
443         func_exit();
444         return 0;
445 }
446
447 /*
448 ** RIOClose the port.
449 ** The operating system thinks that this is last close for the device.
450 ** As there are two interfaces to the port (Modem and tty), we need to
451 ** check that both are closed before we close the device.
452 */
453 int riotclose(void *ptr)
454 {
455         struct Port *PortP = ptr;       /* pointer to the port structure */
456         int deleted = 0;
457         int try = -1;           /* Disable the timeouts by setting them to -1 */
458         int repeat_this = -1;   /* Congrats to those having 15 years of
459                                    uptime! (You get to break the driver.) */
460         unsigned long end_time;
461         struct tty_struct *tty;
462         unsigned long flags;
463         int Modem;
464         int rv = 0;
465
466         rio_dprintk(RIO_DEBUG_TTY, "port close SysPort %d\n", PortP->PortNum);
467
468         /* PortP = p->RIOPortp[SysPort]; */
469         rio_dprintk(RIO_DEBUG_TTY, "Port is at address 0x%x\n", (int) PortP);
470         /* tp = PortP->TtyP; *//* Get tty */
471         tty = PortP->gs.tty;
472         rio_dprintk(RIO_DEBUG_TTY, "TTY is at address 0x%x\n", (int) tty);
473
474         if (PortP->gs.closing_wait)
475                 end_time = jiffies + PortP->gs.closing_wait;
476         else
477                 end_time = jiffies + MAX_SCHEDULE_TIMEOUT;
478
479         Modem = rio_ismodem(tty);
480         rio_spin_lock_irqsave(&PortP->portSem, flags);
481
482         /*
483          ** Setting this flag will make any process trying to open
484          ** this port block until we are complete closing it.
485          */
486         PortP->State |= RIO_CLOSING;
487
488         if ((PortP->State & RIO_DELETED)) {
489                 rio_dprintk(RIO_DEBUG_TTY, "Close on deleted RTA\n");
490                 deleted = 1;
491         }
492
493         if (p->RIOHalted) {
494                 RIOClearUp(PortP);
495                 rv = -EIO;
496                 goto close_end;
497         }
498
499         rio_dprintk(RIO_DEBUG_TTY, "Clear bits\n");
500         /*
501          ** clear the open bits for this device
502          */
503         PortP->State &= (Modem ? ~RIO_MOPEN : ~RIO_LOPEN);
504         PortP->State &= ~RIO_CARR_ON;
505         PortP->ModemState &= ~MSVR1_CD;
506         /*
507          ** If the device was open as both a Modem and a tty line
508          ** then we need to wimp out here, as the port has not really
509          ** been finally closed (gee, whizz!) The test here uses the
510          ** bit for the OTHER mode of operation, to see if THAT is
511          ** still active!
512          */
513         if ((PortP->State & (RIO_LOPEN | RIO_MOPEN))) {
514                 /*
515                  ** The port is still open for the other task -
516                  ** return, pretending that we are still active.
517                  */
518                 rio_dprintk(RIO_DEBUG_TTY, "Channel %d still open !\n", PortP->PortNum);
519                 PortP->State &= ~RIO_CLOSING;
520                 if (PortP->firstOpen)
521                         PortP->firstOpen--;
522                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
523                 return -EIO;
524         }
525
526         rio_dprintk(RIO_DEBUG_TTY, "Closing down - everything must go!\n");
527
528         PortP->State &= ~RIO_DYNOROD;
529
530         /*
531          ** This is where we wait for the port
532          ** to drain down before closing. Bye-bye....
533          ** (We never meant to do this)
534          */
535         rio_dprintk(RIO_DEBUG_TTY, "Timeout 1 starts\n");
536
537         if (!deleted)
538                 while ((PortP->InUse != NOT_INUSE) && !p->RIOHalted && (PortP->TxBufferIn != PortP->TxBufferOut)) {
539                         cprintf("Need to flush the ttyport\n");
540                         if (repeat_this-- <= 0) {
541                                 rv = -EINTR;
542                                 rio_dprintk(RIO_DEBUG_TTY, "Waiting for not idle closed broken by signal\n");
543                                 RIOPreemptiveCmd(p, PortP, FCLOSE);
544                                 goto close_end;
545                         }
546                         rio_dprintk(RIO_DEBUG_TTY, "Calling timeout to flush in closing\n");
547                         rio_spin_unlock_irqrestore(&PortP->portSem, flags);
548                         if (RIODelay_ni(PortP, HUNDRED_MS * 10) == RIO_FAIL) {
549                                 rio_dprintk(RIO_DEBUG_TTY, "RTA EINTR in delay \n");
550                                 rv = -EINTR;
551                                 rio_spin_lock_irqsave(&PortP->portSem, flags);
552                                 goto close_end;
553                         }
554                         rio_spin_lock_irqsave(&PortP->portSem, flags);
555                 }
556
557         PortP->TxBufferIn = PortP->TxBufferOut = 0;
558         repeat_this = 0xff;
559
560         PortP->InUse = 0;
561         if ((PortP->State & (RIO_LOPEN | RIO_MOPEN))) {
562                 /*
563                  ** The port has been re-opened for the other task -
564                  ** return, pretending that we are still active.
565                  */
566                 rio_dprintk(RIO_DEBUG_TTY, "Channel %d re-open!\n", PortP->PortNum);
567                 PortP->State &= ~RIO_CLOSING;
568                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
569                 if (PortP->firstOpen)
570                         PortP->firstOpen--;
571                 return -EIO;
572         }
573
574         if (p->RIOHalted) {
575                 RIOClearUp(PortP);
576                 goto close_end;
577         }
578
579         /* Can't call RIOShortCommand with the port locked. */
580         rio_spin_unlock_irqrestore(&PortP->portSem, flags);
581
582         if (RIOShortCommand(p, PortP, CLOSE, 1, 0) == RIO_FAIL) {
583                 RIOPreemptiveCmd(p, PortP, FCLOSE);
584                 goto close_end;
585         }
586
587         if (!deleted)
588                 while (try && (PortP->PortState & PORT_ISOPEN)) {
589                         try--;
590                         if (time_after(jiffies, end_time)) {
591                                 rio_dprintk(RIO_DEBUG_TTY, "Run out of tries - force the bugger shut!\n");
592                                 RIOPreemptiveCmd(p, PortP, FCLOSE);
593                                 break;
594                         }
595                         rio_dprintk(RIO_DEBUG_TTY, "Close: PortState:ISOPEN is %d\n", PortP->PortState & PORT_ISOPEN);
596
597                         if (p->RIOHalted) {
598                                 RIOClearUp(PortP);
599                                 goto close_end;
600                         }
601                         if (RIODelay(PortP, HUNDRED_MS) == RIO_FAIL) {
602                                 rio_dprintk(RIO_DEBUG_TTY, "RTA EINTR in delay \n");
603                                 RIOPreemptiveCmd(p, PortP, FCLOSE);
604                                 break;
605                         }
606                 }
607         rio_spin_lock_irqsave(&PortP->portSem, flags);
608         rio_dprintk(RIO_DEBUG_TTY, "Close: try was %d on completion\n", try);
609
610         /* RIOPreemptiveCmd(p, PortP, FCLOSE); */
611
612 /*
613 ** 15.10.1998 ARG - ESIL 0761 part fix
614 ** RIO has it's own CTSFLOW and RTSFLOW flags in 'Config' in the port structure,** we need to make sure that the flags are clear when the port is opened.
615 */
616         PortP->Config &= ~(RIO_CTSFLOW | RIO_RTSFLOW);
617
618 #ifdef STATS
619         PortP->Stat.CloseCnt++;
620 #endif
621         /*
622          ** Count opens for port statistics reporting
623          */
624         if (PortP->statsGather)
625                 PortP->closes++;
626
627       close_end:
628         /* XXX: Why would a "DELETED" flag be reset here? I'd have
629            thought that a "deleted" flag means that the port was
630            permanently gone, but here we can make it reappear by it
631            being in close during the "deletion".
632          */
633         PortP->State &= ~(RIO_CLOSING | RIO_DELETED);
634         if (PortP->firstOpen)
635                 PortP->firstOpen--;
636         rio_spin_unlock_irqrestore(&PortP->portSem, flags);
637         rio_dprintk(RIO_DEBUG_TTY, "Return from close\n");
638         return rv;
639 }
640
641
642
643 static void RIOClearUp(PortP)
644 struct Port *PortP;
645 {
646         rio_dprintk(RIO_DEBUG_TTY, "RIOHalted set\n");
647         PortP->Config = 0;      /* Direct semaphore */
648         PortP->PortState = 0;
649         PortP->firstOpen = 0;
650         PortP->FlushCmdBodge = 0;
651         PortP->ModemState = PortP->CookMode = 0;
652         PortP->Mapped = 0;
653         PortP->WflushFlag = 0;
654         PortP->MagicFlags = 0;
655         PortP->RxDataStart = 0;
656         PortP->TxBufferIn = 0;
657         PortP->TxBufferOut = 0;
658 }
659
660 /*
661 ** Put a command onto a port.
662 ** The PortPointer, command, length and arg are passed.
663 ** The len is the length *inclusive* of the command byte,
664 ** and so for a command that takes no data, len==1.
665 ** The arg is a single byte, and is only used if len==2.
666 ** Other values of len aren't allowed, and will cause
667 ** a panic.
668 */
669 int RIOShortCommand(struct rio_info *p, struct Port *PortP, int command, int len, int arg)
670 {
671         PKT *PacketP;
672         int retries = 20;       /* at 10 per second -> 2 seconds */
673         unsigned long flags;
674
675         rio_dprintk(RIO_DEBUG_TTY, "entering shortcommand.\n");
676
677         if (PortP->State & RIO_DELETED) {
678                 rio_dprintk(RIO_DEBUG_TTY, "Short command to deleted RTA ignored\n");
679                 return RIO_FAIL;
680         }
681         rio_spin_lock_irqsave(&PortP->portSem, flags);
682
683         /*
684          ** If the port is in use for pre-emptive command, then wait for it to
685          ** be free again.
686          */
687         while ((PortP->InUse != NOT_INUSE) && !p->RIOHalted) {
688                 rio_dprintk(RIO_DEBUG_TTY, "Waiting for not in use (%d)\n", retries);
689                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
690                 if (retries-- <= 0) {
691                         return RIO_FAIL;
692                 }
693                 if (RIODelay_ni(PortP, HUNDRED_MS) == RIO_FAIL) {
694                         return RIO_FAIL;
695                 }
696                 rio_spin_lock_irqsave(&PortP->portSem, flags);
697         }
698         if (PortP->State & RIO_DELETED) {
699                 rio_dprintk(RIO_DEBUG_TTY, "Short command to deleted RTA ignored\n");
700                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
701                 return RIO_FAIL;
702         }
703
704         while (!can_add_transmit(&PacketP, PortP) && !p->RIOHalted) {
705                 rio_dprintk(RIO_DEBUG_TTY, "Waiting to add short command to queue (%d)\n", retries);
706                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
707                 if (retries-- <= 0) {
708                         rio_dprintk(RIO_DEBUG_TTY, "out of tries. Failing\n");
709                         return RIO_FAIL;
710                 }
711                 if (RIODelay_ni(PortP, HUNDRED_MS) == RIO_FAIL) {
712                         return RIO_FAIL;
713                 }
714                 rio_spin_lock_irqsave(&PortP->portSem, flags);
715         }
716
717         if (p->RIOHalted) {
718                 rio_spin_unlock_irqrestore(&PortP->portSem, flags);
719                 return RIO_FAIL;
720         }
721
722         /*
723          ** set the command byte and the argument byte
724          */
725         WBYTE(PacketP->data[0], command);
726
727         if (len == 2)
728                 WBYTE(PacketP->data[1], arg);
729
730         /*
731          ** set the length of the packet and set the command bit.
732          */
733         WBYTE(PacketP->len, PKT_CMD_BIT | len);
734
735         add_transmit(PortP);
736         /*
737          ** Count characters transmitted for port statistics reporting
738          */
739         if (PortP->statsGather)
740                 PortP->txchars += len;
741
742         rio_spin_unlock_irqrestore(&PortP->portSem, flags);
743         return p->RIOHalted ? RIO_FAIL : ~RIO_FAIL;
744 }
745
746