简体   繁体   中英

Happens-before and volatile variable

Following are just three "happens-before" rules of JMM. I am not listing the other rules as my question is related to these three rules only.

  • Monitor lock rule. An unlock on a monitor lock happens before every subsequent lock on that same monitor lock.
  • Thread start rule. A call to Thread.start on a thread happens before every action in the started thread.
  • Interruption rule. A thread calling interrupt on another thread happens before the interrupted thread detects the interrupt (either by having InterruptedException thrown, or invoking isInterrupted or interrupted).

Questions

  1. 1st rule question - Let's say two threads A and B have synchronized blocks of code. Does the first rule mean that any variable set in a synchronized block in thread A, will be visible to the code in synchronized block of thread B, even if the variable is NOT declared as volatile?

  2. 2nd rule question - Let's say a thread A starts a thread B. Does the second rule mean that any variable set in a parent thread before calling start() will be visible to thread B even if the variable is NOT declared as volatile?

  3. 3rd rule question - Let's say a thread A interrupts a thread B. Does the third rule mean that any variable set in thread A before interrupting thread B will be visible to thread B after the interrupt is detected, even if the variable is not declared as volatile?

Finally, one more question:

  1. In BlockingQueue documentation, it is said,

    Memory consistency effects: As with other concurrent collections, actions in a >thread prior to placing an object into a BlockingQueue happen-before actions >subsequent to the access or removal of that element from the BlockingQueue in >another thread.

Does this mean any variable set in a thread A before enqueuing an object in the blocking queue will be visible to thread B after dequeuing the object from the queue, even if the variable is NOT declared as volatile?

Basically through the above questions, I am trying to understand if the memory flush happens after these events such that the variables need not be declared as volatile in these cases.

1st rule question - Let's say two threads A and B have synchronized blocks of code.

Threads don't have code. Threads execute code.

Does the first rule mean that any variable set in a synchronized block in thread A, will be visible to the code in synchronized block of thread B, even if the variable is NOT declared as volatile?

Yes, Suppose we have:

private int i;
private final Object lock = new Object();

void foobar(...) {
    ...
    synchronized(lock) {
        i = ...;
    }
}

int getI() {
    synchronized(lock) {
        return i;
    }
}

If thread A calls foobar() , and then thread B subsequently calls getI() , then thread B will get the new value of i .

But note! My example above does not include any way for you to prove which call actually happened first. If your program depends on those calls to happen in a particular order, then it's going to need more than just a mutex: It's going to need some means to make thread B wait() for thread A to perform the update.


2nd rule question - Let's say a thread A starts a thread B. Does the second rule mean that any variable set in a parent thread before calling start() will be visible to thread B even if the variable is NOT declared as volatile?

Yes, that's what it means.

3rd rule question...

Yes again.

  1. ... BlockingQueue ...

Yes again.


...Through the above questions, I am trying to understand if the memory flush happens after these events such that...

Don't even think about "memory flush". That is not part of the Java language: If it happens, it's an implementation detail, and you don't need to worry about it unless you are implementing a JVM.

The only concept you need to worry about is the "happens before".

Whenever the JLS says that A happens before B, it means that if A happens in thread 1, and B happens in thread 2, and you can prove that A actually did happen before B in real-time, then any field that was updated by thread 1 before A happened will be guaranteed visible in thread 2 after B happens.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM