Ported the telnet command from FreeBSD - compiles, but might not yet work; it's
completely untested at this point. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@19494 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -7,5 +7,6 @@ SubInclude HAIKU_TOP src bin network ifconfig ;
|
||||
#SubInclude HAIKU_TOP src bin network ppp_up ;
|
||||
SubInclude HAIKU_TOP src bin network ping ;
|
||||
SubInclude HAIKU_TOP src bin network route ;
|
||||
SubInclude HAIKU_TOP src bin network telnet ;
|
||||
SubInclude HAIKU_TOP src bin network telnetd ;
|
||||
SubInclude HAIKU_TOP src bin network traceroute ;
|
||||
|
||||
@@ -0,0 +1,23 @@
|
||||
SubDir HAIKU_TOP src bin network telnet ;
|
||||
|
||||
UseHeaders [ FDirName $(HAIKU_TOP) headers compatibility bsd ] : true ;
|
||||
UseHeaders [ FDirName $(HAIKU_TOP) src libs ] : true ;
|
||||
UseHeaders [ FDirName $(HAIKU_TOP) src libs libtelnet ] : false ;
|
||||
|
||||
local defines = [ FDefines USE_TERMIO=1 OLD_ENVIRON=1 ENV_HACK=1 ] ;
|
||||
|
||||
SubDirCcFlags $(defines) ;
|
||||
SubDirC++Flags $(defines) ;
|
||||
|
||||
BinCommand telnet :
|
||||
authenc.c
|
||||
commands.c
|
||||
main.c
|
||||
network.c
|
||||
ring.c
|
||||
sys_bsd.c
|
||||
telnet.c
|
||||
terminal.c
|
||||
utilities.c
|
||||
: libtermcap.a libncurses.a libtelnet.a libutil.a libbsd.so $(NETWORK_LIBS)
|
||||
;
|
||||
@@ -0,0 +1,111 @@
|
||||
/*-
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#if 0
|
||||
#ifndef lint
|
||||
static const char sccsid[] = "@(#)authenc.c 8.1 (Berkeley) 6/6/93";
|
||||
#endif
|
||||
#endif
|
||||
#include <sys/cdefs.h>
|
||||
__FBSDID("$FreeBSD: src/contrib/telnet/telnet/authenc.c,v 1.6 2003/05/04 02:54:48 obrien Exp $");
|
||||
|
||||
#ifdef AUTHENTICATION
|
||||
#ifdef ENCRYPTION
|
||||
#include <sys/types.h>
|
||||
#include <arpa/telnet.h>
|
||||
#include <pwd.h>
|
||||
#include <unistd.h>
|
||||
#include <libtelnet/encrypt.h>
|
||||
#include <libtelnet/misc.h>
|
||||
|
||||
#include "general.h"
|
||||
#include "ring.h"
|
||||
#include "externs.h"
|
||||
#include "defines.h"
|
||||
#include "types.h"
|
||||
|
||||
int
|
||||
net_write(unsigned char *str, int len)
|
||||
{
|
||||
if (NETROOM() > len) {
|
||||
ring_supply_data(&netoring, str, len);
|
||||
if (str[0] == IAC && str[1] == SE)
|
||||
printsub('>', &str[2], len-2);
|
||||
return(len);
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
void
|
||||
net_encrypt(void)
|
||||
{
|
||||
#ifdef ENCRYPTION
|
||||
if (encrypt_output)
|
||||
ring_encrypt(&netoring, encrypt_output);
|
||||
else
|
||||
ring_clearto(&netoring);
|
||||
#endif /* ENCRYPTION */
|
||||
}
|
||||
|
||||
int
|
||||
telnet_spin(void)
|
||||
{
|
||||
return(-1);
|
||||
}
|
||||
|
||||
char *
|
||||
telnet_getenv(char *val)
|
||||
{
|
||||
return((char *)env_getvalue((unsigned char *)val));
|
||||
}
|
||||
|
||||
char *
|
||||
telnet_gets(const char *prom, char *result, int length, int echo)
|
||||
{
|
||||
extern int globalmode;
|
||||
int om = globalmode;
|
||||
char *res;
|
||||
|
||||
TerminalNewMode(-1);
|
||||
if (echo) {
|
||||
printf("%s", prom);
|
||||
res = fgets(result, length, stdin);
|
||||
} else if ((res = getpass(prom))) {
|
||||
strncpy(result, res, length);
|
||||
res = result;
|
||||
}
|
||||
TerminalNewMode(om);
|
||||
return(res);
|
||||
}
|
||||
#endif /* ENCRYPTION */
|
||||
#endif /* AUTHENTICATION */
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,56 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)defines.h 8.1 (Berkeley) 6/6/93
|
||||
* $FreeBSD: src/contrib/telnet/telnet/defines.h,v 1.2 2001/11/30 21:06:35 markm Exp $
|
||||
*/
|
||||
|
||||
#define settimer(x) clocks.x = clocks.system++
|
||||
|
||||
#define NETADD(c) { *netoring.supply = c; ring_supplied(&netoring, 1); }
|
||||
#define NET2ADD(c1,c2) { NETADD(c1); NETADD(c2); }
|
||||
#define NETBYTES() (ring_full_count(&netoring))
|
||||
#define NETROOM() (ring_empty_count(&netoring))
|
||||
|
||||
#define TTYADD(c) if (!(SYNCHing||flushout)) { \
|
||||
*ttyoring.supply = c; \
|
||||
ring_supplied(&ttyoring, 1); \
|
||||
}
|
||||
#define TTYBYTES() (ring_full_count(&ttyoring))
|
||||
#define TTYROOM() (ring_empty_count(&ttyoring))
|
||||
|
||||
/* Various modes */
|
||||
#define MODE_LOCAL_CHARS(m) ((m)&(MODE_EDIT|MODE_TRAPSIG))
|
||||
#define MODE_LOCAL_ECHO(m) ((m)&MODE_ECHO)
|
||||
#define MODE_COMMAND_LINE(m) ((m)==-1)
|
||||
|
||||
#define CONTROL(x) ((x)&0x1f) /* CTRL(x) is not portable */
|
||||
@@ -0,0 +1,491 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1990, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)externs.h 8.3 (Berkeley) 5/30/95
|
||||
* $FreeBSD: src/contrib/telnet/telnet/externs.h,v 1.10 2003/05/11 18:17:00 markm Exp $
|
||||
*/
|
||||
|
||||
#ifndef BSD
|
||||
# define BSD 43
|
||||
#endif
|
||||
|
||||
/*
|
||||
* ucb stdio.h defines BSD as something weird
|
||||
*/
|
||||
#if defined(sun) && defined(__svr4__)
|
||||
#define BSD 43
|
||||
#endif
|
||||
|
||||
#ifndef USE_TERMIO
|
||||
# if BSD > 43 || defined(SYSV_TERMIO)
|
||||
# define USE_TERMIO
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#include <stdio.h>
|
||||
#include <setjmp.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <errno.h>
|
||||
#ifdef USE_TERMIO
|
||||
# ifndef VINTR
|
||||
# include <termios.h>
|
||||
# endif
|
||||
# define termio termios
|
||||
#endif
|
||||
#if defined(NO_CC_T) || !defined(USE_TERMIO)
|
||||
# if !defined(USE_TERMIO)
|
||||
typedef char cc_t;
|
||||
# else
|
||||
typedef unsigned char cc_t;
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#if defined(IPSEC)
|
||||
#include <netinet6/ipsec.h>
|
||||
#if defined(IPSEC_POLICY_IPSEC)
|
||||
extern char *ipsec_policy_in;
|
||||
extern char *ipsec_policy_out;
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef _POSIX_VDISABLE
|
||||
# ifdef sun
|
||||
# include <sys/param.h> /* pick up VDISABLE definition, mayby */
|
||||
# endif
|
||||
# ifdef VDISABLE
|
||||
# define _POSIX_VDISABLE VDISABLE
|
||||
# else
|
||||
# define _POSIX_VDISABLE ((cc_t)'\377')
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#define SUBBUFSIZE 256
|
||||
|
||||
#if !defined(P)
|
||||
# ifdef __STDC__
|
||||
# define P(x) x
|
||||
# else
|
||||
# define P(x) ()
|
||||
# endif
|
||||
#endif
|
||||
|
||||
extern int
|
||||
autologin, /* Autologin enabled */
|
||||
skiprc, /* Don't process the ~/.telnetrc file */
|
||||
eight, /* use eight bit mode (binary in and/or out */
|
||||
family, /* address family of peer */
|
||||
flushout, /* flush output */
|
||||
connected, /* Are we connected to the other side? */
|
||||
globalmode, /* Mode tty should be in */
|
||||
telnetport, /* Are we connected to the telnet port? */
|
||||
localflow, /* Flow control handled locally */
|
||||
restartany, /* If flow control, restart output on any character */
|
||||
localchars, /* we recognize interrupt/quit */
|
||||
donelclchars, /* the user has set "localchars" */
|
||||
showoptions,
|
||||
net, /* Network file descriptor */
|
||||
tin, /* Terminal input file descriptor */
|
||||
tout, /* Terminal output file descriptor */
|
||||
crlf, /* Should '\r' be mapped to <CR><LF> (or <CR><NUL>)? */
|
||||
autoflush, /* flush output when interrupting? */
|
||||
autosynch, /* send interrupt characters with SYNCH? */
|
||||
SYNCHing, /* Is the stream in telnet SYNCH mode? */
|
||||
donebinarytoggle, /* the user has put us in binary */
|
||||
dontlecho, /* do we suppress local echoing right now? */
|
||||
crmod,
|
||||
netdata, /* Print out network data flow */
|
||||
prettydump, /* Print "netdata" output in user readable format */
|
||||
termdata, /* Print out terminal data flow */
|
||||
telnet_debug, /* Debug level */
|
||||
doaddrlookup, /* do a reverse lookup? */
|
||||
clienteof; /* Client received EOF */
|
||||
|
||||
extern cc_t escape; /* Escape to command mode */
|
||||
extern cc_t rlogin; /* Rlogin mode escape character */
|
||||
#ifdef KLUDGELINEMODE
|
||||
extern cc_t echoc; /* Toggle local echoing */
|
||||
#endif
|
||||
|
||||
extern char
|
||||
*prompt; /* Prompt for command. */
|
||||
|
||||
extern char
|
||||
doopt[],
|
||||
dont[],
|
||||
will[],
|
||||
wont[],
|
||||
options[], /* All the little options */
|
||||
*hostname; /* Who are we connected to? */
|
||||
#ifdef ENCRYPTION
|
||||
extern void (*encrypt_output)(unsigned char *, int);
|
||||
extern int (*decrypt_input)(int);
|
||||
#endif /* ENCRYPTION */
|
||||
|
||||
/*
|
||||
* We keep track of each side of the option negotiation.
|
||||
*/
|
||||
|
||||
#define MY_STATE_WILL 0x01
|
||||
#define MY_WANT_STATE_WILL 0x02
|
||||
#define MY_STATE_DO 0x04
|
||||
#define MY_WANT_STATE_DO 0x08
|
||||
|
||||
/*
|
||||
* Macros to check the current state of things
|
||||
*/
|
||||
|
||||
#define my_state_is_do(opt) (options[opt]&MY_STATE_DO)
|
||||
#define my_state_is_will(opt) (options[opt]&MY_STATE_WILL)
|
||||
#define my_want_state_is_do(opt) (options[opt]&MY_WANT_STATE_DO)
|
||||
#define my_want_state_is_will(opt) (options[opt]&MY_WANT_STATE_WILL)
|
||||
|
||||
#define my_state_is_dont(opt) (!my_state_is_do(opt))
|
||||
#define my_state_is_wont(opt) (!my_state_is_will(opt))
|
||||
#define my_want_state_is_dont(opt) (!my_want_state_is_do(opt))
|
||||
#define my_want_state_is_wont(opt) (!my_want_state_is_will(opt))
|
||||
|
||||
#define set_my_state_do(opt) {options[opt] |= MY_STATE_DO;}
|
||||
#define set_my_state_will(opt) {options[opt] |= MY_STATE_WILL;}
|
||||
#define set_my_want_state_do(opt) {options[opt] |= MY_WANT_STATE_DO;}
|
||||
#define set_my_want_state_will(opt) {options[opt] |= MY_WANT_STATE_WILL;}
|
||||
|
||||
#define set_my_state_dont(opt) {options[opt] &= ~MY_STATE_DO;}
|
||||
#define set_my_state_wont(opt) {options[opt] &= ~MY_STATE_WILL;}
|
||||
#define set_my_want_state_dont(opt) {options[opt] &= ~MY_WANT_STATE_DO;}
|
||||
#define set_my_want_state_wont(opt) {options[opt] &= ~MY_WANT_STATE_WILL;}
|
||||
|
||||
/*
|
||||
* Make everything symetrical
|
||||
*/
|
||||
|
||||
#define HIS_STATE_WILL MY_STATE_DO
|
||||
#define HIS_WANT_STATE_WILL MY_WANT_STATE_DO
|
||||
#define HIS_STATE_DO MY_STATE_WILL
|
||||
#define HIS_WANT_STATE_DO MY_WANT_STATE_WILL
|
||||
|
||||
#define his_state_is_do my_state_is_will
|
||||
#define his_state_is_will my_state_is_do
|
||||
#define his_want_state_is_do my_want_state_is_will
|
||||
#define his_want_state_is_will my_want_state_is_do
|
||||
|
||||
#define his_state_is_dont my_state_is_wont
|
||||
#define his_state_is_wont my_state_is_dont
|
||||
#define his_want_state_is_dont my_want_state_is_wont
|
||||
#define his_want_state_is_wont my_want_state_is_dont
|
||||
|
||||
#define set_his_state_do set_my_state_will
|
||||
#define set_his_state_will set_my_state_do
|
||||
#define set_his_want_state_do set_my_want_state_will
|
||||
#define set_his_want_state_will set_my_want_state_do
|
||||
|
||||
#define set_his_state_dont set_my_state_wont
|
||||
#define set_his_state_wont set_my_state_dont
|
||||
#define set_his_want_state_dont set_my_want_state_wont
|
||||
#define set_his_want_state_wont set_my_want_state_dont
|
||||
|
||||
#if defined(USE_TERMIO)
|
||||
#define SIG_FUNC_RET void
|
||||
#else
|
||||
#define SIG_FUNC_RET int
|
||||
#endif
|
||||
|
||||
#ifdef SIGINFO
|
||||
extern SIG_FUNC_RET
|
||||
ayt_status(void);
|
||||
#endif
|
||||
|
||||
extern FILE
|
||||
*NetTrace; /* Where debugging output goes */
|
||||
extern unsigned char
|
||||
NetTraceFile[]; /* Name of file where debugging output goes */
|
||||
extern void
|
||||
SetNetTrace(char *); /* Function to change where debugging goes */
|
||||
|
||||
extern jmp_buf
|
||||
peerdied,
|
||||
toplevel; /* For error conditions. */
|
||||
|
||||
extern void
|
||||
command(int, const char *, int),
|
||||
Dump(char, unsigned char *, int),
|
||||
env_init(void),
|
||||
Exit(int),
|
||||
ExitString(const char *, int),
|
||||
init_network(void),
|
||||
init_sys(void),
|
||||
init_telnet(void),
|
||||
init_terminal(void),
|
||||
intp(void),
|
||||
optionstatus(void),
|
||||
printoption(const char *, int, int),
|
||||
printsub(char, unsigned char *, int),
|
||||
quit(void),
|
||||
sendabort(void),
|
||||
sendbrk(void),
|
||||
sendeof(void),
|
||||
sendsusp(void),
|
||||
sendnaws(void),
|
||||
sendayt(void),
|
||||
setconnmode(int),
|
||||
setcommandmode(void),
|
||||
set_escape_char(char *s),
|
||||
setneturg(void),
|
||||
sys_telnet_init(void),
|
||||
telnet(char *),
|
||||
tel_enter_binary(int),
|
||||
tel_leave_binary(int),
|
||||
TerminalFlushOutput(void),
|
||||
TerminalNewMode(int),
|
||||
TerminalRestoreState(void),
|
||||
TerminalSaveState(void),
|
||||
TerminalDefaultChars(void),
|
||||
TerminalSpeeds(long *, long *),
|
||||
tninit(void),
|
||||
upcase(char *),
|
||||
willoption(int),
|
||||
wontoption(int);
|
||||
|
||||
extern void
|
||||
send_do(int, int),
|
||||
send_dont(int, int),
|
||||
send_will(int, int),
|
||||
send_wont(int, int);
|
||||
|
||||
extern void
|
||||
lm_will(unsigned char *, int),
|
||||
lm_wont(unsigned char *, int),
|
||||
lm_do(unsigned char *, int),
|
||||
lm_dont(unsigned char *, int),
|
||||
lm_mode(unsigned char *, int, int);
|
||||
|
||||
extern void
|
||||
slc_init(void),
|
||||
slcstate(void),
|
||||
slc_mode_export(void),
|
||||
slc_mode_import(int),
|
||||
slc_import(int),
|
||||
slc_export(void),
|
||||
slc(unsigned char *, int),
|
||||
slc_check(void),
|
||||
slc_start_reply(void),
|
||||
slc_add_reply(unsigned char, unsigned char, cc_t),
|
||||
slc_end_reply(void);
|
||||
extern int
|
||||
getconnmode(void),
|
||||
opt_welldefined(const char *),
|
||||
NetClose(int),
|
||||
netflush(void),
|
||||
process_rings(int, int, int, int, int, int),
|
||||
rlogin_susp(void),
|
||||
SetSockOpt(int, int, int, int),
|
||||
slc_update(void),
|
||||
stilloob(void),
|
||||
telrcv(void),
|
||||
TerminalRead(char *, int),
|
||||
TerminalWrite(char *, int),
|
||||
TerminalAutoFlush(void),
|
||||
TerminalWindowSize(long *, long *),
|
||||
TerminalSpecialChars(int),
|
||||
tn(int, char **),
|
||||
ttyflush(int);
|
||||
|
||||
extern void
|
||||
env_opt(unsigned char *, int),
|
||||
env_opt_start(void),
|
||||
env_opt_start_info(void),
|
||||
env_opt_add(unsigned char *),
|
||||
env_opt_end(int);
|
||||
|
||||
extern unsigned char
|
||||
*env_default(int, int),
|
||||
*env_getvalue(const unsigned char *);
|
||||
|
||||
extern int
|
||||
get_status(char *),
|
||||
dosynch(char *);
|
||||
|
||||
extern cc_t
|
||||
*tcval(int);
|
||||
|
||||
#ifndef USE_TERMIO
|
||||
|
||||
extern struct tchars ntc;
|
||||
extern struct ltchars nltc;
|
||||
extern struct sgttyb nttyb;
|
||||
|
||||
# define termEofChar ntc.t_eofc
|
||||
# define termEraseChar nttyb.sg_erase
|
||||
# define termFlushChar nltc.t_flushc
|
||||
# define termIntChar ntc.t_intrc
|
||||
# define termKillChar nttyb.sg_kill
|
||||
# define termLiteralNextChar nltc.t_lnextc
|
||||
# define termQuitChar ntc.t_quitc
|
||||
# define termSuspChar nltc.t_suspc
|
||||
# define termRprntChar nltc.t_rprntc
|
||||
# define termWerasChar nltc.t_werasc
|
||||
# define termStartChar ntc.t_startc
|
||||
# define termStopChar ntc.t_stopc
|
||||
# define termForw1Char ntc.t_brkc
|
||||
extern cc_t termForw2Char;
|
||||
extern cc_t termAytChar;
|
||||
|
||||
# define termEofCharp (cc_t *)&ntc.t_eofc
|
||||
# define termEraseCharp (cc_t *)&nttyb.sg_erase
|
||||
# define termFlushCharp (cc_t *)&nltc.t_flushc
|
||||
# define termIntCharp (cc_t *)&ntc.t_intrc
|
||||
# define termKillCharp (cc_t *)&nttyb.sg_kill
|
||||
# define termLiteralNextCharp (cc_t *)&nltc.t_lnextc
|
||||
# define termQuitCharp (cc_t *)&ntc.t_quitc
|
||||
# define termSuspCharp (cc_t *)&nltc.t_suspc
|
||||
# define termRprntCharp (cc_t *)&nltc.t_rprntc
|
||||
# define termWerasCharp (cc_t *)&nltc.t_werasc
|
||||
# define termStartCharp (cc_t *)&ntc.t_startc
|
||||
# define termStopCharp (cc_t *)&ntc.t_stopc
|
||||
# define termForw1Charp (cc_t *)&ntc.t_brkc
|
||||
# define termForw2Charp (cc_t *)&termForw2Char
|
||||
# define termAytCharp (cc_t *)&termAytChar
|
||||
|
||||
# else
|
||||
|
||||
extern struct termio new_tc;
|
||||
|
||||
# define termEofChar new_tc.c_cc[VEOF]
|
||||
# define termEraseChar new_tc.c_cc[VERASE]
|
||||
# define termIntChar new_tc.c_cc[VINTR]
|
||||
# define termKillChar new_tc.c_cc[VKILL]
|
||||
# define termQuitChar new_tc.c_cc[VQUIT]
|
||||
|
||||
# ifndef VSUSP
|
||||
extern cc_t termSuspChar;
|
||||
# else
|
||||
# define termSuspChar new_tc.c_cc[VSUSP]
|
||||
# endif
|
||||
# if defined(VFLUSHO) && !defined(VDISCARD)
|
||||
# define VDISCARD VFLUSHO
|
||||
# endif
|
||||
# ifndef VDISCARD
|
||||
extern cc_t termFlushChar;
|
||||
# else
|
||||
# define termFlushChar new_tc.c_cc[VDISCARD]
|
||||
# endif
|
||||
# ifndef VWERASE
|
||||
extern cc_t termWerasChar;
|
||||
# else
|
||||
# define termWerasChar new_tc.c_cc[VWERASE]
|
||||
# endif
|
||||
# ifndef VREPRINT
|
||||
extern cc_t termRprntChar;
|
||||
# else
|
||||
# define termRprntChar new_tc.c_cc[VREPRINT]
|
||||
# endif
|
||||
# ifndef VLNEXT
|
||||
extern cc_t termLiteralNextChar;
|
||||
# else
|
||||
# define termLiteralNextChar new_tc.c_cc[VLNEXT]
|
||||
# endif
|
||||
# ifndef VSTART
|
||||
extern cc_t termStartChar;
|
||||
# else
|
||||
# define termStartChar new_tc.c_cc[VSTART]
|
||||
# endif
|
||||
# ifndef VSTOP
|
||||
extern cc_t termStopChar;
|
||||
# else
|
||||
# define termStopChar new_tc.c_cc[VSTOP]
|
||||
# endif
|
||||
# ifndef VEOL
|
||||
extern cc_t termForw1Char;
|
||||
# else
|
||||
# define termForw1Char new_tc.c_cc[VEOL]
|
||||
# endif
|
||||
# ifndef VEOL2
|
||||
extern cc_t termForw2Char;
|
||||
# else
|
||||
# define termForw2Char new_tc.c_cc[VEOL]
|
||||
# endif
|
||||
# ifndef VSTATUS
|
||||
extern cc_t termAytChar;
|
||||
#else
|
||||
# define termAytChar new_tc.c_cc[VSTATUS]
|
||||
#endif
|
||||
|
||||
# if defined(__STDC__)
|
||||
# define termEofCharp &termEofChar
|
||||
# define termEraseCharp &termEraseChar
|
||||
# define termIntCharp &termIntChar
|
||||
# define termKillCharp &termKillChar
|
||||
# define termQuitCharp &termQuitChar
|
||||
# define termSuspCharp &termSuspChar
|
||||
# define termFlushCharp &termFlushChar
|
||||
# define termWerasCharp &termWerasChar
|
||||
# define termRprntCharp &termRprntChar
|
||||
# define termLiteralNextCharp &termLiteralNextChar
|
||||
# define termStartCharp &termStartChar
|
||||
# define termStopCharp &termStopChar
|
||||
# define termForw1Charp &termForw1Char
|
||||
# define termForw2Charp &termForw2Char
|
||||
# define termAytCharp &termAytChar
|
||||
# else
|
||||
/* Work around a compiler bug */
|
||||
# define termEofCharp 0
|
||||
# define termEraseCharp 0
|
||||
# define termIntCharp 0
|
||||
# define termKillCharp 0
|
||||
# define termQuitCharp 0
|
||||
# define termSuspCharp 0
|
||||
# define termFlushCharp 0
|
||||
# define termWerasCharp 0
|
||||
# define termRprntCharp 0
|
||||
# define termLiteralNextCharp 0
|
||||
# define termStartCharp 0
|
||||
# define termStopCharp 0
|
||||
# define termForw1Charp 0
|
||||
# define termForw2Charp 0
|
||||
# define termAytCharp 0
|
||||
# endif
|
||||
#endif
|
||||
|
||||
|
||||
/* Ring buffer structures which are shared */
|
||||
|
||||
extern Ring
|
||||
netoring,
|
||||
netiring,
|
||||
ttyoring,
|
||||
ttyiring;
|
||||
|
||||
extern void
|
||||
xmitAO(void),
|
||||
xmitEC(void),
|
||||
xmitEL(void);
|
||||
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)fdset.h 8.1 (Berkeley) 6/6/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* The following is defined just in case someone should want to run
|
||||
* this telnet on a 4.2 system.
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef FD_SETSIZE
|
||||
|
||||
#define FD_SET(n, p) ((p)->fds_bits[0] |= (1<<(n)))
|
||||
#define FD_CLR(n, p) ((p)->fds_bits[0] &= ~(1<<(n)))
|
||||
#define FD_ISSET(n, p) ((p)->fds_bits[0] & (1<<(n)))
|
||||
#define FD_ZERO(p) ((p)->fds_bits[0] = 0)
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,45 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)general.h 8.1 (Berkeley) 6/6/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* Some general definitions.
|
||||
*/
|
||||
|
||||
|
||||
#define numberof(x) (sizeof x/sizeof x[0])
|
||||
#define highestof(x) (numberof(x)-1)
|
||||
|
||||
#define ClearElement(x) memset((char *)&x, 0, sizeof x)
|
||||
#define ClearArray(x) memset((char *)x, 0, sizeof x)
|
||||
@@ -0,0 +1,386 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1990, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#if 0
|
||||
#ifndef lint
|
||||
static const char sccsid[] = "@(#)main.c 8.3 (Berkeley) 5/30/95";
|
||||
#endif
|
||||
#endif
|
||||
#include <sys/cdefs.h>
|
||||
__FBSDID("$FreeBSD: src/contrib/telnet/telnet/main.c,v 1.20 2005/01/09 10:24:45 maxim Exp $");
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/socket.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include "ring.h"
|
||||
#include "externs.h"
|
||||
#include "defines.h"
|
||||
|
||||
#ifdef AUTHENTICATION
|
||||
#include <libtelnet/auth.h>
|
||||
#endif
|
||||
#ifdef ENCRYPTION
|
||||
#include <libtelnet/encrypt.h>
|
||||
#endif
|
||||
|
||||
/* These values need to be the same as defined in libtelnet/kerberos5.c */
|
||||
/* Either define them in both places, or put in some common header file. */
|
||||
#define OPTS_FORWARD_CREDS 0x00000002
|
||||
#define OPTS_FORWARDABLE_CREDS 0x00000001
|
||||
|
||||
#if defined(IPSEC) && defined(IPSEC_POLICY_IPSEC)
|
||||
char *ipsec_policy_in = NULL;
|
||||
char *ipsec_policy_out = NULL;
|
||||
#endif
|
||||
|
||||
extern int tos;
|
||||
|
||||
int family = AF_UNSPEC;
|
||||
|
||||
/*
|
||||
* Initialize variables.
|
||||
*/
|
||||
void
|
||||
tninit(void)
|
||||
{
|
||||
init_terminal();
|
||||
|
||||
init_network();
|
||||
|
||||
init_telnet();
|
||||
|
||||
init_sys();
|
||||
}
|
||||
|
||||
static void
|
||||
usage(void)
|
||||
{
|
||||
fprintf(stderr, "usage: %s %s%s%s%s\n",
|
||||
prompt,
|
||||
#ifdef AUTHENTICATION
|
||||
"[-4] [-6] [-8] [-E] [-K] [-L] [-N] [-S tos] [-X atype] [-c] [-d]",
|
||||
"\n\t[-e char] [-k realm] [-l user] [-f/-F] [-n tracefile] ",
|
||||
#else
|
||||
"[-4] [-6] [-8] [-E] [-L] [-N] [-S tos] [-c] [-d]",
|
||||
"\n\t[-e char] [-l user] [-n tracefile] ",
|
||||
#endif
|
||||
"[-r] [-s src_addr] [-u] ",
|
||||
#if defined(IPSEC) && defined(IPSEC_POLICY_IPSEC)
|
||||
"[-P policy] "
|
||||
#endif
|
||||
#ifdef ENCRYPTION
|
||||
"[-y] [host-name [port]]"
|
||||
#else /* ENCRYPTION */
|
||||
"[host-name [port]]"
|
||||
#endif /* ENCRYPTION */
|
||||
);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
/*
|
||||
* main. Parse arguments, invoke the protocol or command parser.
|
||||
*/
|
||||
|
||||
int
|
||||
main(int argc, char *argv[])
|
||||
{
|
||||
int ch;
|
||||
#ifndef __BEOS__
|
||||
char *ep;
|
||||
u_long ultmp;
|
||||
#endif
|
||||
char *user;
|
||||
char *src_addr = NULL;
|
||||
#ifdef FORWARD
|
||||
extern int forward_flags;
|
||||
#endif /* FORWARD */
|
||||
|
||||
tninit(); /* Clear out things */
|
||||
|
||||
TerminalSaveState();
|
||||
|
||||
if ((prompt = strrchr(argv[0], '/')))
|
||||
++prompt;
|
||||
else
|
||||
prompt = argv[0];
|
||||
|
||||
user = NULL;
|
||||
|
||||
rlogin = (strncmp(prompt, "rlog", 4) == 0) ? '~' : _POSIX_VDISABLE;
|
||||
#ifdef AUTHENTICATION
|
||||
autologin = 1;
|
||||
#else
|
||||
autologin = -1;
|
||||
#endif
|
||||
|
||||
#ifdef ENCRYPTION
|
||||
encrypt_auto(1);
|
||||
decrypt_auto(1);
|
||||
#endif
|
||||
|
||||
#if defined(IPSEC) && defined(IPSEC_POLICY_IPSEC)
|
||||
#define IPSECOPT "P:"
|
||||
#else
|
||||
#define IPSECOPT
|
||||
#endif
|
||||
while ((ch = getopt(argc, argv,
|
||||
"468EKLNS:X:acde:fFk:l:n:rs:uxy" IPSECOPT)) != -1)
|
||||
#undef IPSECOPT
|
||||
{
|
||||
switch(ch) {
|
||||
case '4':
|
||||
family = AF_INET;
|
||||
break;
|
||||
#ifdef INET6
|
||||
case '6':
|
||||
family = AF_INET6;
|
||||
break;
|
||||
#endif
|
||||
case '8':
|
||||
eight = 3; /* binary output and input */
|
||||
break;
|
||||
case 'E':
|
||||
rlogin = escape = _POSIX_VDISABLE;
|
||||
break;
|
||||
case 'K':
|
||||
#ifdef AUTHENTICATION
|
||||
autologin = 0;
|
||||
#endif
|
||||
break;
|
||||
case 'L':
|
||||
eight |= 2; /* binary output only */
|
||||
break;
|
||||
case 'N':
|
||||
doaddrlookup = 0;
|
||||
break;
|
||||
case 'S':
|
||||
#ifdef __BEOS__
|
||||
fprintf(stderr, "-S option is not supported\n");
|
||||
#else
|
||||
# ifdef HAS_GETTOS
|
||||
|
||||
if ((tos = parsetos(optarg, "tcp")) < 0)
|
||||
fprintf(stderr, "%s%s%s%s\n",
|
||||
prompt, ": Bad TOS argument '",
|
||||
optarg,
|
||||
"; will try to use default TOS");
|
||||
# else
|
||||
# define MAXTOS 255
|
||||
ultmp = strtoul(optarg, &ep, 0);
|
||||
if (*ep || ep == optarg || ultmp > MAXTOS)
|
||||
fprintf(stderr, "%s%s%s%s\n",
|
||||
prompt, ": Bad TOS argument '",
|
||||
optarg,
|
||||
"; will try to use default TOS");
|
||||
else
|
||||
tos = ultmp;
|
||||
# endif
|
||||
#endif /* __BEOS__ */
|
||||
break;
|
||||
case 'X':
|
||||
#ifdef AUTHENTICATION
|
||||
auth_disable_name(optarg);
|
||||
#endif
|
||||
break;
|
||||
case 'a':
|
||||
#ifdef AUTHENTICATION
|
||||
/* It's the default now, so ignore */
|
||||
#else
|
||||
autologin = 1;
|
||||
#endif
|
||||
break;
|
||||
case 'c':
|
||||
skiprc = 1;
|
||||
break;
|
||||
case 'd':
|
||||
telnet_debug = 1;
|
||||
break;
|
||||
case 'e':
|
||||
set_escape_char(optarg);
|
||||
break;
|
||||
case 'f':
|
||||
#ifdef AUTHENTICATION
|
||||
#if defined(KRB5) && defined(FORWARD)
|
||||
if (forward_flags & OPTS_FORWARD_CREDS) {
|
||||
fprintf(stderr,
|
||||
"%s: Only one of -f and -F allowed.\n",
|
||||
prompt);
|
||||
usage();
|
||||
}
|
||||
forward_flags |= OPTS_FORWARD_CREDS;
|
||||
#else
|
||||
fprintf(stderr,
|
||||
"%s: Warning: -f ignored, no Kerberos V5 support.\n",
|
||||
prompt);
|
||||
#endif
|
||||
#else
|
||||
fprintf(stderr,
|
||||
"%s: Warning: -f ignored, no Kerberos V5 support.\n",
|
||||
prompt);
|
||||
#endif
|
||||
break;
|
||||
case 'F':
|
||||
#ifdef AUTHENTICATION
|
||||
#if defined(KRB5) && defined(FORWARD)
|
||||
if (forward_flags & OPTS_FORWARD_CREDS) {
|
||||
fprintf(stderr,
|
||||
"%s: Only one of -f and -F allowed.\n",
|
||||
prompt);
|
||||
usage();
|
||||
}
|
||||
forward_flags |= OPTS_FORWARD_CREDS;
|
||||
forward_flags |= OPTS_FORWARDABLE_CREDS;
|
||||
#else
|
||||
fprintf(stderr,
|
||||
"%s: Warning: -F ignored, no Kerberos V5 support.\n",
|
||||
prompt);
|
||||
#endif
|
||||
#else
|
||||
fprintf(stderr,
|
||||
"%s: Warning: -F ignored, no Kerberos V5 support.\n",
|
||||
prompt);
|
||||
#endif
|
||||
break;
|
||||
case 'k':
|
||||
#ifdef AUTHENTICATION
|
||||
#if defined(KRB4)
|
||||
{
|
||||
extern char *dest_realm, dst_realm_buf[], dst_realm_sz;
|
||||
dest_realm = dst_realm_buf;
|
||||
(void)strncpy(dest_realm, optarg, dst_realm_sz);
|
||||
}
|
||||
#else
|
||||
fprintf(stderr,
|
||||
"%s: Warning: -k ignored, no Kerberos V4 support.\n",
|
||||
prompt);
|
||||
#endif
|
||||
#else
|
||||
fprintf(stderr,
|
||||
"%s: Warning: -k ignored, no Kerberos V4 support.\n",
|
||||
prompt);
|
||||
#endif
|
||||
break;
|
||||
case 'l':
|
||||
#ifdef AUTHENTICATION
|
||||
/* This is the default now, so ignore it */
|
||||
#else
|
||||
autologin = 1;
|
||||
#endif
|
||||
user = optarg;
|
||||
break;
|
||||
case 'n':
|
||||
SetNetTrace(optarg);
|
||||
break;
|
||||
case 'r':
|
||||
rlogin = '~';
|
||||
break;
|
||||
case 's':
|
||||
src_addr = optarg;
|
||||
break;
|
||||
case 'u':
|
||||
family = AF_UNIX;
|
||||
break;
|
||||
case 'x':
|
||||
#ifndef ENCRYPTION
|
||||
fprintf(stderr,
|
||||
"%s: Warning: -x ignored, no ENCRYPT support.\n",
|
||||
prompt);
|
||||
#endif /* ENCRYPTION */
|
||||
break;
|
||||
case 'y':
|
||||
#ifdef ENCRYPTION
|
||||
encrypt_auto(0);
|
||||
decrypt_auto(0);
|
||||
#else
|
||||
fprintf(stderr,
|
||||
"%s: Warning: -y ignored, no ENCRYPT support.\n",
|
||||
prompt);
|
||||
#endif /* ENCRYPTION */
|
||||
break;
|
||||
#if defined(IPSEC) && defined(IPSEC_POLICY_IPSEC)
|
||||
case 'P':
|
||||
if (!strncmp("in", optarg, 2))
|
||||
ipsec_policy_in = strdup(optarg);
|
||||
else if (!strncmp("out", optarg, 3))
|
||||
ipsec_policy_out = strdup(optarg);
|
||||
else
|
||||
usage();
|
||||
break;
|
||||
#endif
|
||||
case '?':
|
||||
default:
|
||||
usage();
|
||||
/* NOTREACHED */
|
||||
}
|
||||
}
|
||||
if (autologin == -1)
|
||||
autologin = (rlogin == _POSIX_VDISABLE) ? 0 : 1;
|
||||
|
||||
argc -= optind;
|
||||
argv += optind;
|
||||
|
||||
if (argc) {
|
||||
char *args[9], **argp = args;
|
||||
|
||||
if (argc > 2)
|
||||
usage();
|
||||
*argp++ = prompt;
|
||||
if (user) {
|
||||
*argp++ = strdup("-l");
|
||||
*argp++ = user;
|
||||
}
|
||||
if (src_addr) {
|
||||
*argp++ = strdup("-s");
|
||||
*argp++ = src_addr;
|
||||
}
|
||||
*argp++ = argv[0]; /* host */
|
||||
if (argc > 1)
|
||||
*argp++ = argv[1]; /* port */
|
||||
*argp = 0;
|
||||
|
||||
if (setjmp(toplevel) != 0)
|
||||
Exit(0);
|
||||
if (tn(argp - args, args) == 1)
|
||||
return (0);
|
||||
else
|
||||
return (1);
|
||||
}
|
||||
(void)setjmp(toplevel);
|
||||
for (;;) {
|
||||
command(1, 0, 0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,182 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#if 0
|
||||
#ifndef lint
|
||||
static const char sccsid[] = "@(#)network.c 8.2 (Berkeley) 12/15/93";
|
||||
#endif
|
||||
#endif
|
||||
#include <sys/cdefs.h>
|
||||
__FBSDID("$FreeBSD: src/contrib/telnet/telnet/network.c,v 1.7 2003/05/04 02:54:48 obrien Exp $");
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include <arpa/telnet.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include "ring.h"
|
||||
|
||||
#include "defines.h"
|
||||
#include "externs.h"
|
||||
#include "fdset.h"
|
||||
|
||||
Ring netoring, netiring;
|
||||
unsigned char netobuf[2*BUFSIZ], netibuf[BUFSIZ];
|
||||
|
||||
/*
|
||||
* Initialize internal network data structures.
|
||||
*/
|
||||
|
||||
void
|
||||
init_network(void)
|
||||
{
|
||||
if (ring_init(&netoring, netobuf, sizeof netobuf) != 1) {
|
||||
exit(1);
|
||||
}
|
||||
if (ring_init(&netiring, netibuf, sizeof netibuf) != 1) {
|
||||
exit(1);
|
||||
}
|
||||
NetTrace = stdout;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Check to see if any out-of-band data exists on a socket (for
|
||||
* Telnet "synch" processing).
|
||||
*/
|
||||
|
||||
int
|
||||
stilloob(void)
|
||||
{
|
||||
static struct timeval timeout = { 0, 0 };
|
||||
fd_set excepts;
|
||||
int value;
|
||||
|
||||
do {
|
||||
FD_ZERO(&excepts);
|
||||
FD_SET(net, &excepts);
|
||||
value = select(net+1, (fd_set *)0, (fd_set *)0, &excepts, &timeout);
|
||||
} while ((value == -1) && (errno == EINTR));
|
||||
|
||||
if (value < 0) {
|
||||
perror("select");
|
||||
(void) quit();
|
||||
/* NOTREACHED */
|
||||
}
|
||||
if (FD_ISSET(net, &excepts)) {
|
||||
return 1;
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* setneturg()
|
||||
*
|
||||
* Sets "neturg" to the current location.
|
||||
*/
|
||||
|
||||
void
|
||||
setneturg(void)
|
||||
{
|
||||
ring_mark(&netoring);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* netflush
|
||||
* Send as much data as possible to the network,
|
||||
* handling requests for urgent data.
|
||||
*
|
||||
* The return value indicates whether we did any
|
||||
* useful work.
|
||||
*/
|
||||
|
||||
int
|
||||
netflush(void)
|
||||
{
|
||||
int n, n1;
|
||||
|
||||
#ifdef ENCRYPTION
|
||||
if (encrypt_output)
|
||||
ring_encrypt(&netoring, encrypt_output);
|
||||
#endif /* ENCRYPTION */
|
||||
if ((n1 = n = ring_full_consecutive(&netoring)) > 0) {
|
||||
if (!ring_at_mark(&netoring)) {
|
||||
n = send(net, (char *)netoring.consume, n, 0); /* normal write */
|
||||
} else {
|
||||
/*
|
||||
* In 4.2 (and 4.3) systems, there is some question about
|
||||
* what byte in a sendOOB operation is the "OOB" data.
|
||||
* To make ourselves compatible, we only send ONE byte
|
||||
* out of band, the one WE THINK should be OOB (though
|
||||
* we really have more the TCP philosophy of urgent data
|
||||
* rather than the Unix philosophy of OOB data).
|
||||
*/
|
||||
n = send(net, (char *)netoring.consume, 1, MSG_OOB);/* URGENT data */
|
||||
}
|
||||
}
|
||||
if (n < 0) {
|
||||
if (errno != ENOBUFS && errno != EWOULDBLOCK) {
|
||||
setcommandmode();
|
||||
perror(hostname);
|
||||
(void)NetClose(net);
|
||||
ring_clear_mark(&netoring);
|
||||
longjmp(peerdied, -1);
|
||||
/*NOTREACHED*/
|
||||
}
|
||||
n = 0;
|
||||
}
|
||||
if (netdata && n) {
|
||||
Dump('>', netoring.consume, n);
|
||||
}
|
||||
if (n) {
|
||||
ring_consumed(&netoring, n);
|
||||
/*
|
||||
* If we sent all, and more to send, then recurse to pick
|
||||
* up the other half.
|
||||
*/
|
||||
if ((n1 == n) && ring_full_consecutive(&netoring)) {
|
||||
(void) netflush();
|
||||
}
|
||||
return 1;
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,322 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#if 0
|
||||
#ifndef lint
|
||||
static const char sccsid[] = "@(#)ring.c 8.2 (Berkeley) 5/30/95";
|
||||
#endif
|
||||
#endif
|
||||
#include <sys/cdefs.h>
|
||||
__FBSDID("$FreeBSD: src/contrib/telnet/telnet/ring.c,v 1.7 2003/05/04 02:54:48 obrien Exp $");
|
||||
|
||||
/*
|
||||
* This defines a structure for a ring buffer.
|
||||
*
|
||||
* The circular buffer has two parts:
|
||||
*(((
|
||||
* full: [consume, supply)
|
||||
* empty: [supply, consume)
|
||||
*]]]
|
||||
*
|
||||
*/
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#ifdef size_t
|
||||
#undef size_t
|
||||
#endif
|
||||
|
||||
#include <sys/types.h>
|
||||
#ifndef FILIO_H
|
||||
#include <sys/ioctl.h>
|
||||
#endif
|
||||
#include <sys/socket.h>
|
||||
|
||||
#include "ring.h"
|
||||
#include "general.h"
|
||||
|
||||
/* Internal macros */
|
||||
|
||||
#if !defined(MIN)
|
||||
#define MIN(a,b) (((a)<(b))? (a):(b))
|
||||
#endif /* !defined(MIN) */
|
||||
|
||||
#define ring_subtract(d,a,b) (((a)-(b) >= 0)? \
|
||||
(a)-(b): (((a)-(b))+(d)->size))
|
||||
|
||||
#define ring_increment(d,a,c) (((a)+(c) < (d)->top)? \
|
||||
(a)+(c) : (((a)+(c))-(d)->size))
|
||||
|
||||
#define ring_decrement(d,a,c) (((a)-(c) >= (d)->bottom)? \
|
||||
(a)-(c) : (((a)-(c))-(d)->size))
|
||||
|
||||
|
||||
/*
|
||||
* The following is a clock, used to determine full, empty, etc.
|
||||
*
|
||||
* There is some trickiness here. Since the ring buffers are initialized
|
||||
* to ZERO on allocation, we need to make sure, when interpreting the
|
||||
* clock, that when the times are EQUAL, then the buffer is FULL.
|
||||
*/
|
||||
static u_long ring_clock = 0;
|
||||
|
||||
|
||||
#define ring_empty(d) (((d)->consume == (d)->supply) && \
|
||||
((d)->consumetime >= (d)->supplytime))
|
||||
#define ring_full(d) (((d)->supply == (d)->consume) && \
|
||||
((d)->supplytime > (d)->consumetime))
|
||||
|
||||
/* Buffer state transition routines */
|
||||
|
||||
int
|
||||
ring_init(Ring *ring, unsigned char *buffer, int count)
|
||||
{
|
||||
memset((char *)ring, 0, sizeof *ring);
|
||||
|
||||
ring->size = count;
|
||||
|
||||
ring->supply = ring->consume = ring->bottom = buffer;
|
||||
|
||||
ring->top = ring->bottom+ring->size;
|
||||
|
||||
#ifdef ENCRYPTION
|
||||
ring->clearto = 0;
|
||||
#endif /* ENCRYPTION */
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Mark routines */
|
||||
|
||||
/*
|
||||
* Mark the most recently supplied byte.
|
||||
*/
|
||||
|
||||
void
|
||||
ring_mark(Ring *ring)
|
||||
{
|
||||
ring->mark = ring_decrement(ring, ring->supply, 1);
|
||||
}
|
||||
|
||||
/*
|
||||
* Is the ring pointing to the mark?
|
||||
*/
|
||||
|
||||
int
|
||||
ring_at_mark(Ring *ring)
|
||||
{
|
||||
if (ring->mark == ring->consume) {
|
||||
return 1;
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Clear any mark set on the ring.
|
||||
*/
|
||||
|
||||
void
|
||||
ring_clear_mark(Ring *ring)
|
||||
{
|
||||
ring->mark = 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Add characters from current segment to ring buffer.
|
||||
*/
|
||||
void
|
||||
ring_supplied(Ring *ring, int count)
|
||||
{
|
||||
ring->supply = ring_increment(ring, ring->supply, count);
|
||||
ring->supplytime = ++ring_clock;
|
||||
}
|
||||
|
||||
/*
|
||||
* We have just consumed "c" bytes.
|
||||
*/
|
||||
void
|
||||
ring_consumed(Ring *ring, int count)
|
||||
{
|
||||
if (count == 0) /* don't update anything */
|
||||
return;
|
||||
|
||||
if (ring->mark &&
|
||||
(ring_subtract(ring, ring->mark, ring->consume) < count)) {
|
||||
ring->mark = 0;
|
||||
}
|
||||
#ifdef ENCRYPTION
|
||||
if (ring->consume < ring->clearto &&
|
||||
ring->clearto <= ring->consume + count)
|
||||
ring->clearto = 0;
|
||||
else if (ring->consume + count > ring->top &&
|
||||
ring->bottom <= ring->clearto &&
|
||||
ring->bottom + ((ring->consume + count) - ring->top))
|
||||
ring->clearto = 0;
|
||||
#endif /* ENCRYPTION */
|
||||
ring->consume = ring_increment(ring, ring->consume, count);
|
||||
ring->consumetime = ++ring_clock;
|
||||
/*
|
||||
* Try to encourage "ring_empty_consecutive()" to be large.
|
||||
*/
|
||||
if (ring_empty(ring)) {
|
||||
ring->consume = ring->supply = ring->bottom;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* Buffer state query routines */
|
||||
|
||||
|
||||
/* Number of bytes that may be supplied */
|
||||
int
|
||||
ring_empty_count(Ring *ring)
|
||||
{
|
||||
if (ring_empty(ring)) { /* if empty */
|
||||
return ring->size;
|
||||
} else {
|
||||
return ring_subtract(ring, ring->consume, ring->supply);
|
||||
}
|
||||
}
|
||||
|
||||
/* number of CONSECUTIVE bytes that may be supplied */
|
||||
int
|
||||
ring_empty_consecutive(Ring *ring)
|
||||
{
|
||||
if ((ring->consume < ring->supply) || ring_empty(ring)) {
|
||||
/*
|
||||
* if consume is "below" supply, or empty, then
|
||||
* return distance to the top
|
||||
*/
|
||||
return ring_subtract(ring, ring->top, ring->supply);
|
||||
} else {
|
||||
/*
|
||||
* else, return what we may.
|
||||
*/
|
||||
return ring_subtract(ring, ring->consume, ring->supply);
|
||||
}
|
||||
}
|
||||
|
||||
/* Return the number of bytes that are available for consuming
|
||||
* (but don't give more than enough to get to cross over set mark)
|
||||
*/
|
||||
|
||||
int
|
||||
ring_full_count(Ring *ring)
|
||||
{
|
||||
if ((ring->mark == 0) || (ring->mark == ring->consume)) {
|
||||
if (ring_full(ring)) {
|
||||
return ring->size; /* nothing consumed, but full */
|
||||
} else {
|
||||
return ring_subtract(ring, ring->supply, ring->consume);
|
||||
}
|
||||
} else {
|
||||
return ring_subtract(ring, ring->mark, ring->consume);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Return the number of CONSECUTIVE bytes available for consuming.
|
||||
* However, don't return more than enough to cross over set mark.
|
||||
*/
|
||||
int
|
||||
ring_full_consecutive(Ring *ring)
|
||||
{
|
||||
if ((ring->mark == 0) || (ring->mark == ring->consume)) {
|
||||
if ((ring->supply < ring->consume) || ring_full(ring)) {
|
||||
return ring_subtract(ring, ring->top, ring->consume);
|
||||
} else {
|
||||
return ring_subtract(ring, ring->supply, ring->consume);
|
||||
}
|
||||
} else {
|
||||
if (ring->mark < ring->consume) {
|
||||
return ring_subtract(ring, ring->top, ring->consume);
|
||||
} else { /* Else, distance to mark */
|
||||
return ring_subtract(ring, ring->mark, ring->consume);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Move data into the "supply" portion of of the ring buffer.
|
||||
*/
|
||||
void
|
||||
ring_supply_data(Ring *ring, unsigned char *buffer, int count)
|
||||
{
|
||||
int i;
|
||||
|
||||
while (count) {
|
||||
i = MIN(count, ring_empty_consecutive(ring));
|
||||
memcpy(ring->supply, buffer, i);
|
||||
ring_supplied(ring, i);
|
||||
count -= i;
|
||||
buffer += i;
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef ENCRYPTION
|
||||
void
|
||||
ring_encrypt(Ring *ring, void (*encryptor)(unsigned char *, int))
|
||||
{
|
||||
unsigned char *s, *c;
|
||||
|
||||
if (ring_empty(ring) || ring->clearto == ring->supply)
|
||||
return;
|
||||
|
||||
if (!(c = ring->clearto))
|
||||
c = ring->consume;
|
||||
|
||||
s = ring->supply;
|
||||
|
||||
if (s <= c) {
|
||||
(*encryptor)(c, ring->top - c);
|
||||
(*encryptor)(ring->bottom, s - ring->bottom);
|
||||
} else
|
||||
(*encryptor)(c, s - c);
|
||||
|
||||
ring->clearto = ring->supply;
|
||||
}
|
||||
|
||||
void
|
||||
ring_clearto(ring)
|
||||
Ring *ring;
|
||||
{
|
||||
if (!ring_empty(ring))
|
||||
ring->clearto = ring->supply;
|
||||
else
|
||||
ring->clearto = 0;
|
||||
}
|
||||
#endif /* ENCRYPTION */
|
||||
@@ -0,0 +1,107 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)ring.h 8.1 (Berkeley) 6/6/93
|
||||
* $FreeBSD: src/contrib/telnet/telnet/ring.h,v 1.4 2001/11/30 22:28:07 markm Exp $
|
||||
*/
|
||||
|
||||
#if defined(P)
|
||||
# undef P
|
||||
#endif
|
||||
|
||||
#if defined(__STDC__) || defined(LINT_ARGS)
|
||||
# define P(x) x
|
||||
#else
|
||||
# define P(x) ()
|
||||
#endif
|
||||
|
||||
/*
|
||||
* This defines a structure for a ring buffer.
|
||||
*
|
||||
* The circular buffer has two parts:
|
||||
*(((
|
||||
* full: [consume, supply)
|
||||
* empty: [supply, consume)
|
||||
*]]]
|
||||
*
|
||||
*/
|
||||
typedef struct {
|
||||
unsigned char *consume, /* where data comes out of */
|
||||
*supply, /* where data comes in to */
|
||||
*bottom, /* lowest address in buffer */
|
||||
*top, /* highest address+1 in buffer */
|
||||
*mark; /* marker (user defined) */
|
||||
#ifdef ENCRYPTION
|
||||
unsigned char *clearto; /* Data to this point is clear text */
|
||||
unsigned char *encryyptedto; /* Data is encrypted to here */
|
||||
#endif /* ENCRYPTION */
|
||||
int size; /* size in bytes of buffer */
|
||||
u_long consumetime, /* help us keep straight full, empty, etc. */
|
||||
supplytime;
|
||||
} Ring;
|
||||
|
||||
/* Here are some functions and macros to deal with the ring buffer */
|
||||
|
||||
/* Initialization routine */
|
||||
extern int
|
||||
ring_init(Ring *ring, unsigned char *buffer, int count);
|
||||
|
||||
/* Data movement routines */
|
||||
extern void
|
||||
ring_supply_data(Ring *ring, unsigned char *buffer, int count);
|
||||
#ifdef notdef
|
||||
extern void
|
||||
ring_consume_data(Ring *ring, unsigned char *buffer, int count);
|
||||
#endif
|
||||
|
||||
/* Buffer state transition routines */
|
||||
extern void
|
||||
ring_supplied(Ring *ring, int count),
|
||||
ring_consumed(Ring *ring, int count);
|
||||
|
||||
/* Buffer state query routines */
|
||||
extern int
|
||||
ring_at_mark(Ring *),
|
||||
ring_empty_count(Ring *ring),
|
||||
ring_empty_consecutive(Ring *ring),
|
||||
ring_full_count(Ring *ring),
|
||||
ring_full_consecutive(Ring *ring);
|
||||
|
||||
#ifdef ENCRYPTION
|
||||
extern void
|
||||
ring_encrypt(Ring *ring, void (*func)(unsigned char *, int)),
|
||||
ring_clearto(Ring *ring);
|
||||
#endif /* ENCRYPTION */
|
||||
|
||||
extern void
|
||||
ring_clear_mark(Ring *),
|
||||
ring_mark(Ring *);
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,242 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1990, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#if 0
|
||||
#ifndef lint
|
||||
static const char sccsid[] = "@(#)terminal.c 8.2 (Berkeley) 2/16/95";
|
||||
#endif
|
||||
#endif
|
||||
#include <sys/cdefs.h>
|
||||
__FBSDID("$FreeBSD: src/contrib/telnet/telnet/terminal.c,v 1.7 2003/05/04 02:54:48 obrien Exp $");
|
||||
|
||||
#include <arpa/telnet.h>
|
||||
#include <sys/types.h>
|
||||
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "ring.h"
|
||||
|
||||
#include "externs.h"
|
||||
#include "types.h"
|
||||
|
||||
#ifdef ENCRYPTION
|
||||
#include <libtelnet/encrypt.h>
|
||||
#endif
|
||||
|
||||
Ring ttyoring, ttyiring;
|
||||
unsigned char ttyobuf[2*BUFSIZ], ttyibuf[BUFSIZ];
|
||||
|
||||
int termdata; /* Debugging flag */
|
||||
|
||||
#ifdef USE_TERMIO
|
||||
# ifndef VDISCARD
|
||||
cc_t termFlushChar;
|
||||
# endif
|
||||
# ifndef VLNEXT
|
||||
cc_t termLiteralNextChar;
|
||||
# endif
|
||||
# ifndef VSUSP
|
||||
cc_t termSuspChar;
|
||||
# endif
|
||||
# ifndef VWERASE
|
||||
cc_t termWerasChar;
|
||||
# endif
|
||||
# ifndef VREPRINT
|
||||
cc_t termRprntChar;
|
||||
# endif
|
||||
# ifndef VSTART
|
||||
cc_t termStartChar;
|
||||
# endif
|
||||
# ifndef VSTOP
|
||||
cc_t termStopChar;
|
||||
# endif
|
||||
# ifndef VEOL
|
||||
cc_t termForw1Char;
|
||||
# endif
|
||||
# ifndef VEOL2
|
||||
cc_t termForw2Char;
|
||||
# endif
|
||||
# ifndef VSTATUS
|
||||
cc_t termAytChar;
|
||||
# endif
|
||||
#else
|
||||
cc_t termForw2Char;
|
||||
cc_t termAytChar;
|
||||
#endif
|
||||
|
||||
/*
|
||||
* initialize the terminal data structures.
|
||||
*/
|
||||
|
||||
void
|
||||
init_terminal(void)
|
||||
{
|
||||
if (ring_init(&ttyoring, ttyobuf, sizeof ttyobuf) != 1) {
|
||||
exit(1);
|
||||
}
|
||||
if (ring_init(&ttyiring, ttyibuf, sizeof ttyibuf) != 1) {
|
||||
exit(1);
|
||||
}
|
||||
autoflush = TerminalAutoFlush();
|
||||
}
|
||||
|
||||
/*
|
||||
* Send as much data as possible to the terminal.
|
||||
*
|
||||
* Return value:
|
||||
* -1: No useful work done, data waiting to go out.
|
||||
* 0: No data was waiting, so nothing was done.
|
||||
* 1: All waiting data was written out.
|
||||
* n: All data - n was written out.
|
||||
*/
|
||||
|
||||
int
|
||||
ttyflush(int drop)
|
||||
{
|
||||
int n, n0, n1;
|
||||
|
||||
n0 = ring_full_count(&ttyoring);
|
||||
if ((n1 = n = ring_full_consecutive(&ttyoring)) > 0) {
|
||||
if (drop) {
|
||||
TerminalFlushOutput();
|
||||
/* we leave 'n' alone! */
|
||||
} else {
|
||||
n = TerminalWrite(ttyoring.consume, n);
|
||||
}
|
||||
}
|
||||
if (n > 0) {
|
||||
if (termdata && n) {
|
||||
Dump('>', ttyoring.consume, n);
|
||||
}
|
||||
/*
|
||||
* If we wrote everything, and the full count is
|
||||
* larger than what we wrote, then write the
|
||||
* rest of the buffer.
|
||||
*/
|
||||
if (n1 == n && n0 > n) {
|
||||
n1 = n0 - n;
|
||||
if (!drop)
|
||||
n1 = TerminalWrite(ttyoring.bottom, n1);
|
||||
if (n1 > 0)
|
||||
n += n1;
|
||||
}
|
||||
ring_consumed(&ttyoring, n);
|
||||
}
|
||||
if (n < 0)
|
||||
return -1;
|
||||
if (n == n0) {
|
||||
if (n0)
|
||||
return -1;
|
||||
return 0;
|
||||
}
|
||||
return n0 - n + 1;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* These routines decides on what the mode should be (based on the values
|
||||
* of various global variables).
|
||||
*/
|
||||
|
||||
|
||||
int
|
||||
getconnmode(void)
|
||||
{
|
||||
extern int linemode;
|
||||
int mode = 0;
|
||||
#ifdef KLUDGELINEMODE
|
||||
extern int kludgelinemode;
|
||||
#endif
|
||||
|
||||
if (my_want_state_is_dont(TELOPT_ECHO))
|
||||
mode |= MODE_ECHO;
|
||||
|
||||
if (localflow)
|
||||
mode |= MODE_FLOW;
|
||||
|
||||
if (my_want_state_is_will(TELOPT_BINARY))
|
||||
mode |= MODE_INBIN;
|
||||
|
||||
if (his_want_state_is_will(TELOPT_BINARY))
|
||||
mode |= MODE_OUTBIN;
|
||||
|
||||
#ifdef KLUDGELINEMODE
|
||||
if (kludgelinemode) {
|
||||
if (my_want_state_is_dont(TELOPT_SGA)) {
|
||||
mode |= (MODE_TRAPSIG|MODE_EDIT);
|
||||
if (dontlecho && (clocks.echotoggle > clocks.modenegotiated)) {
|
||||
mode &= ~MODE_ECHO;
|
||||
}
|
||||
}
|
||||
return(mode);
|
||||
}
|
||||
#endif
|
||||
if (my_want_state_is_will(TELOPT_LINEMODE))
|
||||
mode |= linemode;
|
||||
return(mode);
|
||||
}
|
||||
|
||||
void
|
||||
setconnmode(int force)
|
||||
{
|
||||
#ifdef ENCRYPTION
|
||||
static int enc_passwd = 0;
|
||||
#endif /* ENCRYPTION */
|
||||
int newmode;
|
||||
|
||||
newmode = getconnmode()|(force?MODE_FORCE:0);
|
||||
|
||||
TerminalNewMode(newmode);
|
||||
|
||||
#ifdef ENCRYPTION
|
||||
if ((newmode & (MODE_ECHO|MODE_EDIT)) == MODE_EDIT) {
|
||||
if (my_want_state_is_will(TELOPT_ENCRYPT)
|
||||
&& (enc_passwd == 0) && !encrypt_output) {
|
||||
encrypt_request_start(0, 0);
|
||||
enc_passwd = 1;
|
||||
}
|
||||
} else {
|
||||
if (enc_passwd) {
|
||||
encrypt_request_end();
|
||||
enc_passwd = 0;
|
||||
}
|
||||
}
|
||||
#endif /* ENCRYPTION */
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
setcommandmode(void)
|
||||
{
|
||||
TerminalNewMode(-1);
|
||||
}
|
||||
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)types.h 8.1 (Berkeley) 6/6/93
|
||||
*/
|
||||
|
||||
typedef struct {
|
||||
char *modedescriptions;
|
||||
char modetype;
|
||||
} Modelist;
|
||||
|
||||
extern Modelist modelist[];
|
||||
|
||||
typedef struct {
|
||||
int
|
||||
system, /* what the current time is */
|
||||
echotoggle, /* last time user entered echo character */
|
||||
modenegotiated, /* last time operating mode negotiated */
|
||||
didnetreceive, /* last time we read data from network */
|
||||
gotDM; /* when did we last see a data mark */
|
||||
} Clocks;
|
||||
|
||||
extern Clocks clocks;
|
||||
@@ -0,0 +1,912 @@
|
||||
/*
|
||||
* Copyright (c) 1988, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#if 0
|
||||
#ifndef lint
|
||||
static const char sccsid[] = "@(#)utilities.c 8.3 (Berkeley) 5/30/95";
|
||||
#endif
|
||||
#endif
|
||||
#include <sys/cdefs.h>
|
||||
__FBSDID("$FreeBSD: src/contrib/telnet/telnet/utilities.c,v 1.8 2003/05/04 02:54:48 obrien Exp $");
|
||||
|
||||
#define TELOPTS
|
||||
#define TELCMDS
|
||||
#define SLC_NAMES
|
||||
#include <arpa/telnet.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/time.h>
|
||||
#include <ctype.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include "general.h"
|
||||
|
||||
#include "fdset.h"
|
||||
|
||||
#include "ring.h"
|
||||
|
||||
#include "defines.h"
|
||||
|
||||
#include "externs.h"
|
||||
|
||||
#ifdef AUTHENTICATION
|
||||
#include <libtelnet/auth.h>
|
||||
#endif
|
||||
#ifdef ENCRYPTION
|
||||
#include <libtelnet/encrypt.h>
|
||||
#endif
|
||||
|
||||
FILE *NetTrace = 0; /* Not in bss, since needs to stay */
|
||||
int prettydump;
|
||||
|
||||
/*
|
||||
* upcase()
|
||||
*
|
||||
* Upcase (in place) the argument.
|
||||
*/
|
||||
|
||||
void
|
||||
upcase(char *argument)
|
||||
{
|
||||
int c;
|
||||
|
||||
while ((c = *argument) != 0) {
|
||||
if (islower(c)) {
|
||||
*argument = toupper(c);
|
||||
}
|
||||
argument++;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* SetSockOpt()
|
||||
*
|
||||
* Compensate for differences in 4.2 and 4.3 systems.
|
||||
*/
|
||||
|
||||
int
|
||||
SetSockOpt(int fd, int level, int option, int yesno)
|
||||
{
|
||||
return setsockopt(fd, level, option,
|
||||
(char *)&yesno, sizeof yesno);
|
||||
}
|
||||
|
||||
/*
|
||||
* The following are routines used to print out debugging information.
|
||||
*/
|
||||
|
||||
unsigned char NetTraceFile[256] = "(standard output)";
|
||||
|
||||
void
|
||||
SetNetTrace(char *file)
|
||||
{
|
||||
if (NetTrace && NetTrace != stdout)
|
||||
fclose(NetTrace);
|
||||
if (file && (strcmp(file, "-") != 0)) {
|
||||
NetTrace = fopen(file, "w");
|
||||
if (NetTrace) {
|
||||
strcpy((char *)NetTraceFile, file);
|
||||
return;
|
||||
}
|
||||
fprintf(stderr, "Cannot open %s.\n", file);
|
||||
}
|
||||
NetTrace = stdout;
|
||||
strcpy((char *)NetTraceFile, "(standard output)");
|
||||
}
|
||||
|
||||
void
|
||||
Dump(char direction, unsigned char *buffer, int length)
|
||||
{
|
||||
# define BYTES_PER_LINE 32
|
||||
# define min(x,y) ((x<y)? x:y)
|
||||
unsigned char *pThis;
|
||||
int offset;
|
||||
|
||||
offset = 0;
|
||||
|
||||
while (length) {
|
||||
/* print one line */
|
||||
fprintf(NetTrace, "%c 0x%x\t", direction, offset);
|
||||
pThis = buffer;
|
||||
if (prettydump) {
|
||||
buffer = buffer + min(length, BYTES_PER_LINE/2);
|
||||
while (pThis < buffer) {
|
||||
fprintf(NetTrace, "%c%.2x",
|
||||
(((*pThis)&0xff) == 0xff) ? '*' : ' ',
|
||||
(*pThis)&0xff);
|
||||
pThis++;
|
||||
}
|
||||
length -= BYTES_PER_LINE/2;
|
||||
offset += BYTES_PER_LINE/2;
|
||||
} else {
|
||||
buffer = buffer + min(length, BYTES_PER_LINE);
|
||||
while (pThis < buffer) {
|
||||
fprintf(NetTrace, "%.2x", (*pThis)&0xff);
|
||||
pThis++;
|
||||
}
|
||||
length -= BYTES_PER_LINE;
|
||||
offset += BYTES_PER_LINE;
|
||||
}
|
||||
if (NetTrace == stdout) {
|
||||
fprintf(NetTrace, "\r\n");
|
||||
} else {
|
||||
fprintf(NetTrace, "\n");
|
||||
}
|
||||
if (length < 0) {
|
||||
fflush(NetTrace);
|
||||
return;
|
||||
}
|
||||
/* find next unique line */
|
||||
}
|
||||
fflush(NetTrace);
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
printoption(const char *direction, int cmd, int option)
|
||||
{
|
||||
if (!showoptions)
|
||||
return;
|
||||
if (cmd == IAC) {
|
||||
if (TELCMD_OK(option))
|
||||
fprintf(NetTrace, "%s IAC %s", direction, TELCMD(option));
|
||||
else
|
||||
fprintf(NetTrace, "%s IAC %d", direction, option);
|
||||
} else {
|
||||
const char *fmt;
|
||||
fmt = (cmd == WILL) ? "WILL" : (cmd == WONT) ? "WONT" :
|
||||
(cmd == DO) ? "DO" : (cmd == DONT) ? "DONT" : 0;
|
||||
if (fmt) {
|
||||
fprintf(NetTrace, "%s %s ", direction, fmt);
|
||||
if (TELOPT_OK(option))
|
||||
fprintf(NetTrace, "%s", TELOPT(option));
|
||||
else if (option == TELOPT_EXOPL)
|
||||
fprintf(NetTrace, "EXOPL");
|
||||
else
|
||||
fprintf(NetTrace, "%d", option);
|
||||
} else
|
||||
fprintf(NetTrace, "%s %d %d", direction, cmd, option);
|
||||
}
|
||||
if (NetTrace == stdout) {
|
||||
fprintf(NetTrace, "\r\n");
|
||||
fflush(NetTrace);
|
||||
} else {
|
||||
fprintf(NetTrace, "\n");
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
void
|
||||
optionstatus(void)
|
||||
{
|
||||
int i;
|
||||
extern char will_wont_resp[], do_dont_resp[];
|
||||
|
||||
for (i = 0; i < 256; i++) {
|
||||
if (do_dont_resp[i]) {
|
||||
if (TELOPT_OK(i))
|
||||
printf("resp DO_DONT %s: %d\n", TELOPT(i), do_dont_resp[i]);
|
||||
else if (TELCMD_OK(i))
|
||||
printf("resp DO_DONT %s: %d\n", TELCMD(i), do_dont_resp[i]);
|
||||
else
|
||||
printf("resp DO_DONT %d: %d\n", i,
|
||||
do_dont_resp[i]);
|
||||
if (my_want_state_is_do(i)) {
|
||||
if (TELOPT_OK(i))
|
||||
printf("want DO %s\n", TELOPT(i));
|
||||
else if (TELCMD_OK(i))
|
||||
printf("want DO %s\n", TELCMD(i));
|
||||
else
|
||||
printf("want DO %d\n", i);
|
||||
} else {
|
||||
if (TELOPT_OK(i))
|
||||
printf("want DONT %s\n", TELOPT(i));
|
||||
else if (TELCMD_OK(i))
|
||||
printf("want DONT %s\n", TELCMD(i));
|
||||
else
|
||||
printf("want DONT %d\n", i);
|
||||
}
|
||||
} else {
|
||||
if (my_state_is_do(i)) {
|
||||
if (TELOPT_OK(i))
|
||||
printf(" DO %s\n", TELOPT(i));
|
||||
else if (TELCMD_OK(i))
|
||||
printf(" DO %s\n", TELCMD(i));
|
||||
else
|
||||
printf(" DO %d\n", i);
|
||||
}
|
||||
}
|
||||
if (will_wont_resp[i]) {
|
||||
if (TELOPT_OK(i))
|
||||
printf("resp WILL_WONT %s: %d\n", TELOPT(i), will_wont_resp[i]);
|
||||
else if (TELCMD_OK(i))
|
||||
printf("resp WILL_WONT %s: %d\n", TELCMD(i), will_wont_resp[i]);
|
||||
else
|
||||
printf("resp WILL_WONT %d: %d\n",
|
||||
i, will_wont_resp[i]);
|
||||
if (my_want_state_is_will(i)) {
|
||||
if (TELOPT_OK(i))
|
||||
printf("want WILL %s\n", TELOPT(i));
|
||||
else if (TELCMD_OK(i))
|
||||
printf("want WILL %s\n", TELCMD(i));
|
||||
else
|
||||
printf("want WILL %d\n", i);
|
||||
} else {
|
||||
if (TELOPT_OK(i))
|
||||
printf("want WONT %s\n", TELOPT(i));
|
||||
else if (TELCMD_OK(i))
|
||||
printf("want WONT %s\n", TELCMD(i));
|
||||
else
|
||||
printf("want WONT %d\n", i);
|
||||
}
|
||||
} else {
|
||||
if (my_state_is_will(i)) {
|
||||
if (TELOPT_OK(i))
|
||||
printf(" WILL %s\n", TELOPT(i));
|
||||
else if (TELCMD_OK(i))
|
||||
printf(" WILL %s\n", TELCMD(i));
|
||||
else
|
||||
printf(" WILL %d\n", i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
printsub(char direction, unsigned char *pointer, int length)
|
||||
{
|
||||
int i;
|
||||
#ifdef AUTHENTICATION
|
||||
char buf[512];
|
||||
#endif
|
||||
extern int want_status_response;
|
||||
|
||||
if (showoptions || direction == 0 ||
|
||||
(want_status_response && (pointer[0] == TELOPT_STATUS))) {
|
||||
if (direction) {
|
||||
fprintf(NetTrace, "%s IAC SB ",
|
||||
(direction == '<')? "RCVD":"SENT");
|
||||
if (length >= 3) {
|
||||
int j;
|
||||
|
||||
i = pointer[length-2];
|
||||
j = pointer[length-1];
|
||||
|
||||
if (i != IAC || j != SE) {
|
||||
fprintf(NetTrace, "(terminated by ");
|
||||
if (TELOPT_OK(i))
|
||||
fprintf(NetTrace, "%s ", TELOPT(i));
|
||||
else if (TELCMD_OK(i))
|
||||
fprintf(NetTrace, "%s ", TELCMD(i));
|
||||
else
|
||||
fprintf(NetTrace, "%d ", i);
|
||||
if (TELOPT_OK(j))
|
||||
fprintf(NetTrace, "%s", TELOPT(j));
|
||||
else if (TELCMD_OK(j))
|
||||
fprintf(NetTrace, "%s", TELCMD(j));
|
||||
else
|
||||
fprintf(NetTrace, "%d", j);
|
||||
fprintf(NetTrace, ", not IAC SE!) ");
|
||||
}
|
||||
}
|
||||
length -= 2;
|
||||
}
|
||||
if (length < 1) {
|
||||
fprintf(NetTrace, "(Empty suboption??\?)");
|
||||
if (NetTrace == stdout)
|
||||
fflush(NetTrace);
|
||||
return;
|
||||
}
|
||||
switch (pointer[0]) {
|
||||
case TELOPT_TTYPE:
|
||||
fprintf(NetTrace, "TERMINAL-TYPE ");
|
||||
switch (pointer[1]) {
|
||||
case TELQUAL_IS:
|
||||
fprintf(NetTrace, "IS \"%.*s\"", length-2, (char *)pointer+2);
|
||||
break;
|
||||
case TELQUAL_SEND:
|
||||
fprintf(NetTrace, "SEND");
|
||||
break;
|
||||
default:
|
||||
fprintf(NetTrace,
|
||||
"- unknown qualifier %d (0x%x).",
|
||||
pointer[1], pointer[1]);
|
||||
}
|
||||
break;
|
||||
case TELOPT_TSPEED:
|
||||
fprintf(NetTrace, "TERMINAL-SPEED");
|
||||
if (length < 2) {
|
||||
fprintf(NetTrace, " (empty suboption??\?)");
|
||||
break;
|
||||
}
|
||||
switch (pointer[1]) {
|
||||
case TELQUAL_IS:
|
||||
fprintf(NetTrace, " IS ");
|
||||
fprintf(NetTrace, "%.*s", length-2, (char *)pointer+2);
|
||||
break;
|
||||
default:
|
||||
if (pointer[1] == 1)
|
||||
fprintf(NetTrace, " SEND");
|
||||
else
|
||||
fprintf(NetTrace, " %d (unknown)", pointer[1]);
|
||||
for (i = 2; i < length; i++)
|
||||
fprintf(NetTrace, " ?%d?", pointer[i]);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case TELOPT_LFLOW:
|
||||
fprintf(NetTrace, "TOGGLE-FLOW-CONTROL");
|
||||
if (length < 2) {
|
||||
fprintf(NetTrace, " (empty suboption??\?)");
|
||||
break;
|
||||
}
|
||||
switch (pointer[1]) {
|
||||
case LFLOW_OFF:
|
||||
fprintf(NetTrace, " OFF"); break;
|
||||
case LFLOW_ON:
|
||||
fprintf(NetTrace, " ON"); break;
|
||||
case LFLOW_RESTART_ANY:
|
||||
fprintf(NetTrace, " RESTART-ANY"); break;
|
||||
case LFLOW_RESTART_XON:
|
||||
fprintf(NetTrace, " RESTART-XON"); break;
|
||||
default:
|
||||
fprintf(NetTrace, " %d (unknown)", pointer[1]);
|
||||
}
|
||||
for (i = 2; i < length; i++)
|
||||
fprintf(NetTrace, " ?%d?", pointer[i]);
|
||||
break;
|
||||
|
||||
case TELOPT_NAWS:
|
||||
fprintf(NetTrace, "NAWS");
|
||||
if (length < 2) {
|
||||
fprintf(NetTrace, " (empty suboption??\?)");
|
||||
break;
|
||||
}
|
||||
if (length == 2) {
|
||||
fprintf(NetTrace, " ?%d?", pointer[1]);
|
||||
break;
|
||||
}
|
||||
fprintf(NetTrace, " %d %d (%d)",
|
||||
pointer[1], pointer[2],
|
||||
(int)((((unsigned int)pointer[1])<<8)|((unsigned int)pointer[2])));
|
||||
if (length == 4) {
|
||||
fprintf(NetTrace, " ?%d?", pointer[3]);
|
||||
break;
|
||||
}
|
||||
fprintf(NetTrace, " %d %d (%d)",
|
||||
pointer[3], pointer[4],
|
||||
(int)((((unsigned int)pointer[3])<<8)|((unsigned int)pointer[4])));
|
||||
for (i = 5; i < length; i++)
|
||||
fprintf(NetTrace, " ?%d?", pointer[i]);
|
||||
break;
|
||||
|
||||
#ifdef AUTHENTICATION
|
||||
case TELOPT_AUTHENTICATION:
|
||||
fprintf(NetTrace, "AUTHENTICATION");
|
||||
if (length < 2) {
|
||||
fprintf(NetTrace, " (empty suboption??\?)");
|
||||
break;
|
||||
}
|
||||
switch (pointer[1]) {
|
||||
case TELQUAL_REPLY:
|
||||
case TELQUAL_IS:
|
||||
fprintf(NetTrace, " %s ", (pointer[1] == TELQUAL_IS) ?
|
||||
"IS" : "REPLY");
|
||||
if (AUTHTYPE_NAME_OK(pointer[2]))
|
||||
fprintf(NetTrace, "%s ", AUTHTYPE_NAME(pointer[2]));
|
||||
else
|
||||
fprintf(NetTrace, "%d ", pointer[2]);
|
||||
if (length < 3) {
|
||||
fprintf(NetTrace, "(partial suboption??\?)");
|
||||
break;
|
||||
}
|
||||
fprintf(NetTrace, "%s|%s",
|
||||
((pointer[3] & AUTH_WHO_MASK) == AUTH_WHO_CLIENT) ?
|
||||
"CLIENT" : "SERVER",
|
||||
((pointer[3] & AUTH_HOW_MASK) == AUTH_HOW_MUTUAL) ?
|
||||
"MUTUAL" : "ONE-WAY");
|
||||
|
||||
auth_printsub(&pointer[1], length - 1, buf, sizeof(buf));
|
||||
fprintf(NetTrace, "%s", buf);
|
||||
break;
|
||||
|
||||
case TELQUAL_SEND:
|
||||
i = 2;
|
||||
fprintf(NetTrace, " SEND ");
|
||||
while (i < length) {
|
||||
if (AUTHTYPE_NAME_OK(pointer[i]))
|
||||
fprintf(NetTrace, "%s ", AUTHTYPE_NAME(pointer[i]));
|
||||
else
|
||||
fprintf(NetTrace, "%d ", pointer[i]);
|
||||
if (++i >= length) {
|
||||
fprintf(NetTrace, "(partial suboption??\?)");
|
||||
break;
|
||||
}
|
||||
fprintf(NetTrace, "%s|%s ",
|
||||
((pointer[i] & AUTH_WHO_MASK) == AUTH_WHO_CLIENT) ?
|
||||
"CLIENT" : "SERVER",
|
||||
((pointer[i] & AUTH_HOW_MASK) == AUTH_HOW_MUTUAL) ?
|
||||
"MUTUAL" : "ONE-WAY");
|
||||
++i;
|
||||
}
|
||||
break;
|
||||
|
||||
case TELQUAL_NAME:
|
||||
i = 2;
|
||||
fprintf(NetTrace, " NAME \"");
|
||||
while (i < length)
|
||||
putc(pointer[i++], NetTrace);
|
||||
putc('"', NetTrace);
|
||||
break;
|
||||
|
||||
default:
|
||||
for (i = 2; i < length; i++)
|
||||
fprintf(NetTrace, " ?%d?", pointer[i]);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
#endif
|
||||
|
||||
#ifdef ENCRYPTION
|
||||
case TELOPT_ENCRYPT:
|
||||
fprintf(NetTrace, "ENCRYPT");
|
||||
if (length < 2) {
|
||||
fprintf(NetTrace, " (empty suboption??\?)");
|
||||
break;
|
||||
}
|
||||
switch (pointer[1]) {
|
||||
case ENCRYPT_START:
|
||||
fprintf(NetTrace, " START");
|
||||
break;
|
||||
|
||||
case ENCRYPT_END:
|
||||
fprintf(NetTrace, " END");
|
||||
break;
|
||||
|
||||
case ENCRYPT_REQSTART:
|
||||
fprintf(NetTrace, " REQUEST-START");
|
||||
break;
|
||||
|
||||
case ENCRYPT_REQEND:
|
||||
fprintf(NetTrace, " REQUEST-END");
|
||||
break;
|
||||
|
||||
case ENCRYPT_IS:
|
||||
case ENCRYPT_REPLY:
|
||||
fprintf(NetTrace, " %s ", (pointer[1] == ENCRYPT_IS) ?
|
||||
"IS" : "REPLY");
|
||||
if (length < 3) {
|
||||
fprintf(NetTrace, " (partial suboption??\?)");
|
||||
break;
|
||||
}
|
||||
if (ENCTYPE_NAME_OK(pointer[2]))
|
||||
fprintf(NetTrace, "%s ", ENCTYPE_NAME(pointer[2]));
|
||||
else
|
||||
fprintf(NetTrace, " %d (unknown)", pointer[2]);
|
||||
|
||||
encrypt_printsub(&pointer[1], length - 1, buf, sizeof(buf));
|
||||
fprintf(NetTrace, "%s", buf);
|
||||
break;
|
||||
|
||||
case ENCRYPT_SUPPORT:
|
||||
i = 2;
|
||||
fprintf(NetTrace, " SUPPORT ");
|
||||
while (i < length) {
|
||||
if (ENCTYPE_NAME_OK(pointer[i]))
|
||||
fprintf(NetTrace, "%s ", ENCTYPE_NAME(pointer[i]));
|
||||
else
|
||||
fprintf(NetTrace, "%d ", pointer[i]);
|
||||
i++;
|
||||
}
|
||||
break;
|
||||
|
||||
case ENCRYPT_ENC_KEYID:
|
||||
fprintf(NetTrace, " ENC_KEYID ");
|
||||
goto encommon;
|
||||
|
||||
case ENCRYPT_DEC_KEYID:
|
||||
fprintf(NetTrace, " DEC_KEYID ");
|
||||
goto encommon;
|
||||
|
||||
default:
|
||||
fprintf(NetTrace, " %d (unknown)", pointer[1]);
|
||||
encommon:
|
||||
for (i = 2; i < length; i++)
|
||||
fprintf(NetTrace, " %d", pointer[i]);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
#endif /* ENCRYPTION */
|
||||
|
||||
case TELOPT_LINEMODE:
|
||||
fprintf(NetTrace, "LINEMODE ");
|
||||
if (length < 2) {
|
||||
fprintf(NetTrace, " (empty suboption??\?)");
|
||||
break;
|
||||
}
|
||||
switch (pointer[1]) {
|
||||
case WILL:
|
||||
fprintf(NetTrace, "WILL ");
|
||||
goto common;
|
||||
case WONT:
|
||||
fprintf(NetTrace, "WONT ");
|
||||
goto common;
|
||||
case DO:
|
||||
fprintf(NetTrace, "DO ");
|
||||
goto common;
|
||||
case DONT:
|
||||
fprintf(NetTrace, "DONT ");
|
||||
common:
|
||||
if (length < 3) {
|
||||
fprintf(NetTrace, "(no option??\?)");
|
||||
break;
|
||||
}
|
||||
switch (pointer[2]) {
|
||||
case LM_FORWARDMASK:
|
||||
fprintf(NetTrace, "Forward Mask");
|
||||
for (i = 3; i < length; i++)
|
||||
fprintf(NetTrace, " %x", pointer[i]);
|
||||
break;
|
||||
default:
|
||||
fprintf(NetTrace, "%d (unknown)", pointer[2]);
|
||||
for (i = 3; i < length; i++)
|
||||
fprintf(NetTrace, " %d", pointer[i]);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case LM_SLC:
|
||||
fprintf(NetTrace, "SLC");
|
||||
for (i = 2; i < length - 2; i += 3) {
|
||||
if (SLC_NAME_OK(pointer[i+SLC_FUNC]))
|
||||
fprintf(NetTrace, " %s", SLC_NAME(pointer[i+SLC_FUNC]));
|
||||
else
|
||||
fprintf(NetTrace, " %d", pointer[i+SLC_FUNC]);
|
||||
switch (pointer[i+SLC_FLAGS]&SLC_LEVELBITS) {
|
||||
case SLC_NOSUPPORT:
|
||||
fprintf(NetTrace, " NOSUPPORT"); break;
|
||||
case SLC_CANTCHANGE:
|
||||
fprintf(NetTrace, " CANTCHANGE"); break;
|
||||
case SLC_VARIABLE:
|
||||
fprintf(NetTrace, " VARIABLE"); break;
|
||||
case SLC_DEFAULT:
|
||||
fprintf(NetTrace, " DEFAULT"); break;
|
||||
}
|
||||
fprintf(NetTrace, "%s%s%s",
|
||||
pointer[i+SLC_FLAGS]&SLC_ACK ? "|ACK" : "",
|
||||
pointer[i+SLC_FLAGS]&SLC_FLUSHIN ? "|FLUSHIN" : "",
|
||||
pointer[i+SLC_FLAGS]&SLC_FLUSHOUT ? "|FLUSHOUT" : "");
|
||||
if (pointer[i+SLC_FLAGS]& ~(SLC_ACK|SLC_FLUSHIN|
|
||||
SLC_FLUSHOUT| SLC_LEVELBITS))
|
||||
fprintf(NetTrace, "(0x%x)", pointer[i+SLC_FLAGS]);
|
||||
fprintf(NetTrace, " %d;", pointer[i+SLC_VALUE]);
|
||||
if ((pointer[i+SLC_VALUE] == IAC) &&
|
||||
(pointer[i+SLC_VALUE+1] == IAC))
|
||||
i++;
|
||||
}
|
||||
for (; i < length; i++)
|
||||
fprintf(NetTrace, " ?%d?", pointer[i]);
|
||||
break;
|
||||
|
||||
case LM_MODE:
|
||||
fprintf(NetTrace, "MODE ");
|
||||
if (length < 3) {
|
||||
fprintf(NetTrace, "(no mode??\?)");
|
||||
break;
|
||||
}
|
||||
{
|
||||
char tbuf[64];
|
||||
sprintf(tbuf, "%s%s%s%s%s",
|
||||
pointer[2]&MODE_EDIT ? "|EDIT" : "",
|
||||
pointer[2]&MODE_TRAPSIG ? "|TRAPSIG" : "",
|
||||
pointer[2]&MODE_SOFT_TAB ? "|SOFT_TAB" : "",
|
||||
pointer[2]&MODE_LIT_ECHO ? "|LIT_ECHO" : "",
|
||||
pointer[2]&MODE_ACK ? "|ACK" : "");
|
||||
fprintf(NetTrace, "%s", tbuf[1] ? &tbuf[1] : "0");
|
||||
}
|
||||
if (pointer[2]&~(MODE_MASK))
|
||||
fprintf(NetTrace, " (0x%x)", pointer[2]);
|
||||
for (i = 3; i < length; i++)
|
||||
fprintf(NetTrace, " ?0x%x?", pointer[i]);
|
||||
break;
|
||||
default:
|
||||
fprintf(NetTrace, "%d (unknown)", pointer[1]);
|
||||
for (i = 2; i < length; i++)
|
||||
fprintf(NetTrace, " %d", pointer[i]);
|
||||
}
|
||||
break;
|
||||
|
||||
case TELOPT_STATUS: {
|
||||
const char *cp;
|
||||
int j, k;
|
||||
|
||||
fprintf(NetTrace, "STATUS");
|
||||
|
||||
switch (pointer[1]) {
|
||||
default:
|
||||
if (pointer[1] == TELQUAL_SEND)
|
||||
fprintf(NetTrace, " SEND");
|
||||
else
|
||||
fprintf(NetTrace, " %d (unknown)", pointer[1]);
|
||||
for (i = 2; i < length; i++)
|
||||
fprintf(NetTrace, " ?%d?", pointer[i]);
|
||||
break;
|
||||
case TELQUAL_IS:
|
||||
if (--want_status_response < 0)
|
||||
want_status_response = 0;
|
||||
if (NetTrace == stdout)
|
||||
fprintf(NetTrace, " IS\r\n");
|
||||
else
|
||||
fprintf(NetTrace, " IS\n");
|
||||
|
||||
for (i = 2; i < length; i++) {
|
||||
switch(pointer[i]) {
|
||||
case DO: cp = "DO"; goto common2;
|
||||
case DONT: cp = "DONT"; goto common2;
|
||||
case WILL: cp = "WILL"; goto common2;
|
||||
case WONT: cp = "WONT"; goto common2;
|
||||
common2:
|
||||
i++;
|
||||
if (TELOPT_OK((int)pointer[i]))
|
||||
fprintf(NetTrace, " %s %s", cp, TELOPT(pointer[i]));
|
||||
else
|
||||
fprintf(NetTrace, " %s %d", cp, pointer[i]);
|
||||
|
||||
if (NetTrace == stdout)
|
||||
fprintf(NetTrace, "\r\n");
|
||||
else
|
||||
fprintf(NetTrace, "\n");
|
||||
break;
|
||||
|
||||
case SB:
|
||||
fprintf(NetTrace, " SB ");
|
||||
i++;
|
||||
j = k = i;
|
||||
while (j < length) {
|
||||
if (pointer[j] == SE) {
|
||||
if (j+1 == length)
|
||||
break;
|
||||
if (pointer[j+1] == SE)
|
||||
j++;
|
||||
else
|
||||
break;
|
||||
}
|
||||
pointer[k++] = pointer[j++];
|
||||
}
|
||||
printsub(0, &pointer[i], k - i);
|
||||
if (i < length) {
|
||||
fprintf(NetTrace, " SE");
|
||||
i = j;
|
||||
} else
|
||||
i = j - 1;
|
||||
|
||||
if (NetTrace == stdout)
|
||||
fprintf(NetTrace, "\r\n");
|
||||
else
|
||||
fprintf(NetTrace, "\n");
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
fprintf(NetTrace, " %d", pointer[i]);
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case TELOPT_XDISPLOC:
|
||||
fprintf(NetTrace, "X-DISPLAY-LOCATION ");
|
||||
switch (pointer[1]) {
|
||||
case TELQUAL_IS:
|
||||
fprintf(NetTrace, "IS \"%.*s\"", length-2, (char *)pointer+2);
|
||||
break;
|
||||
case TELQUAL_SEND:
|
||||
fprintf(NetTrace, "SEND");
|
||||
break;
|
||||
default:
|
||||
fprintf(NetTrace, "- unknown qualifier %d (0x%x).",
|
||||
pointer[1], pointer[1]);
|
||||
}
|
||||
break;
|
||||
|
||||
case TELOPT_NEW_ENVIRON:
|
||||
fprintf(NetTrace, "NEW-ENVIRON ");
|
||||
#ifdef OLD_ENVIRON
|
||||
goto env_common1;
|
||||
case TELOPT_OLD_ENVIRON:
|
||||
fprintf(NetTrace, "OLD-ENVIRON");
|
||||
env_common1:
|
||||
#endif
|
||||
switch (pointer[1]) {
|
||||
case TELQUAL_IS:
|
||||
fprintf(NetTrace, "IS ");
|
||||
goto env_common;
|
||||
case TELQUAL_SEND:
|
||||
fprintf(NetTrace, "SEND ");
|
||||
goto env_common;
|
||||
case TELQUAL_INFO:
|
||||
fprintf(NetTrace, "INFO ");
|
||||
env_common:
|
||||
{
|
||||
int noquote = 2;
|
||||
#if defined(ENV_HACK) && defined(OLD_ENVIRON)
|
||||
extern int old_env_var, old_env_value;
|
||||
#endif
|
||||
for (i = 2; i < length; i++ ) {
|
||||
switch (pointer[i]) {
|
||||
case NEW_ENV_VALUE:
|
||||
#ifdef OLD_ENVIRON
|
||||
/* case NEW_ENV_OVAR: */
|
||||
if (pointer[0] == TELOPT_OLD_ENVIRON) {
|
||||
# ifdef ENV_HACK
|
||||
if (old_env_var == OLD_ENV_VALUE)
|
||||
fprintf(NetTrace, "\" (VALUE) " + noquote);
|
||||
else
|
||||
# endif
|
||||
fprintf(NetTrace, "\" VAR " + noquote);
|
||||
} else
|
||||
#endif /* OLD_ENVIRON */
|
||||
fprintf(NetTrace, "\" VALUE " + noquote);
|
||||
noquote = 2;
|
||||
break;
|
||||
|
||||
case NEW_ENV_VAR:
|
||||
#ifdef OLD_ENVIRON
|
||||
/* case OLD_ENV_VALUE: */
|
||||
if (pointer[0] == TELOPT_OLD_ENVIRON) {
|
||||
# ifdef ENV_HACK
|
||||
if (old_env_value == OLD_ENV_VAR)
|
||||
fprintf(NetTrace, "\" (VAR) " + noquote);
|
||||
else
|
||||
# endif
|
||||
fprintf(NetTrace, "\" VALUE " + noquote);
|
||||
} else
|
||||
#endif /* OLD_ENVIRON */
|
||||
fprintf(NetTrace, "\" VAR " + noquote);
|
||||
noquote = 2;
|
||||
break;
|
||||
|
||||
case ENV_ESC:
|
||||
fprintf(NetTrace, "\" ESC " + noquote);
|
||||
noquote = 2;
|
||||
break;
|
||||
|
||||
case ENV_USERVAR:
|
||||
fprintf(NetTrace, "\" USERVAR " + noquote);
|
||||
noquote = 2;
|
||||
break;
|
||||
|
||||
default:
|
||||
if (isprint(pointer[i]) && pointer[i] != '"') {
|
||||
if (noquote) {
|
||||
putc('"', NetTrace);
|
||||
noquote = 0;
|
||||
}
|
||||
putc(pointer[i], NetTrace);
|
||||
} else {
|
||||
fprintf(NetTrace, "\" %03o " + noquote,
|
||||
pointer[i]);
|
||||
noquote = 2;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!noquote)
|
||||
putc('"', NetTrace);
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
if (TELOPT_OK(pointer[0]))
|
||||
fprintf(NetTrace, "%s (unknown)", TELOPT(pointer[0]));
|
||||
else
|
||||
fprintf(NetTrace, "%d (unknown)", pointer[0]);
|
||||
for (i = 1; i < length; i++)
|
||||
fprintf(NetTrace, " %d", pointer[i]);
|
||||
break;
|
||||
}
|
||||
if (direction) {
|
||||
if (NetTrace == stdout)
|
||||
fprintf(NetTrace, "\r\n");
|
||||
else
|
||||
fprintf(NetTrace, "\n");
|
||||
}
|
||||
if (NetTrace == stdout)
|
||||
fflush(NetTrace);
|
||||
}
|
||||
}
|
||||
|
||||
/* EmptyTerminal - called to make sure that the terminal buffer is empty.
|
||||
* Note that we consider the buffer to run all the
|
||||
* way to the kernel (thus the select).
|
||||
*/
|
||||
|
||||
static void
|
||||
EmptyTerminal(void)
|
||||
{
|
||||
fd_set o;
|
||||
|
||||
FD_ZERO(&o);
|
||||
|
||||
if (TTYBYTES() == 0) {
|
||||
FD_SET(tout, &o);
|
||||
(void) select(tout+1, (fd_set *) 0, &o, (fd_set *) 0,
|
||||
(struct timeval *) 0); /* wait for TTLOWAT */
|
||||
} else {
|
||||
while (TTYBYTES()) {
|
||||
(void) ttyflush(0);
|
||||
FD_SET(tout, &o);
|
||||
(void) select(tout+1, (fd_set *) 0, &o, (fd_set *) 0,
|
||||
(struct timeval *) 0); /* wait for TTLOWAT */
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
SetForExit(void)
|
||||
{
|
||||
setconnmode(0);
|
||||
do {
|
||||
(void)telrcv(); /* Process any incoming data */
|
||||
EmptyTerminal();
|
||||
} while (ring_full_count(&netiring)); /* While there is any */
|
||||
setcommandmode();
|
||||
fflush(stdout);
|
||||
fflush(stderr);
|
||||
setconnmode(0);
|
||||
EmptyTerminal(); /* Flush the path to the tty */
|
||||
setcommandmode();
|
||||
}
|
||||
|
||||
void
|
||||
Exit(int returnCode)
|
||||
{
|
||||
SetForExit();
|
||||
exit(returnCode);
|
||||
}
|
||||
|
||||
void
|
||||
ExitString(const char *string, int returnCode)
|
||||
{
|
||||
SetForExit();
|
||||
fwrite(string, 1, strlen(string), stderr);
|
||||
exit(returnCode);
|
||||
}
|
||||
Reference in New Issue
Block a user