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