spam detection in qmail

To get rid of spam on your Qmail mail server:

  1. Make sure that all domains have the Mail to nonexistent user option set to Reject.This option is available since Parallels Plesk Panel 7.5.3 and can be changed for all the domains using group operations: select the domains, click Modify Selected, in the Preferences section select Switch on for the Mail to nonexistent user option and select the Reject value for it.
  2. Make sure that there are no untrusted IP addresses or networks in the white list.To do this, go to Home > Mail Server Settings > White List tab. To remove untrusted IP addresses or networks, select them in the list and click Remove Selected.
  3. Check how many messages there are in the Qmail queue with:# /var/qmail/bin/qmail-qstat

    messages in queue: 27645

    messages in queue but not yet preprocessed: 82

    If there are too many messages in the queue, try to find out where the spam is coming from. If the mail is being sent by an authorized user, but not from a PHP script, you can find out which user sent most of the messages with the following command:

    # cat /usr/local/psa/var/log/maillog |grep -I smtp_auth |grep -I user |awk '{print $11}' |sort |uniq -c |sort -n

    Note that the SMTP authorization option should be enabled on the server to see these records. The path to maillog may be different depending the OS you use.

  4. Use the qmail-qread utility to read the messages headers:# /var/qmail/bin/qmail-qread

    18 Jul 2005 15:03:07 GMT #2996948 9073 <> bouncing

    done remote

    done remote

    done remote


    The qmail-qread utility shows messages’ senders and recipients. If a message has too many recipients, then it is most probably spam.

  5. Try to find the message in the queue by it’s ID (for example, the message ID is #1234567):# find /var/qmail/queue/mess/ -name 1234567
  6. Look into the message and find the first from the end Received line. It is where the message was initially sent from.
    • If you find something like:Received: (qmail 19514 invoked by uid 12345); 10 Sep 2008 17:48:22 +0700

      it means that this message was sent via a CGI script by user with UID 12345. Use this UID to find a corresponding domain:

      # grep 12345 /etc/passwd

    • Received lines like:Received: (qmail 19622 invoked from network); 10 Sep 2008 17:52:36 +0700

      Received: from (

      mean that the message was accepted for delivery via SMTP and the sender is an authorized mail user.

    • If Received line contains an UID of an apache user (for example invoked by uid 48), it means that the spam was sent via an PHP script. In this case you can try to find the spammer using information from the spam e-mails (from/to addresses, subjects, etc). But usually to find the spam source is very hard in this case. If you are sure that some script is sending spam at the current moment (the queue grows very fast), you can use this little script to find out what PHP scripts are running in real-time:# lsof +r 1 -p `ps axww | grep httpd | grep -v grep | awk ‘ { if(!str) { str=$1 } else { str=str”,”$1}}END{print str}’` | grep vhosts | grep php

      To try to find out from what folder the PHP script that sends mail was run, create /var/qmail/bin/sendmail-wrapper script with the following content:


      (echo X-Additional-Header: $PWD ;cat) | tee -a /var/tmp/mail.send|/var/qmail/bin/sendmail-qmail “$@”

      Note, the paths can slightly differ depending on your OS and Parallels Plesk Panel version.

      Create a log file /var/tmp/mail.send and grant it a+rw rights, make the wrapper executable, rename old sendmail and link it to the new wrapper:

      # touch /var/tmp/mail.send

      # chmod a+rw /var/tmp/mail.send

      # chmod a+x /var/qmail/bin/sendmail-wrapper

      # mv /var/qmail/bin/sendmail /var/qmail/bin/sendmail-qmail

      # ln -s /var/qmail/bin/sendmail-wrapper /var/qmail/bin/sendmail

      Wait for about an hour and revert sendmail back:

      # rm -f /var/qmail/bin/sendmail

      # ln -s /var/qmail/bin/sendmail-qmail /var/qmail/bin/sendmail

      Examine the /var/tmp/mail.send file. There should be lines starting with X-Additional-Header pointing out to domains’ folders where the script that sends the mail is located.

      You can see all the folders where mail PHP scripts were run from with the following command:

      # grep X-Additional /var/tmp/mail.send | grep `cat /etc/psa/psa.conf | grep HTTPD_VHOSTS_D | sed -e ‘s/HTTPD_VHOSTS_D//’ `


Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )


Connecting to %s

%d bloggers like this: