In Joe Duffy's concurrent programming book he defines acquire and release fences like so:
• Acquire fence. Ensures no load or store that comes after the fence will move befo re the fence. Instructions before it may still move after the fence.
• Release fence. Ensures no load or store that comes before the fence will move after the fence. Instructions after it may still happen before the fence.
My question is: How can it be that an operation is allowed to happen before something, but is prevented from happening after. It's difficult to explain, but both these statements look like a chicken or the egg problem to me.
I will try to explain that based on Java
volatile
semantics. Writing some value into avolatile
variable happens-before this value can be read from this variable by other thread(s). How that is achieved? Let's take a closer look on some kind of instructions:volatile
variable;Now, Java memory model provides you with some behavior guarantees, one of them I wrote above. The question is - how is that achieved?
Well,
volatile
modifier forbids some kinds of reorderings - volatile write cannot be put before normal write, volatile read cannot be put after normal read.How to connect that to your question? I'll try to formulate the answer based on what I wrote above.
volatile
illustrates that.