This kind-of links into a thread from October...
We see that dictionary scans continue, but the pattern of presented
HELO and envelope sender keeps changing (not surprisingly). I got
kind-of sick of seeing these bunches of two-dozen-plus RCPT TO
commands per SMTP call being logged in the rejectlog... Typically
these calls are made via open proxies.
We could just leave them to get on with it, but the clutter in the
logs brings the risk that some genuine problem might be overlooked.
And occasionally we see them picking a genuine addressee (some of them
make no attempt to send a message body, but others then try to send
spam - which it seems our spamassassin setup usually blocks).
Presumably they behave the way that they do for some reason, rather
than mere network vandalism, and I'm reluctant to hand out details
which in effect validate some of the addresses they're testing.
Already in 4.10 I see that we have $rcpt_count and $recipients_count
available in ACLs, and I kind-of reasoned that if $rcpt_count had
reached, say, 4, and no (or perhaps at most 1) valid recipient address
had been achieved, then this was probably another dictionary scan
episode. Seem reasonable?
Of course at this point there's no use simply issuing a "deny",
because the smtp call stays up and the caller simply continues with
their merry scan. So instead I would run a sequence of /bin/sleep 59
for long enough (six seems to be enough) for the caller to give up.
Something like:
deny hosts = +rbl_hosts
message = *** Dict scan! $rcpt_count, $recipients_count
condition = ${if ={$rcpt_count}{4}{1}{0}}
condition = ${if <{$recipients_count}{2}{1}{0}}
condition = ${run{/bin/sleep 59}{1}{0}}
condition = ${run{/bin/sleep 59}{1}{0}}
etc...
Optionally, one can also call a script from the ACL which writes the
calling IP into a local blacklist file.
A strong way of using that local blacklist file is as the basis for a
host_reject_connection on subsequent calls from that IP.
That's what I'm doing at the moment; however, that leaves the IP in a
position where it can't even email our postmaster address (normally
freely available) to tell us that their problem is fixed. Well,
there's a separate script to scan the local blacklist file, now and
again, and see whether any of those IP addresses have got themselves
out of the public RBL registers yet.
Anyhow, the procedure has been working for a few days now, if anyone's
interested - or has any comments.
An alternative approach which occurs to me is to use that file to set
the above $rcpt_count test down from 4 to 1, so that per call they get
a single chance to present a valid addressee, failing which they get
fed to the timeout without waiting for more addresses to be probed.
I haven't tried that.
Hope this is of interest.