[concurrency-interest] Unsynchronized lazy conditions

Aleksey Shipilev shade at redhat.com
Thu May 31 03:51:18 EDT 2018


On 05/31/2018 07:07 AM, Shevek via Concurrency-interest wrote:
> Hi,
> 
> I'd like to issue a warning message a relatively low number of times in a multi-threaded
> application. My code is this:
> 
> class Foo {
>   private boolean warned;
> 
>   public void run() {
>     if (!warned) {
>        LOG.warn("Warning");
>        warned = true;
>     }
>   }
> }
> 
> This is the only access to the variable 'warned', the value change is deliberately unsynchronized,
> and monotonic. Am I right to believe that:
> 
> * The first call WILL issue a warning.

Yes.

> * Any thread will issue the warning AT MOST once.

Yes, I think so. It encroaches on darker corners of JMM, but it still does what you want, methinks.

> * Some (later) threads may not issue the warning, if the updated value is flushed to the heap and
> they load it?

Yes, except that "flushed to heap" part: that one is an implementation detail.


> Is there a better way to do this without sacrificing performance? Is this what the mysterious
> AtomicBoolean.lazySet, or even weakCompareAndSet is about?

The classic way to do this is to do test and test-and-set:

class Foo {
   private final AtomicBoolean warned;

   public void run() {
     if (!warned.get() && warned.compareAndSet(false, true)) {
       LOG.warn("Warning");
     }
   }
}

This gives you global only-once property, without sacrificing performance.

There are options how do you represent "warned". I'd start with AtomicBoolean, and then switched to
AtomicIntegerFieldUpdater over volatile field, or VarHandle if footprint became a problem. With
VarHandles, you can even mix the modes: make the first "test" in plain mode, and then do the CAS, if
first volatile check is too costly. But all of this is red herring until there is a pressing need.
One-off guards are doable with just AtomicBoolean.

-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/20180531/920eeac5/attachment-0001.sig>


More information about the Concurrency-interest mailing list