Setting up a mail server
Background
Some terminology:
- MTA: Mail Transport Agent
- MUA: Mail User Agent
- MDA: Mail Delivery Agent
- SMTP: Simple Mail Transfer Protocol
- MX: Mail eXchange
- POP: Post Office Protocol
- IMAP: Internet Message Access Protocol
With SMTP you connect to a server and send two things: envelope and message.
The envelope looks like this:
MAIL FROM: <enrico@enricozini.org> RCPT TO: <rms@fsf.org> RCPT TO: <linus@linux.org>
The message looks like this:
From: <enrico@enricozini.org> To: <rms@fsf.org> Cc: <linus@linux.org> Message-ID: <1234567@enricozini.org> Subject: Test mail Hi Richard, this is a test mail. I'm also writing Linus to show how to send to more people. Cheers, Enrico
There is no authentication.
There is no encryption.
Two usual types of access control:
- Outbound e-mail is normally only accepted from an internal network
- Inbound e-mail is normally accepted from anywhere
The DNS is used to find the SMTP server to use to send a message:
$ host -t MX yahoo.com yahoo.com MX 10 smtp1.yahoo.com yahoo.com MX 20 smtp2.yahoo.com yahoo.com MX 20 smtp3.yahoo.com
The process of sending an E-Mail:
-
Enrico writes an E-Mail:
From: Enrico Zini <enrico@enricozini.org> To: Richard Stallman <rms@fsf.org> Subject: Hello from Addis Hi Richard, Addis is a wonderful city, even if it rains a lot. Bye, Enrico
-
Enrico's MUA connects to the SMTP server (for example, port 25 of smtp.aau.edu.et):
HELO enricozini.org 200 OK Hello enricozini.org MAIL FROM: <enrico@enricozini.org> 200 OK Mail from enrico@enricozini.org RCPT TO: <rms@fsf.org>
Here, the SMTP server performs relay control: "do we relay mail to rms@fsf.org?":
- Outbound e-mail is normally only accepted from an internal network
- Inbound e-mail is normally accepted from anywhere
A target address could be refused:
413 ERR I don't relay for rms@fsf.org
In this case, the destination is not local but the recipient is accepted because I'm inside the local network:
200 OK Destination rms@fsf.org DATA 200 OK Please send message body From: Enrico Zini <enrico@enricozini.org> To: Richard Stallman <rms@fsf.org> Subject: Hello from Addis Date: Mon, 17 Jul 2006 09:49:45 +0300 Message-ID: <124372643@enricozini.org> Hi Richard, Addis is a wonderful city, even if it rains a lot. Bye, Enrico . 200 OK Message accepted QUIT 200 OK Bye.
-
The SMTP server needs to find out where to send the message, using the DNS:
$ host -t MX fsf.org fsf.org MX 10 mail.fsf.org fsf.org MX 20 mail.gnu.org
-
So the SMTP server tries the first one and connects to port 25 of
mail.fsf.org
:HELO smtp.aau.edu.et 200 OK Hello smtp.aau.edu.et MAIL FROM: <enrico@enricozini.org> 200 OK Mail from enrico@enricozini.org RCPT TO: <rms@fsf.org>
The destination is accepted because it's for a local user::
200 OK Destination rms@fsf.org DATA 200 OK Please send message body From: Enrico Zini <enrico@enricozini.org> To: Richard Stallman <rms@fsf.org> Subject: Hello from Addis Date: Mon, 17 Jul 2006 09:49:45 +0300 Message-ID: <124372643@enricozini.org> Received: by mail.aau.edu.et on Mon, 17 Jul 2006 09:55:53 +0300 from 10.4.15.158 Hi Richard, Addis is a wonderful city, even if it rains a lot. Bye, Enrico . 200 OK Message accepted QUIT 200 OK Bye.
-
Now, mail.fsf.org will invoke a MDA to write the mail in Richard Stallman's mailbox.
Example of problems with mail handling:
- Accepting inbound connections:
- Malicious input:
- logic errors
- buffer overflows
- DoS (Denial Of Service) attacks
- Connection floods
- Performing outbound connections:
- Programming errors:
- Flooding of connections
- Performing routing:
- Unauthorised relays
- Mail loops
- Writing to the local hard drive:
- Filling up the hard drive
- Writing to the wrong files
- Writing to the local hard drive as root:
- In case of error or attack, any file in the system can potentially be compromised
RFC-822 is the original standard for E-mail. RFCs are standard Internet documents. Have a look at RFC documents released the 1st of April.
postfix
Common setup: "Internet site with smarthost".
More difficult to maintain: "Internet site".
A smarthost is a machine that will relay e-mail for you.
Questions asked with "Internet site with smarthost":
- Mail name: aau.edu.et (name used to publicly identify the mail server)
- Smarthost name: smtp.telecom.net.et (SMTP server that will relay our e-mail)
To test a mail server::
$ telnet localhost 25
HELO me
MAIL FROM: <a@b.c>
RCPT TO: <mail@of.a.local.user>
DATA
hi
.
QUIT
By default, you find locally delivered mail in /var/mail/username
.
Postfix configuration files:
/etc/postfix/master.cf
: configures how all the postfix components run together (man 5 master
)/etc/postfix/main.cf
: Main postfix configuration (man 5 postconf
)
To rewrite addresses:
-
In
/etc/postfix/main.cf
::canonical_maps = hash:/etc/postfix/canonical
-
Then in
/etc/postfix/canonical
you can add the rewrite rules, like::enrico enrico@enricozini.org
-
When
/etc/postfix/canonical
is modified you need to regenerate the index::sudo postmap canonical
(same is when you change the alias file:
sudo postalias /etc/aliases
)
(see file:///usr/share/doc/postfix/html/ADDRESS_REWRITING_README.html
)
Manipulating the message queue:
mailq
- List the mail queue.
Example::
mailq
postqueue
- Postfix queue control
Examples::
# Like mailq postqueue -p # Tries to send every message in the queue postqueue -f # Tries to send every message in the queue for that site postqueue -s site
postsuper
- Postfix superintendent
Examples::
# Deletes one message sudo postsuper -d 7C4D2EC0F5D # Deletes all messages held in the queue for later delivery sudo postsuper -d ALL deferred
Different mail queues in postfix:
- incoming: mail who just entered the system
- active: mail to be delivered
- deferred: mail to be delivered later because there were problems
- hold: mail that should not be delivered until released from hold
Mail logs are in::
/var/log/mail.log /var/log/mail.err /var/log/mail.info /var/log/mail.warn
Mail delivery
Mailbox formats:
- mbox: single file, mail separated by "From " lines
- maildir: one directory per folder, one file per mail
- mh: similar to maildir, but not really used
Alternate MDA: procmail
: allows to filter mail automatically into different
folders.
Mail forwarding with ~/.forward
: allows to redirect mail to a different
address: just put the address you want to send to in the file ~/.forward
.
POP or IMAP server
Installation:
apt-get install dovecot
Configuration is in::
/etc/dovecot/dovecot.conf
The main thing that is needed is to enable the mail protocols you want::
protocols = imaps
Server monitoring
To make all sorts of graphs::
apt-get install munin munin-node
Example: http://munin.ping.uio.no
To compute more statistics:
- anteater
- isoqlog
- mailgraph
Monitor system logs: logcheck:
- sends you mail with abnormal log lines
- It's important to customize what is normal and you do it with regular expressions
Filtering viruses and spam
clamav - Virus scanner
Virus scanning:
- Postfix gives the mail to clamav that scans it and gives it back if it's clean.
- Strategies for infected mail:
- silently delete it
- refuse the mail and send a notification to the sender
- refuse the mail and send a notification to the receiver
- quarantine the e-mail
- refuse delivery with a SMTP error
- deliver with an extra header that says that it's a virus
spamassassin - Spam filter
Spam scanning:
- Postfix gives the mail to spamd that scans it and gives it back with some spam information.
- Strategies for spam mail:
- silently delete it
- refuse the mail and send a notification to the sender
- refuse the mail and send a notification to the receiver
- quarantine the e-mail
- refuse delivery with a SMTP error
- deliver with an extra header that says that it's spam
- New techniques:
- greylisting: when you receive a mail from a host you've never seen before, refuse it with a temporary error, and accept it the second time (after some time delay). Spammers normally don't retry, and implementing retry would increase their cost of sending e-mail.
- crossassassin: if more than some amount of your users receive a mail with the same message ID, throw it away. Sending mails with different headers would increase the cost of sending e-mail.
Man pages and sections
Man pages are divided in sections:
man man
shows all the sections of the manpagesman 5 postconf
shows the postconf manpage in the "configuration file" section- Normally manpages are referred as manpage(section) (e.g.
postconf(5)
)
Authentication and encryption with SMTP (update by Marius Gedminas)
You can have authentication and encryption with SMTP:
Cheat sheet
Setting up the client (I assume Ubuntu)
# vi /etc/postfix/main.cf relayhost = [hostname.of.your.ISPs.smtp.server] smtp_use_tls = yes smtp_enforce_tls = yes smtp_tls_enforce_peername = no smtp_sasl_auth_enable = yes smtp_sasl_password_maps = hash:/etc/postfix/smtp_auth smtp_sasl_security_options = noanonymous # vi /etc/postfix/smtp_auth [hostname.of.your.ISPs.smtp.server] username:password # chmod 600 /etc/postfix/smtp_auth # postmap /etc/postfix/smtp_auth # postfix reload
(It would be a good idea to make the client verify the server's certificate to prevent man-in-the-middle attacks, but I haven't figured out that part yet...)
Setting up the server
# apt-get install sasl2-bin libsasl2-modules # saslpasswd2 -u hostname.of.the.server -c username1 # saslpasswd2 -u hostname.of.the.server -c username2 ... these commands create /etc/sasldb2 # echo "pwcheck_method: auxprop" > /etc/postfix/sasl/smtpd.conf # touch /var/spool/postfix/etc/sasldb2 # echo mount --bind /etc/sasldb2 /var/spool/postfix/etc/sasldb2 \ > /etc/init.d/local-sasl-for-postfix # chmod +x /etc/init.d/local-sasl-for-postfix # ln -s ../init.d/local-sasl-for-postfix /etc/rc2.d/S19local-sasl-for-postfix # /etc/init.d/local-sasl-for-postfix # adduser postfix sasl these commands let postfix (which runs chrooted) access /etc/salsdb2 # cd /etc/postfix # openssl req -new -outform PEM -out smtpd.cert -newkey rsa:2048 -nodes \ -keyout smtpd.key -keyform PEM -days 365 -x509 # chmod 600 smtpd.key these commands create a self-signed SSL certificate # vi main.cf smtpd_sasl_auth_enable = yes broken_sasl_auth_clients = yes smtpd_sasl_local_domain = hostname.of.the.server smtpd_recipient_restrictions = permit_mynetworks, permit_sasl_authenticated, reject_unauth_destination smtpd_use_tls = yes smtpd_tls_cert_file = /etc/postfix/smtpd.cert smtpd_tls_key_file = /etc/postfix/smtpd.key # /etc/init.d/postfix restart