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