On Mon, Jun 22, 2020 at 09:52:22AM -0400, bfields@xxxxxxxxxxxx wrote: > On Thu, Jun 18, 2020 at 04:09:05PM -0400, bfields@xxxxxxxxxxxx wrote: > > I probably don't understand the algorithm (in particular, how it > > revalidates caches after a write). > > > > How does it avoid a race like this?: > > > > Start with a file whose data is all 0's and change attribute x: > > > > client 0 client 1 > > -------- -------- > > take write lock on byte 0 > > take write lock on byte 1 > > write 1 to offset 0 > > change attribute now x+1 > > write 1 to offset 1 > > change attribute now x+2 > > getattr returns x+2 > > getattr returns x+2 > > unlock > > unlock > > > > take readlock on byte 1 > > > > At this point a getattr will return change attribute x+2, the same as > > was returned after client 0's write. Does that mean client 0 assumes > > the file data is unchanged since its last write? > > Basically: write-locking less than the whole range doesn't prevent > concurrent writes outside that range. And the change attribute gives us > no way to identify whether concurrent writes have happened. (At least, > not without NFS4_CHANGE_TYPE_IS_VERSION_COUNTER.) > > So as far as I can tell, a client implementation has no reliable way to > revalidate its cache outside the write-locked area--instead it needs to > just throw out that part of the cache. Does my description of that race make sense? --b.