Introduction

Intended Audience

I have written this document for individuals confident of their ability to administer a Debian GNU/Linux system. I make the assumption that the reader is familiar with the package management system, Debian's init scripts, and basic troubleshooting using the system's log files. I don't intend to discuss configuring Exim4 to handle incoming mail from off site, but rather stick to mail destined for the local domain from other hosts local to the network, fetched via POP3 from a live mailhost, or sent off site using a smarthost.

Copyright and License

This document, Configuring Exim and Courier IMAP under Debian GNU/Linux, is copyrighted © 2004 by Jason Boxman.

Permission is granted to copy, distribute and/or modify this document under the terms of the GNU Free Documentation License, Version 1. 2 or any later version published by the Free Software Foundation; with no Invariant Sections, with no Front-Cover Texts, and with no Back-Cover Texts. A copy of the license is available at http://www.gnu.org/copyleft/fdl.html.

Linux is a registered trademark of Linus Torvalds.

Disclaimer

No liability for the contents of this document can be accepted. Use the concepts, examples and information at your own risk. There may be errors and inaccuracies, that could be damaging to your system. Proceed with caution, and although this is highly unlikely, the author(s) do not take any responsibility.

All copyrights are held by their respective owners, unless specifically noted otherwise. Use of a term in this document should not be regarded as affecting the validity of any trademark or service mark. Naming of particular products or brands should not be seen as endorsements.

Feedback

Please feel free to contact me with corrections, omissions, and questions: jasonb@edseek.com

New Versions of this Document

The newest version of this HOWTO will always first be made available here.

Installing and Configuring Exim4

Installation of Exim4 from the latest Debian GNU/Linux packages is easy. The installation is now based around debconf. If you are upgrading from a simple Exim3 configuration, you can use exim_convert4r4 to convert your configuration file to the new format. If you used the previous version of this guide, which covered Exim3, the conversion should succeed without incident. I intend to discuss configuration via debconf, including setting up local delivery to Maildir format, handling local domain email, and configuring smarthosting for outbound email.

Installing and Configuring Exim4 Packages

First, install Exim4 using the standard and exciting Debian procedure you know and love.

 
nebula:~# apt-get update
nebula:~# apt-get install exim4

Fetching the meta package will result in the installation of exim4-base, exim4-config, and exim4-daemon-light, all version 4.34 as of this writing.

During installation, debconf will appear and ask you some questions about your shiny new Exim4 installation. If you are upgrading From Exim3, your configuration in /etc/exim/exim.conf will be parsed for appropriate default values. If you intend to convert your existing Exim3 configuration, you can go through the debconf screens, accepting the defaults, skip the rest of this section. (If you haven't made many modifications to your old Exim3 configuration, I encourage you to use the debconf generated configuration, as it's simpler.)

What follows is a discussion of each option presented by debconf. If you do not walk through the debconf screens now or before continuing, the following discussion may not make much sense. If you accidentally broke out of debconf, you can always run the following to restart the configuration process.

 
nebula:~# dpkg-reconfigure exim4-config

 # Split configuration into small files?

For the duration of this guide I assume you have chosen to use the monolithic configuration file, which is the default. Let's walk through the debconf questions on at a time.

First, if your host has a static IP address that is not located in your ISP's dynamic range, you should be able to initiate SMTP connections to remote sites directly and you do not need to use a smarthost. If such is the case, select ”internet site; mail is sent and received directly using SMTP”. For the rest of us, select ”mail sent by smarthost; received via SMTP or fetchmail” as your mail configuration. The system mail name should be your fully qualified domain name. If you have not deployed DNS at your site, you may opt for using your system's /etc/hosts file to give your host such a name as demonstrated below. (If you choose the first option and you do not have DNS configured, you will probably encounter difficulties receiving email.)

 
nebula:~# cat >> /etc/hosts
127.0.0.1 mail.example.com
^D

Next, if the machine you are configuring is your only host, you should accept the default address, 127.0.0.1, as the IP address to listen on. If you intend to connect to Exim4 from other hosts, on the local network or elsewhere, you should either include additional specific addresses for your mail host (e.g. 192.168.33.5), separated by a colon, or delete the suggested value and leave it blank to have Exim4 listen on all available network interfaces.

Now, you need to decide what other destinations this host is the final destination for. If you have no other hosts, you can leave this at its default setting. If you have or intend to have an actual DNS domain across your local network, enter that domain name here. Don't include any hostnames, just the domain itself and its associated top level domain (TLD).

If you indicated your host will be sending and receiving email directly, next you will be asked for which domains you wish to accept email that are not considered local domains. Enter any appropriate domain names that apply to your configuration. If you selected the smarthosting option earlier, then you will not be prompted about which domains you which to relay for.

Next, you are prompted for the address ranges for which this mail host should accept connections for relaying mail elsewhere. For example, for my local network I used the address range 192.168.33.0/24. Include any additional ranges you want, separated by colons. Any hosts in the defined ranges will be allowed to send mail off site. You most definitely want to include hosts on your local network that you wish to send mail to the Internet from.

Now, enter the address of the smarthost through which you relay outgoing mail. Usually this will be your Internet service provider's outbound SMTP server, the server you are probably using to send email from the email client of your choice. You will not be prompted for a smarthost if you have chosen to send and receive mail directly.

Finally, if you are using a smarthost to relay mail, you can opt to have the outgoing address rewritten in the envelope header, if you would prefer your mail appear to have originated from a fully Internet connected host. Enter whatever fully qualified domain you would prefer, or accept the default if you don't care.

Last, you will be asked if you wish to minimize the number of DNS queries performed if you are in a dial-on-demand situation, perhaps with a leased line with metered usage. Ordinarily you can select the default, which is not to minimize DNS queries.

Upon completion of debconf configuration, your shiny new configuration file will be placed in /var/lib/exim4/config.autogenerated. As the filename implies, this is generated from your selections in /etc/exim4/update-exim4.conf.conf and /etc/exim4/exim4.conf.template. Any changes to the actual configuration, such as adding other routers or tweaking existing ones, must be done in the latter file.

You can revisit the debconf configuration at any time by running the following:

 
nebula:~# dpkg-reconfigure exim4-config

Converting Your Exim3 Configuration for Exim4

If you would rather recycle your old configuration using the exim_convert4r4, read on. Otherwise, you can skip this section. If you already configured Exim3 with support for delivering to Maildir style directories, after the conversion you should be good to go. If not, you may wish to simply go with the debconf generated configuration discussed above, since it will be a lot easier to enable Maildir style directories with that.

 
nebula:~# cat /etc/exim/exim.conf | exim_convert4r4 > /etc/exim4/exim4.conf
Runtime configuration file converter for Exim release 4.
** The following comments describe problems that have been encountered
while converting an Exim 3 runtime file for Exim 4. More detail can
be found in the file doc/Exim4.upgrade.
** The receiver_try_verify option no longer exists, and has no equivalent
in Exim 4.
*******************************************************
***** Please review the generated file carefully. *****
*******************************************************

By default, if the file /etc/exim4/exim4.conf exists, the Debian Exim4 initialization scripts will start the daemon using that configuration file and ignore the file in /var/lib/exim4/config.autogenerated completely. If you are happy with your converted configuration, you may wish to disable debconf management of your configuration files entirely by editing /etc/exim4/update-exim4.conf.conf.

# /etc/exim4/update-exim4.conf.conf
#
# Edit this file and /etc/mailname by hand and execute update-exim4.conf
# yourself or use 'dpkg-reconfigure exim4-config'

dc_eximconfig_configtype='none'

Finally, restart the daemon.

 
nebula:~# invoke-rc.d exim4 reload
Reloading exim4 configuration files

Configuring Exim4 for Maildir Delivery

Unlike configuring Exim3 for Maildir, the configuration for Exim4 is straightforward. If you choose to use the debconf generated configuration file, you need merely open /etc/exim4/update-exim4.conf.conf and make a single edit. Add the option dc_localdelivery to the end of the file with a value of maildir_home, or change its value if it already exists, as shown below. (At least since Debian Etch, this is now a configuration time option for the Debian package of Exim4.)

dc_localdelivery=maildir_home

Now, restart the daemon.

 
nebula:~# invoke-rc.d exim4 reload
Reloading exim4 configuration files

If you recycled a previous Exim3 configuration with Maildir already configured, discussed above, then you need not do anything. You're done.

Testing your new Exim4 configuration

It's important that your configuration work correctly before proceeding further. Send yourself an email from another account somewhere on the Internet, or from another user on your own machine. (root works for this.) You might do the following:

 
nebula:/home/jasonb# echo "my test" | mail -s "test message" jasonb

The purpose of this exercise is two fold. First, you'll find out if Exim4 is configured properly. Second, and equally as important, Exim will create the Maildir hierarchy in your home directory, ~/Maildir, which Courier IMAP craves and requires to function. More on that later.

 
nebula:~# tail -f /var/log/exim4/mainlog
2004-09-14 16:58:00 1C7KNE-0006w8-NZ <= root@nebula.internal.foo U=root P=local S=336
2004-09-14 16:58:00 1C7KNE-0006w8-NZ => tester <tester@nebula.internal.foo> R=local_user T=maildir_home
2004-09-14 16:58:00 1C7KNE-0006w8-NZ Completed

Success!

 
nebula:~# ls -ltr /home/tester/
total 0
drwx------ 5 tester tester 120 Sep 14 16:57 Maildir
nebula:~# ls -1 /home/tester/Maildir/new
/home/tester/Maildir/new:
1095195480.H806891P26670.nebula.internal.foo
nebula:~# cat /home/tester/Maildir/new/1095195480.H806891P26670.nebula.internal.foo
Return-path: <root@nebula.internal.foo>
Envelope-to: tester@nebula.internal.foo
Delivery-date: Tue, 14 Sep 2004 16:58:00 -0400
Received: from root by nebula.internal.foo with local (Exim 4.34)
id 1C7KNE-0006w8-NZ
for tester@nebula.internal.foo; Tue, 14 Sep 2004 16:58:00 -0400
To: tester@nebula.internal.foo
Subject: tester
Message-Id: <E1C7KNE-0006w8-NZ@nebula.internal.foo>
From: root <root@nebula.internal.foo>
Date: Tue, 14 Sep 2004 16:58:00 -0400
my test

You can see above Exim4 happily creates Maildir/ directory and sticks your new mail message in the Maildir/new/ directory.

It's necessary for each user to have this directory before Courier IMAP can successfully access a user's mail, otherwise your mail client will return an error. With that in mind, there are a few ways you can ensure that this directory exists. For future users, you can modify your /etc/skel directory and add a Maildir/ directory there. Thusly as root:

 
root@nebula:/# maildirmake /etc/skel/Maildir

All future users will now have a Maildir/ with the proper permissions and subdirectories. It's important to note that maildirmake is only available after you install the courier-base package.

That still leaves existing users, though. You can mail everyone on the system about the new IMAP setup and in doing so, Exim4 will create the very Maildir structure you seek. Or you can write a script to add a Maildir for each existing user with the maildirmake command like we did above for /etc/skel. It's up to you.

You cannot proceed with the next step successfully, in any case, without at least building a Maildir for yourself. So if you didn't send a test message, run the following as your own user:

 
tester@nebula:~$ cd ~
tester@nebula:~$ maildirmake Maildir

Configuring New Mail Notification

If you'd like to continue to receive the notification “You have new mail.”, you need to modify several files.

The following is probably no longer accurate for Debian Etch 4.0.

First, /etc/login.defs. You will want to locate the QMAIL_DIR and MAIL_FILE environment variables and uncomment them. Then, comment out the MAIL_DIR environment variable. The value of MAIL_FILE will be appended to the user's home directory, such that the MAIL environment variable becomes defined as MAIL=$HOME/$MAIL_FILE, which is what you want. An example follows.

QMAIL_DIR    Maildir/
#MAIL_DIR    /var/mail
MAIL_FILE    Maildir/

Second, modify your /etc/pam.d/login to receive new mail notifications when you login on the console. Your /etc/pam.d/login with the correction options for pam_mail.so should look like the example below.

session    optional   pam_mail.so standard noenv dir=~/Maildir

Last, you need to make a similar modification to /etc/pam.d/ssh so you receive new mail notifications when you login via ssh. In order for the MAIL environment variable to be set correctly, you must ensure that the noenv is not passed to pam_mail.so.

# Print the status of the user's mailbox upon successful login.
session    optional     pam_mail.so standard dir=~/Maildir # [1]

Now you can enjoy mail notifications whenever you login to your mail server.

Configuring Exim4 dot forward Filtering

For a detail discussion of Exim's filter system, you should check out Exim's documentation itself. For just the short of it, read on.

In order for Exim to recognize a .forward as having Exim4 filter rules, the first non-whitespace entry must be:

# Exim filter

Character case and anything following it on the same line are ignored.

Next, you'll likely want some rules in your Exim4 filter .forward file. Using a simple if then elif else endif construct you can perform various tests against each incoming email before delivery (or discarding) it to a specified location. You can perform evaluations against any existing entry in an email's header, like so:

# Match any email who's To: header contains "exim"
# and save it to .dir1
if $h_to: contains "exim" then save Maildir/.dir1/

# Match email with a From: header that's
# exactly "not@wanted.com" and save it to .SPAM
elif $h_from: is "not@wanted.com" then save Maildir/.SPAM/

endif

To access the email header of your choice, append $header_, or as abbreviated above, just $h_, to the full name of an email header, following by a colon (:). The keywords is and contains are self explanatory. The save keyword, when followed by a path that ends with a forward slash, will deliver the email being evaluated in Maildir format. As such, the trailing slash is crucial. Don't omit it.

When saving to Maildir format from a filter file, always remember the trailing front slash to ensure Maildir format is used.

In Courier's IMAP hierarchy, directories beneath the root are dot directories. In addition, all subdirectories are denoted by periods, not additional forward slashes. So, lists/Debian/User/ is actually .Lists.Debian.User/ on the filesystem and should be referred to in Exim filters as save Maildir/.Lists.Debian.User/ for things to be saved the way you expect.

My own personal working Exim filter file looks like this:

# Exim filter

# Save yourselves
if error_message then finish endif

# Let's make use of pipes
# The script accepts input on STDIN and does stuff with the mail
if $h_Subject: contains "uptime report"
then
       pipe "$home/bin/uptime.pl"
endif

# Handle mailing lists

if $h_List-Id: contains "leaplist"
  then save Maildir/.mailinglists.leap.linux/
elif $h_from: contains "ebay.com"
  then save Maildir/.Ebay/
elif $h_Sender: contains "LINUX-L"
  then save Maildir/.mailinglists.LUG/
endif

Configuring TLS and Authentication

Exim4 supports TLS for verifying the authenticity of host and client, encryption of the whole SMTP transaction, and a variety of user authentication schemes. The two most common scenarios, using authentication on the server to allow users to initiate a session from a remote network with TLS as the transport and authenticating with a smarthost over TLS are discussed. Many, many other possibilities exist.

Using TLS and Authentication Tokens on the Server

While not strictly necessary for authentication, I consider using TLS a prerequisite for enabling the usage of authentication tokens, the classic user login and password. Thus, let's configure TLS support for Exim4 first, then configure an authentication scheme.

To enable TLS, we will need a X.509 certification. If you already have a certificate, simply copy the appropriate files to /etc/exim4/exim.crt and /etc/exim4/exim.key respectively. Otherwise, let's make one now. The hostname ought to match your mail hosts fully qualified hostname, but may not. It's only fatal if you bail on a certification verification failure, which is not the default.

 
# bash /usr/share/doc/exim4-base/examples/exim-gencert

Next, let Exim4 know about your new certificate. Define MAIN_TLS_ENABLE to a true value somewhere in /etc/exim4/exim4.conf.template.

MAIN_TLS_ENABLE = yes

To verify TLS has been successfully configured, let's install an excellent diagnostic tool named swaks. With swaks, you can interrogate your mail server in ways you never imagined!

 
# apt-get install swaks libnet-ssleay-perl

It's easy to verify whether TLS is working or not.

 
$ swaks -a -tls -q HELO -s localhost -au jasonb -ap '<>'
=== Trying localhost:25...
=== Connected to localhost.
<- 220 evie ESMTP Exim 4.50 Tue, 02 May 2006 17:56:25 -0400
-> EHLO evie
<- 250-evie Hello localhost [127.0.0.1]
<- 250-SIZE 52428800
<- 250-PIPELINING
<- 250-STARTTLS
<- 250 HELP
-> STARTTLS
<- 220 TLS go ahead
=== TLS started w/ cipher DHE-RSA-AES256-SHA
~> EHLO evie
<~ 250-evie Hello localhost [127.0.0.1]
<~ 250-SIZE 52428800
<~ 250-PIPELINING
<~ 250 HELP
~> QUIT
<~ 221 evie closing connection

Above, we connect to our Exim4 daemon locally, start an authentication session, and force TLS. A username and an empty password are supplied to avoid any command line prompts from swaks. The result, above, shows initiating TLS succeeded. Next, we'll add support for an authentication scheme.

With Exim4 you can use a variety of authentication schemes and token backing stores. For a few users with shell access, and thus an entry in /etc/passwd, the easiest to configure is SASL. Once installed, it will use PAM to handle password authentication.

 
# apt-get install sasl2-bin

To allow the saslauthd daemon to run at start, we need to edit /etc/default/saslauthd and uncomment START.

 
# perl -i -pe 's!^.*START.*!START=yes!' /etc/default/saslauthd

The Perl command above quickly removes the leading comment, allowing START to be defined and sourced in /etc/init.d/saslauthd. Now, let's start the daemon.

 
# invoke-rc.d saslauthd start

With SASL's daemon running, now we can uncomment the configuration stanza in /etc/exim4/exim4.conf.template listed below that enables support for authentication via saslauthd using the PLAIN authentication scheme. Not all clients necessarily support LOGIN, though you may wish to uncomment LOGIN, too. Most mail clients consider authentication schemes in the order they're presented to the client.

# Authenticate against local passwords using sasl2-bin
# Requires exim_uid to be a member of sasl group, see README.SMTP-AUTH
 plain_saslauthd_server:
   driver = plaintext
   public_name = PLAIN
   server_condition = ${if saslauthd{{$2}{$3}}{1}{0}}
   server_set_id = $2
   server_prompts = :
   .ifndef AUTH_SERVER_ALLOW_NOTLS_PASSWORDS
   server_advertise_condition = ${if eq{$tls_cipher}{}{}{*}}
   .endif

As indicated above, once you've uncommented the plain_saslauthd_server, it's necessary to add the user that Exim4 runs as to the sasl group so it can speak with saslauthd.

 
# adduser Debian-exim sasl
Adding user `Debian-exim' to group `sasl'...
Done.

Finally, restart Exim4.

 
# invoke-rc.d exim4 restart

Let's test our new server configuration again with swaks, actually performing authentication by specifying a valid username and password before closing the connection after successful authentication.

 
evie:/etc/exim4# swaks -a -tls -q AUTH -s localhost -au jasonb
Password: passwd
=== Trying localhost:25...
=== Connected to localhost.
<- 220 evie ESMTP Exim 4.50 Fri, 05 May 2006 18:10:18 -0400
-> EHLO evie
<- 250-evie Hello localhost [127.0.0.1]
<- 250-SIZE 52428800
<- 250-PIPELINING
<- 250-STARTTLS
<- 250 HELP
-> STARTTLS
<- 220 TLS go ahead
=== TLS started w/ cipher DHE-RSA-AES256-SHA
~> EHLO evie
<~ 250-evie Hello localhost [127.0.0.1]
<~ 250-SIZE 52428800
<~ 250-PIPELINING
<~ 250-AUTH PLAIN
<~ 250 HELP
~> AUTH PLAIN AGphc28uygBOaGVxMHc=
<~ 235 Authentication succeeded
~> QUIT
<~ 221 evie closing connection

If everything has been configured correctly, as demonstrated above with swaks, we notice AUTH PLAIN is available and selected. Further, the password prompted for on the command line is used to successfully authenticate with Exim4. Now relaying will be permitted for any user after successful authentication and the exchange will take place over TLS.

Connecting to a smarthost over TLS with Authentication

Configuring Exim4 to authenticate itself using SMTP authentication is quite easy. You merely need to populate /etc/exim4/passwd.client with a hostname, username, password triplet. The password is specified in plain text, so ensure the file is not world readable.

### CONFDIR/passwd.client
#
# Format:
#targetmailserver.example:login:password
#
# default entry:
### *:bar:foo

example.com:jasonb:passwd

As indicated above, example.com is the hostname of the SMTP server we wish to authenticate with over TLS using either the LOGIN, PLAIN, or CRAM-MD5 authentication. The username and password follow, all separated by colons.

By default on Debian GNU/Linux Sarge, Exim4 will disallow SMTP-AUTH via either LOGIN or PLAIN if TLS has not been successfully negotiated. You can disable this behavior by setting AUTH_CLIENT_ALLOW_NOTLS_PASSWORDS in /etc/exim4/exim4.conf.template, but don't do that.

Sending a test message and looking in /var/log/exim4/mainlog should indicate successful authentication and sending of the message.

 
# echo "test" | mail -s "test" jasonb@edseek.com
# tail -f /var/log/exim4/mainlog
2006-05-05 18:45:56 1Fc93b-0003e4-QG <= root@nebula.internal.foo U=root P=local S=313
2006-05-05 18:45:57 1Fc93b-0003e4-QG => jasonb@edseek.com R=smarthost T=remote_smtp_smarthost
H=example.com [207.36.208.156] X=TLS-1.0:RSA_AES_256_CBC_SHA:32
2006-05-05 18:45:57 1Fc93b-0003e4-QG Completed
...

Installing and Configuring Courier IMAP

Installing Courier IMAP under Debian GNU/Linux is a simple procedure.

Installing Courier IMAP Packages

Install following packages via apt-get. Pulling down courier-imap and courier-imap-ssl should fetch courier-base and the other related files for you.

 
nebula:~# apt-get update
nebula:~# apt-get install courier-imap courier-imap-ssl

During installation, debconf will prompt you to answer some questions regarding the initial configuration of Courier IMAP. For the remainder of this guide, it is assumed you have chosen not to ”Create directories for web-based administration”. You will also be asked ”Path to user's Maildir directory”. The default of Maildir is correct.

Configuring Courier IMAP

There is not much you need to change. In fact, you probably do not need to change anything at all. There are a few options you may wish to evaluate with in /etc/courier/imapd.

You may wish to enable IMAP_CHECK_ALL_FOLDERS if you filter new mail into folders other than your regular inbox. You can enable the IMAP_ENHANCEDIDLE option. Enhanced idle mode notifies all clients immediately when any changes to a folder occur. Ordinarily, a client may not be aware of a change to a folder until it is refreshed. You must install the fam package for it to work, as it relies on the File Access Monitor daemon. You can install the package via the usual method:

 
nebula:/etc/courier# apt-get install fam

If you choose not to install fam, you can still use IMAP_ENHANCEDIDLE, but instead Courier IMAP will poll for changes every 60 seconds for folders opened by IMAP clients.

Testing your Courier IMAP setup

Before going through the process of configuring IMAP clients, let's verify that your setup does indeed work. The default Courier-IMAP configuration should work right out of the box. Telnet to your IMAP server as shown below and issue the commands show and verify the server's response. (imap2 is port 143 if you're curious.)

 
jasonb@nebula:~$ telnet 127.0.0.1 imap2
Trying 127.0.0.1...
Connected to 127.0.0.1.
Escape character is '^]'.
* OK [CAPABILITY IMAP4rev1 UIDPLUS CHILDREN NAMESPACE
THREAD=ORDEREDSUBJECT THREAD=REFERENCES SORT QUOTA IDLE
ACL ACL2=UNION STARTTLS] Courier-IMAP ready.
Copyright 1998-2004 Double Precision, Inc. See COPYING for distribution information.
AB LOGIN "user" "secret"
AB OK LOGIN Ok.
BC SELECT "Inbox"
* FLAGS (\Draft \Answered ... \Recent)
* OK [PERMANENTFLAGS (\* \Draft \Answered ... \Seen)] Limited
* 13 EXISTS
* 0 RECENT
* OK [UIDVALIDITY 1026858715] Ok
* OK [MYRIGHTS "acdilrsw"] ACL
BC OK [READ-WRITE] Ok
ZZZZ LOGOUT
* BYE Courier-IMAP server shutting down
ZZZZ OK LOGOUT completed
Connection closed by foreign host.

I separated each command and server response portion by a couple hard returns to make things more clear. Make sure you substitute your username and password for the dummy values above, and note that the AB, BC, et al. are part of the IMAP protocol and are required, though any sequence of letters will do. (Also, be amused that the actual logout command is indeed ZZZZ LOGOUT – Someone had a sense of humor.)

Creating an X.509 Certificate for TLS Connections

The SSL package for Courier IMAP will generate a generic X.509 certificate for you using the mkimapdcert command. If you are going to use a key signed by a certificate authority (CA), such as Thawte Consulting or Verisign, you can safely replace the generated certificate with your own. In either case, you must have a fully qualified domain name assigned to the IP address Courier IMAP will listen on for TLS/SSL to function correctly.

The certificate generated by mkimapdcert is /etc/courier/imapd.pem, owned by the root user and the root group and readable only by said user. The configuration file used to generate the X.509 certificate is /etc/courier/imapd.cnf, which is the file you will want to edit to generate a personalized, in-house certificate if you do not require one signed by a certificate authority.

 
nebula:/etc/courier# cat imapd.cnf
RANDFILE = /usr/lib/courier/imapd.rand
[ req ]
default_bits = 1024
encrypt_key = yes
distinguished_name = req_dn
x509_extensions = cert_type
prompt = no
[ req_dn ]
C=US
ST=NY
L=New York
O=Courier Mail Server
OU=Automatically-generated IMAP SSL key
CN=localhost
emailAddress=postmaster@example.com
[ cert_type ]
nsCertType = server

The default imapd.cnf is, in fact, a standard OpenSSL configuration for generating a self signed certificate. Full details are available in the OpenSSL man pages, specifically req(1).

You must change the common name (CN) to that of the fully qualified hostname assigned to the IP address Courier IMAP will be listening on, or you will receive a certificate mismatch error when connecting with an IMAP and SSL compatible mail client. The remaining fields, Country (C), State (ST), Location (L), Organization (O), Organizational Unit (OU), and emailAddress are self explanatory and need not be specific values.

When you are happy with the values you have chosen, run mkimapdcert as root to generate a new X.509 certificate. Make sure you remove the existing imapd.pem first, or no new certificate will be created.

 
nebula:/etc/courier# mkimapdcert
Generating a 2048 bit RSA private key
...
subject= /C=US/ST=GA/L=Gainesville/
O=The Vortex/OU=Automatically-generated IMAP SSL key/
CN=host.example.com/emailAddress=user@example.com
notBefore=Sep 27 23:35:31 2004 GMT
notAfter=Sep 27 23:35:31 2005 GMT
MD5 Fingerprint=FA:09:9D:04:A7:04:4A:E9:23:91:09:2A:A7:6C:DF:20

You will notice that the generated certificate will expire in one year. If you need more time, you can modify /usr/sbin/mkimapdcert directly, as it is just a shell script. You can increase the number of days to a value you find more reasonable.

 
nebula:/etc/courier# cat /usr/sbin/mkimapdcert
# ! /bin/sh
...
/usr/bin/openssl req -new -x509 -days 365 -nodes \
-config /etc/courier/imapd.cnf -out /usr/lib/courier/imapd.pem
-keyout /usr/lib/courier/imapd.pem || cleanup
...

If a year is not enough, select an appropriate value and generate your X.509 certificate.

Preventing Unencrypted Communications

If you do not wish to allow clients to communicate with Courier IMAP without using encryption, you can require Transport Layer Security (TLS). Edit /etc/courier/imapd-ssl and change IMAP_TLS_REQUIRED to 1. Additionally, if all your clients support TLS, you can disable listening on port 993 and not use SSL.

# Ok, the following settings are new to imapd-ssl:
#
#  Whether or not to start IMAP over SSL on simap port:

IMAPDSSLSTART=NO

##NAME: IMAPDSTARTTLS:0
#
#  Whether or not to implement IMAP STARTTLS extension instead:

IMAPDSTARTTLS=YES

##NAME: IMAP_TLS_REQUIRED:1
#
# Set IMAP_TLS_REQUIRED to 1 if you REQUIRE STARTTLS for everyone.
# (this option advertises the LOGINDISABLED IMAP capability, until STARTTLS
# is issued).

IMAP_TLS_REQUIRED=1

The configuration above disables access to port 993 entirely and requires encryption or clients cannot connect to port 143.

Webmail Clients and Courier IMAP Performance

If you intend to use a Webmail client with your Courier IMAP configuration, such as SquirrelMail, you may wish to install up-imapproxy. up-imapproxy caches connections between a stateless Webmail client and an IMAP server, so the Webmail client does not actually go through the overhead of logging into the IMAP server for every single transaction. On high volume deployments, it can speed things up a lot. For single user and small deployments, it isn't really necessary.

You can install up-imapproxy via apt-get.

 
nebula:~# apt-get install imapproxy

You will be asked which host to connect to for access to your real IMAP server. The default of localhost is likely acceptable. Thereafter you will want to edit /etc/imapproxy.conf. You may wish to edit listen_port and listen_address to suit your configuration. You should update your Webmail configuration to reflect the port and host you just configured up-imapproxy to use. Restart the up-imapproxy and enjoy.

Accessing Your IMAP Account From Your Mail Client

Accessing your IMAP account from your mail client of choice is usually a simple matter of adding a new account to access for mail, selecting the IMAP protocol, specifying your server's address, and your login and password to the IMAP server. You may then need to subscribe to some or all of your IMAP folders, depending on the client in question.

Many IMAP servers choose to use a NAMESPACE of . for the personal mail. Courier IMAP instead uses INBOX. as the NAMESPACE. Although RFC2342 allows a client to discover the appropriate NAMESPACE, the clients below will not strip the INBOX. preface for private mail. As a result, your actual Inbox will have your other mail folders appear as subdirectories beneath it. Many clients afford you manual remedy of explicitly specifying a path prefix. Look for it in your favorite mail client.

In Mozilla Thunderbird 0.8, but not necessarily on more recent versions, select Tools and then Account Settings. From there, Add Account…, choose Email account, then follow the wizard through until you get to the Server Information window. Select IMAP and enter your IMAP server's IP or hostname. Finish. Now, select the Server Settings entry for your newly created account. Click Use secure connection (SSL) to enable SSL. Next, click on the Advanced… button. For your IMAP server directory enter “INBOX/” without the quotes. This will ensure your folder hierarchy is displayed properly. Hit OK to complete setting up your new IMAP account.

kmail-icon.jpg

In Kmail v1.9.5, choose Settings and Configure KMail and then select the Accounts icon. Switch to the Receiving tab and then Add… to add a new account. Select the IMAP radio button. Now, enter a name for this account, a username, password, and your IMAP server's IP or hostname. From there, select the Security tab and click See What the Server Supports. KMail may respond with two warnings about the invalidity of your X.509 certificate. Accept the certificate anyway if it complains and tell it to use it forever, or for the current session, your choice. KMail should then finish determining what the server supports and should now have Use TLS for secure mail download selected by default. You're done, hit OK. (Earlier versions of KMail may decide to use SSL instead of TLS.)

Since at least KMail 1.9.x, there is no longer a way to specify the root folder to use. Therefore, when using KMail with Courier IMAP, your entire folder hierarchy will appear under a folder called inbox. In future versions of KMail, it may once again be possible to specify a root folder path. A FAQ at Courier IMAP's Web site explains the technical details.

oe6.jpg

In OutLook Express v5.5, select the Tools menu, then select Accounts. Now, select the Mail tab and click on Add. Select Mail… and go through the wizard until you come to the E-mail Server Names section. Here you'll want to enter the IP or hostname of your IMAP server and select IMAP as the server type. For Internet Mail Logon, leave the Secure Password Authentication box unchecked as you will not be using this. Finish, then select your new account from the list under the Mail tab and select Properties. Select the IMAP tab and make sure you enter Inbox as your Root folder path. This is important so the folder hierarchy shows up correctly. Then, go to the Advanced tab and check This server requires a secure connection (SSL) for your incoming mail server. If you ever modify, add or delete folders from another IMAP client, you'll need to select Reset List for your account by right clicking on it in OutLook Express' main window.

For SquirrelMail 1.4.3a, you will want to edit your /etc/squirrelmail/config.php configuration file so it knows you are using Courier IMAP. Set $imap_server_type to courier. SquirrelMail supports SSL using PHP 4.3 or later. Or you can make use of either an OpenSSH tunnel or stunnel to ensure your IMAP sessions are fully secured. The WiKi for SquirrelMail has complete details on how best to setup SquirrelMail to speak SSL.

Known Issues

Troubleshooting of some strange problems with Exim4 and Courier IMAP is presented below.

Issues with Exim4

lock file /var/spool/exim4/db/retry.lockfile: Permission denied

It's possible your Exim4 retry.lockfile may get adopted by root, as alluded to in this thread. This error is symptomatic of such an adoption:

2002-07-24 12:40:52 17XP8Z-0005i2-00 failed to open database
lock file /var/spool/exim4/db/retry.lockfile:
Permission denied (euid=8 egid=8)

Executing a

 
# chown mail:mail /var/spool/exim4/db/*

should resolve the issue – it did for me.

error in forward file (filtering not enabled)

Another error you may encounter is symptomatic of forgetting to enable user forward file filters in /etc/exim/exim4.conf, which is now enabled by default for the Debian Exim4 packages:

 2002-07-24 12:52:17 17XOsd-0005fo-00 == user@localhost
D=userforward defer (-11): error in forward file
(filtering not enabled): missing or malformed
local part (expected word or "<") in "... filter rule ..." 

Though the error mentions several problems, the actual issue is, as it states, filtering isn't enabled for user forward files.

Not a directory: stat() error for ...: Not a directory

It's also possible you might get this error, which results from a file by the same name already existing in your Maildir/:

 2002-07-28 07:36:13 17YmLM-0002bu-00 ==
/home/jasonb/Maildir/.mailinglists.EX/ <jasonb@localhost>
T=address_directory defer (20):
Not a directory: stat() error for
/home/jasonb/Maildir/.mailinglists.EX/: Not a directory 

It's often the result of forgetting to include the trailing forward slash in an Exim4 filter rule and then later adding it. In the meantime, Exim4 will happily save the mail you're directing there in mbox format instead of Maildir format. Later when you fix your filter, if you don't remember to move the mbox dot file out of the way, your mail will get frozen by Exim4.

Issues with Courier IMAP

Courier IMAP immediately disconnects client

If you're getting disconnected from Courier IMAP without any obvious error message, you might have fallen victim to your Maildir being violated. If you run tcpdump against your session, you might see something like the following output I obtained:

* OK [CAPABILITY IMAP4rev1 UIDPLUS ... ] Courier-IMAP ready. \
  Copyright 1998-2003 Double Precision, Inc. \
  See COPYING for distribution information..
0 CAPABILITY.
...
0 OK CAPABILITY completed.
1 LOGIN "jasonb" "[protected]".
1 OK LOGIN Ok..
...
14 LIST "" "INBOX.mailinglists.leap".
* LIST (\Unmarked \HasChildren) "." "INBOX.mailinglists.leap".
14 OK LIST completed..
15 STATUS "INBOX.mailinglists.leap" (UNSEEN).
* BYE [ALERT] Fatal error: No such file or directory.

At that point, the IMAP client is disconnected. However, that's not very helpful, so you may wish to run an strace on the process to investigate further.

 
nebula:~# ps auxw | grep courier
...
root 242 0.0 0.1 1476 516 ? S 00:54 0:00
/usr/sbin/couriertcpd -address=0 -stderrlogger=/usr/sbin/courierlogger
-maxprocs=40 -maxperip=4 -pid=/var/run/courier/imapd.pid -nodnslookup
-noidentlookup 143 /usr/lib/courier/courier/imaplogin
/usr/lib/courier/authlib/authdaemon /usr/bin/imapd Maildir
...
nebula:~# strace -F -f -eopen -p 242
... magic ...
[pid 807] open(".mailinglists.leap/tmp",
O_RDONLY|O_NONBLOCK|O_LARGEFILE|O_DIRECTORY) = -1 ENOENT (No such file or
directory)
...
Process 807 detached

Now, it becomes clear. Somehow, one of the necessary Maildir directories seems to have disappeared. Recreating this directory solves the problem, though not necessarily the mystery of how it disappeared.

 
jasonb@nebula:~/Maildir$ mkdir tmp
jasonb@nebula:~/Maildir$ chmod u=rwx,g=s,o= tmp/

Links and Resources

  • Courier MTA FAQ question pertaining to namespace issues – The “Inbox” thing
 
howto/exim4_courier.txt · Last modified: 2009/04/04 17:18 by jasonb
 
Recent changes RSS feed Creative Commons License Donate Powered by PHP Valid XHTML 1.0 Valid CSS Driven by DokuWiki