lenny@icus.ICUS.COM (Lenny Tropiano) (06/07/90)
This program connects faster than HDB uucp /usr/bin/cu, and it works nicely.
No docs written for it, but it's usage is easy:
$ rlogin nodename
It will connect up to a STARLAN node on the network that is listening and has
the TTYSERVER ["1"] activated.
This program supports <CR>~! that will suspend the session back to the current
shell (environment $SHELL) or /bin/sh if not set, and resumes the connection
when the shell exits.
To exit, have either the STARLAN connection drop, or use <CR>~. both will
disconnect.
Enhancements, bug fixes, suggestions should be sent to me...
Take care,
-Lenny
-- cut here -- -- cut here -- -- cut here -- -- cut here -- -- cut here --
#! /bin/sh
# This is a shell archive. Remove anything before this line, then unpack
# it by saving it into a file and typing "sh file". To overwrite existing
# files, type "sh file -c". You can also feed this as standard input via
# unshar, or by typing "sh <file", e.g.. If this archive is complete, you
# will see the following message at the end:
# "End of shell archive."
# Contents: Makefile rlogin.c
# Wrapped by lenny@icus on Mon Jun 4 00:51:48 1990
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f Makefile -a "${1}" != "-c" ; then
echo shar: Will not over-write existing file \"Makefile\"
else
echo shar: Extracting \"Makefile\" \(621 characters\)
sed "s/^X//" >Makefile <<'END_OF_Makefile'
X#
X# Makefile to compile rlogin.c (Remote Login)
X# By Lenny Tropiano
X# (c)1990 ICUS Software Systems UUCP: lenny@ICUS.COM
X#
XCFLAGS=-v -O
XLDFLAGS=-G -s
XLIBS=-lslan /lib/crt0s.o /lib/shlib.ifile
XDEST=/usr/lbin/
XINCLUDEPATH=/usr/net/include
XLIBPATH=/usr/lib/net
X#
Xall: rlogin
X#
Xrlogin.o:
X $(CC) $(CFLAGS) -I$(INCLUDEPATH) -c rlogin.c
X#
Xrlogin: rlogin.o
X @echo "Loading ..."
X $(LD) $(LDFLAGS) -o rlogin rlogin.o -L$(LIBPATH) $(LIBS)
X
X#
X# You need to be superuser to do this
X#
X$(DEST):
X mkdir $(DEST)
X
Xinstall: all $(DEST)
X cp rlogin $(DEST)
X chown bin $(DEST)rlogin
X chgrp bin $(DEST)rlogin
X chmod 755 $(DEST)rlogin
END_OF_Makefile
if test 621 -ne `wc -c <Makefile`; then
echo shar: \"Makefile\" unpacked with wrong size!
fi
# end of overwriting check
fi
if test -f rlogin.c -a "${1}" != "-c" ; then
echo shar: Will not over-write existing file \"rlogin.c\"
else
echo shar: Extracting \"rlogin.c\" \(7262 characters\)
sed "s/^X//" >rlogin.c <<'END_OF_rlogin.c'
X/************************************************************************\
X** **
X** Program name: rlogin.c (Remote Login to STARLAN Node) **
X** **
X** Programmer: Lenny Tropiano EMAIL: lenny@ICUS.COM **
X** Organization: ICUS Software Systems (c)1990 All rights reserved **
X** Date: June 4, 1990 **
X** Version: 1.0 **
X**************************************************************************
X** **
X** Program use: Execute program with one argument, the remote node to **
X** connect to, and this will call up a remote STARLAN **
X** tty server for the interactive session. Two "cu"-like **
X** commands "~!" for a shell and "~." to disconnect are **
X** included in this program. **
X** **
X**************************************************************************
X** Permission granted to redistribute without profit in the public **
X** domain only. This header must remain in-tact as is. This program **
X** carries no warranties, express or implied, and all consequences **
X** resulting from the use of this program are the sole responsibility **
X** of the user. Any modifications of this program must be mailed to **
X** the author. **
X\************************************************************************/
X
X#include <stdio.h>
X#include <signal.h>
X#include <errno.h>
X#include <sys/types.h>
X#include <net/sys/tiuser.h>
X#include <termio.h>
X
Xstruct termio sttyparam; /* stty parameters */
Xint netd; /* network descriptor */
Xchar *progname, /* program name */
X *remotenode; /* system connected to */
Xchar *getenv(); /* getenv() call */
Xint command_process(); /* shell command */
Xvoid set_rawmode(), /* void function decl. */
X set_normalmode(),
X disconnect(),
X establish_connection(),
X input_process(),
X output_process(),
X run_shell();
X
X#define TTYSERVER "1" /* service number of tty server */
X#define TILDE '~'
X
X/*
X** main process, startup, set terminal, establish connection, and fork the
X** processes to do input and output (I/O)
X*/
X
Xmain(argc, argv)
Xint argc;
Xchar *argv[];
X{
X int cpid; /* child process pid */
X
X progname = argv[0];
X
X if(argc != 2) {
X fprintf(stderr, "Usage: %s node\n", progname);
X exit(1);
X }
X
X remotenode = argv[1];
X
X (void)establish_connection();
X
X set_rawmode();
X
X /*
X ** fork a process to handle the output, as the other process will
X ** handle the input, much like /usr/bin/cu does it.
X */
X
X if (cpid = fork())
X (void)input_process();
X else
X (void)output_process();
X
X /*
X ** if the parent process falls through to this point, we've
X ** encountered some sort of error, kill the child process to avoid
X ** defunct ones out there
X */
X
X kill(cpid, SIGHUP); /* send hangup signal */
X
X (void)disconnect();
X
X}
X
X/*
X** establish a network service connection to the remote node tty server
X*/
X
Xvoid establish_connection()
X{
X printf("\nEstablishing connection to %s ... ", remotenode);
X fflush(stdout);
X
X /*
X ** establish a connection and get a network descriptor for the
X ** node in question
X */
X netd = nlsestablish(remotenode, (char *)NULL);
X if (netd < 0) {
X printf("\n%s: node not listening on STARLAN network.\n",
X remotenode);
X exit(1);
X }
X
X /*
X ** request a server on the established network connection to start
X ** using the network descriptor for communication
X */
X if (nlsrequest(netd, TTYSERVER) < 0) {
X printf("\n%s: node does not have TTY server.\n",
X remotenode);
X t_close(netd);
X exit(1);
X }
X
X /*
X ** check the status of the network device
X */
X if (t_getstate(netd) != T_DATAXFER) {
X printf("\n%s: after connection, unknown error received.\n",
X remotenode);
X t_snddis(netd, (char *)NULL);
X t_unbind(netd);
X t_close(netd);
X exit(1);
X }
X
X /*
X ** Ok, we connected successfully...
X */
X printf("\007Connected.\n\n");
X return;
X}
X
X/*
X** input process to read characters from keyboard and write them to the
X** network device
X*/
X
Xvoid input_process()
X{
X char ch, lastch;
X
X signal(SIGUSR1, disconnect); /* catch the signal to disconnect */
X
X for(;;) {
X read(0, &ch, 1);
X if (ch == TILDE && (lastch == '\n' || lastch == '\r')) {
X if (command_process() == 1)
X break;
X } else
X t_snd(netd, &ch, 1, 0);
X
X lastch = ch;
X }
X}
X
X/*
X** output process to output characters read from network device
X** to standard output
X*/
X
Xvoid output_process()
X{
X char buffer[BUFSIZ];
X int flag, nbytes_read;
X
X signal(SIGINT, SIG_IGN);
X signal(SIGQUIT, SIG_IGN);
X
X close(0); /* we don't need stdin here */
X
X for (;;) {
X nbytes_read = t_rcv(netd, buffer, BUFSIZ, &flag);
X if(nbytes_read < 0 || t_getstate(netd) != T_DATAXFER)
X break;
X write(1, buffer, nbytes_read);
X }
X
X kill(getppid(), SIGUSR1); /* terminate the input process */
X
X exit(1);
X}
X
X/*
X** a ~(tilde) command was received, no check to see if the next character
X** is a valid one, otherwise output it to the network device
X*/
X
Xint command_process()
X{
X char ch;
X
X read(0, &ch, 1);
X switch (ch) {
X case '!': /* ~! = suspend to shell */
X run_shell();
X break;
X case '.': /* ~. = disconnect process */
X return(1);
X break;
X default:
X t_snd(netd, "~", 1, 0);
X case '~':
X t_snd(netd, &ch, 1, 0);
X break;
X }
X return(0);
X}
X
X/*
X** suspend to shell back to calling machine
X*/
X
Xvoid run_shell()
X{
X char *shell;
X
X set_normalmode();
X printf("\n");
X shell = (char *)getenv("SHELL");
X if (shell == (char *)NULL)
X shell = "/bin/sh";
X
X printf("\r\n%s: STARLAN Session Suspended\n\n", remotenode);
X if(fork()) {
X signal(SIGINT, SIG_IGN);
X signal(SIGQUIT, SIG_IGN);
X wait(0);
X } else {
X signal(SIGINT, SIG_DFL);
X signal(SIGQUIT, SIG_DFL);
X (void)execl(shell, shell + 5, (char *)0);
X perror(progname);
X exit(1);
X }
X printf("\r\n%s: STARLAN Session Resumed\n\n", remotenode);
X
X set_rawmode();
X
X signal(SIGINT, SIG_DFL);
X signal(SIGQUIT, SIG_DFL);
X}
X
X/*
X** set current terminal in RAW mode
X** save old parameters for restoration in sttyparam
X*/
X
Xvoid set_rawmode()
X{
X struct termio rawmode;
X
X if (ioctl(0,TCGETA,&sttyparam) < 0)
X return;
X
X memcpy(&rawmode, &sttyparam, sizeof(struct termio));
X
X rawmode.c_cflag |= CS8|CREAD;
X rawmode.c_cflag &= ~PARENB;
X rawmode.c_iflag |= IGNBRK;
X rawmode.c_iflag &= ~(IXOFF|IXON|INPCK|ISTRIP|IGNPAR|BRKINT);
X rawmode.c_lflag &= ~(ISIG|ICANON|ECHO|XCASE|ECHOE|ECHOK|ECHONL);
X rawmode.c_cc[VMIN] = 1; /* 1 char canconical input */
X
X if (ioctl(0,TCSETA,&rawmode) < 0)
X return;
X}
X
X/*
X** reset back to the normal saved parameters
X*/
X
Xvoid set_normalmode()
X{
X (void)ioctl(0,TCSETA,&sttyparam);
X}
X
X/*
X** disconnect from STARLAN and restore terminal back to correct stty params
X*/
X
Xvoid disconnect()
X{
X set_normalmode();
X
X printf("\n\rNode %s: STARLAN Disconnected.\n\n", remotenode);
X
X t_snddis(netd, (char *)NULL);
X t_unbind(netd);
X t_close(netd);
X
X exit(0);
X}
X
END_OF_rlogin.c
if test 7262 -ne `wc -c <rlogin.c`; then
echo shar: \"rlogin.c\" unpacked with wrong size!
fi
# end of overwriting check
fi
echo shar: End of shell archive.
exit 0
--
| Lenny Tropiano ICUS Software Systems lenny@icus.ICUS.COM |
| {ames,pacbell,decuac,sbcs,hombre,rayssd}!icus!lenny attmail!icus!lenny |
+------ ICUS Software Systems -- PO Box 1; Islip Terrace, NY 11752 ------+