interrupt has two r's
[unix-history] / usr / src / usr.bin / tset / tset.c
index 7024362..5aa9621 100644 (file)
@@ -1,5 +1,18 @@
-#
-       char    id_tset[] = "@(#)tset.c 1.4 %G%";
+/*
+ * Copyright (c) 1980 Regents of the University of California.
+ * All rights reserved.  The Berkeley software License Agreement
+ * specifies the terms and conditions for redistribution.
+ */
+
+#ifndef lint
+char copyright[] =
+"@(#) Copyright (c) 1980 Regents of the University of California.\n\
+ All rights reserved.\n";
+#endif not lint
+
+#ifndef lint
+static char sccsid[] = "@(#)tset.c     5.5 (Berkeley) %G%";
+#endif not lint
 
 /*
 **  TSET -- set terminal modes
 
 /*
 **  TSET -- set terminal modes
 **                     the kill character is untouched; however, if
 **                     not specified and the kill character is NULL
 **                     (zero byte), the kill character is set to '@'.
 **                     the kill character is untouched; however, if
 **                     not specified and the kill character is NULL
 **                     (zero byte), the kill character is set to '@'.
-**             -iC -- reserved for setable interrupt character.
+**             -iC -- set the interrupt character to C on all terminals.
+                       Default for C is Delete.  If not specified, the
+                       interrupt character is untouched; however, if
+                       not specified and the kill character is NULL
+                       (zero byte), the interrupt character is set to
+                       Delete.
 **             -qC -- reserved for setable quit character.
 **             -m -- map the system identified type to some user
 **                     specified type. The mapping can be baud rate
 **             -qC -- reserved for setable quit character.
 **             -m -- map the system identified type to some user
 **                     specified type. The mapping can be baud rate
 **                     (-d type  ->  -m dialup:type)
 **                     (-p type  ->  -m plug:type)
 **                     Syntax: -m identifier [test baudrate] :type
 **                     (-d type  ->  -m dialup:type)
 **                     (-p type  ->  -m plug:type)
 **                     Syntax: -m identifier [test baudrate] :type
-**                     where: ``identifier'' is whatever is found in
-**                     /etc/ttytype for this port, (abscence of an identifier
+**                     where: ``identifier'' is terminal type found in
+**                     /etc/ttys for this port, (abscence of an identifier
 **                     matches any identifier); ``test'' may be any combination
 **                     of  >  =  <  !  @; ``baudrate'' is as with stty(1);
 **                     ``type'' is the actual terminal type to use if the
 **                     matches any identifier); ``test'' may be any combination
 **                     of  >  =  <  !  @; ``baudrate'' is as with stty(1);
 **                     ``type'' is the actual terminal type to use if the
 **                     the output of -s to use virtual terminal sequences.
 **
 **     Files:
 **                     the output of -s to use virtual terminal sequences.
 **
 **     Files:
-**             /etc/ttytype
+**             /etc/ttys
 **                     contains a terminal id -> terminal type
 **                     mapping; used when any user mapping is specified,
 **                     or the environment doesn't have TERM set.
 **                     contains a terminal id -> terminal type
 **                     mapping; used when any user mapping is specified,
 **                     or the environment doesn't have TERM set.
 **                     and compiles code to look there.
 **
 **     Requires:
 **                     and compiles code to look there.
 **
 **     Requires:
-**             Routines to handle htmp, ttytype, and ttycap.
+**             Routines to handle htmp, ttys, and ttycap.
 **
 **     Compilation Flags:
 **             OLDFLAGS -- must be defined to compile code for any of
 **
 **     Compilation Flags:
 **             OLDFLAGS -- must be defined to compile code for any of
 **             OLDDIALUP -- accept the -d flag.
 **             OLDPLUGBOARD -- accept the -p flag.
 **             OLDARPANET -- accept the -a flag.
 **             OLDDIALUP -- accept the -d flag.
 **             OLDPLUGBOARD -- accept the -p flag.
 **             OLDARPANET -- accept the -a flag.
-**             FULLLOGIN -- if defined, login sets the ttytype from
-**                     /etc/ttytype file.
 **             V6 -- if clear, use environments, not htmp.
 **                     also use TIOCSETN rather than stty to avoid flushing
 **             V6 -- if clear, use environments, not htmp.
 **                     also use TIOCSETN rather than stty to avoid flushing
-**             GTTYN -- if set, compiles code to look at /etc/ttytype.
+**             GTTYN -- if set, compiles code to look at /etc/ttys.
 **             UCB_NTTY -- set to handle new tty driver modes.
 **
 **     Trace Flags:
 **             UCB_NTTY -- set to handle new tty driver modes.
 **
 **     Trace Flags:
 **             12/78 -- modified for eventual migration to VAX/UNIX,
 **                     so the '-' option is changed to output only
 **                     the terminal type to STDOUT instead of
 **             12/78 -- modified for eventual migration to VAX/UNIX,
 **                     so the '-' option is changed to output only
 **                     the terminal type to STDOUT instead of
-**                     FILEDES.  FULLLOGIN flag added.
+**                     FILEDES.
 **             9/78 -- '-' and '-p' options added (now fully
 **                     compatible with ttytype!), and spaces are
 **                     permitted between the -d and the type.
 **             9/78 -- '-' and '-p' options added (now fully
 **                     compatible with ttytype!), and spaces are
 **                     permitted between the -d and the type.
 **             10/77 -- Written.
 */
 
 **             10/77 -- Written.
 */
 
+#define UCB_NTTY
+
 # ifdef USG
 #  define index strchr
 #  define rindex strrchr
 #  define curerase mode.c_cc[VERASE]
 #  define curkill mode.c_cc[VKILL]
 # ifdef USG
 #  define index strchr
 #  define rindex strrchr
 #  define curerase mode.c_cc[VERASE]
 #  define curkill mode.c_cc[VKILL]
+#  define curintr mode.c_cc[VINTR]
 #  define olderase oldmode.c_cc[VERASE]
 #  define oldkill oldmode.c_cc[VKILL]
 #  define olderase oldmode.c_cc[VERASE]
 #  define oldkill oldmode.c_cc[VKILL]
+#  define oldintr oldmode.c_cc[VINTR]
 # else
 #  define curerase mode.sg_erase
 #  define curkill mode.sg_kill
 # else
 #  define curerase mode.sg_erase
 #  define curkill mode.sg_kill
+#  define curintr tchar.t_intrc
 #  define olderase oldmode.sg_erase
 #  define oldkill oldmode.sg_kill
 #  define olderase oldmode.sg_erase
 #  define oldkill oldmode.sg_kill
+#  define oldintr oldtchar.t_intrc
 # endif
 
 # endif
 
-/*
-# define       FULLLOGIN       1
-/*/
 # ifndef V6
 # ifndef V6
-# define       GTTYN           "/etc/ttytype"
+# define       GTTYN
+# include      <ttyent.h>
 # endif
 
 # ifndef USG
 # endif
 
 # ifndef USG
 # define       isalnum(c)      (c > ' ' && !(index("<@=>!:|\177", c)) )
 # define       OLDERASE        '#'
 # define       OLDKILL         '@'
 # define       isalnum(c)      (c > ' ' && !(index("<@=>!:|\177", c)) )
 # define       OLDERASE        '#'
 # define       OLDKILL         '@'
+# define       OLDINTR         '\177'  /* del */
 
 # define       FILEDES         2       /* do gtty/stty on this descriptor */
 # define       STDOUT          1       /* output of -s/-S to this descriptor */
 
 # define       FILEDES         2       /* do gtty/stty on this descriptor */
 # define       STDOUT          1       /* output of -s/-S to this descriptor */
@@ -416,6 +437,7 @@ int VirTermNo = -2;
 
 char   Erase_char;             /* new erase character */
 char   Kill_char;              /* new kill character */
 
 char   Erase_char;             /* new erase character */
 char   Kill_char;              /* new kill character */
+char   Intr_char;              /* new interrupt character */
 char   Specialerase;           /* set => Erase_char only on terminals with backspace */
 
 # ifdef        GTTYN
 char   Specialerase;           /* set => Erase_char only on terminals with backspace */
 
 # ifdef        GTTYN
@@ -442,6 +464,7 @@ int DoVirtTerm = YES;       /* Set up a virtual terminal */
 int    New = NO;               /* use new tty discipline */
 int    HasAM;                  /* True if terminal has automatic margins */
 int    PadBaud;                /* Min rate of padding needed */
 int    New = NO;               /* use new tty discipline */
 int    HasAM;                  /* True if terminal has automatic margins */
 int    PadBaud;                /* Min rate of padding needed */
+int    lines, columns;
 
 # define CAPBUFSIZ     1024
 char   Capbuf[CAPBUFSIZ];      /* line from /etc/termcap for this TtyType */
 
 # define CAPBUFSIZ     1024
 char   Capbuf[CAPBUFSIZ];      /* line from /etc/termcap for this TtyType */
@@ -461,6 +484,8 @@ struct delay
 # ifndef USG
 struct sgttyb  mode;
 struct sgttyb  oldmode;
 # ifndef USG
 struct sgttyb  mode;
 struct sgttyb  oldmode;
+struct tchars  tchar;
+struct tchars  oldtchar;
 # else
 struct termio  mode;
 struct termio  oldmode;
 # else
 struct termio  mode;
 struct termio  oldmode;
@@ -474,7 +499,7 @@ main(argc, argv)
 int    argc;
 char   *argv[];
 {
 int    argc;
 char   *argv[];
 {
-       char            buf[256];
+       char            buf[CAPBUFSIZ];
        char            termbuf[32];
        auto char       *bufp;
        register char   *p;
        char            termbuf[32];
        auto char       *bufp;
        register char   *p;
@@ -486,6 +511,7 @@ char        *argv[];
        char            *nextarg();
        char            *mapped();
        extern char     *rindex();
        char            *nextarg();
        char            *mapped();
        extern char     *rindex();
+       struct winsize  win;
 # ifdef V6
        extern char     *hsgettype();
 # else
 # ifdef V6
        extern char     *hsgettype();
 # else
@@ -525,6 +551,10 @@ char       *argv[];
                exit(1);
        }
        bmove(&mode, &oldmode, sizeof mode);
                exit(1);
        }
        bmove(&mode, &oldmode, sizeof mode);
+# ifdef TIOCGETC
+       (void)ioctl(FILEDES, TIOCGETC, &tchar);
+       bmove(&tchar, &oldtchar, sizeof tchar);
+# endif
 # ifndef USG
        ospeed = mode.sg_ospeed & 017;
 # else
 # ifndef USG
        ospeed = mode.sg_ospeed & 017;
 # else
@@ -587,7 +617,7 @@ char        *argv[];
                ioctl(FILEDES, TCGETA, &mode);
                curerase = CHK(curerase, OLDERASE);
                curkill = CHK(curkill, OLDKILL);
                ioctl(FILEDES, TCGETA, &mode);
                curerase = CHK(curerase, OLDERASE);
                curkill = CHK(curkill, OLDKILL);
-               mode.c_cc[VINTR] = CHK(mode.c_cc[VINTR], CTRL('?'));
+               curintr = CHK(curintr, CTRL('?'));
                mode.c_cc[VQUIT] = CHK(mode.c_cc[VQUIT], CTRL('\\'));
                mode.c_cc[VEOF] = CHK(mode.c_cc[VEOF], CTRL('D'));
 
                mode.c_cc[VQUIT] = CHK(mode.c_cc[VQUIT], CTRL('\\'));
                mode.c_cc[VEOF] = CHK(mode.c_cc[VEOF], CTRL('D'));
 
@@ -654,6 +684,21 @@ char       *argv[];
                                }
                                continue;
 
                                }
                                continue;
 
+# if defined(USG) || defined(TIOCGETC)
+                         case 'i':     /* erase character */
+                               if (*p == NULL)
+                                       Intr_char = CTRL('C');
+                               else
+                               {
+                                       if (*p == '^' && p[1] != NULL)
+                                               Intr_char = CTRL(*++p);
+                                       else
+                                               Intr_char = *p;
+                                       p++;
+                               }
+                               continue;
+# endif
+
                          case 'k':     /* kill character */
                                if (*p == NULL)
                                        Kill_char = CTRL('X');
                          case 'k':     /* kill character */
                                if (*p == NULL)
                                        Kill_char = CTRL('X');
@@ -847,7 +892,7 @@ mapold:                             Map->Ident = NewType;
        if (bufp && *bufp != '/')
                strcpy(bufp-8, "NOTHING");      /* overwrite only "TERMCAP" */
        /* get current idea of terminal type from environment */
        if (bufp && *bufp != '/')
                strcpy(bufp-8, "NOTHING");      /* overwrite only "TERMCAP" */
        /* get current idea of terminal type from environment */
-       if (!Dash_h && !Mapped && TtyType == 0)
+       if (!Dash_h && TtyType == 0)
                TtyType = getenv("TERM");
 # endif
 
                TtyType = getenv("TERM");
 # endif
 
@@ -894,7 +939,12 @@ mapold:                            Map->Ident = NewType;
 
        /* check for dialup or other mapping */
        if (Mapped)
 
        /* check for dialup or other mapping */
        if (Mapped)
+       {
+               if (!(Alias[0] && isalias(TtyType)))
+                       if (tgetent(Capbuf, TtyType) > 0)
+                               makealias(Capbuf);
                TtyType = mapped(TtyType);
                TtyType = mapped(TtyType);
+       }
 
        /* TtyType now contains a pointer to the type of the terminal */
        /* If the first character is '?', ask the user */
 
        /* TtyType now contains a pointer to the type of the terminal */
        /* If the first character is '?', ask the user */
@@ -907,6 +957,7 @@ mapold:                             Map->Ident = NewType;
        }
        if (Ask)
        {
        }
        if (Ask)
        {
+ask:
                prs("TERM = (");
                prs(TtyType);
                prs(") ");
                prs("TERM = (");
                prs(TtyType);
                prs(") ");
@@ -941,7 +992,8 @@ mapold:                             Map->Ident = NewType;
                        if (DoSetenv)
                        {
                                TtyType = DEFTYPE;
                        if (DoSetenv)
                        {
                                TtyType = DEFTYPE;
-                               tgetent(Capbuf, TtyType);
+                               Alias[0] = '\0';
+                               goto ask;
                        }
                        else
                                exit(1);
                        }
                        else
                                exit(1);
@@ -977,6 +1029,11 @@ mapold:                           Map->Ident = NewType;
                if (Erase_char != 0)
                        curerase = Erase_char;
 
                if (Erase_char != 0)
                        curerase = Erase_char;
 
+               if (curintr == 0)
+                       curintr = OLDKILL;
+               if (Intr_char != 0)
+                       curintr = Intr_char;
+
                if (curkill == 0)
                        curkill = OLDKILL;
                if (Kill_char != 0)
                if (curkill == 0)
                        curkill = OLDKILL;
                if (Kill_char != 0)
@@ -1089,6 +1146,19 @@ mapold:                          Map->Ident = NewType;
                if (tgetstr("pc", &bufp) != 0)
                        PC = buf[0];
 
                if (tgetstr("pc", &bufp) != 0)
                        PC = buf[0];
 
+               columns = tgetnum("co");
+               lines = tgetnum("li");
+
+               /* Set window size */
+               if (DoSetenv) {
+                       ioctl(FILEDES, TIOCGWINSZ, &win);
+                       if (win.ws_row == 0 && win.ws_col == 0 &&
+                           lines > 0 && columns > 0) {
+                               win.ws_row = lines;
+                               win.ws_col = columns;
+                               ioctl(FILEDES, TIOCSWINSZ, &win);
+                       }
+               }
                /* output startup string */
                if (!NoInit)
                {
                /* output startup string */
                if (!NoInit)
                {
@@ -1234,9 +1304,10 @@ mapold:                          Map->Ident = NewType;
        if (RepOnly)
                exit(0);
 
        if (RepOnly)
                exit(0);
 
-       /* tell about changing erase and kill characters */
+       /* tell about changing erase, kill and interrupt characters */
        reportek("Erase", curerase, olderase, OLDERASE);
        reportek("Kill", curkill, oldkill, OLDKILL);
        reportek("Erase", curerase, olderase, OLDERASE);
        reportek("Kill", curkill, oldkill, OLDKILL);
+       reportek("Interrupt", curintr, oldintr, OLDINTR);
 
 # ifdef V6
        /* update htmp */
 
 # ifdef V6
        /* update htmp */
@@ -1275,15 +1346,13 @@ settabs()
        char *capsp = caps;
        char *clear_tabs, *set_tab, *set_column, *set_pos;
        char *tg_out, *tgoto();
        char *capsp = caps;
        char *clear_tabs, *set_tab, *set_column, *set_pos;
        char *tg_out, *tgoto();
-       int columns, lines, c;
+       int c;
 
        clear_tabs = tgetstr("ct", &capsp);
        set_tab = tgetstr("st", &capsp);
        set_column = tgetstr("ch", &capsp);
        if (set_column == 0)
                set_pos = tgetstr("cm", &capsp);
 
        clear_tabs = tgetstr("ct", &capsp);
        set_tab = tgetstr("st", &capsp);
        set_column = tgetstr("ch", &capsp);
        if (set_column == 0)
                set_pos = tgetstr("cm", &capsp);
-       columns = tgetnum("co");
-       lines = tgetnum("li");
 
        if (clear_tabs && set_tab) {
                prc('\r');      /* force to be at left margin */
 
        if (clear_tabs && set_tab) {
                prc('\r');      /* force to be at left margin */
@@ -1325,17 +1394,30 @@ int     flag;
 # else
        struct termio *ttymode;
 # endif
 # else
        struct termio *ttymode;
 # endif
+# ifdef TIOCGETC
+       struct tchars *ttytchars;
+# endif
 
 
-       if (flag < 0)   /* unconditionally reset oldmode (called from init) */
+       if (flag < 0) { /* unconditionally reset oldmode (called from init) */
                ttymode = &oldmode;
                ttymode = &oldmode;
-       else if (!bequal(&mode, &oldmode, sizeof mode))
+# ifdef TIOCGETC
+               ttytchars = &oldtchar;
+# endif
+       } else if (!bequal(&mode, &oldmode, sizeof mode)) {
                ttymode = &mode;
                ttymode = &mode;
-       else            /* don't need it */
+# ifdef TIOCGETC
+               ttytchars = &tchar;
+# endif
+       } else  {       /* don't need it */
 # ifndef USG
        ttymode = (struct sgttyb *)0;
 # else
        ttymode = (struct termio *)0;
 # endif
 # ifndef USG
        ttymode = (struct sgttyb *)0;
 # else
        ttymode = (struct termio *)0;
 # endif
+# ifdef TIOCGETC
+       ttytchars = (struct tchars *)0;
+# endif
+       }
        
        if (ttymode)
        {
        
        if (ttymode)
        {
@@ -1349,6 +1431,11 @@ int      flag;
 #  endif
 # endif
        }
 #  endif
 # endif
        }
+# ifdef TIOCGETC
+       if (ttytchars) {
+               ioctl(FILEDES, TIOCSETC, ttytchars);
+       }
+# endif
 # ifdef CBVIRTTERM
        if (VirTermNo != -2) {
                int r1, r2;
 # ifdef CBVIRTTERM
        if (VirTermNo != -2) {
                int r1, r2;
@@ -1421,7 +1508,7 @@ setdelay(cap, dtab, bits, flags)
 char           *cap;
 struct delay   dtab[];
 int            bits;
 char           *cap;
 struct delay   dtab[];
 int            bits;
-int            *flags;
+short          *flags;
 {
        register int    i;
        register struct delay   *p;
 {
        register int    i;
        register struct delay   *p;
@@ -1604,18 +1691,13 @@ char *
 stypeof(ttyid)
 char   *ttyid;
 {
 stypeof(ttyid)
 char   *ttyid;
 {
-       static char     typebuf[50];
        register char   *PortType;
        register char   *PortName;
        register char   *TtyId;
        register char   *PortType;
        register char   *PortName;
        register char   *TtyId;
-       register char   *p;
-       register FILE   *f;
+       struct ttyent *t;
 
        if (ttyid == NOTTY)
                return (DEFTYPE);
 
        if (ttyid == NOTTY)
                return (DEFTYPE);
-       f = fopen(GTTYN, "r");
-       if (f == NULL)
-               return (DEFTYPE);
 
        /* split off end of name */
        TtyId = ttyid;
 
        /* split off end of name */
        TtyId = ttyid;
@@ -1624,37 +1706,17 @@ char    *ttyid;
                        TtyId = ttyid;
 
        /* scan the file */
                        TtyId = ttyid;
 
        /* scan the file */
-       while (fgets(typebuf, sizeof typebuf, f) != NULL)
+       if ((t = getttynam(TtyId)) != NULL)
        {
        {
-               p = PortType = typebuf;
-               while (*p && isalnum(*p))
-                       p++;
-               *p++ = NULL;
-
-               /* skip separator */
-               while (*p && !isalnum(*p))
-                       p++;
-
-               PortName = p;
-               /* put NULL at end of name */
-               while (*p && isalnum(*p))
-                       p++;
-               *p = NULL;
-
-               /* check match on port name */
-               if (sequal(PortName, TtyId))    /* found it */
-               {
-                       fclose (f);
-                       /* get aliases from termcap entry */
-                       if (Mapped && tgetent(Capbuf, PortType) > 0) {
-                               makealias(Capbuf);
-                               if (sequal(Alias[0], PortType) && Alias[1])
-                                       PortType = Alias[1];
-                       }
-                       return(PortType);
+               PortType = t->ty_type;
+               /* get aliases from termcap entry */
+               if (Mapped && tgetent(Capbuf, PortType) > 0) {
+                       makealias(Capbuf);
+                       if (sequal(Alias[0], PortType) && Alias[1])
+                               PortType = Alias[1];
                }
                }
+               return (PortType);
        }
        }
-       fclose (f);
        return (DEFTYPE);
 }
 # endif
        return (DEFTYPE);
 }
 # endif