1: /*
   2:  * Copyright (c) 1980 Regents of the University of California.
   3:  * All rights reserved.  The Berkeley software License Agreement
   4:  * specifies the terms and conditions for redistribution.
   5:  */
   6: 
   7: #ifndef lint
   8: char copyright[] =
   9: "@(#) Copyright (c) 1980 Regents of the University of California.\n\
  10:  All rights reserved.\n";
  11: #endif not lint
  12: 
  13: #ifndef lint
  14: static char sccsid[] = "@(#)tset.c	5.8 (Berkeley) 4/28/86";
  15: #endif not lint
  16: 
  17: /*
  18: **  TSET -- set terminal modes
  19: **
  20: **	This program does sophisticated terminal initialization.
  21: **	I recommend that you include it in your .profile or .login
  22: **	file to initialize whatever terminal you are on.
  23: **
  24: **	There are several features:
  25: **
  26: **	A special file or sequence (as controlled by the termcap file)
  27: **	is sent to the terminal.
  28: **
  29: **	Mode bits are set on a per-terminal_type basis (much better
  30: **	than UNIX itself).  This allows special delays, automatic
  31: **	tabs, etc.
  32: **
  33: **	Erase and Kill characters can be set to whatever you want.
  34: **	Default is to change erase to control-H on a terminal which
  35: **	can overstrike, and leave it alone on anything else.  Kill
  36: **	is always left alone unless specifically requested.  These
  37: **	characters can be represented as "^X" meaning control-X;
  38: **	X is any character.
  39: **
  40: **	Terminals which are dialups or plugboard types can be aliased
  41: **	to whatever type you may have in your home or office.  Thus,
  42: **	if you know that when you dial up you will always be on a
  43: **	TI 733, you can specify that fact to tset.  You can represent
  44: **	a type as "?type".  This will ask you what type you want it
  45: **	to be -- if you reply with just a newline, it will default
  46: **	to the type given.
  47: **
  48: **	The current terminal type can be queried.
  49: **
  50: **	Usage:
  51: **		tset [-] [-EC] [-eC] [-kC] [-iC] [-s] [-h] [-u] [-r]
  52: **			[-m [ident] [test baudrate] :type]
  53: **			[-Q] [-I] [-S] [type]
  54: **
  55: **		In systems with environments, use:
  56: **			eval `tset -s ...`
  57: **		Actually, this doesn't work in old csh's.
  58: **		Instead, use:
  59: **			tset -s ... > tset.tmp
  60: **			source tset.tmp
  61: **			rm tset.tmp
  62: **		or:
  63: **			set noglob
  64: **			set term=(`tset -S ....`)
  65: **			setenv TERM $term[1]
  66: **			setenv TERMCAP "$term[2]"
  67: **			unset term
  68: **			unset noglob
  69: **
  70: **	Positional Parameters:
  71: **		type -- the terminal type to force.  If this is
  72: **			specified, initialization is for this
  73: **			terminal type.
  74: **
  75: **	Flags:
  76: **		- -- report terminal type.  Whatever type is
  77: **			decided on is reported.  If no other flags
  78: **			are stated, the only affect is to write
  79: **			the terminal type on the standard output.
  80: **		-r -- report to user in addition to other flags.
  81: **		-EC -- set the erase character to C on all terminals
  82: **			except those which cannot backspace (e.g.,
  83: **			a TTY 33).  C defaults to control-H.
  84: **		-eC -- set the erase character to C on all terminals.
  85: **			C defaults to control-H.  If not specified,
  86: **			the erase character is untouched; however, if
  87: **			not specified and the erase character is NULL
  88: **			(zero byte), the erase character  is set to delete.
  89: **		-kC -- set the kill character to C on all terminals.
  90: **			Default for C is control-X.  If not specified,
  91: **			the kill character is untouched; however, if
  92: **			not specified and the kill character is NULL
  93: **			(zero byte), the kill character is set to control-U.
  94: **		-iC -- set the interrupt character to C on all terminals.
  95: **			Default for C is control-C.  If not specified, the
  96: **			interrupt character is untouched; however, if
  97: **			not specified and the interrupt character is NULL
  98: **			(zero byte), the interrupt character is set to
  99: **			control-C.
 100: **		-qC -- reserved for setable quit character.
 101: **		-m -- map the system identified type to some user
 102: **			specified type. The mapping can be baud rate
 103: **			dependent. This replaces the old -d, -p flags.
 104: **			(-d type  ->  -m dialup:type)
 105: **			(-p type  ->  -m plug:type)
 106: **			Syntax:	-m identifier [test baudrate] :type
 107: **			where: ``identifier'' is terminal type found in
 108: **			/etc/ttys for this port, (abscence of an identifier
 109: **			matches any identifier); ``test'' may be any combination
 110: **			of  >  =  <  !  @; ``baudrate'' is as with stty(1);
 111: **			``type'' is the actual terminal type to use if the
 112: **			mapping condition is met. Multiple maps are scanned
 113: **			in order and the first match prevails.
 114: **		-n -- If the new tty driver from UCB is available, this flag
 115: **			will activate the new options for erase and kill
 116: **			processing. This will be different for printers
 117: **			and crt's. For crts, if the baud rate is < 1200 then
 118: **			erase and kill don't remove characters from the screen.
 119: **		-h -- don't read htmp file.  Normally the terminal type
 120: **			is determined by reading the htmp file or the
 121: **			environment (unless some mapping is specified).
 122: **			This forces a read of the ttytype file -- useful
 123: **			when htmp is somehow wrong. (V6 only)
 124: **		-u -- don't update htmp.  It seemed like this should
 125: **			be put in.  Note that htmp is never actually
 126: **			written if there are no changes, so don't bother
 127: **			bother using this for efficiency reasons alone.
 128: **		-s -- output setenv commands for TERM.  This can be
 129: **			used with
 130: **				`tset -s ...`
 131: **			and is to be prefered to:
 132: **				setenv TERM `tset - ...`
 133: **			because -s sets the TERMCAP variable also.
 134: **		-S -- Similar to -s but outputs 2 strings suitable for
 135: **			use in csh .login files as follows:
 136: **				set noglob
 137: **				set term=(`tset -S .....`)
 138: **				setenv TERM $term[1]
 139: **				setenv TERMCAP "$term[2]"
 140: **				unset term
 141: **				unset noglob
 142: **		-Q -- be quiet.  don't output 'Erase set to' etc.
 143: **		-I -- don't do terminal initialization (is & if
 144: **			strings).
 145: **		-v -- On virtual terminal systems, don't set up a
 146: **			virtual terminal.  Otherwise tset will tell
 147: **			the operating system what kind of terminal you
 148: **			are on (if it is a known terminal) and fix up
 149: **			the output of -s to use virtual terminal sequences.
 150: **
 151: **	Files:
 152: **		/etc/ttys
 153: **			contains a terminal id -> terminal type
 154: **			mapping; used when any user mapping is specified,
 155: **			or the environment doesn't have TERM set.
 156: **		/etc/termcap
 157: **			a terminal_type -> terminal_capabilities
 158: **			mapping.
 159: **
 160: **	Return Codes:
 161: **		-1 -- couldn't open ttycap.
 162: **		1 -- bad terminal type, or standard output not tty.
 163: **		0 -- ok.
 164: **
 165: **	Defined Constants:
 166: **		DIALUP -- the type code for a dialup port.
 167: **		PLUGBOARD -- the type code for a plugboard port.
 168: **		ARPANET -- the type code for an arpanet port.
 169: **		BACKSPACE -- control-H, the default for -e.
 170: **		CNTL('X') -- control-X, the default for -k.
 171: **		OLDERASE -- the system default erase character.
 172: **		OLDKILL -- the system default kill character.
 173: **		FILEDES -- the file descriptor to do the operation
 174: **			on, nominally 1 or 2.
 175: **		STDOUT -- the standard output file descriptor.
 176: **		UIDMASK -- the bit pattern to mask with the getuid()
 177: **			call to get just the user id.
 178: **		GTTYN -- defines file containing generalized ttynames
 179: **			and compiles code to look there.
 180: **
 181: **	Requires:
 182: **		Routines to handle htmp, ttys, and ttycap.
 183: **
 184: **	Compilation Flags:
 185: **		OLDFLAGS -- must be defined to compile code for any of
 186: **			the -d, -p, or -a flags.
 187: **		OLDDIALUP -- accept the -d flag.
 188: **		OLDPLUGBOARD -- accept the -p flag.
 189: **		OLDARPANET -- accept the -a flag.
 190: **		V6 -- if clear, use environments, not htmp.
 191: **			also use TIOCSETN rather than stty to avoid flushing
 192: **		GTTYN -- if set, compiles code to look at /etc/ttys.
 193: **		UCB_NTTY -- set to handle new tty driver modes.
 194: **
 195: **	Trace Flags:
 196: **		none
 197: **
 198: **	Diagnostics:
 199: **		Bad flag
 200: **			An incorrect option was specified.
 201: **		Too few args
 202: **			more command line arguments are required.
 203: **		Unexpected arg
 204: **			wrong type of argument was encountered.
 205: **		Cannot open ...
 206: **			The specified file could not be openned.
 207: **		Type ... unknown
 208: **			An unknown terminal type was specified.
 209: **		Cannot update htmp
 210: **			Cannot update htmp file when the standard
 211: **			output is not a terminal.
 212: **		Erase set to ...
 213: **			Telling that the erase character has been
 214: **			set to the specified character.
 215: **		Kill set to ...
 216: **			Ditto for kill
 217: **		Erase is ...    Kill is ...
 218: **			Tells that the erase/kill characters were
 219: **			wierd before, but they are being left as-is.
 220: **		Not a terminal
 221: **			Set if FILEDES is not a terminal.
 222: **
 223: **	Compilation Instructions:
 224: **		cc -n -O tset.c -ltermlib
 225: **		mv a.out tset
 226: **		chown bin tset
 227: **		chmod 4755 tset
 228: **
 229: **		where 'bin' should be whoever owns the 'htmp' file.
 230: **		If 'htmp' is 666, then tset need not be setuid.
 231: **
 232: **		For version 6 the compile command should be:
 233: **		cc -n -O -I/usr/include/retrofit tset.c -ltermlib -lretro -lS
 234: **
 235: **	Author:
 236: **		Eric Allman
 237: **		Electronics Research Labs
 238: **		U.C. Berkeley
 239: **
 240: **	History:
 241: **		1/81 -- Added alias checking for mapping identifiers.
 242: **		9/80 -- Added UCB_NTTY mods to setup the new tty driver.
 243: **			Added the 'reset ...' invocation.
 244: **		7/80 -- '-S' added. '-m' mapping added. TERMCAP string
 245: **			cleaned up.
 246: **		3/80 -- Changed to use tputs.  Prc & flush added.
 247: **		10/79 -- '-s' option extended to handle TERMCAP
 248: **			variable, set noglob, quote the entry,
 249: **			and know about the Bourne shell.  Terminal
 250: **			initialization moved to before any information
 251: **			output so screen clears would not screw you.
 252: **			'-Q' option added.
 253: **		8/79 -- '-' option alone changed to only output
 254: **			type.  '-s' option added.  'VERSION7'
 255: **			changed to 'V6' for compatibility.
 256: **		12/78 -- modified for eventual migration to VAX/UNIX,
 257: **			so the '-' option is changed to output only
 258: **			the terminal type to STDOUT instead of
 259: **			FILEDES.
 260: **		9/78 -- '-' and '-p' options added (now fully
 261: **			compatible with ttytype!), and spaces are
 262: **			permitted between the -d and the type.
 263: **		8/78 -- The sense of -h and -u were reversed, and the
 264: **			-f flag is dropped -- same effect is available
 265: **			by just stating the terminal type.
 266: **		10/77 -- Written.
 267: */
 268: 
 269: #define UCB_NTTY
 270: 
 271: # ifdef USG
 272: #  define index strchr
 273: #  define rindex strrchr
 274: #  define curerase mode.c_cc[VERASE]
 275: #  define curkill mode.c_cc[VKILL]
 276: #  define curintr mode.c_cc[VINTR]
 277: #  define olderase oldmode.c_cc[VERASE]
 278: #  define oldkill oldmode.c_cc[VKILL]
 279: #  define oldintr oldmode.c_cc[VINTR]
 280: # else
 281: #  define curerase mode.sg_erase
 282: #  define curkill mode.sg_kill
 283: #  define curintr tchar.t_intrc
 284: #  define olderase oldmode.sg_erase
 285: #  define oldkill oldmode.sg_kill
 286: #  define oldintr oldtchar.t_intrc
 287: # endif
 288: 
 289: # ifndef V6
 290: # define    GTTYN
 291: # include   <ttyent.h>
 292: # endif
 293: 
 294: # ifndef USG
 295: #  include  <sgtty.h>
 296: # else
 297: #  include  <termio.h>
 298: # endif
 299: 
 300: # include   <stdio.h>
 301: # include   <signal.h>
 302: # ifdef V6
 303: # include   <retrofit.h>
 304: # endif
 305: 
 306: # define    YES     1
 307: # define    NO      0
 308: #undef CNTL
 309: # define    CNTL(c)     ((c)&037)
 310: # define    BACKSPACE   (CNTL('H'))
 311: # define    CHK(val, dft)   (val<=0 ? dft : val)
 312: # define    isdigit(c)  (c >= '0' && c <= '9')
 313: # define    isalnum(c)  (c > ' ' && (index("<@=>!:|\177", c) == NULL))
 314: # define    OLDERASE    '#'
 315: # define    OLDKILL     '@'
 316: # define    OLDINTR     '\177'  /* del */
 317: 
 318: /* default special characters */
 319: #ifndef CERASE
 320: #define CERASE  '\177'
 321: #endif
 322: #ifndef CKILL
 323: #define CKILL   CNTL('U')
 324: #endif
 325: #ifndef CINTR
 326: #define CINTR   CNTL('C')
 327: #endif
 328: #ifndef CDSUSP
 329: #define CQUIT   034     /* FS, ^\ */
 330: #define CSTART  CNTL('Q')
 331: #define CSTOP   CNTL('S')
 332: #define CEOF    CNTL('D')
 333: #define CEOT    CEOF
 334: #define CBRK    0377
 335: #define CSUSP   CNTL('Z')
 336: #define CDSUSP  CNTL('Y')
 337: #define CRPRNT  CNTL('R')
 338: #define CFLUSH  CNTL('O')
 339: #define CWERASE CNTL('W')
 340: #define CLNEXT  CNTL('V')
 341: #endif
 342: 
 343: # define    FILEDES     2   /* do gtty/stty on this descriptor */
 344: # define    STDOUT      1   /* output of -s/-S to this descriptor */
 345: 
 346: # ifdef V6
 347: # define    UIDMASK     0377
 348: # else
 349: # define    UIDMASK     -1
 350: # endif
 351: 
 352: # ifdef UCB_NTTY
 353: # define    USAGE   "usage: tset [-] [-nrsIQS] [-eC] [-kC] [-iC] [-m [ident][test speed]:type] [type]\n"
 354: # else
 355: # define    USAGE   "usage: tset [-] [-rsIQS] [-eC] [-kC] [-iC] [-m [ident][test speed]:type] [type]\n"
 356: # endif
 357: 
 358: # define    OLDFLAGS
 359: # define    DIALUP      "dialup"
 360: # define    OLDDIALUP   "sd"
 361: # define    PLUGBOARD   "plugboard"
 362: # define    OLDPLUGBOARD    "sp"
 363: /***
 364: # define	ARPANET		"arpanet"
 365: # define	OLDARPANET	"sa"
 366: /***/
 367: 
 368: # define    DEFTYPE     "unknown"
 369: 
 370: 
 371: # ifdef GTTYN
 372: # define    NOTTY       0
 373: # else
 374: # define    NOTTY       'x'
 375: # endif
 376: 
 377: /*
 378:  * Baud Rate Conditionals
 379:  */
 380: # define    ANY     0
 381: # define    GT      1
 382: # define    EQ      2
 383: # define    LT      4
 384: # define    GE      (GT|EQ)
 385: # define    LE      (LT|EQ)
 386: # define    NE      (GT|LT)
 387: # define    ALL     (GT|EQ|LT)
 388: 
 389: 
 390: 
 391: # define    NMAP        10
 392: 
 393: struct  map {
 394:     char *Ident;
 395:     char Test;
 396:     char Speed;
 397:     char *Type;
 398: } map[NMAP];
 399: 
 400: struct map *Map = map;
 401: 
 402: /* This should be available in an include file */
 403: struct
 404: {
 405:     char    *string;
 406:     int speed;
 407:     int baudrate;
 408: } speeds[] = {
 409:     "0",    B0, 0,
 410:     "50",   B50,    50,
 411:     "75",   B75,    75,
 412:     "110",  B110,   110,
 413:     "134",  B134,   134,
 414:     "134.5",B134,   134,
 415:     "150",  B150,   150,
 416:     "200",  B200,   200,
 417:     "300",  B300,   300,
 418:     "600",  B600,   600,
 419:     "1200", B1200,  1200,
 420:     "1800", B1800,  1800,
 421:     "2400", B2400,  2400,
 422:     "4800", B4800,  4800,
 423:     "9600", B9600,  9600,
 424:     "19200",EXTA,   19200,
 425:     "exta", EXTA,   19200,
 426:     "extb", EXTB,   38400,
 427:     0,
 428: };
 429: 
 430: #ifdef CBVIRTTERM
 431: struct vterm {
 432:     char cap[2];
 433:     char *value;
 434: } vtab [] = {
 435:     "al",   "\033\120",
 436:     "cd",   "\033\114",
 437:     "ce",   "\033\113",
 438:     "cm",   "\033\107%r%.%.",
 439:     "cl",   "\033\112",
 440:     "dc",   "\033\115",
 441:     "dl",   "\033\116",
 442:     "ic",   "\033\117",
 443:     "kl",   "\033\104",
 444:     "kr",   "\033\103",
 445:     "ku",   "\033\101",
 446:     "kd",   "\033\102",
 447:     "kh",   "\033\105",
 448:     "nd",   "\033\103",
 449:     "se",   "\033\142\004",
 450:     "so",   "\033\141\004",
 451:     "ue",   "\033\142\001",
 452:     "up",   "\033\101",
 453:     "us",   "\033\141\001",
 454:     "\0\0", NULL,
 455: };
 456: 
 457: int VirTermNo = -2;
 458: int HasAM;          /* True if terminal has automatic margins */
 459: # endif CBVIRTTERM
 460: 
 461: char    Erase_char;     /* new erase character */
 462: char    Kill_char;      /* new kill character */
 463: char    Intr_char;      /* new interrupt character */
 464: char    Specialerase;       /* set => Erase_char only on terminals with backspace */
 465: 
 466: # ifdef GTTYN
 467: char    *Ttyid = NOTTY;     /* terminal identifier */
 468: # else
 469: char    Ttyid = NOTTY;      /* terminal identifier */
 470: # endif
 471: char    *TtyType;       /* type of terminal */
 472: char    *DefType;       /* default type if none other computed */
 473: char    *NewType;       /* mapping identifier based on old flags */
 474: int Mapped;         /* mapping has been specified */
 475: int Dash_u;         /* don't update htmp */
 476: int Dash_h;         /* don't read htmp */
 477: int DoSetenv;       /* output setenv commands */
 478: int BeQuiet;        /* be quiet */
 479: int NoInit;         /* don't output initialization string */
 480: int IsReset;        /* invoked as reset */
 481: int Report;         /* report current type */
 482: int Ureport;        /* report to user */
 483: int RepOnly;        /* report only */
 484: int CmndLine;       /* output full command lines (-s option) */
 485: int Ask;            /* ask user for termtype */
 486: int DoVirtTerm = YES;   /* Set up a virtual terminal */
 487: int PadBaud;        /* Min rate of padding needed */
 488: int lines, columns;
 489: 
 490: # define CAPBUFSIZ  1024
 491: char    Capbuf[CAPBUFSIZ];  /* line from /etc/termcap for this TtyType */
 492: char    *Ttycap;        /* termcap line from termcap or environ */
 493: 
 494: char    Aliasbuf[128];
 495: char    *Alias[16];
 496: 
 497: extern char *strcpy();
 498: extern char *index();
 499: 
 500: struct delay
 501: {
 502:     int d_delay;
 503:     int d_bits;
 504: };
 505: 
 506: # include   "tset.delays.h"
 507: 
 508: # ifndef USG
 509: struct sgttyb   mode;
 510: struct sgttyb   oldmode;
 511: struct tchars   tchar;
 512: struct tchars   oldtchar;
 513: # else
 514: struct termio   mode;
 515: struct termio   oldmode;
 516: # endif
 517: # ifdef CBVIRTTERM
 518: struct termcb block = {0, 2, 0, 0, 0, 20};
 519: # endif CBVIRTTERM
 520: 
 521: 
 522: main(argc, argv)
 523: int argc;
 524: char    *argv[];
 525: {
 526:     char        buf[CAPBUFSIZ];
 527:     char        termbuf[32];
 528:     auto char   *bufp;
 529:     register char   *p;
 530:     char        *command;
 531:     register int    i;
 532: # ifdef CBVIRTTERM
 533:     int     j;
 534: # endif CBVIRTTERM
 535:     int     Break;
 536:     int     Not;
 537:     char        *nextarg();
 538:     char        *mapped();
 539:     extern char *rindex();
 540:     struct winsize  win;
 541: # ifdef V6
 542:     extern char *hsgettype();
 543: # else
 544:     extern char *getenv();
 545: # endif
 546: # ifdef GTTYN
 547:     char        *stypeof();
 548:     extern char *ttyname();
 549:     extern char *tgetstr();
 550: # endif
 551:     char        bs_char;
 552:     int     csh;
 553:     int     settle;
 554:     int     setmode();
 555:     extern      prc();
 556:     extern char PC;
 557: # ifdef V6
 558:     extern int  ospeed;
 559: # else
 560:     extern short    ospeed;
 561: # endif
 562: # ifdef UCB_NTTY
 563:     int     lmode;
 564:     int     ldisc;
 565: 
 566:     (void) ioctl(FILEDES, TIOCLGET, (char *)&lmode);
 567:     (void) ioctl(FILEDES, TIOCGETD, (char *)&ldisc);
 568: # endif
 569: 
 570: # ifndef USG
 571:     if (gtty(FILEDES, &mode) < 0)
 572: # else
 573:     if (ioctl(FILEDES, TCGETA, (char *)&mode) < 0)
 574: # endif
 575:     {
 576:         prs("Not a terminal\n");
 577:         exit(1);
 578:     }
 579:     bmove((char *)&mode, (char *)&oldmode, sizeof mode);
 580: # ifdef TIOCGETC
 581:     (void) ioctl(FILEDES, TIOCGETC, (char *)&tchar);
 582:     bmove((char *)&tchar, (char *)&oldtchar, sizeof tchar);
 583: # endif
 584: # ifndef USG
 585:     ospeed = mode.sg_ospeed & 017;
 586: # else
 587:     ospeed = mode.c_cflag & CBAUD;
 588: # endif
 589:     (void) signal(SIGINT, setmode);
 590:     (void) signal(SIGQUIT, setmode);
 591:     (void) signal(SIGTERM, setmode);
 592: 
 593:     if (command = rindex(argv[0], '/'))
 594:         command++;
 595:     else
 596:         command = argv[0];
 597:     if (sequal(command, "reset") )
 598:     {
 599:     /*
 600: 	 * reset the teletype mode bits to a sensible state.
 601: 	 * Copied from the program by Kurt Shoens & Mark Horton.
 602: 	 * Very useful after crapping out in raw.
 603: 	 */
 604: # ifndef V6
 605: #  ifdef UCB_NTTY
 606:         struct ltchars ltc;
 607: 
 608:         if (ldisc == NTTYDISC)
 609:         {
 610:             (void) ioctl(FILEDES, TIOCGLTC, (char *)&ltc);
 611:             ltc.t_suspc = CHK(ltc.t_suspc, CSUSP);
 612:             ltc.t_dsuspc = CHK(ltc.t_dsuspc, CDSUSP);
 613:             ltc.t_rprntc = CHK(ltc.t_rprntc, CRPRNT);
 614:             ltc.t_flushc = CHK(ltc.t_flushc, CFLUSH);
 615:             ltc.t_werasc = CHK(ltc.t_werasc, CWERASE);
 616:             ltc.t_lnextc = CHK(ltc.t_lnextc, CLNEXT);
 617:             (void) ioctl(FILEDES, TIOCSLTC, (char *)&ltc);
 618:         }
 619: #  endif UCB_NTTY
 620: #  ifndef USG
 621: #   ifdef TIOCGETC
 622:         tchar.t_intrc = CHK(tchar.t_intrc, CINTR);
 623:         tchar.t_quitc = CHK(tchar.t_quitc, CQUIT);
 624:         tchar.t_startc = CHK(tchar.t_startc, CSTART);
 625:         tchar.t_stopc = CHK(tchar.t_stopc, CSTOP);
 626:         tchar.t_eofc = CHK(tchar.t_eofc, CEOF);
 627:         /* brkc is left alone */
 628:         (void) ioctl(FILEDES, TIOCSETC, (char *)&tchar);
 629: #   endif TIOCGETC
 630:         mode.sg_flags &= ~(RAW
 631: #   ifdef CBREAK
 632:                     |CBREAK
 633: #   endif CBREAK
 634:                         |VTDELAY|ALLDELAY);
 635:         mode.sg_flags |= XTABS|ECHO|CRMOD|ANYP;
 636:         curerase = CHK(curerase, CERASE);
 637:         curkill = CHK(curkill, CKILL);
 638:         curintr = CHK(curintr, CINTR);
 639: #  else USG
 640:         (void) ioctl(FILEDES, TCGETA, (char *)&mode);
 641:         curerase = CHK(curerase, OLDERASE);
 642:         curkill = CHK(curkill, OLDKILL);
 643:         curintr = CHK(curintr, OLDINTR);
 644:         mode.c_cc[VQUIT] = CHK(mode.c_cc[VQUIT], CQUIT);
 645:         mode.c_cc[VEOF] = CHK(mode.c_cc[VEOF], CEOF);
 646: 
 647:         mode.c_iflag |= (BRKINT|ISTRIP|ICRNL|IXON);
 648:         mode.c_iflag &= ~(IGNBRK|PARMRK|INPCK|INLCR|IGNCR|IUCLC|IXOFF);
 649:         mode.c_oflag |= (OPOST|ONLCR);
 650:         mode.c_oflag &= ~(OLCUC|OCRNL|ONOCR|ONLRET|OFILL|OFDEL|
 651:                 NLDLY|CRDLY|TABDLY|BSDLY|VTDLY|FFDLY);
 652:         mode.c_cflag |= (CS7|CREAD);
 653:         mode.c_cflag &= ~(CSIZE|PARODD|CLOCAL);
 654:         mode.c_lflag |= (ISIG|ICANON|ECHO|ECHOK);
 655:         mode.c_lflag &= ~(XCASE|ECHONL|NOFLSH);
 656:         (void) ioctl(FILEDES, TCSETAW, (char *)&mode);
 657: #  endif USG
 658: # endif V6
 659:         Dash_u = YES;
 660:         BeQuiet = YES;
 661:         IsReset = YES;
 662:     }
 663:     else if (argc == 2 && sequal(argv[1], "-"))
 664:     {
 665:         RepOnly = YES;
 666:         Dash_u = YES;
 667:     }
 668:     argc--;
 669: 
 670:     /* scan argument list and collect flags */
 671:     while (--argc >= 0)
 672:     {
 673:         p = *++argv;
 674:         if (*p == '-')
 675:         {
 676:             if (*++p == NULL)
 677:                 Report = YES; /* report current terminal type */
 678:             else while (*p) switch (*p++)
 679:             {
 680: 
 681: # ifdef UCB_NTTY
 682:               case 'n':
 683:                 ldisc = NTTYDISC;
 684:                 if (ioctl(FILEDES, TIOCSETD, (char *)&ldisc)<0)
 685:                     fatal("ioctl ", "new");
 686:                 continue;
 687: # endif
 688: 
 689:               case 'r': /* report to user */
 690:                 Ureport = YES;
 691:                 continue;
 692: 
 693:               case 'E': /* special erase: operate on all but TTY33 */
 694:                 Specialerase = YES;
 695:                 /* explicit fall-through to -e case */
 696: 
 697:               case 'e': /* erase character */
 698:                 if (*p == NULL)
 699:                     Erase_char = -1;
 700:                 else
 701:                 {
 702:                     if (*p == '^' && p[1] != NULL)
 703:                         if (*++p == '?')
 704:                             Erase_char = '\177';
 705:                         else
 706:                             Erase_char = CNTL(*p);
 707:                     else
 708:                         Erase_char = *p;
 709:                     p++;
 710:                 }
 711:                 continue;
 712: 
 713: # if defined(USG) || defined(TIOCGETC)
 714:               case 'i': /* interrupt character */
 715:                 if (*p == NULL)
 716:                     Intr_char = CNTL('C');
 717:                 else
 718:                 {
 719:                     if (*p == '^' && p[1] != NULL)
 720:                         if (*++p == '?')
 721:                             Intr_char = '\177';
 722:                         else
 723:                             Intr_char = CNTL(*p);
 724:                     else
 725:                         Intr_char = *p;
 726:                     p++;
 727:                 }
 728:                 continue;
 729: # endif
 730: 
 731:               case 'k': /* kill character */
 732:                 if (*p == NULL)
 733:                     Kill_char = CNTL('X');
 734:                 else
 735:                 {
 736:                     if (*p == '^' && p[1] != NULL)
 737:                         if (*++p == '?')
 738:                             Kill_char = '\177';
 739:                         else
 740:                             Kill_char = CNTL(*p);
 741:                     else
 742:                         Kill_char = *p;
 743:                     p++;
 744:                 }
 745:                 continue;
 746: 
 747: # ifdef OLDFLAGS
 748: # ifdef OLDDIALUP
 749:               case 'd': /* dialup type */
 750:                 NewType = DIALUP;
 751:                 goto mapold;
 752: # endif
 753: 
 754: # ifdef OLDPLUGBOARD
 755:               case 'p': /* plugboard type */
 756:                 NewType = PLUGBOARD;
 757:                 goto mapold;
 758: # endif
 759: 
 760: # ifdef OLDARPANET
 761:               case 'a': /* arpanet type */
 762:                 Newtype = ARPANET;
 763:                 goto mapold;
 764: # endif
 765: 
 766: mapold:             Map->Ident = NewType;
 767:                 Map->Test = ALL;
 768:                 if (*p == NULL)
 769:                 {
 770:                     p = nextarg(argc--, argv++);
 771:                 }
 772:                 Map->Type = p;
 773:                 Map++;
 774:                 Mapped = YES;
 775:                 p = "";
 776:                 continue;
 777: # endif
 778: 
 779:               case 'm': /* map identifier to type */
 780:                 /* This code is very loose. Almost no
 781: 				** syntax checking is done!! However,
 782: 				** illegal syntax will only produce
 783: 				** weird results.
 784: 				*/
 785:                 if (*p == NULL)
 786:                 {
 787:                     p = nextarg(argc--, argv++);
 788:                 }
 789:                 if (isalnum(*p))
 790:                 {
 791:                     Map->Ident = p; /* identifier */
 792:                     while (isalnum(*p)) p++;
 793:                 }
 794:                 else
 795:                     Map->Ident = "";
 796:                 Break = NO;
 797:                 Not = NO;
 798:                 while (!Break) switch (*p)
 799:                 {
 800:                     case NULL:
 801:                         p = nextarg(argc--, argv++);
 802:                         continue;
 803: 
 804:                     case ':':   /* mapped type */
 805:                         *p++ = NULL;
 806:                         Break = YES;
 807:                         continue;
 808: 
 809:                     case '>':   /* conditional */
 810:                         Map->Test |= GT;
 811:                         *p++ = NULL;
 812:                         continue;
 813: 
 814:                     case '<':   /* conditional */
 815:                         Map->Test |= LT;
 816:                         *p++ = NULL;
 817:                         continue;
 818: 
 819:                     case '=':   /* conditional */
 820:                     case '@':
 821:                         Map->Test |= EQ;
 822:                         *p++ = NULL;
 823:                         continue;
 824: 
 825:                     case '!':   /* invert conditions */
 826:                         Not = ~Not;
 827:                         *p++ = NULL;
 828:                         continue;
 829: 
 830:                     case 'B':   /* Baud rate */
 831:                         p++;
 832:                         /* intentional fallthru */
 833:                     default:
 834:                         if (isdigit(*p) || *p == 'e')
 835:                         {
 836:                             Map->Speed = baudrate(p);
 837:                             while (isalnum(*p) || *p == '.')
 838:                                 p++;
 839:                         }
 840:                         else
 841:                             Break = YES;
 842:                         continue;
 843:                 }
 844:                 if (Not)    /* invert sense of test */
 845:                 {
 846:                     Map->Test = (~(Map->Test))&ALL;
 847:                 }
 848:                 if (*p == NULL)
 849:                 {
 850:                     p = nextarg(argc--, argv++);
 851:                 }
 852:                 Map->Type = p;
 853:                 p = "";
 854:                 Map++;
 855:                 Mapped = YES;
 856:                 continue;
 857: 
 858:               case 'h': /* don't get type from htmp or env */
 859:                 Dash_h = YES;
 860:                 continue;
 861: 
 862:               case 'u': /* don't update htmp */
 863:                 Dash_u = YES;
 864:                 continue;
 865: 
 866:               case 's': /* output setenv commands */
 867:                 DoSetenv = YES;
 868:                 CmndLine = YES;
 869:                 continue;
 870: 
 871:               case 'S': /* output setenv strings */
 872:                 DoSetenv = YES;
 873:                 CmndLine = NO;
 874:                 continue;
 875: 
 876:               case 'Q': /* be quiet */
 877:                 BeQuiet = YES;
 878:                 continue;
 879: 
 880:               case 'I': /* no initialization */
 881:                 NoInit = YES;
 882:                 continue;
 883: 
 884:               case 'A': /* Ask user */
 885:                 Ask = YES;
 886:                 continue;
 887: 
 888:               case 'v': /* no virtual terminal */
 889:                 DoVirtTerm = NO;
 890:                 continue;
 891: 
 892:               default:
 893:                 *p-- = NULL;
 894:                 fatal("Bad flag -", p);
 895:             }
 896:         }
 897:         else
 898:         {
 899:             /* terminal type */
 900:             DefType = p;
 901:         }
 902:     }
 903: 
 904:     if (DefType)
 905:     {
 906:         if (Mapped)
 907:         {
 908:             Map->Ident = "";    /* means "map any type" */
 909:             Map->Test = ALL;    /* at all baud rates */
 910:             Map->Type = DefType;    /* to the default type */
 911:         }
 912:         else
 913:             TtyType = DefType;
 914:     }
 915: 
 916: # ifndef V6
 917:     /*
 918: 	 * Get rid of $TERMCAP, if it's there, so we get a real
 919: 	 * entry from /etc/termcap.  This prevents us from being
 920: 	 * fooled by out of date stuff in the environment, and
 921: 	 * makes tabs work right on CB/Unix.
 922: 	 */
 923:     bufp = getenv("TERMCAP");
 924:     if (bufp && *bufp != '/')
 925:         (void) strcpy(bufp-8, "NOTHING"); /* overwrite only "TERMCAP" */
 926:     /* get current idea of terminal type from environment */
 927:     if (!Dash_h && TtyType == 0)
 928:         TtyType = getenv("TERM");
 929: # endif
 930: 
 931:     /* determine terminal id if needed */
 932: # ifdef V6
 933:     if (Ttyid == NOTTY && (TtyType == 0 || !Dash_h || !Dash_u))
 934:         Ttyid = ttyn(FILEDES);
 935: # else
 936:     if (!RepOnly && Ttyid == NOTTY && (TtyType == 0 || !Dash_h))
 937:         Ttyid = ttyname(FILEDES);
 938: # endif
 939: 
 940: # ifdef V6
 941:     /* get htmp if ever used */
 942:     if (!Dash_u || (TtyType == 0 && !Dash_h))
 943:     {
 944:         /* get htmp entry -- if error or wrong user use ttytype */
 945:         if (Ttyid == NOTTY || hget(Ttyid) < 0 ||
 946:             hgettype() == 0 || hgetuid() != (getuid() & UIDMASK))
 947:             Dash_h++;
 948:     }
 949: 
 950:     /* find terminal type (if not already known) */
 951:     if (TtyType == 0 && !Dash_h)
 952:     {
 953:         /* get type from /etc/htmp */
 954:         TtyType = hsgettype();
 955:     }
 956: # endif
 957: 
 958: # ifdef GTTYN
 959:     /* If still undefined, look at /etc/ttytype */
 960:     if (TtyType == 0)
 961:     {
 962:         TtyType = stypeof(Ttyid);
 963:     }
 964: # endif
 965: 
 966:     /* If still undefined, use DEFTYPE */
 967:     if (TtyType == 0)
 968:     {
 969:         TtyType = DEFTYPE;
 970:     }
 971: 
 972:     /* check for dialup or other mapping */
 973:     if (Mapped)
 974:     {
 975:         if (!(Alias[0] && isalias(TtyType)))
 976:             if (tgetent(Capbuf, TtyType) > 0)
 977:                 makealias(Capbuf);
 978:         TtyType = mapped(TtyType);
 979:     }
 980: 
 981:     /* TtyType now contains a pointer to the type of the terminal */
 982:     /* If the first character is '?', ask the user */
 983:     if (TtyType[0] == '?')
 984:     {
 985:         Ask = YES;
 986:         TtyType++;
 987:         if (TtyType[0] == '\0')
 988:             TtyType = DEFTYPE;
 989:     }
 990:     if (Ask)
 991:     {
 992: ask:
 993:         prs("TERM = (");
 994:         prs(TtyType);
 995:         prs(") ");
 996:         flush();
 997: 
 998:         /* read the terminal.  If not empty, set type */
 999:         i = read(2, termbuf, sizeof termbuf - 1);
1000:         if (i > 0)
1001:         {
1002:             if (termbuf[i - 1] == '\n')
1003:                 i--;
1004:             termbuf[i] = '\0';
1005:             if (termbuf[0] != '\0')
1006:                 TtyType = termbuf;
1007:         }
1008:     }
1009: 
1010:     /* get terminal capabilities */
1011:     if (!(Alias[0] && isalias(TtyType))) {
1012:         switch (tgetent(Capbuf, TtyType))
1013:         {
1014:           case -1:
1015:             prs("Cannot find termcap\n");
1016:             flush();
1017:             exit(-1);
1018: 
1019:           case 0:
1020:             prs("Type ");
1021:             prs(TtyType);
1022:             prs(" unknown\n");
1023:             flush();
1024:             if (DoSetenv)
1025:             {
1026:                 TtyType = DEFTYPE;
1027:                 Alias[0] = '\0';
1028:                 goto ask;
1029:             }
1030:             else
1031:                 exit(1);
1032:         }
1033:     }
1034:     Ttycap = Capbuf;
1035: 
1036:     if (!RepOnly)
1037:     {
1038:         /* determine erase and kill characters */
1039:         if (Specialerase && !tgetflag("bs"))
1040:             Erase_char = 0;
1041:         bufp = buf;
1042:         p = tgetstr("kb", &bufp);
1043:         if (p == NULL || p[1] != '\0')
1044:             p = tgetstr("bc", &bufp);
1045:         if (p != NULL && p[1] == '\0')
1046:             bs_char = p[0];
1047:         else if (tgetflag("bs"))
1048:             bs_char = BACKSPACE;
1049:         else
1050:             bs_char = 0;
1051:         if (Erase_char == 0 && !tgetflag("os") && curerase == OLDERASE)
1052:         {
1053:             if (tgetflag("bs") || bs_char != 0)
1054:                 Erase_char = -1;
1055:         }
1056:         if (Erase_char < 0)
1057:             Erase_char = (bs_char != 0) ? bs_char : BACKSPACE;
1058: 
1059:         if (curerase == 0)
1060:             curerase = CERASE;
1061:         if (Erase_char != 0)
1062:             curerase = Erase_char;
1063: 
1064:         if (curintr == 0)
1065:             curintr = CINTR;
1066:         if (Intr_char != 0)
1067:             curintr = Intr_char;
1068: 
1069:         if (curkill == 0)
1070:             curkill = CKILL;
1071:         if (Kill_char != 0)
1072:             curkill = Kill_char;
1073: 
1074:         /* set modes */
1075:         PadBaud = tgetnum("pb");    /* OK if fails */
1076:         for (i=0; speeds[i].string; i++)
1077:             if (speeds[i].baudrate == PadBaud) {
1078:                 PadBaud = speeds[i].speed;
1079:                 break;
1080:             }
1081: # ifndef USG
1082:         setdelay("dC", CRdelay, CRbits, &mode.sg_flags);
1083:         setdelay("dN", NLdelay, NLbits, &mode.sg_flags);
1084:         setdelay("dB", BSdelay, BSbits, &mode.sg_flags);
1085:         setdelay("dF", FFdelay, FFbits, &mode.sg_flags);
1086:         setdelay("dT", TBdelay, TBbits, &mode.sg_flags);
1087:         if (tgetflag("UC") || (command[0] & 0140) == 0100)
1088:             mode.sg_flags |= LCASE;
1089:         else if (tgetflag("LC"))
1090:             mode.sg_flags &= ~LCASE;
1091:         mode.sg_flags &= ~(EVENP | ODDP | RAW);
1092: # ifdef CBREAK
1093:         mode.sg_flags &= ~CBREAK;
1094: # endif
1095:         if (tgetflag("EP"))
1096:             mode.sg_flags |= EVENP;
1097:         if (tgetflag("OP"))
1098:             mode.sg_flags |= ODDP;
1099:         if ((mode.sg_flags & (EVENP | ODDP)) == 0)
1100:             mode.sg_flags |= EVENP | ODDP;
1101:         mode.sg_flags |= CRMOD | ECHO | XTABS;
1102:         if (tgetflag("NL")) /* new line, not line feed */
1103:             mode.sg_flags &= ~CRMOD;
1104:         if (tgetflag("HD")) /* half duplex */
1105:             mode.sg_flags &= ~ECHO;
1106:         if (tgetflag("pt")) /* print tabs */
1107:             mode.sg_flags &= ~XTABS;
1108: # else
1109:         setdelay("dC", CRdelay, CRbits, &mode.c_oflag);
1110:         setdelay("dN", NLdelay, NLbits, &mode.c_oflag);
1111:         setdelay("dB", BSdelay, BSbits, &mode.c_oflag);
1112:         setdelay("dF", FFdelay, FFbits, &mode.c_oflag);
1113:         setdelay("dT", TBdelay, TBbits, &mode.c_oflag);
1114:         setdelay("dV", VTdelay, VTbits, &mode.c_oflag);
1115: 
1116:         if (tgetflag("UC") || (command[0] & 0140) == 0100) {
1117:             mode.c_iflag |= IUCLC;
1118:             mode.c_oflag |= OLCUC;
1119:         }
1120:         else if (tgetflag("LC")) {
1121:             mode.c_iflag &= ~IUCLC;
1122:             mode.c_oflag &= ~OLCUC;
1123:         }
1124:         mode.c_iflag &= ~(PARMRK|INPCK);
1125:         mode.c_lflag |= ICANON;
1126:         if (tgetflag("EP")) {
1127:             mode.c_cflag |= PARENB;
1128:             mode.c_cflag &= ~PARODD;
1129:         }
1130:         if (tgetflag("OP")) {
1131:             mode.c_cflag |= PARENB;
1132:             mode.c_cflag |= PARODD;
1133:         }
1134: 
1135:         mode.c_oflag |= ONLCR;
1136:         mode.c_iflag |= ICRNL;
1137:         mode.c_lflag |= ECHO;
1138:         mode.c_oflag |= TAB3;
1139:         if (tgetflag("NL")) {   /* new line, not line feed */
1140:             mode.c_oflag &= ~ONLCR;
1141:             mode.c_iflag &= ~ICRNL;
1142:         }
1143:         if (tgetflag("HD")) /* half duplex */
1144:             mode.c_lflag &= ~ECHO;
1145:         if (tgetflag("pt")) /* print tabs */
1146:             mode.c_oflag &= ~TAB3;
1147: 
1148:         mode.c_lflag |= (ECHOE|ECHOK);
1149: # endif
1150: # ifdef CBVIRTTERM
1151:         HasAM = tgetflag("am");
1152: # endif CBVIRTTERM
1153: # ifdef UCB_NTTY
1154:         if (ldisc == NTTYDISC)
1155:         {
1156:             lmode |= LCTLECH;   /* display ctrl chars */
1157:             if (tgetflag("hc"))
1158:             {   /** set printer modes **/
1159:                 lmode &= ~(LCRTBS|LCRTERA|LCRTKIL);
1160:                 lmode |= LPRTERA;
1161:             }
1162:             else
1163:             {   /** set crt modes **/
1164:                 if (!tgetflag("os"))
1165:                 {
1166:                     lmode &= ~LPRTERA;
1167:                     lmode |= LCRTBS;
1168:                     if (mode.sg_ospeed >= B1200)
1169:                         lmode |= LCRTERA|LCRTKIL;
1170:                 }
1171:             }
1172:         }
1173:         if (IsReset)
1174:             lmode &= ~(LMDMBUF|LLITOUT|LPASS8);
1175:         (void) ioctl(FILEDES, TIOCLSET, (char *)&lmode);
1176: # endif
1177: 
1178:         /* get pad character */
1179:         bufp = buf;
1180:         if (tgetstr("pc", &bufp) != 0)
1181:             PC = buf[0];
1182: 
1183:         columns = tgetnum("co");
1184:         lines = tgetnum("li");
1185: 
1186:         /* Set window size */
1187:         (void) ioctl(FILEDES, TIOCGWINSZ, (char *)&win);
1188:         if (win.ws_row == 0 && win.ws_col == 0 &&
1189:             lines > 0 && columns > 0) {
1190:             win.ws_row = lines;
1191:             win.ws_col = columns;
1192:             (void) ioctl(FILEDES, TIOCSWINSZ, (char *)&win);
1193:         }
1194:         /* output startup string */
1195:         if (!NoInit)
1196:         {
1197: # ifndef USG
1198:             if (oldmode.sg_flags&(XTABS|CRMOD))
1199:             {
1200:                 oldmode.sg_flags &= ~(XTABS|CRMOD);
1201:                 setmode(-1);
1202:             }
1203: # else
1204:             if (oldmode.c_oflag&(TAB3|ONLCR|OCRNL|ONLRET))
1205:             {
1206:                 oldmode.c_oflag &= (TAB3|ONLCR|OCRNL|ONLRET);
1207:                 setmode(-1);
1208:             }
1209: # endif
1210: # ifdef CBVIRTTERM
1211:             block.st_termt = 0;
1212:             (void) ioctl(FILEDES, LDSETT, (char *)&block);
1213: # endif CBVIRTTERM
1214:             if (settabs()) {
1215:                 settle = YES;
1216:                 flush();
1217:             }
1218:             bufp = buf;
1219:             if (IsReset && tgetstr("rs", &bufp) != 0 ||
1220:                 tgetstr("is", &bufp) != 0)
1221:             {
1222:                 tputs(buf, 0, prc);
1223:                 settle = YES;
1224:                 flush();
1225:             }
1226:             bufp = buf;
1227:             if (IsReset && tgetstr("rf", &bufp) != 0 ||
1228:                 tgetstr("if", &bufp) != 0)
1229:             {
1230:                 cat(buf);
1231:                 settle = YES;
1232:             }
1233:             if (settle)
1234:             {
1235:                 prc('\r');
1236:                 flush();
1237:                 sleep(1);   /* let terminal settle down */
1238:             }
1239:         }
1240: 
1241: # ifdef CBVIRTTERM
1242:         if (DoVirtTerm) {
1243:             j = tgetnum("vt");
1244:             VirTermNo = -1;
1245:             for (i=0; vt_map[i].stdnum; i++)
1246:                 if (vt_map[i].stdnum == j)
1247:                     VirTermNo = vt_map[i].localnum;
1248:         } else
1249:             VirTermNo = -1;
1250: # endif CBVIRTTERM
1251: 
1252:         setmode(0); /* set new modes, if they've changed */
1253: 
1254:         /* set up environment for the shell we are using */
1255:         /* (this code is rather heuristic, checking for $SHELL */
1256:         /* ending in the 3 characters "csh") */
1257:         csh = NO;
1258:         if (DoSetenv)
1259:         {
1260: # ifndef V6
1261:             char *sh;
1262: 
1263:             if ((sh = getenv("SHELL")) && (i = strlen(sh)) >= 3)
1264:             {
1265:                 if ((csh = sequal(&sh[i-3], "csh")) && CmndLine)
1266:                 (void) write(STDOUT, "set noglob;\n", 12);
1267:             }
1268:             if (!csh)
1269: # endif
1270:                 /* running Bourne shell */
1271:                 (void) write(STDOUT, "export TERMCAP TERM;\n", 21);
1272:         }
1273:     }
1274: 
1275:     /* report type if appropriate */
1276:     if (DoSetenv || Report || Ureport)
1277:     {
1278:         /* if type is the short name, find first alias (if any) */
1279:         makealias(Ttycap);
1280:         if (sequal(TtyType, Alias[0]) && Alias[1]) {
1281:             TtyType = Alias[1];
1282:         }
1283: 
1284:         if (DoSetenv)
1285:         {
1286:             if (csh)
1287:             {
1288:                 if (CmndLine)
1289:                     (void) write(STDOUT, "setenv TERM ", 12);
1290:                 (void) write(STDOUT, TtyType, strlen(TtyType));
1291:                 (void) write(STDOUT, " ", 1);
1292:                 if (CmndLine)
1293:                     (void) write(STDOUT, ";\n", 2);
1294:             }
1295:             else
1296:             {
1297:                 (void) write(STDOUT, "TERM=", 5);
1298:                 (void) write(STDOUT, TtyType, strlen(TtyType));
1299:                 (void) write(STDOUT, ";\n", 2);
1300:             }
1301:         }
1302:         else if (Report)
1303:         {
1304:             (void) write(STDOUT, TtyType, strlen(TtyType));
1305:             (void) write(STDOUT, "\n", 1);
1306:         }
1307:         if (Ureport)
1308:         {
1309:             prs("Terminal type is ");
1310:             prs(TtyType);
1311:             prs("\n");
1312:             flush();
1313:         }
1314: 
1315:         if (DoSetenv)
1316:         {
1317:             if (csh)
1318:             {
1319:                 if (CmndLine)
1320:                 (void) write(STDOUT, "setenv TERMCAP '", 16);
1321:             }
1322:             else
1323:                 (void) write(STDOUT, "TERMCAP='", 9);
1324:             wrtermcap(Ttycap);
1325:             if (csh)
1326:             {
1327:                 if (CmndLine)
1328:                 {
1329:                     (void) write(STDOUT, "';\n", 3);
1330:                     (void) write(STDOUT, "unset noglob;\n", 14);
1331:                 }
1332:             }
1333:             else
1334:                 (void) write(STDOUT, "';\n", 3);
1335:         }
1336:     }
1337: 
1338:     if (RepOnly)
1339:         exit(0);
1340: 
1341:     /* tell about changing erase, kill and interrupt characters */
1342:     reportek("Erase", curerase, olderase, OLDERASE);
1343:     reportek("Kill", curkill, oldkill, OLDKILL);
1344:     reportek("Interrupt", curintr, oldintr, OLDINTR);
1345: 
1346: # ifdef V6
1347:     /* update htmp */
1348:     if (!Dash_u)
1349:     {
1350:         if (Ttyid == 0)
1351:             Ttyid = ttyn(FILEDES);
1352:         if (Ttyid == 'x')
1353:         {
1354:             prs("Cannot update htmp\n");
1355:             flush();
1356:         }
1357:         else
1358:         {
1359:             /* update htmp file only if changed */
1360:             if (!bequal(Capbuf, hsgettype(), 2))
1361:             {
1362:                 hsettype(Capbuf[0] | (Capbuf[1] << 8));
1363:                 hput(Ttyid);
1364:             }
1365:         }
1366:     }
1367: # endif
1368: 
1369:     exit(0);
1370: }
1371: 
1372: /*
1373:  * Set the hardware tabs on the terminal, using the ct (clear all tabs),
1374:  * st (set one tab) and ch (horizontal cursor addressing) capabilities.
1375:  * This is done before if and is, so they can patch in case we blow this.
1376:  */
1377: settabs()
1378: {
1379:     char caps[100];
1380:     char *capsp = caps;
1381:     char *clear_tabs, *set_tab, *set_column, *set_pos;
1382:     char *tg_out, *tgoto();
1383:     int c;
1384: 
1385:     clear_tabs = tgetstr("ct", &capsp);
1386:     set_tab = tgetstr("st", &capsp);
1387:     set_column = tgetstr("ch", &capsp);
1388:     if (set_column == 0)
1389:         set_pos = tgetstr("cm", &capsp);
1390: 
1391:     if (clear_tabs && set_tab) {
1392:         prc('\r');  /* force to be at left margin */
1393:         tputs(clear_tabs, 0, prc);
1394:     }
1395:     if (set_tab) {
1396:         for (c=8; c<columns; c += 8) {
1397:             /* get to that column. */
1398:             tg_out = "OOPS";    /* also returned by tgoto */
1399:             if (set_column)
1400:                 tg_out = tgoto(set_column, 0, c);
1401:             if (*tg_out == 'O' && set_pos)
1402:                 tg_out = tgoto(set_pos, c, lines-1);
1403:             if (*tg_out != 'O')
1404:                 tputs(tg_out, 1, prc);
1405:             else {
1406:                 prc(' '); prc(' '); prc(' '); prc(' ');
1407:                 prc(' '); prc(' '); prc(' '); prc(' ');
1408:             }
1409:             /* set the tab */
1410:             tputs(set_tab, 0, prc);
1411:         }
1412:         prc('\r');
1413:         return 1;
1414:     }
1415:     return 0;
1416: }
1417: 
1418: setmode(flag)
1419: int flag;
1420: /* flag serves several purposes:
1421:  *	if called as the result of a signal, flag will be > 0.
1422:  *	if called from terminal init, flag == -1 means reset "oldmode".
1423:  *	called with flag == 0 at end of normal mode processing.
1424:  */
1425: {
1426: # ifndef USG
1427:     struct sgttyb *ttymode;
1428: # else
1429:     struct termio *ttymode;
1430: # endif
1431: # ifdef TIOCGETC
1432:     struct tchars *ttytchars;
1433: # endif
1434: 
1435:     if (flag < 0) { /* unconditionally reset oldmode (called from init) */
1436:         ttymode = &oldmode;
1437: # ifdef TIOCGETC
1438:         ttytchars = &oldtchar;
1439: # endif
1440:     } else if (!bequal((char *)&mode, (char *)&oldmode, sizeof mode)) {
1441:         ttymode = &mode;
1442: # ifdef TIOCGETC
1443:         ttytchars = &tchar;
1444: # endif
1445:     } else  {   /* don't need it */
1446: # ifndef USG
1447:     ttymode = (struct sgttyb *)0;
1448: # else
1449:     ttymode = (struct termio *)0;
1450: # endif
1451: # ifdef TIOCGETC
1452:     ttytchars = (struct tchars *)0;
1453: # endif
1454:     }
1455: 
1456:     if (ttymode)
1457:     {
1458: # ifdef USG
1459:         (void) ioctl(FILEDES, TCSETAW, (char *)ttymode);
1460: # else
1461: #  ifndef V6
1462:         /* don't flush */
1463:         (void) ioctl(FILEDES, TIOCSETN, (char *)ttymode);
1464: #  else
1465:         stty(FILEDES, ttymode);
1466: #  endif
1467: # endif
1468:     }
1469: # ifdef TIOCGETC
1470:     if (ttytchars) {
1471:         (void) ioctl(FILEDES, TIOCSETC, (char *)ttytchars);
1472:     }
1473: # endif
1474: # ifdef CBVIRTTERM
1475:     if (VirTermNo != -2) {
1476:         int r1, r2;
1477:         extern int errno;
1478: 
1479:         r1 = ioctl(FILEDES, LDGETT, (char *)&block);
1480:         block.st_flgs |= TM_SET;
1481:         block.st_termt = VirTermNo;
1482:         if (block.st_termt < 0)
1483:             block.st_termt = 0;
1484:         if (!HasAM)
1485:             block.st_flgs |= TM_ANL;
1486:         else
1487:             block.st_flgs &= ~TM_ANL;
1488:         r2 = ioctl(FILEDES, LDSETT, (char *)&block);
1489:     }
1490: # endif
1491: 
1492:     if (flag > 0)   /* trapped signal */
1493:         exit(1);
1494: }
1495: 
1496: reportek(name, new, old, def)
1497: char    *name;
1498: char    old;
1499: char    new;
1500: char    def;
1501: {
1502:     register char   o;
1503:     register char   n;
1504:     register char   *p;
1505:     char        buf[32];
1506:     char        *bufp;
1507: 
1508:     if (BeQuiet)
1509:         return;
1510:     o = old;
1511:     n = new;
1512: 
1513:     if (o == n && n == def)
1514:         return;
1515:     prs(name);
1516:     if (o == n)
1517:         prs(" is ");
1518:     else
1519:         prs(" set to ");
1520:     bufp = buf;
1521:     if (tgetstr("kb", &bufp) > 0 && n == buf[0] && buf[1] == NULL)
1522:         prs("Backspace\n");
1523:     else if (n == 0177)
1524:         prs("Delete\n");
1525:     else
1526:     {
1527:         if (n < 040)
1528:         {
1529:             prs("Ctrl-");
1530:             n ^= 0100;
1531:         }
1532:         p = "x\n";
1533:         p[0] = n;
1534:         prs(p);
1535:     }
1536:     flush();
1537: }
1538: 
1539: 
1540: 
1541: 
1542: setdelay(cap, dtab, bits, flags)
1543: char        *cap;
1544: struct delay    dtab[];
1545: int     bits;
1546: short       *flags;
1547: {
1548:     register int    i;
1549:     register struct delay   *p;
1550: # ifdef V6
1551:     extern int  ospeed;
1552: # else
1553:     extern short    ospeed;
1554: # endif
1555: 
1556:     /* see if this capability exists at all */
1557:     i = tgetnum(cap);
1558:     if (i < 0)
1559:         i = 0;
1560:     /* No padding at speeds below PadBaud */
1561:     if (PadBaud > ospeed)
1562:         i = 0;
1563: 
1564:     /* clear out the bits, replace with new ones */
1565:     *flags &= ~bits;
1566: 
1567:     /* scan dtab for first entry with adequate delay */
1568:     for (p = dtab; p->d_delay >= 0; p++)
1569:     {
1570:         if (p->d_delay >= i)
1571:         {
1572:             p++;
1573:             break;
1574:         }
1575:     }
1576: 
1577:     /* use last entry if none will do */
1578:     *flags |= (--p)->d_bits;
1579: }
1580: 
1581: 
1582: prs(s)
1583: char    *s;
1584: {
1585:     while (*s != '\0')
1586:         prc(*s++);
1587: }
1588: 
1589: 
1590: char    OutBuf[256];
1591: int OutPtr;
1592: 
1593: prc(c)
1594: char    c;
1595: {
1596:     OutBuf[OutPtr++] = c;
1597:     if (OutPtr >= sizeof OutBuf)
1598:         flush();
1599: }
1600: 
1601: flush()
1602: {
1603:     if (OutPtr > 0)
1604:         (void) write(2, OutBuf, OutPtr);
1605:     OutPtr = 0;
1606: }
1607: 
1608: 
1609: cat(file)
1610: char    *file;
1611: {
1612:     register int    fd;
1613:     register int    i;
1614:     char        buf[BUFSIZ];
1615: 
1616:     fd = open(file, 0);
1617:     if (fd < 0)
1618:     {
1619:         prs("Cannot open ");
1620:         prs(file);
1621:         prs("\n");
1622:         flush();
1623:         return;
1624:     }
1625: 
1626:     while ((i = read(fd, buf, BUFSIZ)) > 0)
1627:         (void) write(FILEDES, buf, i);
1628: 
1629:     (void) close(fd);
1630: }
1631: 
1632: 
1633: 
1634: bmove(from, to, length)
1635: char    *from;
1636: char    *to;
1637: int length;
1638: {
1639:     register char   *p, *q;
1640:     register int    i;
1641: 
1642:     i = length;
1643:     p = from;
1644:     q = to;
1645: 
1646:     while (i-- > 0)
1647:         *q++ = *p++;
1648: }
1649: 
1650: 
1651: 
1652: bequal(a, b, len)   /* must be same thru len chars */
1653: char    *a;
1654: char    *b;
1655: int len;
1656: {
1657:     register char   *p, *q;
1658:     register int    i;
1659: 
1660:     i = len;
1661:     p = a;
1662:     q = b;
1663: 
1664:     while ((*p == *q) && --i > 0)
1665:     {
1666:         p++; q++;
1667:     }
1668:     return ((*p == *q) && i >= 0);
1669: }
1670: 
1671: sequal(a, b)    /* must be same thru NULL */
1672: char    *a;
1673: char    *b;
1674: {
1675:     register char *p = a, *q = b;
1676: 
1677:     while (*p && *q && (*p == *q))
1678:     {
1679:         p++; q++;
1680:     }
1681:     return (*p == *q);
1682: }
1683: 
1684: makealias(buf)
1685: char    *buf;
1686: {
1687:     register int i;
1688:     register char *a;
1689:     register char *b;
1690: 
1691:     Alias[0] = a = Aliasbuf;
1692:     b = buf;
1693:     i = 1;
1694:     while (*b && *b != ':') {
1695:         if (*b == '|') {
1696:             *a++ = NULL;
1697:             Alias[i++] = a;
1698:             b++;
1699:         }
1700:         else
1701:             *a++ = *b++;
1702:     }
1703:     *a = NULL;
1704:     Alias[i] = NULL;
1705: # ifdef DEB
1706:     for(i = 0; Alias[i]; printf("A:%s\n", Alias[i++]));
1707: # endif
1708: }
1709: 
1710: isalias(ident)  /* is ident same as one of the aliases? */
1711: char    *ident;
1712: {
1713:     char **a = Alias;
1714: 
1715:     if (*a)
1716:         while (*a)
1717:             if (sequal(ident, *a))
1718:                 return(YES);
1719:             else
1720:                 a++;
1721:     return(NO);
1722: }
1723: 
1724: # ifdef GTTYN
1725: char *
1726: stypeof(ttyid)
1727: char    *ttyid;
1728: {
1729:     register char   *PortType;
1730:     register char   *TtyId;
1731:     struct ttyent *t;
1732: 
1733:     if (ttyid == NOTTY)
1734:         return (DEFTYPE);
1735: 
1736:     /* split off end of name */
1737:     TtyId = ttyid;
1738:     while (*ttyid)
1739:         if (*ttyid++ == '/')
1740:             TtyId = ttyid;
1741: 
1742:     /* scan the file */
1743:     if ((t = getttynam(TtyId)) != NULL)
1744:     {
1745:         PortType = t->ty_type;
1746:         /* get aliases from termcap entry */
1747:         if (Mapped && tgetent(Capbuf, PortType) > 0) {
1748:             makealias(Capbuf);
1749:             if (sequal(Alias[0], PortType) && Alias[1])
1750:                 PortType = Alias[1];
1751:         }
1752:         return (PortType);
1753:     }
1754:     return (DEFTYPE);
1755: }
1756: # endif
1757: 
1758: /*
1759:  * routine to output the string for the environment TERMCAP variable
1760:  */
1761: #define WHITE(c)    (c == ' ' || c == '\t')
1762: char delcap[128][2];
1763: int ncap = 0;
1764: 
1765: wrtermcap(bp)
1766: char *bp;
1767: {
1768:     char buf[CAPBUFSIZ];
1769:     char *p = buf;
1770:     char *tp;
1771:     char *putbuf();
1772:     int space, empty;
1773: # ifdef CBVIRTTERM
1774:     register int i;
1775: # endif CBVIRTTERM
1776: 
1777:     /* discard names with blanks */
1778: /** May not be desireable ? **/
1779:     while (*bp && *bp != ':') {
1780:         if (*bp == '|') {
1781:             tp = bp+1;
1782:             space = NO;
1783:             while (*tp && *tp != '|' && *tp != ':') {
1784:                 space = (space || WHITE(*tp) );
1785:                 tp++;
1786:             }
1787:             if (space) {
1788:                 bp = tp;
1789:                 continue;
1790:             }
1791:         }
1792:         *p++ = *bp++;
1793:     }
1794: /**/
1795: 
1796: # ifdef CBVIRTTERM
1797:     if (VirTermNo > 0) {
1798:         p = putbuf(p, ":am");   /* All virt terms have auto margins */
1799:         cancelled("am");
1800:     }
1801: # endif
1802:     while (*bp) {
1803:         switch (*bp) {
1804:         case ':':   /* discard empty, cancelled  or dupl fields */
1805:             tp = bp+1;
1806:             empty = YES;
1807:             while (*tp && *tp != ':') {
1808:                 empty = (empty && WHITE(*tp) );
1809:                 tp++;
1810:             }
1811: # ifdef CBVIRTTERM
1812:             /*
1813: 			 * Virtual terminals use ic, not im or ei.  Turn
1814: 			 * any of them into ic - duplicates will be cancelled
1815: 			 * below.  I assume that terminals needing im+ic+ei
1816: 			 * are handled by the kernel.
1817: 			 */
1818:             if (VirTermNo > 0 && !HasAM &&
1819:                 (bp[1]=='i' && bp[2]=='m' ||
1820:                  bp[1]=='e' && bp[2]=='i')) {
1821:                 bp[1] = 'i';
1822:                 bp[2] = 'c';
1823:             }
1824:             if (VirTermNo > 0 && !HasAM &&
1825:                 (bp[1]=='c' && bp[2]=='s')) {
1826:                 bp[1] = 'd';
1827:                 bp[2] = 'l';
1828:                 /* Also need al, so kludge: */
1829:                 if (!cancelled("al"))
1830:                     p = putbuf(p, ":al=\033\120");
1831:             }
1832: # endif CBVIRTTERM
1833:             if (empty || cancelled(bp+1)) {
1834:                 bp = tp;
1835:                 continue;
1836:             }
1837: # ifdef CBVIRTTERM
1838:             if (VirTermNo > 0 && !HasAM)
1839:                 for (i = 0; vtab[i].value; i++) {
1840:                     if (vtab[i].cap[0] == bp[1] &&
1841:                         vtab[i].cap[1] == bp[2]) {
1842:                         *p++ = *bp++;   /* colon */
1843:                         *p++ = *bp++;   /* first char */
1844:                         *p++ = *bp++;   /* second "   */
1845:                         *p++ = *bp++;   /* = sign */
1846:                         p = putbuf(p, vtab[i].value);
1847:                         bp = tp;
1848:                         goto contin;
1849:                     }
1850:                 }
1851: # endif CBVIRTTERM
1852:             break;
1853: 
1854:         case ' ':   /* no spaces in output */
1855:             p = putbuf(p, "\\040");
1856:             bp++;
1857:             continue;
1858: 
1859:         case '!':   /* the shell thinks this is history */
1860:             p = putbuf(p, "\\041");
1861:             bp++;
1862:             continue;
1863: 
1864:         case ',':   /* the shell thinks this is history */
1865:             p = putbuf(p, "\\054");
1866:             bp++;
1867:             continue;
1868: 
1869:         case '"':   /* no quotes in output */
1870:             p = putbuf(p, "\\042");
1871:             bp++;
1872:             continue;
1873: 
1874:         case '\'':  /* no quotes in output */
1875:             p = putbuf(p, "\\047");
1876:             bp++;
1877:             continue;
1878: 
1879:         case '`':   /* no back quotes in output */
1880:             p = putbuf(p, "\\140");
1881:             bp++;
1882:             continue;
1883: 
1884:         case '\\':
1885:         case '^':   /* anything following is OK */
1886:             *p++ = *bp++;
1887: # ifdef CBVIRTTERM
1888:             if (*bp == 'E' && VirTermNo > 0 &&
1889:                 (bp[-3]!='\\'||bp[-2]!='E') &&
1890:                 (bp[1]!='\\'||bp[2]!='E'))
1891:                 p = putbuf(p, "E\\");
1892: # endif CBVIRTTERM
1893:         }
1894:         *p++ = *bp++;
1895: # ifdef CBVIRTTERM
1896: contin:     ;
1897: # endif CBVIRTTERM
1898:     }
1899:     *p++ = ':'; /* we skipped the last : with the : lookahead hack */
1900:     (void) write (STDOUT, buf, p-buf);
1901: }
1902: 
1903: cancelled(cap)
1904: char    *cap;
1905: {
1906:     register int i;
1907: 
1908:     for (i = 0; i < ncap; i++)
1909:     {
1910:         if (cap[0] == delcap[i][0] && cap[1] == delcap[i][1])
1911:             return (YES);
1912:     }
1913:     /* delete a second occurrance of the same capability */
1914:     delcap[ncap][0] = cap[0];
1915:     delcap[ncap][1] = cap[1];
1916:     ncap++;
1917:     return (cap[2] == '@');
1918: }
1919: 
1920: char *
1921: putbuf(ptr, str)
1922: char    *ptr;
1923: char    *str;
1924: {
1925:     char buf[20];
1926: 
1927:     while (*str) {
1928:         switch (*str) {
1929:         case '\033':
1930:             ptr = putbuf(ptr, "\\E");
1931:             str++;
1932:             break;
1933:         default:
1934:             if (*str <= ' ') {
1935:                 (void) sprintf(buf, "\\%03o", *str);
1936:                 ptr = putbuf(ptr, buf);
1937:                 str++;
1938:             } else
1939:                 *ptr++ = *str++;
1940:         }
1941:     }
1942:     return (ptr);
1943: }
1944: 
1945: 
1946: baudrate(p)
1947: char    *p;
1948: {
1949:     char buf[8];
1950:     int i = 0;
1951: 
1952:     while (i < 7 && (isalnum(*p) || *p == '.'))
1953:         buf[i++] = *p++;
1954:     buf[i] = NULL;
1955:     for (i=0; speeds[i].string; i++)
1956:         if (sequal(speeds[i].string, buf))
1957:             return (speeds[i].speed);
1958:     return (-1);
1959: }
1960: 
1961: char *
1962: mapped(type)
1963: char    *type;
1964: {
1965: # ifdef V6
1966:     extern int  ospeed;
1967: # else
1968:     extern short    ospeed;
1969: # endif
1970:     int match;
1971: 
1972: # ifdef DEB
1973:     printf ("spd:%d\n", ospeed);
1974:     prmap();
1975: # endif
1976:     Map = map;
1977:     while (Map->Ident)
1978:     {
1979:         if (*(Map->Ident) == NULL || sequal(Map->Ident, type) || isalias(Map->Ident))
1980:         {
1981:             match = NO;
1982:             switch (Map->Test)
1983:             {
1984:                 case ANY:   /* no test specified */
1985:                 case ALL:
1986:                     match = YES;
1987:                     break;
1988: 
1989:                 case GT:
1990:                     match = (ospeed > Map->Speed);
1991:                     break;
1992: 
1993:                 case GE:
1994:                     match = (ospeed >= Map->Speed);
1995:                     break;
1996: 
1997:                 case EQ:
1998:                     match = (ospeed == Map->Speed);
1999:                     break;
2000: 
2001:                 case LE:
2002:                     match = (ospeed <= Map->Speed);
2003:                     break;
2004: 
2005:                 case LT:
2006:                     match = (ospeed < Map->Speed);
2007:                     break;
2008: 
2009:                 case NE:
2010:                     match = (ospeed != Map->Speed);
2011:                     break;
2012:             }
2013:             if (match)
2014:                 return (Map->Type);
2015:         }
2016:         Map++;
2017:     }
2018:     /* no match found; return given type */
2019:     return (type);
2020: }
2021: 
2022: # ifdef DEB
2023: prmap()
2024: {
2025:     Map = map;
2026:     while (Map->Ident)
2027:     {
2028:     printf ("%s t:%d s:%d %s\n",
2029:         Map->Ident, Map->Test, Map->Speed, Map->Type);
2030:     Map++;
2031:     }
2032: }
2033: # endif
2034: 
2035: char *
2036: nextarg(argc, argv)
2037: int argc;
2038: char    *argv[];
2039: {
2040:     if (argc <= 0)
2041:         fatal ("Too few args: ", *argv);
2042:     if (*(*++argv) == '-')
2043:         fatal ("Unexpected arg: ", *argv);
2044:     return (*argv);
2045: }
2046: 
2047: fatal (mesg, obj)
2048: char    *mesg;
2049: char    *obj;
2050: {
2051:     prs (mesg);
2052:     prs (obj);
2053:     prc ('\n');
2054:     prs (USAGE);
2055:     flush();
2056:     exit(1);
2057: }

Defined functions

baudrate defined in line 1946; used 3 times
bequal defined in line 1652; used 2 times
bmove defined in line 1634; used 2 times
cancelled defined in line 1903; used 3 times
cat defined in line 1609; used 1 times
fatal defined in line 2047; used 4 times
flush defined in line 1601; used 12 times
isalias defined in line 1710; used 3 times
main defined in line 522; never used
makealias defined in line 1684; used 3 times
mapped defined in line 1961; used 2 times
nextarg defined in line 2035; used 5 times
prc defined in line 1593; used 18 times
prmap defined in line 2023; used 1 times
prs defined in line 1582; used 25 times
putbuf defined in line 1920; used 13 times
reportek defined in line 1496; used 3 times
sequal defined in line 1671; used 8 times
setdelay defined in line 1542; used 11 times
setmode defined in line 1418; used 7 times
settabs defined in line 1377; used 1 times
stypeof defined in line 1725; used 2 times
wrtermcap defined in line 1765; used 1 times

Defined variables

Alias defined in line 495; used 15 times
Aliasbuf defined in line 494; used 1 times
Ask defined in line 485; used 3 times
BeQuiet defined in line 478; used 3 times
Capbuf defined in line 491; used 9 times
CmndLine defined in line 484; used 7 times
Dash_h defined in line 476; used 7 times
Dash_u defined in line 475; used 6 times
DefType defined in line 472; used 4 times
DoSetenv defined in line 477; used 7 times
DoVirtTerm defined in line 486; used 2 times
Erase_char defined in line 461; used 11 times
HasAM defined in line 458; used 5 times
Intr_char defined in line 463; used 6 times
IsReset defined in line 480; used 4 times
Kill_char defined in line 462; used 6 times
Map defined in line 400; used 38 times
Mapped defined in line 474; used 5 times
NewType defined in line 473; used 3 times
NoInit defined in line 479; used 2 times
OutBuf defined in line 1590; used 3 times
OutPtr defined in line 1591; used 5 times
PadBaud defined in line 487; used 4 times
RepOnly defined in line 483; used 4 times
Report defined in line 481; used 3 times
Specialerase defined in line 464; used 2 times
TtyType defined in line 471; used 35 times
Ttycap defined in line 492; used 3 times
Ttyid defined in line 469; used 11 times
Ureport defined in line 482; used 3 times
VirTermNo defined in line 457; used 10 times
block defined in line 518; used 10 times
columns defined in line 488; used 4 times
copyright defined in line 8; never used
delcap defined in line 1762; used 4 times
lines defined in line 488; used 4 times
map defined in line 398; used 3 times
mode defined in line 514; used 73 times
ncap defined in line 1763; used 4 times
oldmode defined in line 515; used 12 times
oldtchar defined in line 512; used 3 times
sccsid defined in line 14; never used
tchar defined in line 511; used 16 times
vtab defined in line 434; used 4 times

Defined struct's

delay defined in line 500; used 4 times
map defined in line 393; used 2 times
  • in line 400(2)
vterm defined in line 431; never used

Defined macros

ALL defined in line 387; used 3 times
ANY defined in line 380; never used
BACKSPACE defined in line 310; used 2 times
CAPBUFSIZ defined in line 490; used 3 times
CBRK defined in line 334; never used
CDSUSP defined in line 336; used 2 times
CEOF defined in line 332; used 3 times
CEOT defined in line 333; never used
CERASE defined in line 320; used 3 times
CFLUSH defined in line 338; used 1 times
CHK defined in line 311; used 19 times
CINTR defined in line 326; used 4 times
CKILL defined in line 323; used 3 times
CLNEXT defined in line 340; used 1 times
CNTL defined in line 309; used 18 times
CQUIT defined in line 329; used 2 times
CRPRNT defined in line 337; used 1 times
CSTART defined in line 330; used 1 times
CSTOP defined in line 331; used 1 times
CSUSP defined in line 335; used 1 times
CWERASE defined in line 339; used 1 times
DEFTYPE defined in line 368; used 5 times
DIALUP defined in line 359; used 1 times
EQ defined in line 382; used 4 times
FILEDES defined in line 343; used 25 times
GE defined in line 384; never used
GT defined in line 381; used 4 times
GTTYN defined in line 290; used 5 times
LE defined in line 385; never used
LT defined in line 383; used 4 times
NE defined in line 386; never used
NMAP defined in line 391; used 1 times
NO defined in line 307; used 8 times
NOTTY defined in line 374; used 6 times
OLDDIALUP defined in line 360; used 1 times
OLDERASE defined in line 314; used 3 times
OLDFLAGS defined in line 358; used 1 times
OLDINTR defined in line 316; used 2 times
OLDKILL defined in line 315; used 2 times
OLDPLUGBOARD defined in line 362; used 1 times
PLUGBOARD defined in line 361; used 1 times
STDOUT defined in line 344; used 17 times
UCB_NTTY defined in line 269; used 5 times
UIDMASK defined in line 349; used 1 times
USAGE defined in line 355; used 1 times
WHITE defined in line 1761; used 2 times
YES defined in line 306; used 29 times
curerase defined in line 281; used 9 times
curintr defined in line 283; used 8 times
curkill defined in line 282; used 8 times
index defined in line 272; used 2 times
isalnum defined in line 313; used 4 times
isdigit defined in line 312; used 1 times
olderase defined in line 284; used 1 times
oldintr defined in line 286; used 1 times
oldkill defined in line 285; used 1 times
rindex defined in line 273; used 2 times
Last modified: 1986-04-28
Generated: 2016-12-26
Generated by src2html V0.67
page hit count: 3816
Valid CSS Valid XHTML 1.0 Strict