[concurrency-interest] AtomicReference get vs. getAcquire; get/set Opaque

Aleksey Shipilev shade at redhat.com
Mon Sep 26 04:14:26 EDT 2016


On 09/24/2016 03:19 PM, Dávid Karnok wrote:
> I have a one element single-producer single-consumer "queue" implemented
> as this:
> 
> boolean offer(AtomicReference<T> ref, T value) {
>     Objects.requireNonNull(value);
>     if (ref.get() == null) {
>         ref.lazySet(value);
>         return true;
>     }
>     return false;
> }
> 
> T poll(AtomicReference<T> ref) {
>     T v = ref.get();
>     if (v != null) {
>        ref.lazySet(null);
>     }
>     return v;
> }
> 
> Is it okay to turn get() into getAcquire() and lazySet into setRelease()
> (I can see lazySet delegates to setRelease)? 

Replacing {get,set}Volatile with {get,set}Acquire/Release is generally
not okay, as you will relax the sequential consistency. See:
 http://cs.oswego.edu/pipermail/concurrency-interest/2016-May/015104.html
 http://cs.oswego.edu/pipermail/concurrency-interest/2016-March/015037.html

SPSC is more forgiving, and it _appears_ fine to replace with
getAcq/setRel in this example: a) you can publish the value correctly
through setRelease/getAcquire chain; b) you will never observe null in
offer() before poll() pulls the value, since there are WAR data
dependencies between get and lazySet on the same variable.


> In addition, are there examples (or explanations) of when it is okay to
> use getOpaque/setOpaque  and would they work with the concurrent "queue"
> above at all?

It is almost never okay to replace {get,set}{Volatile,Acquire,Release}
with {get,set}Opaque. Opaque does NOT guarantee ANY inter-thread ordering.


Thanks,
-Aleksey


-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 819 bytes
Desc: OpenPGP digital signature
URL: <http://cs.oswego.edu/pipermail/concurrency-interest/attachments/20160926/40156a01/attachment.sig>


More information about the Concurrency-interest mailing list