[concurrency-interest] Stricter read ordering

Roman Elizarov elizarov at devexperts.com
Fri Apr 25 03:02:42 EDT 2014


I cannot not stop thinking that Java 8 solution with Unsafe.loadFence() in StampedLock.validate() method is unsatisfactory. Not that because it is "Unsafe", but because it explicitly invokes a fence, which, in the ideal view of the world, should be just one possible implementation mechanism, not the primitive that the developer uses. To me it does "appear exceptionally unnatural" as Hans Boehm notes in his 2012 paper on seqlocks. 

Reading back and forth that paper I don't see a consolation in its conclusions. On a surface of it, all that is needed to make seqlock idiom implementable in the Java-like (happens-before) memory model are two new kinds of synchronization operations that would establish a synchronizes-with (sw) relation between a read and a subsequent write in synchronization order (so), as opposed to write-release/read-acquire pair that establishes sw-relation between a write and so-subsequent read. There's no need for "read-don't-modify-write". Even if its actual write is optimized away, its memory model effect still looks too strong for seqlock needs. As Hans points out in his paper, the compiler could have safely optimized "read-don't-modify-write" into "fence+read", but seqlock only needs "loadFence+read" in its validate  method.

In the validate method of seqlock we don't need any write (even if it does not modify). We don't need sw relation with so-previous write that "read-don't-modify-write" gives. We only need sw with so-subsequent write. In C++ terms, we just need to be able to memory_order_release on read in seqlock validate method (last read in the read path) and memory_order_acquire on a write in seqlock's first operation in a write path. For a multi-writer seqlock, the writer path uses read-modify-write operation anyway (to acquire lock), so it already has both acquire and release memory order. But what about read-release for validate? We don't have it now. Is there any existing research in that direction that might unify seqlocks with happens-before memory models in a satisfactory way? 
 
-----Original Message-----
From: concurrency-interest-bounces at cs.oswego.edu [mailto:concurrency-interest-bounces at cs.oswego.edu] On Behalf Of Aleksey Shipilev
Sent: Wednesday, April 23, 2014 4:42 PM
To: Tobias Lindaaker; concurrency-interest at cs.oswego.edu
Subject: Re: [concurrency-interest] Stricter read ordering

On 04/16/2014 03:25 PM, Tobias Lindaaker wrote:
> Is there any way I could introduce a fence that guarantees that the 
> data reads will not be moved to after the read of this.next?

I think you are reinventing sequence locks. Prime Java example is StampedLock which deals with ordering reads with Unsafe.loadFence(), see StampedLock.validate().

So, in your example, it amounts to:

       public DataCarrier read() {
         // I allow multiple readers, so this method is not ynchronized
         int x, y;
         long version;
         do {
           version = this.written;
           x = this.x;
           y = this.y;
           Unsafe.loadFence();
         } while ( version != this.next );
         return new DataCarrier( x, y );
       }
     }

-Aleksey.

_______________________________________________
Concurrency-interest mailing list
Concurrency-interest at cs.oswego.edu
http://cs.oswego.edu/mailman/listinfo/concurrency-interest



More information about the Concurrency-interest mailing list