“In this HowTo I will show how to install and configure DenyHosts. DenyHosts is a tool that observes login attempts to SSH, and if it finds failed login attempts again and again from the same IP address, DenyHosts blocks further login attempts from that IP address by putting it into /etc/hosts.deny. DenyHosts can be run by cron or as a daemon. In this tutorial I will run DenyHosts as a daemon.”
Preventing SSH Dictionary Attacks with DenyHosts
About The Author
Follow me on Twitter @thomholwerda
2006-02-19 12:45 pmWereCatf
Uhh…that doesn’t stop someone from just checking all open ports and then test if there’s ssh server running on one of them. Then you are again open to dictionary attacks, or brute force. I myself just use the default port 22, and have DenyHosts block access to every service on my machine for any IP which tries to break in. My /etc/hosts.deny is already quite big ^^
Oh, and just as a side note to anyone who’s a newbie to these kinds of things: do NOT allow root to login remotely from anywhere..It’s just too easy to try to guess the root password using brute force attacks..
2006-02-19 1:16 pmMathman
Absolutely wrong. Unless you’re using a password which can be found in a dictionary, or one that’s less than 8 characters, there’s no way someone is going to brute force it. Try a password cracker out some time and you’ll see what I mean.
Edited 2006-02-19 13:18
2006-02-19 2:56 pmWereCatf
Most sites don’t allow passwords less than 8 chars, and a good bunch doesn’t allow any longer either, so you can just skip anything less and start the guessing from full 8 chars. And yes, it is fully possible. All you need is enough time, and if both the attacker and the host have a decent bandwidth available,it shouldn’t take a week or two. Even if took a month, it is still possible. Trust me, I have tried.
The attacker only needs to know one valid user account, that’s why having root access is so dangerous..
2006-02-19 5:43 pmMathman
If your password is simply lower case letters, that’s already 26^8, or roughly 200 billion different passwords to try. Add on upper case letters and we’re already at 53 trillion different passwords. Add on numbers and it goes up to 200 trillion. Throw in everything else and we’re looking at around 4 quadrillion different passwords you’d need to try. This is just for 8 character passwords. Now go with a 10 character or greater password like I do and we’re up to over a quintillion possible combinations. Good luck brute forcing that over a network. Heck, good luck brute forcing that if you’re on the local network.
In fact, I’ll even make it easy on you and give you a password hash, the one for my luser account. Get back to me in a billion years or so when you figure it out:
2006-02-19 11:28 pmpostmodern
Ever heard of Rainbow hashing? How about DIY Beowulfs? Zombie bot-nets? The excess of bandwidth and CPU power has made brute-forcing much more convenient.
2006-02-20 12:14 amMathman
I thought we were talking about brute forcing an ssh server here. I figure you can saturate my network with all 5M/s of bandwidth or whatever the heck it is. You still won’t get anywhere near what John The Ripper will do, which is what? If we’re really really generous, maybe 10000 md5 passwords per second, or maybe 1000 blowfish passwords per second? I don’t figure that’s going to add up to anywhere near a quintillion in my lifetime.
And sure things become easier when you have the password hash. No argument there. But did I not say I’m making it easy for the guy? Anyway, it would still surprise the heck out of me if he comes back with the unencrypted password any time soon.
2006-02-19 10:40 pmLettherebemorelight
there’s no way someone is going to brute force it.
My log files say otherwise.
FYI I find the way you assume everyone else in the world have the same rigid rules for password creatation as you do quite hillarious.
Edited 2006-02-19 22:42
2006-02-19 11:59 pmMathman
Did I not just say as long as you’re not using dictionary words and have a long enough passwords?
And when did I ever say everyone in the world has rigid rules for password creation? All I said is that using strong passwords makes brute forcing an ssh account pretty much impossible. That isn’t to say there aren’t root accounts out there with passwords of “money” or “root” and what have you.
2006-02-20 1:32 amLettherebemorelight
Nevermind, I’ll just put my last reply in simplified terms. When you replied to WereCatf and wrote “Absolutely wrong.”, infact you are the one who is wrong. What WereCatf wrote is factually correct.
Exactly what part of his post do you think is wrong?
2006-02-20 1:49 amMathman
So you’re going to sit there and tell me it’s possible to do a quintillion or so password attempts across the internet in any reasonable amount of time? Or I dunno, maybe my calculations of 90 or so to the tenth power are way off, but I didn’t think I was getting that rusty.
2006-02-20 1:54 pmLettherebemorelight
Yes it is possible. Im willing to bet that is probably the #1 reason why DenyHosts exists.
2006-02-20 2:36 pmMathman
Edited 2006-02-20 14:36
2006-02-19 11:24 pmpostmodern
Don’t forget about using public key authentication.
2006-02-20 6:38 amphoenix
There’s nothing wrong with allowing root logins via ssh … if you use keys instead of passwords, and put long passphrases onto your private keys. Newer versions of OpenSSH include a nice without-password option to the PermitRootLogin which only allows root logins using keys … no password allowed.
2006-02-20 8:26 amtaschenorakel
> Uhh…that doesn’t stop someone from just checking
> all open ports and then test if there’s ssh server
> running on one of them.
Well, but the funny thing is: Those kids floating your log files don’t do that, so for cleaning up your logfiles for being able to see real treats just moving the port helps.
Ok, but your other suggestion, disabling root login (or at least disabling password authentication) is pretty right. So just another indication, that DenyHosts is overkill for common secure shell setups. Remember: DenyHosts is yet another component which might break…
2006-02-19 1:11 pm_LH_
>This solution is overkill as there is some much more trivial solution to stop those kids trying to breaking automatically: Move your secure shell daemon to another port than 22. At least for me this tiny change blocked kids from one second to another.
That doesn’t really work if you have to provide shell access for hundreds of users some of which are somewhat non-technical.
2006-02-20 6:14 amsteviant
What are these people supposed to do with shell access if they’re so utterly clueless that they can’t even specify a port in their SSH client?
2006-02-19 1:47 pmSEJeff
On your *secure* host with ssh on port 1234, try running ‘nmap -sV’ against it and notice that is shows ssh + the version number with absolutely no problem. Like client side only, security through obscurity is NO security at all.
A better idea would be:
1.) Create a normal unprivileged user on the server with full sudo access.
2.) Use the ‘AllowUsers’ directive in the sshd_config to only allow that certain user.
3.) Make sure to uncomment ‘PermitRootLogin no’
4.) ‘ps -ef | grep sshd’ and find the pid of the ssh daemon.
5.) ‘kill -HUP xxxx’ where xxxx is the pid of sshd to force it to reload it’s configuration without restarting.
If you wanted to be really crazy, you could disable password authentication alltogether and use key based auth only. That is the most secure method.
Edited 2006-02-19 13:53
Probably though a TheHand.sh script appending to hosts.deny – would take (much) less resorces to basically do the same thing:
/etc/hosts.deny isn’t the best way to block incoming network traffic as it is ONLY supported by network daemons that support the older tcp wrappers (normally through xinetd/inetd) or via the newer libwrap. A slightly better approach is to add an address temporarily to an iptables drop rule. Blocking attackers at the firewall level temporarily is generally the best of both worlds. There is a very nice tool for what I speak of named DaemonShield:
Using linblock and it’s ability to read a local file, I made a perl script that checks the auth.log run through a cronjob every 5 minutes for these failed logins. It dumps the ip to a peerguardian formatted file that linblock reads and then adds an iptables rule blocking that ip.
Script and info here:
In all honesty, when I started blocking the RIPE and APNIC ip addresses, I stopped getting most dictionary attacks. Now, the majority of the attacks seem to be hitting my Apache server, looking for Drupal XSS vulernabilities.
FWIW, I’ve be using OpenBSD’s Packet Filter (PF) to address this for quite a while now:
pass in log quick on $ext_if inet proto tcp from ! $int_if:network to
( $ext_if ) port ssh flags S/SA keep state
( max-src-conn 5, max-src-conn-rate 3/30 ) queue ( default, interac )
Basically, if more than three connections are made to ssh in 30 seconds, subsequent connections from the offending IP within this time frame are blocked.
And while I don’t use Linux, the following rule actually blocks most of these “attacks”:
block in log quick on $ext_if inet proto tcp from any os Linux to
( $ext_if ) port ssh
2006-02-20 4:18 pmdruiloor
Althogh i too like the (I)PF syntax better then any off the ones supported by Linux-Netfilter:
iptables -A INPUT -p tcp -i eth0 -m state –state NEW
–dport 22 -m recent –update –seconds 30 -j DROP
iptables -A INPUT -p tcp -i eth0 -m state –state NEW
–dport 22 -m recent –set -j ACCEPT
There are plenty of variations on this theme and of course I’ve written one myself too
Some differences with mine though:
– multiple host sync: i.e. you have multiple hosts and you want them to synchronise the list of banned IPs.
– generic log monitoring system, ships with SSH and Apache config, although you could adapt to block IPs based on other logs too. Apache example is block based on a certain type of match such as PHP or JSP pages, since my site has none of these it’s likely an attack.
– manages iptables automagically, expires blocks automatically too.
For more info see the project site:
I’ve been running DenyHosts for about one year now. I’m pretty pleased. It is efficient and easy to manage. I remember I was looking before for a solution to deny unwanted access to my server through ssh and this was my choice.
The script I set to be executed every 10 minutes, so there could not be made too many tries… still 1 min might be better since it doesn’t overkill the processor.
Of course, requiring key-based authentication will take your brute force times into centuries, depeding on the key strength. This is really the best way to go.
2006-02-20 5:23 pmdruiloor
They’d try and workaround it i’d suppose, and write some exploit against a network service client application (or plugin) you use. If you happen to be running ssh-agent/keychain from the same account they’ll just hijack open sessions. Otherwize they’ll copy your priv-key, and try to brute-force the passphrase.
On a LAN i’d say: GSSAPI/Kerberos is probably the way to go (tickets only live something like 8-10 hours.) From outsite: users should OpenVPN in first.
For some people (using different laptop/PC machines often) one-time-password systems such as S/Key or OPIE should be better then any key/cert atlest in the sence that one needn’t take hardware (other then pen and paper) with them on road trips then.
But i suppose a good password policy (checked against cracklib) is very likely to be good enough most anywere.
[ Edit: s/pub/priv/ ]
Edited 2006-02-20 17:37
Another way to stop dictionary attacks is to turn off password authentication, by adding the following to sshd_config:
No passwords, no dictionary attacks.
This solution is overkill as there is some much more trivial solution to stop those kids trying to breaking automatically: Move your secure shell daemon to another port than 22. At least for me this tiny change blocked kids from one second to another.