No one likes having their SSH server probed for unauthorized access. So why not ban the IP addresses which commit these acts? This post describes how to do just that, using some simple Bash scripts and running them periodically with Cron.

These scripts require iptables currently, but could probably be modified to support other firewall solutions, assuming they use text-based configurations to specify what IPs should be blocked.

One of the biggest requirements of our block script is that it not run if an instance is already running, so that the script doesn’t take up precious server resources. To accomplish this, we use a file lock in /tmp to determine if the script is already running.

Another important thing is to not set your Cron job to run the script too often. In our examples we run the script every 30 minutes. If the server you’re running the script on is a high traffic server you may want to run the script more often, but there’s probably no reason to run it more often than every 30 minutes.

Automated Banning and Unbanning

Let’s take a look at the code. Our first script runs every 30 minutes to set the block commands in iptables for each IP address. We named ours ssh-block.sh:

As you can see there are some customizable options at the top of the script. Most of these should be pretty standard accross Linux distributions but you can change the path to the executables if your system is set up differently. The last two, restart and curdate, should not be changed. The badcount variable sets how many failed login attempts our script needs to see before it blocks an IP address.

To run this script every 30 minutes, we set a line in our crontab:

Set the path to your ssh-block.sh script in the crontab line and save your changes.

Our next script removes the blocked IP addresses after 6 months. We named ours ssh-unblock.sh:

By default, it unblocks IP addresses after 6 months. To change this value, edit this line in ssh-unblock.sh:

For instance, you could specify 1 year ago instead of 6 month ago in the above line to unblock after 1 year.

To run this script once per day at midnight, we set a line in our crontab:

Our script uses the logger command to submit logs to the messages log file. You may need to install logger for this functionality if your system doesn’t already have it installed.

Command Line Banning and Unbanning

Optionally, you can also set up some simple commands to allow you to ban/unban IP addresses quickly with a simple command such as:

On most systems we save our scripts to the /usr/sbin/ directory. Our banip script contains:

Our unbanip script is very similar:

Make sure to chmod +x the banip and unbanip files to ensure they are executable.

If you have any improvements or comments, let us know in the comments below.