https://github.com/smtpd/qpsmtpd/pull/29

I've been running it on my server for a week in RFC policy mode.  I knew from 
hours of watching logs that it would be effective, but measuring it was still 
surprising and delightful.  Of the 10% of connections that make it past the 
dnsbl and karma tests, another 50% are rejected by these HELO tests.  Of those 
50%, more than 95% are connections from Windows (most Win 7) hosts where the 
DNS bears no resemblance to the HELO hostname offered.  

Since expanding the no_matching_dns test (earlier today), I have yet to see a 
single false positive from that test. While I'm still not using that as a 
condition for rejection, it may now be good enough to enforce. 

Matt



NAME
    helo - validate the HELO message presented by a connecting host.

DESCRIPTION
    Validate the HELO hostname. This plugin includes a suite of optional
    tests, selectable by the *policy* setting. The policy section details
    which tests are enforced by each policy option.

    This plugin adds an X-HELO header with the HELO hostname to the message.

    Using *policy rfc* will reject a very large portion of the spam from
    hosts that have yet to get blacklisted.

WHY IT WORKS
    The reverse DNS of the zombie PCs is out of the spam operators control.
    Their only way to get past these tests is to limit themselves to hosts
    with matching forward and reverse DNS, and then use the proper HELO
    hostname when spamming. At present, this presents a very high hurdle.

HELO VALIDATION TESTS
    is_in_badhelo
        Matches in the *badhelo* config file, including yahoo.com and
        aol.com, which neither the real Yahoo or the real AOL use, but which
        spammers use a lot.

        Like qmail with the qregex patch, the badhelo file can also contain
        perl regular expressions. In addition to normal regexp processing, a
        pattern can start with a ! character, and get a negated (!~) match.

    invalid_localhost
        Assure that if a sender uses the 'localhost' hostname, they are
        coming from the localhost IP.

    is_plain_ip
        Disallow plain IP addresses. They are neither a FQDN nor an address
        literal.

    is_address_literal [N.N.N.N]
        An address literal (an IP enclosed in brackets) is legal but rarely,
        if ever, encountered from legit senders.

    is_forged_literal
        If a literal is presented, make sure it matches the senders IP.

    is_not_fqdn
        Makes sure the HELO hostname contains at least one dot and has only
        those characters specifically allowed in domain names (RFC 1035).

    no_forward_dns
        Make sure the HELO hostname resolves.

    no_reverse_dns
        Make sure the senders IP address resolves to a hostname.

    no_matching_dns
        Make sure the HELO hostname has an A or AAAA record that matches the
        senders IP address, and make sure that the senders IP has a PTR that
        resolves to the HELO hostname.

        Since the dawn of SMTP, having matching DNS has been a minimum
        standard expected and oft required of mail servers. While requiring
        matching DNS is prudent, requiring an exact match will reject valid
        email. While testing this plugin with rejection disabled, I noticed
        that mx0.slc.paypal.com sends email from an IP that reverses to
        mx1.slc.paypal.com. While that's technically an error, I believe
        it's an error to reject mail based on it. Especially since SLD and
        TLD match.

        To avoid snagging false positives, matches are extended to the first
        3 octets of the IP and the last two labels of the FQDN. The
        following are considered a match:

          192.0.1.2, 192.0.1.3

          foo.example.com, bar.example.com

        This allows *no_matching_dns* to be used without rejecting mail from
        orgs with pools of servers where the HELO name and IP don't exactly
        match. This list includes Yahoo, Gmail, PayPal, cheaptickets.com,
        exchange.microsoft.com, and likely many more.

CONFIGURATION
  policy [ lenient | rfc | strict ]
    Default: lenient

   lenient
    Reject failures of the following tests: is_in_badhelo,
    invalid_localhost, and is_forged_literal.

    This setting is lenient enough not to cause problems for your Windows
    users. It is comparable to running check_spamhelo, but with the addition
    of regexp support and the prevention of forged localhost and forged IP
    literals.

   rfc
    Per RFC 2821, the HELO hostname must be the FQDN of the sending server
    or an address literal. When *policy rfc* is selected, all the lenient
    checks and the following are enforced: is_plain_ip, is_not_fqdn,
    no_forward_dns, and no_reverse_dns.

    If you have Windows users that send mail via your server, do not choose
    *policy rfc* without *reject naughty* and the naughty plugin. Windows
    users often send unqualified HELO names and will have trouble sending
    mail. <Naughty> can defer the rejection, and if the user subsequently
    authenticates, the rejection will be cancelled.

   strict
    Strict includes all the RFC tests and the following: no_matching_dns,
    and is_address_literal.

    I have yet to see an address literal being used by a hammy sender. But I
    am not certain that blocking them all is prudent.

    It is recommended that *policy strict* be used with <reject 0> and that
    you monitor your logs for false positives before enabling rejection.

  badhelo
    Add domains, hostnames, or perl regexp patterns to the badhelo config
    file; one per line.

  timeout [seconds]
    Default: 5

    The number of seconds before DNS queries timeout.

  reject [ 0 | 1 | naughty ]
    Default: 1

    0: do not reject

    1: reject

    naughty: naughty plugin handles rejection

  reject_type [ temp | perm | disconnect ]
    Default: disconnect

    What type of rejection should be sent? See docs/config.pod

  loglevel
    Adjust the quantity of logging for this plugin. See docs/logging.pod

RFC 2821
  4.1.1.1
    The HELO hostname "...contains the fully-qualified domain name of the
    SMTP client if one is available. In situations in which the SMTP client
    system does not have a meaningful domain name (e.g., when its address is
    dynamically allocated and no reverse mapping record is available), the
    client SHOULD send an address literal (see section 4.1.3), optionally
    followed by information that will help to identify the client system."

  2.3.5
    The domain name, as described in this document and in [22], is the
    entire, fully-qualified name (often referred to as an "FQDN"). A domain
    name that is not in FQDN form is no more than a local alias. Local
    aliases MUST NOT appear in any SMTP transaction.

AUTHOR
    2012 - Matt Simerson

ACKNOWLEDGEMENTS
    badhelo processing from check_badhelo plugin

    badhelo regex processing idea from qregex patch

    additional check ideas from Hakura helo plugin



`````````````````````````````````````````````````````````````````````````
  Matt Simerson                   http://matt.simerson.net/
  Systems Engineer            http://www.tnpi.net/

  Mail::Toaster  - http://mail-toaster.org/
  NicTool          - http://www.nictool.com/
`````````````````````````````````````````````````````````````````````````

Reply via email to