Purchase | Copyright © 2002 Paul Sheer. Click here for copying permissions. | Home |
This chapter effectively explains how to get LINUX up and running as a mail server. I have also included discussion on the process of mail delivery right through to retrieval of mail using POP and IMAP.
exim and sendmail are MTAs (mail transfer agents). An MTA is just a daemon process that listens on port 25 for incoming mail connections, spools [See page about spooling in general.] that mail in a queue (for exim, the /var/spool/exim/input/ directory, for sendmail, the /var/spool/mqueue/ directory), then resends that mail to some other MTA or delivers it locally to some user's mailbox. In other words, the MTA is the very package that handles all mail spooling, routing, and delivery. We saw in Section 10.2 how to manually connect to an MTA with telnet. In that example, sendmail version 8.9.3 was the MTA running on machine mail.cranzgot.co.za.
sendmail is the original and popular UNIX MTA. It is probably necessary to learn how to configure it because so many organizations standardize on it. However, because exim is so easy to configure, it is worthwhile replacing sendmail wherever you see it--there are at least three MTAs that are preferable to sendmail. I explain the minimum of what you need to know about sendmail later on and explain exim in detail.
Before we get into MTA configuration, a background in mail delivery and indexii MX recordDNSMX record handling is necessary. The sequence of events whereby a mail message (sent by a typical interactive mail client) ends up on a distant user's personal workstation is as follows:
POP and IMAP are invoked by inetd or xinetd--see Chapter 29. Except for limiting the range of clients that are allowed to connect (for security reasons), no configuration is required. Client connections authenticate themselves using the normal UNIX login name and password. There are specialized POP and IMAP packages for supporting different mailbox types (like Maildir).
The exim home page <http://www.exim.org/> gives you a full rundown. Here I will just say that exim is the simplest MTA to configure. Moreover, its configuration file works the same way you imagine mail to work. It's really easy to customize the exim configuration to do some really weird things. The whole package fits together cleanly, logically, and intuitively. This is in contrast to sendmail's sendmail.cf file, which is widely considered to be extremely cryptic and impractical. exim also seems to have been written with proper security considerations, although many people argue that postfix and qmail are the last word in secure mail.
You can get exim as a .rpm or .deb file. After installation, the file /usr/share/doc/exim-? .?? /doc/spec.txt [or /usr/doc/]contains the complete exim documentation; there is also an HTML version on the exim web page, whereas the man page contains only command-line information. exim is a drop-in replacement for sendmail, meaning that for every critical sendmail command, there is an exim command of the same name that takes the same options, so that needy scripts won't know the difference. These are:
5 |
/etc/aliases /usr/bin/mailq /usr/bin/newaliases /usr/bin/rmail /usr/lib/sendmail /usr/sbin/sendmail |
Finally, there is the exim binary itself, /usr/sbin/exim, and configuration file /etc/exim/config, /etc/exim.conf, or /etc/exim/exim.conf, depending on your LINUX distribution. Then there are the usual start/stop scripts, /etc/init.d/exim. [or /etc/rc.d/init.d/exim]
As a preliminary example, here we create a simple spooling mail server for a personal workstation, cericon.cranzgot.co.za.
Client applications (especially non-UNIX ones) are usually configured to connect to an MTA running on a remote machine, however, using a remote SMTP host can be irritating if the host or network go down. Running exim on the local workstation enables all applications to use localhost as their SMTP gateway: that is, exim takes care of queuing and periodic retries.
Here is the configuration. The difference between this and a full-blown mail server is actually very slight.
5 10 15 20 25 30 35 40 45 50 |
#################### MAIN CONFIGURATION SETTINGS ##################### log_subject errors_address = postmaster freeze_tell_mailmaster = yes queue_list_requires_admin = false prod_requires_admin = false trusted_users = psheer local_domains = localhost : ${primary_hostname} never_users = root # relay_domains = my.equivalent.domains : more.equivalent.domains host_accept_relay = localhost : *.cranzgot.co.za : 192.168.0.0/16 exim_user = mail exim_group = mail end ###################### TRANSPORTS CONFIGURATION ###################### remote_smtp: driver = smtp hosts = 192.168.2.1 hosts_override local_delivery: driver = appendfile file = /var/spool/mail/${local_part} delivery_date_add envelope_to_add return_path_add group = mail mode_fail_narrower = mode = 0660 end ###################### DIRECTORS CONFIGURATION ####################### localuser: driver = localuser transport = local_delivery end ###################### ROUTERS CONFIGURATION ######################### lookuphost: driver = lookuphost transport = remote_smtp literal: driver = ipliteral transport = remote_smtp end ###################### RETRY CONFIGURATION ########################### * * F,2h,15m; G,16h,1h,1.5; F,4d,8h end ###################### REWRITE CONFIGURATION ######################### *@cericon.cranzgot.co.za psheer@cranzgot.co.za |
The exim config file is divided into six logical sections separated by the end keyword. The top or MAIN section contains global settings. The global settings have the following meanings:
It is important to understand the host_accept_relay and relay_domains options for security. |
We never want to relay from an untrusted host. Why? Because it may, for example, allow someone to send 100,000 messages to 100,000 different addresses, each with us in the message header.
host_accept_relay specifies a list of trusted hosts that are allowed to send such arbitrary messages through us. Note again that the list is colon delimited. In this example, we don't even need to put in addresses of other machines on our LAN, except if we are feeling friendly.
The transport section comes immediately after the main configuration options. It defines various methods of delivering mail. We are going to refer to these methods later in the configuration file. Our manual telneting to port 25 was transporting a mail message by SMTP. Appending a mail message to the end of a mail folder is also a transport method. These are represented by the remote_smtp: and local_delivery: labels, respectively.
(It should be obvious at this stage what these two transports are going to be used for. As far as MTAs are concerned, the only two things that ever happen to an email message are that it either (a) gets sent through SMTP to another host or (b) gets appended to a file.)
If a message arrives and it is listed in local_domains, exim will attempt a local delivery. This means exim works through the list of directors until it finds one that does not fail. The only director listed here is the one labeled localuser: with local_delivery as its transport. So quite simply, email messages having recipient addresses that are listed under local_domains are appended to a user's mailbox file--not very complicated.
A director directs mail to a mailbox.
If a message arrives and it is not listed in local_domains, exim attempts a remote delivery. Similarly, this means exim works through the list of routers until it finds one that does not fail.
Two routers are listed here. The first is for common email addresses. It uses the lookuphost driver, which does a DNS MX query on the domain part of the email address (i.e., everything after the @). The MX records found are then passed to the remote_smtp transport (and in our case, then ignored). The lookuphost driver will fail if the domain part of the email address is a bracketed literal IP address.
The second router uses the ipliteral driver. It sends mail directly to an IP address in the case of bracketed, literal email addresses. For example, root@[111.1.1.1].
A router routes mail to another host.
An actual mail server config file contains very little extra. This one is the example config file that comes by default with exim-3.16:
5 10 15 20 25 30 35 40 45 50 55 60 65 70 75 80 |
#################### MAIN CONFIGURATION SETTINGS ##################### # primary_hostname = # qualify_domain = # qualify_recipient = # local_domains = never_users = root # host_accept_relay = localhost # host_accept_relay = my.friends.host : 131.111.0.0/16 # relay_domains = my.equivalent.domains : more.equivalent.domains host_lookup = 0.0.0.0/0 # receiver_unqualified_hosts = # sender_unqualified_hosts = rbl_domains = rbl.maps.vix.com no_rbl_reject_recipients sender_reject = "*@*.sex*.net:*@sex*.net" host_reject = "open-relay.spamming-site.com" rbl_warn_header # rbl_domains = rbl.maps.vix.com:dul.maps.vix.com:relays.orbs.org # percent_hack_domains = * end ###################### TRANSPORTS CONFIGURATION ###################### remote_smtp: driver = smtp # procmail transport goes here <--- local_delivery: driver = appendfile file = /var/spool/mail/${local_part} delivery_date_add envelope_to_add return_path_add group = mail mode = 0660 address_pipe: driver = pipe return_output address_file: driver = appendfile delivery_date_add envelope_to_add return_path_add address_reply: driver = autoreply end ###################### DIRECTORS CONFIGURATION ####################### # routers because of a "self=local" setting (not used in this configuration). system_aliases: driver = aliasfile file = /etc/aliases search_type = lsearch user = mail group = mail file_transport = address_file pipe_transport = address_pipe userforward: driver = forwardfile file = .forward no_verify no_expn check_ancestor # filter file_transport = address_file pipe_transport = address_pipe reply_transport = address_reply # procmail director goes here <--- localuser: driver = localuser transport = local_delivery end ###################### ROUTERS CONFIGURATION ######################### # widen_domains = "sales.mycompany.com:mycompany.com" lookuphost: driver = lookuphost transport = remote_smtp # widen_domains = literal: driver = ipliteral transport = remote_smtp end ###################### RETRY CONFIGURATION ########################### * * F,2h,15m; G,16h,1h,1.5; F,4d,8h end ###################################################################### |
For procmail support (see procmail(1), procmailrc(6), and procmailex(5)), simply add
|
procmail: driver = pipe command = "/usr/bin/procmail -Y -d ${local_part}" |
after your remote_smtp transport, and then also,
|
procmail: driver = localuser transport = procmail require_files = /usr/bin/procmail |
after your user_forward director.
As with other daemons, you can stop exim, start exim, and cause exim to reread its configuration file with:
|
/etc/init.d/exim stop /etc/init.d/exim start /etc/init.d/exim reload |
You should always do a reload to cause config file changes to take effect. The startup script actually just runs exim -bd -q30m, which tells exim to start as a standalone daemon, listening for connections on port 25, and then execute a runq (explained below) every 30 minutes.
To cause exim [and many other MTAs for that matter] to loop through the queue of pending messages and consider each one for deliver, run
|
runq |
which is the same as exim -q.
To list mail that is queued for delivery, use
|
mailq |
which is the same as exim -bp.
To forcibly attempt delivery on any mail in the queue, use
|
exim -qf |
and then to forcibly retry even frozen messages in the queue, use
|
exim -qff |
To delete a message from the queue, use
|
exim -Mrm <message-id> |
The man page exim(8) contains exhaustive treatment of command-line options. Those above are most of what you will use, however.
It is often useful to check the queue directory /var/spool/exim/input/ for mail messages, just to get an inside look at what's going on. The simple session--
5 10 |
[root@cericon]# mailq 0m 320 14Epss-0008DY-00 <psheer@cranzgot.co.za> freddy@elmstreet.org 0m 304 14Ept8-0008Dg-00 <psheer@cranzgot.co.za> igor@ghostbusters.com [root@cericon]# ls -l /var/spool/exim/input/ total 16 -rw------- 1 root root 25 Jan 6 11:43 14Epss-0008DY-00-D -rw------- 1 root root 550 Jan 6 11:43 14Epss-0008DY-00-H -rw------- 1 root root 25 Jan 6 11:43 14Ept8-0008Dg-00-D -rw------- 1 root root 530 Jan 6 11:43 14Ept8-0008Dg-00-H |
--clearly shows that two messages are queued for delivery. The files ending in -H are envelope headers, and those ending in -D are message bodies. The spec.txt document will show you how to interpret the contents of the header files.
Don't be afraid to manually rm files from this directory, but always delete them in pairs (i.e., remove the both the header and the body file), and make sure exim is not running at the time. In the above example, the commands,
5 |
[root@cericon]# exim -Mrm 14Epss-0008DY-00 14Ept8-0008Dg-00 Message 14Epss-0008DY-00 has been removed Message 14Ept8-0008Dg-00 has been removed [root@cericon]# mailq [root@cericon]# |
work even better.
Often, we would like certain local addresses to actually deliver to other addresses. For instance, we would like all mail destined to user MAILER-DAEMON to actually go to user postmaster; or perhaps some user has two accounts but would like to read mail from only one of them.
The /etc/aliases file performs this mapping. This file has become somewhat of an institution; however you can see that in the case of exim, aliasing is completely arbitrary: you can specify a lookup on any file under the system_aliases: director provided that file is colon delimited.
A default /etc/aliases file could contain as much as the following; you should check that the postmaster account does exist on your system, and test whether you can read, send, and receive mail as user postmaster.
5 10 15 20 25 30 35 40 45 |
# This is a combination of what I found in the Debian # and RedHat distributions. MAILER-DAEMON: postmaster abuse: postmaster anonymous: postmaster backup: postmaster backup-reports: postmaster bin: postmaster daemon: postmaster decode: postmaster dns: postmaster dns-admin: postmaster dumper: postmaster fetchmail-daemon: postmaster games: postmaster gnats: postmaster ingres: postmaster info: postmaster irc: postmaster list: postmaster listmaster: postmaster lp: postmaster mail: postmaster mailer-daemon: postmaster majordom: postmaster man: postmaster manager: postmaster msql: postmaster news: postmaster nobody: postmaster operator: postmaster postgres: postmaster proxy: postmaster root: postmaster sync: postmaster support: postmaster sys: postmaster system: postmaster toor: postmaster uucp: postmaster warnings: postmaster web-master: postmaster www-data: postmaster # some users who want their mail redirected arny: mail@swartzneger.co.us larry: lking@cnn.com |
You can remove a lot of these aliases, since they assume services to be running that might not be installed-- games, ingres, for example. Aliases can do two things: firstly, anticipate what mail people are likely to use if they need to contact the administrator; and secondly, catch any mail sent by system daemons: for example the, email address of the DNS administrator is dictated by the DNS config files, as explained on page .
Note that an alias in the /etc/aliases file does not have to have an account on the system-- larry and arny need not have entries in the /etc/passwd file.
Spam refers to unsolicited [Not looked for or requested; unsought]bulk mail sent to users usually for promotional purposes. That is, mail is sent automatically to many people with whom the sender has no relationship, and where the recipient did nothing to prompt the mail: all on the chance that the recipient might be interested in the subject matter.
Alternatively, spam can be thought of as any mail sent to email addresses, where those addresses were obtained without their owners consent. More practically, anyone who has had an email account for very long will have gotten messages like Subject: Fast way to earn big $$$!, which clutters my mailbox. The longer you have an email address, the more of these messages you will get, and the more irritated you will get.
To send spam is easy. Work your way around the Internet till you find a mail server that allows relaying. Then send it 10,000 email addresses and a message about where to get pictures of naked underage girls. Now you are a genuine worthy-of-being-arrested spammer. Unfortunately for the unsuspecting administrator of that machine and provided you have even a little clue what you're doing, he will probably never be able to track you down. Several other tricks are employed to get the most out of your $100-for-1,000,000-genuine-email-addresses.
Note that spam is not merely email you are not interested in. People often confuse mail with other types of communication... like telephone calls: if you get a telephone call, you have to pick up the phone then and there--the call is an an invasion of your privacy. The beauty of email is that you never need to have your privacy invaded. You can simply delete the mail. If you never want to get email from a particular person again, you can simply add a filter that blocks mail from that person's address (see procmailex(5)). [If you are irritated by the presumption of the sender, then that's your problem. Replying to that person with ``Please don't email me...'' not only shows that you are insecure, but also that you are clueless, don't get much mail, and are therefore also unpopular.]
The point at which email becomes intrusive is purely a question of volume, much like airwave advertisements. Because it comes from a different place each time, you cannot protect yourself against it with a simple mail filter.
Typical spam mail will begin with a spammer subject like Create Wealth From Home Now!! and then the spammer will audaciously append the footer:
This is not a SPAM. You are receiving this because you are on a list of email addresses that I have bought. And you have opted to receive information about business opportunities. If you did not opt in to receive information on business opportunities then please accept our apology. To be REMOVED from this list simply reply with REMOVE as the subject. And you will NEVER receive another email from me.
Need I say that you should be wary of replying with REMOVE, since it clearly tells the sender that your email is a valid address.
You can start by at least adding the following lines to your MAIN configuration section:
|
headers_check_syntax headers_sender_verify sender_verify receiver_verify |
The option headers_check_syntax causes exim to check all headers of incoming mail messages for correct syntax, failing them otherwise. The next three options check that one of the Sender:, Reply-To: or From: headers, as well as both the addresses in the SMTP MAIL and RCPT commands, are genuine email addresses.
The reasoning here is that spammers will often use malformed headers to trick the MTA into sending things it ordinarily wouldn't, I am not sure exactly how this applies in exim's case, but these are for the good measure of rejecting email messages at the point where the SMTP exchange is being initiated.
To find out a lot more about spamming, banning hosts, reporting spam and email usage in general, see MAPS (Mail Abuse Prevention System LLC) <http://www.mail-abuse.org/>, as well as Open Relay Behavior-modification System <http://www.orbs.org/>. [If this site is not working, there is also http://www.orbl.org/ and http://www.ordb.org/.]Real-time Blocking Lists or RBL's are a not-so-new idea that has been incorporated into exim as a feature. It works as follows. The spammer has to use a host that allows relays. The IP of that relay host will be clear to the MTA at the time of connection. The MTA can then check that against a database of publicly available banned IP addresses of relay hosts. For exim, this means the list under rbl_domains. If the rbl_domains friendly has this IP blacklisted, then exim denies it also. You can enable this capability with [This example comes from exim's front web page.]
5 10 |
# reject messages whose sending host is in MAPS/RBL # add warning to messages whose sending host is in ORBS rbl_domains = blackholes.mail-abuse.org/reject : \ dialups.mail-abuse.org/reject : \ relays.mail-abuse.org/reject : \ relays.orbs.org/warn # check all hosts other than those on internal network rbl_hosts = !192.168.0.0/16:0.0.0.0/0 # but allow mail to postmaster@my.dom.ain even from rejected host recipients_reject_except = postmaster@my.dom.ain # change some logging actions (collect more data) rbl_log_headers # log headers of accepted RBLed messages rbl_log_rcpt_count # log recipient info of accepted RBLed messages |
in your MAIN configuration section. Also remember to remove the line no_rbl_reject_recipients; otherwise, exim will only log a warning message and not actually refuse email.
Mail administrator and email users are expected to be aware of the following:
sendmail's configuration file is /etc/sendmail.cf. This file format was inherited from the first UNIX servers and references simpler files under the directory /etc/mail/. You can do most ordinary things by editing one or another file under /etc/mail/ without having to deal with the complexities of /etc/sendmail.cf.
Like most stock MTAs shipped with LINUX distributions, the sendmail package will work by default as a mailer without any configuration. However, as always, you will have to add a list of relay hosts. This is done in the file /etc/mail/access for sendmail-8.10 and above. To relay from yourself and, say, the hosts on network 192.168.0.0/16, as well as, say, the domain hosts .trusted.com, you must have at least:
5 |
localhost.localdomain RELAY localhost RELAY 127.0.0.1 RELAY 192.168 RELAY trusted.com RELAY |
which is exactly what the host_accept_relay option does in the case of exim.
The domains for which you are acting as a backup mail server must be listed in the file /etc/mail/relay-domains, each on a single line. This is analogous to the relay_domains option of exim.
Then, of course, the domains for which sendmail is going to receive mail must also be specified. This is analogous to the local_domains option of exim. These are listed in the file /etc/mail/local-host-names, each on a single line.
The same /etc/aliases file is used by exim and sendmail.
Having configured anything under /etc/mail/, you should now run make in this directory to rebuild lookup tables for these files. You also have to run the command newaliases whenever you modify the /etc/aliases file. In both cases, you must restart sendmail.
sendmail has received a large number of security alerts in its time. It is imperative that you install the latest version. Note that older versions of sendmail have configurations that allowed relaying by default--another reason to upgrade.
A useful resource to for finding out more tricks with sendmail is The Sendmail FAQ <http://www.sendmail.org/faq/>.