Tuesday, January 28, 2014

securerandom vs random

Instances of java.util.Random are not cryptographically secure. Consider instead using SecureRandom to get a cryptographically secure pseudo-random number generator for use by security-sensitive applications.

Java offers a few ways to generate random numbers, the default being java.util.Random. java.security.SecureRandom offers a more-secure extension of java.util.Random which “provides a cryptographically strong random number generator”.

If you run twice java.util.Random.nextLong() with the same seed, it will produce the same number. For security reasons you want to stick with java.security.SecureRandom because it's a lot less predictable.


The Random Class
Java states that the Random class and its subclasses must produce predictable results when seeded with the same data
This however is not why this is insecure, and it is useful when testing.
The reason that this class is predictable though is the way in which it is seeded.
The Random class, in the absence of a seed in its constructor it will seed its random number generator with the current time in milliseconds.
This means that if somebody knows the time that the Random object was seeded and has several consecutive bytes of output then they can reasonably predict the next numbers.
Once somebody has discovered the seed for the generator all number produced from it can be seen as compromised.

The SecureRandom Class
The SecureRandom class is different, it again uses algorithms that when seeded will produce predictable results, but the algorithm is much more complex.
It uses a digest algorithm such as SHA-1 on the seed and a counter to generate random data.
Its true strength however lies in the method in which it is seeded.
The SecureRandom class is seeded using true random data gathered by the operating system
This is data gathered by the OS from sources of true randomisation, such as mouse movements, network packet arrival times, IO statistics and interrupts.
On Linux the data is gathered from /dev/random and on Windows via the CryptGenRandom() call in Windows.

When using SecureRandom
The more random numbers some can get a hold of the more likely they can figure out the seed. You should either throw away the SecureRandom object every now and then or reseed it. Keeping in mind the next point though.
The seeding the generator takes entropy out of the system, if it cannot get any entropy it will block until the system has some. This means if you’re reseeding the generator too often your program will hang along with anything else on the system requiring entropy.
Don’t seed the SecureRandom class yourself, unless you are 100% absolutely sure you are seeding it with purely random data, or you are testing and need repeatable results

if what you are generating is a security token of some sort then you will need a secure generator.
For example a session id, a one time password or an encryption key.

http://www.danielhall.me/2009/09/cryptographically-secure-random-numbers-in-java/

No comments:

Post a Comment