$max_fail_handler()
which
is undefined in default installations.
$max_fail_handler(remote_ip_address)
is called when there are
more than $max_fail
failed login attempts.
For example, I have the following setup (on Linux):
To allow sudo iptables for user fex:
root@fex:/etc/sudoers.d# cat iptables fex ALL=(root) NOPASSWD:/sbin/iptables fex ALL=(root) NOPASSWD:/sbin/ip6tables
fex@fex:~/bin: cat iptables #!/bin/sh exec sudo /sbin/iptables "$@" fex@fex:~/bin: cat ip6tables #!/bin/sh exec sudo /sbin/ip6tables "$@"
And then in fex.ph I have:
my $iptables = '/home/fex/bin/iptables'; my $ip6tables = '/home/fex/bin/ip6tables'; my $mail = 'mailx'; $max_fail = 10; $max_fail_handler = sub { my $ip = shift; local $_; if ($ip =~ /:/) { system "$ip6tables -A BLOCK -s $ip -j LOGREJECT"; } else { system "$iptables -A BLOCK -s $ip -j LOGREJECT"; } if (open my $m,"| $mail -s 'FEX max_fail $ip' fex") { print {$m} "@_\n\n"; if ($faillog and open $faillog,$faillog) { print {$m} $_ while <$faillog>; close $faillog; } close $m; } };With this function every ip address will be blocked after there are more than 10 sequent login failures and a notification e-mail is sent to user framstag. A successfull login will reset the counter.
For the curious:
If you have defined $max_fail_handler()
and $max_fail
in
/home/fex/lib/fex.ph
then you will find the last login failures
in /home/fex/spool/.fail/
Another anti-hacking configuration can be done by defining
$header_hook()
in fex.ph
to disallow certain
headers. Example:
$header_hook = sub { my ($connect,$header,$ip) = @_; my (@dl); local $_; @dl = qw( ^GET.*\.\./\.\./ ^Referer:.*(replica|[Bb]ags|[Gg]ucci|cheap|viagra|-sale) ^User-Agent:.MSIE ^User-Agent:.Internet.Explorer.4 ^User-Agent:.Mozilla.*Win2000 ^User-Agent:.*Windows.9[58] ^User-Agent:.Morfeus ^User-Agent:.Toplistbot ^User-Agent:.Toata ^User-Agent:.Sosospider ^User-Agent:.Hatena ^User-Agent:.bitlybot ^User-Agent:.Comodo ^User-Agent:.COMODO ^User-Agent:.*daum.net ^User-Agent:.*puritysearch ^User-Agent:.*Mp3Bot ^User-Agent:.*TencentTraveler ^User-Agent:.*FunWebProducts ^User-agent:.chroot ^User-[Aa]gent:.*Baidu ^User-Agent:.facebook ^User-Agent:.WhatsApp ^User-Agent:.mattermost ^user-agent:.*Trident/6\.0 ); foreach my $dp (@dl) { if ($header =~ /$dp/) { fexlog($connect,@log,"BADREQUEST $dp"); http_error(403); exit; } } };