write/talk detection

Dan Bernstein brnstnd at kramden.acf.nyu.edu
Tue Oct 30 10:07:21 AEST 1990


In article <1990Oct29.195519.24411 at ecn.purdue.edu> irick at ecn.purdue.edu (GarBear Irick) writes:
> OK, I have an easy one for you wizards out there (Dan???  Dave???:)...

Can tell this guy hasn't been around too long. :-)

> Is there any way, using sh, C, black magic, etc. to detect when another user
> has done a write or a talk-request to yor terminal?

Not reliably (except with black magic). The best solution is to modify
write and talk to do something intelligent when they can't get through.
As an example, enclosed is talkanswer, a quick kludge to new BSD talk to
have it record a message (and send it through the mail) whenever the
target isn't logged on. It also works for someone who's just turned
messages off. 

> "csh | filter_to_grep_for_writes | tee /dev/tty",

The problem with this sort of solution is that talk and write don't
allow intelligent multiplexing. Sure, a human can parse several outputs
from different sources without any clues, but a program will have a hard
time separating the talk invitation from other tty activity. That's the
price you pay for non-modular (immodular?) design.

> I am sure pty will do it (right Dan?), but alas we don't
> have pty installed at our site.

Yes, pty can handle csh's insistence on talking to a terminal. But it
can't fix an interface that *assumes* interactivity. The normal mode of
multiplexing tty outputs is exactly such an interface.

Oh, btw, talkanswer depends on pty. Maybe you can convince your sysadmin
to install them both...

---Dan
Difference between Multics and Ada: Multics was ten years *ahead* of its time.

#! /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:  README talkanswer talkdiff
# Wrapped by brnstnd at kramden on Fri Sep 14 12:15:50 1990
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f 'README' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'README'\"
else
echo shar: Extracting \"'README'\" \(1216 characters\)
sed "s/^X//" >'README' <<'END_OF_FILE'
XThis is talkanswer 1.0, an answering machine for BSD talk. Once you've
Xinstalled it, if anyone talks to a user not logged on to your machine,
Xtalkanswer will answer instead and send the message through normal mail.
XAll the work is done by a shell script that you can easily customize.
X
X
XDon't try to install talkanswer unless you have the new talk. To see if
Xyou have new talk, check for a line containing 518 in /etc/services.
X
XYou need the pty program and setuid utility. pty is available upon
Xrequest to brnstnd at nyu.edu or via anonymous ftp to 128.122.128.22.
Xsetuid is included in the authutil package, which is available from
Xuunet.uu.net:/comp.sources.unix/volume22/auth-utils/part*.
X
XYou need the talkd source to set up talkanswer. If you don't have the
Xsource, get it from uunet.uu.net:/bsd-sources/src/network/talkd.tar.Z.
XApply the patch in talkdiff and recompile.
X
XOnce you've successfully compiled talkd, hide /etc/ntalkd in a safe
Xplace and put the new talkd there.
X
XFinally, put talkanswer into a path that's in inetd's environment. If
Xyou want, change the talkanswer pathname in announce.c for this.
X
XSend comments or complaints to me, Dan Bernstein, at brnstnd at nyu.edu.
XThis is version 1.0, 9/14/90.
END_OF_FILE
if test 1216 -ne `wc -c <'README'`; then
    echo shar: \"'README'\" unpacked with wrong size!
fi
# end of 'README'
fi
if test -f 'talkanswer' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'talkanswer'\"
else
echo shar: Extracting \"'talkanswer'\" \(739 characters\)
sed "s/^X//" >'talkanswer' <<'END_OF_FILE'
X#!/bin/sh
XTERM=vt100;export TERM
X{
X  /bin/setuid "$1" touch /tmp/talkans.$$
X  until grep -s stablished /tmp/talkans.$$
X  do
X    sleep 3
X  done
X  /bin/setuid "$1" rm /tmp/talkans.$$
X  echo "This is the talkanswer system, answering for $1."
X  echo "Please leave your name after the beep."
X  echo "<beep>"
X  sleep 300
X  echo ""
X  echo "Thirty seconds left on the tape."
X  sleep 30
X  echo ""
X  echo "Thank you for calling."
X  echo "<beep>"
X  echo x | tr x '\003'
X} | {
X  echo "From: $2@$3"
X  echo "To: $1"
X  echo ""
X  /bin/setuid "$1" /usr/local/pty -dxuR /usr/ucb/talk "$2@$3" 2>&1
X} | {
X  /bin/setuid "$1" awk '{ print }
X/stablished/ { print "established" >"/tmp/talkans.'$$'" }'
X} | /usr/lib/sendmail -f"$2@$3" -F"talkanswer" "$1" &
Xexit 0
END_OF_FILE
if test 739 -ne `wc -c <'talkanswer'`; then
    echo shar: \"'talkanswer'\" unpacked with wrong size!
fi
chmod +x 'talkanswer'
# end of 'talkanswer'
fi
if test -f 'talkdiff' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'talkdiff'\"
else
echo shar: Extracting \"'talkdiff'\" \(1310 characters\)
sed "s/^X//" >'talkdiff' <<'END_OF_FILE'
X*** announce.c.orig	Sat Jun 18 17:10:48 1988
X--- announce.c	Fri Sep 14 11:33:11 1990
X***************
X*** 28,33 ****
X--- 28,34 ----
X  #include <sys/wait.h>
X  #include <errno.h>
X  #include <syslog.h>
X+ #include <pwd.h>
X  
X  #include <protocols/talkd.h>
X  
X***************
X*** 83,88 ****
X--- 84,96 ----
X  	FILE *tf;
X  	struct stat stbuf;
X  
X+ 	if (request->r_tty[0] == '/')
X+ 	 {
X+ 	  /* Answering machine. */
X+ 	  execlp("talkanswer","talkanswer",request->r_name,
X+ 		  request->l_name,remote_machine,(char *) 0);
X+ 	  return(FAILED);
X+ 	 }
X  	(void)sprintf(full_tty, "/dev/%s", request->r_tty);
X  	if (access(full_tty, 0) != 0)
X  		return (FAILED);
X*** process.c.orig	Sat Jun 18 17:10:49 1988
X--- process.c	Fri Sep 14 11:33:06 1990
X***************
X*** 122,129 ****
X  	/* see if the user is logged */
X  	result = find_user(mp->r_name, mp->r_tty);
X  	if (result != SUCCESS) {
X! 		rp->answer = result;
X! 		return;
X  	}
X  #define	satosin(sa)	((struct sockaddr_in *)(sa))
X  	hp = gethostbyaddr(&satosin(&mp->ctl_addr)->sin_addr,
X--- 122,129 ----
X  	/* see if the user is logged */
X  	result = find_user(mp->r_name, mp->r_tty);
X  	if (result != SUCCESS) {
X! 	  mp->r_tty[0] = '/';
X! 	  result = SUCCESS;
X  	}
X  #define	satosin(sa)	((struct sockaddr_in *)(sa))
X  	hp = gethostbyaddr(&satosin(&mp->ctl_addr)->sin_addr,
END_OF_FILE
if test 1310 -ne `wc -c <'talkdiff'`; then
    echo shar: \"'talkdiff'\" unpacked with wrong size!
fi
# end of 'talkdiff'
fi
echo shar: End of shell archive.
exit 0



More information about the Comp.unix.questions mailing list