Page 1 of 2

Password Hashing

Posted: Mon Nov 01, 2010 10:05 pm
by Plxply
Hello,

I've recently started to learn PHP and in an attempt to further my learning I decided to create a URL shortening service with a registration and login system. At the current time I hash the password and a random unique salt 1,000 times with SHA-512, however I have seen people recommend that you hash the password 100,000 or even 500,000 times. I understand that slowing down the speed of attack is good from a security standpoint, but when testing on my server to hash a password 400,000 times it takes 1 second which would add a reasonable amount of time to the login procedure.

Is hashing a password with SHA-512 1,000 times sufficient, or would it be better to increase it for higher security?

Re: Password Hashing

Posted: Mon Nov 01, 2010 10:19 pm
by Jonah Bron
It is my understanding that once is sufficient. A URL shortening service is not an FBI data center. You may want to skip the login thing altogether.

Re: Password Hashing

Posted: Tue Nov 02, 2010 1:28 am
by Apollo
Plxply wrote:Is hashing a password with SHA-512 1,000 times sufficient, or would it be better to increase it for higher security?
It is completely nonsense, really. Hashing just once with SHA-512 is absolutely fine. Even more so if you use a long salt (e.g. several hundreds of chars).

Re: Password Hashing

Posted: Tue Nov 02, 2010 2:57 am
by Zyxist
People who recommend doing such things have no clue about cryptography at all. It is mathematically proved that hashing function composition H(H(x)) is at most as strong as the original function H(x). So, it does not help at all, and can even make the things worse by increasing the number of possible collisions. The proof is extremely simple:

suppose that we have two strings x and y and a hashing function H(). There can be two cases:

1. H(x) = H(y), then H(H(x)) = H(H(y)) - it's a trivial and obvious case.
2. H(x) != H(y) - we do not have a collision.

The second case is more interesting. The hashes produced for two strings are different, but they are strings, too, so they can be hashed. And we can't say anything about the hashes of hashes without the exact knowledge about the H() function. There can occur another two situations:

1. H(H(x)) != H(H(y)) - the hashes produced from x and y do not produce a collision.
2. H(H(x)) = H(H(y)), even if H(x) != H(y) - if the hashes produced from x and y produce a collision, when hashed.

We can't deny the second situation since we do not know, how H() works, so we must assume that the hashes themselves can collide, too. The result is obvious: double hashing cannot reduce the number of collisions (they are unavoidable since we try to map an infinite set of strings to a finite number of possible hashes), but can produce new ones for strings that haven't previously collided, if there collisions between strings that are valid hashes.

Re: Password Hashing

Posted: Tue Nov 02, 2010 8:34 am
by Plxply
Would hashing a large amount of times not be helpful in the case of a brute force attack? Say for instance my database becomes compromised and the attacker now has all the hashes, he would have to use a dictionary or brute force with the salt for each individual hash. However if it is hashed 1,000 times wouldn't that mean that he would also have to hash 1,000 slowing the attack down?

Re: Password Hashing

Posted: Tue Nov 02, 2010 10:12 am
by Zyxist
True brute force attack is a nonsense. There are way too many combinations to check, even without any protection.

If your database is compromised, and the attacker has the full access to the hashes, the last thing he needs is to decode users' passwords, unless he wants to check if they use the same on other websites. However, if he does want to do so, there are 1092398371928379 much smarter ways to obtain them - if he has an access to the database, then usually he has access to the website files, too, so he can modify the login script to send the passwords back to him.

Furthermore, if he has an access to hashes, he does not have to encrypt it on-the-fly, but rather use some precalculated rainbow tables. If he is desperated enough, he could be a criminal and simply rent a botnet to do the job for him to recalculate them against i.e. x1000 hashing. And if there are collisions between hashes from hashes, especially in such a long chains of function compositions, you can actually simplify the attack. Increasing the algorithm constant does not change it complexity at all, and if you really want to increase the time needed for such attacks, you must increase complexity, not the constant factor. A good way is adding the salt, because it requires the attacker to recalculate the whole rainbow tables for every password separately.

BTW. And the most obvious reason NOT to do in this way: fine, the attacker would need 1000 times more time, but your website will need it, too. On your local computer, where there's only you and your script, one second might not be a problem, but remember that you do not create the website for yourself, but for dozens, hundreds and thousands of people. Just don't be surprised that one day your website will stop working, because the servers will be busy with calculating hashes for people who try to log in.

To sum up: salt is ENOUGH.

Re: Password Hashing

Posted: Tue Nov 02, 2010 10:13 am
by Apollo
Plxply wrote:Would hashing a large amount of times not be helpful in the case of a brute force attack? Say for instance my database becomes compromised and the attacker now has all the hashes, he would have to use a dictionary or brute force with the salt for each individual hash. However if it is hashed 1,000 times wouldn't that mean that he would also have to hash 1,000 slowing the attack down?
Yes, it would. However this effect is only linear, whereas you exponentially increase the number of possibilities (thus the required brute force time) by using a stronger hash. For this reason, a single sha512 hash is much stronger than a 1,000 level nested sha512 hash.

A sha512 hash is (obviously) 512 bits. Suppose your hacker has a botnet consisting of a million 3GHz machines, all capable of doing one check per clock cycle. Which is completely unrealistic, but for the sake of argument. Any clue how long it would take him to brute force just one hash? (hint: way, WAY longer than the current age of the universe)

Re: Password Hashing

Posted: Tue Nov 02, 2010 12:52 pm
by Plxply
Thanks for your help everyone,

Can someone explain if using HMAC with SHA512 would be beneficial when hashing? I have tried Googling it however as with my original question there was conflicting answers and some articles that still recommended the use of MD5 which were published in 2009 even I know that MD5 is insecure. Finally, is there any different hash function which has proven to be more secure than SHA-512, I know that SHA-3 is currently in the voting process and won't be complete until 2011 however I'm wondering if there is another standard that may be more secure which I have overlooked. Also apart from a 30 character side-wide salt and a 10 character randomly generated salt which is separate for each user (in the event for whatever reason my database is dumped however the PHP files are safe) is there anyway I can improve the security of users passwords?
Jonah Bron wrote:It is my understanding that once is sufficient. A URL shortening service is not an FBI data center. You may want to skip the login thing altogether.
This is just a project to learn PHP with and since I was doing that I might as well of learnt how to create a login system, even though the data isn't valuable I assume it's a good idea to get used to using the best available hashing method.

Re: Password Hashing

Posted: Wed Nov 03, 2010 9:10 am
by Apollo
Plxply wrote:Can someone explain if using HMAC with SHA512 would be beneficial when hashing?
Exactly how/what did you have in mind, other than just using a sha512 hash?
Finally, is there any different hash function which has proven to be more secure than SHA-512, I know that SHA-3 is currently in the voting process and won't be complete until 2011 however I'm wondering if there is another standard that may be more secure which I have overlooked.
Besides sha512, the Whirlpool algorithm is also very secure (and 512 bits as well). I wouldn't know which one is more secure, but I wouldn't worry about that, it's safe to assume sha512 to be very strong.

Re: Password Hashing

Posted: Wed Nov 03, 2010 1:09 pm
by Plxply
Apollo wrote:Exactly how/what did you have in mind, other than just using a sha512 hash?
I've read somewhere (sorry I can't find the exact link to the article now), but using hash_hmac is more secure than what I am using now.

What I'm using now:

Code: Select all

hash('sha512',$user_salt.$password.$sitesalt);
Using hash_hmac

Code: Select all

hash_hmac('sha512',$user_salt.$password,$sitesalt);

Re: Password Hashing

Posted: Thu Nov 04, 2010 7:15 am
by Apollo
Plxply wrote:I've read somewhere (sorry I can't find the exact link to the article now), but using hash_hmac is more secure than what I am using now.
I doubt that, hash_hmac does essentially this:

Code: Select all

hash('sha512',$salt1.hash('sha512',$salt2.$user_salt.$password))
with $salt1 and $salt2 both depending on (as in, generated from) $sitesalt.

I don't think this is more secure than what you were doing:
Plxply wrote:

Code: Select all

hash('sha512',$user_salt.$password.$sitesalt);
However if you still know where to find that original article, please post it here, I'd love to see their argument.

Re: Password Hashing

Posted: Sun Nov 14, 2010 4:15 am
by ronaldstarr
SHA 512 is almost twice than the present widely used SHA 256 secured , better go for Whirlpool algorithm , even this piece ( HUGE PIECE) of algorithm offers 512bit of security :)

Re: Password Hashing

Posted: Wed Dec 01, 2010 11:39 pm
by blainarm387
Hello all.

This is my first post to this board. I readily admit that I'm a newbie at PHP, so I hope that you'll indulge me with what may very well be a stupid question.

Am I correct in understanding that when using SHA-512 encryption, it is a common practice to have the PHP script create a unique, random salt to hash each user's password? If that's the case, here are a few questions:

1. What is a good length for a salt?
2. Where is it usually stored? Is it in a separate column in the database? (I'm guessing the answer is yes, because I can't see any other way to do so).
3. If the maximum password length is, say, 16 characters long, how long would the resulting hashed password be? For that matter, what would a reasonable maximum password length be?
4. (Really strange question) Would it make any sense at all to have the script check the hashed password, then once it is verified as correct, to create a new salt each time the user logs in, or is keeping the old salt around protection enough?

Looking forward to reading your answers.

Blain Armstrong
Toride, Japan.

Re: Password Hashing

Posted: Mon Dec 06, 2010 6:39 pm
by Jonah Bron
blainarm387 wrote:1. What is a good length for a salt?
Depends on the length of the user's password. A good generic length to my knowledge would probably be 10+ chars, using all 256 characters available.
blainarm387 wrote:2. Where is it usually stored? Is it in a separate column in the database? (I'm guessing the answer is yes, because I can't see any other way to do so).
Yes, in it's own column.
blainarm387 wrote:3. If the maximum password length is, say, 16 characters long, how long would the resulting hashed password be? For that matter, what would a reasonable maximum password length be?
The resulting hash is always the samelength with SHA-512: 512 characters long. SHA-256 is 256, MD5 is 32 (don't use MD5).
blainarm387 wrote:4. (Really strange question) Would it make any sense at all to have the script check the hashed password, then once it is verified as correct, to create a new salt each time the user logs in, or is keeping the old salt around protection enough?
You could if you want to, if it's a high security site. But if you're asking that, it's likely not :wink:. Basically the only time that would be useful is if someone gains access to your database (unlikely).

Re: Password Hashing

Posted: Tue Dec 07, 2010 2:07 am
by matthijs
At some point you also have to ask yourself if what you're trying to improve is worth the effort. Once you use a strong enough hash, other places in your web app become the weak link. It's like replacing your front door with a 20 inch steel door used in banks, while the back door still has a simple glass window easily breakable.

I wonder what the real weak links are nowadays.
- being hosted on a shared host and having your site hacked by a vulnerability on another website on the same server
- login credentials being stolen from a user (maybe by a virus or something)
- a vulnerability in one of the scripts/plugins used on your website
- etc

Anyway, this is slightly off-topic, but maybe still relevant in the hashing discussion