Cheap VPS & Xen Server

Residential Proxy Network - Hourly & Monthly Packages

Increase your IPv4 security with Fail2Ban and Tinyhoneypot on Debian Jessie

It is a five minutes’ exercise to increase security on an IPv4 addressed machine. The purpose of the setup described in this tutorial is to lock out port scanners and malicious port openers for a period of time. This exercise is only tried out and applied on Debian Jessie. During the exercise, each command is committed as root. It is your deal how to get root access.

Either su -, sudo, console login, etc…

Instruction for lazy beginners: When I represent the bash prompt, just CopyPaste the bold part of the text to your own.

The ingredients

  • The fail2ban software is capable to dynamically handle your firewall rules to lock out bad guys.
  • The tinyhoneypot is capable of listening on a TCP/IP port and logging openers details.
  • The xinetd service starts tinyhoneypot and manages it’s listening ports.

Install ingredients: ( Just CopyPaste the bold part of the text )

root@teszt:~# apt-get install tinyhoneypot fail2ban xinetd


In order to make SSH listen on a different port, replace your ssh configuration file with and alternative ssh port:

root@teszt:~# sed -i.orig ‘s/Port 22/Port 2201/m’ /etc/ssh/sshd_config

Your original /etc/ssh/sshd_config config is saved as /etc/ssh/sshd_config.orig

When you restart your SSH service, it will listen on 2201 port (not in 22) now.

root@teszt:~# service ssh restart
root@teszt:~# netstat -lptn | grep ssh
tcp 0 0* LISTEN 4313/sshd
tcp6 0 0 :::2201 :::* LISTEN 4313/sshd

So far so good..

Configure Xinetd to start tinyhoneypot and listen on Port 22 of TCP:

root@teszt:~# cp -v /usr/share/doc/tinyhoneypot/examples/xinetd.d/thp-pasv /etc/xinetd.d/

Edit your /etc/xinetd.d/thp-pasv to like this:

root@teszt:~# cat /etc/xinetd.d/thp-pasv

# default: on
# description: thp-ftpd calls the generic thpsvcs with param "ftp",
#       resulting in an ftpd emulation.

service thp-pasv
        type                    = UNLISTED
        socket_type             = stream
        protocol                = tcp
        port                    = 22
        wait                    = no
        user                    = thpot
        server                  = /usr/sbin/thpot
        server_args             = nullresp
        nice                    = 10
        disable                 = no
        instances               = 1
        per_source              = 1


(RE)Start xinetd with your new settings and make sure it listens on port 22.

root@teszt:~# service xinetd restart
root@teszt:~# netstat -lptn | grep xinetd
tcp 0 0* LISTEN 4567/xinetd

Make sure it is working

Open an ssh connection from an another machine.

attacker@hackerpc:~$ ssh

After a while nothing should happen, interrupt it by [Ctrl + C]

And check log entries on your test machine:

root@teszt:~# cat /var/log/thpot/captures
Feb 29 13:02:10 SID=56D4334221165.nullresp PID=4837 SRC= SPT=47187 ET=00:00:11 BYTES=39

In case everything went well, there should be an entry in your capture log.

Lets tune your Fail2Ban to cooperate with TinyHoneyPot

root@teszt:~# cd /etc/fail2ban/
root@teszt:/etc/fail2ban# cp -v jail.conf jail.local

Never edit your jail.conf!! Make a copy of it as jail.local and ONLY make changes in the .local file!

Find the [ssh] section in your jail.local and modify it depending on [Port 2201] of /etc/ssh/sshd_config


enabled  = true
port     = 2201
filter   = sshd
logpath  = /var/log/auth.log
maxretry = 6

Make and entry in the JAIL section of jail.local:

This will make Fail2Ban to read the log file of tinyhoneypot and get the IPv4 address from it to deny. I recommend to place it after the [ssh] section. It is about the 137th row.


enabled  = true
port     = all
filter   = thpot
logpath  = /var/log/thpot/captures
banaction = iptables-allports
maxretry = 1
findtime = 1800
bantime = 99999

Fail2ban should have a filter in order to know what to deny. There  is a macro which substitute IPv4 address. Create a filter for it:

root@teszt:~# cat /etc/fail2ban/filter.d/thpot.local


failregex = SRC=<HOST>
ignoreregex =

It has been done!

Just a short testing….

root@teszt:~# service fail2ban restart

You should see something similar at the end of /var/log/fail2ban.log

2016-02-29 13:54:06,915 fail2ban.jail   [6102]: INFO    Creating new jail 'thp-ssh'
2016-02-29 13:54:06,915 fail2ban.jail   [6102]: INFO    Jail 'thp-ssh' uses pyinotify
2016-02-29 13:54:06,920 fail2ban.jail   [6102]: INFO    Initiated 'pyinotify' backend
2016-02-29 13:54:06,922 fail2ban.filter [6102]: INFO    Added logfile = /var/log/thpot/captures
2016-02-29 13:54:06,923 fail2ban.filter [6102]: INFO    Set maxRetry = 1
2016-02-29 13:54:06,925 fail2ban.filter [6102]: INFO    Set findtime = 1800
2016-02-29 13:54:06,926 fail2ban.actions[6102]: INFO    Set banTime = 99999
2016-02-29 13:54:06,934 fail2ban.jail   [6102]: INFO    Jail 'ssh' started
2016-02-29 13:54:06,940 fail2ban.jail   [6102]: INFO    Jail 'thp-ssh' started

You can see your custom values from jail.local and fine tune them if needed.

findtime = 1800
bantime = 99999

Have a look at your current iptables rules:

root@teszt:~# iptables-save

# Generated by iptables-save v1.4.21 on Mon Feb 29 14:05:17 2016
:fail2ban-ssh - [0:0]
:fail2ban-thp-ssh - [0:0]
-A INPUT -p tcp -j fail2ban-thp-ssh
-A INPUT -p tcp -m multiport --dports 2201 -j fail2ban-ssh
-A fail2ban-ssh -j RETURN
-A fail2ban-thp-ssh -j RETURN
# Completed on Mon Feb 29 14:05:17 2016

Let’s check the deny rule from an another machine:

attacker@hackerpc:~# ssh
attacker@hackerpc:~# ssh
ssh: connect to host port 22: Connection refused

The first action will do nothing. The attacker will probably interrupt it after a while The second action will be refused.

Your iptables rules should look like this by now:

root@teszt:~# iptables-save

# Generated by iptables-save v1.4.21 on Mon Feb 29 14:10:53 2016
:fail2ban-ssh - [0:0]
:fail2ban-thp-ssh - [0:0]
-A INPUT -p tcp -j fail2ban-thp-ssh
-A INPUT -p tcp -m multiport --dports 2201 -j fail2ban-ssh
-A fail2ban-ssh -j RETURN
-A fail2ban-thp-ssh -s -j REJECT --reject-with icmp-port-unreachable
-A fail2ban-thp-ssh -j RETURN
# Completed on Mon Feb 29 14:10:53 2016

The result is: The attacker’s PC is REJECTED on each port.

The Postscript

At the time of this HowTo was writing neither Fail2Ban not tinyhoneypot was able to handle IPv6 If you think this Howto is useful, share it! Let your friends know about it.