Exposed SSH servers see constant password-guessing attempts. Key-only authentication defeats them, and sshguard keeps the logs quiet by blocking repeat offenders. Set up and test your SSH key first (see First steps).
1Keys only
Keep an existing session open while you make these changes, so you can recover from a mistake. Edit /etc/ssh/sshd_config:
PermitRootLogin no
PasswordAuthentication no
KbdInteractiveAuthentication no
PubkeyAuthentication yes
AllowGroups wheel
MaxAuthTries 3
LoginGraceTime 30
On FreeBSD, sshd uses PAM through keyboard-interactive authentication, so KbdInteractiveAuthentication no is required as well as PasswordAuthentication no. AllowGroups wheel limits logins to wheel members; adjust it to suit.
2Test and reload
sshd -t # syntax check, no output means OK
service sshd reload
From a new terminal, confirm key login still works, and that password login is refused:
ssh alice@host.example.org
ssh -o PubkeyAuthentication=no -o PreferredAuthentications=password alice@host.example.org
# expect: Permission denied (publickey).
3Install sshguard
pkg install sshguard
Edit /usr/local/etc/sshguard.conf so it uses the PF backend and reads the auth log:
BACKEND="/usr/local/libexec/sshg-fw-pf"
FILES="/var/log/auth.log"
4Wire it into PF
The PF backend adds offenders to a table named sshguard. Your /etc/pf.conf needs the table and a block rule before the SSH pass rule (the PF tutorial's ruleset already has both):
table <sshguard> persist
block in quick on $ext_if from <sshguard>
pfctl -nf /etc/pf.conf && pfctl -f /etc/pf.conf
sysrc sshguard_enable=YES
service sshguard start
5Whitelist yourself
To avoid locking yourself out, add trusted addresses to a whitelist file and reference it in sshguard.conf:
echo '198.51.100.0/24' > /usr/local/etc/sshguard.whitelist
echo 'WHITELIST_FILE=/usr/local/etc/sshguard.whitelist' >> /usr/local/etc/sshguard.conf
service sshguard restart