December 23, 2014

455 words 3 mins read

Using Cloudflare as a Banhammer

These days “Snowulf” has become a loosely knit network of sites and projects. Most of the hosting is for myself, projects I’m involved with, or friends. Since I already pride myself in keeping my server online for the Snowulf Blog, adding a few other sites to the same server isn’t much of an issue. However the major headache of any site addition is… security. Every site and piece of software is slightly different. Most of the work is offloaded to Cloudflare’s Web Application Firewall however they’re not 100%. With some cheap tricks (and PHP), I’ve taught Cloudflare how to be a big banhammer.

The banhammer game started with one of my friends WordPress site. For whatever reason he’s attracted the attention of some people that really want to break his site, or break into it. Of course, the site is secured reasonably in WordPress itself, however brute force attacks are quite abusive to servers. Even with the security, MySQL usage would ramp up and chew my disk IO… which is ironically what originally tipped me off to the attacks. My hosting provider of choice is kind enough to alert me to unusual activity and the Disk IO warnings kept going off.

It didn’t take long to isolate the abuse, so I decided to fix it with a generous application of php duct tape. In short order, with the assistance of Josh, I built the Cloudflare Banhammer. The script is fairly simple and should be considered more of a proof of concept than something recommended for production. It uses an overly complex bash oneliner (because I love oneliners) to find all IPs that hit the login page more than 3 times per second. It’s entirely possible that this could cause a false positive, but I highly doubt there is a legitimate reason to “log in” in that often.

Drop the script into a cron-job to be run every X time (I chose 15mn) and away we go. If a bad actor is found, it uses the Cloudflare API to blacklist the IP address. Since going live with this system I’ve found a new blacklist entry in Cloudflare every day or two. The best part is that my server no longer gets its disk thrashed.

If you’d like to use the script, you’re more than welcome to, however I’d like to reiterate the part where I say it’s a proof of concept. Josh occasionally needs to remind me that you cannot substitute the letter “P” for a “}” brace in PHP (Which is why I hired him to be the programmer). Cloudflare has a lot of nifty features, sometimes you just need a little trickery to use them.

Update 2015-07-30: Updated script link to new repository home.