← News
/PLAYBOOK · 2026-07-25

Fail2ban SSH brute-force defense: first line of server security

Fail2ban tutorial: install, configure, and dynamically ban SSH brute-force IPs. Includes iptables verification and manual unban. Five steps to automated defense.

Scope

This tutorial is for Linux admins who expose SSH to the public internet. SSH brute-force attacks are among the most common automated attacks. Attackers try username/password combinations via dictionaries or enumeration. Fail2ban watches failed-login patterns in logs, then dynamically adds iptables or nftables rules to block malicious IPs. It is a practical first line of defense.

Prerequisites

How it works

Fail2ban is a closed loop: log watch → match rules → dynamic ban.

Steps

Step 1: Install Fail2ban

`# Debian/Ubuntu
sudo apt update
sudo apt install fail2ban -y

# CentOS/RHEL
sudo yum install epel-release -y
sudo yum install fail2ban -y`

Step 2: Confirm SSH log path

`# Debian/Ubuntu default path
ls -la /var/log/auth.log

# CentOS/RHEL default path
ls -la /var/log/secure`

Step 3: Create local config

Do not edit `jail.conf` directly (updates overwrite it). Put custom config in `jail.local`:

`sudo tee /etc/fail2ban/jail.local << 'EOF'
[DEFAULT]
# Ban time: 3600 seconds (1 hour)
bantime = 3600
# Time window: 600 seconds (10 minutes)
findtime = 600
# Threshold: max 5 failures within 10 minutes
maxretry = 5

# Send email notifications (optional, requires sendmail)
# destemail = admin@example.com
# action = %(action_mwl)s

[sshd]
enabled = true
# Log path auto-detected
logpath = %(sshd_log)s
# SSH port
port = ssh

# Whitelist (IPs that are never banned)
# ignoreip = 127.0.0.1/8 192.168.1.0/24
EOF`

Step 4: Start and enable Fail2ban

`# Restart to load the new configuration
sudo systemctl restart fail2ban

# Enable start on boot
sudo systemctl enable fail2ban

# Check running status
sudo systemctl status fail2ban`

Step 5: Check ban status and stats

`# View all jail statuses
sudo fail2ban-client status

# View SSH jail details (banned IP list)
sudo fail2ban-client status sshd

# View recent logs
sudo tail -f /var/log/fail2ban.log`

Verify

Verify 1: Simulate brute force

From another host, test with a wrong password (do not test from the IP you are using):

`# From the test machine, repeatedly log in with a wrong password
ssh testuser@your-serverIP

# After 6 attempts, legitimate SSH should be rejected
# Watch fail2ban logs
sudo tail -20 /var/log/fail2ban.log
# Should see something like: INFO [sshd] Ban xx.xx.xx.xx`

Verify 2: Check iptables rules

`# Confirm Fail2ban has added the rule chain
sudo iptables -L -n | grep -A 20 \"f2b-sshd\"

# Example output:
# Chain f2b-sshd (1 references)
# target     prot opt source               destination
# REJECT     all  --  xx.xx.xx.xx          0.0.0.0/0
# RETURN     all  --  0.0.0.0/0            0.0.0.0/0`

Verify 3: Manually unban a test IP

`# Unban the specified IP
sudo fail2ban-client set sshd unbanip xx.xx.xx.xx

# View the updated ban list
sudo fail2ban-client status sshd`

FAQ

Q1: Fail2ban banned my own IP. What now?

Unban immediately with `fail2ban-client set sshd unbanip your-IP`. Then add a whitelist in `[DEFAULT]` of `jail.local`: `ignoreip = 127.0.0.1/8 your-static-public-IP`. Restart Fail2ban. If you have no static IP, raise maxretry to 10-15 to cut false bans.

Q2: Fail2ban does nothing. No ban records in the log?

Common causes and checks: ① Confirm the service is up: `systemctl status fail2ban`; ② Check the SSH log path: `fail2ban-client get sshd logpath`. If it returns `/var/log/secure` but your system uses `auth.log`, set `logpath = /var/log/auth.log` in jail.local; ③ Confirm the fail2ban user can read the log; ④ In `fail2ban.conf`, change `loglevel = INFO` to `DEBUG` for verbose logs.

Takeaway

Fail2ban is a lightweight SSH brute-force defense. It bans malicious IPs from log analysis. This article covered install, config, and verification. Combine it with SSH key auth (disable password login), a non-default SSH port, and Port Knocking for defense in depth. Check fail2ban ban stats weekly. Watch for abnormal spikes.