|
Boost : |
From: Michael Glassford (glassfordm_at_[hidden])
Date: 2004-06-29 13:45:34
Peter Dimov wrote:
> Michael Glassford wrote:
>
>>Also, you could end up with some interesting situations like this:
>>
>> void f(read_write_mutex m)
>> {
>> read_write_mutex::read_lock r(m);
>> if (...)
>> {
>> read_write_mutex::write_lock w(r); //lock promotion
>> //...
>> }
>> //Point A
>> }
>>
>>The most obvious implementation of promotion would be for the write lock
>>to unlock the read lock if promotion succeeded, but leave it locked if
>>promotion failed. But in the above code, this would mean that if
>>promotion succeeds, neither lock will be locked at "Point A"; however
>>if promotion fails, r will still be read-locked at point A.
>
>
> Not necessarily, ~write_lock can (should) demote the lock back to read (or
> whatever the initial condition of r was).
True. But then, in the reverse case:
void f(read_write_mutex m)
{
read_write_mutex::write_lock w(m);
if (...)
{
read_write_mutex::read_lock r(w); //lock demotion
//...
}
//Point A
}
It may not be possible for r's destructor to re-obtain the write lock,
which means that, at point A:
1) If the write lock can be re-obtained, w is write-locked.
2) Otherwise, w is either unlocked or read-locked. The idea of a
write-lock being read-locked is pretty strange, but having it unlocked
doesn't seem a good choice, either.
I realize that a combined read-write lock has the same problem of
possibly being unable to re-obtain the write-lock, but in that case it
is at least more obvious that the lock state changed and what it changed to:
void f(read_write_mutex m)
{
read_write_mutex::read_write_lock l(m, write_locked);
if (...)
{
l.demote(); //lock demotion
//...
}
//Point A: l is read-locked
}
Or:
void f(read_write_mutex m)
{
read_write_mutex::read_write_lock l(m, write_locked);
if (...)
{
l.demote(); //lock demotion
//...
l.try_promote(); //optional
}
//Point A: l is write-locked if try_promote() succeeded,
//read-locked if it failed; never unlocked.
}
Finally, to take two more realistic use cases:
void f(read_write_mutex m)
{
read_write_mutex::write_lock w(m);
//...
read_write_mutex::read_lock r(w); //lock promotion
//...
}
And:
void f(read_write_mutex m)
{
read_write_mutex::write_lock r(m);
//...
read_write_mutex::read_lock w(r); //lock demotion
//...
}
The second lock does unnecessary work in demoting/promoting the lock for
the first lock, which then immediately unlocks it.
Don't get me wrong: I actually like the idea of separate read and write
locks, but there seem to be some tricky problems to address to make them
work with lock promotion/demotion.
Mike
Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk