On 07/13/16 08:55, Arthur O'Dwyer wrote:
>
> As someone who wasn't involved at all in the design process for
> lock/shared_lock/lock_guard, let me add another reason NOT to add more
> lock variants than we already have: massive confusion for newbies.
>
> When I first learned about std::mutex and std::lock_guard, I thought it
> was the neatest thing ever.
> Then I learned about std::unique_lock, which was even neater — it was
> like lock_guard, but you could actually pass it around from place to
> place. Mind you, you couldn't /*copy*/ it — it was a move-only type —
> this was obviously why they called it /*unique*/_lock, just like C++11's
> other move-only type, /*unique*/_ptr.
>
> Then came shared_mutex. Which kind of makes sense as a name... kind of.
> I mean, anyone who's taken Operating Systems in university knows that
> what it really is is a reader-writer lock
> <https://en.wikipedia.org/wiki/Readers–writer_lock>, a.k.a. r
> <
https://doc.rust-lang.org/std/sync/struct.RwLock.html>w
> <
https://www.npmjs.com/package/rwlock>lo
> <
http://linux.die.net/man/3/pthread_rwlock_init>c
> <
http://www.freebsd.org/cgi/man.cgi?query=rwlock&sektion=9>k
> <
http://docs.libuv.org/en/v1.x/threading.html#read-write-locks>, but
> okay, the Committee hates acronyms or something, so yeah, it does behave
> kind of like a mutex that you can "share". And so it has a method
> lock_shared(). Makes sense if you think about it.
>
> And then... wait a minute. Was my intuition about unique_lock wrong? Did
> it actually get its name not because it's move-only, but because it
> takes an /*exclusive*/ lock on the mutex it controls?
Yes. You can also say the lock offers a unique access to the resource
protected by the mutex.
> (Seeing the
> Committee fumble the noun "rwlock" leads to the horrible thought that
> they might equally have fumbled the adjective "exclusive".) So then
> what's a /shared/_lock? ...which showed up in C++14, as a move-only
> type! This way lies madness. Best to just sweep it under the bed and try
> to forget about it.
I don't see the problem. The shared lock offers a shared access to the
resource, so the name is fitting. The lock could potentially be made
copyable but this would require unnecessary overhead because normally
you don't want to copy locks, only move.
> I welcome anything the Committee can do at this point to limit the
> confusion and preserve the general principle of "/unique_/ things are
> move-only, /shared_/ things are copyable, and things pretty much do what
> they say on the tin (except for shared_mutex which is really rwlock in
> disguise, oops)" — which means I would attempt to oppose the addition of
> any new /shared_/ stuff to the library unless it really clearly did what
> it appeared to say on the tin.
The tail doesn't wag the dog. Objects representing unique resources are
movable-only because when you allow copying there appears two objects
owning the same resource. Objects representing shared resources don't
have that restriction but they still can be movable-only for other
reasons. In either case, the types are not named unique or shared
because they are movable-only or not - copyability and movability are
the consequence and not the cause.
As for the shared_lock_guard, I do think it is needed, even if not the
variadic version. Most of the time I use lock_guard instead of
unique_lock because I don't need neither movability nor elaborate
constructors or lock methods - I just want to have a locked scope and
nothing more. The most frequent use of unique_lock for me is with a
condition variable. I barely ever use std::lock and frankly if you need
to have multiple resources locked then chances are high that you have a
design problem. I believe, with shared locks the situation will be even
more emphasized because you can't use shared locks with condition variables.