1cc6c529chin/*
2de81e71Tim Marsland * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
3cc6c529chin * Use is subject to license terms.
4cc6c529chin */
5cc6c529chin
67c478bdstevel@tonic-gate/*	Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T	*/
7632cbd9Toomas Soome/*	  All Rights Reserved	*/
87c478bdstevel@tonic-gate
97c478bdstevel@tonic-gate
107c478bdstevel@tonic-gate/*
117c478bdstevel@tonic-gate * Copyright (c) 1980 Regents of the University of California.
127c478bdstevel@tonic-gate * All rights reserved. The Berkeley software License Agreement
137c478bdstevel@tonic-gate * specifies the terms and conditions for redistribution.
147c478bdstevel@tonic-gate */
157c478bdstevel@tonic-gate
167c478bdstevel@tonic-gate/*
17de81e71Tim Marsland *  TSET -- set terminal modes
18de81e71Tim Marsland *
19de81e71Tim Marsland *	This program does sophisticated terminal initialization.
20de81e71Tim Marsland *	I recommend that you include it in your .profile or .login
21de81e71Tim Marsland *	file to initialize whatever terminal you are on.
22de81e71Tim Marsland *
23de81e71Tim Marsland *	There are several features:
24de81e71Tim Marsland *
25de81e71Tim Marsland *	A special file or sequence (as controlled by the termcap file)
26de81e71Tim Marsland *	is sent to the terminal.
27de81e71Tim Marsland *
28de81e71Tim Marsland *	Mode bits are set on a per-terminal_type basis (much better
29de81e71Tim Marsland *	than UNIX itself).  This allows special delays, automatic
30de81e71Tim Marsland *	tabs, etc.
31de81e71Tim Marsland *
32de81e71Tim Marsland *	Erase and Kill characters can be set to whatever you want.
33de81e71Tim Marsland *	Default is to change erase to control-H on a terminal which
34de81e71Tim Marsland *	can overstrike, and leave it alone on anything else.  Kill
35de81e71Tim Marsland *	is always left alone unless specifically requested.  These
36de81e71Tim Marsland *	characters can be represented as "^X" meaning control-X;
37de81e71Tim Marsland *	X is any character.
38de81e71Tim Marsland *
39de81e71Tim Marsland *	Terminals which are dialups or plugboard types can be aliased
40de81e71Tim Marsland *	to whatever type you may have in your home or office.  Thus,
41de81e71Tim Marsland *	if you know that when you dial up you will always be on a
42de81e71Tim Marsland *	TI 733, you can specify that fact to tset.  You can represent
43de81e71Tim Marsland *	a type as "?type".  This will ask you what type you want it
44de81e71Tim Marsland *	to be -- if you reply with just a newline, it will default
45de81e71Tim Marsland *	to the type given.
46de81e71Tim Marsland *
47de81e71Tim Marsland *	The current terminal type can be queried.
48de81e71Tim Marsland *
49de81e71Tim Marsland *	Usage:
50de81e71Tim Marsland *		tset [-] [-EC] [-eC] [-kC] [-iC] [-s] [-h] [-u] [-r]
51de81e71Tim Marsland *			[-m [ident] [test baudrate] :type]
52de81e71Tim Marsland *			[-Q] [-I] [-S] [type]
53de81e71Tim Marsland *
54de81e71Tim Marsland *		In systems with environments, use:
55de81e71Tim Marsland *			eval `tset -s ...`
56de81e71Tim Marsland *		Actually, this doesn't work in old csh's.
57de81e71Tim Marsland *		Instead, use:
58de81e71Tim Marsland *			tset -s ... > tset.tmp
59de81e71Tim Marsland *			source tset.tmp
60de81e71Tim Marsland *			rm tset.tmp
61de81e71Tim Marsland *		or:
62de81e71Tim Marsland *			set noglob
63de81e71Tim Marsland *			set term=(`tset -S ....`)
64de81e71Tim Marsland *			setenv TERM $term[1]
65de81e71Tim Marsland *			setenv TERMCAP "$term[2]"
66de81e71Tim Marsland *			unset term
67de81e71Tim Marsland *			unset noglob
68de81e71Tim Marsland *
69de81e71Tim Marsland *	Positional Parameters:
70de81e71Tim Marsland *		type -- the terminal type to force.  If this is
71de81e71Tim Marsland *			specified, initialization is for this
72de81e71Tim Marsland *			terminal type.
73de81e71Tim Marsland *
74de81e71Tim Marsland *	Flags:
75de81e71Tim Marsland *		- -- report terminal type.  Whatever type is
76de81e71Tim Marsland *			decided on is reported.  If no other flags
77de81e71Tim Marsland *			are stated, the only affect is to write
78de81e71Tim Marsland *			the terminal type on the standard output.
79de81e71Tim Marsland *		-r -- report to user in addition to other flags.
80de81e71Tim Marsland *		-EC -- set the erase character to C on all terminals
81de81e71Tim Marsland *			except those which cannot backspace (e.g.,
82de81e71Tim Marsland *			a TTY 33).  C defaults to control-H.
83de81e71Tim Marsland *		-eC -- set the erase character to C on all terminals.
84de81e71Tim Marsland *			C defaults to control-H.  If not specified,
85de81e71Tim Marsland *			the erase character is untouched; however, if
86de81e71Tim Marsland *			not specified and the erase character is NULL
87de81e71Tim Marsland *			(zero byte), the erase character is set to CERASE.
88de81e71Tim Marsland *		-kC -- set the kill character to C on all terminals.
89de81e71Tim Marsland *			Default for C is control-U.  If not specified,
90de81e71Tim Marsland *			the kill character is untouched; however, if
91de81e71Tim Marsland *			not specified and the kill character is NULL
92de81e71Tim Marsland *			(zero byte), the kill character is set to CKILL.
93de81e71Tim Marsland *		-iC -- set the interrupt character to C on all terminals.
94de81e71Tim Marsland *			Default for C is control-C.  If not specified, the
95de81e71Tim Marsland *			interrupt character is untouched; however, if
96de81e71Tim Marsland *			not specified and the interrupt character is NULL
97de81e71Tim Marsland *			(zero byte), the interrupt character is set to
98de81e71Tim Marsland *			control-C.
99de81e71Tim Marsland *		-qC -- reserved for setable quit character.
100de81e71Tim Marsland *		-m -- map the system identified type to some user
101de81e71Tim Marsland *			specified type. The mapping can be baud rate
102de81e71Tim Marsland *			dependent. This replaces the old -d, -p flags.
103de81e71Tim Marsland *			(-d type  ->  -m dialup:type)
104de81e71Tim Marsland *			(-p type  ->  -m plug:type)
105de81e71Tim Marsland *			Syntax:	-m identifier [test baudrate] :type
106de81e71Tim Marsland *			where: ``identifier'' is terminal type found in
107de81e71Tim Marsland *			/etc/ttys for this port, (abscence of an identifier
108de81e71Tim Marsland *			matches any identifier); ``test'' may be any combination
109de81e71Tim Marsland *			of  >  =  <  !  @; ``baudrate'' is as with stty(1);
110de81e71Tim Marsland *			``type'' is the actual terminal type to use if the
111de81e71Tim Marsland *			mapping condition is met. Multiple maps are scanned
112de81e71Tim Marsland *			in order and the first match prevails.
113de81e71Tim Marsland *		-n -- If the new tty driver from UCB is available, this flag
114de81e71Tim Marsland *			will activate the new options for erase and kill
115de81e71Tim Marsland *			processing. This will be different for printers
116de81e71Tim Marsland *			and crt's. For crts, if the baud rate is < 1200 then
117de81e71Tim Marsland *			erase and kill don't remove characters from the screen.
118de81e71Tim Marsland *		-h -- don't read htmp file.  Normally the terminal type
119de81e71Tim Marsland *			is determined by reading the htmp file or the
120de81e71Tim Marsland *			environment (unless some mapping is specified).
121de81e71Tim Marsland *			This forces a read of the ttytype file -- useful
122de81e71Tim Marsland *			when htmp is somehow wrong. (V6 only)
123de81e71Tim Marsland *		-u -- don't update htmp.  It seemed like this should
124de81e71Tim Marsland *			be put in.  Note that htmp is never actually
125de81e71Tim Marsland *			written if there are no changes, so don't bother
126de81e71Tim Marsland *			bother using this for efficiency reasons alone.
127de81e71Tim Marsland *		-s -- output setenv commands for TERM.  This can be
128de81e71Tim Marsland *			used with
129de81e71Tim Marsland *				`tset -s ...`
130de81e71Tim Marsland *			and is to be prefered to:
131de81e71Tim Marsland *				setenv TERM `tset - ...`
132de81e71Tim Marsland *			because -s sets the TERMCAP variable also.
133de81e71Tim Marsland *		-S -- Similar to -s but outputs 2 strings suitable for
134de81e71Tim Marsland *			use in csh .login files as follows:
135de81e71Tim Marsland *				set noglob
136de81e71Tim Marsland *				set term=(`tset -S .....`)
137de81e71Tim Marsland *				setenv TERM $term[1]
138de81e71Tim Marsland *				setenv TERMCAP "$term[2]"
139de81e71Tim Marsland *				unset term
140de81e71Tim Marsland *				unset noglob
141de81e71Tim Marsland *		-Q -- be quiet.  don't output 'Erase set to' etc.
142de81e71Tim Marsland *		-I -- don't do terminal initialization (is & if
143de81e71Tim Marsland *			strings).
144de81e71Tim Marsland *		-v -- On virtual terminal systems, don't set up a
145de81e71Tim Marsland *			virtual terminal.  Otherwise tset will tell
146de81e71Tim Marsland *			the operating system what kind of terminal you
147de81e71Tim Marsland *			are on (if it is a known terminal) and fix up
148de81e71Tim Marsland *			the output of -s to use virtual terminal sequences.
149de81e71Tim Marsland *
150de81e71Tim Marsland *	Files:
151de81e71Tim Marsland *		/etc/ttys
152de81e71Tim Marsland *			contains a terminal id -> terminal type
153de81e71Tim Marsland *			mapping; used when any user mapping is specified,
154de81e71Tim Marsland *			or the environment doesn't have TERM set.
155de81e71Tim Marsland *		/etc/termcap
156de81e71Tim Marsland *			a terminal_type -> terminal_capabilities
157de81e71Tim Marsland *			mapping.
158de81e71Tim Marsland *
159de81e71Tim Marsland *	Return Codes:
160de81e71Tim Marsland *		-1 -- couldn't open termcap.
161de81e71Tim Marsland *		1 -- bad terminal type, or standard output not tty.
162de81e71Tim Marsland *		0 -- ok.
163de81e71Tim Marsland *
164de81e71Tim Marsland *	Defined Constants:
165de81e71Tim Marsland *		DIALUP -- the type code for a dialup port.
166de81e71Tim Marsland *		PLUGBOARD -- the type code for a plugboard port.
167de81e71Tim Marsland *		ARPANET -- the type code for an arpanet port.
168de81e71Tim Marsland *		BACKSPACE -- control-H, the default for -e.
169de81e71Tim Marsland *		CNTL('U') -- control-U, the default for -k.
170de81e71Tim Marsland *		OLDERASE -- the ancient default erase character.
171de81e71Tim Marsland *		FILEDES -- the file descriptor to do the operation
172de81e71Tim Marsland *			on, nominally 1 or 2.
173de81e71Tim Marsland *		STDOUT -- the standard output file descriptor.
174de81e71Tim Marsland *		UIDMASK -- the bit pattern to mask with the getuid()
175de81e71Tim Marsland *			call to get just the user id.
176de81e71Tim Marsland *		GTTYN -- defines file containing generalized ttynames
177de81e71Tim Marsland *			and compiles code to look there.
178de81e71Tim Marsland *
179de81e71Tim Marsland *	Requires:
180de81e71Tim Marsland *		Routines to handle htmp, ttys, and termcap.
181de81e71Tim Marsland *
182de81e71Tim Marsland *	Compilation Flags:
183de81e71Tim Marsland *		OLDFLAGS -- must be defined to compile code for any of
184de81e71Tim Marsland *			the -d, -p, or -a flags.
185de81e71Tim Marsland *		OLDDIALUP -- accept the -d flag.
186de81e71Tim Marsland *		OLDPLUGBOARD -- accept the -p flag.
187de81e71Tim Marsland *		OLDARPANET -- accept the -a flag.
188de81e71Tim Marsland *		V6 -- if clear, use environments, not htmp.
189de81e71Tim Marsland *			also use TIOCSETN rather than stty to avoid flushing
190de81e71Tim Marsland *		GTTYN -- if set, compiles code to look at /etc/ttys.
191de81e71Tim Marsland *
192de81e71Tim Marsland *	Trace Flags:
193de81e71Tim Marsland *		none
194de81e71Tim Marsland *
195de81e71Tim Marsland *	Diagnostics:
196de81e71Tim Marsland *		Bad flag
197de81e71Tim Marsland *			An incorrect option was specified.
198de81e71Tim Marsland *		Too few args
199de81e71Tim Marsland *			more command line arguments are required.
200de81e71Tim Marsland *		Unexpected arg
201de81e71Tim Marsland *			wrong type of argument was encountered.
202de81e71Tim Marsland *		Cannot open ...
203de81e71Tim Marsland *			The specified file could not be openned.
204de81e71Tim Marsland *		Type ... unknown
205de81e71Tim Marsland *			An unknown terminal type was specified.
206de81e71Tim Marsland *		Cannot update htmp
207de81e71Tim Marsland *			Cannot update htmp file when the standard
208de81e71Tim Marsland *			output is not a terminal.
209de81e71Tim Marsland *		Erase set to ...
210de81e71Tim Marsland *			Telling that the erase character has been
211de81e71Tim Marsland *			set to the specified character.
212de81e71Tim Marsland *		Kill set to ...
213de81e71Tim Marsland *			Ditto for kill
214de81e71Tim Marsland *		Erase is ...    Kill is ...
215de81e71Tim Marsland *			Tells that the erase/kill characters were
216de81e71Tim Marsland *			wierd before, but they are being left as-is.
217de81e71Tim Marsland *		Not a terminal
218de81e71Tim Marsland *			Set if FILEDES is not a terminal.
219de81e71Tim Marsland *
220de81e71Tim Marsland *	Compilation Instructions:
221de81e71Tim Marsland *		cc -n -O tset.c -ltermlib
222de81e71Tim Marsland *		mv a.out tset
223de81e71Tim Marsland *		chown bin tset
224de81e71Tim Marsland *		chmod 4755 tset
225de81e71Tim Marsland *
226de81e71Tim Marsland *		where 'bin' should be whoever owns the 'htmp' file.
227de81e71Tim Marsland *		If 'htmp' is 666, then tset need not be setuid.
228de81e71Tim Marsland *
229de81e71Tim Marsland *		For version 6 the compile command should be:
230de81e71Tim Marsland *		cc -n -O -I/usr/include/retrofit tset.c -ltermlib -lretro -lS
231de81e71Tim Marsland *
232de81e71Tim Marsland *
233de81e71Tim Marsland *	History:
234de81e71Tim Marsland *		1/81 -- Added alias checking for mapping identifiers.
235de81e71Tim Marsland *		7/80 -- '-S' added. '-m' mapping added. TERMCAP string
236de81e71Tim Marsland *			cleaned up.
237de81e71Tim Marsland *		3/80 -- Changed to use tputs.  Prc & flush added.
238de81e71Tim Marsland *		10/79 -- '-s' option extended to handle TERMCAP
239de81e71Tim Marsland *			variable, set noglob, quote the entry,
240de81e71Tim Marsland *			and know about the Bourne shell.  Terminal
241de81e71Tim Marsland *			initialization moved to before any information
242de81e71Tim Marsland *			output so screen clears would not screw you.
243de81e71Tim Marsland *			'-Q' option added.
244de81e71Tim Marsland *		8/79 -- '-' option alone changed to only output
245de81e71Tim Marsland *			type.  '-s' option added.  'VERSION7'
246de81e71Tim Marsland *			changed to 'V6' for compatibility.
247de81e71Tim Marsland *		12/78 -- modified for eventual migration to VAX/UNIX,
248de81e71Tim Marsland *			so the '-' option is changed to output only
249de81e71Tim Marsland *			the terminal type to STDOUT instead of
250de81e71Tim Marsland *			FILEDES.
251de81e71Tim Marsland *		9/78 -- '-' and '-p' options added (now fully
252de81e71Tim Marsland *			compatible with ttytype!), and spaces are
253de81e71Tim Marsland *			permitted between the -d and the type.
254de81e71Tim Marsland *		8/78 -- The sense of -h and -u were reversed, and the
255de81e71Tim Marsland *			-f flag is dropped -- same effect is available
256de81e71Tim Marsland *			by just stating the terminal type.
257de81e71Tim Marsland *		10/77 -- Written.
258de81e71Tim Marsland */
259de81e71Tim Marsland
260de81e71Tim Marsland
261de81e71Tim Marsland#define	index strchr
262de81e71Tim Marsland#define	rindex strrchr
263de81e71Tim Marsland#define	curerase modes.c_cc[VERASE]
264de81e71Tim Marsland#define	curkill modes.c_cc[VKILL]
265de81e71Tim Marsland#define	curintr modes.c_cc[VINTR]
266de81e71Tim Marsland#define	olderase oldmodes.c_cc[VERASE]
267de81e71Tim Marsland#define	oldkill oldmodes.c_cc[VKILL]
268de81e71Tim Marsland#define	oldintr oldmodes.c_cc[VINTR]
2697c478bdstevel@tonic-gate
2707c478bdstevel@tonic-gate#include	<stdio.h>
271566b422Toomas Soome#include	<stdlib.h>
2727c478bdstevel@tonic-gate#include	<termio.h>
2737c478bdstevel@tonic-gate#include	<signal.h>
2747c478bdstevel@tonic-gate
2757c478bdstevel@tonic-gate
2767c478bdstevel@tonic-gate#define	YES		1
2777c478bdstevel@tonic-gate#define	NO		0
2787c478bdstevel@tonic-gate#undef CNTL
2797c478bdstevel@tonic-gate#define	CNTL(c)		((c)&037)
2807c478bdstevel@tonic-gate#define	BACKSPACE	(CNTL('H'))
2817c478bdstevel@tonic-gate#define	isdigit(c)	(c >= '0' && c <= '9')
2827c478bdstevel@tonic-gate#define	isalnum(c)	(c > ' ' && (index("<@=>!:|\177", c) == NULL))
2837c478bdstevel@tonic-gate#define	OLDERASE	'#'
2847c478bdstevel@tonic-gate
2857c478bdstevel@tonic-gate/* default special characters */
2867c478bdstevel@tonic-gate#ifndef CERASE
2877c478bdstevel@tonic-gate#define	CERASE	'\177'
2887c478bdstevel@tonic-gate#endif
2897c478bdstevel@tonic-gate#ifndef CKILL
2907c478bdstevel@tonic-gate#define	CKILL	CNTL('U')
2917c478bdstevel@tonic-gate#endif
2927c478bdstevel@tonic-gate#ifndef CINTR
2937c478bdstevel@tonic-gate#define	CINTR	CNTL('C')
2947c478bdstevel@tonic-gate#endif
2957c478bdstevel@tonic-gate#ifndef CDSUSP
2967c478bdstevel@tonic-gate#define	CQUIT	034		/* FS, ^\ */
2977c478bdstevel@tonic-gate#define	CSTART	CNTL('Q')
2987c478bdstevel@tonic-gate#define	CSTOP	CNTL('S')
2997c478bdstevel@tonic-gate#define	CEOF	CNTL('D')
3007c478bdstevel@tonic-gate#define	CEOT	CEOF
3017c478bdstevel@tonic-gate#define	CBRK	0377
3027c478bdstevel@tonic-gate#define	CSUSP	CNTL('Z')
3037c478bdstevel@tonic-gate#define	CDSUSP	CNTL('Y')
3047c478bdstevel@tonic-gate#define	CRPRNT	CNTL('R')
3057c478bdstevel@tonic-gate#define	CFLUSH	CNTL('O')
3067c478bdstevel@tonic-gate#define	CWERASE	CNTL('W')
3077c478bdstevel@tonic-gate#define	CLNEXT	CNTL('V')
3087c478bdstevel@tonic-gate#endif
3097c478bdstevel@tonic-gate
3107c478bdstevel@tonic-gate#define	FILEDES		2	/* do gtty/stty on this descriptor */
3117c478bdstevel@tonic-gate#define	STDOUT		1	/* output of -s/-S to this descriptor */
3127c478bdstevel@tonic-gate
3137c478bdstevel@tonic-gate#define	UIDMASK		-1
3147c478bdstevel@tonic-gate
315de81e71Tim Marsland#define	USAGE	"usage: tset [-] [-rsIQS] [-eC] [-kC] "	\
316de81e71Tim Marsland		"[-iC] [-m [ident][test speed]:type] [type]\n"
3177c478bdstevel@tonic-gate
3187c478bdstevel@tonic-gate#define	OLDFLAGS
3197c478bdstevel@tonic-gate#define	DIALUP		"dialup"
3207c478bdstevel@tonic-gate#define	OLDDIALUP	"sd"
3217c478bdstevel@tonic-gate#define	PLUGBOARD	"plugboard"
3227c478bdstevel@tonic-gate#define	OLDPLUGBOARD	"sp"
3237c478bdstevel@tonic-gate
3247c478bdstevel@tonic-gate#define	DEFTYPE		"unknown"
3257c478bdstevel@tonic-gate
3267c478bdstevel@tonic-gate/*
3277c478bdstevel@tonic-gate * Baud Rate Conditionals
3287c478bdstevel@tonic-gate */
3297c478bdstevel@tonic-gate#define	ANY		0
3307c478bdstevel@tonic-gate#define	GT		1
3317c478bdstevel@tonic-gate#define	EQ		2
3327c478bdstevel@tonic-gate#define	LT		4
3337c478bdstevel@tonic-gate#define	GE		(GT|EQ)
3347c478bdstevel@tonic-gate#define	LE		(LT|EQ)
3357c478bdstevel@tonic-gate#define	NE		(GT|LT)
3367c478bdstevel@tonic-gate#define	ALL		(GT|EQ|LT)
3377c478bdstevel@tonic-gate
3387c478bdstevel@tonic-gate
3397c478bdstevel@tonic-gate
3407c478bdstevel@tonic-gate#define	NMAP		10
3417c478bdstevel@tonic-gate
3427c478bdstevel@tonic-gatestruct	map {
3437c478bdstevel@tonic-gate	char *Ident;
3447c478bdstevel@tonic-gate	char Test;
3457c478bdstevel@tonic-gate	char Speed;
3467c478bdstevel@tonic-gate	char *Type;
3477c478bdstevel@tonic-gate} map[NMAP];
3487c478bdstevel@tonic-gate
3497c478bdstevel@tonic-gatestruct map *Map = map;
3507c478bdstevel@tonic-gate
3517c478bdstevel@tonic-gate/* This should be available in an include file */
3527c478bdstevel@tonic-gatestruct
3537c478bdstevel@tonic-gate{
3547c478bdstevel@tonic-gate	char	*string;
3557c478bdstevel@tonic-gate	int	speed;
3567c478bdstevel@tonic-gate	int	baudrate;
3577c478bdstevel@tonic-gate} speeds[] = {
3587c478bdstevel@tonic-gate	"0",	B0,	0,
3597c478bdstevel@tonic-gate	"50",	B50,	50,
3607c478bdstevel@tonic-gate	"75",	B75,	75,
3617c478bdstevel@tonic-gate	"110",	B110,	110,
3627c478bdstevel@tonic-gate	"134",	B134,	134,
363de81e71Tim Marsland	"134.5", B134,	134,
3647c478bdstevel@tonic-gate	"150",	B150,	150,
3657c478bdstevel@tonic-gate	"200",	B200,	200,
3667c478bdstevel@tonic-gate	"300",	B300,	300,
3677c478bdstevel@tonic-gate	"600",	B600,	600,
3687c478bdstevel@tonic-gate	"1200",	B1200,	1200,
3697c478bdstevel@tonic-gate	"1800",	B1800,	1800,
3707c478bdstevel@tonic-gate	"2400",	B2400,	2400,
3717c478bdstevel@tonic-gate	"4800",	B4800,	4800,
3727c478bdstevel@tonic-gate	"9600",	B9600,	9600,
373de81e71Tim Marsland	"19200", EXTA,	19200,
3747c478bdstevel@tonic-gate	"exta",	EXTA,	19200,
3757c478bdstevel@tonic-gate	"extb",	EXTB,	38400,
376de81e71Tim Marsland	"57600", B57600,	57600,
377de81e71Tim Marsland	"76800", B76800,	76800,
378de81e71Tim Marsland	"115200", B115200, 115200,
379de81e71Tim Marsland	"153600", B153600, 153600,
380de81e71Tim Marsland	"230400", B230400, 230400,
381de81e71Tim Marsland	"307200", B307200, 307200,
382de81e71Tim Marsland	"460800", B460800, 460800,
383de81e71Tim Marsland	"921600", B921600, 921600,
3847c478bdstevel@tonic-gate	0,
3857c478bdstevel@tonic-gate};
3867c478bdstevel@tonic-gate
3877c478bdstevel@tonic-gatesigned char Erase_char;		/* new erase character */
3887c478bdstevel@tonic-gatechar	Kill_char;		/* new kill character */
3897c478bdstevel@tonic-gatechar	Intr_char;		/* new interrupt character */
390de81e71Tim Marslandchar	Specialerase;	/* set => Erase_char only on terminals with backspace */
3917c478bdstevel@tonic-gate
3927c478bdstevel@tonic-gatechar	*TtyType;		/* type of terminal */
3937c478bdstevel@tonic-gatechar	*DefType;		/* default type if none other computed */
3947c478bdstevel@tonic-gatechar	*NewType;		/* mapping identifier based on old flags */
3957c478bdstevel@tonic-gateint	Mapped;			/* mapping has been specified */
3967c478bdstevel@tonic-gateint	Dash_u;			/* don't update htmp */
3977c478bdstevel@tonic-gateint	Dash_h;			/* don't read htmp */
3987c478bdstevel@tonic-gateint	DoSetenv;		/* output setenv commands */
3997c478bdstevel@tonic-gateint	BeQuiet;		/* be quiet */
4007c478bdstevel@tonic-gateint	NoInit;			/* don't output initialization string */
4017c478bdstevel@tonic-gateint	IsReset;		/* invoked as reset */
4027c478bdstevel@tonic-gateint	Report;			/* report current type */
4037c478bdstevel@tonic-gateint	Ureport;		/* report to user */
4047c478bdstevel@tonic-gateint	RepOnly;		/* report only */
4057c478bdstevel@tonic-gateint	CmndLine;		/* output full command lines (-s option) */
4067c478bdstevel@tonic-gateint	Ask;			/* ask user for termtype */
4077c478bdstevel@tonic-gateint	DoVirtTerm = YES;	/* Set up a virtual terminal */
4087c478bdstevel@tonic-gateint	PadBaud;		/* Min rate of padding needed */
4097c478bdstevel@tonic-gate
410de81e71Tim Marsland#define	CAPBUFSIZ	1024
4117c478bdstevel@tonic-gatechar	Capbuf[CAPBUFSIZ];	/* line from /etc/termcap for this TtyType */
4127c478bdstevel@tonic-gatechar	*Ttycap;		/* termcap line from termcap or environ */
4137c478bdstevel@tonic-gate
4147c478bdstevel@tonic-gatechar	Aliasbuf[128];
4157c478bdstevel@tonic-gatechar	*Alias[16];
4167c478bdstevel@tonic-gate
4177c478bdstevel@tonic-gateextern char *strcpy();
4187c478bdstevel@tonic-gateextern char *index();
4197c478bdstevel@tonic-gate
4207c478bdstevel@tonic-gatestruct delay
4217c478bdstevel@tonic-gate{
4227c478bdstevel@tonic-gate	int	d_delay;
4237c478bdstevel@tonic-gate	int	d_bits;
4247c478bdstevel@tonic-gate};
4257c478bdstevel@tonic-gate
4267c478bdstevel@tonic-gate#include	"tset.delays.h"
4277c478bdstevel@tonic-gate
4287c478bdstevel@tonic-gatestruct termio	mode;
4297c478bdstevel@tonic-gatestruct termio	oldmode;
4307c478bdstevel@tonic-gatestruct termios	modes;
4317c478bdstevel@tonic-gatestruct termios	oldmodes;
4327c478bdstevel@tonic-gateint		istermios;
4337c478bdstevel@tonic-gate
434cc6c529chinvoid reportek(char *, char, char, char);
435cc6c529chinvoid setdelay(char *, struct delay [], tcflag_t, tcflag_t *);
436cc6c529chinvoid prs(char *);
437cc6c529chinvoid prc(char);
438cc6c529chinvoid flush(void);
439cc6c529chinvoid cat(char *);
440cc6c529chinvoid bmove(char *, char *, int);
441cc6c529chinvoid makealias(char *);
442cc6c529chinvoid wrtermcap(char *);
443de81e71Tim Marslandvoid fatal(char *, char *);
4447c478bdstevel@tonic-gatechar reset();			/* Routine for checking&resetting chars */
4457c478bdstevel@tonic-gate
446cc6c529chinint
447cc6c529chinmain(int argc, char *argv[])
4487c478bdstevel@tonic-gate{
4497c478bdstevel@tonic-gate	char		buf[CAPBUFSIZ];
4507c478bdstevel@tonic-gate	char		termbuf[32];
4517c478bdstevel@tonic-gate	auto char	*bufp;
452cc6c529chin	char		*p;
4537c478bdstevel@tonic-gate	char		*command;
454cc6c529chin	int		i;
4557c478bdstevel@tonic-gate	int		Break;
4567c478bdstevel@tonic-gate	int		Not;
4577c478bdstevel@tonic-gate	char		*nextarg();
4587c478bdstevel@tonic-gate	char		*mapped();
4597c478bdstevel@tonic-gate	extern char	*rindex();
4607c478bdstevel@tonic-gate	struct winsize	win;
4617c478bdstevel@tonic-gate	extern char	*getenv();
4627c478bdstevel@tonic-gate	extern char	*tgetstr();
4637c478bdstevel@tonic-gate	char		bs_char;
4647c478bdstevel@tonic-gate	int		csh;
4657c478bdstevel@tonic-gate	int		settle = NO;
4667c478bdstevel@tonic-gate	void		setmode();
4677c478bdstevel@tonic-gate	extern char	PC;
4687c478bdstevel@tonic-gate	extern short	ospeed;
4697c478bdstevel@tonic-gate
4707c478bdstevel@tonic-gate	if ((istermios = ioctl(FILEDES, TCGETS, (char *)&modes)) < 0) {
471de81e71Tim Marsland		if (ioctl(FILEDES, TCGETA, (char *)&mode) < 0) {
4727c478bdstevel@tonic-gate			prs("Not a terminal\n");
4737c478bdstevel@tonic-gate			exit(1);
4747c478bdstevel@tonic-gate		}
475de81e71Tim Marsland		bmove((char *)&mode, (char *)&oldmode, sizeof (mode));
4767c478bdstevel@tonic-gate		modes.c_lflag = oldmodes.c_lflag = mode.c_lflag;
4777c478bdstevel@tonic-gate		modes.c_oflag = oldmodes.c_oflag = mode.c_oflag;
4787c478bdstevel@tonic-gate		modes.c_iflag = oldmodes.c_iflag = mode.c_iflag;
4797c478bdstevel@tonic-gate		modes.c_cflag = oldmodes.c_cflag = mode.c_cflag;
480de81e71Tim Marsland		for (i = 0; i < NCC; i++)
4817c478bdstevel@tonic-gate			modes.c_cc[i] = oldmodes.c_cc[i] = mode.c_cc[i];
4827c478bdstevel@tonic-gate	} else
483de81e71Tim Marsland		bmove((char *)&modes, (char *)&oldmodes, sizeof (modes));
4847c478bdstevel@tonic-gate	ospeed = cfgetospeed(&modes);
4857c478bdstevel@tonic-gate	(void) signal(SIGINT, setmode);
4867c478bdstevel@tonic-gate	(void) signal(SIGQUIT, setmode);
4877c478bdstevel@tonic-gate	(void) signal(SIGTERM, setmode);
4887c478bdstevel@tonic-gate
4897c478bdstevel@tonic-gate	if (command = rindex(argv[0], '/'))
4907c478bdstevel@tonic-gate		command++;
4917c478bdstevel@tonic-gate	else
4927c478bdstevel@tonic-gate		command = argv[0];
493de81e71Tim Marsland	if (sequal(command, "reset")) {
4947c478bdstevel@tonic-gate		/*
4957c478bdstevel@tonic-gate		 * Reset the teletype mode bits to a sensible state.
4967c478bdstevel@tonic-gate		 * Copied from the program by Kurt Shoens & Mark Horton.
4977c478bdstevel@tonic-gate		 * Very useful after crapping out in raw.
4987c478bdstevel@tonic-gate		 */
4997c478bdstevel@tonic-gate		if ((istermios = ioctl(FILEDES, TCGETS, (char *)&modes)) < 0) {
5007c478bdstevel@tonic-gate			(void) ioctl(FILEDES, TCGETA, (char *)&mode);
5017c478bdstevel@tonic-gate			modes.c_lflag = mode.c_lflag;
5027c478bdstevel@tonic-gate			modes.c_oflag = mode.c_oflag;
5037c478bdstevel@tonic-gate			modes.c_iflag = mode.c_iflag;
5047c478bdstevel@tonic-gate			modes.c_cflag = mode.c_cflag;
505de81e71Tim Marsland			for (i = 0; i < NCC; i++)
5067c478bdstevel@tonic-gate				modes.c_cc[i] = mode.c_cc[i];
5077c478bdstevel@tonic-gate		}
5087c478bdstevel@tonic-gate		curerase = reset(curerase, CERASE);
5097c478bdstevel@tonic-gate		curkill = reset(curkill, CKILL);
5107c478bdstevel@tonic-gate		curintr = reset(curintr, CINTR);
5117c478bdstevel@tonic-gate		modes.c_cc[VQUIT] = reset(modes.c_cc[VQUIT], CQUIT);
5127c478bdstevel@tonic-gate		modes.c_cc[VEOF] = reset(modes.c_cc[VEOF], CEOF);
5137c478bdstevel@tonic-gate
5147c478bdstevel@tonic-gate		modes.c_iflag |= (BRKINT|ISTRIP|ICRNL|IXON);
5157c478bdstevel@tonic-gate		modes.c_iflag &= ~(IGNBRK|PARMRK|INPCK|INLCR|IGNCR|IUCLC|IXOFF);
5167c478bdstevel@tonic-gate		modes.c_oflag |= (OPOST|ONLCR);
5177c478bdstevel@tonic-gate		modes.c_oflag &= ~(OLCUC|OCRNL|ONOCR|ONLRET|OFILL|OFDEL|
518de81e71Tim Marsland		    NLDLY|CRDLY|TABDLY|BSDLY|VTDLY|FFDLY);
5197c478bdstevel@tonic-gate		modes.c_cflag |= (CS7|CREAD);
5207c478bdstevel@tonic-gate		modes.c_cflag &= ~(PARODD|CLOCAL);
5217c478bdstevel@tonic-gate		modes.c_lflag |= (ISIG|ICANON|ECHO|ECHOK);
5227c478bdstevel@tonic-gate		modes.c_lflag &= ~(XCASE|ECHONL|NOFLSH);
523de81e71Tim Marsland		if (istermios < 0) {
5247c478bdstevel@tonic-gate			mode.c_lflag = modes.c_lflag;
5257c478bdstevel@tonic-gate			mode.c_oflag = modes.c_oflag;
5267c478bdstevel@tonic-gate			mode.c_iflag = modes.c_iflag;
5277c478bdstevel@tonic-gate			mode.c_cflag = modes.c_cflag;
528de81e71Tim Marsland			for (i = 0; i < NCC; i++)
5297c478bdstevel@tonic-gate				mode.c_cc[i] = modes.c_cc[i];
5307c478bdstevel@tonic-gate			(void) ioctl(FILEDES, TCSETAW, (char *)&mode);
5317c478bdstevel@tonic-gate		} else
5327c478bdstevel@tonic-gate			(void) ioctl(FILEDES, TCSETSW, (char *)&modes);
5337c478bdstevel@tonic-gate		Dash_u = YES;
5347c478bdstevel@tonic-gate		BeQuiet = YES;
5357c478bdstevel@tonic-gate		IsReset = YES;
536de81e71Tim Marsland	} else if (argc == 2 && sequal(argv[1], "-")) {
5377c478bdstevel@tonic-gate		RepOnly = YES;
5387c478bdstevel@tonic-gate		Dash_u = YES;
5397c478bdstevel@tonic-gate	}
5407c478bdstevel@tonic-gate	argc--;
5417c478bdstevel@tonic-gate
5427c478bdstevel@tonic-gate	/* scan argument list and collect flags */
543de81e71Tim Marsland	while (--argc >= 0) {
5447c478bdstevel@tonic-gate		p = *++argv;
545de81e71Tim Marsland		if (*p == '-') {
546632cbd9Toomas Soome			if (*++p == '\0')
5477c478bdstevel@tonic-gate				Report = YES; /* report current terminal type */
548de81e71Tim Marsland			else
549de81e71Tim Marsland				while (*p)
550de81e71Tim Marsland					switch (*p++) {
5517c478bdstevel@tonic-gate
552de81e71Tim Marsland			case 'r':	/* report to user */
5537c478bdstevel@tonic-gate				Ureport = YES;
5547c478bdstevel@tonic-gate				continue;
5557c478bdstevel@tonic-gate
556de81e71Tim Marsland			case 'E':
557de81e71Tim Marsland				/* special erase: operate on all but TTY33 */
5587c478bdstevel@tonic-gate				Specialerase = YES;
5597c478bdstevel@tonic-gate				/* explicit fall-through to -e case */
560566b422Toomas Soome				/* FALLTHROUGH */
5617c478bdstevel@tonic-gate
562de81e71Tim Marsland			case 'e':	/* erase character */
563632cbd9Toomas Soome				if (*p == '\0')
5647c478bdstevel@tonic-gate					Erase_char = -1;
565de81e71Tim Marsland				else {
566632cbd9Toomas Soome					if (*p == '^' && p[1] != '\0')
5677c478bdstevel@tonic-gate						if (*++p == '?')
5687c478bdstevel@tonic-gate							Erase_char = '\177';
5697c478bdstevel@tonic-gate						else
5707c478bdstevel@tonic-gate							Erase_char = CNTL(*p);
5717c478bdstevel@tonic-gate					else
5727c478bdstevel@tonic-gate						Erase_char = *p;
5737c478bdstevel@tonic-gate					p++;
5747c478bdstevel@tonic-gate				}
5757c478bdstevel@tonic-gate				continue;
5767c478bdstevel@tonic-gate
577de81e71Tim Marsland			case 'i':	/* interrupt character */
578632cbd9Toomas Soome				if (*p == '\0')
5797c478bdstevel@tonic-gate					Intr_char = CNTL('C');
580de81e71Tim Marsland				else {
581632cbd9Toomas Soome					if (*p == '^' && p[1] != '\0')
5827c478bdstevel@tonic-gate						if (*++p == '?')
5837c478bdstevel@tonic-gate							Intr_char = '\177';
5847c478bdstevel@tonic-gate						else
5857c478bdstevel@tonic-gate							Intr_char = CNTL(*p);
5867c478bdstevel@tonic-gate					else
5877c478bdstevel@tonic-gate						Intr_char = *p;
5887c478bdstevel@tonic-gate					p++;
5897c478bdstevel@tonic-gate				}
5907c478bdstevel@tonic-gate				continue;
5917c478bdstevel@tonic-gate
592de81e71Tim Marsland			case 'k':	/* kill character */
593632cbd9Toomas Soome				if (*p == '\0')
5947c478bdstevel@tonic-gate					Kill_char = CNTL('U');
595de81e71Tim Marsland				else {
596632cbd9Toomas Soome					if (*p == '^' && p[1] != '\0')
5977c478bdstevel@tonic-gate						if (*++p == '?')
5987c478bdstevel@tonic-gate							Kill_char = '\177';
5997c478bdstevel@tonic-gate						else
6007c478bdstevel@tonic-gate							Kill_char = CNTL(*p);
6017c478bdstevel@tonic-gate					else
6027c478bdstevel@tonic-gate						Kill_char = *p;
6037c478bdstevel@tonic-gate					p++;
6047c478bdstevel@tonic-gate				}
6057c478bdstevel@tonic-gate				continue;
6067c478bdstevel@tonic-gate
607de81e71Tim Marsland#ifdef OLDFLAGS
608de81e71Tim Marsland#ifdef	OLDDIALUP
609de81e71Tim Marsland			case 'd':	/* dialup type */
6107c478bdstevel@tonic-gate				NewType = DIALUP;
6117c478bdstevel@tonic-gate				goto mapold;
612de81e71Tim Marsland#endif
6137c478bdstevel@tonic-gate
614de81e71Tim Marsland#ifdef OLDPLUGBOARD
615de81e71Tim Marsland			case 'p':	/* plugboard type */
6167c478bdstevel@tonic-gate				NewType = PLUGBOARD;
6177c478bdstevel@tonic-gate				goto mapold;
618de81e71Tim Marsland#endif
6197c478bdstevel@tonic-gate
620de81e71Tim Marsland#ifdef OLDARPANET
621de81e71Tim Marsland			case 'a':	/* arpanet type */
6227c478bdstevel@tonic-gate				Newtype = ARPANET;
6237c478bdstevel@tonic-gate				goto mapold;
624de81e71Tim Marsland#endif
6257c478bdstevel@tonic-gate
6267c478bdstevel@tonic-gatemapold:				Map->Ident = NewType;
6277c478bdstevel@tonic-gate				Map->Test = ALL;
628632cbd9Toomas Soome				if (*p == '\0') {
6297c478bdstevel@tonic-gate					p = nextarg(argc--, argv++);
6307c478bdstevel@tonic-gate				}
6317c478bdstevel@tonic-gate				Map->Type = p;
6327c478bdstevel@tonic-gate				Map++;
6337c478bdstevel@tonic-gate				Mapped = YES;
6347c478bdstevel@tonic-gate				p = "";
6357c478bdstevel@tonic-gate				continue;
636de81e71Tim Marsland#endif
637de81e71Tim Marsland
638de81e71Tim Marsland			case 'm':	/* map identifier to type */
639de81e71Tim Marsland				/*
640de81e71Tim Marsland				 * This code is very loose. Almost no
641de81e71Tim Marsland				 * syntax checking is done!! However,
642de81e71Tim Marsland				 * illegal syntax will only produce
643de81e71Tim Marsland				 * weird results.
644de81e71Tim Marsland				 */
645632cbd9Toomas Soome				if (*p == '\0') {
6467c478bdstevel@tonic-gate					p = nextarg(argc--, argv++);
6477c478bdstevel@tonic-gate				}
648de81e71Tim Marsland				if (isalnum(*p)) {
6497c478bdstevel@tonic-gate					Map->Ident = p;	/* identifier */
6507c478bdstevel@tonic-gate					while (isalnum(*p)) p++;
6517c478bdstevel@tonic-gate				}
6527c478bdstevel@tonic-gate				else
6537c478bdstevel@tonic-gate					Map->Ident = "";
6547c478bdstevel@tonic-gate				Break = NO;
6557c478bdstevel@tonic-gate				Not = NO;
656de81e71Tim Marsland				while (!Break)
657de81e71Tim Marsland					switch (*p) {
658632cbd9Toomas Soome					case '\0':
6597c478bdstevel@tonic-gate						p = nextarg(argc--, argv++);
6607c478bdstevel@tonic-gate						continue;
6617c478bdstevel@tonic-gate
6627c478bdstevel@tonic-gate					case ':':	/* mapped type */
663632cbd9Toomas Soome						*p++ = '\0';
6647c478bdstevel@tonic-gate						Break = YES;
6657c478bdstevel@tonic-gate						continue;
6667c478bdstevel@tonic-gate
6677c478bdstevel@tonic-gate					case '>':	/* conditional */
6687c478bdstevel@tonic-gate						Map->Test |= GT;
669632cbd9Toomas Soome						*p++ = '\0';
6707c478bdstevel@tonic-gate						continue;
6717c478bdstevel@tonic-gate
6727c478bdstevel@tonic-gate					case '<':	/* conditional */
6737c478bdstevel@tonic-gate						Map->Test |= LT;
674632cbd9Toomas Soome						*p++ = '\0';
6757c478bdstevel@tonic-gate						continue;
6767c478bdstevel@tonic-gate
6777c478bdstevel@tonic-gate					case '=':	/* conditional */
6787c478bdstevel@tonic-gate					case '@':
6797c478bdstevel@tonic-gate						Map->Test |= EQ;
680632cbd9Toomas Soome						*p++ = '\0';
6817c478bdstevel@tonic-gate						continue;
682de81e71Tim Marsland
6837c478bdstevel@tonic-gate					case '!':	/* invert conditions */
6847c478bdstevel@tonic-gate						Not = ~Not;
685632cbd9Toomas Soome						*p++ = '\0';
6867c478bdstevel@tonic-gate						continue;
6877c478bdstevel@tonic-gate
6887c478bdstevel@tonic-gate					case 'B':	/* Baud rate */
6897c478bdstevel@tonic-gate						p++;
6907c478bdstevel@tonic-gate						/* intentional fallthru */
6917c478bdstevel@tonic-gate					default:
692de81e71Tim Marsland						if (isdigit(*p) || *p == 'e') {
693de81e71Tim Marsland							Map->Speed =
694de81e71Tim Marsland							    baudrate(p);
695de81e71Tim Marsland							while (isalnum(*p) ||
696de81e71Tim Marsland							    *p == '.')
6977c478bdstevel@tonic-gate								p++;
698de81e71Tim Marsland						} else
6997c478bdstevel@tonic-gate							Break = YES;
7007c478bdstevel@tonic-gate						continue;
7017c478bdstevel@tonic-gate				}
702de81e71Tim Marsland				if (Not) {	/* invert sense of test */
7037c478bdstevel@tonic-gate					Map->Test = (~(Map->Test))&ALL;
7047c478bdstevel@tonic-gate				}
705632cbd9Toomas Soome				if (*p == '\0') {
7067c478bdstevel@tonic-gate					p = nextarg(argc--, argv++);
7077c478bdstevel@tonic-gate				}
7087c478bdstevel@tonic-gate				Map->Type = p;
7097c478bdstevel@tonic-gate				p = "";
7107c478bdstevel@tonic-gate				Map++;
7117c478bdstevel@tonic-gate				Mapped = YES;
7127c478bdstevel@tonic-gate				continue;
7137c478bdstevel@tonic-gate
714de81e71Tim Marsland			case 'h':	/* don't get type from htmp or env */
7157c478bdstevel@tonic-gate				Dash_h = YES;
7167c478bdstevel@tonic-gate				continue;
7177c478bdstevel@tonic-gate
718de81e71Tim Marsland			case 'u':	/* don't update htmp */
7197c478bdstevel@tonic-gate				Dash_u = YES;
7207c478bdstevel@tonic-gate				continue;
7217c478bdstevel@tonic-gate
722de81e71Tim Marsland			case 's':	/* output setenv commands */
7237c478bdstevel@tonic-gate				DoSetenv = YES;
7247c478bdstevel@tonic-gate				CmndLine = YES;
7257c478bdstevel@tonic-gate				continue;
7267c478bdstevel@tonic-gate
727de81e71Tim Marsland			case 'S':	/* output setenv strings */
7287c478bdstevel@tonic-gate				DoSetenv = YES;
7297c478bdstevel@tonic-gate				CmndLine = NO;
7307c478bdstevel@tonic-gate				continue;
7317c478bdstevel@tonic-gate
732de81e71Tim Marsland			case 'Q':	/* be quiet */
7337c478bdstevel@tonic-gate				BeQuiet = YES;
7347c478bdstevel@tonic-gate				continue;
7357c478bdstevel@tonic-gate
736de81e71Tim Marsland			case 'I':	/* no initialization */
7377c478bdstevel@tonic-gate				NoInit = YES;
7387c478bdstevel@tonic-gate				continue;
7397c478bdstevel@tonic-gate
740de81e71Tim Marsland			case 'A':	/* Ask user */
7417c478bdstevel@tonic-gate				Ask = YES;
7427c478bdstevel@tonic-gate				continue;
743de81e71Tim Marsland
744de81e71Tim Marsland			case 'v':	/* no virtual terminal */
7457c478bdstevel@tonic-gate				DoVirtTerm = NO;
7467c478bdstevel@tonic-gate				continue;
7477c478bdstevel@tonic-gate
748de81e71Tim Marsland			default:
749632cbd9Toomas Soome				*p-- = '\0';
7507c478bdstevel@tonic-gate				fatal("Bad flag -", p);
7517c478bdstevel@tonic-gate			}
752de81e71Tim Marsland		} else {
7537c478bdstevel@tonic-gate			/* terminal type */
7547c478bdstevel@tonic-gate			DefType = p;
7557c478bdstevel@tonic-gate		}
7567c478bdstevel@tonic-gate	}
7577c478bdstevel@tonic-gate
758de81e71Tim Marsland	if (DefType) {
759de81e71Tim Marsland		if (Mapped) {
7607c478bdstevel@tonic-gate			Map->Ident = "";	/* means "map any type" */
7617c478bdstevel@tonic-gate			Map->Test = ALL;	/* at all baud rates */
7627c478bdstevel@tonic-gate			Map->Type = DefType;	/* to the default type */
763de81e71Tim Marsland		} else
7647c478bdstevel@tonic-gate			TtyType = DefType;
7657c478bdstevel@tonic-gate	}
7667c478bdstevel@tonic-gate
7677c478bdstevel@tonic-gate	/*
7687c478bdstevel@tonic-gate	 * Get rid of $TERMCAP, if it's there, so we get a real
7697c478bdstevel@tonic-gate	 * entry from /etc/termcap.  This prevents us from being
7707c478bdstevel@tonic-gate	 * fooled by out of date stuff in the environment, and
7717c478bdstevel@tonic-gate	 * makes tabs work right on CB/Unix.
7727c478bdstevel@tonic-gate	 */
7737c478bdstevel@tonic-gate	bufp = getenv("TERMCAP");
7747c478bdstevel@tonic-gate	if (bufp && *bufp != '/')
7757c478bdstevel@tonic-gate		(void) strcpy(bufp-8, "NOTHING"); /* overwrite only "TERMCAP" */
7767c478bdstevel@tonic-gate	/* get current idea of terminal type from environment */
777566b422Toomas Soome	if (!Dash_h && TtyType == NULL)
7787c478bdstevel@tonic-gate		TtyType = getenv("TERM");
7797c478bdstevel@tonic-gate
7807c478bdstevel@tonic-gate	/* If still undefined, use DEFTYPE */
781566b422Toomas Soome	if (TtyType == NULL) {
7827c478bdstevel@tonic-gate		TtyType = DEFTYPE;
7837c478bdstevel@tonic-gate	}
7847c478bdstevel@tonic-gate
7857c478bdstevel@tonic-gate	/* check for dialup or other mapping */
786de81e71Tim Marsland	if (Mapped) {
7877c478bdstevel@tonic-gate		if (!(Alias[0] && isalias(TtyType)))
7887c478bdstevel@tonic-gate			if (tgetent(Capbuf, TtyType) > 0)
7897c478bdstevel@tonic-gate				makealias(Capbuf);
7907c478bdstevel@tonic-gate		TtyType = mapped(TtyType);
7917c478bdstevel@tonic-gate	}
7927c478bdstevel@tonic-gate
7937c478bdstevel@tonic-gate	/* TtyType now contains a pointer to the type of the terminal */
7947c478bdstevel@tonic-gate	/* If the first character is '?', ask the user */
795de81e71Tim Marsland	if (TtyType[0] == '?') {
7967c478bdstevel@tonic-gate		Ask = YES;
7977c478bdstevel@tonic-gate		TtyType++;
7987c478bdstevel@tonic-gate		if (TtyType[0] == '\0')
7997c478bdstevel@tonic-gate			TtyType = DEFTYPE;
8007c478bdstevel@tonic-gate	}
801de81e71Tim Marsland	if (Ask) {
8027c478bdstevel@tonic-gateask:
8037c478bdstevel@tonic-gate		prs("TERM = (");
8047c478bdstevel@tonic-gate		prs(TtyType);
8057c478bdstevel@tonic-gate		prs(") ");
8067c478bdstevel@tonic-gate		flush();
8077c478bdstevel@tonic-gate
8087c478bdstevel@tonic-gate		/* read the terminal.  If not empty, set type */
809de81e71Tim Marsland		i = read(2, termbuf, sizeof (termbuf) - 1);
810de81e71Tim Marsland		if (i > 0) {
8117c478bdstevel@tonic-gate			if (termbuf[i - 1] == '\n')
8127c478bdstevel@tonic-gate				i--;
8137c478bdstevel@tonic-gate			termbuf[i] = '\0';
8147c478bdstevel@tonic-gate			if (termbuf[0] != '\0')
8157c478bdstevel@tonic-gate				TtyType = termbuf;
8167c478bdstevel@tonic-gate		}
8177c478bdstevel@tonic-gate	}
8187c478bdstevel@tonic-gate
8197c478bdstevel@tonic-gate	/* get terminal capabilities */
8207c478bdstevel@tonic-gate	if (!(Alias[0] && isalias(TtyType))) {
821de81e71Tim Marsland		switch (tgetent(Capbuf, TtyType)) {
822de81e71Tim Marsland		case -1:
8237c478bdstevel@tonic-gate			prs("Cannot find termcap\n");
8247c478bdstevel@tonic-gate			flush();
8257c478bdstevel@tonic-gate			exit(-1);
8267c478bdstevel@tonic-gate
827de81e71Tim Marsland		case 0:
8287c478bdstevel@tonic-gate			prs("Type ");
8297c478bdstevel@tonic-gate			prs(TtyType);
8307c478bdstevel@tonic-gate			prs(" unknown\n");
8317c478bdstevel@tonic-gate			flush();
832de81e71Tim Marsland			if (DoSetenv) {
8337c478bdstevel@tonic-gate				TtyType = DEFTYPE;
8347c478bdstevel@tonic-gate				Alias[0] = '\0';
8357c478bdstevel@tonic-gate				goto ask;
836de81e71Tim Marsland			} else
8377c478bdstevel@tonic-gate				exit(1);
8387c478bdstevel@tonic-gate		}
8397c478bdstevel@tonic-gate	}
8407c478bdstevel@tonic-gate	Ttycap = Capbuf;
8417c478bdstevel@tonic-gate
842de81e71Tim Marsland	if (!RepOnly) {
8437c478bdstevel@tonic-gate		/* determine erase and kill characters */
8447c478bdstevel@tonic-gate		if (Specialerase && !tgetflag("bs"))
8457c478bdstevel@tonic-gate			Erase_char = 0;
8467c478bdstevel@tonic-gate		bufp = buf;
8477c478bdstevel@tonic-gate		p = tgetstr("kb", &bufp);
8487c478bdstevel@tonic-gate		if (p == NULL || p[1] != '\0')
8497c478bdstevel@tonic-gate			p = tgetstr("bc", &bufp);
8507c478bdstevel@tonic-gate		if (p != NULL && p[1] == '\0')
8517c478bdstevel@tonic-gate			bs_char = p[0];
8527c478bdstevel@tonic-gate		else if (tgetflag("bs"))
8537c478bdstevel@tonic-gate			bs_char = BACKSPACE;
8547c478bdstevel@tonic-gate		else
8557c478bdstevel@tonic-gate			bs_char = 0;
8567c478bdstevel@tonic-gate		/*
8577c478bdstevel@tonic-gate		 * The next statement can't be fixed, because now users
8587c478bdstevel@tonic-gate		 * depend on keeping their erase character as DEL if the
8597c478bdstevel@tonic-gate		 * system set it there.  People who want backspace have
8607c478bdstevel@tonic-gate		 * to say tset -e.
8617c478bdstevel@tonic-gate		 */
862de81e71Tim Marsland		if (Erase_char == 0 && !tgetflag("os") &&
863de81e71Tim Marsland		    curerase == OLDERASE) {
8647c478bdstevel@tonic-gate			if (tgetflag("bs") || bs_char != 0)
8657c478bdstevel@tonic-gate				Erase_char = -1;
8667c478bdstevel@tonic-gate		}
8677c478bdstevel@tonic-gate		if (Erase_char < 0)
8687c478bdstevel@tonic-gate			Erase_char = (bs_char != 0) ? bs_char : BACKSPACE;
8697c478bdstevel@tonic-gate
8707c478bdstevel@tonic-gate		if (curerase == 0)
8717c478bdstevel@tonic-gate			curerase = CERASE;
8727c478bdstevel@tonic-gate		if (Erase_char != 0)
8737c478bdstevel@tonic-gate			curerase = Erase_char;
8747c478bdstevel@tonic-gate
8757c478bdstevel@tonic-gate		if (curintr == 0)
8767c478bdstevel@tonic-gate			curintr = CINTR;
8777c478bdstevel@tonic-gate		if (Intr_char != 0)
8787c478bdstevel@tonic-gate			curintr = Intr_char;
8797c478bdstevel@tonic-gate
8807c478bdstevel@tonic-gate		if (curkill == 0)
8817c478bdstevel@tonic-gate			curkill = CKILL;
8827c478bdstevel@tonic-gate		if (Kill_char != 0)
8837c478bdstevel@tonic-gate			curkill = Kill_char;
8847c478bdstevel@tonic-gate
8857c478bdstevel@tonic-gate		/* set modes */
8867c478bdstevel@tonic-gate		PadBaud = tgetnum("pb");	/* OK if fails */
887de81e71Tim Marsland		for (i = 0; speeds[i].string; i++)
8887c478bdstevel@tonic-gate			if (speeds[i].baudrate == PadBaud) {
8897c478bdstevel@tonic-gate				PadBaud = speeds[i].speed;
8907c478bdstevel@tonic-gate				break;
8917c478bdstevel@tonic-gate			}
8927c478bdstevel@tonic-gate		setdelay("dC", CRdelay, CRbits, &modes.c_oflag);
8937c478bdstevel@tonic-gate		setdelay("dN", NLdelay, NLbits, &modes.c_oflag);
8947c478bdstevel@tonic-gate		setdelay("dB", BSdelay, BSbits, &modes.c_oflag);
8957c478bdstevel@tonic-gate		setdelay("dF", FFdelay, FFbits, &modes.c_oflag);
8967c478bdstevel@tonic-gate		setdelay("dT", TBdelay, TBbits, &modes.c_oflag);
8977c478bdstevel@tonic-gate		setdelay("dV", VTdelay, VTbits, &modes.c_oflag);
8987c478bdstevel@tonic-gate
8997c478bdstevel@tonic-gate		if (tgetflag("UC") || (command[0] & 0140) == 0100) {
9007c478bdstevel@tonic-gate			modes.c_iflag |= IUCLC;
9017c478bdstevel@tonic-gate			modes.c_oflag |= OLCUC;
9027c478bdstevel@tonic-gate			modes.c_cflag |= XCASE;
903de81e71Tim Marsland		} else if (tgetflag("LC")) {
9047c478bdstevel@tonic-gate			modes.c_iflag &= ~IUCLC;
9057c478bdstevel@tonic-gate			modes.c_oflag &= ~OLCUC;
9067c478bdstevel@tonic-gate			modes.c_cflag &= ~XCASE;
9077c478bdstevel@tonic-gate		}
9087c478bdstevel@tonic-gate		modes.c_iflag &= ~(PARMRK|INPCK);
9097c478bdstevel@tonic-gate		modes.c_lflag |= ICANON;
9107c478bdstevel@tonic-gate		if (tgetflag("EP")) {
9117c478bdstevel@tonic-gate			modes.c_iflag |= INPCK;
9127c478bdstevel@tonic-gate			modes.c_cflag |= PARENB;
9137c478bdstevel@tonic-gate			modes.c_cflag &= ~PARODD;
9147c478bdstevel@tonic-gate		}
9157c478bdstevel@tonic-gate		if (tgetflag("OP")) {
9167c478bdstevel@tonic-gate			modes.c_iflag |= INPCK;
9177c478bdstevel@tonic-gate			modes.c_cflag |= PARENB;
9187c478bdstevel@tonic-gate			modes.c_cflag |= PARODD;
9197c478bdstevel@tonic-gate		}
9207c478bdstevel@tonic-gate
9217c478bdstevel@tonic-gate		modes.c_oflag |= ONLCR;
9227c478bdstevel@tonic-gate		modes.c_iflag |= ICRNL;
9237c478bdstevel@tonic-gate		modes.c_lflag |= ECHO;
9247c478bdstevel@tonic-gate		modes.c_oflag |= TAB3;
9257c478bdstevel@tonic-gate		if (tgetflag("NL")) {	/* new line, not line feed */
9267c478bdstevel@tonic-gate			modes.c_oflag &= ~ONLCR;
9277c478bdstevel@tonic-gate			modes.c_iflag &= ~ICRNL;
9287c478bdstevel@tonic-gate		}
9297c478bdstevel@tonic-gate		if (tgetflag("HD"))	/* half duplex */
9307c478bdstevel@tonic-gate			modes.c_lflag &= ~ECHO;
9317c478bdstevel@tonic-gate		if (tgetflag("pt"))	/* print tabs */
9327c478bdstevel@tonic-gate			modes.c_oflag &= ~TAB3;
933de81e71Tim Marsland
9347c478bdstevel@tonic-gate		modes.c_lflag |= (ECHOE|ECHOK);
935de81e71Tim Marsland		if (tgetflag("hc")) {	/* set printer modes */
9367c478bdstevel@tonic-gate			modes.c_lflag &= ~ECHOE;
9377c478bdstevel@tonic-gate		}
9387c478bdstevel@tonic-gate
9397c478bdstevel@tonic-gate		/* get pad character */
9407c478bdstevel@tonic-gate		bufp = buf;
9417c478bdstevel@tonic-gate		if (tgetstr("pc", &bufp) != 0)
9427c478bdstevel@tonic-gate			PC = buf[0];
9437c478bdstevel@tonic-gate
9447c478bdstevel@tonic-gate		/* output startup string */
945de81e71Tim Marsland		if (!NoInit) {
946de81e71Tim Marsland			if (oldmodes.c_oflag&(TAB3|ONLCR|OCRNL|ONLRET)) {
9477c478bdstevel@tonic-gate				oldmodes.c_oflag &= (TAB3|ONLCR|OCRNL|ONLRET);
9487c478bdstevel@tonic-gate				setmode(-1);
9497c478bdstevel@tonic-gate			}
9507c478bdstevel@tonic-gate			if (settabs()) {
9517c478bdstevel@tonic-gate				settle = YES;
9527c478bdstevel@tonic-gate				flush();
9537c478bdstevel@tonic-gate			}
9547c478bdstevel@tonic-gate			bufp = buf;
955de81e71Tim Marsland			if (IsReset && tgetstr("rs", &bufp) != 0 ||
956de81e71Tim Marsland			    tgetstr("is", &bufp) != 0) {
9577c478bdstevel@tonic-gate				tputs(buf, 0, prc);
9587c478bdstevel@tonic-gate				settle = YES;
9597c478bdstevel@tonic-gate				flush();
9607c478bdstevel@tonic-gate			}
9617c478bdstevel@tonic-gate			bufp = buf;
9627c478bdstevel@tonic-gate			if (IsReset && tgetstr("rf", &bufp) != 0 ||
963de81e71Tim Marsland			    tgetstr("if", &bufp) != 0) {
9647c478bdstevel@tonic-gate				cat(buf);
9657c478bdstevel@tonic-gate				settle = YES;
9667c478bdstevel@tonic-gate			}
967de81e71Tim Marsland			if (settle) {
9687c478bdstevel@tonic-gate				prc('\r');
9697c478bdstevel@tonic-gate				if (IsReset)
9707c478bdstevel@tonic-gate					prc('\n');  /* newline too */
9717c478bdstevel@tonic-gate				flush();
9727c478bdstevel@tonic-gate				sleep(1);	/* let terminal settle down */
9737c478bdstevel@tonic-gate			}
9747c478bdstevel@tonic-gate		}
9757c478bdstevel@tonic-gate
9767c478bdstevel@tonic-gate		setmode(0);	/* set new modes, if they've changed */
9777c478bdstevel@tonic-gate
9787c478bdstevel@tonic-gate		/* set up environment for the shell we are using */
9797c478bdstevel@tonic-gate		/* (this code is rather heuristic, checking for $SHELL */
9807c478bdstevel@tonic-gate		/* ending in the 3 characters "csh") */
9817c478bdstevel@tonic-gate		csh = NO;
982de81e71Tim Marsland		if (DoSetenv) {
9837c478bdstevel@tonic-gate			char *sh;
9847c478bdstevel@tonic-gate
985de81e71Tim Marsland			if ((sh = getenv("SHELL")) && (i = strlen(sh)) >= 3) {
986de81e71Tim Marsland				if ((csh = sequal(&sh[i-3], "csh")) && CmndLine)
987de81e71Tim Marsland					(void) write(STDOUT,
988de81e71Tim Marsland					    "set noglob;\n", 12);
989de81e71Tim Marsland			}
990de81e71Tim Marsland			if (!csh) {	/* running Bourne shell */
991de81e71Tim Marsland				(void) write(STDOUT,
992de81e71Tim Marsland				    "export TERMCAP TERM;\n", 21);
9937c478bdstevel@tonic-gate			}
9947c478bdstevel@tonic-gate		}
9957c478bdstevel@tonic-gate	}
9967c478bdstevel@tonic-gate
9977c478bdstevel@tonic-gate	/* report type if appropriate */
998de81e71Tim Marsland	if (DoSetenv || Report || Ureport) {
9997c478bdstevel@tonic-gate		/* if type is the short name, find first alias (if any) */
10007c478bdstevel@tonic-gate		makealias(Ttycap);
10017c478bdstevel@tonic-gate		if (sequal(TtyType, Alias[0]) && Alias[1]) {
10027c478bdstevel@tonic-gate			TtyType = Alias[1];
10037c478bdstevel@tonic-gate		}
10047c478bdstevel@tonic-gate
1005de81e71Tim Marsland		if (DoSetenv) {
1006de81e71Tim Marsland			if (csh) {
10077c478bdstevel@tonic-gate				if (CmndLine)
1008de81e71Tim Marsland					(void) write(STDOUT,
1009de81e71Tim Marsland					    "setenv TERM ", 12);
10107c478bdstevel@tonic-gate				(void) write(STDOUT, TtyType, strlen(TtyType));
10117c478bdstevel@tonic-gate				(void) write(STDOUT, " ", 1);
10127c478bdstevel@tonic-gate				if (CmndLine)
1013de81e71Tim Marsland					(void) write(STDOUT, ";\n", 2);
1014de81e71Tim Marsland			} else {
10157c478bdstevel@tonic-gate				(void) write(STDOUT, "TERM=", 5);
10167c478bdstevel@tonic-gate				(void) write(STDOUT, TtyType, strlen(TtyType));
10177c478bdstevel@tonic-gate				(void) write(STDOUT, ";\n", 2);
10187c478bdstevel@tonic-gate			}
1019de81e71Tim Marsland		} else if (Report) {
10207c478bdstevel@tonic-gate			(void) write(STDOUT, TtyType, strlen(TtyType));
10217c478bdstevel@tonic-gate			(void) write(STDOUT, "\n", 1);
10227c478bdstevel@tonic-gate		}
1023de81e71Tim Marsland		if (Ureport) {
10247c478bdstevel@tonic-gate			prs("Terminal type is ");
10257c478bdstevel@tonic-gate			prs(TtyType);
10267c478bdstevel@tonic-gate			prs("\n");
10277c478bdstevel@tonic-gate			flush();
10287c478bdstevel@tonic-gate		}
10297c478bdstevel@tonic-gate
1030de81e71Tim Marsland		if (DoSetenv) {
1031de81e71Tim Marsland			if (csh) {
10327c478bdstevel@tonic-gate				if (CmndLine)
1033de81e71Tim Marsland					(void) write(STDOUT,
1034de81e71Tim Marsland					    "setenv TERMCAP '", 16);
1035de81e71Tim Marsland			} else
1036de81e71Tim Marsland				(void) write(STDOUT, "TERMCAP='", 9);
1037de81e71Tim Marsland			wrtermcap(Ttycap);
1038de81e71Tim Marsland			if (csh) {
1039de81e71Tim Marsland				if (CmndLine) {
1040de81e71Tim Marsland					(void) write(STDOUT, "';\n", 3);
1041de81e71Tim Marsland					(void) write(STDOUT,
1042de81e71Tim Marsland					    "unset noglob;\n", 14);
10437c478bdstevel@tonic-gate				}
1044de81e71Tim Marsland			} else
10457c478bdstevel@tonic-gate				(void) write(STDOUT, "';\n", 3);
10467c478bdstevel@tonic-gate		}
10477c478bdstevel@tonic-gate	}
10487c478bdstevel@tonic-gate
10497c478bdstevel@tonic-gate	if (RepOnly)
10507c478bdstevel@tonic-gate		exit(0);
10517c478bdstevel@tonic-gate
10527c478bdstevel@tonic-gate	/* tell about changing erase, kill and interrupt characters */
10537c478bdstevel@tonic-gate	reportek("Erase", curerase, olderase, CERASE);
10547c478bdstevel@tonic-gate	reportek("Kill", curkill, oldkill, CKILL);
10557c478bdstevel@tonic-gate	reportek("Interrupt", curintr, oldintr, CINTR);
10567c478bdstevel@tonic-gate
1057cc6c529chin	return (0);
10587c478bdstevel@tonic-gate}
10597c478bdstevel@tonic-gate
10607c478bdstevel@tonic-gate/*
10617c478bdstevel@tonic-gate * Set the hardware tabs on the terminal, using the ct (clear all tabs),
10627c478bdstevel@tonic-gate * st (set one tab) and ch (horizontal cursor addressing) capabilities.
10637c478bdstevel@tonic-gate * This is done before if and is, so they can patch in case we blow this.
10647c478bdstevel@tonic-gate */
1065cc6c529chinint
1066cc6c529chinsettabs(void)
10677c478bdstevel@tonic-gate{
10687c478bdstevel@tonic-gate	char caps[100];
10697c478bdstevel@tonic-gate	char *capsp = caps;
10707c478bdstevel@tonic-gate	char *clear_tabs, *set_tab, *set_column, *set_pos;
10717c478bdstevel@tonic-gate	char *tg_out, *tgoto();
10727c478bdstevel@tonic-gate	int c;
10737c478bdstevel@tonic-gate	extern char *tgetstr();
10747c478bdstevel@tonic-gate	int lines, columns;
10757c478bdstevel@tonic-gate
10767c478bdstevel@tonic-gate	clear_tabs = tgetstr("ct", &capsp);
10777c478bdstevel@tonic-gate	set_tab = tgetstr("st", &capsp);
10787c478bdstevel@tonic-gate	set_column = tgetstr("ch", &capsp);
10797c478bdstevel@tonic-gate	if (set_column == 0)
10807c478bdstevel@tonic-gate		set_pos = tgetstr("cm", &capsp);
10817c478bdstevel@tonic-gate
10827c478bdstevel@tonic-gate	if (clear_tabs && set_tab) {
10837c478bdstevel@tonic-gate		prc('\r');	/* force to be at left margin */
10847c478bdstevel@tonic-gate		tputs(clear_tabs, 0, prc);
10857c478bdstevel@tonic-gate	}
10867c478bdstevel@tonic-gate	if (set_tab) {
10877c478bdstevel@tonic-gate		columns = tgetnum("co");
10887c478bdstevel@tonic-gate		lines = tgetnum("li");
1089de81e71Tim Marsland		for (c = 0; c < columns; c += 8) {
10907c478bdstevel@tonic-gate			/* get to that column. */
10917c478bdstevel@tonic-gate			tg_out = "OOPS";	/* also returned by tgoto */
10927c478bdstevel@tonic-gate			if (set_column)
10937c478bdstevel@tonic-gate				tg_out = tgoto(set_column, 0, c);
10947c478bdstevel@tonic-gate			if (*tg_out == 'O' && set_pos)
10957c478bdstevel@tonic-gate				tg_out = tgoto(set_pos, c, lines-1);
10967c478bdstevel@tonic-gate			if (*tg_out != 'O')
10977c478bdstevel@tonic-gate				tputs(tg_out, 1, prc);
10987c478bdstevel@tonic-gate			else if (c != 0) {
10997c478bdstevel@tonic-gate				prc(' '); prc(' '); prc(' '); prc(' ');
11007c478bdstevel@tonic-gate				prc(' '); prc(' '); prc(' '); prc(' ');
11017c478bdstevel@tonic-gate			}
11027c478bdstevel@tonic-gate			/* set the tab */
11037c478bdstevel@tonic-gate			tputs(set_tab, 0, prc);
11047c478bdstevel@tonic-gate		}
11057c478bdstevel@tonic-gate		prc('\r');
1106cc6c529chin		return (1);
11077c478bdstevel@tonic-gate	}
1108cc6c529chin	return (0);
11097c478bdstevel@tonic-gate}
11107c478bdstevel@tonic-gate
1111de81e71Tim Marsland/*
1112de81e71Tim Marsland * flag serves several purposes:
11137c478bdstevel@tonic-gate *	if called as the result of a signal, flag will be > 0.
11147c478bdstevel@tonic-gate *	if called from terminal init, flag == -1 means reset "oldmode".
11157c478bdstevel@tonic-gate *	called with flag == 0 at end of normal mode processing.
11167c478bdstevel@tonic-gate */
1117de81e71Tim Marslandvoid
1118de81e71Tim Marslandsetmode(int flag)
11197c478bdstevel@tonic-gate{
11207c478bdstevel@tonic-gate	struct termio *ttymode;
11217c478bdstevel@tonic-gate	struct termios *ttymodes;
1122cc6c529chin	int i;
11237c478bdstevel@tonic-gate
11247c478bdstevel@tonic-gate	ttymode = (struct termio *)0;
11257c478bdstevel@tonic-gate	ttymodes = (struct termios *)0;
11267c478bdstevel@tonic-gate
11277c478bdstevel@tonic-gate	if (flag < 0) { /* unconditionally reset oldmode (called from init) */
11287c478bdstevel@tonic-gate		if (istermios < 0) {
1129de81e71Tim Marsland			oldmode.c_lflag = oldmodes.c_lflag;
1130de81e71Tim Marsland			oldmode.c_oflag = oldmodes.c_oflag;
1131de81e71Tim Marsland			oldmode.c_iflag = oldmodes.c_iflag;
1132de81e71Tim Marsland			oldmode.c_cflag = oldmodes.c_cflag;
1133de81e71Tim Marsland			for (i = 0; i < NCC; i++)
1134de81e71Tim Marsland				oldmode.c_cc[i] = oldmodes.c_cc[i];
1135de81e71Tim Marsland			ttymode = &oldmode;
11367c478bdstevel@tonic-gate		} else
1137de81e71Tim Marsland			ttymodes = &oldmodes;
11387c478bdstevel@tonic-gate	} else {
11397c478bdstevel@tonic-gate		if (istermios < 0) {
1140de81e71Tim Marsland			oldmode.c_lflag = oldmodes.c_lflag;
1141de81e71Tim Marsland			oldmode.c_oflag = oldmodes.c_oflag;
1142de81e71Tim Marsland			oldmode.c_iflag = oldmodes.c_iflag;
1143de81e71Tim Marsland			oldmode.c_cflag = oldmodes.c_cflag;
1144de81e71Tim Marsland			for (i = 0; i < NCC; i++)
1145de81e71Tim Marsland				oldmode.c_cc[i] = oldmodes.c_cc[i];
1146de81e71Tim Marsland			mode.c_lflag = modes.c_lflag;
1147de81e71Tim Marsland			mode.c_oflag = modes.c_oflag;
1148de81e71Tim Marsland			mode.c_iflag = modes.c_iflag;
1149de81e71Tim Marsland			mode.c_cflag = modes.c_cflag;
1150de81e71Tim Marsland			for (i = 0; i < NCC; i++)
1151de81e71Tim Marsland				mode.c_cc[i] = modes.c_cc[i];
1152de81e71Tim Marsland			if (!bequal((char *)&mode, (char *)&oldmode,
1153de81e71Tim Marsland			    sizeof (mode)))
11547c478bdstevel@tonic-gate				ttymode = &mode;
11557c478bdstevel@tonic-gate		} else if (!bequal((char *)&modes, (char *)&oldmodes,
1156de81e71Tim Marsland		    sizeof (modes)))
1157de81e71Tim Marsland			ttymodes = &modes;
11587c478bdstevel@tonic-gate	}
1159de81e71Tim Marsland
1160de81e71Tim Marsland	if (ttymode) {
11617c478bdstevel@tonic-gate		(void) ioctl(FILEDES, TCSETAW, (char *)ttymode);
11627c478bdstevel@tonic-gate	} else if (ttymodes) {
11637c478bdstevel@tonic-gate		(void) ioctl(FILEDES, TCSETSW, (char *)ttymodes);
11647c478bdstevel@tonic-gate	}
11657c478bdstevel@tonic-gate	if (flag > 0)	/* trapped signal */
11667c478bdstevel@tonic-gate		exit(1);
11677c478bdstevel@tonic-gate}
11687c478bdstevel@tonic-gate
1169cc6c529chinvoid
1170cc6c529chinreportek(char *name, char new, char old, char def)
11717c478bdstevel@tonic-gate{
1172cc6c529chin	char	o;
1173cc6c529chin	char	n;
1174cc6c529chin	char	*p;
11757c478bdstevel@tonic-gate	char		buf[32];
11767c478bdstevel@tonic-gate	char		*bufp;
11777c478bdstevel@tonic-gate	extern char *tgetstr();
11787c478bdstevel@tonic-gate
11797c478bdstevel@tonic-gate	if (BeQuiet)
11807c478bdstevel@tonic-gate		return;
11817c478bdstevel@tonic-gate	o = old;
11827c478bdstevel@tonic-gate	n = new;
11837c478bdstevel@tonic-gate
11847c478bdstevel@tonic-gate	if (o == n && n == def)
11857c478bdstevel@tonic-gate		return;
11867c478bdstevel@tonic-gate	prs(name);
11877c478bdstevel@tonic-gate	if (o == n)
11887c478bdstevel@tonic-gate		prs(" is ");
11897c478bdstevel@tonic-gate	else
11907c478bdstevel@tonic-gate		prs(" set to ");
11917c478bdstevel@tonic-gate	bufp = buf;
1192632cbd9Toomas Soome	if (tgetstr("kb", &bufp) > (char *)0 && n == buf[0] && buf[1] == '\0')
11937c478bdstevel@tonic-gate		prs("Backspace\n");
11947c478bdstevel@tonic-gate	else if (n == 0177)
11957c478bdstevel@tonic-gate		prs("Delete\n");
1196de81e71Tim Marsland	else {
1197de81e71Tim Marsland		if (n < 040) {
11987c478bdstevel@tonic-gate			prs("Ctrl-");
11997c478bdstevel@tonic-gate			n ^= 0100;
12007c478bdstevel@tonic-gate		}
12017c478bdstevel@tonic-gate		p = "x\n";
12027c478bdstevel@tonic-gate		p[0] = n;
12037c478bdstevel@tonic-gate		prs(p);
12047c478bdstevel@tonic-gate	}
12057c478bdstevel@tonic-gate	flush();
12067c478bdstevel@tonic-gate}
12077c478bdstevel@tonic-gate
12087c478bdstevel@tonic-gate
12097c478bdstevel@tonic-gate
1210cc6c529chinvoid
1211cc6c529chinsetdelay(char *cap, struct delay dtab[], tcflag_t bits, tcflag_t *flags)
12127c478bdstevel@tonic-gate{
1213cc6c529chin	int		i;
1214cc6c529chin	struct delay	*p;
12157c478bdstevel@tonic-gate	extern short	ospeed;
12167c478bdstevel@tonic-gate
12177c478bdstevel@tonic-gate	/* see if this capability exists at all */
12187c478bdstevel@tonic-gate	i = tgetnum(cap);
12197c478bdstevel@tonic-gate	if (i < 0)
12207c478bdstevel@tonic-gate		i = 0;
12217c478bdstevel@tonic-gate	/* No padding at speeds below PadBaud */
12227c478bdstevel@tonic-gate	if (PadBaud > ospeed)
12237c478bdstevel@tonic-gate		i = 0;
12247c478bdstevel@tonic-gate
12257c478bdstevel@tonic-gate	/* clear out the bits, replace with new ones */
12267c478bdstevel@tonic-gate	*flags &= ~bits;
12277c478bdstevel@tonic-gate
12287c478bdstevel@tonic-gate	/* scan dtab for first entry with adequate delay */
1229de81e71Tim Marsland	for (p = dtab; p->d_delay >= 0; p++) {
1230de81e71Tim Marsland		if (p->d_delay >= i) {
12317c478bdstevel@tonic-gate			p++;
12327c478bdstevel@tonic-gate			break;
12337c478bdstevel@tonic-gate		}
12347c478bdstevel@tonic-gate	}
12357c478bdstevel@tonic-gate
12367c478bdstevel@tonic-gate	/* use last entry if none will do */
1237cc6c529chin	*flags |= (tcflag_t)((--p)->d_bits);
12387c478bdstevel@tonic-gate}
12397c478bdstevel@tonic-gate
1240cc6c529chinvoid
1241cc6c529chinprs(char *s)
12427c478bdstevel@tonic-gate{
12437c478bdstevel@tonic-gate	while (*s != '\0')
12447c478bdstevel@tonic-gate		prc(*s++);
12457c478bdstevel@tonic-gate}
12467c478bdstevel@tonic-gate
12477c478bdstevel@tonic-gate
12487c478bdstevel@tonic-gatechar	OutBuf[256];
12497c478bdstevel@tonic-gateint	OutPtr;
12507c478bdstevel@tonic-gate
1251cc6c529chinvoid
1252cc6c529chinprc(char c)
12537c478bdstevel@tonic-gate{
12547c478bdstevel@tonic-gate	OutBuf[OutPtr++] = c;
1255de81e71Tim Marsland	if (OutPtr >= sizeof (OutBuf))
12567c478bdstevel@tonic-gate		flush();
12577c478bdstevel@tonic-gate}
12587c478bdstevel@tonic-gate
1259cc6c529chinvoid
1260cc6c529chinflush(void)
12617c478bdstevel@tonic-gate{
12627c478bdstevel@tonic-gate	if (OutPtr > 0)
12637c478bdstevel@tonic-gate		(void) write(2, OutBuf, OutPtr);
12647c478bdstevel@tonic-gate	OutPtr = 0;
12657c478bdstevel@tonic-gate}
12667c478bdstevel@tonic-gate
1267cc6c529chinvoid
1268cc6c529chincat(char *file)
12697c478bdstevel@tonic-gate{
1270cc6c529chin	int	fd;
1271cc6c529chin	int	i;
12727c478bdstevel@tonic-gate	char		buf[BUFSIZ];
12737c478bdstevel@tonic-gate
12747c478bdstevel@tonic-gate	fd = open(file, 0);
1275de81e71Tim Marsland	if (fd < 0) {
12767c478bdstevel@tonic-gate		prs("Cannot open ");
12777c478bdstevel@tonic-gate		prs(file);
12787c478bdstevel@tonic-gate		prs("\n");
12797c478bdstevel@tonic-gate		flush();
12807c478bdstevel@tonic-gate		return;
12817c478bdstevel@tonic-gate	}
12827c478bdstevel@tonic-gate
12837c478bdstevel@tonic-gate	while ((i = read(fd, buf, BUFSIZ)) > 0)
12847c478bdstevel@tonic-gate		(void) write(FILEDES, buf, i);
12857c478bdstevel@tonic-gate
12867c478bdstevel@tonic-gate	(void) close(fd);
12877c478bdstevel@tonic-gate}
12887c478bdstevel@tonic-gate
12897c478bdstevel@tonic-gate
1290cc6c529chinvoid
1291cc6c529chinbmove(char *from, char *to, int length)
12927c478bdstevel@tonic-gate{
1293cc6c529chin	char	*p, *q;
1294cc6c529chin	int	i;
12957c478bdstevel@tonic-gate
12967c478bdstevel@tonic-gate	i = length;
12977c478bdstevel@tonic-gate	p = from;
12987c478bdstevel@tonic-gate	q = to;
12997c478bdstevel@tonic-gate
13007c478bdstevel@tonic-gate	while (i-- > 0)
13017c478bdstevel@tonic-gate		*q++ = *p++;
13027c478bdstevel@tonic-gate}
13037c478bdstevel@tonic-gate
13047c478bdstevel@tonic-gate
1305cc6c529chinint
1306cc6c529chinbequal(char *a, char *b, int len)	/* must be same thru len chars */
13077c478bdstevel@tonic-gate{
1308cc6c529chin	char	*p, *q;
1309cc6c529chin	int	i;
13107c478bdstevel@tonic-gate
13117c478bdstevel@tonic-gate	i = len;
13127c478bdstevel@tonic-gate	p = a;
13137c478bdstevel@tonic-gate	q = b;
13147c478bdstevel@tonic-gate
1315de81e71Tim Marsland	while ((*p == *q) && --i > 0) {
13167c478bdstevel@tonic-gate		p++; q++;
13177c478bdstevel@tonic-gate	}
13187c478bdstevel@tonic-gate	return ((*p == *q) && i >= 0);
13197c478bdstevel@tonic-gate}
13207c478bdstevel@tonic-gate
1321cc6c529chinint
1322cc6c529chinsequal(char *a, char *b)	/* must be same thru NULL */
13237c478bdstevel@tonic-gate{
1324cc6c529chin	char *p = a, *q = b;
13257c478bdstevel@tonic-gate
1326de81e71Tim Marsland	while (*p && *q && (*p == *q)) {
13277c478bdstevel@tonic-gate		p++; q++;
13287c478bdstevel@tonic-gate	}
13297c478bdstevel@tonic-gate	return (*p == *q);
13307c478bdstevel@tonic-gate}
13317c478bdstevel@tonic-gate
1332cc6c529chinvoid
1333cc6c529chinmakealias(char *buf)
13347c478bdstevel@tonic-gate{
1335cc6c529chin	int i;
1336cc6c529chin	char *a;
1337cc6c529chin	char *b;
13387c478bdstevel@tonic-gate
13397c478bdstevel@tonic-gate	Alias[0] = a = Aliasbuf;
13407c478bdstevel@tonic-gate	b = buf;
13417c478bdstevel@tonic-gate	i = 1;
13427c478bdstevel@tonic-gate	while (*b && *b != ':') {
13437c478bdstevel@tonic-gate		if (*b == '|') {
1344632cbd9Toomas Soome			*a++ = '\0';
13457c478bdstevel@tonic-gate			Alias[i++] = a;
13467c478bdstevel@tonic-gate			b++;
1347de81e71Tim Marsland		} else
13487c478bdstevel@tonic-gate			*a++ = *b++;
13497c478bdstevel@tonic-gate	}
1350632cbd9Toomas Soome	*a = '\0';
13517c478bdstevel@tonic-gate	Alias[i] = NULL;
1352de81e71Tim Marsland#ifdef	DEB
1353de81e71Tim Marsland	for (i = 0; Alias[i]; printf("A:%s\n", Alias[i++]))
1354de81e71Tim Marsland		;
1355de81e71Tim Marsland#endif
13567c478bdstevel@tonic-gate}
13577c478bdstevel@tonic-gate
1358cc6c529chinint
1359cc6c529chinisalias(char *ident)	/* is ident same as one of the aliases? */
13607c478bdstevel@tonic-gate{
13617c478bdstevel@tonic-gate	char **a = Alias;
13627c478bdstevel@tonic-gate
13637c478bdstevel@tonic-gate	if (*a)
13647c478bdstevel@tonic-gate		while (*a)
13657c478bdstevel@tonic-gate			if (sequal(ident, *a))
1366de81e71Tim Marsland				return (YES);
13677c478bdstevel@tonic-gate			else
13687c478bdstevel@tonic-gate				a++;
1369de81e71Tim Marsland	return (NO);
13707c478bdstevel@tonic-gate}
13717c478bdstevel@tonic-gate
13727c478bdstevel@tonic-gate
13737c478bdstevel@tonic-gate/*
13747c478bdstevel@tonic-gate * routine to output the string for the environment TERMCAP variable
13757c478bdstevel@tonic-gate */
13767c478bdstevel@tonic-gate#define	WHITE(c)	(c == ' ' || c == '\t')
13777c478bdstevel@tonic-gatechar delcap[128][2];
13787c478bdstevel@tonic-gateint ncap = 0;
13797c478bdstevel@tonic-gate
1380cc6c529chinvoid
1381cc6c529chinwrtermcap(char *bp)
13827c478bdstevel@tonic-gate{
13837c478bdstevel@tonic-gate	char buf[CAPBUFSIZ];
13847c478bdstevel@tonic-gate	char *p = buf;
13857c478bdstevel@tonic-gate	char *tp;
13867c478bdstevel@tonic-gate	char *putbuf();
13877c478bdstevel@tonic-gate	int space, empty;
13887c478bdstevel@tonic-gate
13897c478bdstevel@tonic-gate	/* discard names with blanks */
1390de81e71Tim Marsland/* May not be desireable ? */
13917c478bdstevel@tonic-gate	while (*bp && *bp != ':') {
13927c478bdstevel@tonic-gate		if (*bp == '|') {
13937c478bdstevel@tonic-gate			tp = bp+1;
13947c478bdstevel@tonic-gate			space = NO;
13957c478bdstevel@tonic-gate			while (*tp && *tp != '|' && *tp != ':') {
1396de81e71Tim Marsland				space = (space || WHITE(*tp));
13977c478bdstevel@tonic-gate				tp++;
13987c478bdstevel@tonic-gate			}
13997c478bdstevel@tonic-gate			if (space) {
14007c478bdstevel@tonic-gate				bp = tp;
14017c478bdstevel@tonic-gate				continue;
14027c478bdstevel@tonic-gate			}
14037c478bdstevel@tonic-gate		}
14047c478bdstevel@tonic-gate		*p++ = *bp++;
14057c478bdstevel@tonic-gate	}
14067c478bdstevel@tonic-gate
14077c478bdstevel@tonic-gate	while (*bp) {
14087c478bdstevel@tonic-gate		switch (*bp) {
14097c478bdstevel@tonic-gate		case ':':	/* discard empty, cancelled  or dupl fields */
1410de81e71Tim Marsland			tp = bp + 1;
14117c478bdstevel@tonic-gate			empty = YES;
14127c478bdstevel@tonic-gate			while (*tp && *tp != ':') {
1413de81e71Tim Marsland				empty = (empty && WHITE(*tp));
14147c478bdstevel@tonic-gate				tp++;
14157c478bdstevel@tonic-gate			}
14167c478bdstevel@tonic-gate			if (empty || cancelled(bp+1)) {
14177c478bdstevel@tonic-gate				bp = tp;
14187c478bdstevel@tonic-gate				continue;
14197c478bdstevel@tonic-gate			}
14207c478bdstevel@tonic-gate			break;
14217c478bdstevel@tonic-gate
14227c478bdstevel@tonic-gate		case ' ':	/* no spaces in output */
14237c478bdstevel@tonic-gate			p = putbuf(p, "\\040");
14247c478bdstevel@tonic-gate			bp++;
14257c478bdstevel@tonic-gate			continue;
14267c478bdstevel@tonic-gate
14277c478bdstevel@tonic-gate		case '!':	/* the shell thinks this is history */
14287c478bdstevel@tonic-gate			p = putbuf(p, "\\041");
14297c478bdstevel@tonic-gate			bp++;
14307c478bdstevel@tonic-gate			continue;
14317c478bdstevel@tonic-gate
14327c478bdstevel@tonic-gate		case ',':	/* the shell thinks this is history */
14337c478bdstevel@tonic-gate			p = putbuf(p, "\\054");
14347c478bdstevel@tonic-gate			bp++;
14357c478bdstevel@tonic-gate			continue;
14367c478bdstevel@tonic-gate
14377c478bdstevel@tonic-gate		case '"':	/* no quotes in output */
14387c478bdstevel@tonic-gate			p = putbuf(p, "\\042");
14397c478bdstevel@tonic-gate			bp++;
14407c478bdstevel@tonic-gate			continue;
14417c478bdstevel@tonic-gate
14427c478bdstevel@tonic-gate		case '\'':	/* no quotes in output */
14437c478bdstevel@tonic-gate			p = putbuf(p, "\\047");
14447c478bdstevel@tonic-gate			bp++;
14457c478bdstevel@tonic-gate			continue;
14467c478bdstevel@tonic-gate
14477c478bdstevel@tonic-gate		case '`':	/* no back quotes in output */
14487c478bdstevel@tonic-gate			p = putbuf(p, "\\140");
14497c478bdstevel@tonic-gate			bp++;
14507c478bdstevel@tonic-gate			continue;
14517c478bdstevel@tonic-gate
14527c478bdstevel@tonic-gate		case '\\':
14537c478bdstevel@tonic-gate		case '^':	/* anything following is OK */
14547c478bdstevel@tonic-gate			*p++ = *bp++;
14557c478bdstevel@tonic-gate		}
14567c478bdstevel@tonic-gate		*p++ = *bp++;
14577c478bdstevel@tonic-gate	}
14587c478bdstevel@tonic-gate	*p++ = ':';	/* we skipped the last : with the : lookahead hack */
1459de81e71Tim Marsland	(void) write(STDOUT, buf, p-buf);
14607c478bdstevel@tonic-gate}
14617c478bdstevel@tonic-gate
1462cc6c529chinint
1463cc6c529chincancelled(char *cap)
14647c478bdstevel@tonic-gate{
1465cc6c529chin	int i;
14667c478bdstevel@tonic-gate
1467de81e71Tim Marsland	for (i = 0; i < ncap; i++) {
14687c478bdstevel@tonic-gate		if (cap[0] == delcap[i][0] && cap[1] == delcap[i][1])
14697c478bdstevel@tonic-gate			return (YES);
14707c478bdstevel@tonic-gate	}
14717c478bdstevel@tonic-gate	/* delete a second occurrance of the same capability */
14727c478bdstevel@tonic-gate	delcap[ncap][0] = cap[0];
14737c478bdstevel@tonic-gate	delcap[ncap][1] = cap[1];
14747c478bdstevel@tonic-gate	ncap++;
14757c478bdstevel@tonic-gate	return (cap[2] == '@');
14767c478bdstevel@tonic-gate}
14777c478bdstevel@tonic-gate
14787c478bdstevel@tonic-gatechar *
14797c478bdstevel@tonic-gateputbuf(ptr, str)
14807c478bdstevel@tonic-gatechar	*ptr;
14817c478bdstevel@tonic-gatechar	*str;
14827c478bdstevel@tonic-gate{
14837c478bdstevel@tonic-gate	char buf[20];
14847c478bdstevel@tonic-gate
14857c478bdstevel@tonic-gate	while (*str) {
14867c478bdstevel@tonic-gate		switch (*str) {
14877c478bdstevel@tonic-gate		case '\033':
14887c478bdstevel@tonic-gate			ptr = putbuf(ptr, "\\E");
14897c478bdstevel@tonic-gate			str++;
14907c478bdstevel@tonic-gate			break;
14917c478bdstevel@tonic-gate		default:
14927c478bdstevel@tonic-gate			if (*str <= ' ') {
14937c478bdstevel@tonic-gate				(void) sprintf(buf, "\\%03o", *str);
14947c478bdstevel@tonic-gate				ptr = putbuf(ptr, buf);
14957c478bdstevel@tonic-gate				str++;
14967c478bdstevel@tonic-gate			} else
14977c478bdstevel@tonic-gate				*ptr++ = *str++;
14987c478bdstevel@tonic-gate		}
14997c478bdstevel@tonic-gate	}
15007c478bdstevel@tonic-gate	return (ptr);
15017c478bdstevel@tonic-gate}
15027c478bdstevel@tonic-gate
1503cc6c529chinint
1504cc6c529chinbaudrate(char *p)
15057c478bdstevel@tonic-gate{
15067c478bdstevel@tonic-gate	char buf[8];
15077c478bdstevel@tonic-gate	int i = 0;
15087c478bdstevel@tonic-gate
15097c478bdstevel@tonic-gate	while (i < 7 && (isalnum(*p) || *p == '.'))
15107c478bdstevel@tonic-gate		buf[i++] = *p++;
1511632cbd9Toomas Soome	buf[i] = '\0';
1512de81e71Tim Marsland	for (i = 0; speeds[i].string; i++)
15137c478bdstevel@tonic-gate		if (sequal(speeds[i].string, buf))
15147c478bdstevel@tonic-gate			return (speeds[i].speed);
15157c478bdstevel@tonic-gate	return (-1);
15167c478bdstevel@tonic-gate}
15177c478bdstevel@tonic-gate
15187c478bdstevel@tonic-gatechar *
15197c478bdstevel@tonic-gatemapped(type)
15207c478bdstevel@tonic-gatechar	*type;
15217c478bdstevel@tonic-gate{
15227c478bdstevel@tonic-gate	extern short	ospeed;
15237c478bdstevel@tonic-gate	int	match;
15247c478bdstevel@tonic-gate
1525de81e71Tim Marsland#ifdef DEB
1526de81e71Tim Marsland	printf("spd:%d\n", ospeed);
15277c478bdstevel@tonic-gate	prmap();
1528de81e71Tim Marsland#endif
15297c478bdstevel@tonic-gate	Map = map;
1530de81e71Tim Marsland	while (Map->Ident) {
1531632cbd9Toomas Soome		if (*(Map->Ident) == '\0' ||
1532de81e71Tim Marsland		    sequal(Map->Ident, type) || isalias(Map->Ident)) {
15337c478bdstevel@tonic-gate			match = NO;
1534de81e71Tim Marsland			switch (Map->Test) {
1535de81e71Tim Marsland			case ANY:	/* no test specified */
1536de81e71Tim Marsland			case ALL:
1537de81e71Tim Marsland				match = YES;
1538de81e71Tim Marsland				break;
1539de81e71Tim Marsland
1540de81e71Tim Marsland			case GT:
1541de81e71Tim Marsland				match = (ospeed > Map->Speed);
1542de81e71Tim Marsland				break;
1543de81e71Tim Marsland
1544de81e71Tim Marsland			case GE:
1545de81e71Tim Marsland				match = (ospeed >= Map->Speed);
1546de81e71Tim Marsland				break;
1547de81e71Tim Marsland
1548de81e71Tim Marsland			case EQ:
1549de81e71Tim Marsland				match = (ospeed == Map->Speed);
1550de81e71Tim Marsland				break;
1551de81e71Tim Marsland
1552de81e71Tim Marsland			case LE:
1553de81e71Tim Marsland				match = (ospeed <= Map->Speed);
1554de81e71Tim Marsland				break;
1555de81e71Tim Marsland
1556de81e71Tim Marsland			case LT:
1557de81e71Tim Marsland				match = (ospeed < Map->Speed);
1558de81e71Tim Marsland				break;
1559de81e71Tim Marsland
1560de81e71Tim Marsland			case NE:
1561de81e71Tim Marsland				match = (ospeed != Map->Speed);
1562de81e71Tim Marsland				break;
15637c478bdstevel@tonic-gate			}
15647c478bdstevel@tonic-gate			if (match)
15657c478bdstevel@tonic-gate				return (Map->Type);
15667c478bdstevel@tonic-gate		}
15677c478bdstevel@tonic-gate		Map++;
15687c478bdstevel@tonic-gate	}
15697c478bdstevel@tonic-gate	/* no match found; return given type */
15707c478bdstevel@tonic-gate	return (type);
15717c478bdstevel@tonic-gate}
15727c478bdstevel@tonic-gate
1573de81e71Tim Marsland#ifdef DEB
15747c478bdstevel@tonic-gateprmap()
15757c478bdstevel@tonic-gate{
15767c478bdstevel@tonic-gate	Map = map;
1577de81e71Tim Marsland	while (Map->Ident) {
1578de81e71Tim Marsland		printf("%s t:%d s:%d %s\n",
1579de81e71Tim Marsland		    Map->Ident, Map->Test, Map->Speed, Map->Type);
1580de81e71Tim Marsland		Map++;
15817c478bdstevel@tonic-gate	}
15827c478bdstevel@tonic-gate}
1583de81e71Tim Marsland#endif
15847c478bdstevel@tonic-gate
15857c478bdstevel@tonic-gatechar *
15867c478bdstevel@tonic-gatenextarg(argc, argv)
15877c478bdstevel@tonic-gateint	argc;
15887c478bdstevel@tonic-gatechar	*argv[];
15897c478bdstevel@tonic-gate{
15907c478bdstevel@tonic-gate	if (argc <= 0)
1591de81e71Tim Marsland		fatal("Too few args: ", *argv);
15927c478bdstevel@tonic-gate	if (*(*++argv) == '-')
1593de81e71Tim Marsland		fatal("Unexpected arg: ", *argv);
15947c478bdstevel@tonic-gate	return (*argv);
15957c478bdstevel@tonic-gate}
15967c478bdstevel@tonic-gate
1597cc6c529chinvoid
1598de81e71Tim Marslandfatal(char *mesg, char *obj)
15997c478bdstevel@tonic-gate{
1600de81e71Tim Marsland	prs(mesg);
1601de81e71Tim Marsland	prs(obj);
1602de81e71Tim Marsland	prc('\n');
1603de81e71Tim Marsland	prs(USAGE);
16047c478bdstevel@tonic-gate	flush();
16057c478bdstevel@tonic-gate	exit(1);
16067c478bdstevel@tonic-gate}
16077c478bdstevel@tonic-gate
16087c478bdstevel@tonic-gate
16097c478bdstevel@tonic-gate/*
16107c478bdstevel@tonic-gate * Stolen from /usr/src/ucb/reset.c, which this mod obsoletes.
16117c478bdstevel@tonic-gate */
16127c478bdstevel@tonic-gatechar
16137c478bdstevel@tonic-gatereset(ch, def)
16147c478bdstevel@tonic-gate	char ch;
16157c478bdstevel@tonic-gate	int def;
16167c478bdstevel@tonic-gate{
16177c478bdstevel@tonic-gate	if (ch == 0 || (ch&0377) == 0377)
1618de81e71Tim Marsland		return (def);
1619de81e71Tim Marsland	return (ch);
16207c478bdstevel@tonic-gate}
1621