1/*++
2/* NAME
3/*	pickup 8
4/* SUMMARY
5/*	Postfix local mail pickup
6/* SYNOPSIS
7/*	\fBpickup\fR [generic Postfix daemon options]
8/* DESCRIPTION
9/*	The \fBpickup\fR(8) daemon waits for hints that new mail has been
10/*	dropped into the \fBmaildrop\fR directory, and feeds it into the
11/*	\fBcleanup\fR(8) daemon.
12/*	Ill-formatted files are deleted without notifying the originator.
13/*	This program expects to be run from the \fBmaster\fR(8) process
14/*	manager.
15/* STANDARDS
16/* .ad
17/* .fi
18/*	None. The \fBpickup\fR(8) daemon does not interact with
19/*	the outside world.
20/* SECURITY
21/* .ad
22/* .fi
23/*	The \fBpickup\fR(8) daemon is moderately security sensitive. It runs
24/*	with fixed low privilege and can run in a chrooted environment.
25/*	However, the program reads files from potentially hostile users.
26/*	The \fBpickup\fR(8) daemon opens no files for writing, is careful about
27/*	what files it opens for reading, and does not actually touch any data
28/*	that is sent to its public service endpoint.
29/* DIAGNOSTICS
30/*	Problems and transactions are logged to \fBsyslogd\fR(8).
31/* BUGS
32/*	The \fBpickup\fR(8) daemon copies mail from file to the \fBcleanup\fR(8)
33/*	daemon.  It could avoid message copying overhead by sending a file
34/*	descriptor instead of file data, but then the already complex
35/*	\fBcleanup\fR(8) daemon would have to deal with unfiltered user data.
36/* CONFIGURATION PARAMETERS
37/* .ad
38/* .fi
39/*	As the \fBpickup\fR(8) daemon is a relatively long-running process, up
40/*	to an hour may pass before a \fBmain.cf\fR change takes effect.
41/*	Use the command "\fBpostfix reload\fR" command to speed up a change.
42/*
43/*	The text below provides only a parameter summary. See
44/*	\fBpostconf\fR(5) for more details including examples.
45/* CONTENT INSPECTION CONTROLS
46/* .ad
47/* .fi
48/* .IP "\fBcontent_filter (empty)\fR"
49/*	After the message is queued, send the entire message to the
50/*	specified \fItransport:destination\fR.
51/* .IP "\fBreceive_override_options (empty)\fR"
52/*	Enable or disable recipient validation, built-in content
53/*	filtering, or address mapping.
54/* MISCELLANEOUS CONTROLS
55/* .ad
56/* .fi
57/* .IP "\fBconfig_directory (see 'postconf -d' output)\fR"
58/*	The default location of the Postfix main.cf and master.cf
59/*	configuration files.
60/* .IP "\fBipc_timeout (3600s)\fR"
61/*	The time limit for sending or receiving information over an internal
62/*	communication channel.
63/* .IP "\fBline_length_limit (2048)\fR"
64/*	Upon input, long lines are chopped up into pieces of at most
65/*	this length; upon delivery, long lines are reconstructed.
66/* .IP "\fBmax_idle (100s)\fR"
67/*	The maximum amount of time that an idle Postfix daemon process waits
68/*	for an incoming connection before terminating voluntarily.
69/* .IP "\fBmax_use (100)\fR"
70/*	The maximal number of incoming connections that a Postfix daemon
71/*	process will service before terminating voluntarily.
72/* .IP "\fBprocess_id (read-only)\fR"
73/*	The process ID of a Postfix command or daemon process.
74/* .IP "\fBprocess_name (read-only)\fR"
75/*	The process name of a Postfix command or daemon process.
76/* .IP "\fBqueue_directory (see 'postconf -d' output)\fR"
77/*	The location of the Postfix top-level queue directory.
78/* .IP "\fBsyslog_facility (mail)\fR"
79/*	The syslog facility of Postfix logging.
80/* .IP "\fBsyslog_name (see 'postconf -d' output)\fR"
81/*	The mail system name that is prepended to the process name in syslog
82/*	records, so that "smtpd" becomes, for example, "postfix/smtpd".
83/* SEE ALSO
84/*	cleanup(8), message canonicalization
85/*	sendmail(1), Sendmail-compatible interface
86/*	postdrop(1), mail posting agent
87/*	postconf(5), configuration parameters
88/*	master(5), generic daemon options
89/*	master(8), process manager
90/*	syslogd(8), system logging
91/* LICENSE
92/* .ad
93/* .fi
94/*	The Secure Mailer license must be distributed with this software.
95/* AUTHOR(S)
96/*	Wietse Venema
97/*	IBM T.J. Watson Research
98/*	P.O. Box 704
99/*	Yorktown Heights, NY 10598, USA
100/*--*/
101
102/* System library. */
103
104#include <sys_defs.h>
105#include <sys/stat.h>
106#include <dirent.h>
107#include <unistd.h>
108#include <stdlib.h>
109#include <time.h>
110#include <string.h>
111#include <fcntl.h>
112#include <errno.h>
113#include <ctype.h>
114
115/* Utility library. */
116
117#include <msg.h>
118#include <scan_dir.h>
119#include <vstring.h>
120#include <vstream.h>
121#include <set_ugid.h>
122#include <safe_open.h>
123#include <watchdog.h>
124#include <stringops.h>
125
126/* Global library. */
127
128#include <mail_queue.h>
129#include <mail_open_ok.h>
130#include <mymalloc.h>
131#include <mail_proto.h>
132#include <cleanup_user.h>
133#include <mail_date.h>
134#include <mail_params.h>
135#include <mail_conf.h>
136#include <record.h>
137#include <rec_type.h>
138#include <lex_822.h>
139#include <input_transp.h>
140#include <rec_attr_map.h>
141#include <mail_version.h>
142
143/* Single-threaded server skeleton. */
144
145#include <mail_server.h>
146
147/* Application-specific. */
148
149char   *var_filter_xport;
150char   *var_input_transp;
151
152 /*
153  * Structure to bundle a bunch of information about a queue file.
154  */
155typedef struct {
156    char   *id;				/* queue file basename */
157    struct stat st;			/* queue file status */
158    char   *path;			/* name for open/remove */
159    char   *sender;			/* sender address */
160} PICKUP_INFO;
161
162 /*
163  * What action should be taken after attempting to deliver a message: remove
164  * the file from the maildrop, or leave it alone. The latter is also used
165  * for files that are still being written to.
166  */
167#define REMOVE_MESSAGE_FILE	1
168#define KEEP_MESSAGE_FILE	2
169
170 /*
171  * Transparency: before mail is queued, do we allow address mapping,
172  * automatic bcc, header/body checks?
173  */
174int     pickup_input_transp_mask;
175
176/* file_read_error - handle error while reading queue file */
177
178static int file_read_error(PICKUP_INFO *info, int type)
179{
180    msg_warn("uid=%ld: unexpected or malformed record type %d",
181	     (long) info->st.st_uid, type);
182    return (REMOVE_MESSAGE_FILE);
183}
184
185/* cleanup_service_error_reason - handle error writing to cleanup service. */
186
187static int cleanup_service_error_reason(PICKUP_INFO *info, int status,
188					        const char *reason)
189{
190
191    /*
192     * XXX If the cleanup server gave a reason, then it was already logged.
193     * Don't bother logging it another time.
194     *
195     * XXX Discard a message without recipient. This can happen with "postsuper
196     * -r" when a message is already delivered (or bounced). The Postfix
197     * sendmail command rejects submissions without recipients.
198     */
199    if (reason == 0 || *reason == 0)
200	msg_warn("%s: error writing %s: %s",
201		  info->path, info->id, cleanup_strerror(status));
202    return ((status & (CLEANUP_STAT_BAD | CLEANUP_STAT_RCPT)) ?
203	    REMOVE_MESSAGE_FILE : KEEP_MESSAGE_FILE);
204}
205
206#define cleanup_service_error(info, status) \
207	cleanup_service_error_reason((info), (status), (char *) 0)
208
209/* copy_segment - copy a record group */
210
211static int copy_segment(VSTREAM *qfile, VSTREAM *cleanup, PICKUP_INFO *info,
212			        VSTRING *buf, char *expected)
213{
214    int     type;
215    int     check_first = (*expected == REC_TYPE_CONTENT[0]);
216    int     time_seen = 0;
217    char   *attr_name;
218    char   *attr_value;
219    char   *saved_attr;
220    int     skip_attr;
221
222    /*
223     * Limit the input record size. All front-end programs should protect the
224     * mail system against unreasonable inputs. This also requires that we
225     * limit the size of envelope records written by the local posting agent.
226     *
227     * Records with named attributes are filtered by postdrop(1).
228     *
229     * We must allow PTR records here because of "postsuper -r".
230     */
231    for (;;) {
232	if ((type = rec_get(qfile, buf, var_line_limit)) < 0
233	    || strchr(expected, type) == 0)
234	    return (file_read_error(info, type));
235	if (msg_verbose)
236	    msg_info("%s: read %c %s", info->id, type, vstring_str(buf));
237	if (type == *expected)
238	    break;
239	if (type == REC_TYPE_FROM) {
240	    if (info->sender == 0)
241		info->sender = mystrdup(vstring_str(buf));
242	    /* Compatibility with Postfix < 2.3. */
243	    if (time_seen == 0)
244		rec_fprintf(cleanup, REC_TYPE_TIME, "%ld",
245			    (long) info->st.st_mtime);
246	}
247	if (type == REC_TYPE_TIME)
248	    time_seen = 1;
249
250	/*
251	 * XXX Workaround: REC_TYPE_FILT (used in envelopes) == REC_TYPE_CONT
252	 * (used in message content).
253	 *
254	 * As documented in postsuper(1), ignore content filter record.
255	 */
256	if (*expected != REC_TYPE_CONTENT[0]) {
257	    if (type == REC_TYPE_FILT)
258		/* Discard FILTER record after "postsuper -r". */
259		continue;
260	    if (type == REC_TYPE_RDR)
261		/* Discard REDIRECT record after "postsuper -r". */
262		continue;
263	}
264	if (*expected == REC_TYPE_EXTRACT[0]) {
265	    if (type == REC_TYPE_RRTO)
266		/* Discard return-receipt record after "postsuper -r". */
267		continue;
268	    if (type == REC_TYPE_ERTO)
269		/* Discard errors-to record after "postsuper -r". */
270		continue;
271	    if (type == REC_TYPE_ATTR) {
272		saved_attr = mystrdup(vstring_str(buf));
273		skip_attr = (split_nameval(saved_attr,
274					   &attr_name, &attr_value) == 0
275			     && rec_attr_map(attr_name) == 0);
276		myfree(saved_attr);
277		/* Discard other/header/body action after "postsuper -r". */
278		if (skip_attr)
279		    continue;
280	    }
281	}
282
283	/*
284	 * XXX Force an empty record when the queue file content begins with
285	 * whitespace, so that it won't be considered as being part of our
286	 * own Received: header. What an ugly Kluge.
287	 */
288	if (check_first
289	    && (type == REC_TYPE_NORM || type == REC_TYPE_CONT)) {
290	    check_first = 0;
291	    if (VSTRING_LEN(buf) > 0 && IS_SPACE_TAB(vstring_str(buf)[0]))
292		rec_put(cleanup, REC_TYPE_NORM, "", 0);
293	}
294	if ((REC_PUT_BUF(cleanup, type, buf)) < 0)
295	    return (cleanup_service_error(info, CLEANUP_STAT_WRITE));
296    }
297    return (0);
298}
299
300/* pickup_copy - copy message to cleanup service */
301
302static int pickup_copy(VSTREAM *qfile, VSTREAM *cleanup,
303		               PICKUP_INFO *info, VSTRING *buf)
304{
305    time_t  now = time((time_t *) 0);
306    int     status;
307    char   *name;
308
309    /*
310     * Protect against time-warped time stamps. Warn about mail that has been
311     * queued for an excessive amount of time. Allow for some time drift with
312     * network clients that mount the maildrop remotely - especially clients
313     * that can't get their daylight savings offsets right.
314     */
315#define DAY_SECONDS 86400
316#define HOUR_SECONDS 3600
317
318    if (info->st.st_mtime > now + 2 * HOUR_SECONDS) {
319	msg_warn("%s: message dated %ld seconds into the future",
320		 info->id, (long) (info->st.st_mtime - now));
321	info->st.st_mtime = now;
322    } else if (info->st.st_mtime < now - DAY_SECONDS) {
323	msg_warn("%s: message has been queued for %d days",
324		 info->id, (int) ((now - info->st.st_mtime) / DAY_SECONDS));
325    }
326
327    /*
328     * Add content inspection transport. See also postsuper(1).
329     */
330    if (*var_filter_xport)
331	rec_fprintf(cleanup, REC_TYPE_FILT, "%s", var_filter_xport);
332
333    /*
334     * Copy the message envelope segment. Allow only those records that we
335     * expect to see in the envelope section. The envelope segment must
336     * contain an envelope sender address.
337     */
338    if ((status = copy_segment(qfile, cleanup, info, buf, REC_TYPE_ENVELOPE)) != 0)
339	return (status);
340    if (info->sender == 0) {
341	msg_warn("%s: uid=%ld: no envelope sender",
342		 info->id, (long) info->st.st_uid);
343	return (REMOVE_MESSAGE_FILE);
344    }
345
346    /*
347     * For messages belonging to $mail_owner also log the maildrop queue id.
348     * This supports message tracking for mail requeued via "postsuper -r".
349     */
350#define MAIL_IS_REQUEUED(info) \
351    ((info)->st.st_uid == var_owner_uid && ((info)->st.st_mode & S_IROTH) == 0)
352
353    if (MAIL_IS_REQUEUED(info)) {
354	msg_info("%s: uid=%d from=<%s> orig_id=%s", info->id,
355		 (int) info->st.st_uid, info->sender,
356		 ((name = strrchr(info->path, '/')) != 0 ?
357		  name + 1 : info->path));
358    } else {
359	msg_info("%s: uid=%d from=<%s>", info->id,
360		 (int) info->st.st_uid, info->sender);
361    }
362
363    /*
364     * Message content segment. Send a dummy message length. Prepend a
365     * Received: header to the message contents. For tracing purposes,
366     * include the message file ownership, without revealing the login name.
367     */
368    rec_fputs(cleanup, REC_TYPE_MESG, "");
369    rec_fprintf(cleanup, REC_TYPE_NORM, "Received: by %s (%s, from userid %ld)",
370		var_myhostname, var_mail_name, (long) info->st.st_uid);
371    rec_fprintf(cleanup, REC_TYPE_NORM, "\tid %s; %s", info->id,
372		mail_date(info->st.st_mtime));
373
374    /*
375     * Copy the message content segment. Allow only those records that we
376     * expect to see in the message content section.
377     */
378    if ((status = copy_segment(qfile, cleanup, info, buf, REC_TYPE_CONTENT)) != 0)
379	return (status);
380
381    /*
382     * Send the segment with information extracted from message headers.
383     * Permit a non-empty extracted segment, so that list manager software
384     * can to output recipients after the message, and so that sysadmins can
385     * re-inject messages after a change of configuration.
386     */
387    rec_fputs(cleanup, REC_TYPE_XTRA, "");
388    if ((status = copy_segment(qfile, cleanup, info, buf, REC_TYPE_EXTRACT)) != 0)
389	return (status);
390
391    /*
392     * There are no errors. Send the end-of-data marker, and get the cleanup
393     * service completion status. XXX Since the pickup service is unable to
394     * bounce, the cleanup service can report only soft errors here.
395     */
396    rec_fputs(cleanup, REC_TYPE_END, "");
397    if (attr_scan(cleanup, ATTR_FLAG_MISSING,
398		  ATTR_TYPE_INT, MAIL_ATTR_STATUS, &status,
399		  ATTR_TYPE_STR, MAIL_ATTR_WHY, buf,
400		  ATTR_TYPE_END) != 2)
401	return (cleanup_service_error(info, CLEANUP_STAT_WRITE));
402
403    /*
404     * Depending on the cleanup service completion status, delete the message
405     * file, or try again later. Bounces are dealt with by the cleanup
406     * service itself. The master process wakes up the cleanup service every
407     * now and then.
408     */
409    if (status) {
410	return (cleanup_service_error_reason(info, status, vstring_str(buf)));
411    } else {
412	return (REMOVE_MESSAGE_FILE);
413    }
414}
415
416/* pickup_file - initialize for file copy and cleanup */
417
418static int pickup_file(PICKUP_INFO *info)
419{
420    VSTRING *buf = vstring_alloc(100);
421    int     status;
422    VSTREAM *qfile;
423    VSTREAM *cleanup;
424    int     cleanup_flags;
425
426    /*
427     * Open the submitted file. If we cannot open it, and we're not having a
428     * file descriptor leak problem, delete the submitted file, so that we
429     * won't keep complaining about the same file again and again. XXX
430     * Perhaps we should save "bad" files elsewhere for further inspection.
431     * XXX How can we delete a file when open() fails with ENOENT?
432     */
433    qfile = safe_open(info->path, O_RDONLY | O_NONBLOCK, 0,
434		      (struct stat *) 0, -1, -1, buf);
435    if (qfile == 0) {
436	if (errno != ENOENT)
437	    msg_warn("open input file %s: %s", info->path, vstring_str(buf));
438	vstring_free(buf);
439	if (errno == EACCES)
440	    msg_warn("if this file was created by Postfix < 1.1, then you may have to chmod a+r %s/%s",
441		     var_queue_dir, info->path);
442	return (errno == EACCES ? KEEP_MESSAGE_FILE : REMOVE_MESSAGE_FILE);
443    }
444
445    /*
446     * Contact the cleanup service and read the queue ID that it has
447     * allocated. In case of trouble, request that the cleanup service
448     * bounces its copy of the message. because the original input file is
449     * not readable by the bounce service.
450     *
451     * If mail is re-injected with "postsuper -r", disable Milter applications.
452     * If they were run before the mail was queued then there is no need to
453     * run them again. Moreover, the queue file does not contain enough
454     * information to reproduce the exact same SMTP events and Sendmail
455     * macros that Milters received when the mail originally arrived in
456     * Postfix.
457     *
458     * The actual message copying code is in a separate routine, so that it is
459     * easier to implement the many possible error exits without forgetting
460     * to close files, or to release memory.
461     */
462    cleanup_flags =
463	input_transp_cleanup(CLEANUP_FLAG_BOUNCE | CLEANUP_FLAG_MASK_EXTERNAL,
464			     pickup_input_transp_mask);
465    /* As documented in postsuper(1). */
466    if (MAIL_IS_REQUEUED(info))
467	cleanup_flags &= ~CLEANUP_FLAG_MILTER;
468
469    cleanup = mail_connect_wait(MAIL_CLASS_PUBLIC, var_cleanup_service);
470    if (attr_scan(cleanup, ATTR_FLAG_STRICT,
471		  ATTR_TYPE_STR, MAIL_ATTR_QUEUEID, buf,
472		  ATTR_TYPE_END) != 1
473	|| attr_print(cleanup, ATTR_FLAG_NONE,
474		      ATTR_TYPE_INT, MAIL_ATTR_FLAGS, cleanup_flags,
475		      ATTR_TYPE_END) != 0) {
476	status = KEEP_MESSAGE_FILE;
477    } else {
478	info->id = mystrdup(vstring_str(buf));
479	status = pickup_copy(qfile, cleanup, info, buf);
480    }
481    vstream_fclose(qfile);
482    vstream_fclose(cleanup);
483    vstring_free(buf);
484    return (status);
485}
486
487/* pickup_init - init info structure */
488
489static void pickup_init(PICKUP_INFO *info)
490{
491    info->id = 0;
492    info->path = 0;
493    info->sender = 0;
494}
495
496/* pickup_free - wipe info structure */
497
498static void pickup_free(PICKUP_INFO *info)
499{
500#define SAFE_FREE(x) { if (x) myfree(x); }
501
502    SAFE_FREE(info->id);
503    SAFE_FREE(info->path);
504    SAFE_FREE(info->sender);
505}
506
507/* pickup_service - service client */
508
509static void pickup_service(char *unused_buf, int unused_len,
510			           char *unused_service, char **argv)
511{
512    SCAN_DIR *scan;
513    char   *queue_name;
514    PICKUP_INFO info;
515    const char *path;
516    char   *id;
517    int     file_count;
518
519    /*
520     * Sanity check. This service takes no command-line arguments.
521     */
522    if (argv[0])
523	msg_fatal("unexpected command-line argument: %s", argv[0]);
524
525    /*
526     * Skip over things that we don't want to open, such as files that are
527     * still being written, or garbage. Leave it up to the sysadmin to remove
528     * garbage. Keep scanning the queue directory until we stop removing
529     * files from it.
530     *
531     * When we find a file, stroke the watchdog so that it will not bark while
532     * some application is keeping us busy by injecting lots of mail into the
533     * maildrop directory.
534     */
535    queue_name = MAIL_QUEUE_MAILDROP;		/* XXX should be a list */
536    do {
537	file_count = 0;
538	scan = scan_dir_open(queue_name);
539	while ((id = scan_dir_next(scan)) != 0) {
540	    if (mail_open_ok(queue_name, id, &info.st, &path) == MAIL_OPEN_YES) {
541		pickup_init(&info);
542		info.path = mystrdup(path);
543		watchdog_pat();
544		if (pickup_file(&info) == REMOVE_MESSAGE_FILE) {
545		    if (REMOVE(info.path))
546			msg_warn("remove %s: %m", info.path);
547		    else
548			file_count++;
549		}
550		pickup_free(&info);
551	    }
552	}
553	scan_dir_close(scan);
554    } while (file_count);
555}
556
557/* post_jail_init - drop privileges */
558
559static void post_jail_init(char *unused_name, char **unused_argv)
560{
561
562    /*
563     * In case master.cf was not updated for unprivileged service.
564     */
565    if (getuid() != var_owner_uid)
566	set_ugid(var_owner_uid, var_owner_gid);
567
568    /*
569     * Initialize the receive transparency options: do we want unknown
570     * recipient checks, do we want address mapping.
571     */
572    pickup_input_transp_mask =
573	input_transp_mask(VAR_INPUT_TRANSP, var_input_transp);
574}
575
576MAIL_VERSION_STAMP_DECLARE;
577
578/* main - pass control to the multi-threaded server skeleton */
579
580int     main(int argc, char **argv)
581{
582    static const CONFIG_STR_TABLE str_table[] = {
583	VAR_FILTER_XPORT, DEF_FILTER_XPORT, &var_filter_xport, 0, 0,
584	VAR_INPUT_TRANSP, DEF_INPUT_TRANSP, &var_input_transp, 0, 0,
585	0,
586    };
587
588    /*
589     * Fingerprint executables and core dumps.
590     */
591    MAIL_VERSION_STAMP_ALLOCATE;
592
593    /*
594     * Use the multi-threaded skeleton, because no-one else should be
595     * monitoring our service socket while this process runs.
596     *
597     * XXX The default watchdog timeout for trigger servers is 1000s, while the
598     * cleanup server watchdog timeout is $daemon_timeout (i.e. several
599     * hours). We override the default 1000s timeout to avoid problems with
600     * slow mail submission. The real problem is of course that the
601     * single-threaded pickup server is not a good solution for mail
602     * submissions.
603     */
604    trigger_server_main(argc, argv, pickup_service,
605			MAIL_SERVER_STR_TABLE, str_table,
606			MAIL_SERVER_POST_INIT, post_jail_init,
607			MAIL_SERVER_SOLITARY,
608			MAIL_SERVER_WATCHDOG, &var_daemon_timeout,
609			0);
610}
611