Welcome to LITTLEWHITEDOG.COM
 Telling it like it is...    
Navigation
· Home
· Articles
· Chat
· Downloads
· Forum
· Journal
· Search
· Stories Archive
· Submit News
· Surveys
· Topics
· Web Links
· Your Account

Distributed Computing
· SETI Team News
· SETI Team Info
· Folding Team News
· Folding Team Info

Social Bookmark

del.icio.us

How To Install a Secure BSD System - Part 2





Author: soup4you2
Posted on: 9/21/2003
Discuss: In the forums



Unix File Permissions
One aspect of a Unix system security is putting control on users. There are several different types of controls that can be used, including file permissions, file attributes, file system quotas and system resource limits.

Unix file permissions are a way to allow a user to restrict access to a file or directory on the file system. For files, a user can specify who can read the file, who can write to the file and who can execute the file. For directories, a user can specify who can read the directory, who can write to the directory and who can execute programs located in the directory.

Files
Let's look at a simple example of a file.
($:~)=> ls -a example.txt
-rw-rw-r-- 1 soup4you2 soup4you2 852B Feb 22 00:26 example.txt
Here we execute ls -l. The ls command lists the contents of the directory, or in this case, only the file example.txt the -l option lists the file in long form, which displays quite a bit of information about the file. The output lists the following info:
-rw-rw-r-- 1 soup4you2 soupx 852B Feb 22 00:26 note.txt
Here's a breakdown of what’s being displayed here:
-rw-rw-r-- Permissions
1 Number of links
soup4you2 File Owner
soupx Group
852B File size
Feb 22 00:26 Date last modified
example.txt Filename
Notice that this file has one owner (soup4you2) and belongs to one group (users). The owner and group are important when we discuss file permissions.

The file permissions are as follows:
-rw-rw-r--
The information is divided into four parts
- File Type
rw- Owner Permissions
rw- Group Permissions
r-- World Permissions
The first part of the output is the file type. Common file types are as follows:
- A Normal File
d A Directory
l A Symbolic link
s A Socket
Following the file type are three groups of these characters representing the permissions for the owner group and world. Three characters indicate whether or not permission is granted to read the file (r), write to the file (w), or execute the file (x). If permission is granted, the letter is present. If permission is denied, the letter is, well, you guessed it sparky, not there and a (-) in it's place. Here's another example
rwxr-x--x
The first three characters are the permissions for the owner. The permissions rwx indicate that the owner can read the file, write to the file and execute the file. The next three characters are the permissions for the group associated with the file. The next three characters are the permissions for the group associated with the file. The permissions r-x indicates that members of the group can read the file and execute the file but cannot write to the file. The last three characters are the permissions for the rest of the world. Cannot read the file and cannot write to the file but can execute the file. Getting this yet? It only gets more fun from here.

Take notice that the three permissions are either granted or denied, either on or off (I’ve got to get specific.. you might be a slobbering drunk who needs all the help they can get). Since the permissions can be considered either on or off the permissions can be thought of as collection of 0s or 1s. For instance "rwx" has read, write and execute permissions on. Therefore we can write these permissions as "111", and in octal format the value is 7. Similarly "r-x" has read permissions and execute permissions on and write off. Therefore we can write these permissions as 101 and in octal format the value is 5.

If we put this idea in practice for owner/group/world permissions, then the permissions rwxr-x--x in binary format are 111101001, and if we treat this as a series of three groups of octal numbers, the value is 750

Confused yet? Let me try to clarify just a little bit here.

Read Permissions - you should give a value of 4 Write Permissions - you should give a value of 2 Execute Permissions - you should give a value of 1

So if you want read+execute permissions, add 4 + 1 and get 5. You do this for each of the 3 parts user/group/other

U = User G = Group O = Other (not U or G)

Triplet for u: rwx => 4 + 2 + 1 = 7
Triplet for g: r-x => 4 + 0 + 1 = 5
Tripler for o: r-x => 4 + 0 + 1 = 5
Which makes : 755

-U- --G-- --O--
-rwxr-xr-x 1 nick users 382 Jan 19 11:49
-drwxr-xr-x 3 nick users 1024 Jan 19 11:19 lib/
-rwxr-xr-x 1 nick users 1874 Jan 19 10:23 socktest.pl

Everything goes by 4 2 1

Changing File Permissions
The chmod command changes file permissions. You would use it like so:
chmod mode file [file ...]
To see how to use chmod, let's look at a file lying around.
($:~)=> ls -l a.txt
-rw-rw-r-- 1 soupx users 10 Sep 03 06:50 a.txt
To change the permissions to an explicit mode, use the octal method:
($:~)=> chmod 751 a.txt
($:~)=> ls -l a.txt
-rwx--x--x 1 soupx users 10 Sep 03 06:50 a.txt
Do you see how the permissions 751 translated into rwxr-x-x. And look at this if you're feeling saucy enough.
($:~)=> chmod 640 a.txt
($:~)=> ls -l a.txt
-rw-r----- 1 soupx users 10 Sep 03 06:50 a.txt
Here, 640 translates to rw-r----- You can also use the chmod command in symbolic mode as follows (even though I don’t care too much for this way):
($:~)=> chmod +x a.txt
($:~)=> ls -l a.txt
-rwxr-x--x 1 soupx users 10 Sep 03 06:50 a.txt
This time, chmod is used with +x which means to add executable permissions where the + character is used. It means to add the permissions whereas - character means to remove. Here, +x means to add executable permissions for the owner, group and world. The chmod command can also be used to change permissions for a specific group:
($:~)=> chmod g-r a.txt
($:~)=> ls -l a.txt
-rwx--x--x 1 soupx users 10 Sep 03 06:50 a.txt
This shows chmod being executed with g-r which means "remove group executable permissions." Are you getting tired of my bad spelling yet, or have you drunk enough to where you just don’t care anymore? (proofreader thinks, "Yes", even though spelling/grammar corrections were made, and opens another brewski)

Sticky Bits
If a user has write permissions to a directory that user can delete files and directories within, even if those files are not owned by the user and permissions are set so that the user cannot read or write the file:
($:~)=> ls -ld temp
($:~)=> ls -l a.txt
drwxrwxrwx 1 soupx users 10 Sep 03 06:50 temp
We see here that the temp directory is owned by "soupx", yet writeable by the world. This is bad because somebody else not in the group or owner can delete the file even though they cannot see it. Since I’m a few beers into this, I’m going to skip right along to our next topic.

Default Permissions and Umask
When a user creates a file or directory, that file or directory is given default permissions:
($:~)=> touch a.txt
($:~)=> mkdir testdir
($:~)=> ls -l
total 1
-rw-rw-r-- 1 soupx users 10 Sep 03 06:50 a.txt
drwxrwxr-x 1 soupx users 10 Sep 03 06:50 testdir
Notice that the default permissions for the user soupx are 644 for files and 775 for directories. Default file and directory permissions are set according to the value of the users umask value. The umask value is due to mask off bits from the most permissive default values, 666 for files and 777 for directories. To display your umask, just type in umask
($:~)=> umask
002
The user soupx has a umask value of 002. An easy way to determine the value of soupx's default permissions when soupx creates a file or directory, is to simply subtract the value of umask from the system default permission values.
Files: Directories
666 777
002 002
664 775
To change your default permission change your umask value to create the most restrictive permission, use a value of 777 which would give out the equivalent of 000 permissions. Of course, this is too restrictive since soupx does not have read and write permissions for new files (pretty lame, ehh?). To create files and directories with the most practical restrictive permissions, use a umask value of 077 which will grant read/write/execute for the owner but nothing for the group or world. So it would retain file permissions values of 700. If you wish to change your umask value permanently, add it in to your users login profile.

The easiest way to figure out what umask to use is to take the octal number and subtract it from 777. So, if you wanted all new files to be created in your directory as 754 , subtract that from 777, 777-754=023.

A default mode of 755 would be 777-755 = 022. This is the default umask on most systems as far as I know.

File and directory Flags
The chflags utility comes in very handy when dealing with system security. This utility will place various restrictions on a file on top of their permission values.

Flags are a comma-separated list of keywords that are defined as:
sappnd - set the system append-only flag (superuser only)
This is the system append-only flag. And can only be set and removed by the root user. Files with this flag can be added but cannot be removed or otherwise edited (a particularly useful feature for log files). Setting sappnd on a .history file can be interesting in the event of a system compromise. A popular script kiddie trick is to remove .history or link it to /dev/urandom so that the sysadmin cannot see what was done, but sappnd prevents this tactic from working without changing any file system permissions on the .history file itself. This flag cannot be removed when the system is at securelevel 1 or higher.

schg - set the system immutable flag (superuser only)
The system-level immutable flag can only be set or removed by root. Files with this flag set cannot be changed in any way: not edited, not moved and not replaced. Basically, the kernel will prevent all attempts to touch this file. This flag cannot be removed when the system is running at securelevel 1 or greater.

uappnd - set the user append-only flag (owner or superuser only)
Only the file owner or root can set the user append-only flag. Like the system append-only flag, sappnd, a file with this flag set can be added to but not otherwise edited or removed. This is most useful for logs from personal programs and the like and is primarily a means users can employ to prevent vital files from accidental removal. The user or root may perform this flag at any time.

uchg - set the user immutable flag (owner or superuser only)
Only the owner or root can set the user's immutable flag. Like the schg flag, the user immutable flag prevents a user from changing the file. Again, root can override this, and the user at any securelevel can remove it. An immutable file may not be changed, moved or deleted. An append-only file is immutable except that data may be appended to it. Putting the letters "no" before a flag name causes the flag to be turned off.

For example:
nouchg the immutable bit should be cleared.
The superuser-settable "sappnd" and "schg" flags can be set at any time, but may only be cleared when the system is running at security level 0 or -1 (insecure or permanently insecure mode, respectively). The securelevel is normally set to 0, for example, when running in single-user mode.

Symbolic links do not have flags, so unless the -H or -L option is set, chflags on a symbolic link always succeeds and has no effect. The -H, -L, and -P options are ignored unless the -R option is specified. In addition, these options override each other and the command's actions are determined by the last one specified.

Only the superuser can change the user flags on block and character de-vices. You can use ls -lo to see the flags of existing files. These are just a couple of the flags available. I recommend reading man chflags more for a list of possible flags and their meanings.

The information about chflags was taken from the chflags manpage. And other absolute OpenBSD

Installing and Configuring Mail Services
If you are after one badass secure mail server, then this section is for you. Sendmail is installed by default on FreeBSD systems and unless configured properly, it is extremely insecure. So what I’m going to attempt here is setting up:
  • Postfix With Qmail Maildir support
  • Courrier IMAP / POP3 with IMAP and POP though SSL
  • Procmail
  • SPAMassasin
  • Amavis Virus scanning
  • Virtual domain support
  • Cyrus SASL/TLS authentication, Along With Postfix SSL
I will go into configuring most of these. But for some of these, you’re going to have to do a bit of tweaking and playing around. Installing and Configuring Postfix
Let's start off by installing our new mail server postfix. Use the ports luke.
($:~)=> cd /usr/ports/mail/postfix
($:~)=> make install clean
To avoid any confusion with other applications that use postfix we're going to make a quick symbolic link.
($:~)=> ln -s /usr/local/etc/postfix /etc/postfix
Now let's configure this puppy. Thanks to elmore at screamingelectron.org for providing the configuration we will be using here. We'll start off by going into your postfix directory and editing main.cf with your favorite editor.
($:~)=> vi main.cf
The first thing you're going to modify is the following line:
"myhostname = your.servername.here"
This line will set the mail server host name of your box. This cannot be any arbitrary name; it MUST be a fully qualified domain name!!

The next line to modify is:
"mydomain = some.domain.name"
Again this sets the default domain of the box and must be a Fully Qualified Domain Name Here!

The next line to look at is the following:
"myorigin = $mydomain"
Make sure this variable is set correctly! "$mydomain" is a valid global variable for the file so you should be good with that!

The next line to modify is:
"mydestination = $myhostname, localhost.$mydomain $mydomain virtualdomain1 virtual domain2"
Obviously, this example assumes you'll be setting up virtual domains. It also assumes you'll be setting up sendmail style virtual domains. I know the file says to use the virtual file instead, but I don't do that. I specify here, sendmail style, and if do not want to do that that's fine with me. Just understand in this how-to that we'll be setting up sendmail style virtual domains.

Moving On, the next line to modify is the following:
"home_mailbox = Maildir/"
DO NOT uncomment this line if you do not intend to use imap. If you are using pop or traditional /var/mail spool to deliver mail this is not needed and will undoubtedly mess up your mail delivery. If you are using courier-imap, this line needs to be uncommented!

Moving right along, the next line to modify is the:
"relay_domains = $mydestination, 127.0.0.1"
This will only allow messages to be accepted where the final destination domain is on this box. It also allows delivery over the loopback interface!

Now, modify the following:
"mynetworks = xxx.xxx.xxx.xxx/zz, 127.0.0.1"
This only allows mail to be sent out to the Internet from the specified ips! This can be an entire subnet or just one box - you decide.

This brings us to the next lines to modify:
"local_destination_concurrency_limit = 2"
"default_destination_concurrency_limit = 10"
These lines limit the amount of concurrent connections to a domain. Good to have especially if you have a user that is forwarding mail out of his home via the use of a .forward file.

The next lines I actually insert into the file. They are for the canonical maps. You'll need these if the following is true:

You have virtual domains
You have virtual usernames like full.name@somehost.com mapped back to username@somehost.com
If you’re using one of the above, add it in. If not, don't worry about it!
"sender_canonical_maps = hash:/etc/postfix/canonical"
"recipient_canonical_maps = hash:/etc/postfix/canonical-receive"
We'll be going over canonical tables in more depth in a little while. For now what you need to know is that on table modifies, the incoming mail and one will modify outgoing mail.

The following lines I also add - you may or may not want to add these, depending on how true you want to be to the rfc and how strict you want to be on other hosts trying to send mail to you! These lines will lay down the framework for cutting down on your SPAM!
smtpd_client_restrictions = reject_rbl_client, check_client_access hash:/etc/postfix/client_access, reject_unauth_pipelining

smtpd_recipient_restrictions = regexp:/etc/postfix/regexp_access, check_recipient_access hash:/etc/postfix/access, permit_mynetworks,reject_unknown_recipient_domain, reject_unknown_hostname, reject_rbl_client, reject_unauth_pipelining, reject

smtpd_sender_restrictions = regexp:/etc/postfix/sender_checks.regexp, check_sender_access hash:/etc/postfix/sender_access, reject_unknown_sender_domain, reject_non_fqdn_sender, reject_rbl_client, reject_unauth_pipelining
(That should be 3 lines. Thought I would mention that to avoid future frustrations)

Ok, the first section specifies rejection if a client is not in an access list. An access list is a list I use which details the exact usernames on the box. This list is a necessity if you are running virtual domains. If you don't use it userid1@virtualdomain1 can receive an e-mail to userid1@virtualdomain2 and so on and so forth. This is the most efficient way I know to block this! It is also a good practice to do even if you aren't running virtual domains (opinion). It also specifies a lookup to the rbl list (a real time black hole list for open-relay mail servers). It also does not allow unauthorized pipelining, not exactly sure why that's needed, but it is. If you know, let me know!

The second section does much of the same but is for outside connections (people trying to send mail in). It specifies a regular expression file which sorts through the headers and looks for junk, the access list, and rejects mail from computers that don’t have a fqdn. It also rejects if it can't get the computer hostname through nslookup, and rejects via the rbl list and the pipelining again!

Ok, the next section is a lot more of the same. Nothing really new to explain here!

The next line I add is my rbl line, defining what list to use. I personally use the ordb list which can be found at http://ordb.org (I like it a lot and it's free!)
"maps_rbl_domains = relays.ordb.org"
The next things added are the following body and header checks. They specify lookup files to run against all incoming and outgoing messages!
"header_checks = regexp:/etc/postfix/header_checks"
"body_checks = regexp:/etc/postfix/body_checks"
The final things I add are a couple of reject codes and a message size limit (self-explanatory). Here they are!
"unknown_hostname_reject_code = 554"
"unknown_client_reject_code = 450"
"message_size_limit = 5000000"
After the SMTP helo is sent, the client needs to tell Postfix who the e-mail is from (MAIL FROM) and where to send to (RCPT TO). This communication is supposed to follow RFC-821. Some SPAM software is not strict about its conformance, so we can block SPAM based on this fact.
strict_rfc821_envelopes = yes
With this done, we are now through with the main.cf file. Save it and let's move on to our next section, configuring the rest of postfix! A keynote here - once you finish editing files you need to cap it. Don’t forget to do this whenever you edit your postfix configuration files.
($:~)=> postmap main.cf
Cyrus SASL/TLS And Postfix SSL
let's get SASL2 Installed now.
($:~)=> cd /usr/ports/security/cyrus-sasl2 ; make install clean
Now go ahead and edit postfix’s main.cf so we can tell it to start utilizing the TLS features. Add in the following somewhere near the bottom:
#TLS
smtp_use_tls = yes
smtpd_use_tls = yes
smtpd_tls_auth_only = yes
smtp_tls_note_starttls_offer = yes
smtpd_tls_key_file = /etc/postfix/ssl/post.pem
smtpd_tls_cert_file = /etc/postfix/ssl/post.pem
smtpd_tls_CAfile = /etc/postfix/ssl/post.pem
smtpd_tls_loglevel = 3
smtpd_tls_received_header = yes
smtpd_tls_session_cache_timeout = 3600s
tls_random_source = dev:/dev/urandom

enable_sasl_authentication = yes

smtpd_sasl_auth_enable = yes
smtpd_sasl_security_options = noanonymous
smtpd_sasl_local_domain =
broken_sasl_auth_clients = yes
Also add this in the beginning of your recipient restrictions
($:~)=> permit_sasl_authenticated,
Here we create our postfix SSL Stuff
($:~)=> mkdir /usr/local/etc/postfix/ssl
($:~)=> chmod 700 /usr/local/etc/postfix/ssl
Next we create our SSL certificates for postfix
($:~)=> cd /usr/local/etc/postfix/ssl
($:~)=> vi pst.cnf
The contents of pst.cnf are:
RANDFILE = /etc/postfix/ssl/post.rand

[ req ]
default_bits = 1024
encrypt_key = yes
distinguished_name = req_dn
x509_extensions = cert_type
prompt = no

[ req_dn ]
C=countryName Two letters!
ST=stateOrProvinceName
L=localityName
O=organizationName
OU=OrganizationalUnitName
CN=commonName
emailAddress=emailAddress

[ cert_type ]
nsCertType = server
Be sure to enter the correct options. Next we generate our SSL certificates.
($:~)=> dd if=/dev/urandom of=/etc/postfix/ssl/post.rand count=1 2>/dev/null

($:~)=> /usr/sbin/openssl req -new -x509 -days 365 -nodes
-config /etc/postfix/ssl/pst.cnf -out /etc/postfix/ssl/post.pem
-keyout /etc/postfix/ssl/post.pem

($:~)=> /usr/sbin/openssl gendh -rand /etc/postfix/ssl/post.rand 512
>>/etc/postfix/ssl/post.pem

($:~)=> /usr/sbin/openssl x509 -subject -dates -fingerprint -noout -in
/etc/postfix/ssl/post.pem
Next we need to create a symbolic link before SASL2 gets confused.
($:~)=> ln –s /usr/local/lib/sasl2 /usr/lib/sasl2
Now the next file to edit is /usr/lib/sasl2/smtpd.conf
($:~)=> vi /usr/lib/sasl2/smtpd.conf
The contents of this file look like this:
pwcheck_method: saslauthd
mech_list: plain login
Next we need to tell SASL2 what method we wish to authenticate our mail users. In this document we're going to be using system users and passwords. You might want to read the man page for other methods of authenticating users.
($:~)=> vi /usr/local/etc/rc.d/saslauthd.sh
Now change the sasl_saslauthd_flags variable from -a pam to –a getpwent. The line should like something like this:
sasl_saslauthd_flags=”-a getpwent”
Be sure to send yourself a test e-mail after starting up all the services to ensure they are working properly.

The Access file
This file is the definitive list as that decides who to accept incoming mail from the internet. If you defined it earlier in the main.cf file it must be defined here. Basic syntax is one user per line followed by an OK, so edit /etc/postfix/access now:
"userid1@domain1 OK"
"userid2@domain1 OK"
"userid3@domain2 OK"
etc. etc. Now for a little postfix sorcery, don't specify an account if you don't want them to have the ability to receive internet mail for instance, if you only want the ability for someone to mail local accounts (accounts only contained on your box, leave them out of here) Also, if you are running lots of Virtual domains, you may want to specify system account for each domain, like:
"webmaster@domain1 OK"
"webmaster@domain2 OK"
"postmaster@domain1 OK"
"postmaster@domain2 OK"
Remember, if the specific e-mail you want to receive mail from is not listed in this file, it will bounce. Once you've entered all your info, save that file. From here you must make that file into a hashed db. Also, after any updates you make to this file in the future, you must recompile that hashed db to include your new accounts. Do this by typing the following:
($:~)=> postmap access
And to avoid any delay you should always reload postfix, but don't do that now because we haven’t turned postfix on yet! It can be done like this:
($:~)=> postfix reload
CANONICAL FILES
The next files we'll look at are, /etc/postfix/canonical and /etc/postfix/canonical-receive. Again, if you're not using canonical tables specified in your main.cf file, you don't need to worry about it here.
canonical
The canonical file as defined in this how-to will remap a user's e-mail from the default domain to the appropriate virtual domain. If this is the case you need to specify all users except those in the default domain of the box here! Also if you are mapping a local account to use another name eg. userid1 -> full.name you need to specify that here. Syntax is: userid@domain userid@virtualdomain, or, userid@domain full.name@domain this file handles mail outgoing only! edit /etc/postfix/canonical now
"userid@defaultdomain userid@virtualdomain"
"userid2@defaultdomain userid2@virtualdomain"
Or
"userid@defaultdomain full.name@defaultdomain"
canonical-receive
This file is used to clean up incoming mail so that the virtual addresses don't get remapped to the default domain. All users should have an entry here including system accounts unless they are on the default domain of the box alone, and not using virtual usernames. With that, let's edit /etc/postfix/canonical-receive now!
"userid1@defaultdomain userid1@defaultdomain"
"userid1@virtualdomain userid1@virtualdomain"
"userid2@virtualdomain userid2@virtualdomain"
"postmast@virtualdomain userid2@virtualdomain"
"webmaster@defaultdomain webmaster@defaultdomain"
"webmastr@virtualdomain userid2@virtualdomain"
Or for virtual usernames
"full.name@domain userid@domain"
Got it? Good. It's not that difficult now is it? Again once you're done with these files you’ll need to make a hashed db out of them using the postmap command and you'll need to reload postfix. You remember how to do that right? Good! You're on your way.
CLIENT_ACCESS
The next file we'll be looking at is the /etc/postfix client_access file. This file will specify a list of exceptions and specific denials of mail servers. For instance, your friend, god bless him, has a mail server but is pretty clueless when it comes to dns, he hasn't configured his dns to reverse lookup properly. Well you could bypass that here. Also, you have some evil spammer that keeps sending you mail and the rbl list isn't blocking him, you could add a specific block here. Syntax of this file is xxx.xxx.xxx.xxx function where x is an ip address and function is either OK or REJECT!
"xxx.xxx.xxx.xxx OK"
"xxx.xxx.xxx.xxx REJECT"
after making this file do you know what you need to do? That's right you must make a hashed db out of this file as well! Ok that's done let's move on!

SENDER_ACCESS
This file /etc/postfix/sender_access is where you can specify specific e-mail addresses or domains to block. Usually bogus SPAM addresses. Syntax is fakeemail@bogusdomain.com function where the function is a reject code.
"fakeemail@fakedomain.com 550 No Spam Accepted"
"fakedomain.com 550 What kind of bogus address is that?"
etc. etc. This file further solidifies you box and your place as an anti-SPAM ninja! -For you McDonald! You'll need to make this file a hashed db as well once you're done with it!

BODY_CHECKS
The next file we'll be looking at is /etc/postfix/body_checks. This file is either a regex file or a pcre file (if you compiled postfix with pcre support) I mainly use this file to block troublesome attachments I have no use for anyways. The following blocks certain types of attachments. Self-explanatory.
"/^(.*)name="(.*). (com|vbs|vbe|js|jse|exe|bat|cmd|vxd|scr|hlp|swf|mpeg|mpg|mov|mp3|avi|pif|mpe|shs|ini)"$/ REJECT"
This will help out with viruses among other things, you won't have to worry about vbs scripts and that sort of stupid thing from now on. This file just needs to be in place. There is NO need to make it a hashed db. Although after making changes DO reload postfix!

HEADER_CHECKS
The next file we'll take a look at is /etc/postfix/header_checks. This file does exactly as it says. It checks mail headers. Again either regex or pcre. I will give a couple of examples here that I use:
# This will block 8 non ascii characters in a row, which shouldn't be in the
# header anyway according to the RFC... Japan and Chinese spammers...
"/[^[:print:]]{8}/ REJECT"

# Pegasus uses "Comments: ..." not "Comment: ...". spammers got it wrong.
"/^Comment: Authenticated sender is/ REJECT"
These are just a couple examples. My files are actually really large for this. You can spend a lot of time doing this! Try to avoid going crazy, as it can be fairly obsessive! Again no hashed db needed, just reload postfix when you finish altering.

REGEXP_ACCESS
The next file to look at is regexp_access. This file pretty much does some more of the same, kicking spammers where it hurts! Here is an example I have in mine:
"/[%!@].*[%!@]/ 550 Sender specified routing is not supported here."
There you see, not too bad huh? Ok, again reload postfix when you're done. No db needed, so let's move on.

ALIASES
Let's edit /etc/aliases

The aliases file is very limited with the configuration we have specified here. It does need some things filled in. Standard system aliases should be placed here: aliases for root, postmaster, abuse, etc. etc. Also, if you are running majordomo, you'll specify your outgoing secrets here. If you're forwarding mail to another domain and not using a .forward file in your home, specify that here as well. Other than that, you should be good to go. After editing the aliases file, you should run the command newaliases to tell the system there's new content in that file.

STARTING UP POSTFIX
Ok now, our configuration is complete. Let's start up postfix! Run the following:
($:~)=> postfix start
It should start-up error free! Be sure to send a couple e-mails to yourself through yahoo or something and watch your maillog to ensure everything goes smoothly. I would actually recommend keeping this setup for a week or 2 before continuing with the rest of this article.

Installing Courier POP and IMAP
($:~)=> cd /usr/ports/mail/courier-imap ; make install clean
Next we need to generate our imap ssl certs
($:~)=> /usr/local/share/courier-imap/mkimapdcert
($:~)=> cd /usr/local/etc/courier-imap/
If you notice every configuration file in here is named .dist, so let's copy those so our services actually work.
($:~)=> for foo in *.dist; do cp $foo `basename $foo .dist`; done
($:~)=> mv quotawarnmsg.example quotawarning
Pretty simple on this one.
($:~)=> vi /usr/local/etc/courier-imap/imapd
($:~)=> vi /usr/local/etc/courier-imap/imapd-ssl
Make any changes that you feel are necessary.

Now here’s a brief introduction to imap and what it can do for you:

Introduction to imap and maildirmake
Imap is a great protocol for handling mail. For the reason that all mail that a user gets is still stored on the mailserver, so in the event that windows crashes (and trust me it will) all your valuable e-mail is still nice and safe. You can also setup user quotas and public shared imap folders. A good example of the need for public shared folders is, say that you subscribe to bugtraq mailing lists and the freebsd mailing lists. And you’re not the only geek in the neighborhood who enjoys reading these. Instead of having both accounts get mail from them you can ultimately setup some procmail rules to automatically send those e-mails to the shared imap folder for anybody to read and enjoy.

For each user we need to create a mailbox. We will make one for the user soupx in this demonstration.
($:~)=> cd /home/soupx
($:~)=> su soupx
($:~)=> maildirmake ./Maildir
To make things simple I changed users to soupx so that the permissions are correct. If you do this as root, the folders will be marked with the ownership of root and the local user “soupx” will not be able to write or read mail from there. So unless you want to change the permissions on the Maildir folders, it’s just easier this way.

Now, say we wanted to put a quota on soupx’s mail account. As the root user we would run
($:~)=> maildirmake -q 10000000S ./Maildir
On certain occasions, I’ve run into issues where the quota values do not change. To get around this, create a cron job to perform this task for you every 30 minutes or so on the local mailboxes.

Now let's talk about shared imap folders. First, we need to create a collection of shared folders on a separate Maildir. Since we're sending our SPAM over to /var/mail/spam, it only seems logical to make a maildir in /var/mail/shared.
($:~)=> maildirmake -S /var/mail/shared
Now we create the individual folders we want shared.
($:~)=> maildirmake -s write -f bugtraq /var/mail/shared
Here we are stating that the “bugtraq” folder is created with read/write permissions to everybody. You can set your permissions however you like. Now you can also use maildirmake to join the folders to peoples' mailboxes, but we're going to use a different approach. we're going to be defining things in a simple configuration file:
($:~)=> vi /usr/local/etc/courier-imap/maildirshared
An example is listed below:
# ===========================================
# Shared IMAP Folders
# ===========================================

Bugtraq /var/mail/Shared/Bugtraq
FreeBSD /var/mail/Shared/FreeBSD
OpenBSD /var/mail/Shared/OpenBSD
NetBSD /var/mail/Shared/NetBSD
The first area is the name we wish to display on our shares, followed by a single space or tab, and then the location of the folder.

Congratulations! You should now have POP, IMAP, and IMAP-SSL working on your new postfix install...Now onto bigger and better things.

Configuring Procmail
This part is easy. And any dumbass could probably figure this one out, but just so I don’t get 500 e-mails asking how to do this, I’ll go over it anyways..
($:~)=> cd /usr/ports/mail/procmail ; make install clean
Now let's tell postfix that we now have procmail installed on our system, so let's edit the main.cf file again.
($:~)=> vi /etc/postfix/main.cf
Scroll down to the end of the file and add in:
mailbox_command = /usr/local/bin/procmail -m /usr/local/etc/procmailrc
Save, exit, rehash and reload. Congratulations! Procmail is now installed and ready for the next part of our howto.

Configuring SPAMassasin and vipul's razor to postfix
Thanks to strog over at screamingelectron.org for the information on this one.
($:~)=> cd /ports/mail/p5-Mail-SpamAssassin/ ; make install clean
Now we need to create a procmailrc file
($:~)=> vi /usr/local/etc/procmailrc
# tell procmail we use Maildir style
DEFAULT="$HOME/Maildir/"

# specify the location for identified spam
SPAM="/var/mail/spam/new"

# various debugging stuff uncomment if needed
# VERBOSE=no
# LOGFILE=/var/log/procmailrc
# LOGABSTRACT=no

# Allow previously identified spam to be delivered since it
# must have been approved to get back here with the
# X-Spam-Deferred: YES flag set

:0 w
* ^X-Spam-Deferred: YES
$DEFAULT

# SPAM time
# first send to razor

:0 Wc
|/bin/nice usr/bin/razor-check -home=/root -logfile=/var/log/razor-agent.log

# if previous procmail recipe successfully completed then
# message is spam. prepare for quarantine. use formail to
# rip Delivered-To out (else you'll get loop errors) and tag
# with identifying headers

:0 Waf
| formail -I "Delivered-To:" -A "X-Razor2-Warning: SPAM" -A "X-Spam-Deferred: YES"

# drop razor identified spam into $SPAM (see above)

:0:
* ^X-Razor2-Warning: SPAM
$SPAM

# got this far, time to hand it off to spamassassin

:0fw
| /usr/bin/spamc

# Redirect definitive spam add identifying tags and rip
# postfix Delivered-To headers

:0 f
* ^X-Spam-Flag: YES
| formail -I "Delivered-To:" -A "X-Spam-Deferred: YES"

# quarantine it

:0:
* ^X-Spam-Flag: YES
$SPAM
A quick note on the X-Spam-Deferred: YES flag. We need to add this as mail gets identified so that if we later determine that we want to actually approve that message on to deliver to the intended recipient, we can sneak it back through procmail without getting tossed back into the SPAM trap. Ok, almost done! The next thing is to add a means to easily examine the messages in the SPAM trap. For this we rely on the mighty mutt! We want to add one simple line to Muttrc (usually /usr/local/etc/mutt/Muttrc):
# Approve message identified as spam and deliver it macro index A "| /usr/sbin/sendmail"
Now we need to create the Maildir for our SPAM.
($:~)=> maildirmake /var/mail/spam ; chown root:mail /var/mail/spam
Then we can just use mutt to view /var/mail/spam:
($:~)=> mutt -f /var/mail/spam
You can now browse through identified and quarantined SPAM, looking for incorrectly identified SPAM, etc. If you find a message you want to approve, from the index screen just hit Shift A. This will prompt you asking if you want to pipe to /usr/sbin/sendmail. Hit enter to do it and the message will get delivered, bypassing further SPAM detection. Don't forget to delete the message!!! You can, if you so desired, tack some additional commands on the macro added to mutt to delete the message after approval.

NOTE: If you use mbox style delivery as opposed to Maildir, simply remove the top line of the procmailrc that tells procmail to deliver Maildir style.

You may want to configure SPAMAssassin by editing /usr/local/etc/mail/spamassassin/local.cf. By default, SPAMAssassin modifies messages heavily. I recommend the following options in order to minimally annoy people who don't want to be pestered with this crap:
rewrite_subject 0
report_header 1
defang_mime 0
Congrats you don’t have SPAM. Now we take our journey into defeating those pesky viruses that even the best system administrator can get in their e-mail unless precautions are made.

Now let's do some work with Razor.
($:~)=> cd /usr/ports/mail/razor-agents/ ; make install clean
($:~)=> vi /usr/local/etc/razor.conf
Here’s a good starting configuration to use
debuglevel = 3
identity = identity
ignorelist = 0
listfile catalogue = servers.catalogue.lst
listfile discovery = servers.discovery.lst
listfile nomination = servers.nomination.lst
logfile = razor-agent.log
logic method = 4
min cf = ac + 10
razorzone = razor2.cloudmark.com
rediscovery wait = 172800
report headers = 1
turn off discovery = 0
use engines = 1,2,3,4
whitelist = razor-whitelist
razorhome = /usr/local/etc/razor
logfile = /var/log/razor-agent.log
Configuring Amavis Virus Scanning
This part is extremely easy to setup but can drive the average user nuts trying to get it to work properly. The best software to use in my opinion to do virus scanning is McAfee’s Sophis. However, this is a commercial product and we are cheap bastards here. So in the ideal of this article, we're going to use a primary scanner available in the ports tree called vscan and a secondary backup scanner called clamav.
($:~)=> cd /usr/ports/security/vscan ; make install clean
($:~)=> cd /usr/ports/security/clamav ; make install clean
So let's start off by installing amavisd-new
($:~)=> cd /usr/ports/security/amavisd-new
($:~)=> vi Makefile
Now to follow our maildirectories change
AMAVISQUARANTINE?= /var/virusmails
To
AMAVISQUARANTINE?= /var/mail/virusmails
Now install it
($:~)=> make install clean
Now let's move onto configuring it.
($:~)=> vi /usr/local/etc/amavisd.conf
The main thing to change here is the domain name of our server
$mydomain = ‘example.com’; # Change to reflect your domain
Now we need to set a port and host for amavis.
$forward_method = ‘smtp:127.0.0.1:10025’; # Where to forward checked mail
$notify_method = $forward_method; # Where to submit notifications
$inet_socket_port = 10024; # Where to accept SMTP requests from
Make any other necessary changes to this configuration file. The file is well documented so I don’t believe I need to go in-depth on what needs to be done here. Now we need to tell postfix that amavis is here.
($:~)=> vi /etc/postfix/main.cf
And add in:
content_filter = smtp-amavis:[127.0.0.1]:10024
Next edit the master.cf
($:~)=> vi /etc/postfix/master.cf
And add in:
smtp-amavis unix - - y - 2 smtp
-o smtp_data_done_timeout=1200
-o disable_dns_lookups=yes
127.0.0.1:10025 inet n - y - - smtpd
-o content_filter=
-o local_recipient_maps=
-o smtpd_helo_restrictions=
-o smtpd_client_restrictions=
-o smtpd_sender_restrictions=
-o smtpd_recipient_restrictions=permit_mynetworks,reject
-o mynetworks=127.0.0.0/8
Don’t forget to rehash the files and restart postfix.

Next we need our virus scanner
($:~)=> cd /usr/ports/security/clamav ; make install clean
Cyrus SASL/TLS And Postfix SSL
let's get SASL2 Installed now.
($:~)=> cd /usr/ports/security/cyrus-sasl2 ; make install clean
Now go ahead and edit postfix’s main.cf so we can tell it to start utilizing the TLS features. Add in the following somewhere near the bottom.
#TLS
smtp_use_tls = yes
smtpd_use_tls = yes
smtpd_tls_auth_only = yes
smtp_tls_note_starttls_offer = yes
smtpd_tls_key_file = /etc/postfix/ssl/post.pem
smtpd_tls_cert_file = /etc/postfix/ssl/post.pem
smtpd_tls_CAfile = /etc/postfix/ssl/post.pem
smtpd_tls_loglevel = 3
smtpd_tls_received_header = yes
smtpd_tls_session_cache_timeout = 3600s
tls_random_source = dev:/dev/urandom

enable_sasl_authentication = yes

smtpd_sasl_auth_enable = yes
smtpd_sasl_security_options = noanonymous
smtpd_sasl_local_domain =
broken_sasl_auth_clients = yes
Also add this in the beginning of your recipient restrictions
($:~)=> permit_sasl_authenticated,
Now we create our postfix SSL Stuff
($:~)=> mkdir /usr/local/etc/postfix/ssl
($:~)=> chmod 700 /usr/local/etc/postfix/ssl
Next we create our SSL certificates for postfix
($:~)=> cd /usr/local/etc/postfix/ssl
($:~)=> vi pst.cnf
The contents of pst.cnf are:
RANDFILE = /etc/postfix/ssl/post.rand

[ req ]
default_bits = 1024
encrypt_key = yes
distinguished_name = req_dn
x509_extensions = cert_type
prompt = no

[ req_dn ]
C=countryName Two letters!
ST=stateOrProvinceName
L=localityName
O=organizationName
OU=OrganizationalUnitName
CN=commonName
emailAddress=emailAddress

[ cert_type ]
nsCertType = server
Be sure to make the correct options. Next we generate our SSL certificates.
($:~)=> dd if=/dev/urandom of=/etc/postfix/ssl/post.rand count=1 2>/dev/null

($:~)=> /usr/sbin/openssl req -new -x509 -days 365 -nodes
-config /etc/postfix/ssl/pst.cnf -out /etc/postfix/ssl/post.pem
-keyout /etc/postfix/ssl/post.pem

($:~)=> /usr/sbin/openssl gendh -rand /etc/postfix/ssl/post.rand 512
>>/etc/postfix/ssl/post.pem

($:~)=> /usr/sbin/openssl x509 -subject -dates -fingerprint -noout -in
/etc/postfix/ssl/post.pem
Next we need to create a symbolic link before SASL2 gets confused.
($:~)=> ln –s /usr/local/lib/sasl2 /usr/lib/sasl2
Now next file to edit is /usr/lib/sasl2/smtpd.conf
($:~)=> vi /usr/lib/sasl2/smtpd.conf
The contents of this file look like below:
pwcheck_method: saslauthd
mech_list: plain login
Next we need to tell SASL2 what method we wish to authenticate our mail users. In this document we're going to be using system users and passwords. You might want to read the man page for other methods of authenticating users.
($:~)=> vi /usr/local/etc/rc.d/saslauthd.sh
Now change the sasl_saslauthd_flags variable from -a pam to –a getpwent. The line should like something like this:
sasl_saslauthd_flags=”-a getpwent”
Be sure to send yourself a test e-mail after starting up all the services to ensure they are working properly.

So where do you go from here? My best suggestions would be to study up on different ways that you can authenticate mail users. Ultimately, a good way is to use OpenLDAP to keep a database of users and store mail through there. That’s beyond the scope of this article but a definite nice way to get things done. By utilizing the OpenLDAP services you cannot only have postfix authenticate though they’re but courier-imap and a vast majority of your services. Along with the ability to use a shared contacts system or whatever you can think of.


Continued...
This article has been split into three parts due to the massive load times that were required when it was all one huge article. Follow the links below to veiw the rest of the article.

Part 1 | Part 2 | Part 3









Copyright © by LWD All Rights Reserved.

Published on: 2004-03-08 (14668 reads)

[ Go Back ]
Content ©


This site designed and hosted by littleblackdog.com
All product names throughout this site are trademarks or registered trademarks of their respective holders.
Copyright © 2000-2008, littleblackdog.com | All rights reserved | Please read our legal info
No portion of this site may be duplicated without specific permission from the site owner.

Web site engine code is Copyright © 2003 by PHP-Nuke. All Rights Reserved. PHP-Nuke is Free Software released under the GNU/GPL license.