Difference between __gshared and shared.

Jonathan M Davis via Digitalmars-d digitalmars-d at puremagic.com
Wed Jul 8 05:08:35 PDT 2015


On Wednesday, 8 July 2015 at 10:49:05 UTC, tcak wrote:
> On Wednesday, 8 July 2015 at 10:10:58 UTC, Jonathan M Davis 
> wrote:
>> On Wednesday, 8 July 2015 at 09:54:01 UTC, ketmar wrote:
>>> On Wed, 08 Jul 2015 09:43:38 +0000, wobbles wrote:
>>>
>>>> Ok, so we should prioritise using 'shared' over __gshared as 
>>>> much as possible. Good to know!
>>>
>>> only `shared` is PITA...
>>
>> The primary advantage of shared is that it allows most 
>> everything to be thread-local.
>>
>> Though arguably, shared _should_ be a bit of a pain, since its 
>> usage should normally be very restricted. But we do need to 
>> revisit shared and figure out what we want/need to do with it. 
>> Synchronized classes as described in TDPL were never even 
>> implemented (though I contest that they really make shared 
>> usable in any kind of sane way; I really don't see how you can 
>> do anything other than really basic stuff with shared without 
>> requiring that the programmer deal with the locks and casting 
>> properly on their own). So, more work needs to be done there 
>> even if it's figuring out what shared _isn't_ going to be 
>> doing.
>>
>> Really though, one of the bigger problems is dealing with 
>> allocation and deallocation of shared objects and passing 
>> objects across threads, since we keep wanting to be able to do 
>> stuff like have thread-specific allocators, but the way shared 
>> currently works doesn't actually allow for it. :|
>>
>> Regardless, while I would very much like to see shared 
>> properly ironed out, I'm _very_ grateful that thread-local is 
>> the default in D. It's just so much saner.
>>
>> - Jonathan M Davis
>
> I still couldn't have found my answer though. I have three 
> different use cases, one is missing in the language.
>
> 1. Thread-local object.
> 2. Shared, but implemented as not to be synchronised.
> 3. Shared, and implemented to be synchronised.
>
> There is no simple way to design a class, so that you can 
> implement it for points 2 and 3. The only way is to use 
> _gshared with point one to solve it.
>
> I use shared in many of my classes. Thus I experience different 
> situations.

By using __gshared, you're throwing away the compiler's help, and 
it's _much_ more likely that you're going to write code which 
causes the compiler to generate incorrect machine code, because 
it's assuming that an object is thread-local when it's not.

Generally what you have to do with shared is lock on a mutex, 
cast away shared on the object you want to operate on, do 
whatever you're going to do with it, and then release the lock 
after there are no more thread-local references to the shared 
object. And that's basically what you normally should be doing in 
C++ code except that you don't have to cast away shared, because 
C++ doesn't have it.

I know that there are a number of people who get frustrated with 
shared and using __gshared instead, but unless you fully 
understand what you're doing and how the language works, and 
you're _really_ careful, you're going to shoot yourself in the 
foot it subtle ways if you do that.

- Jonathan M Davis


More information about the Digitalmars-d mailing list