[net.sources] "culog.c" - turn logging on/off under standard "cu"

rpw3@redwood.UUCP (Rob Warnock) (01/01/85)

<<Mild flame ON>>
Given the nature of users to "try things", Mike Newton's "blast" program
comes close to being a menace, given it's cavalier description...

> /* Blast into a users terminal.  Great fun, and sometimes useful. */
> /* {ucbvax,allegra}!cithep!cit-vax!newton.UUCP */

Since the TIOCSTI ioctl (4.1 & 4.2 BSD) can type anything INTO another
user's terminal, it is quite properly a superuser-priviledged call, but
special-purpose programs using it can be relatively safe in "friendly" shops.
<<Mild flame OFF>>

...as in the attached program called "culog".

How many times have you been cu'd to a non-UNIX system and -- right in
the middle of the call -- you suddenly realize you want a permanent copy
of your TTY output? But the foreign system you're on (for example, a stock
quote service) doesn't let you write a program to echo "~>filename"...
Or the system is so baroque you don't know HOW to write programs... 
And the other system ALWAYS has a prompt so you can't just get the
type-in echo to do it... And you may not have sources to "cu" (or the
energy to figure out how to get the front half to signal the back half
properly without losing data).

Anyway, I use "culog" several times a day, and now trust it enough to let
a shell script dial my numbers for me, run "cu", and "~!culog XXX.log.tmp".
(You MUST manually do a "~!culog" before disconnecting from "cu" if you
don't want to lose the last kilochar or so which is buffered in "cu".)

Also included below is a sample /bin/sh script for dialing out on a Cermetek
modem, and logging in on another system (names & psw changed, natch!).
This is NOT portable, and depends on the local environment, but is included
as a sample of usage of "culog".

Rob Warnock

UUCP:	{ihnp4,ucbvax!dual}!fortune!redwood!rpw3
DDD:	(415)572-2607
USPS:	510 Trinidad Lane, Foster City, CA  94404

----first of two files-------first of two files-------first of two files-----
/*
 * culog.c - hack to control cu logging when talking to a non-UNIX system
 *
 * usage: culog [ <filename> ]	# usually from within cu with a ~! escape
 *				# If no filename given, logging is turned off.
 *
 * 840904 rpw3	This program uses the Berkeley ioctl TIOCSTI to stuff the
 *		magic characters into the "other" port of a "cu" connection
 *		to cause the "reverse path cu" to start/stop copying to a
 *		file. Restrictions of first implementation: Only /dev/cul0
 *		is used. Logging ALWAYS appends (never creates). Logging
 *		is always done in non-silent mode (you see what you get).
 *		(Even with that, it's QUITE useful!)
 *
 * Bugs:	Must be installed setuid root, since TIOCSTI is (for good
 *		reason) priviledged. Not safe for use in hostile environments.
 *		Do not use on ttys that can login.
 *
 * Futures:	- Flow control - use FIONREAD or something to make sure the
 *		  entire CULOG_ON string will fit into the tty's input.
 *		- Command-line options for tty name, CULOG_xxx strings.
 *		- Cleaner (i.e. ANY) interlock with uucp, etc.
 */

#include <sys/ioctl.h>

/* These have "extra" newlines at the beginning, which can sometimes get
 * into the log file, but better that than not being able to close a
 * connection that didn't end in a newline! ("cu" only sees these at BOL.)
 */
#define CULOG_ON	"\n~>>%s\n"	/* Append, leaving tty copy on */
#define CULOG_OFF	"\n~>\n"

#define CUDEV		"/dev/cul0"	/* (future) could be an arg */

main(argc,argv)
int argc;
char **argv;
{
	register char *p;
	register int cul0;
	char buf[1024];			/* must hold CULOG_ON and a filename */

	if((cul0 = open(CUDEV,1)) < 0){
		perror(argv[0]);
		exit(1);
	}
	if(argv[1])
		sprintf(buf, CULOG_ON, argv[1]);
	else
		sprintf(buf, CULOG_OFF);

	for(p = buf; *p != '\0'; ++p){
		if(ioctl(cul0, TIOCSTI, p) != 0){
			perror(argv[0]);
			exit(1);
		}
	}
	close(cul0);
	exit(0);
}
----second of two files-------second of two files-------second of two files-----
#! /bin/sh
# Script to dial up system XYZ and log on, with a log file.
# Notice the first 20 lines or so is run in the background.
# Bugs:	(1) NO error checking. Depends on the user watching, and
#	    killing the background job if things "go south".
#	(2) Hacked up from working code to add lots of comments. Not tested.
#	(3) Carriage returns <^M> changed to two chars "^" and "M".
#	    You need to change them back manually.

# run this whole thing (...) in the background:
(stty raw -echo		#since "cu" hasn't run yet
 sleep 5		#wait for "cu" to run
 culog XYZ.log.tmp	#open the log file (will also log the dial-up sequence)
 sleep 2
 echo ; echo -n '^M'	#wake up the Cermetek
 echo ; echo -n '^M'
 sleep 2		#wait across banner message
 echo -n 'xxxyyyy^M'	#the local Telenet number
 sleep 25
 echo -n '^M'		#step through the initial Telenet connection
 echo -n '^M' ; echo -n '^M'
 sleep 1
 echo -n 'c 01234567^M'	#connect to host
 sleep 5		#usually enough - has been known to fail
 echo -n 'my.name^M'	#the hazard is typing your password to Telenet
 sleep 3		#(which hardly cares!) or to the other system (ugh!)
 echo -n 'my.psw^M'
 sleep 1
 ) >/dev/cul0 &

cu -s 1200		#actually run "cu" (finally!)

# "cu" is done. Do the following in the background... can be slow.
# Fix up the log, since it has <CR><LF> sequences in it instead of
# just <NL>, and since any backspace/retyping you do IS logged.
# Change stuff like "Decmeber^H^H^H^H^Hember" into "December",
# which makes the log (usually) look like what the other end saw.
# Make any other line garbage printable (cat -v). Sequence the log --
# "date6" is another little script that prints the date as 6 chars: 841231.

( tr -d '\015\002\033' | col -b | cat -v
  rm -f XYZ.log.tmp
  ) < XYZ.log.tmp >> XYZ.log.`date6` &

# end of script