← All articles

Harden SSH on Ubuntu in three moves

Linux security · July 2, 2026 · 5 min read · from our Hardened Linux Workstation guide

If a machine has SSH open to the internet, it is being probed right now — automated scanners work through the entire IPv4 space around the clock, guessing usernames and passwords. A default SSH installation accepts password authentication, which means those guesses can eventually land. Three changes turn SSH from your most-attacked surface into a near-impenetrable entry point.

Don't use SSH to reach this machine remotely? Then don't run it at all — check with sudo systemctl status ssh and remove or disable anything you don't need. The best attack surface is the one that isn't there.

Move 1: generate a modern key pair

Password authentication can be guessed; key authentication can't be. Generate an Ed25519 key pair — the modern default: small, fast, and strong:

# Generate a modern Ed25519 key pair
ssh-keygen -t ed25519 -C "your-label-here"

# When prompted, set a strong passphrase for the key
# This protects the key even if your private key file is stolen

# The key pair is saved to:
# Private key: ~/.ssh/id_ed25519       (keep this secret)
# Public key:  ~/.ssh/id_ed25519.pub   (share this freely)

# Copy your public key to a remote server
ssh-copy-id -i ~/.ssh/id_ed25519.pub user@remote-server

The passphrase matters: it means a stolen key file alone is still useless.

Move 2: harden the server configuration

Test your key login first — you're about to turn off passwords, and you want a working key before you lock the door behind you. Then edit /etc/ssh/sshd_config:

sudo nano /etc/ssh/sshd_config

# Disable password authentication (use keys only)
PasswordAuthentication no
ChallengeResponseAuthentication no

# Disable root login entirely
PermitRootLogin no

# Allow only specific users
AllowUsers yourusername

# Limit authentication attempts
MaxAuthTries 3
MaxSessions 3

# Restart SSH to apply changes
sudo systemctl restart ssh

Each line closes a door: no passwords to brute-force, no root to target (attackers guess root first, always), an explicit allowlist of who may log in at all, and a hard cap on attempts per connection.

Move 3: make failed guesses expensive with fail2ban

Even with passwords off, the probing traffic is noise you can turn into an automatic blocklist. fail2ban watches the auth log and bans IPs that keep failing:

sudo apt install fail2ban -y

# Create a local configuration (do not edit the original)
sudo cp /etc/fail2ban/jail.conf /etc/fail2ban/jail.local
sudo nano /etc/fail2ban/jail.local

# Under [sshd], set:
# enabled  = true
# maxretry = 3
# bantime  = 3600   # ban for 1 hour
# findtime = 600    # within a 10-minute window

sudo systemctl enable fail2ban
sudo systemctl start fail2ban

# Check banned IPs
sudo fail2ban-client status sshd

Run that last command after a day exposed to the internet and watch the ban list fill up — it's a live view of exactly why this chapter exists.

The other eight layers

SSH is one door. A hardened workstation also locks the disk (LUKS), the network (default-deny UFW), DNS, the browser, application behavior (AppArmor), and your backups — and pairs it all with the operating habits that keep the setup tight.

The full playbook · $9

Build a Hardened Linux Workstation

The complete, step-by-step version — every command, config, and the reasoning behind it. Instant PDF, yours to keep.

Get the guide — $9

Instant PDF · 30-day money-back guarantee · buy once, keep forever