JDK 8 RFC 6470700: Math.random() / Math.initRNG() uses "double checked locking"

Steven Schlansker stevenschlansker at gmail.com
Thu Aug 22 00:35:51 UTC 2013


On Aug 21, 2013, at 4:37 PM, Brian Burkhalter <brian.burkhalter at oracle.com> wrote:

> With respect to this issue
> 
> http://bugs.sun.com/view_bug.do?bug_id=6470700
> 
> the code of concern from java.lang.Math is
> 
> 701    private static Random randomNumberGenerator;
> 702
> 703    private static synchronized Random initRNG() {
> 704        Random rnd = randomNumberGenerator;
> 705        return (rnd == null) ? (randomNumberGenerator = new Random()) : rnd;
> 706     }
> 
> 731    public static double random() {
> 732        Random rnd = randomNumberGenerator;
> 733        if (rnd == null) rnd = initRNG();
> 734        return rnd.nextDouble();
> 735    }
> 
> where the class variable "randomNumberGenerator" is not used anywhere else in the class. The complaint is that this is an instance of the broken double-checked locking pattern. While at first glance this might appear to be the case, it does not seem so to me. It looks more like an attempt to avoid calling a synchronized method if "randomNumberGenerator" has already been initialized.


This looks very much like the "Broken multithreaded version" from
http://www.cs.umd.edu/~pugh/java/memoryModel/DoubleCheckedLocking.html

// Broken multithreaded version
// "Double-Checked Locking" idiom
class Foo { 
  private Helper helper = null;
  public Helper getHelper() {
    if (helper == null) 
      synchronized(this) {
        if (helper == null) 
          helper = new Helper();
      }    
    return helper;
    }
  // other functions and members...
  }


"Unfortunately, that code just does not work in the presence of either optimizing compilers or shared memory multiprocessors."




More information about the core-libs-dev mailing list