Harden SSH on Linux: Key Auth, Rate Limit, and 2FA

Overview: SSH hardening on Linux and why it matters

SSH hardening on Linux is a must for any production server, lab environment, or remote workstation. Attackers continuously scan for exposed SSH services, so enforcing strong authentication, reducing attack surface, and implementing automated protections greatly lowers risk.

This guide gives practical steps to enforce key only authentication, tune sshd_config for security and usability, apply IP rate limit controls, deploy fail2ban, integrate two factor authentication with TOTP or hardware tokens, and validate or roll back changes safely.

Enforce key only authentication

Use SSH keys instead of passwords to remove credential guessing and brute force risk. Start by creating a modern key pair on your workstation, using ed25519 for most cases. Copy the public key to the server, verify key based login works, then disable password auth in sshd_config.

Example commands to generate and install a key:

ssh-keygen -t ed25519 -C "admin@host"
ssh-copy-id -i ~/.ssh/id_ed25519.pub user@server
ssh -i ~/.ssh/id_ed25519 user@server

After testing, set PasswordAuthentication no and ChallengeResponseAuthentication no in sshd_config, then test the configuration with sshd -t and restart sshd.

Harden sshd_config safely

Always back up the existing config before edits. Recommended options to add or verify include PermitRootLogin no, PasswordAuthentication no, MaxAuthTries 2, AllowUsers or Match blocks for specific accounts, X11Forwarding no, UseDNS no, and ClientAliveInterval with ClientAliveCountMax for idle session control.

See also  Linux Systemd Troubleshooting: Fix Failed Units Fast

Commands to check and apply changes:

sudo cp /etc/ssh/sshd_config /etc/ssh/sshd_config.bak
sudo nano /etc/ssh/sshd_config
sudo sshd -t
sudo systemctl restart sshd

If something goes wrong, restore the backup and restart sshd: sudo cp /etc/ssh/sshd_config.bak /etc/ssh/sshd_config, then sudo systemctl restart sshd.

Implement IP rate limit at the network level

Rate limiting reduces the impact of brute force scans by dropping or rejecting excessive connection attempts. On many distributions you can use nftables, iptables, or firewalld depending on your stack. Below is an iptables example that limits new SSH connections per minute per IP.

Example iptables rules to add:

SSH hardening on Linux
sudo iptables -I INPUT -p tcp --dport 22 -m conntrack --ctstate NEW -m recent --set
sudo iptables -I INPUT -p tcp --dport 22 -m conntrack --ctstate NEW -m recent --update --seconds 60 --hitcount 6 -j DROP

Persist these rules using your distribution method, or translate to nftables if you run nft by default. Test connectivity from a safe client before relying on the rules in production.

Deploy fail2ban for adaptive protection

fail2ban watches logs and applies temporary bans on hosts that trigger suspicious behavior, such as repeated failed SSH logins. Install fail2ban, create a jail override for sshd with a sensible bantime and maxretry, and enable at boot.

Basic steps:

  • Install, for example sudo apt install fail2ban or sudo dnf install fail2ban
  • Create /etc/fail2ban/jail.d/sshd.local with appropriate settings
  • Restart fail2ban and monitor with fail2ban-client status

Recommended jail snippet:

[sshd]
enabled = true
port = ssh
filter = sshd
logpath = /var/log/auth.log
maxretry = 5
bantime = 3600
findtime = 600

Integrate two factor authentication: TOTP and YubiKey

Two factor authentication adds a second factor after key based auth, improving account protection. For TOTP use libpam-google-authenticator or the OATH toolkit, and for hardware tokens use pam_u2f or pam_yubico depending on the token type.

See also  Optimize systemd Boot Performance on Linux Servers

Quick TOTP flow: install the PAM module, configure the user with google-authenticator, update /etc/pam.d/sshd to require the module after publickey auth, then enforce ChallengeResponseAuthentication yes and use AuthenticationMethods publickey,keyboard-interactive. Test in a separate session before logging out of active consoles.

Verification and monitoring

After changes, validate access and monitor logs to ensure no unintended lockouts. Useful commands include systemctl status sshd, journalctl -u sshd, sudo tail -f /var/log/auth.log, and fail2ban-client status sshd.

Monitor connection counters and ban lists, review sudo and lastlog entries periodically, and add alerting for unusual spikes in failed auth attempts. A checklist helps to confirm each mitigation is active and working.

  • sshd unit health: sudo systemctl status sshd
  • auth logs: sudo tail -n 200 /var/log/auth.log
  • fail2ban status: sudo fail2ban-client status sshd

Rollback and recovery plan

Always prepare a recovery path before locking down SSH. Options include console access via provider portal, an out of band KVM, a secondary admin user that you do not modify, or a timed cron job that restores the previous sshd_config if you lose access.

Sample emergency restore using a scheduled job:

# create a restore script that runs once in 10 minutes
sudo bash -c 'echo "#!/bin/bash
cp /etc/ssh/sshd_config.bak /etc/ssh/sshd_config
systemctl restart sshd
rm -f /etc/cron.d/ssh-restore" > /etc/cron.d/ssh-restore'
sudo chmod +x /etc/cron.d/ssh-restore

Remove the cron job after confirming normal access. Having console access from your cloud provider or a rescue image is the safest fallback.

Frequently asked questions

Below are common operational questions and concise answers to help with real world deployments.

  • Can I combine key only auth with 2FA: Yes, require both public key and an interactive second factor by setting AuthenticationMethods to publickey,keyboard-interactive in sshd_config, and configure PAM appropriately.
  • Will rate limiting block legitimate users on NATed networks: It can if many users share a single source IP. Tune hitcount and time window, or use geolocation and allowlist rules for known office ranges.
  • How do I test fail2ban without getting locked out: Use a disposable account or test from a single IP you control, monitor fail2ban-client while triggering sample failures, then adjust maxretry and bantime.
  • Is hardware token integration disruptive: It can be if not tested. Deploy for a pilot account first, provide recovery keys, and document registration steps for administrators.
See also  Tune Linux vm.swappiness for Server Performance

Conclusion

Securing SSH on Linux is a layered process that starts with eliminating password based logins and enforcing strong public key authentication, then tuning SSH server parameters, adding network level rate limits, and deploying adaptive tools such as fail2ban. Two factor authentication further raises the bar against account compromise, while monitoring and verification ensure your protections function as intended.

Before you make changes, plan a recovery method such as console access, a secondary admin account, or an automated rollback. Test every change from a separate session, document configuration backups, and automate monitoring to detect regression. Applying these steps yields a resilient SSH posture that balances security and operational continuity, suitable for servers, cloud instances, and remote admin hosts in real world environments.

Leave a Comment

Your email address will not be published. Required fields are marked *

Scroll to Top