javarandomsecure-random

Generating Predictable Secure Random Numbers


How can I instantiate a predictable and secure random number generator which will generate consistent random numbers across Java versions and operating systems?

The following code used to work in Java 8 but no longer works in Java 10:

import java.security.SecureRandom;

public class PredictableRandom {

public static void main(String[] args) {
    PredictableRandom predictableRandom = new PredictableRandom();
    predictableRandom.execute();
}

private void execute() {
    SecureRandom secureRandom = new SecureRandom();
    System.out.println(secureRandom.getAlgorithm());
    System.out.println(secureRandom.getProvider());
    long seed = 12345678L;
    secureRandom.setSeed(seed);
    System.out.println(secureRandom.nextLong());
    SecureRandom secureRandom2 = new SecureRandom();
    secureRandom2.setSeed(seed);
    System.out.println(secureRandom2.nextLong());
}
}

In Java 8 - good, different random objects generate the same random number:

SHA1PRNG
SUN version 1.8
3325995872096263519
3325995872096263519

In Java 10 - bad, different random objects generate different random number:

DRBG
SUN version 10
-3526685326322256981
-2373261409119309182

Solution

  • What you want to do is get the an instance of secure random using the old algorithm using SecureRandom.getInstance.

    Sample code below. You should think about weather or not this is the behaviour that you actually want.

        public void example() throws NoSuchAlgorithmException {
        {
            SecureRandom secureRandom = SecureRandom.getInstance("SHA1PRNG");
            secureRandom.setSeed(12345678L);
            System.out.println(secureRandom.nextLong());
    
        }
        {
            SecureRandom secureRandom = SecureRandom.getInstance("SHA1PRNG");
            secureRandom.setSeed(12345678L);
            System.out.println(secureRandom.nextLong());
    
        }
    
    }
    

    This spits out:

    3325995872096263519
    3325995872096263519
    

    Just like you were looking for.