SlideShare a Scribd company logo
The Java
Memory
Model
Authors: Jeremy Manson, William
Pugh, Sarita V. Adve
Presenter: Keren Zhou
COMP 522
Why Java needs a well-formed
memory model
• Java supports threads running on shared memory
• Java memory model defines multi-threaded Java
program semantics
• Key concerns: Java memory model specifies legal
behaviors and provides safety and security
properties
3/26/19 2
Why should we care about Java
Memory Model
• A programmer should know
• Junior level
• Use monitor, locks, and volatile properly
• Learn safety guarantees of Java
• Intermediate level
• Reason the correctness of concurrent programs
• Use concurrent data structures (e.g ConcurrentHashMap)
• Expert level
• Understand and optimize utilities in java.util.concurrent
• AbstractExecutorService
• Atomic variables
3/26/19 3
Create a singleton to get a static
instance
• Singleton: only want a single instance in a program
• Database
• Logging
• Configuration
3/26/19 4
public class Instance {
private static Instance instance;
public static Instance getInstance() {
if (instance == null)
instance = new Instance();
return instance;
}
}
1
2
3
4
5
6
7
8
The simple singleton is thread-
unsafe
3/26/19 5
public class Instance {
private static Instance instance;
public static Instance getInstance() {
if (instance == null)
instance = new Instance();
return instance;
}
}
1
2
3
4
5
6
7
8
Threads
T0
T1
Line 4
Line 4
Line 5
Line 5
Line 6
Line 6
getInstance
getInstance
Time Line
Create two instances at the same time!
Use synchronized keyword
3/26/19 6
• Java synchronized keyword can be used in different
contexts
• Instance methods
• Code blocks
• Static methods
• Only one thread can execute inside a static synchronized
method per class, irrespective of the number of instances it
has.
The synchronized singleton has
low performance
3/26/19 7
public class Instance {
private static Instance instance;
public synchronized static Instance getInstance() {
if (instance == null)
instance = new Instance();
return instance;
}
}
1
2
3
4
5
6
7
8
Threads
T0
T1
Line 4 Line 5 Line 6
getInstance
getInstance
Time Line
Line 4 Line 5 Line 6
Use double-checked lock to make
it more efficient
• Motivation: In the early days, the cost of
synchronization could be quite high
• Idea: Avoid the costly synchronization for all
invocations of the method except the first
• Solution:
• First check if the instance is null or not
• If instance is null, enter a critical section to create the
object
• If instance is not null, return instance
3/26/19 8
Double checked-lock
implementation
3/26/19 9
public class Instance {
private static Instance instance;
public static Instance getInstance() {
if (instance == null) {
synchronized (Instance.class) {
if (instance == null) {
instance = new Instance();
}
}
}
return instance;
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
How double-checked lock goes
wrong
• Brief answer: instruction reorder
• Suppose T0 is initializing with the following three
steps
1) mem = allocate(); //Allocate memory for Singleton
2) ctorSingleton(mem); //Invoke constructor
3) object.instance = mem; //initialize instance.
• What if step 2 is interchanged with step 3?
• Another thread T1 might see the instance before being
fully constructed
3/26/19 10
A thread returns an object that
has not been constructed
3/26/19 11
public static Instance getInstance() {
if (instance == null) {
synchronized (UnsafeInstance.class) {
if (instance == null) {
instance = new Instance();
}
}
}
return instance;
}
3
4
5
6
7
8
9
10
11
12
Threads
T0
T1
Line 4
Line 4
Line 5
Line 11
Line 6
getInstance
getInstance
Time Line
Line 7
mem = allocate();
object.instance = mem;
ctorSingleton(mem);
T1 returns before constructor completes!
Use volatile to avoid reordering
• The behavior of volatile differs significantly between
programming languages
• C/C++
• Volatile keyword means always read the value of the variable
memory
• Operations on volatile variables are not atomic
• Cannot be used as a portable synchronization mechanism
• Java
• Prevent reordering
• Derive a synchronization order on top of Java Memory Model
3/26/19 12
Use volatile to avoid reordering
• Java’s volatile was not consistent with developers
intuitions
• The original Java memory model allowed for volatile
writes to be reordered with nonvolatile reads and writes
• Under the new Java memory model (from JVM
v1.5), volatile can be used to fix the problems with
double-checked locking
3/26/19 13
Java memory model history
• 1996: An Optimization Pattern for Efficiently
Initializing and Accessing Thread-safe Objects,
Douglas C. Schmidt and etc.
• 1996: The Java Language Specification, chapter 17,
James Gosling and etc.
• 1999: Fixing the Java Memory Model, William Pugh
• 2004: JSR 133---Java Memory Model and Thread
Specification Revision
3/26/19 14
Review: sequential consistency
• Total order: Memory actions must appear to
execute one at a time in a single total order
• Program order: Actions of a given thread must
appear in the same order in which they appear in
the program
3/26/19 15
Review: sequential consistency
violation
3/26/19 16
r2 = x
y = 1
r1 = y
x = 2
Thread 1 Thread 2
Initial conditions: x = y = 0
Final results: r2 == 2 and r1 == 1?
Decision: Disallowed. Violates sequential consistency
1
2
3
4
Circular dependency!
Inter threads dependency
Intra thread dependency
Java memory model balances
between performance and safety
• Sequential consistency
• Easy to understand
• Restricts the use of many compiler and hardware
transformations
• Relaxed memory models
• Allow more optimizations
• Hard to reason about the correctness
3/26/19 17
Java memory model hides underlying
hardware memory model
3/26/19 18
Java Program
High-level Language Memory Model
Java Compiler
Java Runtime
Hardware Memory Model
TSO, Power’s weak model, …
Java defines data-race-free model
• Data race occurs when two threads access the
same memory location, at least one of the accesses
is a write, and there is no intervening
synchronization
• A data-race-free Java program guarantees
sequential consistency (Correctly synchronized)
3/26/19 19
Another definition of data-race from
Java Memory Model’s perspective
• Two accesses x and y form a data race in an
execution of a program if they are from different
threads, they conflict, and they are not ordered by
happens-before
3/26/19 20
Happens-before memory model
• A simpler version than the full Java Memory Model
• Happens-before order
• The transitive closure of program order and the synchronizes-
with order
• Happens-before consistency
• Determines the value that a non-volatile read can see
• Synchronization order consistency
• Determines the value that a volatile read can see
• Solves part of the Java mysterious problems
3/26/19 21
Program order definition
• The program order of thread T is a total order that
reflects the order in which these actions would be
performed according to intra-thread semantics of T
• If x and y are actions of the same thread and x comes
before y in program order, then hb(x, y) (i.e. x happens-
before y)
3/26/19 22
Eliminate ambiguity in program
order definition
• Given a program in Java
• Program order does not mean that y = 6 must be
subsequent to x = 5 from a wall clock perspective. It
only means that the sequence of actions executed
must be consistent with that order
3/26/19 23
y = 6
x = 5
1
2
What should be consistent in
program order
• Happens-before consistency
• A read r of a variable v is allowed to observe a write w to v if
• r does not happen-before w (i.e., it is not the case that hb(r, w)) – a
read cannot see a write that happens-after it, and
• There is no intervening write w0 to v (i.e., no write w0 to v such
that hb(w, w0), hb(w0, r)) –the write w is not overwritten along a
happens-before path.
• Given a Java program
• hb(1, 2) & hb(2, 3) -> hb(1, 3), so z sees 6 be written to
y
3/26/19 24
y = 6
x = 5
z = y
1
2
3
Synchronization Order
• A synchronization order is a total order over all of
the synchronization actions of an execution
• A write to a volatile variable v synchronizes-with all
subsequent reads of v by any thread;
• An unlock action on monitor m synchronizes-with all
subsequent lock actions on m that were performed by
any thread;
• …
• If an action x synchronizes-with a following action y,
then we have hb(x, y)
3/26/19 25
What should be consistent in
synchronization order
• Synchronization order consistency
• Synchronization order is consistent with program order
• Each read r of a volatile variable v sees the last write to v
to come before it in the synchronization order
3/26/19 26
Happens-before memory model
example
3/26/19 27
x = 1
ready = true
if (ready)
r1 = x
Thread 1 Thread 2
1
2
3
4
synchronization-with
program order
Initial conditions: x = 0, ready = false, ready is volatile
Final results: r1 == 1?
Decision: Allowed. The program is correctly synchronized
Proof:
Program order: hb(L1, L2) and hb(L3, L4)
Synchronization order: hb(L2, L3)
Transitive: hb(L1, L4)
Recall data-race definition:
Two accesses x and y form a
data race in an execution of a
program if they are from
different threads, they conflict,
and they are not ordered by
happens-before
Correct double-checked lock with
volatile
3/26/19 28
public class Instance {
private volatile static Instance instance;
public static Instance getInstance() {
if (instance == null) {
synchronized (Instance.class) {
if (instance == null) {
instance = new Instance();
}
}
}
return instance;
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
1. mem = allocate();
2. ctorSingleton(mem);
3. object.instance = mem;
hb(2, 3) ensures that L2’s write to mem can be seen at L3
Happens-before doesn’t solve all
problems
3/26/19 29
r1 = x
if (r1 != 0)
y = 42
r2 = y
if (r2 != 0)
x = 42
Thread 1 Thread 2
Initial conditions: x = y = 0
Final results: r1 == r2 == 42?
Decision: Disallowed. Because the values are out-of-thin-air.
In a future aggressive system, Thread 1 could speculatively write the value 42 to y.
How to propose a methodology to disallow these behaviors?
1
2
3
4
5
6
Happens-before doesn’t solve all
problems
3/26/19 30
r1 = a
r2 = a
if (r1 == r2)
b = 2
r3 = b
a = r3
Thread 1 Thread 2
Initial conditions: a = 0, b = 1
Final results: r1 == r2 == r3 == 2?
Decision: Allowed. A compiler may determines that r1 and r2 have the same value and
eliminate if r1 == r2 (L3). Then, b = 2 (L4) can be moved to an earlier position (L1)
1
2
3
4
5
6
b = 2
r1 = a
r2 = r1
if (true)
r3 = b
a = r3
Thread 1 Thread 2
1
2
3
4
4
5
What’s the difference between
two programs
• One difference between the acceptable and
unacceptable results is that in latter program, the
write that we perform (i.e. b = 2) would also have
occurred if we had carried on the execution in a
sequentially consistent way.
• In the former program, value 42 in any sequentially
consistent execution will not be written.
3/26/19 31
Well-behaved execution
• We distinguish two programs by considering
whether those writes could occur in a sequentially
consistent execution.
• Well-behaved execution
• A read that must return the value of a write that is
ordered before it by happens-before.
3/26/19 32
Disallowed examples-data
dependency
3/26/19 33
r1 = x
a[r1] = 0
r2 = a[0]
y = r2
r3 = y
x = r3
Thread 1 Thread 2
1
2
3
4
5
6
Initial conditions: x = y = 0; a[0] = 1, a[1] = 2
Final results: r1 == r2 == r3 == 1?
Decision: Disallowed. Because values are out-of-thin-air.
Proof: We have hb(L1, L2), hb(L2, L3). To let r2 == 1, a[0] must be 0. Since initially
a[0] == 1 and hb(L2, L3), we have r1 == 0 at a[r1] = 0 (L2). r1 at L2 is the final value
Because hb(L1, L2), r1 at L2 must see the write to r1 at r1 = x (L1).
Disallowed examples-control
dependency
3/26/19 34
z = 1 r1 = z
if (r1 == 0)
x = 1
Thread 1 Thread 2
1 2
3
4
r2 = x
y = r2
Thread 3
r3 = y
x = r3
Thread 4
5
6
7
8
Initial conditions: x = y = z = 0
Final results: r1 == r2 == r3 == 1?
Decision: Disallowed. Because values are out-of-thin-air.
Proof: Because we have hb(L5, L6), to let r2 == 1 (so that y = 1), x = 1 (L4) must be
executed. If L4 is executed, if (r1 == 0) (L3) must be true. However, since r1 == 1 and
hb(L2, L3), L4 cannot be executed.
Disallowed examples-control
dependency
3/26/19 35
r1 = x
if (r1 == 0)
x = 1
Thread 1
1
2
3
r2 = x
y = r2
Thread 2
r3 = y
x = r3
Thread 3
4
5
6
7
Initial conditions: x = y = 0
Final results: r1 == r2 == r3 == 1?
Decision: Disallowed. Because values are out-of-thin-air
Proof: The same reason as the previous example.
Causality
• Actions that are committed earlier may cause
actions that are committed later to occur
• The behavior of incorrectly synchronized programs
is bounded by causality
• The causality requirement is strong enough to
respect the safety and security properties of Java
and weak enough to allow standard compiler and
hardware optimizations
3/26/19 36
Justify a correct execution
• Build up causality constraints to justify executions
• Ensures that the occurrence of a committed action and
its value does not depend on an uncommitted data race
• Justification steps
• Starting with the empty set as C0
• Perform a sequence of steps where we take actions from
the set of actions A and add them to a set of committed
actions Ci to get a new set of committed actions Ci+1
• To demonstrate that this is reasonable, for each Ci we
need to demonstrate an execution E containing Ci that
meets certain conditions
3/26/19 37
Justification examples-reorder
3/26/19 38
r1 = x
y = 1
r2 = y
x = r2
Thread 1 Thread 2
Initial conditions: x = y = 0
Final results: r1 == r2 == 1?
Decision: Allowed, because of compiler transformation. y = 1 (L2) is a constant that
does not affect r1 = x (L2).
1
2
3
4
y = 1
r1 = x
r2 = y
x = r2
Thread 1 Thread 2
1
2
3
4
C1:
y = 1
r2 = y (0)
x = r2 (0)
r1 = x (0)
C2:
y = 1
r2 = y (1)
x = r2 (1)
r1 = x (0)
C3:
y = 1
r2 = y (1)
x = r2 (1)
r1 = x (0)
C4:
y = 1
r2 = y (1)
x = r2 (1)
r1 = x (1)
Justification examples-redundant
elimination
3/26/19 39
r1 = a
if (r1 == 1)
b = 1
r2 = b
if (r2 == 1)
a = 1
if (r2 == 0)
a = 1
Thread 1 Thread 2
1
2
3
4
5
6
7
8
Initial conditions: a = b = 0
Final results: r1 == r2 == 1?
Decision: Allowed. A compiler could determine that Thread 2 always writes 1 to a and
hoists the write to the beginning of Thread 2.
C1:
a = 1
r1 = a (0)
b = 1 (0)
r2 = b (0)
C2:
a = 1
r1 = a (1)
b = 1 (0)
r2 = b (0)
C3:
y = 1
r1 = a (1)
b = 1 (1)
r2 = b (0)
C4:
y = 1
r1 = a (1)
b = 1 (1)
r2 = b (1)
r1 = a
if (r1 == 1)
b = 1
a = 1
r2 = b
Thread 1 Thread 2
1
2
3
4
5
Justification examples-inter
thread analysis
3/26/19 40
r1 = x
r2 = 1 + r1*r1 – r1
y = r2
r3 = y
x = r3
Thread 1 Thread 2
1
2
3
4
5
Initial conditions: x = y = 0
Final results: r1 == r2 == 1?
Decision: Allowed. Interthread analysis could determine that x and y are always either
0 or 1, and thus determine that r2 is always 1. Once this determination is made, the write
of 1 to y could be moved early in Thread 1.
r2 = 1
y = r2
r1 = x
r3 = y
x = r3
Thread 1 Thread 2
1
2
3
4
5
C1:
r2 = 1
y = r2 (0)
r3 = y (0)
x = r3 (0)
r1 = x (0)
C2:
r2 = 1
y = r2 (1)
r3 = y (0)
x = r3 (0)
r1 = x (0)
C3:
r2 = 1
y = r2 (1)
r3 = y (1)
x = r3 (0)
r1 = x (0)
C4:
r2 = 1
y = r2 (1)
r3 = y (1)
x = r3 (1)
r1 = x (0)
C5:
r2 = 1
y = r2 (1)
r3 = y (1)
x = r3 (1)
r1 = x (1)
Comparison between allowed
examples and disallowed examples
3/26/19 41
r1 = x
if (r1 == 0)
x = 1
Thread 1
1
2
3
r2 = x
y = r2
Thread 2
r3 = y
x = r3
Thread 3
4
5
6
7
r1 = x
if (r1 == 0)
x = 1
r2 = x
y = r2
Thread 1
1
2
3
4
5
r3 = y
x = r3
Thread 2
6
7
Initial conditions: x = y = 0
Final results: r1 == r2 == r3 == 1?
Decision: Allowed. Interthread analysis could determine that x is always 0 or 1. So
we can replace r2 = x by r2 = 1 and y = r2 by y = 1. After moving y = 1 and r2 = 1 to an
earlier position, we get r1 == r2 == r3.
y = 1
r2 = 1
r1 = x
if (r1 == 0)
x = 1
Thread 1
r3 = y
x = r3
Thread 2
6
7
1
2
3
4
5
Comparison between allowed
examples and disallowed examples
3/26/19 42
r1 = x
if (r1 == 0)
x = 1
Thread 1
1
2
3
r2 = x
y = r2
Thread 2
r3 = y
x = r3
Thread 3
4
5
6
7
Initial conditions: a = b = 0
Final results: r1 == r2 == r3 == 2?
Decision: Allowed. Although there are some SC executions in which r1 != r2 (L3), we can
hoist b = 2 (L4) to an earlier position and there is an SC execution such that r1 == r2.
For the above case, there’s no SC execution such that r1 == 0 (L2) is true and
r1 == r2 == r3 == 1. That is, if we hoist x = 1 to an earlier position, L2 must be false.
r1 = a
r2 = a
if (r1 == r2)
b = 2
r3 = b
a = r3
Thread 1 Thread 2
1
2
3
4
1
2
1
2
3
1
2
Practical issues-final field
• “For space reasons, we omit discussion of two
important issues in the Java memory model: the
treatment of final fields, and finalization / garbage
collection.”
• Java’s final field also allows programmers to
implement thread-safe immutable objects without
synchronization
3/26/19 43
Rule of thumb
• Set the final fields for an object in that object's
constructor; and do not write a reference to the
object being constructed in a place where another
thread can see it before the object's constructor is
finished.
• What happens in the constructor
• If a read occurs after the field is set in the constructor, it
sees the value the final field is assigned, otherwise it
sees the default value.
3/26/19 44
Can we change a final field?
• Reflection introduces problems
• The specification allows aggressive optimization of
final fields. Within a thread, it is permissible to
reorder reads of a final field with those
modifications of a final field that do not take place
in the constructor.
3/26/19 45
Practical issues-final field
3/26/19 46
• new A().f() could return -1, 0, or 1
class A {
final int x;
A() { x = 1; }
int f() { return d(this,this); }
int d(A a1, A a2) {
int i = a1.x;
g(a1);
int j = a2.x;
return j - i;
}
static void g(A a) {
// uses reflection to change a.x to 2
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
reorder!
Practical issues-final field
3/26/19 47
• new A().f() could return -1, 0, or 1
class A {
final int x;
A() { x = 1; }
int f() { return d(this,this); }
int d(A a1, A a2) {
int i = a1.x;
g(a1);
int j = a2.x;
return j - i;
}
static void g(A a) {
// uses reflection to change a.x to 2
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
return 1
Practical issues-final field
3/26/19 48
• new A().f() could return -1, 0, or 1
class A {
final int x;
A() { x = 1; }
int f() { return d(this,this); }
int d(A a1, A a2) {
g(a1);
int i = a1.x;
int j = a2.x;
return j - i;
}
static void g(A a) {
// uses reflection to change a.x to 2
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
return 0
Practical issues-final field
3/26/19 49
• new A().f() could return -1, 0, or 1
class A {
final int x;
A() { x = 1; }
int f() { return d(this,this); }
int d(A a1, A a2) {
int j = a2.x;
g(a1);
int i = a1.x;
return j - i;
}
static void g(A a) {
// uses reflection to change a.x to 2
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
return -1
Practical issue-efficient singleton
• The initialization-on-demand holder (design pattern)
idiom is a lazy-loaded singleton. In all versions of
Java, the idiom enables a safe, highly concurrent lazy
initialization with good performance.
3/26/19 50
public class SafeInstance {
private SafeInstance() {}
private static class LazyHolder {
static final SafeInstance INSTANCE = new SafeInstance();
}
public static SafeInstance getInstance() {
return LazyHolder.INSTANCE;
}
}
1
2
3
4
5
6
7
8
9
Why initialization-on-demand
holder is safe?
• When the class is initialized?
• A class or interface type T will be initialized
immediately before the first occurrence of any one
of the following:
• A static field declared by T is used and the field is not a
constant variable
• A variable of primitive type or type String, that is final and
initialized with a compile-time constant expression is called a
constant variable.
• …
3/26/19 51
Why initialization-on-demand
holder is safe?
• Why initialization is safe?
• For each class or interface C, there is a unique
initialization lock LC. The mapping from C to LC is
left to the discretion of the Java Virtual Machine
implementation.
• We can also implement singleton by ENUM in Java.
3/26/19 52
Conclusion
• Following happens-before rules allows us to write a
data-race-free program that is correctly
synchronized.
• Java memory model provides a clear definition of
well-behaved executions, preventing values come
out-of-thin-air in the presence of data race.
• Double-checked lock is thread-safe for JVM later
than v1.5.
3/26/19 53
Reference Books
• Goetz, Brian, et al. Java concurrency in practice.
Pearson Education, 2006.
• Gosling, James, et al. The Java language
specification. Pearson Education, 2014.
• Lea, Doug. "The JSR-133 cookbook for compiler
writers." (2008).
3/26/19 54
Reference URLs
• Double-checked locking
https://www.ibm.com/developerworks/java/library/j
-dcl/index.html
• Causality test cases
http://www.cs.umd.edu/~pugh/java/memoryModel/
unifiedProposal/testcases.html
3/26/19 55

More Related Content

Similar to COMP522-2019-Java-Memory-Model.pdf

Modern Java Concurrency
Modern Java ConcurrencyModern Java Concurrency
Modern Java Concurrency
Ben Evans
 
Working With Concurrency In Java 8
Working With Concurrency In Java 8Working With Concurrency In Java 8
Working With Concurrency In Java 8
Heartin Jacob
 
Advanced Introduction to Java Multi-Threading - Full (chok)
Advanced Introduction to Java Multi-Threading - Full (chok)Advanced Introduction to Java Multi-Threading - Full (chok)
Advanced Introduction to Java Multi-Threading - Full (chok)
choksheak
 
The Java Memory Model
The Java Memory ModelThe Java Memory Model
The Java Memory Model
CA Technologies
 
New hope is comming? Project Loom.pdf
New hope is comming? Project Loom.pdfNew hope is comming? Project Loom.pdf
New hope is comming? Project Loom.pdf
Krystian Zybała
 
Java Concurrency and Performance | Multi Threading | Concurrency | Java Conc...
Java Concurrency and Performance | Multi Threading  | Concurrency | Java Conc...Java Concurrency and Performance | Multi Threading  | Concurrency | Java Conc...
Java Concurrency and Performance | Multi Threading | Concurrency | Java Conc...
Anand Narayanan
 
What’s expected in Java 9
What’s expected in Java 9What’s expected in Java 9
What’s expected in Java 9
Gal Marder
 
Building large scale, job processing systems with Scala Akka Actor framework
Building large scale, job processing systems with Scala Akka Actor frameworkBuilding large scale, job processing systems with Scala Akka Actor framework
Building large scale, job processing systems with Scala Akka Actor framework
Vignesh Sukumar
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
Luis Goldster
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
Hoang Nguyen
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
James Wong
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
Fraboni Ec
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
Harry Potter
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
Young Alista
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
Tony Nguyen
 
Reactive Design Patterns: a talk by Typesafe's Dr. Roland Kuhn
Reactive Design Patterns: a talk by Typesafe's Dr. Roland KuhnReactive Design Patterns: a talk by Typesafe's Dr. Roland Kuhn
Reactive Design Patterns: a talk by Typesafe's Dr. Roland Kuhn
Zalando Technology
 
Modern Java Concurrency (Devoxx Nov/2011)
Modern Java Concurrency (Devoxx Nov/2011)Modern Java Concurrency (Devoxx Nov/2011)
Modern Java Concurrency (Devoxx Nov/2011)
Martijn Verburg
 
Cc module 3.pptx
Cc module 3.pptxCc module 3.pptx
Cc module 3.pptx
ssuserbead51
 
Towards a Scalable Non-Blocking Coding Style
Towards a Scalable Non-Blocking Coding StyleTowards a Scalable Non-Blocking Coding Style
Towards a Scalable Non-Blocking Coding Style
Azul Systems Inc.
 
Modern Java Concurrency (OSCON 2012)
Modern Java Concurrency (OSCON 2012)Modern Java Concurrency (OSCON 2012)
Modern Java Concurrency (OSCON 2012)
Martijn Verburg
 

Similar to COMP522-2019-Java-Memory-Model.pdf (20)

Modern Java Concurrency
Modern Java ConcurrencyModern Java Concurrency
Modern Java Concurrency
 
Working With Concurrency In Java 8
Working With Concurrency In Java 8Working With Concurrency In Java 8
Working With Concurrency In Java 8
 
Advanced Introduction to Java Multi-Threading - Full (chok)
Advanced Introduction to Java Multi-Threading - Full (chok)Advanced Introduction to Java Multi-Threading - Full (chok)
Advanced Introduction to Java Multi-Threading - Full (chok)
 
The Java Memory Model
The Java Memory ModelThe Java Memory Model
The Java Memory Model
 
New hope is comming? Project Loom.pdf
New hope is comming? Project Loom.pdfNew hope is comming? Project Loom.pdf
New hope is comming? Project Loom.pdf
 
Java Concurrency and Performance | Multi Threading | Concurrency | Java Conc...
Java Concurrency and Performance | Multi Threading  | Concurrency | Java Conc...Java Concurrency and Performance | Multi Threading  | Concurrency | Java Conc...
Java Concurrency and Performance | Multi Threading | Concurrency | Java Conc...
 
What’s expected in Java 9
What’s expected in Java 9What’s expected in Java 9
What’s expected in Java 9
 
Building large scale, job processing systems with Scala Akka Actor framework
Building large scale, job processing systems with Scala Akka Actor frameworkBuilding large scale, job processing systems with Scala Akka Actor framework
Building large scale, job processing systems with Scala Akka Actor framework
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
 
Concurrency with java
Concurrency with javaConcurrency with java
Concurrency with java
 
Reactive Design Patterns: a talk by Typesafe's Dr. Roland Kuhn
Reactive Design Patterns: a talk by Typesafe's Dr. Roland KuhnReactive Design Patterns: a talk by Typesafe's Dr. Roland Kuhn
Reactive Design Patterns: a talk by Typesafe's Dr. Roland Kuhn
 
Modern Java Concurrency (Devoxx Nov/2011)
Modern Java Concurrency (Devoxx Nov/2011)Modern Java Concurrency (Devoxx Nov/2011)
Modern Java Concurrency (Devoxx Nov/2011)
 
Cc module 3.pptx
Cc module 3.pptxCc module 3.pptx
Cc module 3.pptx
 
Towards a Scalable Non-Blocking Coding Style
Towards a Scalable Non-Blocking Coding StyleTowards a Scalable Non-Blocking Coding Style
Towards a Scalable Non-Blocking Coding Style
 
Modern Java Concurrency (OSCON 2012)
Modern Java Concurrency (OSCON 2012)Modern Java Concurrency (OSCON 2012)
Modern Java Concurrency (OSCON 2012)
 

Recently uploaded

ITSM Integration with MuleSoft.pptx
ITSM  Integration with MuleSoft.pptxITSM  Integration with MuleSoft.pptx
ITSM Integration with MuleSoft.pptx
VANDANAMOHANGOUDA
 
CEC 352 - SATELLITE COMMUNICATION UNIT 1
CEC 352 - SATELLITE COMMUNICATION UNIT 1CEC 352 - SATELLITE COMMUNICATION UNIT 1
CEC 352 - SATELLITE COMMUNICATION UNIT 1
PKavitha10
 
Redefining brain tumor segmentation: a cutting-edge convolutional neural netw...
Redefining brain tumor segmentation: a cutting-edge convolutional neural netw...Redefining brain tumor segmentation: a cutting-edge convolutional neural netw...
Redefining brain tumor segmentation: a cutting-edge convolutional neural netw...
IJECEIAES
 
学校原版美国波士顿大学毕业证学历学位证书原版一模一样
学校原版美国波士顿大学毕业证学历学位证书原版一模一样学校原版美国波士顿大学毕业证学历学位证书原版一模一样
学校原版美国波士顿大学毕业证学历学位证书原版一模一样
171ticu
 
Data Driven Maintenance | UReason Webinar
Data Driven Maintenance | UReason WebinarData Driven Maintenance | UReason Webinar
Data Driven Maintenance | UReason Webinar
UReason
 
Unit-III-ELECTROCHEMICAL STORAGE DEVICES.ppt
Unit-III-ELECTROCHEMICAL STORAGE DEVICES.pptUnit-III-ELECTROCHEMICAL STORAGE DEVICES.ppt
Unit-III-ELECTROCHEMICAL STORAGE DEVICES.ppt
KrishnaveniKrishnara1
 
People as resource Grade IX.pdf minimala
People as resource Grade IX.pdf minimalaPeople as resource Grade IX.pdf minimala
People as resource Grade IX.pdf minimala
riddhimaagrawal986
 
22CYT12-Unit-V-E Waste and its Management.ppt
22CYT12-Unit-V-E Waste and its Management.ppt22CYT12-Unit-V-E Waste and its Management.ppt
22CYT12-Unit-V-E Waste and its Management.ppt
KrishnaveniKrishnara1
 
spirit beverages ppt without graphics.pptx
spirit beverages ppt without graphics.pptxspirit beverages ppt without graphics.pptx
spirit beverages ppt without graphics.pptx
Madan Karki
 
Material for memory and display system h
Material for memory and display system hMaterial for memory and display system h
Material for memory and display system h
gowrishankartb2005
 
BRAIN TUMOR DETECTION for seminar ppt.pdf
BRAIN TUMOR DETECTION for seminar ppt.pdfBRAIN TUMOR DETECTION for seminar ppt.pdf
BRAIN TUMOR DETECTION for seminar ppt.pdf
LAXMAREDDY22
 
Properties Railway Sleepers and Test.pptx
Properties Railway Sleepers and Test.pptxProperties Railway Sleepers and Test.pptx
Properties Railway Sleepers and Test.pptx
MDSABBIROJJAMANPAYEL
 
Use PyCharm for remote debugging of WSL on a Windo cf5c162d672e4e58b4dde5d797...
Use PyCharm for remote debugging of WSL on a Windo cf5c162d672e4e58b4dde5d797...Use PyCharm for remote debugging of WSL on a Windo cf5c162d672e4e58b4dde5d797...
Use PyCharm for remote debugging of WSL on a Windo cf5c162d672e4e58b4dde5d797...
shadow0702a
 
Engineering Drawings Lecture Detail Drawings 2014.pdf
Engineering Drawings Lecture Detail Drawings 2014.pdfEngineering Drawings Lecture Detail Drawings 2014.pdf
Engineering Drawings Lecture Detail Drawings 2014.pdf
abbyasa1014
 
Applications of artificial Intelligence in Mechanical Engineering.pdf
Applications of artificial Intelligence in Mechanical Engineering.pdfApplications of artificial Intelligence in Mechanical Engineering.pdf
Applications of artificial Intelligence in Mechanical Engineering.pdf
Atif Razi
 
Certificates - Mahmoud Mohamed Moursi Ahmed
Certificates - Mahmoud Mohamed Moursi AhmedCertificates - Mahmoud Mohamed Moursi Ahmed
Certificates - Mahmoud Mohamed Moursi Ahmed
Mahmoud Morsy
 
Generative AI leverages algorithms to create various forms of content
Generative AI leverages algorithms to create various forms of contentGenerative AI leverages algorithms to create various forms of content
Generative AI leverages algorithms to create various forms of content
Hitesh Mohapatra
 
An improved modulation technique suitable for a three level flying capacitor ...
An improved modulation technique suitable for a three level flying capacitor ...An improved modulation technique suitable for a three level flying capacitor ...
An improved modulation technique suitable for a three level flying capacitor ...
IJECEIAES
 
Curve Fitting in Numerical Methods Regression
Curve Fitting in Numerical Methods RegressionCurve Fitting in Numerical Methods Regression
Curve Fitting in Numerical Methods Regression
Nada Hikmah
 
cnn.pptx Convolutional neural network used for image classication
cnn.pptx Convolutional neural network used for image classicationcnn.pptx Convolutional neural network used for image classication
cnn.pptx Convolutional neural network used for image classication
SakkaravarthiShanmug
 

Recently uploaded (20)

ITSM Integration with MuleSoft.pptx
ITSM  Integration with MuleSoft.pptxITSM  Integration with MuleSoft.pptx
ITSM Integration with MuleSoft.pptx
 
CEC 352 - SATELLITE COMMUNICATION UNIT 1
CEC 352 - SATELLITE COMMUNICATION UNIT 1CEC 352 - SATELLITE COMMUNICATION UNIT 1
CEC 352 - SATELLITE COMMUNICATION UNIT 1
 
Redefining brain tumor segmentation: a cutting-edge convolutional neural netw...
Redefining brain tumor segmentation: a cutting-edge convolutional neural netw...Redefining brain tumor segmentation: a cutting-edge convolutional neural netw...
Redefining brain tumor segmentation: a cutting-edge convolutional neural netw...
 
学校原版美国波士顿大学毕业证学历学位证书原版一模一样
学校原版美国波士顿大学毕业证学历学位证书原版一模一样学校原版美国波士顿大学毕业证学历学位证书原版一模一样
学校原版美国波士顿大学毕业证学历学位证书原版一模一样
 
Data Driven Maintenance | UReason Webinar
Data Driven Maintenance | UReason WebinarData Driven Maintenance | UReason Webinar
Data Driven Maintenance | UReason Webinar
 
Unit-III-ELECTROCHEMICAL STORAGE DEVICES.ppt
Unit-III-ELECTROCHEMICAL STORAGE DEVICES.pptUnit-III-ELECTROCHEMICAL STORAGE DEVICES.ppt
Unit-III-ELECTROCHEMICAL STORAGE DEVICES.ppt
 
People as resource Grade IX.pdf minimala
People as resource Grade IX.pdf minimalaPeople as resource Grade IX.pdf minimala
People as resource Grade IX.pdf minimala
 
22CYT12-Unit-V-E Waste and its Management.ppt
22CYT12-Unit-V-E Waste and its Management.ppt22CYT12-Unit-V-E Waste and its Management.ppt
22CYT12-Unit-V-E Waste and its Management.ppt
 
spirit beverages ppt without graphics.pptx
spirit beverages ppt without graphics.pptxspirit beverages ppt without graphics.pptx
spirit beverages ppt without graphics.pptx
 
Material for memory and display system h
Material for memory and display system hMaterial for memory and display system h
Material for memory and display system h
 
BRAIN TUMOR DETECTION for seminar ppt.pdf
BRAIN TUMOR DETECTION for seminar ppt.pdfBRAIN TUMOR DETECTION for seminar ppt.pdf
BRAIN TUMOR DETECTION for seminar ppt.pdf
 
Properties Railway Sleepers and Test.pptx
Properties Railway Sleepers and Test.pptxProperties Railway Sleepers and Test.pptx
Properties Railway Sleepers and Test.pptx
 
Use PyCharm for remote debugging of WSL on a Windo cf5c162d672e4e58b4dde5d797...
Use PyCharm for remote debugging of WSL on a Windo cf5c162d672e4e58b4dde5d797...Use PyCharm for remote debugging of WSL on a Windo cf5c162d672e4e58b4dde5d797...
Use PyCharm for remote debugging of WSL on a Windo cf5c162d672e4e58b4dde5d797...
 
Engineering Drawings Lecture Detail Drawings 2014.pdf
Engineering Drawings Lecture Detail Drawings 2014.pdfEngineering Drawings Lecture Detail Drawings 2014.pdf
Engineering Drawings Lecture Detail Drawings 2014.pdf
 
Applications of artificial Intelligence in Mechanical Engineering.pdf
Applications of artificial Intelligence in Mechanical Engineering.pdfApplications of artificial Intelligence in Mechanical Engineering.pdf
Applications of artificial Intelligence in Mechanical Engineering.pdf
 
Certificates - Mahmoud Mohamed Moursi Ahmed
Certificates - Mahmoud Mohamed Moursi AhmedCertificates - Mahmoud Mohamed Moursi Ahmed
Certificates - Mahmoud Mohamed Moursi Ahmed
 
Generative AI leverages algorithms to create various forms of content
Generative AI leverages algorithms to create various forms of contentGenerative AI leverages algorithms to create various forms of content
Generative AI leverages algorithms to create various forms of content
 
An improved modulation technique suitable for a three level flying capacitor ...
An improved modulation technique suitable for a three level flying capacitor ...An improved modulation technique suitable for a three level flying capacitor ...
An improved modulation technique suitable for a three level flying capacitor ...
 
Curve Fitting in Numerical Methods Regression
Curve Fitting in Numerical Methods RegressionCurve Fitting in Numerical Methods Regression
Curve Fitting in Numerical Methods Regression
 
cnn.pptx Convolutional neural network used for image classication
cnn.pptx Convolutional neural network used for image classicationcnn.pptx Convolutional neural network used for image classication
cnn.pptx Convolutional neural network used for image classication
 

COMP522-2019-Java-Memory-Model.pdf

  • 1. The Java Memory Model Authors: Jeremy Manson, William Pugh, Sarita V. Adve Presenter: Keren Zhou COMP 522
  • 2. Why Java needs a well-formed memory model • Java supports threads running on shared memory • Java memory model defines multi-threaded Java program semantics • Key concerns: Java memory model specifies legal behaviors and provides safety and security properties 3/26/19 2
  • 3. Why should we care about Java Memory Model • A programmer should know • Junior level • Use monitor, locks, and volatile properly • Learn safety guarantees of Java • Intermediate level • Reason the correctness of concurrent programs • Use concurrent data structures (e.g ConcurrentHashMap) • Expert level • Understand and optimize utilities in java.util.concurrent • AbstractExecutorService • Atomic variables 3/26/19 3
  • 4. Create a singleton to get a static instance • Singleton: only want a single instance in a program • Database • Logging • Configuration 3/26/19 4 public class Instance { private static Instance instance; public static Instance getInstance() { if (instance == null) instance = new Instance(); return instance; } } 1 2 3 4 5 6 7 8
  • 5. The simple singleton is thread- unsafe 3/26/19 5 public class Instance { private static Instance instance; public static Instance getInstance() { if (instance == null) instance = new Instance(); return instance; } } 1 2 3 4 5 6 7 8 Threads T0 T1 Line 4 Line 4 Line 5 Line 5 Line 6 Line 6 getInstance getInstance Time Line Create two instances at the same time!
  • 6. Use synchronized keyword 3/26/19 6 • Java synchronized keyword can be used in different contexts • Instance methods • Code blocks • Static methods • Only one thread can execute inside a static synchronized method per class, irrespective of the number of instances it has.
  • 7. The synchronized singleton has low performance 3/26/19 7 public class Instance { private static Instance instance; public synchronized static Instance getInstance() { if (instance == null) instance = new Instance(); return instance; } } 1 2 3 4 5 6 7 8 Threads T0 T1 Line 4 Line 5 Line 6 getInstance getInstance Time Line Line 4 Line 5 Line 6
  • 8. Use double-checked lock to make it more efficient • Motivation: In the early days, the cost of synchronization could be quite high • Idea: Avoid the costly synchronization for all invocations of the method except the first • Solution: • First check if the instance is null or not • If instance is null, enter a critical section to create the object • If instance is not null, return instance 3/26/19 8
  • 9. Double checked-lock implementation 3/26/19 9 public class Instance { private static Instance instance; public static Instance getInstance() { if (instance == null) { synchronized (Instance.class) { if (instance == null) { instance = new Instance(); } } } return instance; } } 1 2 3 4 5 6 7 8 9 10 11 12 13
  • 10. How double-checked lock goes wrong • Brief answer: instruction reorder • Suppose T0 is initializing with the following three steps 1) mem = allocate(); //Allocate memory for Singleton 2) ctorSingleton(mem); //Invoke constructor 3) object.instance = mem; //initialize instance. • What if step 2 is interchanged with step 3? • Another thread T1 might see the instance before being fully constructed 3/26/19 10
  • 11. A thread returns an object that has not been constructed 3/26/19 11 public static Instance getInstance() { if (instance == null) { synchronized (UnsafeInstance.class) { if (instance == null) { instance = new Instance(); } } } return instance; } 3 4 5 6 7 8 9 10 11 12 Threads T0 T1 Line 4 Line 4 Line 5 Line 11 Line 6 getInstance getInstance Time Line Line 7 mem = allocate(); object.instance = mem; ctorSingleton(mem); T1 returns before constructor completes!
  • 12. Use volatile to avoid reordering • The behavior of volatile differs significantly between programming languages • C/C++ • Volatile keyword means always read the value of the variable memory • Operations on volatile variables are not atomic • Cannot be used as a portable synchronization mechanism • Java • Prevent reordering • Derive a synchronization order on top of Java Memory Model 3/26/19 12
  • 13. Use volatile to avoid reordering • Java’s volatile was not consistent with developers intuitions • The original Java memory model allowed for volatile writes to be reordered with nonvolatile reads and writes • Under the new Java memory model (from JVM v1.5), volatile can be used to fix the problems with double-checked locking 3/26/19 13
  • 14. Java memory model history • 1996: An Optimization Pattern for Efficiently Initializing and Accessing Thread-safe Objects, Douglas C. Schmidt and etc. • 1996: The Java Language Specification, chapter 17, James Gosling and etc. • 1999: Fixing the Java Memory Model, William Pugh • 2004: JSR 133---Java Memory Model and Thread Specification Revision 3/26/19 14
  • 15. Review: sequential consistency • Total order: Memory actions must appear to execute one at a time in a single total order • Program order: Actions of a given thread must appear in the same order in which they appear in the program 3/26/19 15
  • 16. Review: sequential consistency violation 3/26/19 16 r2 = x y = 1 r1 = y x = 2 Thread 1 Thread 2 Initial conditions: x = y = 0 Final results: r2 == 2 and r1 == 1? Decision: Disallowed. Violates sequential consistency 1 2 3 4 Circular dependency! Inter threads dependency Intra thread dependency
  • 17. Java memory model balances between performance and safety • Sequential consistency • Easy to understand • Restricts the use of many compiler and hardware transformations • Relaxed memory models • Allow more optimizations • Hard to reason about the correctness 3/26/19 17
  • 18. Java memory model hides underlying hardware memory model 3/26/19 18 Java Program High-level Language Memory Model Java Compiler Java Runtime Hardware Memory Model TSO, Power’s weak model, …
  • 19. Java defines data-race-free model • Data race occurs when two threads access the same memory location, at least one of the accesses is a write, and there is no intervening synchronization • A data-race-free Java program guarantees sequential consistency (Correctly synchronized) 3/26/19 19
  • 20. Another definition of data-race from Java Memory Model’s perspective • Two accesses x and y form a data race in an execution of a program if they are from different threads, they conflict, and they are not ordered by happens-before 3/26/19 20
  • 21. Happens-before memory model • A simpler version than the full Java Memory Model • Happens-before order • The transitive closure of program order and the synchronizes- with order • Happens-before consistency • Determines the value that a non-volatile read can see • Synchronization order consistency • Determines the value that a volatile read can see • Solves part of the Java mysterious problems 3/26/19 21
  • 22. Program order definition • The program order of thread T is a total order that reflects the order in which these actions would be performed according to intra-thread semantics of T • If x and y are actions of the same thread and x comes before y in program order, then hb(x, y) (i.e. x happens- before y) 3/26/19 22
  • 23. Eliminate ambiguity in program order definition • Given a program in Java • Program order does not mean that y = 6 must be subsequent to x = 5 from a wall clock perspective. It only means that the sequence of actions executed must be consistent with that order 3/26/19 23 y = 6 x = 5 1 2
  • 24. What should be consistent in program order • Happens-before consistency • A read r of a variable v is allowed to observe a write w to v if • r does not happen-before w (i.e., it is not the case that hb(r, w)) – a read cannot see a write that happens-after it, and • There is no intervening write w0 to v (i.e., no write w0 to v such that hb(w, w0), hb(w0, r)) –the write w is not overwritten along a happens-before path. • Given a Java program • hb(1, 2) & hb(2, 3) -> hb(1, 3), so z sees 6 be written to y 3/26/19 24 y = 6 x = 5 z = y 1 2 3
  • 25. Synchronization Order • A synchronization order is a total order over all of the synchronization actions of an execution • A write to a volatile variable v synchronizes-with all subsequent reads of v by any thread; • An unlock action on monitor m synchronizes-with all subsequent lock actions on m that were performed by any thread; • … • If an action x synchronizes-with a following action y, then we have hb(x, y) 3/26/19 25
  • 26. What should be consistent in synchronization order • Synchronization order consistency • Synchronization order is consistent with program order • Each read r of a volatile variable v sees the last write to v to come before it in the synchronization order 3/26/19 26
  • 27. Happens-before memory model example 3/26/19 27 x = 1 ready = true if (ready) r1 = x Thread 1 Thread 2 1 2 3 4 synchronization-with program order Initial conditions: x = 0, ready = false, ready is volatile Final results: r1 == 1? Decision: Allowed. The program is correctly synchronized Proof: Program order: hb(L1, L2) and hb(L3, L4) Synchronization order: hb(L2, L3) Transitive: hb(L1, L4) Recall data-race definition: Two accesses x and y form a data race in an execution of a program if they are from different threads, they conflict, and they are not ordered by happens-before
  • 28. Correct double-checked lock with volatile 3/26/19 28 public class Instance { private volatile static Instance instance; public static Instance getInstance() { if (instance == null) { synchronized (Instance.class) { if (instance == null) { instance = new Instance(); } } } return instance; } } 1 2 3 4 5 6 7 8 9 10 11 12 13 1. mem = allocate(); 2. ctorSingleton(mem); 3. object.instance = mem; hb(2, 3) ensures that L2’s write to mem can be seen at L3
  • 29. Happens-before doesn’t solve all problems 3/26/19 29 r1 = x if (r1 != 0) y = 42 r2 = y if (r2 != 0) x = 42 Thread 1 Thread 2 Initial conditions: x = y = 0 Final results: r1 == r2 == 42? Decision: Disallowed. Because the values are out-of-thin-air. In a future aggressive system, Thread 1 could speculatively write the value 42 to y. How to propose a methodology to disallow these behaviors? 1 2 3 4 5 6
  • 30. Happens-before doesn’t solve all problems 3/26/19 30 r1 = a r2 = a if (r1 == r2) b = 2 r3 = b a = r3 Thread 1 Thread 2 Initial conditions: a = 0, b = 1 Final results: r1 == r2 == r3 == 2? Decision: Allowed. A compiler may determines that r1 and r2 have the same value and eliminate if r1 == r2 (L3). Then, b = 2 (L4) can be moved to an earlier position (L1) 1 2 3 4 5 6 b = 2 r1 = a r2 = r1 if (true) r3 = b a = r3 Thread 1 Thread 2 1 2 3 4 4 5
  • 31. What’s the difference between two programs • One difference between the acceptable and unacceptable results is that in latter program, the write that we perform (i.e. b = 2) would also have occurred if we had carried on the execution in a sequentially consistent way. • In the former program, value 42 in any sequentially consistent execution will not be written. 3/26/19 31
  • 32. Well-behaved execution • We distinguish two programs by considering whether those writes could occur in a sequentially consistent execution. • Well-behaved execution • A read that must return the value of a write that is ordered before it by happens-before. 3/26/19 32
  • 33. Disallowed examples-data dependency 3/26/19 33 r1 = x a[r1] = 0 r2 = a[0] y = r2 r3 = y x = r3 Thread 1 Thread 2 1 2 3 4 5 6 Initial conditions: x = y = 0; a[0] = 1, a[1] = 2 Final results: r1 == r2 == r3 == 1? Decision: Disallowed. Because values are out-of-thin-air. Proof: We have hb(L1, L2), hb(L2, L3). To let r2 == 1, a[0] must be 0. Since initially a[0] == 1 and hb(L2, L3), we have r1 == 0 at a[r1] = 0 (L2). r1 at L2 is the final value Because hb(L1, L2), r1 at L2 must see the write to r1 at r1 = x (L1).
  • 34. Disallowed examples-control dependency 3/26/19 34 z = 1 r1 = z if (r1 == 0) x = 1 Thread 1 Thread 2 1 2 3 4 r2 = x y = r2 Thread 3 r3 = y x = r3 Thread 4 5 6 7 8 Initial conditions: x = y = z = 0 Final results: r1 == r2 == r3 == 1? Decision: Disallowed. Because values are out-of-thin-air. Proof: Because we have hb(L5, L6), to let r2 == 1 (so that y = 1), x = 1 (L4) must be executed. If L4 is executed, if (r1 == 0) (L3) must be true. However, since r1 == 1 and hb(L2, L3), L4 cannot be executed.
  • 35. Disallowed examples-control dependency 3/26/19 35 r1 = x if (r1 == 0) x = 1 Thread 1 1 2 3 r2 = x y = r2 Thread 2 r3 = y x = r3 Thread 3 4 5 6 7 Initial conditions: x = y = 0 Final results: r1 == r2 == r3 == 1? Decision: Disallowed. Because values are out-of-thin-air Proof: The same reason as the previous example.
  • 36. Causality • Actions that are committed earlier may cause actions that are committed later to occur • The behavior of incorrectly synchronized programs is bounded by causality • The causality requirement is strong enough to respect the safety and security properties of Java and weak enough to allow standard compiler and hardware optimizations 3/26/19 36
  • 37. Justify a correct execution • Build up causality constraints to justify executions • Ensures that the occurrence of a committed action and its value does not depend on an uncommitted data race • Justification steps • Starting with the empty set as C0 • Perform a sequence of steps where we take actions from the set of actions A and add them to a set of committed actions Ci to get a new set of committed actions Ci+1 • To demonstrate that this is reasonable, for each Ci we need to demonstrate an execution E containing Ci that meets certain conditions 3/26/19 37
  • 38. Justification examples-reorder 3/26/19 38 r1 = x y = 1 r2 = y x = r2 Thread 1 Thread 2 Initial conditions: x = y = 0 Final results: r1 == r2 == 1? Decision: Allowed, because of compiler transformation. y = 1 (L2) is a constant that does not affect r1 = x (L2). 1 2 3 4 y = 1 r1 = x r2 = y x = r2 Thread 1 Thread 2 1 2 3 4 C1: y = 1 r2 = y (0) x = r2 (0) r1 = x (0) C2: y = 1 r2 = y (1) x = r2 (1) r1 = x (0) C3: y = 1 r2 = y (1) x = r2 (1) r1 = x (0) C4: y = 1 r2 = y (1) x = r2 (1) r1 = x (1)
  • 39. Justification examples-redundant elimination 3/26/19 39 r1 = a if (r1 == 1) b = 1 r2 = b if (r2 == 1) a = 1 if (r2 == 0) a = 1 Thread 1 Thread 2 1 2 3 4 5 6 7 8 Initial conditions: a = b = 0 Final results: r1 == r2 == 1? Decision: Allowed. A compiler could determine that Thread 2 always writes 1 to a and hoists the write to the beginning of Thread 2. C1: a = 1 r1 = a (0) b = 1 (0) r2 = b (0) C2: a = 1 r1 = a (1) b = 1 (0) r2 = b (0) C3: y = 1 r1 = a (1) b = 1 (1) r2 = b (0) C4: y = 1 r1 = a (1) b = 1 (1) r2 = b (1) r1 = a if (r1 == 1) b = 1 a = 1 r2 = b Thread 1 Thread 2 1 2 3 4 5
  • 40. Justification examples-inter thread analysis 3/26/19 40 r1 = x r2 = 1 + r1*r1 – r1 y = r2 r3 = y x = r3 Thread 1 Thread 2 1 2 3 4 5 Initial conditions: x = y = 0 Final results: r1 == r2 == 1? Decision: Allowed. Interthread analysis could determine that x and y are always either 0 or 1, and thus determine that r2 is always 1. Once this determination is made, the write of 1 to y could be moved early in Thread 1. r2 = 1 y = r2 r1 = x r3 = y x = r3 Thread 1 Thread 2 1 2 3 4 5 C1: r2 = 1 y = r2 (0) r3 = y (0) x = r3 (0) r1 = x (0) C2: r2 = 1 y = r2 (1) r3 = y (0) x = r3 (0) r1 = x (0) C3: r2 = 1 y = r2 (1) r3 = y (1) x = r3 (0) r1 = x (0) C4: r2 = 1 y = r2 (1) r3 = y (1) x = r3 (1) r1 = x (0) C5: r2 = 1 y = r2 (1) r3 = y (1) x = r3 (1) r1 = x (1)
  • 41. Comparison between allowed examples and disallowed examples 3/26/19 41 r1 = x if (r1 == 0) x = 1 Thread 1 1 2 3 r2 = x y = r2 Thread 2 r3 = y x = r3 Thread 3 4 5 6 7 r1 = x if (r1 == 0) x = 1 r2 = x y = r2 Thread 1 1 2 3 4 5 r3 = y x = r3 Thread 2 6 7 Initial conditions: x = y = 0 Final results: r1 == r2 == r3 == 1? Decision: Allowed. Interthread analysis could determine that x is always 0 or 1. So we can replace r2 = x by r2 = 1 and y = r2 by y = 1. After moving y = 1 and r2 = 1 to an earlier position, we get r1 == r2 == r3. y = 1 r2 = 1 r1 = x if (r1 == 0) x = 1 Thread 1 r3 = y x = r3 Thread 2 6 7 1 2 3 4 5
  • 42. Comparison between allowed examples and disallowed examples 3/26/19 42 r1 = x if (r1 == 0) x = 1 Thread 1 1 2 3 r2 = x y = r2 Thread 2 r3 = y x = r3 Thread 3 4 5 6 7 Initial conditions: a = b = 0 Final results: r1 == r2 == r3 == 2? Decision: Allowed. Although there are some SC executions in which r1 != r2 (L3), we can hoist b = 2 (L4) to an earlier position and there is an SC execution such that r1 == r2. For the above case, there’s no SC execution such that r1 == 0 (L2) is true and r1 == r2 == r3 == 1. That is, if we hoist x = 1 to an earlier position, L2 must be false. r1 = a r2 = a if (r1 == r2) b = 2 r3 = b a = r3 Thread 1 Thread 2 1 2 3 4 1 2 1 2 3 1 2
  • 43. Practical issues-final field • “For space reasons, we omit discussion of two important issues in the Java memory model: the treatment of final fields, and finalization / garbage collection.” • Java’s final field also allows programmers to implement thread-safe immutable objects without synchronization 3/26/19 43
  • 44. Rule of thumb • Set the final fields for an object in that object's constructor; and do not write a reference to the object being constructed in a place where another thread can see it before the object's constructor is finished. • What happens in the constructor • If a read occurs after the field is set in the constructor, it sees the value the final field is assigned, otherwise it sees the default value. 3/26/19 44
  • 45. Can we change a final field? • Reflection introduces problems • The specification allows aggressive optimization of final fields. Within a thread, it is permissible to reorder reads of a final field with those modifications of a final field that do not take place in the constructor. 3/26/19 45
  • 46. Practical issues-final field 3/26/19 46 • new A().f() could return -1, 0, or 1 class A { final int x; A() { x = 1; } int f() { return d(this,this); } int d(A a1, A a2) { int i = a1.x; g(a1); int j = a2.x; return j - i; } static void g(A a) { // uses reflection to change a.x to 2 } } 1 2 3 4 5 6 7 8 9 10 11 12 13 14 reorder!
  • 47. Practical issues-final field 3/26/19 47 • new A().f() could return -1, 0, or 1 class A { final int x; A() { x = 1; } int f() { return d(this,this); } int d(A a1, A a2) { int i = a1.x; g(a1); int j = a2.x; return j - i; } static void g(A a) { // uses reflection to change a.x to 2 } } 1 2 3 4 5 6 7 8 9 10 11 12 13 14 return 1
  • 48. Practical issues-final field 3/26/19 48 • new A().f() could return -1, 0, or 1 class A { final int x; A() { x = 1; } int f() { return d(this,this); } int d(A a1, A a2) { g(a1); int i = a1.x; int j = a2.x; return j - i; } static void g(A a) { // uses reflection to change a.x to 2 } } 1 2 3 4 5 6 7 8 9 10 11 12 13 14 return 0
  • 49. Practical issues-final field 3/26/19 49 • new A().f() could return -1, 0, or 1 class A { final int x; A() { x = 1; } int f() { return d(this,this); } int d(A a1, A a2) { int j = a2.x; g(a1); int i = a1.x; return j - i; } static void g(A a) { // uses reflection to change a.x to 2 } } 1 2 3 4 5 6 7 8 9 10 11 12 13 14 return -1
  • 50. Practical issue-efficient singleton • The initialization-on-demand holder (design pattern) idiom is a lazy-loaded singleton. In all versions of Java, the idiom enables a safe, highly concurrent lazy initialization with good performance. 3/26/19 50 public class SafeInstance { private SafeInstance() {} private static class LazyHolder { static final SafeInstance INSTANCE = new SafeInstance(); } public static SafeInstance getInstance() { return LazyHolder.INSTANCE; } } 1 2 3 4 5 6 7 8 9
  • 51. Why initialization-on-demand holder is safe? • When the class is initialized? • A class or interface type T will be initialized immediately before the first occurrence of any one of the following: • A static field declared by T is used and the field is not a constant variable • A variable of primitive type or type String, that is final and initialized with a compile-time constant expression is called a constant variable. • … 3/26/19 51
  • 52. Why initialization-on-demand holder is safe? • Why initialization is safe? • For each class or interface C, there is a unique initialization lock LC. The mapping from C to LC is left to the discretion of the Java Virtual Machine implementation. • We can also implement singleton by ENUM in Java. 3/26/19 52
  • 53. Conclusion • Following happens-before rules allows us to write a data-race-free program that is correctly synchronized. • Java memory model provides a clear definition of well-behaved executions, preventing values come out-of-thin-air in the presence of data race. • Double-checked lock is thread-safe for JVM later than v1.5. 3/26/19 53
  • 54. Reference Books • Goetz, Brian, et al. Java concurrency in practice. Pearson Education, 2006. • Gosling, James, et al. The Java language specification. Pearson Education, 2014. • Lea, Doug. "The JSR-133 cookbook for compiler writers." (2008). 3/26/19 54
  • 55. Reference URLs • Double-checked locking https://www.ibm.com/developerworks/java/library/j -dcl/index.html • Causality test cases http://www.cs.umd.edu/~pugh/java/memoryModel/ unifiedProposal/testcases.html 3/26/19 55