1 /* rcvtty.c - a rcvmail program (a lot like rcvalert) handling IPC ttys */
3 static char ident[] = "@(#)$Id: rcvtty.c,v 1.13 1994/04/21 18:20:50 jromine Exp $";
10 #include "../h/rcvmail.h"
11 #include "../h/scansbr.h"
12 #include "../zotnet/tws.h"
24 "%2(hour{dtimenow}):%02(min{dtimenow}): %<(size)%5(size) %>%<{encrypted}E%>\
25 %<(mymbox{from})%<{to}To:%14(friendly{to})%>%>%<(zero)%17(friendly{from})%> \
26 %{subject}%<{body}<<%{body}>>%>"
28 static struct swit switches[] = {
59 static int message_fd(), header_fd();
63 static int newline = 1;
65 static char *form = NULL;
66 static char *format = NULL;
92 setlocale(LC_ALL, "");
94 invo_name = r1bindex (argv[0], '/');
96 if ((cp = m_find (invo_name)) != NULL) {
97 ap = brkstring (cp = getcpy (cp), " ", "\n");
98 ap = copyip (ap, arguments);
102 (void) copyip (argv + 1, ap);
107 while (cp = *argp++) {
109 switch (smatch (++cp, switches)) {
111 ambigsw (cp, switches);
117 (void) sprintf (buf, "%s [command ...]", invo_name);
118 help (buf, switches);
126 if (!(form = *argp++) || *form == '-')
127 adios (NULLCP, "missing argument to %s", argp[-2]);
131 if (!(format = *argp++) || *format == '-')
132 adios (NULLCP, "missing argument to %s", argp[-2]);
156 if ((md = vecp ? message_fd (vec) : header_fd ()) == NOTOK)
161 if ((uf = fopen ("/etc/utmp", "r")) == NULL)
163 while (fread ((char *) &ut, sizeof ut, 1, uf) == 1)
164 if (ut.ut_name[0] != 0
165 && strncmp (user, ut.ut_name, sizeof ut.ut_name) == 0) {
166 (void) strncpy (tty, ut.ut_line, sizeof ut.ut_line);
181 static TYPESIG alrmser (i)
184 longjmp (myctx, DONE);
188 static int message_fd (vec)
197 (void) unlink (mktemp (strcpy (tmpfil, "/tmp/rcvttyXXXXX")));
198 if ((fd = creat (tmpfil, 0600)) == NOTOK)
202 if ((fd = open (tmpfil, 2)) == NOTOK)
204 (void) unlink (tmpfil);
208 switch (child_id = vfork ()) {
215 if (dup2 (fd, 1) == NOTOK || dup2 (fd, 2) == NOTOK)
219 (void) setpgrp (0, getpid ());
221 execvp (vec[0], vec);
225 switch (setjmp (myctx)) {
227 (void) signal (SIGALRM, alrmser);
228 bytes = fstat (fileno (stdin), &st) != NOTOK
229 ? (int) st.st_size : 100;
232 (void) alarm ((unsigned) (bytes * 60 + 300));
234 (void) pidwait (child_id, OK);
237 if (fstat (fd, &st) != NOTOK && st.st_size > (off_t)0)
244 (void) kill (child_id, SIGKILL);
246 (void) killpg (child_id, SIGKILL);
256 static int header_fd () {
260 (void) strcpy (tmpfil, m_tmpfil (invo_name));
261 if ((fd = creat (tmpfil, 0600)) == NOTOK)
265 if ((fd = open (tmpfil, 2)) == NOTOK)
267 (void) unlink (tmpfil);
270 (void) scan (stdin, 0, 0, new_fs (form, format, SCANFMT), 0, 0, 0,
273 (void) write (fd, "\n\r", 2);
274 (void) write (fd, scanl, strlen (scanl));
276 (void) write (fd, "\007", 1);
284 static alert (tty, md)
294 (void) sprintf (ttyspec, "/dev/%s", tty);
295 if (stat (ttyspec, &st) == NOTOK ||
296 (st.st_mode & (biff ? S_IEXEC :
305 switch (setjmp (myctx)) {
307 (void) signal (SIGALRM, alrmser);
309 td = open (ttyspec, 1);
320 (void) lseek (md, (off_t)0, 0);
322 while ((i = read (md, buffer, sizeof buffer)) > 0)
323 if (write (td, buffer, i) != i)
332 static alert (user, md)
340 if ((td = ttyw ("notify", NULLCP, NULLCP, user)) == NOTOK)
342 (void) signal (SIGPIPE, SIG_IGN);
344 (void) lseek (md, (off_t), 0);
345 while ((i = read (md, buffer, sizeof buffer)) > 0)
346 if (write (td, buffer, i) != i)