Secure SMTP AUTH over SSL/STARTTLS with Sendmail and Cyrus SASL,
and secure IMAP server Howto

by Marion Bates <mbates@whoopis.com>

NOTE: Major update to this howto posted July 6, 2004 regarding SASLv2.

Those of us who run multipurpose servers are probably familiar with the conundrum of what to do about clients who want to use your machine as their primary mail server. It would be easy if everybody had a static IP address, but more likely they have dynamic IPs through a cable modem or dialup account. If you want to allow them to use your SMTP server for their outbound mail, then you have to either maintain an annoying list of their IPs in your access file to allow relaying, and you have to edit that file as needed when they change ISPs or go to their school/office network, or you can simply allow your server to relay mail for anyone; of course, this latter option is easier for you, but you are now a portal for any and all spam. Even if you don't care about being a "good netizen," this also puts you at risk for having your domain added to blacklists, thus hampering your overall email capability.

Here, I will outline an alternative, which allows all of your users to relay mail through your server from anywhere, but which still prevents you from being an open spam relay. This is achieved via the use of SMTP-AUTH, which requires users to authenticate with their username and password before they can send email through your server. This means that your valid users will be able to use your server from anywhere, regardless of whether or not their IPs are in the access list, as long as their mail clients support SMTP-AUTH (which most now do). For added security, we'll enable SSL also, so the login/password and the session can take place over an encrypted layer if users so desire. The addendum at the end describes how to enable secure IMAP (which is far simpler!).


Shortcut to sections:
Step 1 -- backup key files
Step 2 -- install packages to satisfy dependencies; install rpm-build IF you are rebuilding source RPMs; explanation of source RPM tree
Step 3 -- build/install cyrus-sasl. If you're not rebuilding source RPMs, just skip to the red capital "ADDENDUM" in that step.
Step 4 -- build/install sendmail. If you're not rebuilding source RPMs, just skip to the last two lines (i.e. just install the basic RPMs for your version of Linux.)
Step 5 -- verify sendmail to make sure it's compiled with the options we need.
Step 6 -- edit sendmail.mc to add/modify the lines for AUTH and STARTTLS.
Step 7 -- generate certificates.
Step 8 -- recreate sendmail.cf and restart the sendmail daemon; test by hand.
Step 9 -- really test, with a real mail client.
Troubleshooting -- symptoms and fixes for various common mail clients.
IMAP over SSL -- secure IMAP. Easy.
References

Mandrake 10.0 users -- minor fixes you'll need to perform.


NOTE: If you already have RedHat version 8 or higher, or Mandrake version 10.0 or higher, this is much simpler...just do Step 1 (backups), then install the current versions of cyrus-sasl for your system (see addendum in Step 3) and of course install current sendmail and sendmail-cf RPMs, then go to Step 5 and onward. You may need to install some packages to satisfy dependencies -- in that case, refer to the file list in Step 2, but get the current versions. You shouldn't need to rebuild anything from source RPMs, that lengthy process only applies to RH 7 users.

RedHat 9: This procedure works with RH 9 as well. Gerardo Luna (gluna_AT_geer-it-solutions.com) writes the following:

"I installed RedHat 9.0 out of the box (of course it is now hardened), downloaded the security fixes for sendmail that come with RedHat 9.0, followed the steps from your tutorial as if I were installing on RedHat 8.0 and it worked great. My mail client is Outlook Express 6.00.26 and I am using Windows XP Pro."

RedHat Enterprise: Also from Gerardo Luna:

"Just to let you know that your tutorial from ssl and sendmail, works perfectly fine with red hat enterprise edition 3.1 using sendmail version 8.12.11-3 with outlook 2003, outlook express using windows xp. I followed the same steps I mentioned when I installed it on red hat 9.

I am also using it along with the mailscanner (http://www.sng.ecs.soton.ac.uk/mailscanner/) which works perfectly fine and mcafee for linux, f-prot and bitdefender for linux."

Mandrake 10.0: (major thanks to Simon Lewis) Largely the same as for RedHat 8 and higher, but with a few fixes to the Mandrake installation defaults:


Intro. I did this on RedHat 7.3, from RedHat RPMs, several of which I built from RH 8.0 source RPMs in order to get the newer versions of things. An explanation of source RPMs is beyond the scope of this document, but the References section at the end has links to SRPM info. Suffice it to say here that the point was, I wanted sendmail 8.12, but I didn't want to upgrade to RH 8.0 just to get it, and the newest version in the stock RH 7.3 downloads department was 8.11. I could've gone elsewhere (like RawHide) to get a sendmail 8.12 RPM for RedHat 7.3, but I wanted to deviate as little as possible from the stock RH setup, so I elected to use RH 8 rpms but rebuild and install them on my RH 7.3 machine. That may be rather insane.

You will need to be root for most of these steps.

STEP 1: BACKUP. Before doing anything else, back up all your sendmail configuration files! Some of these may be under /etc rather than /etc/mail. To find out, type

 
sendmail -d0.20 -bv | grep sendmail.cf 
You should get output similar to one or more of these:
 
Conf file: /etc/mail/sendmail.cf (default for MTA) 
Conf file: /etc/mail/sendmail.cf (selected) 
Def Conf file: /etc/sendmail.cf 

Make copies of these files and put them in a safe place, like /root.

 
/etc/mail/sendmail.cf 
/etc/mail/sendmail.mc if it exists 
/etc/mail/access
/etc/mail/virtusertable 
/etc/aliases 

STEP 2: Installing everything you need. Somewhere along the way in this process, I had to stop and install about a trillion packages to satisfy dependencies. So let's start there. These are listed in no particular order, and some may have to be installed before others. Some satisfy dependencies needed for building the new sendmail rpm, whereas others are required for building and installing the new version of cyrus-sasl. Paths shown for convenience, adjust accordingly for your download mirror of choice.

Be sure to install the rpm-build package before you install source RPMs, so it creates the proper directory structure under /usr/src:

 
/usr/src/redhat 
/usr/src/redhat/BUILD 
/usr/src/redhat/RPMS
/usr/src/redhat/RPMS/athlon 
/usr/src/redhat/RPMS/i386 
/usr/src/redhat/RPMS/i486
/usr/src/redhat/RPMS/i586 
/usr/src/redhat/RPMS/i686 
/usr/src/redhat/RPMS/noarch
/usr/src/redhat/SOURCES 
/usr/src/redhat/SPECS 
/usr/src/redhat/SRPMS 

Partial explanation of the components of this hierarchy:

/usr/src/redhat 
Top of the directory hierarchy where RedHat SRPMS will place spec and source files.
 
/usr/src/redhat/BUILD 
Where the actual source tarball will be unpacked, altered, and compiled by the RPM build process.
 
/usr/src/redhat/RPMS/i386 
Where the finished RPMs will go. You can then install them on your system like any stock RPM from RedHat. The number may be different, e.g. i686, athlon, or noarch, depending on your architecture and build settings.
 
/usr/src/redhat/SOURCES 
Where the source tar files, patch files, and configuration files go -- all the things that RPM does to the source before actually compiling it, to tweak it for RedHat Linux.
 
/usr/src/redhat/SPECS 
Where spec files go -- spec files are scripts that tell rpmbuild how to unpack the tarball, apply the source files, compile the program, create the RPM with the right settings for where to install the actual binaries, etc.
 
/usr/src/redhat/SRPMS 
Where the resulting source RPMs go after you build from source RPM. Sounds self-referential, eh? :) Any changes you make to the original SRPM's source files or specfile will be reflected within this new source RPM, and under the terms of the GPL, you can now distribute your source and binary RPMs freely.

Here are the packages I had to install to make everything happy.
From the main RedHat 7.3 area:

pub/redhat/linux/7.3/en/os/i386/RedHat/RPMS/rpm-build-4.0.4-7x.18.i386.rpm
pub/redhat/linux/7.3/en/os/i386/RedHat/RPMS/m4-1.4.1-7.i386.rpm

pub/redhat/linux/7.3/en/os/i386/RedHat/RPMS/gdbm-1.8.0-14.i386.rpm
pub/redhat/linux/7.3/en/os/i386/RedHat/RPMS/gdbm-devel-1.8.0-14.i386.rpm

pub/redhat/linux/7.3/en/os/i386/RedHat/RPMS/hesiod-3.0.2-18.i386.rpm
pub/redhat/linux/7.3/en/os/i386/RedHat/RPMS/hesiod-devel-3.0.2-18.i386.rpm

pub/redhat/linux/7.3/en/os/i386/RedHat/RPMS/autoconf253-2.53-3.noarch.rpm

pub/redhat/linux/7.3/en/os/i386/RedHat/RPMS/automake15-1.5-2.noarch.rpm

pub/redhat/linux/7.3/en/os/i386/RedHat/RPMS/libtool-1.4.2-7.i386.rpm 

From the RedHat 7.3 updates area:

pub/redhat/linux/updates/7.3/en/os/i386/openldap-2.0.27-2.7.3.i386.rpm
pub/redhat/linux/updates/7.3/en/os/i386/openldap-devel-2.0.27-2.7.3.i386.rpm

pub/redhat/linux/updates/7.3/en/os/i386/openssl-0.9.6b-32.7.i386.rpm
pub/redhat/linux/updates/7.3/en/os/i386/openssl-perl-0.9.6b-32.7.i386.rpm
pub/redhat/linux/updates/7.3/en/os/i386/openssl-devel-0.9.6b-32.7.i386.rpm

pub/redhat/linux/updates/7.3/en/os/i386/krb5-libs-1.2.4-11.i386.rpm
pub/redhat/linux/updates/7.3/en/os/i386/krb5-devel-1.2.4-11.i386.rpm

pub/redhat/linux/updates/7.3/en/os/i386/pam-0.75-46.7.3.i386.rpm
pub/redhat/linux/updates/7.3/en/os/i386/pam-devel-0.75-46.7.3.i386.rpm 

And from RedHat 8:

pub/redhat/linux/8.0/en/os/i386/RedHat/RPMS/db4-4.0.14-14.src.rpm
pub/redhat/linux/8.0/en/os/i386/RedHat/RPMS/db4-devel-4.0.14-14.i386.rpm 

STEP 3: Build and install cyrus-sasl. If you want to allow other authentication mechanisms (e.g. mechs based on MD5), then you will also need cyrus SASL, which like Sendmail 8.12 requires rebuilding from the RedHat 8.0 SRPM. NOTE Actually, with newer Linuxes and sendmails, it appears that cyrus-sasl (version 2) is essential for ANY kind of SMTP AUTH. Anyway, get the source rpm from

 
pub/redhat/linux/8.0/en/os/i386/SRPMS/cyrus-sasl-2.1.7-2.src.rpm 

And install it by typing

 
rpm -i cyrus-sasl-2.1.7-2.src.rpm 

Because this is a source rpm and not a standard binary package, this does not actually put cyrus-sasl on your system; rather, it installs the spec file and sources (patches, the actual tarball, maybe some config files, etc.) under /usr/src/redhat/ in preparation for you to alter and/or rebuild the "real" binary RPMS for your system.

Assuming you've got all the dependencies satisfied, there is one last thing to do before you build cyrus-sasl. You may not need to do this, but I had to.

cd /usr/src/redhat/SPECS and edit the cyrus-sasl.spec file. Find the line that says:

 
BuildPrereq: autoconfxxx, automake15, libtool 
and change the 3-digit version number (represented by xxx) such that the autoconf version listed there matches what you've got installed. In my case:
 
bash-2.05a# rpm -qa | grep autoconf autoconf253-2.53-3 

So I changed the specfile line to:

 
BuildPrereq: autoconf253, automake15, libtool 

Save and exit. Now do the following (substitute different architecture number under RPMS if needed):

 
rpm -ba cyrus-sasl.spec 
cd ../RPMS/i386 
rpm -Uvh cyrus-sasl*.rpm 
This will install:
 
cyrus-sasl-2.1.7-2 
cyrus-sasl-gssapi-2.1.7-2 
cyrus-sasl-plain-2.1.7-2
cyrus-sasl-devel-2.1.7-2 
cyrus-sasl-md5-2.1.7-2 

You may not need or want all of these -- but if you have them, you've got more flexibility regarding authentication mechanisms.

ADDENDUM: Things have changed with SASL since I wrote this. Here's the lowdown for SASL2:

Install main sasl daemon etc. plus main libs:

cyrus-sasl-2.whatever.rpm
libsasl2-2.whatever.rpm

Install libsasl2 PLUGINS of your choice, at a minimum these two:

libsasl2-plug-login-2.whatever.rpm 
libsasl2-plug-plain-2.whatever.rpm 

I also installed these, but am not sure I'm using them at all:

libsasl2-plug-digestmd5-2.1.15-10mdk.i586.rpm 
libsasl2-plug-gssapi-2.1.15-10mdk.i586.rpm 

Crank up the daemon if it's not running already:

service saslauthd start

STEP 4: Build and install sendmail. WHEW! Okay...NOW, we can finally attempt to build the sendmail RPM. You shouldn't need to change anything in the specfile like we did for cyrus-sasl -- you are just taking the stock RedHat 8.0 source RPM and rebuilding it to install under RedHat 7.3.

Download the sendmail source RPM from a RedHat mirror. At the time of this writing, you can get the one I used here:

/pub/mirrors/ftp.redhat.com/pub/redhat/linux/updates/8.0/en/os/SRPMS/sendmail-8.12.8-1.80.src.rpm 

Install it by typing

 
rpm -i sendmail-8.12.8-1.80.src.rpm 

Go to /usr/src/redhat/SPECS and type

 
rpm -ba sendmail.spec 

If it succeeds without any errors, you should now have a nice new sendmail 8.12 RPM for RedHat 7.3.

Note: Alternatively, you can simply type

 
rpm --rebuild sendmail-8.12.8-1.80.src.rpm 

This combines the two steps shown above, and the only difference is that it does not generate a new source RPM because it assumes you're not changing anything in the original source RPM, which in this case is correct. (We didn't want to do this shortcut for cyrus-sasl, because we had to edit the spec file.)

Actually install it:

 
cd ../RPMS/i386 
rpm -Uvh sendmail-8.12.8-1.80.i386.rpm 
rpm -Uvh sendmail-cf-8.12.8-1.80.i386.rpm 

STEP 5: Verify sendmail. If all goes well, you should now have sendmail 8.12.8 running on your server! (You may also want to install the sendmail-cf, sendmail-docs, and sendmail-devel packages, all under the same RPMS/i386 directory.) You can check to ensure that this version includes the options we need, by typing:

 
bash-2.05a# sendmail -d0.1 -bv 

The output will look something like this:

 
Version 8.12.8 
Compiled with: DNSMAP HESIOD HES_GETMAILHOST LDAPMAP LOG
MAP_REGEX MATCHGECOS MILTER MIME7TO8 MIME8TO7 NAMED_BIND NETINET NETINET6
NETUNIX NEWDB NIS PIPELINING SASL SCANF STARTTLS TCPWRAPPERS USERDB
USE_LDAP_INIT

============ SYSTEM IDENTITY (after readcf) ============ 
	(short domain name) $w = domain 
	(canonical domain name) $j = domain.com 
	(subdomain name) $m = com
	(node name) $k = domain.com
========================================================

Recipient names must be specified 

In the "compiled with" block, look for "SASL" and "STARTTLS". If either one is missing, there is a problem... :(

Okay NOW we should be finished with packages for awhile. Maybe this is a good time to explain why we went to all the trouble to build RH 8 packages, rather than simply use the current sendmail RPMs for RH 7.3. The reason is that starting with sendmail 8.12, the two compile-time options we need -- SASL and STARTTLS -- are included by default in the RedHat RPM. Also, there is some change with regard to the use of crypto libraries, apparently it's better in 8.12 than in prior versions. Another reason: I originally tried to alter and rebuild the RH 7.3 sendmail 8.11 source RPM to include these options, but no matter what, it refused to compile, so I eventually gave up on that approach. But even if I were successful, the next time redcarpet/RHN ran and "upgraded" Sendmail using stock upgrade packages, it would hose my changes. Better to go to a newer version altogether, rather than hack the old version in such a way that no other human or machine knows that it's different from the stock RPM. :)

NOTE: Regarding the rebuilding of the RH 7.3 Sendmail 8.11 source RPM, David Jao <scythe at dominia.org> writes:


"I tried this too, and at first it wouldn't compile. Then I found out that sendmail 8.11 requires sfio (http://www.research.att.com/sw/tools/sfio/) in order to build with STARTTLS support. Sendmail 8.12 does not require sfio. Since all the howtos on the 'net are for version 8.12, it took me quite a long time to figure out this error.

So I installed sfio-1999 from rpmfind.net. Then I added the following lines to sendmail-8.11.0-redhat.patch from the 8.11 src.rpm:

APPENDDEF(`confENVDEF', `-DSFIO')
APPENDDEF(`confLIBS', `-lsfio')
APPENDDEF(`conf_sendmail_ENVDEF', `-DSTARTTLS')
APPENDDEF(`conf_sendmail_LIBS', `-lssl -lcrypto')
APPENDDEF(`confINCDIRS', `-I/usr/include -I/usr/include/sfio')
APPENDDEF(`confLIBDIRS', `-L/usr/lib')

and rebuilt the src.rpm, and it worked. This very email message is being sent through smtp-auth over TLS on redhat 7.3 using the 8.11.6-25.73 rpm with the above changes.

I don't use red carpet or redhat network, so I have to patch the sendmail rpm again every time redhat updates it. RHN users will probably find that upgrading to rh8/9 is an easier solution :) "

Another important thing to note: What happens when red-carpet notices that your version of sendmail does not match the standard RH 7.3 subscribed channel? From William Stearns: "Redcarpet won't notice; it sees you have a sendmail, and when a new version comes out in your subscribed channel, it'll compare version numbers. Your version will always be higher than anything in rh73, which sounds good, but keep in mind that if a crucial bugfix comes out, your self compiled package will never be upgraded. In short, just like software compiled from source with no rpm packaging, the administrator needs to upgrade by hand if an upgrade comes out."

STEP 6: Edit sendmail.mc. Now, we've got a version of sendmail with the compile-time options we need to enable AUTH and SSL. But we still have to specify all that in the sendmail config file. Since sendmail.cf is unintelligible to all normal living things, we will use the sendmail-cf and m4 packages so we can edit the slightly less user-hostile sendmail.mc (macro) file and use it to generate sendmail.cf.

The sendmail RPM ought to not overwrite your old sendmail.cf (and sendmail.mc, if you already had one). It should instead create sendmail.cf.rpmnew and sendmail.mc.rpmnew respectively. If you had made a lot of changes to your old sendmail configs, then you will need to merge them into the new one created by the RPM installation, and I hope you have enough food and water to survive. :) The only change I had made was removing the 127.0.0.1 portion of the MTA line such that other machines can relay mail, not just localhost; the rest of these changes are about SSL and AUTH.

Note: I did not ADD any lines to sendmail.mc, I only uncommented lines that were already included in the mc file. (Except that, later, I did add lines. See next note below.)

Edit sendmail.mc and uncomment (delete "dnl " as needed). You'll be happier if you use an editor with sendmail-savvy syntax highlighting, since you will know right away if a line is being interpreted as a comment or not. When finished, your file ought to look like the one shown below. The inline explanations in the conf file are pretty good; the only part where I had trouble was the "dnl define(`confAUTH_OPTIONS', `A p')dnl" line. Leave that line commented out unless you know you want to use some other login mechanism besides etc/shadow passwords; if you invoke that line, keep in mind that many clients won't work -- notably, some versions of Outlook require PLAIN to be available, and activating that conf line will prevent those users from logging in.

My modified sendmail.mc file is shown here (relevant changes are red). If you want to download a suitable-for-use (no HTML) version, click here.

NOTE: Neal McBurnett <neal _at_ bcn _dot_ boulder _dot_ co _dot_ us> pointed out that I did not include the confCLIENT_CERT and confCLIENT_KEY lines, which when specified, enable sendmail to use SSL for outbound mail (in other words, when sendmail acts as mail client.) The sendmail.mc file shown here has been updated accordingly -- I had to ADD these lines, not just uncomment them. See http://bcn.boulder.co.us/~neal/cablemail.html for Neal's howto on secure end-to-end mail.

 
divert(-1)dnl
dnl #
dnl # This is the sendmail macro config file for m4. If you make changes to
dnl # /etc/mail/sendmail.mc, you will need to regenerate the
dnl # /etc/mail/sendmail.cf file by confirming that the sendmail-cf package is
dnl # installed and then performing a
dnl #
dnl #     make -C /etc/mail
dnl #
include(`/usr/share/sendmail-cf/m4/cf.m4')dnl
VERSIONID(`setup for Red Hat Linux')dnl
OSTYPE(`linux')dnl
dnl #
dnl # Uncomment and edit the following line if your outgoing mail needs to
dnl # be sent out through an external mail server:
dnl #
dnl define(`SMART_HOST',`smtp.your.provider')
dnl #
define(`confDEF_USER_ID',``8:12'')dnl
define(`confTRUSTED_USER', `smmsp')dnl
dnl define(`confAUTO_REBUILD')dnl
define(`confTO_CONNECT', `1m')dnl
define(`confTRY_NULL_MX_LIST',true)dnl
define(`confDONT_PROBE_INTERFACES',true)dnl
define(`PROCMAIL_MAILER_PATH',`/usr/bin/procmail')dnl
define(`ALIAS_FILE', `/etc/aliases')dnl
dnl define(`STATUS_FILE', `/etc/mail/statistics')dnl
define(`UUCP_MAILER_MAX', `2000000')dnl
define(`confUSERDB_SPEC', `/etc/mail/userdb.db')dnl
define(`confPRIVACY_FLAGS', `authwarnings,novrfy,noexpn,restrictqrun')dnl
define(`confAUTH_OPTIONS', `A')dnl
dnl #
dnl # The following allows relaying if the user authenticates, and disallows
dnl # plaintext authentication (PLAIN/LOGIN) on non-TLS links
dnl # Drop the "p" if you want to allow non-encrypted login
dnl # (e.g. for testing your configuration)
dnl #
define(`', `A p')dnl
dnl # 
dnl # PLAIN is the preferred plaintext authentication method and used by
dnl # Mozilla Mail and Evolution, though Outlook Express and other MUAs do
dnl # use LOGIN. Other mechanisms should be used if the connection is not
dnl # guaranteed secure.
dnl #
TRUST_AUTH_MECH(`EXTERNAL GSSAPI DIGEST-MD5 CRAM-MD5 LOGIN PLAIN')dnl
define(`confAUTH_MECHANISMS', `EXTERNAL GSSAPI DIGEST-MD5 CRAM-MD5 LOGIN PLAIN')dnl
dnl #
dnl # Rudimentary information on creating certificates for sendmail TLS:
dnl #     make -C /usr/share/ssl/certs usage
dnl #
define(`confCACERT_PATH',`/usr/share/ssl/certs')
define(`confCACERT',`/usr/share/ssl/certs/ca-bundle.crt')
define(`confSERVER_CERT',`/usr/share/ssl/certs/sendmail.pem')
define(`confSERVER_KEY',`/usr/share/ssl/certs/sendmail.pem')
define(`confCLIENT_CERT',`/usr/share/ssl/certs/sendmail.pem')dnl
define(`confCLIENT_KEY',`/usr/share/ssl/certs/sendmail.pem')dnl
dnl #
dnl # This allows sendmail to use a keyfile that is shared with OpenLDAP's
dnl # slapd, which requires the file to be readble by group ldap
dnl #
dnl define(`confDONT_BLAME_SENDMAIL',`groupreadablekeyfile')dnl
dnl #
dnl define(`confTO_QUEUEWARN', `4h')dnl
dnl define(`confTO_QUEUERETURN', `5d')dnl
dnl define(`confQUEUE_LA', `12')dnl
dnl define(`confREFUSE_LA', `18')dnl
define(`confTO_IDENT', `0')dnl
dnl FEATURE(delay_checks)dnl
FEATURE(`no_default_msa',`dnl')dnl
FEATURE(`smrsh',`/usr/sbin/smrsh')dnl
FEATURE(`mailertable',`hash -o /etc/mail/mailertable.db')dnl
FEATURE(`virtusertable',`hash -o /etc/mail/virtusertable.db')dnl
FEATURE(redirect)dnl
FEATURE(always_add_domain)dnl
FEATURE(use_cw_file)dnl
FEATURE(use_ct_file)dnl
dnl #
dnl # The -t option will retry delivery if e.g. the user runs over his quota.
dnl #
FEATURE(local_procmail,`',`procmail -t -Y -a $h -d $u')dnl
FEATURE(`access_db',`hash -T -o /etc/mail/access.db')dnl
FEATURE(`blacklist_recipients')dnl
EXPOSED_USER(`root')dnl
dnl #
dnl # The following causes sendmail to only listen on the IPv4 loopback address
dnl # 127.0.0.1 and not on any other network devices. Remove the loopback
dnl # address restriction to accept email from the internet or intranet.
dnl #
dnl # DAEMON_OPTIONS(`Port=smtp,Addr=127.0.0.1, Name=MTA')dnl
DAEMON_OPTIONS(`Port=smtp, Name=MTA')dnl
dnl #
dnl # The following causes sendmail to additionally listen to port 587 for
dnl # mail from MUAs that authenticate. Roaming users who can't reach their
dnl # preferred sendmail daemon due to port 25 being blocked or redirected find
dnl # this useful.
dnl #
dnl DAEMON_OPTIONS(`Port=submission, Name=MSA, M=Ea')dnl
dnl #
dnl # The following causes sendmail to additionally listen to port 465, but
dnl # starting immediately in TLS mode upon connecting. Port 25 or 587 followed
dnl # by STARTTLS is preferred, but roaming clients using Outlook Express can't
dnl # do STARTTLS on ports other than 25. Mozilla Mail can ONLY use STARTTLS
dnl # and doesn't support the deprecated smtps; Evolution <1.1.1 uses smtps
dnl # when SSL is enabled-- STARTTLS support is available in version 1.1.1.
dnl #
dnl # For this to work your OpenSSL certificates must be configured.
dnl #
DAEMON_OPTIONS(`Port=smtps, Name=TLSMTA, M=s')dnl
dnl #
dnl # The following causes sendmail to additionally listen on the IPv6 loopback
dnl # device. Remove the loopback address restriction listen to the network.
dnl #
dnl # NOTE: binding both IPv4 and IPv6 daemon to the same port requires
dnl #       a kernel patch
dnl #
dnl DAEMON_OPTIONS(`port=smtp,Addr=::1, Name=MTA-v6, Family=inet6')dnl
dnl #
dnl # We strongly recommend not accepting unresolvable domains if you want to
dnl # protect yourself from spam. However, the laptop and users on computers
dnl # that do not have 24x7 DNS do need this.
dnl #
FEATURE(`accept_unresolvable_domains')dnl
dnl #
dnl FEATURE(`relay_based_on_MX')dnl
dnl # 
dnl # Also accept email sent to "localhost.localdomain" as local email.
dnl # 
LOCAL_DOMAIN(`localhost.localdomain')dnl
dnl #
dnl # The following example makes mail from this host and any additional
dnl # specified domains appear to be sent from mydomain.com
dnl #
dnl MASQUERADE_AS(`mydomain.com')dnl
dnl #
dnl # masquerade not just the headers, but the envelope as well
dnl #
dnl FEATURE(masquerade_envelope)dnl
dnl #
dnl # masquerade not just @mydomainalias.com, but @*.mydomainalias.com as well
dnl #
dnl FEATURE(masquerade_entire_domain)dnl
dnl #
dnl MASQUERADE_DOMAIN(localhost)dnl
dnl MASQUERADE_DOMAIN(localhost.localdomain)dnl
dnl MASQUERADE_DOMAIN(mydomainalias.com)dnl
dnl MASQUERADE_DOMAIN(mydomain.lan)dnl
MAILER(smtp)dnl
MAILER(procmail)dnl

After editing sendmail.mc, save and exit.

STEP 7: Certificates. For the SSL (STARTTLS) portion of this feature, you will need to generate SSL certificates. See the References section if you want to read more about how certificates work. I'm just going to tell you what to type to make it work. :)

 
cd /usr/share/ssl/certs make sendmail.pem 

Answer the prompts, your answers are not crucially important EXCEPT that you MUST specify the fully-qualified domain name for your server (e.g., mail.goober.com).

STEP 8: Activate changes in sendmail and test. Now, use your modified sendmail.mc file to generate a new sendmail.cf file:

 
m4 /etc/mail/sendmail.mc > /etc/mail/sendmail.cf 

Then, restart sendmail:

 
/etc/init.d/sendmail restart 

Assuming sendmail starts up successfully (if not, check for syntax errors in sendmail.mc, and/or check /var/log/maillog for errors), do a check:

 
bash-2.05a# telnet localhost 25 
Trying 127.0.0.1... 
Connected to localhost. 
Escape character is '^]'. 
220 whoopis.com ESMTP Sendmail 8.12.8/8.11.6; Sat, 19 Apr 2003 13:55:43 -0400 

Carefully type:

 
EHLO localhost 

And take a look at the output:

 
250-whoopis.com Hello localhost [127.0.0.1], pleased to meet you
250-ENHANCEDSTATUSCODES
250-PIPELINING
250-8BITMIME
250-SIZE
250-DSN
250-ETRN
250-AUTH GSSAPI LOGIN PLAIN
250-STARTTLS
250-DELIVERBY
250 HELP

Look at the AUTH line. "LOGIN" and "PLAIN" are key; if you see those, along with "STARTTLS", you're good to go. "GSSAPI" refers to Kerberos 5. Basically, anything that follows the AUTH line is the name of an accepted authentication mechanism. If you installed and set up the sasl db, then that line may look like:

 
250-AUTH GSSAPI DIGEST-MD5 CRAM-MD5 LOGIN PLAIN 

NOTE: If you included the "p" in the confAUTH_OPTIONS part of your sendmail.mc file, then you may not see the AUTH options in sendmail's output in this test. That's because sendmail is waiting for the secure STARTTLS link before it authenticates you. Either drop the "p" and rebuild sendmail.cf for testing, or use a real mail client to test (see Step 9).

Some mail clients, such as Apple's Mail, have an option for "MD5 Challenge-Response." This corresponds to the MD5 options enabled by your entry in the sasl database, if you made one.

STEP 9: The acid test. Now try a real mail client. First, remove your client machine's IP range from the access file and restart sendmail -- relaying should now be denied for you (try it). Then set up your client's SMTP config to use SSL, on port 25, and to authenticate using "password." Try sending a message; you should be prompted for your password, most clients have an option to remember the login/password so you don't have to type it for every message. If you get an error like "Server does not support AUTH mechanism PLAIN" then check sendmail.mc again (make sure that one annoying line is still commented out!), regenerate the .cf file, restart sendmail, etc. and try again.

Here's tcpdump output showing what your outbound email looks like after enabling AUTH and SSL, and another sample showing just AUTH without SSL.

You will need to tell your users how to edit their email configurations to use SMTP auth with password and SSL. If your users' mail programs can't handle auth, you can fall back on the old method of keeping their IPs in the access file. Here is a sample explanation meant for non-technical users, which you can adapt and use if you wish.

Troubleshooting. Users may get an error message like this if they use Outlook and SSL:

This is because the certificate you generated is a self-signed certificate, and is therefore untrusted. It's okay for our purposes -- tell your users to hit "yes" to accept the certificate anyway.

If your users see this error:

Then try the solutions posted here: http://www.iron. net/www/troubleshoot/email/outbox.html

NOTE: Matt Carter <matt at matt dot name> writes: "There is an easy solution to avoiding clicking 'yes' every time and it's not on the iron.net link.

  1. Close Outlook
  2. Open up Internet Explorer, go to https://mail.goober.com:995, this should be the same server name you entered as the mail server, and the same name the certificate has been generated under
  3. you will be challenged about the validity of the secure certificate in the same manner as with Outlook
  4. Click view certificate, add certificate, automatic, it should be now added to the root certificate store
  5. Go back to outlook, open up, away you go without any future warnings

Problems with Mozilla? Steve McKinney found that after following the setup outlined here, he was unable to send mail with Mozilla. Click here to see what he did differently.

Self-signed certs and Apple Mail: See this howto.


ADDENDUM: Enabling SSL for IMAP is quite simple. See this link or follow these steps:

1. cd /usr/share/ssl/certs/
2. run "make imapd.pem"
3. answer prompts -- just like for your sendmail.pem file. Answers do not need to be identical, but again, be sure to use the fully-qualified hostname (e.g. mail.domain.com)
4. Check that "imaps" exists under /etc/xinetd.d/ and that it is set to "disable=no" (in other words, enabled!) If imaps isn't there, duplicate and rename the "imap" file. They are functionally identical.
5. Restart imap by restarting xinetd (run "/etc/init.d/xinetd restart", but first make sure there are no important xinetd processes running, like a big ftp job)
6. Run "netstat -anp | less" and check the output:

 
Active Internet connections (servers and established) 
Proto Recv-Q Send-Q Local Address           Foreign Address         State       PID/Program name   
... ... 
tcp        0      0 0.0.0.0:993             0.0.0.0:*               LISTEN      2387/xinetd         
... ... 
tcp        0      0 0.0.0.0:143            	0.0.0.0:*               LISTEN      27562/xinetd 
... ... 

If you see the "0 0.0.0.0:993" line, that's secure IMAP listening on the default port of 993. Configure your mail client(s) to "use SSL" and you should be all set. :) The same potential exists for picky mail clients to whine about the untrusted certificate, but that's ok.


References:

These are listed in no particularly meaningful order...basically, in the order in which I found them. :)


As always, a huge thanks to William Stearns (wstearns at pobox.com) for all the help and proofreading, and especially for the RPM/SRPM details.

Thanks to Lee Patterson (amdusias at whoopis.com) for the Outlook and Outlook Express troubleshooting assistance and screenshots.

Thanks to Gerardo Luna for testing this with RedHat 9.0 and RedHat Enterprise, and Outlook Express under Windows 2000 and XP.

Thanks to David Jao for the note about modifying Sendmail 8.11.

Thanks to Neal McBurnett for the sendmail-as-client SSL info.

Thanks to Steve McKinney for the Mozilla troubleshooting info.

Thanks to Matt Carter for the Outlook/IE "remember the certificate" trick.

Thanks to Simon Lewis <siweb at blueyonder dot co dot uk> for Mandrake 10.0 testing and for drawing attention to the fact that without at least one libsasl2 plugin, saslauthd does precisely squat.