xref: /csrg-svn/usr.bin/telnet/utilities.c (revision 38207)
133686Sbostic /*
233686Sbostic  * Copyright (c) 1988 Regents of the University of California.
333686Sbostic  * All rights reserved.
433686Sbostic  *
533686Sbostic  * Redistribution and use in source and binary forms are permitted
634898Sbostic  * provided that the above copyright notice and this paragraph are
734898Sbostic  * duplicated in all such forms and that any documentation,
834898Sbostic  * advertising materials, and other materials related to such
934898Sbostic  * distribution and use acknowledge that the software was developed
1034898Sbostic  * by the University of California, Berkeley.  The name of the
1134898Sbostic  * University may not be used to endorse or promote products derived
1234898Sbostic  * from this software without specific prior written permission.
1334898Sbostic  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
1434898Sbostic  * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
1534898Sbostic  * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
1633686Sbostic  */
1733686Sbostic 
1833686Sbostic #ifndef lint
19*38207Sminshall static char sccsid[] = "@(#)utilities.c	1.13 (Berkeley) 05/30/89";
2033686Sbostic #endif /* not lint */
2133686Sbostic 
2232149Sminshall #define	TELOPTS
2332149Sminshall #include <arpa/telnet.h>
2432381Sminshall #include <sys/types.h>
2532149Sminshall 
2632149Sminshall #include <ctype.h>
2732149Sminshall 
2834305Sminshall #include "general.h"
2934305Sminshall 
3036280Sminshall #include "fdset.h"
3136280Sminshall 
3232381Sminshall #include "ring.h"
3332381Sminshall 
3436278Sminshall #include "defines.h"
3536278Sminshall 
3632149Sminshall #include "externs.h"
3732149Sminshall 
3832149Sminshall FILE	*NetTrace = 0;		/* Not in bss, since needs to stay */
3932149Sminshall 
4032149Sminshall /*
4132149Sminshall  * upcase()
4232149Sminshall  *
4332149Sminshall  *	Upcase (in place) the argument.
4432149Sminshall  */
4532149Sminshall 
4632149Sminshall void
4732149Sminshall upcase(argument)
4832149Sminshall register char *argument;
4932149Sminshall {
5032149Sminshall     register int c;
5132149Sminshall 
5232149Sminshall     while ((c = *argument) != 0) {
5332149Sminshall 	if (islower(c)) {
5432149Sminshall 	    *argument = toupper(c);
5532149Sminshall 	}
5632149Sminshall 	argument++;
5732149Sminshall     }
5832149Sminshall }
5932149Sminshall 
6032149Sminshall /*
6132149Sminshall  * SetSockOpt()
6232149Sminshall  *
6332149Sminshall  * Compensate for differences in 4.2 and 4.3 systems.
6432149Sminshall  */
6532149Sminshall 
6632149Sminshall int
6732149Sminshall SetSockOpt(fd, level, option, yesno)
6832149Sminshall int
6932149Sminshall 	fd,
7032149Sminshall 	level,
7132149Sminshall 	option,
7232149Sminshall 	yesno;
7332149Sminshall {
7432149Sminshall #ifndef	NOT43
7532149Sminshall     return setsockopt(fd, level, option,
7632149Sminshall 				(char *)&yesno, sizeof yesno);
7732149Sminshall #else	/* NOT43 */
7832149Sminshall     if (yesno == 0) {		/* Can't do that in 4.2! */
7932149Sminshall 	fprintf(stderr, "Error: attempt to turn off an option 0x%x.\n",
8032149Sminshall 				option);
8132149Sminshall 	return -1;
8232149Sminshall     }
8332149Sminshall     return setsockopt(fd, level, option, 0, 0);
8432149Sminshall #endif	/* NOT43 */
8532149Sminshall }
8632149Sminshall 
8732149Sminshall /*
8832149Sminshall  * The following are routines used to print out debugging information.
8932149Sminshall  */
9032149Sminshall 
9132149Sminshall 
9232149Sminshall void
9332149Sminshall Dump(direction, buffer, length)
9432149Sminshall char	direction;
9532149Sminshall char	*buffer;
9632149Sminshall int	length;
9732149Sminshall {
9832149Sminshall #   define BYTES_PER_LINE	32
9932149Sminshall #   define min(x,y)	((x<y)? x:y)
10032149Sminshall     char *pThis;
10132149Sminshall     int offset;
10232149Sminshall 
10332149Sminshall     offset = 0;
10432149Sminshall 
10532149Sminshall     while (length) {
10632149Sminshall 	/* print one line */
10732149Sminshall 	fprintf(NetTrace, "%c 0x%x\t", direction, offset);
10832149Sminshall 	pThis = buffer;
10932149Sminshall 	buffer = buffer+min(length, BYTES_PER_LINE);
11032149Sminshall 	while (pThis < buffer) {
11132149Sminshall 	    fprintf(NetTrace, "%.2x", (*pThis)&0xff);
11232149Sminshall 	    pThis++;
11332149Sminshall 	}
11437226Sminshall 	if (NetTrace == stdout) {
115*38207Sminshall 	    fprintf(NetTrace, "\r\n");
116*38207Sminshall 	} else {
11737226Sminshall 	    fprintf(NetTrace, "\n");
11837226Sminshall 	}
11932149Sminshall 	length -= BYTES_PER_LINE;
12032149Sminshall 	offset += BYTES_PER_LINE;
12132149Sminshall 	if (length < 0) {
12236693Sminshall 	    fflush(NetTrace);
12332149Sminshall 	    return;
12432149Sminshall 	}
12532149Sminshall 	/* find next unique line */
12632149Sminshall     }
12736693Sminshall     fflush(NetTrace);
12832149Sminshall }
12932149Sminshall 
13032149Sminshall 
13132149Sminshall void
13237226Sminshall printoption(direction, fmt, option)
13332149Sminshall 	char *direction, *fmt;
13437226Sminshall 	int option;
13532149Sminshall {
13632149Sminshall 	if (!showoptions)
13732149Sminshall 		return;
13837226Sminshall 	fprintf(NetTrace, "%s ", direction);
13932149Sminshall 	if (option < (sizeof telopts/sizeof telopts[0]))
14032149Sminshall 		fprintf(NetTrace, "%s %s", fmt, telopts[option]);
14132149Sminshall 	else
14232149Sminshall 		fprintf(NetTrace, "%s %d", fmt, option);
14337226Sminshall 	if (NetTrace == stdout) {
14437226Sminshall 	    fprintf(NetTrace, "\r\n");
14537226Sminshall 	} else {
14637226Sminshall 	    fprintf(NetTrace, "\n");
14732149Sminshall 	}
14837226Sminshall 	return;
14932149Sminshall }
15032149Sminshall 
15132149Sminshall void
15232149Sminshall printsub(direction, pointer, length)
15332149Sminshall char	*direction,		/* "<" or ">" */
15432149Sminshall 	*pointer;		/* where suboption data sits */
15532149Sminshall int	length;			/* length of suboption data */
15632149Sminshall {
15732149Sminshall     if (showoptions) {
15832149Sminshall 	fprintf(NetTrace, "%s suboption ",
15932149Sminshall 				(direction[0] == '<')? "Received":"Sent");
16032149Sminshall 	switch (pointer[0]) {
16132149Sminshall 	case TELOPT_TTYPE:
16232149Sminshall 	    fprintf(NetTrace, "Terminal type ");
16332149Sminshall 	    switch (pointer[1]) {
16432149Sminshall 	    case TELQUAL_IS:
16532149Sminshall 		{
16633286Sminshall 		    char tmpbuf[SUBBUFSIZE];
16732149Sminshall 		    int minlen = min(length, sizeof tmpbuf);
16832149Sminshall 
16932149Sminshall 		    memcpy(tmpbuf, pointer+2, minlen);
17032149Sminshall 		    tmpbuf[minlen-1] = 0;
17132149Sminshall 		    fprintf(NetTrace, "is %s.\n", tmpbuf);
17232149Sminshall 		}
17332149Sminshall 		break;
17432149Sminshall 	    case TELQUAL_SEND:
17532149Sminshall 		fprintf(NetTrace, "- request to send.\n");
17632149Sminshall 		break;
17732149Sminshall 	    default:
17832149Sminshall 		fprintf(NetTrace,
17934849Sminshall 				"- unknown qualifier %d (0x%x).\n",
18034849Sminshall 				pointer[1], pointer[1]);
18132149Sminshall 	    }
18232149Sminshall 	    break;
18332149Sminshall 	default:
18432149Sminshall 	    fprintf(NetTrace, "Unknown option %d (0x%x)\n",
18532149Sminshall 					pointer[0], pointer[0]);
18632149Sminshall 	}
18732149Sminshall     }
18832149Sminshall }
18936278Sminshall 
19036278Sminshall /* EmptyTerminal - called to make sure that the terminal buffer is empty.
19136278Sminshall  *			Note that we consider the buffer to run all the
19236278Sminshall  *			way to the kernel (thus the select).
19336278Sminshall  */
19436278Sminshall 
19536278Sminshall void
19636278Sminshall EmptyTerminal()
19736278Sminshall {
19836278Sminshall #if	defined(unix)
19936278Sminshall     fd_set	o;
20036278Sminshall 
20136278Sminshall     FD_ZERO(&o);
20236278Sminshall #endif	/* defined(unix) */
20336278Sminshall 
20436278Sminshall     if (TTYBYTES() == 0) {
20536278Sminshall #if	defined(unix)
20636278Sminshall 	FD_SET(tout, &o);
20736278Sminshall 	(void) select(tout+1, (fd_set *) 0, &o, (fd_set *) 0,
20836278Sminshall 			(struct timeval *) 0);	/* wait for TTLOWAT */
20936278Sminshall #endif	/* defined(unix) */
21036278Sminshall     } else {
21136278Sminshall 	while (TTYBYTES()) {
21236278Sminshall 	    ttyflush(0);
21336278Sminshall #if	defined(unix)
21436278Sminshall 	    FD_SET(tout, &o);
21536278Sminshall 	    (void) select(tout+1, (fd_set *) 0, &o, (fd_set *) 0,
21636278Sminshall 				(struct timeval *) 0);	/* wait for TTLOWAT */
21736278Sminshall #endif	/* defined(unix) */
21836278Sminshall 	}
21936278Sminshall     }
22036278Sminshall }
22136278Sminshall 
22236278Sminshall void
22336278Sminshall SetForExit()
22436278Sminshall {
22536278Sminshall     setconnmode();
22636278Sminshall #if	defined(TN3270)
22736278Sminshall     if (In3270) {
22836278Sminshall 	Finish3270();
22936278Sminshall     }
23036279Sminshall #else	/* defined(TN3270) */
23136279Sminshall     do {
23236279Sminshall 	telrcv();			/* Process any incoming data */
23336279Sminshall 	EmptyTerminal();
23436279Sminshall     } while (ring_full_count(&netiring));	/* While there is any */
23536278Sminshall #endif	/* defined(TN3270) */
23636278Sminshall     setcommandmode();
23736278Sminshall     fflush(stdout);
23836278Sminshall     fflush(stderr);
23936278Sminshall #if	defined(TN3270)
24036278Sminshall     if (In3270) {
24136278Sminshall 	StopScreen(1);
24236278Sminshall     }
24336278Sminshall #endif	/* defined(TN3270) */
24436278Sminshall     setconnmode();
24536278Sminshall     EmptyTerminal();			/* Flush the path to the tty */
24636278Sminshall     setcommandmode();
24736278Sminshall }
24836278Sminshall 
24936278Sminshall void
25036278Sminshall Exit(returnCode)
25136278Sminshall int returnCode;
25236278Sminshall {
25336278Sminshall     SetForExit();
25436278Sminshall     exit(returnCode);
25536278Sminshall }
25636278Sminshall 
25736278Sminshall void
25836278Sminshall ExitString(string, returnCode)
25936278Sminshall char *string;
26036278Sminshall int returnCode;
26136278Sminshall {
26236278Sminshall     SetForExit();
26336278Sminshall     fwrite(string, 1, strlen(string), stderr);
26436278Sminshall     exit(returnCode);
26536278Sminshall }
26636278Sminshall 
26736278Sminshall #if defined(MSDOS)
26836278Sminshall void
26936278Sminshall ExitPerror(string, returnCode)
27036278Sminshall char *string;
27136278Sminshall int returnCode;
27236278Sminshall {
27336278Sminshall     SetForExit();
27436278Sminshall     perror(string);
27536278Sminshall     exit(returnCode);
27636278Sminshall }
27736278Sminshall #endif /* defined(MSDOS) */
278