Commit | Line | Data |
---|---|---|
9552e6b8 DF |
1 | /* |
2 | * Copyright (c) 1980 Regents of the University of California. | |
0c5f72fb KB |
3 | * All rights reserved. |
4 | * | |
5 | * Redistribution and use in source and binary forms are permitted | |
acfc7e9b KB |
6 | * provided that the above copyright notice and this paragraph are |
7 | * duplicated in all such forms and that any documentation, | |
8 | * advertising materials, and other materials related to such | |
9 | * distribution and use acknowledge that the software was developed | |
10 | * by the University of California, Berkeley. The name of the | |
11 | * University may not be used to endorse or promote products derived | |
12 | * from this software without specific prior written permission. | |
13 | * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR | |
14 | * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED | |
15 | * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. | |
9552e6b8 DF |
16 | */ |
17 | ||
acfc7e9b | 18 | #ifndef lint |
0c5f72fb | 19 | char copyright[] = |
9552e6b8 DF |
20 | "@(#) Copyright (c) 1980 Regents of the University of California.\n\ |
21 | All rights reserved.\n"; | |
acfc7e9b | 22 | #endif /* not lint */ |
9552e6b8 | 23 | |
acfc7e9b | 24 | #ifndef lint |
e9d34eb2 | 25 | static char sccsid[] = "@(#)main.c 5.19 (Berkeley) %G%"; |
acfc7e9b | 26 | #endif /* not lint */ |
83f7d6ec KS |
27 | |
28 | #include "rcv.h" | |
29 | #include <sys/stat.h> | |
30 | ||
31 | /* | |
32 | * Mail -- a mail program | |
33 | * | |
34 | * Startup -- interface with user. | |
35 | */ | |
36 | ||
5807729c | 37 | jmp_buf hdrjmp; |
83f7d6ec | 38 | |
83f7d6ec KS |
39 | main(argc, argv) |
40 | char **argv; | |
41 | { | |
790344bc EW |
42 | register int i; |
43 | struct name *to, *cc, *bcc, *smopts; | |
3d6f01e5 EW |
44 | char *subject; |
45 | char *ef; | |
f674e088 | 46 | char nosrc = 0; |
3d6f01e5 | 47 | int hdrstop(), (*prevint)(); |
322c8626 | 48 | int sigchild(); |
790344bc EW |
49 | extern int getopt(), optind, opterr; |
50 | extern char *optarg; | |
83f7d6ec | 51 | |
83f7d6ec | 52 | /* |
828615a1 | 53 | * Set up a reasonable environment. |
322c8626 EW |
54 | * Figure out whether we are being run interactively, |
55 | * start the SIGCHLD catcher, and so forth. | |
83f7d6ec | 56 | */ |
322c8626 | 57 | (void) signal(SIGCHLD, sigchild); |
686f6134 EW |
58 | if (isatty(0)) |
59 | assign("interactive", ""); | |
83f7d6ec | 60 | image = -1; |
83f7d6ec KS |
61 | /* |
62 | * Now, determine how we are being used. | |
723b83d3 | 63 | * We successively pick off - flags. |
83f7d6ec KS |
64 | * If there is anything left, it is the base of the list |
65 | * of users to mail to. Argp will be set to point to the | |
66 | * first of these users. | |
67 | */ | |
83f7d6ec | 68 | ef = NOSTR; |
3d6f01e5 EW |
69 | to = NIL; |
70 | cc = NIL; | |
71 | bcc = NIL; | |
72 | smopts = NIL; | |
73 | subject = NOSTR; | |
723b83d3 EW |
74 | while ((i = getopt(argc, argv, "INT:b:c:dfins:u:v")) != EOF) { |
75 | switch (i) { | |
12a8dbc7 KS |
76 | case 'T': |
77 | /* | |
78 | * Next argument is temp file to write which | |
79 | * articles have been read/deleted for netnews. | |
80 | */ | |
790344bc | 81 | Tflag = optarg; |
723b83d3 | 82 | if ((i = creat(Tflag, 0600)) < 0) { |
e3d4be91 KS |
83 | perror(Tflag); |
84 | exit(1); | |
85 | } | |
723b83d3 | 86 | close(i); |
12a8dbc7 | 87 | break; |
83f7d6ec KS |
88 | case 'u': |
89 | /* | |
90 | * Next argument is person to pretend to be. | |
91 | */ | |
f674e088 | 92 | myname = optarg; |
83f7d6ec | 93 | break; |
83f7d6ec KS |
94 | case 'i': |
95 | /* | |
96 | * User wants to ignore interrupts. | |
97 | * Set the variable "ignore" | |
98 | */ | |
99 | assign("ignore", ""); | |
100 | break; | |
83f7d6ec KS |
101 | case 'd': |
102 | debug++; | |
103 | break; | |
83f7d6ec KS |
104 | case 's': |
105 | /* | |
106 | * Give a subject field for sending from | |
107 | * non terminal | |
108 | */ | |
3d6f01e5 | 109 | subject = optarg; |
83f7d6ec | 110 | break; |
83f7d6ec KS |
111 | case 'f': |
112 | /* | |
113 | * User is specifying file to "edit" with Mail, | |
114 | * as opposed to reading system mailbox. | |
115 | * If no argument is given after -f, we read his | |
2a0f6531 | 116 | * mbox file. |
790344bc EW |
117 | * |
118 | * getopt() can't handle optional arguments, so here | |
119 | * is an ugly hack to get around it. | |
83f7d6ec | 120 | */ |
209a87d1 | 121 | if ((argv[optind]) && (argv[optind][0] != '-')) |
790344bc | 122 | ef = argv[optind++]; |
83f7d6ec | 123 | else |
2a0f6531 | 124 | ef = "&"; |
83f7d6ec | 125 | break; |
83f7d6ec KS |
126 | case 'n': |
127 | /* | |
128 | * User doesn't want to source /usr/lib/Mail.rc | |
129 | */ | |
130 | nosrc++; | |
131 | break; | |
da8590df KS |
132 | case 'N': |
133 | /* | |
134 | * Avoid initial header printing. | |
135 | */ | |
209a87d1 | 136 | assign("noheader", ""); |
da8590df | 137 | break; |
843ac7dd CL |
138 | case 'v': |
139 | /* | |
140 | * Send mailer verbose flag | |
141 | */ | |
142 | assign("verbose", ""); | |
143 | break; | |
0f016ad0 S |
144 | case 'I': |
145 | /* | |
146 | * We're interactive | |
147 | */ | |
686f6134 | 148 | assign("interactive", ""); |
0f016ad0 | 149 | break; |
790344bc EW |
150 | case 'c': |
151 | /* | |
152 | * Get Carbon Copy Recipient list | |
153 | */ | |
3d6f01e5 | 154 | cc = cat(cc, nalloc(optarg, GCC)); |
790344bc EW |
155 | break; |
156 | case 'b': | |
157 | /* | |
158 | * Get Blind Carbon Copy Recipient list | |
159 | */ | |
3d6f01e5 | 160 | bcc = cat(bcc, nalloc(optarg, GBCC)); |
790344bc EW |
161 | break; |
162 | case '?': | |
ecedbe81 EW |
163 | fputs("\ |
164 | Usage: mail [-iInv] [-s subject] [-c cc-addr] [-b bcc-addr] to-addr ...\n\ | |
165 | [- sendmail-options ...]\n\ | |
166 | mail [-iInNv] -f [name]\n\ | |
167 | mail [-iInNv] [-u user]\n", | |
168 | stderr); | |
83f7d6ec KS |
169 | exit(1); |
170 | } | |
171 | } | |
209a87d1 | 172 | for (i = optind; (argv[i]) && (*argv[i] != '-'); i++) |
3d6f01e5 | 173 | to = cat(to, nalloc(argv[i], GTO)); |
790344bc | 174 | for (; argv[i]; i++) |
3d6f01e5 | 175 | smopts = cat(smopts, nalloc(argv[i], 0)); |
83f7d6ec KS |
176 | /* |
177 | * Check for inconsistent arguments. | |
178 | */ | |
3d6f01e5 EW |
179 | if (to == NIL && (subject != NOSTR || cc != NIL || bcc != NIL)) { |
180 | fputs("You must specify direct recipients with -s, -c, or -b.\n", stderr); | |
790344bc EW |
181 | exit(1); |
182 | } | |
3d6f01e5 | 183 | if (ef != NOSTR && to != NIL) { |
83f7d6ec KS |
184 | fprintf(stderr, "Cannot give -f and people to send to.\n"); |
185 | exit(1); | |
186 | } | |
83f7d6ec | 187 | tinit(); |
828615a1 | 188 | setscreensize(); |
5807729c | 189 | input = stdin; |
790344bc | 190 | rcvmode = !to; |
f674e088 | 191 | spreserve(); |
5807729c KS |
192 | if (!nosrc) |
193 | load(MASTER); | |
e9d34eb2 EW |
194 | /* |
195 | * Expand returns a savestr, but load only uses the file name | |
196 | * for fopen, so it's save to do this. | |
197 | */ | |
198 | load(expand("~/.mailrc")); | |
790344bc | 199 | if (!rcvmode) { |
3d6f01e5 | 200 | mail(to, cc, bcc, smopts, subject); |
83f7d6ec KS |
201 | /* |
202 | * why wait? | |
203 | */ | |
83f7d6ec KS |
204 | exit(senderr); |
205 | } | |
83f7d6ec KS |
206 | /* |
207 | * Ok, we are reading mail. | |
208 | * Decide whether we are editing a mailbox or reading | |
209 | * the system mailbox, and open up the right stuff. | |
210 | */ | |
2a0f6531 | 211 | if (ef != NOSTR) |
83f7d6ec | 212 | edit++; |
2a0f6531 EW |
213 | else |
214 | ef = "%"; | |
215 | if ((ef = expand(ef)) == NOSTR) | |
216 | exit(1); /* error already reported */ | |
217 | if (setfile(ef, edit) < 0) { | |
b57443b2 | 218 | if (edit) |
2a0f6531 | 219 | perror(ef); |
b57443b2 KS |
220 | else |
221 | fprintf(stderr, "No mail for %s\n", myname); | |
83f7d6ec | 222 | exit(1); |
b57443b2 | 223 | } |
209a87d1 | 224 | if (setjmp(hdrjmp) == 0) { |
4d20fb09 EW |
225 | extern char *version; |
226 | ||
209a87d1 EW |
227 | if ((prevint = signal(SIGINT, SIG_IGN)) != SIG_IGN) |
228 | signal(SIGINT, hdrstop); | |
4d20fb09 EW |
229 | if (value("quiet") == NOSTR) |
230 | printf("Mail version %s. Type ? for help.\n", | |
231 | version); | |
232 | announce(); | |
209a87d1 EW |
233 | fflush(stdout); |
234 | signal(SIGINT, prevint); | |
5807729c | 235 | } |
ab9ca2ea KS |
236 | if (!edit && msgCount == 0) { |
237 | printf("No mail\n"); | |
238 | fflush(stdout); | |
239 | exit(0); | |
240 | } | |
83f7d6ec | 241 | commands(); |
714288d2 | 242 | if (!edit) { |
828615a1 EW |
243 | signal(SIGHUP, SIG_IGN); |
244 | signal(SIGINT, SIG_IGN); | |
245 | signal(SIGQUIT, SIG_IGN); | |
83f7d6ec | 246 | quit(); |
714288d2 | 247 | } |
83f7d6ec KS |
248 | exit(0); |
249 | } | |
5807729c KS |
250 | |
251 | /* | |
252 | * Interrupt printing of the headers. | |
253 | */ | |
254 | hdrstop() | |
255 | { | |
256 | ||
5807729c | 257 | fflush(stdout); |
80187484 | 258 | fprintf(stderr, "\nInterrupt\n"); |
5807729c KS |
259 | longjmp(hdrjmp, 1); |
260 | } | |
828615a1 EW |
261 | |
262 | /* | |
d56fd190 | 263 | * Compute what the screen size for printing headers should be. |
828615a1 EW |
264 | * We use the following algorithm for the height: |
265 | * If baud rate < 1200, use 9 | |
266 | * If baud rate = 1200, use 14 | |
267 | * If baud rate > 1200, use 24 or ws_row | |
268 | * Width is either 80 or ws_col; | |
269 | */ | |
270 | setscreensize() | |
271 | { | |
d56fd190 | 272 | struct sgttyb tbuf; |
828615a1 EW |
273 | #ifdef TIOCGWINSZ |
274 | struct winsize ws; | |
275 | ||
686f6134 | 276 | if (ioctl(1, TIOCGWINSZ, (char *) &ws) < 0) |
828615a1 | 277 | #endif |
d56fd190 | 278 | ws.ws_col = ws.ws_row = 0; |
686f6134 | 279 | if (gtty(1, &tbuf) < 0) |
d56fd190 EW |
280 | tbuf.sg_ospeed = B9600; |
281 | if (tbuf.sg_ospeed < B1200) | |
828615a1 | 282 | screenheight = 9; |
d56fd190 | 283 | else if (tbuf.sg_ospeed == B1200) |
828615a1 | 284 | screenheight = 14; |
828615a1 EW |
285 | else if (ws.ws_row != 0) |
286 | screenheight = ws.ws_row; | |
828615a1 EW |
287 | else |
288 | screenheight = 24; | |
d56fd190 EW |
289 | if ((realscreenheight = ws.ws_row) == 0) |
290 | realscreenheight = 24; | |
291 | if ((screenwidth = ws.ws_col) == 0) | |
828615a1 EW |
292 | screenwidth = 80; |
293 | } |