]> diplodocus.org Git - nmh/blob - docs/historical/mh-6.8.5/uip/mhmail.c
sbr/mts.c: Delete mmdlm2; use same-valued mmdlm1 instead.
[nmh] / docs / historical / mh-6.8.5 / uip / mhmail.c
1 /* mhmail.c - simple mail program */
2 #ifndef lint
3 static char ident[] = "@(#)$Id: mhmail.c,v 1.9 1993/08/20 15:51:29 jromine Exp $";
4 #endif /* lint */
5
6 #include "../h/mh.h"
7 #include <stdio.h>
8 #include <signal.h>
9 #ifdef LOCALE
10 #include <locale.h>
11 #endif
12
13 /* \f */
14
15 static struct swit switches[] = {
16 #define BODYSW 0
17 "body text", 0,
18
19 #define CCSW 1
20 "cc addrs ...", 0,
21
22 #define FROMSW 2
23 "from addr", 0,
24
25 #define SUBJSW 3
26 "subject text", 0,
27
28 #define HELPSW 4
29 "help", 4,
30
31 #define RESNDSW 5
32 "resent", -6,
33 #define QUEUESW 6
34 "queued", -6,
35
36 NULL, 0
37 };
38
39 /* \f */
40
41 static TYPESIG intrser ();
42
43
44 static char tmpfil[BUFSIZ];
45
46 /* \f */
47
48 /* ARGSUSED */
49
50 main (argc, argv)
51 int argc;
52 char *argv[];
53 {
54 int child_id,
55 status,
56 i,
57 iscc = 0,
58 nvec,
59 queued = 0,
60 resent = 0,
61 somebody;
62 char *cp,
63 *tolist = NULL,
64 *cclist = NULL,
65 *subject = NULL,
66 *from = NULL,
67 *body = NULL,
68 **argp = argv + 1,
69 buf[100],
70 *vec[5];
71 FILE * out;
72
73 #ifdef LOCALE
74 setlocale(LC_ALL, "");
75 #endif
76 invo_name = r1bindex (argv[0], '/');
77 m_foil (NULLCP);
78
79 if (argc == 1) {
80 execlp (incproc, r1bindex (incproc, '/'), NULLCP);
81 adios (incproc, "unable to exec");
82 }
83
84 /* \f */
85
86 while (cp = *argp++) {
87 if (*cp == '-')
88 switch (smatch (++cp, switches)) {
89 case AMBIGSW:
90 ambigsw (cp, switches);
91 done (1);
92
93 case UNKWNSW:
94 adios (NULLCP, "-%s unknown", cp);
95
96 case HELPSW:
97 (void) sprintf (buf, "%s [addrs ... [switches]]",
98 invo_name);
99 help (buf, switches);
100 done (1);
101
102 case FROMSW:
103 if (!(from = *argp++) || *from == '-')
104 adios (NULLCP, "missing argument to %s", argp[-2]);
105 continue;
106
107 case BODYSW:
108 if (!(body = *argp++) || *body == '-')
109 adios (NULLCP, "missing argument to %s", argp[-2]);
110 continue;
111
112 case CCSW:
113 iscc++;
114 continue;
115
116 case SUBJSW:
117 if (!(subject = *argp++) || *subject == '-')
118 adios (NULLCP, "missing argument to %s", argp[-2]);
119 continue;
120
121 case RESNDSW:
122 resent++;
123 continue;
124
125 case QUEUESW:
126 queued++;
127 continue;
128 }
129 if (iscc)
130 cclist = cclist ? add (cp, add (", ", cclist)) : getcpy (cp);
131 else
132 tolist = tolist ? add (cp, add (", ", tolist)) : getcpy (cp);
133 }
134
135 /* \f */
136
137 if (tolist == NULL)
138 adios (NULLCP, "usage: %s addrs ... [switches]", invo_name);
139 (void) strcpy (tmpfil, m_tmpfil (invo_name));
140 if ((out = fopen (tmpfil, "w")) == NULL)
141 adios (tmpfil, "unable to write");
142 (void) chmod (tmpfil, 0600);
143
144 setsig (SIGINT, intrser);
145
146 fprintf (out, "%sTo: %s\n", resent ? "Resent-" : "", tolist);
147 if (cclist)
148 fprintf (out, "%scc: %s\n", resent ? "Resent-" : "", cclist);
149 if (subject)
150 fprintf (out, "%sSubject: %s\n", resent ? "Resent-" : "", subject);
151 if (from)
152 fprintf (out, "%sFrom: %s\n", resent ? "Resent-" : "", from);
153 if (!resent)
154 (void) fputs ("\n", out);
155
156 if (body) {
157 fprintf (out, "%s", body);
158 if (*body && *(body + strlen (body) - 1) != '\n')
159 fputs ("\n", out);
160 }
161 else {
162 for (somebody = 0;
163 (i = fread (buf, sizeof *buf, sizeof buf, stdin)) > 0;
164 somebody++)
165 if (fwrite (buf, sizeof *buf, i, out) != i)
166 adios (tmpfil, "error writing");
167 if (!somebody) {
168 (void) unlink (tmpfil);
169 done (1);
170 }
171 }
172 (void) fclose (out);
173
174 /* \f */
175
176 nvec = 0;
177 vec[nvec++] = r1bindex (postproc, '/');
178 vec[nvec++] = tmpfil;
179 if (resent)
180 vec[nvec++] = "-dist";
181 if (queued)
182 vec[nvec++] = "-queued";
183 vec[nvec] = 0;
184
185 for (i = 0; (child_id = fork ()) == NOTOK && i < 5; i++)
186 sleep (5);
187 switch (child_id) {
188 case NOTOK: /* report failure and then send it */
189 admonish (NULLCP, "unable to fork");
190
191 case OK:
192 execvp (postproc, vec);
193 fprintf (stderr, "unable to exec ");
194 perror (postproc);
195 _exit (-1);
196
197 default:
198 if (status = pidXwait (child_id, postproc)) {
199 fprintf (stderr, "Letter saved in dead.letter\n");
200 execl ("/bin/mv", "mv", tmpfil, "dead.letter", NULLCP);
201 execl ("/usr/bin/mv", "mv", tmpfil, "dead.letter", NULLCP);
202 perror ("mv");
203 _exit (-1);
204 }
205
206 (void) unlink (tmpfil);
207 done (status ? 1 : 0);
208 }
209 }
210
211 /* \f */
212
213 /* ARGSUSED */
214
215 static TYPESIG intrser (i)
216 int i;
217 {
218 #ifndef BSD42
219 if (i)
220 (void) signal (i, SIG_IGN);
221 #endif /* BSD42 */
222
223 (void) unlink (tmpfil);
224 done (i != 0 ? 1 : 0);
225 }