home *** CD-ROM | disk | FTP | other *** search
Text File | 1992-06-20 | 31.8 KB | 1,168 lines |
- Newsgroups: comp.sources.misc
- From: brianb@julian.uwo.ca (Brian Borowski)
- Subject: v30i071: sendopr - Send messages to the operator, Part01/01
- Message-ID: <1992Jun20.171221.2372@sparky.imd.sterling.com>
- X-Md4-Signature: 52786afab6e8bb1342cb52aa4402ad63
- Date: Sat, 20 Jun 1992 17:12:21 GMT
- Approved: kent@sparky.imd.sterling.com
-
- Submitted-by: brianb@julian.uwo.ca (Brian Borowski)
- Posting-number: Volume 30, Issue 71
- Archive-name: sendopr/part01
- Environment: UNIX
-
- >From the README file:
-
- This software has been tested on Sun3, Sun4, mips, and SGI.
- It is currently in use here on these platforms.
- The original author was Hyman Wong, and there have been significant
- upgrades and modifications made by Reg Quinton and myself.
-
- Sendopr allows users to send messages to the operator.
- It is a queuing system which delivers messages to an operator's
- Xterminal. Xmessage is used to display the information.
- ------
- #! /bin/sh
- # This is a shell archive. Remove anything before this line, then feed it
- # into a shell via "sh file" or similar. To overwrite existing files,
- # type "sh file -c".
- # The tool that generated this appeared in the comp.sources.unix newsgroup;
- # send mail to comp-sources-unix@uunet.uu.net if you want that tool.
- # Contents: README BEWARE Makefile sendopr.c sendopr.man sendoprd.c
- # sendoprd.h sendoprd.man tcpopen.c
- # Wrapped by kent@sparky on Sat Jun 20 11:55:50 1992
- PATH=/bin:/usr/bin:/usr/ucb ; export PATH
- echo If this archive is complete, you will see the following message:
- echo ' "shar: End of archive 1 (of 1)."'
- if test -f 'README' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'README'\"
- else
- echo shar: Extracting \"'README'\" \(2542 characters\)
- sed "s/^X//" >'README' <<'END_OF_FILE'
- XThis software has been tested on Sun3, Sun4, mips, and SGI.
- XIt is currently in use here on these platforms.
- XThe original author was Hyman Wong, and there have been significant
- Xupgrades and modifications made by Reg Quinton and myself.
- X
- XSendopr allows users to send messages to the operator.
- XIt is a queuing system which delivers messages to an operator's
- XXterminal. Xmessage is used to display the information.
- X
- XMulti-line messages can come from standard input if the user
- Xis not a tty. The messages appear on the operator's console
- Xwhich is assumed to be an Xterminal.
- XThe geometry of the window should be defined in the operator's
- X.xdefaults file: see man page for more details.
- X
- XTo install:
- X 1. make
- X
- X 2. Include a line in /etc/services similar to:
- Xsendopr xxx/tcp
- X Where xxx is the port number to be used for the service
- X for sendoprd.
- X
- X 3. Include a line in /etc/inetd.conf similar to:
- Xsendopr stream tcp nowait nobody /usr/ccs/lib/sendoprd sendoprd
- X
- X 4. Then execute the command:
- Xkill -HUP "pid of inetd"
- X For kill: Arguments should be jobs or process id's.
- X This will reinitialize inetd.
- X
- XREADME -- July 12, 1991
- X
- XSendopr was written by me, Hyman Wong, for the department of Computing
- Xand Communications Services at the University of Western Ontario. I am
- Xa student working here as a consultant and applications programmer.
- XSendopr is a program utility that allows users to send a message to the
- Xoperator's terminal. Sendopr was written to reduce the clutter on the
- Xoperator's screen by opening up an xmessage window at the same place on
- Xthe operator's display.
- X
- XNov 18, 1991 (Reg Quinton)
- X
- XSendopr sends things to the daemon via E-mail. This requires an E-mail
- Xpipe like
- X
- X sendopr: "|/usr/ccs/lib/sendord"
- X
- Xin /usr/lib/aliases.
- X
- XBrian Borowski:
- XMar. 31, 1992, Revised sendoprd.c to use advisory locks on the .busy file.
- XThis will let the program execute when it is supposed to.
- XResolves the problem with .busy file lock up.
- X
- XApril 9, 1992 (Brian Borowski)
- XThe shell script sendopr was rewritten in C and this implementation
- Xhas been done as a client using a host on the net when messages
- Xare to be queued. In all other respects I have attempted to
- Xduplicate the behaviour of the shell script version of sendopr.
- X
- XApril 16, 1992 (Brian Borowski)
- XPerformed upgrade to fix the getuser problem which arose when the
- Xprogram was being run with no tty (for example, from cron.)
- XAlso modified interface so that the input for the message could come
- Xfrom standard input, rather than just the command line.
- END_OF_FILE
- if test 2542 -ne `wc -c <'README'`; then
- echo shar: \"'README'\" unpacked with wrong size!
- fi
- # end of 'README'
- fi
- if test -f 'BEWARE' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'BEWARE'\"
- else
- echo shar: Extracting \"'BEWARE'\" \(1153 characters\)
- sed "s/^X//" >'BEWARE' <<'END_OF_FILE'
- X $Author: reggers $
- X $Date: 91/07/23 12:31:59 $
- X $Header: /ccs/export/src/usr.local/sendopr/RCS/BEWARE,v 1.1 91/07/23 12:31:59 reggers Exp $
- X $Source: /ccs/export/src/usr.local/sendopr/RCS/BEWARE,v $
- X $State: Exp $
- X
- XOriginal work by Hyman Wong -- Thu Jul 12 12:42:41 EDT 1991
- X
- XBEWARE:
- X
- XSince sendopr uses echo and xmessage, the same restrictions and bugs are
- Xalso found in sendop.
- X
- XMessages can't contain "?" or "!" because of their shell interpretation.
- X
- XThe switches must always come before the message.
- X
- XThe operator's Xresources should be configured to allow messages to be
- Xreceived, ie. "xhost +" should be set. In the operator's .xdefaults file,
- Xthere should be a line similar to:
- X Important.Geometry: 800x500+700+200
- Xto indicate the size and the location of the message window
- X
- XSendopr assumes the operator's terminal is X-based. If the terminal
- Xdoes not support X11, then an email message will be sent to the operator
- Xand the sender will not get a confirmation of the message being received.
- X
- XSendopr does not wrap long lines around to the next line. If a sentence
- Xis longer than the window size, the end of the line is cut off.
- X
- END_OF_FILE
- if test 1153 -ne `wc -c <'BEWARE'`; then
- echo shar: \"'BEWARE'\" unpacked with wrong size!
- fi
- # end of 'BEWARE'
- fi
- if test -f 'Makefile' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'Makefile'\"
- else
- echo shar: Extracting \"'Makefile'\" \(1397 characters\)
- sed "s/^X//" >'Makefile' <<'END_OF_FILE'
- X#
- X# $Author: reggers $
- X# $Date: 1992/06/10 14:02:03 $
- X# $Id: Makefile,v 1.10 1992/06/10 14:02:03 reggers Exp $
- X#
- X# Make and install things in the right places
- X#
- XSHELL=/bin/sh
- XGET = co
- XCC=cc
- X# On SGI's you might need to use a different SIGRET, say void
- X# Instead you can say "make CFLAGS='-O -DSIGRET=void'"
- X#
- X#CFLAGS=-g -DDEBUG
- XCFLAGS=-O
- XOWNER=daemon
- XGROUP=daemon
- X# where do things go?
- XOLD=/usr/ccs/old
- XLIB=/usr/ccs/lib
- XBIN=/usr/ccs/bin
- XSPOOL=/usr/spool/sendoprd
- XMAN1=/usr/ccs/man/man1
- XMAN8=/usr/ccs/man/man8
- XMAN1EXT=1
- XMAN8EXT=8
- X# Sources
- XSRC=Makefile sendopr.c tcpopen.c sendopr.man sendopr.h sendoprd.c sendoprd.man
- XOBJECTS = sendopr.o tcpopen.o
- X
- Xall: sendopr sendoprd
- X
- X${SRC}:
- X ${GET} $@
- X
- X.c.o:
- X ${CC} ${CFLAGS} -c $*.c
- X
- Xsendopr: ${OBJECTS}
- X ${CC} -o $@ ${OBJECTS}
- X
- Xsendoprd: sendoprd.c sendoprd.h
- X ${CC} ${CFLAGS} -o $@ $@.c
- X
- X# On the machine that spools you'll need a spool area
- X
- X${SPOOL}:
- X umask 027; mkdir -p ${SPOOL}
- X chown ${OWNER}.${GROUP} ${SPOOL}
- X
- Xinstall: sendopr sendopr.man sendoprd sendoprd.man
- X -cp ${BIN}/sendopr ${OLD}
- X install -c -m 755 sendopr ${BIN}
- X -cp ${MAN1}/sendopr.${MAN1EXT} ${OLD}
- X install -c -m 644 sendopr.man ${MAN1}/sendopr.${MAN1EXT}
- X -cp ${LIB}/sendoprd ${OLD}
- X install -s -c -m 6755 -o ${OWNER} -g ${GROUP} sendoprd ${LIB}
- X -cp ${MAN8}/sendoprd.${MAN8EXT} ${OLD}
- X install -c -m 644 sendoprd.man ${MAN8}/sendoprd.${MAN8EXT}
- X
- Xclean:
- X -rm sendoprd *.o core *~
- X
- END_OF_FILE
- if test 1397 -ne `wc -c <'Makefile'`; then
- echo shar: \"'Makefile'\" unpacked with wrong size!
- fi
- # end of 'Makefile'
- fi
- if test -f 'sendopr.c' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'sendopr.c'\"
- else
- echo shar: Extracting \"'sendopr.c'\" \(4602 characters\)
- sed "s/^X//" >'sendopr.c' <<'END_OF_FILE'
- X/* $Author: reggers $
- X* $Date: 1992/04/21 14:31:46 $
- X* $Id: sendopr.c,v 1.5 1992/04/21 14:31:46 reggers Exp $
- X* $Source: /usr/src/usr.local/utilities/sendopr/RCS/sendopr.c,v $
- X* $State: Exp $
- X*
- X* Original work done by Brian Borowski on April 10 1992
- X* done during a placement here at UWO
- X* This program sends messages to the operator in one of two modes.
- X* These are immediate where the message on the command line is sent via
- X* xmessage. In this mode the program will pause until the operator
- X* clicks on the button at the bottom of the message window, at which
- X* point the sender will see "okay" and be returned to the prompt.
- X* In the second mode queued mode the message is sent via a host
- X* socket pair using tcp and the message is queued for future reading
- X* by the operator. Immediate and queued can be controlled from the
- X* command line by the -i and -q options. If the controlling device
- X* is not a tty then queued mode is assumed.
- X*/
- X
- Xstatic char *rcsid="$Id: sendopr.c,v 1.5 1992/04/21 14:31:46 reggers Exp $";
- X
- X#ifndef SENDOPRHOST
- X#define SENDOPRHOST "sendoprhost"
- X#endif
- X
- X#ifndef SENDOPRPORT
- X#define SENDOPRPORT "sendopr"
- X#endif
- X
- X#define CFG "/usr/local/share/etc/operator"
- X
- X#include <stdio.h>
- X#include <sysexits.h>
- X#include <sys/types.h>
- X#include <pwd.h>
- X#include <errno.h>
- X#include "sendoprd.h"
- X
- Xchar display_buf[BUFSIZ];
- Xchar msg_buf[BUFSIZ];
- Xchar *usage="sendopr [-i|-q] [-d display] [-s subject] message";
- Xchar *display = DISPLAY;
- Xchar *title = TITLE;
- Xchar *name = NAME;
- Xchar *subject=NAME, *logname, *date;
- Xchar myhost[BUFSIZ]; /* name of host */
- Xint from_stdin=0; /* assume input is from args rather than stdin */
- Xint debug=0;
- X
- X/* msg_print: feeds the users message into the file pointer.
- X Returns no value. Called by main. */
- Xvoid msg_print(argv, argc, start, fp)
- Xchar *argv[];
- Xint argc, start;
- XFILE *fp;
- X{ int i;
- X
- Xfprintf(fp, "From: %s@%s\n", logname, myhost);
- Xfprintf(fp, "Subject: %s\n", subject);
- Xfprintf(fp, "Date: %s\n", date);
- Xif (from_stdin) /* get message from stdin and feed it out */
- X while (fgets(msg_buf, BUFSIZ, stdin) != NULL)
- X fputs(msg_buf, fp);
- X else /* else get message from argv */
- X { for (i = start; argv[i]; i++) /* feed rest of argv into pipe */
- X { fprintf(fp, "%s", argv[i]);
- X if (i < argc-1) putc(' ', fp);
- X } /* end for args */
- X putc('\n', fp);
- X } /* end else from args */
- Xfflush(fp);
- X} /* end msg_print */
- X
- X
- Xmain(argc, argv)
- Xint argc;
- Xchar *argv[];
- X{ int unit, i;
- Xtime_t secs;
- Xchar *getlogin(), *ctime();
- Xextern int optind;
- Xextern char *optarg;
- Xextern int tcpopen();
- Xint immediate, c;
- Xstruct passwd *pw_info;
- XFILE *fp_out, *fp1;
- X
- Xif (isatty(fileno(stdin)))
- X immediate = 1; /* set immediate to true if tty */
- X else immediate = 0;
- X/* parse command line arguments: */
- Xif (argc == 1) /* assume input from stdin */
- X from_stdin=1;
- X else /* check the argv */
- X while ((c = getopt(argc, argv, "iqd:s:")) != EOF)
- X switch(c)
- X { case 'i' : if (optind == 2)
- X immediate=1;
- X break;
- X case 'q' : if (optind == 2)
- X immediate=0;
- X break;
- X case 'd' : display=optarg;
- X break;
- X case 's' : subject = (optarg)? optarg: NAME;
- X break;
- X default : fprintf(stderr, usage);
- X exit(EX_USAGE);
- X } /* end case */
- X
- Xif (optind == argc) from_stdin=1; /* message from stdin */
- Xif (display == DISPLAY) /* then hasn't been changed by command line */
- X if ((fp1=fopen(CFG, "r")) != NULL) /* check for config file */
- X { fgets(display_buf,BUFSIZ,fp1);
- X display = display_buf;
- X fclose(fp1);
- X } /* end get display info */
- Xtime(&secs);
- Xdate = ctime(&secs);
- Xif ((logname = getlogin()) == NULL)
- X { pw_info = getpwuid(getuid()); /* not attached to a tty */
- X logname = pw_info->pw_name;
- X }
- Xif (gethostname(myhost, BUFSIZ) == -1)
- X { fprintf(stderr, "***-cannot get name of host");
- X exit(127);
- X }
- Xif (debug) fprintf(stderr,"got user, date and host\n");
- Xif (immediate) /* send using xmessage */
- X { sprintf(msg_buf, "%s -display %s -title %s -name %s -",
- X XMESSAGE,display,title,name);
- X if ((fp_out=popen(msg_buf, "w")) == NULL)
- X { fprintf(stderr, "cannot pipe to xmessage");
- X exit(127);
- X }
- X msg_print(argv, argc, optind, fp_out);
- X pclose(fp_out);
- X } /* end if immediate */
- X else /* use the sendopr host */
- X { if ((unit=tcpopen(SENDOPRHOST, SENDOPRPORT)) < 0)
- X { fprintf(stderr, "**cannot create a socket\n");
- X exit(127);
- X }
- X fp_out=fdopen(unit, "w");
- X /* feed in the message */
- X msg_print(argv, argc, optind, fp_out);
- X fclose(fp_out);
- X } /* end else use the sendopr host */
- Xexit(0);
- X } /* end main */
- END_OF_FILE
- if test 4602 -ne `wc -c <'sendopr.c'`; then
- echo shar: \"'sendopr.c'\" unpacked with wrong size!
- fi
- # end of 'sendopr.c'
- fi
- if test -f 'sendopr.man' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'sendopr.man'\"
- else
- echo shar: Extracting \"'sendopr.man'\" \(4085 characters\)
- sed "s/^X//" >'sendopr.man' <<'END_OF_FILE'
- X./" $Author: brianb $
- X./" $Date: 1992/04/16 17:24:24 $
- X./" $Header: /usr/src/usr.local/utilities/sendopr/RCS/sendopr.man,v 1.6 1992/04/16 17:24:24 brianb Exp $
- X./" $Source: /usr/src/usr.local/utilities/sendopr/RCS/sendopr.man,v $
- X./"
- X./" Sendopr's man page was written by Hyman Wong -- July 11, 1991.
- X./"
- X.TH SENDOPR Local "11 July 1991"
- X.UC 4
- X.SH NAME
- Xsendopr \- send a message to the operator
- X.SH SYNOPSIS
- X.B sendopr
- X[
- X.B \-i,-q
- X] [
- X.BI \-d " display"
- X] [
- X.BI \-s " subject"
- X] [
- X.BI message
- X]
- X.br
- X.SH DESCRIPTION
- X.PP
- X.I Sendopr
- Xwill send a short one line message to the operator, if the message is part
- Xof the command-line. Otherwise, standard input is used.
- XInput will terminate when EOF is received.
- X.I Sendopr
- Xhas two modes,
- X.I immediate
- Xand
- X.I queued
- Xthat are set with the
- X.B -i
- Xand
- X.B -q
- Xflags.
- X.PP
- XJobs that aren't attached to a terminal (ie. they have no user at a
- Xcontrolling tty device), for example
- Xcron(1) jobs, will use the queued mode as the default. User jobs work
- Xin an immediate mode by default.
- XIn either case
- Xflags can be used to select a mode different from the default.
- X.PP
- XWith the
- X.B \-i
- Xswitch specified,
- X.I sendopr
- Xis in immediate mode and the message is sent immediately to the operator's
- XX-terminal. After the operator reads the message, they will acknowledge
- Xits receipt by clicking on a button in the message window. The button
- Xwill cause
- X.I sendopr
- Xto echo back a short note to the user that the message has been read.
- X.PP
- XIn
- X.I queued
- Xmode,
- X.I sendopr
- Xwill send the message via a queueing strategy and the operators will
- Xread the message only when they check the queue. A verification message
- Xwill not be relayed back to the sender in this case.
- XIn this mode the message is sent via a host on the network.
- X.PP
- XIf the display is specified with the
- X.B \-d
- Xoption, the message will go to the specified Xstation instead of the
- Xdefault display. The default is
- X.BR operator:0 ;
- Xhowever, that can be overridden by the file
- X.B /usr/local/share/etc/operator.
- X.SH ENVIRONMENT
- X.PP
- X.I Sendopr
- Xhonours the following environment variables. The default
- Xvalues can be changed to suit the operator's needs, otherwise
- Xthey will be set to the default values.
- X.PP
- X.TP
- X.B DISPLAY
- Xwhich terminal to open the message window on. The default is
- X.B operator:0
- Xbut this can be over ridden with the
- Xcontents of
- X.B /usr/local/share/etc/operator.
- XThe display is over-ridden yet again if
- X.BI \-d " display"
- Xis specified.
- X.TP
- X.B TITLE
- Xthe title given to the window and the icon when the window is closed.
- XThe default is set to:
- X.BR Important.
- X.TP
- X.B SUBJECT
- Xthe Subject: line of the message sent. The default is set to:
- X.BR Important .
- XAgain, this can be set with the
- X.BI \-s " subject"
- Xflag.
- X.SH FILES
- X.TP
- X.B /usr/local/share/etc/operator
- Xcontains the address of the station where the message will be sent.
- X.SH DIAGNOSTICS
- X.PP
- XThere aren't any. Sorry, but you're on your own.
- X.SH BUGS
- X.PP
- XSince
- X.I sendopr
- Xuses
- X.I xmessage,
- Xthe same restrictions and bugs for
- X.I xmessage
- Xapply to
- X.I sendopr.
- XSome punctuation marks, such as "!" and "?" cannot be used
- Xin the message because of their shell interpretation. (Command recall
- Xand wildcard)
- X.PP
- XIt's desired if
- X.I sendopr
- Xcould beep the terminal at the start of the message to get the
- Xoperator's attention and cause an interfaced lamp to flash, but
- X.I xmessage
- Xseems to filter out any ^G's sent to it.
- X.PP
- XThe operator's Xresources should be configured to allow messages to be
- Xreceived,
- X.I ie. xhost +
- Xshould be set, and in the operator's
- X.I .xdefaults
- Xfile, there should be a line similar to:
- X.SP
- X.NF
- X.I Important.Geometry: 800x500+700+200
- X.BL
- X.FI
- X.SP
- Xto indicate the size and location of the message window on the Xterminal.
- X.PP
- X.I Sendopr
- Xassumes the operator's terminal is X-based.
- X.PP
- X.I Sendopr
- Xdoes not wrap long lines around to the next line if the message
- Xis on the command-line.
- XIf a sentence is
- Xlonger than the window size, the end of the line is cut off.
- XThis restriction is not imposed when standard input is used.
- X.SH SEE ALSO
- Xxmessage(1)
- X.SH AUTHOR
- XHyman Wong; July 1991.
- X
- END_OF_FILE
- if test 4085 -ne `wc -c <'sendopr.man'`; then
- echo shar: \"'sendopr.man'\" unpacked with wrong size!
- fi
- # end of 'sendopr.man'
- fi
- if test -f 'sendoprd.c' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'sendoprd.c'\"
- else
- echo shar: Extracting \"'sendoprd.c'\" \(6814 characters\)
- sed "s/^X//" >'sendoprd.c' <<'END_OF_FILE'
- X/*
- X * $Author: brianb $
- X * $Date: 1992/03/31 20:26:52 $
- X * $Id: sendoprd.c,v 1.4 1992/03/31 20:26:52 brianb Exp $
- X * $Source: /usr/src/usr.local/utilities/sendopr/RCS/sendoprd.c,v $
- X *
- X * Written by Hyman Wong -- August 1, 1991
- X * Spooling routines by Reg Quinton.
- X *
- X * This program will copy messages coming from stdin to temporary files
- X * on disk. Once all the input has been spooled to disk, the program
- X * will try to create a "busy" lock by opening a file on disk called
- X * ".busy". If the file already exists, which means there is another
- X * copy of the daemon running, OPEN will cause an error and the program
- X * will exit. If there is no .busy file, the current program is the only
- X * copy running and it will then create the busy lock. It will then
- X * change directory to the spool area and xmessage each file to the
- X * operator's terminal one at a time and wait for the operator to click
- X * the "okay" button before displaying the next message. When all
- X * messages have been xmessaged, the program will remove the .busy file
- X * and exit.
- X */
- X
- X#include <stdio.h>
- X#include <sysexits.h>
- X#include <syslog.h>
- X#include <signal.h>
- X#include <sys/ioctl.h>
- X#include <sys/file.h>
- X
- X#include "sendoprd.h"
- X
- X/* some global variables */
- X
- Xchar *display=DISPLAY;
- Xchar *title=TITLE;
- Xchar *name=NAME;
- Xint debug=0;
- X
- X/* copy one file to another */
- X
- Xint copy(input,output)
- XFILE *input,*output;
- X{
- X int c;
- X
- X while ((c=getc(input)) != EOF) fputc(c,output);
- X fclose(input); fclose(output);
- X}
- X
- X/* take care of a file, display it to the operator */
- X
- Xshow(text)
- Xchar *text;
- X{
- X FILE *input;
- X int pid,r;
- X
- X if (debug) fprintf(stderr,"Displaying %s\n",text);
- X
- X /* gotta have that file */
- X
- X if (!(input=fopen(text,"r"))) return(0);
- X
- X /* report fork problem if encountered */
- X
- X if ((pid=fork()) == -1)
- X { syslog(LOG_CRIT,"Cannot fork");
- X return(0);
- X }
- X
- X /* parent waits until *all* children have died */
- X
- X if (pid)
- X { fclose(input);
- X if (debug) fprintf(stderr,"Parent waiting for children\n");
- X for (pid=wait(&r); pid != -1; pid=wait(&r));
- X if (debug) fprintf(stderr,"All children have terminated\n");
- X return(1);
- X }
- X
- X /* child closes all files and dups file to stdin */
- X
- X close(0); dup(fileno(input)); fclose(input);
- X
- X /* child does an exec */
- X
- X if (debug) fprintf(stderr,"Child execs %s\n",XMESSAGE);
- X execl(XMESSAGE,XMESSAGE,"-display",display,
- X "-title",title,"-name",name,"-",0);
- X syslog(LOG_CRIT,"Cannot exec %s",XMESSAGE);
- X exit(127); /* exec failed */
- X}
- X
- X/* given a file, rename it into the spool. Return a success code */
- X
- Xint spool(file)
- Xchar *file;
- X{
- X char name[BUFSIZ];
- X int q,tail,head;
- X
- X if ((q=open(SPLRC,O_RDWR | O_CREAT,0644)) < 0)
- X { syslog(LOG_CRIT,"spool \"%s\" cannot open",SPLRC);
- X return(0);
- X };
- X
- X flock(q,LOCK_EX); lseek(q,0,L_SET);
- X
- X if ((read(q,&tail,sizeof(int)) != sizeof(int)) ||
- X (read(q,&head,sizeof(int)) != sizeof(int))) tail=head=0;
- X
- X sprintf(name,"./%d",tail);
- X if (rename(file,name) != 0)
- X {
- X flock(q,LOCK_UN); close(q);
- X return(0);
- X }
- X
- X if (debug) fprintf(stderr,"Spooled as number %d\n",tail);
- X
- X lseek(q,0,L_SET); tail++;
- X write(q,&tail,sizeof(int));
- X write(q,&head,sizeof(int));
- X
- X flock(q,LOCK_UN); close(q);
- X
- X return(1);
- X}
- X
- X/* take care of the queue, return a success code */
- X
- Xint unspool()
- X{
- X char name[BUFSIZ];
- X int q,tail,head;
- X
- X if ((q=open(SPLRC,O_RDWR | O_CREAT, 0664)) < 0)
- X {
- X syslog(LOG_CRIT,"unspool \"%s\" cannot open\n",SPLRC);
- X return(0);
- X }
- X
- X if (debug) fprintf(stderr,"Unspooling\n");
- X while (1)
- X { flock(q,LOCK_EX); lseek(q,0,L_SET);
- X
- X if ((read(q,&tail,sizeof(int)) != sizeof(int)) ||
- X (read(q,&head,sizeof(int)) != sizeof(int)))
- X {
- X lseek(q,0,L_SET); tail=head=0;
- X write(q,&tail,sizeof(int));
- X write(q,&head,sizeof(int));
- X }
- X
- X if (tail == head)
- X { flock(q,LOCK_UN); close(q);
- X return(1);
- X };
- X
- X /* ok got the head name, release the queue manager */
- X
- X flock(q,LOCK_UN);
- X
- X /* now do it, display the file */
- X
- X if (debug) fprintf(stderr,"Will display %d\n",head);
- X sprintf(name,"./%d",head);
- X if (!show(name)) return(0);
- X unlink(name);
- X
- X /* now advance the queue */
- X
- X flock(q,LOCK_EX); lseek(q,0,L_SET);
- X
- X if ((read(q,&tail,sizeof(int)) != sizeof(int)) ||
- X (read(q,&head,sizeof(int)) != sizeof(int)))
- X {
- X lseek(q,0,L_SET); tail=head=0;
- X write(q,&tail,sizeof(int));
- X write(q,&head,sizeof(int));
- X }
- X
- X if (tail == head)
- X { flock(q,LOCK_UN); close(q);
- X return(1);
- X };
- X
- X lseek(q,0,L_SET); head++;
- X
- X write(q,&tail,sizeof(int));
- X write(q,&head,sizeof(int));
- X flock(q,LOCK_UN);
- X }
- X}
- X
- X/* see Unix World Tutorial, Dec. 88 */
- X
- Xvoid detach()
- X{
- X int i;
- X
- X /* let parent go quitely */
- X
- X if (fork()) exit(0);
- X
- X /* change process group */
- X
- X setpgrp(0,getpid());
- X
- X /* get rid of controlling tty */
- X
- X if ((i=open("/dev/tty",O_RDWR)) >= 0)
- X {
- X ioctl(i,TIOCNOTTY,0);
- X close(i);
- X }
- X
- X /* ignore key-board signals */
- X
- X signal(SIGHUP,SIG_IGN);
- X signal(SIGINT,SIG_IGN);
- X signal(SIGQUIT,SIG_IGN);
- X signal(SIGTERM,SIG_IGN);
- X signal(SIGTSTP,SIG_IGN);
- X
- X /* close all open files */
- X
- X for (i=0; i < 3; close(i++));
- X}
- X
- X/* main program starts here */
- X
- Xchar *USAGE="Usage: sendoprd [-d display] [-t title] [-n name]\n";
- X
- Xmain(argc, argv)
- Xint argc;
- Xchar *argv[];
- X{
- X int lockf,c;
- Xextern int optind;
- Xextern char *optarg;
- X char *tmpfile="./tmp.XXXXXX";
- X FILE *output;
- X
- X /* Some day, I'll put this into inetd ... */
- X
- X while ((c=getopt(argc,argv,"xd:t:n:")) != EOF)
- X switch (c)
- X {
- X case 'x': debug++;
- X break;
- X
- X case 'd': display=optarg;
- X break;
- X
- X case 't': title=optarg;
- X break;
- X
- X case 'n': name=optarg;
- X break;
- X
- X default: fprintf(stderr,USAGE);
- X exit(EX_USAGE);
- X }
- X
- X /* we're going to gripe to syslog */
- X
- X openlog("sendopr",LOG_PID,LOG_DAEMON);
- X
- X /* go to the spool area */
- X
- X if (chdir(SPOOL) != 0)
- X { syslog(LOG_CRIT,"Cannot chdir to %s\n",SPOOL);
- X if (debug) fprintf(stderr,"Cannot chdir to %s\n",SPOOL);
- X exit(EX_OSFILE);
- X }
- X
- X umask(UMASK);
- X
- X /* copy the input to a file whose name is given by spool */
- X
- X mktemp(tmpfile);
- X
- X if (debug) fprintf(stderr,"Creating tmpfile %s\n",tmpfile);
- X
- X if (!(output=fopen(tmpfile,"w")))
- X { syslog(LOG_CRIT,"can't create tempfile\n");
- X exit(EX_OSFILE);
- X }
- X
- X copy(stdin,output); spool(tmpfile);
- X
- X /* try to create the busy lock */
- X
- X if ((lockf=open(BUSYLOCK,O_WRONLY|O_CREAT, 644)) < 0)
- X exit(EX_OSFILE);
- X if (flock(lockf, LOCK_EX|LOCK_NB) >= 0)
- X {
- X if (debug) fprintf(stderr,"Busy lock created, will unspool\n");
- X else detach();
- X unspool();
- X flock(lockf, LOCK_UN);
- X close(lockf);
- X unlink(BUSYLOCK);
- X }
- X
- X exit(0);
- X}
- X
- END_OF_FILE
- if test 6814 -ne `wc -c <'sendoprd.c'`; then
- echo shar: \"'sendoprd.c'\" unpacked with wrong size!
- fi
- # end of 'sendoprd.c'
- fi
- if test -f 'sendoprd.h' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'sendoprd.h'\"
- else
- echo shar: Extracting \"'sendoprd.h'\" \(802 characters\)
- sed "s/^X//" >'sendoprd.h' <<'END_OF_FILE'
- X/*
- X * $Author: reggers $
- X * $Date: 91/11/18 09:44:38 $
- X * $Header: /ccs/export/share/ftp/pub/unix/utilities/sendoprd/RCS/sendoprd.h,v 1.1 91/11/18 09:44:38 reggers Exp $
- X *
- X * Various defines used by this code. Customize here.
- X*/
- X
- X#ifndef DISPLAY
- X#define DISPLAY "operator:0.0"
- X#endif
- X
- X/* where is the Xmessage service, what should it be titled? */
- X
- X#ifndef XMESSAGE
- X#define XMESSAGE "/usr/bin/X11/xmessage"
- X#endif
- X
- X#ifndef NAME
- X#define NAME "Important"
- X#endif
- X
- X#ifndef TITLE
- X#define TITLE "Important"
- X#endif
- X
- X/* where are files spooled for processing? */
- X
- X#ifndef SPOOL
- X#define SPOOL "/usr/spool/sendoprd/"
- X#endif
- X
- X#ifndef BUSYLOCK
- X#define BUSYLOCK "./.busy"
- X#endif
- X
- X#ifndef SPLRC
- X#define SPLRC "./.splrc"
- X#endif
- X
- X/* file creation mask */
- X
- X#ifndef UMASK
- X#define UMASK 037
- X#endif
- END_OF_FILE
- if test 802 -ne `wc -c <'sendoprd.h'`; then
- echo shar: \"'sendoprd.h'\" unpacked with wrong size!
- fi
- # end of 'sendoprd.h'
- fi
- if test -f 'sendoprd.man' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'sendoprd.man'\"
- else
- echo shar: Extracting \"'sendoprd.man'\" \(2989 characters\)
- sed "s/^X//" >'sendoprd.man' <<'END_OF_FILE'
- X./" $Author: reggers $
- X./" $Date: 91/11/18 10:30:11 $
- X./" $Header: /ccs/export/share/ftp/pub/unix/utilities/sendoprd/RCS/sendoprd.man,v 1.4 91/11/18 10:30:11 reggers Exp $
- X./" $Source: /ccs/export/share/ftp/pub/unix/utilities/sendoprd/RCS/sendoprd.man,v $
- X./"
- X./" Sendoprd's man page was written by Hyman Wong -- August 1, 1991.
- X./"
- X.TH SENDOPRD Local "1 August 1991"
- X.SH NAME
- Xsendoprd \- sendopr message daemon.
- X.SH SYNOPSIS
- X.B sendoprd
- X[ -d display ] [ -t title ] [ -n name ] [-x]
- X.br
- X.SH DESCRIPTION
- X.PP
- X.I Sendoprd
- Xis a daemon that queues and displays messages on the operator's
- Xterminal using
- X.BR xmessage(1) .
- XThe user interface is the command
- X.BR sendopr(l) .
- X.PP
- X.I Sendoprd
- Xwill spool standard input as a unique file and then attempt to deliver
- Xall messages that have been spooled.
- X.PP
- XWhen the message has been spooled
- X.I sendoprd
- Xwill try to create an exclusive lock file called
- X.BR .busy .
- XIf the file already exits then there is an active daemon processing the
- Xqueue \(em this instance will exit.
- XOtherwise, this instance processes the queue and finally removes the lock.
- X.PP
- XThe strategy ensures that only one daemon delivers
- Xthe spooled messages to the operator's console. This also means that
- Xmessages are displayed and dealt with one at a time.
- X.SH OPTIONS
- X.PP
- XOptions are usually not required.
- X.TP
- X.BI \-d " display"
- XTo change the display terminal, the default display is
- X.BR operator:0.0 .
- X.TP
- X.BI \-t " title"
- XTo change the title of the display, the default is
- X.BR Important .
- X.TP
- X.BI \-n " name"
- XTo change the name of the display, the default is
- X.BR Important .
- X.TP
- X.B \-x
- XTo turn on debugging.
- X.SH FILES
- X.TP
- X.B /usr/spool/sendopr
- XThe spool area for messages received. Messages are filed with a unique
- Xnumber starting at zero.
- X.TP
- X.B /usr/spool/sendopr/.busy
- XThe busy lock. This file will exist when a daemon is
- Xprocessing the queue.
- X.TP
- X.B /usr/spool/sendopr/.splrc
- XThe spool control file, contains numbers for the head and tail of the queue.
- X.SH DIAGNOSTICS
- X.PP
- XAll error messages are sent to
- X.IR syslog(3) .
- X.SH FUTURES
- XThe current implementation is fed messages by the E-mail system,
- Xfutures
- Xinclude a sendopr client that talks to a daemon over the net.
- X.SH BUGS
- X.PP
- X.I Sendoprd
- Xwill not run if the busy lock exists.
- X.PP
- X.I Sendoprd
- Xassumes the operator's terminal is X-based.
- X.PP
- XThe operator's Xresources should be configured to allow messages to be
- Xreceived, ie.
- X.I "xhost +"
- Xshould be set, and in the operator's
- X.I .xdefaults
- Xfile, there should be a line similar to:
- X.sp
- X.nf
- X Important.Geometry: 800x500+700+200
- X.fi
- X.sp
- Xto indicate the size and location of the message window on the Xterminal.
- X.PP
- X.I Sendoprd
- Xdoes not wrap long lines around to the next line. If a sentence is
- Xlonger than the window size, the end of the line is cut off.
- X.PP
- XAfter the operator reads the message, the "okay" from
- X.I xmessage
- Xis echoed back the to the sender.
- X.SH SEE ALSO
- Xsendopr(l), xmessage(1)
- X.SH AUTHOR
- X.PP
- XHyman Wong and Reg Quinton, CCS, UWO.
- END_OF_FILE
- if test 2989 -ne `wc -c <'sendoprd.man'`; then
- echo shar: \"'sendoprd.man'\" unpacked with wrong size!
- fi
- # end of 'sendoprd.man'
- fi
- if test -f 'tcpopen.c' -a "${1}" != "-c" ; then
- echo shar: Will not clobber existing file \"'tcpopen.c'\"
- else
- echo shar: Extracting \"'tcpopen.c'\" \(1983 characters\)
- sed "s/^X//" >'tcpopen.c' <<'END_OF_FILE'
- X/*
- X* $Author: reggers $
- X* $Date: 1992/06/10 14:02:26 $
- X* $Header: /usr/src/usr.local/utilities/sendopr/RCS/tcpopen.c,v 1.2 1992/06/10 14:02:26 reggers Exp $
- X*
- X* Abstract: open a connection to a host/service
- X*
- X* Original work by Reg Quinton; 30 Apr 1991
- X*/
- X
- X#include <stdio.h>
- X#include <signal.h>
- X#include <setjmp.h>
- X#include <sys/types.h>
- X#include <sys/socket.h>
- X#include <netinet/in.h>
- X#include <netdb.h>
- X
- X#ifndef SIGRET
- X#define SIGRET int
- X#endif
- X
- X#ifndef TIMEOUT
- X#define TIMEOUT 60
- X#endif
- X
- Xstatic jmp_buf env; /* for jump back */
- X
- Xstatic
- XSIGRET catcher()
- X{ longjmp(env,1); }
- X
- X/* open a connection to some service on some host */
- X
- Xint tcpopen(host,service)
- Xchar *service, *host;
- X{ int unit;
- Xstatic struct sockaddr_in sin;
- Xstatic struct servent *sp;
- Xstatic struct hostent *hp;
- X SIGRET (*oldsig)();
- X
- X oldsig=signal(SIGALRM,catcher);
- X
- X if (setjmp(env))
- X { signal(SIGALRM,oldsig); alarm(0);
- X return(-1);
- X }
- X
- X alarm(TIMEOUT);
- X
- X /* this is straight line lifting from the 4.2BSD IPC Primer
- X example of section 3.5... the famous figure 1 */
- X
- X if ((sp=getservbyname(service,"tcp")) == NULL)
- X { fprintf(stderr,"Oops ... no such service \"%s\"\n",service);
- X return(-1);
- X }
- X
- X if ((hp=gethostbyname(host)) == NULL)
- X { fprintf(stderr,"Oops ... unknown host \"%s\"\n",host);
- X return(-1);
- X }
- X
- X bzero((char *)&sin, sizeof(sin));
- X bcopy(hp->h_addr,(char *)&sin.sin_addr,hp->h_length);
- X sin.sin_family=hp->h_addrtype;
- X sin.sin_port=sp->s_port;
- X
- X if ((unit=socket(AF_INET,SOCK_STREAM,0)) < 0)
- X { fprintf(stderr,"Oops ... tcp/ip cannot open socket\n");
- X return(-1);
- X }
- X
- X if (connect(unit,(char *)&sin,sizeof(sin)) < 0)
- X { fprintf(stderr,"Oops ... tcp/ip cannot connect to server\n");
- X return(-1);
- X }
- X
- X signal(SIGALRM,oldsig); alarm(0);
- X return(unit);
- X}
- END_OF_FILE
- if test 1983 -ne `wc -c <'tcpopen.c'`; then
- echo shar: \"'tcpopen.c'\" unpacked with wrong size!
- fi
- # end of 'tcpopen.c'
- fi
- echo shar: End of archive 1 \(of 1\).
- cp /dev/null ark1isdone
- MISSING=""
- for I in 1 ; do
- if test ! -f ark${I}isdone ; then
- MISSING="${MISSING} ${I}"
- fi
- done
- if test "${MISSING}" = "" ; then
- echo You have the archive.
- rm -f ark[1-9]isdone
- else
- echo You still must unpack the following archives:
- echo " " ${MISSING}
- fi
- exit 0
- exit 0 # Just in case...
-