I used to get tons of invalid login attempts to my hosted server. A single IP address would repeatedly connect and try hundreds of account names, filling up my logs with junk. A few people I know use sshit to automatically firewall addresses that have too many unsuccessful connections. However, I tried to set up sshit and its weird dependencies on Perl IPC stuff didn't work so well for me. (Multithreaded perl is evil.)
So I took the concept of sshit and rewrote it as a little Python script that does everything I need it to do in 41 lines of code (sshit is 354). It connects to the syslog mechanism through /etc/syslog.conf:
auth.info;authpriv.info |exec /usr/local/sbin/fwssh.py
The script just reads log entries from stdin as they happen, and looks for invalid login attempts, calling ipfw to firewall connections for a while if somebody's being annoying. Here's what it looks like in practice:
Mar 20 07:46:58 occam sshd: Invalid user test from 126.96.36.199 Mar 20 07:47:00 occam sshd: Invalid user guest from 188.8.131.52 Mar 20 07:47:03 occam sshd: Invalid user admin from 184.108.40.206 Mar 20 07:47:03 occam root: 29000 deny ip from 220.127.116.11 to any Mar 20 08:02:03 occam root: 29000 24 1852 deny ip from 18.104.22.168 to any Mar 20 16:10:21 occam sshd: Invalid user guest from 22.214.171.124 Mar 20 16:10:31 occam sshd: Invalid user adm from 126.96.36.199 Mar 20 16:10:34 occam sshd: Invalid user lp from 188.8.131.52 Mar 20 16:10:34 occam root: 29000 deny ip from 184.108.40.206 to any Mar 20 16:25:34 occam root: 29000 25 1924 deny ip from 220.127.116.11 to any Mar 20 17:42:10 occam sshd: Invalid user a from 18.104.22.168 Mar 20 17:42:14 occam sshd: Invalid user b from 22.214.171.124 Mar 20 17:42:20 occam sshd: Invalid user c from 126.96.36.199 Mar 20 17:42:20 occam root: 29000 deny ip from 188.8.131.52 to any Mar 20 17:57:20 occam root: 29000 9 532 deny ip from 184.108.40.206 to any
Notice how the third invalid login attempt triggers the deny rule, then 15 minutes later the output of ipfw show for that rule shows how many packets and bytes were blocked. The rule is deleted after that 15 minutes.
If you'd like the source, you can grab it here.