Skip to content

/commands/ufw/ufw-limit-ssh-rate-limiting

ufw limit ssh: rate limit SSH connections against brute force

The commands on this page have not been executed by our verification runner yet.updated
tool
ufw
versions
ufw 0.36
os
linux

sudo ufw limit ssh (or sudo ufw limit 22/tcp) accepts SSH connections but denies a source address that opens 6 or more new connections within 30 seconds. It slows down password-guessing bots without blocking normal use. Use it instead of ufw allow ssh, not in addition to it: an earlier allow rule for the same port matches first and the limit never applies.

bash
sudo ufw limit ssh                           # port 22 via /etc/services, TCP
sudo ufw limit 2222/tcp comment 'SSH port'   # SSH on a custom port
sudo ufw limit OpenSSH                       # the OpenSSH application profile
sudo ufw delete allow ssh                    # remove an older allow rule, if any
sudo ufw status                              # the rule shows as LIMIT

What the rule does

ufw turns a limit rule into two iptables rules that use the recent match: every new connection records the source address, and when the same address has started 6 connections within 30 seconds the next one is denied. In ufw's source the rule is built from -m conntrack --ctstate NEW -m recent --set and -m recent --update --seconds 30 --hitcount 6. Connections from the address are accepted again once its rate drops below the threshold.

Variants

CommandEffect
ufw limit sshLimit port 22, protocol from /etc/services (TCP).
ufw limit 22/tcpSame with an explicit port and protocol.
ufw limit 2222/tcpFor sshd on a non-default port; the rule follows the port, not the service.
ufw limit OpenSSHUse the application profile shipped with openssh-server.
ufw limit from 192.0.2.0/24 to any port 22 proto tcpLimit only one network; others need their own rule.
ufw limit log 22/tcpAlso log new connections that match the rule.
ufw delete limit sshRemove the limit rule.

Pitfalls

  • Rule order. ufw status numbered must not show an ALLOW for 22/tcp above the LIMIT rule. Delete the allow or insert the limit at position 1.
  • IPv4 and IPv6. ufw has supported limit rules for IPv6 since version 0.33, provided the kernel offers the recent match for ip6tables (ufw tests this capability before creating the IPv6 limit chains). Check that ufw status lists 22/tcp (v6) LIMIT.
  • Automation tools. Ansible, rsync loops or CI jobs that open a new SSH connection per command can exceed 6 connections in 30 seconds. Enable SSH connection multiplexing (ControlMaster) or exempt the automation host with an allow rule inserted above the limit.
  • Profile names. ufw limit OpenSSH needs the profile to exist; otherwise ufw stops with Could not find a profile matching.

Confirm it works

sudo ufw status verbose shows 22/tcp LIMIT IN Anywhere. sudo iptables -S ufw-user-input | grep recent prints the underlying recent rules with --seconds 30 --hitcount 6. With logging enabled, denied attempts appear with the [UFW LIMIT BLOCK] prefix in the kernel log.

FAQ

Can I change the 6 connections in 30 seconds limit?

Not from the ufw command line; the values are fixed in ufw. For other thresholds write your own rules with the iptables recent or hashlimit match in /etc/ufw/before.rules, or use fail2ban, which bans by failed logins rather than by connection count.

Does ufw limit count failed logins?

No. It counts new connections per source address, successful or not. Several SSH sessions opened quickly from the same address, for example by scripts or Ansible without connection reuse, can hit the limit too.

Should I keep ufw allow ssh as well?

No. A limit rule already accepts the connections under the threshold. Keeping an earlier allow rule for the same port makes it match first, and the limit never applies; delete the allow rule.

Sources