Configuring a mail server on FreeBSD

This is a quick walk-through of how to configure a mail system using FreeBSD, Sendmail, SMTP AUTH with SSL.

Configuring the central mail server

 * In the DNS, name the mail server greendragon.hobbiton.org, then point the MX record for hobbiton.org at greendragon.hobbiton.org.


 * In /etc/mail/freebsd.mc, after DOMAIN(generic), add:

FEATURE(`nouucp', 'reject')dnl MASQUERADE_AS(`hobbiton.org')dnl Change From addresses from hostname to hobbiton.org. FEATURE(`masquerade_envelope')dnl Also change Return-Path addresses. FEATURE(`accept_unresolvable_domains')dnl Many people say this feature is a bad idea; see note. Cw hobbiton.org Cw devpit.org

Note: Don't use allmasquerade since that will change To-addresses for devpit.org to hobbiton.org. Unfortunately, this means that mail from cron etc will be addressed from hobbiton.org to greendragon.hobbiton.org. XXX: There's probably a knob to fix this.


 * You want to use maildir, so install mail/procmail. Then create /usr/local/etc/procmailrc:

MAILDIR=$HOME/.maildir ORIGMAIL=$HOME/.maildir/ DEFAULT=$ORIGMAIL DROPPRIVS=1 VERBOSE=on LOGFILE=$HOME/.procmail.log INCLUDERC=$HOME/.procmailrc :0 ./
 * 1) Let the user filter or divert the email to another folder.
 * 1) Default delivery into INBOX.


 * For procmail, in /etc/mail/freebsd.mc, remove FEATURE(local_lmtp) and add:

FEATURE(`local_procmail')dnl


 * Rebuild the mail config:

cd /etc/mail rm -iv `hostname`* make make install /etc/rc.d/sendmail restart

FEATURE(`accept_unresolvable_domains')
Many people don't recommend using this feature, citing spam. It would seem, however, that spammers simply use domains in their from-addresses that exist. On the other hand, requiring resolution will unnecessarily delay or reject legitimate mail when there is a configuration error or broken network link. Moreover, this will happen at a time when automated diagnostic messages about system problems are most useful. It will also cause queuing resources to be used unnecessarily.

If anyone can explain how this tangibly reduces spam, please elaborate here.

SSL and SASL

 * Install security/cyrus-sasl2 and security/cyrus-sasl2-saslauthd. You must do this first so that Sendmail can link to Cyrus-SASL when you rebuild it.


 * Add to /usr/local/lib/sasl2/Sendmail.conf:

pwcheck_method: saslauthd


 * Add to /etc/rc.conf:

saslauthd_enable="YES"


 * Start saslauthd:

/usr/local/etc/rc.d/saslauthd start


 * Add to /etc/make.conf:

SENDMAIL_CFLAGS=-I/usr/local/include/sasl -DSASL SENDMAIL_LDFLAGS=-L/usr/local/lib SENDMAIL_LDADD=-lsasl2 SENDMAIL_CFLAGS+= -D_FFR_SMTP_SSL
 * 1) For SASL:
 * 1) For SSL:


 * Rebuild and reinstall world. Or to save a *lot* of time, just rebuild Sendmail instead:


 * 1) cd /usr/src/lib/libsmutil
 * 2) make cleandir && make obj && make
 * 3) cd /usr/src/lib/libsm
 * 4) make cleandir && make obj && make
 * 5) cd /usr/src/usr.sbin/sendmail
 * 6) make cleandir && make obj && make && make install


 * Add this to /etc/mail/freebsd.mc after the section you added at the beginning:

dnl SASL options TRUST_AUTH_MECH(`GSSAPI DIGEST-MD5 CRAM-MD5 LOGIN')dnl define(`confAUTH_MECHANISMS', `GSSAPI DIGEST-MD5 CRAM-MD5 LOGIN')dnl dnl SSL options define(`confCACERT_PATH', `/project/ssl/hobbiton.org/')dnl define(`confCACERT', `/project/ssl/hobbiton.org/gd_bundle.crt')dnl define(`confSERVER_CERT', `/project/ssl/hobbiton.org/hobbiton.org.crt')dnl define(`confSERVER_KEY', `/project/ssl/hobbiton.org/hobbiton.org.key')dnl DAEMON_OPTIONS(`Port=smtps, Name=TLSMTA, M=s')dnl

Note: Some docs specify another DAEMON_OPTIONS line. Don't; it will cause errors. There is already a default for Port=smtp.

Note: These directions are for a certificate purchased from Godaddy. To get gd_bundle.crt, tell them you're running Apache. Self-signed certificates will work too, with warnings.


 * Rebuild the mail config:

cd /etc/mail rm -iv `hostname`* make make install /etc/rc.d/sendmail restart

Configuring nonmail servers
For servers that only send mail, such as for cron jobs, web services, etc, the easiest configuration is to tell them to spool mail locally. This is actually the default, but you'll want to tweak the configuration to use www@hobbiton.org as the from address instead of www@ivybush.hobbiton.org.


 * Edit /etc/freebsd.submit.mc. After the VERSIONID line, add:

FEATURE(`nouucp', 'reject')dnl MASQUERADE_AS(`hobbiton.org')dnl Change From addresses from hostname to hobbiton.org. FEATURE(`masquerade_envelope')dnl Also change Return-Path addresses. FEATURE(`allmasquerade')dnl Also change To addresses.

Many people prefer to configure these sorts of machines to relay mail through the central server rather than directly spooling it to receiving servers. This is beyond our scope of basic configuration, but has several benefits. This makes SPF records more succinct, centralizes logging, and eliminates the requirement that these nodes be online at all times to retry mail delivery. If you do this, don't forget to somehow configure the central server to relay mail from these machines. A simple approach is IP-based authentication. A more robust one is to configure these machines with an SSL certificate using confCLIENT_CERT and confCLIENT_KEY.

IP-based graylisting and blacklisting
Spamd fits easily into this for graylisting and blacklisting. Spamd docs are easy to find, and the configuration has no impact on the rest of the mail system.

Filtering
Dspam fits snugly into a procmail recipe. To use it for all users, add it to /usr/local/etc/procmailrc. To use it in an opt-in fashion, add it to ~/.procmailrc. Because users need to train it interactively to prevent it from classifying messages entirely at random, opting in usually makes more sense.

Spam Assasin also fits snugly into procmail, and needs no training.

For example, to run dspam, create ~/.procmailrc:

.Spam.unfiltered/ :0fw | /usr/local/bin/dspam --deliver=innocent,spam --stdout :0 * ^X-DSPAM-Result: Spam$ .Spam/
 * 1) Back up all incoming mail in unmodified form in case something goes terribly
 * 2) wrong.
 * 1) Run dspam to add classification headers to the message.
 * 1) Redirect spam into Spam folder.

Then write cron jobs to maintain Spam.ham and Spam.missed folders for retraining.

To forward mail for an account
Create ~user/.procmailrc:



Note: Forwarding mail is less advisable than fetching mail from the other side. Forwarding mail runs a high risk of causing back-scatter from spam.

IMAP
Dovecot is a pretty good imap server that will work well with this arrangement. Others will work too. Since IMAP is outside the mail pipeline, installing it is pretty easy.