Postfix hacks

From Cheatsheet

Jump to: navigation, search

Contents

commands

mailq

shows all the mail sitting on your server, you delete one using one of the scripts at the bottom of this page

postsuper -d ALL

removes all mail in the queue

postsuper -d ALL deferred

removes all mail in the deferred queue

postqueue -f

attempt to deliver all the mail in the queue

postcat -q C95D57032E

see details of that e-mail

Here's an IP blocker, that will measure for spam attacks from the same IP in a short time, and block them before they ever get to Postfix, so Postfix doesn't have to think about it very hard.

 /sbin/iptables -I INPUT -p tcp --dport 25 -i eth0 -m state --state NEW -m recent \
 --set
 /sbin/iptables -I INPUT -p tcp --dport 25 -i eth0 -m state --state NEW -m recent \
 --update --seconds 60 --hitcount 25 -j DROP

that's a modified version of the script that lives here: http://www.debian-administration.org/articles/187 I'm going to watch it and see what happens if you want to see how many failed attempts there are to login, run this:

 grep "FAILED" /var/log/maillog | sed "s/.*for\( invalid user\)*\(.*\)\(from.*\)/\2/" | sort | uniq -c | wc -l

if you want to remove your Iptables rules, do this:

 /sbin/iptables -F
 /sbin/iptables -X

It looks like that did very little, for some reason

sending mail out some single interface

Luigi Rosa wrote: > Given a Linux server with three network cards: > > eth0: 192.168.1.1 (local LAN) > eth1: 20.20.20.20 (default GW, hi speed Internet, dynamic address) > eth2: 30.30.30.30 (Internet, reserved to e-mail, static address) > > This server is the default gateway of the organization and NATs the > local addresses via 20.20.20.20. Al traffic must go through 20.20.20.20 > EXECPT e-mail that should go through 30.30.30.30. > > Binding Postfix (via inet_interfaces directive) to 192.168.1.1 and > 30.30.30.30 (and localhost) will be enough to tell Postfix to deliver > mail via 30.30.30.30 and NOT via the system default gateway 20.20.20.20? > >

You will need smtp_bind_address in main.cf for that purpose. Depending on your configuration need, you could create extra service in master.cf as well, example:

smtp-external unix - - y - - smtp

        -o smtp_bind_address=30.30.30.30

and then in main.cf:

default_transport=smtp-external


Don't forget about relay service definition either, as it's smtp as well, and uses global smtp_bind_address, unless explicitely overridden in master.cf

binding postfix will set the IP in the packets, but it won't change the network routes (by default, routing is done by destination). so you also need to play with "advanced" routing to make sure the packets go out of eth2. this is linux question.

http://lartc.org/howto/index.html http://linux-ip.net/html/ http://www.policyrouting.org/PolicyRoutingBook/ONLINE/TOC.html

smtp settings

good starting point, according to mouss

smtpd_recipient_restrictions =

       permit_mynetworks
       reject_unauth_destination
       reject_non_fqdn_sender
        reject_non_fqdn_recipient
       reject_invalid_helo_hostname
       reject_unlisted_recipient
       reject_unlisted_sender
       #reject_non_fqdn_helo_hostname
       reject_rbl_client zen.spamhaus.org

delete mail

from user@example.com

 mailq | tail +2 | grep -v ’^ *(’ | awk  ´BEGIN { RS = "" }
     # $7=sender, $8=recipient1, $9=recipient2
     { if ($8 == "user@example.com" && $9 == "")
             print $1 }
     ´ | tr -d ’*!’ | postsuper -d -

delete mail with specific text in it somewhere

example ./postfix-delete fromsomebaddomain.com

 vi postfix-delete.pl
   #!/usr/bin/perl
   $REGEXP = shift || die "no email-adress given (regexp-style, e.g. bl.*\@yahoo.com)!";
   @data = qx</usr/sbin/postqueue -p>;
   for (@data) {
     if (/^(\w+)(\*|\!)?\s/) {
        $queue_id = $1;
     }
     if($queue_id) {
       if (/$REGEXP/i) {
         $Q{$queue_id} = 1;
         $queue_id = "";
       }
     }
   }
    #open(POSTSUPER,"|cat") || die "couldn't open postsuper" ;
   open(POSTSUPER,"|postsuper -d -") || die "couldn't open postsuper" ;
   foreach (keys %Q) {
     print POSTSUPER "$_\n";
   };
   close(POSTSUPER);

iptables

 $IPTABLES -N SMTP-BLOCK
 $IPTABLES -A SMTP-BLOCK -m limit --limit 1/m --limit-burst 3 -j LOG  
 - --log-level notice --log-prefix "iptables SMTP-BLOCK "
 $IPTABLES -A SMTP-BLOCK -m recent --name SMTPBLOCK --set -j DROP
 $IPTABLES -A INPUT -p tcp --dport 25 -m state --state NEW -m recent  
 - --name SMTPBLOCK  --rcheck --seconds 360 -j SMTP-BLOCK
 $IPTABLES -A INPUT -p tcp --dport 25 -m state --state NEW -m recent  
 - --name SMTP --set
 $IPTABLES -A INPUT -p tcp --dport 25 -m state --state NEW -m recent  
 - --name SMTP --rcheck --seconds 60 --hitcount 15 -j SMTP-BLOCK
 $IPTABLES -A INPUT -p tcp --dport 25 -m state --state NEW -j ACCEPT

It creates some trap for hosts which open too many connections in a short timeframe. Be aware of the limitations :

The recent module can only handle a limited number of entries to compare so if you have high traffic this list may be overflow/cycled before the offender get caught.
You must adjust the connection/time to match your needs.
For larger sites you maybe have to adjust the size of the blocklist.

from me to me

you know what domains are yours so you can simply use an access list:

check_sender_access hash:/etc/postfix/mydomain

== mydomain example.com REJECT you cannot send on behalf of example.com .example.com REJECT you cannot send on behalf of example.com

please do not advocate SPF on this list. check the archives and you'll see that it is taboo here.

Personal tools