💾 Archived View for thrig.me › blog › 2024 › 06 › 24 › ssh-autoban.gmi captured on 2024-08-18 at 19:18:33. Gemini links have been rewritten to link to archived content
⬅️ Previous capture (2024-07-09)
-=-=-=-=-=-=-
Continuing the recent topic cluster of firewall bans in response to naughty traffic, rumor has it that OpenSSH is adding a temporary autoban and moreover will turn the feature on by default, coming soon to OpenBSD 7.6 (fall 2024); other operating systems will pick up on the new OpenSSH at their leisure, and then eventually users will update their systems to obtain this new feature, or not.
penalise particular problematic client behaviours
enable PerSourcePenalties by default
There are downsides; this could catch users who like to type in their passwords wrongly, though you can whitelist ranges where users are expected to login from. Also there's a CIDR range of how wide the temporary autoban is; this on the one hand will prevent the rotation through temporary IPv6 addresses or using all of a /24 subnet to attack from, but if a host has lots of client systems connecting via NAT a lot of legitimate connections may also be blocked.
Why not fail2ban? For one, it is not packaged for OpenBSD. Another concern is fail2ban has had security vulnerabilities related to poor log parsing; sshd has the socket and thus the peer address in a struct so need not string parse a random log into which an attacker can maybe inject custom strings. Always anchor the regular expressions to better avoid this, if you are using regular expression based log scanning. Let's see how long it takes TCP/22 to get attacked on my cloud virt…
Mon Jun 24 16:46:42 UTC 2024 Jun 24 16:49:25 thrig sshd[50969]: fatal: Timeout before authentication for 60.191.20.210 port 23456
Pretty slow; Windows systems in the olden days could be hacked under a minute of being put on the Internet, though attackers knew that those university subnets were open, high speed, and prone to having users put new Windows systems on them, even after we had told them to apply the patches on the patch CD first, but no they wanted that wafer-thin keyboard driver. Anyways let's assume that you're getting a lot of "Timeout before authentication" logs and want to collect the IP addresses involved; a bad regular expression is the following, where the "\S+" or "not whitespace, infinity to one character in length" matches the IP address, which might also be an IPv6 address.
qr/Timeout before authentication for (\S+)/
The problem here is that an attacker may be able to inject a log entry that contains the substring "Timeout before authentication for 8.8.8.8" where that IP address could be an important internal system, in effect creating a denial of service. An even worse regular expression might be
qr/Timeout before authentication for (.*) port/
as now among other problems the attacker can supply fun IP addresses such as "`rm -rf /`" and hopefully you aren't needlessly running those strings through a system(3) type call? A better regular expression anchors to some end of the string, ideally the beginning, which will help prevent false matches on other portions of the logs. Downside: the regular expression is more fragile and will break if the timestamp format is changed, or if the daemon log messages change. What happens if someone restarts a daemon in some wacky locale, and now the messages are helpfully in Italian?
qr/^\w{3}\s+\d{1,2}\s+[\d:]{8}\s+\S+\sssh\[\d+\]: fatal: Timeout before authentication for (\S+)
There are regular expression libraries that can match both IPv4 and IPv6 addresses, but another method is to run the string through inet_pton(3) to check for validity. sshd(8) meanwhile has a struct with the IP address in it so need not involve regular expression libraries (which have had security vulnerabilities) nor the execution of random shell code (avoid this if at all possible by using an execv(3) type call instead).
My SSH configuration has been modified to only allow connections from modern SSH implementations, which is fine for me (the client system is also OpenBSD 7.5) but bad if you support customers who use ancient SSH software, or you want to use libssh which last I checked did not implement various fancy new ciphers. This could also lock you out if you only have some outdated system to use when your main system dies, so there are tradeoffs here.
Jun 24 16:59:34 thrig sshd[31761]: Unable to negotiate with 152.32.206.87 port 39700: no matching host key type found. Their offer: ssh-rsa [preauth]
$ rubbled 152.32.206.87 152.32.206.87 zen.spamhaus.org. SBL (spammers) 152.32.206.87 zen.spamhaus.org. CSS (snowshoe) 152.32.206.87 zen.spamhaus.org. PBL (non-MTA ip) 152.32.206.87 zen.spamhaus.org. XBL (exploit)
Probably I should blacklist all traffic involving the SBL, CSS, and XBL hosts, but usually SSH is firewalled off to only a few known good subnets. Blocking them would keep more of the ne'er-do-wells away from the Gemini and SMTP services, for less CPU wasted, verses the risk of blocking someone both legitimate and who wants to actually read these ramblings.