This commit was generated by cvs2svn to track changes on a CVS vendor
[unix-history] / sys / kern / tty.c
CommitLineData
15637ed4
RG
1/*-
2 * Copyright (c) 1982, 1986, 1990 The Regents of the University of California.
3 * Copyright (c) 1991 The Regents of the University of California.
4 * All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 * 1. Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * 3. All advertising materials mentioning features or use of this software
15 * must display the following acknowledgement:
16 * This product includes software developed by the University of
17 * California, Berkeley and its contributors.
18 * 4. Neither the name of the University nor the names of its contributors
19 * may be used to endorse or promote products derived from this software
20 * without specific prior written permission.
21 *
22 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
23 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
26 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
27 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
28 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
29 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
31 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32 * SUCH DAMAGE.
33 *
34 * @(#)tty.c 7.44 (Berkeley) 5/28/91
35 *
36 * PATCHES MAGIC LEVEL PATCH THAT GOT US HERE
37 * -------------------- ----- ----------------------
38 * CURRENT PATCH LEVEL: 3 00163
39 * -------------------- ----- ----------------------
40 *
41 * 11 Dec 92 Williams Jolitz Fixed tty handling
42 * 28 Nov 1991 Warren Toomey Cleaned up the use of COMPAT_43
43 * in the 386BSD kernel.
44 * 27 May 93 Bruce Evans Sign Ext fix for TIOCSTI from the net
45 * Kludge to hook in RTS/CTS flow control
46 * Avoid sleeping on lbolt, it slows down
47 * output unnecessarily.
48 */
49static char rcsid[] = "$Header: /usr/bill/working/sys/kern/RCS/tty.c,v 1.3 92/01/21 21:31:11 william Exp $";
50
51#include "param.h"
52#include "systm.h"
53#include "ioctl.h"
54#define TTYDEFCHARS
55#include "tty.h"
56#undef TTYDEFCHARS
57#include "proc.h"
58#include "file.h"
59#include "conf.h"
60#include "dkstat.h"
61#include "uio.h"
62#include "kernel.h"
63#include "vnode.h"
64#include "syslog.h"
65
66#include "vm/vm.h"
67
68static int proc_compare __P((struct proc *p1, struct proc *p2));
69
70/* symbolic sleep message strings */
71char ttyin[] = "ttyin";
72char ttyout[] = "ttyout";
73char ttopen[] = "ttyopn";
74char ttclos[] = "ttycls";
75char ttybg[] = "ttybg";
76char ttybuf[] = "ttybuf";
77
78/*
79 * Table giving parity for characters and indicating
80 * character classes to tty driver. The 8th bit
81 * indicates parity, the 7th bit indicates the character
82 * is an alphameric or underscore (for ALTWERASE), and the
83 * low 6 bits indicate delay type. If the low 6 bits are 0
84 * then the character needs no special processing on output;
85 * classes other than 0 might be translated or (not currently)
86 * require delays.
87 */
88#define PARITY(c) (partab[c] & 0x80)
89#define ISALPHA(c) (partab[(c)&TTY_CHARMASK] & 0x40)
90#define CCLASSMASK 0x3f
91#define CCLASS(c) (partab[c] & CCLASSMASK)
92
93#define E 0x00 /* even parity */
94#define O 0x80 /* odd parity */
95#define ALPHA 0x40 /* alpha or underscore */
96
97#define NO ORDINARY
98#define NA ORDINARY|ALPHA
99#define CC CONTROL
100#define BS BACKSPACE
101#define NL NEWLINE
102#define TB TAB
103#define VT VTAB
104#define CR RETURN
105
106char partab[] = {
107 E|CC, O|CC, O|CC, E|CC, O|CC, E|CC, E|CC, O|CC, /* nul - bel */
108 O|BS, E|TB, E|NL, O|CC, E|VT, O|CR, O|CC, E|CC, /* bs - si */
109 O|CC, E|CC, E|CC, O|CC, E|CC, O|CC, O|CC, E|CC, /* dle - etb */
110 E|CC, O|CC, O|CC, E|CC, O|CC, E|CC, E|CC, O|CC, /* can - us */
111 O|NO, E|NO, E|NO, O|NO, E|NO, O|NO, O|NO, E|NO, /* sp - ' */
112 E|NO, O|NO, O|NO, E|NO, O|NO, E|NO, E|NO, O|NO, /* ( - / */
113 E|NA, O|NA, O|NA, E|NA, O|NA, E|NA, E|NA, O|NA, /* 0 - 7 */
114 O|NA, E|NA, E|NO, O|NO, E|NO, O|NO, O|NO, E|NO, /* 8 - ? */
115 O|NO, E|NA, E|NA, O|NA, E|NA, O|NA, O|NA, E|NA, /* @ - G */
116 E|NA, O|NA, O|NA, E|NA, O|NA, E|NA, E|NA, O|NA, /* H - O */
117 E|NA, O|NA, O|NA, E|NA, O|NA, E|NA, E|NA, O|NA, /* P - W */
118 O|NA, E|NA, E|NA, O|NO, E|NO, O|NO, O|NO, O|NA, /* X - _ */
119 E|NO, O|NA, O|NA, E|NA, O|NA, E|NA, E|NA, O|NA, /* ` - g */
120 O|NA, E|NA, E|NA, O|NA, E|NA, O|NA, O|NA, E|NA, /* h - o */
121 O|NA, E|NA, E|NA, O|NA, E|NA, O|NA, O|NA, E|NA, /* p - w */
122 E|NA, O|NA, O|NA, E|NO, O|NO, E|NO, E|NO, O|CC, /* x - del */
123 /*
124 * "meta" chars; should be settable per charset.
125 * For now, treat all as normal characters.
126 */
127 NA, NA, NA, NA, NA, NA, NA, NA,
128 NA, NA, NA, NA, NA, NA, NA, NA,
129 NA, NA, NA, NA, NA, NA, NA, NA,
130 NA, NA, NA, NA, NA, NA, NA, NA,
131 NA, NA, NA, NA, NA, NA, NA, NA,
132 NA, NA, NA, NA, NA, NA, NA, NA,
133 NA, NA, NA, NA, NA, NA, NA, NA,
134 NA, NA, NA, NA, NA, NA, NA, NA,
135 NA, NA, NA, NA, NA, NA, NA, NA,
136 NA, NA, NA, NA, NA, NA, NA, NA,
137 NA, NA, NA, NA, NA, NA, NA, NA,
138 NA, NA, NA, NA, NA, NA, NA, NA,
139 NA, NA, NA, NA, NA, NA, NA, NA,
140 NA, NA, NA, NA, NA, NA, NA, NA,
141 NA, NA, NA, NA, NA, NA, NA, NA,
142 NA, NA, NA, NA, NA, NA, NA, NA,
143};
144#undef NO
145#undef NA
146#undef CC
147#undef BS
148#undef NL
149#undef TB
150#undef VT
151#undef CR
152
153extern struct tty *constty; /* temporary virtual console */
154
155/*
156 * Is 'c' a line delimiter ("break" character)?
157 */
158#define ttbreakc(c) ((c) == '\n' || ((c) == cc[VEOF] || \
159 (c) == cc[VEOL] || (c) == cc[VEOL2]) && (c) != _POSIX_VDISABLE)
160
161ttychars(tp)
162 struct tty *tp;
163{
164
165 bcopy(ttydefchars, tp->t_cc, sizeof(ttydefchars));
166}
167
168/*
169 * Flush tty after output has drained.
170 */
171ttywflush(tp)
172 struct tty *tp;
173{
174 int error;
175
176 if ((error = ttywait(tp)) == 0)
177 ttyflush(tp, FREAD);
178 return (error);
179}
180
181/*
182 * Wait for output to drain.
183 */
184ttywait(tp)
185 register struct tty *tp;
186{
187 int error = 0, s = spltty();
188
189 while ((RB_LEN(&tp->t_out) || tp->t_state&TS_BUSY) &&
190 (tp->t_state&TS_CARR_ON || tp->t_cflag&CLOCAL) &&
191 tp->t_oproc) {
192 (*tp->t_oproc)(tp);
193 tp->t_state |= TS_ASLEEP;
194 if (error = ttysleep(tp, (caddr_t)&tp->t_out,
195 TTOPRI | PCATCH, ttyout, 0))
196 break;
197 }
198 splx(s);
199 return (error);
200}
201
202#define flushq(qq) { \
203 register struct ringb *r = qq; \
204 r->rb_hd = r->rb_tl; \
205}
206
207/*
208 * Flush TTY read and/or write queues,
209 * notifying anyone waiting.
210 */
211ttyflush(tp, rw)
212 register struct tty *tp;
213{
214 register s;
215
216 s = spltty();
217 if (rw & FREAD) {
218 flushq(&tp->t_can);
219 flushq(&tp->t_raw);
220 tp->t_rocount = 0;
221 tp->t_rocol = 0;
222 tp->t_state &= ~TS_LOCAL;
223 ttwakeup(tp);
224 }
225 if (rw & FWRITE) {
226 tp->t_state &= ~TS_TTSTOP;
227 (*cdevsw[major(tp->t_dev)].d_stop)(tp, rw);
228 flushq(&tp->t_out);
229 wakeup((caddr_t)&tp->t_out);
230 if (tp->t_wsel) {
231 selwakeup(tp->t_wsel, tp->t_state & TS_WCOLL);
232 tp->t_wsel = 0;
233 tp->t_state &= ~TS_WCOLL;
234 }
235 }
236 splx(s);
237}
238
239/*
240 * Send stop character on input overflow.
241 */
242ttyblock(tp)
243 register struct tty *tp;
244{
245 register x;
246 int rawcc, cancc;
247
248 rawcc = RB_LEN(&tp->t_raw);
249 cancc = RB_LEN(&tp->t_can);
250 x = rawcc + cancc;
251 if (rawcc > TTYHOG) {
252 ttyflush(tp, FREAD|FWRITE);
253 tp->t_state &= ~TS_TBLOCK;
254 }
255 /*
256 * Block further input iff:
257 * Current input > threshold AND input is available to user program
258 */
259 if (x >= TTYHOG/2 && (tp->t_state & TS_TBLOCK) == 0 &&
260 ((tp->t_lflag&ICANON) == 0) || (cancc > 0) &&
261 tp->t_cc[VSTOP] != _POSIX_VDISABLE) {
262 if (putc(tp->t_cc[VSTOP], &tp->t_out) == 0) {
263 tp->t_state |= TS_TBLOCK;
264 ttstart(tp);
265 }
266 }
267}
268
269ttstart(tp)
270 struct tty *tp;
271{
272
273 if (tp->t_oproc) /* kludge for pty */
274 (*tp->t_oproc)(tp);
275}
276
277ttrstrt(tp) /* XXX */
278 struct tty *tp;
279{
280
281#ifdef DIAGNOSTIC
282 if (tp == 0)
283 panic("ttrstrt");
284#endif
285 tp->t_state &= ~TS_TIMEOUT;
286 ttstart(tp);
287}
288
289
290/*
291 * Common code for ioctls on tty devices.
292 * Called after line-discipline-specific ioctl
293 * has been called to do discipline-specific functions
294 * and/or reject any of these ioctl commands.
295 */
296/*ARGSUSED*/
297ttioctl(tp, com, data, flag)
298 register struct tty *tp;
299 caddr_t data;
300{
301 register struct proc *p = curproc; /* XXX */
302 extern int nldisp;
303 int s, error;
304
305 /*
306 * If the ioctl involves modification,
307 * hang if in the background.
308 */
309 switch (com) {
310
311 case TIOCSETD:
312 case TIOCFLUSH:
313 /*case TIOCSPGRP:*/
314 case TIOCSTI:
315 case TIOCSWINSZ:
316 case TIOCSETA:
317 case TIOCSETAW:
318 case TIOCSETAF:
319#ifdef COMPAT_43
320 case TIOCSETP:
321 case TIOCSETN:
322 case TIOCSETC:
323 case TIOCSLTC:
324 case TIOCLBIS:
325 case TIOCLBIC:
326 case TIOCLSET:
327 case OTIOCSETD:
328#endif
329 while (isbackground(curproc, tp) &&
330 p->p_pgrp->pg_jobc && (p->p_flag&SPPWAIT) == 0 &&
331 (p->p_sigignore & sigmask(SIGTTOU)) == 0 &&
332 (p->p_sigmask & sigmask(SIGTTOU)) == 0) {
333 pgsignal(p->p_pgrp, SIGTTOU, 1);
334 if (error = ttysleep(tp, (caddr_t)&lbolt,
335 TTOPRI | PCATCH, ttybg, 0))
336 return (error);
337 }
338 break;
339 }
340
341 /*
342 * Process the ioctl.
343 */
344 switch (com) {
345
346 /* get discipline number */
347 case TIOCGETD:
348 *(int *)data = tp->t_line;
349 break;
350
351 /* set line discipline */
352 case TIOCSETD: {
353 register int t = *(int *)data;
354 dev_t dev = tp->t_dev;
355
356 if ((unsigned)t >= nldisp)
357 return (ENXIO);
358 if (t != tp->t_line) {
359 s = spltty();
360 (*linesw[tp->t_line].l_close)(tp, flag);
361 error = (*linesw[t].l_open)(dev, tp);
362 if (error) {
363 (void)(*linesw[tp->t_line].l_open)(dev, tp);
364 splx(s);
365 return (error);
366 }
367 tp->t_line = t;
368 splx(s);
369 }
370 break;
371 }
372
373 /* prevent more opens on channel */
374 case TIOCEXCL:
375 tp->t_state |= TS_XCLUDE;
376 break;
377
378 case TIOCNXCL:
379 tp->t_state &= ~TS_XCLUDE;
380 break;
381
382#ifdef COMPAT_43
383 /* wkt */
384 case TIOCHPCL:
385 tp->t_cflag |= HUPCL;
386 break;
387#endif
388
389 case TIOCFLUSH: {
390 register int flags = *(int *)data;
391
392 if (flags == 0)
393 flags = FREAD|FWRITE;
394 else
395 flags &= FREAD|FWRITE;
396 ttyflush(tp, flags);
397 break;
398 }
399
400 case FIOASYNC:
401 if (*(int *)data)
402 tp->t_state |= TS_ASYNC;
403 else
404 tp->t_state &= ~TS_ASYNC;
405 break;
406
407 case FIONBIO:
408 break; /* XXX remove */
409
410 /* return number of characters immediately available */
411 case FIONREAD:
412 *(off_t *)data = ttnread(tp);
413 break;
414
415 case TIOCOUTQ:
416 *(int *)data = RB_LEN(&tp->t_out);
417 break;
418
419 case TIOCSTOP:
420 s = spltty();
421 if ((tp->t_state&TS_TTSTOP) == 0) {
422 tp->t_state |= TS_TTSTOP;
423 (*cdevsw[major(tp->t_dev)].d_stop)(tp, 0);
424 }
425 splx(s);
426 break;
427
428 case TIOCSTART:
429 s = spltty();
430 if ((tp->t_state&TS_TTSTOP) || (tp->t_lflag&FLUSHO)) {
431 tp->t_state &= ~TS_TTSTOP;
432 tp->t_lflag &= ~FLUSHO;
433 ttstart(tp);
434 }
435 splx(s);
436 break;
437
438 /*
439 * Simulate typing of a character at the terminal.
440 */
441 case TIOCSTI:
442 if (p->p_ucred->cr_uid && (flag & FREAD) == 0)
443 return (EPERM);
444 if (p->p_ucred->cr_uid && !isctty(p, tp))
445 return (EACCES);
446 (*linesw[tp->t_line].l_rint)(*(u_char *)data, tp);
447 break;
448
449 case TIOCGETA: {
450 struct termios *t = (struct termios *)data;
451
452 bcopy(&tp->t_termios, t, sizeof(struct termios));
453 break;
454 }
455
456 case TIOCSETA:
457 case TIOCSETAW:
458 case TIOCSETAF: {
459 register struct termios *t = (struct termios *)data;
460
461 s = spltty();
462 if (com == TIOCSETAW || com == TIOCSETAF) {
463 if (error = ttywait(tp)) {
464 splx(s);
465 return (error);
466 }
467 if (com == TIOCSETAF)
468 ttyflush(tp, FREAD);
469 }
470 if ((t->c_cflag&CIGNORE) == 0) {
471 /*
472 * set device hardware
473 */
474 if (tp->t_param && (error = (*tp->t_param)(tp, t))) {
475 splx(s);
476 return (error);
477 } else {
478 if ((tp->t_state&TS_CARR_ON) == 0 &&
479 (tp->t_cflag&CLOCAL) &&
480 (t->c_cflag&CLOCAL) == 0) {
481 tp->t_state &= ~TS_ISOPEN;
482 tp->t_state |= TS_WOPEN;
483 ttwakeup(tp);
484 }
485 tp->t_cflag = t->c_cflag;
486 tp->t_ispeed = t->c_ispeed;
487 tp->t_ospeed = t->c_ospeed;
488 }
489 ttsetwater(tp);
490 }
491 if (com != TIOCSETAF) {
492 if ((t->c_lflag&ICANON) != (tp->t_lflag&ICANON))
493 if (t->c_lflag&ICANON) {
494 tp->t_lflag |= PENDIN;
495 ttwakeup(tp);
496 }
497 else {
498 catb(&tp->t_raw, &tp->t_can);
499 catb(&tp->t_can, &tp->t_raw);
500 }
501 }
502 tp->t_iflag = t->c_iflag;
503 tp->t_oflag = t->c_oflag;
504 /*
505 * Make the EXTPROC bit read only.
506 */
507 if (tp->t_lflag&EXTPROC)
508 t->c_lflag |= EXTPROC;
509 else
510 t->c_lflag &= ~EXTPROC;
511 tp->t_lflag = t->c_lflag;
512 bcopy(t->c_cc, tp->t_cc, sizeof(t->c_cc));
513 splx(s);
514 break;
515 }
516
517 /*
518 * Set controlling terminal.
519 * Session ctty vnode pointer set in vnode layer.
520 */
521 case TIOCSCTTY:
522 if (!SESS_LEADER(p) ||
523 (p->p_session->s_ttyvp || tp->t_session) &&
524 (tp->t_session != p->p_session))
525 return (EPERM);
526 tp->t_session = p->p_session;
527 tp->t_pgrp = p->p_pgrp;
528 p->p_session->s_ttyp = tp;
529 p->p_flag |= SCTTY;
530 break;
531
532 /*
533 * Set terminal process group.
534 */
535 case TIOCSPGRP: {
536 register struct pgrp *pgrp = pgfind(*(int *)data);
537
538 if (!isctty(p, tp))
539 return (ENOTTY);
540 else if (pgrp == NULL || pgrp->pg_session != p->p_session)
541 return (EPERM);
542 tp->t_pgrp = pgrp;
543 break;
544 }
545
546 case TIOCGPGRP:
547 if (!isctty(p, tp))
548 return (ENOTTY);
549 *(int *)data = tp->t_pgrp ? tp->t_pgrp->pg_id : NO_PID;
550 break;
551
552 case TIOCSWINSZ:
553 if (bcmp((caddr_t)&tp->t_winsize, data,
554 sizeof (struct winsize))) {
555 tp->t_winsize = *(struct winsize *)data;
556 pgsignal(tp->t_pgrp, SIGWINCH, 1);
557 }
558 break;
559
560 case TIOCGWINSZ:
561 *(struct winsize *)data = tp->t_winsize;
562 break;
563
564 case TIOCCONS:
565 if (*(int *)data) {
566 if (constty && constty != tp &&
567 (constty->t_state & (TS_CARR_ON|TS_ISOPEN)) ==
568 (TS_CARR_ON|TS_ISOPEN))
569 return (EBUSY);
570#ifndef UCONSOLE
571 if (error = suser(p->p_ucred, &p->p_acflag))
572 return (error);
573#endif
574 constty = tp;
575 } else if (tp == constty)
576 constty = NULL;
577 break;
578
579 case TIOCDRAIN:
580 if (error = ttywait(tp))
581 return (error);
582 break;
583
584 default:
585#ifdef COMPAT_43
586 return (ttcompat(tp, com, data, flag));
587#else
588 return (-1);
589#endif
590 }
591 return (0);
592}
593
594ttnread(tp)
595 struct tty *tp;
596{
597 int nread = 0;
598
599 if (tp->t_lflag & PENDIN)
600 ttypend(tp);
601 nread = RB_LEN(&tp->t_can);
602 if ((tp->t_lflag & ICANON) == 0)
603 nread += RB_LEN(&tp->t_raw);
604 return (nread);
605}
606
607ttselect(dev, rw, p)
608 dev_t dev;
609 int rw;
610 struct proc *p;
611{
612 register struct tty *tp = &cdevsw[major(dev)].d_ttys[minor(dev)];
613 int nread;
614 int s = spltty();
615 struct proc *selp;
616
617 switch (rw) {
618
619 case FREAD:
620 nread = ttnread(tp);
621 if (nread > 0 ||
622 ((tp->t_cflag&CLOCAL) == 0 && (tp->t_state&TS_CARR_ON) == 0))
623 goto win;
624 if (tp->t_rsel && (selp = pfind(tp->t_rsel)) && selp->p_wchan == (caddr_t)&selwait)
625 tp->t_state |= TS_RCOLL;
626 else
627 tp->t_rsel = p->p_pid;
628 break;
629
630 case FWRITE:
631 if (RB_LEN(&tp->t_out) <= tp->t_lowat)
632 goto win;
633 if (tp->t_wsel && (selp = pfind(tp->t_wsel)) && selp->p_wchan == (caddr_t)&selwait)
634 tp->t_state |= TS_WCOLL;
635 else
636 tp->t_wsel = p->p_pid;
637 break;
638 }
639 splx(s);
640 return (0);
641win:
642 splx(s);
643 return (1);
644}
645
646/*
647 * Initial open of tty, or (re)entry to standard tty line discipline.
648 */
649ttyopen(dev, tp)
650 dev_t dev;
651 register struct tty *tp;
652{
653
654 tp->t_dev = dev;
655
656 tp->t_state &= ~TS_WOPEN;
657 if ((tp->t_state & TS_ISOPEN) == 0) {
658 tp->t_state |= TS_ISOPEN;
659 initrb(&tp->t_raw);
660 initrb(&tp->t_can);
661 initrb(&tp->t_out);
662 bzero((caddr_t)&tp->t_winsize, sizeof(tp->t_winsize));
663 }
664 return (0);
665}
666
667/*
668 * "close" a line discipline
669 */
670ttylclose(tp, flag)
671 struct tty *tp;
672 int flag;
673{
674
675 if (flag&IO_NDELAY)
676 ttyflush(tp, FREAD|FWRITE);
677 else
678 ttywflush(tp);
679}
680
681/*
682 * Handle close() on a tty line: flush and set to initial state,
683 * bumping generation number so that pending read/write calls
684 * can detect recycling of the tty.
685 */
686ttyclose(tp)
687 register struct tty *tp;
688{
689 if (constty == tp)
690 constty = NULL;
691 ttyflush(tp, FREAD|FWRITE);
692 tp->t_session = NULL;
693 tp->t_pgrp = NULL;
694/*
695 * XXX - do we need to send cc[VSTART] or do a ttstart() here in some cases?
696 * (TS_TBLOCK and TS_RTSBLOCK are being cleared.)
697 */
698 tp->t_state = 0;
699 tp->t_gen++;
700 return (0);
701}
702
703/*
704 * Handle modem control transition on a tty.
705 * Flag indicates new state of carrier.
706 * Returns 0 if the line should be turned off, otherwise 1.
707 */
708ttymodem(tp, flag)
709 register struct tty *tp;
710{
711
712 if ((tp->t_state&TS_WOPEN) == 0 && (tp->t_lflag&MDMBUF)) {
713 /*
714 * MDMBUF: do flow control according to carrier flag
715 */
716 if (flag) {
717 tp->t_state &= ~TS_TTSTOP;
718 ttstart(tp);
719 } else if ((tp->t_state&TS_TTSTOP) == 0) {
720 tp->t_state |= TS_TTSTOP;
721 (*cdevsw[major(tp->t_dev)].d_stop)(tp, 0);
722 }
723 } else if (flag == 0) {
724 /*
725 * Lost carrier.
726 */
727 tp->t_state &= ~TS_CARR_ON;
728 if (tp->t_state&TS_ISOPEN && (tp->t_cflag&CLOCAL) == 0) {
729 if (tp->t_session && tp->t_session->s_leader)
730 psignal(tp->t_session->s_leader, SIGHUP);
731 ttyflush(tp, FREAD|FWRITE);
732 return (0);
733 }
734 } else {
735 /*
736 * Carrier now on.
737 */
738 tp->t_state |= TS_CARR_ON;
739 ttwakeup(tp);
740 }
741 return (1);
742}
743
744/*
745 * Default modem control routine (for other line disciplines).
746 * Return argument flag, to turn off device on carrier drop.
747 */
748nullmodem(tp, flag)
749 register struct tty *tp;
750 int flag;
751{
752
753 if (flag)
754 tp->t_state |= TS_CARR_ON;
755 else {
756 tp->t_state &= ~TS_CARR_ON;
757 if ((tp->t_cflag&CLOCAL) == 0) {
758 if (tp->t_session && tp->t_session->s_leader)
759 psignal(tp->t_session->s_leader, SIGHUP);
760 return (0);
761 }
762 }
763 return (1);
764}
765
766/*
767 * reinput pending characters after state switch
768 * call at spltty().
769 */
770ttypend(tp)
771 register struct tty *tp;
772{
773 register c;
774 char *hd, *tl;
775
776 tp->t_lflag &= ~PENDIN;
777 tp->t_state |= TS_TYPEN;
778 hd = tp->t_raw.rb_hd;
779 tl = tp->t_raw.rb_tl;
780 flushq(&tp->t_raw);
781 while (hd != tl) {
782 ttyinput(*hd, tp);
783 hd = RB_SUCC(&tp->t_raw, hd);
784 }
785 tp->t_state &= ~TS_TYPEN;
786}
787
788/*
789 * Process input of a single character received on a tty.
790 */
791ttyinput(c, tp)
792 register c;
793 register struct tty *tp;
794{
795 register int iflag = tp->t_iflag;
796 register int lflag = tp->t_lflag;
797 register u_char *cc = tp->t_cc;
798 int i, err;
799
800 /*
801 * If input is pending take it first.
802 */
803 if (lflag&PENDIN)
804 ttypend(tp);
805 /*
806 * Gather stats.
807 */
808 tk_nin++;
809 if (lflag&ICANON) {
810 tk_cancc++;
811 tp->t_cancc++;
812 } else {
813 tk_rawcc++;
814 tp->t_rawcc++;
815 }
816 /*
817 * Handle exceptional conditions (break, parity, framing).
818 */
819 if (err = (c&TTY_ERRORMASK)) {
820 c &= ~TTY_ERRORMASK;
821 if (err&TTY_FE && !c) { /* break */
822 if (iflag&IGNBRK)
823 goto endcase;
824 else if (iflag&BRKINT && lflag&ISIG &&
825 (cc[VINTR] != _POSIX_VDISABLE))
826 c = cc[VINTR];
827 else if (iflag&PARMRK)
828 goto parmrk;
829 } else if ((err&TTY_PE && iflag&INPCK) || err&TTY_FE) {
830 if (iflag&IGNPAR)
831 goto endcase;
832 else if (iflag&PARMRK) {
833parmrk:
834 putc(0377|TTY_QUOTE, &tp->t_raw);
835 putc(0|TTY_QUOTE, &tp->t_raw);
836 putc(c|TTY_QUOTE, &tp->t_raw);
837 goto endcase;
838 } else
839 c = 0;
840 }
841 }
842 /*
843 * In tandem mode, check high water mark.
844 */
845 if (iflag&IXOFF)
846 ttyblock(tp);
847 if ((tp->t_state&TS_TYPEN) == 0 && (iflag&ISTRIP))
848 c &= ~0x80;
849 if ((tp->t_lflag&EXTPROC) == 0) {
850 /*
851 * Check for literal nexting very first
852 */
853 if (tp->t_state&TS_LNCH) {
854 c |= TTY_QUOTE;
855 tp->t_state &= ~TS_LNCH;
856 }
857 /*
858 * Scan for special characters. This code
859 * is really just a big case statement with
860 * non-constant cases. The bottom of the
861 * case statement is labeled ``endcase'', so goto
862 * it after a case match, or similar.
863 */
864
865 /*
866 * Control chars which aren't controlled
867 * by ICANON, ISIG, or IXON.
868 */
869 if (lflag&IEXTEN) {
870 if (CCEQ(cc[VLNEXT], c)) {
871 if (lflag&ECHO) {
872 if (lflag&ECHOE)
873 ttyoutstr("^\b", tp);
874 else
875 ttyecho(c, tp);
876 }
877 tp->t_state |= TS_LNCH;
878 goto endcase;
879 }
880 if (CCEQ(cc[VDISCARD], c)) {
881 if (lflag&FLUSHO)
882 tp->t_lflag &= ~FLUSHO;
883 else {
884 ttyflush(tp, FWRITE);
885 ttyecho(c, tp);
886 if (RB_LEN(&tp->t_raw) + RB_LEN(&tp->t_can))
887 ttyretype(tp);
888 tp->t_lflag |= FLUSHO;
889 }
890 goto startoutput;
891 }
892 }
893 /*
894 * Signals.
895 */
896 if (lflag&ISIG) {
897 if (CCEQ(cc[VINTR], c) || CCEQ(cc[VQUIT], c)) {
898 if ((lflag&NOFLSH) == 0)
899 ttyflush(tp, FREAD|FWRITE);
900 ttyecho(c, tp);
901 pgsignal(tp->t_pgrp,
902 CCEQ(cc[VINTR], c) ? SIGINT : SIGQUIT, 1);
903 goto endcase;
904 }
905 if (CCEQ(cc[VSUSP], c)) {
906 if ((lflag&NOFLSH) == 0)
907 ttyflush(tp, FREAD);
908 ttyecho(c, tp);
909 pgsignal(tp->t_pgrp, SIGTSTP, 1);
910 goto endcase;
911 }
912 }
913 /*
914 * Handle start/stop characters.
915 */
916 if (iflag&IXON) {
917 if (CCEQ(cc[VSTOP], c)) {
918 if ((tp->t_state&TS_TTSTOP) == 0) {
919 tp->t_state |= TS_TTSTOP;
920 (*cdevsw[major(tp->t_dev)].d_stop)(tp,
921 0);
922 return;
923 }
924 if (!CCEQ(cc[VSTART], c))
925 return;
926 /*
927 * if VSTART == VSTOP then toggle
928 */
929 goto endcase;
930 }
931 if (CCEQ(cc[VSTART], c))
932 goto restartoutput;
933 }
934 /*
935 * IGNCR, ICRNL, & INLCR
936 */
937 if (c == '\r') {
938 if (iflag&IGNCR)
939 goto endcase;
940 else if (iflag&ICRNL)
941 c = '\n';
942 } else if (c == '\n' && iflag&INLCR)
943 c = '\r';
944 }
945 if ((tp->t_lflag&EXTPROC) == 0 && lflag&ICANON) {
946 /*
947 * From here on down canonical mode character
948 * processing takes place.
949 */
950 /*
951 * erase (^H / ^?)
952 */
953 if (CCEQ(cc[VERASE], c)) {
954 if (RB_LEN(&tp->t_raw))
955 ttyrub(unputc(&tp->t_raw), tp);
956 goto endcase;
957 }
958 /*
959 * kill (^U)
960 */
961 if (CCEQ(cc[VKILL], c)) {
962 if (lflag&ECHOKE && RB_LEN(&tp->t_raw) == tp->t_rocount &&
963 (lflag&ECHOPRT) == 0) {
964 while (RB_LEN(&tp->t_raw))
965 ttyrub(unputc(&tp->t_raw), tp);
966 } else {
967 ttyecho(c, tp);
968 if (lflag&ECHOK || lflag&ECHOKE)
969 ttyecho('\n', tp);
970 while (getc(&tp->t_raw) > 0)
971 ;
972 tp->t_rocount = 0;
973 }
974 tp->t_state &= ~TS_LOCAL;
975 goto endcase;
976 }
977 /*
978 * word erase (^W)
979 */
980 if (CCEQ(cc[VWERASE], c)) {
981 int ctype;
982 int alt = lflag&ALTWERASE;
983
984 /*
985 * erase whitespace
986 */
987 while ((c = unputc(&tp->t_raw)) == ' ' || c == '\t')
988 ttyrub(c, tp);
989 if (c == -1)
990 goto endcase;
991 /*
992 * erase last char of word and remember the
993 * next chars type (for ALTWERASE)
994 */
995 ttyrub(c, tp);
996 c = unputc(&tp->t_raw);
997 if (c == -1)
998 goto endcase;
999 ctype = ISALPHA(c);
1000 /*
1001 * erase rest of word
1002 */
1003 do {
1004 ttyrub(c, tp);
1005 c = unputc(&tp->t_raw);
1006 if (c == -1)
1007 goto endcase;
1008 } while (c != ' ' && c != '\t' &&
1009 (alt == 0 || ISALPHA(c) == ctype));
1010 (void) putc(c, &tp->t_raw);
1011 goto endcase;
1012 }
1013 /*
1014 * reprint line (^R)
1015 */
1016 if (CCEQ(cc[VREPRINT], c)) {
1017 ttyretype(tp);
1018 goto endcase;
1019 }
1020 /*
1021 * ^T - kernel info and generate SIGINFO
1022 */
1023 if (CCEQ(cc[VSTATUS], c)) {
1024 pgsignal(tp->t_pgrp, SIGINFO, 1);
1025 if ((lflag&NOKERNINFO) == 0)
1026 ttyinfo(tp);
1027 goto endcase;
1028 }
1029 }
1030 /*
1031 * Check for input buffer overflow
1032 */
1033 if (RB_LEN(&tp->t_raw)+RB_LEN(&tp->t_can) >= TTYHOG) {
1034 if (iflag&IMAXBEL) {
1035 if (RB_LEN(&tp->t_out) < tp->t_hiwat)
1036 (void) ttyoutput(CTRL('g'), tp);
1037 } else
1038 ttyflush(tp, FREAD | FWRITE);
1039 goto endcase;
1040 }
1041 /*
1042 * Put data char in q for user and
1043 * wakeup on seeing a line delimiter.
1044 */
1045 if (putc(c, &tp->t_raw) >= 0) {
1046 if ((lflag&ICANON) == 0) {
1047 ttwakeup(tp);
1048 ttyecho(c, tp);
1049 goto endcase;
1050 }
1051 if (ttbreakc(c)) {
1052 tp->t_rocount = 0;
1053 catb(&tp->t_raw, &tp->t_can);
1054 ttwakeup(tp);
1055 } else if (tp->t_rocount++ == 0)
1056 tp->t_rocol = tp->t_col;
1057 if (tp->t_state&TS_ERASE) {
1058 /*
1059 * end of prterase \.../
1060 */
1061 tp->t_state &= ~TS_ERASE;
1062 (void) ttyoutput('/', tp);
1063 }
1064 i = tp->t_col;
1065 ttyecho(c, tp);
1066 if (CCEQ(cc[VEOF], c) && lflag&ECHO) {
1067 /*
1068 * Place the cursor over the '^' of the ^D.
1069 */
1070 i = MIN(2, tp->t_col - i);
1071 while (i > 0) {
1072 (void) ttyoutput('\b', tp);
1073 i--;
1074 }
1075 }
1076 }
1077endcase:
1078 /*
1079 * IXANY means allow any character to restart output.
1080 */
1081 if ((tp->t_state&TS_TTSTOP) && (iflag&IXANY) == 0 &&
1082 cc[VSTART] != cc[VSTOP])
1083 return;
1084restartoutput:
1085 tp->t_state &= ~TS_TTSTOP;
1086 tp->t_lflag &= ~FLUSHO;
1087startoutput:
1088 ttstart(tp);
1089}
1090
1091/*
1092 * Output a single character on a tty, doing output processing
1093 * as needed (expanding tabs, newline processing, etc.).
1094 * Returns < 0 if putc succeeds, otherwise returns char to resend.
1095 * Must be recursive.
1096 */
1097ttyoutput(c, tp)
1098 register c;
1099 register struct tty *tp;
1100{
1101 register int col;
1102 register long oflag = tp->t_oflag;
1103
1104 if ((oflag&OPOST) == 0) {
1105 if (tp->t_lflag&FLUSHO)
1106 return (-1);
1107 if (putc(c, &tp->t_out))
1108 return (c);
1109 tk_nout++;
1110 tp->t_outcc++;
1111 return (-1);
1112 }
1113 c &= TTY_CHARMASK;
1114 /*
1115 * Do tab expansion if OXTABS is set.
1116 * Special case if we have external processing, we don't
1117 * do the tab expansion because we'll probably get it
1118 * wrong. If tab expansion needs to be done, let it
1119 * happen externally.
1120 */
1121 if (c == '\t' && oflag&OXTABS && (tp->t_lflag&EXTPROC) == 0) {
1122 register int s;
1123
1124 c = 8 - (tp->t_col&7);
1125 if ((tp->t_lflag&FLUSHO) == 0) {
1126 int i;
1127
1128 s = spltty(); /* don't interrupt tabs */
1129#ifdef was
1130 c -= b_to_q(" ", c, &tp->t_outq);
1131#else
1132 i = min (c, RB_CONTIGPUT(&tp->t_out));
1133 bcopy(" ", tp->t_out.rb_tl, i);
1134 tp->t_out.rb_tl =
1135 RB_ROLLOVER(&tp->t_out, tp->t_out.rb_tl+i);
1136 i = min (c-i, RB_CONTIGPUT(&tp->t_out));
1137
1138 /* off end and still have space? */
1139 if (i) {
1140 bcopy(" ", tp->t_out.rb_tl, i);
1141 tp->t_out.rb_tl =
1142 RB_ROLLOVER(&tp->t_out, tp->t_out.rb_tl+i);
1143 }
1144#endif
1145 tk_nout += c;
1146 tp->t_outcc += c;
1147 splx(s);
1148 }
1149 tp->t_col += c;
1150 return (c ? -1 : '\t');
1151 }
1152 if (c == CEOT && oflag&ONOEOT)
1153 return (-1);
1154 tk_nout++;
1155 tp->t_outcc++;
1156 /*
1157 * Newline translation: if ONLCR is set,
1158 * translate newline into "\r\n".
1159 */
1160 if (c == '\n' && (tp->t_oflag&ONLCR) && ttyoutput('\r', tp) >= 0)
1161 return (c);
1162 if ((tp->t_lflag&FLUSHO) == 0 && putc(c, &tp->t_out))
1163 return (c);
1164
1165 col = tp->t_col;
1166 switch (CCLASS(c)) {
1167
1168 case ORDINARY:
1169 col++;
1170
1171 case CONTROL:
1172 break;
1173
1174 case BACKSPACE:
1175 if (col > 0)
1176 col--;
1177 break;
1178
1179 case NEWLINE:
1180 col = 0;
1181 break;
1182
1183 case TAB:
1184 col = (col + 8) &~ 0x7;
1185 break;
1186
1187 case RETURN:
1188 col = 0;
1189 }
1190 tp->t_col = col;
1191 return (-1);
1192}
1193
1194/*
1195 * Process a read call on a tty device.
1196 */
1197ttread(tp, uio, flag)
1198 register struct tty *tp;
1199 struct uio *uio;
1200{
1201 register struct ringb *qp;
1202 register int c;
1203 register long lflag;
1204 register u_char *cc = tp->t_cc;
1205 register struct proc *p = curproc;
1206 int s, first, error = 0;
1207
1208loop:
1209 lflag = tp->t_lflag;
1210 s = spltty();
1211 /*
1212 * take pending input first
1213 */
1214 if (lflag&PENDIN)
1215 ttypend(tp);
1216 splx(s);
1217
1218 /*
1219 * Hang process if it's in the background.
1220 */
1221 if (isbackground(p, tp)) {
1222 if ((p->p_sigignore & sigmask(SIGTTIN)) ||
1223 (p->p_sigmask & sigmask(SIGTTIN)) ||
1224 p->p_flag&SPPWAIT || p->p_pgrp->pg_jobc == 0)
1225 return (EIO);
1226 pgsignal(p->p_pgrp, SIGTTIN, 1);
1227 if (error = ttysleep(tp, (caddr_t)&lbolt, TTIPRI | PCATCH,
1228 ttybg, 0))
1229 return (error);
1230 goto loop;
1231 }
1232
1233 /*
1234 * If canonical, use the canonical queue,
1235 * else use the raw queue.
1236 */
1237 qp = lflag&ICANON ? &tp->t_can : &tp->t_raw;
1238
1239 /*
1240 * If there is no input, sleep on rawq
1241 * awaiting hardware receipt and notification.
1242 * If we have data, we don't need to check for carrier.
1243 */
1244 s = spltty();
1245 if (RB_LEN(qp) <= 0) {
1246 int carrier;
1247
1248 carrier = (tp->t_state&TS_CARR_ON) || (tp->t_cflag&CLOCAL);
1249 if (!carrier && tp->t_state&TS_ISOPEN) {
1250 splx(s);
1251 return (0); /* EOF */
1252 }
1253 if (flag & IO_NDELAY) {
1254 splx(s);
1255 return (EWOULDBLOCK);
1256 }
1257 error = ttysleep(tp, (caddr_t)&tp->t_raw, TTIPRI | PCATCH,
1258 carrier ? ttyin : ttopen, 0);
1259 splx(s);
1260 if (error)
1261 return (error);
1262 goto loop;
1263 }
1264 splx(s);
1265
1266 /*
1267 * Input present, check for input mapping and processing.
1268 */
1269 first = 1;
1270 while ((c = getc(qp)) >= 0) {
1271 /*
1272 * delayed suspend (^Y)
1273 */
1274 if (CCEQ(cc[VDSUSP], c) && lflag&ISIG) {
1275 pgsignal(tp->t_pgrp, SIGTSTP, 1);
1276 if (first) {
1277 if (error = ttysleep(tp, (caddr_t)&lbolt,
1278 TTIPRI | PCATCH, ttybg, 0))
1279 break;
1280 goto loop;
1281 }
1282 break;
1283 }
1284 /*
1285 * Interpret EOF only in canonical mode.
1286 */
1287 if (CCEQ(cc[VEOF], c) && lflag&ICANON)
1288 break;
1289 /*
1290 * Give user character.
1291 */
1292 error = ureadc(c, uio);
1293 if (error)
1294 break;
1295 if (uio->uio_resid == 0)
1296 break;
1297 /*
1298 * In canonical mode check for a "break character"
1299 * marking the end of a "line of input".
1300 */
1301 if (lflag&ICANON && ttbreakc(c))
1302 break;
1303 first = 0;
1304 }
1305 /*
1306 * Look to unblock output now that (presumably)
1307 * the input queue has gone down.
1308 */
1309#if 0
1310 if (tp->t_state&TS_TBLOCK && RB_LEN(&tp->t_raw) < TTYHOG/5) {
1311 if (cc[VSTART] != _POSIX_VDISABLE &&
1312 putc(cc[VSTART], &tp->t_out) == 0) {
1313 tp->t_state &= ~TS_TBLOCK;
1314 ttstart(tp);
1315 }
1316 }
1317#else
1318#define TS_RTSBLOCK TS_TBLOCK /* XXX */
1319#define RB_I_LOW_WATER ((RBSZ - 2 * 256) * 7 / 8) /* XXX */
1320 if (tp->t_state&TS_RTSBLOCK && RB_LEN(&tp->t_raw) <= RB_I_LOW_WATER) {
1321 tp->t_state &= ~TS_RTSBLOCK;
1322 ttstart(tp);
1323 }
1324#endif
1325 return (error);
1326}
1327
1328/*
1329 * Check the output queue on tp for space for a kernel message
1330 * (from uprintf/tprintf). Allow some space over the normal
1331 * hiwater mark so we don't lose messages due to normal flow
1332 * control, but don't let the tty run amok.
1333 * Sleeps here are not interruptible, but we return prematurely
1334 * if new signals come in.
1335 */
1336ttycheckoutq(tp, wait)
1337 register struct tty *tp;
1338 int wait;
1339{
1340 int hiwat, s, oldsig;
1341 extern int wakeup();
1342
1343 hiwat = tp->t_hiwat;
1344 s = spltty();
1345 if (curproc)
1346 oldsig = curproc->p_sig;
1347 else
1348 oldsig = 0;
1349 if (RB_LEN(&tp->t_out) > hiwat + 200)
1350 while (RB_LEN(&tp->t_out) > hiwat) {
1351 ttstart(tp);
1352 if (wait == 0 || (curproc && curproc->p_sig != oldsig)) {
1353 splx(s);
1354 return (0);
1355 }
1356 timeout(wakeup, (caddr_t)&tp->t_out, hz);
1357 tp->t_state |= TS_ASLEEP;
1358 sleep((caddr_t)&tp->t_out, PZERO - 1);
1359 }
1360 splx(s);
1361 return (1);
1362}
1363
1364/*
1365 * Process a write call on a tty device.
1366 */
1367ttwrite(tp, uio, flag)
1368 register struct tty *tp;
1369 register struct uio *uio;
1370{
1371 register char *cp;
1372 register int cc = 0, ce;
1373 register struct proc *p = curproc;
1374 int i, hiwat, cnt, error, s;
1375 char obuf[OBUFSIZ];
1376
1377 hiwat = tp->t_hiwat;
1378 cnt = uio->uio_resid;
1379 error = 0;
1380loop:
1381 s = spltty();
1382 if ((tp->t_state&TS_CARR_ON) == 0 && (tp->t_cflag&CLOCAL) == 0) {
1383 if (tp->t_state&TS_ISOPEN) {
1384 splx(s);
1385 return (EIO);
1386 } else if (flag & IO_NDELAY) {
1387 splx(s);
1388 error = EWOULDBLOCK;
1389 goto out;
1390 } else {
1391 /*
1392 * sleep awaiting carrier
1393 */
1394 error = ttysleep(tp, (caddr_t)&tp->t_raw,
1395 TTIPRI | PCATCH,ttopen, 0);
1396 splx(s);
1397 if (error)
1398 goto out;
1399 goto loop;
1400 }
1401 }
1402 splx(s);
1403 /*
1404 * Hang the process if it's in the background.
1405 */
1406 if (isbackground(p, tp) &&
1407 tp->t_lflag&TOSTOP && (p->p_flag&SPPWAIT) == 0 &&
1408 (p->p_sigignore & sigmask(SIGTTOU)) == 0 &&
1409 (p->p_sigmask & sigmask(SIGTTOU)) == 0 &&
1410 p->p_pgrp->pg_jobc) {
1411 pgsignal(p->p_pgrp, SIGTTOU, 1);
1412 if (error = ttysleep(tp, (caddr_t)&lbolt, TTIPRI | PCATCH,
1413 ttybg, 0))
1414 goto out;
1415 goto loop;
1416 }
1417 /*
1418 * Process the user's data in at most OBUFSIZ
1419 * chunks. Perform any output translation.
1420 * Keep track of high water mark, sleep on overflow
1421 * awaiting device aid in acquiring new space.
1422 */
1423 while (uio->uio_resid > 0 || cc > 0) {
1424 if (tp->t_lflag&FLUSHO) {
1425 uio->uio_resid = 0;
1426 return (0);
1427 }
1428 if (RB_LEN(&tp->t_out) > hiwat)
1429 goto ovhiwat;
1430 /*
1431 * Grab a hunk of data from the user,
1432 * unless we have some leftover from last time.
1433 */
1434 if (cc == 0) {
1435 cc = min(uio->uio_resid, OBUFSIZ);
1436 cp = obuf;
1437 error = uiomove(cp, cc, uio);
1438 if (error) {
1439 cc = 0;
1440 break;
1441 }
1442 }
1443 /*
1444 * If nothing fancy need be done, grab those characters we
1445 * can handle without any of ttyoutput's processing and
1446 * just transfer them to the output q. For those chars
1447 * which require special processing (as indicated by the
1448 * bits in partab), call ttyoutput. After processing
1449 * a hunk of data, look for FLUSHO so ^O's will take effect
1450 * immediately.
1451 */
1452 while (cc > 0) {
1453 if ((tp->t_oflag&OPOST) == 0)
1454 ce = cc;
1455 else {
1456 ce = cc - scanc((unsigned)cc, (u_char *)cp,
1457 (u_char *)partab, CCLASSMASK);
1458 /*
1459 * If ce is zero, then we're processing
1460 * a special character through ttyoutput.
1461 */
1462 if (ce == 0) {
1463 tp->t_rocount = 0;
1464 if (ttyoutput(*cp, tp) >= 0) {
1465 /* no c-lists, wait a bit */
1466 ttstart(tp);
1467printf("\nttysleep - no c-lists\n"); /* XXX */
1468 if (error = ttysleep(tp,
1469 (caddr_t)&lbolt,
1470 TTOPRI | PCATCH, ttybuf, 0))
1471 break;
1472 goto loop;
1473 }
1474 cp++, cc--;
1475 if ((tp->t_lflag&FLUSHO) ||
1476 RB_LEN(&tp->t_out) > hiwat)
1477 goto ovhiwat;
1478 continue;
1479 }
1480 }
1481 /*
1482 * A bunch of normal characters have been found,
1483 * transfer them en masse to the output queue and
1484 * continue processing at the top of the loop.
1485 * If there are any further characters in this
1486 * <= OBUFSIZ chunk, the first should be a character
1487 * requiring special handling by ttyoutput.
1488 */
1489 tp->t_rocount = 0;
1490#ifdef was
1491 i = b_to_q(cp, ce, &tp->t_outq);
1492 ce -= i;
1493#else
1494 i = ce;
1495 ce = min (ce, RB_CONTIGPUT(&tp->t_out));
1496 bcopy(cp, tp->t_out.rb_tl, ce);
1497 tp->t_out.rb_tl = RB_ROLLOVER(&tp->t_out,
1498 tp->t_out.rb_tl + ce);
1499 i -= ce;
1500 if (i > 0) {
1501 int ii;
1502
1503 ii = min (i, RB_CONTIGPUT(&tp->t_out));
1504 bcopy(cp + ce, tp->t_out.rb_tl, ii);
1505 tp->t_out.rb_tl = RB_ROLLOVER(&tp->t_out,
1506 tp->t_out.rb_tl + ii);
1507 i -= ii;
1508 ce += ii;
1509 }
1510#endif
1511 tp->t_col += ce;
1512 cp += ce, cc -= ce, tk_nout += ce;
1513 tp->t_outcc += ce;
1514 if (i > 0) {
1515 ttstart(tp);
1516 if (RB_CONTIGPUT(&tp->t_out) > 0)
1517 goto loop; /* synchronous/fast */
1518 /* out of space, wait a bit */
1519 tp->t_state |= TS_ASLEEP;
1520 if (error = ttysleep(tp, (caddr_t)&tp->t_out,
1521 TTOPRI | PCATCH, ttybuf, 0))
1522 break;
1523 goto loop;
1524 }
1525 if (tp->t_lflag&FLUSHO || RB_LEN(&tp->t_out) > hiwat)
1526 break;
1527 }
1528 ttstart(tp);
1529 }
1530out:
1531 /*
1532 * If cc is nonzero, we leave the uio structure inconsistent,
1533 * as the offset and iov pointers have moved forward,
1534 * but it doesn't matter (the call will either return short
1535 * or restart with a new uio).
1536 */
1537 uio->uio_resid += cc;
1538 return (error);
1539
1540ovhiwat:
1541 ttstart(tp);
1542 s = spltty();
1543 /*
1544 * This can only occur if FLUSHO is set in t_lflag,
1545 * or if ttstart/oproc is synchronous (or very fast).
1546 */
1547 if (RB_LEN(&tp->t_out) <= hiwat) {
1548 splx(s);
1549 goto loop;
1550 }
1551 if (flag & IO_NDELAY) {
1552 splx(s);
1553 uio->uio_resid += cc;
1554 if (uio->uio_resid == cnt)
1555 return (EWOULDBLOCK);
1556 return (0);
1557 }
1558 tp->t_state |= TS_ASLEEP;
1559 error = ttysleep(tp, (caddr_t)&tp->t_out, TTOPRI | PCATCH, ttyout, 0);
1560 splx(s);
1561 if (error)
1562 goto out;
1563 goto loop;
1564}
1565
1566/*
1567 * Rubout one character from the rawq of tp
1568 * as cleanly as possible.
1569 */
1570ttyrub(c, tp)
1571 register c;
1572 register struct tty *tp;
1573{
1574 char *cp;
1575 register int savecol;
1576 int s;
1577
1578 if ((tp->t_lflag&ECHO) == 0 || (tp->t_lflag&EXTPROC))
1579 return;
1580 tp->t_lflag &= ~FLUSHO;
1581 if (tp->t_lflag&ECHOE) {
1582 if (tp->t_rocount == 0) {
1583 /*
1584 * Screwed by ttwrite; retype
1585 */
1586 ttyretype(tp);
1587 return;
1588 }
1589 if (c == ('\t'|TTY_QUOTE) || c == ('\n'|TTY_QUOTE))
1590 ttyrubo(tp, 2);
1591 else switch (CCLASS(c &= TTY_CHARMASK)) {
1592
1593 case ORDINARY:
1594 ttyrubo(tp, 1);
1595 break;
1596
1597 case VTAB:
1598 case BACKSPACE:
1599 case CONTROL:
1600 case RETURN:
1601 case NEWLINE:
1602 if (tp->t_lflag&ECHOCTL)
1603 ttyrubo(tp, 2);
1604 break;
1605
1606 case TAB: {
1607 int c;
1608
1609 if (tp->t_rocount < RB_LEN(&tp->t_raw)) {
1610 ttyretype(tp);
1611 return;
1612 }
1613 s = spltty();
1614 savecol = tp->t_col;
1615 tp->t_state |= TS_CNTTB;
1616 tp->t_lflag |= FLUSHO;
1617 tp->t_col = tp->t_rocol;
1618 cp = tp->t_raw.rb_hd;
1619 for (c = nextc(&cp, &tp->t_raw); c ;
1620 c = nextc(&cp, &tp->t_raw))
1621 ttyecho(c, tp);
1622 tp->t_lflag &= ~FLUSHO;
1623 tp->t_state &= ~TS_CNTTB;
1624 splx(s);
1625 /*
1626 * savecol will now be length of the tab
1627 */
1628 savecol -= tp->t_col;
1629 tp->t_col += savecol;
1630 if (savecol > 8)
1631 savecol = 8; /* overflow screw */
1632 while (--savecol >= 0)
1633 (void) ttyoutput('\b', tp);
1634 break;
1635 }
1636
1637 default:
1638 /* XXX */
1639 printf("ttyrub: would panic c = %d, val = %d\n",
1640 c, CCLASS(c));
1641 /*panic("ttyrub");*/
1642 }
1643 } else if (tp->t_lflag&ECHOPRT) {
1644 if ((tp->t_state&TS_ERASE) == 0) {
1645 (void) ttyoutput('\\', tp);
1646 tp->t_state |= TS_ERASE;
1647 }
1648 ttyecho(c, tp);
1649 } else
1650 ttyecho(tp->t_cc[VERASE], tp);
1651 tp->t_rocount--;
1652}
1653
1654/*
1655 * Crt back over cnt chars perhaps
1656 * erasing them.
1657 */
1658ttyrubo(tp, cnt)
1659 register struct tty *tp;
1660 int cnt;
1661{
1662
1663 while (--cnt >= 0)
1664 ttyoutstr("\b \b", tp);
1665}
1666
1667/*
1668 * Reprint the rawq line.
1669 * We assume c_cc has already been checked.
1670 */
1671ttyretype(tp)
1672 register struct tty *tp;
1673{
1674 char *cp;
1675 int s, c;
1676
1677 if (tp->t_cc[VREPRINT] != _POSIX_VDISABLE)
1678 ttyecho(tp->t_cc[VREPRINT], tp);
1679 (void) ttyoutput('\n', tp);
1680
1681 s = spltty();
1682 cp = tp->t_can.rb_hd;
1683 for (c = nextc(&cp, &tp->t_can); c ; c = nextc(&cp, &tp->t_can))
1684 ttyecho(c, tp);
1685 cp = tp->t_raw.rb_hd;
1686 for (c = nextc(&cp, &tp->t_raw); c ; c = nextc(&cp, &tp->t_raw))
1687 ttyecho(c, tp);
1688 tp->t_state &= ~TS_ERASE;
1689 splx(s);
1690
1691 tp->t_rocount = RB_LEN(&tp->t_raw);
1692 tp->t_rocol = 0;
1693}
1694
1695/*
1696 * Echo a typed character to the terminal.
1697 */
1698ttyecho(c, tp)
1699 register c;
1700 register struct tty *tp;
1701{
1702 if ((tp->t_state&TS_CNTTB) == 0)
1703 tp->t_lflag &= ~FLUSHO;
1704 if (((tp->t_lflag&ECHO) == 0 &&
1705 ((tp->t_lflag&ECHONL) == 0 || c == '\n')) || (tp->t_lflag&EXTPROC))
1706 return;
1707 if (tp->t_lflag&ECHOCTL) {
1708 if ((c&TTY_CHARMASK) <= 037 && c != '\t' && c != '\n' ||
1709 c == 0177) {
1710 (void) ttyoutput('^', tp);
1711 c &= TTY_CHARMASK;
1712 if (c == 0177)
1713 c = '?';
1714 else
1715 c += 'A' - 1;
1716 }
1717 }
1718 (void) ttyoutput(c, tp);
1719}
1720
1721/*
1722 * send string cp to tp
1723 */
1724ttyoutstr(cp, tp)
1725 register char *cp;
1726 register struct tty *tp;
1727{
1728 register char c;
1729
1730 while (c = *cp++)
1731 (void) ttyoutput(c, tp);
1732}
1733
1734/*
1735 * Wake up any readers on a tty.
1736 */
1737ttwakeup(tp)
1738 register struct tty *tp;
1739{
1740
1741 if (tp->t_rsel) {
1742 selwakeup(tp->t_rsel, tp->t_state&TS_RCOLL);
1743 tp->t_state &= ~TS_RCOLL;
1744 tp->t_rsel = 0;
1745 }
1746 if (tp->t_state & TS_ASYNC)
1747 pgsignal(tp->t_pgrp, SIGIO, 1);
1748 wakeup((caddr_t)&tp->t_raw);
1749}
1750
1751/*
1752 * Look up a code for a specified speed in a conversion table;
1753 * used by drivers to map software speed values to hardware parameters.
1754 */
1755ttspeedtab(speed, table)
1756 register struct speedtab *table;
1757{
1758
1759 for ( ; table->sp_speed != -1; table++)
1760 if (table->sp_speed == speed)
1761 return (table->sp_code);
1762 return (-1);
1763}
1764
1765/*
1766 * set tty hi and low water marks
1767 *
1768 * Try to arrange the dynamics so there's about one second
1769 * from hi to low water.
1770 *
1771 */
1772ttsetwater(tp)
1773 struct tty *tp;
1774{
1775 register cps = tp->t_ospeed / 10;
1776 register x;
1777
1778#define clamp(x, h, l) ((x)>h ? h : ((x)<l) ? l : (x))
1779 tp->t_lowat = x = clamp(cps/2, TTMAXLOWAT, TTMINLOWAT);
1780 x += cps;
1781 x = clamp(x, TTMAXHIWAT, TTMINHIWAT);
1782 tp->t_hiwat = roundup(x, CBSIZE);
1783#undef clamp
1784}
1785
1786/*
1787 * Report on state of foreground process group.
1788 */
1789ttyinfo(tp)
1790 register struct tty *tp;
1791{
1792 register struct proc *p, *pick;
1793 struct timeval utime, stime;
1794 int tmp;
1795
1796 if (ttycheckoutq(tp,0) == 0)
1797 return;
1798
1799 /* Print load average. */
1800 tmp = (averunnable[0] * 100 + FSCALE / 2) >> FSHIFT;
1801 ttyprintf(tp, "load: %d.%02d ", tmp / 100, tmp % 100);
1802
1803 if (tp->t_session == NULL)
1804 ttyprintf(tp, "not a controlling terminal\n");
1805 else if (tp->t_pgrp == NULL)
1806 ttyprintf(tp, "no foreground process group\n");
1807 else if ((p = tp->t_pgrp->pg_mem) == NULL)
1808 ttyprintf(tp, "empty foreground process group\n");
1809 else {
1810 /* Pick interesting process. */
1811 for (pick = NULL; p != NULL; p = p->p_pgrpnxt)
1812 if (proc_compare(pick, p))
1813 pick = p;
1814
1815 ttyprintf(tp, " cmd: %s %d [%s] ", pick->p_comm, pick->p_pid,
1816 pick->p_stat == SRUN ? "running" :
1817 pick->p_wmesg ? pick->p_wmesg : "iowait");
1818
1819 /*
1820 * Lock out clock if process is running; get user/system
1821 * cpu time.
1822 */
1823 if (curproc == pick)
1824 tmp = splclock();
1825 utime = pick->p_utime;
1826 stime = pick->p_stime;
1827 if (curproc == pick)
1828 splx(tmp);
1829
1830 /* Print user time. */
1831 ttyprintf(tp, "%d.%02du ",
1832 utime.tv_sec, (utime.tv_usec + 5000) / 10000);
1833
1834 /* Print system time. */
1835 ttyprintf(tp, "%d.%02ds ",
1836 stime.tv_sec, (stime.tv_usec + 5000) / 10000);
1837
1838#define pgtok(a) (((a) * NBPG) / 1024)
1839 /* Print percentage cpu, resident set size. */
1840 tmp = pick->p_pctcpu * 10000 + FSCALE / 2 >> FSHIFT;
1841 ttyprintf(tp, "%d%% %dk\n",
1842 tmp / 100, pgtok(pick->p_vmspace->vm_rssize));
1843 }
1844 tp->t_rocount = 0; /* so pending input will be retyped if BS */
1845}
1846
1847/*
1848 * Returns 1 if p2 is "better" than p1
1849 *
1850 * The algorithm for picking the "interesting" process is thus:
1851 *
1852 * 1) (Only foreground processes are eligable - implied)
1853 * 2) Runnable processes are favored over anything
1854 * else. The runner with the highest cpu
1855 * utilization is picked (p_cpu). Ties are
1856 * broken by picking the highest pid.
1857 * 3 Next, the sleeper with the shortest sleep
1858 * time is favored. With ties, we pick out
1859 * just "short-term" sleepers (SSINTR == 0).
1860 * Further ties are broken by picking the highest
1861 * pid.
1862 *
1863 */
1864#define isrun(p) (((p)->p_stat == SRUN) || ((p)->p_stat == SIDL))
1865#define TESTAB(a, b) ((a)<<1 | (b))
1866#define ONLYA 2
1867#define ONLYB 1
1868#define BOTH 3
1869
1870static int
1871proc_compare(p1, p2)
1872 register struct proc *p1, *p2;
1873{
1874
1875 if (p1 == NULL)
1876 return (1);
1877 /*
1878 * see if at least one of them is runnable
1879 */
1880 switch (TESTAB(isrun(p1), isrun(p2))) {
1881 case ONLYA:
1882 return (0);
1883 case ONLYB:
1884 return (1);
1885 case BOTH:
1886 /*
1887 * tie - favor one with highest recent cpu utilization
1888 */
1889 if (p2->p_cpu > p1->p_cpu)
1890 return (1);
1891 if (p1->p_cpu > p2->p_cpu)
1892 return (0);
1893 return (p2->p_pid > p1->p_pid); /* tie - return highest pid */
1894 }
1895 /*
1896 * weed out zombies
1897 */
1898 switch (TESTAB(p1->p_stat == SZOMB, p2->p_stat == SZOMB)) {
1899 case ONLYA:
1900 return (1);
1901 case ONLYB:
1902 return (0);
1903 case BOTH:
1904 return (p2->p_pid > p1->p_pid); /* tie - return highest pid */
1905 }
1906 /*
1907 * pick the one with the smallest sleep time
1908 */
1909 if (p2->p_slptime > p1->p_slptime)
1910 return (0);
1911 if (p1->p_slptime > p2->p_slptime)
1912 return (1);
1913 /*
1914 * favor one sleeping in a non-interruptible sleep
1915 */
1916 if (p1->p_flag&SSINTR && (p2->p_flag&SSINTR) == 0)
1917 return (1);
1918 if (p2->p_flag&SSINTR && (p1->p_flag&SSINTR) == 0)
1919 return (0);
1920 return (p2->p_pid > p1->p_pid); /* tie - return highest pid */
1921}
1922
1923/*
1924 * Output char to tty; console putchar style.
1925 */
1926tputchar(c, tp)
1927 int c;
1928 struct tty *tp;
1929{
1930 register s = spltty();
1931
1932 if ((tp->t_state & (TS_CARR_ON|TS_ISOPEN)) == (TS_CARR_ON|TS_ISOPEN)) {
1933 if (c == '\n')
1934 (void) ttyoutput('\r', tp);
1935 (void) ttyoutput(c, tp);
1936 ttstart(tp);
1937 splx(s);
1938 return (0);
1939 }
1940 splx(s);
1941 return (-1);
1942}
1943
1944/*
1945 * Sleep on chan, returning ERESTART if tty changed
1946 * while we napped and returning any errors (e.g. EINTR/ETIMEDOUT)
1947 * reported by tsleep. If the tty is revoked, restarting a pending
1948 * call will redo validation done at the start of the call.
1949 */
1950ttysleep(tp, chan, pri, wmesg, timo)
1951 struct tty *tp;
1952 caddr_t chan;
1953 int pri;
1954 char *wmesg;
1955 int timo;
1956{
1957 int error;
1958 short gen = tp->t_gen;
1959
1960 if (error = tsleep(chan, pri, wmesg, timo))
1961 return (error);
1962 if (tp->t_gen != gen)
1963 return (ERESTART);
1964 return (0);
1965}