synchronized (this[.classinfo]) in druntime and phobos

Andrei Alexandrescu SeeWebsiteForEmail at erdani.org
Thu May 31 11:29:27 PDT 2012


On 5/31/12 7:01 AM, Regan Heath wrote:
> I'm
> suggesting "mutex" but kept private inside the class /that it locks/.
> Yes, it's a visibility issue, the issue is that the mutex used by
> synchronized classes/methods is too visible/accessible and this opens it
> up for deadlocks which are otherwise impossible.

You're suggesting an idiom based on an unrestricted abstraction 
("mutex") combined with a language feature ("private"). That's no 
progress because:

1. People can still misuse the unrestricted "mutex" as they have for the 
past 50 years.

2. The idiom can be done TODAY with a regular class that has a member of 
type synchronized class. Alternatively, you could use the mutex type in 
core directly.

So your suggestion actually makes the language worse and adds no power. 
Your impression being that "synchronized" is too deadlock-prone, and you 
believe the solution is taking one step BACK and eliminate it in favor 
of the "private"-based idiom in conjunction with the "mutex" type which 
is deadlock-prone PLUS prone to a variety of other issues.

>> So where's the mutex that would be used to synchronize objects that
>> are not synchronizable?
>
> In the wrapper class/struct/object which derives a synchronized
> class/struct from the original. My D foo is not strong enough to just
> come up with valid D code for the idiom on the fly, but essentially you
> wrap the original object in a new object using a template which adds the
> mutex member and the interface methods (lock, tryLock, and unlock)
> required. No, this doesn't work with "final" classes.. but it shouldn't,
> they're final after all. For them you need to add/manage the mutex
> manually - the price you pay for "final".

Is there anything here that can't be done today, and pronto?

>> There are cases in which you want to do multiple operations under a
>> single critical section, even though the API is otherwise
>> well-designed. That may be for correctness, efficiency, or both. I
>> don't see why we'd want to disallow that, it's a good idiom.
>
> Who suggested disallowing this? No-one. There are 3 main use cases I see
> for this;
>
> 1. Several disparate objects locked by a single mutex - in which case
> the correct solution is a separate mutex/monitor object.

There's also "13.14.3 Forcing Identical Mutexes" in TDPL.

> 2. A single object, locked for serveral method calls - in which case the
> method-passed-a-delegate idea (mentioned below/ described in a separate
> thread) works, unless..

Here the synchronized-based idiom works well if the cost of reacquiring 
an already-owned mutex is sufficiently low.

> 3. The calls span several scopes, in which case good-old manual
> lock/unlock is required (synchronized blocks don't help here)

Right. In these rare cases core.sync.mutex would be recommendable.

>> Looking forward for a fleshed out proposal. Make sure you motivate it
>> properly.
>
> Sorry, I have no spare time to spare. You're getting free ideas/thoughts
> from me, feel free to ignore them.

Thanks. Let me know if I understand correctly that your idea boils down 
to "I don't like synchronized, let's deprecate it and get back to 
core.sync.mutex and recommend the private thingamaroo." In that case, I 
disagree. I believe synchronized has good merits that are being ignored.

>> On first look, the inversion of control using delegates delegates has
>> similar liabilities as straight scoped locking.
>
> True, it's basically the same as a synchronized block in that respect.
> What we actually want is a way to limit the calls made by the delegate
> to methods of the object itself. If it could not call a synchronized
> method on a 2nd object, you could not possibly deadlock. Except, that is
> to say, unless you held a separate lock beforehand - but, the important
> point here is that you would have to take both locks explicitly, rather
> than by an implicit synchronized method call, making the bug far more
> obvious to code inspection.

Right. This is very D-unlike. I don't see anything in the current 
language that can limit the things a lambda/delegate can do.


Andrei



More information about the Digitalmars-d mailing list