Very recently I decided to clean my home FreeBSD server  and start from scratch, meaning deleting everything and reinstalling FreeBSD. The fact that I happened to do this after completely messing up my ports system is purely coincidence… 😉

I took the time to try out the new FreeBSD release 8.0, so I downloaded the iso from the FreeBSD site, burned it and installed it on my home server (the server I’m referring to is in this post). After reinstalling all the ports I had on it previously (Apache, MySQL, PHP5, PHP5-extensions, Java 1.6, Openfire etc.), I decided to go one step further and try something I hadn’t done before, get email working.

DNS settings

To be able to receive email I needed a domain, now it happens that I purchased chrismcdonald.co.uk at some point last year, got it very cheap for 2 years from 123-reg. The domain wasn’t really doing anything and was just being used to forward to this blog (and still is), so I decided to get more use out of it and use a subdomain to point to my home server. I set the hostname of my FreeBSD server to server.chrismcdonald.co.uk by adding hostname=”server.chrismcdonald.co.uk” to /etc/rc.conf and added an entry in /etc/hosts so that it would resolve locally. So my hosts file now contained:               localhost server.chrismcdonald.co.uk

To get the domain to point to my home server I changed my dns records for chrismcdonald.co.uk and added a CNAME record pointing server.chrismcdonald.co.uk to my dynamic dns host chris.is-a-geek.net. I also added an MX record for the root domain which directs email to chrismcdonald.co.uk to chris.is-a-geek.net. Dynamic DNS allows users with a non-static IP (most home internet users) to use a host name to refer to your system’s ip address, which might change whenever you connect to your ISP. It works by having your home system contact the dynamic dns provider every so often to make sure the ip address mapping is kept up to date. I use dyndns.com, you can create a free account with them where you can create some free host names to use. You get to pick your own subdomain from any one of the domains they allow you to use, I chose the domain is-a-geek.net and my subdomain chris. My wireless router has built in support to work with dyndns.com and keep my host ip address updated, but if yours does not, there are some instructions also in my older post to get this working on FreeBSD.

Receiving mail

To ensure I could send and receive email past my wireless router, I added some port forwards for ports 25 (smtp), 465 (secure smtp) and 993 (secure imap), I already have existing port forwards set up for web and ssh access. Sendmail is configured by default to only allow sending of email and receiving mail only from localhost. To enable sendmail to receive mail externally I added this line to /etc/rc.conf and started sendmail again.


/etc/rc.d/sendmail stop
/etc/rc.d/sendmail start

OK so with the domain name sorted out and sendmail set to receive external mail I tried testing it out. I logged into another remote server, which was located outside of my local network on the internet. I used telnet to attempt to manually send an email. Below is the transcript, my commands are in bold, square brackets are for your server name and email.

telnet server.chrismcdonald.co.uk 25
Connected to chris.is-a-geek.net.
Escape character is '^]'.
220 server.chrismcdonald.co.uk ESMTP Sendmail 8.14.4/8.14.3; Sat, 8 May 2010
12:08:15 +0100 (BST)
HELO [remote server name]
250 server.chrismcdonald.co.uk Hello [remote server name and ip] , pleased
to meet you
MAIL FROM: [user@remoteserver]
250 2.1.0 [user@remoteserver]... Sender ok
RCPT TO: [user@server - in this case chris at chrismcdonald.co.uk]
550 5.7.1 [user@server]... Relaying denied
221 2.0.0 server.chrismcdonald.co.uk closing connection

So it appeared that my server was not accepting email for my domain. To fix this I created the file /etc/mail/local-host-names and added the following lines, you would add your own hostnames.


Then when I tried again:

telnet server.chrismcdonald.co.uk 25
Connected to chris.is-a-geek.net.
Escape character is '^]'.
220 server.chrismcdonald.co.uk ESMTP Sendmail 8.14.4/8.14.3; Sat, 8 May 2010
12:08:15 +0100 (BST)
HELO [remote server name]
250 server.chrismcdonald.co.uk Hello [remote server name and ip], pleased
to meet you
MAIL FROM: [user@remoteserver]
250 2.1.0 [user@remoteserver]... Sender ok
RCPT TO: [user@server - in this case chris at chrismcdonald.co.uk]
550 5.7.1 [user@server]... Recipient ok
354 Enter mail, end with "." on a line by itself
Subject: test email again
Just testing
250 2.0.0 o48BLo6R001500 Message accepted for delivery
221 2.0.0 server.chrismcdonald.co.uk closing connection

Sure enough I had the new email in my local mailbox (checked by running mail).

IMAP access

So now I could receive mail from outside, I looked around for a few guides to get started on setting up secure IMAP and secure SMTP sending. I needed a program that would provide IMAP access to mail and came across this blog post on Dovecot on freebsddiary.org, this is a great site with loads of tutorials and info on FreeBSD. I followed the steps in the guide to install Dovecot with some minor adjustments.

cd /usr/ports/mail/dovecot
make install clean

Below are the make options I used:

Dovecot make options

Dovecot make options

You can follow those steps from freebsddiary if you are starting from scratch. I ignored the certificate stuff because I already had a self signed one created, I also chose to use PAM authentication, which uses your user account password to authenticate. The important bits which I changed from /usr/local/etc/dovecot.conf are below, change them where they occur in the file:

protocols = imaps
ssl_cert_file = /etc/ssl/certs/server.chrismcdonald.co.uk.cert
ssl_key_file = /etc/ssl/private/server.chrismcdonald.co.uk.key
ssl_key_password = ******************
mail_location = mbox:~/mail/:INBOX=/var/mail/%u
protocol imap {
listen = *:143
ssl_listen = *:993
# Login executable location.
auth default {
  # Space separated list of wanted authentication mechanisms:
  #   plain login digest-md5 cram-md5 ntlm rpa apop anonymous gssapi otp skey
  #   gss-spnego
  # NOTE: See also disable_plaintext_auth setting.
  mechanisms = plain login

Then add the following to /etc/rc.conf and start dovecot.


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

Now I access my mail using imap securely over port 993. So far the server is able to receive mail, send mail (only from localhost) and has secure imap access to read mail, if this is suitable for what you need you can stop here. If you want to be able to send mail from another machine using your secure smtp read on.

SMTP sending

I found a couple more guides on having secure smtp authentication here and here. I did not follow those steps but borrowed some from both guides. The common setup appears to use cyrus sasl (Simple Authentication and Security Layer) for the authentication and to configure sendmail to use it. SASL SASL support is not build into sendmail by default, the guides said to recompile sendmail from its source /usr/src/usr.sbin/sendmail which I couldn’t find, I guess these things are all done using the ports system now, so here’s what I installed.

cd /usr/ports/security/cyrus-sasl2
make install clean
cd /usr/ports/security/cyrus-sasl2-saslauthd
make install clean
cd /usr/ports/mail/sendmail-sasl
make install clean

Then I needed to enable the sasl daemon by editing /etc/rc.conf and adding this line and starting the sasl daemon.


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

Finally sendmail needed to be configured to use secure smtp authentication, I also copied my certificate files that I generated a while back into /etc/mail/certs. I copied the default freebsd.mc and freebsd.submit.mc files located in /etc/mail to server.chrismcdonald.co.uk.mc and server.chrismcdonald.co.uk.submit.mc and edited server.chrismcdonald.co.uk.mc. Then following bits from both guides I added the following:

dnl set SASL options
dnl Offer SMTP AUTH only after encryption (STARTTLS) has been negotiated

define(`CERT_DIR', `/etc/mail/certs')dnl
define(`confCACERT_PATH', `CERT_DIR')dnl
define(`confCACERT', `CERT_DIR/server.chrismcdonald.co.uk.cert')dnl
define(`confSERVER_CERT', `CERT_DIR/server.chrismcdonald.co.uk.cert')dnl
define(`confSERVER_KEY', `CERT_DIR/server.chrismcdonald.co.uk.key')dnl
define(`confCLIENT_CERT', `CERT_DIR/server.chrismcdonald.co.uk.cert')dnl
define(`confCLIENT_KEY', `CERT_DIR/server.chrismcdonald.co.uk.key')dnl
DAEMON_OPTIONS(`Port=smtps, Name=TLSMTA, M=s')dnl

The lines starting with dnl are comments and those backticks ` are not typos, the opening quote is a backtick and the closing one a normal apostrophe. Finally after running the following in /etc/mail I had secure smtp authentication working:

make install
make restart

Well, that’s it for another post, sorry it was such a long one. I am buying a couple of real servers on eBay that wer e going pretty cheap, the kind they use in datacentres. I will probably have a go at getting internal dns working, so that I won’t be restricted to a single server working at home. If it works I will do another post on it.

2 comments so far

Add Your Comment
  1. Wow, thanks! This is the first posting I found that was simple and understandable enough that I could attempt getting SSL/TLS working with sendmail. I previously had dovecot set up, and it only took about 15 minutes more to add sasld and the sendmail config mods following your instructions. One note, the current FreeBSD ports collection separates cyrus-sasl2-saslauthd into a separate port. That is the one that installs the sasl daemon.

  2. Thanks for this nice tutorial! 🙂