tlh@pbhacker.UUCP (Lee Hounshell) (07/16/88)
I've had a few requests for a repost of the fixed version of phdaemon.. for those of you not familiar with it, phdaemon will monitor both incoming and outgoing calls on your Unix PC. enjoy. Lee Hounshell -----cut here----- /************************************************************************\ ** ** ** Program name: phdaemon.c (Phone Daemon) ** ** Programmers: original version - Paul J. Condie (UUCP=pcbox!pjc) ** ** modified version - Lenny Tropiano (UUCP=icus!lenny) ** ** fixes/enhancements - Lee Hounshell (UUCP=pbhacker!tlh)** ** kernel access rtns - Michael Ditto (ford@crash.CTS.COM)** ** Date: December 13, 1987 ** ** ** ************************************************************************** ** ** ** Program use: Program is run as a daemon process from the boot ** ** procedure /etc/rc. It can be placed in /etc/daemons/ ** ** and will be started up apon system boot. This program ** ** monitors the data line (defined as /dev/ph1) for ** ** any kind of activity (or lack thereof) and displays ** ** the information in the Phone Managers window. Freeing ** ** up any other windows from being allocated for that use ** ** ** ** This program checks for DATA or VOICE, UUCP logins, ** ** User logins, UUCP outgoing, Internal use of outgoing ** ** modem. This process will terminate if the /etc/ph ** ** process is terminated. ** ** ** ** Enhancements: Bugs in properly detecting incoming calls have been ** ** fixed. The program now reports stray lock files in ** ** the status window. Errors are reported by placing ** ** "ERROR" in the status window. User logins and errors ** ** are now logged in the "/usr/adm/phdaemon.log" file. ** ** ** \************************************************************************/ #include <stdio.h> #include <fcntl.h> #include <errno.h> #include <signal.h> #include <status.h> #include <sys/types.h> #include <sys/window.h> #include <sys/stat.h> #include <sys/tune.h> #include <sys/proc.h> #include <sys/user.h> #include <sys/dir.h> #include <sys/ph.h> #include <sys/phone.h> #include <nlist.h> #include <pwd.h> #include <utmp.h> #include <time.h> #define SLEEP 15 /* Sleep time (interval between)*/ #define SNOOZE 5 /* Short Sleep time (short time)*/ #define NICE 5 /* Niceness value */ #define LINE "ph1" /* /etc/utmp user for DATA2 */ #define BEEP "\07\07" /* ring the bell */ #define PHPID "/usr/lib/ua/phpid" /* File has pid of /etc/ph */ #define LOCKDIR "/usr/spool/uucp" /* UUCP Lock Directory */ #define LOCKFIL "LCK.." /* Lock file prefix */ #define OFFSET sizeof(struct phdef) /* kernel offset (0 for ph0) */ #define LOGFILE "/usr/adm/phdaemon.log" /* login tracking file */ /* Command to locate window device in use by /etc/ph */ #define WINDCMD "ps -p%d | grep ph | cut -c9-11" #define ESC 27 #define BOLD 1 #define REV 7 #define ROW 1 #define COL 24 #define ERROR ":%c[%dm ERROR %c[0m" /* an error was detected */ #define INCOMING "<%c[%dm%-8.8s%c[0m" /* Incoming call string */ #define OUTGOING ">%c[%dm%-8.8s%c[0m" /* Outgoing call string */ #define IDLE "%c[0m: IDLE " /* Idle phone device */ #define LOGIN "<LOGIN " /* Incoming login */ #define BLANK ": " #define UUCICO "%c[%dm%cUUCICO %c[0m"/* Incoming undetermined uucico */ #define HOME "%c[%d;%dH" /* Position cursor in a window */ /* Types of calls */ #define IN_USER 1 /* User login */ #define OUT_USER 2 /* User use of on board modem */ #define UUCP 3 /* UUCP login or dial out */ #define LPROCESS 4 /* Login login */ #define PPROCESS 5 /* Pending login */ int wfd; /* Window file descriptor */ int kmemfd; /* /dev/kmem file descriptor */ int memfd; /* /dev/mem file descriptor */ int MAXPROC; /* max processes available */ extern long lseek(); /* lseek(2) function */ void read_kmem(); /* function to read memory */ void read_mem(); /* function to read memory */ char *cur_time(); /* function to return sys time */ char buffer[BUFSIZ]; /* buffer for strings */ char userlogin[12]; /* user login name */ char lockph[64]; /* currently monitored LCK file */ char windev[10]; /* window device of /etc/ph */ struct proc proc; /* Process block read from kmem */ int phpid; /* Process id of /etc/ph */ FILE *log_file; /* /usr/adm/phdaemon.log */ struct nlist unixsym[] = { /* /unix name list of symbols */ { "tuhi", }, { "proc", }, { "phndef", }, { NULL, }, }; /* Program lists for identification */ struct programs { /* CUSTOMIZE TO FIT YOUR NEEDS */ char *name; int type; } prog[] = { { "sh", IN_USER }, /* User program when logged in */ { "ksh", IN_USER }, /* User program when logged in */ { "cu", OUT_USER }, /* Program used to dial out */ { "kermit", OUT_USER }, /* Program used to dial out */ { "async_main", OUT_USER }, /* Program used to dial out */ { "term", OUT_USER }, /* Program used to dial out */ { "uucico", UUCP }, /* UUCP program dial-in/out */ { "uusched", UUCP }, /* UUCP program dial-in/out */ { "login", LPROCESS }, /* Login process */ { "getty", LPROCESS }, /* Login process */ { "uugetty", LPROCESS }, /* Login process */ { "", PPROCESS }, /* FAILS all cases */ }; main(argc,argv) int argc; char *argv[]; { FILE *fp, *pfp; int terminate(); if (fork() != 0) { /* detach process-daemon */ exit(0); } nice(NICE); /* Be a little nice */ signal (SIGHUP, SIG_IGN); signal (SIGINT, SIG_IGN); signal (SIGTERM, terminate); if ((log_file = fopen(LOGFILE, "a")) == NULL) { exit(1); } setbuf(log_file, (char *) 0); setup(); /* setup /dev/kmem and /unix */ if (access(PHPID, 0) == -1) { sprintf(buffer, "phone manager file %s does not exist", PHPID); werror(buffer,0); } if ((fp = fopen(PHPID,"r")) == NULL) { sprintf(buffer, "can't open file %s", PHPID); werror(buffer,0); } fscanf(fp,"%d",&phpid); /* read the process id of /etc/ph */ fclose(fp); if (!findproc(phpid)) { errno = ESRCH; werror("phone manager /etc/ph not running",0); } sprintf(buffer,WINDCMD,phpid); if ((pfp = popen(buffer,"r")) == NULL) { werror("can't open pipe to 'ps' command",0); } if (fgets(buffer,3,pfp) == NULL) { werror("nothing returned from pipe",1); } pclose(pfp); sprintf(windev,"/dev/%s",buffer); setpgrp(); if ((wfd = open(windev,O_RDWR)) == -1) { sprintf(buffer, "can't open %s", windev); werror(buffer,0); } close(0); dup(wfd); close(1); dup(wfd); close(2); dup(wfd); daemon_process(); terminate(); } daemon_process() { int lockfd, calltype; short lockpid; char idle[20], command[DIRSIZ], /* Command of program running */ *findmachine(), *getcommand(), machine[12]; struct phdef phblock; struct passwd *pwent, *getpwnam(), *getpwuid(); struct utmp *getutid(), *utmp, uph1; int dfd; /* Directory file descriptor */ int rflag = 1, beep = 1, fnd_user = 0, wait_a_bit = 0; static struct direct dirbuf; /* Directory entry buffer */ home_cursor(); sprintf(idle, IDLE, ESC); write(0,idle,strlen(idle)); while (findproc(phpid)) { /* Process still exists */ if ((dfd = open(LOCKDIR, O_RDONLY)) == -1) werror("can't open lock directory",0); while (1) { if (rflag) { if (read(dfd, &dirbuf, sizeof (struct direct)) != (sizeof (struct direct))) break; if ((dirbuf.d_ino != 0) && (strncmp(dirbuf.d_name, LOCKFIL, 5) == 0)) { sprintf(lockph,"%s/%s",LOCKDIR,dirbuf.d_name); rflag = 0; } else continue; } else sleep(SNOOZE); /* Take a few ZZzzz... */ read_kmem(&phblock, (unixsym[2].n_value + OFFSET), (long)sizeof (struct phdef)); if (phblock.p_lineparam & DATA) { /* Check lock file existence */ if (access(lockph,0) == -1) { home_cursor(); write(0,idle,strlen(idle)); beep = rflag = 1; continue; /* no file found */ } if ((lockfd = open(lockph, O_RDONLY)) == -1) { sprintf(buffer, "can't open %s", lockph); werror(buffer,0); } read(lockfd, &lockpid, sizeof(short)); read(lockfd, &lockpid, sizeof(short)); /* HDB UUCP */ close(lockfd); if (!findproc(lockpid)) { char lbuf[20]; if (strncmp(&dirbuf.d_name[5], "ph0", 3)) { LCK_ERROR: sprintf(lbuf, "%c[%dm?%-8.8s%c[0m", ESC, REV, &dirbuf.d_name[5], ESC); home_cursor(); write(0,lbuf,strlen(lbuf)); } continue; } sprintf(command,"%s",getcommand()); calltype = check_command(command); if (calltype == PPROCESS) { if (!strncmp(&dirbuf.d_name[5], "ph0", 3)) { rflag = 1; STILL_THERE: strcpy (uph1.ut_id, LINE); /* for getuid */ uph1.ut_type = LOGIN_PROCESS; /* Find out whats happening with data line */ utmpname ("/etc/utmp"); /* rewind */ utmp = getutid (&uph1); if (utmp == NULL || strcmp (utmp->ut_id,LINE)) { werror("Internal Error: /etc/utmp",0); } if (utmp->ut_type == USER_PROCESS) { if (wait_a_bit) { wait_a_bit = 0; sleep(SNOOZE); continue; } if (beep) { sprintf(buffer,INCOMING, ESC,REV,utmp->ut_user,ESC); home_cursor(); write(0,buffer,strlen(buffer)); write(0,BEEP,2); beep = 0; fprintf(log_file, "USER %s logged IN at %s\n", utmp->ut_user, cur_time()); fnd_user = 1; } sleep(SNOOZE); goto STILL_THERE; } if (fnd_user) { fprintf(log_file, "USER %s logged OUT at %s\n", utmp->ut_user, cur_time()); wait_a_bit = 1; fnd_user = 0; continue; } } else goto LCK_ERROR; } wait_a_bit = 1; setpwent(); /* rewind /etc/passwd */ if (calltype == OUT_USER) { if ((pwent = getpwuid(proc.p_uid)) == NULL) { sprintf(buffer, "cannot locate uid %d in /etc/passwd", proc.p_uid); werror(buffer,1); } } else if (calltype == IN_USER) { utmpentry(LINE); if (*userlogin == NULL) { write(0, LOGIN, strlen(LOGIN)); continue; } if ((pwent = getpwnam(userlogin)) == NULL) { sprintf(buffer, "cannot locate user %s in /etc/passwd", userlogin); werror(buffer,1); } } endpwent(); /* close /etc/passwd */ home_cursor(); switch (calltype) { case OUT_USER: if (beep) { sprintf(buffer,OUTGOING,ESC,REV, pwent->pw_name, ESC); write(0,buffer,strlen(buffer)); beep = 0; } break; case UUCP: sprintf(machine,"%s",(char *)findmachine()); utmpentry(LINE); if (*userlogin == NULL) { if (*machine != NULL) { sprintf(buffer,OUTGOING, ESC,BOLD,machine,ESC); } else { sprintf(buffer,UUCICO,ESC, BOLD,'>',ESC); } } else { if (*machine != NULL) { sprintf(buffer,INCOMING, ESC,BOLD,machine,ESC); } else { sprintf(buffer,UUCICO, ESC,BOLD,'<',ESC); } } endutent(); if (beep) { write(0,buffer,strlen(buffer)); write(0,BEEP,2); beep = 0; } break; } } } close(dfd); if (wait_a_bit) sleep(SLEEP); } } check_command(cmd) /* Check the list of commands */ char *cmd; { register i; i = 0; while (*(prog[i].name) != NULL) { if (strcmp(prog[i].name, cmd) == 0) return(prog[i].type); i++; } return(PPROCESS); } utmpentry(line) char *line; { struct utmp *utent, *getutent(); setutent(); while ((utent = getutent()) != NULL) { if (strncmp(utent->ut_line,line,strlen(line)) == 0 && utent->ut_type == USER_PROCESS) { sprintf(userlogin,"%s",utent->ut_user); endutent(); return; } } endutent(); *userlogin = NULL; } home_cursor() { sprintf(buffer,HOME,ESC,ROW,COL); write(0,buffer,7); } int terminate() { home_cursor(1); write(0,BLANK,strlen(BLANK)); close(wfd); close(kmemfd); close(memfd); fclose(log_file); exit(0); } setup() { struct tunable tune; if ((kmemfd=open("/dev/kmem", O_RDWR)) == -1) werror("can't open /dev/kmem",0); if ((memfd=open("/dev/mem", O_RDWR)) == -1) werror("can't open /dev/mem",0); if (nlist("/unix", unixsym)) werror("can't nlist /unix",0); read_kmem((char *)&tune, (unixsym[0].n_value), (long) sizeof tune); read_kmem((char *)&(unixsym[1].n_value), (unixsym[1].n_value), (long)sizeof (unixsym[1].n_value)); MAXPROC = tune.nproc; } void read_kmem(caddr, kaddr, nbytes) char *caddr; long kaddr; long nbytes; { if (lseek(kmemfd, kaddr, 0)<0L || read(kmemfd, caddr, (unsigned)nbytes) != nbytes ) werror("can't read /dev/kmem",0); } void read_mem(caddr, paddr, nbytes) char *caddr; long paddr; long nbytes; { if (lseek(memfd, paddr, 0)<0L || read(memfd, caddr, (unsigned)nbytes) != nbytes) werror("can't read /dev/mem",0); } int findproc(pid) int pid; { register i; for (i=0 ; i<MAXPROC ; ++i) { read_kmem((char *)&proc, (long)&((struct proc *)(unixsym[1].n_value))[i], (long)sizeof proc); if (proc.p_pid == pid) return 1; } return 0; } char *findmachine() { int dfd; /* Directory file descriptor */ static struct direct dirbuf; /* Directory entry buffer */ if ((dfd = open(LOCKDIR, O_RDONLY)) == -1) werror("can't open lock directory",0); while (read(dfd, &dirbuf, sizeof (struct direct)) == (sizeof (struct direct))) { if ((dirbuf.d_ino != 0) && (strncmp(dirbuf.d_name,LOCKFIL,5) == 0)) { if ((strncmp((char *)&dirbuf.d_name[5],"ph",2) != 0) && (strncmp((char *)&dirbuf.d_name[5],"tty",3) != 0)) { close(dfd); return((char *)&dirbuf.d_name[5]); } } } close(dfd); return(NULL); } werror(errstr, mode) char *errstr; int mode; { extern char *sys_errlist[]; /* Log message in /usr/adm/phdaemon.log */ if (mode == 0) { fprintf(log_file, "%s: %s - %s AT %s", __FILE__, errstr, sys_errlist[errno], cur_time()); } else { fprintf(log_file, "%s: %s AT %s", __FILE__, errstr, cur_time()); } /* Warn user about error */ home_cursor(); sprintf(buffer, ERROR, ESC, BOLD, ESC); write(0,buffer,strlen(buffer)); fclose(log_file); exit(1); } char *getcommand() { static struct user users; long upage; if (!proc.p_stat || proc.p_stat == SIDL || proc.p_stat == SZOMB) return 0; if (!(proc.p_flag & SLOAD)) { sprintf(buffer,"can't handle swapped process %d (flag=%05x)", proc.p_pid, proc.p_flag); werror(buffer,1); } upage = (long)ctob(proc.p_addr[0]); read_mem((char *)&users, upage + U_OFFSET, (long) sizeof (struct user)); return(users.u_comm); } char *cur_time() { long tim; char *ptr; tim = time((long *) 0); ptr = ctime(&tim); if (strlen(ptr)) ptr[strlen(ptr) - 1] = 0; return ptr; }
lenny@icus.UUCP (Lenny Tropiano) (07/18/88)
[I know this is not a source, it's really a discussion on one, but we don't have a group called unix-pc.sources.d -- I directed all other discussions to unix-pc.general - LBT] In article <112@pbhacker.UUCP> tlh@pbhacker.UUCP (Lee Hounshell) writes: |>I've had a few requests for a repost of the fixed version of phdaemon.. |>for those of you not familiar with it, phdaemon will monitor both |>incoming and outgoing calls on your Unix PC. |> Some phdaemon history... The phdaemon everyone is familiar with was probably the version I wrote. I've been running it here for over 10 months without any problems. There was some work done by Lee Hounshell (tlh@pbhacker) to avoid those "popup smgr windows" that stopped all cron processes in this version of phdaemon, of which he used the version of phdaemon I wrote. Paul Condie (pjc@pcbox) wrote the *original* phdaemon back in October 1987, and posted his version to the net. It had some deficiencies and problems, so I decided to do a total rewrite and get a new-and-improved version. I posted mine back in November, 1987. It had two problems which I addressed later with patches. One was the handling of LCK..ph* files and possibly getting in a race-condition and causing the popup window to show. The second was the popup windows in the error-handling routine, this was later changed to a [!!] icon which did not halt cron processes. |> |>/************************************************************************\ |> ** ** |> ** Program name: phdaemon.c (Phone Daemon) ** |> ** Programmers: original version - Paul J. Condie (UUCP=pcbox!pjc) ** |> ** modified version - Lenny Tropiano (UUCP=icus!lenny) ** |> ** fixes/enhancements - Lee Hounshell (UUCP=pbhacker!tlh) ** |> ** kernel access rtns - Michael Ditto (ford@crash.CTS.COM) ** Note this was a total rewrite... I did give credit to Paul and Mike in my comment section which was somehow changed (for what reason) by Lee Hounshell. I would appreciate if the header information was left in tack, and you just added your revision history and your comments where appropriate. [I thought this was somehow understood when people add to someone else's programs] In the future anyone who modifies one of my programs, please mail me the context diffs so that I can apply them to my source and keep it up to date. This avoids many people having different copies and each supporting their own version. It would be much better to have one person (usually the original author) handle all revision changes and patches. When someone on the net says their "phdaemon isn't working" (for example) each of us wouldn't have to look to figure out who's is at fault. |> ** Date: December 13, 1987 ** |> ** ** |> ************************************************************************ |> ** ** |> ** Program use: Program is run as a daemon process from the boot ** |> ** procedure /etc/rc. It can be placed in /etc/daemons/ ** |> ** and will be started up apon system boot. This program ** |> ** monitors the data line (defined as /dev/ph1) for ** |> ** any kind of activity (or lack thereof) and displays ** |> ** the information in the Phone Managers window. Freeing ** |> ** up any other windows from being allocated for that use ** |> ** ** |> ** This program checks for DATA or VOICE, UUCP logins, ** |> ** User logins, UUCP outgoing, Internal use of outgoing ** |> ** modem. This process will terminate if the /etc/ph ** |> ** process is terminated. ** |> ** ** |> ** Enhancements: Bugs in properly detecting incoming calls have been ** |> ** fixed. The program now reports stray lock files in ** |> ** the status window. Errors are reported by placing ** |> ** "ERROR" in the status window. User logins and errors ** |> ** are now logged in the "/usr/adm/phdaemon.log" file. ** |> ** ** |>\************************************************************************/ |> ... [ rest of the source omitted ] ... Note: I haven't tested Lee's version, although I assume it works as he wouldn't have posted it if it didn't. The only thing that I see might be a problem is the printing of "ERROR" in the ph-window. That will be erased if the phone is picked up (ie. VOICE 1: ACTIVE) or it rings (ie. VOICE 1: <RING). For historical purposes here is the original header/comment block with the actual credits, organization name (which has since changed to ICUS Software Systems), and date in tack. /************************************************************************\ ** ** ** Program name: phdaemon.c (Phone Daemon) ** ** Programmer: Lenny Tropiano UUCP: ...icus!lenny ** ** Organization: ICUS Computer Group ** ** Date: November 8, 1987 ** ** ** ************************************************************************** ** ** ** Credits: Thanks to Michael Ditto (ford@crash.CTS.COM) for his ** ** Programs fuser and renice which aided me to write the ** ** Kernel accessing routines. ** ** ** ** Again I want to *THANK* Mike Ditto for his infinite ** ** wisdom when it came to the "internals" of the UNIXPC ** ** ** ** Thanks to Paul J. Condie (pcbox!pjc) for his original ** ** idea of the phdaemon program and some tips on writing ** ** my own. ** ** ** ************************************************************************** ** ** ** Program use: Program is run as a daemon process from the boot ** ** procedure /etc/rc. It can be placed in /etc/daemons/ ** ** and will be started up apon system boot. This program ** ** monitors the data line (defined as /dev/ph1) for ** ** any kind of activity (or lack thereof) and displays ** ** the information in the Phone Managers window. Freeing ** ** up any other windows from being allocated for that use ** ** ** ** This program checks for DATA or VOICE, UUCP logins, ** ** User logins, UUCP outgoing, Internal use of outgoing ** ** modem. This process will terminate if the /etc/ph ** ** process is terminated. ** ** ** \************************************************************************/ -- enclosed below are the Makefile and the original README text that -- was omitted from the Lee's phdaemon version. --- 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 README # Wrapped by lenny@icus on Sun Jul 17 18:44:07 1988 PATH=/bin:/usr/bin:/usr/ucb ; export PATH if test -f 'Makefile' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'Makefile'\" else echo shar: Extracting \"'Makefile'\" \(664 characters\) sed "s/^X//" >'Makefile' <<'END_OF_FILE' X# X# Makefile to compile phdaemon.c (Phone Daemon) X# By Lenny Tropiano X# (c)1987 ICUS Computer Group UUCP: ...icus!lenny X# XCFLAGS=-v -O XLDFLAGS=-s XLIBS=/lib/crt0s.o /lib/shlib.ifile XDEST=/etc/daemons/ X# Xphdaemon.o: X $(CC) $(CFLAGS) -c phdaemon.c X# Xphdaemon: phdaemon.o X @echo "Loading ..." X $(LD) $(LDFLAGS) -o phdaemon phdaemon.o $(LIBS) X# X# You need to be super-user to do this. X# X/etc/daemons: X mkdir /etc/daemons X chmod 755 /etc/daemons X# Xinstall: phdaemon /etc/daemons X cp phdaemon /etc/daemons/ X chown root /etc/daemons/phdaemon X chgrp bin /etc/daemons/phdaemon X chmod 4750 /etc/daemons/phdaemon X @echo "Phone Daemon started." X /etc/daemons/phdaemon END_OF_FILE if test 664 -ne `wc -c <'Makefile'`; then echo shar: \"'Makefile'\" unpacked with wrong size! fi # end of 'Makefile' fi if test -f 'README' -a "${1}" != "-c" ; then echo shar: Will not clobber existing file \"'README'\" else echo shar: Extracting \"'README'\" \(4692 characters\) sed "s/^X//" >'README' <<'END_OF_FILE' XThe phone daemon program was written to keep all those people who jump Xto login when they hear the relay click on the UNIX pc. The program Xwas first written by Paul Condie (pcbox!pjc) for this exact reason! X XI give thanks to Paul and Michael Ditto (ford@crash.CTS.COM) for his Xexpertise in the internals of the AT&T UNIX pc kernel. X XAfter unpacking the shar file, "su" and become root. Then type: X X # make install X XThis will create the phdaemon executable and copy it into /etc/daemons/. XThis directory is looked at by /etc/rc apon boot-up to start all system Xdaemons. If the directory doesn't exist, it will be created. Make sure Xthe following code is in /etc/rc somewhere: X X Xif [ -d /etc/daemons ] Xthen X DAEMONS=`ls /etc/daemons/*` X if [ $? != 0 ] ; then DAEMONS=""; fi X for i in $DAEMONS X do X if [ -x $i ] X then nohup $i > /dev/null 2>&1 & X fi X done Xfi X XThings to know about the Phone Daemon. This program is configured Xfor a multi-line system, where ph0 is the VOICE only line, and ph1 is Xthe DATA/VOICE line. The program will need a few revisions to allow Xto work with a ONE line system. If someone cares to do this, please Xmail me the context diffs. X XThe program will display: X X DATA 2:IDLE - obviously when the line is idle. X DATA 2:<LOGIN - Login process (don't know who or what it is yet) X X DATA 2:>PENDING - A process is going out, not sure what it is. X DATA 2:<PENDING - A process is coming in, not sure what it is. X X The following "user" is in INVERSE video. X X DATA 2:>user - When a user locks the modem for outgoing calls X DATA 2:<user - When a user locks the modem when coming in. X DATA 2:>ph1 - When a user locks (not sure what user) going out X (Generally happens when the user uses the async_main X program to dial out) -- The lock file doesn't reflect X the pid of the locking process. -- POSSIBLE BUG? X X The following "machine" is in BOLD video. X X DATA 2:<UUCICO - It is a uucico process but don't know what machine X as of yet. (coming in) X DATA 2:>machine - When a uucico process locks modem going out. X DATA 2:<machine - When a uucico process locks modem coming in. X X---- ---- ---- ---- ---- ---- ---- ---- ---- ---- ---- ---- ---- ---- ---- ---- X XThe program doesn't allocate another window, it just uses the window Xallocated to the /etc/ph process. This will not waste another window. X XThe following parameters can be changed to your liking: X X#define SLEEP 15 /* Sleep time (interval between)*/ X#define SNOOZE 5 /* Short Sleep time (short time)*/ X#define NICE 5 /* Niceness value */ X XThe program is set to a nice value of 25, and it sleeps for 15 seconds Xbetween checks. This will keep the process from bogging down the CPU with Xwasted cycles. When there is a "LOGIN or UUCICO" process that is still Xundetermined, the program will only SNOOZE for 5 seconds, to try to catch Xwho or what is logging in before they logout. X X XThe following is a table of the programs to determine what kind of process Xis going using the modem. The following are my choices, more can be added Xto match what you system requires. Each program must have a type for either X X IN_USER - user login X OUT_USER - user dialing out X UUCP - uucp process X LPROCESS - login process X X { "sh", IN_USER }, /* User program when logged in */ X { "ksh", IN_USER }, /* User program when logged in */ X { "cu", OUT_USER }, /* Program used to dial out */ X { "kermit", OUT_USER }, /* Program used to dial out */ X { "async_main", OUT_USER }, /* Program used to dial out */ X { "term", OUT_USER }, /* Program used to dial out */ X { "uucico", UUCP }, /* UUCP program dial-in/out */ X { "uusched", UUCP }, /* UUCP program dial-in/out */ X { "login", LPROCESS }, /* Login process */ X { "getty", LPROCESS }, /* Login process */ X { "uugetty", LPROCESS }, /* Login process */ X { "", PPROCESS }, /* FAILS all cases: PENDING */ X XNote: term is a program I wrote that acts as a terminal program, I left Xit there for example purposes. X XPlease report any bugs, suggestions and problems to me: X X============================ US MAIL: Lenny Tropiano, ICUS Computer Group X IIIII CCC U U SSSS PO Box 1 X I C C U U S Islip Terrace, New York 11752 X I C U U SSS PHONE: (516) 968-8576 [H] (516) 582-5525 [W] X I C C U U S AT&T MAIL: ...attmail!icus!lenny TELEX: 154232428 X IIIII CCC UUU SSSS UUCP: X============================ ...{uunet!godfre, harvard!talcott}!\ X ...{ihnp4, boulder, mtune, skeeve, ptsfa}! >icus!lenny X"Usenet the final frontier" ...{cmcl2!phri, hoptoad}!dasys1!/ END_OF_FILE if test 4692 -ne `wc -c <'README'`; then echo shar: \"'README'\" unpacked with wrong size! fi # end of 'README' fi echo shar: End of shell archive. exit 0 -- Paper-net: Lenny Tropiano | @-net: lenny@icus.UUCP ICUS Software Systems | !-net: ...att \ PO Box 1 | boulder \ Islip Terrace, NY 11752 | talcott !icus!lenny Vocal-net: (516) 582-5525 [work] | pacbell / (516) 968-8576 [home] | sbcs / Telex-net: 154232428 ICUS | Another-net: attmail!icus!lenny