new terminal driver
authorMarc Teitelbaum <marc@ucbvax.Berkeley.EDU>
Wed, 19 Oct 1988 07:16:58 +0000 (23:16 -0800)
committerMarc Teitelbaum <marc@ucbvax.Berkeley.EDU>
Wed, 19 Oct 1988 07:16:58 +0000 (23:16 -0800)
SCCS-vsn: sys/kern/tty_conf.c 7.3
SCCS-vsn: sys/kern/tty_tty.c 7.2
SCCS-vsn: sys/kern/tty.c 7.13
SCCS-vsn: sys/kern/tty_pty.c 7.4
SCCS-vsn: sys/kern/tty_compat.c 1.2
SCCS-vsn: sys/kern/tty_subr.c 7.4

usr/src/sys/kern/tty.c
usr/src/sys/kern/tty_compat.c
usr/src/sys/kern/tty_conf.c
usr/src/sys/kern/tty_pty.c
usr/src/sys/kern/tty_subr.c
usr/src/sys/kern/tty_tty.c

index b4a1086..9104665 100644 (file)
@@ -3,7 +3,7 @@
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
- *     @(#)tty.c       7.12 (Berkeley) %G%
+ *     @(#)tty.c       7.13 (Berkeley) %G%
  */
 
 #include "../machine/reg.h"
  */
 
 #include "../machine/reg.h"
 #include "ttydefaults.h"
 #undef TTYDEFCHARS
 #include "termios.h"
 #include "ttydefaults.h"
 #undef TTYDEFCHARS
 #include "termios.h"
+#define TTYDEFCHARS
+#include "ttydefaults.h"
+#undef TTYDEFCHARS
+#include "termios.h"
 #include "proc.h"
 #include "file.h"
 #include "conf.h"
 #include "proc.h"
 #include "file.h"
 #include "conf.h"
 #include "uio.h"
 #include "kernel.h"
 #include "syslog.h"
 #include "uio.h"
 #include "kernel.h"
 #include "syslog.h"
+#include "syslog.h"
 
 /*
  * Table giving parity for characters and indicating
 
 /*
  * Table giving parity for characters and indicating
- * character classes to tty driver.  In particular,
- * if the low 6 bits are 0, then the character needs
- * no special processing on output.
+ * character classes to tty driver. The 8th bit
+ * indicates parity, the 7th bit indicates the character
+ * is an alphameric or underscore (for ALTWERASE), and the 
+ * low 6 bits indicate delay type.  If the low 6 bits are 0
+ * then the character needs no special processing on output.
  */
 
 char partab[] = {
  */
 
 char partab[] = {
-       0001,0201,0201,0001,0201,0001,0001,0201,
-       0202,0004,0003,0201,0005,0206,0201,0001,
-       0201,0001,0001,0201,0001,0201,0201,0001,
-       0001,0201,0201,0001,0201,0001,0001,0201,
-       0200,0000,0000,0200,0000,0200,0200,0000,
-       0000,0200,0200,0000,0200,0000,0000,0200,
-       0000,0200,0200,0000,0200,0000,0000,0200,
-       0200,0000,0000,0200,0000,0200,0200,0000,
-       0200,0000,0000,0200,0000,0200,0200,0000,
-       0000,0200,0200,0000,0200,0000,0000,0200,
-       0000,0200,0200,0000,0200,0000,0000,0200,
-       0200,0000,0000,0200,0000,0200,0200,0000,
-       0000,0200,0200,0000,0200,0000,0000,0200,
-       0200,0000,0000,0200,0000,0200,0200,0000,
-       0200,0000,0000,0200,0000,0200,0200,0000,
-       0000,0200,0200,0000,0200,0000,0000,0201,
-
+       0001,0201,0201,0001,0201,0001,0001,0201,        /* nul - bel */
+       0202,0004,0003,0201,0005,0206,0201,0001,        /* bs - si */
+       0201,0001,0001,0201,0001,0201,0201,0001,        /* dle - etb */
+       0001,0201,0201,0001,0201,0001,0001,0201,        /* can - us */
+       0200,0000,0000,0200,0000,0200,0200,0000,        /* sp - ' */
+       0000,0200,0200,0000,0200,0000,0000,0200,        /* ( - / */
+       0100,0300,0300,0100,0300,0100,0100,0300,        /* 0 - 7 */
+       0300,0100,0000,0200,0000,0200,0200,0000,        /* 8 - ? */
+       0200,0100,0100,0300,0100,0300,0300,0100,        /* @ - G */
+       0100,0300,0300,0100,0300,0100,0100,0300,        /* H - O */
+       0100,0300,0300,0100,0300,0100,0100,0300,        /* P - W */
+       0300,0100,0100,0200,0000,0200,0200,0300,        /* X - _ */
+       0000,0300,0300,0100,0300,0100,0100,0300,        /* ` - g */
+       0300,0100,0100,0300,0100,0300,0300,0100,        /* h - o */
+       0300,0100,0100,0300,0100,0300,0300,0100,        /* p - w */
+       0100,0300,0300,0000,0200,0000,0000,0201,        /* x - del */
        /*
        /*
-        * 7 bit ascii ends with the last character above,
-        * but we contine through all 256 codes for the sake
-        * of the tty output routines which use special vax
-        * instructions which need a 256 character trt table.
+        * meta chars
         */
         */
-
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007,
-       0007,0007,0007,0007,0007,0007,0007,0007
-};
-
-/*
- * Input mapping table-- if an entry is non-zero, when the
- * corresponding character is typed preceded by "\" the escape
- * sequence is replaced by the table value.  Mostly used for
- * upper-case only terminals.
- */
-char   maptab[] ={
-       000,000,000,000,000,000,000,000,
-       000,000,000,000,000,000,000,000,
-       000,000,000,000,000,000,000,000,
-       000,000,000,000,000,000,000,000,
-       000,'|',000,000,000,000,000,'`',
-       '{','}',000,000,000,000,000,000,
-       000,000,000,000,000,000,000,000,
-       000,000,000,000,000,000,000,000,
-       000,000,000,000,000,000,000,000,
-       000,000,000,000,000,000,000,000,
-       000,000,000,000,000,000,000,000,
-       000,000,000,000,000,000,'~',000,
-       000,'A','B','C','D','E','F','G',
-       'H','I','J','K','L','M','N','O',
-       'P','Q','R','S','T','U','V','W',
-       'X','Y','Z',000,000,000,000,000,
+       0001,0201,0201,0001,0201,0001,0001,0201,        /* nul - bel */
+       0202,0004,0003,0201,0005,0206,0201,0001,        /* bs - si */
+       0201,0001,0001,0201,0001,0201,0201,0001,        /* dle - etb */
+       0001,0201,0201,0001,0201,0001,0001,0201,        /* can - us */
+       0200,0000,0000,0200,0000,0200,0200,0000,        /* sp - ' */
+       0000,0200,0200,0000,0200,0000,0000,0200,        /* ( - / */
+       0100,0300,0300,0100,0300,0100,0100,0300,        /* 0 - 7 */
+       0300,0100,0000,0200,0000,0200,0200,0000,        /* 8 - ? */
+       0200,0100,0100,0300,0100,0300,0300,0100,        /* @ - G */
+       0100,0300,0300,0100,0300,0100,0100,0300,        /* H - O */
+       0100,0300,0300,0100,0300,0100,0100,0300,        /* P - W */
+       0300,0100,0100,0200,0000,0200,0200,0300,        /* X - _ */
+       0000,0300,0300,0100,0300,0100,0100,0300,        /* ` - g */
+       0300,0100,0100,0300,0100,0300,0300,0100,        /* h - o */
+       0300,0100,0100,0300,0100,0300,0300,0100,        /* p - w */
+       0100,0300,0300,0000,0200,0000,0000,0201,        /* x - del */
 };
 
 };
 
-short  tthiwat[16] =
-   { 100,100,100,100,100,100,100,200,200,400,400,400,650,650,1300,2000 };
-short  ttlowat[16] =
-   {  30, 30, 30, 30, 30, 30, 30, 50, 50,120,120,120,125,125,125,125 };
-
 extern struct tty *constty;            /* temporary virtual console */
 extern char partab[], maptab[];
 
 extern struct tty *constty;            /* temporary virtual console */
 extern char partab[], maptab[];
 
+/*
+ * Is 'c' a line delimiter ("break" character)?
+ */
+#define ttbreakc(c) (c == '\n' || CCEQ(cc[VEOF], c) || \
+               CCEQ(cc[VEOL], c) || CCEQ(cc[VEOL2], c))
+
 /*
  * Debugging aids
  */
 /*
  * Debugging aids
  */
@@ -138,6 +116,9 @@ ttywflush(tp)
        ttyflush(tp, FREAD);
 }
 
        ttyflush(tp, FREAD);
 }
 
+/*
+ * Wait for output to drain.
+ */
 /*
  * Wait for output to drain.
  */
 /*
  * Wait for output to drain.
  */
@@ -252,6 +233,7 @@ ttioctl(tp, com, data, flag)
        caddr_t data;
 {
        extern int nldisp;
        caddr_t data;
 {
        extern int nldisp;
+       int softset = 0;
        int soft;
        int s;
 
        int soft;
        int s;
 
@@ -264,7 +246,6 @@ ttioctl(tp, com, data, flag)
 
        case TIOCSETD: 
        case TIOCFLUSH:
 
        case TIOCSETD: 
        case TIOCFLUSH:
-       case TIOCSPGRP:
        case TIOCSTI:
        case TIOCSWINSZ:
        case TIOCSETA:
        case TIOCSTI:
        case TIOCSWINSZ:
        case TIOCSETA:
@@ -273,12 +254,13 @@ ttioctl(tp, com, data, flag)
        case TIOCSETAS:
        case TIOCSETAWS:
        case TIOCSETAFS:
        case TIOCSETAS:
        case TIOCSETAWS:
        case TIOCSETAFS:
-               while (tp->t_line == POSXDISC &&
-                  u.u_procp->p_pgrp != tp->t_pgrp && tp == u.u_ttyp &&
+               while (u.u_procp->p_pgid != tp->t_pgid &&
+                  tp == u.u_ttyp &&
+                  u.u_procp->p_pgrp->pg_jobc &&
                   (u.u_procp->p_flag&SVFORK) == 0 &&
                   !(u.u_procp->p_sigignore & sigmask(SIGTTOU)) &&
                   !(u.u_procp->p_sigmask & sigmask(SIGTTOU))) {
                   (u.u_procp->p_flag&SVFORK) == 0 &&
                   !(u.u_procp->p_sigignore & sigmask(SIGTTOU)) &&
                   !(u.u_procp->p_sigmask & sigmask(SIGTTOU))) {
-                       gsignal(u.u_procp->p_pgrp, SIGTTOU);
+                       pgsignal(u.u_procp->p_pgrp, SIGTTOU);
                        sleep((caddr_t)&lbolt, TTOPRI);
                }
                break;
                        sleep((caddr_t)&lbolt, TTOPRI);
                }
                break;
@@ -298,9 +280,10 @@ ttioctl(tp, com, data, flag)
        case TIOCSETD: {
                register int t = *(int *)data;
                dev_t dev = tp->t_dev;
        case TIOCSETD: {
                register int t = *(int *)data;
                dev_t dev = tp->t_dev;
+               dev_t dev = tp->t_dev;
                int error = 0;
 
                int error = 0;
 
-               if ((unsigned) t >= nldisp)
+               if ((unsigned)t >= nldisp)
                        return (ENXIO);
                if (t != tp->t_line) {
                        s = spltty();
                        return (ENXIO);
                if (t != tp->t_line) {
                        s = spltty();
@@ -390,20 +373,6 @@ ttioctl(tp, com, data, flag)
                break;
        }
 
                break;
        }
 
-       case TIOCSETAS:
-       case TIOCSETAWS:
-       case TIOCSETAFS:
-               soft = 1;
-               goto set;
-       case TIOCSETA:
-       case TIOCSETAW:
-       case TIOCSETAF:
-               soft = 0;
-set:
-               {
-               register struct termios *t = (struct termios *)data;
-
-               s = spltty();
                if (com == TIOCSETAF || com == TIOCSETAFS) 
                        ttywflush(tp);
                else {
                if (com == TIOCSETAF || com == TIOCSETAFS) 
                        ttywflush(tp);
                else {
@@ -432,16 +401,16 @@ set:
                        tp->t_ispeed = t->c_ispeed;
                        tp->t_ospeed = t->c_ospeed;
                }
                        tp->t_ispeed = t->c_ispeed;
                        tp->t_ospeed = t->c_ospeed;
                }
+               tp->t_iflag = t->c_iflag;
+               tp->t_oflag = t->c_oflag;
+               tp->t_lflag = t->c_lflag;
+               bcopy(t->c_cc, tp->t_cc, sizeof(t->c_cc));
                splx(s);
                if (tp->t_trace & TTRACE_STATE)
                        ttytrace(com, tp);
                break;
        }
 
                splx(s);
                if (tp->t_trace & TTRACE_STATE)
                        ttytrace(com, tp);
                break;
        }
 
-       case TIOCTRACE:
-               tp->t_trace = *(int *)data;
-               break;
-
        case FIONBIO:
                if (*(int *)data)
                        tp->t_state |= TS_NBIO;
        case FIONBIO:
                if (*(int *)data)
                        tp->t_state |= TS_NBIO;
@@ -456,36 +425,34 @@ set:
                        tp->t_state &= ~TS_ASYNC;
                break;
 
                        tp->t_state &= ~TS_ASYNC;
                break;
 
-
        /*
        /*
-        * Allow SPGRP only if tty is open for reading.
-        * Quick check: if we can find a process in the new pgrp,
-        * this user must own that process.
-        * SHOULD VERIFY THAT PGRP IS IN USE AND IS THIS USER'S.
+        * Set terminal process group.
         */
        case TIOCSPGRP: {
         */
        case TIOCSPGRP: {
-               struct proc *p;
-               int pgrp = *(int *)data;
-
-               if (u.u_uid && (flag & FREAD) == 0)
-                       return (EPERM);
-               p = pfind(pgrp);
-               if (p && p->p_pgrp == pgrp &&
-                   p->p_uid != u.u_uid && u.u_uid && !inferior(p))
-                       return (EPERM);
-               tp->t_pgrp = pgrp;
+               register struct proc *p = u.u_procp;
+               register struct pgrp *pgrp = pgfind(*(int *)data);
+
+               if (u.u_uid && 
+                   (tp != u.u_ttyp ||
+                   (pgrp && pgrp->pg_session != p->p_session))) {
+                       if (u.u_ttyp == NULL)
+                               return (ENOTTY);
+                       else
+                               return (EPERM);
+               }
+               tp->t_pgid = *(int *)data;
                break;
        }
 
        case TIOCGPGRP:
                break;
        }
 
        case TIOCGPGRP:
-               *(int *)data = tp->t_pgrp;
+               *(int *)data = tp->t_pgid;
                break;
 
        case TIOCSWINSZ:
                if (bcmp((caddr_t)&tp->t_winsize, data,
                    sizeof (struct winsize))) {
                        tp->t_winsize = *(struct winsize *)data;
                break;
 
        case TIOCSWINSZ:
                if (bcmp((caddr_t)&tp->t_winsize, data,
                    sizeof (struct winsize))) {
                        tp->t_winsize = *(struct winsize *)data;
-                       gsignal(tp->t_pgrp, SIGWINCH);
+                       gsignal(tp->t_pgid, SIGWINCH);
                }
                break;
 
                }
                break;
 
@@ -506,6 +473,23 @@ set:
                        constty = NULL;
                break;
 
                        constty = NULL;
                break;
 
+#ifdef COMPAT_43
+       case TIOCGETP:
+       case TIOCSETP:
+       case TIOCSETN:
+       case TIOCGETC:
+       case TIOCSETC:
+       case TIOCSLTC:
+       case TIOCGLTC:
+       case TIOCLBIS:
+       case TIOCLBIC:
+       case TIOCLSET:
+       case TIOCLGET:
+       case TIOCGETDCOMPAT:
+       case TIOCSETDCOMPAT:
+               return(ttcompat(tp, com, data, flag));
+#endif
+
        /* allow old ioctls for now */
        case TIOCGETP:
        case TIOCSETP:
        /* allow old ioctls for now */
        case TIOCGETP:
        case TIOCSETP:
@@ -600,7 +584,7 @@ ttselect(dev, rw)
                break;
 
        case FWRITE:
                break;
 
        case FWRITE:
-               if (tp->t_outq.c_cc <= TTLOWAT(tp))
+               if (tp->t_outq.c_cc <= tp->t_lowat)
                        goto win;
                if (tp->t_wsel && tp->t_wsel->p_wchan == (caddr_t)&selwait)
                        tp->t_state |= TS_WCOLL;
                        goto win;
                if (tp->t_wsel && tp->t_wsel->p_wchan == (caddr_t)&selwait)
                        tp->t_state |= TS_WCOLL;
@@ -617,8 +601,6 @@ win:
 
 /*
  * Initial open of tty, or (re)entry to line discipline.
 
 /*
  * Initial open of tty, or (re)entry to line discipline.
- * Establish a process group for distribution of
- * quits and interrupts from the tty.
  */
 ttyopen(dev, tp)
        dev_t dev;
  */
 ttyopen(dev, tp)
        dev_t dev;
@@ -626,15 +608,8 @@ ttyopen(dev, tp)
 {
        register struct proc *pp;
 
 {
        register struct proc *pp;
 
-       pp = u.u_procp;
        tp->t_dev = dev;
        tp->t_dev = dev;
-       if (pp->p_pgrp == 0) {  /* XXX - this has got to change */
-               u.u_ttyp = tp;
-               u.u_ttyd = dev;
-               if (tp->t_pgrp == 0)
-                       tp->t_pgrp = pp->p_pid;
-               pp->p_pgrp = tp->t_pgrp;
-       }
+
        tp->t_state &= ~TS_WOPEN;
        if ((tp->t_state & TS_ISOPEN) == 0) {
                tp->t_state |= TS_ISOPEN;
        tp->t_state &= ~TS_WOPEN;
        if ((tp->t_state & TS_ISOPEN) == 0) {
                tp->t_state |= TS_ISOPEN;
@@ -663,11 +638,10 @@ ttylclose(tp)
 ttyclose(tp)
        register struct tty *tp;
 {
 ttyclose(tp)
        register struct tty *tp;
 {
-
        if (constty == tp)
                constty = NULL;
        ttyflush(tp, FREAD|FWRITE);
        if (constty == tp)
                constty = NULL;
        ttyflush(tp, FREAD|FWRITE);
-       tp->t_pgrp = 0;
+       tp->t_pgid = 0;
        tp->t_state = 0;
 }
 
        tp->t_state = 0;
 }
 
@@ -698,8 +672,8 @@ ttymodem(tp, flag)
                tp->t_state &= ~TS_CARR_ON;
                if (tp->t_state & TS_ISOPEN) {
                        if ((tp->t_lflag & NOHANG) == 0) {
                tp->t_state &= ~TS_CARR_ON;
                if (tp->t_state & TS_ISOPEN) {
                        if ((tp->t_lflag & NOHANG) == 0) {
-                               gsignal(tp->t_pgrp, SIGHUP);
-                               gsignal(tp->t_pgrp, SIGCONT);
+                               gsignal(tp->t_pgid, SIGHUP);
+                               gsignal(tp->t_pgid, SIGCONT);
                                ttyflush(tp, FREAD|FWRITE);
                                return (0);
                        }
                                ttyflush(tp, FREAD|FWRITE);
                                return (0);
                        }
@@ -751,6 +725,7 @@ ttypend(tp)
 }
 
 /*
 }
 
 /*
+ *
  *
  * Place a character on raw TTY input queue,
  * putting in delimiters and waking up top
  *
  * Place a character on raw TTY input queue,
  * putting in delimiters and waking up top
@@ -772,9 +747,18 @@ ttyinput(c, tp)
         */
        if (lflag&PENDIN)
                ttypend(tp);
         */
        if (lflag&PENDIN)
                ttypend(tp);
+       /*
+        * Gather stats.
+        */
 
        tk_nin++;
 
        tk_nin++;
-
+       if (lflag&ICANON) {
+               tk_cancc++;
+               tp->t_cancc++;
+       } else {
+               tk_rawcc++;
+               tp->t_rawcc++;
+       }
        /*
         * Handle exceptional conditions (break, parity, framing).
         */
        /*
         * Handle exceptional conditions (break, parity, framing).
         */
@@ -798,7 +782,6 @@ ttyinput(c, tp)
                                c = 0;
                }
        }
                                c = 0;
                }
        }
-
        dprintf("<%o>\n", c);
 
        /*
        dprintf("<%o>\n", c);
 
        /*
@@ -808,8 +791,7 @@ ttyinput(c, tp)
                ttyblock(tp);
 
        /*
                ttyblock(tp);
 
        /*
-        * Ignore any high bit added during
-        * previous ttyinput processing.
+        * In tandem mode, check high water mark.
         */
        if ((tp->t_state&TS_TYPEN) == 0 && (iflag&ISTRIP))
                c &= 0177;
         */
        if ((tp->t_state&TS_TYPEN) == 0 && (iflag&ISTRIP))
                c &= 0177;
@@ -817,10 +799,9 @@ ttyinput(c, tp)
         * Check for literal nexting very first
         */
        if (tp->t_state&TS_LNCH) {
         * Check for literal nexting very first
         */
        if (tp->t_state&TS_LNCH) {
-               c |= 0200;
+               c |= TTY_QUOTE;
                tp->t_state &= ~TS_LNCH;
        }
                tp->t_state &= ~TS_LNCH;
        }
-
        /*
         * Scan for special characters.  This code
         * is really just a big case statement with
        /*
         * Scan for special characters.  This code
         * is really just a big case statement with
@@ -870,11 +851,10 @@ ttyinput(c, tp)
                        if ((lflag&NOFLSH) == 0)
                                ttyflush(tp, FREAD);
                        ttyecho(c, tp);
                        if ((lflag&NOFLSH) == 0)
                                ttyflush(tp, FREAD);
                        ttyecho(c, tp);
-                       gsignal(tp->t_pgrp, SIGTSTP);
+                       gsignal(tp->t_pgid, SIGTSTP);
                        goto endcase;
                }
        }
                        goto endcase;
                }
        }
-
        /*
         * Handle start/stop characters.
         */
        /*
         * Handle start/stop characters.
         */
@@ -895,7 +875,6 @@ ttyinput(c, tp)
                if (CCEQ(cc[VSTART], c))
                        goto restartoutput;
        }
                if (CCEQ(cc[VSTART], c))
                        goto restartoutput;
        }
-
        /*
         * IGNCR, ICRNL, & INLCR
         */
        /*
         * IGNCR, ICRNL, & INLCR
         */
@@ -907,44 +886,29 @@ ttyinput(c, tp)
        }
        else if (c == '\n' && iflag&INLCR)
                c = '\r';
        }
        else if (c == '\n' && iflag&INLCR)
                c = '\r';
-
-#ifdef notdef
-       /*
-        * We'd like to completely remove it.
-        */
-       if (tp->t_flags & LCASE && c <= 0177) {
-               if (tp->t_state&TS_BKSL) {
-                       ttyrub(unputc(&tp->t_rawq), tp);
-                       if (maptab[c])
-                               c = maptab[c];
-                       c |= 0200;
-                       tp->t_state &= ~(TS_BKSL|TS_QUOT);
-               } else if (c >= 'A' && c <= 'Z')
-                       c += 'a' - 'A';
-               else if (c == '\\')
-                       tp->t_state |= TS_BKSL;
-       }
-#endif /*notdef*/
-
+       else if (c == '\n' && iflag&INLCR)
+               c = '\r';
        /*
         * Non canonical mode, don't process line editing
         * characters; check high water mark for wakeup.
         * 
        /*
         * Non canonical mode, don't process line editing
         * characters; check high water mark for wakeup.
         * 
+        * 
         */
        if (!(lflag&ICANON)) {
                if (tp->t_rawq.c_cc > TTYHOG) {
                        if (iflag&IMAXBEL) {
         */
        if (!(lflag&ICANON)) {
                if (tp->t_rawq.c_cc > TTYHOG) {
                        if (iflag&IMAXBEL) {
-                               if (tp->t_outq.c_cc < TTHIWAT(tp))
+                               if (tp->t_outq.c_cc < tp->t_hiwat)
                                        (void) ttyoutput(CTRL('g'), tp);
                        } else
                                ttyflush(tp, FREAD | FWRITE);
                                        (void) ttyoutput(CTRL('g'), tp);
                        } else
                                ttyflush(tp, FREAD | FWRITE);
-               } else if (putc(c, &tp->t_rawq) >= 0) {
-                       ttwakeup(tp);
-                       ttyecho(c, tp);
+               } else {
+                       if (putc(c, &tp->t_rawq) >= 0) {
+                               ttwakeup(tp);
+                               ttyecho(c, tp);
+                       }
                }
                goto endcase;
        }
                }
                goto endcase;
        }
-
        /*
         * From here on down canonical mode character
         * processing takes place.
        /*
         * From here on down canonical mode character
         * processing takes place.
@@ -956,11 +920,6 @@ ttyinput(c, tp)
         * Historically is '\' , but can be changed (read: disabled)
         * with the VQUOTE subscript.
         */
         * Historically is '\' , but can be changed (read: disabled)
         * with the VQUOTE subscript.
         */
-       if ((tp->t_state&TS_QUOT) &&
-           (CCEQ(cc[VERASE], c) || CCEQ(cc[VKILL], c) || CCEQ(cc[VEOF], c))) {
-               ttyrub(unputc(&tp->t_rawq), tp);
-               c |= 0200;
-       }
 
        /*
         * erase (^H / ^?)
 
        /*
         * erase (^H / ^?)
@@ -989,25 +948,9 @@ ttyinput(c, tp)
                tp->t_state &= ~TS_LOCAL;
                goto endcase;
        }
                tp->t_state &= ~TS_LOCAL;
                goto endcase;
        }
-
        /*
         * word erase (^W)
         */
        /*
         * word erase (^W)
         */
-       if (CCEQ(cc[VWERASE], c)) {     
-               if (tp->t_rawq.c_cc == 0)
-                       goto endcase;
-               do {
-                       c = unputc(&tp->t_rawq);
-                       if (c != ' ' && c != '\t')
-                               goto erasenb;
-                       ttyrub(c, tp);
-               } while (tp->t_rawq.c_cc);
-               goto endcase;
-erasenb:
-               do {
-                       ttyrub(c, tp);
-                       if (tp->t_rawq.c_cc == 0)
-                               goto endcase;
                        c = unputc(&tp->t_rawq);
                } while (c != ' ' && c != '\t');
                (void) putc(c, &tp->t_rawq);
                        c = unputc(&tp->t_rawq);
                } while (c != ' ' && c != '\t');
                (void) putc(c, &tp->t_rawq);
@@ -1020,7 +963,13 @@ erasenb:
                ttyretype(tp);
                goto endcase;
        }
                ttyretype(tp);
                goto endcase;
        }
-
+       /*
+        * reprint line (^R)
+        */
+       if (CCEQ(cc[VREPRINT], c)) {
+               ttyretype(tp);
+               goto endcase;
+       }
        /*
         * Check for input buffer overflow
         */
        /*
         * Check for input buffer overflow
         */
@@ -1032,7 +981,6 @@ erasenb:
                        ttyflush(tp, FREAD | FWRITE);
                goto endcase;
        }
                        ttyflush(tp, FREAD | FWRITE);
                goto endcase;
        }
-
        /*
         * Put data char in q for user and
         * wakeup on seeing a line delimiter.
        /*
         * Put data char in q for user and
         * wakeup on seeing a line delimiter.
@@ -1044,10 +992,12 @@ erasenb:
                        ttwakeup(tp);
                } else if (tp->t_rocount++ == 0)
                        tp->t_rocol = tp->t_col;
                        ttwakeup(tp);
                } else if (tp->t_rocount++ == 0)
                        tp->t_rocol = tp->t_col;
-               tp->t_state &= ~TS_QUOT;
                if (CCEQ(cc[VQUOTE], c) && (iflag&ISTRIP))
                        tp->t_state |= TS_QUOT; /* '\' escape */
                if (tp->t_state&TS_ERASE) {
                if (CCEQ(cc[VQUOTE], c) && (iflag&ISTRIP))
                        tp->t_state |= TS_QUOT; /* '\' escape */
                if (tp->t_state&TS_ERASE) {
+                       /*
+                        * end of prterase \.../
+                        */
                        /*
                         * end of prterase \.../
                         */
                        /*
                         * end of prterase \.../
                         */
@@ -1097,13 +1047,13 @@ ttyoutput(c, tp)
 {
        register char *colp;
        register ctype;
 {
        register char *colp;
        register ctype;
-
        if (!(tp->t_oflag&OPOST)) {
                if (tp->t_lflag&FLUSHO) 
                        return (-1);
                if (putc(c, &tp->t_outq))
                        return (c);
                tk_nout++;
        if (!(tp->t_oflag&OPOST)) {
                if (tp->t_lflag&FLUSHO) 
                        return (-1);
                if (putc(c, &tp->t_outq))
                        return (c);
                tk_nout++;
+               tp->t_outcc++;
                return (-1);
        }
        c &= 0377;
                return (-1);
        }
        c &= 0377;
@@ -1118,54 +1068,33 @@ ttyoutput(c, tp)
                        s = spltty();           /* don't interrupt tabs */
                        c -= b_to_q("        ", c, &tp->t_outq);
                        tk_nout += c;
                        s = spltty();           /* don't interrupt tabs */
                        c -= b_to_q("        ", c, &tp->t_outq);
                        tk_nout += c;
+                       tp->t_outcc += c;
                        splx(s);
                }
                tp->t_col += c;
                return (c ? -1 : '\t');
        }
                        splx(s);
                }
                tp->t_col += c;
                return (c ? -1 : '\t');
        }
+       if (c == CEOT && oflag&ONOEOT)
+               return(-1);
        tk_nout++;
        tk_nout++;
+       tp->t_outcc++;
 #ifdef notdef
 #ifdef notdef
-       /*
-        * for upper-case-only terminals,
-        * generate escapes.
-        */
-       if (tp->t_flags&LCASE) {
-               colp = "({)}!|^~'`";
-               while (*colp++)
-                       if (c == *colp++) {
-                               if (ttyoutput('\\', tp) >= 0)
-                                       return (c);
-                               c = colp[-2];
-                               break;
-                       }
-               if ('A' <= c && c <= 'Z') {
-                       if (ttyoutput('\\', tp) >= 0)
-                               return (c);
-               } else if ('a' <= c && c <= 'z')
-                       c += 'A' - 'a';
-       }
-#endif
-
        /*
         * turn <nl> to <cr><lf> if desired.
         */
        /*
         * turn <nl> to <cr><lf> if desired.
         */
-       if (c == '\n' && (tp->t_oflag&ONLCR) && ttyoutput('\r', tp) >= 0)
-                       return (c);
-#ifdef notdef
-       if (c == '~' && tp->t_flags&TILDE)
-               c = '`';
 #endif
 #endif
+       if ((tp->t_lflag&FLUSHO) == 0 && putc(c, &tp->t_outq))
+               return (c);
        if ((tp->t_lflag&FLUSHO) == 0 && putc(c, &tp->t_outq))
                return (c);
        /*
         * Calculate delays.
         * The numbers here represent clock ticks
         * and are not necessarily optimal for all terminals.
        if ((tp->t_lflag&FLUSHO) == 0 && putc(c, &tp->t_outq))
                return (c);
        /*
         * Calculate delays.
         * The numbers here represent clock ticks
         * and are not necessarily optimal for all terminals.
-        * The delays are indicated by characters above 0200.
-        * In raw mode there are no delays and the
-        * transmission path is 8 bits wide.
         *
         * SHOULD JUST ALLOW USER TO SPECIFY DELAYS
         *
         * SHOULD JUST ALLOW USER TO SPECIFY DELAYS
+        *
+        * (actually, should THROW AWAY terminals which need delays)
         */
        colp = &tp->t_col;
        ctype = partab[c];
         */
        colp = &tp->t_col;
        ctype = partab[c];
@@ -1234,7 +1163,7 @@ ttyoutput(c, tp)
                *colp = 0;
        }
        if (c && (tp->t_lflag&FLUSHO) == 0)
                *colp = 0;
        }
        if (c && (tp->t_lflag&FLUSHO) == 0)
-               (void) putc(c|0200, &tp->t_outq);
+               (void) putc(c|TTY_QUOTE, &tp->t_outq);
        return (-1);
 }
 #undef mstohz
        return (-1);
 }
 #undef mstohz
@@ -1263,30 +1192,25 @@ loop:
        if (tp->t_lflag&PENDIN)
                ttypend(tp);
        splx(s);
        if (tp->t_lflag&PENDIN)
                ttypend(tp);
        splx(s);
-
        if ((tp->t_state&TS_CARR_ON)==0)
                return (EIO);
        if ((tp->t_state&TS_CARR_ON)==0)
                return (EIO);
-
        /*
         * Hang process if it's in the background.
         */
        /*
         * Hang process if it's in the background.
         */
-       if (tp == u.u_ttyp && u.u_procp->p_pgrp != tp->t_pgrp) {
+       if (u.u_ttyp == tp && u.u_procp->p_pgid != tp->t_pgid) {
                if ((u.u_procp->p_sigignore & sigmask(SIGTTIN)) ||
                   (u.u_procp->p_sigmask & sigmask(SIGTTIN)) ||
                if ((u.u_procp->p_sigignore & sigmask(SIGTTIN)) ||
                   (u.u_procp->p_sigmask & sigmask(SIGTTIN)) ||
-                   u.u_procp->p_flag&SVFORK)
+                   u.u_procp->p_flag&SVFORK || u.u_procp->p_pgrp->pg_jobc == 0)
                        return (EIO);
                        return (EIO);
-               gsignal(u.u_procp->p_pgrp, SIGTTIN);
+               pgsignal(u.u_procp->p_pgrp, SIGTTIN);
                sleep((caddr_t)&lbolt, TTIPRI);
                goto loop;
        }
                sleep((caddr_t)&lbolt, TTIPRI);
                goto loop;
        }
-       t_flags = tp->t_flags;
-
        /*
         * If canonical, use the canonical queue,
         * else use the raw queue.
         */
        qp = lflag&ICANON ? &tp->t_canq : &tp->t_rawq;
        /*
         * If canonical, use the canonical queue,
         * else use the raw queue.
         */
        qp = lflag&ICANON ? &tp->t_canq : &tp->t_rawq;
-
        /*
         * No input, sleep on rawq awaiting hardware
         * receipt and notification.
        /*
         * No input, sleep on rawq awaiting hardware
         * receipt and notification.
@@ -1303,7 +1227,6 @@ loop:
                goto loop;
        }
        splx(s);
                goto loop;
        }
        splx(s);
-
        /*
         * Input present, check for input mapping and processing.
         */
        /*
         * Input present, check for input mapping and processing.
         */
@@ -1313,7 +1236,7 @@ loop:
                 * delayed suspend (^Y)
                 */
                if (CCEQ(cc[VDSUSP], c) && lflag&ISIG) {
                 * delayed suspend (^Y)
                 */
                if (CCEQ(cc[VDSUSP], c) && lflag&ISIG) {
-                       gsignal(tp->t_pgrp, SIGTSTP);
+                       gsignal(tp->t_pgid, SIGTSTP);
                        if (first) {
                                sleep((caddr_t)&lbolt, TTIPRI);
                                goto loop;
                        if (first) {
                                sleep((caddr_t)&lbolt, TTIPRI);
                                goto loop;
@@ -1340,9 +1263,9 @@ loop:
                if (lflag&ICANON && ttbreakc(c)) {
                        break;
                }
                if (lflag&ICANON && ttbreakc(c)) {
                        break;
                }
+               }
                first = 0;
        }
                first = 0;
        }
-
 checktandem:
        /*
         * Look to unblock output now that (presumably)
 checktandem:
        /*
         * Look to unblock output now that (presumably)
@@ -1355,6 +1278,7 @@ checktandem:
                        ttstart(tp);
                }
        }
                        ttstart(tp);
                }
        }
+       }
        return (error);
 }
 
        return (error);
 }
 
@@ -1372,7 +1296,7 @@ ttycheckoutq(tp, wait)
 {
        int hiwat, s, oldsig;
 
 {
        int hiwat, s, oldsig;
 
-       hiwat = TTHIWAT(tp);
+       hiwat = tp->t_hiwat;
        s = spltty();
        oldsig = u.u_procp->p_sig;
        if (tp->t_outq.c_cc > hiwat + 200)
        s = spltty();
        oldsig = u.u_procp->p_sig;
        if (tp->t_outq.c_cc > hiwat + 200)
@@ -1403,7 +1327,7 @@ ttwrite(tp, uio)
        int i, hiwat, cnt, error, s;
        char obuf[OBUFSIZ];
 
        int i, hiwat, cnt, error, s;
        char obuf[OBUFSIZ];
 
-       hiwat = TTHIWAT(tp);
+       hiwat = tp->t_hiwat;
        cnt = uio->uio_resid;
        error = 0;
 loop:
        cnt = uio->uio_resid;
        error = 0;
 loop:
@@ -1412,15 +1336,14 @@ loop:
        /*
         * Hang the process if it's in the background.
         */
        /*
         * Hang the process if it's in the background.
         */
-       if (u.u_procp->p_pgrp != tp->t_pgrp && tp == u.u_ttyp &&
            (tp->t_lflag&TOSTOP) && (u.u_procp->p_flag&SVFORK)==0 &&
            !(u.u_procp->p_sigignore & sigmask(SIGTTOU)) &&
            (tp->t_lflag&TOSTOP) && (u.u_procp->p_flag&SVFORK)==0 &&
            !(u.u_procp->p_sigignore & sigmask(SIGTTOU)) &&
-           !(u.u_procp->p_sigmask & sigmask(SIGTTOU))) {
-               gsignal(u.u_procp->p_pgrp, SIGTTOU);
+           !(u.u_procp->p_sigmask & sigmask(SIGTTOU)) &&
+            u.u_procp->p_pgrp->pg_jobc) {
+               pgsignal(u.u_procp->p_pgrp, SIGTTOU);
                sleep((caddr_t)&lbolt, TTIPRI);
                goto loop;
        }
                sleep((caddr_t)&lbolt, TTIPRI);
                goto loop;
        }
-
        /*
         * Process the user's data in at most OBUFSIZ
         * chunks.  Perform lower case simulation and
        /*
         * Process the user's data in at most OBUFSIZ
         * chunks.  Perform lower case simulation and
@@ -1453,35 +1376,6 @@ loop:
                if (tp->t_lflag&FLUSHO)
                        continue;
 #ifdef notdef
                if (tp->t_lflag&FLUSHO)
                        continue;
 #ifdef notdef
-               /*
-                * If we're mapping lower case or kludging tildes,
-                * then we've got to look at each character, so
-                * just feed the stuff to ttyoutput...
-                */
-               if (tp->t_flags & (LCASE|TILDE)) {
-                       while (cc > 0) {
-                               c = *cp++;
-                               tp->t_rocount = 0;
-                               while ((c = ttyoutput(c, tp)) >= 0) {
-                                       /* out of clists, wait a bit */
-                                       ttstart(tp);
-                                       sleep((caddr_t)&lbolt, TTOPRI);
-                                       tp->t_rocount = 0;
-                                       if (cc != 0) {
-                                               uio->uio_iov->iov_base -= cc;
-                                               uio->uio_iov->iov_len += cc;
-                                               uio->uio_resid += cc;
-                                               uio->uio_offset -= cc;
-                                       }
-                                       goto loop;
-                               }
-                               --cc;
-                               if (tp->t_outq.c_cc > hiwat)
-                                       goto ovhiwat;
-                       }
-                       continue;
-               }
-#endif
                /*
                 * If nothing fancy need be done, grab those characters we
                 * can handle without any of ttyoutput's processing and
                /*
                 * If nothing fancy need be done, grab those characters we
                 * can handle without any of ttyoutput's processing and
@@ -1535,6 +1429,7 @@ loop:
                        ce -= i;
                        tp->t_col += ce;
                        cp += ce, cc -= ce, tk_nout += ce;
                        ce -= i;
                        tp->t_col += ce;
                        cp += ce, cc -= ce, tk_nout += ce;
+                       tp->t_outcc += ce;
                        if (i > 0) {
                                /* out of c-lists, wait a bit */
                                ttstart(tp);
                        if (i > 0) {
                                /* out of c-lists, wait a bit */
                                ttstart(tp);
@@ -1549,9 +1444,9 @@ loop:
                                goto ovhiwat;
                }
                ttstart(tp);
                                goto ovhiwat;
                }
                ttstart(tp);
+               ttstart(tp);
        }
        return (error);
        }
        return (error);
-
 ovhiwat:
        if (cc != 0) {
                uio->uio_iov->iov_base -= cc;
 ovhiwat:
        if (cc != 0) {
                uio->uio_iov->iov_base -= cc;
@@ -1596,8 +1491,6 @@ ttyrub(c, tp)
 
        if ((tp->t_lflag&ECHO) == 0)
                return;
 
        if ((tp->t_lflag&ECHO) == 0)
                return;
-       tp->t_lflag &= ~FLUSHO; 
-       c &= 0377;
        if (tp->t_lflag&ECHOE) {
                if (tp->t_rocount == 0) {
                        /*
        if (tp->t_lflag&ECHOE) {
                if (tp->t_rocount == 0) {
                        /*
@@ -1607,17 +1500,13 @@ ttyrub(c, tp)
                        return;
                }
                /* if tab or newline was escaped  - XXX - not 8bit */
                        return;
                }
                /* if tab or newline was escaped  - XXX - not 8bit */
-               if (c == ('\t'|0200) || c == ('\n'|0200))
+               if (c == ('\t'|TTY_QUOTE) || c == ('\n'|TTY_QUOTE))
                        ttyrubo(tp, 2);
                        ttyrubo(tp, 2);
-               else switch (partab[c&=0177]&0177) {
+               else switch (partab[c&=0377]&077) {
 
                case ORDINARY:
 #ifdef notdef
 
                case ORDINARY:
 #ifdef notdef
-                       if (tp->t_flags&LCASE && c >= 'A' && c <= 'Z')
-                               ttyrubo(tp, 2);
-                       else
-#endif
-                               ttyrubo(tp, 1);
+                       ttyrubo(tp, 1);
                        break;
 
                case VTAB:
                        break;
 
                case VTAB:
@@ -1628,7 +1517,9 @@ ttyrub(c, tp)
                                ttyrubo(tp, 2);
                        break;
 
                                ttyrubo(tp, 2);
                        break;
 
-               case TAB:
+               case TAB: {
+                       int c;
+
                        if (tp->t_rocount < tp->t_rawq.c_cc) {
                                ttyretype(tp);
                                return;
                        if (tp->t_rocount < tp->t_rawq.c_cc) {
                                ttyretype(tp);
                                return;
@@ -1639,8 +1530,6 @@ ttyrub(c, tp)
                        tp->t_lflag |= FLUSHO;
                        tp->t_col = tp->t_rocol;
                        cp = tp->t_rawq.c_cf;
                        tp->t_lflag |= FLUSHO;
                        tp->t_col = tp->t_rocol;
                        cp = tp->t_rawq.c_cf;
-                       for (; cp; cp = nextc(&tp->t_rawq, cp))
-                               ttyecho(*cp, tp);
                        tp->t_lflag &= ~FLUSHO;
                        tp->t_state &= ~TS_CNTTB;
                        splx(s);
                        tp->t_lflag &= ~FLUSHO;
                        tp->t_state &= ~TS_CNTTB;
                        splx(s);
@@ -1654,9 +1543,12 @@ ttyrub(c, tp)
                        while (--savecol >= 0)
                                (void) ttyoutput('\b', tp);
                        break;
                        while (--savecol >= 0)
                                (void) ttyoutput('\b', tp);
                        break;
+               }
 
                default:
 
                default:
-                       panic("ttyrub");
+                       printf("ttyrub: would panic c = %d, val = %d\n",
+                               c, partab[c&=0377]&077);
+                       /*panic("ttyrub");*/
                }
        } else if (tp->t_lflag&ECHOPRT) {
                if ((tp->t_state&TS_ERASE) == 0) {
                }
        } else if (tp->t_lflag&ECHOPRT) {
                if ((tp->t_state&TS_ERASE) == 0) {
@@ -1680,7 +1572,7 @@ ttyrubo(tp, cnt)
        register char *rubostring = tp->t_lflag&ECHOE ? "\b \b" : "\b";
 
        while (--cnt >= 0)
        register char *rubostring = tp->t_lflag&ECHOE ? "\b \b" : "\b";
 
        while (--cnt >= 0)
-               ttyout(rubostring, tp);
+               ttyout("\b \b", tp);
 }
 
 /*
 }
 
 /*
@@ -1692,16 +1584,20 @@ ttyretype(tp)
 {
        register char *cp;
        char *nextc();
 {
        register char *cp;
        char *nextc();
-       int s;
+       int s, c;
 
        if (tp->t_cc[VREPRINT] != POSIX_V_DISABLE)
                ttyecho(tp->t_cc[VREPRINT], tp);
        (void) ttyoutput('\n', tp);
        s = spltty();
 
        if (tp->t_cc[VREPRINT] != POSIX_V_DISABLE)
                ttyecho(tp->t_cc[VREPRINT], tp);
        (void) ttyoutput('\n', tp);
        s = spltty();
-       for (cp = tp->t_canq.c_cf; cp; cp = nextc(&tp->t_canq, cp))
-               ttyecho(*cp, tp);
-       for (cp = tp->t_rawq.c_cf; cp; cp = nextc(&tp->t_rawq, cp))
-               ttyecho(*cp, tp);
+       /*** XXX *** FIX *** NEXTC IS BROKEN - DOESN'T CHECK QUOTE
+         BIT OF FIRST CHAR ****/
+       for (cp = tp->t_canq.c_cf, c=(cp?*cp:0); cp; cp = nextc(&tp->t_canq, cp, &c)) {
+               ttyecho(c, tp);
+       }
+       for (cp = tp->t_rawq.c_cf, c=(cp?*cp:0); cp; cp = nextc(&tp->t_rawq, cp, &c)) {
+               ttyecho(c, tp);
+       }
        tp->t_state &= ~TS_ERASE;
        splx(s);
        tp->t_rocount = tp->t_rawq.c_cc;
        tp->t_state &= ~TS_ERASE;
        splx(s);
        tp->t_rocount = tp->t_rawq.c_cc;
@@ -1715,30 +1611,24 @@ ttyecho(c, tp)
        register c;
        register struct tty *tp;
 {
        register c;
        register struct tty *tp;
 {
-
        c &= 0377;
        if ((tp->t_state&TS_CNTTB) == 0)
                tp->t_lflag &= ~FLUSHO;
        if ((tp->t_lflag&ECHO) == 0 && !(tp->t_lflag&ECHONL && c == '\n'))
                return;
        if (tp->t_lflag&ECHOCTL) {
        c &= 0377;
        if ((tp->t_state&TS_CNTTB) == 0)
                tp->t_lflag &= ~FLUSHO;
        if ((tp->t_lflag&ECHO) == 0 && !(tp->t_lflag&ECHONL && c == '\n'))
                return;
        if (tp->t_lflag&ECHOCTL) {
-               if ((c&0177) <= 037 && c!='\t' && c!='\n' || (c&0177)==0177) {
+               if ((c&TTY_CHARMASK)<=037 && c!='\t' && c!='\n' || c==0177) {
                        (void) ttyoutput('^', tp);
                        (void) ttyoutput('^', tp);
-                       c &= 0177;
+                       c &= TTY_CHARMASK;
                        if (c == 0177)
                                c = '?';
 #ifdef notdef
                        if (c == 0177)
                                c = '?';
 #ifdef notdef
-                       else if (tp->t_flags&LCASE)
-                               c += 'a' - 1;
 #endif
                        else
                                c += 'A' - 1;
                }
        }
 #endif
                        else
                                c += 'A' - 1;
                }
        }
-       (void) ttyoutput(c&0177, tp);
-}
-
-/*
+       (void) ttyoutput(c, tp);
  * send string cp to tp
  */
 ttyout(cp, tp)
  * send string cp to tp
  */
 ttyout(cp, tp)
@@ -1761,6 +1651,38 @@ ttwakeup(tp)
                tp->t_rsel = 0;
        }
        if (tp->t_state & TS_ASYNC)
                tp->t_rsel = 0;
        }
        if (tp->t_state & TS_ASYNC)
-               gsignal(tp->t_pgrp, SIGIO); 
+               gsignal(tp->t_pgid, SIGIO); 
        wakeup((caddr_t)&tp->t_rawq);
 }
        wakeup((caddr_t)&tp->t_rawq);
 }
+
+/*
+ * set tty hi and low water marks
+ *
+ * Try to arrange the dynamics so there's about one second
+ * from hi to low water.
+ * 
+ */
+ttsetwater(tp)
+       struct tty *tp;
+{
+       register cps = tp->t_ospeed / 10;
+       register x;
+
+#define clamp(x, h, l) ((x)>h ? h : ((x)<l) ? l : (x))
+       tp->t_lowat = x = clamp(cps/2, TTMAXLOWAT, TTMINLOWAT);
+       x += cps;
+       x = clamp(x, TTMAXHIWAT, TTMINHIWAT);
+       tp->t_hiwat = roundup(x, CBSIZE);
+#undef clamp
+}
+
+ttspeedtab(speed, table)
+       struct speedtab table[];
+{
+       register int i;
+
+       for (i = 0; table[i].sp_speed != -1; i++)
+               if (table[i].sp_speed == speed)
+                       return(table[i].sp_code);
+       return(-1);
+}
index 50625d3..c935433 100644 (file)
@@ -3,11 +3,11 @@
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
- *     @(#)ttcompat.c  7.11 (Berkeley) 4/8/88
+ *     @(#)tty_compat.c        1.2 (Berkeley) %G%
  */
 
 /* 
  */
 
 /* 
- * mapping routines for old line disciplines (yuck)
+ * mapping routines for old line discipline (yuck)
  */
 #ifdef COMPAT_43
 
  */
 #ifdef COMPAT_43
 
 #include "kernel.h"
 #include "syslog.h"
 
 #include "kernel.h"
 #include "syslog.h"
 
-/* begin XXX */
-#undef t_erase
-#undef t_kill
-#undef t_intrc
-#undef t_quitc
-#undef t_startc
-#undef t_stopc
-#undef t_eofc
-#undef t_brkc
-#undef t_suspc
-#undef t_dsuspc
-#undef t_rprntc
-#undef t_flushc
-#undef t_werasc
-#undef t_lnextc
-/* end XXX */
+int ttydebug = 0;
 
 
-/* should fold these two tables into one */
+/* XXX - fold these two tables into one */
 static struct speedtab compatspeeds[] = {
        38400,  15,
        19200,  14,
 static struct speedtab compatspeeds[] = {
        38400,  15,
        19200,  14,
@@ -89,10 +74,9 @@ ttcompat(tp, com, data, flag)
                        speed = ttspeedtab(tp->t_ispeed, compatspeeds);
                        sg->sg_ispeed = (speed == -1) ? 15 : speed;
                }
                        speed = ttspeedtab(tp->t_ispeed, compatspeeds);
                        sg->sg_ispeed = (speed == -1) ? 15 : speed;
                }
-
                sg->sg_erase = cc[VERASE];
                sg->sg_kill = cc[VKILL];
                sg->sg_erase = cc[VERASE];
                sg->sg_kill = cc[VKILL];
-               sg->sg_flags = ttcompatgetflags(tp) & 0xffff;
+               sg->sg_flags = ttcompatgetflags(tp);
                break;
        }
 
                break;
        }
 
@@ -103,7 +87,6 @@ ttcompat(tp, com, data, flag)
                int speed;
 
                term = tp->t_termios;
                int speed;
 
                term = tp->t_termios;
-
                if ((speed = sg->sg_ispeed) > 15 || speed < 0)
                        term.c_ispeed = speed;
                else
                if ((speed = sg->sg_ispeed) > 15 || speed < 0)
                        term.c_ispeed = speed;
                else
@@ -112,14 +95,11 @@ ttcompat(tp, com, data, flag)
                        term.c_ospeed = speed;
                else
                        term.c_ospeed = compatspcodes[speed];
                        term.c_ospeed = speed;
                else
                        term.c_ospeed = compatspcodes[speed];
-               
                term.c_cc[VERASE] = sg->sg_erase;
                term.c_cc[VKILL] = sg->sg_kill;
                if (sg->sg_erase == -1)
                term.c_cc[VERASE] = sg->sg_erase;
                term.c_cc[VKILL] = sg->sg_kill;
                if (sg->sg_erase == -1)
-                       term.c_cc[VERASE2] = POSIX_V_DISABLE;
-
+                       term.c_cc[VERASE2] = _POSIX_VDISABLE;
                tp->t_flags = (tp->t_flags&0xffff0000) | sg->sg_flags;
                tp->t_flags = (tp->t_flags&0xffff0000) | sg->sg_flags;
-
                ttcompatsetflags(tp, &term);
                return (ttioctl(tp, com == TIOCSETP ? TIOCSETAF : TIOCSETA, 
                        &term, flag));
                ttcompatsetflags(tp, &term);
                return (ttioctl(tp, com == TIOCSETP ? TIOCSETAF : TIOCSETA, 
                        &term, flag));
@@ -148,7 +128,7 @@ ttcompat(tp, com, data, flag)
                cc[VEOF] = tc->t_eofc;
                cc[VEOL] = tc->t_brkc;
                if (tc->t_brkc == -1)
                cc[VEOF] = tc->t_eofc;
                cc[VEOL] = tc->t_brkc;
                if (tc->t_brkc == -1)
-                       cc[VEOL2] = POSIX_V_DISABLE;
+                       cc[VEOL2] = _POSIX_VDISABLE;
                break;
        }
        case TIOCSLTC: {
                break;
        }
        case TIOCSLTC: {
@@ -182,29 +162,41 @@ ttcompat(tp, com, data, flag)
 
                term = tp->t_termios;
                if (com == TIOCLSET)
 
                term = tp->t_termios;
                if (com == TIOCLSET)
-                       tp->t_flags = (tp->t_flags&0xffff) | *(short *)data<<16;
+                       tp->t_flags = (tp->t_flags&0xffff) | *(int *)data<<16;
                else {
                        tp->t_flags = 
                         (ttcompatgetflags(tp)&0xffff0000)|(tp->t_flags&0xffff);
                        if (com == TIOCLBIS)
                else {
                        tp->t_flags = 
                         (ttcompatgetflags(tp)&0xffff0000)|(tp->t_flags&0xffff);
                        if (com == TIOCLBIS)
-                               tp->t_flags |= *(short *)data<<16;
+                               tp->t_flags |= *(int *)data<<16;
                        else
                        else
-                               tp->t_flags &= ~(*(short *)data<<16);
+                               tp->t_flags &= ~(*(int *)data<<16);
                }
                ttcompatsetlflags(tp, &term);
                return (ttioctl(tp, TIOCSETA, &term, flag));
        }
        case TIOCLGET:
                }
                ttcompatsetlflags(tp, &term);
                return (ttioctl(tp, TIOCSETA, &term, flag));
        }
        case TIOCLGET:
-               *(short *)data = ttcompatgetflags(tp)>>16;
+               *(int *)data = ttcompatgetflags(tp)>>16;
+               if (ttydebug)
+                       printf("CLGET: returning %x\n", *(int *)data);
                break;
                break;
+
+       case TIOCGETDCOMPAT:
+               *(int *)data = tp->t_line ? tp->t_line : 2;
+               break;
+
+       case TIOCSETDCOMPAT: {
+               int ldisczero = 0;
+
+               return(ttioctl(tp, TIOCSETD, 
+                       *(int *)data == 2 ? (caddr_t)&ldisczero : data, flag));
+       }
+
        default:
                return (-1);
        }
        return(0);
 }
 
        default:
                return (-1);
        }
        return(0);
 }
 
-
-
 ttcompatgetflags(tp)
        register struct tty *tp;
 {
 ttcompatgetflags(tp)
        register struct tty *tp;
 {
@@ -242,11 +234,10 @@ ttcompatgetflags(tp)
        }
        if (oflag&OXTABS)
                flags |= XTABS;
        }
        if (oflag&OXTABS)
                flags |= XTABS;
-
        if (lflag&ECHOE)
        if (lflag&ECHOE)
-               flags |= CRTERA;
+               flags |= CRTERA|CRTBS;
        if (lflag&ECHOKE)
        if (lflag&ECHOKE)
-               flags |= CRTKIL;
+               flags |= CRTKIL|CRTBS;
        if (lflag&ECHOPRT)
                flags |= PRTERA;
        if (lflag&ECHOCTL)
        if (lflag&ECHOPRT)
                flags |= PRTERA;
        if (lflag&ECHOCTL)
@@ -254,7 +245,8 @@ ttcompatgetflags(tp)
        if ((iflag&IXANY) == 0)
                flags |= DECCTQ;
        flags |= lflag&(ECHO|MDMBUF|TOSTOP|FLUSHO|NOHANG|PENDIN|NOFLSH);
        if ((iflag&IXANY) == 0)
                flags |= DECCTQ;
        flags |= lflag&(ECHO|MDMBUF|TOSTOP|FLUSHO|NOHANG|PENDIN|NOFLSH);
-
+if (ttydebug)
+       printf("getflags: %x\n", flags);
        return (flags);
 }
 
        return (flags);
 }
 
@@ -326,7 +318,6 @@ ttcompatsetflags(tp, t)
        t->c_cflag = cflag;
 }
 
        t->c_cflag = cflag;
 }
 
-/* XXX - rethink this whole routine */
 ttcompatsetlflags(tp, t)
        register struct tty *tp;
        register struct termios *t;
 ttcompatsetlflags(tp, t)
        register struct tty *tp;
        register struct termios *t;
@@ -336,10 +327,11 @@ ttcompatsetlflags(tp, t)
        register long oflag = t->c_oflag;
        register long lflag = t->c_lflag;
        register long cflag = t->c_cflag;
        register long oflag = t->c_oflag;
        register long lflag = t->c_lflag;
        register long cflag = t->c_cflag;
+
        if (flags&CRTERA)
                lflag |= ECHOE;
        else
        if (flags&CRTERA)
                lflag |= ECHOE;
        else
-               lflag &= ECHOE;
+               lflag &= ~ECHOE;
        if (flags&CRTKIL)
                lflag |= ECHOKE;
        else
        if (flags&CRTKIL)
                lflag |= ECHOKE;
        else
@@ -356,10 +348,8 @@ ttcompatsetlflags(tp, t)
                lflag |= IXANY;
        else
                lflag &= ~IXANY;
                lflag |= IXANY;
        else
                lflag &= ~IXANY;
-
        lflag &= ~(MDMBUF|TOSTOP|FLUSHO|NOHANG|PENDIN|NOFLSH);
        lflag |= flags&(MDMBUF|TOSTOP|FLUSHO|NOHANG|PENDIN|NOFLSH);
        lflag &= ~(MDMBUF|TOSTOP|FLUSHO|NOHANG|PENDIN|NOFLSH);
        lflag |= flags&(MDMBUF|TOSTOP|FLUSHO|NOHANG|PENDIN|NOFLSH);
-
        if (flags&(LITOUT|PASS8)) {
                iflag &= ~ISTRIP;
                cflag &= ~(CSIZE|PARENB);
        if (flags&(LITOUT|PASS8)) {
                iflag &= ~ISTRIP;
                cflag &= ~(CSIZE|PARENB);
index 9e29caf..8907eaf 100644 (file)
@@ -3,7 +3,7 @@
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
- *     @(#)tty_conf.c  7.2 (Berkeley) %G%
+ *     @(#)tty_conf.c  7.3 (Berkeley) %G%
  */
 
 #include "param.h"
  */
 
 #include "param.h"
@@ -19,6 +19,9 @@ int   nulldev();
 int    ttyopen(),ttylclose(),ttread(),ttwrite(),nullioctl(),ttstart();
 int    ttymodem(), nullmodem(), ttyinput();
 
 int    ttyopen(),ttylclose(),ttread(),ttwrite(),nullioctl(),ttstart();
 int    ttymodem(), nullmodem(), ttyinput();
 
+int    ottyopen(), ottylclose(), ottread(), ottwrite();
+int    ottyinput(), ottstart(), ottymodem();
+
 #include "bk.h"
 #if NBK > 0
 int    bkopen(),bkclose(),bkread(),bkinput(),bkioctl();
 #include "bk.h"
 #if NBK > 0
 int    bkopen(),bkclose(),bkread(),bkinput(),bkioctl();
@@ -36,17 +39,17 @@ int slopen(),slclose(),slinput(),sltioctl(),slstart();
 
 struct linesw linesw[] =
 {
 
 struct linesw linesw[] =
 {
-       ttyopen, ttylclose, ttread, ttwrite, nullioctl, /* 0- OTTYDISC */
-       ttyinput, nodev, nulldev, ttstart, ttymodem,
+       ttyopen, ttylclose, ttread, ttwrite, nullioctl,
+       ttyinput, nodev, nulldev, ttstart, ttymodem,    /* 0- termios */
 #if NBK > 0
 #if NBK > 0
-       bkopen, bkclose, bkread, ttwrite, bkioctl,      /* 1- NETLDISC */
-       bkinput, nodev, nulldev, ttstart, nullmodem,
+       bkopen, bkclose, bkread, ttwrite, bkioctl,
+       bkinput, nodev, nulldev, ttstart, nullmodem,    /* 1- NETLDISC */
 #else
        nodev, nodev, nodev, nodev, nodev,
        nodev, nodev, nodev, nodev, nodev,
 #endif
 #else
        nodev, nodev, nodev, nodev, nodev,
        nodev, nodev, nodev, nodev, nodev,
 #endif
-       ttyopen, ttylclose, ttread, ttwrite, nullioctl, /* 2- NTTYDISC */
-       ttyinput, nodev, nulldev, ttstart, ttymodem,
+       nodev, nodev, nodev, nodev, nodev,              /* 2- defunct */
+       nodev, nodev, nodev, nodev, nodev,
 #if NTB > 0
        tbopen, tbclose, tbread, nodev, tbioctl,
        tbinput, nodev, nulldev, ttstart, nullmodem,    /* 3- TABLDISC */
 #if NTB > 0
        tbopen, tbclose, tbread, nodev, tbioctl,
        tbinput, nodev, nulldev, ttstart, nullmodem,    /* 3- TABLDISC */
index c6eaca1..e883c31 100644 (file)
@@ -3,7 +3,7 @@
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
- *     @(#)tty_pty.c   7.3.1.1 (Berkeley) %G%
+ *     @(#)tty_pty.c   7.4 (Berkeley) %G%
  */
 
 /*
  */
 
 /*
@@ -76,8 +76,12 @@ ptsopen(dev, flag)
        tp = &pt_tty[minor(dev)];
        if ((tp->t_state & TS_ISOPEN) == 0) {
                ttychars(tp);           /* Set up default chars */
        tp = &pt_tty[minor(dev)];
        if ((tp->t_state & TS_ISOPEN) == 0) {
                ttychars(tp);           /* Set up default chars */
-               tp->t_ispeed = tp->t_ospeed = EXTB;
-               tp->t_flags = 0;        /* No features (nor raw mode) */
+               tp->t_iflag = TTYDEF_IFLAG;
+               tp->t_oflag = TTYDEF_OFLAG;
+               tp->t_lflag = TTYDEF_LFLAG;
+               tp->t_cflag = TTYDEF_CFLAG;
+               tp->t_ispeed = tp->t_ospeed = TTYDEF_SPEED;
+               ttsetwater(tp);         /* would be done in xxparam() */
        } else if (tp->t_state&TS_XCLUDE && u.u_uid != 0)
                return (EBUSY);
        if (tp->t_oproc)                        /* Ctrlr still around. */
        } else if (tp->t_state&TS_XCLUDE && u.u_uid != 0)
                return (EBUSY);
        if (tp->t_oproc)                        /* Ctrlr still around. */
@@ -113,12 +117,14 @@ ptsread(dev, uio)
 
 again:
        if (pti->pt_flags & PF_REMOTE) {
 
 again:
        if (pti->pt_flags & PF_REMOTE) {
-               while (tp == u.u_ttyp && u.u_procp->p_pgrp != tp->t_pgrp) {
+               while (tp == u.u_ttyp && 
+                      u.u_procp->p_pgrp->pg_id != tp->t_pgid){
                        if ((u.u_procp->p_sigignore & sigmask(SIGTTIN)) ||
                            (u.u_procp->p_sigmask & sigmask(SIGTTIN)) ||
                        if ((u.u_procp->p_sigignore & sigmask(SIGTTIN)) ||
                            (u.u_procp->p_sigmask & sigmask(SIGTTIN)) ||
+                           !u.u_procp->p_pgrp->pg_jobc ||
                            u.u_procp->p_flag&SVFORK)
                                return (EIO);
                            u.u_procp->p_flag&SVFORK)
                                return (EIO);
-                       gsignal(u.u_procp->p_pgrp, SIGTTIN);
+                       pgsignal(u.u_procp->p_pgrp, SIGTTIN);
                        sleep((caddr_t)&lbolt, TTIPRI);
                }
                if (tp->t_canq.c_cc == 0) {
                        sleep((caddr_t)&lbolt, TTIPRI);
                }
                if (tp->t_canq.c_cc == 0) {
@@ -391,8 +397,7 @@ ptcselect(dev, rw)
                        } else {
                            if (tp->t_rawq.c_cc + tp->t_canq.c_cc < TTYHOG-2)
                                    return (1);
                        } else {
                            if (tp->t_rawq.c_cc + tp->t_canq.c_cc < TTYHOG-2)
                                    return (1);
-                           if (tp->t_canq.c_cc == 0 &&
-                               (tp->t_flags & (RAW|CBREAK)) == 0)
+                           if (tp->t_canq.c_cc == 0 && (tp->t_iflag&ICANON))
                                    return (1);
                        }
                }
                                    return (1);
                        }
                }
@@ -471,8 +476,7 @@ again:
                }
                while (cc > 0) {
                        if ((tp->t_rawq.c_cc + tp->t_canq.c_cc) >= TTYHOG - 2 &&
                }
                while (cc > 0) {
                        if ((tp->t_rawq.c_cc + tp->t_canq.c_cc) >= TTYHOG - 2 &&
-                          (tp->t_canq.c_cc > 0 ||
-                             tp->t_flags & (RAW|CBREAK))) {
+                          (tp->t_canq.c_cc > 0 || !(tp->t_iflag&ICANON))) {
                                wakeup((caddr_t)&tp->t_rawq);
                                goto block;
                        }
                                wakeup((caddr_t)&tp->t_rawq);
                                goto block;
                        }
@@ -510,6 +514,7 @@ ptyioctl(dev, cmd, data, flag)
 {
        register struct tty *tp = &pt_tty[minor(dev)];
        register struct pt_ioctl *pti = &pt_ioctl[minor(dev)];
 {
        register struct tty *tp = &pt_tty[minor(dev)];
        register struct pt_ioctl *pti = &pt_ioctl[minor(dev)];
+       register u_char *cc = tp->t_cc;
        int stop, error;
        extern ttyinput();
 
        int stop, error;
        extern ttyinput();
 
@@ -588,9 +593,15 @@ ptyioctl(dev, cmd, data, flag)
                        *(int *)data = tp->t_outq.c_cc;
                        return (0);
 
                        *(int *)data = tp->t_outq.c_cc;
                        return (0);
 
-               case TIOCSETP:
+               case TIOCSETP:          
                case TIOCSETN:
                case TIOCSETD:
                case TIOCSETN:
                case TIOCSETD:
+               case TIOCSETA:
+               case TIOCSETAW:
+               case TIOCSETAF:
+               case TIOCSETAS:
+               case TIOCSETAWS:
+               case TIOCSETAFS:
                        while (getc(&tp->t_outq) >= 0)
                                ;
                        break;
                        while (getc(&tp->t_outq) >= 0)
                                ;
                        break;
@@ -658,7 +669,9 @@ ptyioctl(dev, cmd, data, flag)
        }
 
  doioctl:
        }
 
  doioctl:
-       error = ttioctl(tp, cmd, data, flag);
+       error = (*linesw[tp->t_line].l_ioctl)(tp, cmd, data, flag);
+       if (error < 0)
+                error = ttioctl(tp, cmd, data, flag);
        /*
         * Since we use the tty queues internally,
         * pty's can't be switched to disciplines which overwrite
        /*
         * Since we use the tty queues internally,
         * pty's can't be switched to disciplines which overwrite
@@ -691,8 +704,8 @@ ptyioctl(dev, cmd, data, flag)
                }
                error = ENOTTY;
        }
                }
                error = ENOTTY;
        }
-       stop = (tp->t_flags & RAW) == 0 &&
-           tp->t_stopc == CTRL('s') && tp->t_startc == CTRL('q');
+       stop = (tp->t_iflag & IXON) && CCEQ(cc[VSTOP], CTRL('s')) 
+               && CCEQ(cc[VSTART], CTRL('q'));
        if (pti->pt_flags & PF_NOSTOP) {
                if (stop) {
                        pti->pt_send &= ~TIOCPKT_NOSTOP;
        if (pti->pt_flags & PF_NOSTOP) {
                if (stop) {
                        pti->pt_send &= ~TIOCPKT_NOSTOP;
index 44d708a..c6e3e07 100644 (file)
@@ -3,7 +3,7 @@
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
- *     @(#)tty_subr.c  7.3 (Berkeley) %G%
+ *     @(#)tty_subr.c  7.4 (Berkeley) %G%
  */
 
 #include "param.h"
  */
 
 #include "param.h"
 
 char   cwaiting;
 
 
 char   cwaiting;
 
+#define setquote(cp) \
+       setbit(((char *)((int)(cp)&~CROUND)+sizeof(struct cblock *)), \
+               (int)(cp)&CROUND)
+#define isquote(cp) \
+       isset(((char *)((int)(cp)&~CROUND)+sizeof(struct cblock *)), \
+               (int)(cp)&CROUND)
+#define cbptr(x) ((struct cblock *)(x))
+
 /*
  * Character list get/put
  */
 /*
  * Character list get/put
  */
@@ -30,10 +38,13 @@ getc(p)
                p->c_cc = 0;
                p->c_cf = p->c_cl = NULL;
        } else {
                p->c_cc = 0;
                p->c_cf = p->c_cl = NULL;
        } else {
-               c = *p->c_cf++ & 0377;
+               c = *p->c_cf & 0377;
+               if (isquote(p->c_cf))
+                       c |= TTY_QUOTE;
+               p->c_cf++;
                if (--p->c_cc<=0) {
                if (--p->c_cc<=0) {
-                       bp = (struct cblock *)(p->c_cf-1);
-                       bp = (struct cblock *)((int)bp & ~CROUND);
+                       bp = cbptr(p->c_cf-1);
+                       bp = cbptr((int)bp & ~CROUND);
                        p->c_cf = NULL;
                        p->c_cl = NULL;
                        bp->c_next = cfreelist;
                        p->c_cf = NULL;
                        p->c_cl = NULL;
                        bp->c_next = cfreelist;
@@ -44,7 +55,7 @@ getc(p)
                                cwaiting = 0;
                        }
                } else if (((int)p->c_cf & CROUND) == 0){
                                cwaiting = 0;
                        }
                } else if (((int)p->c_cf & CROUND) == 0){
-                       bp = (struct cblock *)(p->c_cf);
+                       bp = cbptr(p->c_cf);
                        bp--;
                        p->c_cf = bp->c_next->c_info;
                        bp->c_next = cfreelist;
                        bp--;
                        p->c_cf = bp->c_next->c_info;
                        bp->c_next = cfreelist;
@@ -94,8 +105,8 @@ q_to_b(q, cp, cc)
                cc -= nc;
                cp += nc;
                if (q->c_cc <= 0) {
                cc -= nc;
                cp += nc;
                if (q->c_cc <= 0) {
-                       bp = (struct cblock *)(q->c_cf - 1);
-                       bp = (struct cblock *)((int)bp & ~CROUND);
+                       bp = cbptr(q->c_cf - 1);
+                       bp = cbptr((int)bp & ~CROUND);
                        q->c_cf = q->c_cl = NULL;
                        bp->c_next = cfreelist;
                        cfreelist = bp;
                        q->c_cf = q->c_cl = NULL;
                        bp->c_next = cfreelist;
                        cfreelist = bp;
@@ -107,7 +118,7 @@ q_to_b(q, cp, cc)
                        break;
                }
                if (((int)q->c_cf & CROUND) == 0) {
                        break;
                }
                if (((int)q->c_cf & CROUND) == 0) {
-                       bp = (struct cblock *)(q->c_cf);
+                       bp = cbptr(q->c_cf);
                        bp--;
                        q->c_cf = bp->c_next->c_info;
                        bp->c_next = cfreelist;
                        bp--;
                        q->c_cf = bp->c_next->c_info;
                        bp->c_next = cfreelist;
@@ -178,7 +189,7 @@ ndflush(q, cc)
        if (q->c_cc <= 0)
                goto out;
        while (cc>0 && q->c_cc) {
        if (q->c_cc <= 0)
                goto out;
        while (cc>0 && q->c_cc) {
-               bp = (struct cblock *)((int)q->c_cf & ~CROUND);
+               bp = cbptr((int)q->c_cf & ~CROUND);
                if ((int)bp == (((int)q->c_cl-1) & ~CROUND)) {
                        end = q->c_cl;
                } else {
                if ((int)bp == (((int)q->c_cl-1) & ~CROUND)) {
                        end = q->c_cl;
                } else {
@@ -228,7 +239,7 @@ putc(c, p)
        register s;
 
        s = spltty();
        register s;
 
        s = spltty();
-       if ((cp = p->c_cl) == NULL || p->c_cc < 0 ) {
+       if ((cp = p->c_cl) == NULL || p->c_cc < 0 ) {   /* no cblocks yet */
                if ((bp = cfreelist) == NULL) {
                        splx(s);
                        return (-1);
                if ((bp = cfreelist) == NULL) {
                        splx(s);
                        return (-1);
@@ -236,9 +247,10 @@ putc(c, p)
                cfreelist = bp->c_next;
                cfreecount -= CBSIZE;
                bp->c_next = NULL;
                cfreelist = bp->c_next;
                cfreecount -= CBSIZE;
                bp->c_next = NULL;
+               bzero(bp->c_quote, CBQSIZE);
                p->c_cf = cp = bp->c_info;
        } else if (((int)cp & CROUND) == 0) {
                p->c_cf = cp = bp->c_info;
        } else if (((int)cp & CROUND) == 0) {
-               bp = (struct cblock *)cp - 1;
+               bp = cbptr(cp) - 1;     /* pointer arith */
                if ((bp->c_next = cfreelist) == NULL) {
                        splx(s);
                        return (-1);
                if ((bp->c_next = cfreelist) == NULL) {
                        splx(s);
                        return (-1);
@@ -249,6 +261,8 @@ putc(c, p)
                bp->c_next = NULL;
                cp = bp->c_info;
        }
                bp->c_next = NULL;
                cp = bp->c_info;
        }
+       if (c&TTY_QUOTE)
+               setquote(cp);
        *cp++ = c;
        p->c_cc++;
        p->c_cl = cp;
        *cp++ = c;
        p->c_cc++;
        p->c_cl = cp;
@@ -279,18 +293,20 @@ b_to_q(cp, cc, q)
                        goto out;
                cfreelist = bp->c_next;
                cfreecount -= CBSIZE;
                        goto out;
                cfreelist = bp->c_next;
                cfreecount -= CBSIZE;
+               bzero(bp->c_quote, CBQSIZE);
                bp->c_next = NULL;
                q->c_cf = cq = bp->c_info;
        }
 
        while (cc) {
                if (((int)cq & CROUND) == 0) {
                bp->c_next = NULL;
                q->c_cf = cq = bp->c_info;
        }
 
        while (cc) {
                if (((int)cq & CROUND) == 0) {
-                       bp = (struct cblock *)cq - 1;
+                       bp = cbptr(cq) - 1;
                        if ((bp->c_next = cfreelist) == NULL) 
                                goto out;
                        bp = bp->c_next;
                        cfreelist = bp->c_next;
                        cfreecount -= CBSIZE;
                        if ((bp->c_next = cfreelist) == NULL) 
                                goto out;
                        bp = bp->c_next;
                        cfreelist = bp->c_next;
                        cfreecount -= CBSIZE;
+                       bzero(bp->c_quote, CBQSIZE);
                        bp->c_next = NULL;
                        cq = bp->c_info;
                }
                        bp->c_next = NULL;
                        cq = bp->c_info;
                }
@@ -316,14 +332,19 @@ out:
  * pointer becomes invalid.  Note that interrupts are NOT masked.
  */
 char *
  * pointer becomes invalid.  Note that interrupts are NOT masked.
  */
 char *
-nextc(p, cp)
+nextc(p, cp, c)
        register struct clist *p;
        register char *cp;
        register struct clist *p;
        register char *cp;
+       register int *c;
 {
 
        if (p->c_cc && ++cp != p->c_cl) {
 {
 
        if (p->c_cc && ++cp != p->c_cl) {
-               if (((int)cp & CROUND) == 0)
-                       return (((struct cblock *)cp)[-1].c_next->c_info);
+               if (((int)cp & CROUND) == 0) {
+                       cp = (cbptr(cp))[-1].c_next->c_info;
+               }
+               *c = *cp;
+               if (isquote(cp))
+                       *c |= TTY_QUOTE;
                return (cp);
        }
        return (0);
                return (cp);
        }
        return (0);
@@ -338,24 +359,28 @@ unputc(p)
        register struct cblock *bp;
        register int c, s;
        struct cblock *obp;
        register struct cblock *bp;
        register int c, s;
        struct cblock *obp;
+       register int first = 1;
 
        s = spltty();
        if (p->c_cc <= 0)
                c = -1;
        else {
                c = *--p->c_cl;
 
        s = spltty();
        if (p->c_cc <= 0)
                c = -1;
        else {
                c = *--p->c_cl;
+               if (isquote(p->c_cl))
+                       c |= TTY_QUOTE;
                if (--p->c_cc <= 0) {
                if (--p->c_cc <= 0) {
-                       bp = (struct cblock *)p->c_cl;
-                       bp = (struct cblock *)((int)bp & ~CROUND);
+                       bp = cbptr(p->c_cl);
+                       bp = cbptr((int)bp & ~CROUND);
                        p->c_cl = p->c_cf = NULL;
                        bp->c_next = cfreelist;
                        cfreelist = bp;
                        cfreecount += CBSIZE;
                        p->c_cl = p->c_cf = NULL;
                        bp->c_next = cfreelist;
                        cfreelist = bp;
                        cfreecount += CBSIZE;
-               } else if (((int)p->c_cl & CROUND) == sizeof(bp->c_next)) {
+               } else if (p->c_cl == (cbptr((int)p->c_cl & ~CROUND))->c_info) {
                        p->c_cl = (char *)((int)p->c_cl & ~CROUND);
                        p->c_cl = (char *)((int)p->c_cl & ~CROUND);
-                       bp = (struct cblock *)p->c_cf;
-                       bp = (struct cblock *)((int)bp & ~CROUND);
-                       while (bp->c_next != (struct cblock *)p->c_cl)
+
+                       bp = cbptr(p->c_cf);
+                       bp = cbptr((int)bp & ~CROUND);
+                       while (bp->c_next != cbptr(p->c_cl))
                                bp = bp->c_next;
                        obp = bp;
                        p->c_cl = (char *)(bp + 1);
                                bp = bp->c_next;
                        obp = bp;
                        p->c_cl = (char *)(bp + 1);
@@ -377,7 +402,9 @@ unputc(p)
 catq(from, to)
        struct clist *from, *to;
 {
 catq(from, to)
        struct clist *from, *to;
 {
+#ifdef notdef
        char bbuf[CBSIZE*4];
        char bbuf[CBSIZE*4];
+#endif
        register s, c;
 
        s = spltty();
        register s, c;
 
        s = spltty();
@@ -390,10 +417,15 @@ catq(from, to)
                return;
        }
        splx(s);
                return;
        }
        splx(s);
+#ifdef notdef
        while (from->c_cc > 0) {
                c = q_to_b(from, bbuf, sizeof bbuf);
                (void) b_to_q(bbuf, c, to);
        }
        while (from->c_cc > 0) {
                c = q_to_b(from, bbuf, sizeof bbuf);
                (void) b_to_q(bbuf, c, to);
        }
+#endif
+       /* XXX - FIX */
+       while ((c = getc(from)) >= 0)
+               putc(c, to);
 }
 
 #ifdef unneeded
 }
 
 #ifdef unneeded
@@ -419,7 +451,7 @@ getw(p)
 #endif
        }
        s = spltty();
 #endif
        }
        s = spltty();
-#if BYTE_ORDER == LITTLE_ENDIAN
+#if BYTE_ORDER == LITTLE_ENDIAN 
        c = (((u_char *)p->c_cf)[0] << 8) | ((u_char *)p->c_cf)[1];
 #else
        c = (((u_char *)p->c_cf)[1] << 8) | ((u_char *)p->c_cf)[0];
        c = (((u_char *)p->c_cf)[0] << 8) | ((u_char *)p->c_cf)[1];
 #else
        c = (((u_char *)p->c_cf)[1] << 8) | ((u_char *)p->c_cf)[0];
@@ -427,8 +459,8 @@ getw(p)
        p->c_cf += sizeof (word_t);
        p->c_cc -= sizeof (word_t);
        if (p->c_cc <= 0) {
        p->c_cf += sizeof (word_t);
        p->c_cc -= sizeof (word_t);
        if (p->c_cc <= 0) {
-               bp = (struct cblock *)(p->c_cf-1);
-               bp = (struct cblock *)((int)bp & ~CROUND);
+               bp = cbptr(p->c_cf-1);
+               bp = cbptr((int)bp & ~CROUND);
                p->c_cf = NULL;
                p->c_cl = NULL;
                bp->c_next = cfreelist;
                p->c_cf = NULL;
                p->c_cl = NULL;
                bp->c_next = cfreelist;
@@ -439,7 +471,7 @@ getw(p)
                        cwaiting = 0;
                }
        } else if (((int)p->c_cf & CROUND) == 0) {
                        cwaiting = 0;
                }
        } else if (((int)p->c_cf & CROUND) == 0) {
-               bp = (struct cblock *)(p->c_cf);
+               bp = cbptr(p->c_cf);
                bp--;
                p->c_cf = bp->c_next->c_info;
                bp->c_next = cfreelist;
                bp--;
                p->c_cf = bp->c_next->c_info;
                bp->c_next = cfreelist;
@@ -486,7 +518,7 @@ putw(c, p)
                        bp->c_next = NULL;
                        p->c_cf = cp = bp->c_info;
                } else if (((int)cp & CROUND) == 0) {
                        bp->c_next = NULL;
                        p->c_cf = cp = bp->c_info;
                } else if (((int)cp & CROUND) == 0) {
-                       bp = (struct cblock *)cp - 1;
+                       bp = cbptr(cp) - 1;
                        if ((bp->c_next = cfreelist) == NULL) {
                                splx(s);
                                return (-1);
                        if ((bp->c_next = cfreelist) == NULL) {
                                splx(s);
                                return (-1);
index 7d8f258..882b7f5 100644 (file)
@@ -3,7 +3,7 @@
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
  * All rights reserved.  The Berkeley software License Agreement
  * specifies the terms and conditions for redistribution.
  *
- *     @(#)tty_tty.c   7.1 (Berkeley) %G%
+ *     @(#)tty_tty.c   7.2 (Berkeley) %G%
  */
 
 /*
  */
 
 /*
@@ -65,7 +65,13 @@ syioctl(dev, cmd, addr, flag)
        if (cmd == TIOCNOTTY) {
                u.u_ttyp = 0;
                u.u_ttyd = 0;
        if (cmd == TIOCNOTTY) {
                u.u_ttyp = 0;
                u.u_ttyd = 0;
-               u.u_procp->p_pgrp = 0;
+               if (SESS_LEADER(u.u_procp)) {
+                       /* 
+                        * XXX - check posix draft
+                        */
+                       u.u_ttyp->t_session = 0;
+                       u.u_ttyp->t_pgid = 0;
+               }
                return (0);
        }
        if (u.u_ttyp == NULL)
                return (0);
        }
        if (u.u_ttyp == NULL)