in Electronic Mail

MTA hacking

Today has been a day for hacking mail infrastructure. First, I arrived at the office at 8 a.m. to cut over our old RedHat 7.3-based SMTP gateway to a new Fedora Core 4 virtual machine. The purpose of this box (or VMWare GSX Server guest, in our case) is to act as a final sanity check before inbound e-mail hits Microsoft Virus Exchange Server. Previous admins were smart enough to realize that once a virus hits Exchange it will spread like wildfire, so there needs to be a special box placed in front of Exchange to scan for viruses.

The new setup is similar to the old setup, but with updated packages. The machine runs Postfix with amavisd-new as the content_filter, and any clean messages are passed over the internal LAN to the Exchange server. We’re using ClamAV as the antivirus scanner.

I encountered one problem while cutting this over which is that clamd likes to drop privileges right after starting, and I’d forgotten to set AllowSupplementaryGroups in the clamd configuration file. This meant ClamAV couldn’t read any of the temporary spool files written by amavis.

For the rest of the day, I’ve been trying to set up an internal development server’s Postfix configuration so that no mail originating from it ever makes it out into the Internet. This is because we have a live mirror of a customer database, containing real e-mail addresses, and we don’t ever want those customers to get spammed accidentally! What I wanted to do instead, in declining order of preference, is:

  1. Redirect all e-mail originating from the machine to a local user.
  2. Discard all e-mail originating from the machine.

Originally I was hoping to solve this with one line in Postfix’s virtual config file:

@* jdunn

This didn’t work because mail originating on the local machine for e-mail addresses on the Internet would immediately get shunted to the SMTP transport, which obviously will never consult the virtual table.

After some discussions with my former colleague Blake on IRC, I realized I had to hijack Postfix’s internal transport tables, so I tried this in transport:

* discard

That does work, but it’s second on my list of solutions. What about forcing local delivery for all mail to a specified e-mail address?

Unfortunately, one cannot specify additional options to the local(8) delivery agent. If I put * local in the transport map, local(8) would quickly run off and try to interpret the aliases file, etc. and all that smart stuff, probably resulting in a bounce. What I realy wanted was for local(8) to unequivocally shove any incoming e-mail to an mbox file.

The only way I could think of to do this was to define a new delivery agent in master.cf:

override unix – n n – – pipe
user=jdunn argv=/usr/bin/procmail -d jdunn

and then instruct transport to use that:

* override

That works, but it’s messy. It depends on the use of an external program, procmail(1), which might not be available.

Does anyone know of a way to use Postfix’s bundled delivery agents to accomplish this task?