6

I am developing a site in PHP 5.4. Which function is better to use to generate a random salt for password security?

$salt = sha1(openssl_random_pseudo_bytes(23));

or

$seed = '';
$a = @fopen('/dev/urandom','rb');
$seed .= @fread($a,23);
$salt = sha1(seed);

Or should I just go with:

$salt =  openssl_random_pseudo_bytes(40);

or

$salt = '';
$a = @fopen('/dev/urandom','rb');
$salt .= @fread($a,23);
TRiG
  • 610
  • 5
  • 14
John
  • 173
  • 1
  • 6

2 Answers2

7

The right way to generate a salt for password hashing is: do not do it yourself. Use a library which already does thing properly. See @Terry's answer for pointers.

For your exact question, it so happens that openssl_random_pseudo_bytes() relies on OpenSSL's internal PRNG, which itself feeds on what the underlying platform provides, i.e. dev/urandom, so it is safe. Strictly speaking, you should use the second parameter of that function to check whether OpenSSL did find a strong source of randomness on the local platform (see the documentation), but in practice, as long as OpenSSL runs on a Unix-like or Windows-like platform, things will be fine. So it does not really matter, for security, whether you call openssl_random_pseudo_bytes() or read /dev/urandom yourself. For maintenance reasons, I would prefer the former, which is simpler (only one call) and more portable (it will also work on Windows, whereas reading /dev/urandom will not).

Either way, applying SHA-1 on the output of openssl_random_pseudo_bytes() or /dev/urandom, is totally useless. Good PRNG already produce unpredictable uniformly random bytes (and if your PRNG is not good, then why are you using it ?).

Thomas Pornin
  • 326,555
  • 60
  • 792
  • 962
  • He might be using the hash function to convert binary output into human readable encoding. bin2hex() PHP function could be used to achieve the same, without hashing the output. – Matrix Dec 30 '12 at 15:27
  • doesnt have to be readable and thank you, and i was aware of of the second second parameter and had used it to test my system to see if it had enough randomness and entropy, i scoured the doc pages on both before i asked the question, i am writing this more to advance my knowledge than i am to do production development. – John Dec 30 '12 at 20:54
  • as a learning developer i feel that i should thoroughly explore the code i am learning, to give me a better grasp of it and what it does. so down the road when i am using libraries like phpass i will have a better command of what they are doing to handle debugging, and many other thing, what i learn doing this could lead to learning any number of other things. – John Dec 30 '12 at 21:19
3

Note: This doesn't answer the question exactly.

Try not to roll your own crypto. Since you are using PHP, a great bcrypt library - phpass, is readily available that will take care of the password hashing aspect, including generating salts.