pjc@pbhyf.UUCP (Paul Condie) (11/05/87)
/* AT&T UNIX PC - monitor data line, if you please. If you are one of those who everytime the obm (on board modem) clicks you scramble to logon or get out of vi to see who is trying to log in or if it is your uucp job finally coming across, then this might help. To compile just "make phdaemon". To run it must be started from the command line. If someone can get this to work with nohup(1) so that rc can start it at boot time, please send me the patch. */ --------------- as Rocky Balboa said - CUT ME ------------------------------- #ifndef LINT static char Sccsid[] = "%W% DeltaDate %G% ExtrDate %H%"; #endif /* ** PROGRAM: phdaemon ** Monitor data line (ph1). ** ** Displays who is using ph1 next to "DATA 2:" in the status line. ** "DATA 2: > name" - outbound call ** "DATA 2: < name" - inbound call ** If "name" is in reverse_video then uucp/mail is in progress and ** the machine you are talking to is displayed where "name" is. ** If "name" is bold and it is a inbound call then the login name ** of the person calling is displayed, otherwise "ph1" is displayed ** for the outbound call. I leave it up to you to guess who. ** ** You have to start it up from a $ prompt. Does not work ** if you try to nohup it. Therefore rc won't start it at ** boot time. ** ** AUTHOR: Paul J. Condie 10/87 ** {ihnp4!lll-crg,qantel,pyramid}!ptsfa!pbody!pcbox!pjc ** ** CONFIGURATION: ** Voice line on line 1 (ph0). ** Data line on line 2 (ph1). ** You should be able to change PHLINE to monitor a different ** data line but this has not been tested. */ #include <stdio.h> #include <fcntl.h> #include <sys/signal.h> #include <sys/types.h> #include <sys/stat.h> #include <sys/window.h> #include <utmp.h> #define TIMER 15 /* secs between checks */ #define PHLINE "ph1" /* ph line to monitor */ #define ROW 0 /* status window dimensions */ #define COL 216 /* in pixels */ #define HEIGHT 12 #define WIDTH 80 #define BELL 7 #define ESC 27 #define BOLD "[1m" #define DIM "[2m" #define REVERSE "[7m" #define NORMAL "[0m" #define CLEAR "[2J" #define DIALIN 1 #define DIALOUT 2 #define UUCPIN 3 #define UUCPOUT 4 #define INBOUND 5 #define OUTBOUND 6 #define LOCKFILE "/usr/spool/uucp/LCK.." int fd; /* phdaemon status window */ main () { extern unsigned alarm(); extern wakeup(); int bye(); struct stat Statbuf; struct uwdata uwdata; struct utdata utdata; struct utmp *getutid(); struct utmp *utmp; struct utmp uph1; FILE *popen(), *pp; char machine[10]; /* machine name */ char ws[80]; int WhichWay; int mode; strcpy (uph1.ut_id, PHLINE); /* init for getuid */ uph1.ut_type = LOGIN_PROCESS; fd = open ("/dev/window", O_RDWR); /* status window */ ioctl (fd, WIOCGETD, &uwdata); if (fork() != 0) { /* PARENT */ sleep (2); if (!isatty(0)) { /* nohup fix goes here */ } else /* executed from command line */ ioctl (0, WIOCSELECT); exit (0); } /* CHILD */ signal (SIGHUP, SIG_IGN); signal (SIGINT, SIG_IGN); signal (SIGQUIT, bye); setpgrp (); /* kick child out of house */ chdir ("/"); umask (0); close (0); dup (fd); close (1); dup (fd); close (2); dup (fd); close (fd); ioctl (0, WIOCPGRP); /* set controlling group */ uwdata.uw_x = COL; /* set window dimensions */ uwdata.uw_y = ROW; uwdata.uw_width = WIDTH; uwdata.uw_height = HEIGHT; uwdata.uw_uflags = NBORDER; ioctl (0, WIOCSETD, &uwdata); /* To get this process out of the Suspd/Rsume window */ utdata.ut_num = 3; strcpy (utdata.ut_text, "Status Manager"); ioctl (0, WIOCSETTEXT, &utdata); strcpy (machine, ""); while (1) { /* Set wakeup call */ signal (SIGALRM, wakeup); alarm (TIMER); pause (); alarm (0); /* Find out whats happening with data line */ utmpname ("/etc/utmp"); /* rewind file */ utmp = getutid (&uph1); if (utmp == NULL || strcmp (utmp->ut_id, PHLINE) != 0) { /* Internal Error */ continue; } if (strcmp (machine, "") != 0) { /* ** Check if data call is still in progress. ** If one data call ends and another starts up ** between wakeup calls, this code won't update ** the machine/login name. */ if (utmp->ut_type != LOGIN_PROCESS) continue; /* still in progress */ /* blank window */ sprintf (ws, "%c%s", ESC, CLEAR); write (0, ws, strlen(ws)); strcpy (machine, ""); } /* ** Check if a new data call has been started. */ if (utmp->ut_type == LOGIN_PROCESS) continue; /* getty on ph1 */ if (utmp->ut_type == USER_PROCESS) { /* ** If /usr/spool/uucp/LCK.. file exists ** then inbound uucp/mail in progress ** machine name = LCK..machine_name ** else someone has logged in ** user is in ut_user */ WhichWay = INBOUND; sleep (3); /* give uucp time to create LOCKFILE */ sprintf (ws, "ls %s%s", LOCKFILE, "*"); pp = popen (ws, "r"); while (fscanf (pp, "%s", ws) != EOF) { /* ** I ignore ph0 - voice and ** tty000 - external modem */ if (strcmp (PHLINE, "ph1") == 0) { if (strcmp (ws+21, "ph0") == 0) continue; } else if (strcmp (ws+21, "ph1") == 0) continue; if (strcmp (ws+21, "tty000") == 0) continue; strcpy (machine, ws+21); } pclose (pp); if (strcmp (machine, "") == 0) { mode = DIALIN; strcpy (machine, utmp->ut_user); } else mode = UUCPIN; } if (utmp->ut_type == DEAD_PROCESS) { /* ** if only /usr/spool/uucp/LCK..ph1 exists ** then a dial-out call is in progress ** else there sb 2 LCK.. files ** (LCK..ph1 and LCK..machine_name) ** outbound uucp/mail in progress */ WhichWay = OUTBOUND; sleep (2); /* give uucp time to create LOCKFILE */ sprintf (ws, "ls %s%s", LOCKFILE, "*"); pp = popen (ws, "r"); while (fscanf (pp, "%s", ws) != EOF) { if (strcmp (ws+21, "ph0") == 0) continue; if (strcmp (ws+21, "tty000") == 0) continue; if (strcmp (ws+21, "ph1") == 0) continue; strcpy (machine, ws+21); } pclose (pp); if (strcmp (machine, "") == 0) { mode = DIALOUT; strcpy (machine, PHLINE); } else mode = UUCPOUT; } /* show it man...show it */ sprintf (ws, "%c[1;1H", ESC); /* home cursor */ write (0, ws, strlen(ws)); sprintf (ws, "%c%c%c", BELL, BELL, BELL); write (0, ws, strlen (ws)); sleep (1); write (0, ws, strlen (ws)); write (0, ws, strlen (ws)); if (WhichWay == INBOUND) sprintf (ws, "%c%s%c%s<%c%s", ESC, REVERSE, ESC, BOLD, ESC, NORMAL); else sprintf (ws, "%c%s%c%s>%c%s", ESC, REVERSE, ESC, BOLD, ESC, NORMAL); write (0, ws, strlen(ws)); if (mode == DIALOUT || mode == DIALIN) sprintf (ws, "%c%s %-6s%c%s", ESC, BOLD, machine, ESC, NORMAL); else sprintf (ws, "%c%s %-6s%c%s", ESC, REVERSE, machine, ESC, NORMAL); write (0, ws, strlen(ws)); } /* end while (1) */ close (fd); exit (0); } wakeup () { } bye () { close (fd); exit (0); } /* pjc 10/87 */