xref: /freebsd/contrib/sendmail/src/deliver.c (revision 42e5d165)
1 /*
2  * Copyright (c) 1998-2000 Sendmail, Inc. and its suppliers.
3  *	All rights reserved.
4  * Copyright (c) 1983, 1995-1997 Eric P. Allman.  All rights reserved.
5  * Copyright (c) 1988, 1993
6  *	The Regents of the University of California.  All rights reserved.
7  *
8  * By using this file, you agree to the terms and conditions set
9  * forth in the LICENSE file which can be found at the top level of
10  * the sendmail distribution.
11  *
12  */
13 
14 #ifndef lint
15 static char id[] = "@(#)$Id: deliver.c,v 8.600.2.1.2.44 2000/09/21 21:52:17 ca Exp $";
16 #endif /* ! lint */
17 
18 #include <sendmail.h>
19 
20 
21 #if HASSETUSERCONTEXT
22 # include <login_cap.h>
23 #endif /* HASSETUSERCONTEXT */
24 
25 #if STARTTLS || (SASL && SFIO)
26 # include "sfsasl.h"
27 #endif /* STARTTLS || (SASL && SFIO) */
28 
29 static int	deliver __P((ENVELOPE *, ADDRESS *));
30 static void	dup_queue_file __P((ENVELOPE *, ENVELOPE *, int));
31 static void	mailfiletimeout __P((void));
32 static void	markfailure __P((ENVELOPE *, ADDRESS *, MCI *, int, bool));
33 static int	parse_hostsignature __P((char *, char **, MAILER *));
34 static void	sendenvelope __P((ENVELOPE *, int));
35 static char	*hostsignature __P((MAILER *, char *));
36 
37 #if SMTP
38 # if STARTTLS
39 static int	starttls __P((MAILER *, MCI *, ENVELOPE *));
40 # endif /* STARTTLS */
41 #endif /* SMTP */
42 
43 /*
44 **  SENDALL -- actually send all the messages.
45 **
46 **	Parameters:
47 **		e -- the envelope to send.
48 **		mode -- the delivery mode to use.  If SM_DEFAULT, use
49 **			the current e->e_sendmode.
50 **
51 **	Returns:
52 **		none.
53 **
54 **	Side Effects:
55 **		Scans the send lists and sends everything it finds.
56 **		Delivers any appropriate error messages.
57 **		If we are running in a non-interactive mode, takes the
58 **			appropriate action.
59 */
60 
61 void
62 sendall(e, mode)
63 	ENVELOPE *e;
64 	int mode;
65 {
66 	register ADDRESS *q;
67 	char *owner;
68 	int otherowners;
69 	int save_errno;
70 	register ENVELOPE *ee;
71 	ENVELOPE *splitenv = NULL;
72 	int oldverbose = Verbose;
73 	bool somedeliveries = FALSE, expensive = FALSE;
74 	pid_t pid;
75 
76 	/*
77 	**  If this message is to be discarded, don't bother sending
78 	**  the message at all.
79 	*/
80 
81 	if (bitset(EF_DISCARD, e->e_flags))
82 	{
83 		if (tTd(13, 1))
84 			dprintf("sendall: discarding id %s\n", e->e_id);
85 		e->e_flags |= EF_CLRQUEUE;
86 		if (LogLevel > 4)
87 			sm_syslog(LOG_INFO, e->e_id, "discarded");
88 		markstats(e, NULL, TRUE);
89 		return;
90 	}
91 
92 	/*
93 	**  If we have had global, fatal errors, don't bother sending
94 	**  the message at all if we are in SMTP mode.  Local errors
95 	**  (e.g., a single address failing) will still cause the other
96 	**  addresses to be sent.
97 	*/
98 
99 	if (bitset(EF_FATALERRS, e->e_flags) &&
100 	    (OpMode == MD_SMTP || OpMode == MD_DAEMON))
101 	{
102 		e->e_flags |= EF_CLRQUEUE;
103 		return;
104 	}
105 
106 	/* determine actual delivery mode */
107 	if (mode == SM_DEFAULT)
108 	{
109 		mode = e->e_sendmode;
110 		if (mode != SM_VERIFY && mode != SM_DEFER &&
111 		    shouldqueue(e->e_msgpriority, e->e_ctime))
112 			mode = SM_QUEUE;
113 	}
114 
115 	if (tTd(13, 1))
116 	{
117 		dprintf("\n===== SENDALL: mode %c, id %s, e_from ",
118 			mode, e->e_id);
119 		printaddr(&e->e_from, FALSE);
120 		dprintf("\te_flags = ");
121 		printenvflags(e);
122 		dprintf("sendqueue:\n");
123 		printaddr(e->e_sendqueue, TRUE);
124 	}
125 
126 	/*
127 	**  Do any preprocessing necessary for the mode we are running.
128 	**	Check to make sure the hop count is reasonable.
129 	**	Delete sends to the sender in mailing lists.
130 	*/
131 
132 	CurEnv = e;
133 	if (tTd(62, 1))
134 		checkfds(NULL);
135 
136 	if (e->e_hopcount > MaxHopCount)
137 	{
138 		errno = 0;
139 #if QUEUE
140 		queueup(e, mode == SM_QUEUE || mode == SM_DEFER);
141 #endif /* QUEUE */
142 		e->e_flags |= EF_FATALERRS|EF_PM_NOTIFY|EF_CLRQUEUE;
143 		ExitStat = EX_UNAVAILABLE;
144 		syserr("554 5.0.0 Too many hops %d (%d max): from %s via %s, to %s",
145 			e->e_hopcount, MaxHopCount, e->e_from.q_paddr,
146 			RealHostName == NULL ? "localhost" : RealHostName,
147 			e->e_sendqueue->q_paddr);
148 		for (q = e->e_sendqueue; q != NULL; q = q->q_next)
149 		{
150 			if (QS_IS_DEAD(q->q_state))
151 				continue;
152 			q->q_state = QS_BADADDR;
153 			q->q_status = "5.4.6";
154 		}
155 		return;
156 	}
157 
158 	/*
159 	**  Do sender deletion.
160 	**
161 	**	If the sender should be queued up, skip this.
162 	**	This can happen if the name server is hosed when you
163 	**	are trying to send mail.  The result is that the sender
164 	**	is instantiated in the queue as a recipient.
165 	*/
166 
167 	if (!bitset(EF_METOO, e->e_flags) &&
168 	    !QS_IS_QUEUEUP(e->e_from.q_state))
169 	{
170 		if (tTd(13, 5))
171 		{
172 			dprintf("sendall: QS_SENDER ");
173 			printaddr(&e->e_from, FALSE);
174 		}
175 		e->e_from.q_state = QS_SENDER;
176 		(void) recipient(&e->e_from, &e->e_sendqueue, 0, e);
177 	}
178 
179 	/*
180 	**  Handle alias owners.
181 	**
182 	**	We scan up the q_alias chain looking for owners.
183 	**	We discard owners that are the same as the return path.
184 	*/
185 
186 	for (q = e->e_sendqueue; q != NULL; q = q->q_next)
187 	{
188 		register struct address *a;
189 
190 		for (a = q; a != NULL && a->q_owner == NULL; a = a->q_alias)
191 			continue;
192 		if (a != NULL)
193 			q->q_owner = a->q_owner;
194 
195 		if (q->q_owner != NULL &&
196 		    !QS_IS_DEAD(q->q_state) &&
197 		    strcmp(q->q_owner, e->e_from.q_paddr) == 0)
198 			q->q_owner = NULL;
199 	}
200 
201 	if (tTd(13, 25))
202 	{
203 		dprintf("\nAfter first owner pass, sendq =\n");
204 		printaddr(e->e_sendqueue, TRUE);
205 	}
206 
207 	owner = "";
208 	otherowners = 1;
209 	while (owner != NULL && otherowners > 0)
210 	{
211 		if (tTd(13, 28))
212 			dprintf("owner = \"%s\", otherowners = %d\n",
213 				owner, otherowners);
214 		owner = NULL;
215 		otherowners = bitset(EF_SENDRECEIPT, e->e_flags) ? 1 : 0;
216 
217 		for (q = e->e_sendqueue; q != NULL; q = q->q_next)
218 		{
219 			if (tTd(13, 30))
220 			{
221 				dprintf("Checking ");
222 				printaddr(q, FALSE);
223 			}
224 			if (QS_IS_DEAD(q->q_state))
225 			{
226 				if (tTd(13, 30))
227 					dprintf("    ... QS_IS_DEAD\n");
228 				continue;
229 			}
230 			if (tTd(13, 29) && !tTd(13, 30))
231 			{
232 				dprintf("Checking ");
233 				printaddr(q, FALSE);
234 			}
235 
236 			if (q->q_owner != NULL)
237 			{
238 				if (owner == NULL)
239 				{
240 					if (tTd(13, 40))
241 						dprintf("    ... First owner = \"%s\"\n",
242 							q->q_owner);
243 					owner = q->q_owner;
244 				}
245 				else if (owner != q->q_owner)
246 				{
247 					if (strcmp(owner, q->q_owner) == 0)
248 					{
249 						if (tTd(13, 40))
250 							dprintf("    ... Same owner = \"%s\"\n",
251 								owner);
252 
253 						/* make future comparisons cheap */
254 						q->q_owner = owner;
255 					}
256 					else
257 					{
258 						if (tTd(13, 40))
259 							dprintf("    ... Another owner \"%s\"\n",
260 								q->q_owner);
261 						otherowners++;
262 					}
263 					owner = q->q_owner;
264 				}
265 				else if (tTd(13, 40))
266 					dprintf("    ... Same owner = \"%s\"\n",
267 						owner);
268 			}
269 			else
270 			{
271 				if (tTd(13, 40))
272 					dprintf("    ... Null owner\n");
273 				otherowners++;
274 			}
275 
276 			if (QS_IS_BADADDR(q->q_state))
277 			{
278 				if (tTd(13, 30))
279 					dprintf("    ... QS_IS_BADADDR\n");
280 				continue;
281 			}
282 
283 			if (QS_IS_QUEUEUP(q->q_state))
284 			{
285 				MAILER *m = q->q_mailer;
286 
287 				/*
288 				**  If we have temporary address failures
289 				**  (e.g., dns failure) and a fallback MX is
290 				**  set, send directly to the fallback MX host.
291 				*/
292 
293 				if (FallBackMX != NULL &&
294 				    !wordinclass(FallBackMX, 'w') &&
295 				    mode != SM_VERIFY &&
296 				    (strcmp(m->m_mailer, "[IPC]") == 0 ||
297 				     strcmp(m->m_mailer, "[TCP]") == 0) &&
298 				    m->m_argv[0] != NULL &&
299 				    (strcmp(m->m_argv[0], "TCP") == 0 ||
300 				     strcmp(m->m_argv[0], "IPC") == 0))
301 				{
302 					int len;
303 					char *p;
304 
305 					if (tTd(13, 30))
306 						dprintf("    ... FallBackMX\n");
307 
308 					len = strlen(FallBackMX) + 3;
309 					p = xalloc(len);
310 					snprintf(p, len, "[%s]", FallBackMX);
311 					q->q_state = QS_OK;
312 					q->q_host = p;
313 				}
314 				else
315 				{
316 					if (tTd(13, 30))
317 						dprintf("    ... QS_IS_QUEUEUP\n");
318 					continue;
319 				}
320 			}
321 
322 			/*
323 			**  If this mailer is expensive, and if we don't
324 			**  want to make connections now, just mark these
325 			**  addresses and return.  This is useful if we
326 			**  want to batch connections to reduce load.  This
327 			**  will cause the messages to be queued up, and a
328 			**  daemon will come along to send the messages later.
329 			*/
330 
331 			if (NoConnect && !Verbose &&
332 			    bitnset(M_EXPENSIVE, q->q_mailer->m_flags))
333 			{
334 				if (tTd(13, 30))
335 					dprintf("    ... expensive\n");
336 				q->q_state = QS_QUEUEUP;
337 				expensive = TRUE;
338 			}
339 			else if (bitnset(M_HOLD, q->q_mailer->m_flags) &&
340 				 QueueLimitId == NULL &&
341 				 QueueLimitSender == NULL &&
342 				 QueueLimitRecipient == NULL)
343 			{
344 				if (tTd(13, 30))
345 					dprintf("    ... hold\n");
346 				q->q_state = QS_QUEUEUP;
347 				expensive = TRUE;
348 			}
349 			else
350 			{
351 				if (tTd(13, 30))
352 					dprintf("    ... deliverable\n");
353 				somedeliveries = TRUE;
354 			}
355 		}
356 
357 		if (owner != NULL && otherowners > 0)
358 		{
359 			/*
360 			**  Split this envelope into two.
361 			*/
362 
363 			ee = (ENVELOPE *) xalloc(sizeof *ee);
364 			*ee = *e;
365 			ee->e_message = NULL;
366 			ee->e_id = NULL;
367 			assign_queueid(ee);
368 
369 			if (tTd(13, 1))
370 				dprintf("sendall: split %s into %s, owner = \"%s\", otherowners = %d\n",
371 					e->e_id, ee->e_id, owner, otherowners);
372 
373 			ee->e_header = copyheader(e->e_header);
374 			ee->e_sendqueue = copyqueue(e->e_sendqueue);
375 			ee->e_errorqueue = copyqueue(e->e_errorqueue);
376 			ee->e_flags = e->e_flags & ~(EF_INQUEUE|EF_CLRQUEUE|EF_FATALERRS|EF_SENDRECEIPT|EF_RET_PARAM);
377 			ee->e_flags |= EF_NORECEIPT;
378 			setsender(owner, ee, NULL, '\0', TRUE);
379 			if (tTd(13, 5))
380 			{
381 				dprintf("sendall(split): QS_SENDER ");
382 				printaddr(&ee->e_from, FALSE);
383 			}
384 			ee->e_from.q_state = QS_SENDER;
385 			ee->e_dfp = NULL;
386 			ee->e_lockfp = NULL;
387 			ee->e_xfp = NULL;
388 			ee->e_queuedir = e->e_queuedir;
389 			ee->e_errormode = EM_MAIL;
390 			ee->e_sibling = splitenv;
391 			ee->e_statmsg = NULL;
392 			splitenv = ee;
393 
394 			for (q = e->e_sendqueue; q != NULL; q = q->q_next)
395 			{
396 				if (q->q_owner == owner)
397 				{
398 					q->q_state = QS_CLONED;
399 					if (tTd(13, 6))
400 						dprintf("\t... stripping %s from original envelope\n",
401 							q->q_paddr);
402 				}
403 			}
404 			for (q = ee->e_sendqueue; q != NULL; q = q->q_next)
405 			{
406 				if (q->q_owner != owner)
407 				{
408 					q->q_state = QS_CLONED;
409 					if (tTd(13, 6))
410 						dprintf("\t... dropping %s from cloned envelope\n",
411 							q->q_paddr);
412 				}
413 				else
414 				{
415 					/* clear DSN parameters */
416 					q->q_flags &= ~(QHASNOTIFY|Q_PINGFLAGS);
417 					q->q_flags |= DefaultNotify & ~QPINGONSUCCESS;
418 					if (tTd(13, 6))
419 						dprintf("\t... moving %s to cloned envelope\n",
420 							q->q_paddr);
421 				}
422 			}
423 
424 			if (mode != SM_VERIFY && bitset(EF_HAS_DF, e->e_flags))
425 				dup_queue_file(e, ee, 'd');
426 
427 			/*
428 			**  Give the split envelope access to the parent
429 			**  transcript file for errors obtained while
430 			**  processing the recipients (done before the
431 			**  envelope splitting).
432 			*/
433 
434 			if (e->e_xfp != NULL)
435 				ee->e_xfp = bfdup(e->e_xfp);
436 
437 			/* failed to dup e->e_xfp, start a new transcript */
438 			if (ee->e_xfp == NULL)
439 				openxscript(ee);
440 
441 			if (mode != SM_VERIFY && LogLevel > 4)
442 				sm_syslog(LOG_INFO, ee->e_id,
443 					  "clone %s, owner=%s",
444 					  e->e_id, owner);
445 		}
446 	}
447 
448 	if (owner != NULL)
449 	{
450 		setsender(owner, e, NULL, '\0', TRUE);
451 		if (tTd(13, 5))
452 		{
453 			dprintf("sendall(owner): QS_SENDER ");
454 			printaddr(&e->e_from, FALSE);
455 		}
456 		e->e_from.q_state = QS_SENDER;
457 		e->e_errormode = EM_MAIL;
458 		e->e_flags |= EF_NORECEIPT;
459 		e->e_flags &= ~EF_FATALERRS;
460 	}
461 
462 	/* if nothing to be delivered, just queue up everything */
463 	if (!somedeliveries && mode != SM_QUEUE && mode != SM_DEFER &&
464 	    mode != SM_VERIFY)
465 	{
466 		if (tTd(13, 29))
467 			dprintf("No deliveries: auto-queuing\n");
468 		mode = SM_QUEUE;
469 
470 		/* treat this as a delivery in terms of counting tries */
471 		e->e_dtime = curtime();
472 		if (!expensive)
473 			e->e_ntries++;
474 		for (ee = splitenv; ee != NULL; ee = ee->e_sibling)
475 		{
476 			ee->e_dtime = curtime();
477 			if (!expensive)
478 				ee->e_ntries++;
479 		}
480 	}
481 
482 #if QUEUE
483 	if ((mode == SM_QUEUE || mode == SM_DEFER || mode == SM_FORK ||
484 	     (mode != SM_VERIFY && SuperSafe)) &&
485 	    (!bitset(EF_INQUEUE, e->e_flags) || splitenv != NULL))
486 	{
487 		/*
488 		**  Be sure everything is instantiated in the queue.
489 		**  Split envelopes first in case the machine crashes.
490 		**  If the original were done first, we may lose
491 		**  recipients.
492 		*/
493 
494 		for (ee = splitenv; ee != NULL; ee = ee->e_sibling)
495 			queueup(ee, mode == SM_QUEUE || mode == SM_DEFER);
496 		queueup(e, mode == SM_QUEUE || mode == SM_DEFER);
497 	}
498 #endif /* QUEUE */
499 
500 	if (tTd(62, 10))
501 		checkfds("after envelope splitting");
502 
503 	/*
504 	**  If we belong in background, fork now.
505 	*/
506 
507 	if (tTd(13, 20))
508 	{
509 		dprintf("sendall: final mode = %c\n", mode);
510 		if (tTd(13, 21))
511 		{
512 			dprintf("\n================ Final Send Queue(s) =====================\n");
513 			dprintf("\n  *** Envelope %s, e_from=%s ***\n",
514 				e->e_id, e->e_from.q_paddr);
515 			printaddr(e->e_sendqueue, TRUE);
516 			for (ee = splitenv; ee != NULL; ee = ee->e_sibling)
517 			{
518 				dprintf("\n  *** Envelope %s, e_from=%s ***\n",
519 					ee->e_id, ee->e_from.q_paddr);
520 				printaddr(ee->e_sendqueue, TRUE);
521 			}
522 			dprintf("==========================================================\n\n");
523 		}
524 	}
525 	switch (mode)
526 	{
527 	  case SM_VERIFY:
528 		Verbose = 2;
529 		break;
530 
531 	  case SM_QUEUE:
532 	  case SM_DEFER:
533 #if HASFLOCK
534   queueonly:
535 #endif /* HASFLOCK */
536 		if (e->e_nrcpts > 0)
537 			e->e_flags |= EF_INQUEUE;
538 		dropenvelope(e, splitenv != NULL);
539 		for (ee = splitenv; ee != NULL; ee = ee->e_sibling)
540 		{
541 			if (ee->e_nrcpts > 0)
542 				ee->e_flags |= EF_INQUEUE;
543 			dropenvelope(ee, FALSE);
544 		}
545 		return;
546 
547 	  case SM_FORK:
548 		if (e->e_xfp != NULL)
549 			(void) fflush(e->e_xfp);
550 
551 #if !HASFLOCK
552 		/*
553 		**  Since fcntl locking has the interesting semantic that
554 		**  the lock is owned by a process, not by an open file
555 		**  descriptor, we have to flush this to the queue, and
556 		**  then restart from scratch in the child.
557 		*/
558 
559 		{
560 			/* save id for future use */
561 			char *qid = e->e_id;
562 
563 			/* now drop the envelope in the parent */
564 			e->e_flags |= EF_INQUEUE;
565 			dropenvelope(e, splitenv != NULL);
566 
567 			/* arrange to reacquire lock after fork */
568 			e->e_id = qid;
569 		}
570 
571 		for (ee = splitenv; ee != NULL; ee = ee->e_sibling)
572 		{
573 			/* save id for future use */
574 			char *qid = ee->e_id;
575 
576 			/* drop envelope in parent */
577 			ee->e_flags |= EF_INQUEUE;
578 			dropenvelope(ee, FALSE);
579 
580 			/* and save qid for reacquisition */
581 			ee->e_id = qid;
582 		}
583 
584 #endif /* !HASFLOCK */
585 
586 		/*
587 		**  Since the delivery may happen in a child and the parent
588 		**  does not wait, the parent may close the maps thereby
589 		**  removing any shared memory used by the map.  Therefore,
590 		**  close the maps now so the child will dynamically open
591 		**  them if necessary.
592 		*/
593 
594 		closemaps();
595 
596 		pid = fork();
597 		if (pid < 0)
598 		{
599 			syserr("deliver: fork 1");
600 #if HASFLOCK
601 			goto queueonly;
602 #else /* HASFLOCK */
603 			e->e_id = NULL;
604 			for (ee = splitenv; ee != NULL; ee = ee->e_sibling)
605 				ee->e_id = NULL;
606 			return;
607 #endif /* HASFLOCK */
608 		}
609 		else if (pid > 0)
610 		{
611 #if HASFLOCK
612 			/* be sure we leave the temp files to our child */
613 			/* close any random open files in the envelope */
614 			closexscript(e);
615 			if (e->e_dfp != NULL)
616 				(void) bfclose(e->e_dfp);
617 			e->e_dfp = NULL;
618 			e->e_flags &= ~EF_HAS_DF;
619 
620 			/* can't call unlockqueue to avoid unlink of xfp */
621 			if (e->e_lockfp != NULL)
622 				(void) fclose(e->e_lockfp);
623 			else
624 				syserr("%s: sendall: null lockfp", e->e_id);
625 			e->e_lockfp = NULL;
626 #endif /* HASFLOCK */
627 
628 			/* make sure the parent doesn't own the envelope */
629 			e->e_id = NULL;
630 
631 			/* catch intermediate zombie */
632 			(void) waitfor(pid);
633 			return;
634 		}
635 
636 		/*
637 		**  Since we have accepted responsbility for the message,
638 		**  change the SIGTERM handler.  intsig() (the old handler)
639 		**  would remove the envelope if this was a command line
640 		**  message submission.
641 		*/
642 
643 		(void) setsignal(SIGTERM, SIG_DFL);
644 
645 		/* double fork to avoid zombies */
646 		pid = fork();
647 		if (pid > 0)
648 			exit(EX_OK);
649 		save_errno = errno;
650 
651 		/* be sure we are immune from the terminal */
652 		disconnect(2, e);
653 		clearstats();
654 
655 		/* prevent parent from waiting if there was an error */
656 		if (pid < 0)
657 		{
658 			errno = save_errno;
659 			syserr("deliver: fork 2");
660 #if HASFLOCK
661 			e->e_flags |= EF_INQUEUE;
662 #else /* HASFLOCK */
663 			e->e_id = NULL;
664 #endif /* HASFLOCK */
665 			finis(TRUE, ExitStat);
666 		}
667 
668 		/* be sure to give error messages in child */
669 		QuickAbort = FALSE;
670 
671 		/*
672 		**  Close any cached connections.
673 		**
674 		**	We don't send the QUIT protocol because the parent
675 		**	still knows about the connection.
676 		**
677 		**	This should only happen when delivering an error
678 		**	message.
679 		*/
680 
681 		mci_flush(FALSE, NULL);
682 
683 #if HASFLOCK
684 		break;
685 #else /* HASFLOCK */
686 
687 		/*
688 		**  Now reacquire and run the various queue files.
689 		*/
690 
691 		for (ee = splitenv; ee != NULL; ee = ee->e_sibling)
692 		{
693 			ENVELOPE *sibling = ee->e_sibling;
694 
695 			(void) dowork(ee->e_queuedir, ee->e_id,
696 				      FALSE, FALSE, ee);
697 			ee->e_sibling = sibling;
698 		}
699 		(void) dowork(e->e_queuedir, e->e_id,
700 			      FALSE, FALSE, e);
701 		finis(TRUE, ExitStat);
702 #endif /* HASFLOCK */
703 	}
704 
705 	sendenvelope(e, mode);
706 	dropenvelope(e, TRUE);
707 	for (ee = splitenv; ee != NULL; ee = ee->e_sibling)
708 	{
709 		CurEnv = ee;
710 		if (mode != SM_VERIFY)
711 			openxscript(ee);
712 		sendenvelope(ee, mode);
713 		dropenvelope(ee, TRUE);
714 	}
715 	CurEnv = e;
716 
717 	Verbose = oldverbose;
718 	if (mode == SM_FORK)
719 		finis(TRUE, ExitStat);
720 }
721 
722 static void
723 sendenvelope(e, mode)
724 	register ENVELOPE *e;
725 	int mode;
726 {
727 	register ADDRESS *q;
728 	bool didany;
729 
730 	if (tTd(13, 10))
731 		dprintf("sendenvelope(%s) e_flags=0x%lx\n",
732 			e->e_id == NULL ? "[NOQUEUE]" : e->e_id,
733 			e->e_flags);
734 	if (LogLevel > 80)
735 		sm_syslog(LOG_DEBUG, e->e_id,
736 			  "sendenvelope, flags=0x%lx",
737 			  e->e_flags);
738 
739 	/*
740 	**  If we have had global, fatal errors, don't bother sending
741 	**  the message at all if we are in SMTP mode.  Local errors
742 	**  (e.g., a single address failing) will still cause the other
743 	**  addresses to be sent.
744 	*/
745 
746 	if (bitset(EF_FATALERRS, e->e_flags) &&
747 	    (OpMode == MD_SMTP || OpMode == MD_DAEMON))
748 	{
749 		e->e_flags |= EF_CLRQUEUE;
750 		return;
751 	}
752 
753 	/* Don't attempt deliveries if we want to bounce now */
754 	if (!bitset(EF_RESPONSE, e->e_flags) &&
755 	    TimeOuts.to_q_return[e->e_timeoutclass] == NOW)
756 		return;
757 
758 	/*
759 	**  Run through the list and send everything.
760 	**
761 	**	Set EF_GLOBALERRS so that error messages during delivery
762 	**	result in returned mail.
763 	*/
764 
765 	e->e_nsent = 0;
766 	e->e_flags |= EF_GLOBALERRS;
767 
768 	define(macid("{envid}", NULL), e->e_envid, e);
769 	define(macid("{bodytype}", NULL), e->e_bodytype, e);
770 	didany = FALSE;
771 
772 	/* now run through the queue */
773 	for (q = e->e_sendqueue; q != NULL; q = q->q_next)
774 	{
775 #if XDEBUG
776 		char wbuf[MAXNAME + 20];
777 
778 		(void) snprintf(wbuf, sizeof wbuf, "sendall(%.*s)",
779 			MAXNAME, q->q_paddr);
780 		checkfd012(wbuf);
781 #endif /* XDEBUG */
782 		if (mode == SM_VERIFY)
783 		{
784 			e->e_to = q->q_paddr;
785 			if (QS_IS_SENDABLE(q->q_state))
786 			{
787 				if (q->q_host != NULL && q->q_host[0] != '\0')
788 					message("deliverable: mailer %s, host %s, user %s",
789 						q->q_mailer->m_name,
790 						q->q_host,
791 						q->q_user);
792 				else
793 					message("deliverable: mailer %s, user %s",
794 						q->q_mailer->m_name,
795 						q->q_user);
796 			}
797 		}
798 		else if (QS_IS_OK(q->q_state))
799 		{
800 #if QUEUE
801 			/*
802 			**  Checkpoint the send list every few addresses
803 			*/
804 
805 			if (CheckpointInterval > 0 &&
806 			    e->e_nsent >= CheckpointInterval)
807 			{
808 				queueup(e, FALSE);
809 				e->e_nsent = 0;
810 			}
811 #endif /* QUEUE */
812 			(void) deliver(e, q);
813 			didany = TRUE;
814 		}
815 	}
816 	if (didany)
817 	{
818 		e->e_dtime = curtime();
819 		e->e_ntries++;
820 	}
821 
822 #if XDEBUG
823 	checkfd012("end of sendenvelope");
824 #endif /* XDEBUG */
825 }
826 /*
827 **  DUP_QUEUE_FILE -- duplicate a queue file into a split queue
828 **
829 **	Parameters:
830 **		e -- the existing envelope
831 **		ee -- the new envelope
832 **		type -- the queue file type (e.g., 'd')
833 **
834 **	Returns:
835 **		none
836 */
837 
838 static void
839 dup_queue_file(e, ee, type)
840 	struct envelope *e, *ee;
841 	int type;
842 {
843 	char f1buf[MAXPATHLEN], f2buf[MAXPATHLEN];
844 
845 	ee->e_dfp = NULL;
846 	ee->e_xfp = NULL;
847 
848 	/*
849 	**  Make sure both are in the same directory.
850 	*/
851 
852 	snprintf(f1buf, sizeof f1buf, "%s", queuename(e, type));
853 	snprintf(f2buf, sizeof f2buf, "%s", queuename(ee, type));
854 	if (link(f1buf, f2buf) < 0)
855 	{
856 		int save_errno = errno;
857 
858 		syserr("sendall: link(%s, %s)", f1buf, f2buf);
859 		if (save_errno == EEXIST)
860 		{
861 			if (unlink(f2buf) < 0)
862 			{
863 				syserr("!sendall: unlink(%s): permanent",
864 					f2buf);
865 				/* NOTREACHED */
866 			}
867 			if (link(f1buf, f2buf) < 0)
868 			{
869 				syserr("!sendall: link(%s, %s): permanent",
870 					f1buf, f2buf);
871 				/* NOTREACHED */
872 			}
873 		}
874 	}
875 }
876 /*
877 **  DOFORK -- do a fork, retrying a couple of times on failure.
878 **
879 **	This MUST be a macro, since after a vfork we are running
880 **	two processes on the same stack!!!
881 **
882 **	Parameters:
883 **		none.
884 **
885 **	Returns:
886 **		From a macro???  You've got to be kidding!
887 **
888 **	Side Effects:
889 **		Modifies the ==> LOCAL <== variable 'pid', leaving:
890 **			pid of child in parent, zero in child.
891 **			-1 on unrecoverable error.
892 **
893 **	Notes:
894 **		I'm awfully sorry this looks so awful.  That's
895 **		vfork for you.....
896 */
897 
898 #define NFORKTRIES	5
899 
900 #ifndef FORK
901 # define FORK	fork
902 #endif /* ! FORK */
903 
904 #define DOFORK(fORKfN) \
905 {\
906 	register int i;\
907 \
908 	for (i = NFORKTRIES; --i >= 0; )\
909 	{\
910 		pid = fORKfN();\
911 		if (pid >= 0)\
912 			break;\
913 		if (i > 0)\
914 			(void) sleep((unsigned) NFORKTRIES - i);\
915 	}\
916 }
917 /*
918 **  DOFORK -- simple fork interface to DOFORK.
919 **
920 **	Parameters:
921 **		none.
922 **
923 **	Returns:
924 **		pid of child in parent.
925 **		zero in child.
926 **		-1 on error.
927 **
928 **	Side Effects:
929 **		returns twice, once in parent and once in child.
930 */
931 
932 int
933 dofork()
934 {
935 	register pid_t pid = -1;
936 
937 	DOFORK(fork);
938 	return pid;
939 }
940 /*
941 **  DELIVER -- Deliver a message to a list of addresses.
942 **
943 **	This routine delivers to everyone on the same host as the
944 **	user on the head of the list.  It is clever about mailers
945 **	that don't handle multiple users.  It is NOT guaranteed
946 **	that it will deliver to all these addresses however -- so
947 **	deliver should be called once for each address on the
948 **	list.
949 **
950 **	Parameters:
951 **		e -- the envelope to deliver.
952 **		firstto -- head of the address list to deliver to.
953 **
954 **	Returns:
955 **		zero -- successfully delivered.
956 **		else -- some failure, see ExitStat for more info.
957 **
958 **	Side Effects:
959 **		The standard input is passed off to someone.
960 */
961 
962 #ifndef NO_UID
963 # define NO_UID		-1
964 #endif /* ! NO_UID */
965 #ifndef NO_GID
966 # define NO_GID		-1
967 #endif /* ! NO_GID */
968 
969 static int
970 deliver(e, firstto)
971 	register ENVELOPE *e;
972 	ADDRESS *firstto;
973 {
974 	char *host;			/* host being sent to */
975 	char *user;			/* user being sent to */
976 	char **pvp;
977 	register char **mvp;
978 	register char *p;
979 	register MAILER *m;		/* mailer for this recipient */
980 	ADDRESS *volatile ctladdr;
981 	ADDRESS *volatile contextaddr = NULL;
982 	register MCI *volatile mci;
983 	register ADDRESS *to = firstto;
984 	volatile bool clever = FALSE;	/* running user smtp to this mailer */
985 	ADDRESS *volatile tochain = NULL; /* users chain in this mailer call */
986 	int rcode;			/* response code */
987 	int lmtp_rcode = EX_OK;
988 	int nummxhosts = 0;		/* number of MX hosts available */
989 	int hostnum = 0;		/* current MX host index */
990 	char *firstsig;			/* signature of firstto */
991 	pid_t pid = -1;
992 	char *volatile curhost;
993 	register u_short port = 0;
994 #if NETUNIX
995 	char *mux_path = NULL;		/* path to UNIX domain socket */
996 #endif /* NETUNIX */
997 	time_t xstart;
998 	bool suidwarn;
999 	bool anyok;			/* at least one address was OK */
1000 	bool goodmxfound = FALSE;	/* at least one MX was OK */
1001 	bool ovr;
1002 #if _FFR_DYNAMIC_TOBUF
1003 	int strsize;
1004 	int rcptcount;
1005 	static int tobufsize = 0;
1006 	static char *tobuf = NULL;
1007 #else /* _FFR_DYNAMIC_TOBUF */
1008 	char tobuf[TOBUFSIZE];		/* text line of to people */
1009 #endif /* _FFR_DYNAMIC_TOBUF */
1010 	int mpvect[2];
1011 	int rpvect[2];
1012 	char *mxhosts[MAXMXHOSTS + 1];
1013 	char *pv[MAXPV + 1];
1014 	char buf[MAXNAME + 1];
1015 	char rpathbuf[MAXNAME + 1];	/* translated return path */
1016 
1017 	errno = 0;
1018 	if (!QS_IS_OK(to->q_state))
1019 		return 0;
1020 
1021 	suidwarn = geteuid() == 0;
1022 
1023 	m = to->q_mailer;
1024 	host = to->q_host;
1025 	CurEnv = e;			/* just in case */
1026 	e->e_statmsg = NULL;
1027 #if SMTP
1028 	SmtpError[0] = '\0';
1029 #endif /* SMTP */
1030 	xstart = curtime();
1031 
1032 	if (tTd(10, 1))
1033 		dprintf("\n--deliver, id=%s, mailer=%s, host=`%s', first user=`%s'\n",
1034 			e->e_id, m->m_name, host, to->q_user);
1035 	if (tTd(10, 100))
1036 		printopenfds(FALSE);
1037 
1038 	/*
1039 	**  Clear $&{client_*} macros if this is a bounce message to
1040 	**  prevent rejection by check_compat ruleset.
1041 	*/
1042 
1043 	if (bitset(EF_RESPONSE, e->e_flags))
1044 	{
1045 		define(macid("{client_name}", NULL), "", e);
1046 		define(macid("{client_addr}", NULL), "", e);
1047 		define(macid("{client_port}", NULL), "", e);
1048 	}
1049 
1050 	/*
1051 	**  Do initial argv setup.
1052 	**	Insert the mailer name.  Notice that $x expansion is
1053 	**	NOT done on the mailer name.  Then, if the mailer has
1054 	**	a picky -f flag, we insert it as appropriate.  This
1055 	**	code does not check for 'pv' overflow; this places a
1056 	**	manifest lower limit of 4 for MAXPV.
1057 	**		The from address rewrite is expected to make
1058 	**		the address relative to the other end.
1059 	*/
1060 
1061 	/* rewrite from address, using rewriting rules */
1062 	rcode = EX_OK;
1063 	if (bitnset(M_UDBENVELOPE, e->e_from.q_mailer->m_flags))
1064 		p = e->e_sender;
1065 	else
1066 		p = e->e_from.q_paddr;
1067 	p = remotename(p, m, RF_SENDERADDR|RF_CANONICAL, &rcode, e);
1068 	if (strlen(p) >= (SIZE_T) sizeof rpathbuf)
1069 	{
1070 		p = shortenstring(p, MAXSHORTSTR);
1071 		syserr("remotename: huge return %s", p);
1072 	}
1073 	snprintf(rpathbuf, sizeof rpathbuf, "%s", p);
1074 	define('g', rpathbuf, e);		/* translated return path */
1075 	define('h', host, e);			/* to host */
1076 	Errors = 0;
1077 	pvp = pv;
1078 	*pvp++ = m->m_argv[0];
1079 
1080 	/* insert -f or -r flag as appropriate */
1081 	if (FromFlag &&
1082 	    (bitnset(M_FOPT, m->m_flags) ||
1083 	     bitnset(M_ROPT, m->m_flags)))
1084 	{
1085 		if (bitnset(M_FOPT, m->m_flags))
1086 			*pvp++ = "-f";
1087 		else
1088 			*pvp++ = "-r";
1089 		*pvp++ = newstr(rpathbuf);
1090 	}
1091 
1092 	/*
1093 	**  Append the other fixed parts of the argv.  These run
1094 	**  up to the first entry containing "$u".  There can only
1095 	**  be one of these, and there are only a few more slots
1096 	**  in the pv after it.
1097 	*/
1098 
1099 	for (mvp = m->m_argv; (p = *++mvp) != NULL; )
1100 	{
1101 		/* can't use strchr here because of sign extension problems */
1102 		while (*p != '\0')
1103 		{
1104 			if ((*p++ & 0377) == MACROEXPAND)
1105 			{
1106 				if (*p == 'u')
1107 					break;
1108 			}
1109 		}
1110 
1111 		if (*p != '\0')
1112 			break;
1113 
1114 		/* this entry is safe -- go ahead and process it */
1115 		expand(*mvp, buf, sizeof buf, e);
1116 		*pvp++ = newstr(buf);
1117 		if (pvp >= &pv[MAXPV - 3])
1118 		{
1119 			syserr("554 5.3.5 Too many parameters to %s before $u",
1120 			       pv[0]);
1121 			return -1;
1122 		}
1123 	}
1124 
1125 	/*
1126 	**  If we have no substitution for the user name in the argument
1127 	**  list, we know that we must supply the names otherwise -- and
1128 	**  SMTP is the answer!!
1129 	*/
1130 
1131 	if (*mvp == NULL)
1132 	{
1133 		/* running SMTP */
1134 #if SMTP
1135 		clever = TRUE;
1136 		*pvp = NULL;
1137 #else /* SMTP */
1138 		/* oops!  we don't implement SMTP */
1139 		syserr("554 5.3.5 SMTP style mailer not implemented");
1140 		return EX_SOFTWARE;
1141 #endif /* SMTP */
1142 	}
1143 
1144 	/*
1145 	**  At this point *mvp points to the argument with $u.  We
1146 	**  run through our address list and append all the addresses
1147 	**  we can.  If we run out of space, do not fret!  We can
1148 	**  always send another copy later.
1149 	*/
1150 
1151 #if _FFR_DYNAMIC_TOBUF
1152 	e->e_to = NULL;
1153 	strsize = 2;
1154 	rcptcount = 0;
1155 #else /* _FFR_DYNAMIC_TOBUF */
1156 	tobuf[0] = '\0';
1157 	e->e_to = tobuf;
1158 #endif /* _FFR_DYNAMIC_TOBUF */
1159 
1160 	ctladdr = NULL;
1161 	firstsig = hostsignature(firstto->q_mailer, firstto->q_host);
1162 	for (; to != NULL; to = to->q_next)
1163 	{
1164 		/* avoid sending multiple recipients to dumb mailers */
1165 #if _FFR_DYNAMIC_TOBUF
1166 		if (tochain != NULL && !bitnset(M_MUSER, m->m_flags))
1167 			break;
1168 #else /* _FFR_DYNAMIC_TOBUF */
1169 		if (tobuf[0] != '\0' && !bitnset(M_MUSER, m->m_flags))
1170 			break;
1171 #endif /* _FFR_DYNAMIC_TOBUF */
1172 
1173 		/* if already sent or not for this host, don't send */
1174 		if (!QS_IS_OK(to->q_state) ||
1175 		    to->q_mailer != firstto->q_mailer ||
1176 		    strcmp(hostsignature(to->q_mailer, to->q_host),
1177 			   firstsig) != 0)
1178 			continue;
1179 
1180 		/* avoid overflowing tobuf */
1181 #if _FFR_DYNAMIC_TOBUF
1182 		strsize += strlen(to->q_paddr) + 1;
1183 		if (!clever && strsize > TOBUFSIZE)
1184 			break;
1185 
1186 		if (++rcptcount > to->q_mailer->m_maxrcpt)
1187 			break;
1188 #else /* _FFR_DYNAMIC_TOBUF */
1189 		if (sizeof tobuf < (strlen(to->q_paddr) + strlen(tobuf) + 2))
1190 			break;
1191 #endif /* _FFR_DYNAMIC_TOBUF */
1192 
1193 		if (tTd(10, 1))
1194 		{
1195 			dprintf("\nsend to ");
1196 			printaddr(to, FALSE);
1197 		}
1198 
1199 		/* compute effective uid/gid when sending */
1200 		if (bitnset(M_RUNASRCPT, to->q_mailer->m_flags))
1201 			contextaddr = ctladdr = getctladdr(to);
1202 
1203 		if (tTd(10, 2))
1204 		{
1205 			dprintf("ctladdr=");
1206 			printaddr(ctladdr, FALSE);
1207 		}
1208 
1209 		user = to->q_user;
1210 		e->e_to = to->q_paddr;
1211 
1212 		/*
1213 		**  Check to see that these people are allowed to
1214 		**  talk to each other.
1215 		**  Check also for overflow of e_msgsize.
1216 		*/
1217 
1218 		if (m->m_maxsize != 0 &&
1219 		    (e->e_msgsize > m->m_maxsize || e->e_msgsize < 0))
1220 		{
1221 			e->e_flags |= EF_NO_BODY_RETN;
1222 			if (bitnset(M_LOCALMAILER, to->q_mailer->m_flags))
1223 				to->q_status = "5.2.3";
1224 			else
1225 				to->q_status = "5.3.4";
1226 			/* set to->q_rstatus = NULL; or to the following? */
1227 			usrerrenh(to->q_status,
1228 				  "552 Message is too large; %ld bytes max",
1229 				  m->m_maxsize);
1230 			markfailure(e, to, NULL, EX_UNAVAILABLE, FALSE);
1231 			giveresponse(EX_UNAVAILABLE, to->q_status, m,
1232 				     NULL, ctladdr, xstart, e);
1233 			continue;
1234 		}
1235 #if NAMED_BIND
1236 		h_errno = 0;
1237 #endif /* NAMED_BIND */
1238 
1239 		ovr = TRUE;
1240 		/* do config file checking of compatibility */
1241 		rcode = rscheck("check_compat", e->e_from.q_paddr, to->q_paddr,
1242 				e, TRUE, TRUE, 4);
1243 		if (rcode == EX_OK)
1244 		{
1245 			/* do in-code checking if not discarding */
1246 			if (!bitset(EF_DISCARD, e->e_flags))
1247 			{
1248 				rcode = checkcompat(to, e);
1249 				ovr = FALSE;
1250 			}
1251 		}
1252 		if (rcode != EX_OK)
1253 		{
1254 			markfailure(e, to, NULL, rcode, ovr);
1255 			giveresponse(rcode, to->q_status, m,
1256 				     NULL, ctladdr, xstart, e);
1257 			continue;
1258 		}
1259 		if (bitset(EF_DISCARD, e->e_flags))
1260 		{
1261 			if (tTd(10, 5))
1262 			{
1263 				dprintf("deliver: discarding recipient ");
1264 				printaddr(to, FALSE);
1265 			}
1266 
1267 			/* pretend the message was sent */
1268 			/* XXX should we log something here? */
1269 			to->q_state = QS_DISCARDED;
1270 
1271 			/*
1272 			**  Remove discard bit to prevent discard of
1273 			**  future recipients.  This is safe because the
1274 			**  true "global discard" has been handled before
1275 			**  we get here.
1276 			*/
1277 
1278 			e->e_flags &= ~EF_DISCARD;
1279 			continue;
1280 		}
1281 
1282 		/*
1283 		**  Strip quote bits from names if the mailer is dumb
1284 		**	about them.
1285 		*/
1286 
1287 		if (bitnset(M_STRIPQ, m->m_flags))
1288 		{
1289 			stripquotes(user);
1290 			stripquotes(host);
1291 		}
1292 
1293 		/* hack attack -- delivermail compatibility */
1294 		if (m == ProgMailer && *user == '|')
1295 			user++;
1296 
1297 		/*
1298 		**  If an error message has already been given, don't
1299 		**	bother to send to this address.
1300 		**
1301 		**	>>>>>>>>>> This clause assumes that the local mailer
1302 		**	>> NOTE >> cannot do any further aliasing; that
1303 		**	>>>>>>>>>> function is subsumed by sendmail.
1304 		*/
1305 
1306 		if (!QS_IS_OK(to->q_state))
1307 			continue;
1308 
1309 		/*
1310 		**  See if this user name is "special".
1311 		**	If the user name has a slash in it, assume that this
1312 		**	is a file -- send it off without further ado.  Note
1313 		**	that this type of addresses is not processed along
1314 		**	with the others, so we fudge on the To person.
1315 		*/
1316 
1317 		if (strcmp(m->m_mailer, "[FILE]") == 0)
1318 		{
1319 			define('u', user, e);	/* to user */
1320 			p = to->q_home;
1321 			if (p == NULL && ctladdr != NULL)
1322 				p = ctladdr->q_home;
1323 			define('z', p, e);	/* user's home */
1324 			expand(m->m_argv[1], buf, sizeof buf, e);
1325 			if (strlen(buf) > 0)
1326 				rcode = mailfile(buf, m, ctladdr, SFF_CREAT, e);
1327 			else
1328 			{
1329 				syserr("empty filename specification for mailer %s",
1330 				       m->m_name);
1331 				rcode = EX_CONFIG;
1332 			}
1333 			giveresponse(rcode, to->q_status, m, NULL,
1334 				     ctladdr, xstart, e);
1335 			markfailure(e, to, NULL, rcode, TRUE);
1336 			e->e_nsent++;
1337 			if (rcode == EX_OK)
1338 			{
1339 				to->q_state = QS_SENT;
1340 				if (bitnset(M_LOCALMAILER, m->m_flags) &&
1341 				    bitset(QPINGONSUCCESS, to->q_flags))
1342 				{
1343 					to->q_flags |= QDELIVERED;
1344 					to->q_status = "2.1.5";
1345 					fprintf(e->e_xfp, "%s... Successfully delivered\n",
1346 						to->q_paddr);
1347 				}
1348 			}
1349 			to->q_statdate = curtime();
1350 			markstats(e, to, FALSE);
1351 			continue;
1352 		}
1353 
1354 		/*
1355 		**  Address is verified -- add this user to mailer
1356 		**  argv, and add it to the print list of recipients.
1357 		*/
1358 
1359 		/* link together the chain of recipients */
1360 		to->q_tchain = tochain;
1361 		tochain = to;
1362 
1363 #if _FFR_DYNAMIC_TOBUF
1364 		e->e_to = "[CHAIN]";
1365 #else /* _FFR_DYNAMIC_TOBUF */
1366 		/* create list of users for error messages */
1367 		(void) strlcat(tobuf, ",", sizeof tobuf);
1368 		(void) strlcat(tobuf, to->q_paddr, sizeof tobuf);
1369 #endif /* _FFR_DYNAMIC_TOBUF */
1370 
1371 		define('u', user, e);		/* to user */
1372 		p = to->q_home;
1373 		if (p == NULL && ctladdr != NULL)
1374 			p = ctladdr->q_home;
1375 		define('z', p, e);	/* user's home */
1376 
1377 		/* set the ${dsn_notify} macro if applicable */
1378 		if (bitset(QHASNOTIFY, to->q_flags))
1379 		{
1380 			char notify[MAXLINE];
1381 
1382 			notify[0] = '\0';
1383 			if (bitset(QPINGONSUCCESS, to->q_flags))
1384 				(void) strlcat(notify, "SUCCESS,",
1385 					       sizeof notify);
1386 			if (bitset(QPINGONFAILURE, to->q_flags))
1387 				(void) strlcat(notify, "FAILURE,",
1388 					       sizeof notify);
1389 			if (bitset(QPINGONDELAY, to->q_flags))
1390 				(void) strlcat(notify, "DELAY,", sizeof notify);
1391 
1392 			/* Set to NEVER or drop trailing comma */
1393 			if (notify[0] == '\0')
1394 				(void) strlcat(notify, "NEVER", sizeof notify);
1395 			else
1396 				notify[strlen(notify) - 1] = '\0';
1397 
1398 			define(macid("{dsn_notify}", NULL), newstr(notify), e);
1399 		}
1400 		else
1401 			define(macid("{dsn_notify}", NULL), NULL, e);
1402 
1403 		/*
1404 		**  Expand out this user into argument list.
1405 		*/
1406 
1407 		if (!clever)
1408 		{
1409 			expand(*mvp, buf, sizeof buf, e);
1410 			*pvp++ = newstr(buf);
1411 			if (pvp >= &pv[MAXPV - 2])
1412 			{
1413 				/* allow some space for trailing parms */
1414 				break;
1415 			}
1416 		}
1417 	}
1418 
1419 	/* see if any addresses still exist */
1420 #if _FFR_DYNAMIC_TOBUF
1421 	if (tochain == NULL)
1422 #else /* _FFR_DYNAMIC_TOBUF */
1423 	if (tobuf[0] == '\0')
1424 #endif /* _FFR_DYNAMIC_TOBUF */
1425 	{
1426 		define('g', (char *) NULL, e);
1427 		e->e_to = NULL;
1428 		return 0;
1429 	}
1430 
1431 	/* print out messages as full list */
1432 #if _FFR_DYNAMIC_TOBUF
1433 	{
1434 		int l = 1;
1435 		char *tobufptr;
1436 
1437 		for (to = tochain; to != NULL; to = to->q_tchain)
1438 			l += strlen(to->q_paddr) + 1;
1439 		if (l < TOBUFSIZE)
1440 			l = TOBUFSIZE;
1441 		if (l > tobufsize)
1442 		{
1443 			if (tobuf != NULL)
1444 				free(tobuf);
1445 			tobufsize = l;
1446 			tobuf = xalloc(tobufsize);
1447 		}
1448 		tobufptr = tobuf;
1449 		*tobufptr = '\0';
1450 		for (to = tochain; to != NULL; to = to->q_tchain)
1451 		{
1452 			snprintf(tobufptr, tobufsize - (tobufptr - tobuf),
1453 				 ",%s", to->q_paddr);
1454 			tobufptr += strlen(tobufptr);
1455 		}
1456 	}
1457 #endif /* _FFR_DYNAMIC_TOBUF */
1458 	e->e_to = tobuf + 1;
1459 
1460 	/*
1461 	**  Fill out any parameters after the $u parameter.
1462 	*/
1463 
1464 	while (!clever && *++mvp != NULL)
1465 	{
1466 		expand(*mvp, buf, sizeof buf, e);
1467 		*pvp++ = newstr(buf);
1468 		if (pvp >= &pv[MAXPV])
1469 			syserr("554 5.3.0 deliver: pv overflow after $u for %s",
1470 			       pv[0]);
1471 	}
1472 	*pvp++ = NULL;
1473 
1474 	/*
1475 	**  Call the mailer.
1476 	**	The argument vector gets built, pipes
1477 	**	are created as necessary, and we fork & exec as
1478 	**	appropriate.
1479 	**	If we are running SMTP, we just need to clean up.
1480 	*/
1481 
1482 	/* XXX this seems a bit wierd */
1483 	if (ctladdr == NULL && m != ProgMailer && m != FileMailer &&
1484 	    bitset(QGOODUID, e->e_from.q_flags))
1485 		ctladdr = &e->e_from;
1486 
1487 #if NAMED_BIND
1488 	if (ConfigLevel < 2)
1489 		_res.options &= ~(RES_DEFNAMES | RES_DNSRCH);	/* XXX */
1490 #endif /* NAMED_BIND */
1491 
1492 	if (tTd(11, 1))
1493 	{
1494 		dprintf("openmailer:");
1495 		printav(pv);
1496 	}
1497 	errno = 0;
1498 #if NAMED_BIND
1499 	h_errno = 0;
1500 #endif /* NAMED_BIND */
1501 
1502 	CurHostName = NULL;
1503 
1504 	/*
1505 	**  Deal with the special case of mail handled through an IPC
1506 	**  connection.
1507 	**	In this case we don't actually fork.  We must be
1508 	**	running SMTP for this to work.  We will return a
1509 	**	zero pid to indicate that we are running IPC.
1510 	**  We also handle a debug version that just talks to stdin/out.
1511 	*/
1512 
1513 	curhost = NULL;
1514 	SmtpPhase = NULL;
1515 	mci = NULL;
1516 
1517 #if XDEBUG
1518 	{
1519 		char wbuf[MAXLINE];
1520 
1521 		/* make absolutely certain 0, 1, and 2 are in use */
1522 		snprintf(wbuf, sizeof wbuf, "%s... openmailer(%s)",
1523 			shortenstring(e->e_to, MAXSHORTSTR), m->m_name);
1524 		checkfd012(wbuf);
1525 	}
1526 #endif /* XDEBUG */
1527 
1528 	/* check for 8-bit available */
1529 	if (bitset(EF_HAS8BIT, e->e_flags) &&
1530 	    bitnset(M_7BITS, m->m_flags) &&
1531 	    (bitset(EF_DONT_MIME, e->e_flags) ||
1532 	     !(bitset(MM_MIME8BIT, MimeMode) ||
1533 	       (bitset(EF_IS_MIME, e->e_flags) &&
1534 		bitset(MM_CVTMIME, MimeMode)))))
1535 	{
1536 		e->e_status = "5.6.3";
1537 		usrerrenh(e->e_status,
1538 		       "554 Cannot send 8-bit data to 7-bit destination");
1539 		rcode = EX_DATAERR;
1540 		goto give_up;
1541 	}
1542 
1543 	if (tTd(62, 8))
1544 		checkfds("before delivery");
1545 
1546 	/* check for Local Person Communication -- not for mortals!!! */
1547 	if (strcmp(m->m_mailer, "[LPC]") == 0)
1548 	{
1549 		mci = (MCI *) xalloc(sizeof *mci);
1550 		memset((char *) mci, '\0', sizeof *mci);
1551 		mci->mci_in = stdin;
1552 		mci->mci_out = stdout;
1553 		mci->mci_state = clever ? MCIS_OPENING : MCIS_OPEN;
1554 		mci->mci_mailer = m;
1555 	}
1556 	else if (strcmp(m->m_mailer, "[IPC]") == 0 ||
1557 		 strcmp(m->m_mailer, "[TCP]") == 0)
1558 	{
1559 #if DAEMON
1560 		register int i;
1561 
1562 		if (pv[0] == NULL || pv[1] == NULL || pv[1][0] == '\0')
1563 		{
1564 			syserr("null destination for %s mailer", m->m_mailer);
1565 			rcode = EX_CONFIG;
1566 			goto give_up;
1567 		}
1568 
1569 # if NETUNIX
1570 		if (strcmp(pv[0], "FILE") == 0)
1571 		{
1572 			curhost = CurHostName = "localhost";
1573 			mux_path = pv[1];
1574 		}
1575 		else
1576 # endif /* NETUNIX */
1577 		{
1578 			CurHostName = pv[1];
1579 			curhost = hostsignature(m, pv[1]);
1580 		}
1581 
1582 		if (curhost == NULL || curhost[0] == '\0')
1583 		{
1584 			syserr("null host signature for %s", pv[1]);
1585 			rcode = EX_CONFIG;
1586 			goto give_up;
1587 		}
1588 
1589 		if (!clever)
1590 		{
1591 			syserr("554 5.3.5 non-clever IPC");
1592 			rcode = EX_CONFIG;
1593 			goto give_up;
1594 		}
1595 		if (pv[2] != NULL
1596 # if NETUNIX
1597 		    && mux_path == NULL
1598 # endif /* NETUNIX */
1599 		    )
1600 		{
1601 			port = htons((u_short)atoi(pv[2]));
1602 			if (port == 0)
1603 			{
1604 # ifdef NO_GETSERVBYNAME
1605 				syserr("Invalid port number: %s", pv[2]);
1606 # else /* NO_GETSERVBYNAME */
1607 				struct servent *sp = getservbyname(pv[2], "tcp");
1608 
1609 				if (sp == NULL)
1610 					syserr("Service %s unknown", pv[2]);
1611 				else
1612 					port = sp->s_port;
1613 # endif /* NO_GETSERVBYNAME */
1614 			}
1615 		}
1616 
1617 		nummxhosts = parse_hostsignature(curhost, mxhosts, m);
1618 tryhost:
1619 		while (hostnum < nummxhosts)
1620 		{
1621 			char sep = ':';
1622 			char *endp;
1623 			static char hostbuf[MAXNAME + 1];
1624 
1625 # if NETINET6
1626 			if (*mxhosts[hostnum] == '[')
1627 			{
1628 				endp = strchr(mxhosts[hostnum] + 1, ']');
1629 				if (endp != NULL)
1630 					endp = strpbrk(endp + 1, ":,");
1631 			}
1632 			else
1633 				endp = strpbrk(mxhosts[hostnum], ":,");
1634 # else /* NETINET6 */
1635 			endp = strpbrk(mxhosts[hostnum], ":,");
1636 # endif /* NETINET6 */
1637 			if (endp != NULL)
1638 			{
1639 				sep = *endp;
1640 				*endp = '\0';
1641 			}
1642 
1643 			if (*mxhosts[hostnum] == '\0')
1644 			{
1645 				syserr("deliver: null host name in signature");
1646 				hostnum++;
1647 				if (endp != NULL)
1648 					*endp = sep;
1649 				continue;
1650 			}
1651 			(void) strlcpy(hostbuf, mxhosts[hostnum],
1652 				       sizeof hostbuf);
1653 			hostnum++;
1654 			if (endp != NULL)
1655 				*endp = sep;
1656 
1657 			/* see if we already know that this host is fried */
1658 			CurHostName = hostbuf;
1659 			mci = mci_get(hostbuf, m);
1660 			if (mci->mci_state != MCIS_CLOSED)
1661 			{
1662 				if (tTd(11, 1))
1663 				{
1664 					dprintf("openmailer: ");
1665 					mci_dump(mci, FALSE);
1666 				}
1667 				CurHostName = mci->mci_host;
1668 				message("Using cached %sSMTP connection to %s via %s...",
1669 					bitset(MCIF_ESMTP, mci->mci_flags) ? "E" : "",
1670 					hostbuf, m->m_name);
1671 				mci->mci_deliveries++;
1672 				break;
1673 			}
1674 			mci->mci_mailer = m;
1675 			if (mci->mci_exitstat != EX_OK)
1676 			{
1677 				if (mci->mci_exitstat == EX_TEMPFAIL)
1678 					goodmxfound = TRUE;
1679 				continue;
1680 			}
1681 
1682 			if (mci_lock_host(mci) != EX_OK)
1683 			{
1684 				mci_setstat(mci, EX_TEMPFAIL, "4.4.5", NULL);
1685 				goodmxfound = TRUE;
1686 				continue;
1687 			}
1688 
1689 			/* try the connection */
1690 			sm_setproctitle(TRUE, e, "%s %s: %s",
1691 					qid_printname(e),
1692 					hostbuf, "user open");
1693 # if NETUNIX
1694 			if (mux_path != NULL)
1695 			{
1696 				message("Connecting to %s via %s...",
1697 					mux_path, m->m_name);
1698 				i = makeconnection_ds(mux_path, mci);
1699 			}
1700 			else
1701 # endif /* NETUNIX */
1702 			{
1703 				if (port == 0)
1704 					message("Connecting to %s via %s...",
1705 						hostbuf, m->m_name);
1706 				else
1707 					message("Connecting to %s port %d via %s...",
1708 						hostbuf, ntohs(port),
1709 						m->m_name);
1710 				i = makeconnection(hostbuf, port, mci, e);
1711 			}
1712 			mci->mci_lastuse = curtime();
1713 			mci->mci_deliveries = 0;
1714 			mci->mci_exitstat = i;
1715 			mci->mci_errno = errno;
1716 # if NAMED_BIND
1717 			mci->mci_herrno = h_errno;
1718 # endif /* NAMED_BIND */
1719 			if (i == EX_OK)
1720 			{
1721 				goodmxfound = TRUE;
1722 				mci->mci_state = MCIS_OPENING;
1723 				mci_cache(mci);
1724 				if (TrafficLogFile != NULL)
1725 					fprintf(TrafficLogFile, "%05d === CONNECT %s\n",
1726 						(int) getpid(), hostbuf);
1727 				break;
1728 			}
1729 			else
1730 			{
1731 				if (tTd(11, 1))
1732 					dprintf("openmailer: makeconnection => stat=%d, errno=%d\n",
1733 						i, errno);
1734 				if (i == EX_TEMPFAIL)
1735 					goodmxfound = TRUE;
1736 				mci_unlock_host(mci);
1737 			}
1738 
1739 			/* enter status of this host */
1740 			setstat(i);
1741 
1742 			/* should print some message here for -v mode */
1743 		}
1744 		if (mci == NULL)
1745 		{
1746 			syserr("deliver: no host name");
1747 			rcode = EX_SOFTWARE;
1748 			goto give_up;
1749 		}
1750 		mci->mci_pid = 0;
1751 #else /* DAEMON */
1752 		syserr("554 5.3.5 openmailer: no IPC");
1753 		if (tTd(11, 1))
1754 			dprintf("openmailer: NULL\n");
1755 		rcode = EX_UNAVAILABLE;
1756 		goto give_up;
1757 #endif /* DAEMON */
1758 	}
1759 	else
1760 	{
1761 		/* flush any expired connections */
1762 		(void) mci_scan(NULL);
1763 		mci = NULL;
1764 
1765 #if SMTP
1766 		if (bitnset(M_LMTP, m->m_flags))
1767 		{
1768 			/* try to get a cached connection */
1769 			mci = mci_get(m->m_name, m);
1770 			if (mci->mci_host == NULL)
1771 				mci->mci_host = m->m_name;
1772 			CurHostName = mci->mci_host;
1773 			if (mci->mci_state != MCIS_CLOSED)
1774 			{
1775 				message("Using cached LMTP connection for %s...",
1776 					m->m_name);
1777 				mci->mci_deliveries++;
1778 				goto do_transfer;
1779 			}
1780 		}
1781 #endif /* SMTP */
1782 
1783 		/* announce the connection to verbose listeners */
1784 		if (host == NULL || host[0] == '\0')
1785 			message("Connecting to %s...", m->m_name);
1786 		else
1787 			message("Connecting to %s via %s...", host, m->m_name);
1788 		if (TrafficLogFile != NULL)
1789 		{
1790 			char **av;
1791 
1792 			fprintf(TrafficLogFile, "%05d === EXEC", (int) getpid());
1793 			for (av = pv; *av != NULL; av++)
1794 				fprintf(TrafficLogFile, " %s", *av);
1795 			fprintf(TrafficLogFile, "\n");
1796 		}
1797 
1798 #if XDEBUG
1799 		checkfd012("before creating mail pipe");
1800 #endif /* XDEBUG */
1801 
1802 		/* create a pipe to shove the mail through */
1803 		if (pipe(mpvect) < 0)
1804 		{
1805 			syserr("%s... openmailer(%s): pipe (to mailer)",
1806 				shortenstring(e->e_to, MAXSHORTSTR), m->m_name);
1807 			if (tTd(11, 1))
1808 				dprintf("openmailer: NULL\n");
1809 			rcode = EX_OSERR;
1810 			goto give_up;
1811 		}
1812 
1813 #if XDEBUG
1814 		/* make sure we didn't get one of the standard I/O files */
1815 		if (mpvect[0] < 3 || mpvect[1] < 3)
1816 		{
1817 			syserr("%s... openmailer(%s): bogus mpvect %d %d",
1818 				shortenstring(e->e_to, MAXSHORTSTR), m->m_name,
1819 				mpvect[0], mpvect[1]);
1820 			printopenfds(TRUE);
1821 			if (tTd(11, 1))
1822 				dprintf("openmailer: NULL\n");
1823 			rcode = EX_OSERR;
1824 			goto give_up;
1825 		}
1826 
1827 		/* make sure system call isn't dead meat */
1828 		checkfdopen(mpvect[0], "mpvect[0]");
1829 		checkfdopen(mpvect[1], "mpvect[1]");
1830 		if (mpvect[0] == mpvect[1] ||
1831 		    (e->e_lockfp != NULL &&
1832 		     (mpvect[0] == fileno(e->e_lockfp) ||
1833 		      mpvect[1] == fileno(e->e_lockfp))))
1834 		{
1835 			if (e->e_lockfp == NULL)
1836 				syserr("%s... openmailer(%s): overlapping mpvect %d %d",
1837 					shortenstring(e->e_to, MAXSHORTSTR),
1838 					m->m_name, mpvect[0], mpvect[1]);
1839 			else
1840 				syserr("%s... openmailer(%s): overlapping mpvect %d %d, lockfp = %d",
1841 					shortenstring(e->e_to, MAXSHORTSTR),
1842 					m->m_name, mpvect[0], mpvect[1],
1843 					fileno(e->e_lockfp));
1844 		}
1845 #endif /* XDEBUG */
1846 
1847 		/* create a return pipe */
1848 		if (pipe(rpvect) < 0)
1849 		{
1850 			syserr("%s... openmailer(%s): pipe (from mailer)",
1851 				shortenstring(e->e_to, MAXSHORTSTR),
1852 				m->m_name);
1853 			(void) close(mpvect[0]);
1854 			(void) close(mpvect[1]);
1855 			if (tTd(11, 1))
1856 				dprintf("openmailer: NULL\n");
1857 			rcode = EX_OSERR;
1858 			goto give_up;
1859 		}
1860 #if XDEBUG
1861 		checkfdopen(rpvect[0], "rpvect[0]");
1862 		checkfdopen(rpvect[1], "rpvect[1]");
1863 #endif /* XDEBUG */
1864 
1865 		/*
1866 		**  Actually fork the mailer process.
1867 		**	DOFORK is clever about retrying.
1868 		**
1869 		**	Dispose of SIGCHLD signal catchers that may be laying
1870 		**	around so that endmailer will get it.
1871 		*/
1872 
1873 		if (e->e_xfp != NULL)
1874 			(void) fflush(e->e_xfp);	/* for debugging */
1875 		(void) fflush(stdout);
1876 		(void) setsignal(SIGCHLD, SIG_DFL);
1877 
1878 
1879 		DOFORK(FORK);
1880 		/* pid is set by DOFORK */
1881 
1882 		if (pid < 0)
1883 		{
1884 			/* failure */
1885 			syserr("%s... openmailer(%s): cannot fork",
1886 				shortenstring(e->e_to, MAXSHORTSTR), m->m_name);
1887 			(void) close(mpvect[0]);
1888 			(void) close(mpvect[1]);
1889 			(void) close(rpvect[0]);
1890 			(void) close(rpvect[1]);
1891 			if (tTd(11, 1))
1892 				dprintf("openmailer: NULL\n");
1893 			rcode = EX_OSERR;
1894 			goto give_up;
1895 		}
1896 		else if (pid == 0)
1897 		{
1898 			int i;
1899 			int save_errno;
1900 			int new_euid = NO_UID;
1901 			int new_ruid = NO_UID;
1902 			int new_gid = NO_GID;
1903 			struct stat stb;
1904 			extern int DtableSize;
1905 
1906 			if (e->e_lockfp != NULL)
1907 				(void) close(fileno(e->e_lockfp));
1908 
1909 			/* child -- set up input & exec mailer */
1910 			(void) setsignal(SIGINT, SIG_IGN);
1911 			(void) setsignal(SIGHUP, SIG_IGN);
1912 			(void) setsignal(SIGTERM, SIG_DFL);
1913 
1914 			if (m != FileMailer || stat(tochain->q_user, &stb) < 0)
1915 				stb.st_mode = 0;
1916 
1917 # if HASSETUSERCONTEXT
1918 			/*
1919 			**  Set user resources.
1920 			*/
1921 
1922 			if (contextaddr != NULL)
1923 			{
1924 				struct passwd *pwd;
1925 
1926 				if (contextaddr->q_ruser != NULL)
1927 					pwd = sm_getpwnam(contextaddr->q_ruser);
1928 				else
1929 					pwd = sm_getpwnam(contextaddr->q_user);
1930 				if (pwd != NULL)
1931 					(void) setusercontext(NULL,
1932 						pwd, pwd->pw_uid,
1933 						LOGIN_SETRESOURCES|LOGIN_SETPRIORITY);
1934 			}
1935 # endif /* HASSETUSERCONTEXT */
1936 
1937 			/* tweak niceness */
1938 			if (m->m_nice != 0)
1939 				(void) nice(m->m_nice);
1940 
1941 			/* reset group id */
1942 			if (bitnset(M_SPECIFIC_UID, m->m_flags))
1943 				new_gid = m->m_gid;
1944 			else if (bitset(S_ISGID, stb.st_mode))
1945 				new_gid = stb.st_gid;
1946 			else if (ctladdr != NULL && ctladdr->q_gid != 0)
1947 			{
1948 				if (!DontInitGroups)
1949 				{
1950 					char *u = ctladdr->q_ruser;
1951 
1952 					if (u == NULL)
1953 						u = ctladdr->q_user;
1954 
1955 					if (initgroups(u, ctladdr->q_gid) == -1 && suidwarn)
1956 					{
1957 						syserr("openmailer: initgroups(%s, %d) failed",
1958 							u, ctladdr->q_gid);
1959 						exit(EX_TEMPFAIL);
1960 					}
1961 				}
1962 				else
1963 				{
1964 					GIDSET_T gidset[1];
1965 
1966 					gidset[0] = ctladdr->q_gid;
1967 					if (setgroups(1, gidset) == -1 && suidwarn)
1968 					{
1969 						syserr("openmailer: setgroups() failed");
1970 						exit(EX_TEMPFAIL);
1971 					}
1972 				}
1973 				new_gid = ctladdr->q_gid;
1974 			}
1975 			else
1976 			{
1977 				if (!DontInitGroups)
1978 				{
1979 					if (initgroups(DefUser, DefGid) == -1 && suidwarn)
1980 					{
1981 						syserr("openmailer: initgroups(%s, %d) failed",
1982 							DefUser, DefGid);
1983 						exit(EX_TEMPFAIL);
1984 					}
1985 				}
1986 				else
1987 				{
1988 					GIDSET_T gidset[1];
1989 
1990 					gidset[0] = DefGid;
1991 					if (setgroups(1, gidset) == -1 && suidwarn)
1992 					{
1993 						syserr("openmailer: setgroups() failed");
1994 						exit(EX_TEMPFAIL);
1995 					}
1996 				}
1997 				if (m->m_gid == 0)
1998 					new_gid = DefGid;
1999 				else
2000 					new_gid = m->m_gid;
2001 			}
2002 			if (new_gid != NO_GID)
2003 			{
2004 				if (RunAsUid != 0 &&
2005 				    bitnset(M_SPECIFIC_UID, m->m_flags) &&
2006 				    new_gid != getgid() &&
2007 				    new_gid != getegid())
2008 				{
2009 					/* Only root can change the gid */
2010 					syserr("openmailer: insufficient privileges to change gid");
2011 					exit(EX_TEMPFAIL);
2012 				}
2013 
2014 				if (setgid(new_gid) < 0 && suidwarn)
2015 				{
2016 					syserr("openmailer: setgid(%ld) failed",
2017 					       (long) new_gid);
2018 					exit(EX_TEMPFAIL);
2019 				}
2020 			}
2021 
2022 			/* change root to some "safe" directory */
2023 			if (m->m_rootdir != NULL)
2024 			{
2025 				expand(m->m_rootdir, buf, sizeof buf, e);
2026 				if (tTd(11, 20))
2027 					dprintf("openmailer: chroot %s\n",
2028 						buf);
2029 				if (chroot(buf) < 0)
2030 				{
2031 					syserr("openmailer: Cannot chroot(%s)",
2032 					       buf);
2033 					exit(EX_TEMPFAIL);
2034 				}
2035 				if (chdir("/") < 0)
2036 				{
2037 					syserr("openmailer: cannot chdir(/)");
2038 					exit(EX_TEMPFAIL);
2039 				}
2040 			}
2041 
2042 			/* reset user id */
2043 			endpwent();
2044 			if (bitnset(M_SPECIFIC_UID, m->m_flags))
2045 				new_euid = m->m_uid;
2046 			else if (bitset(S_ISUID, stb.st_mode))
2047 				new_ruid = stb.st_uid;
2048 			else if (ctladdr != NULL && ctladdr->q_uid != 0)
2049 				new_ruid = ctladdr->q_uid;
2050 			else if (m->m_uid != 0)
2051 				new_ruid = m->m_uid;
2052 			else
2053 				new_ruid = DefUid;
2054 			if (new_euid != NO_UID)
2055 			{
2056 				if (RunAsUid != 0 && new_euid != RunAsUid)
2057 				{
2058 					/* Only root can change the uid */
2059 					syserr("openmailer: insufficient privileges to change uid");
2060 					exit(EX_TEMPFAIL);
2061 				}
2062 
2063 				vendor_set_uid(new_euid);
2064 # if MAILER_SETUID_METHOD == USE_SETEUID
2065 				if (seteuid(new_euid) < 0 && suidwarn)
2066 				{
2067 					syserr("openmailer: seteuid(%ld) failed",
2068 						(long) new_euid);
2069 					exit(EX_TEMPFAIL);
2070 				}
2071 # endif /* MAILER_SETUID_METHOD == USE_SETEUID */
2072 # if MAILER_SETUID_METHOD == USE_SETREUID
2073 				if (setreuid(new_ruid, new_euid) < 0 && suidwarn)
2074 				{
2075 					syserr("openmailer: setreuid(%ld, %ld) failed",
2076 						(long) new_ruid, (long) new_euid);
2077 					exit(EX_TEMPFAIL);
2078 				}
2079 # endif /* MAILER_SETUID_METHOD == USE_SETREUID */
2080 # if MAILER_SETUID_METHOD == USE_SETUID
2081 				if (new_euid != geteuid() && setuid(new_euid) < 0 && suidwarn)
2082 				{
2083 					syserr("openmailer: setuid(%ld) failed",
2084 						(long) new_euid);
2085 					exit(EX_TEMPFAIL);
2086 				}
2087 # endif /* MAILER_SETUID_METHOD == USE_SETUID */
2088 			}
2089 			else if (new_ruid != NO_UID)
2090 			{
2091 				vendor_set_uid(new_ruid);
2092 				if (setuid(new_ruid) < 0 && suidwarn)
2093 				{
2094 					syserr("openmailer: setuid(%ld) failed",
2095 						(long) new_ruid);
2096 					exit(EX_TEMPFAIL);
2097 				}
2098 			}
2099 
2100 			if (tTd(11, 2))
2101 				dprintf("openmailer: running as r/euid=%d/%d, r/egid=%d/%d\n",
2102 					(int) getuid(), (int) geteuid(),
2103 					(int) getgid(), (int) getegid());
2104 
2105 			/* move into some "safe" directory */
2106 			if (m->m_execdir != NULL)
2107 			{
2108 				char *q;
2109 
2110 				for (p = m->m_execdir; p != NULL; p = q)
2111 				{
2112 					q = strchr(p, ':');
2113 					if (q != NULL)
2114 						*q = '\0';
2115 					expand(p, buf, sizeof buf, e);
2116 					if (q != NULL)
2117 						*q++ = ':';
2118 					if (tTd(11, 20))
2119 						dprintf("openmailer: trydir %s\n",
2120 							buf);
2121 					if (buf[0] != '\0' && chdir(buf) >= 0)
2122 						break;
2123 				}
2124 			}
2125 
2126 			/* arrange to filter std & diag output of command */
2127 			(void) close(rpvect[0]);
2128 			if (dup2(rpvect[1], STDOUT_FILENO) < 0)
2129 			{
2130 				syserr("%s... openmailer(%s): cannot dup pipe %d for stdout",
2131 				       shortenstring(e->e_to, MAXSHORTSTR),
2132 				       m->m_name, rpvect[1]);
2133 				_exit(EX_OSERR);
2134 			}
2135 			(void) close(rpvect[1]);
2136 
2137 			if (dup2(STDOUT_FILENO, STDERR_FILENO) < 0)
2138 			{
2139 				syserr("%s... openmailer(%s): cannot dup stdout for stderr",
2140 					shortenstring(e->e_to, MAXSHORTSTR),
2141 					m->m_name);
2142 				_exit(EX_OSERR);
2143 			}
2144 
2145 			/* arrange to get standard input */
2146 			(void) close(mpvect[1]);
2147 			if (dup2(mpvect[0], STDIN_FILENO) < 0)
2148 			{
2149 				syserr("%s... openmailer(%s): cannot dup pipe %d for stdin",
2150 					shortenstring(e->e_to, MAXSHORTSTR),
2151 					m->m_name, mpvect[0]);
2152 				_exit(EX_OSERR);
2153 			}
2154 			(void) close(mpvect[0]);
2155 
2156 			/* arrange for all the files to be closed */
2157 			for (i = 3; i < DtableSize; i++)
2158 			{
2159 				register int j;
2160 
2161 				if ((j = fcntl(i, F_GETFD, 0)) != -1)
2162 					(void) fcntl(i, F_SETFD,
2163 						     j | FD_CLOEXEC);
2164 			}
2165 
2166 			/* run disconnected from terminal */
2167 			(void) setsid();
2168 
2169 			/* try to execute the mailer */
2170 			(void) execve(m->m_mailer, (ARGV_T) pv,
2171 				      (ARGV_T) UserEnviron);
2172 			save_errno = errno;
2173 			syserr("Cannot exec %s", m->m_mailer);
2174 			if (bitnset(M_LOCALMAILER, m->m_flags) ||
2175 			    transienterror(save_errno))
2176 				_exit(EX_OSERR);
2177 			_exit(EX_UNAVAILABLE);
2178 		}
2179 
2180 		/*
2181 		**  Set up return value.
2182 		*/
2183 
2184 		if (mci == NULL)
2185 		{
2186 			mci = (MCI *) xalloc(sizeof *mci);
2187 			memset((char *) mci, '\0', sizeof *mci);
2188 		}
2189 		mci->mci_mailer = m;
2190 		if (clever)
2191 		{
2192 			mci->mci_state = MCIS_OPENING;
2193 			mci_cache(mci);
2194 		}
2195 		else
2196 		{
2197 			mci->mci_state = MCIS_OPEN;
2198 		}
2199 		mci->mci_pid = pid;
2200 		(void) close(mpvect[0]);
2201 		mci->mci_out = fdopen(mpvect[1], "w");
2202 		if (mci->mci_out == NULL)
2203 		{
2204 			syserr("deliver: cannot create mailer output channel, fd=%d",
2205 				mpvect[1]);
2206 			(void) close(mpvect[1]);
2207 			(void) close(rpvect[0]);
2208 			(void) close(rpvect[1]);
2209 			rcode = EX_OSERR;
2210 			goto give_up;
2211 		}
2212 
2213 		(void) close(rpvect[1]);
2214 		mci->mci_in = fdopen(rpvect[0], "r");
2215 		if (mci->mci_in == NULL)
2216 		{
2217 			syserr("deliver: cannot create mailer input channel, fd=%d",
2218 			       mpvect[1]);
2219 			(void) close(rpvect[0]);
2220 			(void) fclose(mci->mci_out);
2221 			mci->mci_out = NULL;
2222 			rcode = EX_OSERR;
2223 			goto give_up;
2224 		}
2225 
2226 		/* Don't cache non-clever connections */
2227 		if (!clever)
2228 			mci->mci_flags |= MCIF_TEMP;
2229 	}
2230 
2231 	/*
2232 	**  If we are in SMTP opening state, send initial protocol.
2233 	*/
2234 
2235 	if (bitnset(M_7BITS, m->m_flags) &&
2236 	    (!clever || mci->mci_state == MCIS_OPENING))
2237 		mci->mci_flags |= MCIF_7BIT;
2238 #if SMTP
2239 	if (clever && mci->mci_state != MCIS_CLOSED)
2240 	{
2241 		static u_short again;
2242 # if SASL && SFIO
2243 #  define DONE_TLS_B	0x01
2244 #  define DONE_TLS	bitset(DONE_TLS_B, again)
2245 # endif /* SASL && SFIO */
2246 # if STARTTLS
2247 #  define DONE_STARTTLS_B	0x02
2248 #  define DONE_STARTTLS	bitset(DONE_STARTTLS_B, again)
2249 # endif /* STARTTLS */
2250 # define ONLY_HELO_B	0x04
2251 # define ONLY_HELO	bitset(ONLY_HELO_B, again)
2252 # define SET_HELO	again |= ONLY_HELO_B
2253 # define CLR_HELO	again &= ~ONLY_HELO_B
2254 
2255 		again = 0;
2256 # if STARTTLS || (SASL && SFIO)
2257 reconnect:	/* after switching to an authenticated connection */
2258 # endif /* STARTTLS || (SASL && SFIO) */
2259 
2260 # if SASL
2261 		mci->mci_saslcap = NULL;
2262 # endif /* SASL */
2263 		smtpinit(m, mci, e, ONLY_HELO);
2264 		CLR_HELO;
2265 
2266 # if STARTTLS
2267 		/* first TLS then AUTH to provide a security layer */
2268 		if (mci->mci_state != MCIS_CLOSED && !DONE_STARTTLS)
2269 		{
2270 			int olderrors;
2271 			bool hasdot;
2272 			bool usetls;
2273 			bool saveQuickAbort = QuickAbort;
2274 			bool saveSuprErrs = SuprErrs;
2275 #  if _FFR_TLS_CLT1
2276 			char *p;
2277 #  endif /* _FFR_TLS_CLT1 */
2278 			extern SOCKADDR CurHostAddr;
2279 
2280 			rcode = EX_OK;
2281 			usetls = bitset(MCIF_TLS, mci->mci_flags);
2282 #  if _FFR_TLS_CLT1
2283 			if (usetls &&
2284 			    (p = macvalue(macid("{client_flags}", NULL), e))
2285 			    != NULL)
2286 			{
2287 				for (; *p != '\0'; p++)
2288 				{
2289 					/* look for just this one flag */
2290 					if (*p == D_CLTNOTLS)
2291 					{
2292 						usetls = FALSE;
2293 						break;
2294 					}
2295 				}
2296 			}
2297 #  endif /* _FFR_TLS_CLT1 */
2298 
2299 			hasdot = CurHostName[strlen(CurHostName) - 1] == '.';
2300 			if (hasdot)
2301 				CurHostName[strlen(CurHostName) - 1] = '\0';
2302 			define(macid("{server_name}", NULL),
2303 			       newstr(CurHostName), e);
2304 			if (CurHostAddr.sa.sa_family != 0)
2305 				define(macid("{server_addr}", NULL),
2306 				       newstr(anynet_ntoa(&CurHostAddr)), e);
2307 			else
2308 				define(macid("{server_addr}", NULL), NULL, e);
2309 #  if _FFR_TLS_O_T
2310 			if (usetls)
2311 			{
2312 				olderrors = Errors;
2313 				QuickAbort = FALSE;
2314 				SuprErrs = TRUE;
2315 				if (rscheck("try_tls", CurHostName, NULL,
2316 					    e, TRUE, FALSE, 8) != EX_OK
2317 				    || Errors > olderrors)
2318 					usetls = FALSE;
2319 				SuprErrs = saveSuprErrs;
2320 				QuickAbort = saveQuickAbort;
2321 			}
2322 #  endif /* _FFR_TLS_O_T */
2323 
2324 			/* undo change of CurHostName */
2325 			if (hasdot)
2326 				CurHostName[strlen(CurHostName)] = '.';
2327 			if (usetls)
2328 			{
2329 				if ((rcode = starttls(m, mci, e)) == EX_OK)
2330 				{
2331 					/* start again without STARTTLS */
2332 					again |= DONE_STARTTLS_B;
2333 					mci->mci_flags |= MCIF_TLSACT;
2334 				}
2335 				else
2336 				{
2337 					char *s;
2338 
2339 					/*
2340 					**  TLS negotation failed, what to do?
2341 					**  fall back to unencrypted connection
2342 					**  or abort? How to decide?
2343 					**  set a macro and call a ruleset.
2344 					*/
2345 					mci->mci_flags &= ~MCIF_TLS;
2346 					switch (rcode)
2347 					{
2348 					  case EX_TEMPFAIL:
2349 						s = "TEMP";
2350 						break;
2351 					  case EX_USAGE:
2352 						s = "USAGE";
2353 						break;
2354 					  case EX_PROTOCOL:
2355 						s = "PROTOCOL";
2356 						break;
2357 					  case EX_SOFTWARE:
2358 						s = "SOFTWARE";
2359 						break;
2360 
2361 					  /* everything else is a failure */
2362 					  default:
2363 						s = "FAILURE";
2364 						rcode = EX_TEMPFAIL;
2365 					}
2366 					define(macid("{verify}", NULL),
2367 					       newstr(s), e);
2368 				}
2369 			}
2370 			else
2371 				define(macid("{verify}", NULL), "NONE", e);
2372 			olderrors = Errors;
2373 			QuickAbort = FALSE;
2374 			SuprErrs = TRUE;
2375 
2376 			/*
2377 			**  rcode == EX_SOFTWARE is special:
2378 			**  the TLS negotation failed
2379 			**  we have to drop the connection no matter what
2380 			**  However, we call tls_server to give it the chance
2381 			**  to log the problem and return an appropriate
2382 			**  error code.
2383 			*/
2384 			if (rscheck("tls_server",
2385 				     macvalue(macid("{verify}", NULL), e),
2386 				     NULL, e, TRUE, TRUE, 6) != EX_OK ||
2387 			    Errors > olderrors ||
2388 			    rcode == EX_SOFTWARE)
2389 			{
2390 				char enhsc[ENHSCLEN];
2391 				extern char MsgBuf[];
2392 
2393 				if (ISSMTPCODE(MsgBuf) &&
2394 				    extenhsc(MsgBuf + 4, ' ', enhsc) > 0)
2395 				{
2396 					p = newstr(MsgBuf);
2397 				}
2398 				else
2399 				{
2400 					p = "403 4.7.0 server not authenticated.";
2401 					(void) strlcpy(enhsc, "4.7.0",
2402 						       sizeof enhsc);
2403 				}
2404 				SuprErrs = saveSuprErrs;
2405 				QuickAbort = saveQuickAbort;
2406 
2407 				if (rcode == EX_SOFTWARE)
2408 				{
2409 					/* drop the connection */
2410 					mci->mci_state = MCIS_QUITING;
2411 					if (mci->mci_in != NULL)
2412 					{
2413 						(void) fclose(mci->mci_in);
2414 						mci->mci_in = NULL;
2415 					}
2416 					mci->mci_flags &= ~MCIF_TLSACT;
2417 					(void) endmailer(mci, e, pv);
2418 				}
2419 				else
2420 				{
2421 					/* abort transfer */
2422 					smtpquit(m, mci, e);
2423 				}
2424 
2425 				/* temp or permanent failure? */
2426 				rcode = (*p == '4') ? EX_TEMPFAIL
2427 						    : EX_UNAVAILABLE;
2428 				mci_setstat(mci, rcode, newstr(enhsc), p);
2429 
2430 				/*
2431 				**  hack to get the error message into
2432 				**  the envelope (done in giveresponse())
2433 				*/
2434 				(void) strlcpy(SmtpError, p, sizeof SmtpError);
2435 			}
2436 			QuickAbort = saveQuickAbort;
2437 			SuprErrs = saveSuprErrs;
2438 			if (DONE_STARTTLS && mci->mci_state != MCIS_CLOSED)
2439 			{
2440 				SET_HELO;
2441 				mci->mci_flags &= ~MCIF_EXTENS;
2442 				goto reconnect;
2443 			}
2444 		}
2445 # endif /* STARTTLS */
2446 # if SASL
2447 		/* if other server supports authentication let's authenticate */
2448 		if (mci->mci_state != MCIS_CLOSED &&
2449 		    mci->mci_saslcap != NULL &&
2450 #  if SFIO
2451 		    !DONE_TLS &&
2452 #  endif /* SFIO */
2453 		    SASLInfo != NULL)
2454 		{
2455 			/*
2456 			**  should we require some minimum authentication?
2457 			**  XXX ignore result?
2458 			*/
2459 			if (smtpauth(m, mci, e) == EX_OK)
2460 			{
2461 #  if SFIO
2462 				int result;
2463 				sasl_ssf_t *ssf;
2464 
2465 				/* get security strength (features) */
2466 				result = sasl_getprop(mci->mci_conn, SASL_SSF,
2467 						      (void **) &ssf);
2468 				if (LogLevel > 9)
2469 					sm_syslog(LOG_INFO, NOQID,
2470 						  "SASL: outgoing connection to %.64s: mech=%.16s, bits=%d",
2471 						  mci->mci_host,
2472 						  macvalue(macid("{auth_type}",
2473 								 NULL), e),
2474 						  *ssf);
2475 				/*
2476 				**  only switch to encrypted connection
2477 				**  if a security layer has been negotiated
2478 				*/
2479 				if (result == SASL_OK && *ssf > 0)
2480 				{
2481 					/*
2482 					**  convert sfio stuff to use SASL
2483 					**  check return values
2484 					**  if the call fails,
2485 					**  fall back to unencrypted version
2486 					**  unless some cf option requires
2487 					**  encryption then the connection must
2488 					**  be aborted
2489 					*/
2490 					if (sfdcsasl(mci->mci_in, mci->mci_out,
2491 						     mci->mci_conn) == 0)
2492 					{
2493 						again |= DONE_TLS_B;
2494 						SET_HELO;
2495 						mci->mci_flags &= ~MCIF_EXTENS;
2496 						mci->mci_flags |= MCIF_AUTHACT;
2497 						goto reconnect;
2498 					}
2499 					syserr("SASL TLS switch failed in client");
2500 				}
2501 				/* else? XXX */
2502 #  endif /* SFIO */
2503 				mci->mci_flags |= MCIF_AUTHACT;
2504 
2505 			}
2506 		}
2507 # endif /* SASL */
2508 	}
2509 
2510 #endif /* SMTP */
2511 
2512 do_transfer:
2513 	/* clear out per-message flags from connection structure */
2514 	mci->mci_flags &= ~(MCIF_CVT7TO8|MCIF_CVT8TO7);
2515 
2516 	if (bitset(EF_HAS8BIT, e->e_flags) &&
2517 	    !bitset(EF_DONT_MIME, e->e_flags) &&
2518 	    bitnset(M_7BITS, m->m_flags))
2519 		mci->mci_flags |= MCIF_CVT8TO7;
2520 
2521 #if MIME7TO8
2522 	if (bitnset(M_MAKE8BIT, m->m_flags) &&
2523 	    !bitset(MCIF_7BIT, mci->mci_flags) &&
2524 	    (p = hvalue("Content-Transfer-Encoding", e->e_header)) != NULL &&
2525 	     (strcasecmp(p, "quoted-printable") == 0 ||
2526 	      strcasecmp(p, "base64") == 0) &&
2527 	    (p = hvalue("Content-Type", e->e_header)) != NULL)
2528 	{
2529 		/* may want to convert 7 -> 8 */
2530 		/* XXX should really parse it here -- and use a class XXX */
2531 		if (strncasecmp(p, "text/plain", 10) == 0 &&
2532 		    (p[10] == '\0' || p[10] == ' ' || p[10] == ';'))
2533 			mci->mci_flags |= MCIF_CVT7TO8;
2534 	}
2535 #endif /* MIME7TO8 */
2536 
2537 	if (tTd(11, 1))
2538 	{
2539 		dprintf("openmailer: ");
2540 		mci_dump(mci, FALSE);
2541 	}
2542 
2543 	if (mci->mci_state != MCIS_OPEN)
2544 	{
2545 		/* couldn't open the mailer */
2546 		rcode = mci->mci_exitstat;
2547 		errno = mci->mci_errno;
2548 #if NAMED_BIND
2549 		h_errno = mci->mci_herrno;
2550 #endif /* NAMED_BIND */
2551 		if (rcode == EX_OK)
2552 		{
2553 			/* shouldn't happen */
2554 			syserr("554 5.3.5 deliver: mci=%lx rcode=%d errno=%d state=%d sig=%s",
2555 				(u_long) mci, rcode, errno, mci->mci_state,
2556 				firstsig);
2557 			mci_dump_all(TRUE);
2558 			rcode = EX_SOFTWARE;
2559 		}
2560 #if DAEMON
2561 		else if (nummxhosts > hostnum)
2562 		{
2563 			/* try next MX site */
2564 			goto tryhost;
2565 		}
2566 #endif /* DAEMON */
2567 	}
2568 	else if (!clever)
2569 	{
2570 		/*
2571 		**  Format and send message.
2572 		*/
2573 
2574 		putfromline(mci, e);
2575 		(*e->e_puthdr)(mci, e->e_header, e, M87F_OUTER);
2576 		(*e->e_putbody)(mci, e, NULL);
2577 
2578 		/* get the exit status */
2579 		rcode = endmailer(mci, e, pv);
2580 	}
2581 	else
2582 #if SMTP
2583 	{
2584 		/*
2585 		**  Send the MAIL FROM: protocol
2586 		*/
2587 
2588 		rcode = smtpmailfrom(m, mci, e);
2589 		if (rcode == EX_OK)
2590 		{
2591 			register char *t = tobuf;
2592 			register int i;
2593 
2594 			/* send the recipient list */
2595 			tobuf[0] = '\0';
2596 
2597 			for (to = tochain; to != NULL; to = to->q_tchain)
2598 			{
2599 				e->e_to = to->q_paddr;
2600 #if !_FFR_DYNAMIC_TOBUF
2601 				if (strlen(to->q_paddr) +
2602 				    (t - tobuf) + 2 > sizeof tobuf)
2603 				{
2604 					/* not enough room */
2605 					continue;
2606 				}
2607 #endif /* !_FFR_DYNAMIC_TOBUF */
2608 
2609 # if STARTTLS
2610 #  if _FFR_TLS_RCPT
2611 				i = rscheck("tls_rcpt", to->q_user, NULL, e,
2612 					    TRUE, TRUE, 4);
2613 				if (i != EX_OK)
2614 				{
2615 					markfailure(e, to, mci, i, FALSE);
2616 					giveresponse(i, to->q_status,  m,
2617 						     mci, ctladdr, xstart, e);
2618 					continue;
2619 				}
2620 #  endif /* _FFR_TLS_RCPT */
2621 # endif /* STARTTLS */
2622 
2623 				if ((i = smtprcpt(to, m, mci, e)) != EX_OK)
2624 				{
2625 					markfailure(e, to, mci, i, FALSE);
2626 					giveresponse(i, to->q_status,  m,
2627 						     mci, ctladdr, xstart, e);
2628 				}
2629 				else
2630 				{
2631 					*t++ = ',';
2632 					for (p = to->q_paddr; *p; *t++ = *p++)
2633 						continue;
2634 					*t = '\0';
2635 				}
2636 			}
2637 
2638 			/* now send the data */
2639 			if (tobuf[0] == '\0')
2640 			{
2641 				rcode = EX_OK;
2642 				e->e_to = NULL;
2643 				if (bitset(MCIF_CACHED, mci->mci_flags))
2644 					smtprset(m, mci, e);
2645 			}
2646 			else
2647 			{
2648 				e->e_to = tobuf + 1;
2649 				rcode = smtpdata(m, mci, e);
2650 			}
2651 		}
2652 # if DAEMON
2653 		if (rcode == EX_TEMPFAIL && nummxhosts > hostnum)
2654 		{
2655 			/* try next MX site */
2656 			goto tryhost;
2657 		}
2658 # endif /* DAEMON */
2659 	}
2660 #else /* SMTP */
2661 	{
2662 		syserr("554 5.3.5 deliver: need SMTP compiled to use clever mailer");
2663 		rcode = EX_CONFIG;
2664 		goto give_up;
2665 	}
2666 #endif /* SMTP */
2667 #if NAMED_BIND
2668 	if (ConfigLevel < 2)
2669 		_res.options |= RES_DEFNAMES | RES_DNSRCH;	/* XXX */
2670 #endif /* NAMED_BIND */
2671 
2672 	if (tTd(62, 1))
2673 		checkfds("after delivery");
2674 
2675 	/*
2676 	**  Do final status disposal.
2677 	**	We check for something in tobuf for the SMTP case.
2678 	**	If we got a temporary failure, arrange to queue the
2679 	**		addressees.
2680 	*/
2681 
2682   give_up:
2683 #if SMTP
2684 	if (bitnset(M_LMTP, m->m_flags))
2685 	{
2686 		lmtp_rcode = rcode;
2687 		tobuf[0] = '\0';
2688 		anyok = FALSE;
2689 	}
2690 	else
2691 #endif /* SMTP */
2692 		anyok = rcode == EX_OK;
2693 
2694 	for (to = tochain; to != NULL; to = to->q_tchain)
2695 	{
2696 		/* see if address already marked */
2697 		if (!QS_IS_OK(to->q_state))
2698 			continue;
2699 
2700 #if SMTP
2701 		/* if running LMTP, get the status for each address */
2702 		if (bitnset(M_LMTP, m->m_flags))
2703 		{
2704 			if (lmtp_rcode == EX_OK)
2705 				rcode = smtpgetstat(m, mci, e);
2706 			if (rcode == EX_OK)
2707 			{
2708 #if _FFR_DYNAMIC_TOBUF
2709 				(void) strlcat(tobuf, ",", tobufsize);
2710 				(void) strlcat(tobuf, to->q_paddr, tobufsize);
2711 #else /* _FFR_DYNAMIC_TOBUF */
2712 				if (strlen(to->q_paddr) +
2713 				    strlen(tobuf) + 2 > sizeof tobuf)
2714 				{
2715 					syserr("LMTP tobuf overflow");
2716 				}
2717 				else
2718 				{
2719 					(void) strlcat(tobuf, ",",
2720 						       sizeof tobuf);
2721 					(void) strlcat(tobuf, to->q_paddr,
2722 						       sizeof tobuf);
2723 				}
2724 #endif /* _FFR_DYNAMIC_TOBUF */
2725 				anyok = TRUE;
2726 			}
2727 			else
2728 			{
2729 				e->e_to = to->q_paddr;
2730 				markfailure(e, to, mci, rcode, TRUE);
2731 				giveresponse(rcode, to->q_status, m, mci,
2732 					     ctladdr, xstart, e);
2733 				e->e_to = tobuf + 1;
2734 				continue;
2735 			}
2736 		}
2737 		else
2738 #endif /* SMTP */
2739 		{
2740 			/* mark bad addresses */
2741 			if (rcode != EX_OK)
2742 			{
2743 				if (goodmxfound && rcode == EX_NOHOST)
2744 					rcode = EX_TEMPFAIL;
2745 				markfailure(e, to, mci, rcode, TRUE);
2746 				continue;
2747 			}
2748 		}
2749 
2750 		/* successful delivery */
2751 		to->q_state = QS_SENT;
2752 		to->q_statdate = curtime();
2753 		e->e_nsent++;
2754 
2755 #if QUEUE
2756 		/*
2757 		**  Checkpoint the send list every few addresses
2758 		*/
2759 
2760 		if (CheckpointInterval > 0 && e->e_nsent >= CheckpointInterval)
2761 		{
2762 			queueup(e, FALSE);
2763 			e->e_nsent = 0;
2764 		}
2765 #endif /* QUEUE */
2766 
2767 		if (bitnset(M_LOCALMAILER, m->m_flags) &&
2768 		    bitset(QPINGONSUCCESS, to->q_flags))
2769 		{
2770 			to->q_flags |= QDELIVERED;
2771 			to->q_status = "2.1.5";
2772 			fprintf(e->e_xfp, "%s... Successfully delivered\n",
2773 				to->q_paddr);
2774 		}
2775 		else if (bitset(QPINGONSUCCESS, to->q_flags) &&
2776 			 bitset(QPRIMARY, to->q_flags) &&
2777 			 !bitset(MCIF_DSN, mci->mci_flags))
2778 		{
2779 			to->q_flags |= QRELAYED;
2780 			fprintf(e->e_xfp, "%s... relayed; expect no further notifications\n",
2781 				to->q_paddr);
2782 		}
2783 	}
2784 
2785 #if SMTP
2786 	if (bitnset(M_LMTP, m->m_flags))
2787 	{
2788 		/*
2789 		**  Global information applies to the last recipient only;
2790 		**  clear it out to avoid bogus errors.
2791 		*/
2792 
2793 		rcode = EX_OK;
2794 		e->e_statmsg = NULL;
2795 
2796 		/* reset the mci state for the next transaction */
2797 		if (mci != NULL && mci->mci_state == MCIS_ACTIVE)
2798 			mci->mci_state = MCIS_OPEN;
2799 	}
2800 #endif /* SMTP */
2801 
2802 	if (tobuf[0] != '\0')
2803 		giveresponse(rcode, NULL, m, mci, ctladdr, xstart, e);
2804 	if (anyok)
2805 		markstats(e, tochain, FALSE);
2806 	mci_store_persistent(mci);
2807 
2808 #if SMTP
2809 	/* now close the connection */
2810 	if (clever && mci != NULL && mci->mci_state != MCIS_CLOSED &&
2811 	    !bitset(MCIF_CACHED, mci->mci_flags))
2812 		smtpquit(m, mci, e);
2813 #endif /* SMTP */
2814 
2815 	/*
2816 	**  Restore state and return.
2817 	*/
2818 
2819 #if XDEBUG
2820 	{
2821 		char wbuf[MAXLINE];
2822 
2823 		/* make absolutely certain 0, 1, and 2 are in use */
2824 		snprintf(wbuf, sizeof wbuf, "%s... end of deliver(%s)",
2825 			e->e_to == NULL ? "NO-TO-LIST"
2826 					: shortenstring(e->e_to, MAXSHORTSTR),
2827 			m->m_name);
2828 		checkfd012(wbuf);
2829 	}
2830 #endif /* XDEBUG */
2831 
2832 	errno = 0;
2833 	define('g', (char *) NULL, e);
2834 	e->e_to = NULL;
2835 	return rcode;
2836 }
2837 
2838 /*
2839 **  MARKFAILURE -- mark a failure on a specific address.
2840 **
2841 **	Parameters:
2842 **		e -- the envelope we are sending.
2843 **		q -- the address to mark.
2844 **		mci -- mailer connection information.
2845 **		rcode -- the code signifying the particular failure.
2846 **		ovr -- override an existing code?
2847 **
2848 **	Returns:
2849 **		none.
2850 **
2851 **	Side Effects:
2852 **		marks the address (and possibly the envelope) with the
2853 **			failure so that an error will be returned or
2854 **			the message will be queued, as appropriate.
2855 */
2856 
2857 static void
2858 markfailure(e, q, mci, rcode, ovr)
2859 	register ENVELOPE *e;
2860 	register ADDRESS *q;
2861 	register MCI *mci;
2862 	int rcode;
2863 	bool ovr;
2864 {
2865 	char *status = NULL;
2866 	char *rstatus = NULL;
2867 
2868 	switch (rcode)
2869 	{
2870 	  case EX_OK:
2871 		break;
2872 
2873 	  case EX_TEMPFAIL:
2874 	  case EX_IOERR:
2875 	  case EX_OSERR:
2876 		q->q_state = QS_QUEUEUP;
2877 		break;
2878 
2879 	  default:
2880 		q->q_state = QS_BADADDR;
2881 		break;
2882 	}
2883 
2884 	/* find most specific error code possible */
2885 	if (mci != NULL && mci->mci_status != NULL)
2886 	{
2887 		status = mci->mci_status;
2888 		if (mci->mci_rstatus != NULL)
2889 			rstatus = newstr(mci->mci_rstatus);
2890 		else
2891 			rstatus = NULL;
2892 	}
2893 	else if (e->e_status != NULL)
2894 	{
2895 		status = e->e_status;
2896 		rstatus = NULL;
2897 	}
2898 	else
2899 	{
2900 		switch (rcode)
2901 		{
2902 		  case EX_USAGE:
2903 			status = "5.5.4";
2904 			break;
2905 
2906 		  case EX_DATAERR:
2907 			status = "5.5.2";
2908 			break;
2909 
2910 		  case EX_NOUSER:
2911 			status = "5.1.1";
2912 			break;
2913 
2914 		  case EX_NOHOST:
2915 			status = "5.1.2";
2916 			break;
2917 
2918 		  case EX_NOINPUT:
2919 		  case EX_CANTCREAT:
2920 		  case EX_NOPERM:
2921 			status = "5.3.0";
2922 			break;
2923 
2924 		  case EX_UNAVAILABLE:
2925 		  case EX_SOFTWARE:
2926 		  case EX_OSFILE:
2927 		  case EX_PROTOCOL:
2928 		  case EX_CONFIG:
2929 			status = "5.5.0";
2930 			break;
2931 
2932 		  case EX_OSERR:
2933 		  case EX_IOERR:
2934 			status = "4.5.0";
2935 			break;
2936 
2937 		  case EX_TEMPFAIL:
2938 			status = "4.2.0";
2939 			break;
2940 		}
2941 	}
2942 
2943 	/* new status? */
2944 	if (status != NULL && *status != '\0' && (ovr || q->q_status == NULL ||
2945 	    *q->q_status == '\0' || *q->q_status < *status))
2946 	{
2947 		q->q_status = status;
2948 		q->q_rstatus = rstatus;
2949 	}
2950 	if (rcode != EX_OK && q->q_rstatus == NULL &&
2951 	    q->q_mailer != NULL && q->q_mailer->m_diagtype != NULL &&
2952 	    strcasecmp(q->q_mailer->m_diagtype, "X-UNIX") == 0)
2953 	{
2954 		char buf[16];
2955 
2956 		(void) snprintf(buf, sizeof buf, "%d", rcode);
2957 		q->q_rstatus = newstr(buf);
2958 	}
2959 
2960 	q->q_statdate = curtime();
2961 	if (CurHostName != NULL && CurHostName[0] != '\0' &&
2962 	    mci != NULL && !bitset(M_LOCALMAILER, mci->mci_flags))
2963 		q->q_statmta = newstr(CurHostName);
2964 }
2965 /*
2966 **  ENDMAILER -- Wait for mailer to terminate.
2967 **
2968 **	We should never get fatal errors (e.g., segmentation
2969 **	violation), so we report those specially.  For other
2970 **	errors, we choose a status message (into statmsg),
2971 **	and if it represents an error, we print it.
2972 **
2973 **	Parameters:
2974 **		pid -- pid of mailer.
2975 **		e -- the current envelope.
2976 **		pv -- the parameter vector that invoked the mailer
2977 **			(for error messages).
2978 **
2979 **	Returns:
2980 **		exit code of mailer.
2981 **
2982 **	Side Effects:
2983 **		none.
2984 */
2985 
2986 static jmp_buf	EndWaitTimeout;
2987 
2988 static void
2989 endwaittimeout()
2990 {
2991 	errno = ETIMEDOUT;
2992 	longjmp(EndWaitTimeout, 1);
2993 }
2994 
2995 int
2996 endmailer(mci, e, pv)
2997 	register MCI *mci;
2998 	register ENVELOPE *e;
2999 	char **pv;
3000 {
3001 	int st;
3002 	int save_errno = errno;
3003 	char buf[MAXLINE];
3004 	EVENT *ev = NULL;
3005 
3006 
3007 	mci_unlock_host(mci);
3008 
3009 #if SASL
3010 	/* shutdown SASL */
3011 	if (bitset(MCIF_AUTHACT, mci->mci_flags))
3012 	{
3013 		sasl_dispose(&mci->mci_conn);
3014 		mci->mci_flags &= ~MCIF_AUTHACT;
3015 	}
3016 #endif /* SASL */
3017 
3018 #if STARTTLS
3019 	/* shutdown TLS */
3020 	(void) endtlsclt(mci);
3021 #endif /* STARTTLS */
3022 
3023 	/* close output to mailer */
3024 	if (mci->mci_out != NULL)
3025 		(void) fclose(mci->mci_out);
3026 
3027 	/* copy any remaining input to transcript */
3028 	if (mci->mci_in != NULL && mci->mci_state != MCIS_ERROR &&
3029 	    e->e_xfp != NULL)
3030 	{
3031 		while (sfgets(buf, sizeof buf, mci->mci_in,
3032 		       TimeOuts.to_quit, "Draining Input") != NULL)
3033 			(void) fputs(buf, e->e_xfp);
3034 	}
3035 
3036 	/* now close the input */
3037 	if (mci->mci_in != NULL)
3038 		(void) fclose(mci->mci_in);
3039 	mci->mci_in = mci->mci_out = NULL;
3040 	mci->mci_state = MCIS_CLOSED;
3041 
3042 	errno = save_errno;
3043 
3044 	/* in the IPC case there is nothing to wait for */
3045 	if (mci->mci_pid == 0)
3046 		return EX_OK;
3047 
3048 	/* put a timeout around the wait */
3049 	if (mci->mci_mailer->m_wait > 0)
3050 	{
3051 		if (setjmp(EndWaitTimeout) == 0)
3052 			ev = setevent(mci->mci_mailer->m_wait,
3053 				      endwaittimeout, 0);
3054 		else
3055 		{
3056 			syserr("endmailer %s: wait timeout (%ld)",
3057 			       mci->mci_mailer->m_name,
3058 			       (long) mci->mci_mailer->m_wait);
3059 			return EX_TEMPFAIL;
3060 		}
3061 	}
3062 
3063 	/* wait for the mailer process, collect status */
3064 	st = waitfor(mci->mci_pid);
3065 	save_errno = errno;
3066 	if (ev != NULL)
3067 		clrevent(ev);
3068 	errno = save_errno;
3069 
3070 	if (st == -1)
3071 	{
3072 		syserr("endmailer %s: wait", mci->mci_mailer->m_name);
3073 		return EX_SOFTWARE;
3074 	}
3075 
3076 	if (WIFEXITED(st))
3077 	{
3078 		/* normal death -- return status */
3079 		return (WEXITSTATUS(st));
3080 	}
3081 
3082 	/* it died a horrid death */
3083 	syserr("451 4.3.0 mailer %s died with signal %d%s",
3084 		mci->mci_mailer->m_name, WTERMSIG(st),
3085 		WCOREDUMP(st) ? " (core dumped)" :
3086 		(WIFSTOPPED(st) ? " (stopped)" : ""));
3087 
3088 	/* log the arguments */
3089 	if (pv != NULL && e->e_xfp != NULL)
3090 	{
3091 		register char **av;
3092 
3093 		fprintf(e->e_xfp, "Arguments:");
3094 		for (av = pv; *av != NULL; av++)
3095 			fprintf(e->e_xfp, " %s", *av);
3096 		fprintf(e->e_xfp, "\n");
3097 	}
3098 
3099 	ExitStat = EX_TEMPFAIL;
3100 	return EX_TEMPFAIL;
3101 }
3102 /*
3103 **  GIVERESPONSE -- Interpret an error response from a mailer
3104 **
3105 **	Parameters:
3106 **		status -- the status code from the mailer (high byte
3107 **			only; core dumps must have been taken care of
3108 **			already).
3109 **		dsn -- the DSN associated with the address, if any.
3110 **		m -- the mailer info for this mailer.
3111 **		mci -- the mailer connection info -- can be NULL if the
3112 **			response is given before the connection is made.
3113 **		ctladdr -- the controlling address for the recipient
3114 **			address(es).
3115 **		xstart -- the transaction start time, for computing
3116 **			transaction delays.
3117 **		e -- the current envelope.
3118 **
3119 **	Returns:
3120 **		none.
3121 **
3122 **	Side Effects:
3123 **		Errors may be incremented.
3124 **		ExitStat may be set.
3125 */
3126 
3127 void
3128 giveresponse(status, dsn, m, mci, ctladdr, xstart, e)
3129 	int status;
3130 	char *dsn;
3131 	register MAILER *m;
3132 	register MCI *mci;
3133 	ADDRESS *ctladdr;
3134 	time_t xstart;
3135 	ENVELOPE *e;
3136 {
3137 	register const char *statmsg;
3138 	extern char *SysExMsg[];
3139 	register int i;
3140 	int errnum = errno;
3141 	int off = 4;
3142 	extern int N_SysEx;
3143 	char dsnbuf[ENHSCLEN];
3144 	char buf[MAXLINE];
3145 
3146 	if (e == NULL)
3147 		syserr("giveresponse: null envelope");
3148 
3149 	/*
3150 	**  Compute status message from code.
3151 	*/
3152 
3153 	i = status - EX__BASE;
3154 	if (status == 0)
3155 	{
3156 		statmsg = "250 2.0.0 Sent";
3157 		if (e->e_statmsg != NULL)
3158 		{
3159 			(void) snprintf(buf, sizeof buf, "%s (%s)",
3160 					statmsg,
3161 					shortenstring(e->e_statmsg, 403));
3162 			statmsg = buf;
3163 		}
3164 	}
3165 	else if (i < 0 || i >= N_SysEx)
3166 	{
3167 		(void) snprintf(buf, sizeof buf,
3168 				"554 5.3.0 unknown mailer error %d",
3169 				status);
3170 		status = EX_UNAVAILABLE;
3171 		statmsg = buf;
3172 	}
3173 	else if (status == EX_TEMPFAIL)
3174 	{
3175 		char *bp = buf;
3176 
3177 		snprintf(bp, SPACELEFT(buf, bp), "%s", SysExMsg[i] + 1);
3178 		bp += strlen(bp);
3179 #if NAMED_BIND
3180 		if (h_errno == TRY_AGAIN)
3181 			statmsg = errstring(h_errno+E_DNSBASE);
3182 		else
3183 #endif /* NAMED_BIND */
3184 		{
3185 			if (errnum != 0)
3186 				statmsg = errstring(errnum);
3187 			else
3188 			{
3189 #if SMTP
3190 				statmsg = SmtpError;
3191 #else /* SMTP */
3192 				statmsg = NULL;
3193 #endif /* SMTP */
3194 			}
3195 		}
3196 		if (statmsg != NULL && statmsg[0] != '\0')
3197 		{
3198 			switch (errnum)
3199 			{
3200 #ifdef ENETDOWN
3201 			  case ENETDOWN:	/* Network is down */
3202 #endif /* ENETDOWN */
3203 #ifdef ENETUNREACH
3204 			  case ENETUNREACH:	/* Network is unreachable */
3205 #endif /* ENETUNREACH */
3206 #ifdef ENETRESET
3207 			  case ENETRESET:	/* Network dropped connection on reset */
3208 #endif /* ENETRESET */
3209 #ifdef ECONNABORTED
3210 			  case ECONNABORTED:	/* Software caused connection abort */
3211 #endif /* ECONNABORTED */
3212 #ifdef EHOSTDOWN
3213 			  case EHOSTDOWN:	/* Host is down */
3214 #endif /* EHOSTDOWN */
3215 #ifdef EHOSTUNREACH
3216 			  case EHOSTUNREACH:	/* No route to host */
3217 #endif /* EHOSTUNREACH */
3218 				if (mci->mci_host != NULL)
3219 				{
3220 					snprintf(bp, SPACELEFT(buf, bp),
3221 						 ": %s", mci->mci_host);
3222 					bp += strlen(bp);
3223 				}
3224 				break;
3225 			}
3226 			snprintf(bp, SPACELEFT(buf, bp), ": %s", statmsg);
3227 		}
3228 		statmsg = buf;
3229 	}
3230 #if NAMED_BIND
3231 	else if (status == EX_NOHOST && h_errno != 0)
3232 	{
3233 		statmsg = errstring(h_errno + E_DNSBASE);
3234 		(void) snprintf(buf, sizeof buf, "%s (%s)",
3235 			SysExMsg[i] + 1, statmsg);
3236 		statmsg = buf;
3237 	}
3238 #endif /* NAMED_BIND */
3239 	else
3240 	{
3241 		statmsg = SysExMsg[i];
3242 		if (*statmsg++ == ':' && errnum != 0)
3243 		{
3244 			(void) snprintf(buf, sizeof buf, "%s: %s",
3245 				statmsg, errstring(errnum));
3246 			statmsg = buf;
3247 		}
3248 	}
3249 
3250 	/*
3251 	**  Print the message as appropriate
3252 	*/
3253 
3254 	if (status == EX_OK || status == EX_TEMPFAIL)
3255 	{
3256 		extern char MsgBuf[];
3257 
3258 		if ((off = isenhsc(statmsg + 4, ' ')) > 0)
3259 		{
3260 			if (dsn == NULL)
3261 			{
3262 				snprintf(dsnbuf, sizeof dsnbuf,
3263 					 "%.*s", off, statmsg + 4);
3264 				dsn = dsnbuf;
3265 			}
3266 			off += 5;
3267 		}
3268 		else
3269 		{
3270 			off = 4;
3271 		}
3272 		message("%s", statmsg + off);
3273 		if (status == EX_TEMPFAIL && e->e_xfp != NULL)
3274 			fprintf(e->e_xfp, "%s\n", &MsgBuf[4]);
3275 	}
3276 	else
3277 	{
3278 		char mbuf[ENHSCLEN + 4];
3279 
3280 		Errors++;
3281 		if ((off = isenhsc(statmsg + 4, ' ')) > 0 &&
3282 		    off < sizeof mbuf - 4)
3283 		{
3284 			if (dsn == NULL)
3285 			{
3286 				snprintf(dsnbuf, sizeof dsnbuf,
3287 					 "%.*s", off, statmsg + 4);
3288 				dsn = dsnbuf;
3289 			}
3290 			off += 5;
3291 			(void) strlcpy(mbuf, statmsg, off);
3292 			(void) strlcat(mbuf, " %s", sizeof mbuf);
3293 		}
3294 		else
3295 		{
3296 			dsnbuf[0] = '\0';
3297 			(void) snprintf(mbuf, sizeof mbuf, "%.3s %%s", statmsg);
3298 			off = 4;
3299 		}
3300 		usrerr(mbuf, &statmsg[off]);
3301 	}
3302 
3303 	/*
3304 	**  Final cleanup.
3305 	**	Log a record of the transaction.  Compute the new
3306 	**	ExitStat -- if we already had an error, stick with
3307 	**	that.
3308 	*/
3309 
3310 	if (OpMode != MD_VERIFY && !bitset(EF_VRFYONLY, e->e_flags) &&
3311 	    LogLevel > ((status == EX_TEMPFAIL) ? 8 : (status == EX_OK) ? 7 : 6))
3312 		logdelivery(m, mci, dsn, statmsg + off, ctladdr, xstart, e);
3313 
3314 	if (tTd(11, 2))
3315 		dprintf("giveresponse: status=%d, dsn=%s, e->e_message=%s\n",
3316 			status,
3317 			dsn == NULL ? "<NULL>" : dsn,
3318 			e->e_message == NULL ? "<NULL>" : e->e_message);
3319 
3320 	if (status != EX_TEMPFAIL)
3321 		setstat(status);
3322 	if (status != EX_OK && (status != EX_TEMPFAIL || e->e_message == NULL))
3323 	{
3324 		if (e->e_message != NULL)
3325 			free(e->e_message);
3326 		e->e_message = newstr(statmsg + off);
3327 	}
3328 	errno = 0;
3329 #if NAMED_BIND
3330 	h_errno = 0;
3331 #endif /* NAMED_BIND */
3332 }
3333 /*
3334 **  LOGDELIVERY -- log the delivery in the system log
3335 **
3336 **	Care is taken to avoid logging lines that are too long, because
3337 **	some versions of syslog have an unfortunate proclivity for core
3338 **	dumping.  This is a hack, to be sure, that is at best empirical.
3339 **
3340 **	Parameters:
3341 **		m -- the mailer info.  Can be NULL for initial queue.
3342 **		mci -- the mailer connection info -- can be NULL if the
3343 **			log is occurring when no connection is active.
3344 **		dsn -- the DSN attached to the status.
3345 **		status -- the message to print for the status.
3346 **		ctladdr -- the controlling address for the to list.
3347 **		xstart -- the transaction start time, used for
3348 **			computing transaction delay.
3349 **		e -- the current envelope.
3350 **
3351 **	Returns:
3352 **		none
3353 **
3354 **	Side Effects:
3355 **		none
3356 */
3357 
3358 void
3359 logdelivery(m, mci, dsn, status, ctladdr, xstart, e)
3360 	MAILER *m;
3361 	register MCI *mci;
3362 	char *dsn;
3363 	const char *status;
3364 	ADDRESS *ctladdr;
3365 	time_t xstart;
3366 	register ENVELOPE *e;
3367 {
3368 	register char *bp;
3369 	register char *p;
3370 	int l;
3371 	char buf[1024];
3372 
3373 #if (SYSLOG_BUFSIZE) >= 256
3374 	/* ctladdr: max 106 bytes */
3375 	bp = buf;
3376 	if (ctladdr != NULL)
3377 	{
3378 		snprintf(bp, SPACELEFT(buf, bp), ", ctladdr=%s",
3379 			 shortenstring(ctladdr->q_paddr, 83));
3380 		bp += strlen(bp);
3381 		if (bitset(QGOODUID, ctladdr->q_flags))
3382 		{
3383 			(void) snprintf(bp, SPACELEFT(buf, bp), " (%d/%d)",
3384 					(int) ctladdr->q_uid,
3385 					(int) ctladdr->q_gid);
3386 			bp += strlen(bp);
3387 		}
3388 	}
3389 
3390 	/* delay & xdelay: max 41 bytes */
3391 	snprintf(bp, SPACELEFT(buf, bp), ", delay=%s",
3392 		 pintvl(curtime() - e->e_ctime, TRUE));
3393 	bp += strlen(bp);
3394 
3395 	if (xstart != (time_t) 0)
3396 	{
3397 		snprintf(bp, SPACELEFT(buf, bp), ", xdelay=%s",
3398 			 pintvl(curtime() - xstart, TRUE));
3399 		bp += strlen(bp);
3400 	}
3401 
3402 	/* mailer: assume about 19 bytes (max 10 byte mailer name) */
3403 	if (m != NULL)
3404 	{
3405 		snprintf(bp, SPACELEFT(buf, bp), ", mailer=%s", m->m_name);
3406 		bp += strlen(bp);
3407 	}
3408 
3409 	/* pri: changes with each delivery attempt */
3410 	snprintf(bp, SPACELEFT(buf, bp), ", pri=%ld", e->e_msgpriority);
3411 	bp += strlen(bp);
3412 
3413 	/* relay: max 66 bytes for IPv4 addresses */
3414 	if (mci != NULL && mci->mci_host != NULL)
3415 	{
3416 # if DAEMON
3417 		extern SOCKADDR CurHostAddr;
3418 # endif /* DAEMON */
3419 
3420 		snprintf(bp, SPACELEFT(buf, bp), ", relay=%s",
3421 			 shortenstring(mci->mci_host, 40));
3422 		bp += strlen(bp);
3423 
3424 # if DAEMON
3425 		if (CurHostAddr.sa.sa_family != 0)
3426 		{
3427 			snprintf(bp, SPACELEFT(buf, bp), " [%s]",
3428 				 anynet_ntoa(&CurHostAddr));
3429 		}
3430 # endif /* DAEMON */
3431 	}
3432 	else if (strcmp(status, "queued") != 0)
3433 	{
3434 		p = macvalue('h', e);
3435 		if (p != NULL && p[0] != '\0')
3436 		{
3437 			snprintf(bp, SPACELEFT(buf, bp), ", relay=%s",
3438 				 shortenstring(p, 40));
3439 		}
3440 	}
3441 	bp += strlen(bp);
3442 
3443 	/* dsn */
3444 	if (dsn != NULL && *dsn != '\0')
3445 	{
3446 		snprintf(bp, SPACELEFT(buf, bp), ", dsn=%s",
3447 			 shortenstring(dsn, ENHSCLEN));
3448 		bp += strlen(bp);
3449 	}
3450 
3451 # define STATLEN		(((SYSLOG_BUFSIZE) - 100) / 4)
3452 # if (STATLEN) < 63
3453 #  undef STATLEN
3454 #  define STATLEN	63
3455 # endif /* (STATLEN) < 63 */
3456 # if (STATLEN) > 203
3457 #  undef STATLEN
3458 #  define STATLEN	203
3459 # endif /* (STATLEN) > 203 */
3460 
3461 	/* stat: max 210 bytes */
3462 	if ((bp - buf) > (sizeof buf - ((STATLEN) + 20)))
3463 	{
3464 		/* desperation move -- truncate data */
3465 		bp = buf + sizeof buf - ((STATLEN) + 17);
3466 		(void) strlcpy(bp, "...", SPACELEFT(buf, bp));
3467 		bp += 3;
3468 	}
3469 
3470 	(void) strlcpy(bp, ", stat=", SPACELEFT(buf, bp));
3471 	bp += strlen(bp);
3472 
3473 	(void) strlcpy(bp, shortenstring(status, STATLEN), SPACELEFT(buf, bp));
3474 
3475 	/* id, to: max 13 + TOBUFSIZE bytes */
3476 	l = SYSLOG_BUFSIZE - 100 - strlen(buf);
3477 	p = e->e_to == NULL ? "NO-TO-LIST" : e->e_to;
3478 	while (strlen(p) >= (SIZE_T) l)
3479 	{
3480 		register char *q;
3481 
3482 #if _FFR_DYNAMIC_TOBUF
3483 		for (q = p + l; q > p; q--)
3484 		{
3485 			if (*q == ',')
3486 				break;
3487 		}
3488 		if (p == q)
3489 			break;
3490 #else /* _FFR_DYNAMIC_TOBUF */
3491 		q = strchr(p + l, ',');
3492 		if (q == NULL)
3493 			break;
3494 #endif /* _FFR_DYNAMIC_TOBUF */
3495 
3496 		sm_syslog(LOG_INFO, e->e_id,
3497 			  "to=%.*s [more]%s",
3498 			  (int) (++q - p), p, buf);
3499 		p = q;
3500 	}
3501 #if _FFR_DYNAMIC_TOBUF
3502 	sm_syslog(LOG_INFO, e->e_id, "to=%.*s%s", l, p, buf);
3503 #else /* _FFR_DYNAMIC_TOBUF */
3504 	sm_syslog(LOG_INFO, e->e_id, "to=%s%s", p, buf);
3505 #endif /* _FFR_DYNAMIC_TOBUF */
3506 
3507 #else /* (SYSLOG_BUFSIZE) >= 256 */
3508 
3509 	l = SYSLOG_BUFSIZE - 85;
3510 	p = e->e_to == NULL ? "NO-TO-LIST" : e->e_to;
3511 	while (strlen(p) >= (SIZE_T) l)
3512 	{
3513 		register char *q;
3514 
3515 #if _FFR_DYNAMIC_TOBUF
3516 		for (q = p + l; q > p; q--)
3517 		{
3518 			if (*q == ',')
3519 				break;
3520 		}
3521 		if (p == q)
3522 			break;
3523 #else /* _FFR_DYNAMIC_TOBUF */
3524 		q = strchr(p + l, ',');
3525 		if (q == NULL)
3526 			break;
3527 #endif /* _FFR_DYNAMIC_TOBUF */
3528 
3529 		sm_syslog(LOG_INFO, e->e_id,
3530 			  "to=%.*s [more]",
3531 			  (int) (++q - p), p);
3532 		p = q;
3533 	}
3534 #if _FFR_DYNAMIC_TOBUF
3535 	sm_syslog(LOG_INFO, e->e_id, "to=%.*s", l, p);
3536 #else /* _FFR_DYNAMIC_TOBUF */
3537 	sm_syslog(LOG_INFO, e->e_id, "to=%s", p);
3538 #endif /* _FFR_DYNAMIC_TOBUF */
3539 
3540 	if (ctladdr != NULL)
3541 	{
3542 		bp = buf;
3543 		snprintf(bp, SPACELEFT(buf, bp), "ctladdr=%s",
3544 			 shortenstring(ctladdr->q_paddr, 83));
3545 		bp += strlen(bp);
3546 		if (bitset(QGOODUID, ctladdr->q_flags))
3547 		{
3548 			(void) snprintf(bp, SPACELEFT(buf, bp), " (%d/%d)",
3549 					ctladdr->q_uid, ctladdr->q_gid);
3550 			bp += strlen(bp);
3551 		}
3552 		sm_syslog(LOG_INFO, e->e_id, "%s", buf);
3553 	}
3554 	bp = buf;
3555 	snprintf(bp, SPACELEFT(buf, bp), "delay=%s",
3556 		 pintvl(curtime() - e->e_ctime, TRUE));
3557 	bp += strlen(bp);
3558 	if (xstart != (time_t) 0)
3559 	{
3560 		snprintf(bp, SPACELEFT(buf, bp), ", xdelay=%s",
3561 			 pintvl(curtime() - xstart, TRUE));
3562 		bp += strlen(bp);
3563 	}
3564 
3565 	if (m != NULL)
3566 	{
3567 		snprintf(bp, SPACELEFT(buf, bp), ", mailer=%s", m->m_name);
3568 		bp += strlen(bp);
3569 	}
3570 	sm_syslog(LOG_INFO, e->e_id, "%.1000s", buf);
3571 
3572 	buf[0] = '\0';
3573 	bp = buf;
3574 	if (mci != NULL && mci->mci_host != NULL)
3575 	{
3576 # if DAEMON
3577 		extern SOCKADDR CurHostAddr;
3578 # endif /* DAEMON */
3579 
3580 		snprintf(bp, SPACELEFT(buf, bp), "relay=%.100s", mci->mci_host);
3581 		bp += strlen(bp);
3582 
3583 # if DAEMON
3584 		if (CurHostAddr.sa.sa_family != 0)
3585 			snprintf(bp, SPACELEFT(buf, bp), " [%.100s]",
3586 				anynet_ntoa(&CurHostAddr));
3587 # endif /* DAEMON */
3588 	}
3589 	else if (strcmp(status, "queued") != 0)
3590 	{
3591 		p = macvalue('h', e);
3592 		if (p != NULL && p[0] != '\0')
3593 			snprintf(buf, sizeof buf, "relay=%.100s", p);
3594 	}
3595 	if (buf[0] != '\0')
3596 		sm_syslog(LOG_INFO, e->e_id, "%.1000s", buf);
3597 
3598 	sm_syslog(LOG_INFO, e->e_id, "stat=%s", shortenstring(status, 63));
3599 #endif /* (SYSLOG_BUFSIZE) >= 256 */
3600 }
3601 /*
3602 **  PUTFROMLINE -- output a UNIX-style from line (or whatever)
3603 **
3604 **	This can be made an arbitrary message separator by changing $l
3605 **
3606 **	One of the ugliest hacks seen by human eyes is contained herein:
3607 **	UUCP wants those stupid "remote from <host>" lines.  Why oh why
3608 **	does a well-meaning programmer such as myself have to deal with
3609 **	this kind of antique garbage????
3610 **
3611 **	Parameters:
3612 **		mci -- the connection information.
3613 **		e -- the envelope.
3614 **
3615 **	Returns:
3616 **		none
3617 **
3618 **	Side Effects:
3619 **		outputs some text to fp.
3620 */
3621 
3622 void
3623 putfromline(mci, e)
3624 	register MCI *mci;
3625 	ENVELOPE *e;
3626 {
3627 	char *template = UnixFromLine;
3628 	char buf[MAXLINE];
3629 	char xbuf[MAXLINE];
3630 
3631 	if (bitnset(M_NHDR, mci->mci_mailer->m_flags))
3632 		return;
3633 
3634 	mci->mci_flags |= MCIF_INHEADER;
3635 
3636 	if (bitnset(M_UGLYUUCP, mci->mci_mailer->m_flags))
3637 	{
3638 		char *bang;
3639 
3640 		expand("\201g", buf, sizeof buf, e);
3641 		bang = strchr(buf, '!');
3642 		if (bang == NULL)
3643 		{
3644 			char *at;
3645 			char hname[MAXNAME];
3646 
3647 			/*
3648 			**  If we can construct a UUCP path, do so
3649 			*/
3650 
3651 			at = strrchr(buf, '@');
3652 			if (at == NULL)
3653 			{
3654 				expand("\201k", hname, sizeof hname, e);
3655 				at = hname;
3656 			}
3657 			else
3658 				*at++ = '\0';
3659 			(void) snprintf(xbuf, sizeof xbuf,
3660 				"From %.800s  \201d remote from %.100s\n",
3661 				buf, at);
3662 		}
3663 		else
3664 		{
3665 			*bang++ = '\0';
3666 			(void) snprintf(xbuf, sizeof xbuf,
3667 				"From %.800s  \201d remote from %.100s\n",
3668 				bang, buf);
3669 			template = xbuf;
3670 		}
3671 	}
3672 	expand(template, buf, sizeof buf, e);
3673 	putxline(buf, strlen(buf), mci, PXLF_HEADER);
3674 }
3675 /*
3676 **  PUTBODY -- put the body of a message.
3677 **
3678 **	Parameters:
3679 **		mci -- the connection information.
3680 **		e -- the envelope to put out.
3681 **		separator -- if non-NULL, a message separator that must
3682 **			not be permitted in the resulting message.
3683 **
3684 **	Returns:
3685 **		none.
3686 **
3687 **	Side Effects:
3688 **		The message is written onto fp.
3689 */
3690 
3691 /* values for output state variable */
3692 #define OS_HEAD		0	/* at beginning of line */
3693 #define OS_CR		1	/* read a carriage return */
3694 #define OS_INLINE	2	/* putting rest of line */
3695 
3696 void
3697 putbody(mci, e, separator)
3698 	register MCI *mci;
3699 	register ENVELOPE *e;
3700 	char *separator;
3701 {
3702 	bool dead = FALSE;
3703 	char buf[MAXLINE];
3704 	char *boundaries[MAXMIMENESTING + 1];
3705 
3706 	/*
3707 	**  Output the body of the message
3708 	*/
3709 
3710 	if (e->e_dfp == NULL && bitset(EF_HAS_DF, e->e_flags))
3711 	{
3712 		char *df = queuename(e, 'd');
3713 
3714 		e->e_dfp = fopen(df, "r");
3715 		if (e->e_dfp == NULL)
3716 		{
3717 			char *msg = "!putbody: Cannot open %s for %s from %s";
3718 
3719 			if (errno == ENOENT)
3720 				msg++;
3721 			syserr(msg, df, e->e_to, e->e_from.q_paddr);
3722 		}
3723 	}
3724 	if (e->e_dfp == NULL)
3725 	{
3726 		if (bitset(MCIF_INHEADER, mci->mci_flags))
3727 		{
3728 			putline("", mci);
3729 			mci->mci_flags &= ~MCIF_INHEADER;
3730 		}
3731 		putline("<<< No Message Collected >>>", mci);
3732 		goto endofmessage;
3733 	}
3734 
3735 	if (e->e_dfino == (ino_t) 0)
3736 	{
3737 		struct stat stbuf;
3738 
3739 		if (fstat(fileno(e->e_dfp), &stbuf) < 0)
3740 			e->e_dfino = -1;
3741 		else
3742 		{
3743 			e->e_dfdev = stbuf.st_dev;
3744 			e->e_dfino = stbuf.st_ino;
3745 		}
3746 	}
3747 
3748 	/* paranoia: the df file should always be in a rewound state */
3749 	(void) bfrewind(e->e_dfp);
3750 
3751 #if MIME8TO7
3752 	if (bitset(MCIF_CVT8TO7, mci->mci_flags))
3753 	{
3754 		/*
3755 		**  Do 8 to 7 bit MIME conversion.
3756 		*/
3757 
3758 		/* make sure it looks like a MIME message */
3759 		if (hvalue("MIME-Version", e->e_header) == NULL)
3760 			putline("MIME-Version: 1.0", mci);
3761 
3762 		if (hvalue("Content-Type", e->e_header) == NULL)
3763 		{
3764 			snprintf(buf, sizeof buf,
3765 				"Content-Type: text/plain; charset=%s",
3766 				defcharset(e));
3767 			putline(buf, mci);
3768 		}
3769 
3770 		/* now do the hard work */
3771 		boundaries[0] = NULL;
3772 		mci->mci_flags |= MCIF_INHEADER;
3773 		(void) mime8to7(mci, e->e_header, e, boundaries, M87F_OUTER);
3774 	}
3775 # if MIME7TO8
3776 	else if (bitset(MCIF_CVT7TO8, mci->mci_flags))
3777 	{
3778 		(void) mime7to8(mci, e->e_header, e);
3779 	}
3780 # endif /* MIME7TO8 */
3781 	else if (MaxMimeHeaderLength > 0 || MaxMimeFieldLength > 0)
3782 	{
3783 		bool oldsuprerrs = SuprErrs;
3784 
3785 		/* Use mime8to7 to check multipart for MIME header overflows */
3786 		boundaries[0] = NULL;
3787 		mci->mci_flags |= MCIF_INHEADER;
3788 
3789 		/*
3790 		**  If EF_DONT_MIME is set, we have a broken MIME message
3791 		**  and don't want to generate a new bounce message whose
3792 		**  body propagates the broken MIME.  We can't just not call
3793 		**  mime8to7() as is done above since we need the security
3794 		**  checks.  The best we can do is suppress the errors.
3795 		*/
3796 
3797 		if (bitset(EF_DONT_MIME, e->e_flags))
3798 			SuprErrs = TRUE;
3799 
3800 		(void) mime8to7(mci, e->e_header, e, boundaries,
3801 				M87F_OUTER|M87F_NO8TO7);
3802 
3803 		/* restore SuprErrs */
3804 		SuprErrs = oldsuprerrs;
3805 	}
3806 	else
3807 #endif /* MIME8TO7 */
3808 	{
3809 		int ostate;
3810 		register char *bp;
3811 		register char *pbp;
3812 		register int c;
3813 		register char *xp;
3814 		int padc;
3815 		char *buflim;
3816 		int pos = 0;
3817 		char peekbuf[12];
3818 
3819 		if (bitset(MCIF_INHEADER, mci->mci_flags))
3820 		{
3821 			putline("", mci);
3822 			mci->mci_flags &= ~MCIF_INHEADER;
3823 		}
3824 
3825 		/* determine end of buffer; allow for short mailer lines */
3826 		buflim = &buf[sizeof buf - 1];
3827 		if (mci->mci_mailer->m_linelimit > 0 &&
3828 		    mci->mci_mailer->m_linelimit < sizeof buf - 1)
3829 			buflim = &buf[mci->mci_mailer->m_linelimit - 1];
3830 
3831 		/* copy temp file to output with mapping */
3832 		ostate = OS_HEAD;
3833 		bp = buf;
3834 		pbp = peekbuf;
3835 		while (!ferror(mci->mci_out) && !dead)
3836 		{
3837 			if (pbp > peekbuf)
3838 				c = *--pbp;
3839 			else if ((c = getc(e->e_dfp)) == EOF)
3840 				break;
3841 			if (bitset(MCIF_7BIT, mci->mci_flags))
3842 				c &= 0x7f;
3843 			switch (ostate)
3844 			{
3845 			  case OS_HEAD:
3846 #if _FFR_NONULLS
3847 				if (c == '\0' &&
3848 				    bitnset(M_NONULLS, mci->mci_mailer->m_flags))
3849 					break;
3850 #endif /* _FFR_NONULLS */
3851 				if (c != '\r' && c != '\n' && bp < buflim)
3852 				{
3853 					*bp++ = c;
3854 					break;
3855 				}
3856 
3857 				/* check beginning of line for special cases */
3858 				*bp = '\0';
3859 				pos = 0;
3860 				padc = EOF;
3861 				if (buf[0] == 'F' &&
3862 				    bitnset(M_ESCFROM, mci->mci_mailer->m_flags) &&
3863 				    strncmp(buf, "From ", 5) == 0)
3864 				{
3865 					padc = '>';
3866 				}
3867 				if (buf[0] == '-' && buf[1] == '-' &&
3868 				    separator != NULL)
3869 				{
3870 					/* possible separator */
3871 					int sl = strlen(separator);
3872 
3873 					if (strncmp(&buf[2], separator, sl) == 0)
3874 						padc = ' ';
3875 				}
3876 				if (buf[0] == '.' &&
3877 				    bitnset(M_XDOT, mci->mci_mailer->m_flags))
3878 				{
3879 					padc = '.';
3880 				}
3881 
3882 				/* now copy out saved line */
3883 				if (TrafficLogFile != NULL)
3884 				{
3885 					fprintf(TrafficLogFile, "%05d >>> ",
3886 						(int) getpid());
3887 					if (padc != EOF)
3888 						(void) putc(padc,
3889 							    TrafficLogFile);
3890 					for (xp = buf; xp < bp; xp++)
3891 						(void) putc((unsigned char) *xp,
3892 							    TrafficLogFile);
3893 					if (c == '\n')
3894 						(void) fputs(mci->mci_mailer->m_eol,
3895 						      TrafficLogFile);
3896 				}
3897 				if (padc != EOF)
3898 				{
3899 					if (putc(padc, mci->mci_out) == EOF)
3900 					{
3901 						dead = TRUE;
3902 						continue;
3903 					}
3904 					pos++;
3905 				}
3906 				for (xp = buf; xp < bp; xp++)
3907 				{
3908 					if (putc((unsigned char) *xp,
3909 						 mci->mci_out) == EOF)
3910 					{
3911 						dead = TRUE;
3912 						break;
3913 					}
3914 
3915 					/* record progress for DATA timeout */
3916 					DataProgress = TRUE;
3917 				}
3918 				if (dead)
3919 					continue;
3920 				if (c == '\n')
3921 				{
3922 					if (fputs(mci->mci_mailer->m_eol,
3923 						  mci->mci_out) == EOF)
3924 						break;
3925 					pos = 0;
3926 				}
3927 				else
3928 				{
3929 					pos += bp - buf;
3930 					if (c != '\r')
3931 						*pbp++ = c;
3932 				}
3933 
3934 				/* record progress for DATA timeout */
3935 				DataProgress = TRUE;
3936 				bp = buf;
3937 
3938 				/* determine next state */
3939 				if (c == '\n')
3940 					ostate = OS_HEAD;
3941 				else if (c == '\r')
3942 					ostate = OS_CR;
3943 				else
3944 					ostate = OS_INLINE;
3945 				continue;
3946 
3947 			  case OS_CR:
3948 				if (c == '\n')
3949 				{
3950 					/* got CRLF */
3951 					if (fputs(mci->mci_mailer->m_eol,
3952 						  mci->mci_out) == EOF)
3953 						continue;
3954 
3955 					/* record progress for DATA timeout */
3956 					DataProgress = TRUE;
3957 
3958 					if (TrafficLogFile != NULL)
3959 					{
3960 						(void) fputs(mci->mci_mailer->m_eol,
3961 							     TrafficLogFile);
3962 					}
3963 					ostate = OS_HEAD;
3964 					continue;
3965 				}
3966 
3967 				/* had a naked carriage return */
3968 				*pbp++ = c;
3969 				c = '\r';
3970 				ostate = OS_INLINE;
3971 				goto putch;
3972 
3973 			  case OS_INLINE:
3974 				if (c == '\r')
3975 				{
3976 					ostate = OS_CR;
3977 					continue;
3978 				}
3979 #if _FFR_NONULLS
3980 				if (c == '\0' &&
3981 				    bitnset(M_NONULLS, mci->mci_mailer->m_flags))
3982 					break;
3983 #endif /* _FFR_NONULLS */
3984 putch:
3985 				if (mci->mci_mailer->m_linelimit > 0 &&
3986 				    pos >= mci->mci_mailer->m_linelimit - 1 &&
3987 				    c != '\n')
3988 				{
3989 					int d;
3990 
3991 					/* check next character for EOL */
3992 					if (pbp > peekbuf)
3993 						d = *(pbp - 1);
3994 					else if ((d = getc(e->e_dfp)) != EOF)
3995 						*pbp++ = d;
3996 
3997 					if (d == '\n' || d == EOF)
3998 					{
3999 						if (TrafficLogFile != NULL)
4000 							(void) putc((unsigned char) c,
4001 							    TrafficLogFile);
4002 						if (putc((unsigned char) c,
4003 							 mci->mci_out) == EOF)
4004 						{
4005 							dead = TRUE;
4006 							continue;
4007 						}
4008 						pos++;
4009 						continue;
4010 					}
4011 
4012 					if (putc('!', mci->mci_out) == EOF ||
4013 					    fputs(mci->mci_mailer->m_eol,
4014 						  mci->mci_out) == EOF)
4015 					{
4016 						dead = TRUE;
4017 						continue;
4018 					}
4019 
4020 					/* record progress for DATA timeout */
4021 					DataProgress = TRUE;
4022 
4023 					if (TrafficLogFile != NULL)
4024 					{
4025 						fprintf(TrafficLogFile, "!%s",
4026 							mci->mci_mailer->m_eol);
4027 					}
4028 					ostate = OS_HEAD;
4029 					*pbp++ = c;
4030 					continue;
4031 				}
4032 				if (c == '\n')
4033 				{
4034 					if (TrafficLogFile != NULL)
4035 						(void) fputs(mci->mci_mailer->m_eol,
4036 						      TrafficLogFile);
4037 					if (fputs(mci->mci_mailer->m_eol,
4038 						  mci->mci_out) == EOF)
4039 						continue;
4040 					pos = 0;
4041 					ostate = OS_HEAD;
4042 				}
4043 				else
4044 				{
4045 					if (TrafficLogFile != NULL)
4046 						(void) putc((unsigned char) c,
4047 							    TrafficLogFile);
4048 					if (putc((unsigned char) c,
4049 						 mci->mci_out) == EOF)
4050 					{
4051 						dead = TRUE;
4052 						continue;
4053 					}
4054 					pos++;
4055 					ostate = OS_INLINE;
4056 				}
4057 
4058 				/* record progress for DATA timeout */
4059 				DataProgress = TRUE;
4060 				break;
4061 			}
4062 		}
4063 
4064 		/* make sure we are at the beginning of a line */
4065 		if (bp > buf)
4066 		{
4067 			if (TrafficLogFile != NULL)
4068 			{
4069 				for (xp = buf; xp < bp; xp++)
4070 					(void) putc((unsigned char) *xp,
4071 						    TrafficLogFile);
4072 			}
4073 			for (xp = buf; xp < bp; xp++)
4074 			{
4075 				if (putc((unsigned char) *xp, mci->mci_out) ==
4076 				    EOF)
4077 				{
4078 					dead = TRUE;
4079 					break;
4080 				}
4081 
4082 				/* record progress for DATA timeout */
4083 				DataProgress = TRUE;
4084 			}
4085 			pos += bp - buf;
4086 		}
4087 		if (!dead && pos > 0)
4088 		{
4089 			if (TrafficLogFile != NULL)
4090 				(void) fputs(mci->mci_mailer->m_eol,
4091 					     TrafficLogFile);
4092 			(void) fputs(mci->mci_mailer->m_eol, mci->mci_out);
4093 
4094 			/* record progress for DATA timeout */
4095 			DataProgress = TRUE;
4096 		}
4097 	}
4098 
4099 	if (ferror(e->e_dfp))
4100 	{
4101 		syserr("putbody: %s/df%s: read error",
4102 		       qid_printqueue(e->e_queuedir), e->e_id);
4103 		ExitStat = EX_IOERR;
4104 	}
4105 
4106 endofmessage:
4107 	/*
4108 	**  Since mailfile() uses e_dfp in a child process,
4109 	**  the file offset in the stdio library for the
4110 	**  parent process will not agree with the in-kernel
4111 	**  file offset since the file descriptor is shared
4112 	**  between the processes.  Therefore, it is vital
4113 	**  that the file always be rewound.  This forces the
4114 	**  kernel offset (lseek) and stdio library (ftell)
4115 	**  offset to match.
4116 	*/
4117 
4118 	if (e->e_dfp != NULL)
4119 		(void) bfrewind(e->e_dfp);
4120 
4121 	/* some mailers want extra blank line at end of message */
4122 	if (!dead && bitnset(M_BLANKEND, mci->mci_mailer->m_flags) &&
4123 	    buf[0] != '\0' && buf[0] != '\n')
4124 		putline("", mci);
4125 
4126 	(void) fflush(mci->mci_out);
4127 	if (ferror(mci->mci_out) && errno != EPIPE)
4128 	{
4129 		syserr("putbody: write error");
4130 		ExitStat = EX_IOERR;
4131 	}
4132 
4133 	errno = 0;
4134 }
4135 /*
4136 **  MAILFILE -- Send a message to a file.
4137 **
4138 **	If the file has the setuid/setgid bits set, but NO execute
4139 **	bits, sendmail will try to become the owner of that file
4140 **	rather than the real user.  Obviously, this only works if
4141 **	sendmail runs as root.
4142 **
4143 **	This could be done as a subordinate mailer, except that it
4144 **	is used implicitly to save messages in ~/dead.letter.  We
4145 **	view this as being sufficiently important as to include it
4146 **	here.  For example, if the system is dying, we shouldn't have
4147 **	to create another process plus some pipes to save the message.
4148 **
4149 **	Parameters:
4150 **		filename -- the name of the file to send to.
4151 **		mailer -- mailer definition for recipient -- if NULL,
4152 **			use FileMailer.
4153 **		ctladdr -- the controlling address header -- includes
4154 **			the userid/groupid to be when sending.
4155 **		sfflags -- flags for opening.
4156 **		e -- the current envelope.
4157 **
4158 **	Returns:
4159 **		The exit code associated with the operation.
4160 **
4161 **	Side Effects:
4162 **		none.
4163 */
4164 
4165 static jmp_buf	CtxMailfileTimeout;
4166 
4167 int
4168 mailfile(filename, mailer, ctladdr, sfflags, e)
4169 	char *volatile filename;
4170 	MAILER *volatile mailer;
4171 	ADDRESS *ctladdr;
4172 	volatile long sfflags;
4173 	register ENVELOPE *e;
4174 {
4175 	register FILE *f;
4176 	register pid_t pid = -1;
4177 	volatile int mode;
4178 	int len;
4179 	off_t curoff;
4180 	bool suidwarn = geteuid() == 0;
4181 	char *p;
4182 	char *volatile realfile;
4183 	EVENT *ev;
4184 	char buf[MAXLINE + 1];
4185 	char targetfile[MAXPATHLEN + 1];
4186 
4187 	if (tTd(11, 1))
4188 	{
4189 		dprintf("mailfile %s\n  ctladdr=", filename);
4190 		printaddr(ctladdr, FALSE);
4191 	}
4192 
4193 	if (mailer == NULL)
4194 		mailer = FileMailer;
4195 
4196 	if (e->e_xfp != NULL)
4197 		(void) fflush(e->e_xfp);
4198 
4199 	/*
4200 	**  Special case /dev/null.  This allows us to restrict file
4201 	**  delivery to regular files only.
4202 	*/
4203 
4204 	if (strcmp(filename, "/dev/null") == 0)
4205 		return EX_OK;
4206 
4207 	/* check for 8-bit available */
4208 	if (bitset(EF_HAS8BIT, e->e_flags) &&
4209 	    bitnset(M_7BITS, mailer->m_flags) &&
4210 	    (bitset(EF_DONT_MIME, e->e_flags) ||
4211 	     !(bitset(MM_MIME8BIT, MimeMode) ||
4212 	       (bitset(EF_IS_MIME, e->e_flags) &&
4213 		bitset(MM_CVTMIME, MimeMode)))))
4214 	{
4215 		e->e_status = "5.6.3";
4216 		usrerrenh(e->e_status,
4217 		       "554 Cannot send 8-bit data to 7-bit destination");
4218 		return EX_DATAERR;
4219 	}
4220 
4221 	/* Find the actual file */
4222 	if (SafeFileEnv != NULL && SafeFileEnv[0] != '\0')
4223 	{
4224 		len = strlen(SafeFileEnv);
4225 
4226 		if (strncmp(SafeFileEnv, filename, len) == 0)
4227 			filename += len;
4228 
4229 		if (len + strlen(filename) + 1 > MAXPATHLEN)
4230 		{
4231 			syserr("mailfile: filename too long (%s/%s)",
4232 			       SafeFileEnv, filename);
4233 			return EX_CANTCREAT;
4234 		}
4235 		(void) strlcpy(targetfile, SafeFileEnv, sizeof targetfile);
4236 		realfile = targetfile + len;
4237 		if (targetfile[len - 1] != '/')
4238 			(void) strlcat(targetfile, "/", sizeof targetfile);
4239 		if (*filename == '/')
4240 			filename++;
4241 		(void) strlcat(targetfile, filename, sizeof targetfile);
4242 	}
4243 	else if (mailer->m_rootdir != NULL)
4244 	{
4245 		expand(mailer->m_rootdir, targetfile, sizeof targetfile, e);
4246 		len = strlen(targetfile);
4247 
4248 		if (strncmp(targetfile, filename, len) == 0)
4249 			filename += len;
4250 
4251 		if (len + strlen(filename) + 1 > MAXPATHLEN)
4252 		{
4253 			syserr("mailfile: filename too long (%s/%s)",
4254 			       targetfile, filename);
4255 			return EX_CANTCREAT;
4256 		}
4257 		realfile = targetfile + len;
4258 		if (targetfile[len - 1] != '/')
4259 			(void) strlcat(targetfile, "/", sizeof targetfile);
4260 		if (*filename == '/')
4261 			(void) strlcat(targetfile, filename + 1,
4262 				       sizeof targetfile);
4263 		else
4264 			(void) strlcat(targetfile, filename, sizeof targetfile);
4265 	}
4266 	else
4267 	{
4268 		if (strlen(filename) > MAXPATHLEN)
4269 		{
4270 			syserr("mailfile: filename too long (%s)", filename);
4271 			return EX_CANTCREAT;
4272 		}
4273 		(void) strlcpy(targetfile, filename, sizeof targetfile);
4274 		realfile = targetfile;
4275 	}
4276 
4277 	/*
4278 	**  Fork so we can change permissions here.
4279 	**	Note that we MUST use fork, not vfork, because of
4280 	**	the complications of calling subroutines, etc.
4281 	*/
4282 
4283 	DOFORK(fork);
4284 
4285 	if (pid < 0)
4286 		return EX_OSERR;
4287 	else if (pid == 0)
4288 	{
4289 		/* child -- actually write to file */
4290 		struct stat stb;
4291 		MCI mcibuf;
4292 		int err;
4293 		volatile int oflags = O_WRONLY|O_APPEND;
4294 
4295 		if (e->e_lockfp != NULL)
4296 			(void) close(fileno(e->e_lockfp));
4297 
4298 		(void) setsignal(SIGINT, SIG_DFL);
4299 		(void) setsignal(SIGHUP, SIG_DFL);
4300 		(void) setsignal(SIGTERM, SIG_DFL);
4301 		(void) umask(OldUmask);
4302 		e->e_to = filename;
4303 		ExitStat = EX_OK;
4304 
4305 		if (setjmp(CtxMailfileTimeout) != 0)
4306 		{
4307 			exit(EX_TEMPFAIL);
4308 		}
4309 
4310 		if (TimeOuts.to_fileopen > 0)
4311 			ev = setevent(TimeOuts.to_fileopen, mailfiletimeout, 0);
4312 		else
4313 			ev = NULL;
4314 
4315 		/* check file mode to see if setuid */
4316 		if (stat(targetfile, &stb) < 0)
4317 			mode = FileMode;
4318 		else
4319 			mode = stb.st_mode;
4320 
4321 		/* limit the errors to those actually caused in the child */
4322 		errno = 0;
4323 		ExitStat = EX_OK;
4324 
4325 		/* Allow alias expansions to use the S_IS{U,G}ID bits */
4326 		if ((ctladdr != NULL && !bitset(QALIAS, ctladdr->q_flags)) ||
4327 		    bitset(SFF_RUNASREALUID, sfflags))
4328 		{
4329 			/* ignore setuid and setgid bits */
4330 			mode &= ~(S_ISGID|S_ISUID);
4331 			if (tTd(11, 20))
4332 				dprintf("mailfile: ignoring setuid/setgid bits\n");
4333 		}
4334 
4335 		/* we have to open the dfile BEFORE setuid */
4336 		if (e->e_dfp == NULL && bitset(EF_HAS_DF, e->e_flags))
4337 		{
4338 			char *df = queuename(e, 'd');
4339 
4340 			e->e_dfp = fopen(df, "r");
4341 			if (e->e_dfp == NULL)
4342 			{
4343 				syserr("mailfile: Cannot open %s for %s from %s",
4344 					df, e->e_to, e->e_from.q_paddr);
4345 			}
4346 		}
4347 
4348 		/* select a new user to run as */
4349 		if (!bitset(SFF_RUNASREALUID, sfflags))
4350 		{
4351 			if (bitnset(M_SPECIFIC_UID, mailer->m_flags))
4352 			{
4353 				RealUserName = NULL;
4354 				RealUid = mailer->m_uid;
4355 				if (RunAsUid != 0 && RealUid != RunAsUid)
4356 				{
4357 					/* Only root can change the uid */
4358 					syserr("mailfile: insufficient privileges to change uid");
4359 					exit(EX_TEMPFAIL);
4360 				}
4361 			}
4362 			else if (bitset(S_ISUID, mode))
4363 			{
4364 				RealUserName = NULL;
4365 				RealUid = stb.st_uid;
4366 			}
4367 			else if (ctladdr != NULL && ctladdr->q_uid != 0)
4368 			{
4369 				if (ctladdr->q_ruser != NULL)
4370 					RealUserName = ctladdr->q_ruser;
4371 				else
4372 					RealUserName = ctladdr->q_user;
4373 				RealUid = ctladdr->q_uid;
4374 			}
4375 			else if (mailer != NULL && mailer->m_uid != 0)
4376 			{
4377 				RealUserName = DefUser;
4378 				RealUid = mailer->m_uid;
4379 			}
4380 			else
4381 			{
4382 				RealUserName = DefUser;
4383 				RealUid = DefUid;
4384 			}
4385 
4386 			/* select a new group to run as */
4387 			if (bitnset(M_SPECIFIC_UID, mailer->m_flags))
4388 			{
4389 				RealGid = mailer->m_gid;
4390 				if (RunAsUid != 0 &&
4391 				    (RealGid != getgid() ||
4392 				     RealGid != getegid()))
4393 				{
4394 					/* Only root can change the gid */
4395 					syserr("mailfile: insufficient privileges to change gid");
4396 					exit(EX_TEMPFAIL);
4397 				}
4398 			}
4399 			else if (bitset(S_ISGID, mode))
4400 				RealGid = stb.st_gid;
4401 			else if (ctladdr != NULL && ctladdr->q_uid != 0)
4402 				RealGid = ctladdr->q_gid;
4403 			else if (ctladdr != NULL &&
4404 				 ctladdr->q_uid == DefUid &&
4405 				 ctladdr->q_gid == 0)
4406 				RealGid = DefGid;
4407 			else if (mailer != NULL && mailer->m_gid != 0)
4408 				RealGid = mailer->m_gid;
4409 			else
4410 				RealGid = DefGid;
4411 		}
4412 
4413 		/* last ditch */
4414 		if (!bitset(SFF_ROOTOK, sfflags))
4415 		{
4416 			if (RealUid == 0)
4417 				RealUid = DefUid;
4418 			if (RealGid == 0)
4419 				RealGid = DefGid;
4420 		}
4421 
4422 		/* set group id list (needs /etc/group access) */
4423 		if (RealUserName != NULL && !DontInitGroups)
4424 		{
4425 			if (initgroups(RealUserName, RealGid) == -1 && suidwarn)
4426 			{
4427 				syserr("mailfile: initgroups(%s, %d) failed",
4428 					RealUserName, RealGid);
4429 				exit(EX_TEMPFAIL);
4430 			}
4431 		}
4432 		else
4433 		{
4434 			GIDSET_T gidset[1];
4435 
4436 			gidset[0] = RealGid;
4437 			if (setgroups(1, gidset) == -1 && suidwarn)
4438 			{
4439 				syserr("mailfile: setgroups() failed");
4440 				exit(EX_TEMPFAIL);
4441 			}
4442 		}
4443 
4444 		/*
4445 		**  If you have a safe environment, go into it.
4446 		*/
4447 
4448 		if (realfile != targetfile)
4449 		{
4450 			*realfile = '\0';
4451 			if (tTd(11, 20))
4452 				dprintf("mailfile: chroot %s\n", targetfile);
4453 			if (chroot(targetfile) < 0)
4454 			{
4455 				syserr("mailfile: Cannot chroot(%s)",
4456 				       targetfile);
4457 				exit(EX_CANTCREAT);
4458 			}
4459 			*realfile = '/';
4460 		}
4461 
4462 		if (tTd(11, 40))
4463 			dprintf("mailfile: deliver to %s\n", realfile);
4464 
4465 		if (chdir("/") < 0)
4466 		{
4467 			syserr("mailfile: cannot chdir(/)");
4468 			exit(EX_CANTCREAT);
4469 		}
4470 
4471 		/* now reset the group and user ids */
4472 		endpwent();
4473 		if (setgid(RealGid) < 0 && suidwarn)
4474 		{
4475 			syserr("mailfile: setgid(%ld) failed", (long) RealGid);
4476 			exit(EX_TEMPFAIL);
4477 		}
4478 		vendor_set_uid(RealUid);
4479 		if (setuid(RealUid) < 0 && suidwarn)
4480 		{
4481 			syserr("mailfile: setuid(%ld) failed", (long) RealUid);
4482 			exit(EX_TEMPFAIL);
4483 		}
4484 
4485 		if (tTd(11, 2))
4486 			dprintf("mailfile: running as r/euid=%d/%d, r/egid=%d/%d\n",
4487 				(int) getuid(), (int) geteuid(),
4488 				(int) getgid(), (int) getegid());
4489 
4490 
4491 		/* move into some "safe" directory */
4492 		if (mailer->m_execdir != NULL)
4493 		{
4494 			char *q;
4495 
4496 			for (p = mailer->m_execdir; p != NULL; p = q)
4497 			{
4498 				q = strchr(p, ':');
4499 				if (q != NULL)
4500 					*q = '\0';
4501 				expand(p, buf, sizeof buf, e);
4502 				if (q != NULL)
4503 					*q++ = ':';
4504 				if (tTd(11, 20))
4505 					dprintf("mailfile: trydir %s\n", buf);
4506 				if (buf[0] != '\0' && chdir(buf) >= 0)
4507 					break;
4508 			}
4509 		}
4510 
4511 		/*
4512 		**  Recheck the file after we have assumed the ID of the
4513 		**  delivery user to make sure we can deliver to it as
4514 		**  that user.  This is necessary if sendmail is running
4515 		**  as root and the file is on an NFS mount which treats
4516 		**  root as nobody.
4517 		*/
4518 
4519 #if HASLSTAT
4520 		if (bitnset(DBS_FILEDELIVERYTOSYMLINK, DontBlameSendmail))
4521 			err = stat(realfile, &stb);
4522 		else
4523 			err = lstat(realfile, &stb);
4524 #else /* HASLSTAT */
4525 		err = stat(realfile, &stb);
4526 #endif /* HASLSTAT */
4527 
4528 		if (err < 0)
4529 		{
4530 			stb.st_mode = ST_MODE_NOFILE;
4531 			mode = FileMode;
4532 			oflags |= O_CREAT|O_EXCL;
4533 		}
4534 		else if (bitset(S_IXUSR|S_IXGRP|S_IXOTH, mode) ||
4535 			 (!bitnset(DBS_FILEDELIVERYTOHARDLINK,
4536 				   DontBlameSendmail) &&
4537 			  stb.st_nlink != 1) ||
4538 			 (realfile != targetfile && !S_ISREG(mode)))
4539 			exit(EX_CANTCREAT);
4540 		else
4541 			mode = stb.st_mode;
4542 
4543 		if (!bitnset(DBS_FILEDELIVERYTOSYMLINK, DontBlameSendmail))
4544 			sfflags |= SFF_NOSLINK;
4545 		if (!bitnset(DBS_FILEDELIVERYTOHARDLINK, DontBlameSendmail))
4546 			sfflags |= SFF_NOHLINK;
4547 		sfflags &= ~SFF_OPENASROOT;
4548 		f = safefopen(realfile, oflags, mode, sfflags);
4549 		if (f == NULL)
4550 		{
4551 			if (transienterror(errno))
4552 			{
4553 				usrerr("454 4.3.0 cannot open %s: %s",
4554 				       shortenstring(realfile, MAXSHORTSTR),
4555 				       errstring(errno));
4556 				exit(EX_TEMPFAIL);
4557 			}
4558 			else
4559 			{
4560 				usrerr("554 5.3.0 cannot open %s: %s",
4561 				       shortenstring(realfile, MAXSHORTSTR),
4562 				       errstring(errno));
4563 				exit(EX_CANTCREAT);
4564 			}
4565 		}
4566 		if (filechanged(realfile, fileno(f), &stb))
4567 		{
4568 			syserr("554 5.3.0 file changed after open");
4569 			exit(EX_CANTCREAT);
4570 		}
4571 		if (fstat(fileno(f), &stb) < 0)
4572 		{
4573 			syserr("554 5.3.0 cannot fstat %s", errstring(errno));
4574 			exit(EX_CANTCREAT);
4575 		}
4576 
4577 		curoff = stb.st_size;
4578 
4579 		if (ev != NULL)
4580 			clrevent(ev);
4581 
4582 		memset(&mcibuf, '\0', sizeof mcibuf);
4583 		mcibuf.mci_mailer = mailer;
4584 		mcibuf.mci_out = f;
4585 		if (bitnset(M_7BITS, mailer->m_flags))
4586 			mcibuf.mci_flags |= MCIF_7BIT;
4587 
4588 		/* clear out per-message flags from connection structure */
4589 		mcibuf.mci_flags &= ~(MCIF_CVT7TO8|MCIF_CVT8TO7);
4590 
4591 		if (bitset(EF_HAS8BIT, e->e_flags) &&
4592 		    !bitset(EF_DONT_MIME, e->e_flags) &&
4593 		    bitnset(M_7BITS, mailer->m_flags))
4594 			mcibuf.mci_flags |= MCIF_CVT8TO7;
4595 
4596 #if MIME7TO8
4597 		if (bitnset(M_MAKE8BIT, mailer->m_flags) &&
4598 		    !bitset(MCIF_7BIT, mcibuf.mci_flags) &&
4599 		    (p = hvalue("Content-Transfer-Encoding", e->e_header)) != NULL &&
4600 		    (strcasecmp(p, "quoted-printable") == 0 ||
4601 		     strcasecmp(p, "base64") == 0) &&
4602 		    (p = hvalue("Content-Type", e->e_header)) != NULL)
4603 		{
4604 			/* may want to convert 7 -> 8 */
4605 			/* XXX should really parse it here -- and use a class XXX */
4606 			if (strncasecmp(p, "text/plain", 10) == 0 &&
4607 			    (p[10] == '\0' || p[10] == ' ' || p[10] == ';'))
4608 				mcibuf.mci_flags |= MCIF_CVT7TO8;
4609 		}
4610 #endif /* MIME7TO8 */
4611 
4612 		putfromline(&mcibuf, e);
4613 		(*e->e_puthdr)(&mcibuf, e->e_header, e, M87F_OUTER);
4614 		(*e->e_putbody)(&mcibuf, e, NULL);
4615 		putline("\n", &mcibuf);
4616 		if (fflush(f) < 0 ||
4617 		    (SuperSafe && fsync(fileno(f)) < 0) ||
4618 		    ferror(f))
4619 		{
4620 			setstat(EX_IOERR);
4621 #if !NOFTRUNCATE
4622 			(void) ftruncate(fileno(f), curoff);
4623 #endif /* !NOFTRUNCATE */
4624 		}
4625 
4626 		/* reset ISUID & ISGID bits for paranoid systems */
4627 #if HASFCHMOD
4628 		(void) fchmod(fileno(f), (MODE_T) mode);
4629 #else /* HASFCHMOD */
4630 		(void) chmod(filename, (MODE_T) mode);
4631 #endif /* HASFCHMOD */
4632 		if (fclose(f) < 0)
4633 			setstat(EX_IOERR);
4634 		(void) fflush(stdout);
4635 		(void) setuid(RealUid);
4636 		exit(ExitStat);
4637 		/* NOTREACHED */
4638 	}
4639 	else
4640 	{
4641 		/* parent -- wait for exit status */
4642 		int st;
4643 
4644 		st = waitfor(pid);
4645 		if (st == -1)
4646 		{
4647 			syserr("mailfile: %s: wait", mailer->m_name);
4648 			return EX_SOFTWARE;
4649 		}
4650 		if (WIFEXITED(st))
4651 			return (WEXITSTATUS(st));
4652 		else
4653 		{
4654 			syserr("mailfile: %s: child died on signal %d",
4655 			       mailer->m_name, st);
4656 			return EX_UNAVAILABLE;
4657 		}
4658 		/* NOTREACHED */
4659 	}
4660 	return EX_UNAVAILABLE;	/* avoid compiler warning on IRIX */
4661 }
4662 
4663 static void
4664 mailfiletimeout()
4665 {
4666 	longjmp(CtxMailfileTimeout, 1);
4667 }
4668 /*
4669 **  HOSTSIGNATURE -- return the "signature" for a host.
4670 **
4671 **	The signature describes how we are going to send this -- it
4672 **	can be just the hostname (for non-Internet hosts) or can be
4673 **	an ordered list of MX hosts.
4674 **
4675 **	Parameters:
4676 **		m -- the mailer describing this host.
4677 **		host -- the host name.
4678 **
4679 **	Returns:
4680 **		The signature for this host.
4681 **
4682 **	Side Effects:
4683 **		Can tweak the symbol table.
4684 */
4685 #define MAXHOSTSIGNATURE	8192	/* max len of hostsignature */
4686 
4687 static char *
4688 hostsignature(m, host)
4689 	register MAILER *m;
4690 	char *host;
4691 {
4692 	register char *p;
4693 	register STAB *s;
4694 #if NAMED_BIND
4695 	char sep = ':';
4696 	char prevsep = ':';
4697 	int i;
4698 	int len;
4699 	int nmx;
4700 	int hl;
4701 	char *hp;
4702 	char *endp;
4703 	int oldoptions = _res.options;
4704 	char *mxhosts[MAXMXHOSTS + 1];
4705 	u_short mxprefs[MAXMXHOSTS + 1];
4706 #endif /* NAMED_BIND */
4707 
4708 	if (tTd(17, 3))
4709 		dprintf("hostsignature(%s)\n", host);
4710 
4711 	/*
4712 	**  If local delivery, just return a constant.
4713 	*/
4714 
4715 	if (bitnset(M_LOCALMAILER, m->m_flags))
4716 		return "localhost";
4717 
4718 	/*
4719 	**  Check to see if this uses IPC -- if not, it can't have MX records.
4720 	*/
4721 
4722 	p = m->m_mailer;
4723 	if (strcmp(p, "[IPC]") != 0 &&
4724 	    strcmp(p, "[TCP]") != 0)
4725 	{
4726 		/* just an ordinary mailer */
4727 		return host;
4728 	}
4729 #if NETUNIX
4730 	else if (m->m_argv[0] != NULL &&
4731 		 strcmp(m->m_argv[0], "FILE") == 0)
4732 	{
4733 		/* rendezvous in the file system, no MX records */
4734 		return host;
4735 	}
4736 #endif /* NETUNIX */
4737 
4738 	/*
4739 	**  Look it up in the symbol table.
4740 	*/
4741 
4742 	s = stab(host, ST_HOSTSIG, ST_ENTER);
4743 	if (s->s_hostsig != NULL)
4744 	{
4745 		if (tTd(17, 3))
4746 			dprintf("hostsignature(): stab(%s) found %s\n", host,
4747 				s->s_hostsig);
4748 		return s->s_hostsig;
4749 	}
4750 
4751 	/*
4752 	**  Not already there -- create a signature.
4753 	*/
4754 
4755 #if NAMED_BIND
4756 	if (ConfigLevel < 2)
4757 		_res.options &= ~(RES_DEFNAMES | RES_DNSRCH);	/* XXX */
4758 
4759 	for (hp = host; hp != NULL; hp = endp)
4760 	{
4761 #if NETINET6
4762 		if (*hp == '[')
4763 		{
4764 			endp = strchr(hp + 1, ']');
4765 			if (endp != NULL)
4766 				endp = strpbrk(endp + 1, ":,");
4767 		}
4768 		else
4769 			endp = strpbrk(hp, ":,");
4770 #else /* NETINET6 */
4771 		endp = strpbrk(hp, ":,");
4772 #endif /* NETINET6 */
4773 		if (endp != NULL)
4774 		{
4775 			sep = *endp;
4776 			*endp = '\0';
4777 		}
4778 
4779 		if (bitnset(M_NOMX, m->m_flags))
4780 		{
4781 			/* skip MX lookups */
4782 			nmx = 1;
4783 			mxhosts[0] = hp;
4784 		}
4785 		else
4786 		{
4787 			auto int rcode;
4788 
4789 			nmx = getmxrr(hp, mxhosts, mxprefs, TRUE, &rcode);
4790 			if (nmx <= 0)
4791 			{
4792 				register MCI *mci;
4793 
4794 				/* update the connection info for this host */
4795 				mci = mci_get(hp, m);
4796 				mci->mci_errno = errno;
4797 				mci->mci_herrno = h_errno;
4798 				mci->mci_lastuse = curtime();
4799 				if (rcode == EX_NOHOST)
4800 					mci_setstat(mci, rcode, "5.1.2",
4801 						"550 Host unknown");
4802 				else
4803 					mci_setstat(mci, rcode, NULL, NULL);
4804 
4805 				/* use the original host name as signature */
4806 				nmx = 1;
4807 				mxhosts[0] = hp;
4808 			}
4809 			if (tTd(17, 3))
4810 				dprintf("hostsignature(): getmxrr() returned %d, mxhosts[0]=%s\n",
4811 					nmx, mxhosts[0]);
4812 		}
4813 
4814 		len = 0;
4815 		for (i = 0; i < nmx; i++)
4816 			len += strlen(mxhosts[i]) + 1;
4817 		if (s->s_hostsig != NULL)
4818 			len += strlen(s->s_hostsig) + 1;
4819 		if (len >= MAXHOSTSIGNATURE)
4820 		{
4821 			sm_syslog(LOG_WARNING, NOQID, "hostsignature for host '%s' exceeds maxlen (%d): %d",
4822 				  host, MAXHOSTSIGNATURE, len);
4823 			len = MAXHOSTSIGNATURE;
4824 		}
4825 		p = xalloc(len);
4826 		if (s->s_hostsig != NULL)
4827 		{
4828 			(void) strlcpy(p, s->s_hostsig, len);
4829 			free(s->s_hostsig);
4830 			s->s_hostsig = p;
4831 			hl = strlen(p);
4832 			p += hl;
4833 			*p++ = prevsep;
4834 			len -= hl + 1;
4835 		}
4836 		else
4837 			s->s_hostsig = p;
4838 		for (i = 0; i < nmx; i++)
4839 		{
4840 			hl = strlen(mxhosts[i]);
4841 			if (len - 1 < hl || len <= 1)
4842 			{
4843 				/* force to drop out of outer loop */
4844 				len = -1;
4845 				break;
4846 			}
4847 			if (i != 0)
4848 			{
4849 				if (mxprefs[i] == mxprefs[i - 1])
4850 					*p++ = ',';
4851 				else
4852 					*p++ = ':';
4853 				len--;
4854 			}
4855 			(void) strlcpy(p, mxhosts[i], len);
4856 			p += hl;
4857 			len -= hl;
4858 		}
4859 
4860 		/*
4861 		**  break out of loop if len exceeded MAXHOSTSIGNATURE
4862 		**  because we won't have more space for further hosts
4863 		**  anyway (separated by : in the .cf file).
4864 		*/
4865 
4866 		if (len < 0)
4867 			break;
4868 		if (endp != NULL)
4869 			*endp++ = sep;
4870 		prevsep = sep;
4871 	}
4872 	makelower(s->s_hostsig);
4873 	if (ConfigLevel < 2)
4874 		_res.options = oldoptions;
4875 #else /* NAMED_BIND */
4876 	/* not using BIND -- the signature is just the host name */
4877 	s->s_hostsig = host;
4878 #endif /* NAMED_BIND */
4879 	if (tTd(17, 1))
4880 		dprintf("hostsignature(%s) = %s\n", host, s->s_hostsig);
4881 	return s->s_hostsig;
4882 }
4883 /*
4884 **  PARSE_HOSTSIGNATURE -- parse the "signature" and return MX host array.
4885 **
4886 **	The signature describes how we are going to send this -- it
4887 **	can be just the hostname (for non-Internet hosts) or can be
4888 **	an ordered list of MX hosts which must be randomized for equal
4889 **	MX preference values.
4890 **
4891 **	Parameters:
4892 **		sig -- the host signature.
4893 **		mxhosts -- array to populate.
4894 **
4895 **	Returns:
4896 **		The number of hosts inserted into mxhosts array.
4897 **
4898 **	Side Effects:
4899 **		Randomizes equal MX preference hosts in mxhosts.
4900 */
4901 
4902 static int
4903 parse_hostsignature(sig, mxhosts, mailer)
4904 	char *sig;
4905 	char **mxhosts;
4906 	MAILER *mailer;
4907 {
4908 	int nmx = 0;
4909 	int curpref = 0;
4910 	int i, j;
4911 	char *hp, *endp;
4912 	u_short prefer[MAXMXHOSTS];
4913 	long rndm[MAXMXHOSTS];
4914 
4915 	for (hp = sig; hp != NULL; hp = endp)
4916 	{
4917 		char sep = ':';
4918 
4919 #if NETINET6
4920 		if (*hp == '[')
4921 		{
4922 			endp = strchr(hp + 1, ']');
4923 			if (endp != NULL)
4924 				endp = strpbrk(endp + 1, ":,");
4925 		}
4926 		else
4927 			endp = strpbrk(hp, ":,");
4928 #else /* NETINET6 */
4929 		endp = strpbrk(hp, ":,");
4930 #endif /* NETINET6 */
4931 		if (endp != NULL)
4932 		{
4933 			sep = *endp;
4934 			*endp = '\0';
4935 		}
4936 
4937 		mxhosts[nmx] = hp;
4938 		prefer[nmx] = curpref;
4939 		if (mci_match(hp, mailer))
4940 			rndm[nmx] = 0;
4941 		else
4942 			rndm[nmx] = get_random();
4943 
4944 		if (endp != NULL)
4945 		{
4946 			/*
4947 			**  Since we don't have the original MX prefs,
4948 			**  make our own.  If the separator is a ':', that
4949 			**  means the preference for the next host will be
4950 			**  higher than this one, so simply increment curpref.
4951 			*/
4952 
4953 			if (sep == ':')
4954 				curpref++;
4955 
4956 			*endp++ = sep;
4957 		}
4958 		if (++nmx >= MAXMXHOSTS)
4959 			break;
4960 	}
4961 
4962 	/* sort the records using the random factor for equal preferences */
4963 	for (i = 0; i < nmx; i++)
4964 	{
4965 		for (j = i + 1; j < nmx; j++)
4966 		{
4967 			/*
4968 			**  List is already sorted by MX preference, only
4969 			**  need to look for equal preference MX records
4970 			*/
4971 
4972 			if (prefer[i] < prefer[j])
4973 				break;
4974 
4975 			if (prefer[i] > prefer[j] ||
4976 			    (prefer[i] == prefer[j] && rndm[i] > rndm[j]))
4977 			{
4978 				register u_short tempp;
4979 				register long tempr;
4980 				register char *temp1;
4981 
4982 				tempp = prefer[i];
4983 				prefer[i] = prefer[j];
4984 				prefer[j] = tempp;
4985 				temp1 = mxhosts[i];
4986 				mxhosts[i] = mxhosts[j];
4987 				mxhosts[j] = temp1;
4988 				tempr = rndm[i];
4989 				rndm[i] = rndm[j];
4990 				rndm[j] = tempr;
4991 			}
4992 		}
4993 	}
4994 	return nmx;
4995 }
4996 
4997 #if SMTP
4998 # if STARTTLS
4999 static SSL_CTX	*clt_ctx = NULL;
5000 
5001 /*
5002 **  INITCLTTLS -- initialize client side TLS
5003 **
5004 **	Parameters:
5005 **		none.
5006 **
5007 **	Returns:
5008 **		succeeded?
5009 */
5010 
5011 bool
5012 initclttls()
5013 {
5014 	if (clt_ctx != NULL)
5015 		return TRUE;	/* already done */
5016 	return inittls(&clt_ctx, TLS_I_CLT, FALSE, CltCERTfile, Cltkeyfile,
5017 		       CACERTpath, CACERTfile, DHParams);
5018 }
5019 
5020 /*
5021 **  STARTTLS -- try to start secure connection (client side)
5022 **
5023 **	Parameters:
5024 **		m -- the mailer.
5025 **		mci -- the mailer connection info.
5026 **		e -- the envelope.
5027 **
5028 **	Returns:
5029 **		success?
5030 **		(maybe this should be some other code than EX_
5031 **		that denotes which stage failed.)
5032 */
5033 
5034 static int
5035 starttls(m, mci, e)
5036 	MAILER *m;
5037 	MCI *mci;
5038 	ENVELOPE *e;
5039 {
5040 	int smtpresult;
5041 	int result = 0;
5042 	int rfd, wfd;
5043 	SSL *clt_ssl = NULL;
5044 
5045 	if (clt_ctx == NULL && !initclttls())
5046 		return EX_TEMPFAIL;
5047 	smtpmessage("STARTTLS", m, mci);
5048 
5049 	/* get the reply */
5050 	smtpresult = reply(m, mci, e, TimeOuts.to_datafinal, NULL, NULL);
5051 	/* which timeout? XXX */
5052 
5053 	/* check return code from server */
5054 	if (smtpresult == 454)
5055 		return EX_TEMPFAIL;
5056 	if (smtpresult == 501)
5057 		return EX_USAGE;
5058 	if (smtpresult == -1)
5059 		return smtpresult;
5060 	if (smtpresult != 220)
5061 		return EX_PROTOCOL;
5062 
5063 	if (LogLevel > 13)
5064 		sm_syslog(LOG_INFO, e->e_id, "TLS: start client");
5065 
5066 	/* start connection */
5067 	if ((clt_ssl = SSL_new(clt_ctx)) == NULL)
5068 	{
5069 		if (LogLevel > 5)
5070 		{
5071 			sm_syslog(LOG_ERR, e->e_id,
5072 				  "TLS: error: client: SSL_new failed");
5073 			if (LogLevel > 9)
5074 				tlslogerr();
5075 		}
5076 		return EX_SOFTWARE;
5077 	}
5078 
5079 	rfd = fileno(mci->mci_in);
5080 	wfd = fileno(mci->mci_out);
5081 
5082 	/* SSL_clear(clt_ssl); ? */
5083 	if (rfd < 0 || wfd < 0 ||
5084 	    (result = SSL_set_rfd(clt_ssl, rfd)) <= 0 ||
5085 	    (result = SSL_set_wfd(clt_ssl, wfd)) <= 0)
5086 	{
5087 		if (LogLevel > 5)
5088 		{
5089 			sm_syslog(LOG_ERR, e->e_id,
5090 				  "TLS: error: SSL_set_xfd failed=%d", result);
5091 			if (LogLevel > 9)
5092 				tlslogerr();
5093 		}
5094 		return EX_SOFTWARE;
5095 	}
5096 	SSL_set_connect_state(clt_ssl);
5097 	if ((result = SSL_connect(clt_ssl)) <= 0)
5098 	{
5099 		int i;
5100 
5101 		/* what to do in this case? */
5102 		i = SSL_get_error(clt_ssl, result);
5103 		if (LogLevel > 5)
5104 		{
5105 			sm_syslog(LOG_ERR, e->e_id,
5106 				  "TLS: error: SSL_connect failed=%d (%d)",
5107 				  result, i);
5108 			if (LogLevel > 9)
5109 				tlslogerr();
5110 		}
5111 		SSL_free(clt_ssl);
5112 		clt_ssl = NULL;
5113 		return EX_SOFTWARE;
5114 	}
5115 	mci->mci_ssl = clt_ssl;
5116 	result = tls_get_info(clt_ssl, e, FALSE, mci->mci_host);
5117 
5118 	/* switch to use SSL... */
5119 #if SFIO
5120 	if (sfdctls(mci->mci_in, mci->mci_out, mci->mci_ssl) == 0)
5121 		return EX_OK;
5122 #else /* SFIO */
5123 # if _FFR_TLS_TOREK
5124 	if (sfdctls(&mci->mci_in, &mci->mci_out, mci->mci_ssl) == 0)
5125 		return EX_OK;
5126 # endif /* _FFR_TLS_TOREK */
5127 #endif /* SFIO */
5128 
5129 	/* failure */
5130 	SSL_free(clt_ssl);
5131 	clt_ssl = NULL;
5132 	return EX_SOFTWARE;
5133 }
5134 
5135 /*
5136 **  ENDTLSCLT -- shutdown secure connection (client side)
5137 **
5138 **	Parameters:
5139 **		mci -- the mailer connection info.
5140 **
5141 **	Returns:
5142 **		success?
5143 */
5144 int
5145 endtlsclt(mci)
5146 	MCI *mci;
5147 {
5148 	int r;
5149 
5150 	if (!bitset(MCIF_TLSACT, mci->mci_flags))
5151 		return EX_OK;
5152 	r = endtls(mci->mci_ssl, "client");
5153 	mci->mci_flags &= ~MCIF_TLSACT;
5154 	return r;
5155 }
5156 /*
5157 **  ENDTLS -- shutdown secure connection
5158 **
5159 **	Parameters:
5160 **		ssl -- SSL connection information.
5161 **		side -- srv/clt (for logging).
5162 **
5163 **	Returns:
5164 **		success?
5165 */
5166 
5167 int
5168 endtls(ssl, side)
5169 	SSL *ssl;
5170 	char *side;
5171 {
5172 	if (ssl != NULL)
5173 	{
5174 		int r;
5175 
5176 		if ((r = SSL_shutdown(ssl)) < 0)
5177 		{
5178 			if (LogLevel > 11)
5179 				sm_syslog(LOG_WARNING, NOQID,
5180 					  "SSL_shutdown %s failed: %d",
5181 					  side, r);
5182 			return EX_SOFTWARE;
5183 		}
5184 		else if (r == 0)
5185 		{
5186 			if (LogLevel > 13)
5187 				sm_syslog(LOG_WARNING, NOQID,
5188 					  "SSL_shutdown %s not done",
5189 					  side);
5190 			return EX_SOFTWARE;
5191 		}
5192 		SSL_free(ssl);
5193 		ssl = NULL;
5194 	}
5195 	return EX_OK;
5196 }
5197 # endif /* STARTTLS */
5198 #endif /* SMTP */
5199