Happens before ralationship and memory barriers in Java

633 views
Skip to first unread message

arkadiuszbalcerek

unread,
Jan 29, 2016, 9:47:22 AM1/29/16
to mechanical-sympathy
Hi,

I am trying to understand happens-before relationship concept in Java and can not understand one thing. Spec says that it is important for both threads to synchronize on the same monitor in order to set up the happens-before relationship properly. It is not the case that everything visible to thread A when it synchronizes on object X becomes visible to thread B after it synchronizes on object Y. My understanding is that leaving synchronized code is a kind of store memory barrier and entering it is a load memory barrier. Memory barriers are global so why it matters the monitor on which threads synchronize and why it must be the same in both thread?

Thanks for helping with that,
Arek

Vitaly Davidovich

unread,
Jan 29, 2016, 10:06:10 AM1/29/16
to mechanica...@googlegroups.com
The JMM is defined in terms of synchronization edges that create a happens-before edge - it doesn't discuss fences, which is an implementation detail that may be stronger (but not weaker) than what the model prescribes.

It's possible some (weak memory model) architectures don't necessarily order all load/store ops globally, like x86 (or other TSO archs).  For example, I hear AArch64 is a bit funky (I can elaborate a bit more if interested).

There's also the aspect that compiler could, in theory, detect that the two threads don't sync with respect to each other, and reorder code.  Now, real compilers don't have such visibility, but in the model they could.
--
You received this message because you are subscribed to the Google Groups "mechanical-sympathy" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mechanical-symp...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


--
Sent from my phone

Gil Tene

unread,
Jan 29, 2016, 11:30:00 AM1/29/16
to mechanical-sympathy
For a specific example that occurs in HotSpot today: With Biased locking (which is on by default) the runtime can detect that e.g. Object Y is [temporarily] only synchronized on in thread B. The runtime can (and will) bias the monitor on Object Y to thread B as a result. When monitor Y is biased to thread B, the code may enter and leave monitor Y without executing the instructions that would enforce ordering in the CPU, allowing thread B to experience stores done by thread A and/or to expose it's stores to thread A in ways that would not be possible if order-enforcing instructions were executed. On x86, the specific fencing enforcement lost with biasing will be a StoreLoad ordering, but on some other CPUs (that do not enforce StoreStore, LoadLoad, and LoadStore implicitly on all store and load operations like x86 does) more effects are possible.

Note that this loss of ordering on biased monitors is not limited to CPU ordering enforcement. Technically, the compiler would also be allowed to reorder instructions in cases where it decides that the monitor is biased to the thread, but in practice HotSpot does not do that (yet, and to my knowledge).

Vitaly Davidovich

unread,
Jan 29, 2016, 11:43:12 AM1/29/16
to mechanical-sympathy
Good point on biased locking!

Vitaly Davidovich

unread,
Jan 29, 2016, 11:57:43 AM1/29/16
to mechanical-sympathy
Should've also mentioned that if we're talking about biased locking, then there's another opto that Hotspot does which is lock elision for non-escaping objects.  If you sync on such an object, then no atomic operations will be emitted (interestingly, objects with a volatile write inside their constructor that are eliminated by EA still leave behind a fence, IIRC, but I think that may change in future Hotspot version).

Gil Tene

unread,
Jan 29, 2016, 12:44:38 PM1/29/16
to mechanical-sympathy
Right. A general way of looking at it is: If the runtime can convince itself that a monitor is not observed or interacted with in any other thread, it is allowed to ignore ordering rules (outside of program order within the thread) associated with that monitor.

And this is not a hypothetical. Both biased locking and escape-analysis-based-lock-elision are examples of this happening in practice in today's JVMs.

The same may be true for volatiles. E.g. if a volatile or atomic field is proven to not be visible outside a thread (e.g. via escape detection), similar ordering operation removal can happen.

And then there is lazySet, which is not really defined, so we don't really have rules about where it's allowed to be taken away...
To unsubscribe from this group and stop receiving emails from it, send an email to mechanical-sympathy+unsub...@googlegroups.com.

Vitaly Davidovich

unread,
Jan 29, 2016, 1:40:45 PM1/29/16
to mechanical-sympathy
Right. A general way of looking at it is: If the runtime can convince itself that a monitor is not observed or interacted with in any other thread, it is allowed to ignore ordering rules (outside of program order within the thread) associated with that monitor.

I think it boils down to this: fence/barrier conversations are only well defined when talking about fence-based APIs, everything else (e.g. volatile, synchronized, etc) is JMM based.  Any fences emitted as part of the implementation of those constructs are incidental and cannot be relied upon.

And then there is lazySet, which is not really defined, so we don't really have rules about where it's allowed to be taken away..

So while it's true that lazySet is not defined in the (current) JMM at all and one could argue it's not well defined in general, I do consider it a fence-like API and I think most others do as well (especially since Unsafe.putXXXOrdered is used quite a bit as well, which backs the lazySet).  The fence based stuff will get a bit more elaborate with VarHandles, and any possible explicit public fence API.  In case someone issued a fence in, say, an class constructor of an instance whose allocation is eliminated, I'd be hard pressed to imagine the JVM being allowed to remove an explicit fence.  But we shall see how that path evolves ...

To unsubscribe from this group and stop receiving emails from it, send an email to mechanical-symp...@googlegroups.com.

For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups "mechanical-sympathy" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mechanical-symp...@googlegroups.com.
Reply all
Reply to author
Forward
0 new messages